Проверка кода
Я сделал быструю проверку кода в вашем XSL (и CSS) файле.Даже если это не решит вашу проблему, это поможет воспроизвести и понять ее.Вот мои комментарии:
Ваш XSL имеет опечатку: <! begin LI>
не является допустимой вкладкой XML.Это комментарий?
Я предпочитаю использовать concat()
функцию XPath для непосредственного добавления символов.Потому что, если вы сделаете отступ в своем коде, вы можете ввести дополнительные пробелы.
Итак, я заменил:
<xsl:attribute name="href"><xsl:value-of select="@link"/> . </xsl:attribute>
на:
<xsl:attribute name="href">
<xsl:value-of select="concat(@link, ' . ')"/>
</xsl:attribute>
Я добавил xs:if
, чтобы предотвратить создание пустого <ul>
, если в этом нет необходимости:
<xsl:if test="count(outline:item)">
<ul>
<xsl:comment>added to prevent self-closing tags in QtXmlPatterns</xsl:comment>
<xsl:apply-templates select="outline:item"/>
</ul>
</xsl:if>
Я также исправил дублирующиеся или неправильно сформированные записи CSS, язаменено:
li {
border-bottom: 1px dashed rgb(45, 117, 183);
}
span {
float: right;
}
li {
list-style: none;
margin-top: 30px;
}
ul ul {font-size: 80%; padding-top:0px;}
ul {padding-left: 0em; padding-top:0px;}
ul ul {padding-left: 1em; padding-top:0px;}
a {text-decoration:none; color: color:#2d75b7;}
на:
span {
float: right;
}
li {
list-style: none;
margin-top: 30px;
border-bottom: 1px dashed rgb(45, 117, 183);
}
ul {
font-size: 70px;
font-family: arial;
color: #2d75b7;
}
ul ul {
font-size: 80%;
padding-left: 1em;
padding-top: 0px;
}
a {
text-decoration: none;
color: #2d75b7;
}
Если вы нацелены на XHTML, тег <style>
имеет обязательный атрибут type
.То же самое замечание для атрибута <script>
.
<style type="text/css">...</style>
<script type="text/javascript">...</script>
Воспроизведение проблемы
Воспроизвести ошибку было немного сложно из-за недостатка информации.Так что я думаю.
Сначала я создаю пример файла оглавления, который выглядит следующим образом:
outline.xml
<?xml version="1.0" encoding="UTF-8"?>
<outline xmlns="http://wkhtmltopdf.org/outline">
<item>
<item title="Lorem ipsum dolor sit amet, consectetur adipiscing elit." page="2"/>
<item title="Cras at odio ultrices, elementum leo at, facilisis nibh." page="8"/>
<item title="Vestibulum sed libero bibendum, varius massa vitae, dictum arcu." page="19"/>
...
<item title="Sed semper augue quis enim varius viverra." page="467"/>
</item>
</outline>
Этофайл содержит 70 элементов, поэтому я могу видеть разрывы страниц.
Для построения HTML и PDF я использовал ваш (исправленный) XSL-файл и запустил pdfkit:
import io
import os
import pdfkit
from lxml import etree
HERE = os.path.dirname(__file__)
def layout(src_path, dst_path):
# load the XSL
xsl_path = os.path.join(HERE, "layout.xsl")
xsl_tree = etree.parse(xsl_path)
# load the XML source
src_tree = etree.parse(src_path)
# transform
transformer = etree.XSLT(xsl_tree)
dst_tree = transformer.apply(src_tree)
# write the result
with io.open(dst_path, mode="wb") as f:
f.write(etree.tostring(dst_tree, encoding="utf-8", method="html"))
if __name__ == '__main__':
layout(os.path.join(HERE, "outline.xml"), os.path.join(HERE, "outline.html"))
pdfkit.from_file(os.path.join(HERE, "outline.html"),
os.path.join(HERE, "outline.pdf"),
options={'page-size': 'A1', 'orientation': 'landscape'})
note: размер вашей страницы выглядит очень огромным…
Решение
Вы правы, wkhtmltopdf не учитывает поля в вашем CSS:
li {
list-style: none;
border-bottom: 1px dashed rgb(45, 117, 183);
margin-top: 30px; # <-- not working after page break
}
Это нормальное поведение, рассмотрим, например, заголовки абзацев (h1
, h2
и т. Д.).Заголовок может иметь верхнее поле, чтобы добавить пробел между абзацем и следующим заголовком, но, если заголовок начинает новую страницу, мы хотим избавиться от поля и иметь заголовок, касающийся верхнего поля страницы..
Для вашего оглавления есть решение.Вы можете использовать padding
(вместо margin
):
li {
border-bottom: 1px dashed rgb(45, 117, 183);
list-style: none;
padding-top: 30px;
}
На самом деле содержание TOC (#toc
элемент) является фиксированным:
#toc {
width: 50%;
margin-top: 150px;
margin-left: 300px;
}
Итак, вы можетеуменьшите margin-top
в соответствии с вашими потребностями, например:
#toc {
width: 50%;
margin-top: 120px;
margin-left: 300px;
}