Skip to content

Instantly share code, notes, and snippets.

@Adenilson
Created April 9, 2014 23:49
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save Adenilson/10330991 to your computer and use it in GitHub Desktop.
Save Adenilson/10330991 to your computer and use it in GitHub Desktop.
diff --git a/Source/WebCore/platform/graphics/cpu/arm/filters/FELightingNEON.h b/Source/WebCore/platform/graphics/cpu/arm/filters/FELightingNEON.h
index 1e71401..0b75bc1 100644
--- a/Source/WebCore/platform/graphics/cpu/arm/filters/FELightingNEON.h
+++ b/Source/WebCore/platform/graphics/cpu/arm/filters/FELightingNEON.h
@@ -114,16 +114,16 @@ inline void FELighting::platformApplyNeon(LightingData& data, LightSource::Paint
floatArguments.colorBlue = m_lightingColor.blue();
floatArguments.padding4 = 0;
- if (m_lightSource->type() == LS_POINT) {
+ if (data.lightSource->type() == LS_POINT) {
neonData.flags |= FLAG_POINT_LIGHT;
- PointLightSource* pointLightSource = static_cast<PointLightSource*>(m_lightSource.get());
+ PointLightSource* pointLightSource = static_cast<PointLightSource*>(data.lightSource.get());
floatArguments.lightX = pointLightSource->position().x();
floatArguments.lightY = pointLightSource->position().y();
floatArguments.lightZ = pointLightSource->position().z();
floatArguments.padding2 = 0;
- } else if (m_lightSource->type() == LS_SPOT) {
+ } else if (data.lightSource->type() == LS_SPOT) {
neonData.flags |= FLAG_SPOT_LIGHT;
- SpotLightSource* spotLightSource = static_cast<SpotLightSource*>(m_lightSource.get());
+ SpotLightSource* spotLightSource = static_cast<SpotLightSource*>(data.lightSource.get());
floatArguments.lightX = spotLightSource->position().x();
floatArguments.lightY = spotLightSource->position().y();
floatArguments.lightZ = spotLightSource->position().z();
@@ -141,7 +141,7 @@ inline void FELighting::platformApplyNeon(LightingData& data, LightSource::Paint
if (spotLightSource->specularExponent() == 1)
neonData.flags |= FLAG_CONE_EXPONENT_IS_1;
} else {
- ASSERT(m_lightSource->type() == LS_DISTANT);
+ ASSERT(data.lightSource->type() == LS_DISTANT);
floatArguments.lightX = paintingData.lightVector.x();
floatArguments.lightY = paintingData.lightVector.y();
floatArguments.lightZ = paintingData.lightVector.z();
diff --git a/Source/WebCore/platform/graphics/filters/DistantLightSource.cpp b/Source/WebCore/platform/graphics/filters/DistantLightSource.cpp
index 164f36a..49ec8e3 100644
--- a/Source/WebCore/platform/graphics/filters/DistantLightSource.cpp
+++ b/Source/WebCore/platform/graphics/filters/DistantLightSource.cpp
@@ -37,7 +37,7 @@
namespace WebCore {
-void DistantLightSource::initPaintingData(PaintingData& paintingData)
+void DistantLightSource::initPaintingData(PaintingData& paintingData) const
{
float azimuth = deg2rad(m_azimuth);
float elevation = deg2rad(m_elevation);
@@ -47,7 +47,7 @@ void DistantLightSource::initPaintingData(PaintingData& paintingData)
paintingData.lightVectorLength = 1;
}
-void DistantLightSource::updatePaintingData(PaintingData&, int, int, float)
+void DistantLightSource::updatePaintingData(PaintingData&, int, int, float) const
{
}
diff --git a/Source/WebCore/platform/graphics/filters/DistantLightSource.h b/Source/WebCore/platform/graphics/filters/DistantLightSource.h
index bbe224b..9495769 100644
--- a/Source/WebCore/platform/graphics/filters/DistantLightSource.h
+++ b/Source/WebCore/platform/graphics/filters/DistantLightSource.h
@@ -35,14 +35,19 @@ public:
return adoptRef(new DistantLightSource(azimuth, elevation));
}
+ virtual PassRefPtr<LightSource> create(const FloatPoint3D&, const FloatSize&) const override
+ {
+ return adoptRef(new DistantLightSource(m_azimuth, m_elevation));
+ }
+
float azimuth() const { return m_azimuth; }
float elevation() const { return m_elevation; }
virtual bool setAzimuth(float) override;
virtual bool setElevation(float) override;
- virtual void initPaintingData(PaintingData&);
- virtual void updatePaintingData(PaintingData&, int x, int y, float z);
+ virtual void initPaintingData(PaintingData&) const override;
+ virtual void updatePaintingData(PaintingData&, int x, int y, float z) const override;
virtual TextStream& externalRepresentation(TextStream&) const;
diff --git a/Source/WebCore/platform/graphics/filters/FELighting.cpp b/Source/WebCore/platform/graphics/filters/FELighting.cpp
index 1a81803..68987cd 100644
--- a/Source/WebCore/platform/graphics/filters/FELighting.cpp
+++ b/Source/WebCore/platform/graphics/filters/FELighting.cpp
@@ -176,7 +176,7 @@ inline void FELighting::LightingData::bottomRight(int offset, IntPoint& normalVe
inline void FELighting::inlineSetPixel(int offset, LightingData& data, LightSource::PaintingData& paintingData,
int lightX, int lightY, float factorX, float factorY, IntPoint& normal2DVector)
{
- m_lightSource->updatePaintingData(paintingData, lightX, lightY, static_cast<float>(data.pixels->item(offset + cAlphaChannelOffset)) * data.surfaceScale);
+ data.lightSource->updatePaintingData(paintingData, lightX, lightY, static_cast<float>(data.pixels->item(offset + cAlphaChannelOffset)) * data.surfaceScale);
float lightStrength;
if (!normal2DVector.x() && !normal2DVector.y()) {
@@ -291,6 +291,20 @@ inline void FELighting::platformApply(LightingData& data, LightSource::PaintingD
#endif
}
+void FELighting::getTransform(FloatPoint3D* scale, FloatSize* offset) const
+{
+ FloatRect initialEffectRect = effectBoundaries();
+ FloatRect absoluteEffectRect = filter().mapLocalRectToAbsoluteRect(initialEffectRect);
+ FloatPoint absoluteLocation(absolutePaintRect().location());
+ FloatSize positionOffset(absoluteLocation - absoluteEffectRect.location());
+ offset->setWidth(positionOffset.width());
+ offset->setHeight(positionOffset.height());
+ scale->setX(initialEffectRect.width() > 0.0f && initialEffectRect.width() > 0.0f ? absoluteEffectRect.width() / initialEffectRect.width() : 1.0f);
+ scale->setY(initialEffectRect.height() > 0.0f && initialEffectRect.height() > 0.0f ? absoluteEffectRect.height() / initialEffectRect.height() : 1.0f);
+ // X and Y scale should be the same, but, if not, do a best effort by averaging the 2 for Z scale
+ scale->setZ(0.5f * (scale->x() + scale->y()));
+}
+
bool FELighting::drawLighting(Uint8ClampedArray* pixels, int width, int height)
{
LightSource::PaintingData paintingData;
@@ -309,8 +323,14 @@ bool FELighting::drawLighting(Uint8ClampedArray* pixels, int width, int height)
data.widthMultipliedByPixelSize = width * cPixelSize;
data.widthDecreasedByOne = width - 1;
data.heightDecreasedByOne = height - 1;
+ FloatPoint3D worldScale;
+ FloatSize originOffset;
+ getTransform(&worldScale, &originOffset);
+ RefPtr<LightSource> lightSource = m_lightSource->create(worldScale, originOffset);
+ data.lightSource = lightSource.get();
+ Color lightColor = adaptColorToOperatingColorSpace(m_lightingColor);
paintingData.colorVector = FloatPoint3D(m_lightingColor.red(), m_lightingColor.green(), m_lightingColor.blue());
- m_lightSource->initPaintingData(paintingData);
+ data.lightSource->initPaintingData(paintingData);
// Top/Left corner.
IntPoint normalVector;
diff --git a/Source/WebCore/platform/graphics/filters/FELighting.h b/Source/WebCore/platform/graphics/filters/FELighting.h
index eb79bbd..d7c2db9 100644
--- a/Source/WebCore/platform/graphics/filters/FELighting.h
+++ b/Source/WebCore/platform/graphics/filters/FELighting.h
@@ -63,6 +63,7 @@ protected:
int widthMultipliedByPixelSize;
int widthDecreasedByOne;
int heightDecreasedByOne;
+ const LightSource* lightSource;
inline void topLeft(int offset, IntPoint& normalVector);
inline void topRow(int offset, IntPoint& normalVector);
@@ -106,6 +107,7 @@ protected:
static int getPowerCoefficients(float exponent);
inline void platformApplyNeon(LightingData&, LightSource::PaintingData&);
+ void getTransform(FloatPoint3D* scale, FloatSize* offset) const;
LightingType m_lightingType;
RefPtr<LightSource> m_lightSource;
diff --git a/Source/WebCore/platform/graphics/filters/LightSource.h b/Source/WebCore/platform/graphics/filters/LightSource.h
index 7aa270e..688f50f 100644
--- a/Source/WebCore/platform/graphics/filters/LightSource.h
+++ b/Source/WebCore/platform/graphics/filters/LightSource.h
@@ -69,10 +69,11 @@ public:
LightType type() const { return m_type; }
virtual TextStream& externalRepresentation(TextStream&) const = 0;
- virtual void initPaintingData(PaintingData&) = 0;
+ virtual void initPaintingData(PaintingData&) const = 0;
+ virtual PassRefPtr<LightSource> create(const FloatPoint3D& scale, const FloatSize& offset) const = 0;
// z is a float number, since it is the alpha value scaled by a user
// specified "surfaceScale" constant, which type is <number> in the SVG standard
- virtual void updatePaintingData(PaintingData&, int x, int y, float z) = 0;
+ virtual void updatePaintingData(PaintingData&, int x, int y, float z) const = 0;
virtual bool setAzimuth(float) { return false; }
virtual bool setElevation(float) { return false; }
diff --git a/Source/WebCore/platform/graphics/filters/PointLightSource.cpp b/Source/WebCore/platform/graphics/filters/PointLightSource.cpp
index 207ed8e..2d310ae 100644
--- a/Source/WebCore/platform/graphics/filters/PointLightSource.cpp
+++ b/Source/WebCore/platform/graphics/filters/PointLightSource.cpp
@@ -37,11 +37,11 @@
namespace WebCore {
-void PointLightSource::initPaintingData(PaintingData&)
+void PointLightSource::initPaintingData(PaintingData&) const
{
}
-void PointLightSource::updatePaintingData(PaintingData& paintingData, int x, int y, float z)
+void PointLightSource::updatePaintingData(PaintingData& paintingData, int x, int y, float z) const
{
paintingData.lightVector.setX(m_position.x() - x);
paintingData.lightVector.setY(m_position.y() - y);
diff --git a/Source/WebCore/platform/graphics/filters/PointLightSource.h b/Source/WebCore/platform/graphics/filters/PointLightSource.h
index abfacc9..0b4e153 100644
--- a/Source/WebCore/platform/graphics/filters/PointLightSource.h
+++ b/Source/WebCore/platform/graphics/filters/PointLightSource.h
@@ -35,13 +35,19 @@ public:
return adoptRef(new PointLightSource(position));
}
+ virtual PassRefPtr<LightSource> create(const FloatPoint3D& scale, const FloatSize& offset) const override
+ {
+ FloatPoint3D position(m_position.x() * scale.x() - offset.width(), m_position.y() * scale.y() - offset.height(), m_position.z() * scale.z());
+ return adoptRef(new PointLightSource(position));
+ }
+
const FloatPoint3D& position() const { return m_position; }
virtual bool setX(float) override;
virtual bool setY(float) override;
virtual bool setZ(float) override;
- virtual void initPaintingData(PaintingData&);
- virtual void updatePaintingData(PaintingData&, int x, int y, float z);
+ virtual void initPaintingData(PaintingData&) const override;
+ virtual void updatePaintingData(PaintingData&, int x, int y, float z) const override;
virtual TextStream& externalRepresentation(TextStream&) const;
diff --git a/Source/WebCore/platform/graphics/filters/SpotLightSource.cpp b/Source/WebCore/platform/graphics/filters/SpotLightSource.cpp
index 648fcae..d1e8894 100644
--- a/Source/WebCore/platform/graphics/filters/SpotLightSource.cpp
+++ b/Source/WebCore/platform/graphics/filters/SpotLightSource.cpp
@@ -42,7 +42,7 @@ namespace WebCore {
// according to the SVG 1.1 SE light regression tests
static const float antiAliasTreshold = 0.016f;
-void SpotLightSource::initPaintingData(PaintingData& paintingData)
+void SpotLightSource::initPaintingData(PaintingData& paintingData) const
{
paintingData.privateColorVector = paintingData.colorVector;
paintingData.directionVector.setX(m_direction.x() - m_position.x());
@@ -72,7 +72,7 @@ void SpotLightSource::initPaintingData(PaintingData& paintingData)
paintingData.specularExponent = 2;
}
-void SpotLightSource::updatePaintingData(PaintingData& paintingData, int x, int y, float z)
+void SpotLightSource::updatePaintingData(PaintingData& paintingData, int x, int y, float z) const
{
paintingData.lightVector.setX(m_position.x() - x);
paintingData.lightVector.setY(m_position.y() - y);
diff --git a/Source/WebCore/platform/graphics/filters/SpotLightSource.h b/Source/WebCore/platform/graphics/filters/SpotLightSource.h
index ec9c5ca..409483b 100644
--- a/Source/WebCore/platform/graphics/filters/SpotLightSource.h
+++ b/Source/WebCore/platform/graphics/filters/SpotLightSource.h
@@ -36,6 +36,13 @@ public:
return adoptRef(new SpotLightSource(position, direction, specularExponent, limitingConeAngle));
}
+ virtual PassRefPtr<LightSource> create(const FloatPoint3D& scale, const FloatSize& offset) const override
+ {
+ FloatPoint3D position(m_position.x() * scale.x() - offset.width(), m_position.y() * scale.y() - offset.height(), m_position.z() * scale.z());
+ FloatPoint3D direction(m_direction.x() * scale.x() - offset.width(), m_direction.y() * scale.y() - offset.height(), m_direction.z() * scale.z());
+ return adoptRef(new SpotLightSource(position, direction, m_specularExponent, m_limitingConeAngle));
+ }
+
const FloatPoint3D& position() const { return m_position; }
const FloatPoint3D& direction() const { return m_direction; }
float specularExponent() const { return m_specularExponent; }
@@ -51,8 +58,8 @@ public:
virtual bool setSpecularExponent(float) override;
virtual bool setLimitingConeAngle(float) override;
- virtual void initPaintingData(PaintingData&);
- virtual void updatePaintingData(PaintingData&, int x, int y, float z);
+ virtual void initPaintingData(PaintingData&) const override;
+ virtual void updatePaintingData(PaintingData&, int x, int y, float z) const override;
virtual TextStream& externalRepresentation(TextStream&) const;
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment