Unified /labels page (badges, edit, preview), mnemonic ESC/POS parser for the raw receipt field
deploy / deploy (push) Successful in 10s
deploy / deploy (push) Successful in 10s
- Saved labels/receipts now show on one page instead of split across Shipping labels and Receipts, each with a badge for its type/printer, Edit (name+content, in place), Print, and Delete. - ZPL labels get a real visual preview via Labelary's public render API; ESC/POS ones show their raw content (no good general preview for that). - The Receipts free-text field only ever encoded whatever was typed as literal printable characters -- pasting mnemonic ESC/POS notation (ESC/GS/LF as command names, 0xNN as raw bytes) just printed as text instead of being interpreted. Added a small line-based parser for that notation (ReceiptBuilder#raw appends already-resolved bytes verbatim), verified byte-for-byte against an example with align/bold/barcode/cut.
This commit is contained in:
1 parent
66e2e7a5c0
commit
148f7dc248
8 files changed
+180
-51
No files matched your search
@@ -18,6 +18,9 @@
|
||||
<li class="nav-item">
|
||||
<a class="nav-link <%= 'active' if request.path == '/epson' %>" href="/epson">Receipts</a>
|
||||
</li>
|
||||
<li class="nav-item">
|
||||
<a class="nav-link <%= 'active' if request.path.start_with?('/labels') %>" href="/labels">Labels</a>
|
||||
</li>
|
||||
</ul>
|
||||
<% if request.path.start_with?('/brother') %>
|
||||
<span class="navbar-text me-2">Printer:</span>
|
||||
|
||||
+15
-21
@@ -17,8 +17,20 @@
|
||||
|
||||
<hr class="mt-4">
|
||||
|
||||
<h5>Free text (already-formatted ESC/POS)</h5>
|
||||
<p>Sent as-is (just reset + code page prefix and a trailing cut), no title/body template applied.</p>
|
||||
<h5>Free text (ESC/POS mnemonic notation)</h5>
|
||||
<p>
|
||||
One instruction per line: <code>ESC</code>/<code>GS</code>/<code>FS</code>/<code>LF</code>/<code>CR</code>/<code>HT</code>/<code>NUL</code> as
|
||||
command names, <code>0xNN</code> as a raw byte, anything else as literal text. Trailing <code># comment</code> is ignored. Example:
|
||||
</p>
|
||||
<pre class="bg-light p-2"><code>ESC a 0x01 # Align: Center
|
||||
Hello # literal text
|
||||
LF
|
||||
ESC E 0x01 # Bold on
|
||||
World
|
||||
LF
|
||||
ESC E 0x00 # Bold off
|
||||
GS k 0x03 12345678 0x00 # EAN8 barcode
|
||||
GS V 0x00 # Full cut</code></pre>
|
||||
<form action="/epson/raw" method="POST">
|
||||
<div class="mb-3">
|
||||
<textarea name="content" class="form-control" rows="8" style="font-family: monospace;"></textarea>
|
||||
@@ -34,22 +46,4 @@
|
||||
</div>
|
||||
</form>
|
||||
|
||||
<% if @labels && !@labels.empty? %>
|
||||
<hr class="mt-4">
|
||||
<h5>Saved receipts</h5>
|
||||
<div class="list-group">
|
||||
<% @labels.each do |label| %>
|
||||
<div class="list-group-item d-flex justify-content-between align-items-center">
|
||||
<%= label['name'] %>
|
||||
<div class="d-flex gap-2">
|
||||
<form action="/labels/<%= label['id'] %>/print" method="POST">
|
||||
<button class="btn btn-sm btn-secondary" type="submit">Print</button>
|
||||
</form>
|
||||
<form action="/labels/<%= label['id'] %>/delete" method="POST">
|
||||
<button class="btn btn-sm btn-outline-danger" type="submit">Delete</button>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
<% end %>
|
||||
</div>
|
||||
<% end %>
|
||||
<p class="mt-4"><a href="/labels">See saved receipts →</a></p>
|
||||
@@ -0,0 +1,20 @@
|
||||
<h4>Edit label</h4>
|
||||
|
||||
<% if @label['type'] == 'zpl' %>
|
||||
<span class="badge bg-primary">ZPL · Datamax</span>
|
||||
<% else %>
|
||||
<span class="badge bg-info text-dark">ESC/POS · Epson</span>
|
||||
<% end %>
|
||||
|
||||
<form action="/labels/<%= @label['id'] %>" method="POST" class="mt-3">
|
||||
<div class="mb-3">
|
||||
<label for="name" class="form-label">Name</label>
|
||||
<input name="name" class="form-control" type="text" id="name" value="<%= @label['name'] %>" />
|
||||
</div>
|
||||
<div class="mb-3">
|
||||
<label for="content" class="form-label">Content</label>
|
||||
<textarea name="content" class="form-control" id="content" rows="12" style="font-family: monospace;"><%= @label['content'] %></textarea>
|
||||
</div>
|
||||
<button class="btn btn-secondary" type="submit">Save</button>
|
||||
<a href="/labels" class="btn btn-outline-secondary">Cancel</a>
|
||||
</form>
|
||||
@@ -0,0 +1,39 @@
|
||||
<h4>Saved labels & receipts</h4>
|
||||
|
||||
<% if @labels.empty? %>
|
||||
<p>Nothing saved yet -- use "Save as" on <a href="/upload">Shipping labels</a> or <a href="/epson">Receipts</a>.</p>
|
||||
<% else %>
|
||||
<div class="list-group">
|
||||
<% @labels.each do |label| %>
|
||||
<div class="list-group-item">
|
||||
<div class="d-flex justify-content-between align-items-start">
|
||||
<div>
|
||||
<% if label['type'] == 'zpl' %>
|
||||
<span class="badge bg-primary">ZPL · Datamax</span>
|
||||
<% else %>
|
||||
<span class="badge bg-info text-dark">ESC/POS · Epson</span>
|
||||
<% end %>
|
||||
<strong class="ms-2"><%= label['name'] %></strong>
|
||||
</div>
|
||||
<div class="d-flex gap-2">
|
||||
<form action="/labels/<%= label['id'] %>/print" method="POST">
|
||||
<button class="btn btn-sm btn-secondary" type="submit">Print</button>
|
||||
</form>
|
||||
<a href="/labels/<%= label['id'] %>/edit" class="btn btn-sm btn-outline-secondary">Edit</a>
|
||||
<form action="/labels/<%= label['id'] %>/delete" method="POST">
|
||||
<button class="btn btn-sm btn-outline-danger" type="submit">Delete</button>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="mt-2">
|
||||
<% if label['type'] == 'zpl' %>
|
||||
<img src="/labels/<%= label['id'] %>/preview.png" alt="preview" style="max-height: 150px;" onerror="this.remove()" />
|
||||
<% else %>
|
||||
<pre class="bg-light p-2 mb-0" style="max-height: 150px; overflow: auto;"><%= label['content'] %></pre>
|
||||
<% end %>
|
||||
</div>
|
||||
</div>
|
||||
<% end %>
|
||||
</div>
|
||||
<% end %>
|
||||
+1
-19
@@ -32,22 +32,4 @@
|
||||
</div>
|
||||
</form>
|
||||
|
||||
<% if @labels && !@labels.empty? %>
|
||||
<hr class="mt-4">
|
||||
<h5>Saved labels</h5>
|
||||
<div class="list-group">
|
||||
<% @labels.each do |label| %>
|
||||
<div class="list-group-item d-flex justify-content-between align-items-center">
|
||||
<%= label['name'] %>
|
||||
<div class="d-flex gap-2">
|
||||
<form action="/labels/<%= label['id'] %>/print" method="POST">
|
||||
<button class="btn btn-sm btn-secondary" type="submit">Print</button>
|
||||
</form>
|
||||
<form action="/labels/<%= label['id'] %>/delete" method="POST">
|
||||
<button class="btn btn-sm btn-outline-danger" type="submit">Delete</button>
|
||||
</form>
|
||||
</div>
|
||||
</div>
|
||||
<% end %>
|
||||
</div>
|
||||
<% end %>
|
||||
<p class="mt-4"><a href="/labels">See saved labels →</a></p>
|
||||
Reference in new issue
Block a user