Tips en Trucs 2015

PDF omzetten naar webpagina's

PDF en HTML zijn beide standaardformaten. Elk besturingssysteem kan beide documentformaten dan ook zonder probleem weergeven. PDF documenten hebben vaste pagina afmetingen (A4, Letter, enz.) terwijl webpagina's zich aanpassen aan de afmetingen waarop de pagina's worden weergegeven. Dit fundamentele verschil zorgt ervoor dat er steeds compromissen gesloten worden bij de conversie van het ene naar het andere formaat.

Er bestaan dan ook veel conversieprogramma's, met elke hun sterke en zwakke kanten. Met een bash script kan je echter hetzelfde bereiken. Het voordeel van een script is dat je het zelf kunt aanpassen en aanvullen. Je kunt met andere woorden zelf de zwakke punten verbeteren en/of niet gebruikte functies verwijderen.

Onderstaande script zorgt samen met enkele andere onderdelen, zoals enkele HTML bestanden voor de webpagina structuur, CSS- bestanden voor de opmaak, JavaScript bestanden voor de functionaliteit en PHP scripts voor het opslaan en ophalen van notities. Het bash script is de lijm die alles aan elkaar kleeft. Uit onderstaande bash script kan je technieken halen om zelf andere taken te automatiseren.

Ik gebruik het script om cursussen van collega's op het internet te plaatsen. Het script met de afhankelijke HTML, CSS, JavaScript en PHP bestanden kan je hier downloaden. Gebruik het, pas het aan, verbeter het, m.a.w. opensource. Ikzelf gebruik het script om cursussen van collega's voor eigen gebruik op internet te plaatsen. Veel plezier ermee.

#!/bin/bash
#
# pdf2html.sh - script convert a PDF document to editable webpages
# 2015-08 Dany Pinoy <pindanet.be>
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program.  If not, see <http://www.gnu.org/licenses/>.
#
# depends on convert, a part of ImageMagick
#
# Gebruik weergeven bij foutief gebruik
#   Er moet een te converteren PDF document meegegeven worden
#   En de afhankelijke onderdelen moeten aanwezig zijn (enkel de aanwezigheid van pdf.js wordt gecontroleerd)
if [ "$#" -ne 1 ] || [ ! -f pdf.js ]; then
    echo "Zorg dat alle afhankelijke bestanden in de doelmap staan."
    echo "Voer het script uit in de doelmap waarin de HTML pagina's terecht moeten komen."
    echo "Gebruik: pdf2html <pdf-file>"
    exit
fi
# Controleer of ImageMagick op de computer geïnstalleerd is
which convert
if [ $? -ne 0 ]; then
  echo "pdf2html gebruikt convert, een onderdeel van ImageMagick."
  echo "pdf2html kan convert niet vinden. Installeer ImageMagick."
  echo "Script afgebroken."
  exit
fi
# Indien nodig worden afhankelijkheden van derden opgehaald
if [ ! -f diff_match_patch.js ]; then
  wget https://google-diff-match-patch.googlecode.com/svn/trunk/javascript/diff_match_patch.js
fi
# Indien nodig worden afhankelijkheden van derden opgehaald en uitgepakt
if [ ! -d tinymce ]; then
  wget https://github.com/tinymce/tinymce-dist/archive/master.zip
  unzip master.zip
  rm master.zip
  mv tinymce-dist-master tinymce
fi
if [ ! -f tinymce/langs/nl.js ]; then
  wget http://www.tinymce.com/i18n/download.php?download=nl
  unzip -d tinymce/ download.php?download=nl
  rm download.php?download=nl
fi
# Indien nodig wordt een map aangemaakt om de naar het PNG formaat omgezette PDF pagina's op te slaan
if [ ! -d png ]; then
  mkdir png
fi
# PDF Document omzetten naar PNG afbeeldingen
#   $1 bevat het opgegeven PDF bestand
#   -density 150 bepaalt de kwaliteit (dpi) van de PNG bestanden
echo "Even geduld, bezig met omzetten van het PDF document, dit kan even duren..."
convert -density 150 "$1" png/page_%04d.png
if [ $? != 0 ]; then
  echo "Fout bij het omzetten van het PDF document naar PNG bestanden."
  echo "Dit script gebruikt ImageMagick, controleer of dit geïnstalleerd is."
  echo "Script afgebroken."
  exit
