Commit 0638ce85 authored by L. E. Segovia's avatar L. E. Segovia

First working version of the SeExpr generator

Tested and works in macOS and Windows. Linux somehow returns (0,0,0) for
all evaluations of voronoi, ccurve et al...
parent 0ae44fc6
......@@ -594,11 +594,6 @@ set_package_properties(SeExpr2 PROPERTIES
PURPOSE "Required by the SeExpr generator layer"
)
macro_bool_to_01(SeExpr2_FOUND HAVE_SEEXPR)
set(LINK_SEEXPR_LIB)
if(SeExpr2_FOUND)
include_directories(SYSTEM ${SeExpr2_INCLUDE_DIRS})
set(LINK_SEEXPR_LIB ${SeExpr2_LIBRARY_DIRS})
endif()
find_package(ZLIB)
set_package_properties(ZLIB PROPERTIES
......
add_subdirectory(solid)
add_subdirectory(pattern)
add_subdirectory(simplexnoise)
if(SeExpr2_FOUND)
add_subdirectory(seexpr)
endif()
include_directories(SYSTEM ${SeExpr2_INCLUDE_DIRS})
set(kritaseexprgenerator_SOURCES
SeExprVariable.cpp
SeExprExpressionContext.cpp
generator.cpp
kis_wdg_seexpr.cpp
)
ki18n_wrap_ui(kritaseexprgenerator_SOURCES
wdgseexpr.ui
)
add_library(kritaseexprgenerator MODULE ${kritaseexprgenerator_SOURCES})
target_link_directories(kritaseexprgenerator PRIVATE ${SeExpr2_LIBRARY_DIRS})
target_link_libraries(kritaseexprgenerator kritaui SeExpr2)
install(TARGETS kritaseexprgenerator DESTINATION ${KRITA_PLUGIN_INSTALL_DIR})
/*
* This file is part of Krita
*
* Copyright (c) 2020 L. E. Segovia <amy@amyspark.me>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#include "SeExprExpressionContext.h"
SeExprExpressionContext::SeExprExpressionContext(const QString &expr)
: SeExpr2::Expression(expr.toStdString()), m_vars(VariableMap())
{
}
SeExpr2::ExprVarRef *SeExprExpressionContext::resolveVar(const std::string &name) const
{
return m_vars.value(name, nullptr);
}
/*
* This file is part of Krita
*
* Copyright (c) 2020 L. E. Segovia <amy@amyspark.me>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#include <cstring>
#include <QMap>
#include <QString>
#include <SeExpr2/Expression.h>
#include "SeExprVariable.h"
class SeExprExpressionContext : public SeExpr2::Expression
{
public:
typedef QMap<std::string, SeExprVariable*> VariableMap;
VariableMap m_vars;
SeExprExpressionContext(const QString &expr);
virtual SeExpr2::ExprVarRef *resolveVar(const std::string &name) const override;
};
/*
* This file is part of Krita
*
* Copyright (c) 2020 L. E. Segovia <amy@amyspark.me>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#include "SeExprVariable.h"
SeExprVariable::SeExprVariable()
: SeExpr2::ExprVarRef(SeExpr2::ExprType().FP(1).Varying()), m_value(0)
{
}
SeExprVariable::SeExprVariable(const double v)
: SeExpr2::ExprVarRef(SeExpr2::ExprType().FP(1).Varying()), m_value(v)
{
}
void SeExprVariable::eval(double *result)
{
result[0] = m_value;
}
void SeExprVariable::eval(const char **)
{
Q_ASSERT(!"Sanity check");
}
/*
* This file is part of Krita
*
* Copyright (c) 2020 L. E. Segovia <amy@amyspark.me>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#include <QMap>
#include <QString>
#include <SeExpr2/Expression.h>
struct SeExprVariable : public SeExpr2::ExprVarRef
{
public:
double m_value;
SeExprVariable();
SeExprVariable(const double v);
void eval(double *result) override;
void eval(const char **result) override;
};
/*
* This file is part of Krita
*
* Copyright (c) 2020 L. E. Segovia <amy@amyspark.me>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#include "generator.h"
#include <cstdlib>
#include <cstdio>
#include <cstring>
#include <kis_debug.h>
#include <kpluginfactory.h>
#include <klocalizedstring.h>
#include <kis_fill_painter.h>
#include <kis_image.h>
#include <kis_paint_device.h>
#include <kis_layer.h>
#include <kis_global.h>
#include <kis_selection.h>
#include <kis_types.h>
#include <kis_processing_information.h>
#include <KisSequentialIteratorProgress.h>
#include <KoUpdater.h>
#include <filter/kis_filter_configuration.h>
#include <generator/kis_generator_registry.h>
#include "SeExprExpressionContext.h"
#include "kis_wdg_seexpr.h"
#include "ui_wdgseexpr.h"
K_PLUGIN_FACTORY_WITH_JSON(KritaSeExprGeneratorFactory, "generator.json", registerPlugin<KritaSeExprGenerator>();)
KritaSeExprGenerator::KritaSeExprGenerator(QObject *parent, const QVariantList &)
: QObject(parent)
{
KisGeneratorRegistry::instance()->add(new KisSeExprGenerator());
}
KritaSeExprGenerator::~KritaSeExprGenerator()
{
}
KisSeExprGenerator::KisSeExprGenerator() : KisGenerator(id(), KoID("basic"), i18n("&SeExpr..."))
{
setColorSpaceIndependence(FULLY_INDEPENDENT);
setSupportsPainting(false);
}
KisFilterConfigurationSP KisSeExprGenerator::defaultConfiguration() const
{
KisFilterConfigurationSP config = factoryConfiguration();
QVariant script(QStringLiteral(BASE_SCRIPT));
config->setProperty("script", script);
return config;
}
KisConfigWidget *KisSeExprGenerator::createConfigurationWidget(QWidget *parent, const KisPaintDeviceSP dev, bool) const
{
Q_UNUSED(dev);
return new KisWdgSeExpr(parent);
}
void KisSeExprGenerator::generate(KisProcessingInformation dstInfo,
const QSize &size,
const KisFilterConfigurationSP config,
KoUpdater *progressUpdater) const
{
KisPaintDeviceSP device = dstInfo.paintDevice();
Q_ASSERT(!device.isNull());
Q_ASSERT(config);
if (config)
{
QString script = config->getString("script");
QRect bounds = QRect(dstInfo.topLeft(), size);
const KoColorSpace *cs = device->colorSpace();
KisSequentialIteratorProgress it(device, bounds, progressUpdater);
SeExprExpressionContext expression(script);
expression.m_vars["u"] = new SeExprVariable();
expression.m_vars["v"] = new SeExprVariable();
expression.m_vars["w"] = new SeExprVariable(bounds.width());
expression.m_vars["h"] = new SeExprVariable(bounds.height());
if (expression.isValid() && expression.returnType().isFP(3))
{
double pixel_stride_x = 1. / bounds.width();
double pixel_stride_y = 1. / bounds.height();
double &u = expression.m_vars["u"]->m_value;
double &v = expression.m_vars["v"]->m_value;
while(it.nextPixel())
{
u = pixel_stride_x * (it.x() + .5);
v = pixel_stride_y * (it.y() + .5);
const qreal* value = expression.evalFP();
QColor color;
// SeExpr already outputs normalized RGB
color.setRedF(value[0]);
color.setGreenF(value[1]);
color.setBlueF(value[2]);
cs->fromQColor(color, it.rawData());
}
}
}
}
#include "generator.moc"
/*
* This file is part of Krita
*
* Copyright (c) 2020 L. E. Segovia <amy@amyspark.me>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#ifndef SEEXPR_GENERATOR_H
#define SEEXPR_GENERATOR_H
#include <QObject>
#include <QVariant>
#include "generator/kis_generator.h"
#define BASE_SCRIPT "$val=voronoi(5*[$u,$v,.5],4,.6,.2); \n \
$color=ccurve($val,\n\
0.000, [0.141, 0.059, 0.051], 4,\n\
0.185, [0.302, 0.176, 0.122], 4,\n\
0.301, [0.651, 0.447, 0.165], 4,\n\
0.462, [0.976, 0.976, 0.976], 4);\n\
$color\n\
"
class KisConfigWidget;
class KritaSeExprGenerator : public QObject
{
Q_OBJECT
public:
KritaSeExprGenerator(QObject *parent, const QVariantList &);
~KritaSeExprGenerator() override;
};
class KisSeExprGenerator : public KisGenerator
{
public:
KisSeExprGenerator();
using KisGenerator::generate;
void generate(KisProcessingInformation dst,
const QSize& size,
const KisFilterConfigurationSP config,
KoUpdater* progressUpdater
) const override;
static inline KoID id() {
return KoID("seexpr", i18n("SeExpr"));
}
KisFilterConfigurationSP defaultConfiguration() const override;
KisConfigWidget * createConfigurationWidget(QWidget* parent, const KisPaintDeviceSP dev, bool useForMasks) const override;
};
#endif
{
"Id": "SeExpr Generator",
"Type": "Service",
"X-KDE-Library": "kritaseexprgenerator",
"X-KDE-ServiceTypes": [
"Krita/Generator"
],
"X-Krita-Version": "28"
}
/*
* This file is part of Krita
*
* Copyright (c) 2020 L. E. Segovia <amy@amyspark.me>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#include <KoColor.h>
#include <KoResourceServer.h>
#include <KoResourceServerProvider.h>
#include <filter/kis_filter_configuration.h>
#include "generator.h"
#include "kis_wdg_seexpr.h"
#include "ui_wdgseexpr.h"
KisWdgSeExpr::KisWdgSeExpr(QWidget* parent)
: KisConfigWidget(parent)
{
m_widget = new Ui_WdgSeExpr();
m_widget->setupUi(this);
connect(m_widget->btnUpdate, SIGNAL(clicked()), this, SIGNAL(sigConfigurationUpdated()));
}
KisWdgSeExpr::~KisWdgSeExpr()
{
delete m_widget;
}
inline const Ui_WdgSeExpr *KisWdgSeExpr::widget() const {
return m_widget;
}
void KisWdgSeExpr::setConfiguration(const KisPropertiesConfigurationSP config)
{
Q_ASSERT(!config->getString("script").isEmpty());
QString script = config->getString("script");
widget()->txtEditor->setPlainText(script);
}
KisPropertiesConfigurationSP KisWdgSeExpr::configuration() const
{
KisFilterConfigurationSP config = new KisFilterConfiguration("seexpr", 1);
QVariant v(widget()->txtEditor->toPlainText());
config->setProperty("script", v);
return config;
}
/*
* This file is part of Krita
*
* Copyright (c) 2020 L. E. Segovia <amy@amyspark.me>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
#ifndef KIS_WDG_SEEXPR_H
#define KIS_WDG_SEEXPR_H
#include <kis_config_widget.h>
class Ui_WdgSeExpr;
class KisWdgSeExpr : public KisConfigWidget
{
Q_OBJECT
public:
KisWdgSeExpr(QWidget* parent = 0);
~KisWdgSeExpr() override;
public:
inline const Ui_WdgSeExpr* widget() const;
void setConfiguration(const KisPropertiesConfigurationSP) override;
KisPropertiesConfigurationSP configuration() const override;
private:
Ui_WdgSeExpr *m_widget;
};
#endif
<?xml version="1.0" encoding="UTF-8"?>
<ui version="4.0">
<class>WdgSeExpr</class>
<widget class="QWidget" name="WdgSeExpr">
<property name="geometry">
<rect>
<x>0</x>
<y>0</y>
<width>538</width>
<height>274</height>
</rect>
</property>
<layout class="QVBoxLayout" name="rightLayout">
<property name="spacing">
<number>0</number>
</property>
<item>
<widget class="QPlainTextEdit" name="txtEditor"/>
</item>
<item>
<widget class="QPushButton" name="btnUpdate">
<property name="text">
<string>Update</string>
</property>
</widget>
</item>
</layout>
</widget>
<resources/>
<connections/>
</ui>
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment