Code

1303d639305b044d0480f47a0b7c5c722e83f6cd
[inkscape.git] / src / ui / widget / filter-effect-chooser.cpp
1 /*
2  * Filter effect selection selection widget
3  *
4  * Author:
5  *   Nicholas Bishop <nicholasbishop@gmail.com>
6  *
7  * Copyright (C) 2007 Authors
8  *
9  * Released under GNU GPL, read the file 'COPYING' for more information
10  */
12 #include <glibmm/i18n.h>
14 #include "desktop.h"
15 #include "desktop-handles.h"
16 #include "document.h"
17 #include "filter-effect-chooser.h"
18 #include "inkscape.h"
19 #include "ui/dialog/dialog-manager.h"
21 namespace Inkscape {
22 namespace UI {
23 namespace Widget {
25 FilterEffectChooser::FilterEffectChooser()
26 {
27     _model = Gtk::ListStore::create(_columns);
29     g_signal_connect(G_OBJECT(INKSCAPE), "activate_desktop",
30                      G_CALLBACK(&FilterEffectChooser::on_activate_desktop), this);
33     on_activate_desktop(INKSCAPE, SP_ACTIVE_DESKTOP, this);
34 }
36 FilterEffectChooser::~FilterEffectChooser()
37 {
38    _resource_changed.disconnect();
39    _doc_replaced.disconnect();
40 }
42 void FilterEffectChooser::on_activate_desktop(Inkscape::Application*, SPDesktop* desktop, FilterEffectChooser* fec)
43 {
44     fec->update_filters();
46     fec->_doc_replaced.disconnect();
47     fec->_doc_replaced = desktop->connectDocumentReplaced(
48         sigc::mem_fun(fec, &FilterEffectChooser::on_document_replaced));
50     fec->_resource_changed.disconnect();
51     fec->_resource_changed =
52         sp_document_resources_changed_connect(sp_desktop_document(desktop), "filter",
53                                               sigc::mem_fun(fec, &FilterEffectChooser::update_filters));
54 }
56 void FilterEffectChooser::on_document_replaced(SPDesktop* desktop, SPDocument* document)
57 {
58     update_filters();
59 }
61 /* Add all filters in the document to the combobox.
62    Keeps the same selection if possible, otherwise selects the first element */
63 void FilterEffectChooser::update_filters()
64 {
65     SPDesktop* desktop = SP_ACTIVE_DESKTOP;
66     SPDocument* document = sp_desktop_document(desktop);
67     const GSList* filters = sp_document_get_resource_list(document, "filter");
69     _model->clear();
71     for(const GSList *l = filters; l; l = l->next) {
72         Gtk::TreeModel::Row row = *_model->append();
73         SPFilter* f = (SPFilter*)l->data;
74         row[_columns.filter] = f;
75         const gchar* id = SP_OBJECT_ID(f);
76         row[_columns.id] = id ? id : "";
77     }
78 }
80 SimpleFilterModifier::SimpleFilterModifier()
81     : _lb_blend(_("_Blend mode:")),
82       _lb_blur(_("B_lur:"), Gtk::ALIGN_LEFT),
83       _lb_filter(_("F_ilter:"), Gtk::ALIGN_LEFT),
84       _blend(BlendModeConverter),
85       _blur(0, 0, 100, 1, 0.01, 1),
86       _edit_filters(_("_Edit"))
87 {
88     add(_hb_blend);
89     add(_vb_blur);
90     add(_hb_filter);
91     _hb_blend.pack_start(_lb_blend, false, false);
92     _hb_blend.pack_start(_blend);
93     _vb_blur.add(_lb_blur);
94     _vb_blur.add(_blur);
95     _hb_filter.pack_start(_lb_filter, false, false);
96     _hb_filter.pack_start(_hb_filter_sub);
97     _hb_filter_sub.add(_filter);
98     _hb_filter_sub.add(_edit_filters);
100     show_all_children();
102     signal_show().connect(sigc::mem_fun(*this, &SimpleFilterModifier::blend_mode_changed));
103     _hb_blend.set_spacing(12);
104     _hb_filter.set_spacing(12);
105     _lb_blend.set_use_underline();
106     _lb_blend.set_mnemonic_widget(_blend);
107     _lb_blur.set_use_underline();
108     _lb_blur.set_mnemonic_widget(_blur.get_scale());
109     _lb_filter.set_use_underline();
110     _lb_filter.set_mnemonic_widget(_filter);
111     _blend.add_row("Filter");
112     _blend.signal_changed().connect(sigc::mem_fun(*this, &SimpleFilterModifier::blend_mode_changed));
113     _blend.signal_changed().connect(signal_blend_blur_changed());
114     _blur.signal_value_changed().connect(signal_blend_blur_changed());
115     _filter.set_model(_model);
116     _filter.pack_start(_columns.id);
117     _edit_filters.signal_clicked().connect(sigc::mem_fun(*this, &SimpleFilterModifier::show_filter_dialog));
118     _edit_filters.set_use_underline();
120     update_filters();
123 Glib::SignalProxy0<void> SimpleFilterModifier::signal_selection_changed()
125     return _filter.signal_changed();
128 SPFilter* SimpleFilterModifier::get_selected_filter()
130     Gtk::TreeModel::iterator i = _filter.get_active();
132     if(i)
133         return (*i)[_columns.filter];
135     return 0;
138 void SimpleFilterModifier::select_filter(const SPFilter* filter)
140     if(filter) {
141         for(Gtk::TreeModel::iterator i = _model->children().begin();
142             i != _model->children().end(); ++i) {
143             if((*i)[_columns.filter] == filter) {
144                 _filter.set_active(i);
145                 break;
146             }
147         }
148     }
151 sigc::signal<void>& SimpleFilterModifier::signal_blend_blur_changed()
153     return _signal_blend_blur_changed;
156 const Glib::ustring SimpleFilterModifier::get_blend_mode()
158     return _blend.get_active_row_number() == 5 ? "filter" : _blend.get_active_data()->name;
161 void SimpleFilterModifier::set_blend_mode(const int val)
163     _blend.set_active(val);
166 double SimpleFilterModifier::get_blur_value() const
168     return _blur.get_value();
171 void SimpleFilterModifier::set_blur_value(const double val)
173     _blur.set_value(val);
176 void SimpleFilterModifier::set_blur_sensitive(const bool s)
178     _blur.set_sensitive(s);
181 void SimpleFilterModifier::update_filters()
183     const SPFilter* active_filter = get_selected_filter();
185     FilterEffectChooser::update_filters();
187     if(_model->children().empty()) {
188         // Set state if no filters exist
189         Gtk::TreeModel::Row row = *_model->prepend();
190         row[_columns.filter] = 0;
191         row[_columns.id] = "None";
192         _filter.set_sensitive(false);
193         _filter.set_active(0);
194     }
195     else {
196         _filter.set_sensitive(true);
197         select_filter(active_filter);
198     }
201 void SimpleFilterModifier::show_filter_dialog()
203     SP_ACTIVE_DESKTOP->_dlg_mgr->showDialog("FilterEffectsDialog");
206 void SimpleFilterModifier::blend_mode_changed()
208     if(_blend.get_active_row_number() == 5) {
209         _vb_blur.hide();
210         _hb_filter.show();
211     }
212     else {
213         _hb_filter.hide();
214         _vb_blur.show();
215     }
218 /*** From filter-effect-enums.h ***/
219 const EnumData<NR::FilterPrimitiveType> FPData[NR::NR_FILTER_ENDPRIMITIVETYPE] = {
220     {NR::NR_FILTER_BLEND,             _("Blend"),              "svg:feBlend"},
221     {NR::NR_FILTER_COLORMATRIX,       _("Color Matrix"),       "svg:feColorMatrix"},
222     {NR::NR_FILTER_COMPONENTTRANSFER, _("Component Transfer"), "svg:feComponentTransfer"},
223     {NR::NR_FILTER_COMPOSITE,         _("Composite"),          "svg:feComposite"},
224     {NR::NR_FILTER_CONVOLVEMATRIX,    _("Convolve Matrix"),    "svg:feConvolveMatrix"},
225     {NR::NR_FILTER_DIFFUSELIGHTING,   _("Diffuse Lighting"),   "svg:feDiffuseLighting"},
226     {NR::NR_FILTER_DISPLACEMENTMAP,   _("Displacement Map"),   "svg:feDisplacementMap"},
227     {NR::NR_FILTER_FLOOD,             _("Flood"),              "svg:feFlood"},
228     {NR::NR_FILTER_GAUSSIANBLUR,      _("Gaussian Blur"),      "svg:feGaussianBlur"},
229     {NR::NR_FILTER_IMAGE,             _("Image"),              "svg:feImage"},
230     {NR::NR_FILTER_MERGE,             _("Merge"),              "svg:feMerge"},
231     {NR::NR_FILTER_MORPHOLOGY,        _("Morphology"),         "svg:feMorphology"},
232     {NR::NR_FILTER_OFFSET,            _("Offset"),             "svg:feOffset"},
233     {NR::NR_FILTER_SPECULARLIGHTING,  _("Specular Lighting"),  "svg:feSpecularLighting"},
234     {NR::NR_FILTER_TILE,              _("Tile"),               "svg:feTile"},
235     {NR::NR_FILTER_TURBULENCE,        _("Turbulence"),         "svg:feTurbulence"}
236 };
237 const Converter<NR::FilterPrimitiveType> FPConverter(FPData, NR::NR_FILTER_ENDPRIMITIVETYPE);
239 const EnumData<NR::FilterBlendMode> BlendModeData[NR::BLEND_ENDMODE] = {
240     {NR::BLEND_NORMAL, _("Normal"), "normal"},
241     {NR::BLEND_MULTIPLY, _("Multiply"), "multiply"},
242     {NR::BLEND_SCREEN, _("Screen"), "screen"},
243     {NR::BLEND_DARKEN, _("Darken"), "darken"},
244     {NR::BLEND_LIGHTEN, _("Lighten"), "lighten"}
245 };
246 const Converter<NR::FilterBlendMode> BlendModeConverter(BlendModeData, NR::BLEND_ENDMODE);
252 /*
253   Local Variables:
254   mode:c++
255   c-file-style:"stroustrup"
256   c-file-offsets:((innamespace . 0)(inline-open . 0)(case-label . +))
257   indent-tabs-mode:nil
258   fill-column:99
259   End:
260 */
261 // vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:encoding=utf-8:textwidth=99 :