fi
# Maak een Inhoudsopgave in een HTML-bestand (tekstbestand) aan
  cat <<EOF > content.html
<span onclick="fold(this);" title="Inhoudsopgave">...</span>
EOF
# Maak een HTML pagina per pagina in het PDF document aan
page=0
while [ -f png/page_`printf "%04d" $page`.png ];
do
  # Geef de HTML pagina's een naam page_xxxx.html (xxxx bevat het paginanummer met vier cijfers)
  html=page_`printf "%04d" $page`.html
  # Baseer de HTML pagina op de sjabloonpagina template.html
  cp template.html $html
  # Vervang in de HTML pagina de sjabloon variabelen door hun reële waarden
  img=page_`printf "%04d" $page`.png
  sed -i "s/background.png/$img/g" $html
  # Zorg voor een navigatiesysteem (vorige en volgende pagina)
  prev=page_`printf "%04d" $[page - 1]`.html
  if [ -f $prev ]; then
    sed -i "s/prevpage.html/$prev/g" $html
  else
    sed -i "s/prevpage.html/page_0000.html/g" $html
  fi
  next=page_`printf "%04d" $[page + 1]`.html
  if [ -f png/page_`printf "%04d" $[page + 1]`.png ]; then
    sed -i "s/nextpage.html/$next/g" $html
  else
    sed -i "s/nextpage.html/page_0000.html/g" $html
  fi
  # Voeg de pagina toe aan de Inhoudsopgave
  pagenr=`printf "%04d" $[page]`
  echo "<a href=\"$html\">$pagenr</a>" >> content.html
  # Herhaal de werkwijze voor de volgende pagina
  ((page++))
done

Zo gebruik je het script:

dany@new-host-2:~/Documents/SNT/Mac OS X/Web/pdf> sh pdf2html.sh ../../../Lesvoorbereidingen/Mac\ OS\ X\ Yosemite\ theorie\ en\ oefeningen\ deel\ 1.pdf
/usr/bin/convert
--2015-08-26 15:54:48--  https://google-diff-match-patch.googlecode.com/svn/trunk/javascript/diff_match_patch.js
Herleiden van google-diff-match-patch.googlecode.com (google-diff-match-patch.googlecode.com)... 74.125.136.82, 2a00:1450:4013:c01::52
Verbinding maken met google-diff-match-patch.googlecode.com (google-diff-match-patch.googlecode.com)|74.125.136.82|:443... verbonden.
HTTP-verzoek is verzonden; wachten op antwoord... 200 OK
Lengte: 19192 (19K) [text/plain]
Wordt opgeslagen als: ‘diff_match_patch.js’

diff_match_patch.js               100%[============================================================>]  18,74K  --.-KB/s   in 0,04s  

2015-08-26 15:54:48 (508 KB/s) - '‘diff_match_patch.js’' opgeslagen [19192/19192]

--2015-08-26 15:54:48--  https://github.com/tinymce/tinymce-dist/archive/master.zip
Herleiden van github.com (github.com)... 192.30.252.128
Verbinding maken met github.com (github.com)|192.30.252.128|:443... verbonden.
HTTP-verzoek is verzonden; wachten op antwoord... 302 Found
Locatie: https://codeload.github.com/tinymce/tinymce-dist/zip/master [volgen...]
--2015-08-26 15:54:49--  https://codeload.github.com/tinymce/tinymce-dist/zip/master
Herleiden van codeload.github.com (codeload.github.com)... 192.30.252.144
Verbinding maken met codeload.github.com (codeload.github.com)|192.30.252.144|:443... verbonden.
HTTP-verzoek is verzonden; wachten op antwoord... 200 OK
Lengte: 1072704 (1,0M) [application/zip]
Wordt opgeslagen als: ‘master.zip’

master.zip                        100%[============================================================>]   1,02M   605KB/s   in 1,7s   

2015-08-26 15:54:51 (605 KB/s) - '‘master.zip’' opgeslagen [1072704/1072704]

