qr.code.fmx.pas 7.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274
  1. //Copyright (c) 2019 by Jason Southwell
  2. //
  3. //Permission is hereby granted, free of charge, to any person obtaining a copy
  4. //of this software and associated documentation files (the "Software"), to deal
  5. //in the Software without restriction, including without limitation the rights
  6. //to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  7. //copies of the Software, and to permit persons to whom the Software is
  8. //furnished to do so, subject to the following conditions:
  9. //
  10. //The above copyright notice and this permission notice shall be included in all
  11. //copies or substantial portions of the Software.
  12. //
  13. //THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  14. //IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  15. //FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  16. //AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  17. //LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  18. //OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
  19. //SOFTWARE.
  20. unit qr.code.fmx;
  21. interface
  22. uses
  23. System.SysUtils, System.Classes, FMX.Graphics, qr.code;
  24. type
  25. TQRBitmap = class(TBitmap)
  26. private
  27. FQR : TQRCode;
  28. FShowBorder: boolean;
  29. FShowModuleGrid: boolean;
  30. function GetData: TArray<Byte>;
  31. function GetECL: TErrorCorrectionLevel;
  32. function GetMask: TMask;
  33. function GetText: string;
  34. function GetVersion: TVersion;
  35. procedure SetData(const Value: TArray<Byte>);
  36. procedure SetECL(const Value: TErrorCorrectionLevel);
  37. procedure SetMask(const Value: TMask);
  38. procedure SetText(const Value: string);
  39. procedure SetVersion(const Value: TVersion);
  40. procedure SetShowBorder(const Value: boolean);
  41. procedure SetShowModuleGrid(const Value: boolean);
  42. public
  43. constructor Create(AText : string; AWidth, AHeight : Single); overload;
  44. constructor Create(AText : string); overload;
  45. constructor Create(AText : string; APixelsPerModule : integer); overload;
  46. constructor Create(AData : TArray<Byte>; AWidth, AHeight : Single); overload;
  47. constructor Create(AData : TArray<Byte>); overload;
  48. constructor Create(AData : TArray<Byte>; APixelsPerModule : integer); overload;
  49. constructor Create; overload; override;
  50. destructor Destroy; override;
  51. procedure BeginUpdate;
  52. procedure EndUpdate;
  53. property Text : string read GetText write SetText;
  54. property Data : TArray<Byte> read GetData write SetData;
  55. property Version : TVersion read GetVersion write SetVersion;
  56. property ECL : TErrorCorrectionLevel read GetECL write SetECL;
  57. property Mask : TMask read GetMask write SetMask;
  58. property ShowModuleGrid : boolean read FShowModuleGrid write SetShowModuleGrid;
  59. property ShowBorder : boolean read FShowBorder write SetShowBorder;
  60. end;
  61. implementation
  62. uses System.Math, System.Types, System.UITypes;
  63. { TQRCodeBitmap }
  64. procedure TQRBitmap.BeginUpdate;
  65. begin
  66. FQR.BeginUpdate;
  67. end;
  68. constructor TQRBitmap.Create;
  69. begin
  70. inherited Create;
  71. FQR := TQRCode.Create;
  72. FQR.OnPaint :=
  73. procedure(Width, Height : Integer; BlackRects : TArray<TRect>)
  74. var
  75. R : TRect;
  76. x, y : integer;
  77. begin
  78. Self.Width := Width;
  79. Self.Height := Height;
  80. Self.Canvas.BeginScene;
  81. try
  82. Self.Canvas.Fill.Color := TAlphaColorRec.White;
  83. Self.Canvas.Stroke.Color := TAlphaColorRec.White;
  84. Self.Canvas.FillRect(TRect.Create(0,0,Self.Width, Self.Height), 0, 0, [],1);
  85. Self.Canvas.Fill.Color := TAlphaColorRec.Black;
  86. Self.Canvas.Stroke.Color := TAlphaColorRec.Black;
  87. for R in BlackRects do
  88. begin
  89. Self.Canvas.FillRect(R, 0, 0, [], 1);
  90. end;
  91. if FShowModuleGrid then
  92. begin
  93. Self.Canvas.Stroke.Color := TAlphaColorRec.LtGray;
  94. Self.Canvas.Stroke.Dash := TStrokeDash.Dot;
  95. for x := 0 to Self.Width -1 do
  96. if x mod FQR.PixelsPerModule = 0 then
  97. begin
  98. Self.Canvas.DrawLine(TPointF.Create(x,0), TPointF.Create(x,Self.Height-1),1);
  99. end;
  100. for y := 0 to Self.Height-1 do
  101. begin
  102. if y mod FQR.PixelsPerModule = 0 then
  103. begin
  104. Self.Canvas.DrawLine(TPointF.Create(0,y), TPointF.Create(Self.Height-1, y), 1);
  105. end;
  106. end;
  107. end;
  108. if FShowBorder then
  109. begin
  110. Self.Canvas.Fill.Color := TAlphaColorRec.Black;
  111. Self.Canvas.Stroke.Color := TAlphaColorRec.Black;
  112. Self.Canvas.Stroke.Dash := TStrokeDash.Solid;
  113. Self.Canvas.DrawRect(TRect.Create(0,0,Self.Width, Self.Height),0,0,[],1);
  114. end;
  115. finally
  116. Self.Canvas.EndScene;
  117. end;
  118. end;
  119. end;
  120. constructor TQRBitmap.Create(AText: string; APixelsPerModule: integer);
  121. begin
  122. Create;
  123. FQR.BeginUpdate;
  124. try
  125. FQR.Text := AText;
  126. FQR.PixelsPerModule := APixelsPerModule;
  127. finally
  128. FQR.EndUpdate;
  129. end;
  130. end;
  131. constructor TQRBitmap.Create(AData: TArray<Byte>; AWidth, AHeight: Single);
  132. begin
  133. Create;
  134. FQR.BeginUpdate;
  135. try
  136. FQR.Data := AData;
  137. FQR.RenderSize := Round(Min(AWidth, AHeight));
  138. finally
  139. FQR.EndUpdate;
  140. end;
  141. end;
  142. constructor TQRBitmap.Create(AData: TArray<Byte>; APixelsPerModule: integer);
  143. begin
  144. Create;
  145. FQR.BeginUpdate;
  146. try
  147. FQR.Data := AData;
  148. FQR.PixelsPerModule := APixelsPerModule;
  149. finally
  150. FQR.EndUpdate;
  151. end;
  152. end;
  153. constructor TQRBitmap.Create(AData: TArray<Byte>);
  154. begin
  155. Create;
  156. FQR.Data := AData;
  157. end;
  158. constructor TQRBitmap.Create(AText: string);
  159. begin
  160. Create;
  161. FQR.Text := AText;
  162. end;
  163. constructor TQRBitmap.Create(AText: string; AWidth, AHeight: Single);
  164. begin
  165. Create;
  166. FQR.BeginUpdate;
  167. try
  168. FQR.Text := AText;
  169. FQR.RenderSize := Round(Min(AWidth, AHeight));
  170. finally
  171. FQR.EndUpdate;
  172. end;
  173. end;
  174. destructor TQRBitmap.Destroy;
  175. begin
  176. FQR.Free;
  177. inherited;
  178. end;
  179. procedure TQRBitmap.EndUpdate;
  180. begin
  181. FQR.EndUpdate;
  182. end;
  183. function TQRBitmap.GetData: TArray<Byte>;
  184. begin
  185. Result := FQR.Data;
  186. end;
  187. function TQRBitmap.GetECL: TErrorCorrectionLevel;
  188. begin
  189. Result := FQR.ECL;
  190. end;
  191. function TQRBitmap.GetMask: TMask;
  192. begin
  193. Result := FQR.Mask;
  194. end;
  195. function TQRBitmap.GetText: string;
  196. begin
  197. Result := FQR.Text;
  198. end;
  199. function TQRBitmap.GetVersion: TVersion;
  200. begin
  201. Result := FQR.Version;
  202. end;
  203. procedure TQRBitmap.SetData(const Value: TArray<Byte>);
  204. begin
  205. FQR.Data := Value;
  206. end;
  207. procedure TQRBitmap.SetECL(const Value: TErrorCorrectionLevel);
  208. begin
  209. FQR.ECL := Value;
  210. end;
  211. procedure TQRBitmap.SetMask(const Value: TMask);
  212. begin
  213. FQR.Mask := Value;
  214. end;
  215. procedure TQRBitmap.SetShowBorder(const Value: boolean);
  216. begin
  217. FShowBorder := Value;
  218. FQR.Redraw;
  219. end;
  220. procedure TQRBitmap.SetShowModuleGrid(const Value: boolean);
  221. begin
  222. FShowModuleGrid := Value;
  223. FQR.Redraw;
  224. end;
  225. procedure TQRBitmap.SetText(const Value: string);
  226. begin
  227. FQR.Text := Value;
  228. end;
  229. procedure TQRBitmap.SetVersion(const Value: TVersion);
  230. begin
  231. FQR.Version := Value;
  232. end;
  233. end.