1 // -*- Mode: C++; tab-width:2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2 // vi:tw=80:et:ts=2:sts=2
3 //
4 // -----------------------------------------------------------------------
5 //
6 // This file is part of RLVM, a RealLive virtual machine clone.
7 //
8 // -----------------------------------------------------------------------
9 //
10 // Copyright (C) 2007 Elliot Glaysher
11 //
12 // This program is free software; you can redistribute it and/or modify
13 // it under the terms of the GNU General Public License as published by
14 // the Free Software Foundation; either version 3 of the License, or
15 // (at your option) any later version.
16 //
17 // This program is distributed in the hope that it will be useful,
18 // but WITHOUT ANY WARRANTY; without even the implied warranty of
19 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
20 // GNU General Public License for more details.
21 //
22 // You should have received a copy of the GNU General Public License
23 // along with this program; if not, write to the Free Software
24 // Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA.
25 //
26 // -----------------------------------------------------------------------
27
28 #ifndef SRC_SYSTEMS_BASE_GAN_GRAPHICS_OBJECT_DATA_H_
29 #define SRC_SYSTEMS_BASE_GAN_GRAPHICS_OBJECT_DATA_H_
30
31 #include <boost/serialization/access.hpp>
32 #include <boost/serialization/split_member.hpp>
33
34 #include <iosfwd>
35 #include <memory>
36 #include <string>
37 #include <vector>
38
39 #include "machine/rlmachine.h"
40 #include "machine/serialization.h"
41 #include "systems/base/graphics_object_data.h"
42
43 class Surface;
44 class System;
45 class RLMachine;
46 class GraphicsObject;
47
48 // -----------------------------------------------------------------------
49
50 // In-memory representation of a GAN file. Responsible for reading in,
51 // storing, and rendering GAN data as a GraphicsObjectData.
52 class GanGraphicsObjectData : public GraphicsObjectData {
53 public:
54 explicit GanGraphicsObjectData(System& system);
55 GanGraphicsObjectData(System& system,
56 const std::string& ganfile,
57 const std::string& imgfile);
58 virtual ~GanGraphicsObjectData();
59
60 void LoadGANData();
61
62 virtual int PixelWidth(const GraphicsObject& rendering_properties) override;
63 virtual int PixelHeight(const GraphicsObject& rendering_properties) override;
64
65 virtual GraphicsObjectData* Clone() const override;
66 virtual void Execute(RLMachine& machine) override;
67
IsAnimation()68 virtual bool IsAnimation() const override { return true; }
69 virtual void PlaySet(int set) override;
70
71 protected:
72 // Resets to the first frame.
73 virtual void LoopAnimation() override;
74
75 virtual std::shared_ptr<const Surface> CurrentSurface(
76 const GraphicsObject& go) override;
77 virtual Rect SrcRect(const GraphicsObject& go) override;
78 virtual Point DstOrigin(const GraphicsObject& go) override;
79 virtual int GetRenderingAlpha(const GraphicsObject& go,
80 const GraphicsObject* parent) override;
81 virtual void ObjectInfo(std::ostream& tree) override;
82
83 private:
84 struct Frame {
85 int pattern;
86 int x;
87 int y;
88 int time;
89 int alpha;
90 int other; // No idea what this is.
91 };
92
93 typedef std::vector<std::vector<Frame>> AnimationSets;
94
95 void TestFileMagic(const std::string& file_name,
96 std::unique_ptr<char[]>& gan_data,
97 int file_size);
98 void ReadData(const std::string& file_name,
99 std::unique_ptr<char[]>& gan_data,
100 int file_size);
101 Frame ReadSetFrame(const std::string& filename, const char*& data);
102
103 // Throws an error on bad GAN files.
104 void ThrowBadFormat(const std::string& filename, const std::string& error);
105
106 System& system_;
107
108 AnimationSets animation_sets;
109
110 std::string gan_filename_;
111 std::string img_filename_;
112
113 int current_set_;
114 int current_frame_;
115 int time_at_last_frame_change_;
116
117 // The image the above coordinates map into.
118 std::shared_ptr<const Surface> image_;
119
120 friend class boost::serialization::access;
121
122 // boost::serialization forward declaration
123 template <class Archive>
124 void save(Archive& ar, const unsigned int file_version) const;
125
126 // boost::serialization forward declaration
127 template <class Archive>
128 void load(Archive& ar, const unsigned int file_version);
129
130 BOOST_SERIALIZATION_SPLIT_MEMBER()
131 };
132
133 // We need help creating GanGraphicsObjectData s since they don't have a
134 // default constructor:
135 namespace boost {
136 namespace serialization {
137 template <class Archive>
load_construct_data(Archive & ar,GanGraphicsObjectData * t,const unsigned int file_version)138 inline void load_construct_data(Archive& ar,
139 GanGraphicsObjectData* t,
140 const unsigned int file_version) {
141 ::new (t) GanGraphicsObjectData(Serialization::g_current_machine->system());
142 }
143 } // namespace serialization
144 } // namespace boost
145
146 #endif // SRC_SYSTEMS_BASE_GAN_GRAPHICS_OBJECT_DATA_H_
147