summaryrefslogtreecommitdiffstats
path: root/src/live_effects/parameter/random.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/live_effects/parameter/random.cpp')
-rw-r--r--src/live_effects/parameter/random.cpp227
1 files changed, 227 insertions, 0 deletions
diff --git a/src/live_effects/parameter/random.cpp b/src/live_effects/parameter/random.cpp
new file mode 100644
index 0000000..42f5065
--- /dev/null
+++ b/src/live_effects/parameter/random.cpp
@@ -0,0 +1,227 @@
+// SPDX-License-Identifier: GPL-2.0-or-later
+/*
+ * Copyright (C) Johan Engelen 2007 <j.b.c.engelen@utwente.nl>
+ *
+ * Released under GNU GPL v2+, read the file 'COPYING' for more information.
+ */
+
+#include "random.h"
+
+#include <glibmm/i18n.h>
+
+#include "live_effects/effect.h"
+#include "svg/stringstream.h"
+#include "svg/svg.h"
+#include "ui/icon-names.h"
+#include "ui/widget/random.h"
+#include "ui/widget/registered-widget.h"
+
+#define noLPERANDOMPARAM_DEBUG
+
+/* RNG stolen from /display/nr-filter-turbulence.cpp */
+#define RAND_m 2147483647 /* 2**31 - 1 */
+#define RAND_a 16807 /* 7**5; primitive root of m */
+#define RAND_q 127773 /* m / a */
+#define RAND_r 2836 /* m % a */
+#define BSize 0x100
+
+namespace Inkscape {
+
+namespace LivePathEffect {
+
+
+RandomParam::RandomParam( const Glib::ustring& label, const Glib::ustring& tip,
+ const Glib::ustring& key, Inkscape::UI::Widget::Registry* wr,
+ Effect* effect, gdouble default_value, long default_seed, bool randomsign)
+ : Parameter(label, tip, key, wr, effect)
+{
+ defvalue = default_value;
+ value = defvalue;
+ min = -Geom::infinity();
+ max = Geom::infinity();
+ integer = false;
+
+ defseed = default_seed;
+ startseed = defseed;
+ seed = startseed;
+ _randomsign = randomsign;
+}
+
+RandomParam::~RandomParam()
+= default;
+
+bool
+RandomParam::param_readSVGValue(const gchar * strvalue)
+{
+ double newval, newstartseed;
+ gchar** stringarray = g_strsplit (strvalue, ";", 2);
+ unsigned int success = sp_svg_number_read_d(stringarray[0], &newval);
+ if (success == 1) {
+ success += sp_svg_number_read_d(stringarray[1], &newstartseed);
+ if (success == 2) {
+ param_set_value(newval, static_cast<long>(newstartseed));
+ } else {
+ param_set_value(newval, defseed);
+ }
+ g_strfreev(stringarray);
+ return true;
+ }
+ g_strfreev(stringarray);
+ return false;
+}
+
+Glib::ustring
+RandomParam::param_getSVGValue() const
+{
+ Inkscape::SVGOStringStream os;
+ os << value << ';' << startseed;
+ return os.str();
+}
+
+Glib::ustring
+RandomParam::param_getDefaultSVGValue() const
+{
+ Inkscape::SVGOStringStream os;
+ os << defvalue << ';' << defseed;
+ return os.str();
+}
+
+void
+RandomParam::param_set_default()
+{
+ param_set_value(defvalue, defseed);
+}
+
+void
+RandomParam::param_update_default(gdouble default_value){
+ defvalue = default_value;
+}
+
+void
+RandomParam::param_update_default(const gchar * default_value){
+ double newval;
+ unsigned int success = sp_svg_number_read_d(default_value, &newval);
+ if (success == 1) {
+ param_update_default(newval);
+ }
+}
+
+void
+RandomParam::param_set_value(gdouble val, long newseed)
+{
+ value = val;
+ if (integer)
+ value = round(value);
+ if (value > max)
+ value = max;
+ if (value < min)
+ value = min;
+
+ startseed = setup_seed(newseed);
+ // we reach maximum value so randomize over to fix duple in next cycle
+ Glib::ustring version = param_effect->lpeversion.param_getSVGValue();
+ if (startseed == RAND_m - 1 && ((
+ effectType() != ROUGH_HATCHES &&
+ effectType() != ROUGHEN) ||
+ version >= "1.2"))
+ {
+ startseed = rand() * startseed;
+ }
+ seed = startseed;
+}
+
+void
+RandomParam::param_set_range(gdouble min, gdouble max)
+{
+ this->min = min;
+ this->max = max;
+}
+
+void
+RandomParam::param_make_integer(bool yes)
+{
+ integer = yes;
+}
+
+void
+RandomParam::resetRandomizer()
+{
+ seed = startseed;
+}
+
+
+Gtk::Widget *
+RandomParam::param_newWidget()
+{
+ Inkscape::UI::Widget::RegisteredRandom* regrandom = Gtk::manage(
+ new Inkscape::UI::Widget::RegisteredRandom( param_label,
+ param_tooltip,
+ param_key,
+ *param_wr,
+ param_effect->getRepr(),
+ param_effect->getSPDoc() ) );
+
+ regrandom->setValue(value, startseed);
+ if (integer) {
+ regrandom->setDigits(0);
+ regrandom->setIncrements(1, 10);
+ }
+ regrandom->setRange(min, max);
+ regrandom->setProgrammatically = false;
+ regrandom->signal_button_release_event().connect(sigc::mem_fun (*this, &RandomParam::on_button_release));
+
+ regrandom->set_undo_parameters(_("Change random parameter"), INKSCAPE_ICON("dialog-path-effects"));
+
+ return dynamic_cast<Gtk::Widget *> (regrandom);
+}
+
+bool RandomParam::on_button_release(GdkEventButton* button_event) {
+ param_effect->refresh_widgets = true;
+ return false;
+}
+
+RandomParam::operator gdouble()
+{
+ if (_randomsign) {
+ return (rand() * value) - (rand() * value);
+ } else {
+ return rand() * value;
+ }
+};
+
+
+long
+RandomParam::setup_seed(long lSeed)
+{
+ if (lSeed <= 0) lSeed = -(lSeed % (RAND_m - 1)) + 1;
+ if (lSeed > RAND_m - 1) lSeed = RAND_m - 1;
+ return lSeed;
+}
+
+// generates random number between 0 and 1
+gdouble
+RandomParam::rand()
+{
+ long result;
+ result = RAND_a * (seed % RAND_q) - RAND_r * (seed / RAND_q);
+ if (result <= 0) result += RAND_m;
+ seed = result;
+
+ gdouble dresult = (gdouble)(result % BSize) / BSize;
+ return dresult;
+}
+
+
+} /* namespace LivePathEffect */
+} /* namespace Inkscape */
+
+/*
+ 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 :