Skip to content

Commit

Permalink
Adding shadow color interpolation fixing shadow length
Browse files Browse the repository at this point in the history
  • Loading branch information
rinold committed Feb 7, 2015
1 parent 885a3bf commit 5bc5e7a
Show file tree
Hide file tree
Showing 4 changed files with 54 additions and 28 deletions.
32 changes: 20 additions & 12 deletions src/box2dLight/DirectionalLight.java
Original file line number Diff line number Diff line change
Expand Up @@ -229,6 +229,14 @@ protected void updateDynamicShadowMeshes() {
float l = data.height /
(float) Math.tan(height * MathUtils.degRad);
float f = 1f / data.shadowsDropped;

float startColBits = rayHandler.shadowColorInterpolation ?
Color.BLACK.lerp(rayHandler.ambientLight, 1-f).toFloatBits() :
zeroColorBits;
float endColBits = rayHandler.shadowColorInterpolation ?
Color.WHITE.lerp(rayHandler.ambientLight, 1-f).toFloatBits() :
colBits;

if (type == Type.Polygon || type == Type.Chain) {
boolean isPolygon = (type == Type.Polygon);
ChainShape cShape = isPolygon ?
Expand Down Expand Up @@ -296,16 +304,16 @@ protected void updateDynamicShadowMeshes() {

for (int n : ind.toArray()) {
tmpVec.set(tmpVerts.get(n));
tmpEnd.set(tmpVec).sub(lstart).limit(l).add(tmpVec);
tmpEnd.set(tmpVec).sub(lstart).setLength(l).add(tmpVec);

segments[size++] = tmpVec.x;
segments[size++] = tmpVec.y;
segments[size++] = zeroColorBits;
segments[size++] = startColBits;
segments[size++] = f;

segments[size++] = tmpEnd.x;
segments[size++] = tmpEnd.y;
segments[size++] = colBits;
segments[size++] = endColBits;
segments[size++] = f;
}
} else if (type == Type.Circle) {
Expand All @@ -324,13 +332,13 @@ protected void updateDynamicShadowMeshes() {
tmpStart.set(center).add(tmpVec);
segments[size++] = tmpStart.x;
segments[size++] = tmpStart.y;
segments[size++] = zeroColorBits;
segments[size++] = startColBits;
segments[size++] = f;

tmpEnd.set(tmpStart).sub(lstart).limit(l).add(tmpStart);
tmpEnd.set(tmpStart).sub(lstart).setLength(l).add(tmpStart);
segments[size++] = tmpEnd.x;
segments[size++] = tmpEnd.y;
segments[size++] = colBits;
segments[size++] = endColBits;
segments[size++] = f;

tmpVec.rotateRad(angle);
Expand All @@ -343,26 +351,26 @@ protected void updateDynamicShadowMeshes() {

segments[size++] = tmpVec.x;
segments[size++] = tmpVec.y;
segments[size++] = zeroColorBits;
segments[size++] = startColBits;
segments[size++] = f;

tmpEnd.set(tmpVec).sub(lstart).limit(l).add(tmpVec);
tmpEnd.set(tmpVec).sub(lstart).setLength(l).add(tmpVec);
segments[size++] = tmpEnd.x;
segments[size++] = tmpEnd.y;
segments[size++] = colBits;
segments[size++] = endColBits;
segments[size++] = f;

shape.getVertex2(tmpVec);
tmpVec.set(body.getWorldPoint(tmpVec));
segments[size++] = tmpVec.x;
segments[size++] = tmpVec.y;
segments[size++] = zeroColorBits;
segments[size++] = startColBits;
segments[size++] = f;

tmpEnd.set(tmpVec).sub(lstart).limit(l).add(tmpVec);
tmpEnd.set(tmpVec).sub(lstart).setLength(l).add(tmpVec);
segments[size++] = tmpEnd.x;
segments[size++] = tmpEnd.y;
segments[size++] = colBits;
segments[size++] = endColBits;
segments[size++] = f;
}

Expand Down
6 changes: 3 additions & 3 deletions src/box2dLight/LightData.java
Original file line number Diff line number Diff line change
Expand Up @@ -22,16 +22,16 @@ public LightData(Object data, float h) {
public float getLimit(float distance, float lightHeight, float lightRange) {
float l = 0f;
if (lightHeight > height) {
l = lightRange * height / (lightHeight - height);
l = distance * height / (lightHeight - height);
float diff = lightRange - distance;
if (l > diff) l = diff;
} else if (lightHeight == 0f) {
l = lightRange;
} else {
l = lightRange - distance;
}
if (l < 0) l = 0f;
return l;

return l > 0 ? l : 0f;
}

public static Object getUserData(Fixture fixture) {
Expand Down
33 changes: 20 additions & 13 deletions src/box2dLight/PointLight.java
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,7 @@ void dynamicShadowRender () {

protected void updateDynamicShadowMeshes() {
int meshInd = 0;

float colBits = rayHandler.ambientLight.toFloatBits();
for (Fixture fixture : affectedFixtures) {
LightData data = (LightData)fixture.getUserData();
Expand All @@ -97,6 +98,13 @@ protected void updateDynamicShadowMeshes() {
float l = 0f;
float f = 1f / data.shadowsDropped;

float startColBits = rayHandler.shadowColorInterpolation ?
Color.BLACK.lerp(rayHandler.ambientLight, 1-f).toFloatBits() :
zeroColorBits;
float endColBits = rayHandler.shadowColorInterpolation ?
Color.WHITE.lerp(rayHandler.ambientLight, 1-f).toFloatBits() :
colBits;

Shape fixtureShape = fixture.getShape();
Type type = fixtureShape.getType();
Body body = fixture.getBody();
Expand Down Expand Up @@ -170,17 +178,16 @@ protected void updateDynamicShadowMeshes() {

float dst = tmpVec.dst(start);
l = data.getLimit(dst, height, distance);

tmpEnd.set(tmpVec).sub(start).limit(l).add(tmpVec);
tmpEnd.set(tmpVec).sub(start).setLength(l).add(tmpVec);

segments[size++] = tmpVec.x;
segments[size++] = tmpVec.y;
segments[size++] = zeroColorBits;
segments[size++] = startColBits;
segments[size++] = f;

segments[size++] = tmpEnd.x;
segments[size++] = tmpEnd.y;
segments[size++] = colBits;
segments[size++] = endColBits;
segments[size++] = f;
}
} else if (type == Type.Circle) {
Expand All @@ -199,13 +206,13 @@ protected void updateDynamicShadowMeshes() {
tmpStart.set(center).add(tmpVec);
segments[size++] = tmpStart.x;
segments[size++] = tmpStart.y;
segments[size++] = zeroColorBits;
segments[size++] = startColBits;
segments[size++] = f;

tmpEnd.set(tmpStart).sub(start).limit(l).add(tmpStart);
tmpEnd.set(tmpStart).sub(start).setLength(l).add(tmpStart);
segments[size++] = tmpEnd.x;
segments[size++] = tmpEnd.y;
segments[size++] = colBits;
segments[size++] = endColBits;
segments[size++] = f;

tmpVec.rotateRad(angle);
Expand All @@ -220,13 +227,13 @@ protected void updateDynamicShadowMeshes() {

segments[size++] = tmpVec.x;
segments[size++] = tmpVec.y;
segments[size++] = zeroColorBits;
segments[size++] = startColBits;
segments[size++] = f;

tmpEnd.set(tmpVec).sub(start).limit(l).add(tmpVec);
tmpEnd.set(tmpVec).sub(start).setLength(l).add(tmpVec);
segments[size++] = tmpEnd.x;
segments[size++] = tmpEnd.y;
segments[size++] = colBits;
segments[size++] = endColBits;
segments[size++] = f;

shape.getVertex2(tmpVec);
Expand All @@ -236,13 +243,13 @@ protected void updateDynamicShadowMeshes() {

segments[size++] = tmpVec.x;
segments[size++] = tmpVec.y;
segments[size++] = zeroColorBits;
segments[size++] = startColBits;
segments[size++] = f;

tmpEnd.set(tmpVec).sub(start).limit(l).add(tmpVec);
tmpEnd.set(tmpVec).sub(start).setLength(l).add(tmpVec);
segments[size++] = tmpEnd.x;
segments[size++] = tmpEnd.y;
segments[size++] = colBits;
segments[size++] = endColBits;
segments[size++] = f;
}

Expand Down
11 changes: 11 additions & 0 deletions src/box2dLight/RayHandler.java
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,7 @@ public class RayHandler implements Disposable {

/** Experimental mode **/
boolean pseudo3d = false;
boolean shadowColorInterpolation = false;

int blurNum = 1;

Expand Down Expand Up @@ -560,6 +561,16 @@ public void useDefaultViewport() {
public void setPseudo3dLight(boolean flag) {
pseudo3d = flag;
}

/**
* /!\ Experimental mode with dynamic shadowing in pseudo-3d world
*
* @param flag
*/
public void setPseudo3dLight(boolean flag, boolean interpolateShadows) {
pseudo3d = flag;
shadowColorInterpolation = interpolateShadows;
}

/**
* Enables/disables lightMap automatic rendering.
Expand Down

0 comments on commit 5bc5e7a

Please sign in to comment.