Home | Trees | Indices | Help |
|
---|
|
1 """ 2 :mod:`pyffi.formats.tga` --- Targa (.tga) 3 ========================================= 4 5 Implementation 6 -------------- 7 8 .. autoclass:: TgaFormat 9 :show-inheritance: 10 :members: 11 12 Regression tests 13 ---------------- 14 15 Read a TGA file 16 ^^^^^^^^^^^^^^^ 17 18 >>> # check and read tga file 19 >>> stream = open('tests/tga/test.tga', 'rb') 20 >>> data = TgaFormat.Data() 21 >>> data.inspect(stream) 22 >>> data.read(stream) 23 >>> stream.close() 24 >>> data.header.width 25 60 26 >>> data.header.height 27 20 28 29 Parse all TGA files in a directory tree 30 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 31 32 >>> for stream, data in TgaFormat.walkData('tests/tga'): 33 ... data.read(stream) 34 ... print(stream.name) 35 tests/tga/test.tga 36 tests/tga/test_footer.tga 37 38 Create a TGA file from scratch and write to file 39 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ 40 41 >>> data = TgaFormat.Data() 42 >>> from tempfile import TemporaryFile 43 >>> stream = TemporaryFile() 44 >>> data.write(stream) 45 >>> stream.close() 46 """ 47 48 # ***** BEGIN LICENSE BLOCK ***** 49 # 50 # Copyright (c) 2007-2011, Python File Format Interface 51 # All rights reserved. 52 # 53 # Redistribution and use in source and binary forms, with or without 54 # modification, are permitted provided that the following conditions 55 # are met: 56 # 57 # * Redistributions of source code must retain the above copyright 58 # notice, this list of conditions and the following disclaimer. 59 # 60 # * Redistributions in binary form must reproduce the above 61 # copyright notice, this list of conditions and the following 62 # disclaimer in the documentation and/or other materials provided 63 # with the distribution. 64 # 65 # * Neither the name of the Python File Format Interface 66 # project nor the names of its contributors may be used to endorse 67 # or promote products derived from this software without specific 68 # prior written permission. 69 # 70 # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 71 # "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 72 # LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 73 # FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE 74 # COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 75 # INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 76 # BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; 77 # LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER 78 # CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 79 # LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN 80 # ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 81 # POSSIBILITY OF SUCH DAMAGE. 82 # 83 # ***** END LICENSE BLOCK ***** 84 85 import struct, os, re 86 87 import pyffi.object_models.xml 88 import pyffi.object_models.common 89 import pyffi.object_models.xml.basic 90 import pyffi.object_models.xml.struct_ 91 import pyffi.object_models 92 import pyffi.utils.graph 93 from pyffi.utils.graph import EdgeFilter 9496 """This class implements the TGA format.""" 97 xml_file_name = 'tga.xml' 98 # where to look for tga.xml and in what order: 99 # TGAXMLPATH env var, or TgaFormat module directory 100 xml_file_path = [os.getenv('TGAXMLPATH'), os.path.dirname(__file__)] 101 # filter for recognizing tga files by extension 102 RE_FILENAME = re.compile(r'^.*\.tga$', re.IGNORECASE) 103 104 # basic types 105 int = pyffi.object_models.common.Int 106 uint = pyffi.object_models.common.UInt 107 byte = pyffi.object_models.common.Byte 108 ubyte = pyffi.object_models.common.UByte 109 char = pyffi.object_models.common.Char 110 short = pyffi.object_models.common.Short 111 ushort = pyffi.object_models.common.UShort 112 float = pyffi.object_models.common.Float 113 PixelData = pyffi.object_models.common.UndecodedData 114 171299 300 if __name__ == '__main__': 301 import doctest 302 doctest.testmod() 303176211178 data = data 179 if data.header.image_type in (TgaFormat.ImageType.INDEXED, 180 TgaFormat.ImageType.RGB, 181 TgaFormat.ImageType.GREY): 182 self.children = [ 183 TgaFormat.Pixel(argument=data.header.pixel_size) 184 for i in xrange(data.header.width 185 * data.header.height)] 186 for pixel in self.children: 187 pixel.read(stream, data) 188 else: 189 self.children = [] 190 count = 0 191 while count < data.header.width * data.header.height: 192 pixel = TgaFormat.RLEPixels( 193 argument=data.header.pixel_size) 194 pixel.read(stream, data) 195 self.children.append(pixel) 196 count += pixel.header.count + 1197199 data = data 200 for child in self.children: 201 child.arg = data.header.pixel_size 202 child.write(stream, data)203 207213215 self.header = TgaFormat.Header() 216 self.image = TgaFormat.Image() 217 self.footer = None # TgaFormat.Footer() is optional218220 """Quick heuristic check if stream contains Targa data, 221 by looking at the first 18 bytes. 222 223 :param stream: The stream to inspect. 224 :type stream: file 225 """ 226 # XXX todo: set some of the actual fields of the header 227 228 pos = stream.tell() 229 # read header 230 try: 231 id_length, colormap_type, image_type, \ 232 colormap_index, colormap_length, colormap_size, \ 233 x_origin, y_origin, width, height, \ 234 pixel_size, flags = struct.unpack("<BBBHHBHHHHBB", 235 stream.read(18)) 236 except struct.error: 237 # could not read 18 bytes 238 # not a TGA file 239 raise ValueError("Not a Targa file.") 240 finally: 241 stream.seek(pos) 242 # check if tga type is valid 243 # check pixel size 244 # check width and height 245 if not(image_type in (1, 2, 3, 9, 10, 11) 246 and pixel_size in (8, 24, 32) 247 and width <= 100000 248 and height <= 100000): 249 raise ValueError("Not a Targa file.")250 # this looks like a tga file! 251253 """Read a tga file. 254 255 :param stream: The stream from which to read. 256 :type stream: ``file`` 257 """ 258 # read the file 259 self.inspect(stream) # quick check 260 261 # header 262 self.header.read(stream, self) 263 264 # image 265 self.image.read(stream, self) 266 267 # check if we are at the end of the file 268 if not stream.read(1): 269 self.footer = None 270 return 271 272 # footer 273 stream.seek(-26, os.SEEK_END) 274 self.footer = TgaFormat.Footer() 275 self.footer.read(stream, self)276278 """Write a tga file. 279 280 :param stream: The stream to write to. 281 :type stream: ``file`` 282 """ 283 self.header.write(stream, self) 284 self.image.write(stream, self) 285 if self.footer: 286 self.footer.write(stream, self)287 293
Home | Trees | Indices | Help |
|
---|
Generated by Epydoc 3.0.1 on Mon Oct 10 19:04:07 2011 | http://epydoc.sourceforge.net |