Author: Carlos Lopez <[email protected]>
Date: Mon Nov 19 19:08:48 2012 +0100
CairoColor::Blend: Add support for OVERLAY method.
Previously the non directly supported by Cairo blend methods, were performed by
converting the CairoColor to Color and performing the blending and then convert
it back to CairoColor again.
It is really time consuming and this commit offers an specific blend function
for OVERLAY method and CairoColor.
The function just does the overlay operation, but without the blend onto that
is performed by Cairo later.
The old Cairo render time for a file with 23 rectangles was 1.60 seconds and
now it is 0.24. Still away though, from the 0.08 seconds that Software needs to
render the same file.
---
synfig-core/src/synfig/cairo_operators.cpp | 42 ++++++++++++++++++++++++++-
synfig-core/src/synfig/color.cpp | 43 ++++++++++++++++++++++++++++
2 files changed, 84 insertions(+), 1 deletions(-)
diff --git a/synfig-core/src/synfig/cairo_operators.cpp
b/synfig-core/src/synfig/cairo_operators.cpp
index cb53a42..758722a 100644
--- a/synfig-core/src/synfig/cairo_operators.cpp
+++ b/synfig-core/src/synfig/cairo_operators.cpp
@@ -180,12 +180,52 @@ void cairo_paint_with_alpha_operator(cairo_t* acr, float
alpha, Color::BlendMeth
cairo_surface_destroy(source);
break;
}
+ case Color::BLEND_OVERLAY:
+ {
+ cairo_surface_t* target=cairo_get_target(cr);
+ cairo_surface_t* dest=cairo_copy_target_image(target);
+
+ cairo_save(cr);
+ cairo_reset_clip(cr);
+ cairo_set_operator(cr, CAIRO_OPERATOR_CLEAR);
+ cairo_paint(cr);
+ cairo_restore(cr);
+
+ cairo_paint(cr);
+
+ CairoSurface cresult(target);
+ CairoSurface cdest(dest);
+ assert(cdest.map_cairo_image());
+ assert(cresult.map_cairo_image());
+
+ int w=cresult.get_w();
+ int h=cresult.get_h();
+
+ for(int y=0;y<h;y++)
+ for(int x=0;x<w;x++)
+ {
+
cresult[y][x]=CairoColor::blend(cresult[y][x], cdest[y][x], alpha, method);
+ }
+ cresult.unmap_cairo_image();
+ cdest.unmap_cairo_image();
+
+ cairo_save(cr);
+ cairo_reset_clip(cr);
+ cairo_identity_matrix(cr);
+ cairo_set_operator(cr, CAIRO_OPERATOR_DEST_ATOP);
+ cairo_set_source_surface(cr, dest, 0, 0);
+ cairo_paint_with_alpha(cr, alpha);
+ cairo_restore(cr);
+
+ cairo_surface_destroy(dest);
+ break;
+
+ }
case Color::BLEND_ADD:
case Color::BLEND_SUBTRACT:
case Color::BLEND_DIVIDE:
case Color::BLEND_ALPHA_BRIGHTEN:
case Color::BLEND_ALPHA_DARKEN:
- case Color::BLEND_OVERLAY:
default:
{
cairo_surface_t* target=cairo_get_target(cr);
diff --git a/synfig-core/src/synfig/color.cpp b/synfig-core/src/synfig/color.cpp
index 27954b9..67d51ae 100644
--- a/synfig-core/src/synfig/color.cpp
+++ b/synfig-core/src/synfig/color.cpp
@@ -542,6 +542,49 @@ blendfunc_OVERLAY(C &a,C &b,float amount)
return blendfunc_ONTO(ret,b,amount);
}
+//Specialization for CairoColors
+// OVERLAY needs a further compositon with ONTO
+template <>
+static CairoColor
+blendfunc_OVERLAY<CairoColor>(CairoColor &a,CairoColor &b,float amount)
+{
+ //const float one(C::ceil);
+ if(amount<0) a=~a, amount=-amount;
+
+ int ra, ga, ba, aa, ras, gas, bas;
+ int rb, gb, bb, ab;
+ int aaab;
+
+ ra=a.get_r();
+ ras=ra*ra;
+ ga=a.get_g();
+ gas=ga*ga;
+ ba=a.get_b();
+ bas=ba*ba;
+ aa=a.get_a();
+
+ rb=b.get_r();
+ gb=b.get_g();
+ bb=b.get_b();
+ ab=b.get_a();
+
+
+ int rc, gc, bc, ac;
+
+ if(aa==0 || ab==0) return CairoColor();
+
+ aaab=aa*ab;
+
+ rc=(2*aa*rb*ra+ras*ab-2*rb*ras)/aaab;
+ gc=(2*aa*gb*ga+gas*ab-2*gb*gas)/aaab;
+ bc=(2*aa*bb*ba+bas*ab-2*bb*bas)/aaab;
+ ac=aa;
+
+ return CairoColor(rc, gc, bc, ac);
+}
+
+
+
template <class C>
static C
blendfunc_HARD_LIGHT(C &a,C &b,float amount)
------------------------------------------------------------------------------
Monitor your physical, virtual and cloud infrastructure from a single
web console. Get in-depth insight into apps, servers, databases, vmware,
SAP, cloud infrastructure, etc. Download 30-day Free Trial.
Pricing starts from $795 for 25 servers or applications!
http://p.sf.net/sfu/zoho_dev2dev_nov
_______________________________________________
Synfig-devl mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/synfig-devl