Changed: #1193 Code cleanup.

hg/feature/sound
timon 14 years ago
parent 6934b285e2
commit ffb5b2678b

@ -29,10 +29,11 @@
using namespace NLMISC;
namespace NLQT {
namespace NLQT
{
CAnimationDialog::CAnimationDialog(QWidget *parent)
: QDockWidget(parent)
: QDockWidget(parent)
{
_ui.setupUi(this);
@ -45,13 +46,13 @@ CAnimationDialog::CAnimationDialog(QWidget *parent)
connect(_ui.horizontalSlider, SIGNAL(sliderMoved(int)), this, SLOT(changeFrame(int)));
connect(_ui.startSpinBox, SIGNAL(valueChanged(int)), this, SLOT(changeStartAnim(int)));
connect(_ui.endSpinBox, SIGNAL(valueChanged(int)), this, SLOT(changeEndAnim(int)));
// init QTimeLine
_timeLine = new QTimeLine(_ui.endSpinBox->value() * _frameRate, this);
_timeLine->setCurveShape(QTimeLine::LinearCurve);
_timeLine->setUpdateInterval(25);
_timeLine->setFrameRange(_ui.startSpinBox->value(), _ui.endSpinBox->value());
connect(_timeLine, SIGNAL(frameChanged(int)), this, SLOT(updateAnim(int)));
connect(_timeLine, SIGNAL(finished()), this, SLOT(finish()));
@ -65,7 +66,7 @@ CAnimationDialog::CAnimationDialog(QWidget *parent)
CAnimationDialog::~CAnimationDialog()
{
}
NL3D::TAnimationTime CAnimationDialog::getTime ()
{
return float(_timeLine->currentFrame()) / _frameRate;
@ -74,7 +75,7 @@ NL3D::TAnimationTime CAnimationDialog::getTime ()
void CAnimationDialog::changeAnimLength()
{
std::string curObj = Modules::objView().getCurrentObject();
if (curObj.empty())
if (curObj.empty())
return;
CEntity &entity = Modules::objView().getEntity(curObj);
float animLength = entity.getPlayListLength();
@ -85,7 +86,7 @@ void CAnimationDialog::changeAnimLength()
void CAnimationDialog::setCurrentShape(const QString &name)
{
if (name.isEmpty())
if (name.isEmpty())
return;
CEntity &entity = Modules::objView().getEntity(name.toStdString());
@ -108,8 +109,8 @@ void CAnimationDialog::play()
}
CEntity &entity = Modules::objView().getEntity(curObj);
entity.playbackAnim(true);
if (_timeLine->state() == QTimeLine::Running)
if (_timeLine->state() == QTimeLine::Running)
_timeLine->setPaused(true);
else if (_timeLine->currentFrame() == _timeLine->endFrame()) _timeLine->start();
else
@ -123,7 +124,7 @@ void CAnimationDialog::stop()
_ui.playPushButton->setChecked(false);
std::string curObj = Modules::objView().getCurrentObject();
if (curObj.empty())
if (curObj.empty())
return;
CEntity &entity = Modules::objView().getEntity(curObj);
entity.playbackAnim(false);
@ -136,7 +137,7 @@ void CAnimationDialog::end()
void CAnimationDialog::changeFrame(int frame)
{
if (_timeLine->state() == QTimeLine::Running)
if (_timeLine->state() == QTimeLine::Running)
{
_timeLine->setPaused(true);
_timeLine->setCurrentTime((float(frame) / _frameRate) * 1000);
@ -153,7 +154,7 @@ void CAnimationDialog::changeStartAnim(int start)
void CAnimationDialog::changeEndAnim(int end)
{
_ui.horizontalSlider->setMaximum(end);
_ui.horizontalSlider->setMaximum(end);
_timeLine->setDuration((float(end - _ui.startSpinBox->value()) / _frameRate) * 1000);
_timeLine->setFrameRange(_ui.startSpinBox->value(), end);
}
@ -166,7 +167,7 @@ void CAnimationDialog::updateAnim(int frame)
void CAnimationDialog::setInPlace(bool state)
{
std::string curObj = Modules::objView().getCurrentObject();
if (curObj.empty())
if (curObj.empty())
return;
CEntity &entity = Modules::objView().getEntity(curObj);
entity.setInPlace(state);
@ -175,7 +176,7 @@ void CAnimationDialog::setInPlace(bool state)
void CAnimationDialog::setIncPos(bool state)
{
std::string curObj = Modules::objView().getCurrentObject();
if (curObj.empty())
if (curObj.empty())
return;
CEntity &entity = Modules::objView().getEntity(curObj);
entity.setIncPos(state);

@ -33,35 +33,36 @@
// Project includes
namespace NLQT {
namespace NLQT
{
/**
@class CAnimationDialog
@brief Animation model control dialog.
@details The dialogue doesn't affect on the model itself, but only calculates the current time of animations
@details The dialogue doesn't affect on the model itself, but only calculates the current time of animations
that can be obtained through a class method getTime().
The user can influence on the duration of the animation, but he doesn't know the total time for all the animations in the playlist.
Therefore, the class provides a slot that requires a total duration of the animated object animations and set it.
*/
Therefore, the class provides a slot that requires a total duration of the animated object animations and set it.
*/
class CAnimationDialog: public QDockWidget
{
Q_OBJECT
Q_OBJECT
public:
/// Constructor, sets the default length of time from 0 to 99
CAnimationDialog(QWidget *parent = 0);
~CAnimationDialog();
/// Get the current time animations
/// @return Returns the current time animations, which can then be use in class CObjectViewer
NL3D::TAnimationTime getTime ();
public Q_SLOTS:
/// Find the total time of the playlist and sets its
void changeAnimLength();
/// Updates animation status for the selected current object
/// @param name - the name of the selected object
/// @param name - the name of the selected object
void setCurrentShape(const QString &name);
private Q_SLOTS:
@ -78,11 +79,11 @@ private Q_SLOTS:
void finish();
private:
static const int _frameRate = 50;
QTimeLine *_timeLine;
Ui::CAnimationDialog _ui;
friend class CMainWindow;
}; /* CAnimationDialog */

@ -29,10 +29,11 @@
#include "modules.h"
#include "entity.h"
namespace NLQT {
namespace NLQT
{
CAnimationSetDialog::CAnimationSetDialog(QWidget *parent)
: QDockWidget(parent)
: QDockWidget(parent)
{
ui.setupUi(this);
@ -46,7 +47,7 @@ CAnimationSetDialog::CAnimationSetDialog(QWidget *parent)
connect(ui.listRadioButton, SIGNAL(clicked(bool)), this, SLOT(setModeAnim()));
connect(ui.mixerRadioButton, SIGNAL(clicked(bool)), this, SLOT(setModeAnim()));
connect(ui.objectsComboBox, SIGNAL(currentIndexChanged(QString)), this, SLOT(setCurrentShape(QString)));
}
@ -56,22 +57,22 @@ CAnimationSetDialog::~CAnimationSetDialog()
void CAnimationSetDialog::setCurrentShape(const QString &name)
{
if (name.isEmpty())
return;
if (name.isEmpty())
return;
Modules::objView().setCurrentObject(name.toStdString());
updateListAnim();
Q_EMIT changeCurrentShape(name);
}
void CAnimationSetDialog::setModeAnim()
{
std::string curObj = Modules::objView().getCurrentObject();
if (curObj.empty())
return;
if (curObj.empty())
return;
CEntity &entity = Modules::objView().getEntity(curObj);
if (ui.mixerRadioButton->isChecked())
@ -89,11 +90,11 @@ void CAnimationSetDialog::updateListObject()
for (size_t i = 0; i < listObjects.size(); i++)
ui.objectsComboBox->addItem(QString(listObjects[i].c_str()));
if (listObjects.empty())
{
ui.addAnimPushButton->setEnabled(false);
ui.addSwtPushButton->setEnabled(false);
ui.addSwtPushButton->setEnabled(false);
ui.resetPushButton->setEnabled(false);
ui.setLengthPushButton->setEnabled(false);
}
@ -111,52 +112,52 @@ void CAnimationSetDialog::updateListAnim()
ui.animTreeWidget->clear();
ui.animPlaylistWidget->clear();
ui.skeletonTreeWidget->clear();
std::string curObj = Modules::objView().getCurrentObject();
if (curObj.empty())
return;
if (curObj.empty())
return;
CEntity &entity = Modules::objView().getEntity(curObj);
std::vector<std::string>& animationList = entity.getAnimationList();
std::vector<std::string>& swtList = entity.getSWTList();
std::vector<std::string>& playListAnimation = entity.getPlayListAnimation();
// update animation list widget
for(size_t i = 0; i < animationList.size(); ++i)
{
QTreeWidgetItem *item = new QTreeWidgetItem(ui.animTreeWidget);
item->setText(0,QString(animationList[i].c_str()));
}
// update skeleton weight template list widget
for(size_t i = 0; i < swtList.size(); ++i)
{
QTreeWidgetItem *item = new QTreeWidgetItem(ui.skeletonTreeWidget);
item->setText(0,QString(swtList[i].c_str()));
}
// update PlayList animation widget
for(size_t i = 0; i < playListAnimation.size(); ++i)
{
QListWidgetItem *item = new QListWidgetItem(ui.animPlaylistWidget);
item->setText(QString(playListAnimation[i].c_str()));
}
if (animationList.empty())
{
// lock buttons
ui.addToolButton->setEnabled(false);
ui.removeToolButton->setEnabled(false);
ui.removeToolButton->setEnabled(false);
ui.upToolButton->setEnabled(false);
ui.downToolButton->setEnabled(false);
ui.downToolButton->setEnabled(false);
}
else
{
// unlock buttons
// unlock buttons
ui.addToolButton->setEnabled(true);
ui.removeToolButton->setEnabled(true);
ui.removeToolButton->setEnabled(true);
ui.upToolButton->setEnabled(true);
ui.downToolButton->setEnabled(true);
ui.downToolButton->setEnabled(true);
}
}
@ -165,16 +166,16 @@ void CAnimationSetDialog::loadAnim()
CEntity &entity = Modules::objView().getEntity(Modules::objView().getCurrentObject());
QStringList fileNames = QFileDialog::getOpenFileNames(this,
tr("Open NeL anim file"), ".",
tr("NeL anim files (*.anim);;"));
tr("Open NeL anim file"), ".",
tr("NeL anim files (*.anim);;"));
setCursor(Qt::WaitCursor);
if (!fileNames.isEmpty())
if (!fileNames.isEmpty())
{
QStringList list = fileNames;
QStringList::Iterator it = list.begin();
while(it != list.end())
QStringList::Iterator it = list.begin();
while(it != list.end())
{
std::string animName = it->toStdString();
entity.loadAnimation(animName);
@ -188,19 +189,19 @@ void CAnimationSetDialog::loadAnim()
void CAnimationSetDialog::loadSwt()
{
CEntity &entity = Modules::objView().getEntity(Modules::objView().getCurrentObject());
CEntity &entity = Modules::objView().getEntity(Modules::objView().getCurrentObject());
QStringList fileNames = QFileDialog::getOpenFileNames(this,
tr("Open NeL anim file"), ".",
tr("NeL Skeleton Weight Template files (*.swt);;"));
tr("Open NeL anim file"), ".",
tr("NeL Skeleton Weight Template files (*.swt);;"));
setCursor(Qt::WaitCursor);
if (!fileNames.isEmpty())
if (!fileNames.isEmpty())
{
QStringList list = fileNames;
QStringList::Iterator it = list.begin();
while(it != list.end())
QStringList::Iterator it = list.begin();
while(it != list.end())
{
std::string swtName = it->toStdString();
entity.loadSWT(swtName);
@ -216,7 +217,7 @@ void CAnimationSetDialog::resetAnim()
{
CEntity &entity = Modules::objView().getEntity(Modules::objView().getCurrentObject());
entity.reset();
updateListAnim();
}
@ -242,8 +243,8 @@ void CAnimationSetDialog::removeAnim()
{
int row = ui.animPlaylistWidget->row(item);
QListWidgetItem *removeItem = ui.animPlaylistWidget->takeItem(row);
if (!removeItem)
delete removeItem;
if (!removeItem)
delete removeItem;
entity.removeAnimToPlayList(row);
}
}
@ -258,7 +259,7 @@ void CAnimationSetDialog::upAnim()
int frontRow = ui.animPlaylistWidget->row(list.front());
int backRow = ui.animPlaylistWidget->row(list.back());
if (frontRow == 0)
return;
@ -270,7 +271,7 @@ void CAnimationSetDialog::upAnim()
}
void CAnimationSetDialog::downAnim()
{
{
CEntity &entity = Modules::objView().getEntity(Modules::objView().getCurrentObject());
QList<QListWidgetItem*> list = ui.animPlaylistWidget->selectedItems();
@ -279,7 +280,7 @@ void CAnimationSetDialog::downAnim()
int frontRow = ui.animPlaylistWidget->row(list.front());
int backRow = ui.animPlaylistWidget->row(list.back());
if (backRow == (ui.animPlaylistWidget->count() - 1))
return;
@ -289,5 +290,5 @@ void CAnimationSetDialog::downAnim()
for (int i = backRow; i >= frontRow; --i)
entity.swapAnimToPlayList(i, i + 1);
}
} /* namespace NLQT */

@ -28,40 +28,41 @@
// Project includes
namespace NLQT {
/**
namespace NLQT
{
/**
@class CAnimationSetDialog
@brief Dialog - Animations control, loading animation, weight for skeleton and playlist composition.
@details Dialog loads animations files and weight for skeleton animation. Files can also be unloaded.
For loading / unloading and animation control dialog uses the functionality of CEntity class.
But the main opportunity for dialogue is to generating animations playlists.
Also, the dialogue has a control element to select the current shape (emit a signal changeCurrentShape())
Also, the dialogue has a control element to select the current shape (emit a signal changeCurrentShape())
and switch of playlist/mixer (this functionality will soon be transferred to another specialized dialogue).
As each shape has its own list of loaded animations and playlist,when you switch your current shape,
the dialogue should be notified through the slot setCurrentShape ().
*/
*/
class CAnimationSetDialog: public QDockWidget
{
Q_OBJECT
Q_OBJECT
public:
CAnimationSetDialog(QWidget *parent = 0);
~CAnimationSetDialog();
/// Update the objects list (this function should be moved to another dialogue)
void updateListObject();
/// Update the list of loaded animation files
void updateListAnim();
Q_SIGNALS:
/// Signal emitted when changing the current animation object.
void changeCurrentShape(const QString &name);
void changeCurrentShape(const QString &name);
public Q_SLOTS:
/// Updates and displays the list of loaded animations and playlist for the selected current object
/// @param name - the name of the selected object
/// @param name - the name of the selected object
void setCurrentShape(const QString &name);
private Q_SLOTS:
@ -73,11 +74,11 @@ private Q_SLOTS:
void removeAnim();
void upAnim();
void downAnim();
private:
Ui::CAnimationSetDialog ui;
friend class CMainWindow;
}; /* CAnimationDialog */

@ -40,15 +40,16 @@
#include "spinner_dialog.h"
#include "follow_path_dialog.h"
namespace NLQT {
namespace NLQT
{
CAttribWidget::CAttribWidget(QWidget *parent)
: QGroupBox(parent),
_SrcInputEnabled(true),
_EnableConstantValue(true),
_DisableMemoryScheme(false),
_NbCycleEnabled(true),
_Node(NULL), _SchemeWidget(NULL)
: QGroupBox(parent),
_SrcInputEnabled(true),
_EnableConstantValue(true),
_DisableMemoryScheme(false),
_NbCycleEnabled(true),
_Node(NULL), _SchemeWidget(NULL)
{
_ui.setupUi(this);
_ui.constRangeUIntWidget->hide();
@ -87,21 +88,21 @@ void CAttribWidget::updateUi()
{
if (!_EnableConstantValue)
_ui.comboBox->hide();
else
else
_ui.comboBox->show();
if (useScheme())
{
if (_ui.comboBox->currentIndex() == 1)
if (_ui.comboBox->currentIndex() == 1)
schemeValueUpdate();
else
_ui.comboBox->setCurrentIndex(1);
}
else
{
nlassert(_EnableConstantValue);
if (_ui.comboBox->currentIndex() == 0)
if (_ui.comboBox->currentIndex() == 0)
cstValueUpdate();
else
_ui.comboBox->setCurrentIndex(0);
@ -122,14 +123,14 @@ void CAttribWidget::clickedEdit()
void CAttribWidget::setClamp(bool state)
{
// avoid performance warning
// avoid performance warning
if (state != isSchemeClamped())
clampScheme(state);
}
void CAttribWidget::changeCurrentScheme(int index)
{
if (getCurrentScheme() != index)
if (getCurrentScheme() != index)
setCurrentScheme(uint(index));
schemeValueUpdate();
}
@ -137,7 +138,7 @@ void CAttribWidget::changeCurrentScheme(int index)
void CAttribWidget::setCurrentSrc(int index)
{
NL3D::CPSInputType it;
it.InputType = (NL3D::CPSInputType::TInputType) index;
it.InputType = (NL3D::CPSInputType::TInputType) index;
if (it.InputType != getSchemeInput().InputType)
{
if (it.InputType == NL3D::CPSInputType::attrUserParam)
@ -154,7 +155,7 @@ void CAttribWidget::setUserIndex()
bool ok;
int i = QInputDialog::getInt(this, tr("Set user param"), tr(""), getSchemeInput().UserParamNum + 1, 1, 4, 1, &ok);
if (ok)
{
{
NL3D::CPSInputType it = getSchemeInput();
it.UserParamNum = i - 1;
setSchemeInput(it);
@ -172,7 +173,7 @@ void CAttribWidget::changeUseScheme(int index)
}
else
{
if (useScheme())
if (useScheme())
changeCurrentScheme(getCurrentScheme()); // update ui
else
changeCurrentScheme(0); // change scheme
@ -210,7 +211,7 @@ void CAttribWidget::schemeValueUpdate()
if (k == -1) // unknow scheme ...
{
_ui.schemeComboBox->setCurrentIndex(k);
k = 0;
k = 0;
}
if (k != _ui.schemeComboBox->currentIndex())
@ -231,7 +232,7 @@ void CAttribWidget::schemeValueUpdate()
_ui.srcLabel->setEnabled(false);
_ui.srcComboBox->setEnabled(false);
inputValueUpdate();
_ui.clampCheckBox->setEnabled(false);
_ui.inMultiplierWidget->setEnabled(false);
_ui.inputLabel->setEnabled(false);
@ -251,7 +252,7 @@ void CAttribWidget::schemeValueUpdate()
_ui.inMultiplierWidget->hide();
_ui.clampCheckBox->hide();
}
if (isClampingSupported())
_ui.clampCheckBox->setChecked(isSchemeClamped());
}
@ -267,7 +268,7 @@ void CAttribWidget::enableMemoryScheme(bool enabled)
}
CAttribFloatWidget::CAttribFloatWidget(QWidget *parent)
: CAttribWidgetT<float>(parent)
: CAttribWidgetT<float>(parent)
{
_ui.schemeComboBox->addItem(tr("value blender"));
_ui.schemeComboBox->addItem(tr("values gradient"));
@ -280,16 +281,16 @@ CAttribFloatWidget::~CAttribFloatWidget()
{
}
void CAttribFloatWidget::setRange(float minValue, float maxValue)
{
_MinRange = minValue;
_MaxRange = maxValue;
_ui.constRangeFloatWidget->setRange(_MinRange, _MaxRange);
void CAttribFloatWidget::setRange(float minValue, float maxValue)
{
_MinRange = minValue;
_MaxRange = maxValue;
_ui.constRangeFloatWidget->setRange(_MinRange, _MaxRange);
}
void CAttribFloatWidget::setWrapper(IPSWrapper<float> *wrapper)
{
nlassert(wrapper);
{
nlassert(wrapper);
_Wrapper = wrapper;
_ui.constRangeFloatWidget->setWrapper(_Wrapper);
}
@ -298,7 +299,7 @@ QDialog *CAttribFloatWidget::editScheme(void)
{
NL3D::CPSAttribMaker<float> *scheme = _SchemeWrapper->getScheme();
if (dynamic_cast<NL3D::CPSFloatBlender *>(scheme))
if (dynamic_cast<NL3D::CPSFloatBlender *>(scheme))
{
CFloatBlenderDialogClient *myInterface = new CFloatBlenderDialogClient();
myInterface->MinRange = _MinRange;
@ -307,7 +308,7 @@ QDialog *CAttribFloatWidget::editScheme(void)
CValueBlenderDialog *vb = new CValueBlenderDialog(myInterface, _Node, true, this);
return vb;
}
if (dynamic_cast<NL3D::CPSFloatGradient *>(scheme))
if (dynamic_cast<NL3D::CPSFloatGradient *>(scheme))
{
CFloatGradientWrapper *wrapper = new CFloatGradientWrapper;
wrapper->MinRange = _MinRange;
@ -317,19 +318,19 @@ QDialog *CAttribFloatWidget::editScheme(void)
wrapper->DefaultValue = 0.f;
return gd;
}
if (dynamic_cast<NL3D::CPSFloatMemory *>(scheme))
if (dynamic_cast<NL3D::CPSFloatMemory *>(scheme))
{
CAttribFloatWidget *adf = new CAttribFloatWidget();
adf->setRange(_MinRange, _MaxRange);
CValueFromEmitterDialogT<float> *vfe = new CValueFromEmitterDialogT<float>( (NL3D::CPSFloatMemory *)(scheme),
adf,
this);
adf,
this);
vfe->init();
adf->setWorkspaceNode(_Node);
adf->updateUi();
return vfe;
}
if (dynamic_cast<NL3D::CPSFloatBinOp *>(scheme))
if (dynamic_cast<NL3D::CPSFloatBinOp *>(scheme))
{
CAttribFloatWidget *ad[2] = { NULL, NULL};
for (uint k = 0; k <2; ++k)
@ -338,8 +339,8 @@ QDialog *CAttribFloatWidget::editScheme(void)
ad[k]->setRange(_MinRange, _MaxRange);
}
CBinOpDialogT<float> *bod = new CBinOpDialogT<float>( (NL3D::CPSFloatBinOp *)(scheme),
(CAttribWidgetT<float> **) ad,
this);
(CAttribWidgetT<float> **) ad,
this);
bod->init();
for (uint k = 0; k <2; ++k)
{
@ -348,7 +349,7 @@ QDialog *CAttribFloatWidget::editScheme(void)
}
return bod;
}
if (dynamic_cast<NL3D::CPSFloatCurve *>(scheme))
if (dynamic_cast<NL3D::CPSFloatCurve *>(scheme))
{
CurveEditDialog *curve = new CurveEditDialog(&(dynamic_cast<NL3D::CPSFloatCurve *>(scheme)->_F), _Node, this);
return curve;
@ -363,35 +364,35 @@ void CAttribFloatWidget::setCurrentScheme(uint index)
switch (index)
{
case 0:
scheme = new NL3D::CPSFloatBlender(_MinRange, _MaxRange);
break;
case 1:
{
static const float values[2] = { 0.1f, 1.f };
scheme = new NL3D::CPSFloatGradient(values, 2, 16, 1.f);
}
break;
case 2:
{
NL3D::CPSFloatCurve *curve = new NL3D::CPSFloatCurve;
curve->_F.setNumSamples(128);
curve->_F.addControlPoint(NL3D::CPSFloatCurveFunctor::CCtrlPoint(0, 0.5f));
curve->_F.addControlPoint(NL3D::CPSFloatCurveFunctor::CCtrlPoint(1, 0.5f));
scheme = curve;
}
break;
case 3:
scheme = new NL3D::CPSFloatMemory;
((NL3D::CPSAttribMakerMemory<float> *) scheme)->setScheme(new NL3D::CPSFloatBlender(_MinRange, _MaxRange));
break;
case 4 :
scheme = new NL3D::CPSFloatBinOp;
((NL3D::CPSFloatBinOp *) scheme)->setArg(0, new NL3D::CPSFloatBlender);
((NL3D::CPSFloatBinOp *) scheme)->setArg(1, new NL3D::CPSFloatBlender);
break;
default:
break;
case 0:
scheme = new NL3D::CPSFloatBlender(_MinRange, _MaxRange);
break;
case 1:
{
static const float values[2] = { 0.1f, 1.f };
scheme = new NL3D::CPSFloatGradient(values, 2, 16, 1.f);
}
break;
case 2:
{
NL3D::CPSFloatCurve *curve = new NL3D::CPSFloatCurve;
curve->_F.setNumSamples(128);
curve->_F.addControlPoint(NL3D::CPSFloatCurveFunctor::CCtrlPoint(0, 0.5f));
curve->_F.addControlPoint(NL3D::CPSFloatCurveFunctor::CCtrlPoint(1, 0.5f));
scheme = curve;
}
break;
case 3:
scheme = new NL3D::CPSFloatMemory;
((NL3D::CPSAttribMakerMemory<float> *) scheme)->setScheme(new NL3D::CPSFloatBlender(_MinRange, _MaxRange));
break;
case 4 :
scheme = new NL3D::CPSFloatBinOp;
((NL3D::CPSFloatBinOp *) scheme)->setArg(0, new NL3D::CPSFloatBlender);
((NL3D::CPSFloatBinOp *) scheme)->setArg(1, new NL3D::CPSFloatBlender);
break;
default:
break;
}
if (scheme)
@ -404,15 +405,15 @@ sint CAttribFloatWidget::getCurrentScheme(void) const
{
const NL3D::CPSAttribMaker<float> *scheme = _SchemeWrapper->getScheme();
if (dynamic_cast<const NL3D::CPSFloatBlender *>(scheme))
if (dynamic_cast<const NL3D::CPSFloatBlender *>(scheme))
return 0;
if (dynamic_cast<const NL3D::CPSFloatGradient *>(scheme))
if (dynamic_cast<const NL3D::CPSFloatGradient *>(scheme))
return 1;
if (dynamic_cast<const NL3D::CPSFloatCurve *>(scheme))
if (dynamic_cast<const NL3D::CPSFloatCurve *>(scheme))
return 2;
if (dynamic_cast<const NL3D::CPSFloatMemory *>(scheme))
if (dynamic_cast<const NL3D::CPSFloatMemory *>(scheme))
return 3;
if (dynamic_cast<const NL3D::CPSFloatBinOp *>(scheme))
if (dynamic_cast<const NL3D::CPSFloatBinOp *>(scheme))
return 4;
return -1;
@ -429,7 +430,7 @@ void CAttribFloatWidget::cstValueUpdate()
}
CAttribUIntWidget::CAttribUIntWidget(QWidget *parent)
: CAttribWidgetT<uint32>(parent)
: CAttribWidgetT<uint32>(parent)
{
_ui.schemeComboBox->addItem(tr("value blender"));
_ui.schemeComboBox->addItem(tr("values gradient"));
@ -441,25 +442,25 @@ CAttribUIntWidget::~CAttribUIntWidget()
{
}
void CAttribUIntWidget::setRange(uint32 minValue, uint32 maxValue)
{
_MinRange = minValue;
_MaxRange = maxValue;
_ui.constRangeUIntWidget->setRange(_MinRange, _MaxRange);
void CAttribUIntWidget::setRange(uint32 minValue, uint32 maxValue)
{
_MinRange = minValue;
_MaxRange = maxValue;
_ui.constRangeUIntWidget->setRange(_MinRange, _MaxRange);
}
void CAttribUIntWidget::setWrapper(IPSWrapper<uint32> *wrapper)
{
nlassert(wrapper);
{
nlassert(wrapper);
_Wrapper = wrapper;
_ui.constRangeUIntWidget->setWrapper(_Wrapper);
}
QDialog *CAttribUIntWidget::editScheme(void)
{
const NL3D::CPSAttribMaker<uint32> *scheme = _SchemeWrapper->getScheme();
const NL3D::CPSAttribMaker<uint32> *scheme = _SchemeWrapper->getScheme();
if (dynamic_cast<const NL3D::CPSUIntBlender *>(scheme))
if (dynamic_cast<const NL3D::CPSUIntBlender *>(scheme))
{
CUIntBlenderDialogClient *myInterface = new CUIntBlenderDialogClient();
myInterface->MinRange = _MinRange;
@ -468,7 +469,7 @@ QDialog *CAttribUIntWidget::editScheme(void)
CValueBlenderDialog *vb = new CValueBlenderDialog(myInterface, _Node, true, this);
return vb;
}
if (dynamic_cast<const NL3D::CPSUIntGradient *>(scheme))
if (dynamic_cast<const NL3D::CPSUIntGradient *>(scheme))
{
CUIntGradientWrapper *wrapper = new CUIntGradientWrapper;
wrapper->MinRange = _MinRange;
@ -479,19 +480,19 @@ QDialog *CAttribUIntWidget::editScheme(void)
return gd;
}
if (dynamic_cast<const NL3D::CPSUIntMemory *>(scheme))
if (dynamic_cast<const NL3D::CPSUIntMemory *>(scheme))
{
CAttribUIntWidget *adu = new CAttribUIntWidget();
adu->setRange(_MinRange, _MaxRange);
CValueFromEmitterDialogT<uint32> *vfe = new CValueFromEmitterDialogT<uint32>( (NL3D::CPSUIntMemory *)(scheme),
adu,
this);
vfe->init();
adu->setWorkspaceNode(_Node);
adu->updateUi();
return vfe;
adu,
this);
vfe->init();
adu->setWorkspaceNode(_Node);
adu->updateUi();
return vfe;
}
if (dynamic_cast<const NL3D::CPSUIntBinOp *>(scheme))
if (dynamic_cast<const NL3D::CPSUIntBinOp *>(scheme))
{
CAttribUIntWidget *ad[2] = { NULL, NULL};
for (uint k = 0; k <2; ++k)
@ -500,8 +501,8 @@ QDialog *CAttribUIntWidget::editScheme(void)
ad[k]->setRange(_MinRange, _MaxRange);
}
CBinOpDialogT<uint32> *bod = new CBinOpDialogT<uint32>( (NL3D::CPSUIntBinOp *)(scheme),
(CAttribWidgetT<uint32> **) ad,
this);
(CAttribWidgetT<uint32> **) ad,
this);
bod->init();
for (uint k = 0; k <2; ++k)
{
@ -520,23 +521,23 @@ void CAttribUIntWidget::setCurrentScheme(uint index)
switch (index)
{
case 0 :
scheme = new NL3D::CPSUIntBlender(_MinRange, _MaxRange);
break;
case 1 :
scheme = new NL3D::CPSUIntGradient;
break;
case 2 :
scheme = new NL3D::CPSUIntMemory;
((NL3D::CPSAttribMakerMemory<uint32> *) scheme)->setScheme(new NL3D::CPSUIntBlender(_MinRange, _MaxRange) );
break;
case 3 :
scheme = new NL3D::CPSUIntBinOp;
((NL3D::CPSUIntBinOp *) scheme)->setArg(0, new NL3D::CPSUIntBlender);
((NL3D::CPSUIntBinOp *) scheme)->setArg(1, new NL3D::CPSUIntBlender);
break;
default:
break;
case 0 :
scheme = new NL3D::CPSUIntBlender(_MinRange, _MaxRange);
break;
case 1 :
scheme = new NL3D::CPSUIntGradient;
break;
case 2 :
scheme = new NL3D::CPSUIntMemory;
((NL3D::CPSAttribMakerMemory<uint32> *) scheme)->setScheme(new NL3D::CPSUIntBlender(_MinRange, _MaxRange) );
break;
case 3 :
scheme = new NL3D::CPSUIntBinOp;
((NL3D::CPSUIntBinOp *) scheme)->setArg(0, new NL3D::CPSUIntBlender);
((NL3D::CPSUIntBinOp *) scheme)->setArg(1, new NL3D::CPSUIntBlender);
break;
default:
break;
}
if (scheme)
{
@ -566,7 +567,7 @@ void CAttribUIntWidget::cstValueUpdate()
}
CAttribIntWidget::CAttribIntWidget(QWidget *parent)
: CAttribWidgetT<sint32>(parent)
: CAttribWidgetT<sint32>(parent)
{
_ui.schemeComboBox->addItem(tr("value exact blender"));
_ui.schemeComboBox->addItem(tr("values gradient"));
@ -578,16 +579,16 @@ CAttribIntWidget::~CAttribIntWidget()
{
}
void CAttribIntWidget::setRange(sint32 minValue, sint32 maxValue)
{
_MinRange = minValue;
_MaxRange = maxValue;
_ui.constRangeIntWidget->setRange(_MinRange, _MaxRange);
void CAttribIntWidget::setRange(sint32 minValue, sint32 maxValue)
{
_MinRange = minValue;
_MaxRange = maxValue;
_ui.constRangeIntWidget->setRange(_MinRange, _MaxRange);
}
void CAttribIntWidget::setWrapper(IPSWrapper<sint32> *wrapper)
{
nlassert(wrapper);
{
nlassert(wrapper);
_Wrapper = wrapper;
_ui.constRangeIntWidget->setWrapper(_Wrapper);
}
@ -596,8 +597,8 @@ QDialog *CAttribIntWidget::editScheme(void)
{
const NL3D::CPSAttribMaker<sint32> *scheme = _SchemeWrapper->getScheme();
if (dynamic_cast<const NL3D::CPSIntBlender *>(scheme))
{
if (dynamic_cast<const NL3D::CPSIntBlender *>(scheme))
{
CIntBlenderDialogClient *myInterface = new CIntBlenderDialogClient();
myInterface->MinRange = _MinRange;
myInterface->MaxRange = _MaxRange;
@ -605,7 +606,7 @@ QDialog *CAttribIntWidget::editScheme(void)
CValueBlenderDialog *vb = new CValueBlenderDialog(myInterface, _Node, true, this);
return vb;
}
if (dynamic_cast<const NL3D::CPSIntGradient *>(scheme))
if (dynamic_cast<const NL3D::CPSIntGradient *>(scheme))
{
CIntGradientWrapper *wrapper = new CIntGradientWrapper;
wrapper->MinRange = _MinRange;
@ -615,18 +616,18 @@ QDialog *CAttribIntWidget::editScheme(void)
wrapper->DefaultValue = 0;
return gd;
}
if (dynamic_cast<const NL3D::CPSIntMemory *>(scheme))
if (dynamic_cast<const NL3D::CPSIntMemory *>(scheme))
{
CAttribIntWidget *adi = new CAttribIntWidget();
adi->setRange(_MinRange, _MaxRange);
CValueFromEmitterDialogT<sint32> *vfe = new CValueFromEmitterDialogT<sint32>((NL3D::CPSIntMemory *) _SchemeWrapper->getScheme(),
adi, this);
adi, this);
vfe->init();
adi->setWorkspaceNode(_Node);
adi->updateUi();
return vfe;
}
if (dynamic_cast<const NL3D::CPSIntBinOp *>(scheme))
if (dynamic_cast<const NL3D::CPSIntBinOp *>(scheme))
{
CAttribIntWidget *ad[2] = { NULL, NULL};
for (uint k = 0; k <2; ++k)
@ -635,8 +636,8 @@ QDialog *CAttribIntWidget::editScheme(void)
ad[k]->setRange(_MinRange, _MaxRange);
}
CBinOpDialogT<sint32> *bod = new CBinOpDialogT<sint32>( (NL3D::CPSIntBinOp *)(scheme),
(CAttribWidgetT<sint32> **) ad,
this);
(CAttribWidgetT<sint32> **) ad,
this);
bod->init();
for (uint k = 0; k <2; ++k)
{
@ -655,23 +656,23 @@ void CAttribIntWidget::setCurrentScheme(uint index)
switch (index)
{
case 0 :
scheme = new NL3D::CPSIntBlender;
break;
case 1 :
scheme = new NL3D::CPSIntGradient;
break;
case 2 :
scheme = new NL3D::CPSIntMemory;
((NL3D::CPSAttribMakerMemory<sint32> *) scheme)->setScheme(new NL3D::CPSIntBlender(_MinRange, _MaxRange));
break;
case 3 :
scheme = new NL3D::CPSIntBinOp;
((NL3D::CPSIntBinOp *) scheme)->setArg(0, new NL3D::CPSIntBlender);
((NL3D::CPSIntBinOp *) scheme)->setArg(1, new NL3D::CPSIntBlender);
break;
default:
break;
case 0 :
scheme = new NL3D::CPSIntBlender;
break;
case 1 :
scheme = new NL3D::CPSIntGradient;
break;
case 2 :
scheme = new NL3D::CPSIntMemory;
((NL3D::CPSAttribMakerMemory<sint32> *) scheme)->setScheme(new NL3D::CPSIntBlender(_MinRange, _MaxRange));
break;
case 3 :
scheme = new NL3D::CPSIntBinOp;
((NL3D::CPSIntBinOp *) scheme)->setArg(0, new NL3D::CPSIntBlender);
((NL3D::CPSIntBinOp *) scheme)->setArg(1, new NL3D::CPSIntBlender);
break;
default:
break;
}
if (scheme)
{
@ -701,7 +702,7 @@ void CAttribIntWidget::cstValueUpdate()
}
CAttribRGBAWidget::CAttribRGBAWidget(QWidget *parent)
: CAttribWidgetT<NLMISC::CRGBA>(parent)
: CAttribWidgetT<NLMISC::CRGBA>(parent)
{
_ui.schemeComboBox->addItem(tr("color sampled blender"));
_ui.schemeComboBox->addItem(tr("color gradient"));
@ -715,24 +716,24 @@ CAttribRGBAWidget::~CAttribRGBAWidget()
}
void CAttribRGBAWidget::setWrapper(IPSWrapper<NLMISC::CRGBA> *wrapper)
{
nlassert(wrapper);
{
nlassert(wrapper);
_Wrapper = wrapper;
_ui.constRGBAWidget->setWrapper(_Wrapper);
}
QDialog *CAttribRGBAWidget::editScheme(void)
{
const NL3D::CPSAttribMaker<NLMISC::CRGBA> *scheme = _SchemeWrapper->getScheme();
const NL3D::CPSAttribMaker<NLMISC::CRGBA> *scheme = _SchemeWrapper->getScheme();
if (dynamic_cast<const NL3D::CPSColorBlender *>(scheme))
if (dynamic_cast<const NL3D::CPSColorBlender *>(scheme))
{
CRGBABlenderDialogClient *myInterface = new CRGBABlenderDialogClient();
myInterface->SchemeFunc = & ((NL3D::CPSValueBlenderSample<NLMISC::CRGBA, 64> *) scheme)->_F;
CValueBlenderDialog *vb = new CValueBlenderDialog(myInterface, _Node, true, this);
return vb;
}
if (dynamic_cast<const NL3D::CPSColorGradient *>(scheme))
if (dynamic_cast<const NL3D::CPSColorGradient *>(scheme))
{
CColorGradientWrapper *wrapper = new CColorGradientWrapper;
wrapper->Scheme = &(((NL3D::CPSColorGradient *) (_SchemeWrapper->getScheme()) )->_F);
@ -740,22 +741,22 @@ QDialog *CAttribRGBAWidget::editScheme(void)
wrapper->DefaultValue = NLMISC::CRGBA::White;
return gd;
}
if (dynamic_cast<const NL3D::CPSColorBlenderExact *>(scheme))
if (dynamic_cast<const NL3D::CPSColorBlenderExact *>(scheme))
{
return NULL;
}
if (dynamic_cast<const NL3D::CPSColorMemory *>(scheme))
if (dynamic_cast<const NL3D::CPSColorMemory *>(scheme))
{
CAttribRGBAWidget *ad = new CAttribRGBAWidget();
CValueFromEmitterDialogT<NLMISC::CRGBA> *vfe = new CValueFromEmitterDialogT<NLMISC::CRGBA>( (NL3D::CPSColorMemory *)(scheme),
ad,
this);
ad,
this);
vfe->init();
ad->setWorkspaceNode(_Node);
ad->updateUi();
return vfe;
}
if (dynamic_cast<const NL3D::CPSColorBinOp *>(scheme))
if (dynamic_cast<const NL3D::CPSColorBinOp *>(scheme))
{
CAttribRGBAWidget *ad[2] = { NULL, NULL};
for (uint k = 0; k <2; ++k)
@ -763,8 +764,8 @@ QDialog *CAttribRGBAWidget::editScheme(void)
ad[k] = new CAttribRGBAWidget();
}
CBinOpDialogT<NLMISC::CRGBA> *bod = new CBinOpDialogT<NLMISC::CRGBA>( (NL3D::CPSColorBinOp *)(scheme),
(CAttribWidgetT<NLMISC::CRGBA> **) ad,
this);
(CAttribWidgetT<NLMISC::CRGBA> **) ad,
this);
bod->init();
for (uint k = 0; k <2; ++k)
{
@ -783,26 +784,26 @@ void CAttribRGBAWidget::setCurrentScheme(uint index)
switch (index)
{
case 0 :
scheme = new NL3D::CPSColorBlender;
break;
case 1 :
scheme = new NL3D::CPSColorGradient(NL3D::CPSColorGradient::_DefaultGradient, 2, 16, 1.f);
break;
case 2 :
scheme = new NL3D::CPSColorBlenderExact;
break;
case 3 :
scheme = new NL3D::CPSColorMemory;
((NL3D::CPSAttribMakerMemory<NLMISC::CRGBA> *) scheme)->setScheme(new NL3D::CPSColorBlender);
break;
case 4 :
scheme = new NL3D::CPSColorBinOp;
((NL3D::CPSColorBinOp *) scheme)->setArg(0, new NL3D::CPSColorBlender);
((NL3D::CPSColorBinOp *) scheme)->setArg(1, new NL3D::CPSColorBlender);
break;
default:
break;
case 0 :
scheme = new NL3D::CPSColorBlender;
break;
case 1 :
scheme = new NL3D::CPSColorGradient(NL3D::CPSColorGradient::_DefaultGradient, 2, 16, 1.f);
break;
case 2 :
scheme = new NL3D::CPSColorBlenderExact;
break;
case 3 :
scheme = new NL3D::CPSColorMemory;
((NL3D::CPSAttribMakerMemory<NLMISC::CRGBA> *) scheme)->setScheme(new NL3D::CPSColorBlender);
break;
case 4 :
scheme = new NL3D::CPSColorBinOp;
((NL3D::CPSColorBinOp *) scheme)->setArg(0, new NL3D::CPSColorBlender);
((NL3D::CPSColorBinOp *) scheme)->setArg(1, new NL3D::CPSColorBlender);
break;
default:
break;
}
if (scheme)
{
@ -833,7 +834,7 @@ void CAttribRGBAWidget::cstValueUpdate()
}
CAttribPlaneBasisWidget::CAttribPlaneBasisWidget(QWidget *parent)
: CAttribWidgetT<NL3D::CPlaneBasis>(parent)
: CAttribWidgetT<NL3D::CPlaneBasis>(parent)
{
_ui.schemeComboBox->addItem(tr("basis gradient"));
_ui.schemeComboBox->addItem(tr("follow path"));
@ -847,8 +848,8 @@ CAttribPlaneBasisWidget::~CAttribPlaneBasisWidget()
}
void CAttribPlaneBasisWidget::setWrapper(IPSWrapper<NL3D::CPlaneBasis> *wrapper)
{
nlassert(wrapper);
{
nlassert(wrapper);
_Wrapper = wrapper;
_ui.constAttribPlaneWidget->setWrapper(_Wrapper);
}
@ -856,7 +857,7 @@ void CAttribPlaneBasisWidget::setWrapper(IPSWrapper<NL3D::CPlaneBasis> *wrapper)
QDialog *CAttribPlaneBasisWidget::editScheme(void)
{
NL3D::CPSAttribMaker<NL3D::CPlaneBasis> *scheme = _SchemeWrapper->getScheme();
if (dynamic_cast<NL3D::CPSPlaneBasisGradient *>(scheme))
if (dynamic_cast<NL3D::CPSPlaneBasisGradient *>(scheme))
{
CPlaneBasisGradientWrapper *wrapper = new CPlaneBasisGradientWrapper;
wrapper->Scheme = &(((NL3D::CPSPlaneBasisGradient *) (_SchemeWrapper->getScheme()) )->_F);
@ -864,23 +865,23 @@ QDialog *CAttribPlaneBasisWidget::editScheme(void)
wrapper->DefaultValue = NL3D::CPlaneBasis(NLMISC::CVector::K);
return gd;
}
if (dynamic_cast<NL3D::CPSPlaneBasisFollowSpeed *>(scheme))
if (dynamic_cast<NL3D::CPSPlaneBasisFollowSpeed *>(scheme))
{
CFollowPathDialog *dialog = new CFollowPathDialog(dynamic_cast<NL3D::CPSPlaneBasisFollowSpeed *>(scheme), _Node, this);
return dialog;
}
if (dynamic_cast<NL3D::CPSPlaneBasisMemory *>(scheme))
if (dynamic_cast<NL3D::CPSPlaneBasisMemory *>(scheme))
{
CAttribPlaneBasisWidget *ad = new CAttribPlaneBasisWidget();
CValueFromEmitterDialogT<NL3D::CPlaneBasis> *vfe = new CValueFromEmitterDialogT<NL3D::CPlaneBasis>
( (NL3D::CPSPlaneBasisMemory *)(scheme),
ad, this);
( (NL3D::CPSPlaneBasisMemory *)(scheme),
ad, this);
vfe->init();
ad->setWorkspaceNode(_Node);
ad->updateUi();
return vfe;
}
if (dynamic_cast<NL3D::CPSPlaneBasisBinOp *>(scheme))
if (dynamic_cast<NL3D::CPSPlaneBasisBinOp *>(scheme))
{
CAttribPlaneBasisWidget *ad[2] = { NULL, NULL};
for (uint k = 0; k <2; ++k)
@ -888,8 +889,8 @@ QDialog *CAttribPlaneBasisWidget::editScheme(void)
ad[k] = new CAttribPlaneBasisWidget();
}
CBinOpDialogT<NL3D::CPlaneBasis> *bod = new CBinOpDialogT<NL3D::CPlaneBasis>( (NL3D::CPSPlaneBasisBinOp *)(scheme),
(CAttribWidgetT<NL3D::CPlaneBasis> **) ad,
this);
(CAttribWidgetT<NL3D::CPlaneBasis> **) ad,
this);
bod->init();
for (uint k = 0; k <2; ++k)
{
@ -898,7 +899,7 @@ QDialog *CAttribPlaneBasisWidget::editScheme(void)
}
return bod;
}
if (dynamic_cast<NL3D::CPSBasisSpinner *>(scheme))
if (dynamic_cast<NL3D::CPSBasisSpinner *>(scheme))
{
CSpinnerDialog *dialog = new CSpinnerDialog(dynamic_cast<NL3D::CPSBasisSpinner *>(scheme), _Node, this);
return dialog;
@ -912,34 +913,34 @@ void CAttribPlaneBasisWidget::setCurrentScheme(uint index)
NL3D::CPSAttribMaker<NL3D::CPlaneBasis> *scheme = NULL;
switch (index)
{
case 0:
scheme = new NL3D::CPSPlaneBasisGradient;
break;
case 1:
scheme = new NL3D::CPSPlaneBasisFollowSpeed;
break;
case 2:
scheme = new NL3D::CPSBasisSpinner;
static_cast<NL3D::CPSBasisSpinner *>(scheme)->_F.setNumSamples(16);
break;
case 3:
scheme = new NL3D::CPSPlaneBasisMemory;
((NL3D::CPSAttribMakerMemory<NL3D::CPlaneBasis> *) scheme)->setScheme(new NL3D::CPSPlaneBasisFollowSpeed);
if (_Node)
{
_Node->setModified(true);
}
break;
case 4 :
scheme = new NL3D::CPSPlaneBasisBinOp;
((NL3D::CPSPlaneBasisBinOp *) scheme)->setArg(0, new NL3D::CPSPlaneBasisFollowSpeed);
((NL3D::CPSPlaneBasisBinOp *) scheme)->setArg(1, new NL3D::CPSPlaneBasisFollowSpeed);
break;
default:
break;
}
{
case 0:
scheme = new NL3D::CPSPlaneBasisGradient;
break;
case 1:
scheme = new NL3D::CPSPlaneBasisFollowSpeed;
break;
case 2:
scheme = new NL3D::CPSBasisSpinner;
static_cast<NL3D::CPSBasisSpinner *>(scheme)->_F.setNumSamples(16);
break;
case 3:
scheme = new NL3D::CPSPlaneBasisMemory;
((NL3D::CPSAttribMakerMemory<NL3D::CPlaneBasis> *) scheme)->setScheme(new NL3D::CPSPlaneBasisFollowSpeed);
if (_Node)
{
_Node->setModified(true);
}
break;
case 4 :
scheme = new NL3D::CPSPlaneBasisBinOp;
((NL3D::CPSPlaneBasisBinOp *) scheme)->setArg(0, new NL3D::CPSPlaneBasisFollowSpeed);
((NL3D::CPSPlaneBasisBinOp *) scheme)->setArg(1, new NL3D::CPSPlaneBasisFollowSpeed);
break;
default:
break;
}
if (scheme)
{
_SchemeWrapper->setSchemeAndUpdateModifiedFlag(scheme);
@ -955,7 +956,7 @@ sint CAttribPlaneBasisWidget::getCurrentScheme(void) const
if (dynamic_cast<const NL3D::CPSBasisSpinner *>(scheme)) return 2;
if (dynamic_cast<const NL3D::CPSPlaneBasisMemory *>(scheme)) return 3;
if (dynamic_cast<const NL3D::CPSPlaneBasisBinOp *>(scheme)) return 4;
return -1;
}

@ -38,15 +38,16 @@
#include "ps_wrapper.h"
#include "particle_node.h"
namespace NLQT {
namespace NLQT
{
/**
@class CAttribWidget
@brief Base attrib maker edition dialog.
*/
class CAttribWidget: public QGroupBox
{
Q_OBJECT
Q_OBJECT
public:
CAttribWidget(QWidget *parent = 0);
~CAttribWidget();
@ -59,10 +60,10 @@ public:
/// Сonnects all the slots with signals
void init();
/// Sets the pointer CWorkspaceNode* in the wrappers.
virtual void setWorkspaceNode(CWorkspaceNode *node) = 0;
/// Private usage (not private because accessed by a static function) : return the nbCycles parameter of the scheme (e.g the input multiplier).
virtual float getSchemeNbCycles(void) const = 0;
@ -70,21 +71,36 @@ public:
virtual void setSchemeNbCycles(float nbCycles) = 0;
/// Enable the srcInput
void enableSrcInput(bool enable = true) { _SrcInputEnabled = enable; }
bool isSrcInputEnabled() const { return _SrcInputEnabled; }
void enableSrcInput(bool enable = true)
{
_SrcInputEnabled = enable;
}
bool isSrcInputEnabled() const
{
return _SrcInputEnabled;
}
/// Disable the possibility to choose a scheme that has memory. (for example, a scheme for lifetime of a located has no sense
/// because located have already some memory to store it)
void enableMemoryScheme(bool enabled = true);
/// Tells wether memory schemes are enables
/// @see enableMemoryScheme()
bool isMemorySchemeEnabled() const { return !_DisableMemoryScheme; }
bool isMemorySchemeEnabled() const
{
return !_DisableMemoryScheme;
}
/// Enable Nb Cycle tuning
void enableNbCycles(bool enabled) { _NbCycleEnabled = enabled; }
bool isNbCycleEnabled() const { return _NbCycleEnabled; }
void enableNbCycles(bool enabled)
{
_NbCycleEnabled = enabled;
}
bool isNbCycleEnabled() const
{
return _NbCycleEnabled;
}
private Q_SLOTS:
virtual void clickedEdit();
@ -93,7 +109,7 @@ private Q_SLOTS:
virtual void setCurrentSrc(int index);
virtual void setUserIndex();
virtual void changeUseScheme(int index);
protected:
/// change the dialog for constant values
@ -128,10 +144,10 @@ protected:
/// tells wether the scheme supports custom input
virtual bool hasSchemeCustomInput(void) const = 0;
/// retrieve the scheme input id
virtual NL3D::CPSInputType getSchemeInput(void) const = 0;
/// set the scheme input id
virtual void setSchemeInput(const NL3D::CPSInputType &input) = 0;
@ -159,15 +175,21 @@ protected:
/// wrapper to tune the number of cycles
struct CNbCyclesWrapper : public IPSWrapperFloat
{
CAttribWidget *widget;
float get(void) const { return widget->getSchemeNbCycles(); }
void set(const float &v) { widget->setSchemeNbCycles(v); }
CAttribWidget *widget;
float get(void) const
{
return widget->getSchemeNbCycles();
}
void set(const float &v)
{
widget->setSchemeNbCycles(v);
}
} _NbCyclesWrapper;
CWorkspaceNode *_Node;
QDialog *_SchemeWidget;
Ui::CAttribWidget _ui;
}; /* class CAttribWidget */
@ -179,45 +201,78 @@ template <typename T> class CAttribWidgetT : public CAttribWidget
{
public:
CAttribWidgetT(QWidget *parent = 0): CAttribWidget(parent),
_Wrapper(NULL),
_SchemeWrapper(NULL)
_Wrapper(NULL),
_SchemeWrapper(NULL)
{
}
virtual void setWrapper(IPSWrapper<T> *wrapper) = 0;
void setSchemeWrapper(IPSSchemeWrapper<T> *schemeWrapper) { nlassert(schemeWrapper); _SchemeWrapper = schemeWrapper; }
void setSchemeWrapper(IPSSchemeWrapper<T> *schemeWrapper)
{
nlassert(schemeWrapper);
_SchemeWrapper = schemeWrapper;
}
// Inherited from CAttribWidget
virtual QDialog *editScheme(void) = 0;
virtual void setCurrentScheme(uint index) = 0;
virtual sint getCurrentScheme(void) const = 0;
virtual void resetCstValue(void)
{
_Wrapper->setAndUpdateModifiedFlag(_Wrapper->get()); // reuse current color
virtual void resetCstValue(void)
{
_Wrapper->setAndUpdateModifiedFlag(_Wrapper->get()); // reuse current color
}
virtual bool hasSchemeCustomInput(void) const { return _SchemeWrapper->getScheme()->hasCustomInput(); }
virtual NL3D::CPSInputType getSchemeInput(void) const { return _SchemeWrapper->getScheme()->getInput(); }
virtual void setSchemeInput(const NL3D::CPSInputType &input) { _SchemeWrapper->getScheme()->setInput(input); }
virtual bool hasSchemeCustomInput(void) const
{
return _SchemeWrapper->getScheme()->hasCustomInput();
}
virtual NL3D::CPSInputType getSchemeInput(void) const
{
return _SchemeWrapper->getScheme()->getInput();
}
virtual void setSchemeInput(const NL3D::CPSInputType &input)
{
_SchemeWrapper->getScheme()->setInput(input);
}
virtual void setWorkspaceNode(CWorkspaceNode *node)
{
_Node = node; if (_Wrapper != NULL) _Wrapper->OwnerNode = _Node; if (_SchemeWrapper != NULL) _SchemeWrapper->OwnerNode = _Node;
virtual void setWorkspaceNode(CWorkspaceNode *node)
{
_Node = node;
if (_Wrapper != NULL) _Wrapper->OwnerNode = _Node;
if (_SchemeWrapper != NULL) _SchemeWrapper->OwnerNode = _Node;
};
virtual float getSchemeNbCycles(void) const { return _SchemeWrapper->getScheme()->getNbCycles(); }
virtual void setSchemeNbCycles(float nbCycles) { _SchemeWrapper->getScheme()->setNbCycles(nbCycles); }
virtual bool isSchemeClamped(void) const { return _SchemeWrapper->getScheme()->getClamping(); }
virtual void clampScheme(bool clamped = true) { _SchemeWrapper->getScheme()->setClamping(clamped); }
virtual bool isClampingSupported(void) const { return _SchemeWrapper->getScheme()->isClampingSupported(); };
virtual NL3D::CPSAttribMakerBase *getCurrentSchemePtr(void) const { return _SchemeWrapper->getScheme(); }
virtual void setCurrentSchemePtr(NL3D::CPSAttribMakerBase *s)
{
virtual float getSchemeNbCycles(void) const
{
return _SchemeWrapper->getScheme()->getNbCycles();
}
virtual void setSchemeNbCycles(float nbCycles)
{
_SchemeWrapper->getScheme()->setNbCycles(nbCycles);
}
virtual bool isSchemeClamped(void) const
{
return _SchemeWrapper->getScheme()->getClamping();
}
virtual void clampScheme(bool clamped = true)
{
_SchemeWrapper->getScheme()->setClamping(clamped);
}
virtual bool isClampingSupported(void) const
{
return _SchemeWrapper->getScheme()->isClampingSupported();
};
virtual NL3D::CPSAttribMakerBase *getCurrentSchemePtr(void) const
{
return _SchemeWrapper->getScheme();
}
virtual void setCurrentSchemePtr(NL3D::CPSAttribMakerBase *s)
{
_SchemeWrapper->setSchemeAndUpdateModifiedFlag(NLMISC::safe_cast<NL3D::CPSAttribMaker<T> *>(s));
}
virtual void cstValueUpdate() = 0;
protected:
virtual bool useScheme(void) const
{
@ -231,53 +286,53 @@ public:
IPSSchemeWrapper<T> *_SchemeWrapper;
};
/**
/**
@class CAttribFloatWidget
@brief An attribute editor specialized for float values
*/
class CAttribFloatWidget: public CAttribWidgetT<float>
{
Q_OBJECT
Q_OBJECT
public:
CAttribFloatWidget(QWidget *parent = 0);
~CAttribFloatWidget();
void setRange(float minValue = 0, float maxValue = 10);
void setWrapper(IPSWrapper<float> *wrapper);
// inherited from CAttribWidget
virtual QDialog *editScheme(void);
virtual void setCurrentScheme(uint index);
virtual sint getCurrentScheme(void) const;
virtual void cstValueUpdate();
private:
float _MinRange, _MaxRange;
}; /* class CAttribFloatWidget */
/**
/**
@class CAttribUIntWidget
@brief An attribute editor specialized for unsigned int values
*/
class CAttribUIntWidget: public CAttribWidgetT<uint32>
{
Q_OBJECT
Q_OBJECT
public:
CAttribUIntWidget(QWidget *parent = 0);
~CAttribUIntWidget();
void setRange(uint32 minValue = 0, uint32 maxValue = 10);
void setWrapper(IPSWrapper<uint32> *wrapper);
// inherited from CAttribWidget
virtual QDialog *editScheme(void);
virtual void setCurrentScheme(uint index);
virtual sint getCurrentScheme(void) const;
virtual void cstValueUpdate();
private:
uint32 _MinRange, _MaxRange;
@ -289,12 +344,12 @@ private:
*/
class CAttribIntWidget: public CAttribWidgetT<sint32>
{
Q_OBJECT
Q_OBJECT
public:
CAttribIntWidget(QWidget *parent = 0);
~CAttribIntWidget();
void setRange(sint32 minValue = 0, sint32 maxValue = 10);
void setWrapper(IPSWrapper<sint32> *wrapper);
@ -303,7 +358,7 @@ public:
virtual void setCurrentScheme(uint index);
virtual sint getCurrentScheme(void) const;
virtual void cstValueUpdate();
private:
sint32 _MinRange, _MaxRange;
@ -315,20 +370,20 @@ private:
*/
class CAttribRGBAWidget: public CAttribWidgetT<NLMISC::CRGBA>
{
Q_OBJECT
Q_OBJECT
public:
CAttribRGBAWidget(QWidget *parent = 0);
~CAttribRGBAWidget();
void setWrapper(IPSWrapper<NLMISC::CRGBA> *wrapper);
// inherited from CAttribWidget
virtual QDialog *editScheme(void);
virtual void setCurrentScheme(uint index);
virtual sint getCurrentScheme(void) const;
virtual void cstValueUpdate();
private:
}; /* class CAttribRGBAWidget */
@ -339,14 +394,14 @@ private:
*/
class CAttribPlaneBasisWidget: public CAttribWidgetT<NL3D::CPlaneBasis>
{
Q_OBJECT
Q_OBJECT
public:
CAttribPlaneBasisWidget(QWidget *parent = 0);
~CAttribPlaneBasisWidget();
void setWrapper(IPSWrapper<NL3D::CPlaneBasis> *wrapper);
// inherited from CAttribWidget
virtual QDialog *editScheme(void);
virtual void setCurrentScheme(uint index);

@ -28,10 +28,11 @@
// Project includes
namespace NLQT {
namespace NLQT
{
CAutoLODDialog::CAutoLODDialog(CWorkspaceNode *ownerNode, NL3D::CParticleSystem *ps, QWidget *parent)
: QDialog(parent), _Node(ownerNode), _PS(ps)
: QDialog(parent), _Node(ownerNode), _PS(ps)
{
_ui.setupUi(this);
@ -41,14 +42,14 @@ CAutoLODDialog::CAutoLODDialog(CWorkspaceNode *ownerNode, NL3D::CParticleSystem
_MaxDistLODBiasWrapper.PS = _PS;
_DistRatioWrapper.OwnerNode = _Node;
_MaxDistLODBiasWrapper.OwnerNode = _Node;
// Edit the distance at which LOD starts
_ui.startPercentDistWidget->setRange(0.f, 0.99f);
_ui.startPercentDistWidget->enableUpperBound(1.f, true);
_ui.startPercentDistWidget->enableLowerBound(0.f, false);
_ui.startPercentDistWidget->setWrapper(&_DistRatioWrapper);
_ui.startPercentDistWidget->updateUi();
// For non-shared systems only : Set the LOD bias at the max distance, so that some particles are still displayed
_ui.maxDistBiasWidget->setRange(0.f, 1.0f);
_ui.maxDistBiasWidget->enableUpperBound(1.f, false);

@ -32,16 +32,17 @@
// Project includes
#include "ps_wrapper.h"
namespace NLQT {
namespace NLQT
{
class CAutoLODDialog: public QDialog
{
Q_OBJECT
Q_OBJECT
public:
CAutoLODDialog(CWorkspaceNode *ownerNode, NL3D::CParticleSystem *ps, QWidget *parent = 0);
~CAutoLODDialog();
private Q_SLOTS:
void setDegradationExponent(int value);
void setSkipParticles(bool state);
@ -54,17 +55,29 @@ private:
struct CDistRatioWrapper : IPSWrapperFloat
{
NL3D::CParticleSystem *PS;
virtual float get() const { return PS->getAutoLODStartDistPercent(); }
virtual void set(const float &v) { PS->setupAutoLOD(v, PS->getAutoLODDegradationExponent()); }
virtual float get() const
{
return PS->getAutoLODStartDistPercent();
}
virtual void set(const float &v)
{
PS->setupAutoLOD(v, PS->getAutoLODDegradationExponent());
}
} _DistRatioWrapper;
struct CMaxDistLODBiasWrapper : IPSWrapperFloat
{
NL3D::CParticleSystem *PS;
virtual float get() const { return PS->getMaxDistLODBias(); }
virtual void set(const float &v) { PS->setMaxDistLODBias(v); }
virtual float get() const
{
return PS->getMaxDistLODBias();
}
virtual void set(const float &v)
{
PS->setMaxDistLODBias(v);
}
} _MaxDistLODBiasWrapper;
Ui::CAutoLODDialog _ui;
}; /* class CAutoLODDialog */

@ -26,15 +26,16 @@
#include "nel/misc/matrix.h"
#include "nel/misc/vector.h"
namespace NLQT {
namespace NLQT
{
// build an euler matrix
NLMISC::CMatrix BuildEulerMatrix(float psi, float theta, float phi)
{
float ca = cosf(psi), sa = sinf(psi)
, cb = cosf(theta), sb = sinf(theta)
, cc = cosf(phi), sc = sinf(phi);
, cb = cosf(theta), sb = sinf(theta)
, cc = cosf(phi), sc = sinf(phi);
NLMISC::CMatrix m;
m.identity();
m.setRot(NLMISC::CVector(ca * cb * cc - sa * sc, -cc * sa - ca * cb *sc, ca * sb)
@ -53,9 +54,11 @@ NLMISC::CVector GetEulerAngles(const NLMISC::CMatrix &mat)
mat.getRot(v[0], v[1], v[2]);
for (uint l = 0; l < 3; ++l)
{
m[0][l] = v[l].x; m[1][l] = v[l].y; m[2][l] = v[l].z;
m[0][l] = v[l].x;
m[1][l] = v[l].y;
m[2][l] = v[l].z;
}
// there are eight triplet that may satisfy the equation
// we compute them all, and test them against the matrix
@ -85,8 +88,8 @@ NLMISC::CVector GetEulerAngles(const NLMISC::CMatrix &mat)
a2 = (float) NLMISC::Pi - a0;
a3 = (float) NLMISC::Pi - a1;
c2 = (float) NLMISC::Pi - c0;
c3 = (float) NLMISC::Pi - c1;
@ -110,8 +113,8 @@ NLMISC::CVector GetEulerAngles(const NLMISC::CMatrix &mat)
for (uint k = 0; k < 8; ++k)
{
float ca = cosf(sol[k].x), sa = sinf(sol[k].x)
, cb = cosf(sol[k].y), sb = sinf(sol[k].y)
, cc = cosf(sol[k].z), sc = sinf(sol[k].z);
, cb = cosf(sol[k].y), sb = sinf(sol[k].y)
, cc = cosf(sol[k].z), sc = sinf(sol[k].z);
float gap = fabsf(m[0][0] - ca * cb * cc + sa * sc);
gap += fabsf(m[1][0] + cc * sa + ca * cb *sc);
@ -124,7 +127,7 @@ NLMISC::CVector GetEulerAngles(const NLMISC::CMatrix &mat)
if (k == 0 || gap < bestGap)
{
bestGap = gap;
bestIndex = k;
bestIndex = k;
}
}
@ -132,7 +135,7 @@ NLMISC::CVector GetEulerAngles(const NLMISC::CMatrix &mat)
}
CBasicEditWidget::CBasicEditWidget(QWidget *parent)
: QWidget(parent), _Wrapper(NULL)
: QWidget(parent), _Wrapper(NULL)
{
_ui.setupUi(this);
@ -161,26 +164,26 @@ void CBasicEditWidget::updateUi()
_ui.psiSpinBox->blockSignals(true);
_ui.thetaSpinBox->blockSignals(true);
_ui.phiSpinBox->blockSignals(true);
_ui.psiSpinBox->setValue(int(360.f * angles.x / (2.f * (float) NLMISC::Pi)));
_ui.thetaSpinBox->setValue(int(360.f * angles.y / (2.f * (float) NLMISC::Pi)));
_ui.phiSpinBox->setValue(int(360.f * angles.z / (2.f * (float) NLMISC::Pi)));
_ui.psiSpinBox->blockSignals(false);
_ui.thetaSpinBox->blockSignals(false);
_ui.phiSpinBox->blockSignals(false);
repaint();
}
void CBasicEditWidget::updateGraphics()
{
if (_Wrapper == NULL) return;
NLMISC::CVector angles(2.f * (float) NLMISC::Pi * _ui.psiSpinBox->value() / 360.f
, 2.f * (float) NLMISC::Pi * _ui.thetaSpinBox->value() / 360.f
, 2.f * (float) NLMISC::Pi * _ui.phiSpinBox->value() / 360.f
);
, 2.f * (float) NLMISC::Pi * _ui.thetaSpinBox->value() / 360.f
, 2.f * (float) NLMISC::Pi * _ui.phiSpinBox->value() / 360.f
);
NLMISC::CMatrix mat = BuildEulerMatrix(angles.x, angles.y, angles.z);
NL3D::CPlaneBasis pb;
pb.X = mat.getI();

@ -31,16 +31,17 @@
// Project includes
namespace NLQT {
namespace NLQT
{
class CBasicEditWidget: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CBasicEditWidget(QWidget *parent = 0);
~CBasicEditWidget();
void setWrapper(IPSWrapper<NL3D::CPlaneBasis> *wrapper);
void updateUi();
@ -53,7 +54,7 @@ private:
IPSWrapper<NL3D::CPlaneBasis> *_Wrapper ;
Ui::CBasicEditWidget _ui;
}; /* class CBasicEditWidget */
} /* namespace NLQT */

@ -20,8 +20,9 @@
#include "stdpch.h"
#include "bin_op_dialog.h"
namespace NLQT {
namespace NLQT
{
CBinOpDialog::CBinOpDialog(QWidget *widget1, QWidget *widget2, QWidget *parent)
: QDialog(parent)
{
@ -36,7 +37,7 @@ CBinOpDialog::CBinOpDialog(QWidget *widget1, QWidget *widget2, QWidget *parent)
_gridLayout->addItem(_horizontalSpacer, 1, 1, 1, 1);
_gridLayout->addWidget(widget2, 2, 0, 1, 2);
setWindowTitle(tr("Bin operator"));
_comboBox->clear();

@ -38,26 +38,27 @@
#include "ps_wrapper.h"
#include "attrib_widget.h"
namespace NLQT {
namespace NLQT
{
class CBinOpDialog : public QDialog
{
Q_OBJECT
Q_OBJECT
public:
CBinOpDialog(QWidget *widget1, QWidget *widget2, QWidget *parent = 0);
~CBinOpDialog();
virtual void init() = 0;
/// called when a new operator has been selected
/// called when a new operator has been selected
virtual void newOp(uint32 op) = 0 ;
private Q_SLOTS:
void setNewOp(int index);
protected:
QGridLayout *_gridLayout;
QWidget *_widget1;
QComboBox *_comboBox;
@ -66,9 +67,9 @@ protected:
};
/**
/**
@class CBinOpDialogT
@brief Construct a dialog that allow to edit a binary operator that produce argument of a particle system
@brief Construct a dialog that allow to edit a binary operator that produce argument of a particle system
*/
template <class T> class CBinOpDialogT : public CBinOpDialog
{
@ -96,8 +97,8 @@ public:
_AttrbDlg[k]->setSchemeWrapper(&_SchemeWrapper[k]) ;
_AttrbDlg[k]->init();
}
static const char * const operators[] =
static const char * const operators[] =
{
QT_TR_NOOP("Select Arg1"),
QT_TR_NOOP("Select Arg2"),
@ -126,10 +127,10 @@ public:
{
delete _AttrbDlg[k] ;
}
}
}
protected:
NL3D::CPSAttribMakerBinOp<T> *_EditedScheme ;
/// the dialogs that allow us to edit the schemes
@ -140,17 +141,30 @@ protected:
{
NL3D::CPSAttribMakerBinOp<T> *S ;
uint Index ;
virtual NL3D::CPSAttribMaker<T> *getScheme(void) const { return S->getArg(Index) ; }
virtual void setScheme(NL3D::CPSAttribMaker<T> *s) { S->setArg(Index, s) ; } ;
virtual NL3D::CPSAttribMaker<T> *getScheme(void) const
{
return S->getArg(Index) ;
}
virtual void setScheme(NL3D::CPSAttribMaker<T> *s)
{
S->setArg(Index, s) ;
} ;
} _SchemeWrapper[2] ;
/// a dummy wrapper for constant value. This shouldn't be called , however
struct CDummyWrapper : public IPSWrapper<T>
{
T get(void) const { nlassert(false) ; return T() ; }
void set(const T &) { nlassert(false) ; }
T get(void) const
{
nlassert(false) ;
return T() ;
}
void set(const T &)
{
nlassert(false) ;
}
} _DummyWrapper ;
void newOp(uint32 op)
{
@ -158,7 +172,7 @@ protected:
if (_EditedScheme->getOp() != (NL3D::CPSBinOp::BinOp) op)
_EditedScheme->setOp((NL3D::CPSBinOp::BinOp) op);
}
} ;
} /* namespace NLQT */

@ -1,17 +1,17 @@
/*
/*
* Copyright (C) 2010 by authors
*
*
* This file is part of NEL QT.
* NEL QT 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.
*
*
* NEL QT 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 NEL QT; see the file COPYING. If not, see
* <http://www.gnu.org/licenses/>.
@ -20,7 +20,8 @@
#include "stdpch.h"
#include "callback.h"
namespace NLQT {
namespace NLQT
{
} /* namespace NLQT */

@ -1,17 +1,17 @@
/*
/*
* Copyright (C) 2010 by authors
*
*
* This file is part of NEL QT.
* NEL QT 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.
*
*
* NEL QT 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 NEL QT; see the file COPYING. If not, see
* <http://www.gnu.org/licenses/>.
@ -34,7 +34,8 @@
// Project includes
namespace NLQT {
namespace NLQT
{
#define NLQT_CALLBACK_TEMPLATE \
/** \
@ -230,14 +231,14 @@ private: \
CCallbackBase *m_CallbackBase; \
\
}; /* class CCallback */ \
template<typename TReturn, typename TArgsA = void, typename TArgsB = void, typename TArgsC = void, typename TArgsD = void, typename TArgsE = void, typename TArgsF = void, typename TArgsG = void, typename TDummy = void>
class CCallback;
#define NLQT_CALLBACK_ARGS_CLASS CCallback<TReturn, void, void, void, void, void, void, void, void>
#define NLQT_CALLBACK_ARGS_TYPENAME
#define NLQT_CALLBACK_ARGS_DECL
#define NLQT_CALLBACK_ARGS_IMPL
#define NLQT_CALLBACK_ARGS_TYPENAME
#define NLQT_CALLBACK_ARGS_DECL
#define NLQT_CALLBACK_ARGS_IMPL
NLQT_CALLBACK_TEMPLATE
#undef NLQT_CALLBACK_ARGS_CLASS
#undef NLQT_CALLBACK_ARGS_TYPENAME

@ -27,10 +27,11 @@
// Nel includes
#include <nel/misc/rgba.h>
namespace NLQT {
namespace NLQT
{
CColorEditWidget::CColorEditWidget(QWidget *parent)
: QWidget(parent), _Wrapper(NULL), _emit(true)
: QWidget(parent), _Wrapper(NULL), _emit(true)
{
_ui.setupUi(this);
@ -39,7 +40,7 @@ CColorEditWidget::CColorEditWidget(QWidget *parent)
connect(_ui.bSpinBox, SIGNAL(valueChanged(int)), this, SLOT(setBlue(int)));
connect(_ui.aSpinBox, SIGNAL(valueChanged(int)), this, SLOT(setAlpha(int)));
connect(_ui.browsePushButton, SIGNAL(clicked()), this, SLOT(browseColor()));
setColor(QColor(255, 255, 255, 255));
}
@ -86,14 +87,14 @@ void CColorEditWidget::setRed(int r)
if (_emit)
Q_EMIT colorChanged(NLMISC::CRGBA(r, _ui.gSpinBox->value(), _ui.bSpinBox->value(), _ui.aSpinBox->value()));
if (_Wrapper == NULL)
if (_Wrapper == NULL)
return;
NLMISC::CRGBA color = _Wrapper->get();
if (r == color.R)
return;
color.R = r;
_Wrapper->setAndUpdateModifiedFlag(color);
@ -109,10 +110,10 @@ void CColorEditWidget::setGreen(int g)
if (_Wrapper == NULL) return;
NLMISC::CRGBA color = _Wrapper->get();
if (g == color.G)
return;
color.G = g;
_Wrapper->setAndUpdateModifiedFlag(color);
}
@ -127,10 +128,10 @@ void CColorEditWidget::setBlue(int b)
if (_Wrapper == NULL) return;
NLMISC::CRGBA color = _Wrapper->get();
if (b == color.B)
return;
color.B = b;
_Wrapper->setAndUpdateModifiedFlag(color);
}
@ -145,10 +146,10 @@ void CColorEditWidget::setAlpha(int a)
if (_Wrapper == NULL) return;
NLMISC::CRGBA color = _Wrapper->get();
if (a == color.A)
return;
color.A = a;
_Wrapper->setAndUpdateModifiedFlag(color);
}
@ -156,11 +157,11 @@ void CColorEditWidget::setAlpha(int a)
void CColorEditWidget::browseColor()
{
QColor color = QColorDialog::getColor(QColor(_ui.rSpinBox->value(),
_ui.gSpinBox->value(),
_ui.bSpinBox->value(),
_ui.aSpinBox->value()));
_ui.gSpinBox->value(),
_ui.bSpinBox->value(),
_ui.aSpinBox->value()));
if (!color.isValid()) return;
setColor(color);
}

@ -27,8 +27,9 @@
// Project includes
#include "ps_wrapper.h"
namespace NLQT {
namespace NLQT
{
/**
@class CColorEditWidget
@brief The widget provides a 4 horizontal slider or color dialog, to set the color.
@ -36,7 +37,7 @@ namespace NLQT {
Widget at the same time displays the color in the shaded rectangle at the side of the sliders.
Use this widget, have two ways: Qt Q_SIGNAL/SLOT or wrapper.
1. Using the Qt Q_SIGNALS/SLOT can be set current color by class methods setColor() and
1. Using the Qt Q_SIGNALS/SLOT can be set current color by class methods setColor() and
changes in current color(QSliders or QColorDialog) emits the signal colorChanged().
2. Using wrapper, create wpapper struct, example:
@ -52,26 +53,26 @@ to set the current values, need call class methods updateUi();
*/
class CColorEditWidget: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
/// Constructor, sets the default color (255, 255, 255, 255)
CColorEditWidget(QWidget *parent = 0);
~CColorEditWidget();
/// Sets the current color.
/// @param color - NeL NLMISC::CRGBA color
/// @param emit - will emit colorChanged() if the new value is different from the old one and param emit = true
void setColor(const NLMISC::CRGBA &color, bool emit = true);
/// Sets the current color.
/// @param color - Qt QColor color
/// @param emit - will emit colorChanged() if the new value is different from the old one and param emit = true
void setColor(const QColor &color, bool emit = true);
/// Set a wrapper to get/set the datas.
void setWrapper(IPSWrapperRGBA *wrapper);
/// Update the content of the widget using the wrapper.
void updateUi();
@ -84,16 +85,16 @@ private Q_SLOTS:
void setBlue(int b);
void setAlpha(int a);
void browseColor();
private:
// wrapper to the datas
IPSWrapperRGBA *_Wrapper;
bool _emit;
Ui::CColorEditWidget _ui;
}; /* class CColorEditWidget */
} /* namespace NLQT */

@ -31,25 +31,26 @@
using namespace std;
using namespace NLMISC;
namespace NLQT {
namespace NLQT
{
CConfiguration::CConfiguration()
{
}
CConfiguration::~CConfiguration()
{
}
void CConfiguration::init()
{
{
nldebug("CConfiguration::init");
// verify data
nlassert(!ConfigCallbacks.size());
// load config
try
{
@ -67,23 +68,23 @@ void CConfiguration::init()
void CConfiguration::release()
{
nldebug("CConfiguration::release");
Modules::config().dropCallback("SearchPaths");
// save and release the config file
if (ConfigFile.exists("SaveConfig") && ConfigFile.getVarPtr("SaveConfig")->asBool())
// save and release the config file
if (ConfigFile.exists("SaveConfig") && ConfigFile.getVarPtr("SaveConfig")->asBool())
{
ConfigFile.save();
}
ConfigFile.clear();
// release the search paths etc
CPath::releaseInstance();
// verify data
nlassert(!ConfigCallbacks.size());
}
void CConfiguration::updateUtilities()
{
//H_AUTO2
@ -101,7 +102,7 @@ void CConfiguration::configRemapExtensions()
var = ConfigFile.getVarPtr("RemapExtensions");
uint varsize = var->size();
for (uint i = 0; i < varsize; i += 2)
CPath::remapExtension(var->asString(i), var->asString(i + 1), true);
CPath::remapExtension(var->asString(i), var->asString(i + 1), true);
}
void CConfiguration::setAndCallback(const std::string &varName, CConfigCallback configCallback)
@ -127,7 +128,7 @@ float CConfiguration::getValue(const string &varName, float defaultValue)
{
if (ConfigFile.exists(varName)) return ConfigFile.getVar(varName).asFloat();
CConfigFile::CVar varToCopy;
varToCopy.forceAsDouble((double)defaultValue);
varToCopy.forceAsDouble((double)defaultValue);
ConfigFile.insertVar(varName, varToCopy);
return defaultValue;
}
@ -136,7 +137,7 @@ double CConfiguration::getValue(const string &varName, double defaultValue)
{
if (ConfigFile.exists(varName)) return ConfigFile.getVar(varName).asDouble();
CConfigFile::CVar varToCopy;
varToCopy.forceAsDouble(defaultValue);
varToCopy.forceAsDouble(defaultValue);
ConfigFile.insertVar(varName, varToCopy);
return defaultValue;
}
@ -145,7 +146,7 @@ int CConfiguration::getValue(const string &varName, int defaultValue)
{
if (ConfigFile.exists(varName)) return ConfigFile.getVar(varName).asInt();
CConfigFile::CVar varToCopy;
varToCopy.forceAsInt(defaultValue);
varToCopy.forceAsInt(defaultValue);
ConfigFile.insertVar(varName, varToCopy);
return defaultValue;
}
@ -172,14 +173,14 @@ bool CConfiguration::getValue(const string &varName, bool defaultValue)
{
if (ConfigFile.exists(varName)) return ConfigFile.getVar(varName).asBool();
CConfigFile::CVar varToCopy;
varToCopy.forceAsInt(defaultValue ? 1 : 0);
varToCopy.forceAsInt(defaultValue ? 1 : 0);
ConfigFile.insertVar(varName, varToCopy);
return defaultValue;
}
CRGBA CConfiguration::getValue(const string &varName, const CRGBA &defaultValue)
{
if (ConfigFile.exists(varName))
if (ConfigFile.exists(varName))
{
return getValue(ConfigFile.getVar(varName), defaultValue);
}
@ -203,7 +204,7 @@ CRGBA CConfiguration::getValue(const CConfigFile::CVar &var, const CRGBA &defaul
if (var.size() > 4) nlwarning("RGBA value in config value '%s' is too long, ignoring unused values");
return CRGBA((uint8)var.asInt(0), (uint8)var.asInt(1), (uint8)var.asInt(2), var.size() >= 4 ? (uint8)var.asInt(3) : 255);
}
nlwarning("Invalid RGBA value in config value '%s', reverting to default { %i, %i, %i, %i }", var.Name.c_str(), (sint)defaultValue.R, (sint)defaultValue.G, (sint)defaultValue.B, (sint)defaultValue.A);
nlwarning("Invalid RGBA value in config value '%s', reverting to default { %i, %i, %i, %i }", var.Name.c_str(), (sint)defaultValue.R, (sint)defaultValue.G, (sint)defaultValue.B, (sint)defaultValue.A);
return defaultValue;
}
@ -216,7 +217,7 @@ void CConfiguration::cfcbSearchPaths(NLMISC::CConfigFile::CVar &var)
{
uint varsize = var.size();
for (uint i = 0; i < varsize; ++i)
CPath::addSearchPath(var.asString(i), true, false);
CPath::addSearchPath(var.asString(i), true, false);
}
} /* namespace NLQT */

@ -35,7 +35,8 @@
#define NLQT_CONFIG_FILE "object_viewer.cfg"
namespace NLQT {
namespace NLQT
{
typedef CCallback<void, NLMISC::CConfigFile::CVar &> CConfigCallback;
@ -55,7 +56,7 @@ public:
void init();
void release();
void updateUtilities();
void configSearchPaths();
void configRemapExtensions();
@ -63,7 +64,7 @@ public:
void setAndCallback(const std::string &varName, CConfigCallback configCallback);
void setCallback(const std::string &varName, CConfigCallback configCallback);
void dropCallback(const std::string &varName);
float getValue(const std::string &varName, float defaultValue);
double getValue(const std::string &varName, double defaultValue);
int getValue(const std::string &varName, int defaultValue);
@ -72,8 +73,11 @@ public:
bool getValue(const std::string &varName, bool defaultValue);
NLMISC::CRGBA getValue(const std::string &varName, const NLMISC::CRGBA &defaultValue);
NLMISC::CRGBA getValue(const NLMISC::CConfigFile::CVar &var, const NLMISC::CRGBA &defaultValue);
inline NLMISC::CConfigFile &getConfigFile() { return ConfigFile; }
inline NLMISC::CConfigFile &getConfigFile()
{
return ConfigFile;
}
private:
static void cbConfigCallback(NLMISC::CConfigFile::CVar &var);
@ -85,7 +89,7 @@ private:
NLMISC::CConfigFile ConfigFile;
std::map<std::string, CConfigCallback> ConfigCallbacks;
};/* class CConfiguration */
} /* namespace NLQT */

@ -23,23 +23,24 @@
// NeL includes
#include "nel/3d/ps_mesh.h"
namespace NLQT {
namespace NLQT
{
CConstraintMeshWidget::CConstraintMeshWidget(QWidget *parent )
: QWidget(parent)
: QWidget(parent)
{
_ui.setupUi(this);
connect(_ui.stageCheckBox_0, SIGNAL(clicked(bool)), this, SLOT(setForceStage0(bool)));
connect(_ui.stageCheckBox_1, SIGNAL(clicked(bool)), this, SLOT(setForceStage1(bool)));
connect(_ui.stageCheckBox_2, SIGNAL(clicked(bool)), this, SLOT(setForceStage2(bool)));
connect(_ui.stageCheckBox_3, SIGNAL(clicked(bool)), this, SLOT(setForceStage3(bool)));
connect(_ui.vertexColorLightingCheckBox, SIGNAL(clicked(bool)), this, SLOT(setForceVertexColorLighting(bool)));
connect(_ui.texAnimTypeComboBox, SIGNAL(currentIndexChanged(int)), this, SLOT(setTexAnimType(int)));
connect(_ui.reinitCheckBox, SIGNAL(toggled(bool)), this, SLOT(setReinitWhenNewElementIsCreated(bool)));
connect(_ui.stageSpinBox, SIGNAL(valueChanged(int)), this, SLOT(setStage(int)));
connectGlobalTexAnim();
}
@ -55,14 +56,14 @@ void CConstraintMeshWidget::connectGlobalTexAnim()
connect(_ui.transVSpeedDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setGlobalTexAnimValue()));
connect(_ui.transUAccelDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setGlobalTexAnimValue()));
connect(_ui.transVAccelDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setGlobalTexAnimValue()));
connect(_ui.scaleUStartDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setGlobalTexAnimValue()));
connect(_ui.scaleVStartDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setGlobalTexAnimValue()));
connect(_ui.scaleUSpeedDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setGlobalTexAnimValue()));
connect(_ui.scaleVSpeedDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setGlobalTexAnimValue()));
connect(_ui.scaleUAccelDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setGlobalTexAnimValue()));
connect(_ui.scaleVAccelDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setGlobalTexAnimValue()));
connect(_ui.rotSpeedDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setGlobalTexAnimValue()));
connect(_ui.rotAccelDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setGlobalTexAnimValue()));
}
@ -97,7 +98,7 @@ void CConstraintMeshWidget::setCurrentConstraintMesh(CWorkspaceNode *ownerNode,
_ui.stageCheckBox_2->setChecked(_CM->isStageModulationForced(2));
_ui.stageCheckBox_3->setChecked(_CM->isStageModulationForced(3));
_ui.vertexColorLightingCheckBox->setChecked(_CM->isVertexColorLightingForced());
_ui.texAnimTypeComboBox->setCurrentIndex(_CM->getTexAnimType());
if (_CM->getTexAnimType() == NL3D::CPSConstraintMesh::GlobalAnim)
{
@ -135,24 +136,24 @@ void CConstraintMeshWidget::setTexAnimType(int index)
{
switch(index)
{
case 0: // no anim
_CM->setTexAnimType(NL3D::CPSConstraintMesh::NoAnim);
_ui.stageSpinBox->hide();
_ui.stageLabel->hide();
_ui.tabWidget->hide();
_ui.reinitCheckBox->hide();
case 0: // no anim
_CM->setTexAnimType(NL3D::CPSConstraintMesh::NoAnim);
_ui.stageSpinBox->hide();
_ui.stageLabel->hide();
_ui.tabWidget->hide();
_ui.reinitCheckBox->hide();
break;
case 1: // global anim
_CM->setTexAnimType(NL3D::CPSConstraintMesh::GlobalAnim);
_ui.stageSpinBox->show();
_ui.stageLabel->show();
_ui.tabWidget->show();
_ui.reinitCheckBox->show();
_ui.stageSpinBox->setValue(0);
_ui.reinitCheckBox->setChecked(_CM->isGlobalAnimTimeResetOnNewElementForced());
case 1: // global anim
_CM->setTexAnimType(NL3D::CPSConstraintMesh::GlobalAnim);
_ui.stageSpinBox->show();
_ui.stageLabel->show();
_ui.tabWidget->show();
_ui.reinitCheckBox->show();
_ui.stageSpinBox->setValue(0);
_ui.reinitCheckBox->setChecked(_CM->isGlobalAnimTimeResetOnNewElementForced());
break;
default:
nlstop;
default:
nlstop;
break;
}
}
@ -170,7 +171,7 @@ void CConstraintMeshWidget::setStage(int value)
void CConstraintMeshWidget::updateGlobalTexAnim(int value)
{
disconnectGlobalTexAnim();
const NL3D::CPSConstraintMesh::CGlobalTexAnim &gta = _CM->getGlobalTexAnim(value);
_ui.transUStartDoubleSpinBox->setValue(gta.TransOffset.x);
@ -179,41 +180,41 @@ void CConstraintMeshWidget::updateGlobalTexAnim(int value)
_ui.transVSpeedDoubleSpinBox->setValue(gta.TransSpeed.y);
_ui.transUAccelDoubleSpinBox->setValue(gta.TransAccel.x);
_ui.transVAccelDoubleSpinBox->setValue(gta.TransAccel.y);
_ui.scaleUStartDoubleSpinBox->setValue(gta.ScaleStart.x);
_ui.scaleVStartDoubleSpinBox->setValue(gta.ScaleStart.y);
_ui.scaleUSpeedDoubleSpinBox->setValue(gta.ScaleSpeed.x);
_ui.scaleVSpeedDoubleSpinBox->setValue(gta.ScaleSpeed.y);
_ui.scaleUAccelDoubleSpinBox->setValue(gta.ScaleAccel.x);
_ui.scaleVAccelDoubleSpinBox->setValue(gta.ScaleAccel.y);
_ui.rotSpeedDoubleSpinBox->setValue(gta.WRotSpeed);
_ui.rotAccelDoubleSpinBox->setValue(gta.WRotAccel);
connectGlobalTexAnim();
}
void CConstraintMeshWidget::setGlobalTexAnimValue()
{
NL3D::CPSConstraintMesh::CGlobalTexAnim gta;
gta.TransOffset.x = _ui.transUStartDoubleSpinBox->value();
gta.TransOffset.y = _ui.transVStartDoubleSpinBox->value();
gta.TransSpeed.x = _ui.transUSpeedDoubleSpinBox->value();
gta.TransSpeed.y = _ui.transVSpeedDoubleSpinBox->value();
gta.TransAccel.x = _ui.transUAccelDoubleSpinBox->value();
gta.TransAccel.y = _ui.transVAccelDoubleSpinBox->value();
gta.ScaleStart.x = _ui.scaleUStartDoubleSpinBox->value();
gta.ScaleStart.y = _ui.scaleVStartDoubleSpinBox->value();
gta.ScaleSpeed.x = _ui.scaleUSpeedDoubleSpinBox->value();
gta.ScaleSpeed.y = _ui.scaleVSpeedDoubleSpinBox->value();
gta.ScaleAccel.x = _ui.scaleUAccelDoubleSpinBox->value();
gta.ScaleAccel.y = _ui.scaleVAccelDoubleSpinBox->value();
gta.WRotSpeed = _ui.rotSpeedDoubleSpinBox->value();
gta.WRotAccel = _ui.rotAccelDoubleSpinBox->value();
_CM->setGlobalTexAnim(_ui.stageSpinBox->value(), gta);
}

@ -31,11 +31,13 @@
// Project includes
#include "particle_node.h"
namespace NL3D {
class CPSConstraintMesh;
namespace NL3D
{
class CPSConstraintMesh;
}
namespace NLQT {
namespace NLQT
{
/**
@class CConstraintMeshWidget
@ -43,12 +45,12 @@ namespace NLQT {
*/
class CConstraintMeshWidget: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CConstraintMeshWidget(QWidget *parent = 0);
~CConstraintMeshWidget();
/// Set the constraint mesh to edit.
void setCurrentConstraintMesh(CWorkspaceNode *ownerNode, NL3D::CPSConstraintMesh *cm);
@ -62,16 +64,16 @@ private Q_SLOTS:
void setReinitWhenNewElementIsCreated(bool state);
void setStage(int value);
void setGlobalTexAnimValue();
private:
void connectGlobalTexAnim();
void disconnectGlobalTexAnim();
void updateGlobalTexAnim(int value);
CWorkspaceNode *_Node;
NL3D::CPSConstraintMesh *_CM;
Ui::CConstraintMeshWidget _ui;
}; /* class CConstraintMeshWidget */

@ -23,8 +23,9 @@
// Project includes
#include "particle_node.h"
namespace NLQT {
namespace NLQT
{
CurveEditDialog::CurveEditDialog(NL3D::CPSFloatCurveFunctor *curve, CWorkspaceNode *ownerNode, QWidget *parent)
: QDialog(parent) , _Curve(curve), _scale(1.0), _pos(0.0), _Node(ownerNode)
{
@ -32,16 +33,16 @@ CurveEditDialog::CurveEditDialog(NL3D::CPSFloatCurveFunctor *curve, CWorkspaceNo
show();
_hoverPoints = new HoverPoints(_ui.curveWidget, HoverPoints::CircleShape);
if (_Curve->hasSmoothing())
if (_Curve->hasSmoothing())
_hoverPoints->setConnectionType(HoverPoints::CurveConnection);
else
else
_hoverPoints->setConnectionType(HoverPoints::LineConnection);
_ui.smoothingCheckBox->setChecked(_Curve->hasSmoothing());
buildPoints();
_hoverPoints->setSortType(HoverPoints::XSort);
_hoverPoints->setShapePen(QPen(QColor(0, 0, 100, 127), 1));
_hoverPoints->setShapeBrush(QBrush(QColor(0, 0, 200, 127)));
@ -69,11 +70,11 @@ CurveEditDialog::~CurveEditDialog()
void CurveEditDialog::setSmoothing(bool state)
{
if (state)
if (state)
_hoverPoints->setConnectionType(HoverPoints::CurveConnection);
else
else
_hoverPoints->setConnectionType(HoverPoints::LineConnection);
_Curve->enableSmoothing(state);
_ui.curveWidget->update();
@ -85,13 +86,13 @@ void CurveEditDialog::setDisplayInterpolation(bool state)
void CurveEditDialog::curveChanged(const QPolygonF &points)
{
if (_Curve->getNumCtrlPoints() > uint(points.size()))
if (_Curve->getNumCtrlPoints() > uint(points.size()))
_Curve->removeCtrlPoint(0);
else if (_Curve->getNumCtrlPoints() < uint(points.size()))
_Curve->addControlPoint(NL3D::CPSFloatCurveFunctor::CCtrlPoint(1, 0.5f));
for (int i = 0; i < points.size(); i++)
_Curve->setCtrlPoint(uint(i), NL3D::CPSFloatCurveFunctor::CCtrlPoint(points.at(i).x() / _ui.curveWidget->width(),
(_ui.curveWidget->height() - points.at(i).y() + _pos) / (_ui.curveWidget->height() * _scale)));
_Curve->setCtrlPoint(uint(i), NL3D::CPSFloatCurveFunctor::CCtrlPoint(points.at(i).x() / _ui.curveWidget->width(),
(_ui.curveWidget->height() - points.at(i).y() + _pos) / (_ui.curveWidget->height() * _scale)));
}
void CurveEditDialog::setScale(int value)
@ -146,8 +147,8 @@ void CurveEditDialog::buildPoints()
{
QPolygonF points;
for (uint i = 0; i < _Curve->getNumCtrlPoints(); i++)
points << QPointF((_Curve->getControlPoint(i).Date * _ui.curveWidget->width()),
_pos + _ui.curveWidget->height() - (_scale * _Curve->getControlPoint(i).Value * _ui.curveWidget->height()));
points << QPointF((_Curve->getControlPoint(i).Date * _ui.curveWidget->width()),
_pos + _ui.curveWidget->height() - (_scale * _Curve->getControlPoint(i).Value * _ui.curveWidget->height()));
_hoverPoints->setPoints(points);
//_hoverPoints->setPointLock(0, HoverPoints::LockToLeft);

@ -36,7 +36,8 @@
#include "hoverpoints.h"
#include "ps_wrapper.h"
namespace NLQT {
namespace NLQT
{
/**
@class CurveEditDialog
@brief Dialogue editing graphics curve.
@ -45,15 +46,15 @@ The choice of the interpolation algorithm.
*/
class CurveEditDialog : public QDialog
{
Q_OBJECT
Q_OBJECT
public:
CurveEditDialog(NL3D::CPSFloatCurveFunctor *curve, CWorkspaceNode *ownerNode, QWidget *parent = 0);
~CurveEditDialog();
/// the scheme being edited
NL3D::CPSFloatCurveFunctor *_Curve;
private Q_SLOTS:
void setSmoothing(bool state);
void setDisplayInterpolation(bool state);
@ -64,17 +65,17 @@ private Q_SLOTS:
void setLastTiFirst();
void setFirstToLast();
void setNumSamples(uint32 value);
protected:
void buildPoints();
float _scale;
float _pos;
CWorkspaceNode *_Node;
HoverPoints *_hoverPoints;
Ui::CurveEditDialog _ui;
}; /* CurveEditDialog */

@ -26,10 +26,11 @@
// Project includes
#include "modules.h"
namespace NLQT {
namespace NLQT
{
CDayNightDialog::CDayNightDialog(QWidget *parent)
: QDockWidget(parent)
: QDockWidget(parent)
{
_ui.setupUi(this);

@ -28,7 +28,8 @@
// Project includes
namespace NLQT {
namespace NLQT
{
/**
@class CDayNightDialog
@ -37,12 +38,12 @@ namespace NLQT {
*/
class CDayNightDialog: public QDockWidget
{
Q_OBJECT
Q_OBJECT
public:
CDayNightDialog(QWidget *parent = 0);
~CDayNightDialog();
private Q_SLOTS:
void setDayNight(int value);

@ -4,12 +4,12 @@
@section introduce Introduce
@details
The Object Viewer Qt (ovqt) is a tool for working with graphics technology NeL data,
which can be useful durung the development and preparation of the game content.
The Object Viewer Qt (ovqt) is a tool for working with graphics technology NeL data,
which can be useful durung the development and preparation of the game content.
The tool can be used in different tasks:
- Loading and viewing NeL data (.shape, .ps) files with the ability to set wind power, color light.
- Viewing animation shape (loading .anim, .skel, .swt files) using playlist or slot manager(mixing animation).
- Create and modify NeL particle system.
- Create and modify NeL particle system.
- Viewing water shape with the ability to set day/night.
- Modify skeleton (.skel files, .scale file).
- Create and modify micro-vegetation material (.vegetset files)
@ -18,58 +18,58 @@ The tool can be used in different tasks:
@section project_structure Overview of the Object Viewer Qt Project Structure
@details
OVQT - consists of several major subsystems. Each subsystem performs its defined part of the task.
Through Modules:: provides access to all other program subsystems.
OVQT - consists of several major subsystems. Each subsystem performs its defined part of the task.
Through Modules:: provides access to all other program subsystems.
Program has the following subsystems:
- @ref Modules - Main modules aggregated all parts of the program.
- @ref NLQT::CConfiguration - is responsible for loading and saving settings from the configuration file. As well as search path of data.
- @ref NLQT::CObjectViewer - main subsystem of the program, which initializes the driver, creates a scene and other supporting elements.
- @ref NLQT::CObjectViewer - main subsystem of the program, which initializes the driver, creates a scene and other supporting elements.
It is a container for loaded models, which can further be viewed and animated.
- @ref NLQT::CMainWindow - is responsible for the GUI.
- @ref NLQT::CParticleEditor - is responsible for the particle systems and provides access to a container that keeps all the loaded particle systems.
- @ref NLQT::CParticleEditor - is responsible for the particle systems and provides access to a container that keeps all the loaded particle systems.
And also allows you to view an animation of particle systems, with the ability to control its parameters.
- @ref NLQT::CVegetableEditor - is responsible for the landscape zones and the editor of vegetation.
- @ref NLQT::CVegetableEditor - is responsible for the landscape zones and the editor of vegetation.
Allows you to load and view the landscape. Also has the ability to create and edit the parameters of the micro-vegetation.
- @ref NLQT::CSoundSystem - is responsible for the sound in the program.
<b>
The structure of the GUI in the editor of the particles.
The structure of the GUI in the editor of the particles.
</b><br>
This can be useful for new developers who want to add more new dialogs or to improve the functionality of existing dialogues.
<img src="gui_struct.png" alt="Particle Workspace">
ParticleWorkspace dialogue uses the technique of model-view.
Using the signal/slot link QTreeView with QStackWidget, Editor properties dialog.
When you select an item in QTreeView, QStackWidget displays the necessary page(PageWidget) where you can edit the element of the particles system.
Each page is made in the designer and has a separate forms(.ui).
In accordance with the recommendations of dialogues design, with a large number of items,every page uses QTabWidget.
In case when there is a great number of controls, and not everything you want to display,
ParticleWorkspace dialogue uses the technique of model-view.
Using the signal/slot link QTreeView with QStackWidget, Editor properties dialog.
When you select an item in QTreeView, QStackWidget displays the necessary page(PageWidget) where you can edit the element of the particles system.
Each page is made in the designer and has a separate forms(.ui).
In accordance with the recommendations of dialogues design, with a large number of items,every page uses QTabWidget.
In case when there is a great number of controls, and not everything you want to display,
it's used the dynamic creation of tabs. Moreover, each tab uses a separate forms(.ui).
@section for_new_developer Guide for new developers of the Object Viewer Qt.
@details
First of all, to begin developing dialogues that add new features ovqt,
it is needed to read the documentation Qt libs (http://doc.qt.nokia.com/) and NeL documentation.
In order to have convenient using of the tool and its further development,
it is expected to make a unified interface that is why all dialogs should adhere to a standard design,
which will be written further. For this goals program provides some additional widgets,
which are recommended to use. As in the development Qt Designer is actively used.
To get access to founded here widgets from the designer,the technique promotion is used,
In order to have convenient using of the tool and its further development,
it is expected to make a unified interface that is why all dialogs should adhere to a standard design,
which will be written further. For this goals program provides some additional widgets,
which are recommended to use. As in the development Qt Designer is actively used.
To get access to founded here widgets from the designer,the technique promotion is used,
which can be found <a href="http://doc.qt.nokia.com/4.5/designer-using-custom-widgets.html"> here </a>.
<ol>
<li><b>
CEditRangeUIntWidget / CEditRangeIntWidget / CEditRangeFloatWidget
</b><br>
Widgets provides a slider that allows you to specify an integer (or float, depending on which widget used) number within a set range.
The range is also can be set by the user, or for a more accurate selection of numbers, either for receiving large values.
Widgets provides a slider that allows you to specify an integer (or float, depending on which widget used) number within a set range.
The range is also can be set by the user, or for a more accurate selection of numbers, either for receiving large values.
As there may be situations when the range that a user requests,has to be restricted, and widget provides methods that allow you to do so.
<br><br>
<img src="cedit_range_int_widget.png" alt="CEditRangeIntWidget">
<br>
<img src="cedit_range_float_widget.png" alt="CEditRangeFloatWidget">
@see
@ref NLQT::CEditRangeUIntWidget, @ref NLQT::CEditRangeIntWidget, @ref NLQT::CEditRangeFloatWidget
@ref NLQT::CEditRangeUIntWidget, @ref NLQT::CEditRangeIntWidget, @ref NLQT::CEditRangeFloatWidget
<li><b>
CColorEditWidget
@ -81,46 +81,46 @@ Using this widget you can set the color(RGBA) using the four sliders or through
@ref NLQT::CColorEditWidget
<li><b>
CDirectionWidget
CDirectionWidget
</b><br>
This widget helps to choose from several preset directions, or to choose a custom one.
This widget helps to choose from several preset directions, or to choose a custom one.
<br><br>
<img src="cdirection_widget.png" alt="CDirectionWidget">
@see
@ref NLQT::CDirectionWidget
</ol><br><br>
To further convinience of instrument using dialogues interface is recommended to make as follows.
To further convinience of instrument using dialogues interface is recommended to make as follows.
The most sophisticated tools of the program, should take the form of three dock windows (example shown in the screenshot).
<img src="object_viewer_qt_window.png" alt="Object Viewer Qt">
<ol>
<li>
The first dock window - is a control dock window, it should focus all of the control functions of general purpose
(for example: start/stop/pause animations or particles system).
The first dock window - is a control dock window, it should focus all of the control functions of general purpose
(for example: start/stop/pause animations or particles system).
It is recommended to perform of the horizontal type window and placed in the bottom of the main window.
<li>
The second dock window - is a list or a tree of items. In which selecting of the current element,
which assumes to modify or viewis possible.Operations "add/remove/insert or other" items are recommended to make as a popur menu.
The second dock window - is a list or a tree of items. In which selecting of the current element,
which assumes to modify or viewis possible.Operations "add/remove/insert or other" items are recommended to make as a popur menu.
It is recommended to perform of the vertical type window and placed in the left of the main window.
<li>
The third dock - is an editor for properties of the element that was selected in the list or in the tree of elements.
As all the controls occupy much space or do not fit at all, you have to use tabs QTabWidget,
which in total can contains quite a lot of elements.
For a small number of tabs it is allowed to use both horizontal and vertical location.
But with a large number of tabs, it is necessary to apply the vertical arrangement.
The third dock - is an editor for properties of the element that was selected in the list or in the tree of elements.
As all the controls occupy much space or do not fit at all, you have to use tabs QTabWidget,
which in total can contains quite a lot of elements.
For a small number of tabs it is allowed to use both horizontal and vertical location.
But with a large number of tabs, it is necessary to apply the vertical arrangement.
It is recommended to perform of the vertical type of window and placed in the right of the main window.
</ol>
In the simple dialogues do not necessary to use all three windows, but user has to adhere to the recommendations given above as well.
Also, <b>all dialogs must use the qt layout manager</b>. And if you do not use the designer,
Also, <b>all dialogs must use the qt layout manager</b>. And if you do not use the designer,
make sure you use the qt tools internationalization applications.
<br><br>
In ovqt for most dialogs their owner is NLQT::CMainWindow and in its methods creating and initializing all dependent dialogs occur.
For the convenience of the program using, most dialogues are created in the form of docking windows.
Creating all the dialogues are carried out in a private method NLQT::CMainWindow::createDialogs().
Hence, it is necessary to add operations in this method to create new dialogues.
But we must take into account that at this moment is fully available only one component of the program CConfiguration,
to read the settings from the configuration file. The remaining components of the program are available only after the main window stays visible.
Calling the dialogues going through the menu or the toolbar, usually it is a checkable item.
In ovqt for most dialogs their owner is NLQT::CMainWindow and in its methods creating and initializing all dependent dialogs occur.
For the convenience of the program using, most dialogues are created in the form of docking windows.
Creating all the dialogues are carried out in a private method NLQT::CMainWindow::createDialogs().
Hence, it is necessary to add operations in this method to create new dialogues.
But we must take into account that at this moment is fully available only one component of the program CConfiguration,
to read the settings from the configuration file. The remaining components of the program are available only after the main window stays visible.
Calling the dialogues going through the menu or the toolbar, usually it is a checkable item.
Adding of the new menu items or items toolbars is need in methods NLQT::CMainWindow::createMenus(), NLQT::CMainWindow::createToolBars().
@section license_ovqt License Object Viewer Qt

@ -26,19 +26,20 @@
// NeL includes
#include <nel/misc/vector.h>
namespace NLQT {
namespace NLQT
{
CDirectionWidget::CDirectionWidget(QWidget *parent)
: QWidget(parent), _globalName("")
: QWidget(parent), _globalName("")
{
_ui.setupUi(this);
_ui.xzWidget->setMode(Mode::Direction);
_ui.yzWidget->setMode(Mode::Direction);
_ui.xzWidget->setText("XZ");
_ui.yzWidget->setText("YZ");
_ui.globalPushButton->hide();
connect(_ui.globalPushButton ,SIGNAL(clicked()), this, SLOT(setGlobalDirection()));
connect(_ui.incVecIPushButton ,SIGNAL(clicked()), this, SLOT(incVecI()));
connect(_ui.incVecJPushButton ,SIGNAL(clicked()), this, SLOT(incVecJ()));
@ -46,10 +47,10 @@ CDirectionWidget::CDirectionWidget(QWidget *parent)
connect(_ui.decVecIPushButton ,SIGNAL(clicked()), this, SLOT(decVecI()));
connect(_ui.decVecJPushButton ,SIGNAL(clicked()), this, SLOT(decVecJ()));
connect(_ui.decVecKPushButton ,SIGNAL(clicked()), this, SLOT(decVecK()));
connect(_ui.xzWidget, SIGNAL(applyNewVector(float,float)), this, SLOT(setNewVecXZ(float,float)));
connect(_ui.yzWidget, SIGNAL(applyNewVector(float,float)), this, SLOT(setNewVecYZ(float,float)));
// Set default value +K
setValue(NLMISC::CVector::K);
}
@ -72,7 +73,7 @@ void CDirectionWidget::setValue(const NLMISC::CVector &value, bool emit)
_ui.xzWidget->repaint();
_ui.yzWidget->repaint();
if (emit)
if (emit)
{
Q_EMIT valueChanged(_value);
}
@ -81,10 +82,10 @@ void CDirectionWidget::setValue(const NLMISC::CVector &value, bool emit)
void CDirectionWidget::setGlobalName(const QString &globalName, bool emit)
{
_globalName = globalName;
_ui.xzWidget->setVisible(_globalName.isEmpty());
_ui.yzWidget->setVisible(_globalName.isEmpty());
_ui.incVecIPushButton->setEnabled(_globalName.isEmpty());
_ui.incVecJPushButton->setEnabled(_globalName.isEmpty());
_ui.incVecKPushButton->setEnabled(_globalName.isEmpty());
@ -100,10 +101,10 @@ void CDirectionWidget::setGlobalDirection()
{
bool ok;
QString text = QInputDialog::getText(this, tr("Enter Name"),
"", QLineEdit::Normal,
QString(_globalName), &ok);
if (ok)
"", QLineEdit::Normal,
QString(_globalName), &ok);
if (ok)
setGlobalName(text);
}
@ -141,20 +142,20 @@ void CDirectionWidget::setNewVecXZ(float x, float y)
{
const float epsilon = 10E-3f;
NLMISC::CVector v = _value;
v.x = x;
v.z = y;
float d = v.x * v.x + v.z * v.z;
float f;
float f;
if (fabs(d) > epsilon)
f = sqrt((1.f - v.y * v.y) / d);
else
f = 1;
v.x *= f;
v.z *= f;
v.normalize();
setValue(v);
@ -164,20 +165,20 @@ void CDirectionWidget::setNewVecYZ(float x, float y)
{
const float epsilon = 10E-3f;
NLMISC::CVector v = _value;
v.y = x;
v.z = y;
float d = v.y * v.y + v.z * v.z;
float f;
float f;
if (fabs(d) > epsilon)
f = sqrt((1.f - v.x * v.x) / d);
else
f = 1;
v.y *= f;
v.z *= f;
v.normalize();
setValue(v);

@ -29,7 +29,8 @@
// Project includes
namespace NLQT {
namespace NLQT
{
/**
@class CDirectionWidget
@ -38,12 +39,12 @@ namespace NLQT {
*/
class CDirectionWidget: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CDirectionWidget(QWidget *parent = 0);
~CDirectionWidget();
void enabledGlobalVariable(bool enabled);
Q_SIGNALS:
@ -64,13 +65,13 @@ private Q_SLOTS:
void decVecK();
void setNewVecXZ(float x, float y);
void setNewVecYZ(float x, float y);
private:
NLMISC::CVector _value;
QString _globalName;
Ui::CDirectionWidget _ui;
}; /* class CDirectionWidget */
} /* namespace NLQT */

@ -34,23 +34,23 @@ using namespace NL3D;
/** This can duplicate any serializable type by using a serialization policy (polymorphic, non polymorphic ..)
* The serialization policy must have a method to serial a pointer on the object (see example below)
* NB : of course this is slow (but convenient) way of performing a copy
* TODO maybe this could be used elsewhere ?
* The serialization policy must have a method to serial a pointer on the object (see example below)
* NB : of course this is slow (but convenient) way of performing a copy
* TODO maybe this could be used elsewhere ?
*/
template <class TSerializePolicy, typename T>
static T *DupSerializable(const T *in) throw(NLMISC::EStream)
{
NLMISC::CMemStream ms;
NLMISC::CMemStream ms;
nlassert(!ms.isReading());
T *nonConstIn = const_cast<T *>(in);
TSerializePolicy::serial(nonConstIn, ms);
std::vector<uint8> datas(ms.length());
std::copy(ms.buffer(), ms.buffer() + ms.length(), datas.begin());
std::copy(ms.buffer(), ms.buffer() + ms.length(), datas.begin());
ms.resetPtrTable();
ms.invert();
ms.fill(&datas[0], (uint)datas.size());
nlassert(ms.isReading());
nlassert(ms.isReading());
T *newObj = NULL;
TSerializePolicy::serial(newObj, ms);
return newObj;
@ -62,7 +62,7 @@ struct CDupObjPolicy
{
template <typename T>
static void serial(T *&obj, NLMISC::IStream &dest) throw(NLMISC::EStream)
{
{
dest.serialPtr(obj);
/*if (dest.isReading())
{
@ -72,10 +72,10 @@ struct CDupObjPolicy
obj = newObj.release();
}
else
{
{
obj->serial(dest);
}*/
}
}
};
/** A policy to duplicate a polymorphic type
@ -84,8 +84,8 @@ struct CDupPolymorphicObjPolicy
{
template <typename T>
static void serial(T *&obj, NLMISC::IStream &dest) throw(NLMISC::EStream)
{
dest.serialPolyPtr(obj);
{
dest.serialPolyPtr(obj);
}
};
@ -111,10 +111,10 @@ NL3D::CParticleSystemProcess *DupPSLocated(const CParticleSystemProcess *in)
/** Duplicate the system, and detach.
* We can't duplicate the object direclty (it may be referencing other objects in the system, so these objects will be copied too...)
*/
std::auto_ptr<CParticleSystem> newPS(DupSerializable<CDupObjPolicy>(in->getOwner()));
// scene pointer is not serialised, but 'detach' may need the scene to be specified
newPS->setScene(in->getOwner()->getScene());
return newPS->detach(index);
std::auto_ptr<CParticleSystem> newPS(DupSerializable<CDupObjPolicy>(in->getOwner()));
// scene pointer is not serialised, but 'detach' may need the scene to be specified
newPS->setScene(in->getOwner()->getScene());
return newPS->detach(index);
}
}
catch (NLMISC::EStream &e)
@ -141,13 +141,13 @@ NL3D::CPSLocatedBindable *DupPSLocatedBindable(CPSLocatedBindable *in)
else
{
CParticleSystem *srcPS = in->getOwner()->getOwner();
std::auto_ptr<CParticleSystem> newPS(DupSerializable<CDupObjPolicy>(srcPS));
std::auto_ptr<CParticleSystem> newPS(DupSerializable<CDupObjPolicy>(srcPS));
// scene pointer is not serialised, but 'detach' may need the scene to be specified
newPS->setScene(in->getOwner()->getOwner()->getScene());
//
uint index = srcPS->getIndexOf(*(in->getOwner()));
uint subIndex = in->getOwner()->getIndexOf(in);
//
//
newPS->setScene(in->getOwner()->getScene()); // 'unbind' require the scene to be attached
CPSLocated *loc = NLMISC::safe_cast<CPSLocated *>(newPS->getProcess(index));
return loc->unbind(subIndex);

@ -23,8 +23,8 @@
namespace NL3D
{
class CParticleSystemProcess;
class CPSLocatedBindable;
class CParticleSystemProcess;
class CPSLocatedBindable;
}
@ -39,7 +39,7 @@ namespace NL3D
* return NULL if the copy failed
*/
NL3D::CParticleSystemProcess *DupPSLocated(const NL3D::CParticleSystemProcess *in);
/** temp : duplicate a located bindable of a particle system
* return NULL if the copy failed
*/

@ -28,12 +28,13 @@
using namespace NL3D;
using namespace NLMISC;
namespace NLQT {
namespace NLQT
{
const int max_range = 9999;
CEditRangeUIntWidget::CEditRangeUIntWidget(QWidget *parent)
: QWidget(parent), _Wrapper(NULL), _emit(true)
: QWidget(parent), _Wrapper(NULL), _emit(true)
{
_ui.setupUi(this);
@ -44,7 +45,7 @@ CEditRangeUIntWidget::CEditRangeUIntWidget(QWidget *parent)
connect(_ui.startSpinBox, SIGNAL(valueChanged(int)), this, SLOT(setMinimum(int)));
connect(_ui.endSpinBox, SIGNAL(valueChanged(int)), this, SLOT(setMaximum(int)));
connect(_ui.horizontalSlider, SIGNAL(valueChanged(int)), this, SLOT(changeSlider(int)));
setValue(0, false);
}
@ -142,13 +143,13 @@ void CEditRangeUIntWidget::updateUi()
}
CEditRangeIntWidget::CEditRangeIntWidget(QWidget *parent)
: QWidget(parent), _Wrapper(NULL)
: QWidget(parent), _Wrapper(NULL)
{
_ui.setupUi(this);
connect(_ui.startSpinBox, SIGNAL(valueChanged(int)), this, SLOT(setMinimum(int)));
connect(_ui.endSpinBox, SIGNAL(valueChanged(int)), this, SLOT(setMaximum(int)));
connect(_ui.horizontalSlider, SIGNAL(valueChanged(int)), this, SLOT(changeSlider(int)));
setValue(0, false);
}
@ -183,7 +184,7 @@ void CEditRangeIntWidget::setValue(sint32 value, bool emit)
_ui.endSpinBox->setValue(value);
if (value < sint32(_ui.startSpinBox->value()))
_ui.startSpinBox->setValue(value);
_emit = emit;
_ui.horizontalSlider->setValue(value);
_emit = true;
@ -331,8 +332,8 @@ void CEditRangeFloatWidget::disableLowerBound(void)
void CEditRangeFloatWidget::changeRange()
{
if ((_ui.startSpinBox->value() < _ui.currentSpinBox->value()) &&
(_ui.endSpinBox->value() > _ui.currentSpinBox->value()))
if ((_ui.startSpinBox->value() < _ui.currentSpinBox->value()) &&
(_ui.endSpinBox->value() > _ui.currentSpinBox->value()))
setValue(_ui.currentSpinBox->value(), false);
}
@ -341,13 +342,13 @@ void CEditRangeFloatWidget::changeSlider(int value)
float delta = _ui.endSpinBox->value() - _ui.startSpinBox->value();
int deltaSlider = _ui.horizontalSlider->maximum() - _ui.horizontalSlider->minimum();
float newValue = _ui.startSpinBox->value() + ((delta / deltaSlider) * value);
_ui.currentSpinBox->blockSignals(true);
_ui.currentSpinBox->setValue(newValue);
_ui.currentSpinBox->blockSignals(false);
// NeL wrapper
if ((_Wrapper != NULL) && (fabs(newValue - _Wrapper->get()) > 0.0001))
if ((_Wrapper != NULL) && (fabs(newValue - _Wrapper->get()) > 0.0001))
_Wrapper->setAndUpdateModifiedFlag(newValue);
if (_emit)

@ -28,18 +28,19 @@
// Project includes
#include "ps_wrapper.h"
namespace NLQT {
namespace NLQT
{
/**
@class CEditRangeUIntWidget
@brief The widget provides a horizontal slider and 3 QSpinBox(to set start/end value range and сurrent value from this range.).
@details Slider sets the uint32 value within a specified range (start/end QSpinBox).
@details Slider sets the uint32 value within a specified range (start/end QSpinBox).
The values range can be set through the class methods: setRange() or setRangeMin(), setRangeMax().
Or the user input values in the widgets start/end QSpinBox.
Also the range of start/end values can be restricted through the class methods: enableLowerBound(), enableUpperBound()
this widget can be used by a two ways: Qt Q_SIGNAL/SLOT or wrapper.
1. Using the Qt Q_SIGNAL/SLOT current value can be set by class methods setValue() and
1. Using the Qt Q_SIGNAL/SLOT current value can be set by class methods setValue() and
changes in current value(QSlider or QSpinBox) the signal valueChanged() will be emitted.
2. Using wrapper, create wpapper struct, example:
@ -51,13 +52,13 @@ struct CMaxNbParticlesWrapper : public IPSWrapperUInt
void set(const uint32 &v) { Located->setMaxSize(v); }
} _MaxNbParticlesWrapper;
@endcode
to set the current values,it is need to call class methods updateUi();
to set the current values,it is need to call class methods updateUi();
*/
class CEditRangeUIntWidget: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
/// Constructor, sets 0 default current value
CEditRangeUIntWidget(QWidget *parent = 0);
@ -67,7 +68,7 @@ public:
/// NB : The 'OwnerNode' field of the wrapper
void setWrapper(IPSWrapperUInt *wrapper);
/// Convenience function to set the minimum, and maximum values with a single function call
/// Convenience function to set the minimum, and maximum values with a single function call
void setRange(uint32 minValue, uint32 maxValue);
/// Set the minimum value that can take range(slider)
@ -85,21 +86,21 @@ public:
/// @param lowerBound - minimum value of the range
/// @param lowerBoundExcluded - if true then the test is <, otherwise its <=
void enableLowerBound(uint32 lowerBound, bool lowerBoundExcluded);
/// Disable upper bound usage
void disableUpperBound(void);
/// Disable lower bound usage
void disableLowerBound(void);
/// With changes wrapper to be called for the installation of new range values
void updateUi();
Q_SIGNALS:
void valueChanged(uint32 value);
public Q_SLOTS:
/// Set current value
/// Set current value
/// @param value - current value
/// @param emit - will emit valueChanged() if the new value is different from the old one and param emit = true
void setValue(uint32 value, bool emit = true);
@ -120,13 +121,13 @@ private:
/**
@class CEditRangeIntWidget
@brief The widget provides a horizontal slider and 3 QSpinBox(to set start/end value range and сurrent value from this range.).
@details Slider sets the sint32 value within a specified range (start/end QSpinBox).
@details Slider sets the sint32 value within a specified range (start/end QSpinBox).
The values range can be set through the class methods: setRange() or setRangeMin(), setRangeMax().
Or the user input values in the widgets start/end QSpinBox.
Also the range of start/end values can be restricted through the class methods: enableLowerBound(), enableUpperBound()
this widget can be used by a two ways: Qt Q_SIGNAL/SLOT or wrapper.
1. Using the Qt Q_SIGNAL/SLOT current value can be set by class methods setValue() and
1. Using the Qt Q_SIGNAL/SLOT current value can be set by class methods setValue() and
changes in current value(QSlider or QSpinBox) the signal valueChanged() will be emitted.
2. Using wrapper, create wpapper struct, example:
@ -138,13 +139,13 @@ struct CRadialViscosityWrapper : public IPSWrapperFloat
void set(const sint32 &value) { V->setRadialViscosity(value); }
} _RadialViscosityWrapper;
@endcode
to set the current values,it is need to call class methods updateUi();
to set the current values,it is need to call class methods updateUi();
*/
class CEditRangeIntWidget: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
/// Constructor, sets 0 default current value
CEditRangeIntWidget(QWidget *parent = 0);
@ -153,8 +154,8 @@ public:
/// set an interface of a wrapper to read / write values in the particle system
/// NB : The 'OwnerNode' field of the wrapper
void setWrapper(IPSWrapperInt *wrapper);
/// Convenience function to set the minimum, and maximum values with a single function call
/// Convenience function to set the minimum, and maximum values with a single function call
void setRange(sint32 minValue, sint32 maxValue);
/// Set the minimum value that can take range(slider)
@ -162,30 +163,30 @@ public:
/// Set the maximum value that can take range(slider)
void setRangeMax(sint32 maxValue);
/// Enable upper bound use (e.g. value must be < or <= upper bound )
/// @param upperBound - maximum value of the range
/// @param upperBoundExcluded - if true then the test is <, otherwise its <=
void enableUpperBound(sint32 upperBound, bool upperBoundExcluded);
/// Enable lower bound use (e.g. value must be < or <= lower bound )
/// @param lowerBound - minimum value of the range
/// @param lowerBoundExcluded - if true then the test is <, otherwise its <=
void enableLowerBound(sint32 lowerBound, bool lowerBoundExcluded);
/// Disable upper bound usage
void disableUpperBound(void);
/// Disable lower bound usage
void disableLowerBound(void);
/// With changes wrapper to be called for the installation of new range values
void updateUi();
Q_SIGNALS:
void valueChanged(sint32 value);
public Q_SLOTS:
public Q_SLOTS:
/// Set current value
/// @param value - current value
/// @param emit - will emit valueChanged() if the new value is different from the old one and param emit = true
@ -207,13 +208,13 @@ private:
/**
@class CEditRangeFloatWidget
@brief The widget provides a horizontal slider and 3 QDoubleSpinBox(to set start/end value range and сurrent value from this range.).
@details Slider sets the float value within a specified range (start/end QDoubleSpinBox).
@details Slider sets the float value within a specified range (start/end QDoubleSpinBox).
The values range can be set through the class methods: setRange() or setRangeMin(), setRangeMax().
Or the user input values in the widgets start/end QDoubleSpinBox.
Also the range of start/end values can be restricted through the class methods: enableLowerBound(), enableUpperBound()
this widget can be used by a two ways: Qt Q_SIGNAL/SLOT or wrapper.
1. Using the Qt Q_SIGNAL/SLOT current value can be set by class methods setValue() and
1. Using the Qt Q_SIGNAL/SLOT current value can be set by class methods setValue() and
changes in current value(only QSlider) the signal valueChanged()will be emitted.
2. Using wrapper, create wpapper struct, example:
@ -225,22 +226,22 @@ struct CTangentialViscosityWrapper : public IPSWrapperFloat
void set(const float &value) { V->setTangentialViscosity(value); }
} _TangentialViscosityWrapper;
@endcode
to set the current values,it is need to call class methods updateUi();
to set the current values,it is need to call class methods updateUi();
*/
class CEditRangeFloatWidget: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
/// Constructor, sets 0 default current value
CEditRangeFloatWidget(QWidget *parent = 0);
~CEditRangeFloatWidget();
/// Set an interface of a wrapper to read / write values in the particle system
/// NB : The 'OwnerNode' field of the wrapper
void setWrapper(IPSWrapperFloat *wrapper);
/// Convenience function to set the minimum, and maximum values with a single function call
/// Convenience function to set the minimum, and maximum values with a single function call
void setRange(float minValue, float maxValue);
/// Set the minimum value that can take range(slider)
@ -248,12 +249,12 @@ public:
/// Set the maximum value that can take range(slider)
void setRangeMax(float maxValue);
/// Enable upper bound use (e.g. value must be < or <= upper bound )
/// @param upperBound - maximum value of the range
/// @param upperBoundExcluded - if true then the test is <, otherwise its <=
void enableUpperBound(float upperBound, bool upperBoundExcluded);
/// Enable lower bound use (e.g. value must be < or <= lower bound )
/// @param lowerBound - minimum value of the range
/// @param lowerBoundExcluded - if true then the test is <, otherwise its <=
@ -271,7 +272,7 @@ public:
Q_SIGNALS:
void valueChanged(float value);
public Q_SLOTS:
public Q_SLOTS:
/// Set current value
/// @param value - current value
/// @param emit - will emit valueChanged() if the new value is different from the old one and param emit = true

@ -21,7 +21,7 @@
#include "emitter_page.h"
// Qt includes
#include <QtGui/QMessageBox>
#include <QtGui/QMessageBox>
// NeL includes
@ -29,11 +29,12 @@
#include "edit_range_widget.h"
#include "modules.h"
namespace NLQT {
namespace NLQT
{
CEmitterPage::CEmitterPage(QWidget *parent)
: QWidget(parent)
: QWidget(parent)
{
_ui.setupUi(this);
@ -48,7 +49,7 @@ CEmitterPage::CEmitterPage(QWidget *parent)
_ui.genNbWidget->setWrapper(&_GenNbWrapper);
_ui.genNbWidget->setSchemeWrapper(&_GenNbWrapper);
_ui.genNbWidget->init();
// deals with emitters that have a direction
_ui.strenghtModulateWidget->setRange(0, 10);
_ui.strenghtModulateWidget->setWrapper(&_ModulatedStrenghtWrapper);
@ -58,7 +59,7 @@ CEmitterPage::CEmitterPage(QWidget *parent)
// SPEED_INHERITANCE_FACTOR
_ui.speedInherFactorWidget->setRange(-1.f, 1.f);
//_ui.speedInherFactorWidget->setWrapper(&_SpeedInheritanceFactorWrapper);
// DELAYED_EMISSION
_ui.delayedEmissionWidget->setRange(0.f, 10.f);
_ui.delayedEmissionWidget->enableLowerBound(0.f, false);
@ -66,10 +67,10 @@ CEmitterPage::CEmitterPage(QWidget *parent)
// MAX_EMISSION_COUNT
_ui.maxEmissionCountWidget->setRange(0, 100);
_ui.maxEmissionCountWidget->enableUpperBound(256, false);
// radius for conic emitter
_ui.radiusWidget->setRange(0.1f, 2.1f);
connect(_ui.emittedTypeComboBox, SIGNAL(currentIndexChanged(int)), this, SLOT(setEmittedType(int)));
connect(_ui.typeEmissionComboBox, SIGNAL(currentIndexChanged(int)), this, SLOT(setTypeOfEmission(int)));
connect(_ui.directionComboBox, SIGNAL(currentIndexChanged(int)), this, SLOT(setDirectionMode(int)));
@ -117,8 +118,8 @@ void CEmitterPage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocatedBind
}
else
_ui.strenghtModulateWidget->hide();
// deals with emitters that have a direction
if (dynamic_cast<NL3D::CPSDirection *>(_Emitter))
{
@ -127,7 +128,7 @@ void CEmitterPage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocatedBind
}
else
_ui.directionWidget->hide();
// radius for conic emitter
if (dynamic_cast<NL3D::CPSEmitterConic *>(_Emitter))
@ -141,7 +142,7 @@ void CEmitterPage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocatedBind
_ui.radiusWidget->hide();
_ui.radiusLabel->hide();
}
_ui.forceConsistentCheckBox->setChecked(_Emitter->isConsistentEmissionEnabled());
_ui.directionComboBox->blockSignals(true);
@ -170,7 +171,7 @@ void CEmitterPage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocatedBind
nlassert(0);
}
_ui.directionComboBox->blockSignals(false);
updatePeriodWidget();
_ui.typeEmissionComboBox->setCurrentIndex(int(_Emitter->getEmissionType()));
@ -193,20 +194,20 @@ void CEmitterPage::setEmittedType(int index)
{
if (_Emitter->getOwner()->getOwner()->getBehaviourType() == NL3D::CParticleSystem::SpellFX || _Emitter->getOwner()->getOwner()->getBypassMaxNumIntegrationSteps())
{
QMessageBox::critical(this, tr("NeL Particle Editor"),
tr("Can't perform operation : the system is flagged with 'No max nb steps' or uses the preset 'Spell FX',"
"and thus, should have a finite duration. This operation create a loop in the system, and so is forbidden."),
QMessageBox::Ok);
QMessageBox::critical(this, tr("NeL Particle Editor"),
tr("Can't perform operation : the system is flagged with 'No max nb steps' or uses the preset 'Spell FX',"
"and thus, should have a finite duration. This operation create a loop in the system, and so is forbidden."),
QMessageBox::Ok);
}
else
{
QMessageBox::critical(this, tr("NeL Particle Editor"),
tr("Loops with emitters are forbidden."),
QMessageBox::Ok);
QMessageBox::critical(this, tr("NeL Particle Editor"),
tr("Loops with emitters are forbidden."),
QMessageBox::Ok);
}
updateEmittedType();
}
Modules::psEdit().resetAutoCount(_Node);
updateModifiedFlag();
}
@ -216,11 +217,11 @@ void CEmitterPage::setTypeOfEmission(int index)
if (_Emitter->getEmissionType() == index) return;
if (!_Emitter->setEmissionType((NL3D::CPSEmitter::TEmissionType) index))
{
QMessageBox::critical(this, tr("NeL Particle Editor"),
tr("Can't perform operation : the system is flagged with 'No max nb steps' or uses the preset 'Spell FX', "
"and thus, should have a finite duration. Please remove that flag first."),
QMessageBox::Ok);
QMessageBox::critical(this, tr("NeL Particle Editor"),
tr("Can't perform operation : the system is flagged with 'No max nb steps' or uses the preset 'Spell FX', "
"and thus, should have a finite duration. Please remove that flag first."),
QMessageBox::Ok);
_ui.typeEmissionComboBox->setCurrentIndex(int(_Emitter->getEmissionType()));
}
@ -250,28 +251,28 @@ void CEmitterPage::setDirectionMode(int index)
nlassert(_Emitter);
switch(index)
{
case Default:
_Emitter->enableSpeedBasisEmission(false);
_Emitter->enableUserMatrixModeForEmissionDirection(false);
case Default:
_Emitter->enableSpeedBasisEmission(false);
_Emitter->enableUserMatrixModeForEmissionDirection(false);
break;
case AlignOnEmitterDirection:
_Emitter->enableSpeedBasisEmission(true);
_Emitter->enableUserMatrixModeForEmissionDirection(false);
case AlignOnEmitterDirection:
_Emitter->enableSpeedBasisEmission(true);
_Emitter->enableUserMatrixModeForEmissionDirection(false);
break;
case InWorld:
_Emitter->enableSpeedBasisEmission(false);
_Emitter->enableUserMatrixModeForEmissionDirection(true);
_Emitter->setUserMatrixModeForEmissionDirection(NL3D::PSIdentityMatrix);
case InWorld:
_Emitter->enableSpeedBasisEmission(false);
_Emitter->enableUserMatrixModeForEmissionDirection(true);
_Emitter->setUserMatrixModeForEmissionDirection(NL3D::PSIdentityMatrix);
break;
case LocalToSystem:
_Emitter->enableSpeedBasisEmission(false);
_Emitter->enableUserMatrixModeForEmissionDirection(true);
_Emitter->setUserMatrixModeForEmissionDirection(NL3D::PSFXWorldMatrix);
case LocalToSystem:
_Emitter->enableSpeedBasisEmission(false);
_Emitter->enableUserMatrixModeForEmissionDirection(true);
_Emitter->setUserMatrixModeForEmissionDirection(NL3D::PSFXWorldMatrix);
break;
case LocalToFatherSkeleton:
_Emitter->enableSpeedBasisEmission(false);
_Emitter->enableUserMatrixModeForEmissionDirection(true);
_Emitter->setUserMatrixModeForEmissionDirection(NL3D::PSUserMatrix);
case LocalToFatherSkeleton:
_Emitter->enableSpeedBasisEmission(false);
_Emitter->enableUserMatrixModeForEmissionDirection(true);
_Emitter->setUserMatrixModeForEmissionDirection(NL3D::PSUserMatrix);
break;
}
updateModifiedFlag();
@ -291,7 +292,7 @@ void CEmitterPage::setConicEmitterRadius(float value)
void CEmitterPage::setEmitDelay(float value)
{
_Emitter->setEmitDelay(value);
_Emitter->setEmitDelay(value);
Modules::psEdit().resetAutoCount(_Node);
updateModifiedFlag();
}
@ -300,11 +301,11 @@ void CEmitterPage::setMaxEmissionCount(uint32 value)
{
if (!_Emitter->setMaxEmissionCount((uint8)value))
{
QMessageBox::critical(this, tr("NeL Particle Editor"),
tr("Can't perform operation : the system is flagged with 'No max nb steps' or uses the preset 'Spell FX', "
"and thus, should have a finite duration. Please remove that flag first."),
QMessageBox::Ok);
QMessageBox::critical(this, tr("NeL Particle Editor"),
tr("Can't perform operation : the system is flagged with 'No max nb steps' or uses the preset 'Spell FX', "
"and thus, should have a finite duration. Please remove that flag first."),
QMessageBox::Ok);
_ui.maxEmissionCountWidget->setValue((uint32)_Emitter->getMaxEmissionCount(), false);
updateModifiedFlag();
@ -321,7 +322,7 @@ void CEmitterPage::setDir(const NLMISC::CVector &value)
void CEmitterPage::updatePeriodWidget()
{
bool bEnable = _Emitter->getEmissionType() == NL3D::CPSEmitter::regular;
_ui.periodWidget->setEnabled(bEnable);
_ui.delayedEmissionWidget->setEnabled(bEnable);
_ui.delayedEmissionLabel->setEnabled(bEnable);
@ -332,13 +333,13 @@ void CEmitterPage::updatePeriodWidget()
void CEmitterPage::updateEmittedType()
{
disconnect(_ui.emittedTypeComboBox, SIGNAL(currentIndexChanged(int)), this, SLOT(setEmittedType(int)));
_ui.emittedTypeComboBox->clear();
_ui.emittedTypeComboBox->addItem(tr("no emission"));
_LocatedList.clear();
_LocatedList.push_back(NULL);
NL3D::CParticleSystem *ps = _Emitter->getOwner()->getOwner();
uint nbLocated = ps->getNbProcess();
uint nbLocated = ps->getNbProcess();
for (uint k = 0; k < nbLocated; ++k)
{
NL3D::CPSLocated *loc = dynamic_cast<NL3D::CPSLocated *>(ps->getProcess(k));
@ -353,25 +354,25 @@ void CEmitterPage::updateEmittedType()
connect(_ui.emittedTypeComboBox, SIGNAL(currentIndexChanged(int)), this, SLOT(setEmittedType(int)));
}
void CEmitterPage::CPeriodWrapper::set(const float &v)
{
void CEmitterPage::CPeriodWrapper::set(const float &v)
{
E->setPeriod(v);
Modules::psEdit().resetAutoCount(Node);
}
void CEmitterPage::CPeriodWrapper::setScheme(scheme_type *s)
{
void CEmitterPage::CPeriodWrapper::setScheme(scheme_type *s)
{
E->setPeriodScheme(s);
Modules::psEdit().resetAutoCount(Node);
}
void CEmitterPage::CGenNbWrapper::set(const uint32 &v)
{
void CEmitterPage::CGenNbWrapper::set(const uint32 &v)
{
E->setGenNb(v);
Modules::psEdit().resetAutoCount(Node);
}
void CEmitterPage::CGenNbWrapper::setScheme(scheme_type *s)
{
void CEmitterPage::CGenNbWrapper::setScheme(scheme_type *s)
{
E->setGenNbScheme(s);
Modules::psEdit().resetAutoCount(Node);
}

@ -33,7 +33,8 @@
#include "particle_node.h"
#include "ps_wrapper.h"
namespace NLQT {
namespace NLQT
{
/**
@class CEmitterPage
@ -41,19 +42,19 @@ namespace NLQT {
*/
class CEmitterPage: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
/// This enum match the option in the combo box that allow to choose how the direction of emission is computed.
enum TDirectionMode
enum TDirectionMode
{
Default = 0,
AlignOnEmitterDirection,
InWorld,
LocalToSystem,
LocalToFatherSkeleton
Default = 0,
AlignOnEmitterDirection,
InWorld,
LocalToSystem,
LocalToFatherSkeleton
};
CEmitterPage(QWidget *parent = 0);
~CEmitterPage();
@ -72,39 +73,63 @@ private Q_SLOTS:
void setEmitDelay(float value);
void setMaxEmissionCount(uint32 value);
void setDir(const NLMISC::CVector &value);
private:
/// period of emission
struct CPeriodWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
struct CPeriodWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
{
CWorkspaceNode *Node;
NL3D::CPSEmitter *E;
float get(void) const { return E->getPeriod(); }
float get(void) const
{
return E->getPeriod();
}
void set(const float &v);
scheme_type *getScheme(void) const { return E->getPeriodScheme(); }
scheme_type *getScheme(void) const
{
return E->getPeriodScheme();
}
void setScheme(scheme_type *s);
} _PeriodWrapper;
/// number of particle to generate each time
struct CGenNbWrapper : public IPSWrapperUInt, IPSSchemeWrapperUInt
struct CGenNbWrapper : public IPSWrapperUInt, IPSSchemeWrapperUInt
{
CWorkspaceNode *Node;
NL3D::CPSEmitter *E;
uint32 get(void) const { return E->getGenNb(); }
uint32 get(void) const
{
return E->getGenNb();
}
void set(const uint32 &v);
scheme_type *getScheme(void) const { return E->getGenNbScheme(); }
scheme_type *getScheme(void) const
{
return E->getGenNbScheme();
}
void setScheme(scheme_type *s);
} _GenNbWrapper;
/// wrappers to emitters that have strenght modulation
struct CModulateStrenghtWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
struct CModulateStrenghtWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
{
NL3D::CPSModulatedEmitter *E;
float get(void) const { return E->getEmitteeSpeed(); }
void set(const float &v) { E->setEmitteeSpeed(v); }
scheme_type *getScheme(void) const { return E->getEmitteeSpeedScheme(); }
void setScheme(scheme_type *s) { E->setEmitteeSpeedScheme(s); }
float get(void) const
{
return E->getEmitteeSpeed();
}
void set(const float &v)
{
E->setEmitteeSpeed(v);
}
scheme_type *getScheme(void) const
{
return E->getEmitteeSpeedScheme();
}
void setScheme(scheme_type *s)
{
E->setEmitteeSpeedScheme(s);
}
} _ModulatedStrenghtWrapper;
// the emitter being edited
@ -112,12 +137,15 @@ private:
// contains pointers to the located
std::vector<NL3D::CPSLocated *> _LocatedList;
void updateEmittedType();
void updatePeriodWidget();
void updateModifiedFlag() { if (_Node) _Node->setModified(true); }
void updateModifiedFlag()
{
if (_Node) _Node->setModified(true);
}
CWorkspaceNode *_Node;

@ -40,7 +40,8 @@
using namespace NLMISC;
using namespace NL3D;
namespace NLQT {
namespace NLQT
{
CSlotInfo& CSlotInfo::operator=(const CSlotInfo & slotInfo)
{
@ -61,12 +62,12 @@ CSlotInfo& CSlotInfo::operator=(const CSlotInfo & slotInfo)
}
return *this;
}
CEntity::CEntity(void):
_Name("<Unknown>"), _FileNameShape(""),
_FileNameSkeleton(""), _inPlace(false), _incPos(false),
_Instance(NULL), _Skeleton(NULL),
_PlayList(NULL), _AnimationSet(NULL)
_Name("<Unknown>"), _FileNameShape(""),
_FileNameSkeleton(""), _inPlace(false), _incPos(false),
_Instance(NULL), _Skeleton(NULL),
_PlayList(NULL), _AnimationSet(NULL)
{
_CharacterScalePos = 1;
}
@ -99,7 +100,7 @@ CEntity::~CEntity(void)
void CEntity::loadAnimation(std::string &fileName)
{
uint id = _AnimationSet->addAnimation(fileName.c_str(),CFile::getFilenameWithoutExtension(fileName).c_str());
uint id = _AnimationSet->addAnimation(fileName.c_str(),CFile::getFilenameWithoutExtension(fileName).c_str());
_AnimationList.push_back(_AnimationSet->getAnimationName(id));
_AnimationSet->build();
if (!_Skeleton.empty()) _PlayList->registerTransform(_Skeleton);
@ -115,30 +116,30 @@ void CEntity::loadSWT(std::string &fileName)
void CEntity::addAnimToPlayList(std::string &name)
{
_PlayListAnimation.push_back(name);
_AnimationStatus.EndAnim = this->getPlayListLength();
_Instance.start();
}
void CEntity::removeAnimToPlayList(uint row)
{
if (row < _PlayListAnimation.size())
_PlayListAnimation.erase(_PlayListAnimation.begin() + row);
_PlayListAnimation.erase(_PlayListAnimation.begin() + row);
_AnimationStatus.EndAnim = this->getPlayListLength();
}
void CEntity::swapAnimToPlayList(uint row1, uint row2)
{
if ((row1 < _PlayListAnimation.size()) && (row2 < _PlayListAnimation.size()))
std::swap(_PlayListAnimation[row1], _PlayListAnimation[row2]);
std::swap(_PlayListAnimation[row1], _PlayListAnimation[row2]);
}
void CEntity::playbackAnim(bool play)
{
_AnimationStatus.PlayAnim = play;
if (play)
_Instance.start();
else
@ -150,7 +151,7 @@ void CEntity::reset()
_PlayListAnimation.clear();
_AnimationList.clear();
_SWTList.clear();
_PlayList->resetAllChannels();
}
@ -173,14 +174,14 @@ float CEntity::getAnimLength(std::string name)
void CEntity::update(NL3D::TAnimationTime time)
{
this->resetChannel();
switch (_AnimationStatus.Mode)
switch (_AnimationStatus.Mode)
{
case Mode::PlayList:
animatePlayList(time);
break;
case Mode::Mixer:
animateChannelMixer();
break;
case Mode::PlayList:
animatePlayList(time);
break;
case Mode::Mixer:
animateChannelMixer();
break;
}
}
@ -188,11 +189,11 @@ void CEntity::update(NL3D::TAnimationTime time)
void CEntity::resetChannel()
{
for(uint i = 0; i < NL3D::CChannelMixer::NumAnimationSlot; i++)
_PlayList->setAnimation(i, UPlayList::empty);
_PlayList->setAnimation(i, UPlayList::empty);
}
void CEntity::addTransformation (CMatrix &current, UAnimation *anim, float begin, float end, UTrack *posTrack, UTrack *rotquatTrack,
UTrack *nextPosTrack, UTrack *nextRotquatTrack, bool removeLast)
void CEntity::addTransformation (CMatrix &current, UAnimation *anim, float begin, float end, UTrack *posTrack, UTrack *rotquatTrack,
UTrack *nextPosTrack, UTrack *nextRotquatTrack, bool removeLast)
{
// In place ?
if (_inPlace)
@ -272,10 +273,10 @@ void CEntity::animatePlayList(NL3D::TAnimationTime time)
{
// Animation index
uint id = _AnimationSet->getAnimationIdByName(_PlayListAnimation[0].c_str());
// Try channel AnimationSet
NL3D::UAnimation *anim = _AnimationSet->getAnimation(id);
bool there = false;
UTrack *posTrack = NULL;
@ -294,7 +295,7 @@ void CEntity::animatePlayList(NL3D::TAnimationTime time)
// Accumul time
float startTime = 0;
float endTime = anim->getEndTime() - anim->getBeginTime();
uint index = 0;
while (time >= endTime)
{
@ -303,7 +304,7 @@ void CEntity::animatePlayList(NL3D::TAnimationTime time)
{
id = _AnimationSet->getAnimationIdByName(_PlayListAnimation[index].c_str());
NL3D::UAnimation *newAnim = _AnimationSet->getAnimation(id);
UTrack *newPosTrack = newAnim->getTrackByName ("pos");
UTrack *newRotquatTrack = newAnim->getTrackByName ("rotquat");
@ -319,14 +320,14 @@ void CEntity::animatePlayList(NL3D::TAnimationTime time)
startTime = endTime;
endTime = startTime + (anim->getEndTime() - anim->getBeginTime());
}
else
else
{
// Add the transformation
addTransformation (current, anim, 0, anim->getEndTime(), posTrack, rotQuatTrack, NULL, NULL, false);
break;
}
}
// Time cropped ?
if (index >= _PlayListAnimation.size())
{
@ -334,24 +335,24 @@ void CEntity::animatePlayList(NL3D::TAnimationTime time)
index--;
id = _AnimationSet->getAnimationIdByName(_PlayListAnimation[index].c_str());
anim = _AnimationSet->getAnimation(id);
// End time for last anim
startTime = anim->getEndTime() - time;
}
else
{
// No
// No
// Add the transformation
addTransformation (current, anim, 0, anim->getBeginTime() + time - startTime, posTrack, rotQuatTrack, NULL, NULL, false);
id = _AnimationSet->getAnimationIdByName(_PlayListAnimation[index].c_str());
anim = _AnimationSet->getAnimation(id);
// Final time
startTime -= anim->getBeginTime();
}
// Set the slot
_PlayList->setAnimation(0, id);
_PlayList->setTimeOrigin(0, startTime);
@ -360,7 +361,7 @@ void CEntity::animatePlayList(NL3D::TAnimationTime time)
_PlayList->setStartWeight(0, 1, 0);
_PlayList->setEndWeight(0, 1, 1);
_PlayList->setWrapMode(0, UPlayList::Clamp);
// Setup the pos and rot for this shape
if (there)
{
@ -391,11 +392,11 @@ void CEntity::animateChannelMixer()
{
// Set the animation
uint animId = _AnimationSet->getAnimationIdByName(_SlotInfo[i].Animation);
if (animId == UAnimationSet::NotFound)
if (animId == UAnimationSet::NotFound)
_PlayList->setAnimation(i, UPlayList::empty);
else
else
_PlayList->setAnimation(i, animId);
// Set the skeleton weight
uint skelId = _AnimationSet->getSkeletonWeightIdByName(_SlotInfo[i].Skeleton);
if (skelId == UAnimationSet::NotFound)
@ -413,15 +414,15 @@ void CEntity::animateChannelMixer()
// Switch between wrap modes
switch (_SlotInfo[i].ClampMode)
{
case 0:
_PlayList->setWrapMode (i, UPlayList::Clamp);
break;
case 1:
_PlayList->setWrapMode (i, UPlayList::Repeat);
break;
case 2:
_PlayList->setWrapMode (i, UPlayList::Disable);
break;
case 0:
_PlayList->setWrapMode (i, UPlayList::Clamp);
break;
case 1:
_PlayList->setWrapMode (i, UPlayList::Repeat);
break;
case 2:
_PlayList->setWrapMode (i, UPlayList::Disable);
break;
}
}
}

@ -36,13 +36,15 @@
#include <nel/3d/u_skeleton.h>
#include <nel/3d/channel_mixer.h>
namespace NL3D {
class UPlayList;
class UAnimationSet;
namespace NL3D
{
class UPlayList;
class UAnimationSet;
}
namespace NLQT {
namespace NLQT
{
class CSlotInfo
{
public:
@ -51,7 +53,7 @@ public:
Offset(0), StartTime(0), EndTime(0),
StartBlend(1), EndBlend (1), Smoothness(1),
SpeedFactor(1), ClampMode(0),
SkeletonInverted(false),
SkeletonInverted(false),
Enable(true) {} ;
std::string Animation;
@ -67,16 +69,16 @@ public:
sint32 ClampMode;
bool SkeletonInverted;
bool Enable;
CSlotInfo &operator=(const CSlotInfo &);
};
/**
@class CEntity
@brief Class manage animated shape.
@details
Allows you to load animations for shape and skeleton weight.
Allows you to load animations for shape and skeleton weight.
Contains a built-in playlist. Has management and playback Playlists or Mixer.
*/
class CEntity
@ -101,131 +103,176 @@ public:
float EndAnim;
float SpeedAnim;
int Mode;
SAnimationStatus():
LoopAnim(false), PlayAnim(false),
CurrentTimeAnim(0), StartAnim(0),
EndAnim(0), SpeedAnim(1), Mode(Mode::PlayList) {}
};
/// Destructor
~CEntity(void);
/// Loads a file animations
/// @param fileName - name animation file
void loadAnimation(std::string &fileName);
/// Loads a file skeleton weight
void loadSWT(std::string &fileName);
/// Adds an animation to a playlist
/// @param name - name loaded animations
void addAnimToPlayList(std::string &name);
/// Removes the animation from a playlist
/// @param row - number of animations in the playlist
void removeAnimToPlayList(uint row);
/// Swaps animations to a playlist
/// @param row1 - first number of animations in the playlist
/// @param row2 - second number of animations in the playlist
void swapAnimToPlayList(uint row1, uint row2);
/// Playback animation
void swapAnimToPlayList(uint row1, uint row2);
/// Playback animation
void playbackAnim(bool play);
/// Reset playlist and animation
void reset();
/// Get the total time of animation playlist
/// @return total time of animation
float getPlayListLength();
/// get time length single animation
float getAnimLength(std::string name);
/// Get slot infomation
void setSlotInfo(uint num, CSlotInfo& slotInfo) { _SlotInfo[num] = slotInfo; }
void setSlotInfo(uint num, CSlotInfo& slotInfo)
{
_SlotInfo[num] = slotInfo;
}
/// Set use mode playlist or mixer
void setMode(int mode) { _AnimationStatus.Mode = mode; }
void setMode(int mode)
{
_AnimationStatus.Mode = mode;
}
/// Set in place mode animation
void setInPlace(bool enabled) { _inPlace = enabled; }
void setInPlace(bool enabled)
{
_inPlace = enabled;
}
/// Get in place mode
bool getInPlace() { return _inPlace; }
bool getInPlace()
{
return _inPlace;
}
/// Set inc position
void setIncPos(bool enabled) { _incPos = enabled; }
void setIncPos(bool enabled)
{
_incPos = enabled;
}
/// Get inc position
bool getIncPos() { return _incPos; }
bool getIncPos()
{
return _incPos;
}
/// Get information about the current status of playing a playlist
/// @return struct containing current information playback
SAnimationStatus getStatus() { return _AnimationStatus; }
SAnimationStatus getStatus()
{
return _AnimationStatus;
}
/// Get name entity
/// @return name entity
std::string getName() { return _Name; }
std::string getName()
{
return _Name;
}
/// Get file name shape
/// @return file name shape
std::string getFileNameShape() { return _FileNameShape; }
std::string getFileNameShape()
{
return _FileNameShape;
}
/// Get file name skeleton
/// @return file name skeleton
std::string getFileNameSkeleton() { return _FileNameSkeleton; }
std::string getFileNameSkeleton()
{
return _FileNameSkeleton;
}
/// Get slot information
CSlotInfo getSlotInfo(uint num) { return _SlotInfo[num]; }
CSlotInfo getSlotInfo(uint num)
{
return _SlotInfo[num];
}
/// Get list loaded animations files
std::vector<std::string>& getAnimationList() { return _AnimationList; }
std::vector<std::string>& getAnimationList()
{
return _AnimationList;
}
/// Get playlist animations
std::vector<std::string>& getPlayListAnimation() { return _PlayListAnimation; }
std::vector<std::string>& getPlayListAnimation()
{
return _PlayListAnimation;
}
/// Get list loaded skeleton weight template files
std::vector<std::string>& getSWTList() { return _SWTList; }
std::vector<std::string>& getSWTList()
{
return _SWTList;
}
/// Get game interface for manipulating Skeleton.
NL3D::USkeleton getSkeleton() const { return _Skeleton; }
NL3D::USkeleton getSkeleton() const
{
return _Skeleton;
}
private:
/// Constructor
/// Constructor
CEntity(void);
/// Update the animate from the playlist or channel mixer
/// @param time - current time in second
void update(NL3D::TAnimationTime time);
void resetChannel();
/// Update the animate from the playlist
void animatePlayList(NL3D::TAnimationTime time);
/// Update the animate from the mixer
void animateChannelMixer();
void addTransformation (NLMISC::CMatrix &current, NL3D::UAnimation *anim,
float begin, float end,
NL3D::UTrack *posTrack, NL3D::UTrack *rotquatTrack,
NL3D::UTrack *nextPosTrack, NL3D::UTrack *nextRotquatTrack,
bool removeLast);
void addTransformation (NLMISC::CMatrix &current, NL3D::UAnimation *anim,
float begin, float end,
NL3D::UTrack *posTrack, NL3D::UTrack *rotquatTrack,
NL3D::UTrack *nextPosTrack, NL3D::UTrack *nextRotquatTrack,
bool removeLast);
// The name of the entity
std::string _Name;
std::string _FileNameShape;
std::string _FileNameSkeleton;
SAnimationStatus _AnimationStatus;
bool _inPlace;
bool _incPos;
float _CharacterScalePos;
// The mesh instance associated to this entity
NL3D::UInstance _Instance;
@ -238,13 +285,13 @@ private:
// Animation input file
std::vector<std::string> _AnimationList;
// Skeleton weight input file
std::vector<std::string> _SWTList;
// Play list animation
std::vector<std::string > _PlayListAnimation;
// Slot info for this object
CSlotInfo _SlotInfo[NL3D::CChannelMixer::NumAnimationSlot];

@ -26,41 +26,42 @@
// Project includes
#include "particle_node.h"
namespace NLQT {
namespace NLQT
{
CFollowPathDialog::CFollowPathDialog(NL3D::CPSPlaneBasisFollowSpeed *pbfs, CWorkspaceNode *ownerNode, QWidget *parent)
: QDialog(parent), _FollowPath(pbfs), _Node(ownerNode)
: QDialog(parent), _FollowPath(pbfs), _Node(ownerNode)
{
resize(270, 90);
QSizePolicy sizePolicy(QSizePolicy::Preferred, QSizePolicy::Fixed);
sizePolicy.setHorizontalStretch(0);
sizePolicy.setVerticalStretch(0);
sizePolicy.setHeightForWidth(this->sizePolicy().hasHeightForWidth());
setSizePolicy(sizePolicy);
setMinimumSize(QSize(0, 90));
setMaximumSize(QSize(16777215, 90));
gridLayout = new QGridLayout(this);
label = new QLabel(this);
gridLayout->addWidget(label, 0, 0, 1, 1);
comboBox = new QComboBox(this);
gridLayout->addWidget(comboBox, 1, 0, 1, 2);
horizontalSpacer = new QSpacerItem(207, 20, QSizePolicy::Expanding, QSizePolicy::Minimum);
gridLayout->addItem(horizontalSpacer, 2, 0, 1, 1);
pushButton = new QPushButton(this);
gridLayout->addWidget(pushButton, 2, 1, 1, 1);
QSizePolicy sizePolicy(QSizePolicy::Preferred, QSizePolicy::Fixed);
sizePolicy.setHorizontalStretch(0);
sizePolicy.setVerticalStretch(0);
sizePolicy.setHeightForWidth(this->sizePolicy().hasHeightForWidth());
setSizePolicy(sizePolicy);
setMinimumSize(QSize(0, 90));
setMaximumSize(QSize(16777215, 90));
gridLayout = new QGridLayout(this);
label = new QLabel(this);
gridLayout->addWidget(label, 0, 0, 1, 1);
comboBox = new QComboBox(this);
gridLayout->addWidget(comboBox, 1, 0, 1, 2);
horizontalSpacer = new QSpacerItem(207, 20, QSizePolicy::Expanding, QSizePolicy::Minimum);
gridLayout->addItem(horizontalSpacer, 2, 0, 1, 1);
pushButton = new QPushButton(this);
gridLayout->addWidget(pushButton, 2, 1, 1, 1);
setWindowTitle(tr("Follow path param"));
label->setText(tr("Projection plane:"));
comboBox->clear();
comboBox->insertItems(0, QStringList()
<< tr("No projection")
<< tr("XY plane")
<< tr("XZ plane")
<< tr("YZ plane"));
pushButton->setText(("Ok"));
<< tr("No projection")
<< tr("XY plane")
<< tr("XZ plane")
<< tr("YZ plane"));
pushButton->setText(("Ok"));
comboBox->setCurrentIndex(_FollowPath->getProjectionPlane());
setFixedHeight(sizeHint().height());
connect(pushButton, SIGNAL(clicked()), this, SLOT(accept()));

@ -29,17 +29,18 @@
namespace NL3D
{
class CPSPlaneBasisFollowSpeed;
class CPSPlaneBasisFollowSpeed;
}
namespace NLQT {
namespace NLQT
{
class CWorkspaceNode;
class CFollowPathDialog : public QDialog
{
Q_OBJECT
Q_OBJECT
public:
CFollowPathDialog(NL3D::CPSPlaneBasisFollowSpeed *pbfs, CWorkspaceNode *ownerNode, QWidget *parent = 0);
~CFollowPathDialog();
@ -53,7 +54,7 @@ protected:
QComboBox *comboBox;
QSpacerItem *horizontalSpacer;
QPushButton *pushButton;
NL3D::CPSPlaneBasisFollowSpeed *_FollowPath;
CWorkspaceNode *_Node;
}; /* class CFollowPathDialog */

@ -24,10 +24,11 @@
#include "modules.h"
#include <nel/3d/u_scene.h>
namespace NLQT {
namespace NLQT
{
CGlobalWindDialog::CGlobalWindDialog(QWidget *parent)
: QDockWidget(parent)
: QDockWidget(parent)
{
_ui.setupUi(this);

@ -28,30 +28,31 @@
// Project includes
namespace NLQT {
namespace NLQT
{
class CGlobalWindDialog: public QDockWidget
{
Q_OBJECT
Q_OBJECT
public:
CGlobalWindDialog(QWidget *parent = 0);
~CGlobalWindDialog();
private Q_SLOTS:
void setWndPower(int value);
void updateWnd(bool visible);
private:
/// wrappers to tune the direction of wind
/* struct CDirectionWrapper : public IPSWrapper<NLMISC::CVector>
{
NLMISC::CVector get(void) const;
void set(const NLMISC::CVector &d);
} _DirectionWrapper;*/
/* struct CDirectionWrapper : public IPSWrapper<NLMISC::CVector>
{
NLMISC::CVector get(void) const;
void set(const NLMISC::CVector &d);
} _DirectionWrapper;*/
Ui::CGlobalWindDialog _ui;
}; /* class CGlobalWindDialog */
} /* namespace NLQT */

@ -27,12 +27,13 @@
// STL includes
namespace NLQT {
namespace NLQT
{
const int directionSize = 35;
CGraphicsInfoWidget::CGraphicsInfoWidget(QWidget *parent)
: QWidget(parent)
: QWidget(parent)
{
_color = Qt::white;
_mode = Mode::Color;
@ -91,10 +92,10 @@ void CGraphicsInfoWidget::paintEvent(QPaintEvent *event)
painter.drawLine(width() / 2, 4, width() / 2, height() - 4);
painter.drawLine(4, height() / 2, width() - 4, height() / 2);
painter.drawText( 10, 15, _text);
painter.setPen(QPen(Qt::red, 2, Qt::SolidLine));
painter.drawLine(width() / 2, height() / 2,
int((width() / 2) + _x * 0.9f * directionSize), int((height() / 2) - _y * 0.9f * directionSize));
painter.drawLine(width() / 2, height() / 2,
int((width() / 2) + _x * 0.9f * directionSize), int((height() / 2) - _y * 0.9f * directionSize));
}
if (_mode == Mode::PlaneBasic)
{
@ -108,25 +109,25 @@ void CGraphicsInfoWidget::paintEvent(QPaintEvent *event)
{
for(uint k = 0; k < _verts.size() / 2; ++k)
{
painter.drawLine(int((width() / 2.0) * (1 + _verts[2 * k].x)),
int((height() / 2.0) * (1 - _verts[2 * k].y)),
int((width() / 2.0) * (1 + _verts[2 * k + 1].x)),
int((height() / 2.0) * (1 - _verts[2 * k + 1].y)));
painter.drawLine(int((width() / 2.0) * (1 + _verts[2 * k].x)),
int((height() / 2.0) * (1 - _verts[2 * k].y)),
int((width() / 2.0) * (1 + _verts[2 * k + 1].x)),
int((height() / 2.0) * (1 - _verts[2 * k + 1].y)));
}
}
else
{
for(uint k = 1; k < _verts.size(); k++)
{
painter.drawLine(int((width() / 2.0) * (1 + _verts[k - 1].x)),
int((height() / 2.0) * (1 - _verts[k - 1].y)),
int((width() / 2.0) * (1 + _verts[ k].x)),
int((height() / 2.0) * (1 - _verts[k].y)));
painter.drawLine(int((width() / 2.0) * (1 + _verts[k - 1].x)),
int((height() / 2.0) * (1 - _verts[k - 1].y)),
int((width() / 2.0) * (1 + _verts[ k].x)),
int((height() / 2.0) * (1 - _verts[k].y)));
}
painter.drawLine(int((width() / 2.0) * (1 + _verts[0].x)),
int((height() / 2.0) * (1 - _verts[0].y)),
int((width() / 2.0) * (1 + _verts[_verts.size() - 1].x)),
int((height() / 2.0) * (1 - _verts[_verts.size() - 1].y)));
painter.drawLine(int((width() / 2.0) * (1 + _verts[0].x)),
int((height() / 2.0) * (1 - _verts[0].y)),
int((width() / 2.0) * (1 + _verts[_verts.size() - 1].x)),
int((height() / 2.0) * (1 - _verts[_verts.size() - 1].y)));
}
}
}
@ -135,7 +136,7 @@ void CGraphicsInfoWidget::mouseDoubleClickEvent(QMouseEvent *event)
{
float vx = (event->x() - (width() / 2)) / 0.9f;
float vy = ((height() / 2) - event->y()) / 0.9f;
Q_EMIT applyNewVector(vx, vy);
}

@ -30,7 +30,8 @@
// Project includes
namespace NLQT {
namespace NLQT
{
struct Mode
{
@ -42,28 +43,28 @@ struct Mode
RibbonShape
};
};
class CGraphicsInfoWidget: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CGraphicsInfoWidget(QWidget *parent = 0);
~CGraphicsInfoWidget();
void setMode(int mode);
void setColor(const QColor &color);
void setVector(float x, float y);
void setText(const QString &text);
void setRibbonShape(const std::vector<NLMISC::CVector> &verts, bool braceMode);
Q_SIGNALS:
void applyNewVector(float x, float y);
protected:
virtual void paintEvent(QPaintEvent *event);
virtual void mouseDoubleClickEvent(QMouseEvent *event);
int _mode;
QColor _color;
float _x;
@ -71,7 +72,7 @@ protected:
QString _text;
std::vector<NLMISC::CVector> _verts;
bool _braceMode;
}; /* class CGraphicsInfoWidget */
} /* namespace NLQT */

@ -43,27 +43,28 @@
using namespace std;
using namespace NL3D;
namespace NLQT {
namespace NLQT
{
CGraphicsViewport::CGraphicsViewport(QWidget *parent)
CGraphicsViewport::CGraphicsViewport(QWidget *parent)
: QNLWidget(parent)
{
}
CGraphicsViewport::~CGraphicsViewport()
{
}
void CGraphicsViewport::init()
{
//H_AUTO2
nldebug("CGraphicsViewport::init");
#if defined(NL_OS_UNIX) && !defined(NL_OS_MAC)
makeCurrent();
#endif // defined(NL_OS_UNIX) && !defined(NL_OS_MAC)
Modules::objView().init((nlWindow)winId(), width(), height());
Modules::psEdit().init();
@ -74,7 +75,7 @@ void CGraphicsViewport::release()
{
//H_AUTO2
nldebug("CGraphicsViewport::release");
Modules::psEdit().release();
Modules::objView().release();
}
@ -89,7 +90,7 @@ QAction *CGraphicsViewport::createSaveScreenshotAction(QObject *parent)
QAction *CGraphicsViewport::createSetBackgroundColor(QObject *parent)
{
QAction *action = new QAction(parent);
QAction *action = new QAction(parent);
connect(action, SIGNAL(triggered()), this, SLOT(setBackgroundColor()));
return action;
}
@ -102,9 +103,9 @@ void CGraphicsViewport::saveScreenshot()
void CGraphicsViewport::setBackgroundColor()
{
QColor color = QColorDialog::getColor(QColor(Modules::objView().getBackgroundColor().R,
Modules::objView().getBackgroundColor().G,
Modules::objView().getBackgroundColor().B));
if (color.isValid())
Modules::objView().getBackgroundColor().G,
Modules::objView().getBackgroundColor().B));
if (color.isValid())
Modules::objView().setBackgroundColor(NLMISC::CRGBA(color.red(), color.green(), color.blue()));
}

@ -44,7 +44,8 @@ typedef QGLWidget QNLWidget;
class QAction;
namespace NLQT {
namespace NLQT
{
/**
@class CGraphicsViewport
@ -58,7 +59,10 @@ public:
CGraphicsViewport(QWidget *parent);
virtual ~CGraphicsViewport();
virtual QPaintEngine* paintEngine() const { return NULL; }
virtual QPaintEngine* paintEngine() const
{
return NULL;
}
void init();
void release();
@ -69,13 +73,13 @@ public:
private Q_SLOTS:
void saveScreenshot();
void setBackgroundColor();
void submitEvents(NLMISC::CEventServer &server, bool allWindows) { }
void emulateMouseRawMode(bool) { }
protected:
virtual void resizeEvent(QResizeEvent *resizeEvent);
#if defined(NL_OS_WINDOWS)
virtual bool winEvent(MSG * message, long * result);
#elif defined(NL_OS_MAC)
@ -83,11 +87,11 @@ protected:
#elif defined(NL_OS_UNIX)
virtual bool x11Event(XEvent *event);
#endif
private:
CGraphicsViewport(const CGraphicsViewport &);
CGraphicsViewport &operator=(const CGraphicsViewport &);
}; /* class CGraphicsViewport */
} /* namespace NLQT */

@ -39,370 +39,413 @@
**
****************************************************************************/
#include "stdpch.h"
#include "stdpch.h"
#include "hoverpoints.h"
#define printf
HoverPoints::HoverPoints(QWidget *widget, PointShape shape)
: QObject(widget)
: QObject(widget)
{
m_widget = widget;
widget->installEventFilter(this);
widget->setAttribute(Qt::WA_AcceptTouchEvents);
m_connectionType = CurveConnection;
m_sortType = NoSort;
m_shape = shape;
m_pointPen = QPen(QColor(255, 255, 255, 191), 1);
m_connectionPen = QPen(QColor(255, 255, 255, 127), 2);
m_pointBrush = QBrush(QColor(191, 191, 191, 127));
m_pointSize = QSize(11, 11);
m_currentIndex = -1;
m_editable = true;
m_enabled = true;
m_minCountPoints = 2;
createGradient();
connect(this, SIGNAL(pointsChanged(QPolygonF)),
m_widget, SLOT(update()));
m_widget = widget;
widget->installEventFilter(this);
widget->setAttribute(Qt::WA_AcceptTouchEvents);
m_connectionType = CurveConnection;
m_sortType = NoSort;
m_shape = shape;
m_pointPen = QPen(QColor(255, 255, 255, 191), 1);
m_connectionPen = QPen(QColor(255, 255, 255, 127), 2);
m_pointBrush = QBrush(QColor(191, 191, 191, 127));
m_pointSize = QSize(11, 11);
m_currentIndex = -1;
m_editable = true;
m_enabled = true;
m_minCountPoints = 2;
createGradient();
connect(this, SIGNAL(pointsChanged(QPolygonF)),
m_widget, SLOT(update()));
}
void HoverPoints::setEnabled(bool enabled)
{
if (m_enabled != enabled) {
m_enabled = enabled;
m_widget->update();
}
if (m_enabled != enabled)
{
m_enabled = enabled;
m_widget->update();
}
}
bool HoverPoints::eventFilter(QObject *object, QEvent *event)
{
if (object == m_widget && m_enabled) {
switch (event->type()) {
case QEvent::MouseButtonPress:
{
if (!m_fingerPointMapping.isEmpty())
return true;
QMouseEvent *me = (QMouseEvent *) event;
QPointF clickPos = me->pos();
int index = -1;
for (int i=0; i<m_points.size(); ++i) {
QPainterPath path;
if (m_shape == CircleShape)
path.addEllipse(pointBoundingRect(i));
else
path.addRect(pointBoundingRect(i));
if (path.contains(clickPos)) {
index = i;
break;
}
}
if (me->button() == Qt::LeftButton) {
if (index == -1) {
if (!m_editable)
return false;
int pos = 0;
// Insert sort for x or y
if (m_sortType == XSort) {
for (int i=0; i<m_points.size(); ++i)
if (m_points.at(i).x() > clickPos.x()) {
pos = i;
break;
}
} else if (m_sortType == YSort) {
for (int i=0; i<m_points.size(); ++i)
if (m_points.at(i).y() > clickPos.y()) {
pos = i;
break;
}
}
m_points.insert(pos, clickPos);
if (object == m_widget && m_enabled)
{
switch (event->type())
{
case QEvent::MouseButtonPress:
{
if (!m_fingerPointMapping.isEmpty())
return true;
QMouseEvent *me = (QMouseEvent *) event;
QPointF clickPos = me->pos();
int index = -1;
for (int i=0; i<m_points.size(); ++i)
{
QPainterPath path;
if (m_shape == CircleShape)
path.addEllipse(pointBoundingRect(i));
else
path.addRect(pointBoundingRect(i));
if (path.contains(clickPos))
{
index = i;
break;
}
}
if (me->button() == Qt::LeftButton)
{
if (index == -1)
{
if (!m_editable)
return false;
int pos = 0;
// Insert sort for x or y
if (m_sortType == XSort)
{
for (int i=0; i<m_points.size(); ++i)
if (m_points.at(i).x() > clickPos.x())
{
pos = i;
break;
}
}
else if (m_sortType == YSort)
{
for (int i=0; i<m_points.size(); ++i)
if (m_points.at(i).y() > clickPos.y())
{
pos = i;
break;
}
}
m_points.insert(pos, clickPos);
m_locks.insert(pos, 0);
m_currentIndex = pos;
firePointChange();
} else {
}
else
{
m_currentIndex = index;
}
return true;
} else if (me->button() == Qt::RightButton) {
if (index >= 0 && m_editable) {
if ((m_points.size() - 1) < m_minCountPoints)
return true;
if (m_locks[index] == 0) {
m_locks.remove(index);
m_points.remove(index);
}
firePointChange();
return true;
}
}
}
break;
case QEvent::MouseButtonRelease:
if (!m_fingerPointMapping.isEmpty())
return true;
m_currentIndex = -1;
break;
case QEvent::MouseMove:
if (!m_fingerPointMapping.isEmpty())
return true;
if (m_currentIndex >= 0)
movePoint(m_currentIndex, ((QMouseEvent *)event)->pos());
break;
case QEvent::TouchBegin:
case QEvent::TouchUpdate:
{
const QTouchEvent *const touchEvent = static_cast<const QTouchEvent*>(event);
const QList<QTouchEvent::TouchPoint> points = touchEvent->touchPoints();
const qreal pointSize = qMax(m_pointSize.width(), m_pointSize.height());
Q_FOREACH (const QTouchEvent::TouchPoint &touchPoint, points) {
const int id = touchPoint.id();
switch (touchPoint.state()) {
case Qt::TouchPointPressed:
{
// find the point, move it
QSet<int> activePoints = QSet<int>::fromList(m_fingerPointMapping.values());
int activePoint = -1;
qreal distance = -1;
const int pointsCount = m_points.size();
const int activePointCount = activePoints.size();
if (pointsCount == 2 && activePointCount == 1) { // only two points
activePoint = activePoints.contains(0) ? 1 : 0;
} else {
for (int i=0; i<pointsCount; ++i) {
if (activePoints.contains(i))
continue;
qreal d = QLineF(touchPoint.pos(), m_points.at(i)).length();
if ((distance < 0 && d < 12 * pointSize) || d < distance) {
distance = d;
activePoint = i;
}
}
}
if (activePoint != -1) {
m_fingerPointMapping.insert(touchPoint.id(), activePoint);
movePoint(activePoint, touchPoint.pos());
}
}
break;
case Qt::TouchPointReleased:
{
// move the point and release
QHash<int,int>::iterator it = m_fingerPointMapping.find(id);
movePoint(it.value(), touchPoint.pos());
m_fingerPointMapping.erase(it);
}
break;
case Qt::TouchPointMoved:
{
// move the point
const int pointIdx = m_fingerPointMapping.value(id, -1);
if (pointIdx >= 0) // do we track this point?
movePoint(pointIdx, touchPoint.pos());
}
break;
default:
break;
}
}
if (m_fingerPointMapping.isEmpty()) {
event->ignore();
return false;
} else {
return true;
}
}
break;
case QEvent::TouchEnd:
if (m_fingerPointMapping.isEmpty()) {
event->ignore();
return false;
}
return true;
break;
case QEvent::Resize:
{
QResizeEvent *e = (QResizeEvent *) event;
if (e->oldSize().width() == 0 || e->oldSize().height() == 0)
break;
qreal stretch_x = e->size().width() / qreal(e->oldSize().width());
qreal stretch_y = e->size().height() / qreal(e->oldSize().height());
for (int i=0; i<m_points.size(); ++i) {
QPointF p = m_points[i];
movePoint(i, QPointF(p.x() * stretch_x, p.y() * stretch_y), false);
}
firePointChange();
break;
}
case QEvent::Paint:
{
QWidget *that_widget = m_widget;
m_widget = 0;
QApplication::sendEvent(object, event);
m_widget = that_widget;
paintPoints();
return true;
}
default:
break;
}
}
return false;
}
return true;
}
else if (me->button() == Qt::RightButton)
{
if (index >= 0 && m_editable)
{
if ((m_points.size() - 1) < m_minCountPoints)
return true;
if (m_locks[index] == 0)
{
m_locks.remove(index);
m_points.remove(index);
}
firePointChange();
return true;
}
}
}
break;
case QEvent::MouseButtonRelease:
if (!m_fingerPointMapping.isEmpty())
return true;
m_currentIndex = -1;
break;
case QEvent::MouseMove:
if (!m_fingerPointMapping.isEmpty())
return true;
if (m_currentIndex >= 0)
movePoint(m_currentIndex, ((QMouseEvent *)event)->pos());
break;
case QEvent::TouchBegin:
case QEvent::TouchUpdate:
{
const QTouchEvent *const touchEvent = static_cast<const QTouchEvent*>(event);
const QList<QTouchEvent::TouchPoint> points = touchEvent->touchPoints();
const qreal pointSize = qMax(m_pointSize.width(), m_pointSize.height());
Q_FOREACH (const QTouchEvent::TouchPoint &touchPoint, points)
{
const int id = touchPoint.id();
switch (touchPoint.state())
{
case Qt::TouchPointPressed:
{
// find the point, move it
QSet<int> activePoints = QSet<int>::fromList(m_fingerPointMapping.values());
int activePoint = -1;
qreal distance = -1;
const int pointsCount = m_points.size();
const int activePointCount = activePoints.size();
if (pointsCount == 2 && activePointCount == 1) // only two points
{
activePoint = activePoints.contains(0) ? 1 : 0;
}
else
{
for (int i=0; i<pointsCount; ++i)
{
if (activePoints.contains(i))
continue;
qreal d = QLineF(touchPoint.pos(), m_points.at(i)).length();
if ((distance < 0 && d < 12 * pointSize) || d < distance)
{
distance = d;
activePoint = i;
}
}
}
if (activePoint != -1)
{
m_fingerPointMapping.insert(touchPoint.id(), activePoint);
movePoint(activePoint, touchPoint.pos());
}
}
break;
case Qt::TouchPointReleased:
{
// move the point and release
QHash<int,int>::iterator it = m_fingerPointMapping.find(id);
movePoint(it.value(), touchPoint.pos());
m_fingerPointMapping.erase(it);
}
break;
case Qt::TouchPointMoved:
{
// move the point
const int pointIdx = m_fingerPointMapping.value(id, -1);
if (pointIdx >= 0) // do we track this point?
movePoint(pointIdx, touchPoint.pos());
}
break;
default:
break;
}
}
if (m_fingerPointMapping.isEmpty())
{
event->ignore();
return false;
}
else
{
return true;
}
}
break;
case QEvent::TouchEnd:
if (m_fingerPointMapping.isEmpty())
{
event->ignore();
return false;
}
return true;
break;
case QEvent::Resize:
{
QResizeEvent *e = (QResizeEvent *) event;
if (e->oldSize().width() == 0 || e->oldSize().height() == 0)
break;
qreal stretch_x = e->size().width() / qreal(e->oldSize().width());
qreal stretch_y = e->size().height() / qreal(e->oldSize().height());
for (int i=0; i<m_points.size(); ++i)
{
QPointF p = m_points[i];
movePoint(i, QPointF(p.x() * stretch_x, p.y() * stretch_y), false);
}
firePointChange();
break;
}
case QEvent::Paint:
{
QWidget *that_widget = m_widget;
m_widget = 0;
QApplication::sendEvent(object, event);
m_widget = that_widget;
paintPoints();
return true;
}
default:
break;
}
}
return false;
}
void HoverPoints::paintPoints()
{
QPainter p;
p.begin(m_widget);
p.setRenderHint(QPainter::Antialiasing);
p.setBrush(m_gradient);
//p.setBrush(QColor(230,230,230));
p.setPen(QPen(Qt::black, 1, Qt::SolidLine, Qt::RoundCap, Qt::RoundJoin));
p.drawRoundedRect(QRect(1, 1, m_widget->width() - 2, m_widget->height() - 2), 4.0, 4.0);
p.setBrush(QBrush());
if (m_connectionPen.style() != Qt::NoPen && m_connectionType != NoConnection) {
p.setPen(m_connectionPen);
if (m_connectionType == CurveConnection) {
QPainterPath path;
path.moveTo(m_points.at(0));
for (int i=1; i<m_points.size(); ++i) {
QPointF p1 = m_points.at(i-1);
QPointF p2 = m_points.at(i);
qreal distance = p2.x() - p1.x();
path.cubicTo(p1.x() + distance / 2, p1.y(),
p1.x() + distance / 2, p2.y(),
p2.x(), p2.y());
}
p.drawPath(path);
} else {
p.drawPolyline(m_points);
}
}
p.setPen(m_pointPen);
p.setBrush(m_pointBrush);
for (int i=0; i<m_points.size(); ++i) {
QRectF bounds = pointBoundingRect(i);
if (m_shape == CircleShape)
p.drawEllipse(bounds);
else
p.drawRect(bounds);
}
QPainter p;
p.begin(m_widget);
p.setRenderHint(QPainter::Antialiasing);
p.setBrush(m_gradient);
//p.setBrush(QColor(230,230,230));
p.setPen(QPen(Qt::black, 1, Qt::SolidLine, Qt::RoundCap, Qt::RoundJoin));
p.drawRoundedRect(QRect(1, 1, m_widget->width() - 2, m_widget->height() - 2), 4.0, 4.0);
p.setBrush(QBrush());
if (m_connectionPen.style() != Qt::NoPen && m_connectionType != NoConnection)
{
p.setPen(m_connectionPen);
if (m_connectionType == CurveConnection)
{
QPainterPath path;
path.moveTo(m_points.at(0));
for (int i=1; i<m_points.size(); ++i)
{
QPointF p1 = m_points.at(i-1);
QPointF p2 = m_points.at(i);
qreal distance = p2.x() - p1.x();
path.cubicTo(p1.x() + distance / 2, p1.y(),
p1.x() + distance / 2, p2.y(),
p2.x(), p2.y());
}
p.drawPath(path);
}
else
{
p.drawPolyline(m_points);
}
}
p.setPen(m_pointPen);
p.setBrush(m_pointBrush);
for (int i=0; i<m_points.size(); ++i)
{
QRectF bounds = pointBoundingRect(i);
if (m_shape == CircleShape)
p.drawEllipse(bounds);
else
p.drawRect(bounds);
}
}
static QPointF bound_point(const QPointF &point, const QRectF &bounds, int lock)
{
QPointF p = point;
QPointF p = point;
qreal left = bounds.left();
qreal right = bounds.right();
qreal top = bounds.top();
qreal bottom = bounds.bottom();
qreal left = bounds.left();
qreal right = bounds.right();
qreal top = bounds.top();
qreal bottom = bounds.bottom();
if (p.x() < left || (lock & HoverPoints::LockToLeft)) p.setX(left);
else if (p.x() > right || (lock & HoverPoints::LockToRight)) p.setX(right);
if (p.x() < left || (lock & HoverPoints::LockToLeft)) p.setX(left);
else if (p.x() > right || (lock & HoverPoints::LockToRight)) p.setX(right);
/* if (p.y() < top || (lock & HoverPoints::LockToTop)) p.setY(top);
else if (p.y() > bottom || (lock & HoverPoints::LockToBottom)) p.setY(bottom);
*/
return p;
/* if (p.y() < top || (lock & HoverPoints::LockToTop)) p.setY(top);
else if (p.y() > bottom || (lock & HoverPoints::LockToBottom)) p.setY(bottom);
*/
return p;
}
void HoverPoints::setPoints(const QPolygonF &points)
{
if (points.size() != m_points.size())
m_fingerPointMapping.clear();
m_points.clear();
for (int i=0; i<points.size(); ++i)
m_points << bound_point(points.at(i), boundingRect(), 0);
m_locks.clear();
if (m_points.size() > 0) {
m_locks.resize(m_points.size());
m_locks.fill(0);
}
if (points.size() != m_points.size())
m_fingerPointMapping.clear();
m_points.clear();
for (int i=0; i<points.size(); ++i)
m_points << bound_point(points.at(i), boundingRect(), 0);
m_locks.clear();
if (m_points.size() > 0)
{
m_locks.resize(m_points.size());
m_locks.fill(0);
}
}
void HoverPoints::movePoint(int index, const QPointF &point, bool emitUpdate)
{
m_points[index] = bound_point(point, boundingRect(), m_locks.at(index));
if (emitUpdate)
firePointChange();
m_points[index] = bound_point(point, boundingRect(), m_locks.at(index));
if (emitUpdate)
firePointChange();
}
void HoverPoints::createGradient()
{
m_gradient.setCoordinateMode(QGradient::ObjectBoundingMode);
m_gradient.setCenter(0.45, 0.50);
m_gradient.setFocalPoint(0.40, 0.45);
m_gradient.setColorAt(0.0, QColor(175, 216, 252));
m_gradient.setColorAt(0.4, QColor(151, 183, 220));
m_gradient.setColorAt(0.8, QColor(86, 126, 191));
m_gradient.setCoordinateMode(QGradient::ObjectBoundingMode);
m_gradient.setCenter(0.45, 0.50);
m_gradient.setFocalPoint(0.40, 0.45);
m_gradient.setColorAt(0.0, QColor(175, 216, 252));
m_gradient.setColorAt(0.4, QColor(151, 183, 220));
m_gradient.setColorAt(0.8, QColor(86, 126, 191));
}
inline static bool x_less_than(const QPointF &p1, const QPointF &p2)
{
return p1.x() < p2.x();
return p1.x() < p2.x();
}
inline static bool y_less_than(const QPointF &p1, const QPointF &p2)
{
return p1.y() < p2.y();
return p1.y() < p2.y();
}
void HoverPoints::firePointChange()
{
if (m_sortType != NoSort) {
QPointF oldCurrent;
if (m_currentIndex != -1) {
oldCurrent = m_points[m_currentIndex];
}
if (m_sortType == XSort)
qSort(m_points.begin(), m_points.end(), x_less_than);
else if (m_sortType == YSort)
qSort(m_points.begin(), m_points.end(), y_less_than);
// Compensate for changed order...
if (m_currentIndex != -1) {
for (int i=0; i<m_points.size(); ++i) {
if (m_points[i] == oldCurrent) {
m_currentIndex = i;
break;
}
}
}
}
Q_EMIT pointsChanged(m_points);
{
if (m_sortType != NoSort)
{
QPointF oldCurrent;
if (m_currentIndex != -1)
{
oldCurrent = m_points[m_currentIndex];
}
if (m_sortType == XSort)
qSort(m_points.begin(), m_points.end(), x_less_than);
else if (m_sortType == YSort)
qSort(m_points.begin(), m_points.end(), y_less_than);
// Compensate for changed order...
if (m_currentIndex != -1)
{
for (int i=0; i<m_points.size(); ++i)
{
if (m_points[i] == oldCurrent)
{
m_currentIndex = i;
break;
}
}
}
}
Q_EMIT pointsChanged(m_points);
}

@ -48,118 +48,167 @@ QT_FORWARD_DECLARE_CLASS(QBypassWidget)
class HoverPoints : public QObject
{
Q_OBJECT
Q_OBJECT
public:
enum PointShape {
CircleShape,
RectangleShape
};
enum PointShape
{
CircleShape,
RectangleShape
};
enum LockType
{
LockToLeft = 0x01,
LockToRight = 0x02,
LockToTop = 0x04,
LockToBottom = 0x08
};
enum SortType
{
NoSort,
XSort,
YSort
};
enum ConnectionType
{
NoConnection,
LineConnection,
CurveConnection
};
HoverPoints(QWidget *widget, PointShape shape);
bool eventFilter(QObject *object, QEvent *event);
void paintPoints();
inline QRectF boundingRect() const;
void setBoundingRect(const QRectF &boundingRect)
{
m_bounds = boundingRect;
}
QPolygonF points() const
{
return m_points;
}
void setPoints(const QPolygonF &points);
QSizeF pointSize() const
{
return m_pointSize;
}
void setPointSize(const QSizeF &size)
{
m_pointSize = size;
}
SortType sortType() const
{
return m_sortType;
}
void setSortType(SortType sortType)
{
m_sortType = sortType;
}
ConnectionType connectionType() const
{
return m_connectionType;
}
void setConnectionType(ConnectionType connectionType)
{
m_connectionType = connectionType;
}
void setConnectionPen(const QPen &pen)
{
m_connectionPen = pen;
}
void setShapePen(const QPen &pen)
{
m_pointPen = pen;
}
void setShapeBrush(const QBrush &brush)
{
m_pointBrush = brush;
}
void setPointLock(int pos, LockType lock)
{
m_locks[pos] = lock;
}
void setEditable(bool editable)
{
m_editable = editable;
}
bool editable() const
{
return m_editable;
}
enum LockType {
LockToLeft = 0x01,
LockToRight = 0x02,
LockToTop = 0x04,
LockToBottom = 0x08
};
enum SortType {
NoSort,
XSort,
YSort
};
enum ConnectionType {
NoConnection,
LineConnection,
CurveConnection
};
HoverPoints(QWidget *widget, PointShape shape);
bool eventFilter(QObject *object, QEvent *event);
void paintPoints();
inline QRectF boundingRect() const;
void setBoundingRect(const QRectF &boundingRect) { m_bounds = boundingRect; }
QPolygonF points() const { return m_points; }
void setPoints(const QPolygonF &points);
QSizeF pointSize() const { return m_pointSize; }
void setPointSize(const QSizeF &size) { m_pointSize = size; }
public Q_SLOTS:
void setEnabled(bool enabled);
void setDisabled(bool disabled)
{
setEnabled(!disabled);
}
SortType sortType() const { return m_sortType; }
void setSortType(SortType sortType) { m_sortType = sortType; }
Q_SIGNALS:
void pointsChanged(const QPolygonF &points);
ConnectionType connectionType() const { return m_connectionType; }
void setConnectionType(ConnectionType connectionType) { m_connectionType = connectionType; }
public:
void firePointChange();
void setConnectionPen(const QPen &pen) { m_connectionPen = pen; }
void setShapePen(const QPen &pen) { m_pointPen = pen; }
void setShapeBrush(const QBrush &brush) { m_pointBrush = brush; }
private:
inline QRectF pointBoundingRect(int i) const;
void movePoint(int i, const QPointF &newPos, bool emitChange = true);
void createGradient();
void setPointLock(int pos, LockType lock) { m_locks[pos] = lock; }
QWidget *m_widget;
void setEditable(bool editable) { m_editable = editable; }
bool editable() const { return m_editable; }
QPolygonF m_points;
QRectF m_bounds;
PointShape m_shape;
SortType m_sortType;
ConnectionType m_connectionType;
public Q_SLOTS:
void setEnabled(bool enabled);
void setDisabled(bool disabled) { setEnabled(!disabled); }
QVector<uint> m_locks;
Q_SIGNALS:
void pointsChanged(const QPolygonF &points);
QSizeF m_pointSize;
int m_currentIndex;
int m_minCountPoints;
bool m_editable;
bool m_enabled;
public:
void firePointChange();
QHash<int, int> m_fingerPointMapping;
private:
inline QRectF pointBoundingRect(int i) const;
void movePoint(int i, const QPointF &newPos, bool emitChange = true);
void createGradient();
QWidget *m_widget;
QPolygonF m_points;
QRectF m_bounds;
PointShape m_shape;
SortType m_sortType;
ConnectionType m_connectionType;
QVector<uint> m_locks;
QSizeF m_pointSize;
int m_currentIndex;
int m_minCountPoints;
bool m_editable;
bool m_enabled;
QHash<int, int> m_fingerPointMapping;
QPen m_pointPen;
QBrush m_pointBrush;
QPen m_connectionPen;
QRadialGradient m_gradient;
QPen m_pointPen;
QBrush m_pointBrush;
QPen m_connectionPen;
QRadialGradient m_gradient;
};
inline QRectF HoverPoints::pointBoundingRect(int i) const
{
QPointF p = m_points.at(i);
qreal w = m_pointSize.width();
qreal h = m_pointSize.height();
qreal x = p.x() - w / 2;
qreal y = p.y() - h / 2;
return QRectF(x, y, w, h);
QPointF p = m_points.at(i);
qreal w = m_pointSize.width();
qreal h = m_pointSize.height();
qreal x = p.x() - w / 2;
qreal y = p.y() - h / 2;
return QRectF(x, y, w, h);
}
inline QRectF HoverPoints::boundingRect() const
{
if (m_bounds.isEmpty())
return m_widget->rect();
else
return m_bounds;
if (m_bounds.isEmpty())
return m_widget->rect();
else
return m_bounds;
}
#endif // HOVERPOINTS_H

@ -29,10 +29,11 @@
// Project includes
#include "modules.h"
namespace NLQT {
namespace NLQT
{
CLocatedBindablePage::CLocatedBindablePage(QWidget *parent)
: QWidget(parent)
: QWidget(parent)
{
_ui.setupUi(this);
@ -57,11 +58,11 @@ CLocatedBindablePage::CLocatedBindablePage(QWidget *parent)
_ui.particlePlaneBasicWidget->setWrapper(&_PlaneBasisWrapper);
_ui.particlePlaneBasicWidget->setSchemeWrapper(&_PlaneBasisWrapper);
_ui.particlePlaneBasicWidget->init();
// Fake motion blur coeff
_ui.blurCoeffWidget->setRange(0.0, 5.0);
_ui.blurCoeffWidget->setWrapper(&_MotionBlurCoeffWrapper);
// Fake motion blur threshold
_ui.blurTresholdWidget->setRange(0.0, 5.0);
_ui.blurTresholdWidget->setWrapper(&_MotionBlurThresholdWrapper);
@ -106,7 +107,7 @@ CLocatedBindablePage::CLocatedBindablePage(QWidget *parent)
// Ribbon texture U factor
_ui.ribbonTexUfactorWidget->setRange(0, 5);
_ui.ribbonTexUfactorWidget->setWrapper(&_RibbonUFactorWrapper);
// Ribbon texture V factor
_ui.ribbonTexVfactorWidget->setRange(0, 5);
_ui.ribbonTexVfactorWidget->setWrapper(&_RibbonVFactorWrapper);
@ -129,9 +130,9 @@ CLocatedBindablePage::CLocatedBindablePage(QWidget *parent)
_ui.particleTextureWidget->setWrapper(&_TextureNoAnimWrapper);
_ui.particleTextureWidget->enableRemoveButton(true);
hideAllWidget();
connect(_ui.autoLodCheckBox, SIGNAL(toggled(bool)), this, SLOT(setAutoLOD(bool)));
connect(_ui.globalColorLightingCheckBox, SIGNAL(toggled(bool)), this, SLOT(setGlobalColorLight(bool)));
connect(_ui.independantSizeCheckBox, SIGNAL(toggled(bool)), this, SLOT(setIndependantSize(bool)));
@ -159,7 +160,7 @@ void CLocatedBindablePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLoc
{
_Node = ownerNode;
_Bindable = locatedBindable;
hideAllWidget();
// No Auto LOD
@ -209,26 +210,26 @@ void CLocatedBindablePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLoc
}
else
_ui.globalColorLightingCheckBox->hide();
// check support for color
if (dynamic_cast<NL3D::CPSColoredParticle *>(_Bindable))
{
_ColorWrapper.S = dynamic_cast<NL3D::CPSColoredParticle *>(_Bindable);
_ui.colorWidget->setWorkspaceNode(_Node);
_ui.colorWidget->updateUi();
// Add material page in tabWidget
_ui.tabWidget->addTab(_ui.materialPage, tr("Material"));
}
if (dynamic_cast<NL3D::CPSSizedParticle *>(_Bindable))
if (dynamic_cast<NL3D::CPSSizedParticle *>(_Bindable))
{
updateSizeControl();
// Size/Angle2D page in tabWidget
_ui.tabWidget->addTab(_ui.sizeAnglePage, tr("Size/Angle 2D"));
}
// check support for angle 2D
if (dynamic_cast<NL3D::CPSRotated2DParticle *>(_Bindable))
{
@ -239,7 +240,7 @@ void CLocatedBindablePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLoc
}
else
_ui.angle2DWidget->hide();
// check support for plane basis
if (dynamic_cast<NL3D::CPSRotated3DPlaneParticle *>(_Bindable))
{
@ -247,7 +248,7 @@ void CLocatedBindablePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLoc
_ui.particlePlaneBasicWidget->setWorkspaceNode(_Node);
_ui.particlePlaneBasicWidget->updateUi();
_ui.particlePlaneBasicWidget->setEnabled(true);
// Add material page in tabWidget
_ui.tabWidget->addTab(_ui.rotatePage, tr("Rotations"));
}
@ -275,18 +276,18 @@ void CLocatedBindablePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLoc
_MotionBlurThresholdWrapper.P = fla;
_MotionBlurThresholdWrapper.OwnerNode = _Node;
_ui.blurTresholdWidget->updateUi();
_ui.zalignCheckBox->show();
_ui.alignCheckBox->show();
_ui.alignCheckBox->setChecked(fla->getAlignOnMotion());
_ui.zalignCheckBox->setChecked(fla->getAlignOnZAxis());
// 'look at' independant sizes
_ui.independantSizeCheckBox->setChecked(fla->hasIndependantSizes());
_ui.independantSizeCheckBox->show();
_ui.independantGroupBox->show();
// Add Look at page in tabWidget
_ui.tabWidget->addTab(_ui.lookAtPage, tr("Look At param"));
}
@ -300,7 +301,7 @@ void CLocatedBindablePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLoc
if (dynamic_cast<NL3D::CPSShockWave *>(_Bindable))
{
NL3D::CPSShockWave *sw = static_cast<NL3D::CPSShockWave *>(_Bindable);
_RadiusCutWrapper.OwnerNode = _Node;
_RadiusCutWrapper.S = sw;
_ui.radiusCutWidget->updateUi();
@ -323,19 +324,19 @@ void CLocatedBindablePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLoc
_FanLightWrapper.OwnerNode = _Node;
_FanLightWrapper.P = dynamic_cast<NL3D::CPSFanLight *>(_Bindable);
_ui.nbFanLightWidget->updateUi();
_FanLightSmoothnessWrapper.OwnerNode = _Node;
_FanLightSmoothnessWrapper.P = static_cast<NL3D::CPSFanLight *>(_Bindable);
_ui.phaseSmoothnesWidget->updateUi();
_FanLightPhaseWrapper.OwnerNode = _Node;
_FanLightPhaseWrapper.P = static_cast<NL3D::CPSFanLight *>(_Bindable);
_ui.fanLightSpeedWidget->updateUi();
_FanLightIntensityWrapper.OwnerNode = _Node;
_FanLightIntensityWrapper.P = static_cast<NL3D::CPSFanLight *>(_Bindable);
_ui.fanLightIntensityWidget->updateUi();
// Add Fan Light page in tabWidget
_ui.tabWidget->addTab(_ui.fanLightPage, tr("Fan Light param"));
}
@ -349,14 +350,14 @@ void CLocatedBindablePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLoc
_TailParticleWrapper.OwnerNode = _Node;
_TailParticleWrapper.P = dynamic_cast<NL3D::CPSTailParticle *>(_Bindable);
_ui.tailNbSegsWidget->updateUi();
_ui.tailWidget->setCurrentTailParticle(_Node, dynamic_cast<NL3D::CPSTailParticle *>(_Bindable));
_ui.ribbonTexUfactorWidget->hide();
_ui.ribbonTexVfactorWidget->hide();
_ui.tailTexUflabel->hide();
_ui.tailTexVflabel->hide();
// Add tail page in tabWidget
_ui.tabWidget->addTab(_ui.ribbonTailPage, tr("Tail param"));
}
@ -384,10 +385,10 @@ void CLocatedBindablePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLoc
if (dynamic_cast<NL3D::CPSTexturedParticle *>(_Bindable))
{
_ui.texAnimWidget->setCurrentTextureAnim(dynamic_cast<NL3D::CPSTexturedParticle *>(_Bindable),
dynamic_cast<NL3D::CPSMultiTexturedParticle *>(_Bindable),
_Node);
dynamic_cast<NL3D::CPSMultiTexturedParticle *>(_Bindable),
_Node);
_ui.texAnimWidget->show();
_ui.tabWidget->addTab(_ui.texturePage, tr("Texture param"));
}
else
@ -401,7 +402,7 @@ void CLocatedBindablePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLoc
_ui.particleTextureWidget->updateUi();
_ui.particleTextureWidget->show();
_ui.tabWidget->addTab(_ui.texturePage, tr("Texture param"));
}
else
@ -417,7 +418,7 @@ void CLocatedBindablePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLoc
_RibbonVFactorWrapper.OwnerNode = _Node;
_RibbonVFactorWrapper.R = static_cast<NL3D::CPSRibbon *>(_Bindable);
_ui.ribbonTexVfactorWidget->updateUi();
_ui.ribbonTexUfactorWidget->show();
_ui.ribbonTexVfactorWidget->show();
_ui.tailTexUflabel->show();
@ -441,12 +442,12 @@ void CLocatedBindablePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLoc
_LODDegradationWrapper.OwnerNode = _Node;
_LODDegradationWrapper.R = ribbon;
_ui.lodDegradationWidget->updateUi();
// Coord system
_ui.coordSystemComboBox->setCurrentIndex(ribbon->getMatrixMode());
_ui.useHermitteCheckBox->setChecked(ribbon->getInterpolationMode() == NL3D::CPSRibbonBase::Hermitte);
_ui.constantLengthCheckBox->setChecked(ribbon->getRibbonMode() == NL3D::CPSRibbonBase::FixedSize);
}
}
}
}
@ -569,7 +570,7 @@ void CLocatedBindablePage::setRotSpeedMax(double value)
nlassert(rotatedParticle);
float valueMin, valueMax;
uint32 nbModels = rotatedParticle->checkHintRotateTheSame(valueMin, valueMax);
if (valueMax != value)
if (valueMax != value)
{
rotatedParticle->hintRotateTheSame(nbModels, valueMin, value);
updateModifiedFlag();
@ -582,7 +583,7 @@ void CLocatedBindablePage::setRotSpeedMin(double value)
nlassert(rotatedParticle);
float valueMin, valueMax;
uint32 nbModels = rotatedParticle->checkHintRotateTheSame(valueMin, valueMax);
if (valueMin != value)
if (valueMin != value)
{
rotatedParticle->hintRotateTheSame(nbModels, value, valueMax);
updateModifiedFlag();
@ -595,9 +596,9 @@ void CLocatedBindablePage::setNumModels(int value)
nlassert(rotatedParticle);
float valueMin, valueMax;
sint32 nbModels;
nbModels = rotatedParticle->checkHintRotateTheSame(valueMin, valueMax);
if (nbModels != value)
if (nbModels != value)
{
rotatedParticle->hintRotateTheSame((uint32) value, valueMin, valueMax);
updateModifiedFlag();
@ -640,7 +641,7 @@ void CLocatedBindablePage::updateValidWidgetForAlignOnMotion(bool align)
void CLocatedBindablePage::updateSizeControl()
{
if (!dynamic_cast<NL3D::CPSSizedParticle *>(_Bindable)) return;
NL3D::CPSFaceLookAt *fla = dynamic_cast<NL3D::CPSFaceLookAt *>(_Bindable);
// LookAt case
if (fla && fla->hasIndependantSizes())
@ -649,7 +650,7 @@ void CLocatedBindablePage::updateSizeControl()
_ui.sizeWidget->setTitle(tr("Width"));
else
_ui.sizeWidget->setTitle(tr("Height"));
if (_ui.widthRadioButton->isChecked()) // wrap to the wanted size
_SizeWrapper.S = fla;
else
@ -660,7 +661,7 @@ void CLocatedBindablePage::updateSizeControl()
_SizeWrapper.S = dynamic_cast<NL3D::CPSSizedParticle *>(_Bindable);
_ui.sizeWidget->setTitle(tr("Size"));
}
_ui.sizeWidget->setWorkspaceNode(_Node);
_ui.sizeWidget->updateUi();
}
@ -677,7 +678,7 @@ void CLocatedBindablePage::hideAllWidget()
void CLocatedBindablePage::touchPSState()
{
if (_Node && _Node->getPSModel())
{
{
_Node->getPSModel()->touchTransparencyState();
_Node->getPSModel()->touchLightableState();
}

@ -37,7 +37,8 @@
#include "ps_wrapper.h"
#include "particle_node.h"
namespace NLQT {
namespace NLQT
{
/**
@class CLocatedBindablePage
@ -45,8 +46,8 @@ namespace NLQT {
*/
class CLocatedBindablePage: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CLocatedBindablePage(QWidget *parent = 0);
~CLocatedBindablePage();
@ -77,181 +78,328 @@ private:
/// Wrappers to various element of bindables
/// Size
struct CSizeWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
struct CSizeWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
{
NL3D::CPSSizedParticle *S;
float get(void) const { return S->getSize(); }
void set(const float &v) { S->setSize(v); }
scheme_type *getScheme(void) const { return S->getSizeScheme(); }
void setScheme(scheme_type *s) { S->setSizeScheme(s); }
float get(void) const
{
return S->getSize();
}
void set(const float &v)
{
S->setSize(v);
}
scheme_type *getScheme(void) const
{
return S->getSizeScheme();
}
void setScheme(scheme_type *s)
{
S->setSizeScheme(s);
}
} _SizeWrapper;
/// Color
struct CColorWrapper : public IPSWrapperRGBA, IPSSchemeWrapperRGBA
{
NL3D::CPSColoredParticle *S;
NLMISC::CRGBA get(void) const { return S->getColor(); }
void set(const NLMISC::CRGBA &v) { S->setColor(v); }
scheme_type *getScheme(void) const { return S->getColorScheme(); }
void setScheme(scheme_type *s) { S->setColorScheme(s); }
NLMISC::CRGBA get(void) const
{
return S->getColor();
}
void set(const NLMISC::CRGBA &v)
{
S->setColor(v);
}
scheme_type *getScheme(void) const
{
return S->getColorScheme();
}
void setScheme(scheme_type *s)
{
S->setColorScheme(s);
}
} _ColorWrapper;
/// Angle 2D
struct CAngle2DWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
{
NL3D::CPSRotated2DParticle *S;
float get(void) const { return S->getAngle2D(); }
void set(const float &v) { S->setAngle2D(v); }
scheme_type *getScheme(void) const { return S->getAngle2DScheme(); }
void setScheme(scheme_type *s) { S->setAngle2DScheme(s); }
float get(void) const
{
return S->getAngle2D();
}
void set(const float &v)
{
S->setAngle2D(v);
}
scheme_type *getScheme(void) const
{
return S->getAngle2DScheme();
}
void setScheme(scheme_type *s)
{
S->setAngle2DScheme(s);
}
} _Angle2DWrapper;
/// Plane basis
struct CPlaneBasisWrapper : public IPSWrapper<NL3D::CPlaneBasis>, IPSSchemeWrapper<NL3D::CPlaneBasis>
{
NL3D::CPSRotated3DPlaneParticle *S;
NL3D::CPlaneBasis get(void) const { return S->getPlaneBasis(); }
void set(const NL3D::CPlaneBasis &p) { S->setPlaneBasis(p); }
scheme_type *getScheme(void) const { return S->getPlaneBasisScheme(); }
void setScheme(scheme_type *s) { S->setPlaneBasisScheme(s); }
NL3D::CPlaneBasis get(void) const
{
return S->getPlaneBasis();
}
void set(const NL3D::CPlaneBasis &p)
{
S->setPlaneBasis(p);
}
scheme_type *getScheme(void) const
{
return S->getPlaneBasisScheme();
}
void setScheme(scheme_type *s)
{
S->setPlaneBasisScheme(s);
}
} _PlaneBasisWrapper;
/// Motion blur coeff
struct CMotionBlurCoeffWrapper : public IPSWrapperFloat
{
NL3D::CPSFaceLookAt *P;
float get(void) const { return P->getMotionBlurCoeff(); }
void set(const float &v) { P->setMotionBlurCoeff(v); }
float get(void) const
{
return P->getMotionBlurCoeff();
}
void set(const float &v)
{
P->setMotionBlurCoeff(v);
}
} _MotionBlurCoeffWrapper;
struct CMotionBlurThresholdWrapper : public IPSWrapperFloat
{
NL3D::CPSFaceLookAt *P;
float get(void) const { return P->getMotionBlurThreshold(); }
void set(const float &v) { P->setMotionBlurThreshold(v); }
float get(void) const
{
return P->getMotionBlurThreshold();
}
void set(const float &v)
{
P->setMotionBlurThreshold(v);
}
} _MotionBlurThresholdWrapper;
/// Fanlight
/// Fanlight
struct CFanLightWrapper : public IPSWrapperUInt
{
NL3D::CPSFanLight *P;
uint32 get(void) const { return P->getNbFans(); }
void set(const uint32 &v) { P->setNbFans(v); }
uint32 get(void) const
{
return P->getNbFans();
}
void set(const uint32 &v)
{
P->setNbFans(v);
}
} _FanLightWrapper;
struct CFanLightSmoothnessWrapper : public IPSWrapperUInt
{
NL3D::CPSFanLight *P;
uint32 get(void) const { return P->getPhaseSmoothness(); }
void set(const uint32 &v) { P->setPhaseSmoothness(v); }
uint32 get(void) const
{
return P->getPhaseSmoothness();
}
void set(const uint32 &v)
{
P->setPhaseSmoothness(v);
}
} _FanLightSmoothnessWrapper;
struct CFanLightPhase : public IPSWrapperFloat
{
NL3D::CPSFanLight *P;
float get(void) const { return P->getPhaseSpeed(); }
void set(const float &v) { P->setPhaseSpeed(v); }
float get(void) const
{
return P->getPhaseSpeed();
}
void set(const float &v)
{
P->setPhaseSpeed(v);
}
} _FanLightPhaseWrapper;
struct CFanLightIntensityWrapper : public IPSWrapperFloat
{
NL3D::CPSFanLight *P;
float get(void) const { return P->getMoveIntensity(); }
void set(const float &v) { P->setMoveIntensity(v); }
float get(void) const
{
return P->getMoveIntensity();
}
void set(const float &v)
{
P->setMoveIntensity(v);
}
} _FanLightIntensityWrapper;
/// Ribbon / tail dot
struct CTailParticleWrapper : public IPSWrapperUInt
{
NL3D::CPSTailParticle *P;
uint32 get(void) const { return P->getTailNbSeg(); }
void set(const uint32 &v) { P->setTailNbSeg(v); }
uint32 get(void) const
{
return P->getTailNbSeg();
}
void set(const uint32 &v)
{
P->setTailNbSeg(v);
}
} _TailParticleWrapper;
/// Duration of segment for a ribbon
struct CSegDurationWrapper : public IPSWrapperFloat
{
NL3D::CPSRibbonBase *R;
float get(void) const { return R->getSegDuration(); }
void set(const float &v) { R->setSegDuration(v); }
float get(void) const
{
return R->getSegDuration();
}
void set(const float &v)
{
R->setSegDuration(v);
}
} _SegDurationWrapper;
/// Shockwave
struct CRadiusCutWrapper : public IPSWrapperFloat
{
NL3D::CPSShockWave *S;
float get(void) const { return S->getRadiusCut(); }
void set(const float &v) { S->setRadiusCut(v); }
float get(void) const
{
return S->getRadiusCut();
}
void set(const float &v)
{
S->setRadiusCut(v);
}
} _RadiusCutWrapper;
struct CShockWaveNbSegWrapper : public IPSWrapperUInt
{
NL3D::CPSShockWave *S;
uint32 get(void) const { return S->getNbSegs(); }
void set(const uint32 &v) { S->setNbSegs(v); }
uint32 get(void) const
{
return S->getNbSegs();
}
void set(const uint32 &v)
{
S->setNbSegs(v);
}
} _ShockWaveNbSegWrapper;
struct CShockWaveUFactorWrapper : public IPSWrapperFloat
{
NL3D::CPSShockWave *S;
float get(void) const { return S->getUFactor(); }
void set(const float &v) { S->setUFactor(v); }
float get(void) const
{
return S->getUFactor();
}
void set(const float &v)
{
S->setUFactor(v);
}
} _ShockWaveUFactorWrapper;
/// Unanimated texture
struct CTextureNoAnimWrapper : public IPSWrapperTexture
{
NL3D::CPSTexturedParticleNoAnim *TP;
virtual NL3D::ITexture *get(void) { return TP->getTexture(); }
virtual void set(NL3D::ITexture *t) { TP->setTexture(t); }
virtual NL3D::ITexture *get(void)
{
return TP->getTexture();
}
virtual void set(NL3D::ITexture *t)
{
TP->setTexture(t);
}
} _TextureNoAnimWrapper;
/// u / v factors for ribbon
struct CRibbonUFactorWrapper : public IPSWrapperFloat
{
NL3D::CPSRibbon *R;
float get(void) const { return R->getUFactor(); }
void set(const float &u) { R->setTexFactor(u, R->getVFactor()); }
float get(void) const
{
return R->getUFactor();
}
void set(const float &u)
{
R->setTexFactor(u, R->getVFactor());
}
} _RibbonUFactorWrapper;
struct CRibbonVFactorWrapper : public IPSWrapperFloat
{
NL3D::CPSRibbon *R;
float get(void) const { return R->getVFactor(); }
void set(const float &v) { R->setTexFactor(R->getUFactor(), v); }
float get(void) const
{
return R->getVFactor();
}
void set(const float &v)
{
R->setTexFactor(R->getUFactor(), v);
}
} _RibbonVFactorWrapper;
struct CRibbonLengthWrapper : IPSWrapperFloat
{
NL3D::CPSRibbonBase *R;
float get() const { return R->getRibbonLength(); }
void set(const float &v) { R->setRibbonLength(v); }
float get() const
{
return R->getRibbonLength();
}
void set(const float &v)
{
R->setRibbonLength(v);
}
} _RibbonLengthWrapper;
struct CLODDegradationWrapper : IPSWrapperFloat
{
NL3D::CPSRibbonBase *R;
float get() const { return R->getLODDegradation(); }
void set(const float &v) { R->setLODDegradation(v); }
float get() const
{
return R->getLODDegradation();
}
void set(const float &v)
{
R->setLODDegradation(v);
}
} _LODDegradationWrapper;
void updateValidWidgetForAlignOnMotion(bool align);
void updateSizeControl();
void updateModifiedFlag() { if (_Node) _Node->setModified(true); }
void updateModifiedFlag()
{
if (_Node) _Node->setModified(true);
}
void hideAllWidget();
void touchPSState();
CWorkspaceNode *_Node;
/// The bindable being edited
NL3D::CPSLocatedBindable *_Bindable;
Ui::CLocatedBindablePage _ui;
}; /* class CLocatedBindablePage */
} /* namespace NLQT */

@ -22,7 +22,7 @@
// Qt includes
#include <QtGui/QMessageBox>
#include <QtGui/QInputDialog>
#include <QtGui/QInputDialog>
// NeL includes
#include <nel/3d/particle_system.h>
@ -30,13 +30,14 @@
// Project includes
#include "modules.h"
namespace NLQT {
namespace NLQT
{
CLocatedPage::CLocatedPage(QWidget *parent)
: QWidget(parent)
: QWidget(parent)
{
_ui.setupUi(this);
_ui.lifeWidget->setRange(0, 10);
_ui.lifeWidget->setWrapper(&_LifeWrapper);
_ui.lifeWidget->setSchemeWrapper(&_LifeWrapper);
@ -44,7 +45,7 @@ CLocatedPage::CLocatedPage(QWidget *parent)
///_ui.lifeWidget->enableLowerBound(0, true);
_ui.lifeWidget->enableMemoryScheme(false);
_ui.lifeWidget->init();
_ui.massWidget->setRange(0.001f, 10);
_ui.massWidget->setWrapper(&_MassWrapper);
_ui.massWidget->setSchemeWrapper(&_MassWrapper);
@ -52,10 +53,10 @@ CLocatedPage::CLocatedPage(QWidget *parent)
///_ui.massWidget->enableLowerBound(0, true);
_ui.massWidget->enableMemoryScheme(false);
_ui.massWidget->init();
_ui.maxNumParticleWidget->setRange(1, 501);
_ui.maxNumParticleWidget->enableUpperBound(1 << 16, true);
connect(_ui.coordSystemComboBox, SIGNAL(currentIndexChanged(int)), this, SLOT(setMatrixMode(int)));
connect(_ui.disgradeWithLODCheckBox, SIGNAL(toggled(bool)), this, SLOT(setDisgradeWithLod(bool)));
connect(_ui.parametricMotionCheckBox, SIGNAL(toggled(bool)), this, SLOT(setParametricMotion(bool)));
@ -75,12 +76,12 @@ void CLocatedPage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocated *lo
{
_Located = located;
_Node = ownerNode;
_LifeWrapper.Located = _Located;
_LifeWrapper.Node = _Node;
_ui.lifeWidget->setWorkspaceNode(_Node);
_ui.lifeWidget->updateUi();
if (_Located->getLastForever())
_ui.lifeWidget->setEnabled(false);
@ -89,17 +90,17 @@ void CLocatedPage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocated *lo
_ui.massWidget->setWorkspaceNode(_Node);
_ui.massWidget->updateUi();
if (_Located->getOwner())
_ui.maxNumParticleWidget->setEnabled(!_Located->getOwner()->getAutoCountFlag());
if (_Located->getOwner())
_ui.maxNumParticleWidget->setEnabled(!_Located->getOwner()->getAutoCountFlag());
_ui.maxNumParticleWidget->setValue(_Located->getMaxSize(), false);
_ui.maxNumParticleWidget->setValue(_Located->getMaxSize(), false);
_ui.coordSystemComboBox->setCurrentIndex(int(_Located->getMatrixMode()));
_ui.limitedLifeTimeCheckBox->setChecked(!_Located->getLastForever());
_ui.lifeWidget->setEnabled(!_Located->getLastForever());
_ui.trigerOnDeathCheckBox->setChecked(_Located->isTriggerOnDeathEnabled());
updateTriggerOnDeath();
_ui.disgradeWithLODCheckBox->setChecked(_Located->hasLODDegradation());
updateIntegrable();
updateTriggerOnDeath();
@ -127,13 +128,13 @@ void CLocatedPage::setLimitedLifeTime(bool state)
forceApplied = true;
break;
}
}
}
if (forceApplied)
{
int ret = QMessageBox::critical(this, tr("NeL particle system editor"),
tr("The object has force(s) applied on it. If it last forever, "
"its motion can become instable after a while. Continue anyway ? (clue : you've been warned ..)"),
QMessageBox::Ok | QMessageBox::Cancel);
int ret = QMessageBox::critical(this, tr("NeL particle system editor"),
tr("The object has force(s) applied on it. If it last forever, "
"its motion can become instable after a while. Continue anyway ? (clue : you've been warned ..)"),
QMessageBox::Ok | QMessageBox::Cancel);
if (ret == QMessageBox::Cancel)
{
@ -147,10 +148,10 @@ void CLocatedPage::setLimitedLifeTime(bool state)
}
else
{
QMessageBox::critical(this, tr("NeL particle system editor"),
tr("Can't perform operation : the system is flagged with 'No max nb steps' or uses the preset 'Spell FX', "
"and thus, should have a finite duration. Please remove that flag first."),
QMessageBox::Ok);
QMessageBox::critical(this, tr("NeL particle system editor"),
tr("Can't perform operation : the system is flagged with 'No max nb steps' or uses the preset 'Spell FX', "
"and thus, should have a finite duration. Please remove that flag first."),
QMessageBox::Ok);
_ui.limitedLifeTimeCheckBox->setChecked(true);
}
}
@ -184,10 +185,10 @@ void CLocatedPage::setParametricMotion(bool state)
void CLocatedPage::editTriggerOnDeath()
{
bool ok;
bool ok;
int i = QInputDialog::getInt(this, tr("Set the extern ID"),
tr("0 means no extern access."),
_Located->getTriggerEmitterID(), 0, 9999, 1, &ok);
tr("0 means no extern access."),
_Located->getTriggerEmitterID(), 0, 9999, 1, &ok);
if (ok)
{
_Located->setTriggerEmitterID(uint32(i));
@ -233,7 +234,7 @@ void CLocatedPage::setNewMaxSize(uint32 value)
/// WARNING:
///TreeCtrl->suppressLocatedInstanceNbItem(*Node, v);
}
_Located->resize(value);
_Located->resize(value);
updateModifiedFlag();
}
@ -246,21 +247,21 @@ void CLocatedPage::updateIntegrable(void)
void CLocatedPage::updateTriggerOnDeath(void)
{
nlassert(_Located);
nlassert(_Located);
bool enable = !_Located->getLastForever();
_ui.trigerOnDeathCheckBox->setEnabled(enable);
_ui.editPushButton->setEnabled(enable && _Located->isTriggerOnDeathEnabled());
}
void CLocatedPage::CLifeWrapper::set(const float &v)
{
void CLocatedPage::CLifeWrapper::set(const float &v)
{
Located->setInitialLife(v);
Modules::psEdit().resetAutoCount(Node);
}
void CLocatedPage::CLifeWrapper::setScheme(scheme_type *s)
{
void CLocatedPage::CLifeWrapper::setScheme(scheme_type *s)
{
Located->setLifeScheme(s);
Modules::psEdit().resetAutoCount(Node);
}
} /* namespace NLQT */

@ -33,10 +33,11 @@
namespace NL3D
{
class CPSLocated;
class CPSLocated;
}
namespace NLQT {
namespace NLQT
{
/**
@class CLocatedPage
@ -44,15 +45,15 @@ namespace NLQT {
*/
class CLocatedPage: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CLocatedPage(QWidget *parent = 0);
~CLocatedPage();
/// Set the located to edit.
void setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocated *located);
private Q_SLOTS:
void setDisabledCountPS(bool state);
void setLimitedLifeTime(bool state);
@ -70,21 +71,39 @@ private:
/// wrapper to tune the mass of particles
struct CMassWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
{
NL3D::CPSLocated *Located;
float get(void) const { return Located->getInitialMass(); }
void set(const float &v) { Located->setInitialMass(v); }
virtual scheme_type *getScheme(void) const { return Located->getMassScheme(); }
virtual void setScheme(scheme_type *s) { Located->setMassScheme(s); }
NL3D::CPSLocated *Located;
float get(void) const
{
return Located->getInitialMass();
}
void set(const float &v)
{
Located->setInitialMass(v);
}
virtual scheme_type *getScheme(void) const
{
return Located->getMassScheme();
}
virtual void setScheme(scheme_type *s)
{
Located->setMassScheme(s);
}
} _MassWrapper;
struct CLifeWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
{
NL3D::CPSLocated *Located;
CWorkspaceNode *Node;
float get(void) const { return Located->getInitialLife(); }
void set(const float &v);
virtual scheme_type *getScheme(void) const { return Located->getLifeScheme(); }
virtual void setScheme(scheme_type *s);
NL3D::CPSLocated *Located;
CWorkspaceNode *Node;
float get(void) const
{
return Located->getInitialLife();
}
void set(const float &v);
virtual scheme_type *getScheme(void) const
{
return Located->getLifeScheme();
}
virtual void setScheme(scheme_type *s);
} _LifeWrapper;
/// the located this dialog is editing
@ -98,7 +117,10 @@ private:
/// update the 'trigger on death' control
void updateTriggerOnDeath(void);
void updateModifiedFlag() { if (_Node) _Node->setModified(true); }
void updateModifiedFlag()
{
if (_Node) _Node->setModified(true);
}
Ui::CLocatedPage _ui;
}; /* class CLocatedPage */

@ -32,9 +32,11 @@
using namespace std;
using namespace NLMISC;
namespace NLQT {
namespace NLQT
{
namespace {
namespace
{
CFileDisplayer *s_FileDisplayer = NULL;
@ -57,7 +59,7 @@ CFileDisplayer *s_FileDisplayer = NULL;
sint main(int argc, char **argv)
{
// go nel!
// go nel!
{
// use log.log if NEL_LOG_IN_FILE and NLQT_USE_LOG_LOG defined as 1
createDebug(NULL, NLQT_USE_LOG_LOG, false);
@ -74,10 +76,10 @@ sint main(int argc, char **argv)
WarningLog->addDisplayer(NLQT::s_FileDisplayer);
AssertLog->addDisplayer(NLQT::s_FileDisplayer);
ErrorLog->addDisplayer(NLQT::s_FileDisplayer);
#endif
#endif
nlinfo("Welcome to NeL!");
NLMISC::CPath::remapExtension("tga", "png", true);
}
@ -85,7 +87,7 @@ sint main(int argc, char **argv)
QSplashScreen *splash = new QSplashScreen();
splash->setPixmap(QPixmap(":/images/nel_ide_load.png"));
splash->show();
Modules::init();
// load and set remap extensions from config

@ -49,17 +49,18 @@
using namespace std;
using namespace NLMISC;
namespace NLQT {
namespace NLQT
{
CMainWindow::CMainWindow(QWidget *parent)
: QMainWindow(parent),
_isGraphicsInitialized(false), _isGraphicsEnabled(false),
_isSoundInitialized(false), _isSoundEnabled(false),
_isLandscapeInitialized(false), _isLandscapeEnabled(false),
_GraphicsViewport(NULL), _lastDir(".")
_isGraphicsInitialized(false), _isGraphicsEnabled(false),
_isSoundInitialized(false), _isSoundEnabled(false),
_isLandscapeInitialized(false), _isLandscapeEnabled(false),
_GraphicsViewport(NULL), _lastDir(".")
{
nldebug("CMainWindow::CMainWindow:");
// create NeL viewport
_GraphicsViewport = new CGraphicsViewport(this);
setCentralWidget(_GraphicsViewport);
@ -78,9 +79,9 @@ CMainWindow::CMainWindow(QWidget *parent)
createMenus();
createToolBars();
createStatusBar();
setWindowIcon(QIcon(":/images/nel.png"));
QSettings settings("object_viewer_qt.ini", QSettings::IniFormat);
settings.beginGroup("WindowSettings");
restoreState(settings.value("QtWindowState").toByteArray());
@ -90,25 +91,25 @@ CMainWindow::CMainWindow(QWidget *parent)
_isGraphicsEnabled = true;
_isLandscapeEnabled = true;
// As a special case, a QTimer with a timeout of 0 will time out as soon as all the events in the window system's event queue have been processed.
// As a special case, a QTimer with a timeout of 0 will time out as soon as all the events in the window system's event queue have been processed.
// This can be used to do heavy work while providing a snappy user interface.
_mainTimer = new QTimer(this);
connect(_mainTimer, SIGNAL(timeout()), this, SLOT(updateRender()));
// timer->start(); // <- timeout 0
// it's heavy on cpu, though, when no 3d driver initialized :)
_mainTimer->start(25); // 25fps
_statusBarTimer = new QTimer(this);
connect(_statusBarTimer, SIGNAL(timeout()), this, SLOT(updateStatusBar()));
_statusBarTimer->start(5000);
Modules::config().setAndCallback("SoundEnabled", CConfigCallback(this, &CMainWindow::cfcbSoundEnabled));
}
CMainWindow::~CMainWindow()
{
nldebug("CMainWindow::~CMainWindow:");
nldebug("CMainWindow::~CMainWindow:");
// save state & geometry of window and widgets
QSettings settings("object_viewer_qt.ini", QSettings::IniFormat);
settings.beginGroup("WindowSettings");
@ -159,23 +160,23 @@ int CMainWindow::getFrameRate()
void CMainWindow::open()
{
QStringList fileNames = QFileDialog::getOpenFileNames(this,
tr("Open NeL data file"), _lastDir,
tr("All NeL files (*.shape *.ps);;"
"NeL shape files (*.shape);;"
"NeL particle system files (*.ps)"));
tr("Open NeL data file"), _lastDir,
tr("All NeL files (*.shape *.ps);;"
"NeL shape files (*.shape);;"
"NeL particle system files (*.ps)"));
setCursor(Qt::WaitCursor);
if (!fileNames.isEmpty())
if (!fileNames.isEmpty())
{
QStringList list = fileNames;
_lastDir = QFileInfo(list.front()).absolutePath();
QString skelFileName = QFileDialog::getOpenFileName(this,
tr("Open skeleton file"), _lastDir,
tr("NeL skeleton file (*.skel)"));
tr("Open skeleton file"), _lastDir,
tr("NeL skeleton file (*.skel)"));
Q_FOREACH(QString fileName, list)
loadFile(fileName, skelFileName);
loadFile(fileName, skelFileName);
_AnimationSetDialog->updateListObject();
_AnimationSetDialog->updateListAnim();
@ -203,14 +204,14 @@ void CMainWindow::settings()
void CMainWindow::about()
{
QMessageBox::about(this, tr("About Object Viewer Qt"),
tr("<h2>Object Viewer Qt 8-)</h2>"
"<p> Authors: dnk-88, sfb, Kaetemi, kervala <p>Compiled on %1 %2").arg(__DATE__).arg(__TIME__));
tr("<h2>Object Viewer Qt 8-)</h2>"
"<p> Authors: dnk-88, sfb, Kaetemi, kervala <p>Compiled on %1 %2").arg(__DATE__).arg(__TIME__));
}
void CMainWindow::updateStatusBar()
{
if (_isGraphicsInitialized)
statusBar()->showMessage(QString(Modules::objView().getDriver()->getVideocardInformation()));
if (_isGraphicsInitialized)
statusBar()->showMessage(QString(Modules::objView().getDriver()->getVideocardInformation()));
}
void CMainWindow::updateInitialization(bool visible)
@ -221,7 +222,7 @@ void CMainWindow::updateInitialization(bool visible)
done = true; // set false whenever change
bool wantSound = _isSoundEnabled && visible;
bool wantGraphics = _isGraphicsEnabled && visible;
// TODO WARNING: made Landscape stuff
// TODO WARNING: made Landscape stuff
bool wantLandscape = wantGraphics && _isGraphicsInitialized && _isLandscapeEnabled;
// .. stuff that depends on other stuff goes on top to prioritize deinitialization
@ -273,7 +274,7 @@ void CMainWindow::updateInitialization(bool visible)
done = false;
}
}
// Sound (AudioMixer)
if (_isSoundInitialized)
{
@ -298,17 +299,18 @@ void CMainWindow::updateInitialization(bool visible)
}
}
} while (!done);
}
while (!done);
}
void CMainWindow::createActions()
{
{
_openAction = new QAction(tr("&Open..."), this);
_openAction->setIcon(QIcon(":/images/open-file.png"));
_openAction->setShortcut(QKeySequence::Open);
_openAction->setStatusTip(tr("Open an existing file"));
connect(_openAction, SIGNAL(triggered()), this, SLOT(open()));
_exitAction = new QAction(tr("E&xit"), this);
_exitAction->setShortcut(tr("Ctrl+Q"));
_exitAction->setStatusTip(tr("Exit the application"));
@ -318,7 +320,7 @@ void CMainWindow::createActions()
_setBackColorAction->setText(tr("Set &background color"));
_setBackColorAction->setIcon(QIcon(":/images/ico_bgcolor.png"));
_setBackColorAction->setStatusTip(tr("Set background color"));
_resetSceneAction = new QAction(tr("&Reset scene"), this);
_resetSceneAction->setStatusTip(tr("Reset current scene"));
connect(_resetSceneAction, SIGNAL(triggered()), this, SLOT(resetScene()));
@ -331,7 +333,7 @@ void CMainWindow::createActions()
_settingsAction->setIcon(QIcon(":/images/preferences.png"));
_settingsAction->setStatusTip(tr("Settings"));
connect(_settingsAction, SIGNAL(triggered()), this, SLOT(settings()));
_aboutAction = new QAction(tr("&About"), this);
_aboutAction->setStatusTip(tr("Show the application's About box"));
connect(_aboutAction, SIGNAL(triggered()), this, SLOT(about()));
@ -351,43 +353,43 @@ void CMainWindow::createMenus()
_viewMenu = menuBar()->addMenu(tr("&View"));
_viewMenu->addAction(_setBackColorAction);
_viewMenu->addAction(_SetupFog->toggleViewAction());
_sceneMenu = menuBar()->addMenu(tr("&Scene"));
_sceneMenu->addAction(_resetSceneAction);
_sceneMenu->addAction(_saveScreenshotAction);
_toolsMenu = menuBar()->addMenu(tr("&Tools"));
_toolsMenu->addAction(_AnimationDialog->toggleViewAction());
_AnimationDialog->toggleViewAction()->setIcon(QIcon(":/images/anim.png"));
_toolsMenu->addAction(_AnimationSetDialog->toggleViewAction());
_AnimationSetDialog->toggleViewAction()->setIcon(QIcon(":/images/animset.png"));
_toolsMenu->addAction(_SlotManagerDialog->toggleViewAction());
_SlotManagerDialog->toggleViewAction()->setIcon(QIcon(":/images/mixer.png"));
_toolsMenu->addAction(_ParticleControlDialog->toggleViewAction());
_ParticleControlDialog->toggleViewAction()->setIcon(QIcon(":/images/pqrticles.png"));
_toolsMenu->addAction(_DayNightDialog->toggleViewAction());
_DayNightDialog->toggleViewAction()->setIcon(QIcon(":/images/dqynight.png"));
_toolsMenu->addAction(_WaterPoolDialog->toggleViewAction());
_WaterPoolDialog->toggleViewAction()->setIcon(QIcon(":/images/water.png"));
_WaterPoolDialog->toggleViewAction()->setEnabled(false);
_toolsMenu->addAction(_VegetableDialog->toggleViewAction());
_VegetableDialog->toggleViewAction()->setIcon(QIcon(":/images/veget.png"));
_toolsMenu->addAction(_GlobalWindDialog->toggleViewAction());
_GlobalWindDialog->toggleViewAction()->setIcon(QIcon(":/images/wind.png"));
_toolsMenu->addAction(_SkeletonScaleDialog->toggleViewAction());
_SkeletonScaleDialog->toggleViewAction()->setIcon(QIcon(":/images/ico_skelscale.png"));
_toolsMenu->addAction(_SunColorDialog->toggleViewAction());
connect(_ParticleControlDialog->toggleViewAction(), SIGNAL(triggered(bool)),
_ParticleWorkspaceDialog, SLOT(setVisible(bool)));
@ -395,7 +397,7 @@ void CMainWindow::createMenus()
_ParticleWorkspaceDialog->_PropertyDialog, SLOT(setVisible(bool)));
_toolsMenu->addSeparator();
_toolsMenu->addAction(_settingsAction);
menuBar()->addSeparator();
@ -409,7 +411,7 @@ void CMainWindow::createToolBars()
{
_fileToolBar = addToolBar(tr("&File"));
_fileToolBar->addAction(_openAction);
//_editToolBar = addToolBar(tr("&Edit"));
//_editToolBar->addSeparator();
_toolsBar = addToolBar(tr("&Tools"));
@ -435,7 +437,7 @@ void CMainWindow::createDialogs()
_AnimationDialog = new CAnimationDialog(this);
addDockWidget(Qt::BottomDockWidgetArea, _AnimationDialog);
_AnimationDialog->setVisible(false);
// create animation set manager dialog
_AnimationSetDialog = new CAnimationSetDialog(this);
addDockWidget(Qt::LeftDockWidgetArea, _AnimationSetDialog);
@ -445,7 +447,7 @@ void CMainWindow::createDialogs()
_SlotManagerDialog = new CSlotManagerDialog(this);
addDockWidget(Qt::RightDockWidgetArea, _SlotManagerDialog);
_SlotManagerDialog->setVisible(false);
// create particle control dialog
_ParticleControlDialog = new CParticleControlDialog(_SkeletonTreeModel ,this);
addDockWidget(Qt::BottomDockWidgetArea, _ParticleControlDialog);
@ -475,7 +477,7 @@ void CMainWindow::createDialogs()
_GlobalWindDialog = new CGlobalWindDialog(this);
addDockWidget(Qt::TopDockWidgetArea, _GlobalWindDialog);
_GlobalWindDialog->setVisible(false);
// create sun color dialog
_SunColorDialog = new CSunColorDialog(this);
addDockWidget(Qt::LeftDockWidgetArea, _SunColorDialog);
@ -489,12 +491,12 @@ void CMainWindow::createDialogs()
_SkeletonScaleDialog = new CSkeletonScaleDialog(_SkeletonTreeModel, this);
addDockWidget(Qt::RightDockWidgetArea, _SkeletonScaleDialog);
_SkeletonScaleDialog->setVisible(false);
// create setup fog dialog
_SetupFog = new CSetupFog(this);
addDockWidget(Qt::RightDockWidgetArea, _SetupFog);
_SetupFog->setVisible(false);
connect(_ParticleControlDialog, SIGNAL(changeState()), _ParticleWorkspaceDialog, SLOT(setNewState()));
connect(_ParticleWorkspaceDialog, SIGNAL(changeActiveNode()), _ParticleControlDialog, SLOT(updateActiveNode()));
connect(_AnimationSetDialog->ui.setLengthPushButton, SIGNAL(clicked()), _AnimationDialog, SLOT(changeAnimLength()));
@ -535,23 +537,23 @@ void CMainWindow::cfcbSoundEnabled(NLMISC::CConfigFile::CVar &var)
void CMainWindow::updateRender()
{
updateInitialization(isVisible());
if (isVisible())
{
// call all update functions
// 01. Update Utilities (configuration etc)
// 02. Update Time (deltas)
// ...
// 03. Update Receive (network, servertime, receive messages)
// ...
// 04. Update Input (keyboard controls, etc)
if (_isGraphicsInitialized)
Modules::objView().updateInput();
// 05. Update Weather (sky, snow, wind, fog, sun)
// ...
@ -563,29 +565,29 @@ void CMainWindow::updateRender()
// 07. Update Landscape (async zone loading near entity)
// 08. Update Collisions (entities)
// - Update entities
// - Update move container (swap with Update entities? todo: check code!)
// - Update bullets
Modules::veget().update();
// 09. Update Animations (playlists)
// - Needs to be either before or after entities, not sure,
// - Needs to be either before or after entities, not sure,
// there was a problem with wrong order a while ago!!!
Modules::objView().updateAnimatePS();
Modules::objView().updateAnimation(_AnimationDialog->getTime());
// 09.2 Update Particle system editor
Modules::psEdit().update();
// 10. Update Camera (depends on entities)
// ...
// 11. Update Interface (login, ui, etc)
// ...
// 12. Update Sound (sound driver)
if (_isSoundInitialized)
{
@ -594,24 +596,24 @@ void CMainWindow::updateRender()
}
// 13. Update Send (network, send new position etc)
// ...
// 14. Update Debug (stuff for dev)
// ...
if (_isGraphicsInitialized && !Modules::objView().getDriver()->isLost())
{
// 01. Render Driver (background color)
// 01. Render Driver (background color)
Modules::objView().renderDriver(); // clear all buffers
// 02. Render Sky (sky scene)
// ...
// 04. Render Scene (entity scene)
Modules::objView().renderScene();
// 05. Render Effects (flare)
// ...
// 06. Render Interface 3D (player names)
// ...
@ -620,7 +622,7 @@ void CMainWindow::updateRender()
// 08. Render Interface 2D (chatboxes etc, optionally does have 3d)
// ...
// 09. Render Debug 2D (stuff for dev)
Modules::objView().renderDebug2D();

@ -30,11 +30,13 @@
// Project includes
namespace NLMISC {
class CConfigFile;
namespace NLMISC
{
class CConfigFile;
}
namespace NLQT {
namespace NLQT
{
class CGraphicsViewport;
class CAnimationDialog;
@ -60,10 +62,12 @@ public:
~CMainWindow();
virtual void setVisible(bool visible);
int getFrameRate();
CSkeletonTreeModel *getSkeletonModel() const
{ return _SkeletonTreeModel; }
{
return _SkeletonTreeModel;
}
private Q_SLOTS:
void open();
@ -72,7 +76,7 @@ private Q_SLOTS:
void about();
void updateStatusBar();
void updateRender();
private:
void createActions();
void createMenus();
@ -82,11 +86,11 @@ private:
void updateInitialization(bool visible);
bool loadFile(const QString &fileName, const QString &skelName);
void cfcbQtStyle(NLMISC::CConfigFile::CVar &var);
void cfcbQtPalette(NLMISC::CConfigFile::CVar &var);
void cfcbSoundEnabled(NLMISC::CConfigFile::CVar &var);
bool _isGraphicsInitialized, _isGraphicsEnabled;
bool _isSoundInitialized, _isSoundEnabled;
bool _isLandscapeInitialized, _isLandscapeEnabled;
@ -106,7 +110,7 @@ private:
CSunColorDialog *_SunColorDialog;
CSkeletonTreeModel *_SkeletonTreeModel;
QPalette _originalPalette;
QString _lastDir;

@ -34,13 +34,14 @@
#include "mesh_widget.h"
#include "morph_mesh_dialog.h"
namespace NLQT {
namespace NLQT
{
CMeshWidget::CMeshWidget(QWidget *parent)
: QGroupBox(parent)
: QGroupBox(parent)
{
_ui.setupUi(this);
connect(_ui.browsePushButton, SIGNAL(clicked(bool)), this, SLOT(browseShape()));
connect(_ui.editPushButton, SIGNAL(clicked(bool)), this, SLOT(editMorph()));
connect(_ui.morphCheckBox, SIGNAL(toggled(bool)), this, SLOT(setMorphMesh(bool)));
@ -54,11 +55,11 @@ void CMeshWidget::setCurrentShape(CWorkspaceNode *ownerNode, NL3D::CPSShapeParti
{
_Node = ownerNode;
_ShapeParticle = sp;
if (!dynamic_cast<NL3D::CPSConstraintMesh *>(_ShapeParticle))
{
_ui.groupBox->hide();
_ui.browsePushButton->setEnabled(true);
_ui.browsePushButton->setEnabled(true);
_ui.meshLineEdit->setEnabled(true);
_ui.label->setEnabled(true);
_ui.meshLineEdit->setText(_ShapeParticle->getShape().c_str());
@ -69,7 +70,7 @@ void CMeshWidget::setCurrentShape(CWorkspaceNode *ownerNode, NL3D::CPSShapeParti
NL3D::CPSConstraintMesh *cm = NLMISC::safe_cast<NL3D::CPSConstraintMesh *>(_ShapeParticle);
if (cm->getNumShapes() > 1)
_ui.morphCheckBox->setChecked(true);
else
else
_ui.morphCheckBox->setChecked(false);
updateForMorph();
@ -79,11 +80,11 @@ void CMeshWidget::setCurrentShape(CWorkspaceNode *ownerNode, NL3D::CPSShapeParti
void CMeshWidget::browseShape()
{
QString fileName = QFileDialog::getOpenFileName(this,
tr("Open NeL data file"), ".",
tr("NeL shape file (*.shape)"));
tr("Open NeL data file"), ".",
tr("NeL shape file (*.shape)"));
setCursor(Qt::WaitCursor);
if (!fileName.isEmpty())
if (!fileName.isEmpty())
{
NLMISC::CPath::addSearchPath(NLMISC::CFile::getPath(fileName.toStdString()));
try
@ -137,11 +138,11 @@ void CMeshWidget::editMorph()
void CMeshWidget::updateForMorph()
{
NL3D::CPSConstraintMesh *cm = NLMISC::safe_cast<NL3D::CPSConstraintMesh *>(_ShapeParticle);
NL3D::CPSConstraintMesh *cm = NLMISC::safe_cast<NL3D::CPSConstraintMesh *>(_ShapeParticle);
if (cm)
{
bool enable = cm->getNumShapes() > 1;
_ui.browsePushButton->setEnabled(!enable);
_ui.browsePushButton->setEnabled(!enable);
_ui.meshLineEdit->setEnabled(!enable);
_ui.label->setEnabled(!enable);
if (!enable)
@ -163,7 +164,7 @@ void CMeshWidget::updateMeshErrorString()
if (numVerts.empty()) return;
if (numVerts.size() == 1)
_ui.infoLabel->setText(getShapeErrorString(numVerts[0]));
else
{
// display error msg for morphed meshs
@ -185,10 +186,13 @@ QString CMeshWidget::getShapeErrorString(sint errorCode)
{
switch(errorCode)
{
case NL3D::CPSConstraintMesh::ShapeFileIsNotAMesh: return tr("Not a mesh");
case NL3D::CPSConstraintMesh::ShapeFileNotLoaded: return tr("Shape not loaded");
case NL3D::CPSConstraintMesh::ShapeHasTooMuchVertices: return tr("Too much vertices");
default:
case NL3D::CPSConstraintMesh::ShapeFileIsNotAMesh:
return tr("Not a mesh");
case NL3D::CPSConstraintMesh::ShapeFileNotLoaded:
return tr("Shape not loaded");
case NL3D::CPSConstraintMesh::ShapeHasTooMuchVertices:
return tr("Too much vertices");
default:
break;
};
return QString();

@ -33,41 +33,45 @@
namespace NL3D
{
struct CPSShapeParticle;
struct CPSShapeParticle;
}
namespace NLQT {
namespace NLQT
{
class CMeshWidget: public QGroupBox
{
Q_OBJECT
Q_OBJECT
public:
CMeshWidget(QWidget *parent = 0);
~CMeshWidget();
void setCurrentShape(CWorkspaceNode *ownerNode, NL3D::CPSShapeParticle *sp);
QString getShapeErrorString(sint errorCode);
private Q_SLOTS:
void browseShape();
void setMorphMesh(bool state);
void editMorph();
private:
CWorkspaceNode *_Node;
NL3D::CPSShapeParticle *_ShapeParticle;
void updateForMorph();
void updateMeshErrorString();
void updateModifiedFlag() { if (_Node) _Node->setModified(true); }
void updateModifiedFlag()
{
if (_Node) _Node->setModified(true);
}
void touchPSState();
Ui::CMeshWidget _ui;
}; /* class CMeshWidget */

@ -31,7 +31,7 @@ void Modules::init()
{
if (_configuration == NULL) _configuration = new NLQT::CConfiguration;
config().init();
if (_objectViewer == NULL) _objectViewer = new NLQT::CObjectViewer;
if (_soundSystem == NULL) _soundSystem = new NLQT::CSoundSystem;
if (_particleEditor == NULL) _particleEditor = new NLQT::CParticleEditor;
@ -41,12 +41,18 @@ void Modules::init()
void Modules::release()
{
delete _mainWindow; _mainWindow = NULL;
delete _particleEditor; _particleEditor = NULL;
delete _vegetableEditor; _vegetableEditor = NULL;
delete _soundSystem; _soundSystem = NULL;
delete _objectViewer; _objectViewer = NULL;
delete _mainWindow;
_mainWindow = NULL;
delete _particleEditor;
_particleEditor = NULL;
delete _vegetableEditor;
_vegetableEditor = NULL;
delete _soundSystem;
_soundSystem = NULL;
delete _objectViewer;
_objectViewer = NULL;
config().release();
delete _configuration; _configuration = NULL;
delete _configuration;
_configuration = NULL;
}

@ -36,13 +36,31 @@ class Modules
public:
static void init();
static void release();
static NLQT::CConfiguration &config() { return *_configuration; }
static NLQT::CObjectViewer &objView() { return *_objectViewer; }
static NLQT::CMainWindow &mainWin() { return *_mainWindow; }
static NLQT::CParticleEditor &psEdit() { return *_particleEditor; }
static NLQT::CSoundSystem &sound() { return *_soundSystem; }
static NLQT::CVegetableEditor &veget() { return *_vegetableEditor; }
static NLQT::CConfiguration &config()
{
return *_configuration;
}
static NLQT::CObjectViewer &objView()
{
return *_objectViewer;
}
static NLQT::CMainWindow &mainWin()
{
return *_mainWindow;
}
static NLQT::CParticleEditor &psEdit()
{
return *_particleEditor;
}
static NLQT::CSoundSystem &sound()
{
return *_soundSystem;
}
static NLQT::CVegetableEditor &veget()
{
return *_vegetableEditor;
}
private:
static NLQT::CConfiguration *_configuration;
static NLQT::CObjectViewer *_objectViewer;

@ -30,26 +30,27 @@
// Projects includes
#include "mesh_widget.h"
namespace NLQT {
namespace NLQT
{
CMorphMeshDialog::CMorphMeshDialog(CWorkspaceNode *ownerNode, NL3D::CPSConstraintMesh *cm, QWidget *parent)
: QDialog(parent), _Node(ownerNode), _CM(cm)
: QDialog(parent), _Node(ownerNode), _CM(cm)
{
_ui.setupUi(this);
_ui.morphValueWidget->setRange(0, 10);
_ui.morphValueWidget->setWrapper(&_MorphSchemeWrapper);
_ui.morphValueWidget->setSchemeWrapper(&_MorphSchemeWrapper);
_ui.morphValueWidget->init();
_MorphSchemeWrapper.CM = _CM;
_ui.morphValueWidget->setWorkspaceNode(_Node);
_ui.morphValueWidget->updateUi();
updateMeshList();
_ui.infoLabel->setVisible(!_CM->isValidBuild());
connect(_ui.addPushButton, SIGNAL(clicked()), this, SLOT(add()));
connect(_ui.removePushButton, SIGNAL(clicked()), this, SLOT(remove()));
connect(_ui.insertPushButton, SIGNAL(clicked()), this, SLOT(insert()));
@ -70,7 +71,7 @@ void CMorphMeshDialog::updateMeshList()
_ui.listWidget->clear();
for (uint k = 0; k < _CM->getNumShapes(); ++k)
_ui.listWidget->addItem(getShapeDescStr(k, numVerts[k]));
_ui.listWidget->setCurrentRow(0);
if (_CM->getNumShapes() < 2)
_ui.removePushButton->setEnabled(false);
@ -81,7 +82,7 @@ void CMorphMeshDialog::updateMeshList()
QString CMorphMeshDialog::getShapeDescStr(uint shapeIndex, sint numVerts) const
{
if (numVerts >= 0)
{
{
QString verts(tr("vertices"));
QString msg = _CM->getShape(shapeIndex).c_str() + tr(" (%1 vertices)").arg(numVerts);
return msg;
@ -97,11 +98,11 @@ QString CMorphMeshDialog::getShapeDescStr(uint shapeIndex, sint numVerts) const
void CMorphMeshDialog::add()
{
QString fileName = QFileDialog::getOpenFileName(this,
tr("Open NeL data file"), ".",
tr("NeL shape files (*.shape)"));
tr("Open NeL data file"), ".",
tr("NeL shape files (*.shape)"));
setCursor(Qt::WaitCursor);
if (!fileName.isEmpty())
if (!fileName.isEmpty())
{
std::vector<std::string> shapeNames;
shapeNames.resize(_CM->getNumShapes() + 1);
@ -127,10 +128,10 @@ void CMorphMeshDialog::remove()
_CM->getShapesNames(&shapeNames[0]);
shapeNames.erase(shapeNames.begin() + row);
_CM->setShapes(&shapeNames[0], (uint)shapeNames.size());
if (_CM->getNumShapes() < 2)
_ui.removePushButton->setEnabled(false);
touchPSState();
updateMeshList();
_ui.infoLabel->setVisible(!_CM->isValidBuild());
@ -139,11 +140,11 @@ void CMorphMeshDialog::remove()
void CMorphMeshDialog::insert()
{
QString fileName = QFileDialog::getOpenFileName(this,
tr("Open NeL data file"), ".",
tr("NeL shape files (*.shape)"));
tr("Open NeL data file"), ".",
tr("NeL shape files (*.shape)"));
setCursor(Qt::WaitCursor);
if (!fileName.isEmpty())
if (!fileName.isEmpty())
{
sint row = _ui.listWidget->currentRow();
std::vector<std::string> shapeNames;
@ -162,11 +163,11 @@ void CMorphMeshDialog::insert()
void CMorphMeshDialog::change()
{
QString fileName = QFileDialog::getOpenFileName(this,
tr("Open NeL data file"), ".",
tr("NeL shape files (*.shape)"));
tr("Open NeL data file"), ".",
tr("NeL shape files (*.shape)"));
setCursor(Qt::WaitCursor);
if (!fileName.isEmpty())
if (!fileName.isEmpty())
{
sint row = _ui.listWidget->currentRow();
_CM->setShape(row, fileName.toStdString());
@ -193,7 +194,7 @@ void CMorphMeshDialog::up()
void CMorphMeshDialog::down()
{
sint row = _ui.listWidget->currentRow();
sint row = _ui.listWidget->currentRow();
if (row == (sint) (_CM->getNumShapes() - 1)) return;
std::vector<std::string> shapeNames;
shapeNames.resize(_CM->getNumShapes());
@ -208,7 +209,7 @@ void CMorphMeshDialog::down()
void CMorphMeshDialog::touchPSState()
{
if (_Node && _Node->getPSModel())
{
{
_Node->getPSModel()->touchTransparencyState();
_Node->getPSModel()->touchLightableState();
}

@ -33,15 +33,16 @@
namespace NL3D
{
class CPSConstraintMesh;
class CPSConstraintMesh;
}
namespace NLQT {
namespace NLQT
{
class CMorphMeshDialog: public QDialog
{
Q_OBJECT
Q_OBJECT
public:
CMorphMeshDialog(CWorkspaceNode *ownerNode, NL3D::CPSConstraintMesh *cm, QWidget *parent = 0);
~CMorphMeshDialog();
@ -53,7 +54,7 @@ private Q_SLOTS:
void change();
void up();
void down();
private:
/// fill the mesh list with the mesh names in the object being edited
void updateMeshList();
@ -69,11 +70,11 @@ private:
virtual scheme_type *getScheme(void) const;
virtual void setScheme(scheme_type *s);
} _MorphSchemeWrapper;
void touchPSState();
CWorkspaceNode *_Node;
// the constraint mesh being edited
NL3D::CPSConstraintMesh *_CM;

@ -1,7 +1,7 @@
/*
Object Viewer Qt
Copyright (C) 2010 Dzmitry Kamiahin <dnk-88@tut.by>
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 3 of the License, or
@ -27,23 +27,24 @@
// Project includes
#include "particle_node.h"
namespace NLQT {
namespace NLQT
{
CMultiTexDialog::CMultiTexDialog(CWorkspaceNode *ownerNode, NL3D::CPSMultiTexturedParticle *mtp, QWidget *parent)
: QDialog(parent), _Node(ownerNode), _MTP(mtp)
: QDialog(parent), _Node(ownerNode), _MTP(mtp)
{
_ui.setupUi(this);
nlassert(_MTP);
_ui.basicCapsCheckBox->setChecked(NL3D::CPSMultiTexturedParticle::areBasicCapsForced());
_ui.useParticleDataCheckBox->setChecked(_MTP->getUseLocalDateAlt());
_ui.useParticleDataCheckBox_2->setChecked(_MTP->getUseLocalDate());
bool bEnvBumpMapUsed = _MTP->getMainTexOp() == NL3D::CPSMultiTexturedParticle::EnvBumpMap ? true : false;
_ui.bumpFactorLabel->setEnabled(bEnvBumpMapUsed);
_ui.bumpFactorDoubleSpinBox->setEnabled(bEnvBumpMapUsed);
_TexWrapper.OwnerNode = _Node;
_AlternateTexWrapper.OwnerNode = _Node;
_TexWrapper.MTP = _MTP;
@ -51,18 +52,18 @@ CMultiTexDialog::CMultiTexDialog(CWorkspaceNode *ownerNode, NL3D::CPSMultiTextur
_ui.texWidget->setWrapper(&_TexWrapper);
_ui.texWidget->updateUi();
_ui.texWidget_2->setWrapper(&_AlternateTexWrapper);
_ui.texWidget_2->updateUi();
readValues();
_ui.enableAlternateCheckBox->setChecked(_MTP->isAlternateTexEnabled());
_ui.alternateTab->setEnabled(_MTP->isAlternateTexEnabled());
_ui.texOpComboBox->setCurrentIndex(int(_MTP->getMainTexOp()));
_ui.texOpComboBox_2->setCurrentIndex(int(_MTP->getAlternateTexOp()));
connect(_ui.bumpFactorDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(updateValues()));
connect(_ui.enableAlternateCheckBox, SIGNAL(toggled(bool)), this, SLOT(setEnabledAlternate(bool)));
connect(_ui.basicCapsCheckBox, SIGNAL(toggled(bool)), this, SLOT(setForceBasicCaps(bool)));
@ -100,15 +101,15 @@ void CMultiTexDialog::updateValues()
vs1.x = _ui.uSpeed1DoubleSpinBox->value();
vs1.y = _ui.vSpeed1DoubleSpinBox->value();
vs2.x = _ui.uSpeed2DoubleSpinBox->value();
vs2.y = _ui.vSpeed2DoubleSpinBox->value();
_MTP->setScrollSpeed(0, vs1);
_MTP->setScrollSpeed(1, vs2);
_MTP->setBumpFactor(_ui.bumpFactorDoubleSpinBox->value());
updateModifiedFlag();
}
@ -118,13 +119,13 @@ void CMultiTexDialog::updateValuesAlternate()
vs1.x = _ui.uSpeed1DoubleSpinBox_2->value();
vs1.y = _ui.vSpeed1DoubleSpinBox_2->value();
vs2.x = _ui.uSpeed2DoubleSpinBox_2->value();
vs2.y = _ui.vSpeed2DoubleSpinBox_2->value();
_MTP->setAlternateScrollSpeed(0, vs1);
_MTP->setAlternateScrollSpeed(1, vs2);
updateModifiedFlag();
}
@ -146,7 +147,7 @@ void CMultiTexDialog::setMainOp(int index)
void CMultiTexDialog::setForceBasicCaps(bool state)
{
NL3D::CPSMultiTexturedParticle::forceBasicCaps(state);
NL3D::CPSMultiTexturedParticle::forceBasicCaps(state);
}
void CMultiTexDialog::setUseParticleDate(bool state)

@ -34,17 +34,18 @@
namespace NL3D
{
class CPSMultiTexturedParticle;
class CPSMultiTexturedParticle;
}
namespace NLQT {
namespace NLQT
{
class CWorkspaceNode;
class CMultiTexDialog: public QDialog
{
Q_OBJECT
Q_OBJECT
public:
CMultiTexDialog(CWorkspaceNode *ownerNode, NL3D::CPSMultiTexturedParticle *mtp, QWidget *parent = 0);
~CMultiTexDialog();
@ -58,7 +59,7 @@ private Q_SLOTS:
void setForceBasicCaps(bool state);
void setUseParticleDate(bool state);
void setUseParticleDateAlt(bool state);
private:
struct CMainTexWrapper : IPSWrapperTexture
{
@ -73,14 +74,17 @@ private:
virtual NL3D::ITexture *get(void);
virtual void set(NL3D::ITexture *);
} _AlternateTexWrapper;
CWorkspaceNode *_Node;
NL3D::CPSMultiTexturedParticle *_MTP;
void readValues();
void updateModifiedFlag() { if (_Node) _Node->setModified(true); }
void updateModifiedFlag()
{
if (_Node) _Node->setModified(true);
}
Ui::CMultiTexDialog _ui;
}; /* class CMultiTexDialog */

@ -50,16 +50,17 @@ using namespace std;
using namespace NLMISC;
using namespace NL3D;
namespace NLQT {
namespace NLQT
{
CObjectViewer::CObjectViewer()
CObjectViewer::CObjectViewer()
: _Driver(NULL), _TextContext(NULL),
_phi(0), _psi(0),_dist(20),
_CameraFocal(75),
_CurrentInstance(""),
_BloomEffect(false), _Scene(0)
_phi(0), _psi(0),_dist(20),
_CameraFocal(75),
_CurrentInstance(""),
_BloomEffect(false), _Scene(0)
{
}
CObjectViewer::~CObjectViewer()
@ -70,7 +71,7 @@ void CObjectViewer::init(nlWindow wnd, uint16 w, uint16 h)
{
//H_AUTO2
nldebug("CObjectViewert::init");
loadConfig();
// create the driver
@ -78,12 +79,12 @@ void CObjectViewer::init(nlWindow wnd, uint16 w, uint16 h)
_Driver = UDriver::createDriver(0, _Direct3D, 0);
nlassert(_Driver);
// initialize the window with config file values
_Driver->setDisplay(wnd, NL3D::UDriver::CMode(w, h, 32));
_Light = ULight::createLight();
// set mode of the light
_Light->setMode(ULight::DirectionalLight);
@ -96,25 +97,25 @@ void CObjectViewer::init(nlWindow wnd, uint16 w, uint16 h)
// set and enable the light
_Driver->setLight(0, *_Light);
_Driver->enableLight(0);
// Create a scene
_Scene = _Driver->createScene(true);
_PlayListManager = _Scene->createPlayListManager();
_Scene->enableLightingSystem(true);
// create the camera
UCamera camera = _Scene->getCam();
camera.setTransformMode (UTransformable::DirectMatrix);
setSizeViewport(w, h);
// camera will look at entities
updateCamera(0,0,0);
NLMISC::CVector hotSpot=NLMISC::CVector(0,0,0);
_MouseListener = _Driver->create3dMouseListener();
_MouseListener->setMatrix(Modules::objView().getScene()->getCam().getMatrix());
_MouseListener->setFrustrum(Modules::objView().getScene()->getCam().getFrustum());
@ -123,7 +124,7 @@ void CObjectViewer::init(nlWindow wnd, uint16 w, uint16 h)
// set the cache size for the font manager(in bytes)
_Driver->setFontManagerMaxMemory(2097152);
// create the text context
nlassert(!_TextContext);
_TextContext = _Driver->createTextContext(_FontName);
@ -140,7 +141,7 @@ void CObjectViewer::release()
{
//H_AUTO2
nldebug("CObjectViewer::release");
saveConfig();
// release text context
@ -171,7 +172,7 @@ void CObjectViewer::release()
void CObjectViewer::updateInput()
{
_Driver->EventServer.pump();
// New matrix from camera
_Scene->getCam().setTransformMode(NL3D::UTransformable::DirectMatrix);
_Scene->getCam().setMatrix (_MouseListener->getViewMatrix());
@ -182,7 +183,7 @@ void CObjectViewer::renderDriver()
// Render the scene.
if((NL3D::CBloomEffect::instance().getDriver() != NULL) && (_BloomEffect))
{
NL3D::CBloomEffect::instance().initBloom();
NL3D::CBloomEffect::instance().initBloom();
}
_Driver->clearBuffers(_BackgroundColor);
}
@ -194,8 +195,8 @@ void CObjectViewer::renderScene()
if((NL3D::CBloomEffect::instance().getDriver() != NULL) && (_BloomEffect))
{
NL3D::CBloomEffect::instance().endBloom();
NL3D::CBloomEffect::instance().endInterfacesDisplayBloom();
NL3D::CBloomEffect::instance().endBloom();
NL3D::CBloomEffect::instance().endInterfacesDisplayBloom();
}
}
@ -208,7 +209,7 @@ void CObjectViewer::saveScreenshot(const std::string &nameFile, bool jpg, bool p
//H_AUTO2
// FIXME: create screenshot path if it doesn't exist!
// empty bitmap
CBitmap bitmap;
// copy the driver buffer to the bitmap
@ -242,29 +243,29 @@ void CObjectViewer::saveScreenshot(const std::string &nameFile, bool jpg, bool p
bool CObjectViewer::loadMesh(const std::string &meshFileName, const std::string &skelFileName)
{
std::string fileName = CFile::getFilenameWithoutExtension(meshFileName);
if ( _Entities.count(fileName) != 0)
if ( _Entities.count(fileName) != 0)
return false;
CPath::addSearchPath(CFile::getPath(meshFileName), false, false);
// create instance of the mesh character
UInstance Entity = _Scene->createInstance(meshFileName);
USkeleton Skeleton = _Scene->createSkeleton(skelFileName);
// if we can't create entity, skip it
if (Entity.empty()) return false;
// TODO: remade at typedef std::map<std::string, *CEntity> CEntities;
EIT eit = (_Entities.insert (make_pair (fileName, CEntity()))).first;
CEntity &entity = (*eit).second;
// set the entity up
entity._Name = fileName;
entity._FileNameShape = meshFileName;
entity._FileNameSkeleton = skelFileName;
entity._Instance = Entity;
if (!Skeleton.empty())
if (!Skeleton.empty())
{
entity._Skeleton = Skeleton;
entity._Skeleton.bindSkin (entity._Instance);
@ -277,18 +278,18 @@ bool CObjectViewer::loadMesh(const std::string &meshFileName, const std::string
void CObjectViewer::resetScene()
{
deleteEntities();
// Reset camera.
//..
// to load files with the same name but located in different directories
CPath::clearMap();
// load and set search paths from config
Modules::config().configSearchPaths();
_CurrentInstance = "";
nlinfo("Scene cleared");
}
@ -297,15 +298,15 @@ void CObjectViewer::updateCamera(float deltaPsi, float deltaPhi, float deltaDist
_phi += deltaPhi;
_psi += deltaPsi;
_dist += deltaDist;
if(_phi < -NLMISC::Pi/2) _phi -= deltaPhi;
if(_phi > NLMISC::Pi/2) _phi -= deltaPsi;
if(_phi > NLMISC::Pi/2) _phi -= deltaPsi;
if (_dist < 1) _dist = 1;
NLMISC::CQuat q0,q1,q2;
NLMISC::CVector up(0,0,1);
NLMISC::CVector v(0,0,1);
q0.setAngleAxis(v,_psi);
v = NLMISC::CVector(0,1,0);
q1.setAngleAxis(v,_phi);
@ -337,15 +338,15 @@ void CObjectViewer::updateAnimation(NL3D::TAnimationTime time)
CEntity &entity = (*eit).second;
entity.update(time);
}
// Animate scene animation
Modules::objView().getPlayListManager()->setup(time);
}
void CObjectViewer::setBackgroundColor(NLMISC::CRGBA backgroundColor)
{
_BackgroundColor = backgroundColor;
// config file variable changes
Modules::config().getConfigFile().getVar("BackgroundColor").setAsInt(_BackgroundColor.R, 0);
Modules::config().getConfigFile().getVar("BackgroundColor").setAsInt(_BackgroundColor.G, 1);
@ -389,13 +390,13 @@ void CObjectViewer::getListObjects(std::vector<std::string> &listObj)
void CObjectViewer::loadConfig()
{
// set background color from config
Modules::config().setAndCallback("BackgroundColor", CConfigCallback(this, &CObjectViewer::cfcbBackgroundColor));
Modules::config().setAndCallback("BackgroundColor", CConfigCallback(this, &CObjectViewer::cfcbBackgroundColor));
// set graphics driver from config
Modules::config().setAndCallback("GraphicsDriver",CConfigCallback(this,&CObjectViewer::cfcbGraphicsDriver));
Modules::config().setAndCallback("CameraFocal",CConfigCallback(this,&CObjectViewer::cfcbCameraFocal));
Modules::config().setAndCallback("FontName",CConfigCallback(this,&CObjectViewer::cfcbFontName));
Modules::config().setAndCallback("BloomEffect",CConfigCallback(this,&CObjectViewer::cfcbBloomEffect));
@ -425,7 +426,7 @@ void CObjectViewer::cfcbGraphicsDriver(NLMISC::CConfigFile::CVar &var)
{
// Choose driver opengl to work correctly under Linux example
_Direct3D = false; //_Driver = OpenGL;
#ifdef NL_OS_WINDOWS
std::string driver = var.asString();
if (driver == "Direct3D") _Direct3D = true; //m_Driver = Direct3D;
@ -446,7 +447,7 @@ void CObjectViewer::cfcbFontName(NLMISC::CConfigFile::CVar &var)
void CObjectViewer::cfcbBloomEffect(NLMISC::CConfigFile::CVar &var)
{
_BloomEffect = var.asBool();
_BloomEffect = var.asBool();
}
} /* namespace NLQT */

@ -34,24 +34,26 @@
// Project includes
#include "entity.h"
namespace NL3D {
class UDriver;
class UScene;
class ULight;
class UInstance;
class UCamera;
class USkeleton;
class UTextContext;
class UPlayListManager;
class U3dMouseListener;
namespace NL3D
{
class UDriver;
class UScene;
class ULight;
class UInstance;
class UCamera;
class USkeleton;
class UTextContext;
class UPlayListManager;
class U3dMouseListener;
}
namespace NLQT {
namespace NLQT
{
/**
@class CObjectViewer
@brief The class initializes the driver and creates a scene, provides basic control functions over the stage driver.
@details The class initializes the driver (by choosing OpenGL or Direct3D), and creates a scene (set an aspect), respectively
@details The class initializes the driver (by choosing OpenGL or Direct3D), and creates a scene (set an aspect), respectively
creates a light as well, load the font that is available further for
all other subsystems (eg: the signature of the coordinate axes) and Mouse Listener.
Settings are loaded from the configuration file.
@ -60,7 +62,7 @@ Also, the class provides the following features to scene control:
- Provides access to a animation object (getEntity(), getListObjects()).
- Select of current object for various operation (mainly related to the animation and editing skeleton):setCurrentObject(), getCurrentObject().
- Operations with the viewport, setting the correct perspective and creating of a screenshot.
- Function's updating keyboard and mouse (acts on the camera updateInput()), update(updateAnimatePS(), updateAnimation())
- Function's updating keyboard and mouse (acts on the camera updateInput()), update(updateAnimatePS(), updateAnimation())
and render the scene (renderDriver(), renderScene()).
- Provides access to a general NeL systems (getDriver(), getScene(), getPlayListManager(), getTextContext(), get3dMouseListener()).
*/
@ -69,7 +71,7 @@ class CObjectViewer
public:
/// Default constructor.
CObjectViewer();
virtual ~CObjectViewer();
/// Init a driver and create scene.
@ -131,8 +133,11 @@ public:
/// @param w - width window.
/// @param h - height window.
void setSizeViewport(uint16 w, uint16 h);
void setBloomEffect(bool enabled) { _BloomEffect = enabled; }
void setBloomEffect(bool enabled)
{
_BloomEffect = enabled;
}
/// Select instance from the scene
/// @param name - name instance, "" if no instance edited
@ -140,8 +145,11 @@ public:
/// Get current instance from the scene
/// @return name current instance, "" if no instance edited
const std::string& getCurrentObject() { return _CurrentInstance; }
const std::string& getCurrentObject()
{
return _CurrentInstance;
}
/// Get entity from the scene
/// @return ref Entity
CEntity& getEntity(const std::string &name);
@ -152,49 +160,73 @@ public:
/// Get value background color.
/// @return background color.
inline NLMISC::CRGBA getBackgroundColor() const { return _BackgroundColor; }
inline NLMISC::CRGBA getBackgroundColor() const
{
return _BackgroundColor;
}
/// Get type driver.
/// @return true if have used Direct3D driver, false OpenGL driver.
inline bool getDirect3D() const { return _Direct3D; }
inline bool getDirect3D() const
{
return _Direct3D;
}
inline bool getBloomEffect() const { return _BloomEffect; }
inline bool getBloomEffect() const
{
return _BloomEffect;
}
/// Get a game interface for window driver.
/// @return pointer to the driver.
inline NL3D::UDriver *getDriver() const { return _Driver; }
inline NL3D::UDriver *getDriver() const
{
return _Driver;
}
/// Get a game interface for scene.
/// @return pointer to the scene.
inline NL3D::UScene *getScene() const { return _Scene; }
inline NL3D::UScene *getScene() const
{
return _Scene;
}
/// Get a manager of playlist
/// @return pointer to the UPlayListManager
inline NL3D::UPlayListManager *getPlayListManager() const { return _PlayListManager; }
inline NL3D::UPlayListManager *getPlayListManager() const
{
return _PlayListManager;
}
/// Get a game interface to render string
/// Get a game interface to render string
/// @return pointer to the UPlayListManager
inline NL3D::UTextContext *getTextContext() const { return _TextContext; }
inline NL3D::UTextContext *getTextContext() const
{
return _TextContext;
}
/// Get a 3d mouse listener
/// @return pointer to the U3dMouseListener
inline NL3D::U3dMouseListener *get3dMouseListener() const { return _MouseListener; }
inline NL3D::U3dMouseListener *get3dMouseListener() const
{
return _MouseListener;
}
private:
void loadConfig();
void saveConfig();
// Delete all entities
void deleteEntities();
// Load background color from config file, intended for CConfiguration.
void cfcbBackgroundColor(NLMISC::CConfigFile::CVar &var);
void cfcbGraphicsDriver(NLMISC::CConfigFile::CVar &var);
void cfcbCameraFocal(NLMISC::CConfigFile::CVar &var);
void cfcbFontName(NLMISC::CConfigFile::CVar &var);
void cfcbBloomEffect(NLMISC::CConfigFile::CVar &var);
NLMISC::CRGBA _BackgroundColor;
NL3D::UDriver *_Driver;
@ -207,17 +239,17 @@ private:
// The entities storage
CEntities _Entities;
/// Camera parameters.
float _phi, _psi, _dist;
float _CameraFocal;
std::string _FontName;
bool _Direct3D;
bool _BloomEffect;
std::string _CurrentInstance;
};/* class CObjectViewer */

@ -32,26 +32,27 @@
#include "particle_link_skeleton_dialog.h"
#include "modules.h"
namespace NLQT {
namespace NLQT
{
CParticleControlDialog::CParticleControlDialog(CSkeletonTreeModel *model, QWidget *parent)
: QDockWidget(parent)
: QDockWidget(parent)
{
_ui.setupUi(this);
_timer = new QTimer(this);
_particleLinkDialog = new CParticleLinkDialog(model, parent);
_particleLinkDialog->setVisible(false);
_ui.numParticlesLabel->setMinimumWidth(_ui.numParticlesLabel->sizeHint().width());
_ui.numWantedFacesLabel->setMinimumWidth(_ui.numWantedFacesLabel->sizeHint().width());
_ui.systemTimesLabel->setMinimumWidth(_ui.systemTimesLabel->sizeHint().width());
stop();
connect(_timer, SIGNAL(timeout()), this, SLOT(updateCount()));
connect(_ui.playToolButton, SIGNAL(clicked()), this, SLOT(play()));
connect(_ui.stopToolButton, SIGNAL(clicked()), this, SLOT(stop()));
connect(_ui.horizontalSlider, SIGNAL(sliderMoved(int)), this, SLOT(sliderMoved(int)));
@ -60,7 +61,7 @@ CParticleControlDialog::CParticleControlDialog(CSkeletonTreeModel *model, QWidge
connect(_ui.loopCheckBox, SIGNAL(toggled(bool)), this, SLOT(autoRepeat(bool)));
connect(_ui.autoCountCheckBox, SIGNAL(toggled(bool)), this, SLOT(setEnabledAutoCount(bool)));
connect(_ui.resetAutoCountPushButton, SIGNAL(clicked()), this, SLOT(resetAutoCount()));
connect(_ui.linkSkelPushButton, SIGNAL(clicked()), this, SLOT(linkSceleton()));
connect(_ui.unlinkSkelPushButton, SIGNAL(clicked()), this, SLOT(unlink()));
connect(_ui.setAnimPushButton, SIGNAL(clicked()), this, SLOT(setAnim()));
@ -95,7 +96,7 @@ void CParticleControlDialog::play()
Modules::psEdit().startMultiple();
else
Modules::psEdit().start();
_timer->start(200);
_ui.multipleCheckBox->setEnabled(false);
Q_EMIT changeState();
@ -107,11 +108,11 @@ void CParticleControlDialog::stop()
_ui.playToolButton->setChecked(false);
Modules::psEdit().stop();
_ui.multipleCheckBox->setEnabled(true);
_ui.numParticlesLabel->setText(tr("Num particles:"));
_ui.numWantedFacesLabel->setText(tr("Num wanted faces:"));
_ui.systemTimesLabel->setText(tr("System time:"));
Q_EMIT changeState();
}
@ -154,18 +155,18 @@ void CParticleControlDialog::updateCount()
{
if (Modules::psEdit().getActiveNode() == NULL)
return;
NL3D::CParticleSystem *ps = Modules::psEdit().getActiveNode()->getPSPointer();
sint currNumParticles = (sint) ps->getCurrNumParticles();
// display number of particles for the currently active node
_ui.numParticlesLabel->setText(tr("Num particles: %1").arg(currNumParticles));
// display max number of wanted faces
NLMISC::CMatrix camMat = ps->getScene()->getCam()->getMatrix();
sint numWantedFaces = (uint) ps->getWantedNumTris((ps->getSysMat().getPos() - camMat.getPos()).norm());
_ui.numWantedFacesLabel->setText(tr("Num wanted faces: %1").arg(numWantedFaces));
// display system date
_ui.systemTimesLabel->setText(tr("System time: %1").arg(ps->getSystemDate(),0,'f',2));
@ -180,7 +181,7 @@ void CParticleControlDialog::linkSceleton()
void CParticleControlDialog::unlink()
{
CWorkspaceNode *node = Modules::psEdit().getActiveNode();
if (node == NULL)
if (node == NULL)
return;
node->unstickPSFromSkeleton();
@ -197,7 +198,7 @@ void CParticleControlDialog::clearAnim()
void CParticleControlDialog::restickObjects()
{
CParticleWorkspace *pw = Modules::psEdit().getParticleWorkspace();
if (pw == NULL)
if (pw == NULL)
return;
pw->restickAllObjects();

@ -25,14 +25,15 @@
// Project includes
namespace NLQT {
namespace NLQT
{
class CSkeletonTreeModel;
class CParticleLinkDialog;
class CParticleControlDialog: public QDockWidget
{
Q_OBJECT
Q_OBJECT
public:
CParticleControlDialog(CSkeletonTreeModel *model, QWidget *parent = 0);
~CParticleControlDialog();
@ -48,7 +49,7 @@ public Q_SLOTS:
private Q_SLOTS:
void play();
void stop();
void sliderMoved(int value);
void sliderMoved(int value);
void displayHelpers(bool state);
void displayBBox(bool state);
void autoRepeat(bool state);

@ -31,15 +31,16 @@
// Project includes
#include "modules.h"
namespace NLQT {
CParticleEditor::CParticleEditor(void):
_ActiveNode(NULL), _State(State::Stopped), _Speed(1.0f),
_AutoRepeat(false), _DisplayBBox(false),
_DisplayHelpers(false), _AutoUpdateBBox(false),
_EmptyBBox(true), _PW(NULL),
_Driver(NULL), _Scene(NULL),
_FontManager(NULL), _FontGen(NULL)
namespace NLQT
{
CParticleEditor::CParticleEditor(void):
_ActiveNode(NULL), _State(State::Stopped), _Speed(1.0f),
_AutoRepeat(false), _DisplayBBox(false),
_DisplayHelpers(false), _AutoUpdateBBox(false),
_EmptyBBox(true), _PW(NULL),
_Driver(NULL), _Scene(NULL),
_FontManager(NULL), _FontGen(NULL)
{
}
@ -48,10 +49,10 @@ CParticleEditor::~CParticleEditor(void)
}
void CParticleEditor::init()
{
{
NL3D::CDriverUser *driver = dynamic_cast<NL3D::CDriverUser*>(Modules::objView().getDriver());
_Driver = driver->getDriver();
NL3D::CSceneUser *scene = dynamic_cast<NL3D::CSceneUser*>(Modules::objView().getScene());
_Scene = &scene->getScene();
@ -96,7 +97,7 @@ void CParticleEditor::loadWorkspace(const std::string &fullPath)
// Add to the path
std::auto_ptr<CParticleWorkspace> newPW(new CParticleWorkspace);
newPW->init(fullPath);
// save empty workspace
try
{
@ -106,8 +107,8 @@ void CParticleEditor::loadWorkspace(const std::string &fullPath)
{
nlerror(e.what());
return;
}
}
// try to load each ps
CWorkspaceNode *firstLoadedNode = NULL;
TPWNodeItr itr = newPW->getNodeList().begin();
@ -188,27 +189,27 @@ void CParticleEditor::start()
{
case State::Stopped:
if (_ActiveNode)
{
{
if (checkHasLoop(*_ActiveNode)) return;
play(*_ActiveNode);
nlassert(_PlayingNodes.empty());
_PlayingNodes.push_back(_ActiveNode);
}
break;
break;
case State::RunningSingle:
// no-op
return;
break;
return;
break;
case State::RunningMultiple:
stop();
start();
break;
break;
case State::PausedSingle:
if (_ActiveNode)
{
unpause(*_ActiveNode);
}
break;
break;
case State::PausedMultiple:
for(uint k = 0; k < _PlayingNodes.size(); ++k)
{
@ -219,10 +220,10 @@ void CParticleEditor::start()
}
stop();
start();
break;
break;
default:
nlassert(0);
break;
break;
}
_State = State::RunningSingle;
}
@ -232,54 +233,54 @@ void CParticleEditor::startMultiple()
switch(_State)
{
case State::Stopped:
{
if (!_PW) return;
nlassert(_PlayingNodes.empty());
TPWNodeItr itr = _PW->getNodeList().begin();
while(itr != _PW->getNodeList().end())
{
if (!_PW) return;
nlassert(_PlayingNodes.empty());
TPWNodeItr itr = _PW->getNodeList().begin();
while(itr != _PW->getNodeList().end())
{
CWorkspaceNode *node = (*itr);
if (node->isLoaded())
if (checkHasLoop(*node)) return;
itr++;
}
itr = _PW->getNodeList().begin();
while(itr != _PW->getNodeList().end())
CWorkspaceNode *node = (*itr);
if (node->isLoaded())
if (checkHasLoop(*node)) return;
itr++;
}
itr = _PW->getNodeList().begin();
while(itr != _PW->getNodeList().end())
{
CWorkspaceNode *node = (*itr);
if (node->isLoaded())
{
CWorkspaceNode *node = (*itr);
if (node->isLoaded())
{
// really start the node only if there's no trigger anim
if (node->getTriggerAnim().empty())
play(*node);
// really start the node only if there's no trigger anim
if (node->getTriggerAnim().empty())
play(*node);
_PlayingNodes.push_back(node);
}
itr++;
_PlayingNodes.push_back(node);
}
itr++;
}
}
break;
case State::PausedSingle:
case State::RunningSingle:
stop();
startMultiple();
break;
case State::PausedSingle:
case State::RunningSingle:
stop();
startMultiple();
break;
case State::RunningMultiple:
// no-op
return;
case State::RunningMultiple:
// no-op
return;
break;
case State::PausedMultiple:
for(uint k = 0; k < _PlayingNodes.size(); ++k)
case State::PausedMultiple:
for(uint k = 0; k < _PlayingNodes.size(); ++k)
{
if (_PlayingNodes[k])
{
if (_PlayingNodes[k])
{
unpause(*_PlayingNodes[k]);
}
unpause(*_PlayingNodes[k]);
}
}
break;
default:
nlassert(0);
default:
nlassert(0);
break;
}
_State = State::RunningMultiple;
@ -290,31 +291,31 @@ void CParticleEditor::pause()
switch(_State)
{
case State::Stopped:
// no-op
return;
case State::RunningSingle:
if (_ActiveNode)
{
pause(*_ActiveNode);
}
_State = State::PausedSingle;
// no-op
return;
case State::RunningSingle:
if (_ActiveNode)
{
pause(*_ActiveNode);
}
_State = State::PausedSingle;
break;
case State::RunningMultiple:
for(uint k = 0; k < _PlayingNodes.size(); ++k)
case State::RunningMultiple:
for(uint k = 0; k < _PlayingNodes.size(); ++k)
{
if (_PlayingNodes[k])
{
if (_PlayingNodes[k])
{
pause(*_PlayingNodes[k]);
}
pause(*_PlayingNodes[k]);
}
_State = State::PausedMultiple;
}
_State = State::PausedMultiple;
break;
case State::PausedSingle:
case State::PausedMultiple:
// no-op
return;
default:
nlassert(0);
case State::PausedSingle:
case State::PausedMultiple:
// no-op
return;
default:
nlassert(0);
break;
}
}
@ -323,28 +324,28 @@ void CParticleEditor::stop()
{
switch(_State)
{
case State::Stopped:
// no-op
return;
case State::RunningSingle:
case State::RunningMultiple:
case State::PausedSingle:
case State::PausedMultiple:
for(uint k = 0; k < _PlayingNodes.size(); ++k)
case State::Stopped:
// no-op
return;
case State::RunningSingle:
case State::RunningMultiple:
case State::PausedSingle:
case State::PausedMultiple:
for(uint k = 0; k < _PlayingNodes.size(); ++k)
{
if (_PlayingNodes[k])
{
if (_PlayingNodes[k])
{
stop(*_PlayingNodes[k]);
}
stop(*_PlayingNodes[k]);
}
_PlayingNodes.clear();
}
_PlayingNodes.clear();
break;
default:
nlassert(0);
default:
nlassert(0);
break;
}
_State = State::Stopped;
}
}
void CParticleEditor::update()
{
@ -352,7 +353,7 @@ void CParticleEditor::update()
if (_PW == NULL) return;
NL3D::CParticleSystem *currPS = _ActiveNode->getPSPointer();
// compute BBox
if (_DisplayBBox)
{
@ -372,7 +373,7 @@ void CParticleEditor::update()
currPS->setPrecomputedBBox(_CurrBBox);
}
}
// auto repeat feature
if (_AutoRepeat)
{
@ -394,7 +395,7 @@ void CParticleEditor::update()
allFXFinished = false;
break;
}
else
else
{
if (node->getPSPointer()->getCurrNumParticles() != 0)
{
@ -456,7 +457,7 @@ void CParticleEditor::restartAllFX()
}
}
else
{
{
for(uint k = 0; k < _PlayingNodes.size(); ++k)
{
if (_PlayingNodes[k])
@ -484,14 +485,14 @@ void CParticleEditor::setSpeed(float value)
}
}
void CParticleEditor::setDisplayBBox(bool enable)
{
void CParticleEditor::setDisplayBBox(bool enable)
{
_DisplayBBox = enable;
NL3D::CParticleSystem::forceDisplayBBox(enable);
}
void CParticleEditor::enableAutoCount(bool enable)
{
{
if (!_ActiveNode) return;
if (enable == _ActiveNode->getPSPointer()->getAutoCountFlag()) return;
_ActiveNode->getPSPointer()->setAutoCountFlag(enable);
@ -517,7 +518,7 @@ bool CParticleEditor::checkHasLoop(CWorkspaceNode &node)
{
nlassert(node.isLoaded());
if (!node.getPSPointer()->hasLoop()) return false;
return true;
return true;
}
void CParticleEditor::play(CWorkspaceNode &node)
@ -527,7 +528,7 @@ void CParticleEditor::play(CWorkspaceNode &node)
nlassert(node.isLoaded());
// if node not started, start it
node.memorizeState();
// enable the system to take the right date from the scene
// enable the system to take the right date from the scene
node.getPSModel()->enableAutoGetEllapsedTime(true);
node.getPSPointer()->setSystemDate(0.f);
node.getPSPointer()->reactivateSound();
@ -540,8 +541,8 @@ void CParticleEditor::play(CWorkspaceNode &node)
node.getPSPointer()->matchArraySize();
}
resetAutoCount(&node, false);
}
}
// Set speed playback particle system
node.getPSModel()->setEllapsedTimeRatio(_Speed);
}
@ -571,5 +572,5 @@ void CParticleEditor::stop(CWorkspaceNode &node)
node.getPSModel()->activateEmitters(true);
node.getPSPointer()->stopSound();
}
} /* namespace NLQT */

@ -34,26 +34,28 @@
// Projects includes
#include "particle_node.h"
namespace NL3D {
class CParticleSystem;
class CParticleSystemModel;
class CShapeBank;
class CScene;
class IDriver;
class CFontManager;
class CFontGenerator;
namespace NL3D
{
class CParticleSystem;
class CParticleSystemModel;
class CShapeBank;
class CScene;
class IDriver;
class CFontManager;
class CFontGenerator;
}
namespace NLQT {
namespace NLQT
{
/**
@class CParticleEditor
@brief The main class of the particles editor.
@details - Provides access to a container containing all of the particles systems (getParticleWorkspace())
and also allows you to create an empty container (createNewWorkspace()) load / save from the file
and also allows you to create an empty container (createNewWorkspace()) load / save from the file
and unload (loadWorkspace(), saveWorkspaceStructure(), saveWorkspaceContent())
- Has basic operations management system to control a particles systems (start(), stop(), pause(), setSpeed() / setAutoRepeat())
- Has basic operations management system to control a particles systems (start(), stop(), pause(), setSpeed() / setAutoRepeat())
as in single mode, and in the multiple (start(), startMultiple()).
- Additional functions of particle systems: display / hide the assistanse elements (setDisplayHelpers()),
- Additional functions of particle systems: display / hide the assistanse elements (setDisplayHelpers()),
the calculation of bounding box (setAutoBBox(), getAutoBBox()), switching on the autoCount mode (setAutoBBox(), getAutoBBox()).
- Selection of the current system of particles for making various operations (setActiveNode(), getActiveNode()).
*/
@ -65,29 +67,35 @@ public:
enum List
{
Stopped = 1,
RunningSingle,
RunningMultiple,
PausedSingle,
RunningSingle,
RunningMultiple,
PausedSingle,
PausedMultiple
};
};
CParticleEditor(void);
~CParticleEditor(void);
void init();
void release();
/// Active a new node of the workspace
/// Current active node is ready for edition.
/// Its bbox is displayed.
void setActiveNode(CWorkspaceNode *node);
/// Get the node of the workspace that is currently active
CWorkspaceNode *getActiveNode() const { return _ActiveNode; }
CWorkspaceNode *getActiveNode() const
{
return _ActiveNode;
}
/// Get the particle system model that is currently active
NL3D::CParticleSystemModel *getActivePSM() const { return _ActiveNode ? _ActiveNode->getPSModel() : NULL; }
NL3D::CParticleSystemModel *getActivePSM() const
{
return _ActiveNode ? _ActiveNode->getPSModel() : NULL;
}
/// Get a model from a ps pointer. The ps must belong to the workspace
NL3D::CParticleSystemModel *getModelFromPS(NL3D::CParticleSystem *ps) const;
@ -126,56 +134,92 @@ public:
void setDisplayBBox(bool enable);
void setDisplayHelpers(bool enable) { _DisplayHelpers = enable; }
void setDisplayHelpers(bool enable)
{
_DisplayHelpers = enable;
}
void setAutoRepeat(bool enable) { _AutoRepeat = enable; }
void setAutoRepeat(bool enable)
{
_AutoRepeat = enable;
}
/// Auto bbox for fx
void setAutoBBox(bool enable) { _AutoUpdateBBox = enable; }
void setAutoBBox(bool enable)
{
_AutoUpdateBBox = enable;
}
bool getAutoBBox() const
{
return _AutoUpdateBBox;
}
bool getAutoBBox() const { return _AutoUpdateBBox; }
/// Enable / disbale auto-count
void enableAutoCount(bool enable);
/// Reset the autocount the next time the system will be started
void enableAutoCount(bool enable);
/// Reset the autocount the next time the system will be started
void resetAutoCount(CWorkspaceNode *node, bool reset = true);
/// Reset the auto compute bbox
void resetAutoBBox() { _EmptyBBox = true; }
void resetAutoBBox()
{
_EmptyBBox = true;
}
/// Get current state
int getState() const { return _State; }
int getState() const
{
return _State;
}
/// Return true if one or several system are being played
bool isRunning() const { return _State == State::RunningSingle || _State == State::RunningMultiple; }
bool isRunning() const
{
return _State == State::RunningSingle || _State == State::RunningMultiple;
}
/// Return true if a system is paused.
/// Must call only if running
bool isPaused() const
bool isPaused() const
{
return _State == State::PausedSingle || _State == State::PausedMultiple;
}
CParticleWorkspace *getParticleWorkspace() const { return _PW; }
NL3D::IDriver *getDriver() const { return _Driver; }
NL3D::CScene *getScene() const { return _Scene; }
CParticleWorkspace *getParticleWorkspace() const
{
return _PW;
}
NL3D::IDriver *getDriver() const
{
return _Driver;
}
NL3D::CScene *getScene() const
{
return _Scene;
}
/// Get the fontManager
NL3D::CFontManager *getFontManager() const {return _FontManager;}
NL3D::CFontManager *getFontManager() const
{
return _FontManager;
}
/// Get the fontGenerator
NL3D::CFontGenerator *getFontGenerator () const { return _FontGen; }
NL3D::CFontGenerator *getFontGenerator () const
{
return _FontGen;
}
private:
// Check if a node is inserted in the running list (it may be paused)
bool isRunning(CWorkspaceNode *node);
// Check is a node has loops
bool checkHasLoop(CWorkspaceNode &node);
void play(CWorkspaceNode &node);
void unpause(CWorkspaceNode &node);
void pause(CWorkspaceNode &node);
@ -194,15 +238,15 @@ private:
bool _AutoRepeat;
bool _DisplayBBox;
bool _DisplayHelpers;
// The system bbox must be updated automatically
bool _AutoUpdateBBox;
// The last computed bbox for the system
bool _EmptyBBox;
NLMISC::CAABBox _CurrBBox;
CParticleWorkspace *_PW;
NL3D::IDriver *_Driver;
NL3D::CScene *_Scene;

@ -21,29 +21,30 @@
#include "particle_force_page.h"
// Qt includes
#include <QtGui/QMessageBox>
#include <QtGui/QMessageBox>
// NeL includes
#include <nel/3d/particle_system.h>
// Project includes
namespace NLQT {
namespace NLQT
{
CForcePage::CForcePage(QWidget *parent)
: QWidget(parent)
: QWidget(parent)
{
_ui.setupUi(this);
_ui.forceIntensityWidget->setRange(0, 10);
_ui.forceIntensityWidget->setWrapper(&_ForceIntensityWrapper);
_ui.forceIntensityWidget->setSchemeWrapper(&_ForceIntensityWrapper);
_ui.forceIntensityWidget->init();
_ui.parametricFactorWidget->setRange(0.0, 64.0);
_ui.radialViscosityWidget->setRange(0.0, 1.0);
_ui.tangentialViscosityWidget->setRange(0, 1);
connect(_ui.toTargetsPushButton, SIGNAL(clicked()), this, SLOT(addTarget()));
connect(_ui.toAvaibleTargetsPushButton, SIGNAL(clicked()), this, SLOT(removeTarget()));
@ -61,7 +62,7 @@ CForcePage::~CForcePage()
void CForcePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocatedBindable *locatedBindable)
{
nlassert(locatedBindable);
hideAdditionalWidget();
_Node = ownerNode;
_LBTarget = static_cast<NL3D::CPSTargetLocatedBindable *>(locatedBindable);
@ -116,31 +117,31 @@ void CForcePage::addTarget()
if ((totalCount == 0) || (_ui.avaibleTargetsListWidget->currentRow() == -1)) return;
CLocatedItem *item = dynamic_cast<CLocatedItem *>(_ui.avaibleTargetsListWidget->currentItem());
NL3D::CPSLocated *loc = item->getUserData();
nlassert(loc);
// check that force isn't applied on a forever lasting object
if (dynamic_cast<NL3D::CPSForce *>(_LBTarget))
{
{
if (loc->getLastForever())
{
int ret = QMessageBox::warning(this, tr("NeL particle system editor"),
tr("The target object last forever. Applying a force on such an object may result in instability in the system after a while. "
"Continue ? (clue : you've been warned..)"),
QMessageBox::Ok | QMessageBox::Cancel);
int ret = QMessageBox::warning(this, tr("NeL particle system editor"),
tr("The target object last forever. Applying a force on such an object may result in instability in the system after a while. "
"Continue ? (clue : you've been warned..)"),
QMessageBox::Ok | QMessageBox::Cancel);
if (ret == QMessageBox::Cancel)
return;
}
}
//
_LBTarget->attachTarget(loc);
_ui.avaibleTargetsListWidget->takeItem(_ui.avaibleTargetsListWidget->currentRow());
_ui.targetsListWidget->addItem(item);
updateModifiedFlag();
}
@ -151,7 +152,7 @@ void CForcePage::removeTarget()
if ((totalCount == 0) || (_ui.targetsListWidget->currentRow() == -1)) return;
CLocatedItem *item = dynamic_cast<CLocatedItem *>(_ui.targetsListWidget->takeItem(_ui.targetsListWidget->currentRow()));
NL3D::CPSLocated *loc = item->getUserData();
nlassert(loc);
@ -218,14 +219,14 @@ void CForcePage::updateTargets()
uint nbTarg = _LBTarget->getNbTargets();
_ui.targetsListWidget->clear();
std::set<NL3D::CPSLocated *> targetSet;
// fill the box thta tells us what the target are
for(k = 0; k < nbTarg; ++k)
{
CLocatedItem *item = new CLocatedItem(QString(_LBTarget->getTarget(k)->getName().c_str()),
_ui.targetsListWidget);
CLocatedItem *item = new CLocatedItem(QString(_LBTarget->getTarget(k)->getName().c_str()),
_ui.targetsListWidget);
item->setUserData(_LBTarget->getTarget(k));
targetSet.insert(_LBTarget->getTarget(k));
};
@ -236,7 +237,7 @@ void CForcePage::updateTargets()
uint nbLocated = ps->getNbProcess();
_ui.avaibleTargetsListWidget->clear();
for (k = 0; k < nbLocated; ++k)
{
NL3D::CPSLocated *loc = dynamic_cast<NL3D::CPSLocated *>(ps->getProcess(k));
@ -244,8 +245,8 @@ void CForcePage::updateTargets()
{
if (targetSet.find(loc) == targetSet.end())
{
CLocatedItem *item = new CLocatedItem(QString(loc->getName().c_str()),
_ui.avaibleTargetsListWidget);
CLocatedItem *item = new CLocatedItem(QString(loc->getName().c_str()),
_ui.avaibleTargetsListWidget);
item->setUserData(loc);
}
}

@ -33,8 +33,9 @@
#include "particle_node.h"
#include "ps_wrapper.h"
namespace NLQT {
namespace NLQT
{
/**
@class CLocatedItem
@brief Contain pointer to CPSLocated.
@ -42,14 +43,20 @@ namespace NLQT {
class CLocatedItem: public QListWidgetItem
{
public:
CLocatedItem ( const QString & text, QListWidget * parent = 0, int type = UserType ):
QListWidgetItem(text, parent, type), _loc(NULL) {}
void setUserData(NL3D::CPSLocated *loc) { _loc = loc;}
NL3D::CPSLocated *getUserData() const { return _loc;}
CLocatedItem ( const QString & text, QListWidget * parent = 0, int type = UserType ):
QListWidgetItem(text, parent, type), _loc(NULL) {}
void setUserData(NL3D::CPSLocated *loc)
{
_loc = loc;
}
NL3D::CPSLocated *getUserData() const
{
return _loc;
}
private:
NL3D::CPSLocated *_loc;
}; /* class CLocatedItem */
@ -59,8 +66,8 @@ private:
*/
class CForcePage: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CForcePage(QWidget *parent = 0);
virtual ~CForcePage();
@ -71,7 +78,7 @@ public:
private Q_SLOTS:
void addTarget();
void removeTarget();
void setRadialViscosity(float value);
void setTangentialViscosity(float value);
void setDir(const NLMISC::CVector &value);
@ -79,30 +86,45 @@ private Q_SLOTS:
void setFactorBrownianForce(float value);
private:
/// wrapper to tune the intensity of a force
struct CForceIntensityWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
{
NL3D::CPSForceIntensity *F;
float get(void) const { return F->getIntensity(); }
void set(const float &value) {F->setIntensity(value); }
scheme_type *getScheme(void) const { return F->getIntensityScheme(); }
void setScheme(scheme_type *s) {F->setIntensityScheme(s); }
float get(void) const
{
return F->getIntensity();
}
void set(const float &value)
{
F->setIntensity(value);
}
scheme_type *getScheme(void) const
{
return F->getIntensityScheme();
}
void setScheme(scheme_type *s)
{
F->setIntensityScheme(s);
}
} _ForceIntensityWrapper;
void hideAdditionalWidget();
void updateTargets();
void updateModifiedFlag() { if (_Node) _Node->setModified(true); }
void updateModifiedFlag()
{
if (_Node) _Node->setModified(true);
}
// the target we're focusing on
NL3D::CPSTargetLocatedBindable *_LBTarget;
CWorkspaceNode *_Node;
Ui::CForcePage _ui;
}; /* class CForcePage */
} /* namespace NLQT */

@ -27,10 +27,11 @@
// Project includes
#include "modules.h"
namespace NLQT {
namespace NLQT
{
CLightPage::CLightPage(QWidget *parent)
: QWidget(parent)
: QWidget(parent)
{
_ui.setupUi(this);
@ -57,7 +58,7 @@ void CLightPage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocatedBindab
{
_Node = ownerNode;
_Light = static_cast<NL3D::CPSLight *>(locatedBindable);
_ColorWrapper.L = _Light;
_ui.lightColorWidget->setWorkspaceNode(_Node);
_ui.lightColorWidget->updateUi();

@ -32,7 +32,8 @@
// Project includes
#include "ps_wrapper.h"
namespace NLQT {
namespace NLQT
{
/**
@class CLightPage
@ -40,15 +41,15 @@ namespace NLQT {
*/
class CLightPage: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CLightPage(QWidget *parent = 0);
~CLightPage();
/// Set the light to edit.
void setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocatedBindable *locatedBindable);
private Q_SLOTS:
private:
@ -56,36 +57,72 @@ private:
struct CColorWrapper : public IPSWrapperRGBA, IPSSchemeWrapperRGBA
{
NL3D::CPSLight *L;
NLMISC::CRGBA get(void) const { return L->getColor(); }
void set(const NLMISC::CRGBA &v) { L->setColor(v); }
scheme_type *getScheme(void) const { return L->getColorScheme(); }
void setScheme(scheme_type *s) { L->setColorScheme(s); }
NLMISC::CRGBA get(void) const
{
return L->getColor();
}
void set(const NLMISC::CRGBA &v)
{
L->setColor(v);
}
scheme_type *getScheme(void) const
{
return L->getColorScheme();
}
void setScheme(scheme_type *s)
{
L->setColorScheme(s);
}
} _ColorWrapper;
/// wrapper to set start atten radius
struct CAttenStartWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
{
NL3D::CPSLight *L;
float get(void) const { return L->getAttenStart(); }
void set(const float &v) { L->setAttenStart(v); }
scheme_type *getScheme(void) const { return L->getAttenStartScheme(); }
void setScheme(scheme_type *s) { L->setAttenStartScheme(s); }
float get(void) const
{
return L->getAttenStart();
}
void set(const float &v)
{
L->setAttenStart(v);
}
scheme_type *getScheme(void) const
{
return L->getAttenStartScheme();
}
void setScheme(scheme_type *s)
{
L->setAttenStartScheme(s);
}
} _AttenStartWrapper;
/// wrapper to set end atten radius
struct CAttenEndWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
{
NL3D::CPSLight *L;
float get(void) const { return L->getAttenEnd(); }
void set(const float &v) { L->setAttenEnd(v); }
scheme_type *getScheme(void) const { return L->getAttenEndScheme(); }
void setScheme(scheme_type *s) { L->setAttenEndScheme(s); }
float get(void) const
{
return L->getAttenEnd();
}
void set(const float &v)
{
L->setAttenEnd(v);
}
scheme_type *getScheme(void) const
{
return L->getAttenEndScheme();
}
void setScheme(scheme_type *s)
{
L->setAttenEndScheme(s);
}
} _AttenEndWrapper;
NL3D::CPSLight *_Light;
CWorkspaceNode *_Node;
Ui::CLightPage _ui;
}; /* class CLightPage */

@ -27,17 +27,18 @@
#include "modules.h"
#include "particle_node.h"
namespace NLQT {
namespace NLQT
{
CParticleLinkDialog::CParticleLinkDialog(CSkeletonTreeModel *model, QWidget *parent)
: QDockWidget(parent)
: QDockWidget(parent)
{
_ui.setupUi(this);
qobject_cast< QMainWindow* >(parent)->addDockWidget(Qt::RightDockWidgetArea, this);
_ui.treeView->setModel(model);
connect(model, SIGNAL(modelReset()), this, SLOT(resetModel()));
connect(_ui.linkPushButton, SIGNAL(clicked()), this, SLOT(setLink()));
connect(_ui.unlinkPushButton, SIGNAL(clicked()), this, SLOT(setUnlink()));
@ -51,11 +52,11 @@ CParticleLinkDialog::~CParticleLinkDialog()
void CParticleLinkDialog::setLink()
{
CWorkspaceNode *node = Modules::psEdit().getActiveNode();
if (node == NULL)
if (node == NULL)
return;
std::string curObj = Modules::objView().getCurrentObject();
if (curObj.empty())
if (curObj.empty())
return;
CSkeletonTreeItem *item = static_cast<CSkeletonTreeItem*>(_ui.treeView->currentIndex().internalPointer());
@ -71,7 +72,7 @@ void CParticleLinkDialog::setLink()
void CParticleLinkDialog::setUnlink()
{
CWorkspaceNode *node = Modules::psEdit().getActiveNode();
if (node == NULL)
if (node == NULL)
return;
node->unstickPSFromSkeleton();

@ -29,16 +29,17 @@
// Project includes
#include "skeleton_tree_model.h"
namespace NLQT {
namespace NLQT
{
class CParticleLinkDialog: public QDockWidget
{
Q_OBJECT
Q_OBJECT
public:
CParticleLinkDialog(CSkeletonTreeModel *model, QWidget *parent = 0);
~CParticleLinkDialog();
private Q_SLOTS:
void setLink();
void setUnlink();
@ -46,9 +47,9 @@ private Q_SLOTS:
void clickedItem(const QModelIndex & index);
private:
Ui::CParticleLinkDialog _ui;
}; /* class CParticleLinkDialog */
} /* namespace NLQT */

@ -34,7 +34,8 @@
using namespace NLMISC;
using namespace NL3D;
namespace NLQT {
namespace NLQT
{
CWorkspaceNode::CWorkspaceNode()
{
@ -72,9 +73,9 @@ bool CWorkspaceNode::isStateMemorized() const
}
void CWorkspaceNode::stickPSToSkeleton(NL3D::CSkeletonModel *skel,
uint bone,
const std::string &parentSkelName,
const std::string &parentBoneName)
uint bone,
const std::string &parentSkelName,
const std::string &parentBoneName)
{
nlassert(_WS);
if (!_PSM) return;
@ -103,20 +104,20 @@ void CWorkspaceNode::unstickPSFromSkeleton()
{
_ParentSkel->detachSkeletonSon(_PSM);
_ParentSkel = NULL;
}
}
}
void CWorkspaceNode::removeLocated(NL3D::CPSLocated *loc)
{
{
nlassert(_WS);
if (_InitialPos.isStateMemorized())
{
{
_InitialPos.removeLocated(loc);
}
}
void CWorkspaceNode::removeLocatedBindable(NL3D::CPSLocatedBindable *lb)
{
{
nlassert(_WS);
if (_InitialPos.isStateMemorized())
{
@ -160,7 +161,7 @@ void CWorkspaceNode::setup(NL3D::CParticleSystemModel &psm)
psm.bypassGlobalUserParamValue(k);
}
psm.enableAutoGetEllapsedTime(false);
psm.setEllapsedTime(0.f); // system is paused
psm.setEllapsedTime(0.f); // system is paused
// initialy, the ps is hidden
psm.hide();
// link to the root for manipulation
@ -172,7 +173,7 @@ void CWorkspaceNode::setup(NL3D::CParticleSystemModel &psm)
ps->setFontGenerator(Modules::psEdit().getFontGenerator());
ps->stopSound();
// flush textures
psm.Shape->flushTextures(*Modules::psEdit().getDriver(), 0);
psm.Shape->flushTextures(*Modules::psEdit().getDriver(), 0);
}
void CWorkspaceNode::setTriggerAnim(const std::string &anim)
@ -184,7 +185,7 @@ void CWorkspaceNode::setTriggerAnim(const std::string &anim)
}
void CWorkspaceNode::createEmptyPS()
{
{
nlassert(_WS);
NL3D::CParticleSystem emptyPS;
NL3D::CParticleSystemShape *pss = new NL3D::CParticleSystemShape;
@ -207,7 +208,7 @@ void CWorkspaceNode::createEmptyPS()
}
void CWorkspaceNode::init(CParticleWorkspace *ws)
{
{
nlassert(ws);
_WS = ws;
}
@ -219,20 +220,20 @@ void CWorkspaceNode::setRelativePath(const std::string &relativePath)
}
void CWorkspaceNode::serial(NLMISC::IStream &f)
{
{
nlassert(_WS);
f.xmlPush("PROJECT_FILE");
sint version = f.serialVersion(2);
f.xmlSerial(_RelativePath, "RELATIVE_PATH");
if (version >= 1)
{
f.xmlSerial(_TriggerAnim, "TRIGGER_ANIMATION");
}
if (version >= 2)
{
f.xmlSerial(_ParentSkelName, "PARENT_SKEL_NAME");
f.xmlSerial(_ParentBoneName, "PARENT_BONE_NAME");
}
sint version = f.serialVersion(2);
f.xmlSerial(_RelativePath, "RELATIVE_PATH");
if (version >= 1)
{
f.xmlSerial(_TriggerAnim, "TRIGGER_ANIMATION");
}
if (version >= 2)
{
f.xmlSerial(_ParentSkelName, "PARENT_SKEL_NAME");
f.xmlSerial(_ParentBoneName, "PARENT_BONE_NAME");
}
f.xmlPop();
}
@ -260,7 +261,7 @@ std::string CWorkspaceNode::getFullPath() const
}
bool CWorkspaceNode::loadPS() throw(NLMISC::EStream)
{
{
nlassert(_WS);
// manually load the PS shape (so that we can deal with exceptions)
NL3D::CShapeStream ss;
@ -294,7 +295,7 @@ bool CWorkspaceNode::loadPS() throw(NLMISC::EStream)
_PSM = psm;
_ShapeBank = sb.release();
_Modified = false;
return true;
return true;
}
@ -313,7 +314,7 @@ CParticleWorkspace::~CParticleWorkspace()
}
void CParticleWorkspace::init(const std::string &filename)
{
{
_Filename = filename;
}
@ -329,24 +330,24 @@ void CParticleWorkspace::setFileName(const std::string &fileName)
}
std::string CParticleWorkspace::getFilename() const
{
return CFile::getFilename(_Filename);
{
return CFile::getFilename(_Filename);
}
CWorkspaceNode *CParticleWorkspace::addNode(const std::string &filenameWithFullPath) throw( NLMISC::Exception)
{
// Check that file is not already inserted
{
// Check that file is not already inserted
std::string fileName = NLMISC::CFile::getFilename(filenameWithFullPath);
for(uint k = 0; k < _Nodes.size(); ++k)
{
if (NLMISC::nlstricmp(_Nodes[k]->getFilename(), fileName) == 0) return NULL;
}
}
// char resultPath[MAX_PATH];
// std::string dosPath = NLMISC::CPath::standardizeDosPath(getPath());
std::string relativePath;
// if (!PathRelativePathTo(resultPath, dosPath.c_str(), FILE_ATTRIBUTE_DIRECTORY, filenameWithFullPath.c_str(), 0))
// {
relativePath = filenameWithFullPath;
relativePath = filenameWithFullPath;
// }
// else
// {
@ -418,7 +419,7 @@ void CParticleWorkspace::serial(NLMISC::IStream &f) throw(NLMISC::EStream)
_Nodes.push_back(new CWorkspaceNode());
_Nodes.back()->init(this);
f.serial(*_Nodes.back());
}
}
}
else
{
@ -492,32 +493,32 @@ bool CParticleWorkspace::isContentModified() const
void CParticleWorkspace::restickAllObjects()
{
/* for(uint k = 0; k < _Nodes.size(); ++k)
{
std::string parentSkelName = _Nodes[k]->getParentSkelName();
std::string parentBoneName = _Nodes[k]->getParentBoneName();
//
_Nodes[k]->unstickPSFromSkeleton();
if (!parentSkelName.empty())
// find instance to stick to in the scene
for(uint l = 0; l < ov->getNumInstance(); ++l)
/* for(uint k = 0; k < _Nodes.size(); ++k)
{
CInstanceInfo *ii = ov->getInstance(l);
if (ii->TransformShape && ii->Saved.ShapeFilename == parentSkelName)
std::string parentSkelName = _Nodes[k]->getParentSkelName();
std::string parentBoneName = _Nodes[k]->getParentBoneName();
//
_Nodes[k]->unstickPSFromSkeleton();
if (!parentSkelName.empty())
// find instance to stick to in the scene
for(uint l = 0; l < ov->getNumInstance(); ++l)
{
NL3D::CSkeletonModel *skel = dynamic_cast<NL3D::CSkeletonModel *>(ii->TransformShape);
if (skel)
CInstanceInfo *ii = ov->getInstance(l);
if (ii->TransformShape && ii->Saved.ShapeFilename == parentSkelName)
{
sint boneID = skel->getBoneIdByName(parentBoneName);
if (boneID != -1)
NL3D::CSkeletonModel *skel = dynamic_cast<NL3D::CSkeletonModel *>(ii->TransformShape);
if (skel)
{
_Nodes[k]->stickPSToSkeleton(skel, (uint) boneID, parentSkelName, parentBoneName);
break;
sint boneID = skel->getBoneIdByName(parentBoneName);
if (boneID != -1)
{
_Nodes[k]->stickPSToSkeleton(skel, (uint) boneID, parentSkelName, parentBoneName);
break;
}
}
}
}
}
}*/
}*/
}
} /* namespace NLQT */

@ -32,14 +32,16 @@
#include "ps_initial_pos.h"
namespace NL3D {
class CParticleSystem;
class CParticleSystemModel;
class CShapeBank;
namespace NL3D
{
class CParticleSystem;
class CParticleSystemModel;
class CShapeBank;
}
namespace NLQT {
namespace NLQT
{
class CParticleWorkspace;
/**
@ -53,93 +55,126 @@ class CParticleWorkspace;
- Loading and saving the existing system of particles.
- Linking / unlinking of the system of particles to any bone of the skeleton model.
- Operations with the name and directory location of the particles system file.
- Has a flag indicating if the particles system changed or not (intended for the editor)
- Has a flag indicating if the particles system changed or not (intended for the editor)
*/
class CWorkspaceNode : public NLMISC::CRefCount
{
public:
void init(CParticleWorkspace *ws);
void setRelativePath(const std::string &relativePath);
const std::string &getRelativePath() const { return _RelativePath; }
const std::string &getRelativePath() const
{
return _RelativePath;
}
std::string getFullPath() const;
std::string getFilename() const { return NLMISC::CFile::getFilename(_RelativePath); }
std::string getFilename() const
{
return NLMISC::CFile::getFilename(_RelativePath);
}
/// Serial node information into workspace stream. This does not save the particle system shape, only a reference to its file
void serial(NLMISC::IStream &f);
/// Save the particle system target file
void savePS() throw(NLMISC::EStream);
/// Save particle system with an arbitrary filename
void savePSAs(const std::string &fullPath) throw(NLMISC::EStream);
/// put back in the unloaded state
void unload();
/// Load the particle system target file
/// @return true if loading succeed (false means that loading was ok, but this is not a particle system). Other cases throw an exception.
bool loadPS() throw(NLMISC::EStream);
/// Create an empty particle system
void createEmptyPS();
/// Helper flag to know if a ps has been modified
/// @{
bool isModified() const { return _Modified; }
bool isModified() const
{
return _Modified;
}
void setModified(bool modified);
/// @}
NL3D::CParticleSystem *getPSPointer() const { return _PS; }
NL3D::CParticleSystemModel *getPSModel() const { return _PSM; }
NL3D::CParticleSystem *getPSPointer() const
{
return _PS;
}
NL3D::CParticleSystemModel *getPSModel() const
{
return _PSM;
}
/// See if this node ps has been loaded
bool isLoaded() const { return _PS != NULL; }
bool isLoaded() const
{
return _PS != NULL;
}
/// Get the workspace in which this node is inserted
CParticleWorkspace *getWorkspace() const { return _WS; }
CParticleWorkspace *getWorkspace() const
{
return _WS;
}
/// Memorize current position of object in the system. Useful to play the system because instances can be created / deleted
void memorizeState();
/// Restore state previously memorize. Is usually called when the user stops a particle system
void restoreState();
/// Test if state is currenlty memorized
bool isStateMemorized() const;
/// For edition : If the state of the system has been memorized, keep it on par with the system when it is modified
void removeLocated(NL3D::CPSLocated *loc);
/// For edition : If the state of the system has been memorized, keep it on par with the system when it is modified
/// For edition : If the state of the system has been memorized, keep it on par with the system when it is modified
void removeLocatedBindable(NL3D::CPSLocatedBindable *lb);
/// Returns the skeleton to which the ps is currently sticked
NL3D::CSkeletonModel *getParentSkel() const { return _ParentSkel; }
const std::string &getParentSkelName() const { return _ParentSkelName; }
const std::string &getParentBoneName() const { return _ParentBoneName; }
std::string getTriggerAnim() { return _TriggerAnim; }
NL3D::CSkeletonModel *getParentSkel() const
{
return _ParentSkel;
}
const std::string &getParentSkelName() const
{
return _ParentSkelName;
}
const std::string &getParentBoneName() const
{
return _ParentBoneName;
}
std::string getTriggerAnim()
{
return _TriggerAnim;
}
void setTriggerAnim(const std::string &anim);
private:
std::string _TriggerAnim;
NL3D::CParticleSystem *_PS;
NL3D::CParticleSystemModel *_PSM;
// Keep a shape bank per node because we want the whole path to identify the ps, not just its filename
// (shape bank keeps the filename only)
NL3D::CShapeBank *_ShapeBank;
// Relative path from which the ps was inserted
// relative path is also a unique identifier for this ps in the workspace
std::string _RelativePath;
// initial pos of system. Allow to restore the initial instances of the system when doing start / stop
CPSInitialPos _InitialPos;
bool _Modified;
@ -152,14 +187,20 @@ private:
private:
void setup(NL3D::CParticleSystemModel &psm);
public:
bool getResetAutoCountFlag() const { return _ResetAutoCount; }
void setResetAutoCountFlag(bool reset) { _ResetAutoCount = reset; }
bool getResetAutoCountFlag() const
{
return _ResetAutoCount;
}
void setResetAutoCountFlag(bool reset)
{
_ResetAutoCount = reset;
}
/// Stick to a skeleton
void stickPSToSkeleton(NL3D::CSkeletonModel *skel,
uint bone,
const std::string &parentSkelName, // for callback after loading
const std::string &parentBoneName
const std::string &parentBoneName
);
void unstickPSFromSkeleton();
private:
@ -174,7 +215,7 @@ public:
typedef std::vector<NLMISC::CRefPtr<CWorkspaceNode> > TNodeVect;
typedef TNodeVect::iterator TPWNodeItr;
/**
/**
@class CParticleWorkspace
@author Nicolas Vizerie
@author Nevrax France
@ -182,11 +223,11 @@ typedef TNodeVect::iterator TPWNodeItr;
@brief A container containing all the loaded particle system.
@details Allows you to load \ save in xml file list of systems of particles (the path to each file as well)
and additional parameters (skeleton model, and to which bone it is attached)
There is a feedback mechanism showed changes are being made with the container,with a particle system or connection to the skeleton.
There is a feedback mechanism showed changes are being made with the container,with a particle system or connection to the skeleton.
*/
class CParticleWorkspace
{
public:
public:
/// callback to know when a workspace node has been modified
struct IModificationCallback
{
@ -200,88 +241,115 @@ public:
~CParticleWorkspace();
/// Init the workspace for the given object viewer
/// must be called prior to other methods
/// must be called prior to other methods
void init(const std::string &filename);
/// Set a new name for the workspace (not its filename)
void setName(const std::string &name);
/// Set a new file name for the workspace
void setFileName(const std::string &fileName);
std::string getName() const { return _Name; }
std::string getName() const
{
return _Name;
}
/// Get the path in which workpsace is located with a trailing slash
std::string getPath() const;
std::string getFilename() const;
/// Get Number of nodes in the workspace
uint getNumNode() const { return (uint)_Nodes.size(); }
uint getNumNode() const
{
return (uint)_Nodes.size();
}
/// Get a node in workspace
/// Can keep pointer safely as long as the node is not deleted
CWorkspaceNode *getNode(uint index) const { return _Nodes[index]; }
CWorkspaceNode *getNode(uint index) const
{
return _Nodes[index];
}
/// Get a node from a pointer on a particle system
CWorkspaceNode *getNodeFromPS(NL3D::CParticleSystem *ps) const;
/// Test if the workspace already contains a node with the given filename name
/// NB : 2 node with the same name re not allowed, even if their path is different
bool containsFile(std::string filename) const;
/// Add a node in the workspace. Will succeed only if fx filename does not already exist in the workspace.
/// The node is in the 'unloaded' state, so caller must load it afterward.
/// NB : no lookup is done, full path must be provided.
/// @return pointer to new node, or NULL if already inserted
/// The node is in the 'unloaded' state, so caller must load it afterward.
/// NB : no lookup is done, full path must be provided.
/// @return pointer to new node, or NULL if already inserted
CWorkspaceNode *addNode(const std::string &filenameWithFullPath) throw( NLMISC::Exception);
/// Remove a node by it's index
void removeNode(uint index);
/// Remove a node by it's pointer
void removeNode(CWorkspaceNode *ptr);
/// Get index of a node from its pointer, or -1 if not found
sint getIndexFromNode(CWorkspaceNode *node) const;
/// Save the workspace structure. The target file is the one given when this object was created
/// Save the workspace structure. The target file is the one given when this object was created
/// NB : ps shape are not saved, only the structure is. To save the shapes, call CNode::save()
void save() throw(NLMISC::EStream);
/// Load the workspace structure. The target file is the one given when this object was created
/// All nodes are in the 'unloaded" state, so it is to the caller to load them by calling load() on their node
void load() throw(NLMISC::EStream);
/// Test whether the structure of the workspace has been modified (does not test if ps inside the workspace have been modified)
bool isModified() const { return _Modified; }
bool isModified() const
{
return _Modified;
}
/// Test whether the content of the workspace has ben modified
bool isContentModified() const;
void touch() { setModifiedFlag(true); }
void clearModifiedFlag() { setModifiedFlag(false); }
void touch()
{
setModifiedFlag(true);
}
void clearModifiedFlag()
{
setModifiedFlag(false);
}
/// Set a callback to know when a node is modified
void setModificationCallback(IModificationCallback *cb) { _ModificationCallback = cb; }
IModificationCallback *getModificationCallback() const { return _ModificationCallback; }
void setModificationCallback(IModificationCallback *cb)
{
_ModificationCallback = cb;
}
IModificationCallback *getModificationCallback() const
{
return _ModificationCallback;
}
/// Restick all objects, useful after loading
void restickAllObjects();
TNodeVect& getNodeList() { return _Nodes; }
TNodeVect& getNodeList()
{
return _Nodes;
}
private:
// use smart ptr to avoir prb wih resize
TNodeVect _Nodes;
// path + name of workspace
std::string _Filename;
std::string _Filename;
bool _Modified;
IModificationCallback *_ModificationCallback;
// workspace user name
std::string _Name;
/// serial the object
void serial(NLMISC::IStream &f) throw(NLMISC::EStream);
void serial(NLMISC::IStream &f) throw(NLMISC::EStream);
/// set the 'modified flag' and call the callback
void setModifiedFlag(bool modified);

@ -25,7 +25,8 @@
// Project includes
#include "modules.h"
namespace NLQT {
namespace NLQT
{
CPropertyDialog::CPropertyDialog(CParticleTreeModel *treeModel, QWidget *parent)
: QDockWidget(parent)
@ -41,19 +42,19 @@ CPropertyDialog::~CPropertyDialog()
void CPropertyDialog::setupUi()
{
setObjectName(QString::fromUtf8("CPropertyDialog"));
QIcon icon;
icon.addFile(QString::fromUtf8(":/images/pqrticles.png"), QSize(), QIcon::Normal, QIcon::Off);
setWindowIcon(icon);
setWindowIcon(icon);
_dockWidgetContents = new QWidget();
_gridLayout = new QGridLayout(_dockWidgetContents);
_scrollArea = new QScrollArea(_dockWidgetContents);
_scrollArea->setWidgetResizable(true);
_scrollAreaWidgetContents = new QWidget();
_pagesGridLayout = new QGridLayout(_scrollAreaWidgetContents);
_stackedWidget = new QStackedWidget(_scrollAreaWidgetContents);
_wpPage = new CWorkspacePage(_treeModel);
@ -76,15 +77,15 @@ void CPropertyDialog::setupUi()
_stackedWidget->addWidget(_emitterPage);
_psMoverPage = new CPSMoverPage(_stackedWidget);
_stackedWidget->addWidget(_psMoverPage);
_pagesGridLayout->addWidget(_stackedWidget, 0, 0, 1, 1);
_scrollArea->setWidget(_scrollAreaWidgetContents);
_gridLayout->addWidget(_scrollArea, 0, 0, 1, 1);
setWidget(_dockWidgetContents);
setWindowTitle(tr("Property editor"));
setWindowTitle(tr("Property editor"));
}
void CPropertyDialog::setCurrentEditedElement(CParticleTreeItem *editedItem)
@ -127,9 +128,9 @@ void CPropertyDialog::setCurrentEditedElement(CParticleTreeItem *editedItem)
case ItemType::LocatedInstance:
_psMoverPage->setEditedItem(_treeModel->getOwnerNode(editedItem) ,editedItem->getLoc(), editedItem->getLocatedInstanceIndex());
_stackedWidget->setCurrentWidget(_psMoverPage);
_treeModel->getOwnerNode(editedItem)->getPSPointer()->setCurrentEditedElement(editedItem->getLoc(),
editedItem->getLocatedInstanceIndex(),
_psMoverPage->getLocatedBindable());
_treeModel->getOwnerNode(editedItem)->getPSPointer()->setCurrentEditedElement(editedItem->getLoc(),
editedItem->getLocatedInstanceIndex(),
_psMoverPage->getLocatedBindable());
break;
default:
_stackedWidget->setCurrentWidget(_wpPage);

@ -44,7 +44,8 @@
#include "particle_tree_model.h"
#include "particle_node.h"
namespace NLQT {
namespace NLQT
{
class CPropertyDialog: public QDockWidget
{
@ -52,21 +53,27 @@ class CPropertyDialog: public QDockWidget
public:
CPropertyDialog(CParticleTreeModel *treeModel, QWidget *parent = 0);
~CPropertyDialog();
void setCurrentEditedElement(CParticleTreeItem *editedItem);
CLocatedPage *getLocatedPage() const { return _locatedPage; };
CPSMoverPage *getMoverPage() const { return _psMoverPage; };
CLocatedPage *getLocatedPage() const
{
return _locatedPage;
};
CPSMoverPage *getMoverPage() const
{
return _psMoverPage;
};
private:
void setupUi();
QWidget *_dockWidgetContents;
QGridLayout *_gridLayout;
QGridLayout *_pagesGridLayout;
QScrollArea *_scrollArea;
QWidget *_scrollAreaWidgetContents;
QStackedWidget *_stackedWidget;
CWorkspacePage *_wpPage;
CParticleSystemPage *_psPage;
@ -80,7 +87,7 @@ private:
CPSMoverPage *_psMoverPage;
CParticleTreeModel *_treeModel;
friend class CParticleWorkspaceDialog;
}; /* class CPropertyDialog */

@ -32,13 +32,14 @@
#include "modules.h"
#include "sound_system.h"
namespace NLQT {
namespace NLQT
{
CSoundPage::CSoundPage(QWidget *parent)
: QWidget(parent)
: QWidget(parent)
{
_ui.setupUi(this);
// setup dialog the sounds gain
_ui.gainWidget->setRange(0.f, 1.f);
_ui.gainWidget->setWrapper(&_GainWrapper);
@ -53,7 +54,7 @@ CSoundPage::CSoundPage(QWidget *parent)
// setup dialog the percent of sound emissions
_ui.emissionWidget->setRange(0.f, 1.f);
connect(_ui.browsePushButton ,SIGNAL(clicked()), this, SLOT(browse()));
connect(_ui.playPushButton ,SIGNAL(clicked()), this, SLOT(play()));
connect(_ui.spawnCheckBox ,SIGNAL(toggled(bool)), this, SLOT(setSpawn(bool)));
@ -72,9 +73,9 @@ void CSoundPage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocatedBindab
{
_Sound = static_cast<NL3D::CPSSound *>(locatedBindable);
_Node = ownerNode;
nlassert(_Sound);
_ui.emissionWidget->setValue(_Sound->getEmissionPercent(), false);
_GainWrapper.S = _Sound;
@ -95,7 +96,7 @@ void CSoundPage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocatedBindab
void CSoundPage::browse()
{
std::vector<NLMISC::TStringId> names;
NLSOUND::UAudioMixer *audioMixer = Modules::sound().getAudioMixer();
if (audioMixer)
@ -106,14 +107,14 @@ void CSoundPage::browse()
// TODO: create CPickSound dialog
QStringList items;
items << tr("");
for(size_t i = 0; i < names.size(); ++i)
items << QString(names[i]->c_str());
for(size_t i = 0; i < names.size(); ++i)
items << QString(names[i]->c_str());
bool ok;
QString item = QInputDialog::getItem(this, tr("Select your sound"),
tr("Sound:"), items, 0, false, &ok);
tr("Sound:"), items, 0, false, &ok);
if (ok)
{
{
_ui.soundNameLineEdit->setText(item);
updateModifiedFlag();
}

@ -35,19 +35,20 @@
namespace NLSOUND
{
class UAudioMixer;
class UAudioMixer;
}
namespace NLQT {
namespace NLQT
{
/**
@class CSoundPage
@brief Page for QStackWidget, to edit sounds in a particle system
*/
*/
class CSoundPage: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CSoundPage(QWidget *parent = 0);
~CSoundPage();
@ -65,36 +66,63 @@ private Q_SLOTS:
void setEmissionPercent(float value);
private:
/// wrapper to set the gain of sounds
struct CGainWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
{
NL3D::CPSSound *S;
float get(void) const { return S->getGain(); }
void set(const float &v) { S->setGain(v); }
scheme_type *getScheme(void) const { return S->getGainScheme(); }
void setScheme(scheme_type *s) { S->setGainScheme(s); }
float get(void) const
{
return S->getGain();
}
void set(const float &v)
{
S->setGain(v);
}
scheme_type *getScheme(void) const
{
return S->getGainScheme();
}
void setScheme(scheme_type *s)
{
S->setGainScheme(s);
}
} _GainWrapper;
/// wrapper to set the pitch of sounds
struct CPitchWrapper : public IPSWrapperFloat, IPSSchemeWrapperFloat
{
NL3D::CPSSound *S;
float get(void) const { return S->getPitch(); }
void set(const float &v) { S->setPitch(v); }
scheme_type *getScheme(void) const { return S->getPitchScheme(); }
void setScheme(scheme_type *s) { S->setPitchScheme(s); }
float get(void) const
{
return S->getPitch();
}
void set(const float &v)
{
S->setPitch(v);
}
scheme_type *getScheme(void) const
{
return S->getPitchScheme();
}
void setScheme(scheme_type *s)
{
S->setPitchScheme(s);
}
} _PitchWrapper;
void updateModifiedFlag() { if (_Node) _Node->setModified(true); }
void updateModifiedFlag()
{
if (_Node) _Node->setModified(true);
}
/// the sound being edited
NL3D::CPSSound *_Sound;
CWorkspaceNode *_Node;
Ui::CSoundPage _ui;
}; /* class CSoundPage */
} /* namespace NLQT */

@ -38,25 +38,26 @@
using namespace NL3D;
using namespace NLMISC;
namespace NLQT {
namespace NLQT
{
static void chooseGlobalUserParam(uint userParam, NL3D::CParticleSystem *ps, QWidget *parent)
{
nlassert(ps);
bool ok;
QString text = QInputDialog::getText(parent, "Choose Global User Param",
"User name:", QLineEdit::Normal,
QString(ps->getGlobalValueName(userParam).c_str()), &ok);
if (ok)
ps->bindGlobalValueToUserParam(text.toStdString(), userParam);
"User name:", QLineEdit::Normal,
QString(ps->getGlobalValueName(userParam).c_str()), &ok);
if (ok)
ps->bindGlobalValueToUserParam(text.toStdString(), userParam);
}
CParticleSystemPage::CParticleSystemPage(QWidget *parent)
: QWidget(parent)
: QWidget(parent)
{
_ui.setupUi(this);
_ui.timeThresholdWidget->setRange(0.005f, 0.3f);
_ui.timeThresholdWidget->enableLowerBound(0, true);
@ -81,11 +82,11 @@ CParticleSystemPage::CParticleSystemPage(QWidget *parent)
_ui.maxViewDistWidget->setRange(0, 400.f);
_ui.maxViewDistWidget->enableLowerBound(0, true);
_ui.lodRatioWidget->setRange(0, 1.f);
_ui.lodRatioWidget->enableLowerBound(0, true);
_ui.lodRatioWidget->enableUpperBound(1, true);
_ui.colorWidget->setSchemeWrapper(&_GlobalColorWrapper);
_ui.colorWidget->enableMemoryScheme(false);
_ui.colorWidget->enableNbCycles(false);
@ -93,27 +94,27 @@ CParticleSystemPage::CParticleSystemPage(QWidget *parent)
_ui.colorWidget->setEnabledConstantValue(false);
_ui.colorWidget->init();
_ui.colorWidget->hide();
// Integration tab
connect(_ui.loadBalancingCheckBox ,SIGNAL(toggled(bool)), this, SLOT(setLoadBalancing(bool)));
connect(_ui.integrationCheckBox ,SIGNAL(toggled(bool)), this, SLOT(setIntegration(bool)));
connect(_ui.motionSlowDownCheckBox ,SIGNAL(toggled(bool)), this, SLOT(setMotionSlowDown(bool)));
connect(_ui.lockPushButton ,SIGNAL(toggled(bool)), this, SLOT(setLock(bool)));
connect(_ui.timeThresholdWidget ,SIGNAL(valueChanged(float)), this, SLOT(setTimeThreshold(float)));
connect(_ui.maxStepsWidget ,SIGNAL(valueChanged(uint32)), this, SLOT(setMaxSteps(uint32)));
// User param tab
connect(_ui.globalPushButton_1 ,SIGNAL(clicked()), this, SLOT(setGloabal1()));
connect(_ui.globalPushButton_2 ,SIGNAL(clicked()), this, SLOT(setGloabal2()));
connect(_ui.globalPushButton_3 ,SIGNAL(clicked()), this, SLOT(setGloabal3()));
connect(_ui.globalPushButton_4 ,SIGNAL(clicked()), this, SLOT(setGloabal4()));
connect(_ui.userParamWidget_1 ,SIGNAL(valueChanged(float)), this, SLOT(setUserParam1(float)));
connect(_ui.userParamWidget_2 ,SIGNAL(valueChanged(float)), this, SLOT(setUserParam2(float)));
connect(_ui.userParamWidget_3 ,SIGNAL(valueChanged(float)), this, SLOT(setUserParam3(float)));
connect(_ui.userParamWidget_4 ,SIGNAL(valueChanged(float)), this, SLOT(setUserParam4(float)));
// BBox tab
connect(_ui.enablePBBCheckBox ,SIGNAL(toggled(bool)), this, SLOT(setEnableBbox(bool)));
connect(_ui.autoCheckBox ,SIGNAL(toggled(bool)), this, SLOT(setAutoBbox(bool)));
@ -123,7 +124,7 @@ CParticleSystemPage::CParticleSystemPage(QWidget *parent)
connect(_ui.xDoubleSpinBox ,SIGNAL(valueChanged(double)), this, SLOT(setXBbox(double)));
connect(_ui.yDoubleSpinBox ,SIGNAL(valueChanged(double)), this, SLOT(setYBbox(double)));
connect(_ui.zDoubleSpinBox ,SIGNAL(valueChanged(double)), this, SLOT(setZBbox(double)));
// LOD param tab
connect(_ui.sharableCheckBox ,SIGNAL(toggled(bool)), this, SLOT(setSharable(bool)));
connect(_ui.autoLODCheckBox ,SIGNAL(toggled(bool)), this, SLOT(setAutoLOD(bool)));
@ -131,11 +132,11 @@ CParticleSystemPage::CParticleSystemPage(QWidget *parent)
connect(_ui.maxViewDistWidget ,SIGNAL(valueChanged(float)), this, SLOT(setMaxViewDist(float)));
connect(_ui.lodRatioWidget ,SIGNAL(valueChanged(float)), this, SLOT(setLodRatio(float)));
// Global color tab
connect(_ui.editGlobalColorCheckBox ,SIGNAL(toggled(bool)), this, SLOT(setEditGlobalColor(bool)));
connect(_ui.globalLightCheckBox ,SIGNAL(toggled(bool)), this, SLOT(setGlobalLight(bool)));
// Life mgt param tab
connect(_ui.presetBehaviourComboBox ,SIGNAL(currentIndexChanged(int)), this, SLOT(setPresetBehaviour(int)));
connect(_ui.modelRemovedCheckBox ,SIGNAL(toggled(bool)), this, SLOT(setModelRemoved(bool)));
@ -158,7 +159,7 @@ void CParticleSystemPage::setEditedParticleSystem(CWorkspaceNode *node)
{
_Node = node;
enabledModifiedFlag = false;
NL3D::TAnimationTime t;
uint32 max;
bool csd;
@ -167,16 +168,16 @@ void CParticleSystemPage::setEditedParticleSystem(CWorkspaceNode *node)
// Update param Time threshold.
_ui.timeThresholdWidget->setValue(t, false);
// Update param Max steps.
_ui.maxStepsWidget->setValue(max, false);
// Update param User Param
_ui.userParamWidget_1->setValue(_Node->getPSPointer()->getUserParam(0) , false);
_ui.userParamWidget_2->setValue(_Node->getPSPointer()->getUserParam(1) , false);
_ui.userParamWidget_3->setValue(_Node->getPSPointer()->getUserParam(2) , false);
_ui.userParamWidget_4->setValue(_Node->getPSPointer()->getUserParam(3) , false);
// Update param Max view dist.
_ui.maxViewDistWidget->setValue(_Node->getPSPointer()->getMaxViewDist(), false);
@ -187,7 +188,7 @@ void CParticleSystemPage::setEditedParticleSystem(CWorkspaceNode *node)
_ui.integrationCheckBox->setChecked(_Node->getPSPointer()->isAccurateIntegrationEnabled());
_ui.loadBalancingCheckBox->setChecked(_Node->getPSPointer()->isLoadBalancingEnabled());
_ui.motionSlowDownCheckBox->setChecked(csd);
// Precomputed Bbox
_ui.enablePBBCheckBox->setChecked(!_Node->getPSPointer()->getAutoComputeBBox());
@ -198,9 +199,9 @@ void CParticleSystemPage::setEditedParticleSystem(CWorkspaceNode *node)
_ui.colorWidget->setWorkspaceNode(_Node);
int bGlobalColor = _Node->getPSPointer()->getColorAttenuationScheme() != NULL ? 1 : 0;
_ui.editGlobalColorCheckBox->setChecked(bGlobalColor);
if (bGlobalColor)
if (bGlobalColor)
_ui.colorWidget->updateUi();
// Life mgt parameters
_ui.presetBehaviourComboBox->setCurrentIndex(_Node->getPSPointer()->getBehaviourType());
_ui.sharableCheckBox->setChecked(_Node->getPSPointer()->isSharingEnabled());
@ -211,10 +212,10 @@ void CParticleSystemPage::setEditedParticleSystem(CWorkspaceNode *node)
_ui.noMaxNBStepsCheckBox->setChecked(_Node->getPSPointer()->getBypassMaxNumIntegrationSteps());
_ui.lifeTimeUpdateCheckBox->setChecked(klt);
_ui.dieComboBox->setCurrentIndex(_Node->getPSPointer()->getDestroyCondition());
_ui.dieComboBox->setCurrentIndex(_Node->getPSPointer()->getDestroyCondition());
_ui.animTypeComboBox->setCurrentIndex(_Node->getPSPointer()->getAnimType());
_ui.autoDelayCheckBox->setChecked(_Node->getPSPointer()->getAutoComputeDelayBeforeDeathConditionTest());
enabledModifiedFlag = true;
}
@ -241,7 +242,7 @@ void CParticleSystemPage::updateDieOnEventParams()
void CParticleSystemPage::updateLifeMgtPresets()
{
bool bEnable = _Node->getPSPointer()->getBehaviourType() == NL3D::CParticleSystem::UserBehaviour ? true : false;
_ui.modelRemovedCheckBox->setEnabled(bEnable);
_ui.psResourceCheckBox->setEnabled(bEnable);
_ui.lifeTimeUpdateCheckBox->setEnabled(bEnable);
@ -269,8 +270,8 @@ void CParticleSystemPage::setLoadBalancing(bool state)
{
QMessageBox::StandardButton reply;
reply = QMessageBox::question(this, tr("Are you sure?"),
tr("Load balancing on/off"),
QMessageBox::Yes | QMessageBox::No);
tr("Load balancing on/off"),
QMessageBox::Yes | QMessageBox::No);
if (reply == QMessageBox::Yes)
_Node->getPSPointer()->enableLoadBalancing(false);
else
@ -286,7 +287,7 @@ void CParticleSystemPage::setLoadBalancing(bool state)
void CParticleSystemPage::setIntegration(bool state)
{
// enable/disable accurate integration.
if (state != _Node->getPSPointer()->isAccurateIntegrationEnabled())
if (state != _Node->getPSPointer()->isAccurateIntegrationEnabled())
{
_Node->getPSPointer()->enableAccurateIntegration(state);
updateModifiedFlag();
@ -310,7 +311,7 @@ void CParticleSystemPage::setMotionSlowDown(bool state)
void CParticleSystemPage::setLock(bool checked)
{
// Need frame delay dialog.
// Need frame delay dialog.
}
void CParticleSystemPage::setGloabal1()
@ -322,19 +323,19 @@ void CParticleSystemPage::setGloabal1()
void CParticleSystemPage::setGloabal2()
{
chooseGlobalUserParam(1, _Node->getPSPointer(), this);
updateModifiedFlag();
chooseGlobalUserParam(1, _Node->getPSPointer(), this);
updateModifiedFlag();
}
void CParticleSystemPage::setGloabal3()
{
chooseGlobalUserParam(2, _Node->getPSPointer(), this);
chooseGlobalUserParam(2, _Node->getPSPointer(), this);
updateModifiedFlag();
}
void CParticleSystemPage::setGloabal4()
{
chooseGlobalUserParam(3, _Node->getPSPointer(), this);
chooseGlobalUserParam(3, _Node->getPSPointer(), this);
updateModifiedFlag();
}
@ -345,7 +346,7 @@ void CParticleSystemPage::setEnableBbox(bool state)
_Node->getPSPointer()->setAutoComputeBBox(!state);
updateModifiedFlag();
}
if (state)
updatePrecomputedBBoxParams();
else
@ -366,7 +367,7 @@ void CParticleSystemPage::resetBbox()
void CParticleSystemPage::incBbox()
{
NLMISC::CAABBox b;
NLMISC::CAABBox b;
_Node->getPSPointer()->computeBBox(b);
b.setHalfSize(1.1f * b.getHalfSize());
_Node->getPSPointer()->setPrecomputedBBox(b);
@ -421,7 +422,7 @@ void CParticleSystemPage::setZBbox(double value)
void CParticleSystemPage::setEditGlobalColor(bool state)
{
bool bGlobalColor = _Node->getPSPointer()->getColorAttenuationScheme() != NULL ? true : false;
if (state != bGlobalColor)
if (state != bGlobalColor)
{
// if the system hasn't a global color scheme, add one.
if (_Node->getPSPointer()->getColorAttenuationScheme() == NULL)
@ -444,7 +445,7 @@ void CParticleSystemPage::setPresetBehaviour(int index)
updateLifeMgtPresets();
if (index == _Node->getPSPointer()->getBehaviourType()) return;
if (index == NL3D::CParticleSystem::SpellFX ||
index == NL3D::CParticleSystem::SpawnedEnvironmentFX)
index == NL3D::CParticleSystem::SpawnedEnvironmentFX)
{
NL3D::CPSLocatedBindable *lb;
if (!_Node->getPSPointer()->canFinish(&lb))
@ -455,13 +456,13 @@ void CParticleSystemPage::setPresetBehaviour(int index)
if (!lb)
{
errorMessage->showMessage(tr("Can't perform operation : the system is flagged with 'No max nb steps' or uses the preset 'Spell FX', "
"and thus, should have a finite duration. Please remove that flag first."));
"and thus, should have a finite duration. Please remove that flag first."));
errorMessage->exec();
}
else
{
errorMessage->showMessage(tr("The system must have a finite duration for this setting! Please check that the following object "
"doesn't live forever or doesn't create a loop in the system :") + QString(lb->getName().c_str()));
"doesn't live forever or doesn't create a loop in the system :") + QString(lb->getName().c_str()));
errorMessage->exec();
}
delete errorMessage;
@ -476,7 +477,7 @@ void CParticleSystemPage::setPresetBehaviour(int index)
void CParticleSystemPage::setSharable(bool state)
{
if (state == _Node->getPSPointer()->isSharingEnabled()) return;
_Node->getPSPointer()->enableSharing(state);
_Node->getPSPointer()->enableSharing(state);
updateModifiedFlag();
}
@ -505,7 +506,7 @@ void CParticleSystemPage::setModelRemoved(bool state)
void CParticleSystemPage::setPSResource(bool state)
{
if (state != _Node->getPSPointer()->doesDestroyWhenOutOfFrustum())
if (state != _Node->getPSPointer()->doesDestroyWhenOutOfFrustum())
{
_Node->getPSPointer()->destroyWhenOutOfFrustum(state);
updateModifiedFlag();
@ -530,7 +531,7 @@ void CParticleSystemPage::setNoMaxNBSteps(bool state)
_ui.maxStepsWidget->setEnabled(!state);
if (state == _Node->getPSPointer()->getBypassMaxNumIntegrationSteps()) return;
if (state && !_Node->getPSPointer()->canFinish())
{
{
QErrorMessage *errorMessage = new QErrorMessage();
errorMessage->setModal(true);
errorMessage->showMessage(tr("The system must have a finite duration for this setting! Please check that."));
@ -562,7 +563,7 @@ void CParticleSystemPage::setAnimType(int index)
void CParticleSystemPage::setDie(int index)
{
if (index != _Node->getPSPointer()->getDestroyCondition())
{
{
_Node->getPSPointer()->setDestroyCondition((NL3D::CParticleSystem::TDieCondition) index);
updateModifiedFlag();
}
@ -578,7 +579,7 @@ void CParticleSystemPage::setAfterDelay(double value)
}
}
void CParticleSystemPage::setTimeThreshold(float value)
{
NL3D::TAnimationTime t;
@ -586,7 +587,7 @@ void CParticleSystemPage::setTimeThreshold(float value)
bool csd;
bool klt;
_Node->getPSPointer()->getAccurateIntegrationParams(t, max, csd, klt);
_Node->getPSPointer()->setAccurateIntegrationParams(value, max, csd, klt);
_Node->getPSPointer()->setAccurateIntegrationParams(value, max, csd, klt);
updateModifiedFlag();
}
@ -597,25 +598,25 @@ void CParticleSystemPage::setMaxSteps(uint32 value)
bool csd;
bool klt;
_Node->getPSPointer()->getAccurateIntegrationParams(t, max, csd, klt);
_Node->getPSPointer()->setAccurateIntegrationParams(t, value, csd, klt);
_Node->getPSPointer()->setAccurateIntegrationParams(t, value, csd, klt);
updateModifiedFlag();
}
void CParticleSystemPage::setUserParam1(float value)
{
_Node->getPSPointer()->setUserParam(0, value);
_Node->getPSPointer()->setUserParam(0, value);
updateModifiedFlag();
}
void CParticleSystemPage::setUserParam2(float value)
{
_Node->getPSPointer()->setUserParam(1, value);
_Node->getPSPointer()->setUserParam(1, value);
updateModifiedFlag();
}
void CParticleSystemPage::setUserParam3(float value)
{
_Node->getPSPointer()->setUserParam(2, value);
_Node->getPSPointer()->setUserParam(2, value);
updateModifiedFlag();
}

@ -33,19 +33,20 @@
// Project includes
#include "edit_range_widget.h"
namespace NLQT {
namespace NLQT
{
/**
@class CParticleSystemPage
@brief Page for QStackWidget, to edit workspace node in a particle system
*/
class CParticleSystemPage: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CParticleSystemPage(QWidget *parent = 0);
~CParticleSystemPage();
/// Set the workspace node to edit.
void setEditedParticleSystem(CWorkspaceNode *node);
@ -55,7 +56,7 @@ private Q_SLOTS:
void setIntegration(bool state);
void setMotionSlowDown(bool state);
void setLock(bool checked);
void setTimeThreshold(float value);
void setMaxSteps(uint32 value);
@ -79,19 +80,19 @@ private Q_SLOTS:
void setXBbox(double value);
void setYBbox(double value);
void setZBbox(double value);
// LOD Param
void setSharable(bool state);
void setAutoLOD(bool state);
void settings();
void setMaxViewDist(float value);
void setLodRatio(float value);
// Global color tab
void setGlobalLight(bool state);
void setEditGlobalColor(bool state);
// Life mgt param
void setPresetBehaviour(int index);
void setModelRemoved(bool state);
@ -102,16 +103,19 @@ private Q_SLOTS:
void setAnimType(int index);
void setDie(int index);
void setAfterDelay(double value);
private:
void updatePrecomputedBBoxParams();
void updateDieOnEventParams();
void updateLifeMgtPresets();
bool enabledModifiedFlag;
void updateModifiedFlag() { if ((_Node) && (enabledModifiedFlag)) _Node->setModified(true); }
void updateModifiedFlag()
{
if ((_Node) && (enabledModifiedFlag)) _Node->setModified(true);
}
CWorkspaceNode *_Node;
struct CGlobalColorWrapper : public IPSSchemeWrapperRGBA
@ -121,9 +125,9 @@ private:
virtual void setScheme(scheme_type *s);
}
_GlobalColorWrapper;
Ui::CParticleSystemPage _ui;
}; /* class CParticleSystemPage */
} /* namespace NLQT */

@ -31,20 +31,21 @@
#include "value_gradient_dialog.h"
#include "multi_tex_dialog.h"
namespace NLQT {
namespace NLQT
{
CParticleTextureAnimWidget::CParticleTextureAnimWidget(QWidget *parent)
: QWidget(parent)
: QWidget(parent)
{
_ui.setupUi(this);
_ui.texIndexWidget->setRange(0, 1);
_ui.texIndexWidget->setWrapper(&_TextureIndexWrapper );
_ui.texIndexWidget->setSchemeWrapper(&_TextureIndexWrapper );
_ui.texIndexWidget->init();
_ui.texWidget->setWrapper(&_TextureWrapper);
connect(_ui.texAnimCheckBox, SIGNAL(toggled(bool)), this, SLOT(setEnabledTexAnim(bool)));
connect(_ui.multitexturingCheckBox, SIGNAL(toggled(bool)), this, SLOT(setMultitexturing(bool)));
connect(_ui.editPushButton, SIGNAL(clicked()), this, SLOT(editMultitexturing()));
@ -60,13 +61,13 @@ void CParticleTextureAnimWidget::setCurrentTextureAnim(NL3D::CPSTexturedParticle
_Node = ownerNode;
_EditedParticle = tp;
_MTP = mtp;
disconnect(_ui.texAnimCheckBox, SIGNAL(toggled(bool)), this, SLOT(setEnabledTexAnim(bool)));
bool isAnimTex = _EditedParticle->getTextureGroup() ? true : false;
_ui.texAnimCheckBox->setChecked(isAnimTex);
updateTexAnimState(isAnimTex);
if (_MTP)
{
_ui.multitexturingCheckBox->setChecked(_MTP->isMultiTextureEnabled());
@ -74,20 +75,20 @@ void CParticleTextureAnimWidget::setCurrentTextureAnim(NL3D::CPSTexturedParticle
}
else
_ui.multitexturingGroupBox->hide();
connect(_ui.texAnimCheckBox, SIGNAL(toggled(bool)), this, SLOT(setEnabledTexAnim(bool)));
}
void CParticleTextureAnimWidget::setEnabledTexAnim(bool state)
{
if (state)
if (state)
{
if (_MTP)
_ui.multitexturingCheckBox->setChecked(false);
// When you try to load a dummy texture, remove alternative paths, an assertion is thrown otherwise
NLMISC::CPath::removeAllAlternativeSearchPath();
// put a dummy texture as a first texture
NLMISC::CSmartPtr<NL3D::ITexture> tex = (NL3D::ITexture *) new NL3D::CTextureFile(std::string(""));
NL3D::CTextureGrouped *tg = new NL3D::CTextureGrouped;

@ -34,16 +34,17 @@
namespace NL3D
{
class CPSTexturedParticle;
class CPSMultiTexturedParticle;
class CPSTexturedParticle;
class CPSMultiTexturedParticle;
}
namespace NLQT {
namespace NLQT
{
class CParticleTextureAnimWidget: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CParticleTextureAnimWidget(QWidget *parent = 0);
~CParticleTextureAnimWidget();
@ -55,34 +56,55 @@ private Q_SLOTS:
void setEnabledTexAnim(bool state);
void setMultitexturing(bool enabled);
void editMultitexturing();
private:
private:
void updateTexAnimState(bool state);
/// Wrapper for single texture
struct CTextureWrapper : public IPSWrapperTexture
{
NL3D::CPSTexturedParticle *P;
NL3D::ITexture *get(void) { return P->getTexture(); }
void set(NL3D::ITexture *t) { P->setTexture(t); }
NL3D::ITexture *get(void)
{
return P->getTexture();
}
void set(NL3D::ITexture *t)
{
P->setTexture(t);
}
} _TextureWrapper;
/// Wrapper for texture anim sequence
struct CTextureIndexWrapper : public IPSWrapper<sint32>, IPSSchemeWrapper<sint32>
{
NL3D::CPSTexturedParticle *P;
sint32 get(void) const { return P->getTextureIndex(); }
void set(const sint32 &v) { P->setTextureIndex(v); }
scheme_type *getScheme(void) const { return P->getTextureIndexScheme(); }
void setScheme(scheme_type *s) { P->setTextureIndexScheme(s); }
sint32 get(void) const
{
return P->getTextureIndex();
}
void set(const sint32 &v)
{
P->setTextureIndex(v);
}
scheme_type *getScheme(void) const
{
return P->getTextureIndexScheme();
}
void setScheme(scheme_type *s)
{
P->setTextureIndexScheme(s);
}
} _TextureIndexWrapper;
void updateModifiedFlag() { if (_Node) _Node->setModified(true); }
void updateModifiedFlag()
{
if (_Node) _Node->setModified(true);
}
NL3D::CPSTexturedParticle *_EditedParticle;
NL3D::CPSMultiTexturedParticle *_MTP;
CWorkspaceNode *_Node;
Ui::CParticleTextureAnimWidget _ui;

@ -30,16 +30,17 @@
#include "nel/3d/ps_particle_basic.h"
#include "nel/misc/path.h"
namespace NLQT {
namespace NLQT
{
CParticleTextureWidget::CParticleTextureWidget(QWidget *parent)
: QWidget(parent), _Wrapper(NULL)
: QWidget(parent), _Wrapper(NULL)
{
_ui.setupUi(this);
_ui.imageLabel->setScaledContents(true);
_ui.removePushButton->setVisible(false);
connect(_ui.chooseTexPushButton, SIGNAL(clicked()), this, SLOT(chooseTexture()));
connect(_ui.removePushButton, SIGNAL(clicked()), this, SLOT(removeTexture()));
}
@ -51,7 +52,7 @@ CParticleTextureWidget::~CParticleTextureWidget()
void CParticleTextureWidget::updateUi()
{
nlassert(_Wrapper);
_Texture = _Wrapper->get();
updateTexture();
@ -68,11 +69,11 @@ void CParticleTextureWidget::chooseTexture()
}
QString fileName = QFileDialog::getOpenFileName(this,
tr("Open texture file"), texName.c_str(),
tr("Image file (*.tga *.png)"));
tr("Open texture file"), texName.c_str(),
tr("Image file (*.tga *.png)"));
setCursor(Qt::WaitCursor);
if (!fileName.isEmpty())
if (!fileName.isEmpty())
{
// Add search path for the texture
NLMISC::CPath::addSearchPath(NLMISC::CFile::getPath(fileName.toStdString()));
@ -89,7 +90,7 @@ void CParticleTextureWidget::chooseTexture()
{
QMessageBox::critical(this, tr("Texture loading error"), e.what(), QMessageBox::Ok);
}
}
setCursor(Qt::ArrowCursor);
}
@ -108,7 +109,7 @@ void CParticleTextureWidget::removeTexture()
void CParticleTextureWidget::updateTexture()
{
if (!_Texture)
if (!_Texture)
{
_ui.imageLabel->setPixmap(QPixmap());
return;

@ -34,38 +34,45 @@
// Project includes
#include "ps_wrapper.h"
namespace NLQT {
namespace NLQT
{
class CParticleTextureWidget: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CParticleTextureWidget(QWidget *parent = 0);
~CParticleTextureWidget();
void updateUi();
// set a wrapper to get the datas, called before setCurrentTextureNoAnim
void setWrapper(IPSWrapperTexture *wrapper) { _Wrapper = wrapper ; }
void enableRemoveButton(bool enabled) { _ui.removePushButton->setVisible(enabled); }
void setWrapper(IPSWrapperTexture *wrapper)
{
_Wrapper = wrapper ;
}
void enableRemoveButton(bool enabled)
{
_ui.removePushButton->setVisible(enabled);
}
Q_SIGNALS:
void textureChanged(const QString &texName);
private Q_SLOTS:
void chooseTexture();
void removeTexture();
private:
void updateTexture();
IPSWrapperTexture *_Wrapper ;
// the current texture
NLMISC::CSmartPtr<NL3D::ITexture> _Texture ;
Ui::CParticleTextureWidget _ui;
}; /* class CParticleTextureWidget */

@ -28,46 +28,47 @@
// Project includes
#include "modules.h"
namespace NLQT {
namespace NLQT
{
CParticleTreeItem::CParticleTreeItem(const QList<QVariant> &data, const int typeItem, CParticleTreeItem *parent):
_itemData(data), _itemIconType(typeItem), _parentItem(parent)
_itemData(data), _itemIconType(typeItem), _parentItem(parent)
{
}
CParticleTreeItem::CParticleTreeItem(CParticleWorkspace *ws, const QList<QVariant> &data, const int typeItem, CParticleTreeItem *parent):
_itemData(data), _itemIconType(typeItem), _parentItem(parent)
_itemData(data), _itemIconType(typeItem), _parentItem(parent)
{
nlassert(ws);
nlassert(ws);
_WS = ws;
}
CParticleTreeItem::CParticleTreeItem(NL3D::CPSLocated *loc, const QList<QVariant> &data, const int typeItem, CParticleTreeItem *parent):
_itemData(data), _itemIconType(typeItem), _parentItem(parent)
_itemData(data), _itemIconType(typeItem), _parentItem(parent)
{
nlassert(loc);
nlassert(loc);
_Loc = loc;
}
CParticleTreeItem::CParticleTreeItem(NL3D::CPSLocated *loc, uint32 index, const QList<QVariant> &data, const int typeItem, CParticleTreeItem *parent):
_itemData(data), _itemIconType(typeItem), _parentItem(parent)
_itemData(data), _itemIconType(typeItem), _parentItem(parent)
{
nlassert(loc);
_Loc = loc;
_Loc = loc;
_LocatedInstanceIndex = index;
}
CParticleTreeItem::CParticleTreeItem(CWorkspaceNode *node, const QList<QVariant> &data, const int typeItem, CParticleTreeItem *parent):
_itemData(data), _itemIconType(typeItem), _parentItem(parent)
_itemData(data), _itemIconType(typeItem), _parentItem(parent)
{
_PS = node;
}
CParticleTreeItem::CParticleTreeItem(NL3D::CPSLocatedBindable *lb, const QList<QVariant> &data, const int typeItem, CParticleTreeItem *parent):
_itemData(data), _itemIconType(typeItem), _parentItem(parent)
_itemData(data), _itemIconType(typeItem), _parentItem(parent)
{
_Bind = lb;
_Bind = lb;
}
CParticleTreeItem::~CParticleTreeItem()
@ -113,7 +114,7 @@ CParticleTreeItem *CParticleTreeItem::parent()
int CParticleTreeItem::row() const
{
if (_parentItem)
return _parentItem->_childItems.indexOf(const_cast<CParticleTreeItem*>(this));
return _parentItem->_childItems.indexOf(const_cast<CParticleTreeItem*>(this));
return 0;
}
@ -160,7 +161,7 @@ void CParticleTreeItem::setLocatedInstanceIndex(uint32 index)
}
CParticleTreeModel::CParticleTreeModel(QObject *parent)
: QAbstractItemModel(parent)
: QAbstractItemModel(parent)
{
QList<QVariant> rootData;
rootData << "Name";
@ -175,27 +176,27 @@ CParticleTreeModel::~CParticleTreeModel()
int CParticleTreeModel::columnCount(const QModelIndex &parent) const
{
if (parent.isValid())
return static_cast<CParticleTreeItem*>(parent.internalPointer())->columnCount();
return static_cast<CParticleTreeItem*>(parent.internalPointer())->columnCount();
else
return _rootItem->columnCount();
return _rootItem->columnCount();
}
QVariant CParticleTreeModel::data(const QModelIndex &index, int role) const
{
if (!index.isValid())
return QVariant();
return QVariant();
if (role == Qt::DisplayRole)
{
CParticleTreeItem *item = static_cast<CParticleTreeItem*>(index.internalPointer());
if (item->itemType() == ItemType::ParticleSystem)
{
if (item->getNode()->isModified())
if (item->getNode()->isModified())
return "*" + item->data(index.column()).toString();
}
if (item->itemType() == ItemType::Workspace)
{
if (item->getPW()->isModified())
if (item->getPW()->isModified())
return "*" + item->data(index.column()).toString();
}
return item->data(index.column());
@ -210,8 +211,8 @@ QVariant CParticleTreeModel::data(const QModelIndex &index, int role) const
}
return QFont("SansSerif", 9, QFont::Normal);
}
if (role == Qt::DecorationRole)
return qVariantFromValue(getIcon(index));
if (role == Qt::DecorationRole)
return qVariantFromValue(getIcon(index));
return QVariant();
}
@ -219,78 +220,78 @@ QVariant CParticleTreeModel::data(const QModelIndex &index, int role) const
Qt::ItemFlags CParticleTreeModel::flags(const QModelIndex &index) const
{
Qt::ItemFlags itmFlags = Qt::NoItemFlags;
if (!index.isValid())
return itmFlags;
return itmFlags;
CParticleTreeItem *item = static_cast<CParticleTreeItem*>(index.internalPointer());
switch (item->itemType())
{
case ItemType::Particle:
case ItemType::Emitter:
case ItemType::Force:
case ItemType::Light:
case ItemType::Sound:
case ItemType::Located:
case ItemType::CollisionZone:
itmFlags = Qt::ItemIsEnabled | Qt::ItemIsSelectable | Qt::ItemIsEditable;
break;
case ItemType::LocatedInstance:
if (Modules::psEdit().isRunning())
itmFlags = Qt::NoItemFlags;
else
itmFlags = Qt::ItemIsEnabled | Qt::ItemIsSelectable;
break;
default:
case ItemType::Particle:
case ItemType::Emitter:
case ItemType::Force:
case ItemType::Light:
case ItemType::Sound:
case ItemType::Located:
case ItemType::CollisionZone:
itmFlags = Qt::ItemIsEnabled | Qt::ItemIsSelectable | Qt::ItemIsEditable;
break;
case ItemType::LocatedInstance:
if (Modules::psEdit().isRunning())
itmFlags = Qt::NoItemFlags;
else
itmFlags = Qt::ItemIsEnabled | Qt::ItemIsSelectable;
break;
break;
default:
itmFlags = Qt::ItemIsEnabled | Qt::ItemIsSelectable;
break;
}
//CParticleWorkspaceDialog *pwsd = qobject_cast<CParticleWorkspaceDialog*>(QObject::parent());
//pwsd->updateTreeView();
return itmFlags;
}
QVariant CParticleTreeModel::headerData(int section, Qt::Orientation orientation,
int role) const
int role) const
{
if (orientation == Qt::Horizontal && role == Qt::DisplayRole)
return _rootItem->data(section);
return _rootItem->data(section);
return QVariant();
}
QModelIndex CParticleTreeModel::index(int row, int column, const QModelIndex &parent)
const
const
{
if (!hasIndex(row, column, parent))
return QModelIndex();
return QModelIndex();
CParticleTreeItem *parentItem;
if (!parent.isValid())
parentItem = _rootItem;
parentItem = _rootItem;
else
parentItem = static_cast<CParticleTreeItem*>(parent.internalPointer());
parentItem = static_cast<CParticleTreeItem*>(parent.internalPointer());
CParticleTreeItem *childItem = parentItem->child(row);
if (childItem)
return createIndex(row, column, childItem);
return createIndex(row, column, childItem);
else
return QModelIndex();
return QModelIndex();
}
QModelIndex CParticleTreeModel::parent(const QModelIndex &index) const
{
if (!index.isValid())
return QModelIndex();
return QModelIndex();
CParticleTreeItem *childItem = static_cast<CParticleTreeItem*>(index.internalPointer());
CParticleTreeItem *parentItem = childItem->parent();
if (parentItem == _rootItem)
return QModelIndex();
return QModelIndex();
return createIndex(parentItem->row(), 0, parentItem);
}
@ -299,28 +300,28 @@ int CParticleTreeModel::rowCount(const QModelIndex &parent) const
{
CParticleTreeItem *parentItem;
if (parent.column() > 0)
return 0;
return 0;
if (!parent.isValid())
parentItem = _rootItem;
parentItem = _rootItem;
else
parentItem = static_cast<CParticleTreeItem*>(parent.internalPointer());
parentItem = static_cast<CParticleTreeItem*>(parent.internalPointer());
return parentItem->childCount();
}
bool CParticleTreeModel::setData(const QModelIndex &index, const QVariant &value, int role)
{
if (index.isValid() && role == Qt::EditRole)
if (index.isValid() && role == Qt::EditRole)
{
CParticleTreeItem *item = static_cast<CParticleTreeItem*>(index.internalPointer());
QList<QVariant> listData;
listData << value;
item->replace(listData);
std::string name = value.toString().toStdString();
if (item->itemType() == ItemType::Located)
std::string name = value.toString().toStdString();
if (item->itemType() == ItemType::Located)
item->getLoc()->setName(name);
else
else
item->getBind()->setName(name);
Q_EMIT dataChanged(index, index);
return true;
@ -333,30 +334,30 @@ QIcon CParticleTreeModel::getIcon(const QModelIndex &index) const
CParticleTreeItem *item = static_cast<CParticleTreeItem*>(index.internalPointer());
switch (item->itemType())
{
case ItemType::Root:
break;
case ItemType::Workspace:
return QIcon(":/images/Workspace.bmp");
case ItemType::ParticleSystem:
return QIcon(":/images/ParticleSystem.bmp");
case ItemType::Particle:
return QIcon(":/images/Particle.bmp");
case ItemType::Emitter:
return QIcon(":/images/Emitter.bmp");
case ItemType::Force:
return QIcon(":/images/Force.bmp");
case ItemType::Light:
return QIcon(":/images/Light.bmp");
case ItemType::Sound:
return QIcon(":/images/Sound.bmp");
case ItemType::Located:
return QIcon(":/images/Located.bmp");
case ItemType::CollisionZone:
return QIcon(":/images/CollisionZone.bmp");
case ItemType::LocatedInstance:
return QIcon(":/images/LocatedInstance.bmp");
case ItemType::ParticleSystemNotLoaded:
return QIcon(":/images/ParticleSystemNotLoaded.bmp");
case ItemType::Root:
break;
case ItemType::Workspace:
return QIcon(":/images/Workspace.bmp");
case ItemType::ParticleSystem:
return QIcon(":/images/ParticleSystem.bmp");
case ItemType::Particle:
return QIcon(":/images/Particle.bmp");
case ItemType::Emitter:
return QIcon(":/images/Emitter.bmp");
case ItemType::Force:
return QIcon(":/images/Force.bmp");
case ItemType::Light:
return QIcon(":/images/Light.bmp");
case ItemType::Sound:
return QIcon(":/images/Sound.bmp");
case ItemType::Located:
return QIcon(":/images/Located.bmp");
case ItemType::CollisionZone:
return QIcon(":/images/CollisionZone.bmp");
case ItemType::LocatedInstance:
return QIcon(":/images/LocatedInstance.bmp");
case ItemType::ParticleSystemNotLoaded:
return QIcon(":/images/ParticleSystemNotLoaded.bmp");
}
return QIcon();
}
@ -364,11 +365,11 @@ QIcon CParticleTreeModel::getIcon(const QModelIndex &index) const
bool CParticleTreeModel::insertRows(CWorkspaceNode *node, int position, const QModelIndex &parent)
{
CParticleTreeItem *item = static_cast<CParticleTreeItem*>(parent.internalPointer());
beginInsertRows(parent, position, position);
setupModelFromPS(node, item);
setupModelFromPS(node, item);
endInsertRows();
if (node->isLoaded())
{
QModelIndex indexPS = index(item->childCount() - 1, 0, parent);
@ -384,9 +385,9 @@ bool CParticleTreeModel::insertRows(CWorkspaceNode *node, int position, const QM
bool CParticleTreeModel::insertRows(NL3D::CPSLocated *loc, int position, const QModelIndex &parent)
{
CParticleTreeItem *item = static_cast<CParticleTreeItem*>(parent.internalPointer());
beginInsertRows(parent, position, position);
createItemFromLocated(loc, item);
createItemFromLocated(loc, item);
endInsertRows();
QModelIndex indexLocated = index(item->childCount() - 1, 0, parent);
@ -402,7 +403,7 @@ bool CParticleTreeModel::insertRows(NL3D::CPSLocated *loc, int position, const Q
bool CParticleTreeModel::insertRow(NL3D::CPSLocated *loc, uint32 index, int position, const QModelIndex &parent)
{
beginInsertRows(parent, position, position);
createItemFromLocatedInstance(loc, index, static_cast<CParticleTreeItem*>(parent.internalPointer()));
createItemFromLocatedInstance(loc, index, static_cast<CParticleTreeItem*>(parent.internalPointer()));
endInsertRows();
return true;
}
@ -414,7 +415,7 @@ bool CParticleTreeModel::insertRow(NL3D::CPSLocatedBindable *lb, int position, c
endInsertRows();
return true;
}
bool CParticleTreeModel::removeRows(int position, const QModelIndex &parent)
{
CParticleTreeItem *item = static_cast<CParticleTreeItem*>(parent.internalPointer())->child(position);
@ -422,31 +423,31 @@ bool CParticleTreeModel::removeRows(int position, const QModelIndex &parent)
removeRows(0, parent.child(position, 0));
beginRemoveRows(parent, position, position);
static_cast<CParticleTreeItem*>(parent.internalPointer())->deleteChild(position);
static_cast<CParticleTreeItem*>(parent.internalPointer())->deleteChild(position);
endRemoveRows();
return false;
}
CWorkspaceNode *CParticleTreeModel::getOwnerNode(CParticleTreeItem *item) const
{
CWorkspaceNode *node = NULL;
switch (item->itemType())
{
case ItemType::ParticleSystem:
node = item->getNode();
break;
case ItemType::Located:
node = item->parent()->getNode();
break;
case ItemType::LocatedInstance:
case ItemType::Particle:
case ItemType::Emitter:
case ItemType::Force:
case ItemType::Light:
case ItemType::Sound:
case ItemType::CollisionZone:
node = item->parent()->parent()->getNode();
break;
case ItemType::ParticleSystem:
node = item->getNode();
break;
case ItemType::Located:
node = item->parent()->getNode();
break;
case ItemType::LocatedInstance:
case ItemType::Particle:
case ItemType::Emitter:
case ItemType::Force:
case ItemType::Light:
case ItemType::Sound:
case ItemType::CollisionZone:
node = item->parent()->parent()->getNode();
break;
}
return node;
}
@ -477,17 +478,17 @@ void CParticleTreeModel::setupModelFromWorkSpace()
QList<QVariant> workspaceData;
CParticleWorkspace *workspace = Modules::psEdit().getParticleWorkspace();
if (workspace == NULL)
if (workspace == NULL)
{
endResetModel();
return;
}
}
workspaceData << workspace->getFilename().c_str();
CParticleTreeItem *parent = new CParticleTreeItem(workspace ,workspaceData, ItemType::Workspace, _rootItem);
_rootItem->appendChild(parent);
endResetModel();
QModelIndex rootIndex = index(0, 0);
uint numNode = workspace->getNumNode();
for (uint i = 0; i < numNode; i++)
@ -504,7 +505,7 @@ void CParticleTreeModel::setupModelFromPS(CWorkspaceNode *node, CParticleTreeIte
child = new CParticleTreeItem(node, particleSystemData, ItemType::ParticleSystem, parent);
parent->appendChild(child);
}
else
else
{
child = new CParticleTreeItem(node, particleSystemData, ItemType::ParticleSystemNotLoaded, parent);
parent->appendChild(child);

@ -34,8 +34,9 @@
// Projects includes
#include "particle_node.h"
namespace NLQT {
namespace NLQT
{
struct ItemType
{
enum List
@ -64,15 +65,15 @@ class CParticleTreeItem
{
public:
CParticleTreeItem(const QList<QVariant> &data, const int typeItem, CParticleTreeItem *parent = 0);
CParticleTreeItem(CParticleWorkspace *ws, const QList<QVariant> &data, const int typeItem, CParticleTreeItem *parent );
CParticleTreeItem(NL3D::CPSLocated *loc, const QList<QVariant> &data, const int typeItem, CParticleTreeItem *parent);
CParticleTreeItem(NL3D::CPSLocated *loc, uint32 index, const QList<QVariant> &data, const int typeItem, CParticleTreeItem *parent);
CParticleTreeItem(CWorkspaceNode *node, const QList<QVariant> &data, const int typeItem, CParticleTreeItem *parent);
CParticleTreeItem(NL3D::CPSLocatedBindable *lb, const QList<QVariant> &data, const int typeItem, CParticleTreeItem *parent);
~CParticleTreeItem();
@ -94,7 +95,7 @@ public:
CWorkspaceNode *getNode() const;
uint32 getLocatedInstanceIndex() const;
void setLocatedInstanceIndex(uint32 index);
private:
union
{
@ -103,16 +104,16 @@ private:
NL3D::CPSLocatedBindable *_Bind;
CWorkspaceNode *_PS;
};
// for the located instance type, this is the index of the instance
uint32 _LocatedInstanceIndex;
QList<CParticleTreeItem*> _childItems;
QList<QVariant> _itemData;
int _itemIconType;
CParticleTreeItem *_parentItem;
};
/**
@class CParticleTreeModel
@brief Tree model particles workspace.
@ -128,9 +129,9 @@ public:
QVariant data(const QModelIndex &index, int role) const;
Qt::ItemFlags flags(const QModelIndex &index) const;
QVariant headerData(int section, Qt::Orientation orientation,
int role = Qt::DisplayRole) const;
int role = Qt::DisplayRole) const;
QModelIndex index(int row, int column,
const QModelIndex &parent = QModelIndex()) const;
const QModelIndex &parent = QModelIndex()) const;
QModelIndex parent(const QModelIndex &index) const;
int rowCount(const QModelIndex &parent = QModelIndex()) const;
int columnCount(const QModelIndex &parent = QModelIndex()) const;
@ -141,41 +142,41 @@ public:
/// Insert WorkspaceNode in model and add all its sub-item.
bool insertRows(CWorkspaceNode *node, int position, const QModelIndex &parent = QModelIndex());
/// Insert Located item in model and add all its sub-item.
bool insertRows(NL3D::CPSLocated *loc, int position, const QModelIndex &parent = QModelIndex());
/// Insert Located item in model.
bool insertRow(NL3D::CPSLocated *loc, uint32 index, int position, const QModelIndex &parent = QModelIndex());
/// Insert LocatedBindable item in model.
bool insertRow(NL3D::CPSLocatedBindable *lb, int position, const QModelIndex &parent = QModelIndex());
/// Deletes a tree item and all its children.
bool removeRows(int position, const QModelIndex &parent = QModelIndex());
/// Get the parent node in the workspace for the given element in the tree
CWorkspaceNode *getOwnerNode(CParticleTreeItem *item) const;
/// Rebuild the located instance in the tree (after loading for example)
void rebuildLocatedInstance(const QModelIndex &parent);
/// Build the whole tree from a workspace
void setupModelFromWorkSpace();
private:
/// Build a portion of the tree using the given particle system
void setupModelFromPS(CWorkspaceNode *node, CParticleTreeItem *parent);
/// Add item from the given located
void createItemFromLocated(NL3D::CPSLocated *loc, CParticleTreeItem *parent);
/// Add item from the given located instance
void createItemFromLocatedInstance(NL3D::CPSLocated *loc, uint32 index, CParticleTreeItem *parent);
/// Add item from the given located bindable
void createItemFromLocatedBindable(NL3D::CPSLocatedBindable *lb, CParticleTreeItem *parent);
CParticleTreeItem *_rootItem;
};

@ -42,9 +42,11 @@
#include "dup_ps.h"
#include "modules.h"
namespace NLQT {
namespace NLQT
{
static const char * const LocatedBindable[] = {
static const char * const LocatedBindable[] =
{
QT_TR_NOOP("Point"),
QT_TR_NOOP("LookAt"),
QT_TR_NOOP("FanLight"),
@ -121,13 +123,13 @@ struct Action
static std::map<std::string, uint> _PSElementIdentifiers;
CParticleWorkspaceDialog::CParticleWorkspaceDialog(QWidget *parent)
: QDockWidget(parent), _currentItem(NULL)
: QDockWidget(parent), _currentItem(NULL)
{
_ui.setupUi(this);
connect(_ui.treeView, SIGNAL(clicked(QModelIndex)), this, SLOT(clickedItem(QModelIndex)));
connect(_ui.treeView, SIGNAL(customContextMenuRequested(QPoint)), this, SLOT(customContextMenu()));
// Init tree model
_treeModel = new CParticleTreeModel(this);
_ui.treeView->setModel(_treeModel);
@ -136,14 +138,14 @@ CParticleWorkspaceDialog::CParticleWorkspaceDialog(QWidget *parent)
_PropertyDialog = new CPropertyDialog(_treeModel, this);
_signalMapper = new QSignalMapper(this);
_setActivePSAction = new QAction(tr("Set as active particle system"), this);
_savePSAction = new QAction(tr("Save"), this);
_saveAsPSAction = new QAction(tr("Save as"), this);
_clearContentAction = new QAction(tr("Clear content"), this);
_removeFromWSAction = new QAction(tr("Remove from workspace"), this);
_mergeAction = new QAction(tr("Merge"), this);
_newLocatedAction = new QAction(tr("New located"), this);
_pasteLocatedAction = new QAction(tr("Paste located"), this);
@ -151,13 +153,13 @@ CParticleWorkspaceDialog::CParticleWorkspaceDialog(QWidget *parent)
_bindNewLocatedBindable[i] = new QAction(tr(LocatedBindable[i]), this);
_forceZBiasAction = new QAction(tr("Force ZBias"), this);
_instanciateAction = new QAction(tr("Instanciate"), this);
_copyLocatedAction = new QAction(tr("Copy located"), this);
_copyBindableAction = new QAction(tr("Copy bindable"), this);
_pasteBindableAction = new QAction(tr("Paste bindable"), this);
_deleteAction = new QAction(tr("Delete"), this);
_allLODAction = new QAction(tr("All LOD"), this);
_allLODAction->setCheckable(true);
_lod1Action = new QAction(tr("LOD 1"), this);
@ -165,7 +167,7 @@ CParticleWorkspaceDialog::CParticleWorkspaceDialog(QWidget *parent)
_lod2Action = new QAction(tr("LOD 2"), this);
_lod2Action->setCheckable(true);
_externIDAction = new QAction(tr("extern ID"), this);
connect(_setActivePSAction, SIGNAL(triggered()), this, SLOT(setActiveNode()));
connect(_savePSAction, SIGNAL(triggered()), this, SLOT(savePS()));
connect(_saveAsPSAction, SIGNAL(triggered()), this, SLOT(saveAsPS()));
@ -183,7 +185,7 @@ CParticleWorkspaceDialog::CParticleWorkspaceDialog(QWidget *parent)
}
connect(_forceZBiasAction, SIGNAL(triggered()), this, SLOT(forceZBias()));
connect(_copyLocatedAction, SIGNAL(triggered()), this, SLOT(copyLocated()));
connect(_copyBindableAction, SIGNAL(triggered()), this, SLOT(copyBindable()));
connect(_pasteBindableAction, SIGNAL(triggered()), this, SLOT(pasteBindable()));
@ -215,14 +217,14 @@ void CParticleWorkspaceDialog::clickedItem(const QModelIndex & index)
{
if (_currentItem != NULL)
_treeModel->getOwnerNode(_currentItem)->getPSPointer()->setCurrentEditedElement(NULL);
_currentItem = static_cast<CParticleTreeItem*>(index.internalPointer());
if (index.flags() != Qt::NoItemFlags)
_PropertyDialog->setCurrentEditedElement(_currentItem);
if ((_currentItem->itemType() == ItemType::Workspace) ||
(_currentItem->itemType() == ItemType::ParticleSystemNotLoaded))
(_currentItem->itemType() == ItemType::ParticleSystemNotLoaded))
_currentItem = NULL;
}
@ -234,56 +236,56 @@ void CParticleWorkspaceDialog::customContextMenu()
QMenu *popurMenu = new QMenu(this);
switch (_currentItem->itemType())
{
case ItemType::ParticleSystem:
popurMenu->addAction(_setActivePSAction);
popurMenu->addAction(_savePSAction);
popurMenu->addAction(_saveAsPSAction);
popurMenu->addAction(_clearContentAction);
popurMenu->addAction(_removeFromWSAction);
popurMenu->addAction(_mergeAction);
popurMenu->addSeparator();
popurMenu->addAction(_newLocatedAction);
popurMenu->addAction(_pasteLocatedAction);
popurMenu->addSeparator();
buildMenu(popurMenu);
popurMenu->addSeparator();
popurMenu->addAction(_forceZBiasAction);
break;
case ItemType::Located:
popurMenu->addAction(_instanciateAction);
popurMenu->addSeparator();
buildMenu(popurMenu);
popurMenu->addSeparator();
popurMenu->addAction(_copyLocatedAction);
popurMenu->addAction(_pasteBindableAction);
popurMenu->addAction(_deleteAction);
break;
case ItemType::Force:
case ItemType::Particle:
case ItemType::Emitter:
case ItemType::Light:
case ItemType::CollisionZone:
case ItemType::Sound:
popurMenu->addAction(_copyBindableAction);
popurMenu->addAction(_deleteAction);
popurMenu->addSeparator();
popurMenu->addAction(_allLODAction);
popurMenu->addAction(_lod1Action);
popurMenu->addAction(_lod2Action);
popurMenu->addSeparator();
popurMenu->addAction(_externIDAction);
// check the menu to tell which lod is used for this located bindable
if (_currentItem->getBind()->getLOD() == NL3D::PSLod1n2) _allLODAction->setChecked(true);
else _allLODAction->setChecked(false);
if (_currentItem->getBind()->getLOD() == NL3D::PSLod1) _lod1Action->setChecked(true);
else _lod1Action->setChecked(false);
if (_currentItem->getBind()->getLOD() == NL3D::PSLod2) _lod2Action->setChecked(true);
else _lod2Action->setChecked(false);
break;
case ItemType::LocatedInstance:
popurMenu->addAction(_deleteAction);
break;
case ItemType::ParticleSystem:
popurMenu->addAction(_setActivePSAction);
popurMenu->addAction(_savePSAction);
popurMenu->addAction(_saveAsPSAction);
popurMenu->addAction(_clearContentAction);
popurMenu->addAction(_removeFromWSAction);
popurMenu->addAction(_mergeAction);
popurMenu->addSeparator();
popurMenu->addAction(_newLocatedAction);
popurMenu->addAction(_pasteLocatedAction);
popurMenu->addSeparator();
buildMenu(popurMenu);
popurMenu->addSeparator();
popurMenu->addAction(_forceZBiasAction);
break;
case ItemType::Located:
popurMenu->addAction(_instanciateAction);
popurMenu->addSeparator();
buildMenu(popurMenu);
popurMenu->addSeparator();
popurMenu->addAction(_copyLocatedAction);
popurMenu->addAction(_pasteBindableAction);
popurMenu->addAction(_deleteAction);
break;
case ItemType::Force:
case ItemType::Particle:
case ItemType::Emitter:
case ItemType::Light:
case ItemType::CollisionZone:
case ItemType::Sound:
popurMenu->addAction(_copyBindableAction);
popurMenu->addAction(_deleteAction);
popurMenu->addSeparator();
popurMenu->addAction(_allLODAction);
popurMenu->addAction(_lod1Action);
popurMenu->addAction(_lod2Action);
popurMenu->addSeparator();
popurMenu->addAction(_externIDAction);
// check the menu to tell which lod is used for this located bindable
if (_currentItem->getBind()->getLOD() == NL3D::PSLod1n2) _allLODAction->setChecked(true);
else _allLODAction->setChecked(false);
if (_currentItem->getBind()->getLOD() == NL3D::PSLod1) _lod1Action->setChecked(true);
else _lod1Action->setChecked(false);
if (_currentItem->getBind()->getLOD() == NL3D::PSLod2) _lod2Action->setChecked(true);
else _lod2Action->setChecked(false);
break;
case ItemType::LocatedInstance:
popurMenu->addAction(_deleteAction);
break;
}
bool stopped = Modules::psEdit().getState() == CParticleEditor::State::Stopped ? true : false;
@ -319,21 +321,21 @@ void CParticleWorkspaceDialog::saveAsPS()
//if (nt->PS->getResetAutoCountFlag() && nt->PS->getPSPointer()->getAutoCountFlag())
if (node->getPSPointer()->getAutoCountFlag())
{
QMessageBox::critical(this, tr("NeL particle system editor"),
QString(node->getFilename().c_str()) + tr(" uses auto count feature, and it has been modified. "
"You should run the system entirely at least once at full detail before saving so that the editor can compute the number of particles in the system. "
"If user params are used to modify system aspect, you should run the system for extreme cases before saving. "),
QMessageBox::Ok);
QMessageBox::critical(this, tr("NeL particle system editor"),
QString(node->getFilename().c_str()) + tr(" uses auto count feature, and it has been modified. "
"You should run the system entirely at least once at full detail before saving so that the editor can compute the number of particles in the system. "
"If user params are used to modify system aspect, you should run the system for extreme cases before saving. "),
QMessageBox::Ok);
}
else
{
Modules::psEdit().stop();
QString fileName = QFileDialog::getSaveFileName(this, tr("Save as ps file"),
".",
tr("ps files (*.ps)"));
// after check
if (!fileName.isEmpty())
".",
tr("ps files (*.ps)"));
// after check
if (!fileName.isEmpty())
node->savePSAs(fileName.toStdString());
}
}
@ -341,8 +343,8 @@ void CParticleWorkspaceDialog::saveAsPS()
void CParticleWorkspaceDialog::clearContent()
{
int ret = QMessageBox::question(this, tr("NeL particle system editor"),
tr("Clear content ?"), QMessageBox::Yes | QMessageBox::No);
tr("Clear content ?"), QMessageBox::Yes | QMessageBox::No);
if (ret == QMessageBox::Yes)
{
CWorkspaceNode *node = _treeModel->getOwnerNode(_currentItem);
@ -383,7 +385,7 @@ void CParticleWorkspaceDialog::pasteLocated()
_treeModel->getOwnerNode(_currentItem)->setModified(true);
Modules::psEdit().resetAutoCount(_treeModel->getOwnerNode(_currentItem));
NL3D::CPSLocated *copy = dynamic_cast<NL3D::CPSLocated *>(::DupPSLocated(_LocatedCopy.get()));
if (!copy) return;
if (_currentItem->getNode()->getPSPointer()->attach(copy))
@ -391,10 +393,10 @@ void CParticleWorkspaceDialog::pasteLocated()
else
{
delete copy;
QMessageBox::critical(this, tr("NeL particle system editor"),
tr("Can't perform operation : the system is flagged with 'No max nb steps' or uses the preset 'Spell FX', "
"and thus, should have a finite duration. Please remove that flag first."),
QMessageBox::Ok);
QMessageBox::critical(this, tr("NeL particle system editor"),
tr("Can't perform operation : the system is flagged with 'No max nb steps' or uses the preset 'Spell FX', "
"and thus, should have a finite duration. Please remove that flag first."),
QMessageBox::Ok);
}
}
@ -403,101 +405,101 @@ void CParticleWorkspaceDialog::bindNewLocatedBindable(int id)
NL3D::CPSLocatedBindable *toCreate = NULL;
switch (id)
{
case Action::ParticlePoint:
toCreate = new NL3D::CPSDot;
break;
case Action::ParticleLookAt:
toCreate = new NL3D::CPSFaceLookAt;
break;
case Action::ParticleFanLight:
toCreate = new NL3D::CPSFanLight;
break;
case Action::ParticleRibbon:
toCreate = new NL3D::CPSRibbon;
break;
case Action::ParticleTailDot:
toCreate = new NL3D::CPSTailDot;
break;
case Action::ParticleMesh:
toCreate = new NL3D::CPSMesh;
break;
case Action::ParticleConstraintMesh:
toCreate = new NL3D::CPSConstraintMesh;
break;
case Action::ParticleFace:
toCreate = new NL3D::CPSFace;
break;
case Action::ParticleShockWave:
toCreate = new NL3D::CPSShockWave;
break;
case Action::ParticleRibbonLookAt:
toCreate = new NL3D::CPSRibbonLookAt;
break;
case Action::ForceGravity:
toCreate = new NL3D::CPSGravity;
break;
case Action::ForceDirectional:
toCreate = new NL3D::CPSDirectionnalForce;
break;
case Action::ForceSpring:
toCreate = new NL3D::CPSSpring;
break;
case Action::ForceFlyidFriction:
toCreate = new NL3D::CPSFluidFriction;
break;
case Action::ForceCentralGravity:
toCreate = new NL3D::CPSCentralGravity;
break;
case Action::ForceCylindricVortex:
toCreate = new NL3D::CPSCylindricVortex;
break;
case Action::ForceBrownianMove:
toCreate = new NL3D::CPSBrownianForce;
break;
case Action::ForceMagnetic:
toCreate = new NL3D::CPSMagneticForce;
break;
case Action::ZonePlane:
toCreate = new NL3D::CPSZonePlane;
break;
case Action::ZoneSphere:
toCreate = new NL3D::CPSZoneSphere;
break;
case Action::ZoneRectangle:
toCreate = new NL3D::CPSZoneRectangle;
break;
case Action::ZoneDisc:
toCreate = new NL3D::CPSZoneDisc;
break;
case Action::ZoneCylinder:
toCreate = new NL3D::CPSZoneCylinder;
break;
case Action::EmitterDirectional:
toCreate = new NL3D::CPSEmitterDirectionnal;
break;
case Action::EmitterOmniDirectional:
toCreate = new NL3D::CPSEmitterOmni;
break;
case Action::EmitterRectangle:
toCreate = new NL3D::CPSEmitterRectangle;
break;
case Action::EmitterConic:
toCreate = new NL3D::CPSEmitterConic;
break;
case Action::EmitterSpherical:
toCreate = new NL3D::CPSSphericalEmitter;
break;
case Action::EmitterRadial:
toCreate = new NL3D::CPSRadialEmitter;
break;
case Action::Sound:
toCreate = new NL3D::CPSSound;
if (!Modules::psEdit().isRunning())
(static_cast<NL3D::CPSSound *>(toCreate))->stopSound();
break;
case Action::Light:
toCreate = new NL3D::CPSLight;
break;
case Action::ParticlePoint:
toCreate = new NL3D::CPSDot;
break;
case Action::ParticleLookAt:
toCreate = new NL3D::CPSFaceLookAt;
break;
case Action::ParticleFanLight:
toCreate = new NL3D::CPSFanLight;
break;
case Action::ParticleRibbon:
toCreate = new NL3D::CPSRibbon;
break;
case Action::ParticleTailDot:
toCreate = new NL3D::CPSTailDot;
break;
case Action::ParticleMesh:
toCreate = new NL3D::CPSMesh;
break;
case Action::ParticleConstraintMesh:
toCreate = new NL3D::CPSConstraintMesh;
break;
case Action::ParticleFace:
toCreate = new NL3D::CPSFace;
break;
case Action::ParticleShockWave:
toCreate = new NL3D::CPSShockWave;
break;
case Action::ParticleRibbonLookAt:
toCreate = new NL3D::CPSRibbonLookAt;
break;
case Action::ForceGravity:
toCreate = new NL3D::CPSGravity;
break;
case Action::ForceDirectional:
toCreate = new NL3D::CPSDirectionnalForce;
break;
case Action::ForceSpring:
toCreate = new NL3D::CPSSpring;
break;
case Action::ForceFlyidFriction:
toCreate = new NL3D::CPSFluidFriction;
break;
case Action::ForceCentralGravity:
toCreate = new NL3D::CPSCentralGravity;
break;
case Action::ForceCylindricVortex:
toCreate = new NL3D::CPSCylindricVortex;
break;
case Action::ForceBrownianMove:
toCreate = new NL3D::CPSBrownianForce;
break;
case Action::ForceMagnetic:
toCreate = new NL3D::CPSMagneticForce;
break;
case Action::ZonePlane:
toCreate = new NL3D::CPSZonePlane;
break;
case Action::ZoneSphere:
toCreate = new NL3D::CPSZoneSphere;
break;
case Action::ZoneRectangle:
toCreate = new NL3D::CPSZoneRectangle;
break;
case Action::ZoneDisc:
toCreate = new NL3D::CPSZoneDisc;
break;
case Action::ZoneCylinder:
toCreate = new NL3D::CPSZoneCylinder;
break;
case Action::EmitterDirectional:
toCreate = new NL3D::CPSEmitterDirectionnal;
break;
case Action::EmitterOmniDirectional:
toCreate = new NL3D::CPSEmitterOmni;
break;
case Action::EmitterRectangle:
toCreate = new NL3D::CPSEmitterRectangle;
break;
case Action::EmitterConic:
toCreate = new NL3D::CPSEmitterConic;
break;
case Action::EmitterSpherical:
toCreate = new NL3D::CPSSphericalEmitter;
break;
case Action::EmitterRadial:
toCreate = new NL3D::CPSRadialEmitter;
break;
case Action::Sound:
toCreate = new NL3D::CPSSound;
if (!Modules::psEdit().isRunning())
(static_cast<NL3D::CPSSound *>(toCreate))->stopSound();
break;
case Action::Light:
toCreate = new NL3D::CPSLight;
break;
}
_treeModel->getOwnerNode(_currentItem)->setModified(true);
@ -510,7 +512,7 @@ void CParticleWorkspaceDialog::bindNewLocatedBindable(int id)
if (_treeModel->getOwnerNode(_currentItem)->getPSPointer()->getBypassMaxNumIntegrationSteps())
{
if (toCreate->getType() == NL3D::PSParticle || toCreate->getType() == NL3D::PSEmitter)
loc->setInitialLife(1.f);
loc->setInitialLife(1.f);
// object must have finite duration with that flag
}
}
@ -519,10 +521,10 @@ void CParticleWorkspaceDialog::bindNewLocatedBindable(int id)
if (!loc->bind(toCreate))
{
QMessageBox::critical(this, tr("NeL particle system editor"),
tr("The system is flagged with 'No max Nb steps', or uses the preset 'Spell FX'."
"System must have finite duration. Can't add object. To solve this, set a limited life time for the father."),
QMessageBox::Ok);
QMessageBox::critical(this, tr("NeL particle system editor"),
tr("The system is flagged with 'No max Nb steps', or uses the preset 'Spell FX'."
"System must have finite duration. Can't add object. To solve this, set a limited life time for the father."),
QMessageBox::Ok);
delete toCreate;
return;
}
@ -535,7 +537,7 @@ void CParticleWorkspaceDialog::bindNewLocatedBindable(int id)
toCreate->setName(name);
}
else
{
{
_PSElementIdentifiers[toCreate->getName()] = 0;
toCreate->setName(name + "0");
}
@ -543,7 +545,7 @@ void CParticleWorkspaceDialog::bindNewLocatedBindable(int id)
touchPSState(_currentItem);
Modules::psEdit().resetAutoCount(_treeModel->getOwnerNode(_currentItem));
// update treeView
if (_currentItem->itemType() == ItemType::ParticleSystem)
{
@ -592,10 +594,10 @@ void CParticleWorkspaceDialog::pasteBindable()
else
{
delete copy;
QMessageBox::critical(this, tr("NeL particle system editor"),
tr("Can't perform operation : the system is flagged with 'No max nb steps' or uses the preset 'Spell FX', "
"and thus, should have a finite duration. Please remove that flag first."),
QMessageBox::Ok);
QMessageBox::critical(this, tr("NeL particle system editor"),
tr("Can't perform operation : the system is flagged with 'No max nb steps' or uses the preset 'Spell FX', "
"and thus, should have a finite duration. Please remove that flag first."),
QMessageBox::Ok);
}
}
@ -610,50 +612,50 @@ void CParticleWorkspaceDialog::deleteItem()
clickedItem(index.parent());
switch(item->itemType())
{
case ItemType::Located:
{
NL3D::CPSLocated *loc = item->getLoc();
touchPSState(item);
ownerNode->setModified(true);
// if the system is running, we must destroy initial infos about the located,
// as they won't need to be restored when the stop button will be pressed
ownerNode->removeLocated(loc);
Modules::psEdit().resetAutoCount(ownerNode);
ownerNode->getPSPointer()->remove(loc);
_treeModel->removeRows(index.row(), index.parent());
}
break;
case ItemType::LocatedInstance:
{
Modules::psEdit().resetAutoCount(ownerNode);
NL3D::CPSEmitter::setBypassEmitOnDeath(true);
item->getLoc()->deleteElement(item->getLocatedInstanceIndex());
NL3D::CPSEmitter::setBypassEmitOnDeath(false);
_treeModel->removeRows(index.row(), index.parent());
_treeModel->rebuildLocatedInstance(_ui.treeView->currentIndex());
}
break;
case ItemType::Particle:
case ItemType::Emitter:
case ItemType::Force:
case ItemType::Light:
case ItemType::Sound:
case ItemType::CollisionZone:
{
NL3D::CPSLocatedBindable *lb = item->getBind();
touchPSState(item);
// if the system is running, we must destroy initial infos
// that what saved about the located bindable, when the start button was pressed, as they won't need
// to be restored
ownerNode->removeLocatedBindable(lb);
ownerNode->setModified(true);
Modules::psEdit().resetAutoCount(ownerNode);
lb->getOwner()->remove(lb);
_treeModel->removeRows(index.row(), index.parent());
}
break;
case ItemType::Located:
{
NL3D::CPSLocated *loc = item->getLoc();
touchPSState(item);
ownerNode->setModified(true);
// if the system is running, we must destroy initial infos about the located,
// as they won't need to be restored when the stop button will be pressed
ownerNode->removeLocated(loc);
Modules::psEdit().resetAutoCount(ownerNode);
ownerNode->getPSPointer()->remove(loc);
_treeModel->removeRows(index.row(), index.parent());
}
break;
case ItemType::LocatedInstance:
{
Modules::psEdit().resetAutoCount(ownerNode);
NL3D::CPSEmitter::setBypassEmitOnDeath(true);
item->getLoc()->deleteElement(item->getLocatedInstanceIndex());
NL3D::CPSEmitter::setBypassEmitOnDeath(false);
_treeModel->removeRows(index.row(), index.parent());
_treeModel->rebuildLocatedInstance(_ui.treeView->currentIndex());
}
break;
case ItemType::Particle:
case ItemType::Emitter:
case ItemType::Force:
case ItemType::Light:
case ItemType::Sound:
case ItemType::CollisionZone:
{
NL3D::CPSLocatedBindable *lb = item->getBind();
touchPSState(item);
// if the system is running, we must destroy initial infos
// that what saved about the located bindable, when the start button was pressed, as they won't need
// to be restored
ownerNode->removeLocatedBindable(lb);
ownerNode->setModified(true);
Modules::psEdit().resetAutoCount(ownerNode);
lb->getOwner()->remove(lb);
_treeModel->removeRows(index.row(), index.parent());
}
break;
}
}
@ -662,12 +664,12 @@ void CParticleWorkspaceDialog::setInstanciate()
_treeModel->getOwnerNode(_currentItem)->setModified(true);
Modules::psEdit().resetAutoCount(_treeModel->getOwnerNode(_currentItem));
if (_currentItem->getLoc()->getSize() == _currentItem->getLoc()->getMaxSize())
_currentItem->getLoc()->resize(_currentItem->getLoc()->getMaxSize() + 1);
sint32 objIndex = _currentItem->getLoc()->newElement(NLMISC::CVector::Null, NLMISC::CVector::Null,
NULL, 0, _currentItem->getLoc()->getMatrixMode(), 0.f);
sint32 objIndex = _currentItem->getLoc()->newElement(NLMISC::CVector::Null, NLMISC::CVector::Null,
NULL, 0, _currentItem->getLoc()->getMatrixMode(), 0.f);
_treeModel->insertRow(_currentItem->getLoc(), objIndex, _currentItem->childCount(), _ui.treeView->currentIndex());
}
@ -694,8 +696,8 @@ void CParticleWorkspaceDialog::setExternID()
{
bool ok;
int i = QInputDialog::getInt(this, tr("Set the extern ID"),
tr("0 means no extern access."),
_currentItem->getBind()->getExternID(), 0, 9999, 1, &ok);
tr("0 means no extern access."),
_currentItem->getBind()->getExternID(), 0, 9999, 1, &ok);
if (ok)
{
_currentItem->getBind()->setExternID(uint32(i));
@ -727,7 +729,7 @@ void CParticleWorkspaceDialog::buildMenu(QMenu *menu)
menu->addAction(bindParticleMenu->menuAction());
for(int i = Action::ParticlePoint; i <= Action::ParticleRibbonLookAt; ++i)
bindParticleMenu->addAction(_bindNewLocatedBindable[i]);
QMenu *bindForceMenu = new QMenu(tr("Bind force..."), menu);
menu->addAction(bindForceMenu->menuAction());
for(int i = Action::ForceGravity; i <= Action::ForceMagnetic; ++i)
@ -750,7 +752,7 @@ void CParticleWorkspaceDialog::buildMenu(QMenu *menu)
NL3D::CPSLocated *CParticleWorkspaceDialog::createLocated(NL3D::CParticleSystem *ps)
{
// build new name
std::string name;
std::string name;
if (_PSElementIdentifiers.count(std::string("located")))
name = (QString("located %1").arg(++_PSElementIdentifiers[std::string("located")])).toStdString();

@ -34,7 +34,8 @@
#include "particle_tree_model.h"
#include "particle_node.h"
namespace NLQT {
namespace NLQT
{
/**
@class ParticleWorkspaceDialog
@ -46,18 +47,21 @@ class CParticleWorkspaceDialog: public QDockWidget
public:
CParticleWorkspaceDialog(QWidget *parent = 0);
~CParticleWorkspaceDialog();
void touchPSState(CParticleTreeItem *item);
CPropertyDialog *getPropertyDialog() const { return _PropertyDialog; }
CPropertyDialog *getPropertyDialog() const
{
return _PropertyDialog;
}
Q_SIGNALS:
/// Emits change active particle system node.
void changeActiveNode();
private Q_SLOTS:
void clickedItem(const QModelIndex & index);
void customContextMenu();
void setActiveNode();
void savePS();
void saveAsPS();
@ -71,32 +75,32 @@ private Q_SLOTS:
void bindNewLocatedBindable(int id);
void forceZBias();
void copyLocated();
void copyBindable();
void pasteBindable();
void deleteItem();
void setInstanciate();
void setAllLOD();
void setLOD1();
void setLOD2();
void setExternID();
void setNewState();
void updateTreeView();
private:
void buildMenu(QMenu *menu);
NL3D::CPSLocated *createLocated(NL3D::CParticleSystem *ps);
CPropertyDialog *_PropertyDialog;
CParticleTreeModel *_treeModel;
QSignalMapper *_signalMapper;
QAction *_setActivePSAction;
QAction *_savePSAction;
QAction *_saveAsPSAction;
@ -107,23 +111,23 @@ private:
QAction *_pasteLocatedAction;
QAction *_bindNewLocatedBindable[32];
QAction *_forceZBiasAction;
QAction *_instanciateAction;
QAction *_copyLocatedAction;
QAction *_copyBindableAction;
QAction *_pasteBindableAction;
QAction *_deleteAction;
QAction *_allLODAction;
QAction *_lod1Action;
QAction *_lod2Action;
QAction *_externIDAction;
std::auto_ptr<NL3D::CPSLocated> _LocatedCopy;
std::auto_ptr<NL3D::CPSLocatedBindable> _LocatedBindableCopy;
CParticleTreeItem *_currentItem;
Ui::CParticleWorkspaceDialog _ui;
friend class CMainWindow;
}; /* class CParticleWorkspaceDialog */

@ -24,19 +24,20 @@
#include <QtGui/QWidget>
#include <QtGui/QFileDialog>
#include <QtGui/QMessageBox>
// NeL includes
// Project includes
#include "modules.h"
namespace NLQT {
namespace NLQT
{
CWorkspacePage::CWorkspacePage(CParticleTreeModel *treeModel, QWidget *parent)
: QWidget(parent)
: QWidget(parent)
{
_ui.setupUi(this);
_treeModel = treeModel;
connect(_ui.newToolButton, SIGNAL(clicked()), this, SLOT(newWP()));
@ -57,9 +58,9 @@ void CWorkspacePage::newWP()
//checkModifiedWorkSpace();
// ask name of the new workspace to create
QString fileName = QFileDialog::getSaveFileName(this, tr("Create new pws file"),
".",
tr("pws files (*.pws)"));
if (!fileName.isEmpty())
".",
tr("pws files (*.pws)"));
if (!fileName.isEmpty())
{
Modules::psEdit().createNewWorkspace(fileName.toStdString());
_treeModel->setupModelFromWorkSpace();
@ -75,11 +76,11 @@ void CWorkspacePage::loadWP()
{
//checkModifiedWorkSpace();
QString fileName = QFileDialog::getOpenFileName(this,
tr("Open NeL data file"), ".",
tr("Particle Workspace file (*.pws);;"));
tr("Open NeL data file"), ".",
tr("Particle Workspace file (*.pws);;"));
setCursor(Qt::WaitCursor);
if (!fileName.isEmpty())
if (!fileName.isEmpty())
{
Modules::psEdit().loadWorkspace(fileName.toStdString());
_treeModel->setupModelFromWorkSpace();
@ -102,9 +103,9 @@ void CWorkspacePage::saveWP()
void CWorkspacePage::saveAsWP()
{
QString fileName = QFileDialog::getSaveFileName(this, tr("Save as pws file"),
".",
tr("pws files (*.pws)"));
if (!fileName.isEmpty())
".",
tr("pws files (*.pws)"));
if (!fileName.isEmpty())
{
Modules::psEdit().getParticleWorkspace()->setFileName(fileName.toStdString());
Modules::psEdit().saveWorkspaceStructure();
@ -116,10 +117,10 @@ void CWorkspacePage::saveAsWP()
void CWorkspacePage::insertPS()
{
QString fileName = QFileDialog::getOpenFileName(this,
tr("Open NeL data file"), ".",
tr("Particle System file (*.ps);;"));
tr("Open NeL data file"), ".",
tr("Particle System file (*.ps);;"));
if (!fileName.isEmpty())
if (!fileName.isEmpty())
{
// TODO: create method particle editor insertNewPS and multiple add
CWorkspaceNode *node = Modules::psEdit().getParticleWorkspace()->addNode(NLMISC::CFile::getFilename(fileName.toStdString()));
@ -131,11 +132,11 @@ void CWorkspacePage::insertPS()
}
catch(NLMISC::EStream &e)
{
QMessageBox::critical(this, tr("NeL particle system editor"),
QString(e.what()),
QMessageBox::Ok);
QMessageBox::critical(this, tr("NeL particle system editor"),
QString(e.what()),
QMessageBox::Ok);
}
if (!node->isLoaded())
if (!node->isLoaded())
Modules::psEdit().getParticleWorkspace()->removeNode(Modules::psEdit().getParticleWorkspace()->getNumNode() - 1);
else
{
@ -149,17 +150,17 @@ void CWorkspacePage::insertPS()
void CWorkspacePage::createPS()
{
QString fileName = QFileDialog::getSaveFileName(this, tr("Create new particle system file"),
".",
tr("ps files (*.ps)"));
if (!fileName.isEmpty())
".",
tr("ps files (*.ps)"));
if (!fileName.isEmpty())
{
// TODO: create method particle editor createNewPS
if (Modules::psEdit().getParticleWorkspace()->containsFile(NLMISC::CFile::getFilename(fileName.toStdString())))
{
QMessageBox::critical(this, tr("NeL particle system editor"),
tr("Failed to create new particle system"),
QMessageBox::Ok);
QMessageBox::critical(this, tr("NeL particle system editor"),
tr("Failed to create new particle system"),
QMessageBox::Ok);
return;
}
CWorkspaceNode *node = Modules::psEdit().getParticleWorkspace()->addNode(NLMISC::CFile::getFilename(fileName.toStdString()));
@ -173,10 +174,10 @@ void CWorkspacePage::createPS()
}
catch (NLMISC::Exception &e)
{
QMessageBox::critical(this, tr("NeL particle system editor"),
QString(e.what()),
QMessageBox::Ok);
return;
QMessageBox::critical(this, tr("NeL particle system editor"),
QString(e.what()),
QMessageBox::Ok);
return;
}
QModelIndex index = _treeModel->index(0, 0);
_treeModel->insertRows(node, static_cast<CParticleTreeItem*>(index.internalPointer())->childCount(), index);
@ -190,7 +191,7 @@ void CWorkspacePage::removeAllPS()
uint numNodes = Modules::psEdit().getParticleWorkspace()->getNumNode();
for(uint k = 0; k < numNodes; ++k)
Modules::psEdit().getParticleWorkspace()->removeNode((uint) 0);
_treeModel->setupModelFromWorkSpace();
}

@ -31,7 +31,8 @@
// Project includes
#include "particle_tree_model.h"
namespace NLQT {
namespace NLQT
{
/**
@class CWorkspacePage
@ -39,12 +40,12 @@ namespace NLQT {
*/
class CWorkspacePage: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CWorkspacePage(CParticleTreeModel *treeModel, QWidget *parent = 0);
~CWorkspacePage();
private Q_SLOTS:
void newWP();
void loadWP();
@ -53,9 +54,9 @@ private Q_SLOTS:
void insertPS();
void createPS();
void removeAllPS();
private:
Ui::CWorkspacePage _ui;
CParticleTreeModel *_treeModel;

@ -28,15 +28,16 @@
#include "particle_force_page.h"
#include "modules.h"
namespace NLQT {
namespace NLQT
{
CZonePage::CZonePage(QWidget *parent)
: QWidget(parent)
: QWidget(parent)
{
_ui.setupUi(this);
_ui.bounceFactorWidget->setRange(0.f, 1.f);
connect(_ui.toTargetsPushButton, SIGNAL(clicked()), this, SLOT(addTarget()));
connect(_ui.toAvaibleTargetsPushButton, SIGNAL(clicked()), this, SLOT(removeTarget()));
connect(_ui.bounceComboBox, SIGNAL(currentIndexChanged(int)), this, SLOT(setBounce(int)));
@ -50,10 +51,10 @@ CZonePage::~CZonePage()
void CZonePage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocatedBindable *locatedBindable)
{
_Node = ownerNode;
_Node = ownerNode;
_LBTarget = static_cast<NL3D::CPSTargetLocatedBindable *>(locatedBindable);
_Zone = dynamic_cast<NL3D::CPSZone *>(_LBTarget);
updateTargets();
_ui.bounceFactorWidget->setValue(_Zone->getBounceFactor() ,false);
_ui.bounceComboBox->setCurrentIndex( _Zone->getCollisionBehaviour());
@ -66,15 +67,15 @@ void CZonePage::addTarget()
if ((totalCount == 0) || (_ui.avaibleTargetsListWidget->currentRow() == -1)) return;
CLocatedItem *item = dynamic_cast<CLocatedItem *>(_ui.avaibleTargetsListWidget->currentItem());
NL3D::CPSLocated *loc = item->getUserData();
nlassert(loc);
_LBTarget->attachTarget(loc);
_ui.avaibleTargetsListWidget->takeItem(_ui.avaibleTargetsListWidget->currentRow());
_ui.targetsListWidget->addItem(item);
updateModifiedFlag();
}
@ -85,7 +86,7 @@ void CZonePage::removeTarget()
if ((totalCount == 0) || (_ui.targetsListWidget->currentRow() == -1)) return;
CLocatedItem *item = dynamic_cast<CLocatedItem *>(_ui.targetsListWidget->takeItem(_ui.targetsListWidget->currentRow()));
NL3D::CPSLocated *loc = item->getUserData();
nlassert(loc);
@ -97,9 +98,9 @@ void CZonePage::removeTarget()
void CZonePage::setBounce(int index)
{
if (_Zone->getCollisionBehaviour() != index)
if (_Zone->getCollisionBehaviour() != index)
_Zone->setCollisionBehaviour( (NL3D::CPSZone::TCollisionBehaviour) index);
_ui.bounceFactorWidget->setEnabled(_Zone->getCollisionBehaviour() == NL3D::CPSZone::bounce ? true : false);
Modules::psEdit().resetAutoCount(_Node);
}
@ -107,7 +108,7 @@ void CZonePage::setBounce(int index)
void CZonePage::setBounceFactor(float value)
{
_Zone->setBounceFactor(value);
updateModifiedFlag();
updateModifiedFlag();
}
void CZonePage::updateTargets()
@ -116,14 +117,14 @@ void CZonePage::updateTargets()
uint nbTarg = _LBTarget->getNbTargets();
_ui.targetsListWidget->clear();
std::set<NL3D::CPSLocated *> targetSet;
// fill the box thta tells us what the target are
for(k = 0; k < nbTarg; ++k)
{
CLocatedItem *item = new CLocatedItem(QString(_LBTarget->getTarget(k)->getName().c_str()),
_ui.targetsListWidget);
CLocatedItem *item = new CLocatedItem(QString(_LBTarget->getTarget(k)->getName().c_str()),
_ui.targetsListWidget);
item->setUserData(_LBTarget->getTarget(k));
targetSet.insert(_LBTarget->getTarget(k));
};
@ -134,7 +135,7 @@ void CZonePage::updateTargets()
uint nbLocated = ps->getNbProcess();
_ui.avaibleTargetsListWidget->clear();
for (k = 0; k < nbLocated; ++k)
{
NL3D::CPSLocated *loc = dynamic_cast<NL3D::CPSLocated *>(ps->getProcess(k));
@ -142,8 +143,8 @@ void CZonePage::updateTargets()
{
if (targetSet.find(loc) == targetSet.end())
{
CLocatedItem *item = new CLocatedItem(QString(loc->getName().c_str()),
_ui.avaibleTargetsListWidget);
CLocatedItem *item = new CLocatedItem(QString(loc->getName().c_str()),
_ui.avaibleTargetsListWidget);
item->setUserData(loc);
}
}

@ -31,16 +31,17 @@
// Project includes
#include "particle_node.h"
namespace NLQT {
namespace NLQT
{
class CZonePage: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CZonePage(QWidget *parent = 0);
virtual ~CZonePage();
void setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocatedBindable *locatedBindable);
private Q_SLOTS:
@ -53,18 +54,21 @@ private Q_SLOTS:
private:
void updateTargets();
void updateModifiedFlag() { if (_Node) _Node->setModified(true); }
void updateModifiedFlag()
{
if (_Node) _Node->setModified(true);
}
/// the target we're focusing on
NL3D::CPSTargetLocatedBindable *_LBTarget;
/// the collision zone being edited
NL3D::CPSZone *_Zone ;
CWorkspaceNode *_Node;
Ui::CZonePage _ui;
}; /* class CZonePage */
} /* namespace NLQT */

@ -15,7 +15,7 @@
// along with this program. If not, see <http://www.gnu.org/licenses/>.
#include "stdpch.h"
#include "stdpch.h"
#include "ps_initial_pos.h"
#include "nel/3d/particle_system.h"
@ -23,7 +23,8 @@
#include "nel/3d/ps_edit.h"
#include "nel/3d/ps_emitter.h"
namespace NLQT {
namespace NLQT
{
void CPSInitialPos::reset()
{
@ -38,7 +39,7 @@ void CPSInitialPos::copySystemInitialPos(NL3D::CParticleSystem *ps)
reset();
uint32 nbLocated = ps->getNbProcess();
_PS = ps;
_PS = ps;
for(uint32 k = 0; k < nbLocated; ++k)
{
@ -56,7 +57,7 @@ void CPSInitialPos::copySystemInitialPos(NL3D::CParticleSystem *ps)
ii.Pos = loc->getPos()[l];
ii.Speed = loc->getSpeed()[l];
_InitInfoVect.push_back(ii);
for (uint32 m = 0; m < loc->getNbBoundObjects(); ++m)
{
@ -67,14 +68,14 @@ void CPSInitialPos::copySystemInitialPos(NL3D::CParticleSystem *ps)
rsi.LB = loc->getBoundObject(m);
rsi.Index = l;
rsi.Psm = dynamic_cast<NL3D::IPSMover *>(loc->getBoundObject(m));
rsi.Scale = rsi.Psm->getScale(l);
rsi.Scale = rsi.Psm->getScale(l);
rsi.Rot = rsi.Psm->getMatrix(l);
_RotScaleInfoVect.push_back(rsi);
}
}
}
}
}
}
}
@ -87,19 +88,28 @@ struct CRemoveLocatedPred
// private : predicate to remove located from a CPSInitialPos::TInitialLocatedSizeVect vector
struct CRemoveLocatedFromLocatedSizePred : public CRemoveLocatedPred
{
bool operator()(const std::pair<NL3D::CPSLocated *, uint32> &value) { return Loc == value.first; }
bool operator()(const std::pair<NL3D::CPSLocated *, uint32> &value)
{
return Loc == value.first;
}
};
// private : predicate to remove located from a PSInitialPos::CInitPSInstanceInfo vector
struct CRemoveLocatedFromInitPSInstanceInfoVectPred : public CRemoveLocatedPred
{
bool operator()(const CPSInitialPos::CInitPSInstanceInfo &value) { return value.Loc == Loc; }
bool operator()(const CPSInitialPos::CInitPSInstanceInfo &value)
{
return value.Loc == Loc;
}
};
// private : predicate to remove located from a PSInitialPos::CRotScaleInfo vector
struct CRemoveLocatedFromRotScaleInfoVectPred : public CRemoveLocatedPred
{
bool operator()(const CPSInitialPos::CRotScaleInfo &value) { return value.Loc == Loc; }
bool operator()(const CPSInitialPos::CRotScaleInfo &value)
{
return value.Loc == Loc;
}
};
// private : predicate to remove located bindable pointers in a TRotScaleInfoVect vect
@ -107,18 +117,21 @@ struct CRemoveLocatedBindableFromRotScaleInfoVectPred
{
// the located bindable taht has been removed
NL3D::CPSLocatedBindable *LB;
bool operator()(const CPSInitialPos::CRotScaleInfo &value) { return value.LB == LB; }
bool operator()(const CPSInitialPos::CRotScaleInfo &value)
{
return value.LB == LB;
}
};
void CPSInitialPos::removeLocated(NL3D::CPSLocated *loc)
{
{
// in each container, we delete every element that has a pointer over lthe located loc
// , by using the dedicated predicate.
// , by using the dedicated predicate.
CRemoveLocatedFromLocatedSizePred p;
p.Loc = loc;
_InitialSizeVect.erase(std::remove_if(_InitialSizeVect.begin(), _InitialSizeVect.end(), p)
, _InitialSizeVect.end() );
, _InitialSizeVect.end() );
CRemoveLocatedFromInitPSInstanceInfoVectPred p2;
p2.Loc = loc;
@ -128,12 +141,12 @@ void CPSInitialPos::removeLocated(NL3D::CPSLocated *loc)
CRemoveLocatedFromRotScaleInfoVectPred p3;
p3.Loc = loc;
_RotScaleInfoVect.erase(std::remove_if(_RotScaleInfoVect.begin(), _RotScaleInfoVect.end(), p3)
, _RotScaleInfoVect.end());
, _RotScaleInfoVect.end());
}
void CPSInitialPos::removeLocatedBindable(NL3D::CPSLocatedBindable *lb)
{
{
CRemoveLocatedBindableFromRotScaleInfoVectPred p;
p.LB = lb;
_RotScaleInfoVect.erase(std::remove_if(_RotScaleInfoVect.begin(), _RotScaleInfoVect.end(), p), _RotScaleInfoVect.end() );
@ -158,11 +171,11 @@ void CPSInitialPos::restoreSystem()
nlassert(loc->getSize() == 0);
}
}
}
// recreate the initial number of instances
for (TInitialLocatedSizeVect ::iterator itSize = _InitialSizeVect.begin(); itSize != _InitialSizeVect.end(); ++itSize)
{
// nlassert(itSize->first->getSize() == 0)
// nlassert(itSize->first->getSize() == 0)
for (uint l = 0; l < itSize->second; ++l)
{
itSize->first->newElement(NLMISC::CVector::Null, NLMISC::CVector::Null, NULL, 0, itSize->first->getMatrixMode(), 0.f);
@ -170,7 +183,7 @@ void CPSInitialPos::restoreSystem()
uint realSize = itSize->first->getSize();
uint size = itSize->second;
}
NL3D::CPSEmitter::setBypassEmitOnDeath(false);
for (TInitInfoVect::iterator it = _InitInfoVect.begin(); it != _InitInfoVect.end(); ++it)
@ -185,7 +198,7 @@ void CPSInitialPos::restoreSystem()
it->Loc->getParametricInfos()[it->Index].Pos = it->Pos;
it->Loc->getParametricInfos()[it->Index].Speed = it->Speed;
it->Loc->getParametricInfos()[it->Index].Date = 0.f;
}
}
}
}
for (TRotScaleInfoVect::iterator it2 = _RotScaleInfoVect.begin(); it2 != _RotScaleInfoVect.end(); ++it2)

@ -24,13 +24,14 @@
namespace NL3D
{
class CParticleSystem;
class CPSLocated;
class CPSLocatedBindable;
struct IPSMover;
class CParticleSystem;
class CPSLocated;
class CPSLocatedBindable;
struct IPSMover;
}
namespace NLQT {
namespace NLQT
{
/**
@class CPSInitialPos
This class helps to copy the position of initial instances in a particle
@ -41,35 +42,35 @@ class CPSInitialPos
{
public:
CPSInitialPos() : _PS(NULL) {}
/// construct this by copying the datas of the system
void copySystemInitialPos(NL3D::CParticleSystem *ps);
/// reinitialize the system with its initial instances positions
/// Works only once per copySystemInitialPos() call
void restoreSystem();
/// send back true when bbox display is enabled
bool isBBoxDisplayEnabled();
/// update data when a located in a particle system has been removed
/// update data when a located in a particle system has been removed
void removeLocated(NL3D::CPSLocated *loc);
/// update data when a located bindable in a particle system has been removed
void removeLocatedBindable(NL3D::CPSLocatedBindable *lb);
/// update data when a located bindable in a particle system has been removed
void removeLocatedBindable(NL3D::CPSLocatedBindable *lb);
/// initial position and speed of a located instance in a particle system
struct CInitPSInstanceInfo
{
{
uint32 Index;
NL3D::CPSLocated *Loc;
NLMISC::CVector Speed;
NLMISC::CVector Pos;
NLMISC::CVector Pos;
};
/// rotation and scale of an element
struct CRotScaleInfo
{
{
uint32 Index;
NL3D::CPSLocated *Loc;
NL3D::CPSLocatedBindable *LB;
@ -77,9 +78,18 @@ public:
NLMISC::CMatrix Rot;
NLMISC::CVector Scale;
};
NL3D::CParticleSystem *getPS() { return _PS; }
const NL3D::CParticleSystem *getPS() const { return _PS; }
bool isStateMemorized() const { return _PS != NULL; }
NL3D::CParticleSystem *getPS()
{
return _PS;
}
const NL3D::CParticleSystem *getPS() const
{
return _PS;
}
bool isStateMemorized() const
{
return _PS != NULL;
}
private:
typedef std::vector<CInitPSInstanceInfo> TInitInfoVect;
@ -87,13 +97,13 @@ private:
typedef std::vector< std::pair<NL3D::CPSLocated *, uint32> > TInitialLocatedSizeVect;
TInitInfoVect _InitInfoVect;
TRotScaleInfoVect _RotScaleInfoVect;
/// initial number of instances for each located
TInitialLocatedSizeVect _InitialSizeVect;
NL3D::CParticleSystem *_PS;
NL3D::CParticleSystem *_PS;
/// reset all initial infos
void reset();
void reset();
};
} /* namespace NLQT */

@ -27,15 +27,16 @@
// Project includes
#include "modules.h"
namespace NLQT {
namespace NLQT
{
const float epsilon = 10E-3f;
CPSMoverPage::CPSMoverPage(QWidget *parent)
: QWidget(parent)
: QWidget(parent)
{
_ui.setupUi(this);
_ui.scaleWidget->setRange(0.f, 4.f);
_ui.scaleWidget->setWrapper(&_UniformScaleWrapper);
@ -49,15 +50,15 @@ CPSMoverPage::CPSMoverPage(QWidget *parent)
_ui.scaleZWidget->setWrapper(&_ZScaleWrapper);
//_ui.directionWidget->setWrapper(&_DirectionWrapper);
connect(_ui.xDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setXPosition(double)));
connect(_ui.yDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setYPosition(double)));
connect(_ui.zDoubleSpinBox, SIGNAL(valueChanged(double)), this, SLOT(setZPosition(double)));
connect(_ui.directionWidget, SIGNAL(valueChanged(NLMISC::CVector)), this, SLOT(setDir(NLMISC::CVector)));
connect(_ui.listWidget, SIGNAL(currentItemChanged(QListWidgetItem*,QListWidgetItem*)),
this, SLOT(changeSubComponent()));
connect(_ui.listWidget, SIGNAL(currentItemChanged(QListWidgetItem*,QListWidgetItem*)),
this, SLOT(changeSubComponent()));
}
CPSMoverPage::~CPSMoverPage()
@ -71,20 +72,20 @@ void CPSMoverPage::setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocated *lo
_EditedLocatedIndex = editedLocatedIndex;
updatePosition();
_ui.listWidget->clear();
hideAdditionalWidget();
uint numBound = _EditedLocated->getNbBoundObjects();
uint nbCandidates = 0;
for (uint k = 0; k < numBound; ++k)
{
if (dynamic_cast<NL3D::IPSMover *>(_EditedLocated->getBoundObject(k)))
{
CLocatedBindableItem *item = new CLocatedBindableItem(QString(_EditedLocated->getBoundObject(k)->getName().c_str()),
_ui.listWidget);
_ui.listWidget);
item->setUserData(_EditedLocated->getBoundObject(k));
++nbCandidates;
}
@ -118,15 +119,15 @@ void CPSMoverPage::hideAdditionalWidget()
void CPSMoverPage::updateListener(void)
{
/* if(_ParticleDlg->MainFrame->isMoveElement())
{
const NLMISC::CVector &pos = _EditedLocated->getPos()[_EditedLocatedIndex];
NLMISC::CMatrix m;
m = _MouseListener->getModelMatrix();
m.setPos(pos);
_MouseListener->setModelMatrix(m);
_Node->setModified(true);
}*/
/* if(_ParticleDlg->MainFrame->isMoveElement())
{
const NLMISC::CVector &pos = _EditedLocated->getPos()[_EditedLocatedIndex];
NLMISC::CMatrix m;
m = _MouseListener->getModelMatrix();
m.setPos(pos);
_MouseListener->setModelMatrix(m);
_Node->setModified(true);
}*/
}
void CPSMoverPage::setXPosition(double value)
@ -167,17 +168,17 @@ void CPSMoverPage::changeSubComponent()
hideAdditionalWidget();
NL3D::IPSMover *m = getMoverInterface();
if (!m) return;
_Node->getPSPointer()->setCurrentEditedElement(NULL);
_Node->getPSPointer()->setCurrentEditedElement(_EditedLocated, _EditedLocatedIndex, getLocatedBindable());
if (m->supportUniformScaling() && ! m->supportNonUniformScaling() )
{
_UniformScaleWrapper.OwnerNode = _Node;
_UniformScaleWrapper.M = m;
_UniformScaleWrapper.Index = _EditedLocatedIndex;
_ui.scaleWidget->updateUi();
_ui.scaleLabel->show();
_ui.scaleWidget->show();
@ -188,31 +189,31 @@ void CPSMoverPage::changeSubComponent()
_XScaleWrapper.OwnerNode = _Node;
_XScaleWrapper.M = m;
_XScaleWrapper.Index = _EditedLocatedIndex;
_ui.scaleXWidget->updateUi();
_ui.scaleXLabel->show();
_ui.scaleXWidget->show();
// dialog for edition of y scale
_YScaleWrapper.OwnerNode = _Node;
_YScaleWrapper.M = m;
_YScaleWrapper.Index = _EditedLocatedIndex;
_ui.scaleYWidget->updateUi();
_ui.scaleYLabel->show();
_ui.scaleYWidget->show();
// dialog for edition of x scale
_ZScaleWrapper.OwnerNode = _Node;
_ZScaleWrapper.M = m;
_ZScaleWrapper.Index = _EditedLocatedIndex;
_ui.scaleZWidget->updateUi();
_ui.scaleZLabel->show();
_ui.scaleZWidget->show();
}
if (m->onlyStoreNormal())
{
_ui.directionWidget->setValue(getMoverInterface()->getNormal(getLocatedIndex()), false);
@ -231,7 +232,7 @@ NL3D::IPSMover *CPSMoverPage::getMoverInterface(void)
nlassert(_EditedLocated);
sint currIndex = _ui.listWidget->currentRow();
if (currIndex == -1) return NULL;
CLocatedBindableItem *item = dynamic_cast<CLocatedBindableItem *>(_ui.listWidget->currentItem());
return dynamic_cast<NL3D::IPSMover *>(item->getUserData());
}

@ -35,7 +35,8 @@
// Project includes
#include "ps_wrapper.h"
namespace NLQT {
namespace NLQT
{
/**
@class CLocatedBindableItem
@ -44,14 +45,20 @@ namespace NLQT {
class CLocatedBindableItem: public QListWidgetItem
{
public:
CLocatedBindableItem ( const QString & text, QListWidget * parent = 0, int type = UserType ):
QListWidgetItem(text, parent, type), _lb(NULL) {}
void setUserData(NL3D::CPSLocatedBindable *loc) { _lb = loc;}
NL3D::CPSLocatedBindable *getUserData() const { return _lb;}
CLocatedBindableItem ( const QString & text, QListWidget * parent = 0, int type = UserType ):
QListWidgetItem(text, parent, type), _lb(NULL) {}
void setUserData(NL3D::CPSLocatedBindable *loc)
{
_lb = loc;
}
NL3D::CPSLocatedBindable *getUserData() const
{
return _lb;
}
private:
NL3D::CPSLocatedBindable *_lb;
}; /* class CTargetItem */
@ -61,15 +68,15 @@ private:
*/
class CPSMoverPage: public QWidget
{
Q_OBJECT
Q_OBJECT
public:
CPSMoverPage(QWidget *parent = 0);
~CPSMoverPage();
/// Set the instance to edit.
void setEditedItem(CWorkspaceNode *ownerNode, NL3D::CPSLocated *located, uint32 editedLocatedIndex);
/// position has to be updated (for mouse edition)
void updatePosition(void) ;
@ -77,11 +84,20 @@ public:
NL3D::IPSMover *getMoverInterface(void) ;
/// get the located being edited
NL3D::CPSLocated *getLocated(void) { return _EditedLocated ; }
const NL3D::CPSLocated *getLocated(void) const { return _EditedLocated ; }
NL3D::CPSLocated *getLocated(void)
{
return _EditedLocated ;
}
const NL3D::CPSLocated *getLocated(void) const
{
return _EditedLocated ;
}
/// get the index of the current edited item
uint32 getLocatedIndex(void) const { return _EditedLocatedIndex ; }
uint32 getLocatedIndex(void) const
{
return _EditedLocatedIndex ;
}
/// ghet the current located bindable being edited, or null
NL3D::CPSLocatedBindable *getLocatedBindable(void) ;
@ -91,18 +107,24 @@ private Q_SLOTS:
void setYPosition(double value);
void setZPosition(double value);
void changeSubComponent();
void setDir(const NLMISC::CVector &value);
private:
/// wrappers to scale objects
struct CUniformScaleWrapper : public IPSWrapperFloat
{
uint32 Index ;
NL3D::IPSMover *M ;
float get(void) const { return M->getScale(Index).x ; }
void set(const float &v) { M->setScale(Index, v) ; }
float get(void) const
{
return M->getScale(Index).x ;
}
void set(const float &v)
{
M->setScale(Index, v) ;
}
} _UniformScaleWrapper ;
/// wrapper to scale the X coordinate
@ -110,11 +132,14 @@ private:
{
uint32 Index ;
NL3D::IPSMover *M ;
float get(void) const { return M->getScale(Index).x ; }
void set(const float &s)
{
float get(void) const
{
return M->getScale(Index).x ;
}
void set(const float &s)
{
NLMISC::CVector v = M->getScale(Index) ;
M->setScale(Index, NLMISC::CVector(s, v.y, v.z)) ;
M->setScale(Index, NLMISC::CVector(s, v.y, v.z)) ;
}
} _XScaleWrapper ;
@ -123,11 +148,14 @@ private:
{
uint32 Index ;
NL3D::IPSMover *M ;
float get(void) const { return M->getScale(Index).y ; }
void set(const float &s)
{
float get(void) const
{
return M->getScale(Index).y ;
}
void set(const float &s)
{
NLMISC::CVector v = M->getScale(Index) ;
M->setScale(Index, NLMISC::CVector(v.x, s, v.z) ) ;
M->setScale(Index, NLMISC::CVector(v.x, s, v.z) ) ;
}
} _YScaleWrapper ;
@ -136,27 +164,33 @@ private:
{
uint32 Index ;
NL3D::IPSMover *M ;
float get(void) const { return M->getScale(Index).z ; }
void set(const float &s)
{
float get(void) const
{
return M->getScale(Index).z ;
}
void set(const float &s)
{
NLMISC::CVector v = M->getScale(Index) ;
M->setScale(Index, NLMISC::CVector(v.x, v.y, s) ) ;
M->setScale(Index, NLMISC::CVector(v.x, v.y, s) ) ;
}
} _ZScaleWrapper ;
void hideAdditionalWidget();
void updateModifiedFlag() { if (_Node) _Node->setModified(true); }
void updateModifiedFlag()
{
if (_Node) _Node->setModified(true);
}
/// update the mouse listener position when the user entered a value with the keyboard
void updateListener(void) ;
CWorkspaceNode *_Node;
NL3D::CPSLocated *_EditedLocated ;
uint32 _EditedLocatedIndex ;
Ui::CPSMoverPage _ui;
}; /* class CPSMoverPage */

@ -30,8 +30,9 @@
//
#include "particle_node.h"
namespace NLQT {
namespace NLQT
{
/// Wrapper to read/write a value of type T
template <class T> class IPSWrapper
{
@ -66,7 +67,7 @@ public:
IPSSchemeWrapper() : OwnerNode(NULL) {}
typedef NL3D::CPSAttribMaker<T> scheme_type;
virtual scheme_type *getScheme(void) const = 0;
void setSchemeAndUpdateModifiedFlag(scheme_type *s)
void setSchemeAndUpdateModifiedFlag(scheme_type *s)
{
if (OwnerNode)
{

@ -34,13 +34,14 @@
using namespace NLMISC;
namespace NLQT {
namespace NLQT
{
CSettingsDialog::CSettingsDialog(QWidget *parent)
: QDialog(parent)
: QDialog(parent)
{
ui.setupUi(this);
loadGraphicsSettings();
loadSoundSettings();
loadPathsSettings();
@ -49,19 +50,19 @@ CSettingsDialog::CSettingsDialog(QWidget *parent)
connect(ui.enableBloomCheckBox, SIGNAL(toggled(bool)), this, SLOT(setEnableBloom(bool)));
connect(ui.squareBloomCheckBox, SIGNAL(toggled(bool)), this, SLOT(setEnableSquareBloon(bool)));
connect(ui.bloomDensityHorizontalSlider, SIGNAL(valueChanged(int)), this, SLOT(setDensityBloom(int)));
connect(ui.addToolButton, SIGNAL(clicked()), this, SLOT(addPath()));
connect(ui.removeToolButton, SIGNAL(clicked()), this, SLOT(removePath()));
connect(ui.upToolButton, SIGNAL(clicked()), this, SLOT(upPath()));
connect(ui.downToolButton, SIGNAL(clicked()), this, SLOT(downPath()));
connect(ui.buttonBox, SIGNAL(accepted()), this, SLOT(applyPressed()));
connect(ui.tileBankToolButton, SIGNAL(clicked()), this, SLOT(setTileBank()));
connect(ui.tileFarBankToolButton, SIGNAL(clicked()), this, SLOT(setTileFarBank()));
connect(ui.vegetTexToolButton, SIGNAL(clicked()), this, SLOT(setTextureVegetable()));
connect(ui.addZoneToolButton, SIGNAL(clicked()), this, SLOT(addZone()));
connect(ui.removeZoneToolButton, SIGNAL(clicked()), this, SLOT(removeZone()));
#ifdef NL_OS_UNIX
ui.driverGraphComboBox->setEnabled(false);
#endif
@ -79,7 +80,7 @@ void CSettingsDialog::addPath()
{
QListWidgetItem *newItem = new QListWidgetItem;
QString newPath = QFileDialog::getExistingDirectory(this);
if (!(newPath == ""))
if (!(newPath == ""))
{
newItem->setText(newPath);
newItem->setFlags(Qt::ItemIsEditable | Qt::ItemIsEnabled | Qt::ItemIsSelectable);
@ -99,7 +100,7 @@ void CSettingsDialog::upPath()
if (!(currentRow == 0))
{
QListWidgetItem *item = ui.pathsListWidget->takeItem(currentRow);
ui.pathsListWidget->insertItem(--currentRow, item);
ui.pathsListWidget->insertItem(--currentRow, item);
ui.pathsListWidget->setCurrentRow(currentRow);
}
}
@ -110,20 +111,20 @@ void CSettingsDialog::downPath()
if (!(currentRow == ui.pathsListWidget->count()-1))
{
QListWidgetItem *item = ui.pathsListWidget->takeItem(currentRow);
ui.pathsListWidget->insertItem(++currentRow, item);
ui.pathsListWidget->insertItem(++currentRow, item);
ui.pathsListWidget->setCurrentRow(currentRow);
}
}
void CSettingsDialog::applyPressed()
{
// settings take after restart the program
QMessageBox::warning(this, tr("Settings"),
tr("Graphics and sound settings "
"take after restart the program"),
QMessageBox::Ok);
QMessageBox::warning(this, tr("Settings"),
tr("Graphics and sound settings "
"take after restart the program"),
QMessageBox::Ok);
saveGraphicsSettings();
saveSoundSettings();
savePathsSettings();
@ -131,7 +132,7 @@ void CSettingsDialog::applyPressed()
// save config file
Modules::config().getConfigFile().save();
// reload search paths
Modules::config().configSearchPaths();
}
@ -139,9 +140,9 @@ void CSettingsDialog::applyPressed()
void CSettingsDialog::setTileBank()
{
QString fileName = QFileDialog::getOpenFileName(this, tr("Set new tile bank"),
ui.tileBankLineEdit->text(),
tr("Tile Bank file (*.smallbank *.bank);;"));
if (!fileName.isEmpty())
ui.tileBankLineEdit->text(),
tr("Tile Bank file (*.smallbank *.bank);;"));
if (!fileName.isEmpty())
{
ui.tileBankLineEdit->setText(fileName);
}
@ -149,10 +150,10 @@ void CSettingsDialog::setTileBank()
void CSettingsDialog::setTileFarBank()
{
QString fileName = QFileDialog::getOpenFileName(this, tr("Set new tile far bank"),
ui.tileFarBankLineEdit->text(),
tr("Tile Far Bank file (*.farbank);;"));
if (!fileName.isEmpty())
QString fileName = QFileDialog::getOpenFileName(this, tr("Set new tile far bank"),
ui.tileFarBankLineEdit->text(),
tr("Tile Far Bank file (*.farbank);;"));
if (!fileName.isEmpty())
{
ui.tileFarBankLineEdit->setText(fileName);
}
@ -161,9 +162,9 @@ void CSettingsDialog::setTileFarBank()
void CSettingsDialog::setTextureVegetable()
{
QString fileName = QFileDialog::getOpenFileName(this, tr("Set MicroVegetable texture"),
ui.vegetTextureLineEdit->text(),
tr("Texture file (*.tga *.png *.jpg *.dds);;"));
if (!fileName.isEmpty())
ui.vegetTextureLineEdit->text(),
tr("Texture file (*.tga *.png *.jpg *.dds);;"));
if (!fileName.isEmpty())
{
ui.vegetTextureLineEdit->setText(fileName);
}
@ -172,21 +173,21 @@ void CSettingsDialog::setTextureVegetable()
void CSettingsDialog::addZone()
{
QStringList fileNames = QFileDialog::getOpenFileNames(this,
tr("Add zone files"), ".",
tr("Zonel files (*.zonel);;"));
tr("Add zone files"), ".",
tr("Zonel files (*.zonel);;"));
if (!fileNames.isEmpty())
if (!fileNames.isEmpty())
{
QStringList list = fileNames;
QStringList::Iterator it = list.begin();
while(it != list.end())
while(it != list.end())
{
QListWidgetItem *newItem = new QListWidgetItem;
QListWidgetItem *newItem = new QListWidgetItem;
newItem->setText(*it);
newItem->setFlags(Qt::ItemIsEditable | Qt::ItemIsEnabled | Qt::ItemIsSelectable);
ui.zonesListWidget->addItem(newItem);
++it;
}
}
}
}
@ -215,11 +216,11 @@ void CSettingsDialog::cfcbGraphicsDrivers(NLMISC::CConfigFile::CVar &var)
{
while (ui.driverGraphComboBox->count())
ui.driverGraphComboBox->removeItem(0);
// load types graphics driver from the config file
for (uint i = 0; i < var.size(); ++i)
ui.driverGraphComboBox->addItem(var.asString(i).c_str());
// set graphics driver from the config file
QString value = Modules::config().getValue("GraphicsDriver",std::string("OpenGL")).c_str();
QString dn = value.toLower();
@ -237,11 +238,11 @@ void CSettingsDialog::cfcbSoundDrivers(NLMISC::CConfigFile::CVar& var)
{
while (ui.driverSndComboBox->count())
ui.driverSndComboBox->removeItem(0);
// load types sound driver from the config file
for (uint i = 0; i < var.size(); ++i)
ui.driverSndComboBox->addItem(var.asString(i).c_str());
// set sound driver from the config file
QString value = Modules::config().getValue("SoundDriver",std::string("Auto")).c_str();
QString dn = value.toLower();
@ -260,7 +261,7 @@ void CSettingsDialog::cfcbSearchPaths(NLMISC::CConfigFile::CVar &var)
/// TODO: create custom widget add/insert/del/up/down paths (also this is use landscape zones)
ui.pathsListWidget->clear();
// load search paths from the config file
for (uint i = 0; i < var.size(); ++i)
{
@ -305,7 +306,7 @@ void CSettingsDialog::loadVegetableSettings()
ui.tileBankLineEdit->setText(Modules::config().getConfigFile().getVar("VegetTileBank").asString().c_str());
ui.tileFarBankLineEdit->setText(Modules::config().getConfigFile().getVar("VegetTileFarBank").asString().c_str());
ui.vegetTextureLineEdit->setText(Modules::config().getConfigFile().getVar("VegetTexture").asString().c_str());
ui.zonesListWidget->clear();
// load vegetable landscape zone paths from config file

@ -30,7 +30,8 @@
// Project includes
namespace NLQT {
namespace NLQT
{
/**
@class CSettingsDialog
@ -38,7 +39,7 @@ namespace NLQT {
*/
class CSettingsDialog: public QDialog
{
Q_OBJECT
Q_OBJECT
public:
CSettingsDialog(QWidget *parent = 0);
@ -65,7 +66,7 @@ private:
void cfcbGraphicsDrivers(NLMISC::CConfigFile::CVar &var);
void cfcbSoundDrivers(NLMISC::CConfigFile::CVar &var);
void cfcbSearchPaths(NLMISC::CConfigFile::CVar &var);
void loadGraphicsSettings();
void loadSoundSettings();
void loadPathsSettings();
@ -74,7 +75,7 @@ private:
void saveSoundSettings();
void savePathsSettings();
void saveVegetableSettings();
Ui::CSettingsDialog ui;
}; /* class CSettingsDialog */

@ -34,18 +34,19 @@
using namespace NL3D;
using namespace NLMISC;
namespace NLQT {
namespace NLQT
{
CSetupFog::CSetupFog(QWidget *parent)
: QDockWidget(parent)
: QDockWidget(parent)
{
ui.setupUi(this);
// load fog value from config file
ui.startDoubleSpinBox->setValue(Modules::config().getValue("FogStart", 0.0));
ui.endDoubleSpinBox->setValue(Modules::config().getValue("FogEnd", 0.0));
colorFog = Modules::config().getValue("FogColor",CRGBA(0.0, 0.0, 0.0));
connect(ui.applyPushButton, SIGNAL(clicked()), this, SLOT(apply()));
connect(ui.colorPushButton, SIGNAL(clicked()), this, SLOT(setColor()));
}
@ -63,17 +64,17 @@ CSetupFog::~CSetupFog()
void CSetupFog::apply()
{
Modules::objView().getDriver()->setupFog(ui.startDoubleSpinBox->value(),
ui.endDoubleSpinBox->value(),
colorFog);
Modules::objView().getDriver()->setupFog(ui.startDoubleSpinBox->value(),
ui.endDoubleSpinBox->value(),
colorFog);
Modules::objView().getDriver()->enableFog(ui.enableFogCheckBox->isChecked());
}
void CSetupFog::setColor()
{
QColor color = QColorDialog::getColor(QColor(colorFog.R,
colorFog.G,
colorFog.B));
colorFog.G,
colorFog.B));
colorFog.set(color.red(), color.green(), color.blue());
}

Some files were not shown because too many files have changed in this diff Show More

Loading…
Cancel
Save