Claw  1.7.3
targa_reader.tpp
Go to the documentation of this file.
1 /*
2  CLAW - a C++ Library Absolutely Wonderful
3 
4  CLAW is a free library without any particular aim but being useful to
5  anyone.
6 
7  Copyright (C) 2005-2011 Julien Jorge
8 
9  This library is free software; you can redistribute it and/or
10  modify it under the terms of the GNU Lesser General Public
11  License as published by the Free Software Foundation; either
12  version 2.1 of the License, or (at your option) any later version.
13 
14  This library is distributed in the hope that it will be useful,
15  but WITHOUT ANY WARRANTY; without even the implied warranty of
16  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
17  Lesser General Public License for more details.
18 
19  You should have received a copy of the GNU Lesser General Public
20  License along with this library; if not, write to the Free Software
21  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
22 
23  contact: julien.jorge@gamned.org
24 */
31 #include <limits>
32 #include <iterator>
33 
34 /*----------------------------------------------------------------------------*/
39 template< typename Pixel >
40 claw::graphic::targa::reader::file_input_buffer<Pixel>::file_input_buffer
41 ( std::istream& f )
42  : buffered_istream<std::istream>(f)
43 {
44 
45 } // targa::reader::file_input_buffer::file_input_buffer
46 
47 
48 
49 
50 //*****************************************************************************/
51 
52 
53 
54 
55 /*----------------------------------------------------------------------------*/
61 template< typename Pixel >
62 claw::graphic::targa::reader::mapped_file_input_buffer<Pixel>::
63 mapped_file_input_buffer
64 ( std::istream& f, const color_palette32& p )
65  : buffered_istream<std::istream>(f), m_palette(p)
66 {
67 
68 } // targa::reader::mapped_file_input_buffer::mapped_file_input_buffer
69 
70 
71 
72 
73 //*****************************************************************************/
74 
75 
76 
77 
78 /*----------------------------------------------------------------------------*/
85 template<typename InputBuffer>
86 claw::graphic::targa::reader::rle_targa_output_buffer<InputBuffer>::
87 rle_targa_output_buffer( image& img, bool up_down, bool left_right )
88  : m_image(img), m_x_inc(left_right ? 1 : -1), m_y_inc(up_down ? 1 : -1)
89 {
90  if (up_down)
91  m_y = 0;
92  else
93  m_y = m_image.height() - 1;
94 
95  if (left_right)
96  m_x = 0;
97  else
98  m_x = m_image.width() - 1;
99 } // targa::reader::rle_targa_output_buffer::rle_targa_output_buffer()
100 
101 /*----------------------------------------------------------------------------*/
107 template<typename InputBuffer>
108 void claw::graphic::targa::reader::rle_targa_output_buffer<InputBuffer>::fill
109 ( unsigned int n, rgba_pixel_8 pattern )
110 {
111  assert( (int)(m_x + m_x_inc * n) >= -1 );
112  assert( m_x + m_x_inc * n <= m_image.width() );
113 
114  const int bound = (int)m_x + m_x_inc * n;
115  int x = m_x;
116 
117  for ( ; x != bound; x += m_x_inc )
118  m_image[m_y][x] = pattern;
119 
120  adjust_position(x);
121 } // targa::reader::rle_targa_output_buffer::fill()
122 
123 /*----------------------------------------------------------------------------*/
129 template<typename InputBuffer>
130 void claw::graphic::targa::reader::rle_targa_output_buffer<InputBuffer>::copy
131 ( unsigned int n, input_buffer_type& buffer )
132 {
133  assert( (int)(m_x + m_x_inc * n) >= -1 );
134  assert( m_x + m_x_inc * n <= m_image.width() );
135 
136  const int bound = (int)m_x + m_x_inc * n;
137  int x = m_x;
138 
139  for ( ; x != bound; x += m_x_inc )
140  m_image[m_y][x] = buffer.get_pixel();
141 
142  adjust_position(x);
143 } // targa::reader::rle_targa_output_buffer::copy()
144 
145 /*----------------------------------------------------------------------------*/
149 template<typename InputBuffer>
150 bool claw::graphic::targa::reader::rle_targa_output_buffer<InputBuffer>::
151 completed() const
152 {
153  return ( (int)m_y == -1 ) || ( m_y == m_image.height() );
154 } // targa::reader::rle_targa_output_buffer::completed()
155 
156 /*----------------------------------------------------------------------------*/
165 template<typename InputBuffer>
166 void
167 claw::graphic::targa::reader::rle_targa_output_buffer<InputBuffer>::
168 adjust_position(int x)
169 {
170  if (x < 0)
171  {
172  m_x = m_image.width() - 1;
173  m_y += m_y_inc;
174  }
175  else if (x >= (int)m_image.width())
176  {
177  m_x = 0;
178  m_y += m_y_inc;
179  }
180  else
181  m_x = x;
182 } // targa::reader::rle_targa_output_buffer::adjust_position()
183 
184 
185 
186 //*****************************************************************************/
187 
188 
189 
190 /*----------------------------------------------------------------------------*/
196 template< typename InputBuffer, typename OutputBuffer >
197 void
198 claw::graphic::targa::reader::rle_targa_decoder<InputBuffer, OutputBuffer>::
199 read_mode( input_buffer_type& input, output_buffer_type& output )
200 {
201  this->m_mode = this->stop;
202  bool ok = !output.completed();
203 
204  if ( ok && (input.remaining() < 1) )
205  ok = input.read_more(1);
206 
207  if (ok)
208  {
209  char key = input.get_next();
210 
211  this->m_count = (key & 0x7F) + 1;
212 
213  if (key & 0x80) // compressed
214  {
215  this->m_mode = this->compressed;
216  this->m_pattern = input.get_pixel();
217  }
218  else
219  this->m_mode = this->raw;
220  }
221 } // targa::reader::rle_targa_decoder::read_mode()
222 
223 
224 
225 //*****************************************************************************/
226 
227 
228 /*----------------------------------------------------------------------------*/
236 template<typename Pixel>
237 void claw::graphic::targa::reader::load_color_mapped_raw
238 ( const header& h, std::istream& f, const color_palette32& palette )
239 {
240  /* We use a part of the rle framework but there isn't any compressed data
241  here. We only use the direct copy of the rle algorithm. */
242 
243  typedef mapped_file_input_buffer<Pixel> input_buffer_type;
244 
245  rle_targa_output_buffer<input_buffer_type> output
246  ( m_image, h.image_specification.up_down_oriented(),
247  h.image_specification.left_right_oriented() );
248  input_buffer_type input(f, palette);
249 
250  for ( unsigned int i=0; i!=m_image.height(); ++i )
251  output.copy( m_image.width(), input );
252 } // targa::reader::load_true_color_raw()
253 
254 /*----------------------------------------------------------------------------*/
262 template<typename Decoder>
263 void claw::graphic::targa::reader::decompress_rle_color_mapped
264 ( const header& h, std::istream& f, const color_palette32& palette )
265 {
266  Decoder decoder;
267  typename Decoder::output_buffer_type output_buffer
268  (m_image, h.image_specification.up_down_oriented(),
269  h.image_specification.left_right_oriented() );
270  typename Decoder::input_buffer_type input_buffer(f, palette);
271 
272  decoder.decode(input_buffer, output_buffer);
273 } // targa::reader::decompress_rle_color_mapped()
274 
275 /*----------------------------------------------------------------------------*/
282 template<typename Pixel>
283 void claw::graphic::targa::reader::load_true_color_raw
284 ( const header& h, std::istream& f )
285 {
286  assert(!h.color_map);
287 
288  /* We use a part of the rle framework but there isn't any compressed data
289  here. We only use the direct copy of the rle algorithm. */
290 
291  typedef file_input_buffer<Pixel> input_buffer_type;
292 
293  rle_targa_output_buffer<input_buffer_type> output
294  ( m_image, h.image_specification.up_down_oriented(),
295  h.image_specification.left_right_oriented() );
296  input_buffer_type input(f);
297 
298  for ( unsigned int i=0; i!=m_image.height(); ++i )
299  output.copy( m_image.width(), input );
300 } // targa::reader::load_true_color_raw()
301 
302 /*----------------------------------------------------------------------------*/
309 template<typename Decoder>
310 void claw::graphic::targa::reader::decompress_rle_true_color
311 ( const header& h, std::istream& f )
312 {
313  assert(!h.color_map);
314 
315  Decoder decoder;
316  typename Decoder::output_buffer_type output_buffer
317  (m_image, h.image_specification.up_down_oriented(),
318  h.image_specification.left_right_oriented() );
319  typename Decoder::input_buffer_type input_buffer(f);
320 
321  decoder.decode(input_buffer, output_buffer);
322 } // targa::reader::decompress_rle_true_color()
323 
324 /*----------------------------------------------------------------------------*/
330 template<typename Pixel>
331 void claw::graphic::targa::reader::load_palette_content
332 ( std::istream& f, color_palette32& palette ) const
333 {
334  file_input_buffer<Pixel> input(f);
335 
336  for (unsigned int i=0; i!=palette.size(); ++i)
337  palette[i] = input.get_pixel();
338 } // targa::reader::load_palette_content()