From ed7c2fe3d68326b71122bf3cb82f11a9cc5f40ba Mon Sep 17 00:00:00 2001 From: Ykkrosh Date: Thu, 22 Dec 2005 04:20:16 +0000 Subject: [PATCH] Atlas: Allow placement of actors. This was SVN commit r3275. --- .../AtlasUI/ScenarioEditor/ScenarioEditor.cpp | 2 + .../ScenarioEditor/Sections/Object/Object.cpp | 80 +++++++-- .../ScenarioEditor/Sections/Object/Object.h | 6 +- .../ScenarioEditor/Tools/PlaceObject.cpp | 6 +- .../GameInterface/Handlers/ObjectHandlers.cpp | 152 ++++++++++++++---- source/tools/atlas/GameInterface/Messages.h | 12 +- 6 files changed, 202 insertions(+), 56 deletions(-) diff --git a/source/tools/atlas/AtlasUI/ScenarioEditor/ScenarioEditor.cpp b/source/tools/atlas/AtlasUI/ScenarioEditor/ScenarioEditor.cpp index ce64c8c506..69d8fad98f 100644 --- a/source/tools/atlas/AtlasUI/ScenarioEditor/ScenarioEditor.cpp +++ b/source/tools/atlas/AtlasUI/ScenarioEditor/ScenarioEditor.cpp @@ -400,6 +400,8 @@ ScenarioEditor::ScenarioEditor(wxWindow* parent) toolbar->AddToolButton(_("Paint Terrain"), _("Paint terrain texture"), _T("paintterrain.png"), _T("PaintTerrain")); toolbar->Realize(); SetToolBar(toolbar); + // Set the default tool to be selected + SetCurrentTool(_T("")); ////////////////////////////////////////////////////////////////////////// // Main window diff --git a/source/tools/atlas/AtlasUI/ScenarioEditor/Sections/Object/Object.cpp b/source/tools/atlas/AtlasUI/ScenarioEditor/Sections/Object/Object.cpp index 9c3ab3ac06..bfbe5dc6a9 100644 --- a/source/tools/atlas/AtlasUI/ScenarioEditor/Sections/Object/Object.cpp +++ b/source/tools/atlas/AtlasUI/ScenarioEditor/Sections/Object/Object.cpp @@ -12,7 +12,7 @@ class ObjectSelectListBox : public wxListBox { public: ObjectSelectListBox(wxWindow* parent) - : wxListBox(parent, wxID_ANY, wxDefaultPosition, wxDefaultSize, 0, NULL, wxLB_SINGLE) + : wxListBox(parent, wxID_ANY, wxDefaultPosition, wxDefaultSize, 0, NULL, wxLB_SINGLE|wxLB_HSCROLL) { } @@ -28,35 +28,87 @@ BEGIN_EVENT_TABLE(ObjectSelectListBox, wxListBox) EVT_LISTBOX(wxID_ANY, ObjectSelectListBox::OnSelect) END_EVENT_TABLE(); + +class ObjectChoiceCtrl : public wxChoice +{ +public: + ObjectChoiceCtrl(wxWindow* parent, const wxArrayString& strings, ObjectSidebar& sidebar) + : wxChoice(parent, wxID_ANY, wxDefaultPosition, wxDefaultSize, strings), + m_Sidebar(sidebar) + { + SetSelection(0); + } + + void OnSelect(wxCommandEvent& evt) + { + m_Sidebar.SetObjectFilter(evt.GetSelection()); + } +private: + ObjectSidebar& m_Sidebar; + DECLARE_EVENT_TABLE(); +}; +BEGIN_EVENT_TABLE(ObjectChoiceCtrl, wxChoice) + EVT_CHOICE(wxID_ANY, ObjectChoiceCtrl::OnSelect) +END_EVENT_TABLE(); + ////////////////////////////////////////////////////////////////////////// -ObjectSidebar::ObjectSidebar(wxWindow* parent) -: Sidebar(parent), m_BottomBar(NULL) +struct ObjectSidebarImpl { - m_ObjectListBox = new ObjectSelectListBox(this); - m_MainSizer->Add(m_ObjectListBox, wxSizerFlags().Proportion(1).Expand()); - + ObjectSidebarImpl() : m_BottomBar(NULL), m_ObjectListBox(NULL) { } + wxWindow* m_BottomBar; + wxListBox* m_ObjectListBox; + std::vector m_Objects; +}; + +ObjectSidebar::ObjectSidebar(wxWindow* parent) +: Sidebar(parent), p(new ObjectSidebarImpl()) +{ + wxArrayString strings; + strings.Add(_("Entities")); + strings.Add(_("Actors (all)")); + m_MainSizer->Add(new ObjectChoiceCtrl(this, strings, *this), wxSizerFlags().Expand()); + + p->m_ObjectListBox = new ObjectSelectListBox(this); + m_MainSizer->Add(p->m_ObjectListBox, wxSizerFlags().Proportion(1).Expand()); +} + +ObjectSidebar::~ObjectSidebar() +{ + delete p; } wxWindow* ObjectSidebar::GetBottomBar(wxWindow* WXUNUSED(parent)) { - if (m_BottomBar) - return m_BottomBar; + if (p->m_BottomBar) + return p->m_BottomBar; // m_BottomBar = new ObjectBottomBar(parent); - return m_BottomBar; + return p->m_BottomBar; } void ObjectSidebar::OnFirstDisplay() { - AtlasMessage::qGetEntitiesList qry; + AtlasMessage::qGetObjectsList qry; qry.Post(); - for (std::vector::iterator it = qry.entities.begin(); it != qry.entities.end(); ++it) + p->m_Objects = qry.objects; + SetObjectFilter(0); +} + +void ObjectSidebar::SetObjectFilter(int type) +{ + p->m_ObjectListBox->Freeze(); + p->m_ObjectListBox->Clear(); + for (std::vector::iterator it = p->m_Objects.begin(); it != p->m_Objects.end(); ++it) { - wxString id = it->id.c_str(); - wxString name = it->name.c_str(); - m_ObjectListBox->Append(name, new wxStringClientData(id)); + if (it->type == type) + { + wxString id = it->id.c_str(); + wxString name = it->name.c_str(); + p->m_ObjectListBox->Append(name, new wxStringClientData(id)); + } } + p->m_ObjectListBox->Thaw(); } ////////////////////////////////////////////////////////////////////////// diff --git a/source/tools/atlas/AtlasUI/ScenarioEditor/Sections/Object/Object.h b/source/tools/atlas/AtlasUI/ScenarioEditor/Sections/Object/Object.h index ad3fa7fbf4..3c93025345 100644 --- a/source/tools/atlas/AtlasUI/ScenarioEditor/Sections/Object/Object.h +++ b/source/tools/atlas/AtlasUI/ScenarioEditor/Sections/Object/Object.h @@ -1,17 +1,19 @@ #include "../Common/Sidebar.h" +struct ObjectSidebarImpl; class ObjectSidebar : public Sidebar { public: ObjectSidebar(wxWindow* parent); + ~ObjectSidebar(); wxWindow* GetBottomBar(wxWindow* parent); + void SetObjectFilter(int type); protected: void OnFirstDisplay(); private: - wxWindow* m_BottomBar; - wxListBox* m_ObjectListBox; + ObjectSidebarImpl* p; }; class ObjectBottomBar : public wxPanel diff --git a/source/tools/atlas/AtlasUI/ScenarioEditor/Tools/PlaceObject.cpp b/source/tools/atlas/AtlasUI/ScenarioEditor/Tools/PlaceObject.cpp index 091731a21c..bbd9853b24 100644 --- a/source/tools/atlas/AtlasUI/ScenarioEditor/Tools/PlaceObject.cpp +++ b/source/tools/atlas/AtlasUI/ScenarioEditor/Tools/PlaceObject.cpp @@ -29,9 +29,9 @@ public: + (m_ScreenPos.type1.y-m_Target.type1.y)*(m_ScreenPos.type1.y-m_Target.type1.y); bool useTarget = (dragDistSq >= 16*16); if (preview) - POST_MESSAGE(EntityPreview(m_ObjectID.c_str(), m_ObjPos, useTarget, m_Target, g_DefaultAngle)); + POST_MESSAGE(ObjectPreview(m_ObjectID.c_str(), m_ObjPos, useTarget, m_Target, g_DefaultAngle)); else - POST_COMMAND(CreateEntity, (m_ObjectID.c_str(), m_ObjPos, useTarget, m_Target, g_DefaultAngle)); + POST_COMMAND(CreateObject,(m_ObjectID.c_str(), m_ObjPos, useTarget, m_Target, g_DefaultAngle)); } virtual void Init(void* initData) @@ -60,7 +60,7 @@ public: * Mouse move -> if moved > [limit], rotate unit to face mouse; else default orientation * Left mouse release -> finalise placement of object on map - * Scroll wheel -> rotate default orientation + * Page up/down -> rotate default orientation * Escape -> cancel placement tool diff --git a/source/tools/atlas/GameInterface/Handlers/ObjectHandlers.cpp b/source/tools/atlas/GameInterface/Handlers/ObjectHandlers.cpp index adfa17a3c0..ef844fcc4a 100644 --- a/source/tools/atlas/GameInterface/Handlers/ObjectHandlers.cpp +++ b/source/tools/atlas/GameInterface/Handlers/ObjectHandlers.cpp @@ -10,6 +10,7 @@ #include "graphics/Unit.h" #include "graphics/UnitManager.h" #include "graphics/Model.h" +#include "graphics/ObjectManager.h" #include "maths/Matrix3D.h" #include "maths/MathUtil.h" #include "ps/CLogger.h" @@ -20,18 +21,41 @@ namespace AtlasMessage { -QUERYHANDLER(GetEntitiesList) +static bool SortObjectsList(const sObjectsListItem& a, const sObjectsListItem& b) +{ + return a.name < b.name; +} + +QUERYHANDLER(GetObjectsList) { - std::vector names; - g_EntityTemplateCollection.getBaseEntityNames(names); - for (std::vector::iterator it = names.begin(); it != names.end(); ++it) { - //CBaseEntity* baseent = g_EntityTemplateCollection.getTemplate(*it); - sEntitiesListItem e; - e.id = *it; - e.name = *it; //baseent->m_Tag - msg->entities.push_back(e); + std::vector names; + g_EntityTemplateCollection.getBaseEntityNames(names); + for (std::vector::iterator it = names.begin(); it != names.end(); ++it) + { + //CBaseEntity* baseent = g_EntityTemplateCollection.getTemplate(*it); + sObjectsListItem e; + e.id = L"(e) " + *it; + e.name = *it; //baseent->m_Tag + e.type = 0; + msg->objects.push_back(e); + } } + + { + std::vector names; + //g_ObjMan.GetPropObjectNames(names); + g_ObjMan.GetAllObjectNames(names); + for (std::vector::iterator it = names.begin(); it != names.end(); ++it) + { + sObjectsListItem e; + e.id = L"(n) " + CStrW(*it); + e.name = CStrW(*it).AfterFirst(/*L"props/"*/ L"actors/"); + e.type = 1; + msg->objects.push_back(e); + } + } + std::sort(msg->objects.begin(), msg->objects.end(), SortObjectsList); } @@ -104,7 +128,27 @@ static CVector3D GetUnitPos(const Position& pos) return vec; } -MESSAGEHANDLER(EntityPreview) +static bool ParseObjectName(const std::wstring& obj, bool& isEntity, std::wstring& name) +{ + if (obj.substr(0, 4) == L"(e) ") + { + isEntity = true; + name = obj.substr(4); + return true; + } + else if (obj.substr(0, 4) == L"(n) ") + { + isEntity = false; + name = obj.substr(4); + return true; + } + else + { + return false; + } +} + +MESSAGEHANDLER(ObjectPreview) { if (msg->id != g_PreviewUnitID) { @@ -116,18 +160,27 @@ MESSAGEHANDLER(EntityPreview) g_PreviewUnit = NULL; } - if (msg->id.length()) + bool isEntity; + std::wstring name; + if (ParseObjectName(msg->id, isEntity, name)) { // Create new unit - CBaseEntity* base = g_EntityTemplateCollection.getTemplate(msg->id); - if (base) // (ignore errors) + if (isEntity) { - g_PreviewUnit = g_UnitMan.CreateUnit(base->m_actorName, NULL); - // TODO: set player (for colour) - // TODO: variations + CBaseEntity* base = g_EntityTemplateCollection.getTemplate(name); + if (base) // (ignore errors) + { + g_PreviewUnit = g_UnitMan.CreateUnit(base->m_actorName, NULL); + // TODO: set player (for colour) + // TODO: variations + } + } + else + { + g_PreviewUnit = g_UnitMan.CreateUnit(name, NULL); } - } + g_PreviewUnitID = msg->id; } @@ -161,7 +214,7 @@ MESSAGEHANDLER(EntityPreview) } } -BEGIN_COMMAND(CreateEntity) +BEGIN_COMMAND(CreateObject) CVector3D m_Pos; float m_Angle; @@ -190,21 +243,50 @@ BEGIN_COMMAND(CreateEntity) void Redo() { - CBaseEntity* base = g_EntityTemplateCollection.getTemplate(d->id); - if (! base) - LOG(ERROR, LOG_CATEGORY, "Failed to load entity template '%ls'", d->id.c_str()); - else + bool isEntity; + std::wstring name; + if (ParseObjectName(d->id, isEntity, name)) { - HEntity ent = g_EntityManager.create(base, m_Pos, m_Angle); + if (isEntity) + { + CBaseEntity* base = g_EntityTemplateCollection.getTemplate(name); + if (! base) + LOG(ERROR, LOG_CATEGORY, "Failed to load entity template '%ls'", name.c_str()); + else + { + HEntity ent = g_EntityManager.create(base, m_Pos, m_Angle); - if (! ent) - LOG(ERROR, LOG_CATEGORY, "Failed to create entity of type '%ls'", d->id.c_str()); + if (! ent) + LOG(ERROR, LOG_CATEGORY, "Failed to create entity of type '%ls'", name.c_str()); + else + { + // TODO: proper player ID + ent->SetPlayer(g_Game->GetLocalPlayer()); + + ent->m_actor->SetID(m_ID); + } + } + } else { - // TODO: proper player ID - ent->SetPlayer(g_Game->GetLocalPlayer()); + CUnit* unit = g_UnitMan.CreateUnit(name, NULL); + if (! unit) + LOG(ERROR, LOG_CATEGORY, "Failed to load nonentity actor '%ls'", name.c_str()); + else + { + unit->SetID(m_ID); - ent->m_actor->SetID(m_ID); + float s = sin(m_Angle); + float c = cos(m_Angle); + + CMatrix3D m; + m._11 = -c; m._12 = 0.0f; m._13 = -s; m._14 = m_Pos.X; + m._21 = 0.0f; m._22 = 1.0f; m._23 = 0.0f; m._24 = m_Pos.Y; + m._31 = s; m._32 = 0.0f; m._33 = -c; m._34 = m_Pos.Z; + m._41 = 0.0f; m._42 = 0.0f; m._43 = 0.0f; m._44 = 1.0f; + unit->GetModel()->SetTransform(m); + + } } } } @@ -212,11 +294,19 @@ BEGIN_COMMAND(CreateEntity) void Undo() { CUnit* unit = g_UnitMan.FindByID(m_ID); - if (unit && unit->GetEntity()) - unit->GetEntity()->kill(); + if (unit) + { + if (unit->GetEntity()) + unit->GetEntity()->kill(); + else + { + g_UnitMan.RemoveUnit(unit); + delete unit; + } + } } -END_COMMAND(CreateEntity) +END_COMMAND(CreateObject) QUERYHANDLER(SelectObject) diff --git a/source/tools/atlas/GameInterface/Messages.h b/source/tools/atlas/GameInterface/Messages.h index 21b23643d2..e2f24cf282 100644 --- a/source/tools/atlas/GameInterface/Messages.h +++ b/source/tools/atlas/GameInterface/Messages.h @@ -87,18 +87,18 @@ QUERY(GetTerrainGroupPreviews, ////////////////////////////////////////////////////////////////////////// -struct sEntitiesListItem +struct sObjectsListItem { std::wstring id; std::wstring name; - // ... + int type; // 0 = entity, 1 = actor }; -QUERY(GetEntitiesList, +QUERY(GetObjectsList, , // no inputs - ((std::vector, entities)) + ((std::vector, objects)) ); -MESSAGE(EntityPreview, +MESSAGE(ObjectPreview, ((std::wstring, id)) // or empty string => disable ((Position, pos)) ((bool, usetarget)) // true => use 'target' for orientation; false => use 'angle' @@ -106,7 +106,7 @@ MESSAGE(EntityPreview, ((float, angle)) ); -COMMAND(CreateEntity, NOMERGE, +COMMAND(CreateObject, NOMERGE, ((std::wstring, id)) ((Position, pos)) ((bool, usetarget)) // true => use 'target' for orientation; false => use 'angle'