#include "DataModelV2/PartInstance.h" #include "Globals.h" #include "../../Renderer.h" #include #include PartInstance::PartInstance(void) { PVInstance::PVInstance(); glList = glGenLists(1); name = "Unnamed PVItem"; className = "Part"; canCollide = true; anchored = false; size = Vector3(2,1,4); setCFrame(CoordinateFrame(Vector3(0,0,0))); color = Color3::gray(); velocity = Vector3(0,0,0); rotVelocity = Vector3(0,0,0); top = Enum::SurfaceType::Smooth; front = Enum::SurfaceType::Smooth; right = Enum::SurfaceType::Smooth; back = Enum::SurfaceType::Smooth; left = Enum::SurfaceType::Smooth; bottom = Enum::SurfaceType::Smooth; shape = Enum::Shape::Block; } Vector3 PartInstance::getVelocity() { return velocity; } Vector3 PartInstance::getRotVelocity() { return rotVelocity; } void PartInstance::setVelocity(Vector3 v) { velocity = v; } void PartInstance::setRotVelocity(Vector3 v) { rotVelocity = v; } void PartInstance::postRender(RenderDevice *rd) { if(!nameShown) return; G3D::GFontRef fnt = NULL; Instance* dm = parent; while(dm != NULL) { if(DataModelInstance* mod = dynamic_cast(dm)) { fnt = mod->font; break; } dm = dm->getParent(); } if(!fnt.isNull()) { Vector3 gamepoint = position + Vector3(0,1.5,0); Vector3 camerapoint = rd->getCameraToWorldMatrix().translation; float distance = pow(pow((double)gamepoint.x - (double)camerapoint.x, 2) + pow((double)gamepoint.y - (double)camerapoint.y, 2) + pow((double)gamepoint.z - (double)camerapoint.z, 2), 0.5); if(distance < 100 && distance > -100) { if(distance < 0) distance = distance*-1; glDisable(GL_DEPTH_TEST); fnt->draw3D(rd, name, CoordinateFrame(rd->getCameraToWorldMatrix().rotation, gamepoint), 0.03*distance, Color3::yellow(), Color3::black(), G3D::GFont::XALIGN_CENTER, G3D::GFont::YALIGN_CENTER); glEnable(GL_DEPTH_TEST); } } } void PartInstance::setParent(Instance* prnt) { Instance * cparent = getParent(); while(cparent != NULL) { if(WorkspaceInstance* workspace = dynamic_cast(cparent)) { std::cout << "Removed from partarray " << std::endl; workspace->partObjects.erase(std::remove(workspace->partObjects.begin(), workspace->partObjects.end(), this), workspace->partObjects.end()); break; } cparent = cparent->getParent(); } Instance::setParent(prnt); while(parent != NULL) { if(WorkspaceInstance* workspace = dynamic_cast(parent)) { workspace->partObjects.push_back(this); break; } parent = parent->getParent(); } } PartInstance::PartInstance(const PartInstance &oinst) { PVInstance::PVInstance(oinst); glList = glGenLists(1); //name = oinst.name; //className = "Part"; name = oinst.name; canCollide = oinst.canCollide; setParent(oinst.parent); anchored = oinst.anchored; size = oinst.size; setCFrame(oinst.cFrame); color = oinst.color; velocity = oinst.velocity; rotVelocity = oinst.rotVelocity; top = oinst.top; front = oinst.front; right = oinst.right; back = oinst.back; left = oinst.left; bottom = oinst.bottom; shape = oinst.shape; changed = true; } void PartInstance::setSize(Vector3 newSize) { int minsize = 1; int maxsize = 512; changed = true; int sizex = (int)newSize.x; if(sizex <= 0) sizex = 1; if(sizex > 512) sizex = 512; int sizey = (int)newSize.y; if(sizey <= 0) sizey = 1; if(sizey > 512) sizey = 512; int sizez = (int)newSize.z; if(sizez <= 0) sizez = 1; if(sizez > 512) sizez = 512; if(shape != Enum::Shape::Block) { int max = sizex; if(sizey > max) max = sizey; if(sizez > max) max = sizez; sizex = sizey = sizez = max; } size = Vector3(sizex, sizey, sizez); } Vector3 PartInstance::getSize() { return size; } Vector3 PartInstance::getPosition() { return position; } void PartInstance::setShape(Enum::Shape::Value shape) { switch(shape) { case Enum::Shape::Block: this->shape = shape; break; default: this->shape = shape; this->setSize(this->getSize()); } changed = true; } void PartInstance::setPosition(Vector3 pos) { position = pos; cFrame = CoordinateFrame(cFrame.rotation, pos); changed = true; } CoordinateFrame PartInstance::getCFrame() { return cFrame; } void PartInstance::setCFrame(CoordinateFrame coordinateFrame) { cFrame = coordinateFrame; position = coordinateFrame.translation; changed = true; } bool PartInstance::collides(PartInstance * part) { if(shape == Enum::Shape::Block) { if(part->shape == Enum::Shape::Block) return G3D::CollisionDetection::fixedSolidBoxIntersectsFixedSolidBox(getBox(), part->getBox()); else return G3D::CollisionDetection::fixedSolidSphereIntersectsFixedSolidBox(part->getSphere(), getBox()); } else { if(part->shape == Enum::Shape::Block) return G3D::CollisionDetection::fixedSolidSphereIntersectsFixedSolidBox(getSphere(), part->getBox()); else return G3D::CollisionDetection::fixedSolidSphereIntersectsFixedSolidSphere(getSphere(), part->getSphere()); } } Box PartInstance::getBox() { Box box = Box(Vector3(size.x/2, size.y/2, size.z/2) ,Vector3(-size.x/2,-size.y/2,-size.z/2)); CoordinateFrame c = getCFrame(); itemBox = c.toWorldSpace(box); return itemBox; } Sphere PartInstance::getSphere() { Sphere sphere = Sphere(Vector3(0,0,0), size.y/2); CoordinateFrame c = getCFrame(); return sphere; } bool PartInstance::collides(Box box) { return CollisionDetection::fixedSolidBoxIntersectsFixedSolidBox(getBox(), box); } void PartInstance::render(RenderDevice* rd) { if (changed) { changed=false; Vector3 renderSize = size/2; glNewList(glList, GL_COMPILE); renderShape(this->shape, renderSize, color); glEndList(); } rd->setObjectToWorldMatrix(cFrame); glCallList(glList); postRender(rd); } PartInstance::~PartInstance(void) { glDeleteLists(glList, 1); } char pto[512]; char pto2[512]; #include static Enum::Shape::Value strEnum(TCHAR* shape) { if(strcmp("Block", shape) == 0) return Enum::Shape::Block; if(strcmp("Cylinder", shape) == 0) return Enum::Shape::Cylinder; return Enum::Shape::Ball; } static TCHAR* enumStr(int shape) { switch(shape) { case Enum::Shape::Block: return "Block"; case Enum::Shape::Ball: return "Ball"; case Enum::Shape::Cylinder: return "Cylinder"; } return "Block"; } void PartInstance::PropUpdate(LPPROPGRIDITEM &item) { if(strcmp(item->lpszPropName, "Color3") == 0) { color = Color3(GetRValue(item->lpCurValue)/255.0F,GetGValue(item->lpCurValue)/255.0F,GetBValue(item->lpCurValue)/255.0F); changed=true; } if(strcmp(item->lpszPropName, "Anchored") == 0) { anchored= item->lpCurValue == TRUE; changed=true; } else if(strcmp(item->lpszPropName, "Offset") == 0) { std::string str = (LPTSTR)item->lpCurValue; std::vector vect; std::stringstream ss(str); float i; while (ss >> i) { vect.push_back(i); if (ss.peek() == ',') ss.ignore(); } //if(vect.size() != 3) //{ //sprintf(pto, "%g, %g, %g", cFrame.translation.x, cFrame.translation.y, cFrame.translation.z, "what"); //LPCSTR str = LPCSTR(pto); //item->lpCurValue = (LPARAM)str; //} //else if(vect.size() == 3) { Vector3 pos(vect.at(0),vect.at(1),vect.at(2)); setPosition(pos); } } else if(strcmp(item->lpszPropName, "Size") == 0) { std::string str = (LPTSTR)item->lpCurValue; std::vector vect; std::stringstream ss(str); float i; while (ss >> i) { vect.push_back(i); if (ss.peek() == ',') ss.ignore(); } /*if(vect.size() != 3) { sprintf(pto, "%g, %g, %g", cFrame.translation.x, cFrame.translation.y, cFrame.translation.z, "what"); LPCSTR str = LPCSTR(pto); item->lpCurValue = (LPARAM)str; } else*/ if(vect.size() == 3) { Vector3 size(vect.at(0),vect.at(1),vect.at(2)); setSize(size); } } if(strcmp(item->lpszPropName, "Shape") == 0) { printf("%s", enumStr(strEnum((TCHAR*)item->lpCurValue))); setShape(strEnum((TCHAR*)item->lpCurValue)); } else PVInstance::PropUpdate(item); } std::vector PartInstance::getProperties() { std::vector properties = PVInstance::getProperties(); properties.push_back(createPGI( "Properties", "Color3", "The color of the selected part", RGB((color.r*255),(color.g*255),(color.b*255)), PIT_COLOR )); properties.push_back(createPGI( "Item", "Anchored", "Whether the block can move or not", (LPARAM)anchored, PIT_CHECK )); sprintf_s(pto, "%g, %g, %g", position.x, position.y, position.z); properties.push_back(createPGI( "Item", "Offset", "The position of the object in the workspace", (LPARAM)pto, PIT_EDIT )); sprintf_s(pto2, "%g, %g, %g", size.x, size.y, size.z); properties.push_back(createPGI( "Item", "Size", "The position of the object in the workspace", (LPARAM)pto2, PIT_EDIT )); properties.push_back(createPGI( "Item", "Shape", "The shape of the object in the workspace", (LPARAM)enumStr(shape), PIT_COMBO, TEXT("Ball\0Block\0Cylinder\0") )); return properties; }