Hacks: PNG transparency in xoops for ie

Posted by: ristoon 2004/4/19 14:47:35 7048 reads
Image transparency has been a problem for as long as gif has existed. with png the solution was here. But not quite. Microsoft with their internet explorer (ie) has not bean able to handle png transparency natively. So we all started the big wait and nothing happened. Until…..

This little script came along.
<?php 
/* 
*   replacePngTags - Justin Koivisto [W.A. Fisher Interactive] 7/1/2003 10:45AM 
*   Modified: 4/14/2004 9:38AM 

*   Modifies IMG and INPUT tags for MSIE5+ browsers to ensure that PNG-24 
*   transparencies are displayed correctly.  Replaces original SRC attribute 
*   with a transparent GIF file (spacer.gif) that is located in the same 
*   directory as the orignal image, and adds the STYLE attribute needed to for 
*   the browser. (Matching is case-insensitive. However, the width attribute 
*   should come before height. 

*   Also replaces code for PNG images specified as backgrounds via: 
*   background-image: url('image.png'); When using PNG images in the background, 
*   there is no need to use a spacer.gif image. (Only supports inline CSS at 
*   this point.) 

*   @param  $x  String containing the content to search and replace in. 
*   @result Returns the modified string. 
*/ 
function replacePngTags($x){ 
    
$arr2=array(); 
    
// make sure that we are only replacing for the Windows versions of Internet 
    // Explorer 5+ 
    
$msie='/msies([5-9]).?[0-9]*.*(win)/i'
    if(!isset(
$_SERVER['HTTP_USER_AGENT']) || 
        !
preg_match($msie,$_SERVER['HTTP_USER_AGENT']) || 
        
preg_match('/opera/i',$_SERVER['HTTP_USER_AGENT'])) 
        return 
$x

    
// find all the png images in backgrounds 
    
preg_match_all('/background-image:s*url('(.*.png)');/Uis',$x,$background); 
    for(
$i=0;$i<count($background[0]);$i++){ 
        
// simply replace: 
        //  "background-image: url('image.png');" 
        // with: 
        //  "filter:progid:DXImageTransform.Microsoft.AlphaImageLoader( 
        //      enabled=true, sizingMethod=scale src='image.png');" 
        // haven't tested to see if background-repeat styles work... 
        
$x=str_replace($background[0][$i],'filter:progid:DXImageTransform.'
                
'Microsoft.AlphaImageLoader(enabled=true, sizingMethod=scale'
                
' src=''.$background[1][$i].'');',$x); 

    } 

    
// OK, time to find all the IMG tags with ".png" in them 
    
preg_match_all('/<(input|img).*src=(\'|\")(.*.png)2.*>/Ui',$x,$images); 
    for(
$num_images=0;$num_images<count($images[0]);$num_images++){ 
        
$original=$images[0][$num_images]; 
        
$quote=$images[2][$num_images]; 
        
$atts=''; $width=0; $height=0; 
        // If the size is defined by styles, find 
        preg_match_all( 
            '/style=(\'|\"
).*(s?width:s?([0-9]+(px|%));).*'. 
            '
(s?height:s?([0-9]+(px|%));).*\1/Ui', 
            $images[0][$num_images],$arr2); 
        if(is_array($arr2) && count($arr2[0])){ 
            // size was defined by styles, get values 
            $width=$arr2[3][0]; 
            $height=$arr2[6][0]; 

            // remove the width and height from the style 
            $stripper=str_replace(' ','
s','/('.$arr2[2][0].'|'.$arr2[5][0].')/'); 
            // Also remove any empty style tags 
            $modified=preg_replace( 
                '
`style='.$arr2[1][0].$arr2[1][0].'`i', 
                '', 
                preg_replace($stripper,'',$original)); 
        } 
        // size was not defined by styles, get values 
        preg_match_all('
/width=(\'|\")?([0-9%]+)\1/i',$images[0][$num_images],$arr2); 
        if(
is_array($arr2) && count($arr2[0])){ 
            
$width=$arr2[2][0]; 
            if(
is_numeric($width)) 
                
$width.='px'

            
// remove this from the tag 
            
$modified=str_replace($arr2[0][0],'',$original); 
        } 
        
preg_match_all('/height=(\'|\")?([0-9%]+)\1?/i',$images[0][$num_images],$arr2); 
        if(is_array(
$arr2) && count($arr2[0])){ 
            
$height=$arr2[2][0]; 
            if(is_numeric(
$height)) 
                
$height.='px'; 

            // remove this from the tag 
            
$modified=str_replace($arr2[0][0],'',$modified); 
        } 

        preg_match_all('/src=(\'|\"
)([^"]+.png)\1/i',$images[0][$num_images],$arr2); 
        if(isset(
$arr2[2][0]) && !empty($arr2[1][0])) 
            
$image=$arr2[2][0]; 
        else 
            
$image=NULL; 

        // We do this so that we can put our spacer.gif image in the same 
        // directory as the image 
        
$tmp=split('[\/]',$image); 
        array_pop(
$tmp); 
        
$image_path=join('/',$tmp); 
        if(strlen(
$image_path)) $image_path.='/'; 

        // end quote is already supplied by originial src attribute 
        
$replace_src_with=$image_path.'spacer.gif'.$quote.' style="width'.$width. 
            '
height'.$height.'filterprogid:DXImageTransform.'. 
            '
Microsoft.AlphaImageLoader(src=''.$image.''sizingMethod='. 
            ''scale'
);"'; 

        // now create the new tag from the old 
        
$new_tag=str_replace($image.$quote,$replace_src_with
            str_replace('  ',' ',
$modified)); 

        // now place the new tag into the content 
        
$x=str_replace($original,$new_tag,$x); 
        
$i++; 
    } 
    return 
$x

?>


If you now would like png transparency to work on ie in xoops you do the following.
1) Save the above code as functions.php in the site root.
2) Open header.php in the same location and add the following code at the beginning of the file:
include_once XOOPS_ROOT_PATH.'/function.php';
    
ob_start();

3) Open footer.php in the same location and add following code at the very end of the file:
$x=ob_get_contents();
    
ob_end_clean();
    echo 
replacePngTags($x);

That’s it. Its all done. You now have png transparency enabled for ie in your xoops site.