]> git.tokkee.org Git - inkscape.git/commitdiff

Code

Created NR::FilterSlot to handle pixblocks in rendering filters
authorkiirala <kiirala@users.sourceforge.net>
Tue, 4 Jul 2006 14:05:32 +0000 (14:05 +0000)
committerkiirala <kiirala@users.sourceforge.net>
Tue, 4 Jul 2006 14:05:32 +0000 (14:05 +0000)
doc/nr-filter-interface.txt
src/display/Makefile_insert
src/display/nr-filter-gaussian.cpp
src/display/nr-filter-gaussian.h
src/display/nr-filter-primitive.cpp
src/display/nr-filter-primitive.h
src/display/nr-filter-slot.cpp [new file with mode: 0644]
src/display/nr-filter-slot.h [new file with mode: 0644]
src/display/nr-filter-types.h
src/display/nr-filter.cpp

index d5eb84a529c4b34758bfac170ac62b01a927cfb2..6065333fea98129d36689246b9526c21404e7267 100644 (file)
@@ -84,7 +84,7 @@ Constant name                 Corresponding SVG input name
 NR_FILTER_SOURCEGRAPHIC                SourceGraphic
 NR_FILTER_SOURCEALPHA          SourceAlpha
 NR_FILTER_BACKGROUNDIMAGE      BackgroundImage
-NR_FILTER_BACKGROUNDAPLHA      BackgroundAlpha
+NR_FILTER_BACKGROUNDALPHA      BackgroundAlpha
 NR_FILTER_FILLPAINT            FillPaint
 NR_FILTER_SOURCEPAINT          SourcePaint
 (defined in display/nr-filter-types.h)
index 5aec6894f2d28611854769056ce7002e3c744672..f19ced22018e3f68b31ad39ee21cf042c75a9df3 100644 (file)
@@ -66,7 +66,10 @@ display_libspdisplay_a_SOURCES = \
        display/nr-filter-primitive.cpp \
        display/nr-filter-primitive.h   \
        display/nr-filter-gaussian.cpp  \
-       display/nr-filter-gaussian.h
+       display/nr-filter-gaussian.h    \
+       display/nr-filter-slot.cpp      \
+       display/nr-filter-slot.h        \
+       display/nr-filter-types.h
 
 display_bezier_utils_test_SOURCES = display/bezier-utils-test.cpp
 display_bezier_utils_test_LDADD = libnr/libnr.a -lglib-2.0
index d8cb84a02d904351c6ce39d0b5f7a3fa00ade49d..ee1fd7d99997bf58202c8bbc5993e5ff6e112c93 100644 (file)
@@ -18,6 +18,7 @@ using std::isnormal;
 
 #include "display/nr-filter-primitive.h"
 #include "display/nr-filter-gaussian.h"
+#include "display/nr-filter-types.h"
 #include "libnr/nr-pixblock.h"
 #include "libnr/nr-matrix.h"
 #include "prefs-utils.h"
@@ -136,10 +137,10 @@ inline void _check_index(NRPixBlock const * const pb, int const location, int co
     }
 }
 
-int FilterGaussian::render(NRPixBlock **pb, Matrix const &trans)
+int FilterGaussian::render(FilterSlot &slot, Matrix const &trans)
 {
     /* in holds the input pixblock */
-    NRPixBlock *in = pb[0];
+    NRPixBlock *in = slot.get(_input);
 
     /* If to either direction, the standard deviation is zero, a transparent
      * black image should be returned */
@@ -148,7 +149,7 @@ int FilterGaussian::render(NRPixBlock **pb, Matrix const &trans)
         nr_pixblock_setup_fast(out, in->mode, in->area.x0, in->area.y0,
                                in->area.x1, in->area.y1, true);
         out->empty = false;
-        pb[1] = out;
+        slot.set(_output, out);
         return 0;
     }
 
@@ -397,7 +398,7 @@ int FilterGaussian::render(NRPixBlock **pb, Matrix const &trans)
     delete bufy;
 
     out->empty = FALSE;
-    pb[1] = out;
+    slot.set(_output, out);
 
     return 0;
 }
