溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務(wù)條款》

怎么將PHP網(wǎng)頁導(dǎo)出為Word文件

發(fā)布時間:2021-02-05 09:37:55 來源:億速云 閱讀:264 作者:小新 欄目:web開發(fā)

這篇文章給大家分享的是有關(guān)怎么將PHP網(wǎng)頁導(dǎo)出為Word文件的內(nèi)容。小編覺得挺實用的,因此分享給大家做個參考,一起跟隨小編過來看看吧。

原理

一般,有2種方法可以導(dǎo)出doc文檔,一種是使用com,并且作為php的一個擴(kuò)展庫安裝到服務(wù)器上,然后創(chuàng)建一個com,調(diào)用它的方法。安裝過office的服務(wù)器可以調(diào)用一個叫word.application的com,可以生成word文檔,不過這種方式我不推薦,因為執(zhí)行效率比較低(我測試了一下,在執(zhí)行代碼的時候,服務(wù)器會真的去打開一個word客戶端)。理想的com應(yīng)該是沒有界面的,在后臺進(jìn)行數(shù)據(jù)轉(zhuǎn)換,這樣效果會比較好,但是這些擴(kuò)展一般需要收費。

第2種方法,就是用PHP將我們的doc文檔內(nèi)容直接寫入一個后綴為doc的文件中即可。使用這種方法不需要依賴第三方擴(kuò)展,而且執(zhí)行效率較高。

word本身的功能還是很強(qiáng)大的,它可以打開html格式的文件,并且能夠保留格式,即使后綴為doc,它也能識別正常打開。這就為我們提供了方便。但是有一個問題,html格式的文件中的圖片只有一個地址,真正的圖片是保存在其他地方的,也就是說,如果將HTML格式寫入doc中,那么doc中將不能包含圖片。那我們?nèi)绾蝿?chuàng)建包含圖片的doc文檔呢?我們可以使用和html很接近的mht格式。

mht格式和html很類似,只不過在mht格式中,外部鏈接進(jìn)來的文件,比如圖片、Javascript、CSS會被base64進(jìn)行編碼存儲。因此,單個mht文件就可以保存一個網(wǎng)頁中的所有資源,當(dāng)然,相比html,它的尺寸也會比較大。

mht格式能被word識別嗎?我將一個網(wǎng)頁保存成mht,然后修改后綴名為doc,再用word打開,OK,word也可以識別mht文件,并且可以顯示圖片。

好了,既然doc可以識別mht,下面就是考慮如何將圖片放入mht了。由于html代碼中的圖片的地址都是寫在img標(biāo)簽的src屬性中,因此,只要提取html代碼中的src屬性值,就可以獲得圖片地址。當(dāng)然,有可能您獲取到的是相對路徑,沒關(guān)系,加上URL的前綴,改成絕對路徑就可以了。有了圖片地址,我們就可以通過file_get_content函數(shù)獲取到圖片文件的具體內(nèi)容,然后調(diào)用base64_encode函數(shù)將文件內(nèi)容編碼成base64編碼,最后插入到mht文件的合適位置即可。

最后,我們有兩種方法將文件發(fā)送給客戶端,一種是先在服務(wù)器端生成一個doc文檔,然后將這個doc文檔的地址記錄下來,最后,通過header("location:xx.doc");就可以讓客戶端下載這個doc。還有一種是直接發(fā)送html請求,修改HTML協(xié)議的header部分,將它的content-type設(shè)置為application/doc,將content-disposition設(shè)置為attachment,后面跟上文件名,發(fā)送完html協(xié)議以后,直接將文件內(nèi)容發(fā)送給客戶端,也可以讓客戶端下載到這個doc文檔。

實現(xiàn)

通過以上的原理介紹,相信大家應(yīng)該對實現(xiàn)的過程有個初步的了解了,下面我給出一個導(dǎo)出函數(shù),這個函數(shù)可以將HTML代碼導(dǎo)出成一個mht文檔,參數(shù)有3個,其中后2個為可選參數(shù)

content:要轉(zhuǎn)換的HTML代碼

absolutePath: 如果HTML代碼中的圖片地址都是相對路徑,那么這個參數(shù)就是HTML代碼中缺少的絕對路徑。

isEraseLink:是否去掉HTML代碼中的超鏈接

返回值為mht的文件內(nèi)容,您可以通過file_put_content將它保存成后綴名為doc的文件

這個函數(shù)的主要功能其實就是分析HTML代碼中的所有圖片地址,并且依次下載下來。獲取到了圖片的內(nèi)容以后,調(diào)用MhtFileMaker類,將圖片添加到mht文件中。具體的添加細(xì)節(jié),封裝在MhtFileMaker類中了。

PHP代碼

/** 
 * 根據(jù)HTML代碼獲取word文檔內(nèi)容 
 * 該函數(shù)依賴于類MhtFileMaker 
 *  
 * @param string $content HTML內(nèi)容 
 * @param bool $isEraseLink 是否去掉HTML內(nèi)容中的鏈接 
 */   
