Code

5d62030993deb76b3234245e94cf9a6a9c5c60ca
[inkscape.git] / src / extension / parameter.cpp
1 /** \file
2  * Parameters for extensions.
3  */
5 /*
6  * Authors:
7  *   Ted Gould <ted@gould.cx>
8  *
9  * Copyright (C) 2005 Authors
10  *
11  * Released under GNU GPL, read the file 'COPYING' for more information
12  */
14 #ifdef HAVE_CONFIG_H
15 # include "config.h"
16 #endif
19 #include <gtkmm/adjustment.h>
20 #include <gtkmm/box.h>
21 #include <gtkmm/spinbutton.h>
23 #include <glibmm/i18n.h>
25 #include "extension.h"
26 #include "prefs-utils.h"
28 #include "parameter.h"
30 /** \brief  The root directory in the preferences database for extension
31             related parameters. */
32 #define PREF_DIR "extensions"
34 namespace Inkscape {
35 namespace Extension {
37 /** \brief  A boolean parameter */
38 class ParamBool : public Parameter {
39 private:
40     /** \brief  Internal value. */
41     bool _value;
42 public:
43     ParamBool(const gchar * name, const gchar * guitext, Inkscape::Extension::Extension * ext, Inkscape::XML::Node * xml);
44     /** \brief  Returns \c _value */
45     bool get (const Inkscape::XML::Document * doc, const Inkscape::XML::Node * node) { return _value; }
46     bool set (bool in, Inkscape::XML::Document * doc, const Inkscape::XML::Node * node);
47     Gtk::Widget * get_widget(void);
48     Glib::ustring * string (void);
49 };
51 /** \brief  Use the superclass' allocator and set the \c _value */
52 ParamBool::ParamBool (const gchar * name, const gchar * guitext, Inkscape::Extension::Extension * ext, Inkscape::XML::Node * xml) :
53         Parameter(name, guitext, ext), _value(false)
54 {
55     const char * defaultval = NULL;
56     if (sp_repr_children(xml) != NULL)
57         defaultval = sp_repr_children(xml)->content();
59     if (defaultval != NULL && (!strcmp(defaultval, "TRUE") || !strcmp(defaultval, "true") || !strcmp(defaultval, "1"))) {
60         _value = true;
61     } else {
62         _value = false;
63     }
65     gchar * pref_name = this->pref_name();
66     _value = (bool)prefs_get_int_attribute(PREF_DIR, pref_name, _value);
67     g_free(pref_name);
69     return;
70 }
72 class ParamInt : public Parameter {
73 private:
74     /** \brief  Internal value. */
75     int _value;
76     int _min;
77     int _max;
78 public:
79     ParamInt (const gchar * name, const gchar * guitext, Inkscape::Extension::Extension * ext, Inkscape::XML::Node * xml);
80     /** \brief  Returns \c _value */
81     int get (const Inkscape::XML::Document * doc, const Inkscape::XML::Node * node) { return _value; }
82     int set (int in, Inkscape::XML::Document * doc, const Inkscape::XML::Node * node);
83     int max (void) { return _max; }
84     int min (void) { return _min; }
85     Gtk::Widget * get_widget(void);
86     Glib::ustring * string (void);
87 };
89 /** \brief  Use the superclass' allocator and set the \c _value */
90 ParamInt::ParamInt (const gchar * name, const gchar * guitext, Inkscape::Extension::Extension * ext, Inkscape::XML::Node * xml) :
91         Parameter(name, guitext, ext), _value(0), _min(0), _max(10)
92 {
93     const char * defaultval = NULL;
94     if (sp_repr_children(xml) != NULL)
95         defaultval = sp_repr_children(xml)->content();
96     if (defaultval != NULL) {
97         _value = atoi(defaultval);
98     }
100     const char * maxval = xml->attribute("max");
101     if (maxval != NULL)
102         _max = atoi(maxval);
104     const char * minval = xml->attribute("min");
105     if (minval != NULL)
106         _min = atoi(minval);
108     /* We're handling this by just killing both values */
109     if (_max < _min) {
110         _max = 10;
111         _min = 0;
112     }
114     gchar * pref_name = this->pref_name();
115     _value = prefs_get_int_attribute(PREF_DIR, pref_name, _value);
116     g_free(pref_name);
118     // std::cout << "New Int::  value: " << _value << "  max: " << _max << "  min: " << _min << std::endl;
120     if (_value > _max) _value = _max;
121     if (_value < _min) _value = _min;
123     return;
126 class ParamFloat : public Parameter {
127 private:
128     /** \brief  Internal value. */
129     float _value;
130     float _min;
131     float _max;
132 public:
133     ParamFloat (const gchar * name, const gchar * guitext, Inkscape::Extension::Extension * ext, Inkscape::XML::Node * xml);
134     /** \brief  Returns \c _value */
135     float get (const Inkscape::XML::Document * doc, const Inkscape::XML::Node * node) { return _value; }
136     float set (float in, Inkscape::XML::Document * doc, const Inkscape::XML::Node * node);
137     float max (void) { return _max; }
138     float min (void) { return _min; }
139     Gtk::Widget * get_widget(void);
140     Glib::ustring * string (void);
141 };
143 /** \brief  Use the superclass' allocator and set the \c _value */
144 ParamFloat::ParamFloat (const gchar * name, const gchar * guitext, Inkscape::Extension::Extension * ext, Inkscape::XML::Node * xml) :
145         Parameter(name, guitext, ext), _value(0.0), _min(0.0), _max(10.0)
147     const char * defaultval = NULL;
148     if (sp_repr_children(xml) != NULL)
149         defaultval = sp_repr_children(xml)->content();
150     if (defaultval != NULL) {
151         _value = atof(defaultval);
152     }
154     const char * maxval = xml->attribute("max");
155     if (maxval != NULL)
156         _max = atof(maxval);
158     const char * minval = xml->attribute("min");
159     if (minval != NULL)
160         _min = atof(minval);
162     /* We're handling this by just killing both values */
163     if (_max < _min) {
164         _max = 10.0;
165         _min = 0.0;
166     }
168     gchar * pref_name = this->pref_name();
169     _value = prefs_get_double_attribute(PREF_DIR, pref_name, _value);
170     g_free(pref_name);
172     // std::cout << "New Float::  value: " << _value << "  max: " << _max << "  min: " << _min << std::endl;
174     if (_value > _max) _value = _max;
175     if (_value < _min) _value = _min;
177     return;
180 class ParamString : public Parameter {
181 private:
182     /** \brief  Internal value.  This should point to a string that has
183                 been allocated in memory.  And should be free'd. */
184     gchar * _value;
185 public:
186     ParamString(const gchar * name, const gchar * guitext, Inkscape::Extension::Extension * ext, Inkscape::XML::Node * xml);
187     ~ParamString(void);
188     /** \brief  Returns \c _value, with a \i const to protect it. */
189     const gchar * get (const Inkscape::XML::Document * doc, const Inkscape::XML::Node * node) { return _value; }
190     const gchar * set (const gchar * in, Inkscape::XML::Document * doc, const Inkscape::XML::Node * node);
191     Gtk::Widget * get_widget(void);
192     Glib::ustring * string (void);
193 };
195 /**
196     \return None
197     \brief  This function creates a parameter that can be used later.  This
198             is typically done in the creation of the extension and defined
199             in the XML file describing the extension (it's private so people
200             have to use the system) :)
201     \param  in_repr  The XML describing the parameter
203     This function first grabs all of the data out of the Repr and puts
204     it into local variables.  Actually, these are just pointers, and the
205     data is not duplicated so we need to be careful with it.  If there
206     isn't a name or a type in the XML, then no parameter is created as
207     the function just returns.
209     From this point on, we're pretty committed as we've allocated an
210     object and we're starting to fill it.  The name is set first, and
211     is created with a strdup to actually allocate memory for it.  Then
212     there is a case statement (roughly because strcmp requires 'ifs')
213     based on what type of parameter this is.  Depending which type it
214     is, the value is interpreted differently, but they are relatively
215     straight forward.  In all cases the value is set to the default
216     value from the XML and the type is set to the interpreted type.
217 */
218 Parameter *
219 Parameter::make (Inkscape::XML::Node * in_repr, Inkscape::Extension::Extension * in_ext)
221     const char * name;
222     const char * type;
223     const char * guitext;
225     name = in_repr->attribute("name");
226     type = in_repr->attribute("type");
227     guitext = in_repr->attribute("gui-text");
228     if (guitext == NULL)
229         guitext = in_repr->attribute("_gui-text");
231     /* In this case we just don't have enough information */
232     if (name == NULL || type == NULL) {
233         return NULL;
234     }
236     Parameter * param = NULL;
237     if (!strcmp(type, "boolean")) {
238         param = new ParamBool(name, guitext, in_ext, in_repr);
239     } else if (!strcmp(type, "int")) {
240         param = new ParamInt(name, guitext, in_ext, in_repr);
241     } else if (!strcmp(type, "float")) {
242         param = new ParamFloat(name, guitext, in_ext, in_repr);
243     } else if (!strcmp(type, "string")) {
244         param = new ParamString(name, guitext, in_ext, in_repr);
245     }
247     /* Note: param could equal NULL */
248     return param;
251 /** \brief  A function to set the \c _value
252     \param  in   The value to set to
253     \param  doc  A document that should be used to set the value.
254     \param  node The node where the value may be placed
256     This function sets the internal value, but it also sets the value
257     in the preferences structure.  To put it in the right place, \c PREF_DIR
258     and \c pref_name() are used.
259 */
260 bool
261 ParamBool::set (bool in, Inkscape::XML::Document * doc, Inkscape::XML::Node * node)
263     _value = in;
265     gchar * prefname = this->pref_name();
266     prefs_set_int_attribute(PREF_DIR, prefname, _value == true ? 1 : 0);
267     g_free(prefname);
269     return _value;
272 /** \brief  A function to set the \c _value
273     \param  in   The value to set to
274     \param  doc  A document that should be used to set the value.
275     \param  node The node where the value may be placed
277     This function sets the internal value, but it also sets the value
278     in the preferences structure.  To put it in the right place, \c PREF_DIR
279     and \c pref_name() are used.
280 */
281 int
282 ParamInt::set (int in, Inkscape::XML::Document * doc, Inkscape::XML::Node * node)
284     _value = in;
285     if (_value > _max) _value = _max;
286     if (_value < _min) _value = _min;
288     gchar * prefname = this->pref_name();
289     prefs_set_int_attribute(PREF_DIR, prefname, _value);
290     g_free(prefname);
292     return _value;
295 /** \brief  A function to set the \c _value
296     \param  in   The value to set to
297     \param  doc  A document that should be used to set the value.
298     \param  node The node where the value may be placed
300     This function sets the internal value, but it also sets the value
301     in the preferences structure.  To put it in the right place, \c PREF_DIR
302     and \c pref_name() are used.
303 */
304 float
305 ParamFloat::set (float in, Inkscape::XML::Document * doc, Inkscape::XML::Node * node)
307     _value = in;
308     if (_value > _max) _value = _max;
309     if (_value < _min) _value = _min;
311     gchar * prefname = this->pref_name();
312     prefs_set_double_attribute(PREF_DIR, prefname, _value);
313     g_free(prefname);
315     return _value;
318 /** \brief  A function to set the \c _value
319     \param  in   The value to set to
320     \param  doc  A document that should be used to set the value.
321     \param  node The node where the value may be placed
323     This function sets the internal value, but it also sets the value
324     in the preferences structure.  To put it in the right place, \c PREF_DIR
325     and \c pref_name() are used.
327     To copy the data into _value the old memory must be free'd first.
328     It is important to note that \c g_free handles \c NULL just fine.  Then
329     the passed in value is duplicated using \c g_strdup().
330 */
331 const gchar *
332 ParamString::set (const gchar * in, Inkscape::XML::Document * doc, Inkscape::XML::Node * node)
334     if (in == NULL) return NULL; /* Can't have NULL string */
336     if (_value != NULL)
337         g_free(_value);
338     _value = g_strdup(in);
340     gchar * prefname = this->pref_name();
341     prefs_set_string_attribute(PREF_DIR, prefname, _value);
342     g_free(prefname);
344     return _value;
347 /** \brief  Wrapper to cast to the object and use it's function.  */
348 bool
349 Parameter::get_bool (const Inkscape::XML::Document * doc, const Inkscape::XML::Node * node)
351     ParamBool * boolpntr;
352     boolpntr = dynamic_cast<ParamBool *>(this);
353     if (boolpntr == NULL)
354         throw Extension::param_wrong_type();
355     return boolpntr->get(doc, node);
358 /** \brief  Wrapper to cast to the object and use it's function.  */
359 int
360 Parameter::get_int (const Inkscape::XML::Document * doc, const Inkscape::XML::Node * node)
362     ParamInt * intpntr;
363     intpntr = dynamic_cast<ParamInt *>(this);
364     if (intpntr == NULL)
365         throw Extension::param_wrong_type();
366     return intpntr->get(doc);
369 /** \brief  Wrapper to cast to the object and use it's function.  */
370 float
371 Parameter::get_float (const Inkscape::XML::Document * doc, const Inkscape::XML::Node * node)
373     ParamFloat * floatpntr;
374     floatpntr = dynamic_cast<ParamFloat *>(this);
375     if (floatpntr == NULL)
376         throw Extension::param_wrong_type();
377     return floatpntr->get(doc);
380 /** \brief  Wrapper to cast to the object and use it's function.  */
381 const gchar *
382 Parameter::get_string (const Inkscape::XML::Document * doc, const Inkscape::XML::Node * node)
384     ParamString * stringpntr;
385     stringpntr = dynamic_cast<ParamString *>(this);
386     if (stringpntr == NULL)
387         throw Extension::param_wrong_type();
388     return stringpntr->get(doc);
391 /** \brief  Wrapper to cast to the object and use it's function.  */
392 bool
393 Parameter::set_bool (bool in, Inkscape::XML::Document * doc, Inkscape::XML::Node * node)
395     ParamBool * boolpntr;
396     boolpntr = dynamic_cast<ParamBool *>(this);
397     if (boolpntr == NULL)
398         throw Extension::param_wrong_type();
399     return boolpntr->set(in, doc, node);
402 /** \brief  Wrapper to cast to the object and use it's function.  */
403 int
404 Parameter::set_int (int in, Inkscape::XML::Document * doc, Inkscape::XML::Node * node)
406     ParamInt * intpntr;
407     intpntr = dynamic_cast<ParamInt *>(this);
408     if (intpntr == NULL)
409         throw Extension::param_wrong_type();
410     return intpntr->set(in, doc, node);
413 /** \brief  Wrapper to cast to the object and use it's function.  */
414 float
415 Parameter::set_float (float in, Inkscape::XML::Document * doc, Inkscape::XML::Node * node)
417     ParamFloat * floatpntr;
418     floatpntr = dynamic_cast<ParamFloat *>(this);
419     if (floatpntr == NULL)
420         throw Extension::param_wrong_type();
421     return floatpntr->set(in, doc, node);
424 /** \brief  Wrapper to cast to the object and use it's function.  */
425 const gchar *
426 Parameter::set_string (const gchar * in, Inkscape::XML::Document * doc, Inkscape::XML::Node * node)
428     ParamString * stringpntr;
429     stringpntr = dynamic_cast<ParamString *>(this);
430     if (stringpntr == NULL)
431         throw Extension::param_wrong_type();
432     return stringpntr->set(in, doc, node);
435 /** \brief  Initialize the object, to do that, copy the data. */
436 ParamString::ParamString (const gchar * name, const gchar * guitext, Inkscape::Extension::Extension * ext, Inkscape::XML::Node * xml) :
437     Parameter(name, guitext, ext), _value(NULL)
439     const char * defaultval = NULL;
440     if (sp_repr_children(xml) != NULL)
441         defaultval = sp_repr_children(xml)->content();
443     gchar * pref_name = this->pref_name();
444     const gchar * paramval = prefs_get_string_attribute(PREF_DIR, pref_name);
445     g_free(pref_name);
447     if (paramval != NULL)
448         defaultval = paramval;
449     if (defaultval != NULL)
450         _value = g_strdup(defaultval);
452     return;
455 /** \brief  Free the allocated data. */
456 ParamString::~ParamString(void)
458     g_free(_value);
461 /** \brief  Oop, now that we need a parameter, we need it's name.  */
462 Parameter::Parameter (const gchar * name, const gchar * guitext, Inkscape::Extension::Extension * ext) :
463     extension(ext), _name(NULL), _text(NULL)
465     _name = g_strdup(name);
466     if (guitext != NULL)
467         _text = g_strdup(guitext);
468     else
469         _text = g_strdup(name);
472 /** \brief  Just free the allocated name. */
473 Parameter::~Parameter (void)
475     g_free(_name);
476     g_free(_text);
479 /** \brief  Build the name to write the parameter from the extension's
480             ID and the name of this parameter. */
481 gchar *
482 Parameter::pref_name (void)
484     return g_strdup_printf("%s.%s", extension->get_id(), _name);
487 /** \brief  Basically, if there is no widget pass a NULL. */
488 Gtk::Widget *
489 Parameter::get_widget (void)
491     return NULL;
494 /** \brief  If I'm not sure which it is, just don't return a value. */
495 Glib::ustring *
496 Parameter::string (void)
498     Glib::ustring * mystring = new Glib::ustring("");
499     return mystring;
502 /** \brief  A class to make an adjustment that uses Extension params */
503 class ParamFloatAdjustment : public Gtk::Adjustment {
504     /** The parameter to adjust */
505     ParamFloat * _pref;
506 public:
507     /** \brief  Make the adjustment using an extension and the string
508                 describing the parameter. */
509     ParamFloatAdjustment (ParamFloat * param) :
510             Gtk::Adjustment(0.0, param->min(), param->max(), 0.1), _pref(param) {
511         this->set_value(_pref->get(NULL) /* \todo fix */);
512         this->signal_value_changed().connect(sigc::mem_fun(this, &ParamFloatAdjustment::val_changed));
513         return;
514     };
516     void val_changed (void);
517 }; /* class ParamFloatAdjustment */
519 /** \brief  A function to respond to the value_changed signal from the
520             adjustment.
522     This function just grabs the value from the adjustment and writes
523     it to the parameter.  Very simple, but yet beautiful.
524 */
525 void
526 ParamFloatAdjustment::val_changed (void)
528     // std::cout << "Value Changed to: " << this->get_value() << std::endl;
529     _pref->set(this->get_value(), NULL /* \todo fix */);
530     return;
533 /** \brief  A class to make an adjustment that uses Extension params */
534 class ParamIntAdjustment : public Gtk::Adjustment {
535     /** The parameter to adjust */
536     ParamInt * _pref;
537 public:
538     /** \brief  Make the adjustment using an extension and the string
539                 describing the parameter. */
540     ParamIntAdjustment (ParamInt * param) :
541             Gtk::Adjustment(0.0, param->min(), param->max(), 1.0), _pref(param) {
542         this->set_value(_pref->get(NULL) /* \todo fix */);
543         this->signal_value_changed().connect(sigc::mem_fun(this, &ParamIntAdjustment::val_changed));
544         return;
545     };
547     void val_changed (void);
548 }; /* class ParamIntAdjustment */
550 /** \brief  A function to respond to the value_changed signal from the
551             adjustment.
553     This function just grabs the value from the adjustment and writes
554     it to the parameter.  Very simple, but yet beautiful.
555 */
556 void
557 ParamIntAdjustment::val_changed (void)
559     // std::cout << "Value Changed to: " << this->get_value() << std::endl;
560     _pref->set((int)this->get_value(), NULL /* \todo fix */);
561     return;
564 /**
565     \brief  Creates a Float Adjustment for a float parameter
567     Builds a hbox with a label and a float adjustment in it.
568 */
569 Gtk::Widget *
570 ParamFloat::get_widget (void)
572     Gtk::HBox * hbox = new Gtk::HBox();
574     Gtk::Label * label = new Gtk::Label(_(_text), Gtk::ALIGN_LEFT);
575     label->show();
576     hbox->pack_start(*label, true, true);
578     ParamFloatAdjustment * fadjust = new ParamFloatAdjustment(this);
579     Gtk::SpinButton * spin = new Gtk::SpinButton(*fadjust, 0.1, 1);
580     spin->show();
581     hbox->pack_start(*spin, false, false);
583     hbox->show();
585     return dynamic_cast<Gtk::Widget *>(hbox);
588 /**
589     \brief  Creates a Int Adjustment for a int parameter
591     Builds a hbox with a label and a int adjustment in it.
592 */
593 Gtk::Widget *
594 ParamInt::get_widget (void)
596     Gtk::HBox * hbox = new Gtk::HBox();
598     Gtk::Label * label = new Gtk::Label(_(_text), Gtk::ALIGN_LEFT);
599     label->show();
600     hbox->pack_start(*label, true, true);
602     ParamIntAdjustment * fadjust = new ParamIntAdjustment(this);
603     Gtk::SpinButton * spin = new Gtk::SpinButton(*fadjust, 1.0, 0);
604     spin->show();
605     hbox->pack_start(*spin, false, false);
607     hbox->show();
609     return dynamic_cast<Gtk::Widget *>(hbox);
612 /** \brief  A check button which is Param aware.  It works with the
613             parameter to change it's value as the check button changes
614             value. */
615 class ParamBoolCheckButton : public Gtk::CheckButton {
616 private:
617     /** \brief  Param to change */
618     ParamBool * _pref;
619 public:
620     /** \brief  Initialize the check button
621         \param  param  Which parameter to adjust on changing the check button
623         This function sets the value of the checkbox to be that of the
624         parameter, and then sets up a callback to \c on_toggle.
625     */
626     ParamBoolCheckButton (ParamBool * param) :
627             Gtk::CheckButton(), _pref(param) {
628         this->set_active(_pref->get(NULL) /**\todo fix */);
629         this->signal_toggled().connect(sigc::mem_fun(this, &ParamBoolCheckButton::on_toggle));
630         return;
631     }
632     void on_toggle (void);
633 };
635 /**
636     \brief  A function to respond to the check box changing
638     Adjusts the value of the preference to match that in the check box.
639 */
640 void
641 ParamBoolCheckButton::on_toggle (void)
643     _pref->set(this->get_active(), NULL /**\todo fix this */);
644     return;
647 /**
648     \brief  Creates a bool check button for a bool parameter
650     Builds a hbox with a label and a check button in it.
651 */
652 Gtk::Widget *
653 ParamBool::get_widget (void)
655     Gtk::HBox * hbox = new Gtk::HBox();
657     Gtk::Label * label = new Gtk::Label(_(_text), Gtk::ALIGN_LEFT);
658     label->show();
659     hbox->pack_start(*label, true, true);
661     ParamBoolCheckButton * checkbox = new ParamBoolCheckButton(this);
662     checkbox->show();
663     hbox->pack_start(*checkbox, false, false);
665     hbox->show();
667     return dynamic_cast<Gtk::Widget *>(hbox);
670 /** \brief  A special category of Gtk::Entry to handle string parameteres */
671 class ParamStringEntry : public Gtk::Entry {
672 private:
673     ParamString * _pref;
674 public:
675     /** \brief  Build a string preference for the given parameter
676         \param  pref  Where to get the string from, and where to put it
677                       when it changes.
678     */
679     ParamStringEntry (ParamString * pref) :
680         Gtk::Entry(), _pref(pref) {
681         if (_pref->get(NULL) != NULL)
682             this->set_text(Glib::ustring(_pref->get(NULL)));
683         this->signal_changed().connect(sigc::mem_fun(this, &ParamStringEntry::changed_text));
684     };
685     void changed_text (void);
686 };
688 /** \brief  Respond to the text box changing
690     This function responds to the box changing by grabbing the value
691     from the text box and putting it in the parameter.
692 */
693 void
694 ParamStringEntry::changed_text (void)
696     Glib::ustring data = this->get_text();
697     _pref->set(data.c_str(), NULL);
698     return;
701 /**
702     \brief  Creates a text box for the string parameter
704     Builds a hbox with a label and a text box in it.
705 */
706 Gtk::Widget *
707 ParamString::get_widget (void)
709     Gtk::HBox * hbox = new Gtk::HBox();
711     Gtk::Label * label = new Gtk::Label(_(_text), Gtk::ALIGN_LEFT);
712     label->show();
713     hbox->pack_start(*label, true, true);
715     ParamStringEntry * textbox = new ParamStringEntry(this);
716     textbox->show();
717     hbox->pack_start(*textbox, false, false);
719     hbox->show();
721     return dynamic_cast<Gtk::Widget *>(hbox);
724 /** \brief  Return 'true' or 'false' */
725 Glib::ustring *
726 ParamBool::string (void)
728     Glib::ustring * mystring;
730     if (_value)
731         mystring = new Glib::ustring("true");
732     else
733         mystring = new Glib::ustring("false");
735     return mystring;
738 /** \brief  Return the value as a string */
739 Glib::ustring *
740 ParamInt::string (void)
742     char startstring[32];
743     sprintf(startstring, "%d", _value);
744     Glib::ustring * mystring = new Glib::ustring(startstring);
745     return mystring;
748 /** \brief  Return the value as a string */
749 Glib::ustring *
750 ParamFloat::string (void)
752     char startstring[G_ASCII_DTOSTR_BUF_SIZE];
753     g_ascii_dtostr(startstring, G_ASCII_DTOSTR_BUF_SIZE, _value);
754     Glib::ustring * mystring = new Glib::ustring(startstring);
755     return mystring;
758 /** \brief  Return the value as a string */
759 Glib::ustring *
760 ParamString::string (void)
762     Glib::ustring * mystring = new Glib::ustring("");
763     *mystring += "\"";
764     *mystring += _value;
765     *mystring += "\"";
766     return mystring;
770 }  /* namespace Extension */
771 }  /* namespace Inkscape */
773 /*
774   Local Variables:
775   mode:c++
776   c-file-style:"stroustrup"
777   c-file-offsets:((innamespace . 0)(inline-open . 0)(case-label . +))
778   indent-tabs-mode:nil
779   fill-column:99
780   End:
781 */
782 // vim: filetype=cpp:expandtab:shiftwidth=4:tabstop=8:softtabstop=4 :