We made a Tax Invoice format that looks like the one from Tally for icebreaking a tally user. Not sure what is the best procedure to contribute so pasting it here.
It is always better to share a screenshot to get users attention.
Thanks
This looks very good.
Good to have you to contribute it back to the community.
You can Post the print format script here if you want so those who would like to use this script can make use of your source code.
[ { "align_labels_right": 0, "css": ".print-format {\npadding-left: 5mm;\npadding-right: 5mm;\npadding-top: 10mm;\npadding-bottom: 5mm;\n}\n", "custom_format": 1, "default_print_language": null, "disabled": 0, "doc_type": "Sales Invoice", "docstatus": 0, "doctype": "Print Format", "font": "Default", "format_data": "[{\"fieldname\": \"print_heading_template\", \"fieldtype\": \"Custom HTML\", \"options\": \"\\t\\t\\t\\t\\n\"}, {\"fieldtype\": \"Section Break\", \"label\": \"Address\"}, {\"fieldtype\": \"Column Break\"}, {\"print_hide\": 0, \"fieldname\": \"address_display\", \"label\": \"Address\"}, {\"print_hide\": 0, \"fieldname\": \"contact_display\", \"label\": \"Contact\"}, {\"print_hide\": 0, \"fieldname\": \"contact_mobile\", \"label\": \"Mobile No\"}, {\"fieldtype\": \"Column Break\"}, {\"fieldtype\": \"Section Break\", \"label\": \"Currency\"}, {\"fieldtype\": \"Column Break\"}, {\"print_hide\": 0, \"fieldname\": \"conversion_rate\", \"label\": \"Exchange Rate\"}, {\"fieldtype\": \"Column Break\"}, {\"fieldtype\": \"Section Break\", \"label\": \"\"}, {\"fieldtype\": \"Column Break\"}, {\"print_hide\": 0, \"fieldname\": \"scan_barcode\", \"label\": \"Scan Barcode\"}, {\"visible_columns\": [{\"print_hide\": 0, \"fieldname\": \"item_code\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"description\", \"print_width\": \"200px\"}, {\"print_hide\": 0, \"fieldname\": \"image\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"qty\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"stock_uom\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"uom\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"discount_amount\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"rate\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"amount\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"pricing_rule\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"deferred_revenue_account\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"service_stop_date\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"enable_deferred_revenue\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"service_start_date\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"service_end_date\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"quality_inspection\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"serial_no\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"asset\", \"print_width\": \"\"}], \"print_hide\": 0, \"fieldname\": \"items\", \"label\": \"Items\"}, {\"fieldtype\": \"Section Break\", \"label\": \"\"}, {\"fieldtype\": \"Column Break\"}, {\"print_hide\": 0, \"fieldname\": \"total_qty\", \"label\": \"Total Quantity\"}, {\"fieldtype\": \"Column Break\"}, {\"print_hide\": 0, \"fieldname\": \"total\", \"label\": \"Total\"}, {\"fieldtype\": \"Section Break\", \"label\": \"\"}, {\"fieldtype\": \"Column Break\"}, {\"visible_columns\": [{\"print_hide\": 0, \"fieldname\": \"charge_type\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"row_id\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"account_head\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"cost_center\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"description\", \"print_width\": \"300px\"}, {\"print_hide\": 0, \"fieldname\": \"rate\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"tax_amount\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"total\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"tax_amount_after_discount_amount\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"base_tax_amount\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"base_total\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"base_tax_amount_after_discount_amount\", \"print_width\": \"\"}, {\"print_hide\": 0, \"fieldname\": \"item_wise_tax_detail\", \"print_width\": \"\"}], \"print_hide\": 0, \"fieldname\": \"taxes\", \"label\": \"Sales Taxes and Charges\"}, {\"fieldtype\": \"Section Break\", \"label\": \"Loyalty\"}, {\"fieldtype\": \"Column Break\"}, {\"fieldtype\": \"Column Break\"}, {\"print_hide\": 0, \"fieldname\": \"loyalty_redemption_account\", \"label\": \"Redemption Account\"}, {\"print_hide\": 0, \"fieldname\": \"loyalty_redemption_cost_center\", \"label\": \"Redemption Cost Center\"}, {\"fieldtype\": \"Section Break\", \"label\": \"\"}, {\"fieldtype\": \"Column Break\"}, {\"print_hide\": 0, \"fieldname\": \"base_grand_total\", \"align\": \"left\", \"label\": \"Grand Total (TZS)\"}, {\"print_hide\": 0, \"fieldname\": \"base_rounded_total\", \"align\": \"left\", \"label\": \"Rounded Total (TZS)\"}, {\"print_hide\": 0, \"fieldname\": \"base_in_words\", \"align\": \"left\", \"label\": \"In Words (TZS)\"}, {\"fieldtype\": \"Column Break\"}, {\"print_hide\": 0, \"fieldname\": \"grand_total\", \"label\": \"Grand Total\"}, {\"print_hide\": 0, \"fieldname\": \"rounded_total\", \"label\": \"Rounded Total\"}, {\"print_hide\": 0, \"fieldname\": \"in_words\", \"label\": \"In Words\"}, {\"fieldtype\": \"Section Break\", \"label\": \"Advance\"}, {\"fieldtype\": \"Column Break\"}, {\"print_hide\": 0, \"fieldname\": \"allocate_advances_automatically\", \"label\": \"Allocate Advances Automatically (FIFO)\"}, {\"print_hide\": 0, \"fieldname\": \"get_advances\", \"label\": \"Get Advances Received\"}, {\"fieldtype\": \"Section Break\", \"label\": \"Terms\"}, {\"fieldtype\": \"Column Break\"}, {\"print_hide\": 0, \"fieldname\": \"terms\", \"label\": \"Terms and Conditions Details\"}, {\"fieldtype\": \"Section Break\", \"label\": \"More\"}, {\"fieldtype\": \"Column Break\"}, {\"print_hide\": 0, \"fieldname\": \"inter_company_invoice_reference\", \"label\": \"Inter Company Invoice Reference\"}, {\"fieldtype\": \"Column Break\"}, {\"fieldtype\": \"Section Break\", \"label\": \"Subscription\"}, {\"fieldtype\": \"Column Break\"}, {\"fieldtype\": \"Column Break\"}, {\"print_hide\": 0, \"fieldname\": \"update_auto_repeat_reference\", \"label\": \"Update Auto Repeat Reference\"}]", "html": "Tax Invoice
\\nTax Invoice
\n\n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n \n
\n {{ doc.company or \"\" }} \n {{ frappe.db.get_value(\"Company\", doc.company, \"registration_details\") or \"\" }}\n |
\n Invoice No. \n {{ doc.name }}\n |
\n Dated \n\t {{ frappe.utils.formatdate(doc.posting_date) }}\n |
\n Delivery Note \n\t \n |
\n Mode/Terms of Payment \n\t \n |
|
\n Supplier's Ref. \n\t \n |
\n Other Reference(s) \n\t \n |
|
\n Customer \n {{ doc.customer_name or \"\" }} \n\t {{ doc.address_display or \"\" }}\n |
\n Buyer's Order No. \n\t \n |
\n Dated \n\t \n |
\n Despatch Document No. \n\t \n |
\n Dated \n\t \n |
|
\n Despatched through \n\t \n |
\n Destination \n\t \n |
|
\n Terms of Delivery \n\t \n |
Sl\n\t | Particulars\n\t | QTY\n\t | Rate\n\t | VAT\n\t | Amount\n |
---|---|---|---|---|---|
{{ loop.index }} | {{ item.item_name }} | {{ item.get_formatted(\"qty\", 0) }} | {{ item.get_formatted(\"rate\", doc) }} | \n\t\t{% set mydict = json.loads(item.item_tax_rate) %}\n\t\t{% if item.item_tax_rate == \"{}\" %}\n\t\t\t{% for row in doc.taxes %}\n\t\t\t\t{{ row.rate }}.0%\n\t\t\t{% endfor %}\n\t\t{% else %}\n\t\t\t{% for key, value in mydict.items() %}\n\t\t\t\t{{ value }}%\n\t\t\t{% endfor %}\n\t\t{% endif %}\n\n\n | {{ item.get_formatted(\"amount\", doc) }} |
\n Amount in Words \n {{ doc.in_words }} \n {{ doc.base_in_words }}\n |
SUB TOTAL | {{ doc.get_formatted(\"base_total\", doc) }} | {{ doc.get_formatted(\"total\", doc) }} |
VAT | {{ doc.get_formatted(\"base_total_taxes_and_charges\", doc) }} | {{ doc.get_formatted(\"total_taxes_and_charges\", doc) }} | |
TOTAL | {{ doc.get_formatted(\"base_grand_total\", doc) }} | {{ doc.get_formatted(\"grand_total\", doc) }} | |
{{ doc.remarks }} | \n for {{ doc.company }}\n \n \n \n Authorised Signatory\n \n |
Hope this helps others. Need to enhance it, but it is a start.
There’s no easy way to export a print format as a file. Not sure what would be a better way out? Data export of print format DocType?
Will need help, but surely can do it if the correct method is known.
No the issue is the above script which you have posted, the UI of this forum has tried to render the html in it. If you can just post the HTML and CSS separately, I think that would do.
Does this help?
<center><h3>Tax Invoice</h3><center>
<table width=90% height=30% border=1>
<tr>
<td width=50% rowspan=3>
<strong>{{ doc.company or "" }}</strong><br>
{{ frappe.db.get_value("Company", doc.company, "registration_details") or "" }}
</td>
<td width=25%>
Invoice No.<br>
<b>{{ doc.name }}</b>
</td>
<td width=25%>
Dated<br>
<b>{{ frappe.utils.formatdate(doc.posting_date) }}</b>
</td>
</tr>
<tr>
<td width=25%>
Delivery Note<br>
<b> </b>
</td>
<td width=25%>
Mode/Terms of Payment<br>
<b> </b>
</td>
</tr>
<tr>
<td width=25%>
Supplier's Ref.<br>
<b> </b>
</td>
<td width=25%>
Other Reference(s)<br>
<b> </b>
</td>
</tr>
<tr>
<td width=50% rowspan=4>
<i>Customer</i><br>
<strong>{{ doc.customer_name or "" }}</strong><br>
{{ doc.address_display or "" }}
</td>
<td width=25%>
Buyer's Order No.<br>
<b> </b>
</td>
<td width=25%>
Dated<br>
<b> </b>
</td>
</tr>
<tr>
<td width=25%>
Despatch Document No.<br>
<b> </b>
</td>
<td width=25%>
Dated<br>
<b> </b>
</td>
</tr>
<tr>
<td width=25%>
Despatched through<br>
<b> </b>
</td>
<td width=25%>
Destination<br>
<b> </b>
</td>
</tr>
<tr>
<td width=25% height=100 colspan=2>
Terms of Delivery<br>
<b> </b>
</td>
</tr>
</table>
<TABLE cellpadding=0 cellspacing=0 width=90% border=1>
<TR>
<TH WIDTH=1%>Sl</TD>
<TH>Particulars</TD>
<TH WIDTH=3%>QTY</TD>
<TH WIDTH=20%>Rate</TD>
<TH WIDTH=20%>VAT</TD>
<TH WIDTH=20%>Amount</TD>
</TR>
{% for item in doc.items %}
{% set remrows = 10 - loop.revindex %}
<TR>
<TD>{{ loop.index }}</TD>
<TD>{{ item.item_name }}</TD>
<TD align=center>{{ item.get_formatted("qty", 0) }}</TD>
<TD align=right>{{ item.get_formatted("rate", doc) }}</TD>
<td align=center>
{% set mydict = json.loads(item.item_tax_rate) %}
{% if item.item_tax_rate == "{}" %}
{% for row in doc.taxes %}
{{ row.rate }}.0%
{% endfor %}
{% else %}
{% for key, value in mydict.items() %}
{{ value }}%
{% endfor %}
{% endif %}
</td>
<TD align=right>{{ item.get_formatted("amount", doc) }}</TD>
</TR>
{% set trate = "" %}
{% endfor %}
<!-- {% set loop = 10 - doc.items|length %}
{% for i in range(loop) %}
<TR>
<TD> </TD>
<TD> </TD>
<TD> </TD>
<TD> </TD>
<TD> </TD>
</TR>
{% endfor %} -->
</TABLE>
<TABLE cellpadding=0 cellspacing=0 width=90% border=1>
<TR>
<TD rowspan=3 >
Amount in Words<br>
<B>{{ doc.in_words }}</B><br><br>
<B>{{ doc.base_in_words }}</B>
</TD>
<TD WIDTH=13% align=right><B>SUB TOTAL</B></TD>
<TD WIDTH=20% align=right><B>{{ doc.get_formatted("base_total", doc) }}</B></TD>
<TD WIDTH=20% align=right><B>{{ doc.get_formatted("total", doc) }}</B></TD>
</TR>
<TR>
<TD align=right><B>VAT</B></TD>
<TD WIDTH=20% align=right><B>{{ doc.get_formatted("base_total_taxes_and_charges", doc) }}</B></TD>
<TD WIDTH=20% align=right><B>{{ doc.get_formatted("total_taxes_and_charges", doc) }}</B></TD>
</TR>
<TR>
<TD align=right><B>TOTAL</B></TD>
<TD WIDTH=20% align=right><B>{{ doc.get_formatted("base_grand_total", doc) }}</B></TD>
<TD WIDTH=20% align=right><B>{{ doc.get_formatted("grand_total", doc) }}</B></TD>
</TR>
<TR>
<TD colspan=2 height=120>{{ doc.remarks }}</B></TD>
<TD align=right colspan=3>
<B>for {{ doc.company }}</B>
<div style="position: relative; height: 100px; border: solid; border-style: none;">
<div style="position: absolute; height: 10px; border: solid; bottom: 0; right: 0; left: 0; border-style: none;">
Authorised Signatory
</div>
</div>
</TD>
</TR>
</TABLE>
I think this will help a great deal. Let me try it and let you know. Again thanks for sharing and appreciate your efforts.
Palash
Can someone please tell me where do I get a list of all the values like doc.get_formatted("base_total, doc.get_formatted(“total”, doc) etc, so that I can customise the format further ?.
I can help but I don’t understand what you want to do. Share some final outcome you need so that we can assist.
e.g.
{{ frappe.db.get_value(“Company”, doc.company, “registration_details”) or “” }}
Thank you very much for the contribution.
I’ve tried the layout and I’ve noticed that there is always an extra blank page whenever the PDF is saved. (even when the invoice has one entry)
How have you managed to overcome this?
Thanking You
hey,
I’ve tried your print format, its good.
I am trying to bring tax rate & tax calculations on row basis, rather that tax charges shown below.
I am running
ERPNext: v12.x.x-develop () (develop)
Frappe Framework: v12.0.18 (version-12)
& I am using item tax template to calculate different taxes.
Can you please help me bring calculations to a single line in your format.
Not sure if this will help but give it a shot:
<TABLE border=1 style="width: 100%; border-collapse: collapse; border: 1px solid black;">
<colgroup>
<col style="width: 5%">
<col style="width: 35%">
<col style="width: 10%">
<col style="width: 10%">
<col style="width: 20%">
<col style="width: 20%">
</colgroup>
<THEAD>
<TR>
<TH style="text-align:center">SI</TD>
<TH style="text-align:center">Particulars</TD>
<TH style="text-align:center">QTY</TD>
<TH style="text-align:center">VAT</TD>
<TH style="text-align:center">Rate</TD>
<TH style="text-align:center">Amount</TD>
</TR>
</THEAD>
{% for item in doc.items %}
<TR>
<TD>{{ loop.index }}</TD>
<TD>
<b>{{ item.item_name }}</b>
{% if (item.description != item.item_name) %}
<br>{{ item.description }}
{% endif %}
</TD>
<TD align=center>
{{ item.get_formatted("qty", 0) }}
{{ item.get_formatted("uom", 0) }}
</TD>
<TD align=center>
{% set mydict = json.loads(item.item_tax_rate) %}
{% if item.item_tax_rate == "{}" %}
{% for row in doc.taxes %}
{{ row.get_formatted("rate",0) }}%
{% endfor %}
{% else %}
{% set ns = namespace(vat=none) %}
{% for key, value in mydict.items() %}
{% set ns.vat = value %}
{% endfor %}
{{ ns.vat }}%
{% endif %}
</TD>
<TD align=right>{{ item.get_formatted("net_rate", doc) }}</TD>
<TD align=right>{{ item.get_formatted("net_amount", doc) }}</TD>
</TR>
{% endfor %}
<TR>
<TD rowspan=5 colspan=4 style="vertical-align: top !important;">
Amount in Words<br>
<B>{{ doc.in_words }}</B><br><br>
<B>
{% if doc.currency != "TZS" %}
{{ doc.base_in_words }}
{% endif %}
</B>
</TD>
<TD align=right><B>SUB. TOTAL</B></TD>
<TD align=right><B>{{ doc.get_formatted("net_total", doc) }}</B></TD>
</TR>
<TR>
<TD align=right><B>V.A.T.</B></TD>
<TD align=right><B>{{ doc.get_formatted("total_taxes_and_charges", doc) }}</B></TD>
</TR>
<TR>
<TD align=right><B>TOTAL</B></TD>
<TD align=right><B>{{ doc.get_formatted("grand_total", doc) }}</B></TD>
</TR>
<TR>
<TD colspan=2 align=right><i><small><strong>E&OE</strong></small></i></TD>
</TR>
<TR>
<TD align=left><STRONG>Assessable Value:</STRONG></TD>
<TD align=right>
{% if (doc.base_total_taxes_and_charges == 0) %}
{{ frappe.utils.fmt_money(0, currency="") }}
{% else %}
{% if (doc.base_net_total != doc.base_total) %}
{{ frappe.utils.fmt_money(doc.base_net_total, currency="") }}
{% else %}
{{ frappe.utils.fmt_money(doc.base_total_taxes_and_charges / 0.18, currency="") }}
{% endif %}
{% endif %}
</TD>
</TR>
<TR>
<TD colspan=4 rowspan=5 style="padding:0px; margin:0px; vertical-align: top !important;">
{% if (doc.from_date != None) %}
PERIOD: FROM {{ frappe.utils.formatdate(doc.from_date, 'dd-MMM-YYYY') }} TO {{ frappe.utils.formatdate(doc.to_date, 'dd-MMM-YYYY') }}<br>
{% endif %}
{% if (doc.remarks != "No Remarks") %}{{ doc.remarks }}{% endif %}
</TD>
<TD align=left><STRONG>VAT Amount:</STRONG></TD>
<TD align=right>{{ frappe.utils.fmt_money(doc.base_total_taxes_and_charges, currency="") }}</TD>
</TR>
<TR>
<TD align=left><STRONG>Exempt:</STRONG></TD>
<TD align=right>
{% if (doc.base_total_taxes_and_charges == 0) %}
{{ frappe.utils.fmt_money(doc.base_total, currency="") }}
{% else %}
{% if (doc.base_net_total != doc.base_total) %}
{{ frappe.utils.fmt_money(doc.base_grand_total - (doc.base_net_total + doc.base_total_taxes_and_charges), currency="") }}
{% else %}
{{ frappe.utils.fmt_money(doc.base_grand_total - ((doc.base_total_taxes_and_charges / 0.18) + doc.base_total_taxes_and_charges), currency="") }}
{% endif %}
{% endif %}
</TD>
</TR>
<TR>
<TD align=left><STRONG>Special Relief:</STRONG></TD>
<TD align=right> </TD>
</TR>
<TR>
<TD align=left><STRONG>Zero Rated:</STRONG></TD>
<TD align=right> </TD>
</TR>
<TR>
<TD align=left><STRONG>Total:</STRONG></TD>
<TD align=right style="border-top: 2px solid black;"><b>{{ frappe.utils.fmt_money(doc.base_grand_total, currency="") }}</b></TD>
</TR>
</TABLE>
<div id="header-html" class="hidden-pdf">
<div id="variables" style="display:none;">
<span id="margin-top">1mm</span>
<span id="margin-left">1mm</span>
<span id="margin-right">1mm</span>
<span id="margin-bottom">0mm</span>
</div>
</div>
It has got some hardcoding for our environment, so you may have to soft-code it. If you do, then share the code as well.
Hey thanks for prompt reply.
Here is print format screenshot of the code you sent.
This is what we have setup, based on your print format.
We have three tax heads CGST, SGST & IGST.
In the print format above of sales invoice two tax heads are applicable, CGST 6% & SGST 6% (These are applicable for inter-state, if supply would have been made intra-state then IGST would have been applicable @ 12%)
What I want, please find s.s below
Can you please help with this type of format.
You will have to use this part of the code in every tax column with its respected tax name. And using its percentage you can get the tax value. This will be a formula which will calculate the rate in the basis on item master tax table tax rate.
Hey.
Thanks for ur reply
I will try it out soon and get back to you.
Thanx
Please share the Screenshot of the Item Tax table in Item form and of item tax details in sales invoice Item row.
Will try to help you with the script.