123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153 |
- //
- // Copyright 2012 Kenneth Riddile, Christian Henning
- //
- // Distributed under the Boost Software License, Version 1.0
- // See accompanying file LICENSE_1_0.txt or copy at
- // http://www.boost.org/LICENSE_1_0.txt
- //
- #ifndef BOOST_GIL_EXTENSION_IO_TARGA_DETAIL_SCANLINE_READ_HPP
- #define BOOST_GIL_EXTENSION_IO_TARGA_DETAIL_SCANLINE_READ_HPP
- #include <boost/gil/extension/io/targa/detail/is_allowed.hpp>
- #include <boost/gil/extension/io/targa/detail/reader_backend.hpp>
- #include <boost/gil/io/base.hpp>
- #include <boost/gil/io/bit_operations.hpp>
- #include <boost/gil/io/conversion_policies.hpp>
- #include <boost/gil/io/device.hpp>
- #include <boost/gil/io/reader_base.hpp>
- #include <boost/gil/io/row_buffer_helper.hpp>
- #include <boost/gil/io/scanline_read_iterator.hpp>
- #include <boost/gil/io/typedefs.hpp>
- #include <vector>
- namespace boost { namespace gil {
- ///
- /// Targa Scanline Reader
- ///
- template< typename Device >
- class scanline_reader< Device
- , targa_tag
- >
- : public reader_backend< Device
- , targa_tag
- >
- {
- public:
- using tag_t = targa_tag;
- using backend_t = reader_backend<Device, tag_t>;
- using this_t = scanline_reader<Device, tag_t>;
- using iterator_t = scanline_read_iterator<this_t>;
- //
- // Constructor
- //
- scanline_reader( Device& device
- , const image_read_settings< targa_tag >& settings
- )
- : backend_t( device
- , settings
- )
- {
- initialize();
- }
- /// Read part of image defined by View and return the data.
- void read( byte_t* dst, int pos )
- {
- // jump to scanline
- long offset = this->_info._offset
- + ( this->_info._height - 1 - pos ) * static_cast< long >( this->_scanline_length );
- this->_io_dev.seek( offset );
- read_row( dst );
- }
- /// Skip over a scanline.
- void skip( byte_t*, int )
- {
- this->_io_dev.seek( static_cast<long>( this->_scanline_length )
- , SEEK_CUR
- );
- }
- iterator_t begin() { return iterator_t( *this ); }
- iterator_t end() { return iterator_t( *this, this->_info._height ); }
- private:
- void initialize()
- {
- if( this->_info._color_map_type != targa_color_map_type::_rgb )
- {
- io_error( "scanline reader cannot read indexed targa files." );
- }
- if( this->_info._image_type != targa_image_type::_rgb )
- {
- io_error( "scanline reader cannot read this targa image type." );
- }
- switch( this->_info._image_type )
- {
- case targa_image_type::_rgb:
- {
- if( this->_info._color_map_type != targa_color_map_type::_rgb )
- {
- io_error( "Inconsistent color map type and image type in targa file." );
- }
- if( this->_info._color_map_length != 0 )
- {
- io_error( "Non-indexed targa files containing a palette are not supported." );
- }
- if( this->_info._screen_origin_bit )
- {
- io_error( "scanline reader cannot read targa files which have screen origin bit set." );
- }
- switch( this->_info._bits_per_pixel )
- {
- case 24:
- case 32:
- {
- this->_scanline_length = this->_info._width * ( this->_info._bits_per_pixel / 8 );
- // jump to first scanline
- this->_io_dev.seek( static_cast< long >( this->_info._offset ));
- break;
- }
- default:
- {
- io_error( "Unsupported bit depth in targa file." );
- break;
- }
- }
- break;
- }
- default:
- {
- io_error( "Unsupported image type in targa file." );
- break;
- }
- }
- }
- void read_row( byte_t* dst )
- {
- this->_io_dev.read( dst, this->_scanline_length );
- }
- };
- } // namespace gil
- } // namespace boost
- #endif
|