paysages: Color gradation editor with curves.

git-svn-id: https://subversion.assembla.com/svn/thunderk/paysages@281 b1fd45b6-86a6-48da-8261-f70d1f35bdcc
This commit is contained in:
Michaël Lemaire 2012-03-31 11:32:03 +00:00 committed by ThunderK
parent 85f4017bf1
commit decaf96036
7 changed files with 167 additions and 54 deletions

View file

@ -2,6 +2,7 @@
#include <QVBoxLayout> #include <QVBoxLayout>
#include <QHBoxLayout> #include <QHBoxLayout>
#include <QGridLayout>
#include <QImage> #include <QImage>
#include <QLabel> #include <QLabel>
#include <QColor> #include <QColor>
@ -18,6 +19,8 @@ DialogColorGradation::DialogColorGradation(QWidget *parent, ColorGradation* grad
QDialog(parent) QDialog(parent)
{ {
QWidget* buttons; QWidget* buttons;
QWidget* form;
QGridLayout* form_layout;
_base = gradation; _base = gradation;
_current = colorGradationCreate(); _current = colorGradationCreate();
@ -25,28 +28,38 @@ DialogColorGradation::DialogColorGradation(QWidget *parent, ColorGradation* grad
setLayout(new QVBoxLayout()); setLayout(new QVBoxLayout());
_curve_editor = new WidgetCurveEditor(this); form = new QWidget(this);
layout()->addWidget(_curve_editor); form_layout = new QGridLayout();
form->setLayout(form_layout);
layout()->addWidget(form);
form_layout->addWidget(new QLabel(tr("This is the curve editor for color components.\nClick on a component preview below to edit it.\nClick on points and drag them to move them.\nDouble click to add a new point.\nRight click on a point to delete it."), form), 0, 0);
_curve_editor = new WidgetCurveEditor(form);
form_layout->addWidget(_curve_editor, 0, 1);
connect(_curve_editor, SIGNAL(liveChanged()), this, SLOT(updateColors())); connect(_curve_editor, SIGNAL(liveChanged()), this, SLOT(updateColors()));
_preview_red = new PreviewColorGradation(this, _current, COLORGRADATIONBAND_RED); form_layout->addWidget(new QLabel(tr("Red preview, click to edit"), form), 1, 0);
_preview_red = new PreviewColorGradation(form, _current, COLORGRADATIONBAND_RED);
_preview_red->setMinimumHeight(50); _preview_red->setMinimumHeight(50);
connect(_preview_red, SIGNAL(clicked()), this, SLOT(selectRed())); connect(_preview_red, SIGNAL(clicked()), this, SLOT(selectRed()));
layout()->addWidget(_preview_red); form_layout->addWidget(_preview_red, 1, 1);
_preview_green = new PreviewColorGradation(this, _current, COLORGRADATIONBAND_GREEN); form_layout->addWidget(new QLabel(tr("Green preview, click to edit"), form), 2, 0);
_preview_green = new PreviewColorGradation(form, _current, COLORGRADATIONBAND_GREEN);
_preview_green->setMinimumHeight(50); _preview_green->setMinimumHeight(50);
connect(_preview_green, SIGNAL(clicked()), this, SLOT(selectGreen())); connect(_preview_green, SIGNAL(clicked()), this, SLOT(selectGreen()));
layout()->addWidget(_preview_green); form_layout->addWidget(_preview_green, 2, 1);
_preview_blue = new PreviewColorGradation(this, _current, COLORGRADATIONBAND_BLUE); form_layout->addWidget(new QLabel(tr("Blue preview, click to edit"), form), 3, 0);
_preview_blue = new PreviewColorGradation(form, _current, COLORGRADATIONBAND_BLUE);
_preview_blue->setMinimumHeight(50); _preview_blue->setMinimumHeight(50);
connect(_preview_blue, SIGNAL(clicked()), this, SLOT(selectBlue())); connect(_preview_blue, SIGNAL(clicked()), this, SLOT(selectBlue()));
layout()->addWidget(_preview_blue); form_layout->addWidget(_preview_blue, 3, 1);
_preview_final = new PreviewColorGradation(this, _current, COLORGRADATIONBAND_FINAL); form_layout->addWidget(new QLabel(tr("Final preview"), form), 4, 0);
_preview_final = new PreviewColorGradation(form, _current, COLORGRADATIONBAND_FINAL);
_preview_final->setMinimumHeight(50); _preview_final->setMinimumHeight(50);
layout()->addWidget(_preview_final); form_layout->addWidget(_preview_final, 4, 1);
buttons = new QWidget(this); buttons = new QWidget(this);
layout()->addWidget(buttons); layout()->addWidget(buttons);
@ -111,6 +124,7 @@ void DialogColorGradation::selectRed()
{ {
colorGradationGetRedCurve(_current, _curve); colorGradationGetRedCurve(_current, _curve);
_curve_editor->setCurve(_curve); _curve_editor->setCurve(_curve);
_curve_editor->setPenColor(QColor(255, 0, 0));
_selected = 1; _selected = 1;
} }
@ -118,6 +132,7 @@ void DialogColorGradation::selectGreen()
{ {
colorGradationGetGreenCurve(_current, _curve); colorGradationGetGreenCurve(_current, _curve);
_curve_editor->setCurve(_curve); _curve_editor->setCurve(_curve);
_curve_editor->setPenColor(QColor(0, 200, 0));
_selected = 2; _selected = 2;
} }
@ -125,6 +140,7 @@ void DialogColorGradation::selectBlue()
{ {
colorGradationGetBlueCurve(_current, _curve); colorGradationGetBlueCurve(_current, _curve);
_curve_editor->setCurve(_curve); _curve_editor->setCurve(_curve);
_curve_editor->setPenColor(QColor(0, 0, 255));
_selected = 3; _selected = 3;
} }

View file

@ -19,7 +19,7 @@ DialogWanderer::DialogWanderer(QWidget* parent, CameraDefinition* camera, bool c
panel = new QWidget(this); panel = new QWidget(this);
panel->setLayout(new QVBoxLayout()); panel->setLayout(new QVBoxLayout());
panel->setMaximumWidth(200); panel->setMaximumWidth(230);
button = new QPushButton(tr("Reset camera"), panel); button = new QPushButton(tr("Reset camera"), panel);
panel->layout()->addWidget(button); panel->layout()->addWidget(button);

View file

@ -8,6 +8,7 @@ WidgetCurveEditor::WidgetCurveEditor(QWidget *parent) : QWidget(parent)
{ {
_curve = curveCreate(); _curve = curveCreate();
_dragged = -1; _dragged = -1;
_pen = QColor(0, 0, 0);
setMinimumSize(500, 500); setMinimumSize(500, 500);
setMaximumSize(500, 500); setMaximumSize(500, 500);
@ -29,6 +30,12 @@ void WidgetCurveEditor::getCurve(Curve* curve)
curveCopy(_curve, curve); curveCopy(_curve, curve);
} }
void WidgetCurveEditor::setPenColor(QColor color)
{
_pen = color;
update();
}
void WidgetCurveEditor::paintEvent(QPaintEvent* event) void WidgetCurveEditor::paintEvent(QPaintEvent* event)
{ {
int i, n; int i, n;
@ -37,7 +44,7 @@ void WidgetCurveEditor::paintEvent(QPaintEvent* event)
QPainter painter(this); QPainter painter(this);
painter.fillRect(0, 0, 500, 500, QColor(255, 255, 255)); painter.fillRect(0, 0, 500, 500, QColor(255, 255, 255));
painter.setPen(QColor(255, 0, 0)); painter.setPen(_pen);
for (int x = 0; x < 500; x++) for (int x = 0; x < 500; x++)
{ {
@ -56,41 +63,9 @@ void WidgetCurveEditor::paintEvent(QPaintEvent* event)
void WidgetCurveEditor::mousePressEvent(QMouseEvent* event) void WidgetCurveEditor::mousePressEvent(QMouseEvent* event)
{ {
int i, n; if (event->button() == Qt::LeftButton && _dragged < 0)
int nearest;
double mousex, mousey;
double distance, ndistance;
CurvePoint point;
n = curveGetPointCount(_curve);
if (n < 1)
{ {
return; _dragged = getPointAt(event->x(), event->y());
}
mousex = ((double)event->x()) / 499.0;
mousey = 1.0 - ((double)event->y()) / 499.0;
nearest = -1;
// Find nearest point
for (i = 0; i < n; i++)
{
curveGetPoint(_curve, i, &point);
ndistance = toolsGetDistance2D(point.position, point.value, mousex, mousey);
if (nearest < 0 || ndistance < distance)
{
distance = ndistance;
nearest = i;
}
}
if (distance < 0.015)
{
_dragged = nearest;
}
else
{
_dragged = -1;
} }
event->accept(); event->accept();
@ -100,7 +75,7 @@ void WidgetCurveEditor::mouseMoveEvent(QMouseEvent* event)
{ {
CurvePoint point; CurvePoint point;
if (_dragged >= 0) if (_dragged >= 0 && (event->buttons() & Qt::LeftButton))
{ {
point.position = ((double)event->x()) / 499.0; point.position = ((double)event->x()) / 499.0;
point.value = 1.0 - ((double)event->y()) / 499.0; point.value = 1.0 - ((double)event->y()) / 499.0;
@ -122,13 +97,81 @@ void WidgetCurveEditor::mouseMoveEvent(QMouseEvent* event)
void WidgetCurveEditor::mouseReleaseEvent(QMouseEvent* event) void WidgetCurveEditor::mouseReleaseEvent(QMouseEvent* event)
{ {
if (_dragged >= 0) int clicked;
if (event->button() == Qt::RightButton)
{
clicked = getPointAt(event->x(), event->y());
if (clicked >= 0)
{
curveRemovePoint(_curve, clicked);
update();
emit liveChanged();
}
}
else if (event->button() == Qt::LeftButton && _dragged >= 0)
{ {
_dragged = -1; _dragged = -1;
curveValidate(_curve); curveValidate(_curve);
update(); update();
} }
event->accept(); event->accept();
} }
void WidgetCurveEditor::mouseDoubleClickEvent(QMouseEvent* event)
{
CurvePoint point;
if (event->button() == Qt::LeftButton && _dragged < 0)
{
if (getPointAt(event->x(), event->y()) < 0)
{
point.position = ((double)event->x()) / 499.0;
point.value = 1.0 - ((double)event->y()) / 499.0;
curveAddPoint(_curve, &point);
curveValidate(_curve);
update();
emit liveChanged();
}
}
}
int WidgetCurveEditor::getPointAt(int x, int y)
{
int n;
int nearest;
double distance, ndistance;
CurvePoint point;
double dx = ((double)x) / 499.0;
double dy = 1.0 - ((double)y) / 499.0;
n = curveGetPointCount(_curve);
if (n < 1)
{
return -1;
}
// Find nearest point
nearest = -1;
for (int i = 0; i < n; i++)
{
curveGetPoint(_curve, i, &point);
ndistance = toolsGetDistance2D(point.position, point.value, dx, dy);
if (nearest < 0 || ndistance < distance)
{
distance = ndistance;
nearest = i;
}
}
if (nearest >= 0 && distance < 0.015)
{
return nearest;
}
else
{
return -1;
}
}

View file

@ -2,6 +2,7 @@
#define _PAYSAGES_QT_WIDGETCURVEEDITOR_H_ #define _PAYSAGES_QT_WIDGETCURVEEDITOR_H_
#include <QWidget> #include <QWidget>
#include <QColor>
#include "../lib_paysages/curve.h" #include "../lib_paysages/curve.h"
class WidgetCurveEditor : public QWidget class WidgetCurveEditor : public QWidget
@ -15,6 +16,8 @@ public:
void setCurve(Curve* curve); void setCurve(Curve* curve);
void getCurve(Curve* curve); void getCurve(Curve* curve);
void setPenColor(QColor color);
signals: signals:
void liveChanged(); void liveChanged();
@ -23,10 +26,14 @@ protected:
void mousePressEvent(QMouseEvent* event); void mousePressEvent(QMouseEvent* event);
void mouseMoveEvent(QMouseEvent* event); void mouseMoveEvent(QMouseEvent* event);
void mouseReleaseEvent(QMouseEvent* event); void mouseReleaseEvent(QMouseEvent* event);
void mouseDoubleClickEvent(QMouseEvent* event);
private: private:
int getPointAt(int x, int y);
Curve* _curve; Curve* _curve;
int _dragged; int _dragged;
QColor _pen;
}; };
#endif #endif

View file

@ -37,22 +37,55 @@
<context> <context>
<name>DialogColorGradation</name> <name>DialogColorGradation</name>
<message> <message>
<location filename="../gui_qt/dialogcolorgradation.cpp" line="55"/> <location filename="../gui_qt/dialogcolorgradation.cpp" line="36"/>
<source>This is the curve editor for color components.
Click on a component preview below to edit it.
Click on points and drag them to move them.
Double click to add a new point.
Right click on a point to delete it.</source>
<translation>Ceci est l&apos;éditeur de courbes pour les couleurs.
Cliquez sur une des couleurs ci-dessous pour l&apos;éditer.
Cliquez sur les points pour les déplacer.
Double cliquez sur le fond pour ajouter un point.
Cliquez avec le bouton droit sur un point pour le supprimer.</translation>
</message>
<message>
<location filename="../gui_qt/dialogcolorgradation.cpp" line="41"/>
<source>Red preview, click to edit</source>
<translation>Aperçu du rouge, cliquer pour éditer</translation>
</message>
<message>
<location filename="../gui_qt/dialogcolorgradation.cpp" line="47"/>
<source>Green preview, click to edit</source>
<translation>Aperçu du vert, cliquer pour éditer</translation>
</message>
<message>
<location filename="../gui_qt/dialogcolorgradation.cpp" line="53"/>
<source>Blue preview, click to edit</source>
<translation>Aperçu du bleu, cliquez pour éditer</translation>
</message>
<message>
<location filename="../gui_qt/dialogcolorgradation.cpp" line="59"/>
<source>Final preview</source>
<translation>Aperçu du gradient final</translation>
</message>
<message>
<location filename="../gui_qt/dialogcolorgradation.cpp" line="68"/>
<source>Validate</source> <source>Validate</source>
<translation>Valider</translation> <translation>Valider</translation>
</message> </message>
<message> <message>
<location filename="../gui_qt/dialogcolorgradation.cpp" line="59"/> <location filename="../gui_qt/dialogcolorgradation.cpp" line="72"/>
<source>Revert</source> <source>Revert</source>
<translation>Recommencer</translation> <translation>Recommencer</translation>
</message> </message>
<message> <message>
<location filename="../gui_qt/dialogcolorgradation.cpp" line="63"/> <location filename="../gui_qt/dialogcolorgradation.cpp" line="76"/>
<source>Cancel</source> <source>Cancel</source>
<translation>Annuler</translation> <translation>Annuler</translation>
</message> </message>
<message> <message>
<location filename="../gui_qt/dialogcolorgradation.cpp" line="69"/> <location filename="../gui_qt/dialogcolorgradation.cpp" line="82"/>
<source>Paysages 3D - Color gradation editor</source> <source>Paysages 3D - Color gradation editor</source>
<translation>Paysages 3D - Editeur de gradients de couleur</translation> <translation>Paysages 3D - Editeur de gradients de couleur</translation>
</message> </message>
@ -143,7 +176,7 @@
<message> <message>
<location filename="../gui_qt/dialogwanderer.cpp" line="30"/> <location filename="../gui_qt/dialogwanderer.cpp" line="30"/>
<source>Validate as render camera</source> <source>Validate as render camera</source>
<translation>Valider comme caméra de rendu</translation> <translation>Choisir comme caméra de rendu</translation>
</message> </message>
<message> <message>
<location filename="../gui_qt/dialogwanderer.cpp" line="35"/> <location filename="../gui_qt/dialogwanderer.cpp" line="35"/>

View file

@ -1,6 +1,7 @@
#include "curve.h" #include "curve.h"
#include <stdlib.h> #include <stdlib.h>
#include <string.h>
#include "tools.h" #include "tools.h"
#define MAX_NB_POINTS 40 #define MAX_NB_POINTS 40
@ -104,6 +105,18 @@ void curveSetPoint(Curve* curve, int number, CurvePoint* point)
} }
} }
void curveRemovePoint(Curve* curve, int number)
{
if (number >= 0 && number < curve->nbpoints)
{
if (curve->nbpoints > 0 && number < curve->nbpoints - 1)
{
memmove(curve->points + number, curve->points + number + 1, sizeof(CurvePoint) * (curve->nbpoints - number - 1));
}
curve->nbpoints--;
}
}
int _point_compare(const void* part1, const void* part2) int _point_compare(const void* part1, const void* part2)
{ {
if (((CurvePoint*)part1)->position > ((CurvePoint*)part2)->position) if (((CurvePoint*)part1)->position > ((CurvePoint*)part2)->position)

View file

@ -26,6 +26,7 @@ int curveQuickAddPoint(Curve* curve, double position, double value);
int curveGetPointCount(Curve* curve); int curveGetPointCount(Curve* curve);
void curveGetPoint(Curve* curve, int number, CurvePoint* point); void curveGetPoint(Curve* curve, int number, CurvePoint* point);
void curveSetPoint(Curve* curve, int number, CurvePoint* point); void curveSetPoint(Curve* curve, int number, CurvePoint* point);
void curveRemovePoint(Curve* curve, int number);
void curveValidate(Curve* curve); void curveValidate(Curve* curve);
double curveGetValue(Curve* curve, double position); double curveGetValue(Curve* curve, double position);