]> Dogcows Code - chaz/yoink/blob - src/Moof/Tilemap.cc
85c117e271a4833266c95fcf2554102fced07bb4
[chaz/yoink] / src / Moof / Tilemap.cc
1
2 /*******************************************************************************
3
4 Copyright (c) 2009, Charles McGarvey
5 All rights reserved.
6
7 Redistribution and use in source and binary forms, with or without
8 modification, are permitted provided that the following conditions are met:
9
10 * Redistributions of source code must retain the above copyright notice,
11 this list of conditions and the following disclaimer.
12 * Redistributions in binary form must reproduce the above copyright notice,
13 this list of conditions and the following disclaimer in the documentation
14 and/or other materials provided with the distribution.
15
16 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
17 AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
18 IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
19 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
20 FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
21 DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
22 SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
23 CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
24 OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
25 OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
26
27 *******************************************************************************/
28
29 #include "Deserializer.hh"
30 #include "Mippleton.hh"
31 #include "OpenGL.hh"
32 #include "Serializable.hh"
33 #include "Tilemap.hh"
34
35
36 namespace Mf {
37
38
39 class Tilemap::Impl : public Mippleton<Impl>
40 {
41 static GLint filterFromString(const std::string& filter)
42 {
43 if (filter == "linear")
44 {
45 return GL_LINEAR;
46 }
47 else if (filter == "nearest_mipmap_nearest")
48 {
49 return GL_NEAREST_MIPMAP_NEAREST;
50 }
51 else if (filter == "nearest_mipmap_linear")
52 {
53 return GL_NEAREST_MIPMAP_LINEAR;
54 }
55 else if (filter == "linear_mipmap_nearest")
56 {
57 return GL_LINEAR_MIPMAP_NEAREST;
58 }
59 else if (filter == "linear_mipmap_linear")
60 {
61 return GL_LINEAR_MIPMAP_LINEAR;
62 }
63
64 return GL_NEAREST;
65 }
66
67 static GLint wrapFromString(const std::string& wrap)
68 {
69 if (wrap == "repeat")
70 {
71 return GL_REPEAT;
72 }
73
74 return GL_CLAMP;
75 }
76
77 public:
78 Impl(const std::string& name) :
79 Mippleton<Impl>(name),
80 magFilter_(GL_NEAREST),
81 minFilter_(GL_NEAREST),
82 nTilesS_(1),
83 nTilesT_(1),
84 wrapS_(GL_CLAMP),
85 wrapT_(GL_CLAMP)
86 {
87 loadFromFile();
88 }
89
90 void loadFromFile()
91 {
92 Deserializer deserializer(Tilemap::getPath(getName()));
93
94 SerializablePtr root = deserializer.deserialize();
95
96 if (root)
97 {
98 std::map<std::string,SerializablePtr> rootObj;
99
100 if (root->get(rootObj))
101 {
102 std::map<std::string,SerializablePtr>::iterator it;
103
104 if ((it = rootObj.find("tiles_s")) != rootObj.end())
105 {
106 long value;
107 if ((*it).second->get(value))
108 {
109 nTilesS_ = unsigned(value);
110 }
111 }
112 if ((it = rootObj.find("tiles_t")) != rootObj.end())
113 {
114 long value;
115 if ((*it).second->get(value))
116 {
117 nTilesT_ = unsigned(value);
118 }
119 }
120 if ((it = rootObj.find("min_filter")) != rootObj.end())
121 {
122 std::string value;
123 if ((*it).second->get(value))
124 {
125 minFilter_ = filterFromString(value);
126 }
127 }
128 if ((it = rootObj.find("mag_filter")) != rootObj.end())
129 {
130 std::string value;
131 if ((*it).second->get(value))
132 {
133 magFilter_ = filterFromString(value);
134 }
135 }
136 if ((it = rootObj.find("wrap_s")) != rootObj.end())
137 {
138 std::string value;
139 if ((*it).second->get(value))
140 {
141 wrapS_ = wrapFromString(value);
142 }
143 }
144 if ((it = rootObj.find("wrap_t")) != rootObj.end())
145 {
146 std::string value;
147 if ((*it).second->get(value))
148 {
149 wrapT_ = wrapFromString(value);
150 }
151 }
152 }
153 }
154 }
155
156 GLuint magFilter_;
157 GLuint minFilter_;
158 unsigned nTilesS_;
159 unsigned nTilesT_;
160 GLuint wrapS_;
161 GLuint wrapT_;
162 };
163
164
165 Tilemap::Tilemap(const std::string& name) :
166 Texture(name),
167 impl_(Tilemap::Impl::getInstance(name))
168 {
169 setMinFilter(impl_->minFilter_);
170 setMagFilter(impl_->magFilter_);
171 setWrapS(impl_->wrapS_);
172 setWrapT(impl_->wrapT_);
173 }
174
175
176 bool Tilemap::getTileCoords(unsigned index, Scalar coords[8]) const
177 {
178 // make sure the index represents a real tile
179 if (index >= impl_->nTilesS_ * impl_->nTilesT_) return false;
180
181 Scalar w = 1.0 / Scalar(impl_->nTilesS_);
182 Scalar h = 1.0 / Scalar(impl_->nTilesT_);
183
184 coords[0] = Scalar(index % impl_->nTilesS_) * w;
185 coords[1] = (Scalar(impl_->nTilesT_ - 1) -
186 Scalar(index / impl_->nTilesS_)) * h;
187 coords[2] = coords[0] + w;
188 coords[3] = coords[1];
189 coords[4] = coords[2];
190 coords[5] = coords[1] + h;
191 coords[6] = coords[0];
192 coords[7] = coords[5];
193
194 return true;
195 }
196
197 bool Tilemap::getTileCoords(unsigned index, Scalar coords[8],
198 Orientation orientation) const
199 {
200 if (getTileCoords(index, coords))
201 {
202 if (orientation & FLIP)
203 {
204 // this looks kinda weird, but it's just swapping in a way that
205 // doesn't require an intermediate variable
206 coords[1] = coords[5];
207 coords[5] = coords[3];
208 coords[3] = coords[7];
209 coords[7] = coords[5];
210 }
211 if (orientation & REVERSE)
212 {
213 coords[0] = coords[2];
214 coords[2] = coords[6];
215 coords[4] = coords[6];
216 coords[6] = coords[0];
217 }
218
219 return true;
220 }
221
222 return false;
223 }
224
225
226 std::string Tilemap::getPath(const std::string& name)
227 {
228 return Resource::getPath("tilemaps/" + name + ".json");
229 }
230
231
232 } // namespace Mf
233
234 /** vim: set ts=4 sw=4 tw=80: *************************************************/
235
This page took 0.037771 seconds and 3 git commands to generate.