Label Printing
Sources: samples/labels/source/LABEL.PRG, LITEM.PRG, PDLABEL.PRG — by Manuel Calero Solis (1995)
FWH includes a complete label printing system in samples/labels/ with 17 sample programs and full source code. It prints labels in a grid layout (e.g. 2 across, 7 down) with automatic page breaks, positioning, and bitmap support. Labels can output to printer, preview window, or text file.
Architecture
graph LR
A["LABEL Command"] --> B["TLabel Engine"]
B --> C["TPrinter"]
B --> D["TRFile (text)"]
B --> E["Preview Dialog"]
F["TLItem"] --> B
G["LBLITEM Command"] --> F
Commands (include/label.ch)
LABEL
LABEL oLabel ;
SIZE nWidth, nHeight ; // mm
SEPARATORS nH, nV ; // horizontal, vertical gap in mm
ON LINE nCount ; // labels per row
FONT aFonts PEN aPens ; // optional font/pen arrays
TO PRINTER | PREVIEW | FILE cFile | DEVICE oDevice ;
CAPTION cTitle
LBLITEM
LBLITEM DATA bData1, bData2, ... ;
AT nCol ; // column offset
SIZE nChars ; // width in characters
PICTURE cPict1, cPict2, ... ;
FONT uFont ; // font index or name
LEFT | CENTER | RIGHT ;
SHADOW ; // gray background
GRID nPen // bottom grid line
ACTIVATE LABEL
ACTIVATE LABEL oLabel ;
FOR bFor WHILE bWhile ;
ON INIT bInit ;
ON STARTPAGE bStartPage ON ENDPAGE bEndPage ;
ON STARTLINE bStartLine ON ENDLINE bEndLine ;
ON STARTLABEL bStartLabel ON ENDLABEL bEndLabel ;
ON CHANGE bChange
TLabel Class
Core label engine. Manages label grid layout, page breaks, fonts, and output device.
| DATA | Description |
|---|---|
oDevice | Output device (TPrinter, TRFile, or screen) |
nLblWidth / nLblHeight | Label dimensions in pixels |
nHSeparator / nVSeparator | Horizontal/vertical gap between labels |
nLblOnLine | Labels per row across the page |
aoItems | Array of TLItem objects (label fields) |
aFont / aPen | Font and pen arrays (scaled to device) |
nLeftMargin / nRightMargin / nTopMargin / nDnMargin | Page margins in pixels |
| Method | Description |
|---|---|
New(nW,nH,hSep,vSep,nPerLine,aFont,aPen,...) | Constructor, creates device, scales units |
AddItem(oItem) | Append a TLItem to the label |
Activate(bFor,bWhile,bInit,...) | Set hooks and start the print loop |
Say(nRow,nCol,xText,nFont,nPad) | Print text with left/center/right alignment |
SayBitmap(nRow,nCol,cBmp,nW,nH) | Render bitmap at position |
Box(nRow,nCol,nBottom,nRight,nPen) | Draw rectangle |
Line(nTop,nLeft,nBottom,nRight,nPen) | Draw line |
Shadow(nH,nItem,nLine) | Gray background fill behind a label |
Grid(nH,nItem,nLine) | Horizontal grid line across label |
Margin(nVal,nType) | Set individual margins |
TLItem Class
Represents one data field within a label. Created by the LBLITEM command.
| DATA | Description |
|---|---|
aData | Array of code blocks returning values to print |
aPicture | PICTURE clauses per data block |
bDataFont | Code block returning font index |
nWidth / nDataHeight | Field dimensions in pixels |
nCol | Optional column offset from left edge |
nPad | Alignment: RPT_LEFT(1), RPT_RIGHT(2), RPT_CENTER(3) |
lShadow / lGrid | Enable shadow background / bottom grid line |
Example: Simple Address Label
#include "FiveWin.ch"
#include "label.ch"
FUNCTION Label01()
local oLabel
USE TEST NEW SHARED ALIAS "TEST"
// 89x23mm labels, 2 per row, preview
LABEL oLabel SIZE 89, 23 ;
SEPARATORS 5, 2 ;
ON LINE 2 ;
PREVIEW ;
CAPTION "Address Labels"
LBLITEM DATA "N.: " + Str( TEST->( RECNO() ), 0 )
LBLITEM DATA TEST->FIRST
LBLITEM DATA TEST->LAST
LBLITEM DATA TEST->STREET
END LABEL oLabel
ACTIVATE LABEL oLabel
CLOSE TEST
RETURN NIL
Labels with QR Codes
Combine label printing with QR codes using FW_BarCodeBmp() + SayBitmap():
REQUEST FWZEBRA
LABEL oLabel SIZE 100, 60 ;
SEPARATORS 3, 3 ;
ON LINE 2 ;
PREVIEW
LBLITEM DATA CUSTOMER->FIRST
LBLITEM DATA CUSTOMER->LAST
LBLITEM DATA CUSTOMER->CITY
ACTIVATE LABEL oLabel ;
ON STARTLABEL { || ;
oLabel:SayBitmap( 1, 3.5, ;
FW_BarCodeBmp( ;
"https://example.com/" + CUSTOMER->ID, ;
"QR", 150, 150 ), ;
0.5, 0.5 ) }
END LABEL oLabel
Sample Programs
The samples/labels/ directory contains 17 ready-to-run examples:
LABEL01.PRGthroughLABEL17.PRG— progressive examples covering address labels, product labels, barcodes, multi-page, file output, and previewDEMO.PRG— combined demonstrationsource/LABEL.PRG— TLabel engine classsource/LITEM.PRG— TLItem data field classsource/PDLABEL.PRG— command helper functionsinclude/LABEL.CH— #xcommand definitionsilabel/— Italian label subsystem (ILABELS.PRG, MLABEL.PRG)
Tips
- Labels are measured in millimeters by default. Use
TO PRINTERfor direct printing orPREVIEWfor on-screen preview. - The
ON STARTLABELandON ENDLABELhooks are the best place to add custom drawings (images, barcodes, QR codes). - For QR codes on labels, generate a bitmap with
FW_BarCodeBmp()and render it viaoLabel:SayBitmap()inside a STARTLABEL hook. - For standalone label printing without the TLabel system, use
TPrinterdirectly: set paper size, loop records, callSay()for each field, and manage positions manually.