如何在 PHP 中將 PDF 文檔轉換為預覽圖像?

| | | | | | | | | | | | | | | | | | | | | | | | | | | | | | | |
然而,在這篇文章中,我們將把自己限制在一個小得多的例子上,即從給定的 PDF 文檔創建圖像的預覽。 “為什麼要預覽?,",你問。好吧,他的圖書館管理系統,她的在線電子書店,或者只是一些瘋狂的周末編程任務可能需要它。你認為你可以在你的項目中使用這個概念嗎?讓我在評論中知道。從頭開始實現完整的轉換算法已不再可能,因此我們將使用第三方庫來簡化我們的任務。我在此場景中發現有吸引力的技術基於以下工具:
  • Ghostscript:是一個命令行實用程序,可用於所有三個主要平台,即解釋 PostSript 和 PDF 文件的 Windows、Linux 和 Mac。您可以在他的 官方網站
  • ImageMagick:這是一個免費的開源軟件包,用於顯示、轉換和編輯光柵圖像和矢量圖像文件。它適用於大多數主要的編程語言,包括 PHP。這裡是快速概覽的標准文檔。
U唱 Ghostscript 要在您的項目中使用 Ghostscript,首先要安裝它。如果您在 Windows 上,請從下載頁面下載可執行文件。Linux 用戶可以通過默認的包管理器直接安裝 Ghostscript;
# RPM based distros, Fedora 26/27/28 $sudo dnf install ghostscript 
驗證使用此命令進行安裝,
$gs --version 
安裝後,導航到包含 PDF 文件的目錄並運行以下命令。
$gs -dSAFER -dBATCH -sDEVICE = jpeg -dTextAlphaBits = 4 -dGraphicsAlphaBits = 4 -dFirstPage = 1 -dLastPage = 1 -r300 -sOutputFile = preview.jpg input.pdf 這將創建文檔第一頁的圖像。讓我們來了解它的實際作用;
  • -sDEVICE:設置輸出圖像文件格式。
  • -sTEXTVAL,-sGRAPHICVAL:為生成的圖像設置抗鋸齒。有效值為 1、2 和 4。
  • -r {NUM}:設置圖像的分辨率(以 dpi 為單位)。
  • -sFirstPage, -sLastPage:設置要顯示的文檔的第一頁和最後一頁。
  • -sOutputFile:設置輸出的名稱文件。
  • input.pdf:這是用於轉換的實際 PDF 文檔。
現在,要在 PHP 中使用此命令,我們調用 exec() 函數。例如: exec ( "ls -l" , $output_str , $return_val ); foreach ( $output_str as $line ) { echo $line . "" ; }
?>;
這個例子在 Linux 上會執行 ls 並將所有目錄和文件打印到控制台。我們可以使用這個概念並從我們的 PHP 代碼中執行命令。我就是這樣做的;< tbody> function is_pdf ( $file ) { $file_content = file_get_contents ( $file ) ; if (preg_match ( " / ^% PDF- [0-1 ]. [0-9] + / " , $file_content )) { return true; } else { return false; } } function create_preview ( $file ) { <代碼>$output_format = "jpeg" ; $antialiasing = "4" ; $preview_page = <代碼>“1” <代碼>; $resolution = "300" ; $output_file = "preview.jpg" ; <代碼>
$exec_command = " gs -dSAFER -dBATCH -dNOPAUSE -sDEVICE = " . $output_format . "" ; $exec_command <代碼>。 = "- dTextAlphaBits =" . $antialiasing . "-dGraphicsAlphaBits =" . $antialiasing . "" ; $exec_command 。 = "-dFirstPage =" . $preview_page . "-dLastPage =" . $preview_page . "" ; $exec_command 。 = "-r" . $resolution . "" ; $exec_command 。 = "- sOutputFile =" . $output_file . "` " . $file . "` " ; echo " 正在執行命令..." ; exec ( $exec_command , $command_output , $ return_val ); foreach ( $command_output as $line ) { echo $line . "" ; } if (! $return_val ) { echo "預覽創建成功!!" ; } <代碼>其他 <代碼>{ echo “創建預覽時出錯。” ; } } function __ main __() { global $argv ; $input_file = $argv [1]; if (is_pdf ( $input_file )) { // 創建 PDF 預覽 create_preview ( $input_file ); } else { echo “輸入文件” . $input_file . “不是有效的 PDF 文檔。” ; } }
__ main __();
?>
執行之星帶有 __main __() 的 ts,它在命令行上接受 PDF 文件。它檢查輸入文件是否是有效的 PDF。如果有效,它將對輸入文件執行命令。
退出:
$php pdf_preview.php input.pdf 正在執行命令 ... GPL Ghostscript 9.22 (2017-10-04)版權所有 (C) 2017 Artifex Software, Inc. 保留所有權利。此軟件不提供任何擔保:有關詳細信息,請參閱文件 PUBLIC。正在處理第 1 頁到第 1 頁。第 1 頁預覽創建成功! 
使用 ImageMagick 像往常一樣,我們將首先在系統上安裝 ImageMagick 二進製文件。讓我們從依賴關係開始;
$sudo dnf install gcc php-devel php-pear 
然後安裝 ImageMagick;
$sudo dnf install ImageMagick ImageMagick-devel 
然後安裝 PHP 包裝類;
$sudo pecl install imagick $sudo bash -c "echo" extension = imagick.so "> /etc /php.d/imagick.ini "
如果您打算在 LAMP 架構中使用它,請考慮重新啟動 Apache Web 服務器;
$sudo service httpd restart 

現在我們的系統已經準備好了,我們可以在示例項目中使用 ImageMagick。腳本的基本功能保持不變。您所要做的就是將 create_preview() 函數的內容替換為以下代碼。function create_preview ( $file ) { $output_format = "jpeg" <代碼>; $preview_page = "1" ; <代碼> $resolution = "300" ; $output_file = "imagick_preview.jpg" ; echo " 正在獲取預覽... " ; $img_data = new Imagick(); $img_data -> setResolution ( <代碼>$resolution , $resolution ); $img_data -> readImage ( $file . "[" . ( $preview_page - 1). " ] " ); $img_data -> setImageFormat( $output_format ); file_put_contents ( $output_file , $img_data , FILE_USE_INCLUDE_PATH ); } 代碼是不言自明的。我們定義一個Imagick類型的實例,並設置各種參數,如分辨率、文件格式等。您要顯示的PDF頁面在文件名後稱為數組索引。例如:

第一頁:input.pdf [0] 第二頁:input.pdf [1]。 ... ... 第 N 頁:input.pdf [N - 1] 
Output:
$php pdf_preview.php input.pdf 獲取預覽 ... 你們中的一些人可能想知道為什麼在前一種方法上使用這種方法。好吧,我發現 ImageMagick 可以很好地匹配 PHP 代碼。編程中的命令行看起來不太好,有時會成為常識。但是,使用相同的配置集,Ghostscript 生成的圖像文件比 ImageMagick 生成的文件要小。我不確定這是否是由於一些優化問題,但這不是區別。選擇其中一個只是根據您自己的喜好。因此,這就是您為給定 PDF 文檔創建預覽的方式。我希望你從這篇文章中學到了一些新東西。您更喜歡哪種方法?有什麼進一步改進的建議嗎?隨時在評論中提及它們。