index c3bf398c99f4bbf376d2dc013bf3e9ace59f73d1..07ee2392ba591dd77436f139e9d6d9e283b860e3 100644 (file)
@@ -13,6 +13,7 @@
  */
 
 #include "display/nr-filter-primitive.h"
+#include "display/nr-filter-slot.h"
 #include "libnr/nr-pixblock.h"
 #include "libnr/nr-matrix.h"
 
@@ -24,7 +25,7 @@ public:
     static FilterPrimitive *create();
     virtual ~FilterGaussian();
 
-    virtual int render(NRPixBlock **pb, Matrix const &trans);
+    virtual int render(FilterSlot &slot, Matrix const &trans);
     virtual int get_enlarge(Matrix const &m);
 
     /**
index e69a499d46beea4c15d7d872015a512ceff249f1..f45f909f62c148d95f62530b03332ddcd9620596 100644 (file)
@@ -34,13 +34,13 @@ FilterPrimitive::~FilterPrimitive()
     // Nothing to do here
 }
 
-int FilterPrimitive::render(NRPixBlock **pb, NRMatrix const *trans) {
+int FilterPrimitive::render(FilterSlot &slot, NRMatrix const *trans) {
     if(trans) {
-        return this->render(pb, *trans);
+        return this->render(slot, *trans);
     } else {
         Matrix tmp;
         tmp.set_identity();
-        return this->render(pb, tmp);
+        return this->render(slot, tmp);
     }
 }
 
index 64625f4c22e3d153b9c5de2028a92d0bdfbda509..7c8018fe2a40762747fe8219bbcb5078ae0897dc 100644 (file)
@@ -12,6 +12,7 @@
  * Released under GNU GPL, read the file 'COPYING' for more information
  */
 
+#include "display/nr-filter-slot.h"
 #include "libnr/nr-pixblock.h"
 #include "libnr/nr-matrix.h"
 #include "svg/svg-length.h"
@@ -23,8 +24,8 @@ public:
     FilterPrimitive();
     virtual ~FilterPrimitive();
 
