Showing
8 changed files
with
85 additions
and
19 deletions
@@ -6,6 +6,7 @@ | @@ -6,6 +6,7 @@ | ||
6 | - Document.save() now returns a Future | 6 | - Document.save() now returns a Future |
7 | - Implement pan and zoom on PdfPreview widget | 7 | - Implement pan and zoom on PdfPreview widget |
8 | - Improve orientation handling | 8 | - Improve orientation handling |
9 | +- Improve directPrint | ||
9 | 10 | ||
10 | ## 3.7.2 | 11 | ## 3.7.2 |
11 | 12 |
@@ -165,6 +165,9 @@ class MethodChannelPrinting extends PrintingPlatform { | @@ -165,6 +165,9 @@ class MethodChannelPrinting extends PrintingPlatform { | ||
165 | name: printer['name'], | 165 | name: printer['name'], |
166 | model: printer['model'], | 166 | model: printer['model'], |
167 | location: printer['location'], | 167 | location: printer['location'], |
168 | + comment: printer['comment'], | ||
169 | + isDefault: printer['default'], | ||
170 | + available: printer['available'], | ||
168 | )); | 171 | )); |
169 | } | 172 | } |
170 | 173 |
@@ -25,6 +25,9 @@ class Printer { | @@ -25,6 +25,9 @@ class Printer { | ||
25 | this.name, | 25 | this.name, |
26 | this.model, | 26 | this.model, |
27 | this.location, | 27 | this.location, |
28 | + this.comment, | ||
29 | + this.isDefault = false, | ||
30 | + this.available = true, | ||
28 | }) : assert(url != null); | 31 | }) : assert(url != null); |
29 | 32 | ||
30 | /// The platform specific printer identification | 33 | /// The platform specific printer identification |
@@ -39,6 +42,15 @@ class Printer { | @@ -39,6 +42,15 @@ class Printer { | ||
39 | /// The physical location of the printer | 42 | /// The physical location of the printer |
40 | final String location; | 43 | final String location; |
41 | 44 | ||
45 | + /// A user comment about the printer | ||
46 | + final String comment; | ||
47 | + | ||
48 | + /// Is this the default printer on the system | ||
49 | + final bool isDefault; | ||
50 | + | ||
51 | + /// The printer is available for printing | ||
52 | + final bool available; | ||
53 | + | ||
42 | @override | 54 | @override |
43 | String toString() => name ?? url; | 55 | String toString() => name ?? url; |
44 | } | 56 | } |
@@ -65,6 +65,7 @@ mixin Printing { | @@ -65,6 +65,7 @@ mixin Printing { | ||
65 | static Future<Printer> pickPrinter({ | 65 | static Future<Printer> pickPrinter({ |
66 | @required BuildContext context, | 66 | @required BuildContext context, |
67 | Rect bounds, | 67 | Rect bounds, |
68 | + String title, | ||
68 | }) async { | 69 | }) async { |
69 | final _info = await info(); | 70 | final _info = await info(); |
70 | 71 | ||
@@ -74,17 +75,35 @@ mixin Printing { | @@ -74,17 +75,35 @@ mixin Printing { | ||
74 | 'Pass a BuildContext to pickPrinter to display a selection list', | 75 | 'Pass a BuildContext to pickPrinter to display a selection list', |
75 | ); | 76 | ); |
76 | final printers = await listPrinters(); | 77 | final printers = await listPrinters(); |
78 | + printers.sort((a, b) { | ||
79 | + if (a.isDefault) { | ||
80 | + return -1; | ||
81 | + } | ||
82 | + if (b.isDefault) { | ||
83 | + return 1; | ||
84 | + } | ||
85 | + return a.name.compareTo(b.name); | ||
86 | + }); | ||
87 | + | ||
77 | return await showDialog<Printer>( | 88 | return await showDialog<Printer>( |
78 | context: context, | 89 | context: context, |
79 | builder: (context) => SimpleDialog( | 90 | builder: (context) => SimpleDialog( |
80 | - children: printers | ||
81 | - .map<Widget>( | ||
82 | - (e) => SimpleDialogOption( | ||
83 | - child: Text(e.name), | ||
84 | - onPressed: () => Navigator.of(context).pop(e), | 91 | + title: Text(title ?? 'Select Printer'), |
92 | + children: [ | ||
93 | + for (final printer in printers) | ||
94 | + if (printer.available) | ||
95 | + SimpleDialogOption( | ||
96 | + child: Text( | ||
97 | + printer.name, | ||
98 | + style: TextStyle( | ||
99 | + fontStyle: printer.isDefault | ||
100 | + ? FontStyle.italic | ||
101 | + : FontStyle.normal, | ||
102 | + ), | ||
103 | + ), | ||
104 | + onPressed: () => Navigator.of(context).pop(printer), | ||
85 | ), | 105 | ), |
86 | - ) | ||
87 | - .toList(), | 106 | + ], |
88 | ), | 107 | ), |
89 | ); | 108 | ); |
90 | } | 109 | } |
printing/windows/CMakeLists.txt
100755 → 100644
@@ -134,6 +134,7 @@ bool PrintJob::printPdf(std::string name) { | @@ -134,6 +134,7 @@ bool PrintJob::printPdf(std::string name) { | ||
134 | ZeroMemory(dm, sizeof(DEVMODE)); | 134 | ZeroMemory(dm, sizeof(DEVMODE)); |
135 | dm->dmFields = DM_ORIENTATION; | 135 | dm->dmFields = DM_ORIENTATION; |
136 | dm->dmOrientation = 2; | 136 | dm->dmOrientation = 2; |
137 | + printf("Printing ... \n"); | ||
137 | 138 | ||
138 | // Initialize PRINTDLG | 139 | // Initialize PRINTDLG |
139 | ZeroMemory(&pd, sizeof(pd)); | 140 | ZeroMemory(&pd, sizeof(pd)); |
@@ -186,19 +187,28 @@ bool PrintJob::printPdf(std::string name) { | @@ -186,19 +187,28 @@ bool PrintJob::printPdf(std::string name) { | ||
186 | } | 187 | } |
187 | 188 | ||
188 | std::vector<Printer> PrintJob::listPrinters() { | 189 | std::vector<Printer> PrintJob::listPrinters() { |
190 | + LPTSTR defaultPrinter; | ||
191 | + DWORD size = 0; | ||
192 | + GetDefaultPrinter(nullptr, &size); | ||
193 | + | ||
194 | + defaultPrinter = static_cast<LPTSTR>(malloc(size * sizeof(TCHAR))); | ||
195 | + if (!GetDefaultPrinter(defaultPrinter, &size)) { | ||
196 | + size = 0; | ||
197 | + } | ||
198 | + | ||
189 | auto printers = std::vector<Printer>{}; | 199 | auto printers = std::vector<Printer>{}; |
190 | DWORD needed = 0; | 200 | DWORD needed = 0; |
191 | DWORD returned = 0; | 201 | DWORD returned = 0; |
192 | const auto flags = PRINTER_ENUM_LOCAL | PRINTER_ENUM_CONNECTIONS; | 202 | const auto flags = PRINTER_ENUM_LOCAL | PRINTER_ENUM_CONNECTIONS; |
193 | 203 | ||
194 | - EnumPrinters(flags, nullptr, 1, nullptr, 0, &needed, &returned); | 204 | + EnumPrinters(flags, nullptr, 2, nullptr, 0, &needed, &returned); |
195 | 205 | ||
196 | - auto buffer = (PRINTER_INFO_1*)malloc(needed); | 206 | + auto buffer = (PRINTER_INFO_2*)malloc(needed); |
197 | if (!buffer) { | 207 | if (!buffer) { |
198 | return printers; | 208 | return printers; |
199 | } | 209 | } |
200 | 210 | ||
201 | - auto result = EnumPrinters(flags, nullptr, 1, (LPBYTE)buffer, needed, &needed, | 211 | + auto result = EnumPrinters(flags, nullptr, 2, (LPBYTE)buffer, needed, &needed, |
202 | &returned); | 212 | &returned); |
203 | 213 | ||
204 | if (result == 0) { | 214 | if (result == 0) { |
@@ -208,14 +218,17 @@ std::vector<Printer> PrintJob::listPrinters() { | @@ -208,14 +218,17 @@ std::vector<Printer> PrintJob::listPrinters() { | ||
208 | 218 | ||
209 | for (DWORD i = 0; i < returned; i++) { | 219 | for (DWORD i = 0; i < returned; i++) { |
210 | printers.push_back(Printer{ | 220 | printers.push_back(Printer{ |
211 | - toUtf8(buffer[i].pName), | ||
212 | - toUtf8(buffer[i].pName), | ||
213 | - toUtf8(buffer[i].pDescription), | 221 | + toUtf8(buffer[i].pPrinterName), toUtf8(buffer[i].pPrinterName), |
222 | + toUtf8(buffer[i].pDriverName), toUtf8(buffer[i].pLocation), | ||
214 | toUtf8(buffer[i].pComment), | 223 | toUtf8(buffer[i].pComment), |
215 | - }); | 224 | + size > 0 && _tcsncmp(buffer[i].pPrinterName, defaultPrinter, size) == 0, |
225 | + (buffer[i].Status & | ||
226 | + (PRINTER_STATUS_NOT_AVAILABLE | PRINTER_STATUS_ERROR | | ||
227 | + PRINTER_STATUS_OFFLINE | PRINTER_STATUS_PAUSED)) == 0}); | ||
216 | } | 228 | } |
217 | 229 | ||
218 | free(buffer); | 230 | free(buffer); |
231 | + free(defaultPrinter); | ||
219 | return printers; | 232 | return printers; |
220 | } | 233 | } |
221 | 234 |
@@ -34,13 +34,25 @@ struct Printer { | @@ -34,13 +34,25 @@ struct Printer { | ||
34 | const std::string name; | 34 | const std::string name; |
35 | const std::string url; | 35 | const std::string url; |
36 | const std::string model; | 36 | const std::string model; |
37 | - const std::string description; | 37 | + const std::string location; |
38 | + const std::string comment; | ||
39 | + const bool default; | ||
40 | + const bool available; | ||
38 | 41 | ||
39 | Printer(std::string name, | 42 | Printer(std::string name, |
40 | std::string url, | 43 | std::string url, |
41 | std::string model, | 44 | std::string model, |
42 | - std::string description) | ||
43 | - : name(name), url(url), model(model), description(description) {} | 45 | + std::string location, |
46 | + std::string comment, | ||
47 | + bool default, | ||
48 | + bool available) | ||
49 | + : name(name), | ||
50 | + url(url), | ||
51 | + model(model), | ||
52 | + location(location), | ||
53 | + comment(comment), | ||
54 | + default(default), | ||
55 | + available(available) {} | ||
44 | }; | 56 | }; |
45 | 57 | ||
46 | class PrintJob { | 58 | class PrintJob { |
@@ -125,8 +125,14 @@ class PrintingPlugin : public flutter::Plugin { | @@ -125,8 +125,14 @@ class PrintingPlugin : public flutter::Plugin { | ||
125 | flutter::EncodableValue(printer.url); | 125 | flutter::EncodableValue(printer.url); |
126 | mp[flutter::EncodableValue("model")] = | 126 | mp[flutter::EncodableValue("model")] = |
127 | flutter::EncodableValue(printer.model); | 127 | flutter::EncodableValue(printer.model); |
128 | - mp[flutter::EncodableValue("description")] = | ||
129 | - flutter::EncodableValue(printer.description); | 128 | + mp[flutter::EncodableValue("location")] = |
129 | + flutter::EncodableValue(printer.location); | ||
130 | + mp[flutter::EncodableValue("comment")] = | ||
131 | + flutter::EncodableValue(printer.comment); | ||
132 | + mp[flutter::EncodableValue("default")] = | ||
133 | + flutter::EncodableValue(printer.default); | ||
134 | + mp[flutter::EncodableValue("available")] = | ||
135 | + flutter::EncodableValue(printer.available); | ||
130 | pl.push_back(mp); | 136 | pl.push_back(mp); |
131 | } | 137 | } |
132 | result->Success(pl); | 138 | result->Success(pl); |
-
Please register or login to post a comment