View file sys/inc/gifdecoder.php

File size: 7.54Kb
<?php
/*
:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
::
::	GIFDecoder Version 2.0 by László Zsidi, http://gifs.hu
::
::	Created at 2007. 02. 01. '07.47.AM'
::
::
::
::
::  Try on-line GIFBuilder Form demo based on GIFDecoder.
::
::  http://phpclasses.gifs.hu/demos/GifBuilder/
::
:::::::::::::::::::::::::::::::::::::::::::::::::::::::::::
*/
Class GIFDecoder
{
    var $GIF_buffer = Array( );
    var $GIF_arrays = Array( );
    var $GIF_delays = Array( );
    var $GIF_offset = Array( );
    var $GIF_stream = "";
    var $GIF_string = "";
    var $GIF_bfseek = 0;
    var $GIF_screen = Array( );
    var $GIF_global = Array( );
    var $GIF_sorted;
    var $GIF_colorS;
    var $GIF_colorC;
    var $GIF_colorF;
    /*
    :::::::::::::::::::::::::::::::::::::::::::::::::::
    ::
    ::	GIFDecoder ( $GIF_pointer )
    ::
    */
    function GIFDecoder( $GIF_pointer )
    {
        $this->GIF_stream = $GIF_pointer;
        GIFDecoder::GIFGetByte( 6 ); // GIF89a
        GIFDecoder::GIFGetByte( 7 ); // Logical Screen Descriptor
        $this->GIF_screen = $this->GIF_buffer;
        $this->GIF_colorF = $this->GIF_buffer[4] & 0x80 ? 1 : 0;
        $this->GIF_sorted = $this->GIF_buffer[4] & 0x08 ? 1 : 0;
        $this->GIF_colorC = $this->GIF_buffer[4] & 0x07;
        $this->GIF_colorS = 2 << $this->GIF_colorC;
        if ( $this->GIF_colorF == 1 ) {
            GIFDecoder::GIFGetByte( 3 * $this->GIF_colorS );
            $this->GIF_global = $this->GIF_buffer;
        }
        /*
         *
         *  05.06.2007.
         *  Made a little modification
         *
         *
         -	for ( $cycle = 1; $cycle; ) {
         +		if ( GIFDecoder::GIFGetByte ( 1 ) ) {
         -			switch ( $this->GIF_buffer [ 0 ] ) {
         -				case 0x21:
         -					GIFDecoder::GIFReadExtensions ( );
         -					break;
         -				case 0x2C:
         -					GIFDecoder::GIFReadDescriptor ( );
         -					break;
         -				case 0x3B:
         -					$cycle = 0;
         -					break;
         -		  	}
         -		}
         +		else {
         +			$cycle = 0;
         +		}
         -	}
         */
        for ( $cycle = 1; $cycle; ) {
            if ( GIFDecoder::GIFGetByte( 1 ) ) {
                switch ( $this->GIF_buffer[0] ) {
                    case 0x21:
                        GIFDecoder::GIFReadExtensions();
                        break;
                    case 0x2C:
                        GIFDecoder::GIFReadDescriptor();
                        break;
                    case 0x3B:
                        $cycle = 0;
                        break;
                }
            } else {
                $cycle = 0;
            }
        }
    }
    /*
    :::::::::::::::::::::::::::::::::::::::::::::::::::
    ::
    ::	GIFReadExtension ( )
    ::
    */
    function GIFReadExtensions( )
    {
        GIFDecoder::GIFGetByte( 1 );
        for ( ;; ) {
            GIFDecoder::GIFGetByte( 1 );
            if ( ( $u = $this->GIF_buffer[0] ) == 0x00 ) {
                break;
            }
            GIFDecoder::GIFGetByte( $u );
            /*
             * 07.05.2007.
             * Implemented a new line for a new function
             * to determine the originaly delays between
             * frames.
             *
             */
            if ( $u == 4 ) {
                $this->GIF_delays[] = ( $this->GIF_buffer[1] | $this->GIF_buffer[2] << 8 );
            }
        }
    }
    /*
    :::::::::::::::::::::::::::::::::::::::::::::::::::
    ::
    ::	GIFReadExtension ( )
    ::
    */
    function GIFReadDescriptor( )
    {
        $GIF_screen = Array( );
        GIFDecoder::GIFGetByte( 9 );
        $GIF_screen         = $this->GIF_buffer;
        /*
         * 11.19.2007.
         * Implemented a new line for a new function
         * to determine the originaly XY offsets between
         * frames.
         *
         */
        $this->GIF_offset[] = Array(
             ( $this->GIF_buffer[0] | $this->GIF_buffer[1] << 8 ),
            ( $this->GIF_buffer[2] | $this->GIF_buffer[3] << 8 ) 
        );
        $GIF_colorF         = $this->GIF_buffer[8] & 0x80 ? 1 : 0;
        if ( $GIF_colorF ) {
            $GIF_code = $this->GIF_buffer[8] & 0x07;
            $GIF_sort = $this->GIF_buffer[8] & 0x20 ? 1 : 0;
        } else {
            $GIF_code = $this->GIF_colorC;
            $GIF_sort = $this->GIF_sorted;
        }
        $GIF_size = 2 << $GIF_code;
        $this->GIF_screen[4] &= 0x70;
        $this->GIF_screen[4] |= 0x80;
        $this->GIF_screen[4] |= $GIF_code;
        if ( $GIF_sort ) {
            $this->GIF_screen[4] |= 0x08;
        }
        $this->GIF_string = "GIF87a";
        GIFDecoder::GIFPutByte( $this->GIF_screen );
        if ( $GIF_colorF == 1 ) {
            GIFDecoder::GIFGetByte( 3 * $GIF_size );
            GIFDecoder::GIFPutByte( $this->GIF_buffer );
        } else {
            GIFDecoder::GIFPutByte( $this->GIF_global );
        }
        $this->GIF_string .= chr( 0x2C );
        $GIF_screen[8] &= 0x40;
        GIFDecoder::GIFPutByte( $GIF_screen );
        GIFDecoder::GIFGetByte( 1 );
        GIFDecoder::GIFPutByte( $this->GIF_buffer );
        for ( ;; ) {
            GIFDecoder::GIFGetByte( 1 );
            GIFDecoder::GIFPutByte( $this->GIF_buffer );
            if ( ( $u = $this->GIF_buffer[0] ) == 0x00 ) {
                break;
            }
            GIFDecoder::GIFGetByte( $u );
            GIFDecoder::GIFPutByte( $this->GIF_buffer );
        }
        $this->GIF_string .= chr( 0x3B );
        /*
         *
         * Add frames into $GIF_stream array...
         *
         */
        $this->GIF_arrays[] = $this->GIF_string;
    }
    /*
    :::::::::::::::::::::::::::::::::::::::::::::::::::
    ::
    ::	GIFGetByte ( $len )
    ::
    */
    /*
     *
     *  05.06.2007.
     *  Made a little modification
     *
     *
     -	function GIFGetByte ( $len ) {
     -		$this->GIF_buffer = Array ( );
     -
     -		for ( $i = 0; $i < $len; $i++ ) {
     +			if ( $this->GIF_bfseek > strlen ( $this->GIF_stream ) ) {
     +				return 0;
     +			}
     -			$this->GIF_buffer [ ] = ord ( $this->GIF_stream { $this->GIF_bfseek++ } );
     -		}
     +		return 1;
     -	}
     */
    function GIFGetByte( $len )
    {
        $this->GIF_buffer = Array( );
        for ( $i = 0; $i < $len; $i++ ) {
            if ( $this->GIF_bfseek > strlen( $this->GIF_stream ) ) {
                return 0;
            }
            $this->GIF_buffer[] = ord( $this->GIF_stream{$this->GIF_bfseek++} );
        }
        return 1;
    }
    /*
    :::::::::::::::::::::::::::::::::::::::::::::::::::
    ::
    ::	GIFPutByte ( $bytes )
    ::
    */
    function GIFPutByte( $bytes )
    {
        for ( $i = 0; $i < count( $bytes ); $i++ ) {
            $this->GIF_string .= chr( $bytes[$i] );
        }
    }
    /*
    :::::::::::::::::::::::::::::::::::::::::::::::::::
    ::
    ::	PUBLIC FUNCTIONS
    ::
    ::
    ::	GIFGetFrames ( )
    ::
    */
    function GIFGetFrames( )
    {
        return ( $this->GIF_arrays );
    }
    /*
    :::::::::::::::::::::::::::::::::::::::::::::::::::
    ::
    ::	GIFGetDelays ( )
    ::
    */
    function GIFGetDelays( )
    {
        return ( $this->GIF_delays );
    }
    /*
    :::::::::::::::::::::::::::::::::::::::::::::::::::
    ::
    ::	GIFGetOffset ( )
    ::
    */
    function GIFGetOffset( )
    {
        return ( $this->GIF_offset );
    }
}
?>