-    int render(NRPixBlock **pb, NRMatrix const *trans);
-    virtual int render(NRPixBlock **pb, Matrix const &trans) = 0;
+    int render(FilterSlot &slot, NRMatrix const *trans);
+    virtual int render(FilterSlot &slot, Matrix const &trans) = 0;
     virtual int get_enlarge(Matrix const &m);
 
     /**
diff --git a/src/display/nr-filter-slot.cpp b/src/display/nr-filter-slot.cpp
new file mode 100644 (file)
index 0000000..6072e79
--- /dev/null
@@ -0,0 +1,160 @@
+#define __NR_FILTER_SLOT_CPP__
+
+/*
+ * A container class for filter slots. Allows for simple getting and
+ * setting images in filter slots without having to bother with
+ * table indexes and such.
+ *
+ * Author:
+ *   Niko Kiirala <niko@kiirala.com>
+ *
+ * Copyright (C) 2006 Niko Kiirala
+ *
+ * Released under GNU GPL, read the file 'COPYING' for more information
+ */
+
+#include <assert.h>
+#include "libnr/nr-pixblock.h"
+#include "display/nr-filter-types.h"
+#include "display/nr-filter-slot.h"
+
+namespace NR {
+
+FilterSlot::FilterSlot()
+{
+    _slot_count = 2;
+    _slot = new NRPixBlock*[_slot_count];
+    _slot_number = new int[_slot_count];
+
+    for (int i = 0 ; i < _slot_count ; i++) {
+        _slot[i] = NULL;
+        _slot_number[i] = NR_FILTER_SLOT_NOT_SET;
+    }
+
+    _last_out = -1;
+}
+
+FilterSlot::FilterSlot(int slots)
+{
+    _slot_count = slots;
+    _slot = new NRPixBlock*[_slot_count];
+    _slot_number = new int[_slot_count];
+
+    for (int i = 0 ; i < _slot_count ; i++) {
+        _slot[i] = NULL;
+        _slot_number[i] = NR_FILTER_SLOT_NOT_SET;
+    }
+
+    _last_out = -1;
+}
+
+FilterSlot::~FilterSlot()
+{
+    for (int i = 0 ; i < _slot_count ; i++) {
+        if (_slot[i]) {
+            nr_pixblock_release(_slot[i]);
+            delete _slot[i];
+        }
+    }
+    delete[] _slot;
+    delete[] _slot_number;
+}
+
+NRPixBlock *FilterSlot::get(int slot_nr)
+{
+    int index = _get_index(slot_nr);
+    assert(index >= 0);
+    assert(slot_nr == NR_FILTER_SLOT_NOT_SET ||_slot_number[index] == slot_nr);
+    return _slot[index];
+}
+
+void FilterSlot::set(int slot_nr, NRPixBlock *pb)
+{
+    int index = _get_index(slot_nr);
+    assert(index >= 0);
+    assert(slot_nr == NR_FILTER_SLOT_NOT_SET ||_slot_number[index] == slot_nr);
+
+    if(_slot[index]) {
+        nr_pixblock_release(_slot[index]);
+        delete _slot[index];
+    }
+    _slot[index] = pb;
+    _last_out = index;
+}
+
+int FilterSlot::get_slot_count()
+{
+    int seek = _slot_count;
+    do {
+        seek--;
+    } while (_slot[seek] == NULL);
+    
+    return seek + 1;
+}
+
+int FilterSlot::_get_index(int slot_nr)
+{
+    assert(slot_nr >= 0 ||
+           slot_nr == NR_FILTER_SLOT_NOT_SET ||
+           slot_nr == NR_FILTER_SOURCEGRAPHIC ||
+           slot_nr == NR_FILTER_SOURCEALPHA ||
+           slot_nr == NR_FILTER_BACKGROUNDIMAGE ||
+           slot_nr == NR_FILTER_BACKGROUNDALPHA ||
+           slot_nr == NR_FILTER_FILLPAINT ||
+           slot_nr == NR_FILTER_SOURCEPAINT);
+
+    int index = -1;
+    if (slot_nr == NR_FILTER_SLOT_NOT_SET) {
+        return _last_out;
+    }
+    /* Search, if the slot already exists */
+    for (int i = 0 ; i < _slot_count ; i++) {
+        if (_slot_number[i] == slot_nr) {
+            index = i;
+            break;
+        }
+    }
+
+    /* If the slot doesn't already exist, create it */
+    if (index == -1) {
+        int seek = _slot_count;
+        do {
+            seek--;
+        } while (_slot[seek] == NULL);
+        /* If there is no space for more slots, create more space */
+        if (seek == _slot_count - 1) {
+            NRPixBlock **new_slot = new NRPixBlock*[_slot_count * 2];
+            int *new_number = new int[_slot_count * 2];
+            for (int i = 0 ; i < _slot_count ; i++) {
+                new_slot[i] = _slot[i];
+                new_number[i] = _slot_number[i];
+            }
+            for (int i = _slot_count ; i < _slot_count * 2 ; i++) {
+                _slot[i] = NULL;
+                _slot_number[i] = NR_FILTER_SLOT_NOT_SET;
+            }
+            delete[] _slot;
+            delete[] _slot_number;
+            _slot = new_slot;
+            _slot_number = new_number;
+            _slot_count *= 2;
+        }
+        /* Now that there is space, create the slot */
+        _slot_number[seek + 1] = slot_nr;
+        index = seek + 1;
+    }
+    return index;
+}
+
+}
+
+/*
+  Local Variables:
+  mode:c++
+  c-file-style:"stroustrup"
+  c-file-offsets:((innamespace . 0)(inline-open . 0)(case-label . +))
+  indent-tabs-mode:nil
+  fill-column:99
+  End:
+*/
+// vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:encoding=utf-8:textwidth=99 :
diff --git a/src/display/nr-filter-slot.h b/src/display/nr-filter-slot.h
new file mode 100644 (file)
index 0000000..74cf7e0
--- /dev/null
@@ -0,0 +1,54 @@
+#ifndef __NR_FILTER_SLOT_H__
+#define __NR_FILTER_SLOT_H__
+
+/*
+ * A container class for filter slots. Allows for simple getting and
+ * setting images in filter slots without having to bother with
+ * table indexes and such.
+ *
+ * Author:
+ *   Niko Kiirala <niko@kiirala.com>
+ *
+ * Copyright (C) 2006 Niko Kiirala
+ *
+ * Released under GNU GPL, read the file 'COPYING' for more information
+ */
+
+#include "libnr/nr-pixblock.h"
+
+namespace NR {
+
+class FilterSlot {
+public:
+    FilterSlot();
+    FilterSlot(int slots);
+    ~FilterSlot();
+
+    NRPixBlock *get(int slot);
+    void set(int slot, NRPixBlock *pb);
+
+    int get_slot_count();
+
+private:
+    NRPixBlock **_slot;
+    int *_slot_number;
+    int _slot_count;
+
+    int _last_out;
+
+    int _get_index(int slot);
+};
+
+}
+
+#endif // __NR_FILTER_SLOT_H__
+/*
+  Local Variables:
+  mode:c++
+  c-file-style:"stroustrup"
+  c-file-offsets:((innamespace . 0)(inline-open . 0)(case-label . +))
+  indent-tabs-mode:nil
+  fill-column:99
+  End:
+*/
+// vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:encoding=utf-8:textwidth=99 :
index a6f539d03d57b93ed63844fa45487e222c8ad5ed..3eebe37319089edb341ae0073ba959d8779f1499 100644 (file)
@@ -29,7 +29,7 @@ enum {
     NR_FILTER_SOURCEGRAPHIC = -2,
     NR_FILTER_SOURCEALPHA = -3,
     NR_FILTER_BACKGROUNDIMAGE = -4,
-    NR_FILTER_BACKGROUNDAPLHA = -5,
+    NR_FILTER_BACKGROUNDALPHA = -5,
     NR_FILTER_FILLPAINT = -6,
     NR_FILTER_SOURCEPAINT = -7
 };