Archive:  master.zip
aafc1144b1561d6c8485f81f9d63495b5db575c8
   creating: tinymce-dist-master/
  inflating: tinymce-dist-master/.npmignore  
  inflating: tinymce-dist-master/bower.json  
  inflating: tinymce-dist-master/changelog.txt  
  inflating: tinymce-dist-master/composer.json  
  inflating: tinymce-dist-master/jquery.tinymce.min.js  
  inflating: tinymce-dist-master/license.txt  
  inflating: tinymce-dist-master/package.json  
   creating: tinymce-dist-master/plugins/
   creating: tinymce-dist-master/plugins/advlist/
  inflating: tinymce-dist-master/plugins/advlist/plugin.js  
  inflating: tinymce-dist-master/plugins/advlist/plugin.min.js  
   creating: tinymce-dist-master/plugins/anchor/
  inflating: tinymce-dist-master/plugins/anchor/plugin.js  
  inflating: tinymce-dist-master/plugins/anchor/plugin.min.js  
   creating: tinymce-dist-master/plugins/autolink/
  inflating: tinymce-dist-master/plugins/autolink/plugin.js  
  inflating: tinymce-dist-master/plugins/autolink/plugin.min.js  
   creating: tinymce-dist-master/plugins/autoresize/
  inflating: tinymce-dist-master/plugins/autoresize/plugin.js  
  inflating: tinymce-dist-master/plugins/autoresize/plugin.min.js  
   creating: tinymce-dist-master/plugins/autosave/
  inflating: tinymce-dist-master/plugins/autosave/plugin.js  
  inflating: tinymce-dist-master/plugins/autosave/plugin.min.js  
   creating: tinymce-dist-master/plugins/bbcode/
  inflating: tinymce-dist-master/plugins/bbcode/plugin.js  
  inflating: tinymce-dist-master/plugins/bbcode/plugin.min.js  
   creating: tinymce-dist-master/plugins/charmap/
  inflating: tinymce-dist-master/plugins/charmap/plugin.js  
  inflating: tinymce-dist-master/plugins/charmap/plugin.min.js  
   creating: tinymce-dist-master/plugins/code/
  inflating: tinymce-dist-master/plugins/code/plugin.js  
  inflating: tinymce-dist-master/plugins/code/plugin.min.js  
   creating: tinymce-dist-master/plugins/colorpicker/
  inflating: tinymce-dist-master/plugins/colorpicker/plugin.js  
  inflating: tinymce-dist-master/plugins/colorpicker/plugin.min.js  
   creating: tinymce-dist-master/plugins/contextmenu/
  inflating: tinymce-dist-master/plugins/contextmenu/plugin.js  
  inflating: tinymce-dist-master/plugins/contextmenu/plugin.min.js  
   creating: tinymce-dist-master/plugins/directionality/
  inflating: tinymce-dist-master/plugins/directionality/plugin.js  
  inflating: tinymce-dist-master/plugins/directionality/plugin.min.js  
   creating: tinymce-dist-master/plugins/emoticons/
   creating: tinymce-dist-master/plugins/emoticons/img/
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-cool.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-cry.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-embarassed.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-foot-in-mouth.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-frown.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-innocent.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-kiss.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-laughing.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-money-mouth.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-sealed.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-smile.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-surprised.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-tongue-out.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-undecided.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-wink.gif  
 extracting: tinymce-dist-master/plugins/emoticons/img/smiley-yell.gif  
  inflating: tinymce-dist-master/plugins/emoticons/plugin.js  
  inflating: tinymce-dist-master/plugins/emoticons/plugin.min.js  
   creating: tinymce-dist-master/plugins/fullpage/
  inflating: tinymce-dist-master/plugins/fullpage/plugin.js  
  inflating: tinymce-dist-master/plugins/fullpage/plugin.min.js  
   creating: tinymce-dist-master/plugins/fullscreen/
  inflating: tinymce-dist-master/plugins/fullscreen/plugin.js  
  inflating: tinymce-dist-master/plugins/fullscreen/plugin.min.js  
   creating: tinymce-dist-master/plugins/hr/
  inflating: tinymce-dist-master/plugins/hr/plugin.js  
  inflating: tinymce-dist-master/plugins/hr/plugin.min.js  
   creating: tinymce-dist-master/plugins/image/
  inflating: tinymce-dist-master/plugins/image/plugin.js  
  inflating: tinymce-dist-master/plugins/image/plugin.min.js  
   creating: tinymce-dist-master/plugins/imagetools/
  inflating: tinymce-dist-master/plugins/imagetools/plugin.js  
  inflating: tinymce-dist-master/plugins/imagetools/plugin.min.js  
   creating: tinymce-dist-master/plugins/importcss/
  inflating: tinymce-dist-master/plugins/importcss/plugin.js  
  inflating: tinymce-dist-master/plugins/importcss/plugin.min.js  
   creating: tinymce-dist-master/plugins/insertdatetime/
  inflating: tinymce-dist-master/plugins/insertdatetime/plugin.js  
  inflating: tinymce-dist-master/plugins/insertdatetime/plugin.min.js  
   creating: tinymce-dist-master/plugins/layer/
  inflating: tinymce-dist-master/plugins/layer/plugin.js  
  inflating: tinymce-dist-master/plugins/layer/plugin.min.js  
   creating: tinymce-dist-master/plugins/legacyoutput/
  inflating: tinymce-dist-master/plugins/legacyoutput/plugin.js  
  inflating: tinymce-dist-master/plugins/legacyoutput/plugin.min.js  
   creating: tinymce-dist-master/plugins/link/
  inflating: tinymce-dist-master/plugins/link/plugin.js  
  inflating: tinymce-dist-master/plugins/link/plugin.min.js  
   creating: tinymce-dist-master/plugins/lists/
  inflating: tinymce-dist-master/plugins/lists/plugin.js  
  inflating: tinymce-dist-master/plugins/lists/plugin.min.js  
   creating: tinymce-dist-master/plugins/media/
 extracting: tinymce-dist-master/plugins/media/moxieplayer.swf  
  inflating: tinymce-dist-master/plugins/media/plugin.js  
  inflating: tinymce-dist-master/plugins/media/plugin.min.js  
   creating: tinymce-dist-master/plugins/nonbreaking/
  inflating: tinymce-dist-master/plugins/nonbreaking/plugin.js  
  inflating: tinymce-dist-master/plugins/nonbreaking/plugin.min.js  
   creating: tinymce-dist-master/plugins/noneditable/
  inflating: tinymce-dist-master/plugins/noneditable/plugin.js  
  inflating: tinymce-dist-master/plugins/noneditable/plugin.min.js  
   creating: tinymce-dist-master/plugins/pagebreak/
  inflating: tinymce-dist-master/plugins/pagebreak/plugin.js  
  inflating: tinymce-dist-master/plugins/pagebreak/plugin.min.js  
   creating: tinymce-dist-master/plugins/paste/
  inflating: tinymce-dist-master/plugins/paste/plugin.js  
  inflating: tinymce-dist-master/plugins/paste/plugin.min.js  
   creating: tinymce-dist-master/plugins/preview/
  inflating: tinymce-dist-master/plugins/preview/plugin.js  
  inflating: tinymce-dist-master/plugins/preview/plugin.min.js  
   creating: tinymce-dist-master/plugins/print/
  inflating: tinymce-dist-master/plugins/print/plugin.js  
  inflating: tinymce-dist-master/plugins/print/plugin.min.js  
   creating: tinymce-dist-master/plugins/save/
  inflating: tinymce-dist-master/plugins/save/plugin.js  
  inflating: tinymce-dist-master/plugins/save/plugin.min.js  
   creating: tinymce-dist-master/plugins/searchreplace/
  inflating: tinymce-dist-master/plugins/searchreplace/plugin.js  
  inflating: tinymce-dist-master/plugins/searchreplace/plugin.min.js  
   creating: tinymce-dist-master/plugins/spellchecker/
  inflating: tinymce-dist-master/plugins/spellchecker/plugin.js  
  inflating: tinymce-dist-master/plugins/spellchecker/plugin.min.js  
   creating: tinymce-dist-master/plugins/tabfocus/
  inflating: tinymce-dist-master/plugins/tabfocus/plugin.js  
  inflating: tinymce-dist-master/plugins/tabfocus/plugin.min.js  
   creating: tinymce-dist-master/plugins/table/
  inflating: tinymce-dist-master/plugins/table/plugin.js  
  inflating: tinymce-dist-master/plugins/table/plugin.min.js  
   creating: tinymce-dist-master/plugins/template/
  inflating: tinymce-dist-master/plugins/template/plugin.js  
  inflating: tinymce-dist-master/plugins/template/plugin.min.js  
   creating: tinymce-dist-master/plugins/textcolor/
  inflating: tinymce-dist-master/plugins/textcolor/plugin.js  
  inflating: tinymce-dist-master/plugins/textcolor/plugin.min.js  
   creating: tinymce-dist-master/plugins/textpattern/
  inflating: tinymce-dist-master/plugins/textpattern/plugin.js  
  inflating: tinymce-dist-master/plugins/textpattern/plugin.min.js  
   creating: tinymce-dist-master/plugins/visualblocks/
   creating: tinymce-dist-master/plugins/visualblocks/css/
  inflating: tinymce-dist-master/plugins/visualblocks/css/visualblocks.css  
  inflating: tinymce-dist-master/plugins/visualblocks/plugin.js  
  inflating: tinymce-dist-master/plugins/visualblocks/plugin.min.js  
   creating: tinymce-dist-master/plugins/visualchars/
  inflating: tinymce-dist-master/plugins/visualchars/plugin.js  
  inflating: tinymce-dist-master/plugins/visualchars/plugin.min.js  
   creating: tinymce-dist-master/plugins/wordcount/
  inflating: tinymce-dist-master/plugins/wordcount/plugin.js  
  inflating: tinymce-dist-master/plugins/wordcount/plugin.min.js  
  inflating: tinymce-dist-master/readme.md  
   creating: tinymce-dist-master/skins/
   creating: tinymce-dist-master/skins/lightgray/
  inflating: tinymce-dist-master/skins/lightgray/content.inline.min.css  
  inflating: tinymce-dist-master/skins/lightgray/content.min.css  
   creating: tinymce-dist-master/skins/lightgray/fonts/
  inflating: tinymce-dist-master/skins/lightgray/fonts/tinymce-small.eot  
  inflating: tinymce-dist-master/skins/lightgray/fonts/tinymce-small.svg  
  inflating: tinymce-dist-master/skins/lightgray/fonts/tinymce-small.ttf  
  inflating: tinymce-dist-master/skins/lightgray/fonts/tinymce-small.woff  
  inflating: tinymce-dist-master/skins/lightgray/fonts/tinymce.eot  
  inflating: tinymce-dist-master/skins/lightgray/fonts/tinymce.svg  
  inflating: tinymce-dist-master/skins/lightgray/fonts/tinymce.ttf  
  inflating: tinymce-dist-master/skins/lightgray/fonts/tinymce.woff  
   creating: tinymce-dist-master/skins/lightgray/img/
  inflating: tinymce-dist-master/skins/lightgray/img/anchor.gif  
  inflating: tinymce-dist-master/skins/lightgray/img/loader.gif  
 extracting: tinymce-dist-master/skins/lightgray/img/object.gif  
  inflating: tinymce-dist-master/skins/lightgray/img/trans.gif  
  inflating: tinymce-dist-master/skins/lightgray/skin.ie7.min.css  
  inflating: tinymce-dist-master/skins/lightgray/skin.min.css  
   creating: tinymce-dist-master/themes/
   creating: tinymce-dist-master/themes/modern/
  inflating: tinymce-dist-master/themes/modern/theme.js  
  inflating: tinymce-dist-master/themes/modern/theme.min.js  
  inflating: tinymce-dist-master/tinymce.jquery.js  
  inflating: tinymce-dist-master/tinymce.jquery.min.js  
  inflating: tinymce-dist-master/tinymce.js  
  inflating: tinymce-dist-master/tinymce.min.js  
