diff options
Diffstat (limited to 'edit.cpp')
-rw-r--r-- | edit.cpp | 170 |
1 files changed, 170 insertions, 0 deletions
diff --git a/edit.cpp b/edit.cpp new file mode 100644 index 0000000..c54f308 --- /dev/null +++ b/edit.cpp @@ -0,0 +1,170 @@ +#include "edit.h" +#include "level.h" +#include "geometry.h" +#include <stdlib.h> + + +static int editMode = EDIT_MODE_VIEW; + +static ROOM *activeRoom = NULL; +static ROOM *hoveredRoom = NULL; + +static VERTEX hoveredVertex; +static int hasHoveredVertex = 0; + +int getEditMode() { + return editMode; +} + +ROOM *getActiveRoom() { + return activeRoom; +} + +void setActiveRoom(ROOM *room) { + activeRoom = room; + + if(room == NULL) { + editMode = EDIT_MODE_VIEW; + } + else if(editMode == EDIT_MODE_VIEW) { + editMode = EDIT_MODE_SELECTED; + } +} + +VERTEX *getHoveredVertex() { + if(hasHoveredVertex) return &hoveredVertex; + else return NULL; +} + +void setHoveredVertex(VERTEX *v) { + int i; + LEVEL *l; + + if(v) { + hasHoveredVertex = 1; + hoveredVertex = *v; + + l = getLevel(); + hoveredRoom = NULL; + + for(i = 0; i < l->nRooms; i++) { + if(vertexInPolygon(v, &l->rooms[i].polygon)) { + hoveredRoom = &l->rooms[i]; + break; + } + } + } + else { + hasHoveredVertex = 0; + hoveredRoom = NULL; + } +} + +void startAddMode() { + activeRoom = (ROOM*)calloc(1, sizeof(ROOM)); + activeRoom->polygon.nVertices = 0; + activeRoom->polygon.vertices = NULL; + activeRoom->name = (char*)calloc(1, sizeof(unsigned char)); + + editMode = EDIT_MODE_ADD; +} + +void endAddMode() { + editMode = activeRoom ? EDIT_MODE_SELECTED : EDIT_MODE_VIEW; +} + +ROOM *getHoveredRoom() { + return hoveredRoom; +} + +static int isLineOk(LINE *l) { + LEVEL *lvl = getLevel(); + LINE l2; + int i; + + + if(activeRoom) { + for(i = 0; i+2 < activeRoom->polygon.nVertices; i++) { + l2.v1 = activeRoom->polygon.vertices[i]; + l2.v2 = activeRoom->polygon.vertices[i+1]; + + if(lineIntersection(l, &l2, NULL) == INTERSECTION_SEGMENT_SEGMENT) return 0; + } + + if(activeRoom->polygon.nVertices > 1) { + l2.v1 = activeRoom->polygon.vertices[activeRoom->polygon.nVertices-2]; + l2.v2 = activeRoom->polygon.vertices[activeRoom->polygon.nVertices-1]; + if(vertexOnLine(&l->v2, &l2)) return 0; + } + } + + for(i = 0; i < lvl->nRooms; i++) { + if(linePolygonIntersection(l, &lvl->rooms[i].polygon)) + return 0; + } + + return 1; +} + +int isVertexOk(VERTEX *v) { + LEVEL *lvl = getLevel(); + LINE l; + int i; + + for(i = 0; i < lvl->nRooms; i++) { + if(vertexInPolygon(v, &lvl->rooms[i].polygon)) return 0; + } + + if(!(getActiveRoom() && getActiveRoom()->polygon.nVertices)) + return 1; + + l.v1 = getActiveRoom()->polygon.vertices[getActiveRoom()->polygon.nVertices-1]; + l.v2 = *v; + + return isLineOk(&l); +} + + + +int isPolygonOk(POLYGON *polygon) { + LEVEL *lvl = getLevel(); + LINE l, l2; + int i, j; + + if(!polygon->nVertices) return 0; + + for(i = 0; i < lvl->nRooms; i++) { + if(!lvl->rooms[i].polygon.nVertices) continue; + + if(vertexInPolygon(&polygon->vertices[0], &lvl->rooms[i].polygon)) + return 0; + + if(vertexInPolygon(&lvl->rooms[i].polygon.vertices[0], polygon)) + return 0; + } + + if(polygon->nVertices == 1) + return 1; + + for(i = 0; i < polygon->nVertices; i++) { + l.v1 = polygon->vertices[i]; + l.v2 = polygon->vertices[(i+1)%polygon->nVertices]; + + for(j = 0; j < lvl->nRooms; j++) { + if(linePolygonIntersection(&l, &lvl->rooms[j].polygon)) + return 0; + } + + for(j = i+2; j < polygon->nVertices; j++) { + if(i == 0 && j == polygon->nVertices-1) continue; + + l2.v1 = polygon->vertices[j]; + l2.v2 = polygon->vertices[(j+1)%polygon->nVertices]; + + if(lineIntersection(&l, &l2, NULL) == INTERSECTION_SEGMENT_SEGMENT) + return 0; + } + } + + return 1; +} |