<?php
namespace
YBL;
class
Gd{
private
$img
;
private
$info
;
public
$error
;
private
$gif_proess
;
public
function
__construct(
$gif_proess
=true) {
$this
->gif_proess=
$gif_proess
;
}
public
function
open(
$imgname
){
if
(!
is_file
(
$imgname
)){
$this
->error='不存在的图像文件';
return
false;
}
$info
=
getimagesize
(
$imgname
);
if
(false ===
$info
|| (IMAGETYPE_GIF ===
$info
[2] &&
empty
(
$info
['bits']))){
$this
->error='非法图像文件';
return
false;
}
$this
->info =
array
(
'width' =>
$info
[0],
'height' =>
$info
[1],
'type' => image_type_to_extension(
$info
[2], false),
'mime' =>
$info
['mime'],
);
empty
(
$this
->img) || imagedestroy(
$this
->img);
if
(('gif' ==
$this
->info['type'])&&
$this
->gif_proess){
$this
->gif =
new
GIF(
$imgname
);
$this
->img = imagecreatefromstring(
$this
->gif->image());
}
else
{
$fun
=
"imagecreatefrom{$this->info['type']}"
;
$this
->img =
$fun
(
$imgname
);
}
}
public
function
save(
$imgname
,
$type
= null,
$quality
=80,
$interlace
= true){
if
(
empty
(
$this
->img)){
$this
->error='没有可以被保存的图像资源';
return
false;
}
if
(
is_null
(
$type
)){
$type
=
$this
->info['type'];
}
else
{
$type
=
strtolower
(
$type
);
}
if
('jpeg' ==
$type
|| 'jpg' ==
$type
){
imageinterlace(
$this
->img,
$interlace
);
imagejpeg(
$this
->img,
$imgname
,
$quality
);
}
elseif
(('gif' ==
$type
)&& !
empty
(
$this
->gif)){
$this
->gif->save(
$imgname
);
}
else
{
$fun
= 'image'.
$type
;
$fun
(
$this
->img,
$imgname
);
}
}
public
function
width(){
if
(
empty
(
$this
->img)){
$this
->error='没有指定图像资源';
return
false;
}
return
$this
->info['width'];
}
public
function
height(){
if
(
empty
(
$this
->img)){
$this
->error='没有指定图像资源';
return
false;
}
return
$this
->info['height'];
}
public
function
type(){
if
(
empty
(
$this
->img)){
$this
->error='没有指定图像资源';
return
false;}
return
$this
->info['type'];
}
public
function
mime(){
if
(
empty
(
$this
->img)){
$this
->error='没有指定图像资源';
return
false;
}
return
$this
->info['mime'];
}
public
function
size(){
if
(
empty
(
$this
->img)) {
$this
->error='没有指定图像资源';
return
false;
}
return
array
(
$this
->info['width'],
$this
->info['height']);
}
public
function
crop(
$w
,
$h
,
$x
= 0,
$y
= 0,
$width
= null,
$height
= null){
if
(
empty
(
$this
->img)){
$this
->error='没有可以被裁剪的图像资源';
return
false;
}
empty
(
$width
) &&
$width
=
$w
;
empty
(
$height
) &&
$height
=
$h
;
do
{
$img
= imagecreatetruecolor(
$width
,
$height
);
$color
= imagecolorallocate(
$img
, 255, 255, 255);
imagefill(
$img
, 0, 0,
$color
);
imagecopyresampled(
$img
,
$this
->img, 0, 0,
$x
,
$y
,
$width
,
$height
,
$w
,
$h
);
imagedestroy(
$this
->img);
$this
->img =
$img
;
}
while
(!
empty
(
$this
->gif)&&
$this
->gifNext());
$this
->info['width'] =
$width
;
$this
->info['height'] =
$height
;
}
public
function
thumb(
$width
,
$height
,
$type
= Image::IMAGE_THUMB_SCALE){
if
(
empty
(
$this
->img)){
$this
->error='没有可以被缩略的图像资源';
return
false;
}
$w
=
$this
->info['width'];
$h
=
$this
->info['height'];
switch
(
$type
) {
case
Image::IMAGE_THUMB_SCALE:
if
(
$w
<
$width
&&
$h
<
$height
)
return
;
$scale
= min(
$width
/
$w
,
$height
/
$h
);
$x
=
$y
= 0;
$width
=
$w
*
$scale
;
$height
=
$h
*
$scale
;
break
;
case
Image::IMAGE_THUMB_CENTER:
$scale
= max(
$width
/
$w
,
$height
/
$h
);
$w
=
$width
/
$scale
;
$h
=
$height
/
$scale
;
$x
= (
$this
->info['width'] -
$w
)/2;
$y
= (
$this
->info['height'] -
$h
)/2;
break
;
case
Image::IMAGE_THUMB_NORTHWEST:
$scale
= max(
$width
/
$w
,
$height
/
$h
);
$x
=
$y
= 0;
$w
=
$width
/
$scale
;
$h
=
$height
/
$scale
;
break
;
case
Image::IMAGE_THUMB_SOUTHEAST:
$scale
= max(
$width
/
$w
,
$height
/
$h
);
$w
=
$width
/
$scale
;
$h
=
$height
/
$scale
;
$x
=
$this
->info['width'] -
$w
;
$y
=
$this
->info['height'] -
$h
;
break
;
case
Image::IMAGE_THUMB_FILLED:
if
(
$w
<
$width
&&
$h
<
$height
){
$scale
= 1;
}
else
{
$scale
= min(
$width
/
$w
,
$height
/
$h
);
}
$neww
=
$w
*
$scale
;
$newh
=
$h
*
$scale
;
$posx
= (
$width
-
$w
*
$scale
)/2;
$posy
= (
$height
-
$h
*
$scale
)/2;
do
{
$img
= imagecreatetruecolor(
$width
,
$height
);
$color
= imagecolorallocate(
$img
, 255, 255, 255);
imagefill(
$img
, 0, 0,
$color
);
imagecopyresampled(
$img
,
$this
->img,
$posx
,
$posy
,
$x
,
$y
,
$neww
,
$newh
,
$w
,
$h
);
imagedestroy(
$this
->img);
$this
->img =
$img
;
}
while
(!
empty
(
$this
->gif)&&
$this
->gifNext());
$this
->info['width'] =
$width
;
$this
->info['height'] =
$height
;
return
;
case
Image::IMAGE_THUMB_FIXED:
$x
=
$y
= 0;
break
;
default
:
$this
->error='不支持的缩略图裁剪类型';
return
false;
}
$this
->crop(
$w
,
$h
,
$x
,
$y
,
$width
,
$height
);
}
public
function
water(
$source
,
$locate
= Image::IMAGE_WATER_SOUTHEAST,
$alpha
=80){
if
(
empty
(
$this
->img)) {
$this
->error='没有可以被添加水印的图像资源';
return
false;
}
if
(!
is_file
(
$source
)) {
$this
->error='水印图像不存在';
return
false;
}
$info
=
getimagesize
(
$source
);
if
(false ===
$info
|| (IMAGETYPE_GIF ===
$info
[2] &&
empty
(
$info
['bits']))){
$this
->error='非法水印文件';
return
false;
}
$fun
= 'imagecreatefrom' . image_type_to_extension(
$info
[2], false);
$water
=
$fun
(
$source
);
imagealphablending(
$water
, true);
switch
(
$locate
) {
case
Image::IMAGE_WATER_SOUTHEAST:
$x
=
$this
->info['width'] -
$info
[0];
$y
=
$this
->info['height'] -
$info
[1];
break
;
case
Image::IMAGE_WATER_SOUTHWEST:
$x
= 0;
$y
=
$this
->info['height'] -
$info
[1];
break
;
case
Image::IMAGE_WATER_NORTHWEST:
$x
=
$y
= 0;
break
;
case
Image::IMAGE_WATER_NORTHEAST:
$x
=
$this
->info['width'] -
$info
[0];
$y
= 0;
break
;
case
Image::IMAGE_WATER_CENTER:
$x
= (
$this
->info['width'] -
$info
[0])/2;
$y
= (
$this
->info['height'] -
$info
[1])/2;
break
;
case
Image::IMAGE_WATER_SOUTH:
$x
= (
$this
->info['width'] -
$info
[0])/2;
$y
=
$this
->info['height'] -
$info
[1];
break
;
case
Image::IMAGE_WATER_EAST:
$x
=
$this
->info['width'] -
$info
[0];
$y
= (
$this
->info['height'] -
$info
[1])/2;
break
;
case
Image::IMAGE_WATER_NORTH:
$x
= (
$this
->info['width'] -
$info
[0])/2;
$y
= 0;
break
;
case
Image::IMAGE_WATER_WEST:
$x
= 0;
$y
= (
$this
->info['height'] -
$info
[1])/2;
break
;
default
:
if
(
is_array
(
$locate
)){
list(
$x
,
$y
) =
$locate
;
}
else
{
$this
->error='不支持的水印位置类型';
return
false;
}
}
do
{
$src
= imagecreatetruecolor(
$info
[0],
$info
[1]);
$color
= imagecolorallocate(
$src
, 255, 255, 255);
imagefill(
$src
, 0, 0,
$color
);
imagecopy(
$src
,
$this
->img, 0, 0,
$x
,
$y
,
$info
[0],
$info
[1]);
imagecopy(
$src
,
$water
, 0, 0, 0, 0,
$info
[0],
$info
[1]);
imagecopymerge(
$this
->img,
$src
,
$x
,
$y
, 0, 0,
$info
[0],
$info
[1],
$alpha
);
imagedestroy(
$src
);
}
while
(!
empty
(
$this
->gif)&&
$this
->gifNext());
imagedestroy(
$water
);
}
public
function
text(
$text
,
$font
,
$size
,
$color
= '#00000000',
$locate
= Image::IMAGE_WATER_SOUTHEAST,
$offset
= 0,
$angle
= 0){
if
(
empty
(
$this
->img)){
$this
->error='没有可以被写入文字的图像资源';
return
false;
}
if
(!
is_file
(
$font
)){
$this
->error=
"不存在的字体文件:{$font}"
;
return
false;
}
$info
= imagettfbbox(
$size
,
$angle
,
$font
,
$text
);
$minx
= min(
$info
[0],
$info
[2],
$info
[4],
$info
[6]);
$maxx
= max(
$info
[0],
$info
[2],
$info
[4],
$info
[6]);
$miny
= min(
$info
[1],
$info
[3],
$info
[5],
$info
[7]);
$maxy
= max(
$info
[1],
$info
[3],
$info
[5],
$info
[7]);
$x
=
$minx
;
$y
=
abs
(
$miny
);
$w
=
$maxx
-
$minx
;
$h
=
$maxy
-
$miny
;
switch
(
$locate
) {
case
Image::IMAGE_WATER_SOUTHEAST:
$x
+=
$this
->info['width'] -
$w
;
$y
+=
$this
->info['height'] -
$h
;
break
;
case
Image::IMAGE_WATER_SOUTHWEST:
$y
+=
$this
->info['height'] -
$h
;
break
;
case
Image::IMAGE_WATER_NORTHWEST:
break
;
case
Image::IMAGE_WATER_NORTHEAST:
$x
+=
$this
->info['width'] -
$w
;
break
;
case
Image::IMAGE_WATER_CENTER:
$x
+= (
$this
->info['width'] -
$w
)/2;
$y
+= (
$this
->info['height'] -
$h
)/2;
break
;
case
Image::IMAGE_WATER_SOUTH:
$x
+= (
$this
->info['width'] -
$w
)/2;
$y
+=
$this
->info['height'] -
$h
;
break
;
case
Image::IMAGE_WATER_EAST:
$x
+=
$this
->info['width'] -
$w
;
$y
+= (
$this
->info['height'] -
$h
)/2;
break
;
case
Image::IMAGE_WATER_NORTH:
$x
+= (
$this
->info['width'] -
$w
)/2;
break
;
case
Image::IMAGE_WATER_WEST:
$y
+= (
$this
->info['height'] -
$h
)/2;
break
;
default
:
if
(
is_array
(
$locate
)){
list(
$posx
,
$posy
) =
$locate
;
$x
+=
$posx
;
$y
+=
$posy
;
}
else
{
$this
->error='不支持的文字位置类型';
return
false;
}
}
if
(
is_array
(
$offset
)){
$offset
=
array_map
('
intval
',
$offset
);
list(
$ox
,
$oy
) =
$offset
;
}
else
{
$offset
=
intval
(
$offset
);
$ox
=
$oy
=
$offset
;
}
if
(
is_string
(
$color
) && 0 ===
strpos
(
$color
, '#')){
$color
=
str_split
(
substr
(
$color
, 1), 2);
$color
=
array_map
('hexdec',
$color
);
if
(
empty
(
$color
[3]) ||
$color
[3] > 127){
$color
[3] = 0;
}
}
elseif
(!
is_array
(
$color
)) {
$this
->error='错误的颜色值';
return
false;
}
do
{
$col
= imagecolorallocatealpha(
$this
->img,
$color
[0],
$color
[1],
$color
[2],
$color
[3]);
imagettftext(
$this
->img,
$size
,
$angle
,
$x
+
$ox
,
$y
+
$oy
,
$col
,
$font
,
$text
);
}
while
(!
empty
(
$this
->gif)&&
$this
->gifNext());
}
private
function
gifNext(){
ob_start();
ob_implicit_flush(0);
imagegif(
$this
->img);
$img
= ob_get_clean();
$this
->gif->image(
$img
);
$next
=
$this
->gif->nextImage();
if
(
$next
){
$this
->img = imagecreatefromstring(
$next
);
return
$next
;
}
else
{
$this
->img = imagecreatefromstring(
$this
->gif->image());
return
false;
}
}
public
function
__destruct() {
empty
(
$this
->img) || imagedestroy(
$this
->img);
}
}
class
GIF{
private
$frames
=
array
();
private
$delays
=
array
();
public
function
__construct(
$src
= null,
$mod
= 'url') {
if
(!
is_null
(
$src
)){
if
('url' ==
$mod
&&
is_file
(
$src
)){
$src
=
file_get_contents
(
$src
);
}
try
{
$de
=
new
GIFDecoder(
$src
);
$this
->frames =
$de
->GIFGetFrames();
$this
->delays =
$de
->GIFGetDelays();
}
catch
(Exception
$e
){
$this
->error='解码GIF图片出错';
return
false;
}
}
}
public
function
image(
$stream
= null){
if
(
is_null
(
$stream
)){
$current
= current(
$this
->frames);
return
false ===
$current
? reset(
$this
->frames) :
$current
;
}
else
{
$this
->frames[key(
$this
->frames)] =
$stream
;
}
}
public
function
nextImage(){
return
next(
$this
->frames);
}
public
function
save(
$gifname
){
$gif
=
new
GIFEncoder(
$this
->frames,
$this
->delays, 0, 2, 0, 0, 0, 'bin');
file_put_contents
(
$gifname
,
$gif
->GetAnimation());
}
}
Class GIFEncoder {
private
$GIF
=
"GIF89a"
;
private
$VER
=
"GIFEncoder V2.05"
;
private
$BUF
= Array ( );
private
$LOP
= 0;
private
$DIS
= 2;
private
$COL
= -1;
private
$IMG
= -1;
private
$ERR
= Array (
'ERR00' =>
"Does not supported function for only one image!"
,
'ERR01' =>
"Source is not a GIF image!"
,
'ERR02' =>
"Unintelligible flag "
,
'ERR03' =>
"Does not make animation from animated GIF source"
,
);
public
function
__construct(
$GIF_src
,
$GIF_dly
,
$GIF_lop
,
$GIF_dis
,
$GIF_red
,
$GIF_grn
,
$GIF_blu
,
$GIF_mod
) {
if
( !
is_array
(
$GIF_src
) && !
is_array
(
$GIF_dly
) ) {
printf (
"%s: %s"
,
$this
->VER,
$this
->ERR [ 'ERR00' ] );
exit
( 0 );
}
$this
->LOP = (
$GIF_lop
> -1 ) ?
$GIF_lop
: 0;
$this
->DIS = (
$GIF_dis
> -1 ) ? ( (
$GIF_dis
< 3 ) ?
$GIF_dis
: 3 ) : 2;
$this
->COL = (
$GIF_red
> -1 &&
$GIF_grn
> -1 &&
$GIF_blu
> -1 ) ?
(
$GIF_red
| (
$GIF_grn
<< 8 ) | (
$GIF_blu
<< 16 ) ) : -1;
for
(
$i
= 0;
$i
<
count
(
$GIF_src
);
$i
++ ) {
if
(
strToLower
(
$GIF_mod
) ==
"url"
) {
$this
->BUF [ ] =
fread
(
fopen
(
$GIF_src
[
$i
],
"rb"
),
filesize
(
$GIF_src
[
$i
] ) );
}
else
if
(
strToLower
(
$GIF_mod
) ==
"bin"
) {
$this
->BUF [ ] =
$GIF_src
[
$i
];
}
else
{
printf (
"%s: %s ( %s )!"
,
$this
->VER,
$this
->ERR [ 'ERR02' ],
$GIF_mod
);
exit
( 0 );
}
if
(
substr
(
$this
->BUF [
$i
], 0, 6 ) !=
"GIF87a"
&&
substr
(
$this
->BUF [
$i
], 0, 6 ) !=
"GIF89a"
) {
printf (
"%s: %d %s"
,
$this
->VER,
$i
,
$this
->ERR [ 'ERR01' ] );
exit
( 0 );
}
for
(
$j
= ( 13 + 3 * ( 2 << ( ord (
$this
->BUF [
$i
] { 10 } ) & 0x07 ) ) ),
$k
= TRUE;
$k
;
$j
++ ) {
switch
(
$this
->BUF [
$i
] {
$j
} ) {
case
"!"
:
if
( (
substr
(
$this
->BUF [
$i
], (
$j
+ 3 ), 8 ) ) ==
"NETSCAPE"
) {
printf (
"%s: %s ( %s source )!"
,
$this
->VER,
$this
->ERR [ 'ERR03' ], (
$i
+ 1 ) );
exit
( 0 );
}
break
;
case
";"
:
$k
= FALSE;
break
;
}
}
}
$this
->GIFAddHeader ( );
for
(
$i
= 0;
$i
<
count
(
$this
->BUF );
$i
++ ) {
$this
->GIFAddFrames (
$i
,
$GIF_dly
[
$i
] );
}
$this
->GIFAddFooter ( );
}
private
function
GIFAddHeader ( ) {
$cmap
= 0;
if
( ord (
$this
->BUF [ 0 ] { 10 } ) & 0x80 ) {
$cmap
= 3 * ( 2 << ( ord (
$this
->BUF [ 0 ] { 10 } ) & 0x07 ) );
$this
->GIF .=
substr
(
$this
->BUF [ 0 ], 6, 7 );
$this
->GIF .=
substr
(
$this
->BUF [ 0 ], 13,
$cmap
);
$this
->GIF .=
"!\377\13NETSCAPE2.0\3\1"
.
$this
->GIFWord (
$this
->LOP ) .
"\0"
;
}
}
private
function
GIFAddFrames (
$i
,
$d
) {
$Locals_str
= 13 + 3 * ( 2 << ( ord (
$this
->BUF [
$i
] { 10 } ) & 0x07 ) );
$Locals_end
=
strlen
(
$this
->BUF [
$i
] ) -
$Locals_str
- 1;
$Locals_tmp
=
substr
(
$this
->BUF [
$i
],
$Locals_str
,
$Locals_end
);
$Global_len
= 2 << ( ord (
$this
->BUF [ 0 ] { 10 } ) & 0x07 );
$Locals_len
= 2 << ( ord (
$this
->BUF [
$i
] { 10 } ) & 0x07 );
$Global_rgb
=
substr
(
$this
->BUF [ 0 ], 13,
3 * ( 2 << ( ord (
$this
->BUF [ 0 ] { 10 } ) & 0x07 ) ) );
$Locals_rgb
=
substr
(
$this
->BUF [
$i
], 13,
3 * ( 2 << ( ord (
$this
->BUF [
$i
] { 10 } ) & 0x07 ) ) );
$Locals_ext
=
"!\xF9\x04"
.
chr
( (
$this
->DIS << 2 ) + 0 ) .
chr
( (
$d
>> 0 ) & 0xFF ) .
chr
( (
$d
>> 8 ) & 0xFF ) .
"\x0\x0"
;
if
(
$this
->COL > -1 && ord (
$this
->BUF [
$i
] { 10 } ) & 0x80 ) {
for
(
$j
= 0;
$j
< ( 2 << ( ord (
$this
->BUF [
$i
] { 10 } ) & 0x07 ) );
$j
++ ) {
if
(
ord (
$Locals_rgb
{ 3 *
$j
+ 0 } ) == ( (
$this
->COL >> 16 ) & 0xFF ) &&
ord (
$Locals_rgb
{ 3 *
$j
+ 1 } ) == ( (
$this
->COL >> 8 ) & 0xFF ) &&
ord (
$Locals_rgb
{ 3 *
$j
+ 2 } ) == ( (
$this
->COL >> 0 ) & 0xFF )
) {
$Locals_ext
=
"!\xF9\x04"
.
chr
( (
$this
->DIS << 2 ) + 1 ) .
chr
( (
$d
>> 0 ) & 0xFF ) .
chr
( (
$d
>> 8 ) & 0xFF ) .
chr
(
$j
) .
"\x0"
;
break
;
}
}
}
switch
(
$Locals_tmp
{ 0 } ) {
case
"!"
:
$Locals_img
=
substr
(
$Locals_tmp
, 8, 10 );
$Locals_tmp
=
substr
(
$Locals_tmp
, 18,
strlen
(
$Locals_tmp
) - 18 );
break
;
case
","
:
$Locals_img
=
substr
(
$Locals_tmp
, 0, 10 );
$Locals_tmp
=
substr
(
$Locals_tmp
, 10,
strlen
(
$Locals_tmp
) - 10 );
break
;
}
if
( ord (
$this
->BUF [
$i
] { 10 } ) & 0x80 &&
$this
->IMG > -1 ) {
if
(
$Global_len
==
$Locals_len
) {
if
(
$this
->GIFBlockCompare (
$Global_rgb
,
$Locals_rgb
,
$Global_len
) ) {
$this
->GIF .= (
$Locals_ext
.
$Locals_img
.
$Locals_tmp
);
}
else
{
$byte
= ord (
$Locals_img
{ 9 } );
$byte
|= 0x80;
$byte
&= 0xF8;
$byte
|= ( ord (
$this
->BUF [ 0 ] { 10 } ) & 0x07 );
$Locals_img
{ 9 } =
chr
(
$byte
);
$this
->GIF .= (
$Locals_ext
.
$Locals_img
.
$Locals_rgb
.
$Locals_tmp
);
}
}
else
{
$byte
= ord (
$Locals_img
{ 9 } );
$byte
|= 0x80;
$byte
&= 0xF8;
$byte
|= ( ord (
$this
->BUF [
$i
] { 10 } ) & 0x07 );
$Locals_img
{ 9 } =
chr
(
$byte
);
$this
->GIF .= (
$Locals_ext
.
$Locals_img
.
$Locals_rgb
.
$Locals_tmp
);
}
}
else
{
$this
->GIF .= (
$Locals_ext
.
$Locals_img
.
$Locals_tmp
);
}
$this
->IMG = 1;
}
private
function
GIFAddFooter ( ) {
$this
->GIF .=
";"
;
}
private
function
GIFBlockCompare (
$GlobalBlock
,
$LocalBlock
,
$Len
) {
for
(
$i
= 0;
$i
<
$Len
;
$i
++ ) {
if
(
$GlobalBlock
{ 3 *
$i
+ 0 } !=
$LocalBlock
{ 3 *
$i
+ 0 } ||
$GlobalBlock
{ 3 *
$i
+ 1 } !=
$LocalBlock
{ 3 *
$i
+ 1 } ||
$GlobalBlock
{ 3 *
$i
+ 2 } !=
$LocalBlock
{ 3 *
$i
+ 2 }
) {
return
( 0 );
}
}
return
( 1 );
}
private
function
GIFWord (
$int
) {
return
(
chr
(
$int
& 0xFF ) .
chr
( (
$int
>> 8 ) & 0xFF ) );
}
public
function
GetAnimation ( ) {
return
(
$this
->GIF );
}
}
Class GIFDecoder {
private
$GIF_buffer
= Array ( );
private
$GIF_arrays
= Array ( );
private
$GIF_delays
= Array ( );
private
$GIF_stream
=
""
;
private
$GIF_string
=
""
;
private
$GIF_bfseek
= 0;
private
$GIF_screen
= Array ( );
private
$GIF_global
= Array ( );
private
$GIF_sorted
;
private
$GIF_colorS
;
private
$GIF_colorC
;
private
$GIF_colorF
;
public
function
__construct (
$GIF_pointer
) {
$this
->GIF_stream =
$GIF_pointer
;
$this
->GIFGetByte ( 6 );
$this
->GIFGetByte ( 7 );
$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 ) {
$this
->GIFGetByte ( 3 *
$this
->GIF_colorS );
$this
->GIF_global =
$this
->GIF_buffer;
}
for
(
$cycle
= 1;
$cycle
; ) {
if
(
$this
->GIFGetByte ( 1 ) ) {
switch
(
$this
->GIF_buffer [ 0 ] ) {
case
0x21:
$this
->GIFReadExtensions ( );
break
;
case
0x2C:
$this
->GIFReadDescriptor ( );
break
;
case
0x3B:
$cycle
= 0;
break
;
}
}
else
{
$cycle
= 0;
}
}
}
private
function
GIFReadExtensions ( ) {
$this
->GIFGetByte ( 1 );
for
( ; ; ) {
$this
->GIFGetByte ( 1 );
if
( (
$u
=
$this
->GIF_buffer [ 0 ] ) == 0x00 ) {
break
;
}
$this
->GIFGetByte (
$u
);
if
(
$u
== 4 ) {
$this
->GIF_delays [ ] = (
$this
->GIF_buffer [ 1 ] |
$this
->GIF_buffer [ 2 ] << 8 );
}
}
}
private
function
GIFReadDescriptor ( ) {
$GIF_screen
= Array ( );
$this
->GIFGetByte ( 9 );
$GIF_screen
=
$this
->GIF_buffer;
$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"
;
$this
->GIFPutByte (
$this
->GIF_screen );
if
(
$GIF_colorF
== 1 ) {
$this
->GIFGetByte ( 3 *
$GIF_size
);
$this
->GIFPutByte (
$this
->GIF_buffer );
}
else
{
$this
->GIFPutByte (
$this
->GIF_global );
}
$this
->GIF_string .=
chr
( 0x2C );
$GIF_screen
[ 8 ] &= 0x40;
$this
->GIFPutByte (
$GIF_screen
);
$this
->GIFGetByte ( 1 );
$this
->GIFPutByte (
$this
->GIF_buffer );
for
( ; ; ) {
$this
->GIFGetByte ( 1 );
$this
->GIFPutByte (
$this
->GIF_buffer );
if
( (
$u
=
$this
->GIF_buffer [ 0 ] ) == 0x00 ) {
break
;
}
$this
->GIFGetByte (
$u
);
$this
->GIFPutByte (
$this
->GIF_buffer );
}
$this
->GIF_string .=
chr
( 0x3B );
$this
->GIF_arrays [ ] =
$this
->GIF_string;
}
private
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;
}
private
function
GIFPutByte (
$bytes
) {
for
(
$i
= 0;
$i
<
count
(
$bytes
);
$i
++ ) {
$this
->GIF_string .=
chr
(
$bytes
[
$i
] );
}
}
public
function
GIFGetFrames ( ) {
return
(
$this
->GIF_arrays );
}
public
function
GIFGetDelays ( ) {
return
(
$this
->GIF_delays );
}
}