--2015-08-26 15:54:51--  http://www.tinymce.com/i18n/download.php?download=nl
Herleiden van www.tinymce.com (www.tinymce.com)... 168.62.48.183
Verbinding maken met www.tinymce.com (www.tinymce.com)|168.62.48.183|:80... verbonden.
HTTP-verzoek is verzonden; wachten op antwoord... 200 OK
Lengte: 3085 (3,0K) [application/octet-stream]
Wordt opgeslagen als: ‘download.php?download=nl’

download.php?download=nl          100%[============================================================>]   3,01K  --.-KB/s   in 0,007s 

2015-08-26 15:54:52 (436 KB/s) - '‘download.php?download=nl’' opgeslagen [3085/3085]

Archive:  download.php?download=nl
  inflating: tinymce/langs/nl.js     
Even geduld, bezig met omzetten van het PDF document, dit kan even duren...

Bij een tweede omzetting worden de afhankelijke delen niet meer opgehaald en uitgepakt wordt het volgende weergegeven:

dany@new-host-2:~/Documents/SNT/Mac OS X/Web/pdf> sh pdf2html.sh ../../../Lesvoorbereidingen/Mac\ OS\ X\ Yosemite\ theorie\ en\ oefeningen\ deel\ 1.pdf
/usr/bin/convert
Even geduld, bezig met omzetten van het PDF document, dit kan even duren...

Dit wordt het resultaat:
pdf2html