index 336ac357619807cd86a6fe39d13ff22a5f0dcc36..363663ac3c8c34c946916077a4f73f8bd8cfc9f2 100644 (file)
--- a/src/filter-chemistry.cpp
+++ b/src/filter-chemistry.cpp
* bulia byak
* Niko Kiirala
*
- * Copyright (C) 2006,2007 authors
+ * Copyright (C) 2006-2008 authors
*
* Released under GNU GPL, read the file 'COPYING' for more information
*/
#include "document-private.h"
#include "desktop-style.h"
-#include "sp-feblend.h"
+#include "filter-chemistry.h"
+#include "filter-enums.h"
+
+#include "filters/blend.h"
#include "sp-filter.h"
+#include "sp-filter-reference.h"
#include "sp-gaussian-blur.h"
#include "svg/css-ostringstream.h"
+#include "libnr/nr-matrix-fns.h"
#include "xml/repr.h"
SPStyle *style = SP_OBJECT_STYLE(o);
if (style
&& style->filter.set
- && style->filter.filter == filter)
+ && style->getFilter() == filter)
{
i ++;
}
}
SPFilterPrimitive *
-filter_add_primitive(SPFilter *filter, const gchar *type)
+filter_add_primitive(SPFilter *filter, const Inkscape::Filters::FilterPrimitiveType type)
{
Inkscape::XML::Document *xml_doc = sp_document_repr_doc(filter->document);
//create filter primitive node
Inkscape::XML::Node *repr;
- repr = xml_doc->createElement(type);
- repr->setAttribute("inkscape:collect", "always");
+ repr = xml_doc->createElement(FPConverter.get_key(type).c_str());
+
+ // set default values
+ switch(type) {
+ case Inkscape::Filters::NR_FILTER_BLEND:
+ repr->setAttribute("blend", "normal");
+ break;
+ case Inkscape::Filters::NR_FILTER_COLORMATRIX:
+ break;
+ case Inkscape::Filters::NR_FILTER_COMPONENTTRANSFER:
+ break;
+ case Inkscape::Filters::NR_FILTER_COMPOSITE:
+ break;
+ case Inkscape::Filters::NR_FILTER_CONVOLVEMATRIX:
+ repr->setAttribute("order", "3 3");
+ repr->setAttribute("kernelMatrix", "0 0 0 0 0 0 0 0 0");
+ break;
+ case Inkscape::Filters::NR_FILTER_DIFFUSELIGHTING:
+ break;
+ case Inkscape::Filters::NR_FILTER_DISPLACEMENTMAP:
+ break;
+ case Inkscape::Filters::NR_FILTER_FLOOD:
+ break;
+ case Inkscape::Filters::NR_FILTER_GAUSSIANBLUR:
+ repr->setAttribute("stdDeviation", "1");
+ break;
+ case Inkscape::Filters::NR_FILTER_IMAGE:
+ break;
+ case Inkscape::Filters::NR_FILTER_MERGE:
+ break;
+ case Inkscape::Filters::NR_FILTER_MORPHOLOGY:
+ break;
+ case Inkscape::Filters::NR_FILTER_OFFSET:
+ repr->setAttribute("dx", "0");
+ repr->setAttribute("dy", "0");
+ break;
+ case Inkscape::Filters::NR_FILTER_SPECULARLIGHTING:
+ break;
+ case Inkscape::Filters::NR_FILTER_TILE:
+ break;
+ case Inkscape::Filters::NR_FILTER_TURBULENCE:
+ break;
+ default:
+ break;
+ }
//set primitive as child of filter node
filter->repr->appendChild(repr);
@@ -211,21 +259,6 @@ new_filter_blend_gaussian_blur (SPDocument *document, const char *blendmode, gdo
// get corresponding object
SPFilter *f = SP_FILTER( document->getObjectByRepr(repr) );
- // Blend primitive
- if(strcmp(blendmode, "normal")) {
- Inkscape::XML::Node *b_repr;
- b_repr = xml_doc->createElement("svg:feBlend");
- b_repr->setAttribute("inkscape::collect", "always");
- b_repr->setAttribute("mode", blendmode);
-
- // set feBlend as child of filter node
- repr->appendChild(b_repr);
- Inkscape::GC::release(b_repr);
-
- SPFeBlend *b = SP_FEBLEND(document->getObjectByRepr(b_repr));
- g_assert(b != NULL);
- g_assert(SP_IS_FEBLEND(b));
- }
// Gaussian blur primitive
if(radius != 0) {
set_filter_area(repr, radius, expansion, expansionX, expansionY, width, height);
@@ -250,6 +283,28 @@ new_filter_blend_gaussian_blur (SPDocument *document, const char *blendmode, gdo
g_assert(b != NULL);
g_assert(SP_IS_GAUSSIANBLUR(b));
}
+ // Blend primitive
+ if(strcmp(blendmode, "normal")) {
+ Inkscape::XML::Node *b_repr;
+ b_repr = xml_doc->createElement("svg:feBlend");
+ b_repr->setAttribute("inkscape:collect", "always");
+ b_repr->setAttribute("mode", blendmode);
+ b_repr->setAttribute("in2", "BackgroundImage");
+
+ // set feBlend as child of filter node
+ repr->appendChild(b_repr);
+ Inkscape::GC::release(b_repr);
+
+ // Enable background image buffer for document
+ Inkscape::XML::Node *root = b_repr->root();
+ if (!root->attribute("enable-background")) {
+ root->setAttribute("enable-background", "new");
+ }
+
+ SPFeBlend *b = SP_FEBLEND(document->getObjectByRepr(b_repr));
+ g_assert(b != NULL);
+ g_assert(SP_IS_FEBLEND(b));
+ }
g_assert(f != NULL);
g_assert(SP_IS_FILTER(f));
@@ -264,20 +319,20 @@ new_filter_blend_gaussian_blur (SPDocument *document, const char *blendmode, gdo
SPFilter *
new_filter_simple_from_item (SPDocument *document, SPItem *item, const char *mode, gdouble radius)
{
- NR::Maybe<NR::Rect> const r = sp_item_bbox_desktop(item);
+ Geom::OptRect const r = sp_item_bbox_desktop(item, SPItem::GEOMETRIC_BBOX);
double width;
double height;
if (r) {
- width = r->extent(NR::X);
- height= r->extent(NR::Y);
+ width = r->dimensions()[Geom::X];
+ height= r->dimensions()[Geom::Y];
} else {
width = height = 0;
}
- NR::Matrix i2d = sp_item_i2d_affine (item);
+ Geom::Matrix i2d (sp_item_i2d_affine (item) );
- return (new_filter_blend_gaussian_blur (document, mode, radius, i2d.expansion(), i2d.expansionX(), i2d.expansionY(), width, height));
+ return (new_filter_blend_gaussian_blur (document, mode, radius, i2d.descrim(), i2d.expansionX(), i2d.expansionY(), width, height));
}
/**
gdouble radius)
{
if (!item->style || !item->style->filter.set) {
- //return new_filter_gaussian_blur_from_item(document, item, radius);
+ return new_filter_simple_from_item(document, item, "normal", radius);
}
- SPFilter *filter = SP_FILTER(item->style->filter.filter);
+ SPFilter *filter = SP_FILTER(item->style->getFilter());
Inkscape::XML::Document *xml_doc = sp_document_repr_doc(document);
// If there are more users for this filter, duplicate it
if (SP_OBJECT_HREFCOUNT(filter) > count_filter_hrefs(item, filter)) {
Inkscape::XML::Node *repr;
- repr = SP_OBJECT_REPR(item->style->filter.filter)->duplicate(xml_doc);
+ repr = SP_OBJECT_REPR(item->style->getFilter())->duplicate(xml_doc);
SPDefs *defs = (SPDefs *) SP_DOCUMENT_DEFS(document);
SP_OBJECT_REPR(defs)->appendChild(repr);
}
// Determine the required standard deviation value
- NR::Matrix i2d = sp_item_i2d_affine (item);
- double expansion = i2d.expansion();
+ Geom::Matrix i2d (sp_item_i2d_affine (item));
+ double expansion = i2d.descrim();
double stdDeviation = radius;
if (expansion != 0)
stdDeviation /= expansion;
// Get the object size
- NR::Maybe<NR::Rect> const r = sp_item_bbox_desktop(item);
+ Geom::OptRect const r = sp_item_bbox_desktop(item, SPItem::GEOMETRIC_BBOX);
double width;
double height;
if (r) {
- width = r->extent(NR::X);
- height= r->extent(NR::Y);
+ width = r->dimensions()[Geom::X];
+ height= r->dimensions()[Geom::Y];
} else {
width = height = 0;
}
// Set the filter effects area
- Inkscape::XML::Node *repr = SP_OBJECT_REPR(item->style->filter.filter);
+ Inkscape::XML::Node *repr = SP_OBJECT_REPR(item->style->getFilter());
set_filter_area(repr, radius, expansion, i2d.expansionX(),
i2d.expansionY(), width, height);
* be handled gracefully */
void remove_filter_gaussian_blur (SPObject *item)
{
- if (item->style && item->style->filter.set && item->style->filter.filter) {
+ if (item->style && item->style->filter.set && item->style->getFilter()) {
// Search for the first blur primitive and remove it. (if found)
- Inkscape::XML::Node *repr = SP_OBJECT_REPR(item->style->filter.filter);
+ Inkscape::XML::Node *repr = SP_OBJECT_REPR(item->style->getFilter());
Inkscape::XML::Node *primitive = repr->firstChild();
while (primitive) {
if (strcmp("svg:feGaussianBlur", primitive->name()) == 0) {
}
}
+bool filter_is_single_gaussian_blur(SPFilter *filter)
+{
+ return (SP_OBJECT(filter)->firstChild() &&
+ SP_OBJECT(filter)->firstChild() == SP_OBJECT(filter)->lastChild() &&
+ SP_IS_GAUSSIANBLUR(SP_OBJECT(filter)->firstChild()));
+}
+
+double get_single_gaussian_blur_radius(SPFilter *filter)
+{
+ if (SP_OBJECT(filter)->firstChild() &&
+ SP_OBJECT(filter)->firstChild() == SP_OBJECT(filter)->lastChild() &&
+ SP_IS_GAUSSIANBLUR(SP_OBJECT(filter)->firstChild())) {
+
+ SPGaussianBlur *gb = SP_GAUSSIANBLUR(SP_OBJECT(filter)->firstChild());
+ double x = gb->stdDeviation.getNumber();
+ double y = gb->stdDeviation.getOptNumber();
+ if (x > 0 && y > 0) {
+ return MAX(x, y);
+ }
+ return x;
+ }
+ return 0.0;
+}
+
+
+
/*
Local Variables:
mode:c++