OSDN Git Service

イニシャルコミット。
[marathon/ShapeFusion.git] / Shapes / ShapesElements.h
1 /*
2  * This file is part of ShapeFusion (Copyright 2000 Tito Dal Canton)
3  *
4  * ShapeFusion is free software; you can redistribute it and/or modify
5  * it under the terms of the GNU General Public License as published by
6  * the Free Software Foundation; either version 2 of the License, or
7  * (at your option) any later version.
8  *
9  * ShapeFusion is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with ShapeFusion; if not, write to the Free Software
16  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
17 */
18
19 #ifndef SHAPESLOADERS_H
20 #define SHAPESLOADERS_H
21
22 #include "wx/wxprec.h"
23 #ifndef WX_PRECOMP
24     #include "wx/wx.h"
25 #include "wx/clipbrd.h"
26 #endif
27 #include <vector>
28 using std::vector;
29 #include "../BigEndianBuffer.h"
30
31 #define COLLECTIONS_PER_FILE            32
32
33 #define SIZEOF_collection_header        32
34
35 class ShapesElement
36 {
37 private:
38         bool    mVerboseLoading;
39
40 protected:
41         // So that subclasses can change their status
42         bool    mGoodData;
43
44 public:
45         ShapesElement(bool verbose): mVerboseLoading(verbose), mGoodData(false) {}
46         ~ShapesElement(void) {}
47         
48         bool IsGood() const { return mGoodData; }
49         bool IsVerbose() const { return mVerboseLoading; }
50 };
51
52 // internal-use utility constants
53 enum {
54         COLL_VERSION_8BIT = 0,
55         COLL_VERSION_TRUECOLOR
56 };
57
58 // a color
59 class ShapesColor: public ShapesElement
60 {
61 private:
62         bool                    mLuminescent;
63         unsigned char   mValue;
64         unsigned short  mRed, mGreen, mBlue;
65
66 public:
67         // constructor/destructor
68         ShapesColor(bool verbose = false);
69         ShapesColor(unsigned int r, unsigned int g, unsigned int b, unsigned int value, bool luminescent = false, bool verbose = false);
70         ~ShapesColor(void);
71
72         // operators
73         bool operator==(const ShapesColor& other) const;
74         bool operator!=(const ShapesColor& other) const { return !(*this == other); }
75         // accessors
76         bool Luminescent(void) const { return mLuminescent; }
77         unsigned char Value(void) const { return mValue; }
78         unsigned short Red(void) const { return mRed; }
79         unsigned short Green(void) const { return mGreen; }
80         unsigned short Blue(void) const { return mBlue; }
81         void SetLuminescent(bool l) { mLuminescent = l; }
82         void SetRed(unsigned short c) { mRed = c; }
83         void SetGreen(unsigned short c) { mGreen = c; }
84         void SetBlue(unsigned short c) { mBlue = c; }
85         // utilities
86         BigEndianBuffer& SaveObject(BigEndianBuffer& buffer);
87         BigEndianBuffer& LoadObject(BigEndianBuffer& buffer);
88 };
89
90 // a color table
91 class ShapesColorTable: public ShapesElement
92 {
93 private:
94         vector<ShapesColor*>    mColors;
95
96 public:
97         ShapesColorTable(bool verbose = false);
98         ShapesColorTable(std::ifstream& ifs, wxString file_ext);
99         ~ShapesColorTable(void);
100
101         // operators
102         bool operator==(const ShapesColorTable& other) const;
103         bool operator!=(const ShapesColorTable& other) const { return !(*this == other); }
104
105         unsigned int ColorCount(void) const { return mColors.size(); }
106         ShapesColor *GetColor(unsigned int index) const { return mColors[index]; }
107         void InsertColor(ShapesColor *color) { mColors.push_back(color); }
108
109         unsigned int SizeInFile() const;
110
111         BigEndianBuffer& SaveObject(BigEndianBuffer& buffer);
112         BigEndianBuffer& LoadObject(BigEndianBuffer& buffer, unsigned int offset, unsigned int color_count);
113         BigEndianBuffer& SavePatch(BigEndianBuffer& buffer, int index);
114         int SaveToGimp(wxString path) const;
115         int SaveToPhotoshop(wxString path) const;
116 };
117
118 // a bitmap
119 class ShapesBitmap: public ShapesElement
120 {
121 private:
122         short                   mWidth, mHeight,
123                                         mBytesPerRow,   // width for uncompressed bitmaps, -1 for compressed ones
124                                         mBitDepth;              // 8
125         bool                    mColumnOrder,   // store in column-order format
126                                         mTransparent;
127         unsigned char   *mPixels;
128         // list of frames referencing this bitmap
129         vector<int>             mUsers;
130
131 public:
132         // constructor/destructor
133         ShapesBitmap(bool verbose = false);
134         ShapesBitmap(wxImage image, ShapesColorTable *colortable);
135         ~ShapesBitmap(void);
136
137         // operators
138         bool operator==(const ShapesBitmap& other) const;
139         bool operator!=(const ShapesBitmap& other) const { return !(*this == other); }
140
141         // accessors
142         short Width(void) const { return mWidth; }
143         short Height(void) const { return mHeight; }
144         short BytesPerRow(void) const { return mBytesPerRow; }
145         short BitDepth(void) const { return mBitDepth; }
146         bool IsColumnOrdered(void) const { return mColumnOrder; }
147         bool IsTransparent(void) const { return mTransparent; }
148         unsigned char* Pixels(void) const { return mPixels; }
149         // mutators
150         void SetWidth(short w) { mWidth = w; }
151         void SetHeight(short h) { mHeight = h; }
152         void SetBytesPerRow(short b) { mBytesPerRow = b; }
153         void SetBitDepth(short b) { mBitDepth = b; }
154         void SetColumnOrdered(bool b) { mColumnOrder = b; }
155         void SetTransparent(bool n) { mTransparent = n; }
156         // utilities
157         void ClipboardCopy(ShapesColorTable* colorTable) const;
158         void ClipboardPaste(ShapesColorTable* colorTable);
159         void FromImage(wxImage image, ShapesColorTable* colorTable);
160         unsigned int SizeInFile() const;
161         unsigned int SizeInPatch() const { return SizeInFile() + 12; }
162         BigEndianBuffer& SaveObject(BigEndianBuffer& buffer);
163         BigEndianBuffer& LoadObject(BigEndianBuffer& buffer, unsigned int offset);
164         BigEndianBuffer& SavePatch(BigEndianBuffer& buffer, int index);
165         void SaveToBMP(wxString path, ShapesColorTable *colorTable) const;
166         void SaveMaskToBMP(wxString path) const;
167 };
168
169 // a frame, aka "low level shape definition"
170 class ShapesFrame : public ShapesElement
171 {
172 private:
173         bool            mXmirror,
174                                 mYmirror,
175                                 mKeypointObscured;
176         float           mMinimumLightIntensity;
177         short           mBitmapIndex;
178         // bitmap scale factor. Computed when loading Shapes
179         // using world_* fields and associated bitmap dimensions
180         int                     mScaleFactor;
181         // logical origin
182         short           mOriginX, mOriginY;
183         // keypoint. Used in player legs shapes to specify where to attach torso shapes
184         short           mKeyX, mKeyY;
185         // FIXME do we really need to store these fields here?
186         // scaled bitmap rectangle in world coordinates. The physical bitmap rectangle
187         // is scaled around the frame origin position, which gets translated to (0,0).
188         // Computed as:
189         //   world_left = -scale_factor * origin_x
190         //   world_top = scale_factor * origin_y
191         //   world_right = scale_factor * (width - origin_x)
192         //   world_bottom = -scale_factor * (height - origin_y)
193         short           mWorldLeft, mWorldRight, mWorldTop, mWorldBottom;
194         // scaled keypoint position in world coordinates. Computed as:
195         //   world_x0 = scale_factor * (key_x - origin_x)
196         //   world_y0 = -scale_factor * (key_y - origin_y)
197         short           mWorldX0, mWorldY0;
198         // list of sequences referencing this frame
199         vector<int>     mUsers;
200
201 public:
202         // constructor/destructor
203         ShapesFrame(bool verbose = false);
204         ~ShapesFrame(void);
205         // operators
206         bool operator==(const ShapesFrame& other) const;
207         bool operator!=(const ShapesFrame& other) const { return !(*this == other); }
208         // accessors
209         bool IsXmirrored(void) const {return mXmirror;}
210         bool IsYmirrored(void) const {return mYmirror;}
211         bool IsKeypointObscured(void) const {return mKeypointObscured;}
212         float MinimumLightIntensity(void) const {return mMinimumLightIntensity;}
213         int ScaleFactor(void) const {return mScaleFactor;}
214         short BitmapIndex(void) const {return mBitmapIndex;}
215         short OriginX(void) const {return mOriginX;}
216         short OriginY(void) const {return mOriginY;}
217         short KeyX(void) const {return mKeyX;}
218         short KeyY(void) const {return mKeyY;}
219         short WorldLeft(void) const {return mWorldLeft;}
220         short WorldRight(void) const {return mWorldRight;}
221         short WorldTop(void) const {return mWorldTop;}
222         short WorldBottom(void) const {return mWorldBottom;}
223         short WorldX0(void) const {return mWorldX0;}
224         short WorldY0(void) const {return mWorldY0;}
225         // mutators
226         void SetXmirrored(bool b) {mXmirror = b;}
227         void SetYmirrored(bool b) {mYmirror = b;}
228         void SetKeypointObscured(bool b) {mKeypointObscured = b;}
229         void SetMinimumLightIntensity(float v) {mMinimumLightIntensity = v;}
230         void SetBitmapIndex(short i) {mBitmapIndex = i;}
231         void SetScaleFactor(int s) {mScaleFactor = s;}
232         void SetOriginX(short x) {mOriginX = x;}
233         void SetOriginY(short y) {mOriginY = y;}
234         void SetKeyX(short x) {mKeyX = x;}
235         void SetKeyY(short y) {mKeyY = y;}
236         void SetWorldLeft(short s) {mWorldLeft = s;}
237         void SetWorldRight(short s) {mWorldRight = s;}
238         void SetWorldTop(short s) {mWorldTop = s;}
239         void SetWorldBottom(short s)  {mWorldBottom = s;}
240         void SetWorldX0(short s) {mWorldX0 = s;}
241         void SetWorldY0(short s) {mWorldY0 = s;}
242         // utilities
243         unsigned int SizeInFile() const;
244         BigEndianBuffer& SaveObject(BigEndianBuffer& buffer);
245         BigEndianBuffer& SavePatch(BigEndianBuffer& buffer, int index);
246         BigEndianBuffer& LoadObject(BigEndianBuffer& buffer, unsigned int offset);
247 };
248
249 // sequence types (ShapesSequence.number_of_views). Nobody
250 // seems to know what these values really mean, they just
251 // tell the actual number of views in a redundant way
252 enum {
253         ANIMATED_1 = 1,         // simple isotropic animation
254         ANIMATED_2TO8 = 2,      // 8 view animation
255         ANIMATED_3TO4 = 3,      // 4 view animation
256         ANIMATED_4 = 4,         // 4 view animation
257         ANIMATED_5TO8 = 5,      // 8 view animation
258         ANIMATED_8 = 8,         // 8 view animation
259         ANIMATED_3TO5 = 9,      // 5 view animation
260         UNANIMATED = 10,        // no animation, choose a random frame
261         ANIMATED_5 = 11         // 5 view animation
262 };
263
264 // a sequence, aka "high level shape definition"
265 class ShapesSequence: public ShapesElement
266 {
267 private:
268         short                   mType;
269         unsigned short  mFlags;
270         wxString                mName;
271         short                   mNumberOfViews,
272                                         mFramesPerView,
273                                         mTicksPerFrame,
274                                         mKeyFrame,
275                                         mTransferMode,
276                                         mTransferModePeriod,
277                                         mFirstFrameSound,
278                                         mKeyFrameSound,
279                                         mLastFrameSound,
280                                         mPixelsToWorld,
281                                         mLoopFrame;
282 //FIXME This could be made private
283 public:
284         vector<short>   mFrameIndexes;
285
286 public:
287         // constructor/destructor
288         ShapesSequence(bool verbose = false);
289         ~ShapesSequence(void);
290         // operators
291         bool operator==(const ShapesSequence& other) const;
292         bool operator!=(const ShapesSequence& other) const { return !(*this == other); }
293         // accessors
294         short Type(void) const {return mType;}
295         unsigned short Flags(void) const {return mFlags;}
296         wxString Name(void) const {return mName;}
297         short NumberOfViews(void) const {return mNumberOfViews;}
298         short FramesPerView(void) const {return mFramesPerView;}
299         short TicksPerFrame(void) const {return mTicksPerFrame;}
300         short KeyFrame(void) const {return mKeyFrame;}
301         short TransferMode(void) const {return mTransferMode;}
302         short TransferModePeriod(void) const {return mTransferModePeriod;}
303         short FirstFrameSound(void) const {return mFirstFrameSound;}
304         short KeyFrameSound(void) const {return mKeyFrameSound;}
305         short LastFrameSound(void) const {return mLastFrameSound;}
306         short PixelsToWorld(void) const {return mPixelsToWorld;}
307         short LoopFrame(void) const {return mLoopFrame;}
308         unsigned int FrameIndexCount(void) const {return mFrameIndexes.size();}
309         short GetFrameIndex(unsigned int index) const {return mFrameIndexes[index];}
310         // mutators
311         void SetType(short t) {mType = t;}
312         void SetFlags(unsigned short f) {mFlags = f;}
313         void SetName(wxString name) {mName = name;}
314         void SetNumberOfViews(short n) {mNumberOfViews = n;}
315         void SetFramesPerView(short n) {mFramesPerView = n;}
316         void SetTicksPerFrame(short n) {mTicksPerFrame = n;}
317         void SetKeyFrame(short n) {mKeyFrame = n;}
318         void SetTransferMode(short n) {mTransferMode = n;}
319         void SetTransferModePeriod(short n) {mTransferModePeriod = n;}
320         void SetFirstFrameSound(short n) {mFirstFrameSound = n;}
321         void SetKeyFrameSound(short n) {mKeyFrameSound = n;}
322         void SetLastFrameSound(short n) {mLastFrameSound = n;}
323         void SetPixelsToWorld(short n) {mPixelsToWorld = n;}
324         void SetLoopFrame(short n) {mLoopFrame = n;}
325         void SetFrameIndex(unsigned int index, short value) {mFrameIndexes[index] = value;}     
326         // utilities
327         unsigned int SizeInFile() const;
328         unsigned int SizeInPatch() const { return SizeInFile() + 12; }
329         BigEndianBuffer& SaveObject(BigEndianBuffer& buffer);
330         BigEndianBuffer& LoadObject(BigEndianBuffer& buffer, long offset);
331         BigEndianBuffer& SavePatch(BigEndianBuffer& buffer, int index);
332 };
333
334 int ActualNumberOfViews(int t);
335
336 // chunk types. Bitmap encoding seems to depend on this setting
337 enum {
338         _unused_collection = 0, // plain
339         _wall_collection,               // plain
340         _object_collection,             // RLE
341         _interface_collection,  // plain
342         _scenery_collection             // RLE
343 };
344
345 // a Shapes chunk
346 class ShapesChunk: public ShapesElement
347 {
348 private:
349         short                   mVersion;       // COLLECTION_VERSION (same for all Marathon games)
350         short                   mType;
351         unsigned short  mFlags;         // unused; 0 in Durandal/Infinity, 1 in Rubicon and others
352         short                   mPixelsToWorld;
353
354         vector<ShapesColorTable*>       mColorTables;
355         vector<ShapesSequence*>         mSequences;
356         vector<ShapesFrame*>            mFrames;
357         vector<ShapesBitmap*>           mBitmaps;
358
359 public:
360         // constructor/destructor
361         ShapesChunk(bool verbose = false);
362         ~ShapesChunk(void);
363         void Clear(void);
364         bool operator==(const ShapesChunk& other) const;
365         bool operator!=(const ShapesChunk& other) const { return !(*this == other); }
366         // chunk data access
367         int Version() const {return mVersion;}
368         int Type() const {return mType;}
369         int Flags() const {return mFlags;}
370         int ScaleFactor() const {return mPixelsToWorld;}
371         unsigned int ColorTableCount() const {return mColorTables.size();}
372         unsigned int BitmapCount() const {return mBitmaps.size();}
373         unsigned int FrameCount() const {return mFrames.size();}
374         unsigned int SequenceCount() const {return mSequences.size();}
375         ShapesColorTable* GetColorTable(unsigned int index) const;
376         ShapesBitmap* GetBitmap(unsigned int index) const;
377         ShapesFrame* GetFrame(unsigned int index) const;
378         ShapesSequence* GetSequence(unsigned int index) const;
379         // chunk alteration
380         void InsertColorTable(ShapesColorTable *ct);
381         void DeleteColorTable(unsigned int ct);
382         void InsertBitmap(ShapesBitmap *b);
383         void DeleteBitmap(unsigned int b);
384         void InsertFrame(ShapesFrame *f);
385         void DeleteFrame(unsigned int f);
386         void InsertSequence(ShapesSequence *s);
387         void DeleteSequence(unsigned int s);
388         // utilities
389
390         void ClipboardCopy();
391         void ClipboardPaste();
392         unsigned int SizeInFile() const;
393         unsigned int SizeInPatch(const ShapesChunk* other) const;
394         BigEndianBuffer& SaveObject(BigEndianBuffer& stream);
395         BigEndianBuffer& SavePatch(BigEndianBuffer& stream, const ShapesChunk* other);
396         BigEndianBuffer& LoadObject(BigEndianBuffer& stream);
397         BigEndianBuffer& LoadPatch(BigEndianBuffer& buffer);
398 };
399
400 // a Shapes collection
401 class ShapesCollection: public ShapesElement
402 {
403 private:
404         short                   mStatus;
405         unsigned short  mFlags;
406         ShapesChunk             *mChunks[2];    // chunks for 8-bit and truecolor game
407
408 public:
409         ShapesCollection(bool verbose = false);
410         ~ShapesCollection(void);
411         // accessors
412         int Status(void) const {return mStatus;}
413         int Flags(void) const {return mFlags;}
414         // collection data access
415         bool Defined(unsigned int chunk) const;
416         int Version(unsigned int chunk) const;
417         int Type(unsigned int chunk) const;
418         int Flags(unsigned int chunk) const;
419         int ScaleFactor(unsigned int chunk) const;
420         int ColorTableCount(unsigned int chunk) const;
421         int BitmapCount(unsigned int chunk) const;
422         int FrameCount(unsigned int chunk) const;
423         int SequenceCount(unsigned int chunk) const;
424         ShapesColorTable* GetColorTable(unsigned int chunk, unsigned int index) const;
425         ShapesBitmap* GetBitmap(unsigned int chunk, unsigned int index) const;
426         ShapesFrame* GetFrame(unsigned int chunk, unsigned int index) const;
427         ShapesSequence* GetSequence(unsigned int chunk, unsigned int index) const;
428         ShapesChunk* GetChunk(unsigned int chunk) const;
429         // collection alteration
430         void InsertColorTable(ShapesColorTable *ct, unsigned int chunk);
431         void DeleteColorTable(unsigned int chunk, unsigned int ct);
432         void InsertBitmap(ShapesBitmap *b, unsigned int chunk);
433         void DeleteBitmap(unsigned int chunk, unsigned int b);
434         void InsertFrame(ShapesFrame *f, unsigned int chunk);
435         void DeleteFrame(unsigned int chunk, unsigned int f);
436         void InsertSequence(ShapesSequence *s, unsigned int chunk);
437         void DeleteSequence(unsigned int chunk, unsigned int s);
438         // utilities
439         unsigned int SizeInFile(unsigned int chunk) const;
440         
441 #if wxUSE_STD_IOSTREAM
442         wxSTD ostream& SaveObject(wxSTD ostream& stream);
443         wxSTD ostream& SavePatch(wxSTD ostream& stream, const ShapesCollection& other, int index, int depth);
444         wxSTD istream& LoadObject(wxSTD istream& stream);
445 #else
446         wxOutputStream& SaveObject(wxOutputStream& stream);
447         wxOutputStream& SavePatch(wxOutputStream& stream, const ShapesCollection& other, int index, int depth);
448         wxInputStream& LoadObject(wxInputStream& stream);
449 #endif
450         BigEndianBuffer& LoadPatch(BigEndianBuffer& buffer);
451 };
452
453 #endif
454