index 35f348389cbf4d53f130cfa314a9afdde9ba6579..7e558dd6ce306d021d95dbd267e95eab5cc85a7d 100644 (file)
@@ -14,6 +14,8 @@
 #include "display/nr-filter.h"
 #include "display/nr-filter-primitive.h"
 #include "display/nr-filter-gaussian.h"
+#include "display/nr-filter-slot.h"
+#include "display/nr-filter-types.h"
 
 #include "display/nr-arena-item.h"
 #include "libnr/nr-pixblock.h"
@@ -47,7 +49,7 @@ Filter::Filter(int n)
 
 void Filter::_common_init() {
     _slot_count = 1;
-    _output_slot = -1;
+    _output_slot = NR_FILTER_SLOT_NOT_SET;
 
     _region_x.set(SVGLength::PERCENT, -10, 0);
     _region_y.set(SVGLength::PERCENT, -10, 0);
@@ -70,24 +72,27 @@ Filter::~Filter()
 
 int Filter::render(NRArenaItem const *item, NRPixBlock *pb)
 {
-    NRPixBlock *slot[2];
-    slot[0] = pb;
-    slot[1] = NULL;
+    FilterSlot slot(_slot_count);
+    NRPixBlock *in = new NRPixBlock;
+    nr_pixblock_setup_fast(in, pb->mode,
+                           pb->area.x0, pb->area.y0,
+                           pb->area.x1, pb->area.y1, true);
+    nr_blit_pixblock_pixblock(in, pb);
+    slot.set(NR_FILTER_SOURCEGRAPHIC, in);
+    in = NULL; // in is now handled by FilterSlot, we should not touch it
 
     _primitive[0]->render(slot, *item->ctm);
 
+    NRPixBlock *out = slot.get(_output_slot);
 
-    int size = (slot[0]->area.x1 - slot[0]->area.x0)
-        * (slot[0]->area.y1 - slot[0]->area.y0)
-        * NR_PIXBLOCK_BPP(slot[0]);
-    memset(NR_PIXBLOCK_PX(slot[0]), 0, size);
+    int size = (pb->area.x1 - pb->area.x0)
+        * (pb->area.y1 - pb->area.y0)
+        * NR_PIXBLOCK_BPP(pb);
+    memset(NR_PIXBLOCK_PX(pb), 0, size);
 
-    nr_blit_pixblock_pixblock(slot[0], slot[1]);
-
-    slot[0]->visible_area = slot[0]->area;
-
-    nr_pixblock_release(slot[1]);
+    nr_blit_pixblock_pixblock(pb, out);
 
+    _slot_count = slot.get_slot_count();
     return 0;
 }