function  getWordDocument(  $content  ,  $absolutePath  =  ""  ,  $isEraseLink  = true )  
{  
     $mht  =  new  MhtFileMaker();  
     if  ( $isEraseLink )  
         $content  = preg_replace( '/
  
     $images  =  array ();  
     $files  =  array ();  
     $matches  =  array ();  
     //這個算法要求src后的屬性值必須使用引號括起來   
     if  ( preg_match_all( '/
    {  
         $arrPath  =  $matches [1];  
         for  (  $i =0; $i < count ( $arrPath ); $i ++)  
        {  
             $path  =  $arrPath [ $i ];  
             $imgPath  = trim(  $path  );  
             if  (  $imgPath  != " " ) 
            { 
                $files[] = $imgPath; 
                if( substr($imgPath,0,7) == 'http://') 
                { 
                    //絕對鏈接,不加前綴 
                } 
                else 
                { 
                    $imgPath = $absolutePath.$imgPath; 
                } 
                $images[] = $imgPath; 
            } 
        } 
    } 
    $mht->AddContents(" tmp.html ",$mht->GetMimeType(" tmp.html "),$content); 
     
    for ( $i=0;$i<count($images);$i++) 
    { 
        $image = $images[$i]; 
        if ( @fopen($image , 'r') ) 
        { 
            $imgcontent = @file_get_contents( $image ); 
            if ( $content ) 
                $mht->AddContents($files[$i],$mht->GetMimeType($image),$imgcontent); 
        } 
        else 
        { 
            echo " file: ".$image."  not exist!
        }  
    }  
      
     return   $mht ->GetFile();  
}

使用方法:

PHP代碼

$fileContent  = getWordDocument( $content , "http://www.yoursite.com/Music/etc/" );  
$fp  =  fopen ( "test.doc" ,  'w' );  
fwrite( $fp ,  $fileContent );  
fclose( $fp );

其中,$content變量應(yīng)該是HTML源代碼,后面的鏈接應(yīng)該是能填補(bǔ)HTML代碼中圖片相對路徑的URL地址

注意,在使用這個函數(shù)之前,您需要先包含類MhtFileMaker,這個類可以幫助我們生成Mht文檔。

PHP代碼

<?php  
Class:        Mht File Maker 
Version:      1.2 beta 
Date:         02/11/2007 
Author:       Wudi 
Description:  The class can make .mht file. 
  
  
class  MhtFileMaker{  
     var   $config  =  array ();  
     var   $headers  =  array ();  
     var   $headers_exists  =  array ();  
     var   $files  =  array ();  
     var   $boundary ;  
     var   $dir_base ;  
     var   $page_first ;  
  
     function  MhtFile( $config  =  array ()){  
  
    }  
  
     function  SetHeader( $header ){  
         $this ->headers[] =  $header ;  
         $key  =  strtolower ( substr ( $header , 0,  strpos ( $header ,  ':' )));  
         $this ->headers_exists[ $key ] = TRUE;  
    }  
  
     function  SetFrom( $from ){  
         $this ->SetHeader( "From: $from" );  
    }  
  
     function  SetSubject( $subject ){  
         $this ->SetHeader( "Subject: $subject" );  
    }  
  
     function  SetDate( $date  = NULL,  $istimestamp  = FALSE){  
         if  ( $date  == NULL) {  
             $date  = time();  
        }  
         if  ( $istimestamp  == TRUE) {  
             $date  =  date ( 'D, d M Y H:i:s O' ,  $date );  
        }  
         $this ->SetHeader( "Date: $date" );  
    }  
  
     function  SetBoundary( $boundary  = NULL){  
         if  ( $boundary  == NULL) {  
             $this ->boundary =  '--'  .  strtoupper (md5(mt_rand())) .  '_MULTIPART_MIXED' ;  
        }  else  {  
             $this ->boundary =  $boundary ;  
        }  
    }  
  
     function  SetBaseDir( $dir ){  
         $this ->dir_base =  str_replace ( "\\", " / ", realpath($dir)); 
    } 
 
    function SetFirstPage($filename){ 
        $this->page_first = str_replace(" \\ ", " / ", realpath(" { $this ->dir_base}/ $filename ")); 
    } 
 
    function AutoAddFiles(){ 
        if (!isset($this->page_first)) { 
            exit ('Not set the first page.'); 
        } 
        $filepath = str_replace($this->dir_base, '', $this->page_first); 
        $filepath = 'http://mhtfile' . $filepath; 
        $this->AddFile($this->page_first, $filepath, NULL); 
        $this->AddDir($this->dir_base); 
    } 
 
    function AddDir($dir){ 
        $handle_dir = opendir($dir); 
        while ($filename = readdir($handle_dir)) { 
            if (($filename!='.') && ($filename!='..') && (" $dir / $filename "!=$this->page_first)) { 
                if (is_dir(" $dir / $filename ")) { 
                    $this->AddDir(" $dir / $filename "); 
                } elseif (is_file(" $dir / $filename ")) { 
                    $filepath = str_replace($this->dir_base, '', " $dir / $filename "); 
                    $filepath = 'http://mhtfile' . $filepath; 
                    $this->AddFile(" $dir / $filename ", $filepath, NULL); 
                } 
            } 
        } 
        closedir($handle_dir); 
    } 
 
    function AddFile($filename, $filepath = NULL, $encoding = NULL){ 
        if ($filepath == NULL) { 
            $filepath = $filename; 
        } 
        $mimetype = $this->GetMimeType($filename); 
        $filecont = file_get_contents($filename); 
        $this->AddContents($filepath, $mimetype, $filecont, $encoding); 
    } 
 
    function AddContents($filepath, $mimetype, $filecont, $encoding = NULL){ 
        if ($encoding == NULL) { 
            $filecont = chunk_split(base64_encode($filecont), 76); 
            $encoding = 'base64'; 
        } 
        $this->files[] = array('filepath' => $filepath, 
                               'mimetype' => $mimetype, 
                               'filecont' => $filecont, 
                               'encoding' => $encoding); 
    } 
 
    function CheckHeaders(){ 
        if (!array_key_exists('date', $this->headers_exists)) { 
            $this->SetDate(NULL, TRUE); 
        } 
        if ($this->boundary == NULL) { 
            $this->SetBoundary(); 
        } 
    } 
 
    function CheckFiles(){ 
        if (count($this->files) == 0) { 
            return FALSE; 
        } else { 
            return TRUE; 
        } 
    } 
 
    function GetFile(){ 
        $this->CheckHeaders(); 
        if (!$this->CheckFiles()) { 
            exit ('No file was added.'); 
        } 
        $contents = implode(" \r\n ", $this->headers); 
        $contents .= " \r\n "; 
        $contents .= " MIME-Version: 1.0\r\n "; 
        $contents .= " Content-Type: multipart/related;\r\n "; 
        $contents .= " \tboundary=\ "{$this->boundary}\";\r\n" ;  
         $contents  .=  "\ttype=\""  .  $this ->files[0][ 'mimetype' ] .  "\"\r\n" ;  
         $contents  .=  "X-MimeOLE: Produced By Mht File Maker v1.0 beta\r\n" ;  
         $contents  .=  "\r\n" ;  
         $contents  .=  "This is a multi-part message in MIME format.\r\n" ;  
         $contents  .=  "\r\n" ;  
         foreach  ( $this ->files  as   $file ) {  
             $contents  .=  "--{$this->boundary}\r\n" ;  
             $contents  .=  "Content-Type: $file[mimetype]\r\n" ;  
             $contents  .=  "Content-Transfer-Encoding: $file[encoding]\r\n" ;  
             $contents  .=  "Content-Location: $file[filepath]\r\n" ;  
             $contents  .=  "\r\n" ;  
             $contents  .=  $file [ 'filecont' ];  
             $contents  .=  "\r\n" ;  
        }  
         $contents  .=  "--{$this->boundary}--\r\n" ;  
         return   $contents ;  
    }  
  
     function  MakeFile( $filename ){  
         $contents  =  $this ->GetFile();  
         $fp  =  fopen ( $filename ,  'w' );  
        fwrite( $fp ,  $contents );  
        fclose( $fp );  
    }  
  
     function  GetMimeType( $filename ){  
         $pathinfo  =  pathinfo ( $filename );  
         switch  ( $pathinfo [ 'extension' ]) {  
             case   'htm' :  $mimetype  =  'text/html' ;  break ;  
             case   'html' :  $mimetype  =  'text/html' ;  break ;  
             case   'txt' :  $mimetype  =  'text/plain' ;  break ;  
             case   'cgi' :  $mimetype  =  'text/plain' ;  break ;  
             case   'php' :  $mimetype  =  'text/plain' ;  break ;  
             case   'css' :  $mimetype  =  'text/css' ;  break ;  
             case   'jpg' :  $mimetype  =  'image/jpeg' ;  break ;  
             case   'jpeg' :  $mimetype  =  'image/jpeg' ;  break ;  
             case   'jpe' :  $mimetype  =  'image/jpeg' ;  break ;  
             case   'gif' :  $mimetype  =  'image/gif' ;  break ;  
             case   'png' :  $mimetype  =  'image/png' ;  break ;  
             default :  $mimetype  =  'application/octet-stream' ;  break ;  
        }  
         return   $mimetype ;  
    }  
}  
?>

上面我們討論了通過mht文件,來實現(xiàn)PHP導(dǎo)出doc格式的。這種方法可以解決一個難題,就是使導(dǎo)出的doc文件中包含圖片,當(dāng)然,如果您要包含更多的內(nèi)容,比如CSS樣式表,只需要用正則表達(dá)式分析HTML代碼中的link標(biāo)簽,提取css樣式文件的地址,然后讀取并編碼成base64,最后加入到mht文件中就可以了。

感謝各位的閱讀!關(guān)于“怎么將PHP網(wǎng)頁導(dǎo)出為Word文件”這篇文章就分享到這里了,希望以上內(nèi)容可以對大家有一定的幫助,讓大家可以學(xué)到更多知識,如果覺得文章不錯,可以把它分享出去讓更多的人看到吧!

向AI問一下細(xì)節(jié)

免責(zé)聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進(jìn)行舉報,并提供相關(guān)證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI