begin rewriting libsharperang into libpaperang
This commit is contained in:
parent
09d9ccb628
commit
46012df5d5
|
@ -0,0 +1,52 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
|
||||
namespace libpaperang.Helpers {
|
||||
public class CRC {
|
||||
public uint iv { get => ~iv; private set => iv=~value; }
|
||||
public uint mv = 0x35769521;
|
||||
private uint poly = 0xedb88320;
|
||||
private uint[] crctable;
|
||||
public bool IsInitialised=false;
|
||||
public CRC() { this.iv=0; }
|
||||
public CRC(uint iv) => this.iv=iv;
|
||||
public void Initialise() {
|
||||
crctable=Enumerable.Range(0, 256).Select(i => {
|
||||
uint e=(uint)i;
|
||||
for (ushort eb = 0; eb<8; eb++)
|
||||
e=((e&1)!=0)
|
||||
? (poly^(e>>1))
|
||||
: (e>>1);
|
||||
return e;
|
||||
}).ToArray();
|
||||
IsInitialised=true;
|
||||
}
|
||||
public uint Reflect(uint iv) {
|
||||
uint ivr=0;
|
||||
for (int i = 0; i<32; i++) {
|
||||
uint b=(iv>>i)&1;
|
||||
ivr|=(b<<(31-i));
|
||||
}
|
||||
return ~ivr;
|
||||
}
|
||||
public uint GetChecksumUint<T>(IEnumerable<T> data) {
|
||||
if (!IsInitialised) throw new InvalidOperationException("CRC object has not been Initialise()'d first. Please do that.");
|
||||
try {
|
||||
return ~data.Aggregate(iv,
|
||||
(cti, cb) => crctable[(cti&0xFF)^Convert.ToByte(cb)]^(cti>>8));
|
||||
} catch (FormatException e) {
|
||||
throw new FormatException("Could not read input as a byte stream", e);
|
||||
} catch (InvalidCastException e) {
|
||||
throw new InvalidCastException("Could not read input as a byte stream", e);
|
||||
} catch (OverflowException e) {
|
||||
throw new OverflowException("Could not read input as a byte stream", e);
|
||||
}
|
||||
}
|
||||
public byte[] GetChecksumBytes<T>(IEnumerable<T> data) => BitConverter.GetBytes(GetChecksumUint(data));
|
||||
public uint GetCrcIv() => iv == mv
|
||||
? iv
|
||||
: iv ^ mv;
|
||||
public byte[] GetCrcIvBytes() => BitConverter.GetBytes(GetCrcIv());
|
||||
}
|
||||
}
|
|
@ -0,0 +1,5 @@
|
|||
|
||||
namespace libpaperang.Helpers {
|
||||
class Media {
|
||||
}
|
||||
}
|
|
@ -0,0 +1,12 @@
|
|||
|
||||
namespace libpaperang.Helpers {
|
||||
class Transforms {
|
||||
public BaseTypes.Packet Frame;
|
||||
public BaseTypes.Opcodes Op;
|
||||
public Transforms(BaseTypes.Packet FrameConstruction, BaseTypes.Opcodes Operations) {
|
||||
Frame=FrameConstruction;
|
||||
Op=Operations;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
|
@ -0,0 +1,60 @@
|
|||
|
||||
|
||||
namespace libpaperang {
|
||||
public abstract class BaseTypes {
|
||||
public enum Connection {
|
||||
None,
|
||||
UART,
|
||||
USB,
|
||||
Bluetooth
|
||||
}
|
||||
public struct Packet {
|
||||
byte Start;
|
||||
byte End;
|
||||
}
|
||||
public enum Model {
|
||||
P1,
|
||||
T1,
|
||||
P2,
|
||||
P2S
|
||||
}
|
||||
public enum State {
|
||||
Offline,
|
||||
Available,
|
||||
Ready,
|
||||
NotReady,
|
||||
Printing,
|
||||
}
|
||||
public enum Fault {
|
||||
PaperEmpty,
|
||||
DoorOpen
|
||||
}
|
||||
public enum Operations {
|
||||
NoOp,
|
||||
LineFeed,
|
||||
CrcTransmit,
|
||||
Print
|
||||
}
|
||||
public struct Opcodes {
|
||||
byte[] NoOp;
|
||||
byte[] LineFeed;
|
||||
byte[] Print;
|
||||
byte[] TransmitCrc;
|
||||
}
|
||||
}
|
||||
interface IPrinter {
|
||||
short LineWidth { get; }
|
||||
BaseTypes.Connection ConnectionMethod { get; }
|
||||
BaseTypes.Model PrinterVariant { get; }
|
||||
BaseTypes.State Status { get; }
|
||||
bool IsPrinterAvailable();
|
||||
bool IsPrinterInitialised();
|
||||
bool Initialise();
|
||||
bool OpenPrinter();
|
||||
bool ClosePrinter();
|
||||
bool Deinitialise();
|
||||
bool WriteBytes(byte[] packet);
|
||||
bool WriteBytes(byte[] packet, int delay);
|
||||
bool[] ReadBytes();
|
||||
}
|
||||
}
|
|
@ -0,0 +1,23 @@
|
|||
using System;
|
||||
|
||||
namespace libpaperang {
|
||||
public class USB : IPrinter {
|
||||
public short LineWidth => throw new NotImplementedException();
|
||||
|
||||
public BaseTypes.Connection ConnectionMethod => throw new NotImplementedException();
|
||||
|
||||
public BaseTypes.Model PrinterVariant => throw new NotImplementedException();
|
||||
|
||||
public BaseTypes.State Status => throw new NotImplementedException();
|
||||
|
||||
public bool ClosePrinter() => throw new NotImplementedException();
|
||||
public bool Deinitialise() => throw new NotImplementedException();
|
||||
public bool Initialise() => throw new NotImplementedException();
|
||||
public bool IsPrinterAvailable() => throw new NotImplementedException();
|
||||
public bool IsPrinterInitialised() => throw new NotImplementedException();
|
||||
public bool OpenPrinter() => throw new NotImplementedException();
|
||||
public bool[] ReadBytes() => throw new NotImplementedException();
|
||||
public bool WriteBytes(byte[] packet) => throw new NotImplementedException();
|
||||
public bool WriteBytes(byte[] packet, int delay) => throw new NotImplementedException();
|
||||
}
|
||||
}
|
|
@ -0,0 +1,11 @@
|
|||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>netstandard2.0</TargetFramework>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="LibUsbDotNet" Version="2.2.29" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
|
@ -8,7 +8,6 @@ namespace libsharperang {
|
|||
Bluetooth
|
||||
}
|
||||
internal DataTransforms transform=new DataTransforms();
|
||||
//public Printer printer;
|
||||
public string Model { get; internal set; }
|
||||
public string FirmwareVer { get; internal set; }
|
||||
public int Battery { get; internal set; }
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading;
|
||||
using LibUsbDotNet;
|
||||
using LibUsbDotNet.Main;
|
||||
|
||||
|
@ -31,7 +32,7 @@ namespace libsharperang {
|
|||
private byte[] ResolveOpcode(Opcode opcode) {
|
||||
switch (opcode) {
|
||||
case Opcode.SessionBegin: return new byte[] { 0x06, 0x00, 0x02, 0x00 };
|
||||
case Opcode.Feed: return new byte[] { 0x1a, 0x00, 0x02, 0x00 };
|
||||
case Opcode.Feed: return new byte[] { 0x1a, 0x00, 0x02, 0x00 };
|
||||
case Opcode.CrcTransmit: return new byte[] { 0x18, 0x01, 0x04, 0x00 };
|
||||
default: throw new NullReferenceException();
|
||||
}
|
||||
|
@ -73,7 +74,7 @@ namespace libsharperang {
|
|||
|
||||
public USBPrinter() {
|
||||
ActiveConnectionType=ConnectionType.USB;
|
||||
ImageWidth=48;
|
||||
ImageWidth=72;
|
||||
}
|
||||
~USBPrinter() {
|
||||
Close();
|
||||
|
@ -156,15 +157,16 @@ namespace libsharperang {
|
|||
}
|
||||
public void PollPrinter() {
|
||||
StartSession();
|
||||
NoOp();
|
||||
NoOp();
|
||||
}
|
||||
public void Feed() => Feed(100);
|
||||
//Feed 0 is equivalent to a no-op, though on the P2 model it appears to engage the roller even though it doesn't ultimately result in any rotation
|
||||
public void NoOp() => Feed(0);
|
||||
public void Feed(int milliseconds) => WriteBytes(builder.Build(Frame.Opcode.Feed, BitConverter.GetBytes(transform.SwapEndianness(
|
||||
0x00000000 | (((((
|
||||
(uint)milliseconds & 0xFFU) << 16) |
|
||||
(uint)milliseconds) & 0xFFFF00U) >> 8))).Skip(2).ToArray()));
|
||||
public void Feed() => Feed(100);
|
||||
//Feed 0 is equivalent to a no-op, though on the P2 model it appears to engage the roller even though it doesn't ultimately result in any rotation
|
||||
public void NoOp() => Feed(0);
|
||||
public void Feed(int milliseconds) => WriteBytes(
|
||||
builder.Build(Frame.Opcode.Feed, BitConverter.GetBytes(
|
||||
transform.SwapEndianness(0x00000000 | (((((
|
||||
(uint)milliseconds & 0xFFU) << 16) |
|
||||
(uint)milliseconds) & 0xFFFF00U) >> 8))).Skip(2).ToArray()));
|
||||
public void PrintBytes(byte[] data, bool autofeed=true) {
|
||||
List<byte[]> datas = data
|
||||
.Select((b, i) => new {Index = i, Value = b })
|
||||
|
@ -172,7 +174,7 @@ namespace libsharperang {
|
|||
.Select(b => b.Select(bb => bb.Value).ToArray())
|
||||
.ToList();
|
||||
datas.ForEach(b => WriteBytes(builder.Build(transform.GeneratePrintOpcode(b), b)));
|
||||
if (autofeed) Feed(60);
|
||||
if (autofeed) Feed(200);
|
||||
}
|
||||
public bool IsPrinterPresent() => (Devices != null && Devices.Count > 0);
|
||||
bool IPrinter.Initialised() => Initialised();
|
||||
|
@ -186,8 +188,13 @@ namespace libsharperang {
|
|||
return bRead;
|
||||
}
|
||||
public bool WriteBytes(byte[] Frame) {
|
||||
return WriteBytes(Frame, ImageWidth*3);
|
||||
}
|
||||
public bool WriteBytes(byte[] Frame, int milliseconds) {
|
||||
if (_uWr==null) _uWr=_uDv?.OpenEndpointWriter(WriteEndpointID.Ep02);
|
||||
return (_uWr.Write(Frame, 1000, out int _) == ErrorCode.None);
|
||||
bool result = _uWr.Write(Frame, 500, out int _) == ErrorCode.None;
|
||||
Thread.Sleep(milliseconds);
|
||||
return result;
|
||||
}
|
||||
}
|
||||
}
|
|
@ -5,7 +5,9 @@ VisualStudioVersion = 16.0.29215.179
|
|||
MinimumVisualStudioVersion = 10.0.40219.1
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "sharperang", "sharperang\sharperang.csproj", "{677A8867-809E-4476-A9AE-7BEB5CE02F96}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "libsharperang", "libsharperang\libsharperang.csproj", "{93203F87-29D0-4CDE-B2EE-156488E30186}"
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "libsharperang", "libsharperang\libsharperang.csproj", "{93203F87-29D0-4CDE-B2EE-156488E30186}"
|
||||
EndProject
|
||||
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "libpaperang", "libpaperang\libpaperang.csproj", "{A429CCEB-9331-4CD9-B3C0-A8F736732DEA}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
|
@ -21,6 +23,10 @@ Global
|
|||
{93203F87-29D0-4CDE-B2EE-156488E30186}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{93203F87-29D0-4CDE-B2EE-156488E30186}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{93203F87-29D0-4CDE-B2EE-156488E30186}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{A429CCEB-9331-4CD9-B3C0-A8F736732DEA}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{A429CCEB-9331-4CD9-B3C0-A8F736732DEA}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{A429CCEB-9331-4CD9-B3C0-A8F736732DEA}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{A429CCEB-9331-4CD9-B3C0-A8F736732DEA}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
|
|
|
@ -8,9 +8,6 @@ using System.Drawing.Imaging;
|
|||
using System.IO;
|
||||
|
||||
namespace sharperang {
|
||||
/// <summary>
|
||||
/// Interaction logic for MainWindow.xaml
|
||||
/// </summary>
|
||||
public partial class MainWindow : Window {
|
||||
private LogBridge logger;
|
||||
private USBPrinter printer=new USBPrinter();
|
||||
|
@ -26,7 +23,7 @@ namespace sharperang {
|
|||
logger.ClearBuffer();
|
||||
private void BtInitUSB_Click(object sender, RoutedEventArgs e) {
|
||||
logger.Info("USB Initialising");
|
||||
printer.Initialise();
|
||||
printer.Initialise();
|
||||
//printer = new LibSharperang(logger);
|
||||
logger.Debug("IsPrinterPresent => "+printer.IsPrinterPresent());
|
||||
logger.Debug("FoundPrinterGuids => "+printer.FoundPrinterGuids());
|
||||
|
@ -37,30 +34,30 @@ namespace sharperang {
|
|||
printer.InitPrinter();
|
||||
logger.Debug("Printer initialised and ready");
|
||||
}
|
||||
private void BtTestLine_Click(object sender, RoutedEventArgs e) => printer.Feed(200);
|
||||
private void BtTestLine_Click(object sender, RoutedEventArgs e) => printer.Feed(200);
|
||||
private void BtLoadImage_Click(object sender, RoutedEventArgs e) {
|
||||
logger.Debug("Loading image for print");
|
||||
logger.Debug("Loading image for print");
|
||||
OpenFileDialog r = new OpenFileDialog {
|
||||
Title="Select 1 (one) image file",
|
||||
Multiselect=false,
|
||||
Filter="PNG files (*.png)|*.png|JPEG files (*.jpe?g)|*.jpg *.jpeg|Jraphics Interchange Format files (*.gif)|*.gif|Bitte-Mappe files (*.bmp)|*.bmp|All of the above|*.jpg *.jpeg *.png *.gif *.bmp",
|
||||
AutoUpgradeEnabled=true
|
||||
};
|
||||
if (r.ShowDialog() == System.Windows.Forms.DialogResult.Cancel) {
|
||||
logger.Debug("Image load cancelled");
|
||||
return;
|
||||
}
|
||||
if (r.ShowDialog() == System.Windows.Forms.DialogResult.Cancel) {
|
||||
logger.Debug("Image load cancelled");
|
||||
return;
|
||||
}
|
||||
Image _=Image.FromFile(r.FileName);
|
||||
logger.Debug("Loaded image " + r.FileName);
|
||||
r.Dispose();
|
||||
logger.Debug("Disposed of dialog");
|
||||
logger.Debug("Loaded image " + r.FileName);
|
||||
r.Dispose();
|
||||
logger.Debug("Disposed of dialog");
|
||||
bimg=new Bitmap(_,
|
||||
(printer.ImageWidth*8), (int)((double)(printer.ImageWidth*8)*(double)((double)_.Height/(double)_.Width)));
|
||||
logger.Debug("Loaded image as Bitmap");
|
||||
_.Dispose();
|
||||
logger.Debug("Disposed of Image");
|
||||
logger.Debug("Loaded image as Bitmap");
|
||||
_.Dispose();
|
||||
logger.Debug("Disposed of Image");
|
||||
bimg=CopyToBpp(bimg);
|
||||
logger.Debug("Converted Bitmap to Bitmap with 1-bit colour depth");
|
||||
logger.Debug("Converted Bitmap to Bitmap with 1-bit colour depth");
|
||||
//BitArray img = new BitArray(bimg.Height*96*8);
|
||||
byte[] iimg = new byte[bimg.Height*printer.ImageWidth];
|
||||
byte[] img;
|
||||
|
@ -68,20 +65,20 @@ namespace sharperang {
|
|||
bimg.Save(s, ImageFormat.Bmp);
|
||||
img=s.ToArray();
|
||||
}
|
||||
logger.Debug("Got bitmap's bytes");
|
||||
int startoffset=img.Length-((bimg.Width/8)+(bimg.Height*printer.ImageWidth));
|
||||
logger.Debug("Processing bytes with offset " + startoffset);
|
||||
logger.Debug("Got bitmap's bytes");
|
||||
int startoffset=img.Length-(bimg.Height*printer.ImageWidth);
|
||||
logger.Debug("Processing bytes with offset " + startoffset);
|
||||
for(int h=0;h<bimg.Height;h++) {
|
||||
for (int w=0;w<printer.ImageWidth;w++) {
|
||||
iimg[(printer.ImageWidth*(bimg.Height-1-h))+(printer.ImageWidth-1-w)]=(byte)~
|
||||
(img[startoffset+(printer.ImageWidth*h)+(printer.ImageWidth-1-w)]);
|
||||
}
|
||||
}
|
||||
logger.Debug("Have print data of length " + iimg.Length);
|
||||
bimg.Dispose();
|
||||
logger.Debug("Disposed of Bitmap");
|
||||
}
|
||||
logger.Debug("Have print data of length " + iimg.Length);
|
||||
bimg.Dispose();
|
||||
logger.Debug("Disposed of Bitmap");
|
||||
printer.PrintBytes(iimg, false);
|
||||
logger.Debug("Feeding for 200ms");
|
||||
logger.Debug("Feeding for 200ms");
|
||||
printer.Feed(200);
|
||||
}
|
||||
static uint BitSwap1(uint x) => ((x & 0x55555555u) << 1) | ((x & (~0x55555555u)) >> 1);
|
||||
|
|
|
@ -50,12 +50,6 @@
|
|||
<WarningLevel>4</WarningLevel>
|
||||
</PropertyGroup>
|
||||
<ItemGroup>
|
||||
<Reference Include="LibUsbDotNet.LibUsbDotNet, Version=2.2.0.0, Culture=neutral, PublicKeyToken=c677239abe1e02a9, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\LibUsbDotNet.2.2.29\lib\net45\LibUsbDotNet.LibUsbDotNet.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="Microsoft.Win32.Registry, Version=4.1.1.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\Microsoft.Win32.Registry.4.5.0\lib\net461\Microsoft.Win32.Registry.dll</HintPath>
|
||||
</Reference>
|
||||
<Reference Include="System" />
|
||||
<Reference Include="System.Collections.Specialized, Version=4.0.2.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
|
||||
<HintPath>..\packages\System.Collections.Specialized.4.3.0\lib\net46\System.Collections.Specialized.dll</HintPath>
|
||||
|
@ -198,6 +192,7 @@
|
|||
<ProjectReference Include="..\libsharperang\libsharperang.csproj">
|
||||
<Project>{93203f87-29d0-4cde-b2ee-156488e30186}</Project>
|
||||
<Name>libsharperang</Name>
|
||||
<EmbedInteropTypes>False</EmbedInteropTypes>
|
||||
</ProjectReference>
|
||||
</ItemGroup>
|
||||
<ItemGroup>
|
||||
|
|
Loading…
Reference in New Issue