{"id":726,"date":"2014-11-27T17:59:46","date_gmt":"2014-11-27T17:59:46","guid":{"rendered":"http:\/\/www.budus.it\/Blog\/?p=726"},"modified":"2017-06-18T07:25:16","modified_gmt":"2017-06-18T07:25:16","slug":"php-convertire-e-proteggere-un-pdf-multipagina","status":"publish","type":"post","link":"https:\/\/www.budus.it\/Blog\/php-convertire-e-proteggere-un-pdf-multipagina\/","title":{"rendered":"PHP: Convertire e Proteggere un PDF multipagina"},"content":{"rendered":"<p>Ho avuto necessit\u00e0 di crearmi uno strumento, fruibile online, che mi consenta di caricare un PDF &#8211; generato da un programma di Office, quindi, con testo e immagini selezionabili e copiabile &#8211; in uno che invece non consenta la copia, anzi, deve trattarsi di pagine costituite da immagini (praticamente il testo e le immagini vengono convertite in immagini, una sorta di screenshot delle varie pagine) che, via via, risultano sempre pi\u00f9 offuscate fino a risultare illeggibili.<\/p>\n<p>Chiaramente le necessit\u00e0 di\u00a0<em>offuscamento<\/em>\u00a0varieranno a seconda delle proprie necessit\u00e0 ma, grosso modo, do qui qualche consiglio su come operare la cosa in PHP.<\/p>\n<p><!--more--><\/p>\n<p>La prima cosa da fare \u00e8 creare un oggetto &#8220;Imagick&#8221; del manuale che vogliamo convertire:<\/p>\n<pre>$imagick = new Imagick();<\/pre>\n<p>Dato che un PDF convertito da &#8220;testo in immagine&#8221; pu\u00f2 aumentare notevolmente le dimensioni, pu\u00f2 essere opportuno variarne la\u00a0<em>risoluzione<\/em>; io ho optato per una cosa di questo tipo:<\/p>\n<pre>$imagick-&gt;setResolution(50, 50);<\/pre>\n<p>ma, chiaramente, variando i valori &#8211; o non mettendo proprio la riga &#8211; si possono ottenere risultati diversi.<\/p>\n<p>Fatto questo bisogna caricare il file PDF, cos\u00ec:<\/p>\n<pre>$imagick-&gt;readImage('file.pdf');<\/pre>\n<p>Il file cos\u00ec caricato va a creare un array nell&#8217;oggetto &#8220;imagick&#8221; che pu\u00f2 essere elaborato in questo modo:<\/p>\n<pre>foreach ($imagick as $key =&gt; $image) {\r\n $image-&gt;adaptiveBlurImage($key \/ 5, $key \/ 5);<\/pre>\n<p>dove &#8220;$image&#8221; rappresenta la singola pagina e &#8220;$key&#8221; il numero di pagina.<\/p>\n<p>Tramite il metodo &#8220;<a title=\"adaptiveBlurImage\" href=\"http:\/\/php.net\/manual\/it\/imagick.adaptiveblurimage.php\" target=\"_blank\" rel=\"noopener\">adaptiveBlurImage<\/a>&#8221; si ottiene una sfocatura delle pagine; nel mio caso, dato che lego i valori di sfocatura al numero della pagina in elaborazione, ottengo un effetto che va ad aumentare progressivamente.<\/p>\n<p>Dato che, come dicevo sopra, la dimensione del PDF potrebbe aumentare considerevolmente (un file da 1Mb pu\u00f2 tranquillamente diventare 10Mb, cio\u00e8 10 volte tanto o peggio), ho optato per un troncamento del PDF dopo una certa pagina, in questo modo:<\/p>\n<pre> if ($key &gt;= 25) {\r\n  $image-&gt;removeImage();\r\n }\r\n}<\/pre>\n<p>Nel mio caso specifico, non contento, ho anche voluto aggiungere un testo (dopo un certo numero di pagina) in sovrapposizione e l&#8217;ho ottenuto con un codice come il seguente:<\/p>\n<pre>$draw = new ImagickDraw();\r\n$draw-&gt;setFillColor('#000000');\r\n$draw-&gt;setFontSize(16);\r\n$draw-&gt;setTextUnderColor('#ff000088');<\/pre>\n<p>nel quale ho preparato l&#8217;oggetto da sovrapporre alle varie pagine (quindi <strong>prima<\/strong> del ciclo &#8220;foreach&#8221; di cui sopra) e ho applicato il medesimo con:<\/p>\n<pre>$image-&gt;annotateImage($draw, 20, 170, 0, $messaggio);<\/pre>\n<p>dove &#8220;$messaggio&#8221; \u00e8 chiaramente una variabile che possiamo impostare in precedenza a piacimento, con tanto di &#8220;ritorno a capo&#8221; costituito dalla sequenza di escape &#8220;\\n&#8221;.<\/p>\n<p>Infine, per salvare il risultato, ho usato:<\/p>\n<pre>$imagick-&gt;writeImages('file_preview.pdf', true);<\/pre>\n<p>che serve per salvare\u00a0<strong>tutte le pagine PDF<\/strong> e non solo l&#8217;ultima.<\/p>\n<p>Infine, per farmi spedire il risultato, ho usato:<\/p>\n<pre>header(\"Content-type: Application\/pdf\");\r\nheader(\"Content-Description: PDF Protetto\");\r\nheader(\"Content-Length: \".filesize(\"file_preview.pdf\"));\r\nheader('Content-Disposition: attachment; filename=\"file_preview.pdf\"');\r\nreadfile(\"file_preview.pdf\");<\/pre>\n<p>Quello che si ottiene \u00e8 un PDF Protetto &#8211; il cui contenuto non pu\u00f2 essere copiato e nemmeno riconosciuto da un <a title=\"OCR\" href=\"http:\/\/it.wikipedia.org\/wiki\/Riconoscimento_ottico_dei_caratteri\" target=\"_blank\" rel=\"noopener\">OCR<\/a> &#8211; che si pu\u00f2 spedire come &#8220;anteprima&#8221; di quello originale.<\/p>\n","protected":false},"excerpt":{"rendered":"<p>Ho avuto necessit\u00e0 di crearmi uno strumento, fruibile online, che mi consenta di caricare un PDF &#8211; generato da un programma di Office, quindi, con testo e immagini selezionabili e copiabile &#8211; in uno che invece non consenta la copia, anzi, deve trattarsi di pagine costituite da immagini (praticamente il testo e le immagini vengono &hellip; <a href=\"https:\/\/www.budus.it\/Blog\/php-convertire-e-proteggere-un-pdf-multipagina\/\" class=\"more-link\">Leggi tutto<span class=\"screen-reader-text\"> &#8220;PHP: Convertire e Proteggere un PDF multipagina&#8221;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[57],"tags":[216,215,207],"class_list":["post-726","post","type-post","status-publish","format-standard","hentry","category-development","tag-imagemagick","tag-pdf","tag-php"],"_links":{"self":[{"href":"https:\/\/www.budus.it\/Blog\/wp-json\/wp\/v2\/posts\/726","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.budus.it\/Blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.budus.it\/Blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.budus.it\/Blog\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/www.budus.it\/Blog\/wp-json\/wp\/v2\/comments?post=726"}],"version-history":[{"count":3,"href":"https:\/\/www.budus.it\/Blog\/wp-json\/wp\/v2\/posts\/726\/revisions"}],"predecessor-version":[{"id":836,"href":"https:\/\/www.budus.it\/Blog\/wp-json\/wp\/v2\/posts\/726\/revisions\/836"}],"wp:attachment":[{"href":"https:\/\/www.budus.it\/Blog\/wp-json\/wp\/v2\/media?parent=726"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.budus.it\/Blog\/wp-json\/wp\/v2\/categories?post=726"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.budus.it\/Blog\/wp-json\/wp\/v2\/tags?post=726"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}