Skip to content

Commit

Permalink
#5787: Add "Create Particle" option to ortho context menu.
Browse files Browse the repository at this point in the history
  • Loading branch information
codereader committed Apr 3, 2022
1 parent 325f188 commit c76852f
Show file tree
Hide file tree
Showing 2 changed files with 57 additions and 37 deletions.
91 changes: 55 additions & 36 deletions radiant/ui/ortho/OrthoContextMenu.cpp
Expand Up @@ -2,12 +2,10 @@

#include "i18n.h"
#include "selectionlib.h"
#include "ibrush.h"
#include "isound.h"
#include "ui/iresourcechooser.h"
#include "ui/idialogmanager.h"
#include "entitylib.h" // EntityFindByClassnameWalker
#include "selectionlib.h"
#include "ientity.h" // Node_getEntity()
#include "iregistry.h"
#include "ui/imainframe.h"
Expand All @@ -19,6 +17,7 @@

#include "ui/modelselector/ModelSelector.h"
#include "ui/prefabselector/PrefabSelector.h"
#include "ui/particles/ParticlesChooser.h"

#include "string/convert.h"
#include "scene/GroupNodeChecker.h"
Expand All @@ -41,6 +40,7 @@ namespace {
const char* LIGHT_CLASSNAME = "light";
const char* MODEL_CLASSNAME_ANIMATED = "func_animate";
const char* MODEL_CLASSNAME_STATIC = "func_static";
const char* PARTICLE_EMITTER_CLASSNAME = "func_emitter";
const char* PLAYERSTART_CLASSNAME = "info_player_start";

const char* ADD_ENTITY_TEXT = N_("Create Entity...");
Expand All @@ -50,6 +50,8 @@ namespace {
const char* PLACE_PLAYERSTART_ICON = "player_start16.png";
const char* ADD_MODEL_TEXT = N_("Create Model...");
const char* ADD_MODEL_ICON = "cmenu_add_model.png";
const char* ADD_PARTICLE_TEXT = N_("Create Particle...");
const char* ADD_PARTICLE_ICON = "particle16.png";
const char* ADD_MONSTERCLIP_TEXT = N_("Surround with Monsterclip");
const char* ADD_MONSTERCLIP_ICON = "monsterclip16.png";
const char* ADD_LIGHT_TEXT = N_("Create Light...");
Expand Down Expand Up @@ -190,7 +192,7 @@ bool OrthoContextMenu::checkAddEntity()
return !_selectionInfo.anythingSelected || _selectionInfo.onlyPrimitivesSelected;
}

bool OrthoContextMenu::checkAddModel()
bool OrthoContextMenu::checkAddModelOrParticle()
{
return !_selectionInfo.anythingSelected;
}
Expand Down Expand Up @@ -331,50 +333,59 @@ void OrthoContextMenu::callbackAddModel()
{
UndoableCommand command("addModel");

const SelectionInfo& info = GlobalSelectionSystem().getSelectionInfo();
// Display the model selector and block waiting for a selection (may be empty)
ModelSelectorResult ms = ModelSelector::chooseModel("", true, true);

// If a model was selected, create the entity and set its model key
if (ms.model.empty())
{
return;
}

// To create a model selection must be empty
if (info.totalCount == 0)
try
{
// Display the model selector and block waiting for a selection (may be empty)
ModelSelectorResult ms = ui::ModelSelector::chooseModel("", true, true);
auto modelDef = GlobalEntityClassManager().findModel(ms.model);

auto className = modelDef ? MODEL_CLASSNAME_ANIMATED : MODEL_CLASSNAME_STATIC;

// If a model was selected, create the entity and set its model key
if (ms.model.empty())
auto modelNode = GlobalEntityModule().createEntityFromSelection(
className, _lastPoint
);

//Node_getTraversable(GlobalSceneGraph().root())->insert(modelNode);
modelNode->getEntity().setKeyValue("model", ms.model);
modelNode->getEntity().setKeyValue("skin", ms.skin);

// If 'createClip' is ticked, create a clip brush
if (ms.createClip)
{
return;
GlobalCommandSystem().execute("SurroundWithMonsterclip");
}
}
catch (cmd::ExecutionFailure& e)
{
wxutil::Messagebox::ShowError(fmt::format(_("Unable to create model: {0}"), e.what()));
}
}

try
{
auto modelDef = GlobalEntityClassManager().findModel(ms.model);
void OrthoContextMenu::callbackAddParticle()
{
UndoableCommand command("addParticle");

auto className = modelDef ? MODEL_CLASSNAME_ANIMATED : MODEL_CLASSNAME_STATIC;
// Display the particle selector and block waiting for a selection (may be empty)
auto selectedParticle = ParticlesChooser::ChooseParticle();

auto modelNode = GlobalEntityModule().createEntityFromSelection(
className, _lastPoint
);
if (selectedParticle.empty()) return;

//Node_getTraversable(GlobalSceneGraph().root())->insert(modelNode);
modelNode->getEntity().setKeyValue("model", ms.model);
modelNode->getEntity().setKeyValue("skin", ms.skin);
try
{
auto node = GlobalEntityModule().createEntityFromSelection(PARTICLE_EMITTER_CLASSNAME, _lastPoint);

// If 'createClip' is ticked, create a clip brush
if (ms.createClip)
{
GlobalCommandSystem().execute("SurroundWithMonsterclip");
}
}
catch (cmd::ExecutionFailure& e)
{
wxutil::Messagebox::ShowError(fmt::format(_("Unable to create model: {0}"), e.what()));
}
node->getEntity().setKeyValue("model", selectedParticle);
}
else
catch (cmd::ExecutionFailure& e)
{
wxutil::Messagebox::ShowError(
_("Nothing must be selected for model creation")
);
wxutil::Messagebox::ShowError(fmt::format(_("Unable to create particle entity: {0}"), e.what()));
}
}

Expand Down Expand Up @@ -410,7 +421,14 @@ void OrthoContextMenu::registerDefaultItems()
new wxutil::MenuItem(
new wxutil::IconTextMenuItem(_(ADD_MODEL_TEXT), ADD_MODEL_ICON),
std::bind(&OrthoContextMenu::callbackAddModel, this),
std::bind(&OrthoContextMenu::checkAddModel, this))
std::bind(&OrthoContextMenu::checkAddModelOrParticle, this))
);

