/** Sets this matrix to a rotation matrix that will rotate any vector in counter-clockwise direction around the z-axis. * @param degrees The angle in degrees. * @return This matrix for the purpose of chaining operations. */ public Affine2 setToRotation (float degrees) { float cos = MathUtils.cosDeg(degrees); float sin = MathUtils.sinDeg(degrees); m00 = cos; m01 = -sin; m02 = 0; m10 = sin; m11 = cos; m12 = 0; return this; }
/** Sets this matrix to a rotation matrix that will rotate any vector in counter-clockwise direction around the z-axis. * @param degrees The angle in degrees. * @return This matrix for the purpose of chaining operations. */ public Affine2 setToRotation (float degrees) { float cos = MathUtils.cosDeg(degrees); float sin = MathUtils.sinDeg(degrees); m00 = cos; m01 = -sin; m02 = 0; m10 = sin; m11 = cos; m12 = 0; return this; }
/** Postmultiplies this matrix with a (counter-clockwise) rotation matrix. * @param degrees The angle in degrees * @return This matrix for the purpose of chaining. */ public Affine2 rotate (float degrees) { if (degrees == 0) return this; float cos = MathUtils.cosDeg(degrees); float sin = MathUtils.sinDeg(degrees); float tmp00 = m00 * cos + m01 * sin; float tmp01 = m00 * -sin + m01 * cos; float tmp10 = m10 * cos + m11 * sin; float tmp11 = m10 * -sin + m11 * cos; m00 = tmp00; m01 = tmp01; m10 = tmp10; m11 = tmp11; return this; }
/** Postmultiplies this matrix with a (counter-clockwise) rotation matrix. * @param degrees The angle in degrees * @return This matrix for the purpose of chaining. */ public Affine2 rotate (float degrees) { if (degrees == 0) return this; float cos = MathUtils.cosDeg(degrees); float sin = MathUtils.sinDeg(degrees); float tmp00 = m00 * cos + m01 * sin; float tmp01 = m00 * -sin + m01 * cos; float tmp10 = m10 * cos + m11 * sin; float tmp11 = m10 * -sin + m11 * cos; m00 = tmp00; m01 = tmp01; m10 = tmp10; m11 = tmp11; return this; }
/** Premultiplies this matrix with a (counter-clockwise) rotation matrix. * @param degrees The angle in degrees * @return This matrix for the purpose of chaining. */ public Affine2 preRotate (float degrees) { if (degrees == 0) return this; float cos = MathUtils.cosDeg(degrees); float sin = MathUtils.sinDeg(degrees); float tmp00 = cos * m00 - sin * m10; float tmp01 = cos * m01 - sin * m11; float tmp02 = cos * m02 - sin * m12; float tmp10 = sin * m00 + cos * m10; float tmp11 = sin * m01 + cos * m11; float tmp12 = sin * m02 + cos * m12; m00 = tmp00; m01 = tmp01; m02 = tmp02; m10 = tmp10; m11 = tmp11; m12 = tmp12; return this; }
/** Premultiplies this matrix with a (counter-clockwise) rotation matrix. * @param degrees The angle in degrees * @return This matrix for the purpose of chaining. */ public Affine2 preRotate (float degrees) { if (degrees == 0) return this; float cos = MathUtils.cosDeg(degrees); float sin = MathUtils.sinDeg(degrees); float tmp00 = cos * m00 - sin * m10; float tmp01 = cos * m01 - sin * m11; float tmp02 = cos * m02 - sin * m12; float tmp10 = sin * m00 + cos * m10; float tmp11 = sin * m01 + cos * m11; float tmp12 = sin * m02 + cos * m12; m00 = tmp00; m01 = tmp01; m02 = tmp02; m10 = tmp10; m11 = tmp11; m12 = tmp12; return this; }
/** Sets this matrix to a concatenation of translation, rotation and scale. It is a more efficient form for: * <code>idt().translate(x, y).rotate(degrees).scale(scaleX, scaleY)</code> * @param x The translation in x. * @param y The translation in y. * @param degrees The angle in degrees. * @param scaleX The scale in y. * @param scaleY The scale in x. * @return This matrix for the purpose of chaining operations. */ public Affine2 setToTrnRotScl (float x, float y, float degrees, float scaleX, float scaleY) { m02 = x; m12 = y; if (degrees == 0) { m00 = scaleX; m01 = 0; m10 = 0; m11 = scaleY; } else { float sin = MathUtils.sinDeg(degrees); float cos = MathUtils.cosDeg(degrees); m00 = cos * scaleX; m01 = -sin * scaleY; m10 = sin * scaleX; m11 = cos * scaleY; } return this; }
/** Sets this matrix to a concatenation of translation, rotation and scale. It is a more efficient form for: * <code>idt().translate(x, y).rotate(degrees).scale(scaleX, scaleY)</code> * @param x The translation in x. * @param y The translation in y. * @param degrees The angle in degrees. * @param scaleX The scale in y. * @param scaleY The scale in x. * @return This matrix for the purpose of chaining operations. */ public Affine2 setToTrnRotScl (float x, float y, float degrees, float scaleX, float scaleY) { m02 = x; m12 = y; if (degrees == 0) { m00 = scaleX; m01 = 0; m10 = 0; m11 = scaleY; } else { float sin = MathUtils.sinDeg(degrees); float cos = MathUtils.cosDeg(degrees); m00 = cos * scaleX; m01 = -sin * scaleY; m10 = sin * scaleX; m11 = cos * scaleY; } return this; }
public Matrix3 setToRotation (Vector3 axis, float degrees) { return setToRotation(axis, MathUtils.cosDeg(degrees), MathUtils.sinDeg(degrees)); }
public Matrix3 setToRotation (Vector3 axis, float degrees) { return setToRotation(axis, MathUtils.cosDeg(degrees), MathUtils.sinDeg(degrees)); }
public void draw (Batch batch, float x, float y, float originX, float originY, float width, float height, float scaleX, float scaleY, float rotation) { prepareVertices(batch, x, y, width, height); float worldOriginX = x + originX, worldOriginY = y + originY; int n = this.idx; float[] vertices = this.vertices; if (rotation != 0) { for (int i = 0; i < n; i += 5) { float vx = (vertices[i] - worldOriginX) * scaleX, vy = (vertices[i + 1] - worldOriginY) * scaleY; float cos = MathUtils.cosDeg(rotation), sin = MathUtils.sinDeg(rotation); vertices[i] = cos * vx - sin * vy + worldOriginX; vertices[i + 1] = sin * vx + cos * vy + worldOriginY; } } else if (scaleX != 1 || scaleY != 1) { for (int i = 0; i < n; i += 5) { vertices[i] = (vertices[i] - worldOriginX) * scaleX + worldOriginX; vertices[i + 1] = (vertices[i + 1] - worldOriginY) * scaleY + worldOriginY; } } batch.draw(texture, vertices, 0, n); }
public void draw (Batch batch, float x, float y, float originX, float originY, float width, float height, float scaleX, float scaleY, float rotation) { prepareVertices(batch, x, y, width, height); float worldOriginX = x + originX, worldOriginY = y + originY; int n = this.idx; float[] vertices = this.vertices; if (rotation != 0) { for (int i = 0; i < n; i += 5) { float vx = (vertices[i] - worldOriginX) * scaleX, vy = (vertices[i + 1] - worldOriginY) * scaleY; float cos = MathUtils.cosDeg(rotation), sin = MathUtils.sinDeg(rotation); vertices[i] = cos * vx - sin * vy + worldOriginX; vertices[i + 1] = sin * vx + cos * vy + worldOriginY; } } else if (scaleX != 1 || scaleY != 1) { for (int i = 0; i < n; i += 5) { vertices[i] = (vertices[i] - worldOriginX) * scaleX + worldOriginX; vertices[i + 1] = (vertices[i + 1] - worldOriginY) * scaleY + worldOriginY; } } batch.draw(texture, vertices, 0, n); }
/** Returns the packed vertices, colors, and texture coordinates for this sprite. */ public float[] getVertices () { if (!dirty) return vertices; dirty = false; final float originX = this.originX; final float originY = this.originY; final float scaleX = this.scaleX; final float scaleY = this.scaleY; final PolygonRegion region = this.region; final float[] vertices = this.vertices; final float[] regionVertices = region.vertices; final float worldOriginX = x + originX; final float worldOriginY = y + originY; final float sX = width / region.region.getRegionWidth(); final float sY = height / region.region.getRegionHeight(); final float cos = MathUtils.cosDeg(rotation); final float sin = MathUtils.sinDeg(rotation); float fx, fy; for (int i = 0, v = 0, n = regionVertices.length; i < n; i += 2, v += 5) { fx = (regionVertices[i] * sX - originX) * scaleX; fy = (regionVertices[i + 1] * sY - originY) * scaleY; vertices[v] = cos * fx - sin * fy + worldOriginX; vertices[v + 1] = sin * fx + cos * fy + worldOriginY; } return vertices; }
/** Returns the packed vertices, colors, and texture coordinates for this sprite. */ public float[] getVertices () { if (!dirty) return vertices; dirty = false; final float originX = this.originX; final float originY = this.originY; final float scaleX = this.scaleX; final float scaleY = this.scaleY; final PolygonRegion region = this.region; final float[] vertices = this.vertices; final float[] regionVertices = region.vertices; final float worldOriginX = x + originX; final float worldOriginY = y + originY; final float sX = width / region.region.getRegionWidth(); final float sY = height / region.region.getRegionHeight(); final float cos = MathUtils.cosDeg(rotation); final float sin = MathUtils.sinDeg(rotation); float fx, fy; for (int i = 0, v = 0, n = regionVertices.length; i < n; i += 2, v += 5) { fx = (regionVertices[i] * sX - originX) * scaleX; fy = (regionVertices[i + 1] * sY - originY) * scaleY; vertices[v] = cos * fx - sin * fy + worldOriginX; vertices[v + 1] = sin * fx + cos * fy + worldOriginY; } return vertices; }
@Override public void update () { for (int i = 0, l = ParticleChannels.LifePercentOffset, s = 0, a = 0, c = i + controller.particles.size * directionalVelocityChannel.strideSize; i < c; s += strengthChannel.strideSize, i += directionalVelocityChannel.strideSize, a += angularChannel.strideSize, l += lifeChannel.strideSize) { float lifePercent = lifeChannel.data[l], strength = strengthChannel.data[s + ParticleChannels.VelocityStrengthStartOffset] + strengthChannel.data[s + ParticleChannels.VelocityStrengthDiffOffset] * strengthValue.getScale(lifePercent), phi = angularChannel.data[a + ParticleChannels.VelocityPhiStartOffset] + angularChannel.data[a + ParticleChannels.VelocityPhiDiffOffset] * phiValue.getScale(lifePercent), theta = angularChannel.data[a + ParticleChannels.VelocityThetaStartOffset] + angularChannel.data[a + ParticleChannels.VelocityThetaDiffOffset] * thetaValue.getScale(lifePercent); float cosTheta = MathUtils.cosDeg(theta), sinTheta = MathUtils.sinDeg(theta), cosPhi = MathUtils.cosDeg(phi), sinPhi = MathUtils .sinDeg(phi); TMP_V3.set(cosTheta * sinPhi, cosPhi, sinTheta * sinPhi).nor().scl(strength); directionalVelocityChannel.data[i + ParticleChannels.XOffset] += TMP_V3.x; directionalVelocityChannel.data[i + ParticleChannels.YOffset] += TMP_V3.y; directionalVelocityChannel.data[i + ParticleChannels.ZOffset] += TMP_V3.z; } }
@Override public void update () { for (int i = 0, l = ParticleChannels.LifePercentOffset, s = 0, a = 0, c = i + controller.particles.size * directionalVelocityChannel.strideSize; i < c; s += strengthChannel.strideSize, i += directionalVelocityChannel.strideSize, a += angularChannel.strideSize, l += lifeChannel.strideSize) { float lifePercent = lifeChannel.data[l], strength = strengthChannel.data[s + ParticleChannels.VelocityStrengthStartOffset] + strengthChannel.data[s + ParticleChannels.VelocityStrengthDiffOffset] * strengthValue.getScale(lifePercent), phi = angularChannel.data[a + ParticleChannels.VelocityPhiStartOffset] + angularChannel.data[a + ParticleChannels.VelocityPhiDiffOffset] * phiValue.getScale(lifePercent), theta = angularChannel.data[a + ParticleChannels.VelocityThetaStartOffset] + angularChannel.data[a + ParticleChannels.VelocityThetaDiffOffset] * thetaValue.getScale(lifePercent); float cosTheta = MathUtils.cosDeg(theta), sinTheta = MathUtils.sinDeg(theta), cosPhi = MathUtils.cosDeg(phi), sinPhi = MathUtils .sinDeg(phi); TMP_V3.set(cosTheta * sinPhi, cosPhi, sinTheta * sinPhi).nor().scl(strength); directionalVelocityChannel.data[i + ParticleChannels.XOffset] += TMP_V3.x; directionalVelocityChannel.data[i + ParticleChannels.YOffset] += TMP_V3.y; directionalVelocityChannel.data[i + ParticleChannels.ZOffset] += TMP_V3.z; } }
@Override public void update () { for (int i = 0, l = ParticleChannels.LifePercentOffset, s = 0, a = 0, positionOffset = 0, c = i + controller.particles.size * directionalVelocityChannel.strideSize; i < c; s += strengthChannel.strideSize, i += directionalVelocityChannel.strideSize, a += angularChannel.strideSize, l += lifeChannel.strideSize, positionOffset += positionChannel.strideSize) { float lifePercent = lifeChannel.data[l], strength = strengthChannel.data[s + ParticleChannels.VelocityStrengthStartOffset] + strengthChannel.data[s + ParticleChannels.VelocityStrengthDiffOffset] * strengthValue.getScale(lifePercent), phi = angularChannel.data[a + ParticleChannels.VelocityPhiStartOffset] + angularChannel.data[a + ParticleChannels.VelocityPhiDiffOffset] * phiValue.getScale(lifePercent), theta = angularChannel.data[a + ParticleChannels.VelocityThetaStartOffset] + angularChannel.data[a + ParticleChannels.VelocityThetaDiffOffset] * thetaValue.getScale(lifePercent); float cosTheta = MathUtils.cosDeg(theta), sinTheta = MathUtils.sinDeg(theta), cosPhi = MathUtils.cosDeg(phi), sinPhi = MathUtils .sinDeg(phi); TMP_V3 .set(cosTheta * sinPhi, cosPhi, sinTheta * sinPhi) .crs(positionChannel.data[positionOffset + ParticleChannels.XOffset], positionChannel.data[positionOffset + ParticleChannels.YOffset], positionChannel.data[positionOffset + ParticleChannels.ZOffset]).nor().scl(strength); directionalVelocityChannel.data[i + ParticleChannels.XOffset] += TMP_V3.x; directionalVelocityChannel.data[i + ParticleChannels.YOffset] += TMP_V3.y; directionalVelocityChannel.data[i + ParticleChannels.ZOffset] += TMP_V3.z; } }
@Override public void update () { for (int i = 0, l = ParticleChannels.LifePercentOffset, s = 0, a = 0, positionOffset = 0, c = i + controller.particles.size * directionalVelocityChannel.strideSize; i < c; s += strengthChannel.strideSize, i += directionalVelocityChannel.strideSize, a += angularChannel.strideSize, l += lifeChannel.strideSize, positionOffset += positionChannel.strideSize) { float lifePercent = lifeChannel.data[l], strength = strengthChannel.data[s + ParticleChannels.VelocityStrengthStartOffset] + strengthChannel.data[s + ParticleChannels.VelocityStrengthDiffOffset] * strengthValue.getScale(lifePercent), phi = angularChannel.data[a + ParticleChannels.VelocityPhiStartOffset] + angularChannel.data[a + ParticleChannels.VelocityPhiDiffOffset] * phiValue.getScale(lifePercent), theta = angularChannel.data[a + ParticleChannels.VelocityThetaStartOffset] + angularChannel.data[a + ParticleChannels.VelocityThetaDiffOffset] * thetaValue.getScale(lifePercent); float cosTheta = MathUtils.cosDeg(theta), sinTheta = MathUtils.sinDeg(theta), cosPhi = MathUtils.cosDeg(phi), sinPhi = MathUtils .sinDeg(phi); TMP_V3 .set(cosTheta * sinPhi, cosPhi, sinTheta * sinPhi) .crs(positionChannel.data[positionOffset + ParticleChannels.XOffset], positionChannel.data[positionOffset + ParticleChannels.YOffset], positionChannel.data[positionOffset + ParticleChannels.ZOffset]).nor().scl(strength); directionalVelocityChannel.data[i + ParticleChannels.XOffset] += TMP_V3.x; directionalVelocityChannel.data[i + ParticleChannels.YOffset] += TMP_V3.y; directionalVelocityChannel.data[i + ParticleChannels.ZOffset] += TMP_V3.z; } }
/** translate particle given amount. Continuous collision detection achieved by using RayCast from oldPos to newPos. * * @param velocityX * @param velocityY */ @Override public void translate (float velocityX, float velocityY) { /** If velocities squares summed is shorter than Epsilon it could lead ~0 length rayCast that cause nasty c++ assertion * inside box2d. This is so short distance that moving particle has no effect so this return early. */ if ((velocityX * velocityX + velocityY * velocityY) < EPSILON) return; /** Position offset is half of sprite texture size. */ final float x = getX() + getWidth() / 2f; final float y = getY() + getHeight() / 2f; /** collision flag to false */ particleCollided = false; startPoint.set(x, y); endPoint.set(x + velocityX, y + velocityY); if (world != null) world.rayCast(rayCallBack, startPoint, endPoint); /** If ray collided boolean has set to true at rayCallBack */ if (particleCollided) { // perfect reflection angle = 2f * normalAngle - angle - 180f; angleCos = MathUtils.cosDeg(angle); angleSin = MathUtils.sinDeg(angle); velocityX *= angleCos; velocityY *= angleSin; } super.translate(velocityX, velocityY); } }
@Override public void spawnAux (Vector3 vector, float percent) { // Generate the point on the surface of the sphere float width = spawnWidth + (spawnWidthDiff * spawnWidthValue.getScale(percent)); float height = spawnHeight + (spawnHeightDiff * spawnHeightValue.getScale(percent)); float depth = spawnDepth + (spawnDepthDiff * spawnDepthValue.getScale(percent)); float radiusX, radiusZ; float hf = height / 2; float ty = MathUtils.random(height) - hf; // Where generate the point, on edges or inside ? if (edges) { radiusX = width / 2; radiusZ = depth / 2; } else { radiusX = MathUtils.random(width) / 2; radiusZ = MathUtils.random(depth) / 2; } float spawnTheta = 0; // Generate theta boolean isRadiusXZero = radiusX == 0, isRadiusZZero = radiusZ == 0; if (!isRadiusXZero && !isRadiusZZero) spawnTheta = MathUtils.random(360f); else { if (isRadiusXZero) spawnTheta = MathUtils.random(1) == 0 ? -90 : 90; else if (isRadiusZZero) spawnTheta = MathUtils.random(1) == 0 ? 0 : 180; } vector.set(radiusX * MathUtils.cosDeg(spawnTheta), ty, radiusZ * MathUtils.sinDeg(spawnTheta)); }