Comments (4)
I've used the template in combination with nunjucks.
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta http-equiv="content-type" content="text/html; charset=utf-8">
<style>
@font-face {
font-family: 'SackersGothicStd';
font-style: normal;
font-weight: 500;
src: url(file:///path/to/fonts/SackersGothicStd-Medium.otf);
}
@font-face {
font-family: 'Cambria';
font-style: normal;
font-weight: 400;
src: url(file:///path/to/fonts/Cambria-Regular.ttf);
}
@font-face {
font-family: 'Cambria';
font-style: normal;
font-weight: 700;
src: url(file:///path/to/fonts/Cambria-Bold.ttf);
}
</style>
</head>
<body>
<div id="pageHeader">
<style>
/*
*
* Header
*
*/
#pageHeader {
margin: 10mm 20mm 0 25mm;
position: relative;
}
#pageHeader .line1 {
position: absolute;
left: 0;
width: 230px;
top: 80px;
height: 1px;
background: #888888;
}
#pageHeader .line2 {
position: absolute;
right: 0;
width: 230px;
top: 80px;
height: 1px;
background: #888888;
}
#pageHeader #logo {
position: absolute;
top: 0;
left: 50%;
height: 120px;
width: 120px;
margin-left: -60px;
}
#pageHeader p {
font-family: "SackersGothicStd";
font-weight: 500;
padding-top: 100px;
text-align: center;
font-size: 14px;
color: #888888;
margin-bottom: 0;
text-transform:lowercase;
}
</style>
<div class="line1"></div>
<div class="line2"></div>
<svg id="logo" xmlns="http://www.w3.org/2000/svg" version="1.1">
<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<svg version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px" viewBox="0 0 100 100" enable-background="new 0 0 100 100" xml:space="preserve">
<g id="background">
<rect fill="none" width="100" height="100"/>
</g>
<g>
<g>
<g>
<path d="M30.115,63.806c-0.53-0.297-1.234-0.74-2.641-0.74c-1.185,0-1.79,0.309-1.79,0.852c0,0.617,0.222,0.814,2.062,0.814
c2.888,0,3.22,0.876,3.22,1.876c0,1.839-1.715,2.16-3.147,2.16c-2.184,0-3.332-0.79-3.751-1.087l0.519-0.95
c0.741,0.444,1.456,0.95,3.258,0.95c1.148,0,1.95-0.246,1.95-0.962c0-0.815-0.42-0.84-2.814-0.901
c-1.457-0.024-2.468-0.444-2.468-1.777c0-1.073,0.802-2.061,2.949-2.061c1.556,0,2.728,0.629,3.16,0.851L30.115,63.806z"/>
<path d="M39.587,65.793c0,1.616-0.556,2.975-3.086,2.975c-2.518,0-3.085-1.358-3.085-2.975v-3.616h1.085v3.616
c0,1.159,0.223,1.888,2,1.888c1.777,0,2-0.729,2-1.888v-3.616h1.086V65.793z"/>
<path d="M43.84,68.569h-1.086v-6.393h1.086V68.569z"/>
<path d="M49.631,68.569h-1.085v-5.307h-2.469v-1.086h5.998v1.086h-2.444V68.569z"/>
<path d="M60.269,68.569h-1.284l-0.815-1.493h-3.9l-0.79,1.493h-1.234l3.456-6.393h1.086L60.269,68.569z M56.232,63.398
l-1.395,2.592h2.79L56.232,63.398z"/>
<path d="M68.712,68.569h-1.358l-1.838-2.616h-2.247v2.616h-1.086v-6.393h3.95c1.284,0,2.431,0.432,2.431,1.839
c0,1.419-0.963,1.789-1.716,1.913L68.712,68.569z M66.243,64.867c0.716,0,1.234-0.197,1.234-0.827
c0-0.716-0.469-0.777-1.296-0.777h-2.913v1.604H66.243z"/>
<path d="M73.872,68.569h-1.086v-5.307h-2.468v-1.086h5.998v1.086h-2.443V68.569z"/>
</g>
<path d="M70.072,46.906H30.833c-4.328,0-7.835-3.508-7.836-7.836l0,0c0.001-4.329,3.507-7.836,7.836-7.837l0,0h40.242l5.929,3.644
l-1.856,3.019l-5.075-3.119H30.833c-2.37,0.004-4.289,1.922-4.293,4.293l0,0c0.004,2.369,1.921,4.288,4.293,4.292l0,0h40.242
l5.924,3.646v0.001l-1.857,3.016L70.072,46.906L70.072,46.906z"/>
</g>
</g>
</svg>
<p>{{place.defaults.letter.header_center | lng(order.lng) | default('Address line 1 • 8000 Zurich • Switzerland') | lower}}</p>
</div>
<div id="pageContent">
<style>
body {
font-family: 'Cambria';
font-size: 15px;
margin: 0;
}
#pageContent {
margin: 0 20mm 0 25mm;
position: relative;
}
h1 {
font-size: 16px;
margin-bottom: 20px;
}
h1 small {
font-size: 15px;
margin-left: 20px;
color: #777;
}
#address {
position: absolute;
top: 20px;
left: 325px;
right: 0;
height: 200px;
line-height: 1.2em;
}
#content {
position: absolute;
top: 180px;
left: 0;
right: 0;
bottom: 0;
}
#date {
position: absolute;
top: 11px;
left: 325px;
}
#prefix {
margin-bottom: 10px;
}
#total {
margin-bottom: 30px;
}
#postfix {
clear: both;
}
#total {
float:right;
}
#line_items {
border-top: 1px solid rgb(200,200,200);
}
#line_items .price, #total .price {
width: 90px;
}
#total .tax {
font-size: 0.9em;
}
table {
border-collapse: collapse;
border-spacing: 0;
background: rgb(255, 255, 255);
margin-bottom: 0.25em;
}
thead, tfoot {
background: rgb(230, 230, 230);
font-weight: 700;
}
thead td, tfoot td {
padding: .4em .625em .4em;
font-size: .875em;
color: rgb(20, 20, 20);
vertical-align: center;
}
tbody td {
padding: .5em .625em .625em;
font-size: .875em;
color: rgb(50, 50, 50);
text-align: left;
vertical-align: top;
}
td .b {
font-weight: 700;
}
td .d {
margin: 5px 0 0 0;
}
tr {
border-bottom: solid 1px rgb(200, 200, 200);
}
tr.highlight {
background: #808080;
}
</style>
<div id="address">
<p>
{% set address = order.getAddress() %}
<div class="name">{{address.name}}</div>
<div class="thoroughfare">{{address.thoroughfare}}</div>
<div class="premise">{{address.premise}}</div>
<div class="locality">{{address.postalcode}} {{address.locality}}<br></div>
<div class="country">{{address.country | country(order.lng)}}</div>
</p>
</div>
<div id="content">
<h1>Quittung<small>{{order.data.ordernumber or order.ordernumber }}</small></h1>
<div id="date">
{% if place.title %}<span class="place">{{place.title}}, </span>{% endif %}
<span class="date">{{order.created_at | date('L', order.lng)}}</span>
</div>
<div id="prefix">
{{order.data.prefix | default('') | markdown}}
{{place.defaults.letter.prefix}}
</div>
<div id="main">
<table id="line_items" width="100%">
<thead>
<tr>
<td>#</td>
<td>Product</td>
<td class="unit_price">Unit price</td>
<td>Quantity</td>
<td class="price">Total</td>
</tr>
</thead>
<tbody>
{% for lineitem in order.line_items %}
<tr>
<td>{{loop.index}}</td>
<td>
<div class="b">{{lineitem.getTitle()}}</div>
<div class="d"></div>
</td>
<td>{{lineitem.getPrice() | currency(order.currency)}}</td>
<td>{{lineitem.quantity}}</td>
<td>{{lineitem.totalPrice() | currency(order.currency)}}</td>
</tr>
{% endfor %}
</tbody>
</table>
<table id="total" width="60%">
<tfoot>
<tr>
<td>Total</td>
<td class="price">{{order.total_price | currency(order.currency)}}</td>
</tr>
</tfoot>
<tbody>
<tr>
<td>Subtotal</td>
<td class="price">{{order.subtotal_price | currency(order.currency)}}</td>
</tr>
<tr class="tax">
<td><small>Taxes</small></td>
<td class="price">{{order.total_tax | currency(order.currency)}}</td>
</tr>
</tbody>
</table>
<table id="total" width="60%">
{% for snap in order.snapshots %}
<tbody>
<tr>
<td>Transaction date</td>
<td class="price">{{snap.created_at | date('L', order.lng)}}</td>
</tr>
{% for transaction in snap.transactions %}
<tr>
<td class="tax"><small>{{transaction.type | transaction(order.lng)}}</small></td>
<td class="tax"><small>{{transaction.amount | currency(order.currency)}}</small></td>
</tr>
{% endfor %}
</tbody>
{% endfor %}
</table>
<table id="total" width="60%">
<tbody>
<tr>
<td><b>Amount paid</b></td>
<td><b>{{order.total_transactions | currency(order.currency)}}</b></td>
</tr>
{% if order.total_balance %}
<tr>
<td>Outstanding amount</td>
<td class="price">{{order.total_balance | currency(order.currency)}}</td>
</tr>
{% endif %}
</tbody>
</table>
</div>
<br/>
<br/>
<br/>
<div id="postfix">
{{place.defaults.letter.postfix | lng(order.lng) }}<br/>
{{order.data.postfix | default('') | markdown}}
</div>
</div>
</div>
<div id="pageFooter">
<style>
#pageFooter {
position: absolute;
bottom: 0;
width: 100%;
height: 90px;
font-family: 'Cambria';
color: #888888;
}
.block {
position: absolute;
top: 6px;
width: 250px;
font-size: 12px;
}
.left {
left: 25mm;
text-align: left;
}
.center {
left: 50%;
margin-left: -125px;
text-align: center;
}
.right {
right: 20mm;
text-align: right;
}
</style>
<div class="block left">
{{place.defaults.letter.footer_left | lng(order.lng) | default('Example Ltd.<br/>Address line 1<br/>8000 Zurich')}}
</div>
<div class="block center">
{{place.defaults.letter.footer_center | lng(order.lng) | default('UID: CHE-000.000.000<br/>IBAN: AA00 0000 0000 0000 0000 0')}}
</div>
<div class="block right">
{{place.defaults.letter.footer_right | lng(order.lng) | default('0800 800 678<br/>[email protected]<br/>www.example.com')}}
</div>
</div>
</body>
</html>
from node-html-pdf.
from node-html-pdf.
@marcbachmann How did you manage to use your fonts ? Something like gridFs?
from node-html-pdf.
gridfs is only a file-database implementation. You'll need to serve the file in a supported way.
Phantomjs accepts urls using the file:// & http:// protocol. So as
long as you can serve the font using a webserver or a file system, you
can embed the font in the pdf.
In my case I stored the fonts in my project directory.
from node-html-pdf.
Related Issues (20)
- Text not being displayed on Mac. Working fine on Windows HOT 1
- Custom font not working HOT 1
- How can I make sure table header section should have at least one row.
- Background color not applying those area where no html
- Image not showing when uploaded on vps server
- QR code not visible over generated pdf post ami upgrade HOT 2
- Fonts don't work properly on server HOT 4
- stream (.toStream) not generated after deploying to k8s HOT 2
- The download pdf always have an empty page at last HOT 1
- html-pdf: Unknown Error throw new ERR_INVALID_ARG_TYPE(name, 'string', value); Docker HOT 1
- Pdf saved in TMP directory HOT 1
- Is watermark possible in pdf? HOT 3
- Not able to resize the chebox size while generating the pdf
- Syntax for forcing a page break HOT 2
- Potential injection vulnerability in node-html-pdf
- Page overflow with white line
- PDF Creation Error: spawn /root/pando-app/node_modules/phantomjs-prebuilt/lib/phantom/bin/phantomjs ENOENT HOT 1
- The answer to how to resolve Windows error of phantomjs ENOENT issue
- Error: spawn E2BIG
- error HOT 2
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from node-html-pdf.