wxutil::MenuItemPtr addParticle(
new wxutil::MenuItem(
new wxutil::IconTextMenuItem(_(ADD_PARTICLE_TEXT), ADD_PARTICLE_ICON),
std::bind(&OrthoContextMenu::callbackAddParticle, this),
std::bind(&OrthoContextMenu::checkAddModelOrParticle, this))
);

wxutil::CommandMenuItemPtr surroundWithMonsterClip(
Expand Down Expand Up @@ -474,6 +492,7 @@ void OrthoContextMenu::registerDefaultItems()
// Register all constructed items
addItem(_createEntityItem, SECTION_CREATE);
addItem(addModel, SECTION_CREATE);
addItem(addParticle, SECTION_CREATE);
addItem(addLight, SECTION_CREATE);
addItem(addSpeaker, SECTION_CREATE);
addItem(addPrefab, SECTION_CREATE);
Expand Down
3 changes: 2 additions & 1 deletion radiant/ui/ortho/OrthoContextMenu.h
Expand Up @@ -102,11 +102,12 @@ class OrthoContextMenu :
bool checkMakeVisportal();
bool checkAddMonsterclip();
bool checkAddEntity();
bool checkAddModel();
bool checkAddModelOrParticle();

void addEntity();
void placePlayerStart();
void callbackAddModel();
void callbackAddParticle();
void callbackAddLight();
void callbackAddPrefab();
void callbackAddSpeaker();
Expand Down

0 comments on commit c76852f

Please sign in to comment.