From a6a43f1b95bd33990a21fd1a52bff8c4a129d4e9 Mon Sep 17 00:00:00 2001 From: leo Date: Tue, 22 Aug 2000 14:14:07 +0000 Subject: Several changes, see docs/CHANGES.txt for a complete list git-svn-id: http://svn.leocad.org/trunk@103 c7d43263-9d01-0410-8a33-9dba5d9f93d6 --- common/camera.cpp | 6 +- common/globals.cpp | 106 ---------- common/globals.h | 3 - common/library.cpp | 233 ++++++++++++++++++++- common/library.h | 98 ++++++++- common/light.cpp | 2 - common/minifig.cpp | 578 +++++++++++++++++++++++++++++++++++++++++++++++++++++ common/minifig.h | 60 ++++++ common/module.mk | 2 +- common/piece.cpp | 84 +++----- common/piece.h | 10 +- common/project.cpp | 252 ++++++++++++----------- common/project.h | 25 +-- common/system.h | 4 +- common/typedefs.h | 25 +-- 15 files changed, 1154 insertions(+), 334 deletions(-) create mode 100644 common/minifig.cpp create mode 100644 common/minifig.h (limited to 'common') diff --git a/common/camera.cpp b/common/camera.cpp index 1fbf576..17155c4 100644 --- a/common/camera.cpp +++ b/common/camera.cpp @@ -317,7 +317,8 @@ Camera::Camera (float ex, float ey, float ez, float tx, float ty, float tz, Came Camera::~Camera() { - RemoveKeys(); + RemoveKeys (); + delete m_pTarget; } void Camera::Initialize() @@ -593,7 +594,7 @@ void Camera::ChangeKey (unsigned short nTime, bool bAnimation, bool bAddKey, flo newpos->param[2] = param[2]; } -void Camera::Move(unsigned short nTime, bool bAnimation, bool bAddKey, float dx, float dy, float dz) +void Camera::Move (unsigned short nTime, bool bAnimation, bool bAddKey, float dx, float dy, float dz) { if (IsSide()) { @@ -916,7 +917,6 @@ void Camera::MinIntersectDist(LC_CLICKLINE* pLine) return; dist = BoundingBoxIntersectDist (pLine); - if (dist < pLine->mindist) { pLine->mindist = dist; diff --git a/common/globals.cpp b/common/globals.cpp index e57757f..34e4336 100644 --- a/common/globals.cpp +++ b/common/globals.cpp @@ -87,109 +87,3 @@ unsigned char ColorArray[31][4] = { { 51, 51, 51, 255 }, //28 - Edges { 229, 76, 102, 255 }, //29 - Selected { 102, 76, 229, 255 }}; //30 - Focused - -// ========================================================= -// Minifig Wizard options - -MFW_PIECEINFO mfwpieceinfo[] = { - { "3624", "Police Hat", MF_HAT }, - { "3626BP01", "Smiley Face", MF_HEAD }, - { "973", "Plain Torso", MF_TORSO }, - { "3838", "Airtanks", MF_NECK }, - { "976", "Left Arm", MF_ARML }, - { "975", "Right Arm", MF_ARMR }, - { "977", "Hand", MF_HAND }, - { "977", "Hand", MF_HAND }, - { "3899", "Cup", MF_TOOL }, - { "4528", "Frypan", MF_TOOL }, - { "970", "Hips", MF_HIPS }, - { "972", "Left Leg", MF_LEGL }, - { "971", "Right Leg", MF_LEGR }, - { "2599", "Flipper", MF_SHOE }, - { "6120", "Ski", MF_SHOE }, - { "4485", "Baseball Cap", MF_HAT }, - { "3626B", "Plain Face", MF_HEAD }, - { "3626BP02", "Woman Face", MF_HEAD }, - { "973P11", "Dungarees", MF_TORSO }, - { "973P47", "Castle Red/Gray Symbol", MF_TORSO }, - { "973P51", "Blacktron II", MF_TORSO }, - { "973P01", "Vertical Strips Red/Blue", MF_TORSO }, - { "973P02", "Vertical Strips Blue/Red", MF_TORSO }, - { "973P60", "Shell Logo", MF_TORSO }, - { "973P61", "Gold Ice Planet Pattern", MF_TORSO }, - { "4349", "Loudhailer", MF_TOOL }, - { "3962", "Radio", MF_TOOL }, - { "4529", "Saucepan", MF_TOOL }, - { "3959", "Space Gun", MF_TOOL }, - { "4360", "Space Laser Gun", MF_TOOL }, - { "4479", "Metal Detector", MF_TOOL }, - { "6246A", "Screwdriver", MF_TOOL }, - { "6246B", "Hammer", MF_TOOL }, - { "6246D", "Box Wrench", MF_TOOL }, - { "6246E", "Open End Wrench", MF_TOOL }, - { "3896", "Castle Helmet with Chin-Guard", MF_HAT }, - { "3844", "Castle Helmet with Neck Protect", MF_HAT }, - { "3833", "Construction Helmet", MF_HAT }, - { "82359", "Skeleton Skull", MF_HEAD }, - { "973P14", "'S' Logo", MF_TORSO }, - { "973P16", "Airplane Logo", MF_TORSO }, - { "973P52", "Blacktron I Pattern", MF_TORSO }, - { "973P15", "Horizontal Stripes", MF_TORSO }, - { "973P68", "Mtron Logo", MF_TORSO }, - { "973P17", "Red V-Neck and Buttons", MF_TORSO }, - { "973P63", "Robot Pattern", MF_TORSO }, - { "973P18", "Suit and Tie ", MF_TORSO }, - { "4736", "Jet-Pack with Stud On Front", MF_NECK }, - { "4522", "Mallet", MF_TOOL }, - { "6246C", "Power Drill", MF_TOOL }, - { "4006", "Spanner/Screwdriver", MF_TOOL }, - { "194", "Hose Nozzle", MF_TOOL }, - { "2446", "Helmet", MF_HAT }, - { "3840", "Vest", MF_NECK }, - { "970P63", "Hips with Robot Pattern", MF_HIPS }, - { "972P63", "Left Leg with Robot Pattern", MF_LEGL }, - { "971P63", "Right Leg with Robot Pattern", MF_LEGR }, - { "2524", "Backpack Non-Opening", MF_NECK }, - { "4497", "Spear", MF_TOOL }, - { "37", "Knife", MF_TOOL }, - { "38", "Harpoon", MF_TOOL }, - { "3626BP03", "Pointed Moustache", MF_HEAD }, - { "3626BP04", "Sunglasses", MF_HEAD }, - { "3626BP05", "Grin and Eyebrows", MF_HEAD }, - { "973P19", "Train Chevron", MF_TORSO }, - { "973P31", "Pirate Strips (Red/Cream)", MF_TORSO }, - { "973P32", "Pirate Strips (Blue/Cream)", MF_TORSO }, - { "973P33", "Pirate Strips (Red/Black)", MF_TORSO }, - { "973P41", "Castle Chainmail", MF_TORSO }, - { "973P62", "Silver Ice Planet", MF_TORSO }, - { "6131", "Wizard Hat", MF_HAT }, - { "973P20", "Waiter", MF_TORSO }, - { "973P49", "Forestman Blue Collar", MF_TORSO }, - { "973P48", "Forestman Maroon Collar", MF_TORSO }, - { "973P50", "Forestman Black Collar", MF_TORSO }, - { "3841", "Pickaxe", MF_TOOL }, - { "973P21", "Five Button Fire Fighter", MF_TORSO }, - { "973P22", "Red Shirt and Suit", MF_TORSO }, - { "973P34", "Open Jacket over Striped Vest", MF_TORSO }, - { "973P46", "Forestman and Purse", MF_TORSO }, - { "973P101", "SW Rebel Pilot", MF_TORSO }, - { "4498", "Arrow Quiver", MF_NECK }, - { "4499", "Bow with Arrow", MF_TOOL }, - { "3852", "Hairbrush", MF_TOOL }, - { "30152", "Magnifying Glass", MF_TOOL }, - { "973P23", "'S' Logo Yellow / Blue Pattern", MF_TORSO }, - { "973P42", "Castle Crossed Pikes Pattern", MF_TORSO }, - { "973P65", "Futuron Pattern", MF_TORSO }, - { "973P25", "Red Cross & Stethoscope Pattern", MF_TORSO }, - { "973P24", "Red Cross Pattern", MF_TORSO }, - { "973P64", "Unitron Pattern", MF_TORSO }, - { "4524", "Cape", MF_NECK }, - { "2570", "Crossbow", MF_TOOL }, - { "3834", "Fire Helmet", MF_HAT }, - { "2614", "Fishing Rod", MF_TOOL } -}; - -int MFW_PIECES = sizeof(mfwpieceinfo)/sizeof(MFW_PIECEINFO); - -// { "770", "Shield Ovoid", MF_TOOL }, -// 2447 Minifig Helmet Visor diff --git a/common/globals.h b/common/globals.h index 88d4711..ff1cbda 100644 --- a/common/globals.h +++ b/common/globals.h @@ -11,6 +11,3 @@ extern unsigned char FlatColorArray[31][3]; extern unsigned char ColorArray[31][4]; extern const char* colornames[LC_MAXCOLORS]; extern const char* altcolornames[LC_MAXCOLORS]; - -extern int MFW_PIECES; -extern MFW_PIECEINFO mfwpieceinfo[]; diff --git a/common/library.cpp b/common/library.cpp index f46291c..af110c5 100755 --- a/common/library.cpp +++ b/common/library.cpp @@ -12,8 +12,239 @@ #include "system.h" #include "file.h" #include "library.h" +#include "pieceinf.h" -// ======================================================== +// ============================================================================= +// LibraryDialog class + +static const char ver_str[32] = "LeoCAD Group Configuration File"; +static const float ver_flt = 0.3f; + +LibraryDialog::LibraryDialog () +{ + m_nPieces = 0; + m_pPieces = NULL; + m_nGroups = 0; + m_nCurrentGroup = 0; + m_bReload = false; + m_bModified = false; + strcpy (m_strFile, ""); +} + +LibraryDialog::~LibraryDialog () +{ + free (m_pPieces); +} + +bool LibraryDialog::Initialize () +{ + FileDisk idx; + char filename[LC_MAXPATH]; + + // Read the piece library index. + strcpy(filename, project->GetLibraryPath()); + strcat(filename, "pieces.idx"); + if (!idx.Open(filename, "rb")) + return false; + idx.Seek(34, SEEK_SET); // skip update byte + + m_nPieces = project->GetPieceLibraryCount(); + m_pPieces = (LC_LIBDLG_PIECEINFO*) malloc (sizeof (LC_LIBDLG_PIECEINFO) * m_nPieces); + for (int i = 0; i < m_nPieces; i++) + { + LC_LIBDLG_PIECEINFO* inf = &m_pPieces[i]; + inf->info = project->GetPieceInfo(i); + inf->current_groups = inf->info->m_nGroups; + + idx.Seek (85, SEEK_CUR); + idx.ReadLong (&inf->default_groups, 1); + idx.Seek (8, SEEK_CUR); + } + idx.Close(); + + // FIX ME: get the current settings + strcpy (m_strGroups[0], "Plates"); + strcpy (m_strGroups[1], "Bricks"); + strcpy (m_strGroups[2], "Tiles"); + strcpy (m_strGroups[3], "Slope Bricks"); + strcpy (m_strGroups[4], "Technic"); + strcpy (m_strGroups[5], "Space"); + strcpy (m_strGroups[6], "Train"); + strcpy (m_strGroups[7], "Other Bricks"); + strcpy (m_strGroups[8], "Accessories"); + m_nGroups = 9; + + // UpdateList(); + UpdateTree(); + + return true; +} + +void LibraryDialog::HandleCommand (int id) +{ + switch (id) + { + case LC_LIBDLG_FILE_RESET: + { + int i; + + for (i = 0; i < m_nPieces; i++) + m_pPieces[i].current_groups = m_pPieces[i].default_groups; + + strcpy (m_strFile, ""); + m_nGroups = 9; + /* + m_ImageList.DeleteImageList(); + m_ImageList.Create(IDB_PIECEBAR, 16, 0, 0x00ff00ff); + + CString str; + for (i = 0; i < 32; i++) + { + str.LoadString (ID_PIECE_GROUP01 + i); + strcpy (m_strGroups[i], str); + m_nBitmaps[i] = min(i,9); + } + */ + m_bModified = false; + UpdateList(); + UpdateTree(); + } break; + + case LC_LIBDLG_FILE_OPEN: + { + } break; + + case LC_LIBDLG_FILE_SAVE: + { + } break; + + case LC_LIBDLG_FILE_SAVEAS: + { + } break; + + case LC_LIBDLG_FILE_PRINTCATALOG: + { + } break; + + case LC_LIBDLG_FILE_MERGEUPDATE: + { + char filename[LC_MAXPATH]; + + // CFileDialog filedlg(TRUE, ".lup\0", NULL,OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT, + // "LeoCAD Library Updates (*.lup)|*.lup|All Files (*.*)|*.*||", this); + if (!SystemDoDialog (LC_DLG_FILE_OPEN, filename)) + return; + + LoadUpdate (filename); + +// update m_Parts + UpdateList(); + m_bReload = true; + } break; + + case LC_LIBDLG_FILE_IMPORTPIECE: + { + char filename[LC_MAXPATH]; + LC_LDRAW_PIECE piece; + + // CFileDialog dlg(TRUE, ".dat\0", NULL,OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT, + // "LDraw Files (*.dat)|*.dat|All Files (*.*)|*.*||",this); + if (!SystemDoDialog (LC_DLG_FILE_OPEN, filename)) + return; + + Sys_BeginWait (); + + if (ReadLDrawPiece(filename, &piece)) + { + if (project->FindPieceInfo(piece.name) != NULL) + Sys_MessageBox ("Piece already exists in the library !"); + + if (SaveLDrawPiece(&piece)) + Sys_MessageBox ("Piece successfully imported."); + else + Sys_MessageBox ("Error saving library."); + } + else + Sys_MessageBox ("Error reading file."); + + Sys_EndWait (); + FreeLDrawPiece(&piece); + } break; + + case LC_LIBDLG_FILE_RETURN: + break; + case LC_LIBDLG_FILE_CANCEL: + break; + case LC_LIBDLG_GROUP_INSERT: + break; + case LC_LIBDLG_GROUP_DELETE: + break; + case LC_LIBDLG_GROUP_EDIT: + break; + case LC_LIBDLG_GROUP_MOVEUP: + break; + case LC_LIBDLG_GROUP_MOVEDOWN: + break; + case LC_LIBDLG_PIECE_NEW: + break; + case LC_LIBDLG_PIECE_EDIT: + break; + case LC_LIBDLG_PIECE_DELETE: + break; + } +} + +bool LibraryDialog::DoSave (bool bAskName) +{ + if (bAskName || (strlen (m_strFile) == 0)) + { + char filename[LC_MAXPATH]; + + // CFileDialog dlg(FALSE, ".lgf\0", NULL,OFN_HIDEREADONLY | OFN_OVERWRITEPROMPT, + // "LeoCAD Group Files (*.lgf)|*.lgf|All Files (*.*)|*.*||",this); + if (!SystemDoDialog (LC_DLG_FILE_SAVE, filename)) + return false; + strcpy (m_strFile, filename); + } + + /* + Sys_BeginWait (); + FileDisk f; + int i; + + if (!f.Open (m_strFile, "wb")) + return false; + + f.Write (ver_str, sizeof (ver_str)); + f.Write (ver_flt, sizeof (ver_flt)); + f.WriteByte (&m_nMaxGroups); + + for (i = 0; i < m_nMaxGroups; i++) + { + f.Write (m_strGroups[i], sizeof(m_strGroups[i])); + ar << m_nBitmaps[i]; + } + + m_ImageList.Write(&ar); + + ar << (int) m_Parts.GetSize(); + for (i = 0; i < m_Parts.GetSize(); i++) + { + ar.Write (m_Parts[i].info->m_strName, sizeof(m_Parts[i].info->m_strName)); + ar << m_Parts[i].group; + } + ar.Close(); + f.Close(); + m_bModified = FALSE; +// m_bLoaded = TRUE; + + fclose (f); + Sys_EndWait (); + */ + return true; +} + +// ============================================================================= static unsigned long GetDefaultPieceGroup(char* name) { diff --git a/common/library.h b/common/library.h index 77d142e..464627f 100755 --- a/common/library.h +++ b/common/library.h @@ -1,5 +1,97 @@ -#ifndef _MISC_H_ -#define _MISC_H_ +#ifndef _LIBRARY_H_ +#define _LIBRARY_H_ + +typedef enum { + LC_LIBDLG_FILE_RESET, + LC_LIBDLG_FILE_OPEN, + LC_LIBDLG_FILE_SAVE, + LC_LIBDLG_FILE_SAVEAS, + LC_LIBDLG_FILE_PRINTCATALOG, + LC_LIBDLG_FILE_MERGEUPDATE, + LC_LIBDLG_FILE_IMPORTPIECE, + LC_LIBDLG_FILE_RETURN, + LC_LIBDLG_FILE_CANCEL, + LC_LIBDLG_GROUP_INSERT, + LC_LIBDLG_GROUP_DELETE, + LC_LIBDLG_GROUP_EDIT, + LC_LIBDLG_GROUP_MOVEUP, + LC_LIBDLG_GROUP_MOVEDOWN, + LC_LIBDLG_PIECE_NEW, + LC_LIBDLG_PIECE_EDIT, + LC_LIBDLG_PIECE_DELETE +} LC_LIBDLG_COMMANDS; + +class PieceInfo; +class LibraryDialog; + +typedef struct +{ + PieceInfo* info; + unsigned long current_groups; + unsigned long default_groups; +} LC_LIBDLG_PIECEINFO; + +#define LC_LIBDLG_MAXGROUPS 32 +#define LC_LIBDLG_MAXNAME 32 + +typedef void (*PFNLIBDLGUPDATELISTFUNC) (LC_LIBDLG_PIECEINFO *piece_info, int count, int group, void *data); +typedef void (*PFNLIBDLGUPDATETREEFUNC) (int num_groups, char str_groups[][LC_LIBDLG_MAXNAME+1], void *data); + +class LibraryDialog +{ + public: + LibraryDialog (); + virtual ~LibraryDialog (); + + void HandleCommand (int id); + bool DoSave (bool bAskName); + bool Initialize (); + + void SetListFunc (PFNLIBDLGUPDATELISTFUNC func, void *data) + { + m_pUpdateListFunc = func; + m_pUpdateListData = data; + } + + void SetTreeFunc (PFNLIBDLGUPDATETREEFUNC func, void *data) + { + m_pUpdateTreeFunc = func; + m_pUpdateTreeData = data; + } + + void UpdateList () + { + m_pUpdateListFunc (m_pPieces, m_nPieces, m_nCurrentGroup, m_pUpdateListData); + } + + void UpdateTree () + { + m_pUpdateTreeFunc (m_nGroups, m_strGroups, m_pUpdateTreeData); + } + + void SetCurrentGroup (unsigned long group) + { + m_nCurrentGroup = group; + UpdateList (); + } + + protected: + void *m_pUpdateListData; + void *m_pUpdateTreeData; + PFNLIBDLGUPDATELISTFUNC m_pUpdateListFunc; + PFNLIBDLGUPDATETREEFUNC m_pUpdateTreeFunc; + + int m_nPieces; + LC_LIBDLG_PIECEINFO* m_pPieces; + + unsigned char m_nGroups; + char m_strGroups[LC_LIBDLG_MAXGROUPS][LC_LIBDLG_MAXNAME+1]; + int m_nCurrentGroup; + + bool m_bModified; + bool m_bReload; + char m_strFile[LC_MAXPATH]; +}; typedef struct connection_s { @@ -50,4 +142,4 @@ void FreeLDrawPiece(LC_LDRAW_PIECE* piece); bool DeletePiece(char** names, int numpieces); bool LoadUpdate(const char* update); -#endif // _MISC_H_ +#endif // _LIBRARY_H_ diff --git a/common/light.cpp b/common/light.cpp index 5638b35..b106f33 100644 --- a/common/light.cpp +++ b/common/light.cpp @@ -10,8 +10,6 @@ Light::Light() : Object (LC_OBJECT_LIGHT) { - // m_BoundingBox.Initialize(this, LC_LIGHT); - // m_TargetBoundingBox.Initialize(this, LC_LIGHT_TARGET); m_pNext = NULL; m_nState = 0; } diff --git a/common/minifig.cpp b/common/minifig.cpp new file mode 100644 index 0000000..f56148d --- /dev/null +++ b/common/minifig.cpp @@ -0,0 +1,578 @@ +// +// Minifig Wizard base class, calculates position/rotation of all pieces. +// + +#include +#include +#include +#include "minifig.h" +#include "opengl.h" +#include "pieceinf.h" +#include "globals.h" +#include "project.h" +#include "matrix.h" + +// ============================================================================= +// Static variables + +static LC_MFW_PIECEINFO mfw_pieceinfo[] = { + { "3624", "Police Hat", LC_MFW_HAT }, + { "3626BP01", "Smiley Face", LC_MFW_HEAD }, + { "973", "Plain Torso", LC_MFW_TORSO }, + { "3838", "Airtanks", LC_MFW_NECK }, + { "976", "Left Arm", LC_MFW_LEFT_ARM }, + { "975", "Right Arm", LC_MFW_RIGHT_ARM }, + { "977", "Hand", LC_MFW_LEFT_HAND }, + { "977", "Hand", LC_MFW_LEFT_HAND }, + { "3899", "Cup", LC_MFW_LEFT_TOOL }, + { "4528", "Frypan", LC_MFW_LEFT_TOOL }, + { "970", "Hips", LC_MFW_HIPS }, + { "972", "Left Leg", LC_MFW_LEFT_LEG }, + { "971", "Right Leg", LC_MFW_RIGHT_LEG }, + { "2599", "Flipper", LC_MFW_LEFT_SHOE }, + { "6120", "Ski", LC_MFW_LEFT_SHOE }, + { "4485", "Baseball Cap", LC_MFW_HAT }, + { "3626B", "Plain Face", LC_MFW_HEAD }, + { "3626BP02", "Woman Face", LC_MFW_HEAD }, + { "973P11", "Dungarees", LC_MFW_TORSO }, + { "973P47", "Castle Red/Gray Symbol", LC_MFW_TORSO }, + { "973P51", "Blacktron II", LC_MFW_TORSO }, + { "973P01", "Vertical Strips Red/Blue", LC_MFW_TORSO }, + { "973P02", "Vertical Strips Blue/Red", LC_MFW_TORSO }, + { "973P60", "Shell Logo", LC_MFW_TORSO }, + { "973P61", "Gold Ice Planet Pattern", LC_MFW_TORSO }, + { "4349", "Loudhailer", LC_MFW_LEFT_TOOL }, + { "3962", "Radio", LC_MFW_LEFT_TOOL }, + { "4529", "Saucepan", LC_MFW_LEFT_TOOL }, + { "3959", "Space Gun", LC_MFW_LEFT_TOOL }, + { "4360", "Space Laser Gun", LC_MFW_LEFT_TOOL }, + { "4479", "Metal Detector", LC_MFW_LEFT_TOOL }, + { "6246A", "Screwdriver", LC_MFW_LEFT_TOOL }, + { "6246B", "Hammer", LC_MFW_LEFT_TOOL }, + { "6246D", "Box Wrench", LC_MFW_LEFT_TOOL }, + { "6246E", "Open End Wrench", LC_MFW_LEFT_TOOL }, + { "3896", "Castle Helmet with Chin-Guard", LC_MFW_HAT }, + { "3844", "Castle Helmet with Neck Protect", LC_MFW_HAT }, + { "3833", "Construction Helmet", LC_MFW_HAT }, + { "82359", "Skeleton Skull", LC_MFW_HEAD }, + { "973P14", "'S' Logo", LC_MFW_TORSO }, + { "973P16", "Airplane Logo", LC_MFW_TORSO }, + { "973P52", "Blacktron I Pattern", LC_MFW_TORSO }, + { "973P15", "Horizontal Stripes", LC_MFW_TORSO }, + { "973P68", "Mtron Logo", LC_MFW_TORSO }, + { "973P17", "Red V-Neck and Buttons", LC_MFW_TORSO }, + { "973P63", "Robot Pattern", LC_MFW_TORSO }, + { "973P18", "Suit and Tie ", LC_MFW_TORSO }, + { "4736", "Jet-Pack with Stud On Front", LC_MFW_NECK }, + { "4522", "Mallet", LC_MFW_LEFT_TOOL }, + { "6246C", "Power Drill", LC_MFW_LEFT_TOOL }, + { "4006", "Spanner/Screwdriver", LC_MFW_LEFT_TOOL }, + { "194", "Hose Nozzle", LC_MFW_LEFT_TOOL }, + { "2446", "Helmet", LC_MFW_HAT }, + { "3840", "Vest", LC_MFW_NECK }, + { "970P63", "Hips with Robot Pattern", LC_MFW_HIPS }, + { "972P63", "Left Leg with Robot Pattern", LC_MFW_LEFT_LEG }, + { "971P63", "Right Leg with Robot Pattern", LC_MFW_RIGHT_LEG }, + { "2524", "Backpack Non-Opening", LC_MFW_NECK }, + { "4497", "Spear", LC_MFW_LEFT_TOOL }, + { "37", "Knife", LC_MFW_LEFT_TOOL }, + { "38", "Harpoon", LC_MFW_LEFT_TOOL }, + { "3626BP03", "Pointed Moustache", LC_MFW_HEAD }, + { "3626BP04", "Sunglasses", LC_MFW_HEAD }, + { "3626BP05", "Grin and Eyebrows", LC_MFW_HEAD }, + { "973P19", "Train Chevron", LC_MFW_TORSO }, + { "973P31", "Pirate Strips (Red/Cream)", LC_MFW_TORSO }, + { "973P32", "Pirate Strips (Blue/Cream)", LC_MFW_TORSO }, + { "973P33", "Pirate Strips (Red/Black)", LC_MFW_TORSO }, + { "973P41", "Castle Chainmail", LC_MFW_TORSO }, + { "973P62", "Silver Ice Planet", LC_MFW_TORSO }, + { "6131", "Wizard Hat", LC_MFW_HAT }, + { "973P20", "Waiter", LC_MFW_TORSO }, + { "973P49", "Forestman Blue Collar", LC_MFW_TORSO }, + { "973P48", "Forestman Maroon Collar", LC_MFW_TORSO }, + { "973P50", "Forestman Black Collar", LC_MFW_TORSO }, + { "3841", "Pickaxe", LC_MFW_LEFT_TOOL }, + { "973P21", "Five Button Fire Fighter", LC_MFW_TORSO }, + { "973P22", "Red Shirt and Suit", LC_MFW_TORSO }, + { "973P34", "Open Jacket over Striped Vest", LC_MFW_TORSO }, + { "973P46", "Forestman and Purse", LC_MFW_TORSO }, + { "973P101", "SW Rebel Pilot", LC_MFW_TORSO }, + { "4498", "Arrow Quiver", LC_MFW_NECK }, + { "4499", "Bow with Arrow", LC_MFW_LEFT_TOOL }, + { "3852", "Hairbrush", LC_MFW_LEFT_TOOL }, + { "30152", "Magnifying Glass", LC_MFW_LEFT_TOOL }, + { "973P23", "'S' Logo Yellow / Blue Pattern", LC_MFW_TORSO }, + { "973P42", "Castle Crossed Pikes Pattern", LC_MFW_TORSO }, + { "973P65", "Futuron Pattern", LC_MFW_TORSO }, + { "973P25", "Red Cross & Stethoscope Pattern", LC_MFW_TORSO }, + { "973P24", "Red Cross Pattern", LC_MFW_TORSO }, + { "973P64", "Unitron Pattern", LC_MFW_TORSO }, + { "4524", "Cape", LC_MFW_NECK }, + { "2570", "Crossbow", LC_MFW_LEFT_TOOL }, + { "3834", "Fire Helmet", LC_MFW_HAT }, + { "2614", "Fishing Rod", LC_MFW_LEFT_TOOL } +// { "770", "Shield Ovoid", LC_MFW_LEFT_TOOL }, +// 2447 Minifig Helmet Visor +}; + +static int mfw_pieces = sizeof (mfw_pieceinfo)/sizeof (LC_MFW_PIECEINFO); + +// ============================================================================= +// MinifigWizard class + +MinifigWizard::MinifigWizard () +{ + const unsigned char colors[15] = { 0, 6, 4, 22, 0, 0, 6, 6, 22, 22, 9, 9, 9, 22, 22 }; + const float pos[15][3] = { {0,0,3.84f}, {0,0,3.84f}, {0,0,2.88f}, {0,0,2.96f}, {0,0,2.56f}, + {0,0,2.56f}, {0.9f,-0.62f,1.76f}, {-0.9f,-0.62f,1.76f}, {0.92f,-0.62f,1.76f}, + {-0.92f,-0.62f,1.76f}, {0,0,1.6f}, {0,0,1.12f}, {0,0,1.12f}, {0.42f,0,0}, + {-0.42f,0,0} }; + int i; + + for (i = 0; i < 15; i++) + { + m_Info[i] = NULL; + m_Colors[i] = colors[i]; + m_Pos[i][0] = pos[i][0]; + m_Pos[i][1] = pos[i][1]; + m_Pos[i][2] = pos[i][2]; + m_Rot[i][0] = 0; + m_Rot[i][1] = 0; + m_Rot[i][2] = 0; + } + + for (i = 0; i < 13; i++) + { + if (i == 3 || i == 7 || i == 8 || i == 9) + continue; + + PieceInfo* pInfo = project->FindPieceInfo (mfw_pieceinfo[i].name); + if (pInfo == NULL) + continue; + + if (i == 6) + { + m_Info[6] = pInfo; + m_Info[7] = pInfo; + pInfo->AddRef(); + pInfo->AddRef(); + m_Rot[6][0] = 45; + m_Rot[6][2] = 90; + m_Rot[7][0] = 45; + m_Rot[7][2] = 90; + } + else + { + m_Info[i] = pInfo; + pInfo->AddRef(); + } + } +} + +MinifigWizard::~MinifigWizard () +{ +} + +void MinifigWizard::Resize (int width, int height) +{ + float aspect = (float)width/(float)height; + glViewport(0, 0, width, height); + glMatrixMode(GL_PROJECTION); + glLoadIdentity(); + gluPerspective(30.0f, aspect, 1.0f, 20.0f); + glMatrixMode(GL_MODELVIEW); + glLoadIdentity(); + + gluLookAt (0, -9, 4, 0, 5, 1, 0, 0, 1); + glEnable(GL_DEPTH_TEST); + glDepthFunc(GL_LEQUAL); + glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA); + float *bg = project->GetBackgroundColor(); + glClearColor(bg[0], bg[1], bg[2], bg[3]); + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + glDisable (GL_DITHER); + glShadeModel (GL_FLAT); +} + +void MinifigWizard::Redraw () +{ + int i; + + glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + Calculate (); + + for (i = 0; i < LC_MFW_NUMITEMS; i++) + { + if (m_Info[i] == NULL) + continue; + + glPushMatrix (); + glTranslatef (m_Position[i][0], m_Position[i][1], m_Position[i][2]); + glRotatef (m_Rotation[i][3], m_Rotation[i][0], m_Rotation[i][1], m_Rotation[i][2]); + m_Info[i]->RenderPiece(m_Colors[i]); + glPopMatrix (); + } + + glFinish(); +} + +void MinifigWizard::Calculate () +{ + Matrix mat, m2, m3; + + // hat + m_Position[LC_MFW_HAT][0] = m_Pos[LC_MFW_HAT][0]; + m_Position[LC_MFW_HAT][1] = m_Pos[LC_MFW_HAT][1]; + m_Position[LC_MFW_HAT][2] = m_Pos[LC_MFW_HAT][2]; + m_Rotation[LC_MFW_HAT][0] = 0.0f; + m_Rotation[LC_MFW_HAT][1] = 0.0f; + m_Rotation[LC_MFW_HAT][2] = -1.0f; + m_Rotation[LC_MFW_HAT][3] = m_Angles[LC_MFW_HAT] + m_Angles[LC_MFW_HEAD]; + + // head + m_Position[LC_MFW_HEAD][0] = m_Pos[LC_MFW_HEAD][0]; + m_Position[LC_MFW_HEAD][1] = m_Pos[LC_MFW_HEAD][1]; + m_Position[LC_MFW_HEAD][2] = m_Pos[LC_MFW_HEAD][2]; + m_Rotation[LC_MFW_HEAD][0] = 0.0f; + m_Rotation[LC_MFW_HEAD][1] = 0.0f; + m_Rotation[LC_MFW_HEAD][2] = -1.0f; + m_Rotation[LC_MFW_HEAD][3] = m_Angles[LC_MFW_HEAD]; + + // neck + mat.LoadIdentity (); + mat.CreateOld (0,0,0,m_Rot[LC_MFW_NECK][0], m_Rot[LC_MFW_NECK][1], m_Rot[LC_MFW_NECK][2]); + mat.Rotate (m_Angles[LC_MFW_NECK], 0, 0, -1); + mat.SetTranslation (m_Pos[LC_MFW_NECK][0], m_Pos[LC_MFW_NECK][1], + m_Pos[LC_MFW_NECK][2]); + mat.ToAxisAngle (m_Rotation[LC_MFW_NECK]); + mat.GetTranslation (m_Position[LC_MFW_NECK]); + + // torso + m_Position[LC_MFW_TORSO][0] = m_Pos[LC_MFW_TORSO][0]; + m_Position[LC_MFW_TORSO][1] = m_Pos[LC_MFW_TORSO][1]; + m_Position[LC_MFW_TORSO][2] = m_Pos[LC_MFW_TORSO][2]; + m_Rotation[LC_MFW_TORSO][0] = 0.0f; + m_Rotation[LC_MFW_TORSO][1] = 0.0f; + m_Rotation[LC_MFW_TORSO][2] = 1.0f; + m_Rotation[LC_MFW_TORSO][3] = 0.0f; + + // left arm/hand/tool + mat.LoadIdentity (); + mat.Rotate (m_Angles[LC_MFW_LEFT_ARM], -1, 0, 0); + mat.SetTranslation (m_Pos[LC_MFW_LEFT_ARM][0], m_Pos[LC_MFW_LEFT_ARM][1], + m_Pos[LC_MFW_LEFT_ARM][2]); + mat.ToAxisAngle (m_Rotation[LC_MFW_LEFT_ARM]); + mat.GetTranslation (m_Position[LC_MFW_LEFT_ARM]); + + mat.Translate (m_Pos[LC_MFW_LEFT_HAND][0]-m_Pos[LC_MFW_LEFT_ARM][0], + m_Pos[LC_MFW_LEFT_HAND][1]-m_Pos[LC_MFW_LEFT_ARM][1], + m_Pos[LC_MFW_LEFT_HAND][2]-m_Pos[LC_MFW_LEFT_ARM][2]); + m2.CreateOld (0,0,0,m_Rot[LC_MFW_LEFT_HAND][0],m_Rot[LC_MFW_LEFT_HAND][1],m_Rot[LC_MFW_LEFT_HAND][2]); + m3.Multiply (mat, m2); + m3.Translate (0,0,-0.16f); + mat.LoadIdentity (); + mat.Translate (0,0,0.16f); + mat.Rotate (m_Angles[LC_MFW_LEFT_HAND], 1, 0, 0); + m2.Multiply (m3, mat); + m2.ToAxisAngle (m_Rotation[LC_MFW_LEFT_HAND]); + m2.GetTranslation (m_Position[LC_MFW_LEFT_HAND]); + + m2.Translate (m_Pos[LC_MFW_LEFT_TOOL][0]-m_Pos[LC_MFW_LEFT_ARM][0], + m_Pos[LC_MFW_LEFT_TOOL][1]-m_Pos[LC_MFW_LEFT_ARM][1], + m_Pos[LC_MFW_LEFT_TOOL][2]-m_Pos[LC_MFW_LEFT_ARM][2]); + m3.CreateOld (0,0,0,m_Rot[LC_MFW_LEFT_TOOL][0]-m_Rot[LC_MFW_LEFT_HAND][0], + m_Rot[LC_MFW_LEFT_TOOL][1]-m_Rot[LC_MFW_LEFT_HAND][1], + m_Rot[LC_MFW_LEFT_TOOL][2]-m_Rot[LC_MFW_LEFT_HAND][2]); + mat.Multiply (m2, m3); + m2.LoadIdentity (); + m2.Rotate (m_Angles[LC_MFW_LEFT_TOOL], 0, 0, 1); + m3.Multiply (mat, m2); + m3.ToAxisAngle (m_Rotation[LC_MFW_LEFT_TOOL]); + m3.GetTranslation (m_Position[LC_MFW_LEFT_TOOL]); + + // right arm/hand/tool + mat.LoadIdentity (); + mat.Rotate (m_Angles[LC_MFW_RIGHT_ARM], -1, 0, 0); + mat.SetTranslation (m_Pos[LC_MFW_RIGHT_ARM][0], m_Pos[LC_MFW_RIGHT_ARM][1], + m_Pos[LC_MFW_RIGHT_ARM][2]); + mat.ToAxisAngle (m_Rotation[LC_MFW_RIGHT_ARM]); + mat.GetTranslation (m_Position[LC_MFW_RIGHT_ARM]); + + mat.Translate (m_Pos[LC_MFW_RIGHT_HAND][0]-m_Pos[LC_MFW_RIGHT_ARM][0], + m_Pos[LC_MFW_RIGHT_HAND][1]-m_Pos[LC_MFW_RIGHT_ARM][1], + m_Pos[LC_MFW_RIGHT_HAND][2]-m_Pos[LC_MFW_RIGHT_ARM][2]); + m2.CreateOld (0,0,0,m_Rot[LC_MFW_RIGHT_HAND][0],m_Rot[LC_MFW_RIGHT_HAND][1],m_Rot[LC_MFW_RIGHT_HAND][2]); + m3.Multiply (mat, m2); + m3.Translate (0,0,-0.16f); + mat.LoadIdentity (); + mat.Translate (0,0,0.16f); + mat.Rotate (m_Angles[LC_MFW_RIGHT_HAND], 1, 0, 0); + m2.Multiply (m3, mat); + m2.ToAxisAngle (m_Rotation[LC_MFW_RIGHT_HAND]); + m2.GetTranslation (m_Position[LC_MFW_RIGHT_HAND]); + + // hips + m_Position[LC_MFW_HIPS][0] = m_Pos[LC_MFW_HIPS][0]; + m_Position[LC_MFW_HIPS][1] = m_Pos[LC_MFW_HIPS][1]; + m_Position[LC_MFW_HIPS][2] = m_Pos[LC_MFW_HIPS][2]; + m_Rotation[LC_MFW_HIPS][0] = 0.0f; + m_Rotation[LC_MFW_HIPS][1] = 0.0f; + m_Rotation[LC_MFW_HIPS][2] = 1.0f; + m_Rotation[LC_MFW_HIPS][3] = 0.0f; + + // left leg/shoe + mat.LoadIdentity (); + mat.Rotate (m_Angles[LC_MFW_LEFT_LEG], -1, 0, 0); + mat.SetTranslation (m_Pos[LC_MFW_LEFT_LEG][0], m_Pos[LC_MFW_LEFT_LEG][1], + m_Pos[LC_MFW_LEFT_LEG][2]); + mat.ToAxisAngle (m_Rotation[LC_MFW_LEFT_LEG]); + mat.GetTranslation (m_Position[LC_MFW_LEFT_LEG]); + mat.Translate (m_Pos[LC_MFW_LEFT_SHOE][0]-m_Pos[LC_MFW_LEFT_LEG][0], + m_Pos[LC_MFW_LEFT_SHOE][1]-m_Pos[LC_MFW_LEFT_LEG][1], + m_Pos[LC_MFW_LEFT_SHOE][2]-m_Pos[LC_MFW_LEFT_LEG][2]); + m2.CreateOld (0,0,0,m_Rot[LC_MFW_LEFT_SHOE][0],m_Rot[LC_MFW_LEFT_SHOE][1],m_Rot[LC_MFW_LEFT_SHOE][2]); + m3.Multiply (mat, m2); + mat.LoadIdentity (); + mat.Rotate (m_Angles[LC_MFW_LEFT_SHOE], 0, 0, 1); + m2.Multiply (m3, mat); + m2.ToAxisAngle (m_Rotation[LC_MFW_LEFT_SHOE]); + m2.GetTranslation (m_Position[LC_MFW_LEFT_SHOE]); + + // right leg/shoe + mat.LoadIdentity (); + mat.Rotate (m_Angles[LC_MFW_RIGHT_LEG], -1, 0, 0); + mat.SetTranslation (m_Pos[LC_MFW_RIGHT_LEG][0], m_Pos[LC_MFW_RIGHT_LEG][1], + m_Pos[LC_MFW_RIGHT_LEG][2]); + mat.ToAxisAngle (m_Rotation[LC_MFW_RIGHT_LEG]); + mat.GetTranslation (m_Position[LC_MFW_RIGHT_LEG]); + mat.Translate (m_Pos[LC_MFW_RIGHT_SHOE][0]-m_Pos[LC_MFW_RIGHT_LEG][0], + m_Pos[LC_MFW_RIGHT_SHOE][1]-m_Pos[LC_MFW_RIGHT_LEG][1], + m_Pos[LC_MFW_RIGHT_SHOE][2]-m_Pos[LC_MFW_RIGHT_LEG][2]); + m2.CreateOld (0,0,0,m_Rot[LC_MFW_RIGHT_SHOE][0],m_Rot[LC_MFW_RIGHT_SHOE][1],m_Rot[LC_MFW_RIGHT_SHOE][2]); + m3.Multiply (mat, m2); + mat.LoadIdentity (); + mat.Rotate (m_Angles[LC_MFW_RIGHT_SHOE], 0, 0, 1); + m2.Multiply (m3, mat); + m2.ToAxisAngle (m_Rotation[LC_MFW_RIGHT_SHOE]); + m2.GetTranslation (m_Position[LC_MFW_RIGHT_SHOE]); +} + +void MinifigWizard::GetDescriptions (int type, char ***names, int *count) +{ + char **list = (char**)malloc (sizeof (char*)*mfw_pieces); + *names = list; + *count = 0; + int i, j; + + for (i = 0; i < mfw_pieces; i++) + { + PieceInfo* piece_info; + + piece_info = project->FindPieceInfo (mfw_pieceinfo[i].name); + if (piece_info == NULL) + continue; + + switch (type) + { + case LC_MFW_HAT: + case LC_MFW_HEAD: + case LC_MFW_TORSO: + case LC_MFW_NECK: + case LC_MFW_LEFT_ARM: + case LC_MFW_RIGHT_ARM: + case LC_MFW_HIPS: + case LC_MFW_LEFT_LEG: + case LC_MFW_RIGHT_LEG: + case LC_MFW_LEFT_HAND: + case LC_MFW_LEFT_TOOL: + case LC_MFW_LEFT_SHOE: + if (mfw_pieceinfo[i].type != type) + continue; + break; + + case LC_MFW_RIGHT_HAND: + if (mfw_pieceinfo[i].type != LC_MFW_LEFT_HAND) + continue; + break; + + case LC_MFW_RIGHT_TOOL: + if (mfw_pieceinfo[i].type != LC_MFW_LEFT_TOOL) + continue; + break; + + case LC_MFW_RIGHT_SHOE: + if (mfw_pieceinfo[i].type != LC_MFW_LEFT_SHOE) + continue; + break; + + default: + continue; + } + + list[(*count)++] = mfw_pieceinfo[i].description; + + if (i == 6) i++; // two hands are listed + } + + // ugly sort + for (i = 0; i < (*count) - 1; i++) + for (j = 0; j < (*count) - 1; j++) + { + if (strcmp (list[j], list[j+1]) > 0) + { + char *tmp = list[j]; + list[j] = list[j+1]; + list[j+1] = tmp; + } + } + + if ((type == LC_MFW_HAT) || (type == LC_MFW_NECK) || + (type == LC_MFW_LEFT_TOOL) || (type == LC_MFW_RIGHT_TOOL) || + (type == LC_MFW_LEFT_SHOE) || (type == LC_MFW_RIGHT_SHOE)) + { + memmove (list+1, list, *count*sizeof (char*)); + list[0] = "None"; + (*count)++; + } +} + +void MinifigWizard::ChangePiece (int type, const char *desc) +{ + PieceInfo* piece_info = NULL; + int j; + + for (j = 0; j < mfw_pieces; j++) + { + if (strcmp (desc, mfw_pieceinfo[j].description) == 0) + { + piece_info = project->FindPieceInfo (mfw_pieceinfo[j].name); + if (piece_info == NULL) + continue; + + if (m_Info[type]) + m_Info[type]->DeRef(); + m_Info[type] = piece_info; + piece_info->AddRef(); + break; + } + } + + // Piece not found ("None") + if (j == mfw_pieces) + { + if (m_Info[type]) + m_Info[type]->DeRef(); + m_Info[type] = NULL; + } + + // Get the pieces in the right place + if (type == LC_MFW_NECK) + { + if (m_Info[3] != NULL) + { + m_Pos[0][2] = 3.92f; + m_Pos[1][2] = 3.92f; + + if (strcmp (piece_info->m_strName,"4498") == 0) + m_Rot[3][2] = 180.0f; + else + m_Rot[3][2] = 0.0f; + } + else + { + m_Pos[0][2] = 3.84f; + m_Pos[1][2] = 3.84f; + } + } + + if (type == LC_MFW_LEFT_SHOE) + { + if (strcmp (desc, "Ski")) + m_Pos[13][1] = 0; + else + m_Pos[13][1] = -0.12f; + } + + if (type == LC_MFW_RIGHT_SHOE) + { + if (strcmp (desc, "Ski")) + m_Pos[14][1] = 0; + else + m_Pos[14][1] = -0.12f; + } + + if ((type == LC_MFW_LEFT_TOOL) || (type == LC_MFW_RIGHT_TOOL)) + if (piece_info != NULL) + { + float rx = 45, ry = 0, rz = 0, x = 0.92f, y = -0.62f, z = 1.76f; + + if (strcmp (piece_info->m_strName,"4529") == 0) + { rx = -45; y = -1.14f; z = 2.36f; } + if (strcmp (piece_info->m_strName,"3899") == 0) + { y = -1.64f; z = 1.38f; } + if (strcmp (piece_info->m_strName,"4528") == 0) + { rx = -45; y = -1.26f; z = 2.36f; } + if (strcmp (piece_info->m_strName,"4479") == 0) + { rz = 90; y = -1.22f; z = 2.44f; } + if (strcmp (piece_info->m_strName,"3962") == 0) + { rz = 90; y = -0.7f; z = 1.62f; } + if (strcmp (piece_info->m_strName,"4360") == 0) + { rz = -90; y = -1.22f; z = 2.44f; } + if (strncmp (piece_info->m_strName,"6246",4) == 0) + { y = -1.82f; z = 2.72f; rz = 90; } + if (strcmp (piece_info->m_strName,"4349") == 0) + { y = -1.16f; z = 2.0f; } + if (strcmp (piece_info->m_strName,"4479") == 0) + { y = -1.42f; z = 2.26f; } + if (strcmp (piece_info->m_strName,"3959") == 0) + { y = -1.0f; z = 1.88f; } + if (strcmp (piece_info->m_strName,"4522") == 0) + { y = -1.64f; z = 2.48f; } + if (strcmp (piece_info->m_strName,"194") == 0) + { rz = 180; y = -1.04f; z = 1.94f; } + if (strcmp (piece_info->m_strName,"4006") == 0) + { rz = 180; y = -1.24f; z = 2.18f; } + if (strcmp (piece_info->m_strName,"6246C") == 0) + { rx = 45; rz = 0; y = -0.86f; z = 1.78f; } + if (strcmp (piece_info->m_strName,"4497") == 0) + { y = -2.16f; z = 3.08f; rz = 90; } + if (strcmp (piece_info->m_strName,"30092") == 0) + { x = 0; rz = 180; } + if (strcmp (piece_info->m_strName,"37") == 0) + { z = 1.52f; y = -0.64f; } + if (strcmp (piece_info->m_strName,"38") == 0) + { z = 1.24f; y = -0.34f; } + if (strcmp (piece_info->m_strName,"3841") == 0) + { z = 2.24f; y = -1.34f; rz = 180; } + if (strcmp (piece_info->m_strName,"4499") == 0) + { rz = ((type == LC_MFW_RIGHT_TOOL) ? 10 : -10); z = 1.52f; } + if (strcmp (piece_info->m_strName,"3852") == 0) + { rz = -90; x = 0.90f; y = -0.8f; z = 1.84f; } + if (strcmp (piece_info->m_strName,"30152") == 0) + { z = 3.06f; y = -2.16f; } + if (strcmp (piece_info->m_strName,"2570") == 0) + { z = 1.68f; y = -0.8f; } + if (strcmp (piece_info->m_strName,"2614") == 0) + { z = 1.74f; y = -0.86f; } + + if (type == LC_MFW_RIGHT_TOOL) + x = -x; + + m_Pos[type][0] = x; + m_Pos[type][1] = y; + m_Pos[type][2] = z; + m_Rot[type][0] = rx; + m_Rot[type][1] = ry; + m_Rot[type][2] = rz; + } +} + +void MinifigWizard::ChangeColor (int type, int color) +{ + m_Colors[type] = color; +} + +void MinifigWizard::ChangeAngle (int type, float angle) +{ + m_Angles[type] = angle; +} diff --git a/common/minifig.h b/common/minifig.h new file mode 100644 index 0000000..409d81b --- /dev/null +++ b/common/minifig.h @@ -0,0 +1,60 @@ +#ifndef _MINIFIG_H_ +#define _MINIFIG_H_ + +class PieceInfo; + +typedef enum +{ + LC_MFW_HAT, + LC_MFW_HEAD, + LC_MFW_TORSO, + LC_MFW_NECK, + LC_MFW_LEFT_ARM, + LC_MFW_RIGHT_ARM, + LC_MFW_LEFT_HAND, + LC_MFW_RIGHT_HAND, + LC_MFW_LEFT_TOOL, + LC_MFW_RIGHT_TOOL, + LC_MFW_HIPS, + LC_MFW_LEFT_LEG, + LC_MFW_RIGHT_LEG, + LC_MFW_LEFT_SHOE, + LC_MFW_RIGHT_SHOE, + LC_MFW_NUMITEMS +} LC_MFW_TYPES; + +typedef struct +{ + char name[9]; + char description[32]; + int type; +} LC_MFW_PIECEINFO; + +class MinifigWizard +{ + public: + MinifigWizard (); + ~MinifigWizard (); + + void Redraw (); + void Resize (int width, int height); + void Calculate (); + void GetDescriptions (int type, char ***names, int *count); + void ChangePiece (int type, const char *description); + void ChangeColor (int type, int color); + void ChangeAngle (int type, float angle); + + public: + PieceInfo* m_Info[LC_MFW_NUMITEMS]; + int m_Colors[LC_MFW_NUMITEMS]; + float m_Position[LC_MFW_NUMITEMS][3]; + float m_Rotation[LC_MFW_NUMITEMS][4]; + + protected: + // internal variables used to calculate the real position/rotation + float m_Pos[LC_MFW_NUMITEMS][3]; + float m_Rot[LC_MFW_NUMITEMS][3]; + float m_Angles[LC_MFW_NUMITEMS]; +}; + +#endif // _MINIFIG_H_ diff --git a/common/module.mk b/common/module.mk index add1743..a22bcbe 100644 --- a/common/module.mk +++ b/common/module.mk @@ -1,4 +1,4 @@ -SRC += common/camera.cpp common/file.cpp common/globals.cpp common/group.cpp common/image.cpp common/im_bmp.cpp common/im_png.cpp common/library.cpp common/light.cpp common/matrix.cpp common/piece.cpp common/pieceinf.cpp common/project.cpp common/quant.cpp common/terrain.cpp common/texture.cpp common/tr.cpp common/vector.cpp common/opengl.cpp common/object.cpp +SRC += common/camera.cpp common/file.cpp common/globals.cpp common/group.cpp common/image.cpp common/im_bmp.cpp common/im_png.cpp common/library.cpp common/light.cpp common/matrix.cpp common/piece.cpp common/pieceinf.cpp common/project.cpp common/quant.cpp common/terrain.cpp common/texture.cpp common/tr.cpp common/vector.cpp common/opengl.cpp common/object.cpp common/minifig.cpp LIBS += -ljpeg -lpng -lz -lm diff --git a/common/piece.cpp b/common/piece.cpp index 1f14020..133ccec 100644 --- a/common/piece.cpp +++ b/common/piece.cpp @@ -16,26 +16,26 @@ ///////////////////////////////////////////////////////////////////////////// // Static functions -static PIECE_KEY* AddNode (PIECE_KEY *node, unsigned short nTime, unsigned char nType) +static LC_PIECE_KEY* AddNode (LC_PIECE_KEY *node, unsigned short nTime, unsigned char nType) { - PIECE_KEY* newnode = (PIECE_KEY*)malloc(sizeof(PIECE_KEY)); + LC_PIECE_KEY* newnode = (LC_PIECE_KEY*)malloc(sizeof(LC_PIECE_KEY)); - if (node) - { - newnode->next = node->next; - node->next = newnode; - } - else - newnode->next = NULL; + if (node) + { + newnode->next = node->next; + node->next = newnode; + } + else + newnode->next = NULL; - newnode->type = nType; - newnode->time = nTime; - newnode->param[0] = newnode->param[1] = newnode->param[2] = newnode->param[3] = 0; + newnode->type = nType; + newnode->time = nTime; + newnode->param[0] = newnode->param[1] = newnode->param[2] = newnode->param[3] = 0; - if (nType == PK_ROTATION) - newnode->param[2] = 1; + if (nType == PK_ROTATION) + newnode->param[2] = 1; - return newnode; + return newnode; } inline static void SetCurrentColor(unsigned char nColor, bool* bTrans, bool bLighting, bool bNoAlpha) @@ -94,50 +94,18 @@ inline static void SetCurrentColor(unsigned char nColor, bool* bTrans, bool bLig ///////////////////////////////////////////////////////////////////////////// // Piece construction/destruction -#if ! (defined (GL_EXT_compiled_vertex_array)) - -#ifdef LC_LINUX -#include -#define wglGetProcAddress(func) glXGetProcAddressARB((const GLubyte *) func) -#endif - -#ifdef LC_WINDOWS -typedef void (APIENTRY * GLLOCKARRAYSEXTPROC) (GLint first, GLsizei count); -typedef void (APIENTRY * GLUNLOCKARRAYSEXTPROC) (); -#else -// TODO: get the entry point under different OS's -#define glLockArraysEXT(a,b) {} -#define glUnlockArraysEXT() {} -#endif - -static GLLOCKARRAYSEXTPROC glLockArraysEXT; -static GLUNLOCKARRAYSEXTPROC glUnlockArraysEXT; - static bool lockarrays = false; -#else -static bool lockarrays = true; -#endif Piece::Piece(PieceInfo* pPieceInfo) : Object (LC_OBJECT_PIECE) { -#if ! (defined (GL_EXT_compiled_vertex_array)) + static bool first_time = true; - static bool first_time = true; - - if (first_time) - { - first_time = false; - char* extensions = (char*)glGetString(GL_EXTENSIONS); - - if (strstr(extensions, "GL_EXT_compiled_vertex_array ")) - { - glLockArraysEXT = (GLLOCKARRAYSEXTPROC)wglGetProcAddress("glLockArraysEXT"); - glUnlockArraysEXT = (GLUNLOCKARRAYSEXTPROC)wglGetProcAddress("glUnlockArraysEXT"); - lockarrays = true; - } - } -#endif + if (first_time) + { + first_time = false; + lockarrays = GL_HasCompiledVertexArrays (); + } m_pNext = NULL; m_pPieceInfo = pPieceInfo; @@ -205,7 +173,7 @@ void Piece::SetPieceInfo(PieceInfo* pPieceInfo) void Piece::FileLoad(File* file, char* name) { - PIECE_KEY *node; + LC_PIECE_KEY *node; unsigned char version, ch; file->ReadByte(&version, 1); @@ -370,7 +338,7 @@ void Piece::FileLoad(File* file, char* name) void Piece::FileSave(File* file, Group* pGroups) { - PIECE_KEY *node; + LC_PIECE_KEY *node; unsigned char ch = 8; // LeoCAD 0.70 unsigned long n; @@ -614,7 +582,7 @@ void Piece::Move(unsigned short nTime, bool bAnimation, bool bAddKey, float x, f void Piece::ChangeKey(unsigned short nTime, bool bAnimation, bool bAddKey, float* param, unsigned char nKeyType) { - PIECE_KEY *node, *poskey = NULL, *newpos = NULL; + LC_PIECE_KEY *node, *poskey = NULL, *newpos = NULL; if (bAnimation) node = m_pAnimationKeys; else @@ -653,7 +621,7 @@ void Piece::ChangeKey(unsigned short nTime, bool bAnimation, bool bAddKey, float void Piece::RemoveKeys() { - PIECE_KEY *node, *prev; + LC_PIECE_KEY *node, *prev; for (node = m_pInstructionKeys; node;) { @@ -718,7 +686,7 @@ void Piece::CompareBoundingBox(float box[6]) bool Piece::CalculatePositionRotation(unsigned short nTime, bool bAnimation, float pos[3], float rot[4]) { - PIECE_KEY *node, *prevpos = NULL, *nextpos = NULL, *prevrot = NULL, *nextrot = NULL; + LC_PIECE_KEY *node, *prevpos = NULL, *nextpos = NULL, *prevrot = NULL, *nextrot = NULL; if (bAnimation) node = m_pAnimationKeys; else diff --git a/common/piece.h b/common/piece.h index 849ec23..cafa5ec 100644 --- a/common/piece.h +++ b/common/piece.h @@ -21,12 +21,12 @@ class PieceInfo; typedef enum { PK_POSITION, PK_ROTATION } PK_TYPES; -typedef struct PIECE_KEY { +typedef struct LC_PIECE_KEY { unsigned short time; float param[4]; unsigned char type; - PIECE_KEY* next; -} PIECE_KEY; + LC_PIECE_KEY* next; +} LC_PIECE_KEY; class Piece : public Object { @@ -159,8 +159,8 @@ protected: void BuildDrawInfo(); // Position - PIECE_KEY* m_pAnimationKeys; - PIECE_KEY* m_pInstructionKeys; + LC_PIECE_KEY* m_pAnimationKeys; + LC_PIECE_KEY* m_pInstructionKeys; // Atributes PieceInfo* m_pPieceInfo; diff --git a/common/project.cpp b/common/project.cpp index c76af9e..2b070ab 100644 --- a/common/project.cpp +++ b/common/project.cpp @@ -20,36 +20,51 @@ #include "image.h" #include "system.h" #include "globals.h" +#include "minifig.h" typedef struct { - unsigned char n; - float dim [4][4]; -} VIEWPORT; - -static VIEWPORT viewports[14] = { - { 1, {{0, 0, 1, 1}, { 0, 0, 0, 0}, { 0, 0, 0, 0}, { 0, 0, 0, 0} }}, // 1 - { 2, {{0, 0, 0.5f, 1}, { 0.5f, 0, 0.5f, 1}, { 0, 0, 0, 0}, { 0, 0, 0, 0} }}, // 2V - { 2, {{0, 0, 1, 0.5f}, { 0, 0.5f, 1, 0.5f}, { 0, 0, 0, 0}, { 0, 0, 0, 0} }}, // 2H - { 2, {{0, 0, 1, 0.7f}, { 0, 0.7f, 1, 0.3f}, { 0, 0, 0, 0}, { 0, 0, 0, 0} }}, // 2HT - { 2, {{0, 0, 1, 0.3f}, { 0, 0.3f, 1, 0.7f}, { 0, 0, 0, 0}, { 0, 0, 0, 0} }}, // 2HB - { 3, {{0, 0, 0.5f, 0.5f}, { 0, 0.5f, 0.5f, 0.5f}, { 0.5f, 0, 0.5f, 1}, { 0, 0, 0, 0} }}, // 3VL - { 3, {{0, 0, 0.5f, 1}, { 0.5f, 0, 0.5f, 0.5f}, { 0.5f, 0.5f, 0.5f, 0.5f}, { 0, 0, 0, 0} }}, // 3VR - { 3, {{0, 0, 1, 0.5f}, { 0, 0.5f, 0.5f, 0.5f}, { 0.5f, 0.5f, 0.5f, 0.5f}, { 0, 0, 0, 0} }}, // 3HB - { 3, {{0, 0, 0.5f, 0.5f}, { 0.5f, 0, 0.5f, 0.5f}, { 0, 0.5f, 1, 0.5f}, { 0, 0, 0, 0} }}, // 3HT - { 4, {{0, 0, 0.3f, 0.3f}, { 0, 0.3f, 0.3f, 0.4f}, { 0, 0.7f, 0.3f, 0.3f}, { 0.3f, 0, 0.7f, 1} }}, // 4VL - { 4, {{0, 0, 0.7f, 1}, { 0.7f, 0, 0.3f, 0.3f}, { 0.7f, 0.3f, 0.3f, 0.4f}, { 0.7f, 0.7f, 0.3f, 0.3f} }}, // 4VR - { 4, {{0, 0, 1, 0.7f}, { 0, 0.7f, 0.3f, 0.3f}, { 0.3f, 0.7f, 0.4f, 0.3f}, { 0.7f, 0.7f, 0.3f, 0.3f} }}, // 4HT - { 4, {{0, 0, 0.3f, 0.3f}, { 0.3f, 0, 0.4f, 0.3f}, { 0.7f, 0, 0.3f, 0.3f}, { 0, 0.3f, 1, 0.7f} }}, // 4HB - { 4, {{0, 0, 0.5f, 0.5f}, { 0.5f, 0, 0.5f, 0.5f}, { 0, 0.5f, 0.5f, 0.5f}, { 0.5f, 0.5f, 0.5f, 0.5f} }}};// 4 + unsigned char n; + float dim [4][4]; +} LC_VIEWPORT; + +static LC_VIEWPORT viewports[14] = { + { 1, {{ 0.0f, 0.0f, 1.0f, 1.0f }, { 0.0f, 0.0f, 0.0f, 0.0f }, + { 0.0f, 0.0f, 0.0f, 0.0f }, { 0.0f, 0.0f, 0.0f, 0.0f } }}, // 1 + { 2, {{ 0.0f, 0.0f, 0.5f, 1.0f }, { 0.5f, 0.0f, 0.5f, 1.0f }, + { 0.0f, 0.0f, 0.0f, 0.0f }, { 0.0f, 0.0f, 0.0f, 0.0f } }}, // 2V + { 2, {{ 0.0f, 0.0f, 1.0f, 0.5f }, { 0.0f, 0.5f, 1.0f, 0.5f }, + { 0.0f, 0.0f, 0.0f, 0.0f }, { 0.0f, 0.0f, 0.0f, 0.0f } }}, // 2H + { 2, {{ 0.0f, 0.0f, 1.0f, 0.7f }, { 0.0f, 0.7f, 1.0f, 0.3f }, + { 0.0f, 0.0f, 0.0f, 0.0f }, { 0.0f, 0.0f, 0.0f, 0.0f } }}, // 2HT + { 2, {{ 0.0f, 0.0f, 1.0f, 0.3f }, { 0.0f, 0.3f, 1.0f, 0.7f }, + { 0.0f, 0.0f, 0.0f, 0.0f }, { 0.0f, 0.0f, 0.0f, 0.0f } }}, // 2HB + { 3, {{ 0.0f, 0.0f, 0.5f, 0.5f }, { 0.0f, 0.5f, 0.5f, 0.5f }, + { 0.5f, 0.0f, 0.5f, 1.0f }, { 0.0f, 0.0f, 0.0f, 0.0f } }}, // 3VL + { 3, {{ 0.0f, 0.0f, 0.5f, 1.0f }, { 0.5f, 0.0f, 0.5f, 0.5f }, + { 0.5f, 0.5f, 0.5f, 0.5f }, { 0.0f, 0.0f, 0.0f, 0.0f } }}, // 3VR + { 3, {{ 0.0f, 0.0f, 1.0f, 0.5f }, { 0.0f, 0.5f, 0.5f, 0.5f }, + { 0.5f, 0.5f, 0.5f, 0.5f }, { 0.0f, 0.0f, 0.0f, 0.0f } }}, // 3HB + { 3, {{ 0.0f, 0.0f, 0.5f, 0.5f }, { 0.5f, 0.0f, 0.5f, 0.5f }, + { 0.0f, 0.5f, 1.0f, 0.5f }, { 0.0f, 0.0f, 0.0f, 0.0f } }}, // 3HT + { 4, {{ 0.0f, 0.0f, 0.3f, 0.3f }, { 0.0f, 0.3f, 0.3f, 0.4f }, + { 0.0f, 0.7f, 0.3f, 0.3f }, { 0.3f, 0.0f, 0.7f, 1.0f } }}, // 4VL + { 4, {{ 0.0f, 0.0f, 0.7f, 1.0f }, { 0.7f, 0.0f, 0.3f, 0.3f }, + { 0.7f, 0.3f, 0.3f, 0.4f }, { 0.7f, 0.7f, 0.3f, 0.3f } }}, // 4VR + { 4, {{ 0.0f, 0.0f, 1.0f, 0.7f }, { 0.0f, 0.7f, 0.3f, 0.3f }, + { 0.3f, 0.7f, 0.4f, 0.3f }, { 0.7f, 0.7f, 0.3f, 0.3f } }}, // 4HT + { 4, {{ 0.0f, 0.0f, 0.3f, 0.3f }, { 0.3f, 0.0f, 0.4f, 0.3f }, + { 0.7f, 0.0f, 0.3f, 0.3f }, { 0.0f, 0.3f, 1.0f, 0.7f } }}, // 4HB + { 4, {{ 0.0f, 0.0f, 0.5f, 0.5f }, { 0.5f, 0.0f, 0.5f, 0.5f }, + { 0.0f, 0.5f, 0.5f, 0.5f }, { 0.5f, 0.5f, 0.5f, 0.5f } }}};// 4 typedef struct { - unsigned char width; - float left, right, top, bottom; -} TXFVERT; + unsigned char width; + float left, right, top, bottom; +} LC_TXFVERT; -static TXFVERT glyphs[93]; +static LC_TXFVERT glyphs[93]; ///////////////////////////////////////////////////////////////////////////// // Project construction/destruction @@ -177,9 +192,18 @@ Project::~Project() // Project attributes, general services // The main window should be created before calling this -bool Project::Initialize(int argc, char *argv[], char* libpath) +bool Project::Initialize(int argc, char *argv[], char* binpath, char* libpath) { - m_LibraryPath = libpath; + char *env_path; + bool loaded = false; + + strcpy (m_AppPath, binpath); + + // check if there's an environment variable for the piece library + env_path = getenv ("LEOCAD_LIB"); + if (env_path != NULL) + libpath = env_path; + m_strPathName[0] = 0; LC_IMAGE_OPTS imopts; @@ -208,7 +232,7 @@ bool Project::Initialize(int argc, char *argv[], char* libpath) if ((strcmp (param, "l") == 0) && ((i+1) < argc)) { i++; - m_LibraryPath = argv[i]; + libpath = argv[i]; } if (strcmp (param, "i") == 0) @@ -254,7 +278,15 @@ bool Project::Initialize(int argc, char *argv[], char* libpath) } } - if (LoadPieceLibrary() == false) + // if the user specified a library, try to load it first + if (libpath != NULL) + loaded = LoadPieceLibrary (libpath); + + // if we couldn't find a library, try the executable path + if (!loaded) + loaded = LoadPieceLibrary (binpath); + + if (!loaded) { #ifdef LC_WINDOWS SystemDoMessageBox("Cannot load piece library.", LC_MB_OK|LC_MB_ICONERROR); @@ -324,7 +356,7 @@ bool Project::Initialize(int argc, char *argv[], char* libpath) } // Load the piece library -bool Project::LoadPieceLibrary() +bool Project::LoadPieceLibrary (char *libpath) { FileDisk idx; char filename[LC_MAXPATH]; @@ -335,6 +367,8 @@ bool Project::LoadPieceLibrary() Texture* pTexture; int i; + strcpy (m_LibraryPath, libpath); + // Make sure that the path ends with a '/' i = strlen(m_LibraryPath)-1; if ((m_LibraryPath[i] != '\\') && (m_LibraryPath[i] != '/')) @@ -477,7 +511,7 @@ void Project::DeleteContents(bool bUndo) if (!bUndo) { - UNDOINFO* pUndo; + LC_UNDOINFO* pUndo; while (m_pUndoList) { @@ -1620,10 +1654,10 @@ void Project::SetPathName(char* lpszPathName, bool bAddToMRU) // Undo/Redo support // Save current state. -void Project::CheckPoint(char* text) +void Project::CheckPoint (const char* text) { - UNDOINFO* pTmp; - UNDOINFO* pUndo = new UNDOINFO; + LC_UNDOINFO* pTmp; + LC_UNDOINFO* pUndo = new LC_UNDOINFO; int i; strcpy(pUndo->strText, text); @@ -1957,7 +1991,7 @@ glLightfv(GL_LIGHT0, GL_SPECULAR, one); glEnable(GL_TEXTURE_2D); glEnable(GL_ALPHA_TEST); - TXFVERT* glyph; + LC_TXFVERT* glyph; glPushMatrix(); glTranslatef(1.4f*ds, 0, 0); @@ -2562,6 +2596,7 @@ void CCADDoc::AddPiece(CPiece* pNewPiece) else { m_pPieces = pPiece; + pPiece->m_pNext = NULL; } pPiece->AddConnections(m_pConnections); @@ -3976,7 +4011,7 @@ void Project::HandleCommand(LC_COMMANDS id, unsigned long nParam) case LC_EDIT_UNDO: case LC_EDIT_REDO: { - UNDOINFO *pUndo, *pTmp; + LC_UNDOINFO *pUndo, *pTmp; int i; if (id == LC_EDIT_UNDO) @@ -4401,6 +4436,7 @@ void Project::HandleCommand(LC_COMMANDS id, unsigned long nParam) pPiece->Initialize(pos[0], pos[1], pos[2], m_nCurStep, m_nCurFrame, m_nCurColor); pPiece->ChangeKey(1, false, false, rot, PK_ROTATION); pPiece->ChangeKey(1, true, false, rot, PK_ROTATION); + pPiece->UpdatePosition(1, false); } else pPiece->Initialize(0, 0, 0, m_nCurStep, m_nCurFrame, m_nCurColor); @@ -4437,78 +4473,35 @@ void Project::HandleCommand(LC_COMMANDS id, unsigned long nParam) case LC_PIECE_MINIFIG: { - LC_MINIFIGDLG_OPTS opts; - const unsigned char colors[15] = { 0, 6, 4, 22, 0, 0, 6, 6, 22, 22, 9, 9, 9, 22, 22 }; - const float pos[15][3] = { {0,0,3.84f},{0,0,3.84f},{0,0,2.88f},{0,0,2.96f},{0,0,2.56f},{0,0,2.56f},{0.9f,-0.62f,1.76f}, - {-0.9f,-0.62f,1.76f},{0.92f,-0.62f,1.76f},{-0.92f,-0.62f,1.76f},{0,0,1.6f},{0,0,1.12f},{0,0,1.12f},{0.42f,0,0},{-0.42f,0,0} }; - int i; - - for (i = 0; i < 15; i++) - { - opts.info[i] = NULL; - opts.colors[i] = colors[i]; - opts.pos[i][0] = pos[i][0]; - opts.pos[i][1] = pos[i][1]; - opts.pos[i][2] = pos[i][2]; - opts.rot[i][0] = 0; - opts.rot[i][1] = 0; - opts.rot[i][2] = 0; - } + MinifigWizard wiz; + int i; - for (i = 0; i < 13; i++) - { - if (i == 3 || i == 7 || i == 8 || i == 9) - continue; + if (SystemDoDialog (LC_DLG_MINIFIG, &wiz)) + { + SelectAndFocusNone(false); - PieceInfo* pInfo = FindPieceInfo(mfwpieceinfo[i].name); - if (pInfo == NULL) - continue; + for (i = 0; i < LC_MFW_NUMITEMS; i++) + { + if (wiz.m_Info[i] == NULL) + continue; - if (i == 6) - { - opts.info[6] = pInfo; - opts.info[7] = pInfo; - pInfo->AddRef(); - pInfo->AddRef(); - opts.rot[6][0] = 45; - opts.rot[6][2] = 90; - opts.rot[7][0] = 45; - opts.rot[7][2] = 90; - } - else - { - opts.info[i] = pInfo; - pInfo->AddRef(); - } - } + Matrix mat; + Piece* pPiece = new Piece(wiz.m_Info[i]); - if (SystemDoDialog(LC_DLG_MINIFIG, &opts)) - { - SelectAndFocusNone(false); + pPiece->Initialize(wiz.m_Position[i][0], wiz.m_Position[i][1], wiz.m_Position[i][2], + m_nCurStep, m_nCurFrame, wiz.m_Colors[i]); + pPiece->CreateName(m_pPieces); + AddPiece(pPiece); + pPiece->Select(); - for (i = 0; i < 15; i++) - { - if (opts.info[i] == NULL) - continue; + pPiece->ChangeKey(1, false, false, wiz.m_Rotation[i], PK_ROTATION); + pPiece->ChangeKey(1, true, false, wiz.m_Rotation[i], PK_ROTATION); + pPiece->UpdatePosition(m_bAnimation ? m_nCurFrame : m_nCurStep, m_bAnimation); + pPiece->CalculateConnections(m_pConnections, m_bAnimation ? m_nCurFrame : m_nCurStep, + m_bAnimation, false, true); - Matrix mat; - float rot[4]; - Piece* pPiece = new Piece(opts.info[i]); - - pPiece->Initialize(opts.pos[i][0], opts.pos[i][1], opts.pos[i][2], m_nCurStep, m_nCurFrame, opts.colors[i]); - pPiece->CreateName(m_pPieces); - AddPiece(pPiece); - pPiece->Select(); - - mat.CreateOld(0,0,0,opts.rot[i][0],opts.rot[i][1],opts.rot[i][2]); - mat.ToAxisAngle(rot); - pPiece->ChangeKey(1, false, false, rot, PK_ROTATION); - pPiece->ChangeKey(1, true, false, rot, PK_ROTATION); - pPiece->UpdatePosition(m_bAnimation ? m_nCurFrame : m_nCurStep, m_bAnimation); - pPiece->CalculateConnections(m_pConnections, m_bAnimation ? m_nCurFrame : m_nCurStep, m_bAnimation, false, true); - - SystemPieceComboAdd(opts.info[i]->m_strDescription); - } + SystemPieceComboAdd(wiz.m_Info[i]->m_strDescription); + } float bs[6] = { 10000, 10000, 10000, -10000, -10000, -10000 }; int max = 0; @@ -4543,9 +4536,9 @@ void Project::HandleCommand(LC_COMMANDS id, unsigned long nParam) CheckPoint("Minifig"); } - for (i = 0; i < 15; i++) - if (opts.info[i]) - opts.info[i]->DeRef(); + for (i = 0; i < LC_MFW_NUMITEMS; i++) + if (wiz.m_Info[i]) + wiz.m_Info[i]->DeRef(); } break; case LC_PIECE_ARRAY: @@ -5072,14 +5065,10 @@ void Project::HandleCommand(LC_COMMANDS id, unsigned long nParam) case LC_VIEW_ZOOMEXTENTS: { + // FIXME: rewrite using the FustrumCull function if (m_pPieces == 0) break; + bool bControl = Sys_KeyDown (KEY_CONTROL); - // HACK !!! HACK !!! HACK -#ifdef LC_WINDOWS - bool bControl = (GetKeyState(KEY_CONTROL) < 0); -#else - bool bControl = false; -#endif GLdouble modelMatrix[16], projMatrix[16]; float up[3], eye[3], target[3]; float bs[6] = { 10000, 10000, 10000, -10000, -10000, -10000 }; @@ -5881,6 +5870,11 @@ bool Project::StopTracking(bool bAccept) SetModifiedFlag(true); CheckPoint("Inserting"); } + else if (m_nCurAction == LC_ACTION_CURVE) + { + SetModifiedFlag(true); + CheckPoint("Inserting"); + } } else if (m_pTrackFile != NULL) { @@ -6483,7 +6477,7 @@ bool Project::OnKeyDown(char nKey, bool bControl, bool bShift) MoveSelectedObjects(axis[0], axis[1], axis[2]); SystemRedrawView(); SetModifiedFlag(true); - CheckPoint((bShift) ? (char*) "Rotating" : (char*) "Moving"); + CheckPoint((bShift) ? "Rotating" : "Moving"); SystemUpdateFocus(NULL, 0); ret = true; } break; @@ -6783,11 +6777,12 @@ void Project::OnLeftButtonDoubleClick(int x, int y, bool bControl, bool bShift) if (SetActiveViewport(x, y)) return; - LoadViewportProjection(); - glGetDoublev(GL_MODELVIEW_MATRIX, modelMatrix); - glGetDoublev(GL_PROJECTION_MATRIX, projMatrix); - glGetIntegerv(GL_VIEWPORT, viewport); + LoadViewportProjection (); + glGetDoublev (GL_MODELVIEW_MATRIX, modelMatrix); + glGetDoublev (GL_PROJECTION_MATRIX, projMatrix); + glGetIntegerv (GL_VIEWPORT, viewport); + // why this is here ? gluUnProject(x, y, 0.9, modelMatrix, projMatrix, viewport, &point[0], &point[1], &point[2]); m_fTrack[0] = (float)point[0]; m_fTrack[1] = (float)point[1]; m_fTrack[2] = (float)point[2]; @@ -7154,5 +7149,34 @@ void Project::OnMouseMove(int x, int y, bool bControl, bool bShift) SystemUpdateFocus(NULL, 0); SystemRedrawView(); } break; + /* + case LC_ACTION_CURVE: + { + float mouse = 10.0f/(21 - m_nMouse); + float dx = (ptx - m_fTrack[0])*mouse; + float dy = (pty - m_fTrack[1])*mouse; + float dz = (ptz - m_fTrack[2])*mouse; + Object *pObj = NULL; + Curve *pCurve; + + m_fTrack[0] = ptx; + m_fTrack[1] = pty; + m_fTrack[2] = ptz; + + for (pObj = m_pObjects; pObj != NULL; pObj = pObj->m_pNext) + if (pObj->IsSelected ()) + break; + + if (pObj == NULL) + break; + pCurve = (Curve*)pObj; + + pCurve->Move (1, m_bAnimation, false, dx, dy, dz); + pCurve->UpdatePosition(1, m_bAnimation); + + SystemUpdateFocus(NULL, 0); + SystemRedrawView(); + } break; + */ } } diff --git a/common/project.h b/common/project.h index 651c199..ff0ba4e 100644 --- a/common/project.h +++ b/common/project.h @@ -25,13 +25,13 @@ class Matrix; #include "file.h" -typedef struct UNDOINFO +typedef struct LC_UNDOINFO { - FileMem file; - char strText[21]; - UNDOINFO* pNext; - UNDOINFO() { pNext = NULL; }; -} UNDOINFO; + FileMem file; + char strText[21]; + LC_UNDOINFO* pNext; + LC_UNDOINFO() { pNext = NULL; }; +} LC_UNDOINFO; class Project { @@ -39,7 +39,7 @@ public: // Constructors Project(); ~Project(); - bool Initialize(int argc, char *argv[], char* libpath); + bool Initialize(int argc, char *argv[], char* binpath, char* libpath); // Attributes public: @@ -107,8 +107,9 @@ protected: char m_strComments[256]; // Piece library - bool LoadPieceLibrary(); - char* m_LibraryPath; // path to the library files + bool LoadPieceLibrary (char* libpath); + char m_LibraryPath[LC_MAXPATH]; // path to the library files + char m_AppPath[LC_MAXPATH]; // path to the LeoCAD executable int m_nPieceCount; // number of pieces PieceInfo* m_pPieceIdx; // index int m_nTextureCount; @@ -117,10 +118,10 @@ protected: int m_nMovedCount; // Undo support - UNDOINFO* m_pUndoList; - UNDOINFO* m_pRedoList; + LC_UNDOINFO* m_pUndoList; + LC_UNDOINFO* m_pRedoList; bool m_bUndoOriginal; - void CheckPoint(char* text); + void CheckPoint (const char* text); // Objects Piece* m_pPieces; diff --git a/common/system.h b/common/system.h index a41aff9..8a53939 100755 --- a/common/system.h +++ b/common/system.h @@ -46,8 +46,8 @@ void Sys_SetCursorPos (int x, int y); int Sys_MessageBox (const char* text, const char* caption="LeoCAD", int type=LC_MB_OK|LC_MB_ICONINFORMATION); - - +// Misc stuff +bool Sys_KeyDown (int key); diff --git a/common/typedefs.h b/common/typedefs.h index 4930cfb..fea9198 100644 --- a/common/typedefs.h +++ b/common/typedefs.h @@ -90,6 +90,7 @@ typedef enum { LC_ACTION_LIGHT, LC_ACTION_SPOTLIGHT, LC_ACTION_CAMERA, + LC_ACTION_CURVE, LC_ACTION_MOVE, LC_ACTION_ROTATE, LC_ACTION_ERASER, @@ -125,20 +126,6 @@ typedef struct unsigned short numentries; } CONNECTION_TYPE; -// Minifig Wizard information - -typedef enum { - MF_HAT, MF_HEAD, MF_TORSO, MF_NECK, MF_ARML, MF_ARMR, - MF_HAND, MF_TOOL, MF_HIPS, MF_LEGL, MF_LEGR, MF_SHOE -} MFW_TYPES; - -typedef struct { - char name[9]; - char description[32]; - int type; -} MFW_PIECEINFO; - - // Select by Name dialog data typedef enum @@ -263,16 +250,6 @@ typedef struct LC_IMAGEDLG_OPTS imdlg; } LC_HTMLDLG_OPTS; -// hat, head, torso, neck, arml, armr, handl, handr, tooll, -// toolr, hips, legl, legr, shoel, shoer -typedef struct -{ - PieceInfo* info[15]; - int colors[15]; - float pos[15][3]; - float rot[15][3]; -} LC_MINIFIGDLG_OPTS; - typedef struct { unsigned short n1DCount; -- cgit v1.2.3