summaryrefslogtreecommitdiff
path: root/scripts/context/lua/mtx-epub.lua
diff options
context:
space:
mode:
Diffstat (limited to 'scripts/context/lua/mtx-epub.lua')
-rw-r--r--scripts/context/lua/mtx-epub.lua879
1 files changed, 708 insertions, 171 deletions
diff --git a/scripts/context/lua/mtx-epub.lua b/scripts/context/lua/mtx-epub.lua
index 11f0a2024..956ce4931 100644
--- a/scripts/context/lua/mtx-epub.lua
+++ b/scripts/context/lua/mtx-epub.lua
@@ -18,8 +18,89 @@ if not modules then modules = { } end modules ['mtx-epub'] = {
-- first we need a decent strategy to export them. More information will be
-- available on the wiki.
-local format, gsub = string.format, string.gsub
-local concat = table.concat
+-- META-INF
+-- container.xml
+-- OEBPS
+-- content.opf
+-- toc.ncx
+-- images
+-- styles
+-- mimetype
+
+-- todo:
+--
+-- remove m_k_v_i prefixes
+-- remap fonts %mono% in css so that we can replace
+-- coverpage tests
+-- split up
+
+-- todo: automated cover page:
+--
+-- \startMPpage
+-- StartPage ;
+-- fill Page withcolor .5red ;
+-- numeric n ;
+-- for i=10 downto 1 :
+-- n := i * PaperWidth/40 ;
+-- draw
+-- lrcorner Page shifted (0,n)
+-- % -- lrcorner Page
+-- -- lrcorner Page shifted (-n,0)
+-- % -- cycle
+-- withpen pencircle scaled 1mm
+-- withcolor white ;
+-- endfor ;
+-- picture p ; p := image (
+-- draw
+-- anchored.top(
+-- textext.bot("\tttf Some Title")
+-- xsized .8PaperWidth
+-- ,center topboundary Page
+-- )
+-- withcolor white ;
+-- ) ;
+-- picture q ; q := image (
+-- draw
+-- anchored.top(
+-- textext.bot("\tttf An Author")
+-- xsized .4PaperWidth
+-- shifted (0,-PaperHeight/40)
+-- ,center bottomboundary p
+-- )
+-- withcolor white ;
+-- ) ;
+-- draw p ;
+-- draw q ;
+-- StopPage ;
+-- \stopMPpage
+
+local format, gsub, find = string.format, string.gsub, string.find
+local concat, sortedhash = table.concat, table.sortedhash
+
+local formatters = string.formatters
+local replacetemplate = utilities.templates.replace
+
+local addsuffix = file.addsuffix
+local nameonly = file.nameonly
+local basename = file.basename
+local pathpart = file.pathpart
+local joinfile = file.join
+local suffix = file.suffix
+local addsuffix = file.addsuffix
+local removesuffix = file.removesuffix
+local replacesuffix = file.replacesuffix
+
+local copyfile = file.copy
+local removefile = os.remove
+
+local needsupdating = file.needsupdating
+
+local isdir = lfs.isdir
+local isfile = lfs.isfile
+local mkdir = lfs.mkdir
+
+local pushdir = dir.push
+local popdir = dir.pop
local helpinfo = [[
<?xml version="1.0"?>
@@ -27,12 +108,17 @@ local helpinfo = [[
<metadata>
<entry name="name">mtx-epub</entry>
<entry name="detail">ConTeXt EPUB Helpers</entry>
- <entry name="version">0.12</entry>
+ <entry name="version">1.10</entry>
</metadata>
<flags>
<category name="basic">
<subcategory>
<flag name="make"><short>create epub zip file</short></flag>
+ <flag name="purge"><short>remove obsolete files</short></flag>
+ <flag name="rename"><short>rename images to sane names</short></flag>
+ <flag name="svgmath"><short>convert mathml to svg</short></flag>
+ <flag name="svgstyle"><short>use given tex style for svg generation (overloads style in specification)</short></flag>
+ <flag name="all"><short>assume: --purge --rename --svgmath (for fast testing)</short></flag>
</subcategory>
</category>
</flags>
@@ -49,10 +135,12 @@ local helpinfo = [[
local application = logs.application {
name = "mtx-epub",
- banner = "ConTeXt EPUB Helpers 0.12",
+ banner = "ConTeXt EPUB Helpers 1.10",
helpinfo = helpinfo,
}
+local report = application.report
+
-- script code
scripts = scripts or { }
@@ -60,91 +148,142 @@ scripts.epub = scripts.epub or { }
local mimetype = "application/epub+zip"
-local container = [[
+local t_container = [[
<?xml version="1.0" encoding="UTF-8"?>
<container version="1.0" xmlns="urn:oasis:names:tc:opendocument:xmlns:container">
<rootfiles>
- <rootfile full-path="OEBPS/%s" media-type="application/oebps-package+xml"/>
+ <rootfile full-path="OEBPS/%rootfile%" media-type="application/oebps-package+xml"/>
</rootfiles>
</container>
]]
-local package = [[
+-- urn:uuid:
+
+-- <dc:identifier id="%identifier%" opf:scheme="UUID">%uuid%</dc:identifier>
+
+local t_package = [[
<?xml version="1.0" encoding="UTF-8"?>
-<package version="2.0" xmlns="http://www.idpf.org/2007/opf" unique-identifier="%s">
+<package xmlns="http://www.idpf.org/2007/opf" unique-identifier="%identifier%" version="3.0">
<metadata xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:opf="http://www.idpf.org/2007/opf">
- <dc:title>%s</dc:title>
- <dc:language>%s</dc:language>
- <dc:identifier id="%s" opf:scheme="UUID">urn:uuid:%s</dc:identifier>
- <dc:creator>%s</dc:creator>
- <dc:date>%s</dc:date>
- <meta name="cover" content="%s" />
+ <dc:title>%title%</dc:title>
+ <dc:language>%language%</dc:language>
+ <dc:identifier id="%identifier%">%uuid%</dc:identifier>
+ <dc:creator>%creator%</dc:creator>
+ <dc:date>%date%</dc:date>
+ <!--
+ <dc:subject>%subject%</dc:subject>
+ <dc:description>%description%</dc:description>
+ <dc:publisher>%publisher%</dc:publisher>
+ <dc:source>%source%</dc:source>
+ <dc:relation>%relation%</dc:relation>
+ <dc:coverage>%coverage%</dc:coverage>
+ <dc:rights>%rights%</dc:rights>
+ -->
+ <meta name="cover" content="%coverpage%" />
+ <meta name="generator" content="ConTeXt MkIV" />
+ <meta property="dcterms:modified">%date%</meta>
</metadata>
<manifest>
-%s
+%manifest%
</manifest>
<spine toc="ncx">
<itemref idref="cover-xhtml" />
- <itemref idref="%s" />
+ <itemref idref="%rootfile%" />
</spine>
</package>
]]
-local item = [[ <item id="%s" href="%s" media-type="%s"/>]]
-local toc = [[
-<?xml version="1.0"?>
+local t_item = [[ <item id="%id%" href="%filename%" media-type="%mime%" />]]
+local t_prop = [[ <item id="%id%" href="%filename%" media-type="%mime%" properties="%properties%" />]]
+
+-- <!DOCTYPE ncx PUBLIC "-//NISO//DTD ncx 2005-1//EN" "http://www.daisy.org/z3986/2005/ncx-2005-1.dtd">
+
+local t_toc = [[
+<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE ncx PUBLIC "-//NISO//DTD ncx 2005-1//EN" "http://www.daisy.org/z3986/2005/ncx-2005-1.dtd">
+<!-- this is no longer needed in epub 3.0+ -->
<ncx xmlns="http://www.daisy.org/z3986/2005/ncx/" version="2005-1">
<head>
- <meta name="dtb:uid" content="%s" />
+ <meta name="generator" content="ConTeXt MkIV" />
+ <meta name="dtb:uid" content="%identifier%" />
<meta name="dtb:depth" content="2" />
<meta name="dtb:totalPgeCount" content="0" />
<meta name="dtb:maxPageNumber" content="0" />
</head>
<docTitle>
- <text>%s</text>
+ <text>%title%</text>
</docTitle>
+ <docAuthor>
+ <text>%author%</text>
+ </docAuthor>
+
<navMap>
<navPoint id="np-1" playOrder="1">
<navLabel>
<text>start</text>
</navLabel>
- <content src="%s"/>
+ <content src="%root%"/>
</navPoint>
</navMap>
</ncx>
]]
-local coverxhtml = [[
+local t_navtoc = [[
<?xml version="1.0" encoding="UTF-8"?>
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
+<html xmlns="http://www.w3.org/1999/xhtml" xmlns:epub="http://www.idpf.org/2007/ops">
+ <head>
+ <meta charset="utf-8" />
+ <title>navtoc</title>
+ </head>
+ <body>
+ <div class="navtoc">
+ <!-- <nav epub:type="lot"> -->
+ <nav epub:type="toc" id="navtoc">
+ <ol>
+ <li><a href="%root%">document</a></li>
+ </ol>
+ </nav>
+ </div>
+ </body>
+</html>
+]]
+
+-- <html xmlns="http://www.w3.org/1999/xhtml">
+-- <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
+
+local t_coverxhtml = [[
+<?xml version="1.0" encoding="UTF-8"?>
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
- <title>cover.xhtml</title>
+ <meta charset="utf-8" />
+ <title>cover page</title>
</head>
<body>
- <div>
- <img src="%s" alt="The cover image" style="max-width: 100%%;" />
+ <div class="coverpage">
+ %content%
</div>
</body>
</html>
]]
+local t_coverimg = [[
+ <img src="%image%" alt="The cover image" style="max-width: 100%%;" />
+]]
+
-- We need to figure out what is permitted. Numbers only seem to give
-- problems is some applications as do names with dashes. Also the
-- optional toc is supposed to be there and although id's are by
@@ -154,12 +293,13 @@ local coverxhtml = [[
local function dumbid(filename)
-- return (string.gsub(os.uuid(),"%-%","")) -- to be tested
- return file.nameonly(filename) .. "-" .. file.suffix(filename)
+ return nameonly(filename) .. "-" .. suffix(filename)
end
local mimetypes = {
xhtml = "application/xhtml+xml",
xml = "application/xhtml+xml",
+ html = "application/html",
css = "text/css",
svg = "image/svg+xml",
png = "image/png",
@@ -175,204 +315,601 @@ local idmakers = {
default = function(filename) return dumbid(filename) end,
}
--- specification = {
--- name = "document",
--- identifier = "123",
--- root = "a.xhtml",
--- files = {
--- "a.xhtml",
--- "b.css",
--- "c.png",
--- }
--- }
-
-local function locateimages(oldname,newname,subpath)
+local function relocateimages(imagedata,oldname,newname,subpath,rename)
local data = io.loaddata(oldname)
- local images = { }
- local done = gsub(data,"(background%-image *: * url%()(.-)(%))", function(before,name,after)
- if subpath then
- name = file.join(subpath,name)
+ if data then
+ subpath = joinfile("..",subpath)
+ report("relocating images")
+ local n = 0
+ local done = gsub(data,[[(id=")(.-)(".-background%-image *: *url%()(.-)(%))]], function(s1,id,s2,name,s3)
+ local data = imagedata[id]
+ if data then
+ local newname = data[id].newname
+ if newname then
+ if subpath then
+ name = joinfile(subpath,basename(newname))
+ else
+ name = basename(newname)
+ end
+ -- name = url.addscheme(name)
+ end
+ if newname then
+ n = n + 1
+ if rename then
+ name = joinfile(subpath,addsuffix(id,suffix(name)))
+ end
+ return s1 .. id .. s2 .. name .. s3
+ end
+ end
+ end)
+ report("%s images relocated in %a",n,newname)
+ if newname then
+ io.savedata(newname,done)
end
- images[#images+1] = name
- return before .. name .. after
- end)
- if newname then
- io.savedata(done,newname)
end
return images
end
+function reportobsolete(oldfiles,newfiles,purge)
+
+ for i=1,#oldfiles do oldfiles[i] = gsub(oldfiles[i],"^[%./]+","") end
+ for i=1,#newfiles do newfiles[i] = gsub(newfiles[i],"^[%./]+","") end
+
+ local old = table.tohash(oldfiles)
+ local new = table.tohash(newfiles)
+ local done = false
+
+ for name in sortedhash(old) do
+ if not new[name] then
+ if not done then
+ report()
+ if purge then
+ report("removing obsolete files:")
+ else
+ report("obsolete files:")
+ end
+ report()
+ done = true
+ end
+ report(" %s",name)
+ if purge then
+ removefile(name)
+ end
+ end
+ end
+
+ if done then
+ report()
+ end
+
+ return done
+
+end
+
+
local zippers = {
{
name = "zip",
+ binary = "zip",
uncompressed = "zip %s -X -0 %s",
compressed = "zip %s -X -9 -r %s",
},
{
- name = "7zip (7z)",
+ name = "7z (7zip)",
+ binary = "7z",
uncompressed = "7z a -tzip -mx0 %s %s",
compressed = "7z a -tzip %s %s",
},
}
-function scripts.epub.make()
+function scripts.epub.make(purge,rename,svgmath,svgstyle)
+
+ -- one can enter a jobname or jobname-export but the simple jobname is
+ -- preferred
local filename = environment.files[1]
- if filename and filename ~= "" and type(filename) == "string" then
+ if not filename or filename == "" or type(filename) ~= "string" then
+ report("provide filename")
+ return
+ end
+
+ local specpath, specname, specfull
- filename = file.basename(filename)
- local specfile = file.replacesuffix(filename,"specification")
- local specification = lfs.isfile(specfile) and dofile(specfile) or { }
+ if isdir(filename) then
+ specpath = filename
+ specname = addsuffix(specpath,"lua")
+ specfull = joinfile(specpath,specname)
+ end
+
+ if not specfull or not isfile(specfull) then
+ specpath = filename .. "-export"
+ specname = addsuffix(filename .. "-pub","lua")
+ specfull = joinfile(specpath,specname)
+ end
+
+ if not specfull or not isfile(specfull) then
+ report("unknown specificaton file %a for %a",specfull or "?",filename)
+ return
+ end
--- inspect(specification)
+ local specification = dofile(specfull)
+
+ if not specification or not next(specification) then
+ report("invalid specificaton file %a",specfile)
+ return
+ end
+
+ report("using specification file %a",specfull)
+
+ -- images: { ... url = location ... }
+
+ local defaultcoverpage = "cover.xhtml"
+
+ local name = specification.name or nameonly(filename)
+ local identifier = specification.identifier or ""
+ local htmlfiles = specification.htmlfiles or { }
+ local styles = specification.styles or { }
+ local images = specification.images or { }
+ local htmlroot = specification.htmlroot or htmlfiles[1] or ""
+ local language = specification.language or "en"
+ local creator = specification.creator or "context mkiv"
+ local author = specification.author or "anonymous"
+ local title = specification.title or name
+ local subtitle = specification.subtitle or ""
+ local imagefile = specification.imagefile or ""
+ local imagepath = specification.imagepath or "images"
+ local stylepath = specification.stylepath or "styles"
+ local coverpage = specification.firstpage or defaultcoverpage
+
+ if type(svgstyle) == "string" and not svgstyle then
+ svgstyle = specification.svgstyle or ""
+ end
- local name = specification.name or file.removesuffix(filename)
- local identifier = specification.identifier or os.uuid(true)
- local files = specification.files or { file.addsuffix(filename,"xhtml") }
- local images = specification.images or { }
- local root = specification.root or files[1]
- local language = specification.language or "en"
- local creator = specification.author or "My Self"
- local title = specification.title or "My Title"
- local firstpage = specification.firstpage or ""
- local lastpage = specification.lastpage or ""
+ local obsolete = false
- -- identifier = gsub(identifier,"[^a-zA-z0-9]","")
+ if #htmlfiles == 0 then
+ report("no html files specified")
+ return
+ end
+ if htmlroot == "" then
+ report("no html root file specified")
+ return
+ end
+
+ if subtitle ~= "" then
+ title = format("%s, %s",title,subtitle)
+ end
+
+ local htmlsource = specpath
+ local imagesource = joinfile(specpath,imagepath)
+ local stylesource = joinfile(specpath,stylepath)
+
+ -- once we're here we can start moving files to the right spot; first we deal
+ -- with images
+
+ -- ["image-1"]={
+ -- height = "7.056cm",
+ -- name = "file:///t:/sources/cow.svg",
+ -- page = "1",
+ -- width = "9.701cm",
+ -- }
+
+ -- end of todo
+
+ local pdftosvg = os.which("mudraw") and formatters[ [[mudraw -o "%s" "%s" %s]] ]
+
+ local f_svgpage = formatters["%s-page-%s.svg"]
+ local f_svgname = formatters["%s.svg"]
+
+ local notupdated = 0
+ local updated = 0
+ local skipped = 0
+ local oldfiles = dir.glob(file.join(imagesource,"*"))
+ local newfiles = { }
+
+ if not pdftosvg then
+ report("the %a binary is not present","mudraw")
+ end
+
+ -- a coverpage file has to be in the root of the export tree
+
+ if not coverpage then
+ report("no cover page (image) defined")
+ elseif suffix(coverpage) ~= "xhtml" then
+ report("using cover page %a",coverpage)
+ local source = coverpage
+ local target = joinfile(htmlsource,coverpage)
+ htmlfiles[#htmlfiles+1 ] = coverpage
+ report("copying coverpage %a to %a",source,target)
+ copyfile(source,target)
+ elseif isfile(coverpage) then
+ report("using cover page image %a",coverpage)
+ images.cover = {
+ height = "100%",
+ width = "100%",
+ page = "1",
+ name = url.filename(coverpage),
+ used = coverpage,
+ }
+ local data = replacetemplate(t_coverxhtml, {
+ content = replacetemplate(t_coverimg, {
+ image = coverpage,
+ })
+ })
+ coverpage = defaultcoverpage
+ local target = joinfile(htmlsource,coverpage)
+ report("saving coverpage to %a",target)
+ io.savedata(target,data)
+ htmlfiles[#htmlfiles+1 ] = coverpage
+ else
+ report("cover page image %a is not present",coverpage)
+ coverpage = false
+ end
+
+ if not coverpage then
+ local data = replacetemplate(t_coverxhtml, {
+ content = "no cover page"
+ })
+ coverpage = defaultcoverpage
+ local target = joinfile(htmlsource,coverpage)
+ report("saving dummy coverpage to %a",target)
+ io.savedata(target,data)
+ htmlfiles[#htmlfiles+1 ] = coverpage
+ end
- if firstpage ~= "" then
- images[firstpage] = firstpage
+ for id, data in sortedhash(images) do
+ local name = url.filename(data.name)
+ local used = url.filename(data.used)
+ local base = basename(used)
+ local page = tonumber(data.page) or 1
+ -- todo : check timestamp and prefix, rename to image-*
+ if suffix(used) == "pdf" then
+ -- todo: pass svg name
+ if page > 1 then
+ name = f_svgpage(nameonly(name),page)
+ else
+ name = f_svgname(nameonly(name))
+ end
+ local source = used
+ local target = joinfile(imagesource,name)
+ if needsupdating(source,target) then
+ if pdftosvg then
+ local command = pdftosvg(target,source,page)
+ report("running command %a",command)
+ os.execute(command)
+ updated = updated + 1
+ else
+ skipped = skipped + 1
+ end
+ else
+ notupdated = notupdated + 1
+ end
+ newfiles[#newfiles+1] = target
+ else
+ name = basename(used)
+ local source = used
+ local target = joinfile(imagesource,name)
+ if needsupdating(source,target) then
+ report("copying %a to %a",source,target)
+ copyfile(source,target)
+ updated = updated + 1
+ else
+ notupdated = notupdated + 1
+ -- no message
+ end
+ newfiles[#newfiles+1] = target
end
- if lastpage ~= "" then
- images[lastpage] = lastpage
+ local target = newfiles[#newfiles]
+ if suffix(target) == "svg" and isfile(target) then
+ local data = io.loaddata(target)
+ if data then
+ local done = gsub(data,"<!(DOCTYPE.-)>","<!-- %1 -->",1)
+ if data ~= done then
+ report("doctype fixed in %a",target)
+ io.savedata(target,data)
+ end
+ end
end
+ data.newname = name -- without path
+ end
+
+ report("%s images checked, %s updated, %s kept, %s skipped",updated + notupdated + skipped,updated,notupdated,skipped)
- identifier = "BookId" -- weird requirement
-
- local epubname = name
- local epubpath = file.replacesuffix(name,"tree")
- local epubfile = file.replacesuffix(name,"epub")
- local epubroot = file.replacesuffix(name,"opf")
- local epubtoc = "toc.ncx"
- local epubcover = "cover.xhtml"
-
- application.report("creating paths in tree %s",epubpath)
- lfs.mkdir(epubpath)
- lfs.mkdir(file.join(epubpath,"META-INF"))
- lfs.mkdir(file.join(epubpath,"OEBPS"))
-
- local used = { }
-
- local function copyone(filename)
- local suffix = file.suffix(filename)
- local mime = mimetypes[suffix]
- if mime then
- local idmaker = idmakers[suffix] or idmakers.default
- local target = file.join(epubpath,"OEBPS",filename)
- file.copy(filename,target)
- application.report("copying %s to %s",filename,target)
- used[#used+1] = format(item,idmaker(filename),filename,mime)
+ if reportobsolete(oldfiles,newfiles,purge) then
+ obsolete = true
+ end
+
+ -- here we can decide not to make an epub
+
+ local uuid = format("urn:uuid:%s",os.uuid(true)) -- os.uuid()
+ local identifier = "bookid" -- for now
+
+ local epubname = removesuffix(name)
+ local epubpath = name .. "-epub"
+ local epubfile = replacesuffix(name,"epub")
+ local epubroot = replacesuffix(name,"opf")
+ local epubtoc = "toc.ncx"
+ local epubmimetypes = "mimetype"
+ local epubcontainer = "container.xml"
+ local epubnavigator = "nav.xhtml"
+
+ local metapath = "META-INF"
+ local datapath = "OEBPS"
+
+ local oldfiles = dir.glob(file.join(epubpath,"**/*"))
+ local newfiles = { }
+
+ report("creating paths in tree %a",epubpath)
+
+ if not isdir(epubpath) then
+ mkdir(epubpath)
+ end
+ if not isdir(epubpath) then
+ report("unable to create path %a",epubpath)
+ return
+ end
+
+ local metatarget = joinfile(epubpath,metapath)
+ local htmltarget = joinfile(epubpath,datapath)
+ local styletarget = joinfile(epubpath,datapath,stylepath)
+ local imagetarget = joinfile(epubpath,datapath,imagepath)
+
+ mkdir(metatarget)
+ mkdir(htmltarget)
+ mkdir(styletarget)
+ mkdir(imagetarget)
+
+ local used = { }
+ local notupdated = 0
+ local updated = 0
+
+ local oldimagespecification = joinfile(htmlsource,imagefile)
+ local newimagespecification = joinfile(htmltarget,imagefile)
+
+ report("removing %a",newimagespecification)
+ -- removefile(newimagespecification) -- because we update that one
+
+ local function registerone(path,filename,mathml)
+ local suffix = suffix(filename)
+ local mime = mimetypes[suffix]
+ if mime then
+ local idmaker = idmakers[suffix] or idmakers.default
+ local fullname = path and joinfile(path,filename) or filename
+ if mathml then
+ used[#used+1] = replacetemplate(t_prop, {
+ id = idmaker(filename),
+ filename = fullname,
+ mime = mime,
+ properties = "mathml",
+ } )
+ else
+ used[#used+1] = replacetemplate(t_item, {
+ id = idmaker(filename),
+ filename = fullname,
+ mime = mime,
+ } )
end
+ return true
+ end
+ end
+
+ local function registerandcopyfile(check,path,name,sourcepath,targetpath,newname,image)
+
+ if name == "" then
+ report("ignoring unknown image")
+ return
+ end
+
+ if newname then
+ newname = replacesuffix(newname,suffix(name))
+ else
+ newname = name
end
- copyone("cover.xhtml")
- copyone("toc.ncx")
+ local source = joinfile(sourcepath,name)
+ local target = joinfile(targetpath,newname)
+ local mathml = false
- local function copythem(files)
- for i=1,#files do
- local filename = files[i]
- if type(filename) == "string" then
- copyone(filename)
+ if suffix(source) == "xhtml" then
+ if find(io.loaddata(source),"MathML") then
+ mathml = true -- inbelievable: the property is only valid when there is mathml
+ end
+ else
+ report("checking image %a -> %a",source,target)
+ end
+ if registerone(path,newname,mathml) then
+ if not check or needsupdating(source,target) or mathml and svgmath then
+ report("copying %a to %a",source,target)
+ copyfile(source,target)
+ updated = updated + 1
+ else
+ notupdated = notupdated + 1
+ end
+ newfiles[#newfiles+1] = target
+ if mathml and svgmath then
+ report()
+ report("converting mathml into svg in %a",target)
+ report()
+ local status, total, unique = moduledata.svgmath.convert(target,svgstyle)
+ report()
+ if status then
+ report("%s formulas converted, %s are unique",total,unique)
+ else
+ report("warning: %a in %a",total,target)
end
+ report()
end
end
+ end
- copythem(files)
+ -- local nofdummies = 0
+ -- local dummyname = formatters["dummy-figure-%03i"]
+ -- local makedummy = formatters["context --extra=dummies --noconsole --once --result=%s"]
+ --
+ -- local function registerandcopydummy(targetpath,name)
+ -- nofdummies = nofdummies + 1
+ -- local newname = dummyname(nofdummies)
+ -- local target = joinfile(targetpath,newname)
+ -- if not isfile(target) then
+ -- pushdir(targetpath)
+ -- report("generating dummy %a for %a",newname,name or "unknown")
+ -- os.execute(makedummy(newname))
+ -- popdir()
+ -- end
+ -- return newname
+ -- end
+
+ for image, data in sortedhash(images) do
+ -- if data.used == "" then
+ -- data.newname = registerandcopydummy(imagetarget,data.name)
+ -- end
+ registerandcopyfile(true,imagepath,data.newname,imagesource,imagetarget,rename and image,true)
+ end
+ for i=1,#styles do
+ registerandcopyfile(false,stylepath,styles[i],stylesource,styletarget)
+ end
+ for i=1,#htmlfiles do
+ registerandcopyfile(false,false,htmlfiles[i],htmlsource,htmltarget)
+ end
- local theimages = { }
+ relocateimages(images,oldimagespecification,oldimagespecification,imagepath,rename)
+ relocateimages(images,oldimagespecification,newimagespecification,imagepath,rename)
- for k, v in table.sortedpairs(images) do
- theimages[#theimages+1] = k
- if not lfs.isfile(k) and file.suffix(k) == "svg" and file.suffix(v) == "pdf" then
- local command = format("inkscape --export-plain-svg=%s %s",k,v)
- application.report("running command '%s'\n\n",command)
- os.execute(command)
- end
+ report("%s files registered, %s updated, %s kept",updated + notupdated,updated,notupdated)
+
+ local function saveinfile(what,name,data)
+ report("saving %s in %a",what,name)
+ io.savedata(name,data)
+ newfiles[#newfiles+1] = name
+ end
+
+ used[#used+1] = replacetemplate(t_prop, {
+ id = "nav",
+ filename = epubnavigator,
+ properties = "nav",
+ mime = "application/xhtml+xml",
+ })
+
+ registerone(false,epubtoc)
+
+ saveinfile("navigation data",joinfile(htmltarget,epubnavigator),replacetemplate(t_navtoc, { -- version 3.0
+ root = htmlroot,
+ } ) )
+
+ saveinfile("used mimetypes",joinfile(epubpath,epubmimetypes),mimetype)
+
+ saveinfile("version 2.0 container",joinfile(metatarget,epubcontainer),replacetemplate(t_container, {
+ rootfile = epubroot
+ } ) )
+
+ local idmaker = idmakers[suffix(htmlroot)] or idmakers.default
+
+ saveinfile("package specification",joinfile(htmltarget,epubroot),replacetemplate(t_package, {
+ identifier = identifier,
+ title = title,
+ language = language,
+ uuid = uuid,
+ creator = creator,
+ date = os.date("!%Y-%m-%dT%H:%M:%SZ"),
+ coverpage = idmaker(coverpage),
+ manifest = concat(used,"\n"),
+ rootfile = idmaker(htmlroot)
+ } ) )
+
+ -- t_toc is replaced by t_navtoc in >= 3
+
+ saveinfile("table of contents",joinfile(htmltarget,epubtoc), replacetemplate(t_toc, {
+ identifier = uuid, -- identifier,
+ title = title,
+ author = author,
+ root = htmlroot,
+ } ) )
+
+ report("creating archive\n\n")
+
+ pushdir(epubpath)
+
+ removefile(epubfile)
+
+ local usedzipper = false
+
+ local function zipped(zipper)
+ local ok = os.execute(format(zipper.uncompressed,epubfile,epubmimetypes))
+ if ok == 0 then
+ os.execute(format(zipper.compressed,epubfile,metapath))
+ os.execute(format(zipper.compressed,epubfile,datapath))
+ usedzipper = zipper.name
+ return true
end
+ end
+
+ -- nice way
+
+ for i=1,#zippers do
+ if os.which(zippers[i].binary) and zipped(zippers[i]) then
+ break
+ end
+ end
- copythem(theimages)
-
- local idmaker = idmakers[file.suffix(root)] or idmakers.default
-
- container = format(container,
- epubroot
- )
- package = format(package,
- identifier,
- title,
- language,
- identifier,
- os.uuid(),
- creator,
- os.date("!%Y-%m-%dT%H:%M:%SZ"),
- idmaker(firstpage),
- concat(used,"\n"),
- idmaker(root)
- )
- toc = format(toc,
- identifier,
- title,
- root
- )
- coverxhtml = format(coverxhtml,
- firstpage
- )
-
- io.savedata(file.join(epubpath,"mimetype"),mimetype)
- io.savedata(file.join(epubpath,"META-INF","container.xml"),container)
- io.savedata(file.join(epubpath,"OEBPS",epubroot),package)
- io.savedata(file.join(epubpath,"OEBPS",epubtoc),toc)
- io.savedata(file.join(epubpath,"OEBPS",epubcover),coverxhtml)
-
- application.report("creating archive\n\n")
-
- lfs.chdir(epubpath)
- os.remove(epubfile)
-
- local done = false
+ -- trial and error
+ if not usedzipper then
for i=1,#zippers do
- local zipper = zippers[i]
- if os.execute(format(zipper.uncompressed,epubfile,"mimetype")) then
- os.execute(format(zipper.compressed,epubfile,"META-INF"))
- os.execute(format(zipper.compressed,epubfile,"OEBPS"))
- done = zipper.name
+ if zipped(zippers[i]) then
break
end
end
+ end
- lfs.chdir("..")
+ popdir()
- if done then
- application.report("epub archive made using %s: %s",done,file.join(epubpath,epubfile))
- else
- local list = { }
- for i=1,#zippers do
- list[#list+1] = zipper.name
- end
- application.report("no epub archive made, install one of: %s",concat(list," "))
+ if usedzipper then
+ local treefile = joinfile(epubpath,epubfile)
+ removefile(epubfile)
+ copyfile(treefile,epubfile)
+ if isfile(epubfile) then
+ removefile(treefile)
end
+ report("epub archive made using %s: %s",usedzipper,epubfile)
+ else
+ local list = { }
+ for i=1,#zippers do
+ list[#list+1] = zippers[i].name
+ end
+ report("no epub archive made, install one of: % | t",list)
+ end
+
+ if reportobsolete(oldfiles,newfiles,purge) then
+ obsolete = true
+ end
+ if obsolete and not purge then
+ report("use --purge to remove obsolete files")
end
end
--
-if environment.argument("make") then
- scripts.epub.make()
-elseif environment.argument("exporthelp") then
- application.export(environment.argument("exporthelp"),environment.files[1])
+local a_exporthelp = environment.argument("exporthelp")
+local a_make = environment.argument("make")
+local a_all = environment.argument("all")
+local a_purge = a_all or environment.argument("purge")
+local a_rename = a_all or environment.argument("rename")
+local a_svgmath = a_all or environment.argument("svgmath")
+local a_svgstyle = environment.argument("svgstyle")
+
+if a_make and a_svgmath then
+ require("x-math-svg")
+end
+
+if a_make then
+ scripts.epub.make(a_purge,a_rename,a_svgmath,a_svgstyle)
+elseif a_exporthelp then
+ application.export(a_exporthelp,environment.files[1])
else
application.help()
end
+
+-- java -jar d:\epubcheck\epubcheck-3.0.1.jar -v 3.0 -mode xhtml mkiv-publications.tree\mkiv-publications.epub