summaryrefslogtreecommitdiffstats
path: root/src/display
diff options
context:
space:
mode:
authorFelipe Corr??a da Silva Sanches <juca@members.fsf.org>2008-02-11 01:48:14 +0000
committerJucaBlues <JucaBlues@users.sourceforge.net>2008-02-11 01:48:14 +0000
commit38fcf14ef7489c2d8cd366cf02443891225e41af (patch)
tree5b8574a4d07aa990289d44e43cb885c92acc9f6f /src/display
parentUpdate scriptfu from siod to tinyscheme (diff)
downloadinkscape-38fcf14ef7489c2d8cd366cf02443891225e41af.tar.gz
inkscape-38fcf14ef7489c2d8cd366cf02443891225e41af.zip
Offline work done during weekend:
* handle fefuncR, fefuncG, fefuncB and fefuncA nodes * implement fecomponenttransfer renderer ** identity and gamma modes render perfectly ** linear and table modes are rendering with very slight imperfections This commit still mantains feComponentTransfer out of UI (still not implemented) (bzr r4704)
Diffstat (limited to 'src/display')
-rw-r--r--src/display/nr-filter-component-transfer.cpp113
-rw-r--r--src/display/nr-filter-component-transfer.h23
2 files changed, 84 insertions, 52 deletions
diff --git a/src/display/nr-filter-component-transfer.cpp b/src/display/nr-filter-component-transfer.cpp
index 9b2003402..1edb3ac98 100644
--- a/src/display/nr-filter-component-transfer.cpp
+++ b/src/display/nr-filter-component-transfer.cpp
@@ -11,12 +11,15 @@
#include "display/nr-filter-component-transfer.h"
#include "display/nr-filter-units.h"
+#include "display/nr-filter-utils.h"
+#include "libnr/nr-pixblock.h"
+#include "libnr/nr-blit.h"
+#include <math.h>
namespace NR {
FilterComponentTransfer::FilterComponentTransfer()
{
- g_warning("FilterComponentTransfer::render not implemented.");
}
FilterPrimitive * FilterComponentTransfer::create() {
@@ -28,25 +31,92 @@ FilterComponentTransfer::~FilterComponentTransfer()
int FilterComponentTransfer::render(FilterSlot &slot, FilterUnits const &/*units*/) {
NRPixBlock *in = slot.get(_input);
+
if (!in) {
g_warning("Missing source image for feComponentTransfer (in=%d)", _input);
return 1;
}
- NRPixBlock *out = new NRPixBlock;
+ int x0=in->area.x0;
+ int x1=in->area.x1;
+ int y0=in->area.y0;
+ int y1=in->area.y1;
- nr_pixblock_setup_fast(out, in->mode,
- in->area.x0, in->area.y0, in->area.x1, in->area.y1,
- true);
+ NRPixBlock *out = new NRPixBlock;
+ nr_pixblock_setup_fast(out, NR_PIXBLOCK_MODE_R8G8B8A8N, x0, y0, x1, y1, true);
+
+ // this primitive is defined for non-premultiplied RGBA values,
+ // thus convert them to that format before blending
+ if (in->mode != NR_PIXBLOCK_MODE_R8G8B8A8N) {
+ NRPixBlock *original_in = in;
+ in = new NRPixBlock;
+ nr_pixblock_setup_fast(in, NR_PIXBLOCK_MODE_R8G8B8A8N,
+ original_in->area.x0, original_in->area.y0,
+ original_in->area.x1, original_in->area.y1,
+ false);
+ nr_blit_pixblock_pixblock(in, original_in);
+ }
unsigned char *in_data = NR_PIXBLOCK_PX(in);
unsigned char *out_data = NR_PIXBLOCK_PX(out);
-//IMPLEMENT ME!
- g_warning("Renderer for feComponentTransfer is not implemented.");
(void)in_data;
(void)out_data;
+ int size = 4 * (y1-y0) * (x1-x0);
+ int i;
+
+ for (int color=0;color<4;color++){
+ int _vsize = tableValues[color].size();
+ std::vector<gdouble> _tableValues = tableValues[color];
+ double _intercept = intercept[color];
+ double _slope = slope[color];
+ double _amplitude = amplitude[color];
+ double _exponent = exponent[color];
+ double _offset = offset[color];
+ switch(type[color]){
+ case COMPONENTTRANSFER_TYPE_IDENTITY:
+ for(i=color;i<size;i+=4){
+ out_data[i]=in_data[i];
+ }
+ break;
+ case COMPONENTTRANSFER_TYPE_TABLE:
+ if (_vsize==0){
+ for(i=color;i<size;i+=4){
+ out_data[i]=in_data[i];
+ }
+ } else {
+ for(i=color;i<size;i+=4){
+ int k = (int)(((_vsize-1) * (double)in_data[i])/256);
+ double dx = ((_vsize-1) * (double)in_data[i])/256 - k;
+ out_data[i] = CLAMP_D_TO_U8(256 * (_tableValues[k] + dx * (_tableValues[k+1] - _tableValues[k]) ));
+ }
+ }
+ break;
+ case COMPONENTTRANSFER_TYPE_DISCRETE:
+ if (_vsize==0){
+ for(i=color;i<size;i+=4){
+ out_data[i] = in_data[i];
+ }
+ } else {
+ for(i=color;i<size;i+=4){
+ out_data[i] = CLAMP_D_TO_U8(256 * _tableValues[(int)((_vsize-1)*(double)in_data[i]/256)] );
+ }
+ }
+ break;
+ case COMPONENTTRANSFER_TYPE_LINEAR:
+ for(i=color;i<size;i+=4){
+ out_data[i] = CLAMP_D_TO_U8(256 * (_slope * (double)in_data[i]/256 + _intercept));
+ }
+ break;
+ case COMPONENTTRANSFER_TYPE_GAMMA:
+ for(i=color;i<size;i+=4){
+ out_data[i] = CLAMP_D_TO_U8(256 * (_amplitude * pow((double)in_data[i]/256, _exponent) + _offset));
+ }
+ break;
+ }
+ }
+
out->empty = FALSE;
slot.set(_output, out);
return 0;
@@ -56,35 +126,6 @@ void FilterComponentTransfer::area_enlarge(NRRectL &/*area*/, Matrix const &/*tr
{
}
-void FilterComponentTransfer::set_type(FilterComponentTransferType t){
- type = t;
-}
-
-void FilterComponentTransfer::set_slope(double s){
- slope = s;
-}
-
-void FilterComponentTransfer::set_tableValues(std::vector<double> &tv){
- tableValues = tv;
-}
-
-
-void FilterComponentTransfer::set_intercept(double i){
- intercept = i;
-}
-
-void FilterComponentTransfer::set_amplitude(double a){
- amplitude = a;
-}
-
-void FilterComponentTransfer::set_exponent(double e){
- exponent = e;
-}
-
-void FilterComponentTransfer::set_offset(double o){
- offset = o;
-}
-
} /* namespace NR */
/*
diff --git a/src/display/nr-filter-component-transfer.h b/src/display/nr-filter-component-transfer.h
index 30b793777..ae08d6f29 100644
--- a/src/display/nr-filter-component-transfer.h
+++ b/src/display/nr-filter-component-transfer.h
@@ -37,22 +37,13 @@ public:
virtual int render(FilterSlot &slot, FilterUnits const &units);
virtual void area_enlarge(NRRectL &area, Matrix const &trans);
- void set_type(FilterComponentTransferType t);
- void set_tableValues(std::vector<gdouble>& tv);
- void set_slope(double s);
- void set_intercept(double i);
- void set_amplitude(double a);
- void set_exponent(double e);
- void set_offset(double o);
-
-private:
- FilterComponentTransferType type;
- std::vector<gdouble> tableValues;
- double slope;
- double intercept;
- double amplitude;
- double exponent;
- double offset;
+ FilterComponentTransferType type[4];
+ std::vector<gdouble> tableValues[4];
+ double slope[4];
+ double intercept[4];
+ double amplitude[4];
+ double exponent[4];
+ double offset[4];
};
} /* namespace NR */