From acb1721e94a49a4941bb11dfc2f832c3848aa204 Mon Sep 17 00:00:00 2001 From: neoraider Date: Fri, 8 Feb 2008 21:21:01 +0000 Subject: zoomedit: Implemented Rotate tool; added simple gates. --- Level.h | 2 ++ LevelObject.h | 3 +++ Makefile.am | 2 +- Makefile.in | 19 ++++++++++++-- PlayerStart.h | 2 +- Portal.h | 73 ++++++++++++++++++++++++++++++++++++++++++++++++++++++ Renderer.cpp | 41 +++++++++++++++++++++++++++++- Renderer.h | 4 ++- Room.h | 21 ++++++++++++++++ SidebarManager.cpp | 4 ++- SidebarManager.h | 2 ++ ToolGrab.cpp | 2 +- ToolRotate.cpp | 70 +++++++++++++++++++++++++++++++++++++++++++++++++++ ToolRotate.h | 56 +++++++++++++++++++++++++++++++++++++++++ Vertex.cpp | 22 ++++++++++++++++ Vertex.h | 5 ++++ 16 files changed, 320 insertions(+), 8 deletions(-) create mode 100644 Portal.h create mode 100644 ToolRotate.cpp create mode 100644 ToolRotate.h diff --git a/Level.h b/Level.h index 74e835d..ede34db 100644 --- a/Level.h +++ b/Level.h @@ -5,12 +5,14 @@ #include "LevelObject.h" #include "SharedPtr.h" #include "PlayerStart.h" +#include "Portal.h" #include class Level : public std::vector > { public: Level() { push_back(SharedPtr(new PlayerStart())); + push_back(SharedPtr(new Portal(2, 2, 0.4f))); } }; diff --git a/LevelObject.h b/LevelObject.h index 5dcdd74..4cb56a4 100644 --- a/LevelObject.h +++ b/LevelObject.h @@ -13,6 +13,9 @@ class LevelObject : public Object { virtual int getPriority() const = 0; virtual void move(float x, float y) {} + virtual void rotate(float a) {} + + virtual Vertex getCenter() const {return Vertex();} }; #endif /*LEVELOBJECT_H_*/ diff --git a/Makefile.am b/Makefile.am index 474e944..946d987 100644 --- a/Makefile.am +++ b/Makefile.am @@ -5,6 +5,6 @@ zoomedit_SOURCES = zoomedit.cpp UIManager.cpp Renderer.cpp Vertex.cpp \ Window.cpp SidebarView.cpp SidebarAdd.cpp Drawer.cpp \ EditManager.cpp FileManager.cpp SidebarToolbox.cpp \ ToolSelector.cpp ToolAddPolygon.cpp ToolAddRect.cpp \ - ToolGrab.cpp Vertex3d.cpp + ToolGrab.cpp ToolRotate.cpp Vertex3d.cpp zoomedit_CPPFLAGS = @GTK_CFLAGS@ @GTKGLEXT_CFLAGS@ @libxml2_CFLAGS@ zoomedit_LDADD = @GTK_LIBS@ @GTKGLEXT_LIBS@ @libxml2_LIBS@ \ No newline at end of file diff --git a/Makefile.in b/Makefile.in index 4db79b8..3c2feed 100644 --- a/Makefile.in +++ b/Makefile.in @@ -62,7 +62,7 @@ am_zoomedit_OBJECTS = zoomedit-zoomedit.$(OBJEXT) \ zoomedit-ToolSelector.$(OBJEXT) \ zoomedit-ToolAddPolygon.$(OBJEXT) \ zoomedit-ToolAddRect.$(OBJEXT) zoomedit-ToolGrab.$(OBJEXT) \ - zoomedit-Vertex3d.$(OBJEXT) + zoomedit-ToolRotate.$(OBJEXT) zoomedit-Vertex3d.$(OBJEXT) zoomedit_OBJECTS = $(am_zoomedit_OBJECTS) zoomedit_DEPENDENCIES = DEFAULT_INCLUDES = -I.@am__isrc@ @@ -190,7 +190,7 @@ zoomedit_SOURCES = zoomedit.cpp UIManager.cpp Renderer.cpp Vertex.cpp \ Window.cpp SidebarView.cpp SidebarAdd.cpp Drawer.cpp \ EditManager.cpp FileManager.cpp SidebarToolbox.cpp \ ToolSelector.cpp ToolAddPolygon.cpp ToolAddRect.cpp \ - ToolGrab.cpp Vertex3d.cpp + ToolGrab.cpp ToolRotate.cpp Vertex3d.cpp zoomedit_CPPFLAGS = @GTK_CFLAGS@ @GTKGLEXT_CFLAGS@ @libxml2_CFLAGS@ zoomedit_LDADD = @GTK_LIBS@ @GTKGLEXT_LIBS@ @libxml2_LIBS@ @@ -297,6 +297,7 @@ distclean-compile: @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/zoomedit-ToolAddPolygon.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/zoomedit-ToolAddRect.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/zoomedit-ToolGrab.Po@am__quote@ +@AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/zoomedit-ToolRotate.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/zoomedit-ToolSelector.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/zoomedit-Triangle.Po@am__quote@ @AMDEP_TRUE@@am__include@ @am__quote@./$(DEPDIR)/zoomedit-UIManager.Po@am__quote@ @@ -628,6 +629,20 @@ zoomedit-ToolGrab.obj: ToolGrab.cpp @AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@ @am__fastdepCXX_FALSE@ $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(zoomedit_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o zoomedit-ToolGrab.obj `if test -f 'ToolGrab.cpp'; then $(CYGPATH_W) 'ToolGrab.cpp'; else $(CYGPATH_W) '$(srcdir)/ToolGrab.cpp'; fi` +zoomedit-ToolRotate.o: ToolRotate.cpp +@am__fastdepCXX_TRUE@ $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(zoomedit_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT zoomedit-ToolRotate.o -MD -MP -MF $(DEPDIR)/zoomedit-ToolRotate.Tpo -c -o zoomedit-ToolRotate.o `test -f 'ToolRotate.cpp' || echo '$(srcdir)/'`ToolRotate.cpp +@am__fastdepCXX_TRUE@ mv -f $(DEPDIR)/zoomedit-ToolRotate.Tpo $(DEPDIR)/zoomedit-ToolRotate.Po +@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='ToolRotate.cpp' object='zoomedit-ToolRotate.o' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCXX_FALSE@ $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(zoomedit_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o zoomedit-ToolRotate.o `test -f 'ToolRotate.cpp' || echo '$(srcdir)/'`ToolRotate.cpp + +zoomedit-ToolRotate.obj: ToolRotate.cpp +@am__fastdepCXX_TRUE@ $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(zoomedit_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT zoomedit-ToolRotate.obj -MD -MP -MF $(DEPDIR)/zoomedit-ToolRotate.Tpo -c -o zoomedit-ToolRotate.obj `if test -f 'ToolRotate.cpp'; then $(CYGPATH_W) 'ToolRotate.cpp'; else $(CYGPATH_W) '$(srcdir)/ToolRotate.cpp'; fi` +@am__fastdepCXX_TRUE@ mv -f $(DEPDIR)/zoomedit-ToolRotate.Tpo $(DEPDIR)/zoomedit-ToolRotate.Po +@AMDEP_TRUE@@am__fastdepCXX_FALSE@ source='ToolRotate.cpp' object='zoomedit-ToolRotate.obj' libtool=no @AMDEPBACKSLASH@ +@AMDEP_TRUE@@am__fastdepCXX_FALSE@ DEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@ +@am__fastdepCXX_FALSE@ $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(zoomedit_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o zoomedit-ToolRotate.obj `if test -f 'ToolRotate.cpp'; then $(CYGPATH_W) 'ToolRotate.cpp'; else $(CYGPATH_W) '$(srcdir)/ToolRotate.cpp'; fi` + zoomedit-Vertex3d.o: Vertex3d.cpp @am__fastdepCXX_TRUE@ $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(zoomedit_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT zoomedit-Vertex3d.o -MD -MP -MF $(DEPDIR)/zoomedit-Vertex3d.Tpo -c -o zoomedit-Vertex3d.o `test -f 'Vertex3d.cpp' || echo '$(srcdir)/'`Vertex3d.cpp @am__fastdepCXX_TRUE@ mv -f $(DEPDIR)/zoomedit-Vertex3d.Tpo $(DEPDIR)/zoomedit-Vertex3d.Po diff --git a/PlayerStart.h b/PlayerStart.h index d5c10cd..b40b49e 100644 --- a/PlayerStart.h +++ b/PlayerStart.h @@ -11,7 +11,7 @@ class PlayerStart : public Vertex3d, public LevelObject { return (v.distanceSq(Vertex(getX(), getZ())) < 0.09); } - virtual int getPriority() const {return 1;} + virtual int getPriority() const {return 10;} virtual const char* getType() const { return "PlayerStart"; diff --git a/Portal.h b/Portal.h new file mode 100644 index 0000000..a4cb349 --- /dev/null +++ b/Portal.h @@ -0,0 +1,73 @@ +#ifndef PORTAL_H_ +#define PORTAL_H_ + +#include "LevelObject.h" +#include "Polygon.h" +#include + + +class Portal : public LevelObject { + private: + float width, height, thickness; + Vertex pos; + float orient; + + Polygon createPolygon() const { + Polygon p; + + float s = sinf(orient); + float c = cosf(orient); + float x = width/2*c; + float y = width/2*s; + float ts = thickness/2*s; + float tc = thickness/2*c; + + p.push_back(Vertex(pos.getX()-x-ts, pos.getY()-y+tc)); + p.push_back(Vertex(pos.getX()-x+ts, pos.getY()-y-tc)); + p.push_back(Vertex(pos.getX()+x+ts, pos.getY()+y-tc)); + p.push_back(Vertex(pos.getX()+x-ts, pos.getY()+y+tc)); + + return p; + } + + public: + Portal(float width, float height, float thickness) { + this->width = width; + this->height = height; + this->thickness = thickness; + + orient = 0; + } + + float getWidth() const {return width;} + float getHeight() const {return height;} + float getThickness() const {return thickness;} + + const Vertex& getPosition() const {return pos;} + void setPosition(Vertex v) {pos = v;} + + float getOrientation() const {return orient;} + void setOrientation(float orient) {this->orient = orient;} + + virtual bool hit(const Vertex &v) const {return createPolygon().contains(v);} + virtual int getPriority() const {return 1;} + + virtual const char* getType() const { + return "Portal"; + } + + virtual void move(float x, float y) { + pos.setX(pos.getX()+x); + pos.setY(pos.getY()+y); + } + + virtual void rotate(float a) { + orient = fmodf(orient+a, 2*M_PI); + } + + virtual Vertex getCenter() const { + return pos; + } +}; + +#endif /*PORTAL_H_*/ diff --git a/Renderer.cpp b/Renderer.cpp index 98859d9..c8ecac2 100644 --- a/Renderer.cpp +++ b/Renderer.cpp @@ -86,6 +86,8 @@ void Renderer::renderObject(const LevelObject &object, bool selected, bool highl renderRoom(*(Room*)&object, selected, highlighted, scale); else if(object.isOfType("PlayerStart")) renderPlayerStart(*(PlayerStart*)&object, selected, highlighted, scale); + else if(object.isOfType("Portal")) + renderPortal(*(Portal*)&object, selected, highlighted, scale); } void Renderer::renderRoom(const Room &room, bool selected, bool highlighted, float scale) { @@ -125,13 +127,50 @@ void Renderer::renderPlayerStart(const PlayerStart &start, bool selected, bool h glColor4f(0.0f, 0.7f, 0.7f, 0.7f); glLineWidth(1.0f); } - drawCircle(Vertex(start.getX(), start.getZ()), 0.3f, 128); + drawCircle(Vertex(start.getX(), start.getZ()), 0.3f); glLineWidth(2.0f); glColor4f(1.0f, 1.0f, 1.0f, 0.7f); drawCross(Vertex(start.getX(), start.getZ()), 0.5f/sqrtf(scale)); } +void Renderer::renderPortal(const Portal &portal, bool selected, bool highlighted, float scale) { + if(selected) { + glColor4f(1.0f, 1.0f, 1.0f, 0.9f); + glLineWidth(2.0f); + } + else if(highlighted) { + glColor4f(0.0f, 0.7f, 0.7f, 0.7f); + glLineWidth(2.0f); + } + else { + glColor4f(0.0f, 0.7f, 0.7f, 0.7f); + glLineWidth(1.0f); + } + + float s = sinf(portal.getOrientation()); + float c = cosf(portal.getOrientation()); + float x = portal.getWidth()/2*c; + float y = portal.getWidth()/2*s; + float ts = portal.getThickness()/2*s; + float tc = portal.getThickness()/2*c; + + glBegin(GL_LINES); + + glVertex2f(portal.getPosition().getX()-x+ts, portal.getPosition().getY()-y-tc); + glVertex2f(portal.getPosition().getX()-x-ts, portal.getPosition().getY()-y+tc); + + glVertex2f(portal.getPosition().getX()+x+ts, portal.getPosition().getY()+y-tc); + glVertex2f(portal.getPosition().getX()+x-ts, portal.getPosition().getY()+y+tc); + + glColor4f(1.0f, 1.0f, 1.0f, 0.9f); + + glVertex2f(portal.getPosition().getX()-x, portal.getPosition().getY()-y); + glVertex2f(portal.getPosition().getX()+x, portal.getPosition().getY()+y); + + glEnd(); +} + void Renderer::render(const Level &level, const Rectangle &rect, float scale) { glClear(GL_COLOR_BUFFER_BIT); diff --git a/Renderer.h b/Renderer.h index 76221b8..38c822d 100644 --- a/Renderer.h +++ b/Renderer.h @@ -7,6 +7,7 @@ #include "Level.h" #include "Room.h" #include "PlayerStart.h" +#include "Portal.h" class Renderer { @@ -18,13 +19,14 @@ class Renderer { protected: void fillPolygon(const Polygon &polygon); void drawPolygon(const Polygon &polygon, bool close = true); - void drawCircle(const Vertex &m, float r, int n); + void drawCircle(const Vertex &m, float r, int n = 64); void drawCross(const Vertex &m, float r); void renderObject(const LevelObject &object, bool selected, bool highlighted, float scale); void renderRoom(const Room &room, bool selected, bool highlighted, float scale); void renderPlayerStart(const PlayerStart &start, bool selected, bool highlighted, float scale); + void renderPortal(const Portal &portal, bool selected, bool highlighted, float scale); public: Renderer(EditManager *editManager) { diff --git a/Room.h b/Room.h index 8e72c61..1cac5d9 100644 --- a/Room.h +++ b/Room.h @@ -35,6 +35,27 @@ class Room : public Polygon, public LevelObject { v->setY(v->getY()+y); } } + + virtual void rotate(float a) { + Vertex z = getCenter(); + float s = sinf(a); + float c = cosf(a); + + for(iterator v = begin(); v != end(); v++) { + *v -= z; + v->setLocation(c*v->getX() - s*v->getY(), c*v->getY() + s*v->getX()); + *v += z; + } + } + + virtual Vertex getCenter() const { + Vertex ret; + + for(const_iterator v = begin(); v != end(); v++) + ret += *v; + + return ret / size(); + } }; #endif /*ROOM_H_*/ diff --git a/SidebarManager.cpp b/SidebarManager.cpp index 4cf0e36..15bff81 100644 --- a/SidebarManager.cpp +++ b/SidebarManager.cpp @@ -4,7 +4,8 @@ SidebarManager::SidebarManager(Window *window) : sidebarToolbox(window), toolGrab(&window->getEditManager()), - toolAddRect(&window->getEditManager()), toolAddPolygon(&window->getEditManager()) + toolRotate(&window->getEditManager()), toolAddRect(&window->getEditManager()), + toolAddPolygon(&window->getEditManager()) { this->window = window; activeSidebar = NULL; @@ -29,6 +30,7 @@ SidebarManager::SidebarManager(Window *window) gtk_container_add(GTK_CONTAINER(scrolledWindow), viewport); sidebarToolbox.addTool(&toolGrab); + sidebarToolbox.addTool(&toolRotate); sidebarToolbox.addTool(&toolAddRect); sidebarToolbox.addTool(&toolAddPolygon); diff --git a/SidebarManager.h b/SidebarManager.h index b8deb72..4f1cd45 100644 --- a/SidebarManager.h +++ b/SidebarManager.h @@ -6,6 +6,7 @@ #include "SidebarToolbox.h" #include "EditManager.h" #include "ToolGrab.h" +#include "ToolRotate.h" #include "ToolAddRect.h" #include "ToolAddPolygon.h" @@ -24,6 +25,7 @@ class SidebarManager { Window *window; ToolGrab toolGrab; + ToolRotate toolRotate; ToolAddRect toolAddRect; ToolAddPolygon toolAddPolygon; diff --git a/ToolGrab.cpp b/ToolGrab.cpp index ed27c05..54543fd 100644 --- a/ToolGrab.cpp +++ b/ToolGrab.cpp @@ -20,7 +20,7 @@ void ToolGrab::activate() { } bool ToolGrab::buttonPress(unsigned int button) { - if(button != 1) + if(button != 1 || !editManager->getHoveredObject()) return false; pressed = true; diff --git a/ToolRotate.cpp b/ToolRotate.cpp new file mode 100644 index 0000000..6cd7626 --- /dev/null +++ b/ToolRotate.cpp @@ -0,0 +1,70 @@ +#include "ToolRotate.h" + +ToolRotate::ToolRotate(EditManager *editManager) : sidebar(editManager) { + this->editManager = editManager; + + pressed = false; + + image = gtk_image_new_from_stock(GTK_STOCK_MISSING_IMAGE, GTK_ICON_SIZE_BUTTON); + g_object_ref_sink(G_OBJECT(image)); +} + +ToolRotate::~ToolRotate() { + g_object_unref(G_OBJECT(image)); +} + +void ToolRotate::activate() { + pressed = false; + editManager->highlightHoveredObject(); + editManager->setSelectedObject(NULL); +} + +bool ToolRotate::buttonPress(unsigned int button) { + if(button != 1 || !editManager->getHoveredObject()) + return false; + + pressed = true; + Vertex v = *editManager->getHoveredVertex() - editManager->getHoveredObject()->getCenter(); + angle = atan2(v.getY(), v.getX()); + + editManager->setSelectedObject(editManager->getHoveredObject()); + + editManager->redraw(); + sidebar.update(); + + return true; +} + +bool ToolRotate::buttonRelease(unsigned int button) { + if(button != 1) + return false; + + pressed = false; + + editManager->setSelectedObject(NULL); + + editManager->redraw(); + sidebar.update(); + + return true; +} + +bool ToolRotate::motion() { + if(!pressed) { + editManager->highlightHoveredObject(); + return true; + } + + if(!editManager->getHoveredVertex()) + return false; + + Vertex v = *editManager->getHoveredVertex() - editManager->getSelectedObject()->getCenter(); + + float a = atan2(v.getY(), v.getX()); + + editManager->getSelectedObject()->rotate(a-angle); + + angle = a; + + return false; +} diff --git a/ToolRotate.h b/ToolRotate.h new file mode 100644 index 0000000..419eb6a --- /dev/null +++ b/ToolRotate.h @@ -0,0 +1,56 @@ +#ifndef TOOLROTATE_H_ +#define TOOLROTATE_H_ + +#include "Tool.h" +#include "SidebarView.h" + +class ToolRotate : public Tool, EventHandler { + private: + GtkWidget *image; + + EditManager *editManager; + + SidebarView sidebar; + + bool pressed; + float angle; + + // prevent shallow copy + ToolRotate(const ToolRotate &t); + const ToolRotate& operator=(const ToolRotate &t); + public: + ToolRotate(EditManager *editManager); + virtual ~ToolRotate(); + + virtual void activate(); + + virtual const char *getType() const { + return "ToolRotate"; + } + + virtual const char *getName() const { + return "Rotate"; + } + + virtual bool isSensitive() { + return TRUE; + } + + virtual GtkWidget *getImage() { + return image; + } + + virtual EventHandler* getEventHandler() { + return this; + } + + virtual bool buttonPress(unsigned int button); + virtual bool buttonRelease(unsigned int button); + virtual bool motion(); + + virtual Sidebar* getSidebar() { + return &sidebar; + } +}; + +#endif /*TOOLROTATE_H_*/ diff --git a/Vertex.cpp b/Vertex.cpp index 7e2528f..6e1f26b 100644 --- a/Vertex.cpp +++ b/Vertex.cpp @@ -18,6 +18,14 @@ Vertex Vertex::operator-(const Vertex &v) const { return Vertex(x - v.x, y - v.y); } +Vertex Vertex::operator*(float f) const { + return Vertex(x*f, y*f); +} + +Vertex Vertex::operator/(float f) const { + return Vertex(x/f, y/f); +} + Vertex& Vertex::operator+=(const Vertex &v) { x += v.x; y += v.y; @@ -31,3 +39,17 @@ Vertex& Vertex::operator-=(const Vertex &v) { return *this; } + +Vertex& Vertex::operator*=(float f) { + x *= f; + y *= f; + + return *this; +} + +Vertex& Vertex::operator/=(float f) { + x /= f; + y /= f; + + return *this; +} diff --git a/Vertex.h b/Vertex.h index c367bb2..5f0db76 100644 --- a/Vertex.h +++ b/Vertex.h @@ -22,9 +22,14 @@ class Vertex { Vertex operator+(const Vertex &v) const; Vertex operator-(const Vertex &v) const; + Vertex operator*(float f) const; + Vertex operator/(float f) const; Vertex& operator+=(const Vertex &v); Vertex& operator-=(const Vertex &v); + Vertex& operator*=(float f); + Vertex& operator/=(float f); + }; #endif /*VERTEX_H_*/ -- cgit v1.2.3