tbf/Results/Output/Printers/MultiLabel/MultiLabelPrintDocument.cs

176 lines
6.7 KiB
C#

///
/// Copyright (c) 2020 Sensus Slovensko a.s.
///
using System;
using System.Collections.Generic;
using System.Drawing;
using System.Drawing.Drawing2D;
using System.Drawing.Printing;
using System.IO;
using Gma.QrCodeNet.Encoding;
using Common;
using Results.Resources;
using GenCode128;
namespace Results.Output.Printers.MultiLabel
{
public class MultiLabelPrintDocument : PrintersCommon
{
static QrEncoder encoder = new QrEncoder();
/// Size of the printed area without margins, after taking into account 'pageOrientation'
readonly int labelHeight;
readonly int labelWidth;
/// Selected font
readonly Font font;
/// Data to print
Results.Entities.Batch batch;
MultiLabelPrinterCfg cfg;
IList<Results.Entities.WaterMeter> waterMeters;
/// Items to print
IList<WMeterRsltItemSpec> itemsToPrint;
/// <summary>
/// Constructor
/// </summary>
/// <param name="textToPrint">Text to be printed</param>
public MultiLabelPrintDocument(Results.Entities.Batch batch, MultiLabelPrinterCfg cfg, string documentName)
{
DocumentName = documentName;
this.batch = batch;
this.waterMeters = batch.WaterMeters;
this.cfg = cfg;
this.itemsToPrint = Results.WMeterRsltItemSpec.FromStrArray(cfg.ItemsToPrint);
/// Initialize fonts
font = new Font((cfg.FontFamily != null ? cfg.FontFamily : "Arial"),
(cfg.FontSize > 0 ? cfg.FontSize : 10),
(FontStyle)cfg.FontStyle);
/// Set print area size and margins (in dots using 100 dpi)
DefaultPageSettings.Landscape = (cfg.PageOrientation == PageOrientation.Landscape);
///
labelHeight = cfg.LabelHeight;
labelWidth = cfg.LabelWidth;
}
/// <summary>
/// Override the default onbeginPrint method of the PrintDocument Object
/// </summary>
/// <param name=e></param>
/// <remarks></remarks>
protected override void OnBeginPrint(System.Drawing.Printing.PrintEventArgs e)
{
base.OnBeginPrint(e);
}
/// <summary>
/// Override the default OnPrintPage method of the PrintDocument.
/// </summary>
/// <param name=e></param>
/// <remarks>This provides the print logic for our document</remarks>
protected override void OnPrintPage(System.Drawing.Printing.PrintPageEventArgs e)
{
/// Run base code
base.OnPrintPage(e);
int labelColumn = 0;
int labelLeft = cfg.LeftTopLabelLeft;
int labelTop = cfg.LeftTopLabelTop;
foreach (var wm in waterMeters)
{
if (!wm.Disabled && (!cfg.GoodOnly || wm.Passed))
{
if (!string.IsNullOrEmpty(cfg.Template))
{
string templatePath = Path.Combine("C:\\TBF\\Templates\\", cfg.Template);
if (File.Exists(templatePath))
{
e.Graphics.DrawImage(new Bitmap(Image.FromFile(templatePath), labelWidth, labelHeight), new Rectangle(labelLeft, labelTop, labelWidth, labelHeight));
}
}
foreach (var item in itemsToPrint)
{
string[] coords = item.Caption.Split(new char[] { ';' });
int x, y;
if (coords.Length >= 2 && int.TryParse(coords[0].Trim(new char[] { ' ' }), out x)
&& int.TryParse(coords[1].Trim(new char[] { ' ' }), out y))
{
RectangleF printArea = new RectangleF(labelLeft + x, labelTop + y, labelWidth - x, labelHeight - y);
e.Graphics.DrawString(item.Print(wm), this.font, Brushes.Black, printArea);
}
}
if (cfg.BarcodeType != BarcodeType.None && cfg.BarcodeType < BarcodeType.Count)
{
try
{
if (cfg.BarcodeType == BarcodeType.QR_Code)
{
QrCode qrCode = encoder.Encode(wm.SerialNr);
DrawQR(e.Graphics, qrCode, labelLeft + cfg.BarcodeLeft, labelTop + cfg.BarcodeTop, cfg.BarcodeWidth, cfg.BarcodeHeight);
}
else if (cfg.BarcodeType == BarcodeType.Code_128_Horizontally || cfg.BarcodeType == BarcodeType.Code_128_Vertically)
{
Image img = Code128Rendering.MakeBarcodeImage(wm.SerialNr, 1, true);
if (cfg.BarcodeType == BarcodeType.Code_128_Vertically)
{
img.RotateFlip(RotateFlipType.Rotate90FlipNone);
}
e.Graphics.DrawImage(img, labelLeft + cfg.BarcodeLeft, labelTop + cfg.BarcodeTop, cfg.BarcodeWidth, cfg.BarcodeHeight);
}
}
catch (Exception)
{
}
}
///
/// Move (labelLeft, labelTop) coordinates to the next label
///
if (++labelColumn == cfg.LabelColumnsCount)
{
labelColumn = 0;
labelLeft = cfg.LeftTopLabelLeft;
labelTop += cfg.LabelHeight;
}
else
{
labelLeft += cfg.LabelWidth;
}
}
}
}
public static void DrawQR(Graphics g, QrCode qrCode, float left, float top, float width, float height)
{
/// Assuming 100 dpi (printer)
g.SmoothingMode = SmoothingMode.AntiAlias;
g.InterpolationMode = InterpolationMode.HighQualityBicubic;
g.PixelOffsetMode = PixelOffsetMode.HighQuality;
float qrPixWidth = width / qrCode.Matrix.Width;
float qrPixHeight = height / qrCode.Matrix.Height;
for (int i = 0; i < qrCode.Matrix.Height; i++)
{
for (int j = 0; j < qrCode.Matrix.Width; j++)
{
if (qrCode.Matrix[j, i])
{
g.FillRectangle(Brushes.Black, new RectangleF(left + j * qrPixWidth,
top + i * qrPixHeight,
qrPixWidth,
qrPixHeight));
}
}
}
}
}
}