Showing
14 changed files
with
142 additions
and
231 deletions
@@ -5,6 +5,7 @@ | @@ -5,6 +5,7 @@ | ||
5 | - Add PdfPreview Widget | 5 | - Add PdfPreview Widget |
6 | - Implement Printing.raster() on Flutter Web | 6 | - Implement Printing.raster() on Flutter Web |
7 | - Fix Swift 5 deprecated function | 7 | - Fix Swift 5 deprecated function |
8 | +- Improve code documentation | ||
8 | 9 | ||
9 | ## 3.3.1 | 10 | ## 3.3.1 |
10 | 11 |
1 | -# Specify analysis options. | ||
2 | -# | ||
3 | -# Until there are meta linter rules, each desired lint must be explicitly enabled. | ||
4 | -# See: https://github.com/dart-lang/linter/issues/288 | ||
5 | -# | ||
6 | -# For a list of lints, see: http://dart-lang.github.io/linter/lints/ | ||
7 | -# See the configuration guide for more | ||
8 | -# https://github.com/dart-lang/sdk/tree/master/pkg/analyzer#configuring-the-analyzer | ||
9 | -# | ||
10 | -# There are other similar analysis options files in the flutter repos, | ||
11 | -# which should be kept in sync with this file: | ||
12 | -# | ||
13 | -# - analysis_options.yaml (this file) | ||
14 | -# - packages/flutter/lib/analysis_options_user.yaml | ||
15 | -# - https://github.com/flutter/plugins/blob/master/analysis_options.yaml | ||
16 | -# - https://github.com/flutter/engine/blob/master/analysis_options.yaml | ||
17 | -# | ||
18 | -# This file contains the analysis options used by Flutter tools, such as IntelliJ, | ||
19 | -# Android Studio, and the `flutter analyze` command. | 1 | +include: package:pedantic/analysis_options.yaml |
20 | 2 | ||
21 | analyzer: | 3 | analyzer: |
22 | strong-mode: | 4 | strong-mode: |
23 | implicit-dynamic: false | 5 | implicit-dynamic: false |
24 | errors: | 6 | errors: |
25 | - # treat missing required parameters as a warning (not a hint) | ||
26 | missing_required_param: warning | 7 | missing_required_param: warning |
27 | - # treat missing returns as a warning (not a hint) | ||
28 | missing_return: warning | 8 | missing_return: warning |
29 | - # allow having TODOs in the code | 9 | + public_member_api_docs: warning |
30 | todo: ignore | 10 | todo: ignore |
31 | - # Ignore analyzer hints for updating pubspecs when using Future or | ||
32 | - # Stream and not importing dart:async | ||
33 | - # Please see https://github.com/flutter/flutter/pull/24528 for details. | ||
34 | - sdk_version_async_exported_from_core: ignore | ||
35 | - exclude: | ||
36 | - - "bin/cache/**" | ||
37 | - # the following two are relative to the stocks example and the flutter package respectively | ||
38 | - # see https://github.com/dart-lang/sdk/issues/28463 | ||
39 | - - "lib/i18n/stock_messages_*.dart" | ||
40 | - - "lib/src/http/**" | ||
41 | 11 | ||
42 | linter: | 12 | linter: |
43 | rules: | 13 | rules: |
44 | - # these rules are documented on and in the same order as | ||
45 | - # the Dart Lint rules page to make maintenance easier | ||
46 | - # https://github.com/dart-lang/linter/blob/master/example/all.yaml | ||
47 | - - always_declare_return_types | ||
48 | - always_put_control_body_on_new_line | 14 | - always_put_control_body_on_new_line |
49 | - # - always_put_required_named_parameters_first # we prefer having parameters in the same order as fields https://github.com/flutter/flutter/issues/10219 | ||
50 | - - always_require_non_null_named_parameters | ||
51 | - - always_specify_types | ||
52 | - - annotate_overrides | ||
53 | - # - avoid_annotating_with_dynamic # conflicts with always_specify_types | ||
54 | - avoid_as | 15 | - avoid_as |
55 | - avoid_bool_literals_in_conditional_expressions | 16 | - avoid_bool_literals_in_conditional_expressions |
56 | - # - avoid_catches_without_on_clauses # we do this commonly | ||
57 | - # - avoid_catching_errors # we do this commonly | ||
58 | - avoid_classes_with_only_static_members | 17 | - avoid_classes_with_only_static_members |
59 | - # - avoid_double_and_int_checks # only useful when targeting JS runtime | ||
60 | - - avoid_empty_else | ||
61 | - avoid_field_initializers_in_const_classes | 18 | - avoid_field_initializers_in_const_classes |
62 | - avoid_function_literals_in_foreach_calls | 19 | - avoid_function_literals_in_foreach_calls |
63 | - # - avoid_implementing_value_types # not yet tested | ||
64 | - - avoid_init_to_null | ||
65 | - # - avoid_js_rounded_ints # only useful when targeting JS runtime | ||
66 | - - avoid_null_checks_in_equality_operators | ||
67 | - # - avoid_positional_boolean_parameters # not yet tested | ||
68 | - # - avoid_private_typedef_functions # we prefer having typedef (discussion in https://github.com/flutter/flutter/pull/16356) | ||
69 | - - avoid_relative_lib_imports | ||
70 | - avoid_renaming_method_parameters | 20 | - avoid_renaming_method_parameters |
71 | - - avoid_return_types_on_setters | ||
72 | - # - avoid_returning_null # there are plenty of valid reasons to return null | ||
73 | - # - avoid_returning_null_for_future # not yet tested | ||
74 | - avoid_returning_null_for_void | 21 | - avoid_returning_null_for_void |
75 | - # - avoid_returning_this # there are plenty of valid reasons to return this | ||
76 | - # - avoid_setters_without_getters # not yet tested | ||
77 | - # - avoid_shadowing_type_parameters # not yet tested | ||
78 | - # - avoid_single_cascade_in_expression_statements # not yet tested | ||
79 | - avoid_slow_async_io | 22 | - avoid_slow_async_io |
80 | - - avoid_types_as_parameter_names | ||
81 | - # - avoid_types_on_closure_parameters # conflicts with always_specify_types | ||
82 | - avoid_unused_constructor_parameters | 23 | - avoid_unused_constructor_parameters |
83 | - avoid_void_async | 24 | - avoid_void_async |
84 | - await_only_futures | 25 | - await_only_futures |
85 | - camel_case_types | 26 | - camel_case_types |
86 | - cancel_subscriptions | 27 | - cancel_subscriptions |
87 | - # - cascade_invocations # not yet tested | ||
88 | - # - close_sinks # not reliable enough | ||
89 | - # - comment_references # blocked on https://github.com/flutter/flutter/issues/20765 | ||
90 | - # - constant_identifier_names # needs an opt-out https://github.com/dart-lang/linter/issues/204 | ||
91 | - control_flow_in_finally | 28 | - control_flow_in_finally |
92 | - # - curly_braces_in_flow_control_structures # not yet tested | ||
93 | - # - diagnostic_describe_all_properties # not yet tested | ||
94 | - directives_ordering | 29 | - directives_ordering |
95 | - - empty_catches | ||
96 | - - empty_constructor_bodies | ||
97 | - empty_statements | 30 | - empty_statements |
98 | - # - file_names # not yet tested | ||
99 | - flutter_style_todos | 31 | - flutter_style_todos |
100 | - hash_and_equals | 32 | - hash_and_equals |
101 | - implementation_imports | 33 | - implementation_imports |
102 | - # - invariant_booleans # too many false positives: https://github.com/dart-lang/linter/issues/811 | ||
103 | - iterable_contains_unrelated_type | 34 | - iterable_contains_unrelated_type |
104 | - # - join_return_with_assignment # not yet tested | ||
105 | - - library_names | ||
106 | - - library_prefixes | ||
107 | - # - lines_longer_than_80_chars # not yet tested | ||
108 | - list_remove_unrelated_type | 35 | - list_remove_unrelated_type |
109 | - # - literal_only_boolean_expressions # too many false positives: https://github.com/dart-lang/sdk/issues/34181 | ||
110 | - no_adjacent_strings_in_list | 36 | - no_adjacent_strings_in_list |
111 | - - no_duplicate_case_values | ||
112 | - non_constant_identifier_names | 37 | - non_constant_identifier_names |
113 | - # - null_closures # not yet tested | ||
114 | - # - omit_local_variable_types # opposite of always_specify_types | ||
115 | - # - one_member_abstracts # too many false positives | ||
116 | - # - only_throw_errors # https://github.com/flutter/flutter/issues/5792 | 38 | + - omit_local_variable_types |
117 | - overridden_fields | 39 | - overridden_fields |
118 | - package_api_docs | 40 | - package_api_docs |
119 | - package_names | 41 | - package_names |
120 | - package_prefixed_library_names | 42 | - package_prefixed_library_names |
121 | - # - parameter_assignments # we do this commonly | ||
122 | - - prefer_adjacent_string_concatenation | ||
123 | - prefer_asserts_in_initializer_lists | 43 | - prefer_asserts_in_initializer_lists |
124 | - # - prefer_asserts_with_message # not yet tested | ||
125 | - - prefer_collection_literals | ||
126 | - - prefer_conditional_assignment | ||
127 | - prefer_const_constructors | 44 | - prefer_const_constructors |
128 | - prefer_const_constructors_in_immutables | 45 | - prefer_const_constructors_in_immutables |
129 | - prefer_const_declarations | 46 | - prefer_const_declarations |
130 | - prefer_const_literals_to_create_immutables | 47 | - prefer_const_literals_to_create_immutables |
131 | - # - prefer_constructors_over_static_methods # not yet tested | ||
132 | - - prefer_contains | ||
133 | - # - prefer_double_quotes # opposite of prefer_single_quotes | ||
134 | - - prefer_equal_for_default_values | ||
135 | - # - prefer_expression_function_bodies # conflicts with https://github.com/flutter/flutter/wiki/Style-guide-for-Flutter-repo#consider-using--for-short-functions-and-methods | ||
136 | - - prefer_final_fields | ||
137 | - # - prefer_final_in_for_each # not yet tested | ||
138 | - prefer_final_locals | 48 | - prefer_final_locals |
139 | - # - prefer_for_elements_to_map_fromIterable # not yet tested | ||
140 | - prefer_foreach | 49 | - prefer_foreach |
141 | - # - prefer_function_declarations_over_variables # not yet tested | ||
142 | - - prefer_generic_function_type_aliases | ||
143 | - prefer_if_elements_to_conditional_expressions | 50 | - prefer_if_elements_to_conditional_expressions |
144 | - - prefer_if_null_operators | ||
145 | - prefer_initializing_formals | 51 | - prefer_initializing_formals |
146 | - prefer_inlined_adds | 52 | - prefer_inlined_adds |
147 | - # - prefer_int_literals # not yet tested | ||
148 | - # - prefer_interpolation_to_compose_strings # not yet tested | ||
149 | - - prefer_is_empty | ||
150 | - - prefer_is_not_empty | ||
151 | - - prefer_iterable_whereType | ||
152 | - # - prefer_mixin # https://github.com/dart-lang/language/issues/32 | ||
153 | - # - prefer_null_aware_operators # disable until NNBD, see https://github.com/flutter/flutter/pull/32711#issuecomment-492930932 | ||
154 | - - prefer_single_quotes | ||
155 | - - prefer_spread_collections | ||
156 | - prefer_typing_uninitialized_variables | 53 | - prefer_typing_uninitialized_variables |
157 | - prefer_void_to_null | 54 | - prefer_void_to_null |
158 | - # - provide_deprecation_message # not yet tested | ||
159 | - # - public_member_api_docs # enabled on a case-by-case basis; see e.g. packages/analysis_options.yaml | ||
160 | - - recursive_getters | ||
161 | - - slash_for_doc_comments | ||
162 | - # - sort_child_properties_last # not yet tested | 55 | + - public_member_api_docs |
163 | - sort_constructors_first | 56 | - sort_constructors_first |
164 | - sort_pub_dependencies | 57 | - sort_pub_dependencies |
165 | - sort_unnamed_constructors_first | 58 | - sort_unnamed_constructors_first |
166 | - test_types_in_equals | 59 | - test_types_in_equals |
167 | - throw_in_finally | 60 | - throw_in_finally |
168 | - # - type_annotate_public_apis # subset of always_specify_types | ||
169 | - - type_init_formals | ||
170 | - # - unawaited_futures # too many false positives | ||
171 | - # - unnecessary_await_in_return # not yet tested | ||
172 | - unnecessary_brace_in_string_interps | 61 | - unnecessary_brace_in_string_interps |
173 | - - unnecessary_const | ||
174 | - unnecessary_getters_setters | 62 | - unnecessary_getters_setters |
175 | - # - unnecessary_lambdas # has false positives: https://github.com/dart-lang/linter/issues/498 | ||
176 | - - unnecessary_new | ||
177 | - unnecessary_null_aware_assignments | 63 | - unnecessary_null_aware_assignments |
178 | - - unnecessary_null_in_if_null_operators | ||
179 | - unnecessary_overrides | 64 | - unnecessary_overrides |
180 | - unnecessary_parenthesis | 65 | - unnecessary_parenthesis |
181 | - unnecessary_statements | 66 | - unnecessary_statements |
182 | - - unnecessary_this | ||
183 | - - unrelated_type_equality_checks | ||
184 | - # - unsafe_html # not yet tested | ||
185 | - use_full_hex_values_for_flutter_colors | 67 | - use_full_hex_values_for_flutter_colors |
186 | - # - use_function_type_syntax_for_parameters # not yet tested | ||
187 | - - use_rethrow_when_possible | ||
188 | - # - use_setters_to_change_properties # not yet tested | ||
189 | - # - use_string_buffers # has false positives: https://github.com/dart-lang/sdk/issues/34182 | ||
190 | - # - use_to_and_as_if_applicable # has false positives, so we prefer to catch this by code-review | ||
191 | - - valid_regexps | ||
192 | - # - void_checks # not yet tested |
@@ -15,7 +15,6 @@ | @@ -15,7 +15,6 @@ | ||
15 | */ | 15 | */ |
16 | 16 | ||
17 | import 'dart:async'; | 17 | import 'dart:async'; |
18 | -import 'dart:typed_data'; | ||
19 | import 'dart:ui' as ui; | 18 | import 'dart:ui' as ui; |
20 | 19 | ||
21 | import 'package:flutter/rendering.dart'; | 20 | import 'package:flutter/rendering.dart'; |
@@ -28,8 +27,7 @@ import 'package:pdf/widgets.dart'; | @@ -28,8 +27,7 @@ import 'package:pdf/widgets.dart'; | ||
28 | /// into a [PdfImage] instance | 27 | /// into a [PdfImage] instance |
29 | Future<PdfImage> pdfImageFromImage( | 28 | Future<PdfImage> pdfImageFromImage( |
30 | {@required PdfDocument pdf, @required ui.Image image}) async { | 29 | {@required PdfDocument pdf, @required ui.Image image}) async { |
31 | - final ByteData bytes = | ||
32 | - await image.toByteData(format: ui.ImageByteFormat.rawRgba); | 30 | + final bytes = await image.toByteData(format: ui.ImageByteFormat.rawRgba); |
33 | 31 | ||
34 | return PdfImage(pdf, | 32 | return PdfImage(pdf, |
35 | image: bytes.buffer.asUint8List(), | 33 | image: bytes.buffer.asUint8List(), |
@@ -44,14 +42,12 @@ Future<PdfImage> pdfImageFromImageProvider( | @@ -44,14 +42,12 @@ Future<PdfImage> pdfImageFromImageProvider( | ||
44 | @required ImageProvider image, | 42 | @required ImageProvider image, |
45 | ImageConfiguration configuration, | 43 | ImageConfiguration configuration, |
46 | ImageErrorListener onError}) async { | 44 | ImageErrorListener onError}) async { |
47 | - final Completer<PdfImage> completer = Completer<PdfImage>(); | ||
48 | - final ImageStream stream = | ||
49 | - image.resolve(configuration ?? ImageConfiguration.empty); | 45 | + final completer = Completer<PdfImage>(); |
46 | + final stream = image.resolve(configuration ?? ImageConfiguration.empty); | ||
50 | 47 | ||
51 | ImageStreamListener listener; | 48 | ImageStreamListener listener; |
52 | listener = ImageStreamListener((ImageInfo image, bool sync) async { | 49 | listener = ImageStreamListener((ImageInfo image, bool sync) async { |
53 | - final PdfImage result = | ||
54 | - await pdfImageFromImage(pdf: pdf, image: image.image); | 50 | + final result = await pdfImageFromImage(pdf: pdf, image: image.image); |
55 | if (!completer.isCompleted) { | 51 | if (!completer.isCompleted) { |
56 | completer.complete(result); | 52 | completer.complete(result); |
57 | } | 53 | } |
@@ -75,6 +71,6 @@ Future<PdfImage> pdfImageFromImageProvider( | @@ -75,6 +71,6 @@ Future<PdfImage> pdfImageFromImageProvider( | ||
75 | /// Loads a font from an asset bundle key. If used multiple times with the same font name, | 71 | /// Loads a font from an asset bundle key. If used multiple times with the same font name, |
76 | /// it will be included multiple times in the pdf file | 72 | /// it will be included multiple times in the pdf file |
77 | Future<TtfFont> fontFromAssetBundle(String key, AssetBundle bundle) async { | 73 | Future<TtfFont> fontFromAssetBundle(String key, AssetBundle bundle) async { |
78 | - final ByteData data = await bundle.load(key); | 74 | + final data = await bundle.load(key); |
79 | return TtfFont(data); | 75 | return TtfFont(data); |
80 | } | 76 | } |
@@ -32,6 +32,7 @@ const MethodChannel _channel = MethodChannel('net.nfet.printing'); | @@ -32,6 +32,7 @@ const MethodChannel _channel = MethodChannel('net.nfet.printing'); | ||
32 | 32 | ||
33 | /// An implementation of [PrintingPlatform] that uses method channels. | 33 | /// An implementation of [PrintingPlatform] that uses method channels. |
34 | class MethodChannelPrinting extends PrintingPlatform { | 34 | class MethodChannelPrinting extends PrintingPlatform { |
35 | + /// Create a [PrintingPlatform] object for method channels. | ||
35 | MethodChannelPrinting() : super() { | 36 | MethodChannelPrinting() : super() { |
36 | _channel.setMethodCallHandler(_handleMethod); | 37 | _channel.setMethodCallHandler(_handleMethod); |
37 | } | 38 | } |
@@ -43,8 +44,8 @@ class MethodChannelPrinting extends PrintingPlatform { | @@ -43,8 +44,8 @@ class MethodChannelPrinting extends PrintingPlatform { | ||
43 | static Future<dynamic> _handleMethod(MethodCall call) async { | 44 | static Future<dynamic> _handleMethod(MethodCall call) async { |
44 | switch (call.method) { | 45 | switch (call.method) { |
45 | case 'onLayout': | 46 | case 'onLayout': |
46 | - final PrintJob job = _printJobs[call.arguments['job']]; | ||
47 | - final PdfPageFormat format = PdfPageFormat( | 47 | + final job = _printJobs[call.arguments['job']]; |
48 | + final format = PdfPageFormat( | ||
48 | call.arguments['width'], | 49 | call.arguments['width'], |
49 | call.arguments['height'], | 50 | call.arguments['height'], |
50 | marginLeft: call.arguments['marginLeft'], | 51 | marginLeft: call.arguments['marginLeft'], |
@@ -53,7 +54,7 @@ class MethodChannelPrinting extends PrintingPlatform { | @@ -53,7 +54,7 @@ class MethodChannelPrinting extends PrintingPlatform { | ||
53 | marginBottom: call.arguments['marginBottom'], | 54 | marginBottom: call.arguments['marginBottom'], |
54 | ); | 55 | ); |
55 | 56 | ||
56 | - final Uint8List bytes = await job.onLayout(format); | 57 | + final bytes = await job.onLayout(format); |
57 | 58 | ||
58 | if (bytes == null) { | 59 | if (bytes == null) { |
59 | throw 'onLayout returned null'; | 60 | throw 'onLayout returned null'; |
@@ -64,7 +65,7 @@ class MethodChannelPrinting extends PrintingPlatform { | @@ -64,7 +65,7 @@ class MethodChannelPrinting extends PrintingPlatform { | ||
64 | case 'onCompleted': | 65 | case 'onCompleted': |
65 | final bool completed = call.arguments['completed']; | 66 | final bool completed = call.arguments['completed']; |
66 | final String error = call.arguments['error']; | 67 | final String error = call.arguments['error']; |
67 | - final PrintJob job = _printJobs[call.arguments['job']]; | 68 | + final job = _printJobs[call.arguments['job']]; |
68 | if (completed == false && error != null) { | 69 | if (completed == false && error != null) { |
69 | job.onCompleted.completeError(error); | 70 | job.onCompleted.completeError(error); |
70 | } else { | 71 | } else { |
@@ -72,16 +73,16 @@ class MethodChannelPrinting extends PrintingPlatform { | @@ -72,16 +73,16 @@ class MethodChannelPrinting extends PrintingPlatform { | ||
72 | } | 73 | } |
73 | break; | 74 | break; |
74 | case 'onHtmlRendered': | 75 | case 'onHtmlRendered': |
75 | - final PrintJob job = _printJobs[call.arguments['job']]; | 76 | + final job = _printJobs[call.arguments['job']]; |
76 | job.onHtmlRendered.complete(call.arguments['doc']); | 77 | job.onHtmlRendered.complete(call.arguments['doc']); |
77 | break; | 78 | break; |
78 | case 'onHtmlError': | 79 | case 'onHtmlError': |
79 | - final PrintJob job = _printJobs[call.arguments['job']]; | 80 | + final job = _printJobs[call.arguments['job']]; |
80 | job.onHtmlRendered.completeError(call.arguments['error']); | 81 | job.onHtmlRendered.completeError(call.arguments['error']); |
81 | break; | 82 | break; |
82 | case 'onPageRasterized': | 83 | case 'onPageRasterized': |
83 | - final PrintJob job = _printJobs[call.arguments['job']]; | ||
84 | - final PdfRaster raster = PdfRaster( | 84 | + final job = _printJobs[call.arguments['job']]; |
85 | + final raster = PdfRaster( | ||
85 | call.arguments['width'], | 86 | call.arguments['width'], |
86 | call.arguments['height'], | 87 | call.arguments['height'], |
87 | call.arguments['image'], | 88 | call.arguments['image'], |
@@ -89,7 +90,7 @@ class MethodChannelPrinting extends PrintingPlatform { | @@ -89,7 +90,7 @@ class MethodChannelPrinting extends PrintingPlatform { | ||
89 | job.onPageRasterized.add(raster); | 90 | job.onPageRasterized.add(raster); |
90 | break; | 91 | break; |
91 | case 'onPageRasterEnd': | 92 | case 'onPageRasterEnd': |
92 | - final PrintJob job = _printJobs[call.arguments['job']]; | 93 | + final job = _printJobs[call.arguments['job']]; |
93 | job.onPageRasterized.close(); | 94 | job.onPageRasterized.close(); |
94 | _printJobs.remove(job.index); | 95 | _printJobs.remove(job.index); |
95 | break; | 96 | break; |
@@ -126,12 +127,12 @@ class MethodChannelPrinting extends PrintingPlatform { | @@ -126,12 +127,12 @@ class MethodChannelPrinting extends PrintingPlatform { | ||
126 | String name, | 127 | String name, |
127 | PdfPageFormat format, | 128 | PdfPageFormat format, |
128 | ) async { | 129 | ) async { |
129 | - final PrintJob job = _newPrintJob(PrintJob( | 130 | + final job = _newPrintJob(PrintJob( |
130 | onCompleted: Completer<bool>(), | 131 | onCompleted: Completer<bool>(), |
131 | onLayout: onLayout, | 132 | onLayout: onLayout, |
132 | )); | 133 | )); |
133 | 134 | ||
134 | - final Map<String, dynamic> params = <String, dynamic>{ | 135 | + final params = <String, dynamic>{ |
135 | 'name': name, | 136 | 'name': name, |
136 | 'job': job.index, | 137 | 'job': job.index, |
137 | 'width': format.width, | 138 | 'width': format.width, |
@@ -152,14 +153,14 @@ class MethodChannelPrinting extends PrintingPlatform { | @@ -152,14 +153,14 @@ class MethodChannelPrinting extends PrintingPlatform { | ||
152 | 153 | ||
153 | @override | 154 | @override |
154 | Future<Printer> pickPrinter(Rect bounds) async { | 155 | Future<Printer> pickPrinter(Rect bounds) async { |
155 | - final Map<String, dynamic> params = <String, dynamic>{ | 156 | + final params = <String, dynamic>{ |
156 | 'x': bounds.left, | 157 | 'x': bounds.left, |
157 | 'y': bounds.top, | 158 | 'y': bounds.top, |
158 | 'w': bounds.width, | 159 | 'w': bounds.width, |
159 | 'h': bounds.height, | 160 | 'h': bounds.height, |
160 | }; | 161 | }; |
161 | - final Map<dynamic, dynamic> printer = await _channel | ||
162 | - .invokeMethod<Map<dynamic, dynamic>>('pickPrinter', params); | 162 | + final printer = await _channel.invokeMethod<Map<dynamic, dynamic>>( |
163 | + 'pickPrinter', params); | ||
163 | if (printer == null) { | 164 | if (printer == null) { |
164 | return null; | 165 | return null; |
165 | } | 166 | } |
@@ -178,23 +179,23 @@ class MethodChannelPrinting extends PrintingPlatform { | @@ -178,23 +179,23 @@ class MethodChannelPrinting extends PrintingPlatform { | ||
178 | String name, | 179 | String name, |
179 | PdfPageFormat format, | 180 | PdfPageFormat format, |
180 | ) async { | 181 | ) async { |
181 | - final PrintJob job = _newPrintJob(PrintJob( | 182 | + final job = _newPrintJob(PrintJob( |
182 | onCompleted: Completer<bool>(), | 183 | onCompleted: Completer<bool>(), |
183 | )); | 184 | )); |
184 | 185 | ||
185 | - final Uint8List bytes = await onLayout(format); | 186 | + final bytes = await onLayout(format); |
186 | if (bytes == null) { | 187 | if (bytes == null) { |
187 | return false; | 188 | return false; |
188 | } | 189 | } |
189 | 190 | ||
190 | - final Map<String, dynamic> params = <String, dynamic>{ | 191 | + final params = <String, dynamic>{ |
191 | 'name': name, | 192 | 'name': name, |
192 | 'printer': printer.url, | 193 | 'printer': printer.url, |
193 | 'doc': Uint8List.fromList(bytes), | 194 | 'doc': Uint8List.fromList(bytes), |
194 | 'job': job.index, | 195 | 'job': job.index, |
195 | }; | 196 | }; |
196 | await _channel.invokeMethod<int>('directPrintPdf', params); | 197 | await _channel.invokeMethod<int>('directPrintPdf', params); |
197 | - final bool result = await job.onCompleted.future; | 198 | + final result = await job.onCompleted.future; |
198 | _printJobs.remove(job.index); | 199 | _printJobs.remove(job.index); |
199 | return result; | 200 | return result; |
200 | } | 201 | } |
@@ -205,7 +206,7 @@ class MethodChannelPrinting extends PrintingPlatform { | @@ -205,7 +206,7 @@ class MethodChannelPrinting extends PrintingPlatform { | ||
205 | String filename, | 206 | String filename, |
206 | Rect bounds, | 207 | Rect bounds, |
207 | ) async { | 208 | ) async { |
208 | - final Map<String, dynamic> params = <String, dynamic>{ | 209 | + final params = <String, dynamic>{ |
209 | 'doc': Uint8List.fromList(bytes), | 210 | 'doc': Uint8List.fromList(bytes), |
210 | 'name': filename, | 211 | 'name': filename, |
211 | 'x': bounds.left, | 212 | 'x': bounds.left, |
@@ -219,11 +220,11 @@ class MethodChannelPrinting extends PrintingPlatform { | @@ -219,11 +220,11 @@ class MethodChannelPrinting extends PrintingPlatform { | ||
219 | @override | 220 | @override |
220 | Future<Uint8List> convertHtml( | 221 | Future<Uint8List> convertHtml( |
221 | String html, String baseUrl, PdfPageFormat format) async { | 222 | String html, String baseUrl, PdfPageFormat format) async { |
222 | - final PrintJob job = _newPrintJob(PrintJob( | 223 | + final job = _newPrintJob(PrintJob( |
223 | onHtmlRendered: Completer<Uint8List>(), | 224 | onHtmlRendered: Completer<Uint8List>(), |
224 | )); | 225 | )); |
225 | 226 | ||
226 | - final Map<String, dynamic> params = <String, dynamic>{ | 227 | + final params = <String, dynamic>{ |
227 | 'html': html, | 228 | 'html': html, |
228 | 'baseUrl': baseUrl, | 229 | 'baseUrl': baseUrl, |
229 | 'width': format.width, | 230 | 'width': format.width, |
@@ -236,7 +237,7 @@ class MethodChannelPrinting extends PrintingPlatform { | @@ -236,7 +237,7 @@ class MethodChannelPrinting extends PrintingPlatform { | ||
236 | }; | 237 | }; |
237 | 238 | ||
238 | await _channel.invokeMethod<void>('convertHtml', params); | 239 | await _channel.invokeMethod<void>('convertHtml', params); |
239 | - final Uint8List result = await job.onHtmlRendered.future; | 240 | + final result = await job.onHtmlRendered.future; |
240 | _printJobs.remove(job.index); | 241 | _printJobs.remove(job.index); |
241 | return result; | 242 | return result; |
242 | } | 243 | } |
@@ -247,11 +248,11 @@ class MethodChannelPrinting extends PrintingPlatform { | @@ -247,11 +248,11 @@ class MethodChannelPrinting extends PrintingPlatform { | ||
247 | List<int> pages, | 248 | List<int> pages, |
248 | double dpi, | 249 | double dpi, |
249 | ) { | 250 | ) { |
250 | - final PrintJob job = _newPrintJob(PrintJob( | 251 | + final job = _newPrintJob(PrintJob( |
251 | onPageRasterized: StreamController<PdfRaster>(), | 252 | onPageRasterized: StreamController<PdfRaster>(), |
252 | )); | 253 | )); |
253 | 254 | ||
254 | - final Map<String, dynamic> params = <String, dynamic>{ | 255 | + final params = <String, dynamic>{ |
255 | 'doc': Uint8List.fromList(document), | 256 | 'doc': Uint8List.fromList(document), |
256 | 'pages': pages, | 257 | 'pages': pages, |
257 | 'scale': dpi / PdfPageFormat.inch, | 258 | 'scale': dpi / PdfPageFormat.inch, |
@@ -10,7 +10,9 @@ import 'printing.dart'; | @@ -10,7 +10,9 @@ import 'printing.dart'; | ||
10 | import 'printing_info.dart'; | 10 | import 'printing_info.dart'; |
11 | import 'raster.dart'; | 11 | import 'raster.dart'; |
12 | 12 | ||
13 | +/// Flutter widget that uses the rasterized pdf pages to display a document. | ||
13 | class PdfPreview extends StatefulWidget { | 14 | class PdfPreview extends StatefulWidget { |
15 | + /// Show a pdf document built on demand | ||
14 | const PdfPreview({ | 16 | const PdfPreview({ |
15 | Key key, | 17 | Key key, |
16 | @required this.build, | 18 | @required this.build, |
@@ -26,26 +28,37 @@ class PdfPreview extends StatefulWidget { | @@ -26,26 +28,37 @@ class PdfPreview extends StatefulWidget { | ||
26 | this.onShared, | 28 | this.onShared, |
27 | }) : super(key: key); | 29 | }) : super(key: key); |
28 | 30 | ||
31 | + /// Called when a pdf document is needed | ||
29 | final LayoutCallback build; | 32 | final LayoutCallback build; |
30 | 33 | ||
34 | + /// Pdf page format asked for the first display | ||
31 | final PdfPageFormat initialPageFormat; | 35 | final PdfPageFormat initialPageFormat; |
32 | 36 | ||
37 | + /// Add a button to print the pdf document | ||
33 | final bool allowPrinting; | 38 | final bool allowPrinting; |
34 | 39 | ||
40 | + /// Add a button to share the pdf document | ||
35 | final bool allowSharing; | 41 | final bool allowSharing; |
36 | 42 | ||
43 | + /// Maximum width of the pdf document on screen | ||
37 | final double maxPageWidth; | 44 | final double maxPageWidth; |
38 | 45 | ||
46 | + /// Add a drop-down menu to choose the page format | ||
39 | final bool canChangePageFormat; | 47 | final bool canChangePageFormat; |
40 | 48 | ||
49 | + /// Additionnal actions to add to the widget | ||
41 | final List<PdfPreviewAction> actions; | 50 | final List<PdfPreviewAction> actions; |
42 | 51 | ||
52 | + /// List of page formats the user can choose | ||
43 | final Map<String, PdfPageFormat> pageFormats; | 53 | final Map<String, PdfPageFormat> pageFormats; |
44 | 54 | ||
55 | + /// Called if an error creating the Pdf occured | ||
45 | final Widget Function(BuildContext context) onError; | 56 | final Widget Function(BuildContext context) onError; |
46 | 57 | ||
58 | + /// Called if the user prints the pdf document | ||
47 | final void Function(BuildContext context) onPrinted; | 59 | final void Function(BuildContext context) onPrinted; |
48 | 60 | ||
61 | + /// Called if the user shares the pdf document | ||
49 | final void Function(BuildContext context) onShared; | 62 | final void Function(BuildContext context) onShared; |
50 | 63 | ||
51 | @override | 64 | @override |
@@ -93,7 +106,7 @@ class _PdfPreviewState extends State<PdfPreview> { | @@ -93,7 +106,7 @@ class _PdfPreviewState extends State<PdfPreview> { | ||
93 | }); | 106 | }); |
94 | } | 107 | } |
95 | 108 | ||
96 | - int pageNum = 0; | 109 | + var pageNum = 0; |
97 | await for (final PdfRaster page in Printing.raster(_doc, dpi: dpi)) { | 110 | await for (final PdfRaster page in Printing.raster(_doc, dpi: dpi)) { |
98 | setState(() { | 111 | setState(() { |
99 | if (pages.length <= pageNum) { | 112 | if (pages.length <= pageNum) { |
@@ -111,9 +124,9 @@ class _PdfPreviewState extends State<PdfPreview> { | @@ -111,9 +124,9 @@ class _PdfPreviewState extends State<PdfPreview> { | ||
111 | 124 | ||
112 | @override | 125 | @override |
113 | void initState() { | 126 | void initState() { |
114 | - final Locale locale = | 127 | + final locale = |
115 | WidgetsBinding.instance.window.locale ?? const Locale('en', 'US'); | 128 | WidgetsBinding.instance.window.locale ?? const Locale('en', 'US'); |
116 | - final String cc = locale.countryCode; | 129 | + final cc = locale.countryCode; |
117 | if (cc == 'US' || cc == 'CA' || cc == 'MX') { | 130 | if (cc == 'US' || cc == 'CA' || cc == 'MX') { |
118 | pageFormat = widget.initialPageFormat ?? PdfPageFormat.letter; | 131 | pageFormat = widget.initialPageFormat ?? PdfPageFormat.letter; |
119 | } else { | 132 | } else { |
@@ -150,7 +163,7 @@ class _PdfPreviewState extends State<PdfPreview> { | @@ -150,7 +163,7 @@ class _PdfPreviewState extends State<PdfPreview> { | ||
150 | }); | 163 | }); |
151 | } | 164 | } |
152 | 165 | ||
153 | - final MediaQueryData mq = MediaQuery.of(context); | 166 | + final mq = MediaQuery.of(context); |
154 | dpi = (min(mq.size.width - 16, widget.maxPageWidth ?? double.infinity)) * | 167 | dpi = (min(mq.size.width - 16, widget.maxPageWidth ?? double.infinity)) * |
155 | mq.devicePixelRatio / | 168 | mq.devicePixelRatio / |
156 | pageFormat.width * | 169 | pageFormat.width * |
@@ -177,7 +190,7 @@ class _PdfPreviewState extends State<PdfPreview> { | @@ -177,7 +190,7 @@ class _PdfPreviewState extends State<PdfPreview> { | ||
177 | 190 | ||
178 | Widget _createPreview() { | 191 | Widget _createPreview() { |
179 | if (error != null) { | 192 | if (error != null) { |
180 | - Widget content = _showError(); | 193 | + var content = _showError(); |
181 | assert(() { | 194 | assert(() { |
182 | print(error); | 195 | print(error); |
183 | content = ErrorWidget(error); | 196 | content = ErrorWidget(error); |
@@ -204,7 +217,7 @@ class _PdfPreviewState extends State<PdfPreview> { | @@ -204,7 +217,7 @@ class _PdfPreviewState extends State<PdfPreview> { | ||
204 | 217 | ||
205 | @override | 218 | @override |
206 | Widget build(BuildContext context) { | 219 | Widget build(BuildContext context) { |
207 | - final ThemeData theme = Theme.of(context); | 220 | + final theme = Theme.of(context); |
208 | 221 | ||
209 | final Widget scrollView = Container( | 222 | final Widget scrollView = Container( |
210 | decoration: BoxDecoration( | 223 | decoration: BoxDecoration( |
@@ -224,7 +237,7 @@ class _PdfPreviewState extends State<PdfPreview> { | @@ -224,7 +237,7 @@ class _PdfPreviewState extends State<PdfPreview> { | ||
224 | ), | 237 | ), |
225 | ); | 238 | ); |
226 | 239 | ||
227 | - final List<Widget> actions = <Widget>[]; | 240 | + final actions = <Widget>[]; |
228 | 241 | ||
229 | if (widget.allowPrinting && info.canPrint) { | 242 | if (widget.allowPrinting && info.canPrint) { |
230 | actions.add( | 243 | actions.add( |
@@ -248,9 +261,8 @@ class _PdfPreviewState extends State<PdfPreview> { | @@ -248,9 +261,8 @@ class _PdfPreviewState extends State<PdfPreview> { | ||
248 | } | 261 | } |
249 | 262 | ||
250 | if (widget.canChangePageFormat) { | 263 | if (widget.canChangePageFormat) { |
251 | - final Map<String, PdfPageFormat> _pageFormats = | ||
252 | - widget.pageFormats ?? defaultPageFormats; | ||
253 | - final List<String> keys = _pageFormats.keys.toList(); | 264 | + final _pageFormats = widget.pageFormats ?? defaultPageFormats; |
265 | + final keys = _pageFormats.keys.toList(); | ||
254 | actions.add( | 266 | actions.add( |
255 | DropdownButton<PdfPageFormat>( | 267 | DropdownButton<PdfPageFormat>( |
256 | icon: Icon( | 268 | icon: Icon( |
@@ -261,8 +273,8 @@ class _PdfPreviewState extends State<PdfPreview> { | @@ -261,8 +273,8 @@ class _PdfPreviewState extends State<PdfPreview> { | ||
261 | items: List<DropdownMenuItem<PdfPageFormat>>.generate( | 273 | items: List<DropdownMenuItem<PdfPageFormat>>.generate( |
262 | _pageFormats.length, | 274 | _pageFormats.length, |
263 | (int index) { | 275 | (int index) { |
264 | - final String key = keys[index]; | ||
265 | - final PdfPageFormat val = _pageFormats[key]; | 276 | + final key = keys[index]; |
277 | + final val = _pageFormats[key]; | ||
266 | return DropdownMenuItem<PdfPageFormat>( | 278 | return DropdownMenuItem<PdfPageFormat>( |
267 | child: Text(key), | 279 | child: Text(key), |
268 | value: val, | 280 | value: val, |
@@ -280,7 +292,7 @@ class _PdfPreviewState extends State<PdfPreview> { | @@ -280,7 +292,7 @@ class _PdfPreviewState extends State<PdfPreview> { | ||
280 | } | 292 | } |
281 | 293 | ||
282 | if (widget.actions != null) { | 294 | if (widget.actions != null) { |
283 | - for (final PdfPreviewAction action in widget.actions) { | 295 | + for (final action in widget.actions) { |
284 | actions.add( | 296 | actions.add( |
285 | IconButton( | 297 | IconButton( |
286 | icon: action.icon, | 298 | icon: action.icon, |
@@ -338,7 +350,7 @@ class _PdfPreviewState extends State<PdfPreview> { | @@ -338,7 +350,7 @@ class _PdfPreviewState extends State<PdfPreview> { | ||
338 | } | 350 | } |
339 | 351 | ||
340 | Future<void> _print() async { | 352 | Future<void> _print() async { |
341 | - final bool result = await Printing.layoutPdf(onLayout: widget.build); | 353 | + final result = await Printing.layoutPdf(onLayout: widget.build); |
342 | 354 | ||
343 | if (result && widget.onPrinted != null) { | 355 | if (result && widget.onPrinted != null) { |
344 | widget.onPrinted(context); | 356 | widget.onPrinted(context); |
@@ -349,14 +361,14 @@ class _PdfPreviewState extends State<PdfPreview> { | @@ -349,14 +361,14 @@ class _PdfPreviewState extends State<PdfPreview> { | ||
349 | // Calculate the widget center for iPad sharing popup position | 361 | // Calculate the widget center for iPad sharing popup position |
350 | final RenderBox referenceBox = | 362 | final RenderBox referenceBox = |
351 | shareWidget.currentContext.findRenderObject(); | 363 | shareWidget.currentContext.findRenderObject(); |
352 | - final Offset topLeft = | 364 | + final topLeft = |
353 | referenceBox.localToGlobal(referenceBox.paintBounds.topLeft); | 365 | referenceBox.localToGlobal(referenceBox.paintBounds.topLeft); |
354 | - final Offset bottomRight = | 366 | + final bottomRight = |
355 | referenceBox.localToGlobal(referenceBox.paintBounds.bottomRight); | 367 | referenceBox.localToGlobal(referenceBox.paintBounds.bottomRight); |
356 | - final Rect bounds = Rect.fromPoints(topLeft, bottomRight); | 368 | + final bounds = Rect.fromPoints(topLeft, bottomRight); |
357 | 369 | ||
358 | - final Uint8List bytes = await widget.build(pageFormat); | ||
359 | - final bool result = await Printing.sharePdf(bytes: bytes, bounds: bounds); | 370 | + final bytes = await widget.build(pageFormat); |
371 | + final result = await Printing.sharePdf(bytes: bytes, bounds: bounds); | ||
360 | 372 | ||
361 | if (result && widget.onShared != null) { | 373 | if (result && widget.onShared != null) { |
362 | widget.onShared(context); | 374 | widget.onShared(context); |
@@ -374,7 +386,7 @@ class _PdfPreviewPage extends StatelessWidget { | @@ -374,7 +386,7 @@ class _PdfPreviewPage extends StatelessWidget { | ||
374 | 386 | ||
375 | @override | 387 | @override |
376 | Widget build(BuildContext context) { | 388 | Widget build(BuildContext context) { |
377 | - final PdfRasterImage im = PdfRasterImage(page); | 389 | + final im = PdfRasterImage(page); |
378 | 390 | ||
379 | return Container( | 391 | return Container( |
380 | margin: const EdgeInsets.only( | 392 | margin: const EdgeInsets.only( |
@@ -410,12 +422,17 @@ typedef OnPdfPreviewActionPressed = void Function( | @@ -410,12 +422,17 @@ typedef OnPdfPreviewActionPressed = void Function( | ||
410 | PdfPageFormat pageFormat, | 422 | PdfPageFormat pageFormat, |
411 | ); | 423 | ); |
412 | 424 | ||
425 | +/// Action to add the the [PdfPreview] widget | ||
413 | class PdfPreviewAction { | 426 | class PdfPreviewAction { |
427 | + /// Represents an icon to add to [PdfPreview] | ||
414 | const PdfPreviewAction({ | 428 | const PdfPreviewAction({ |
415 | @required this.icon, | 429 | @required this.icon, |
416 | @required this.onPressed, | 430 | @required this.onPressed, |
417 | }) : assert(icon != null); | 431 | }) : assert(icon != null); |
418 | 432 | ||
433 | + /// The icon to display | ||
419 | final Icon icon; | 434 | final Icon icon; |
435 | + | ||
436 | + /// The callback called when the user tap on the icon | ||
420 | final OnPdfPreviewActionPressed onPressed; | 437 | final OnPdfPreviewActionPressed onPressed; |
421 | } | 438 | } |
1 | +/* | ||
2 | + * Copyright (C) 2017, David PHAM-VAN <dev.nfet.net@gmail.com> | ||
3 | + * | ||
4 | + * Licensed under the Apache License, Version 2.0 (the "License"); | ||
5 | + * you may not use this file except in compliance with the License. | ||
6 | + * You may obtain a copy of the License at | ||
7 | + * | ||
8 | + * http://www.apache.org/licenses/LICENSE-2.0 | ||
9 | + * | ||
10 | + * Unless required by applicable law or agreed to in writing, software | ||
11 | + * distributed under the License is distributed on an "AS IS" BASIS, | ||
12 | + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. | ||
13 | + * See the License for the specific language governing permissions and | ||
14 | + * limitations under the License. | ||
15 | + */ | ||
16 | + | ||
17 | +/// ignore_for_file: public_member_api_docs | ||
18 | + | ||
1 | @JS() | 19 | @JS() |
2 | library pdf.js; | 20 | library pdf.js; |
3 | 21 |
@@ -20,7 +20,9 @@ import 'dart:typed_data'; | @@ -20,7 +20,9 @@ import 'dart:typed_data'; | ||
20 | import 'callback.dart'; | 20 | import 'callback.dart'; |
21 | import 'raster.dart'; | 21 | import 'raster.dart'; |
22 | 22 | ||
23 | +/// Represents a print job to communicate with the platform implementation | ||
23 | class PrintJob { | 24 | class PrintJob { |
25 | + /// Create a print job | ||
24 | PrintJob({ | 26 | PrintJob({ |
25 | this.onLayout, | 27 | this.onLayout, |
26 | this.onHtmlRendered, | 28 | this.onHtmlRendered, |
@@ -28,10 +30,18 @@ class PrintJob { | @@ -28,10 +30,18 @@ class PrintJob { | ||
28 | this.onPageRasterized, | 30 | this.onPageRasterized, |
29 | }); | 31 | }); |
30 | 32 | ||
33 | + /// Callback used when calling Printing.layoutPdf() | ||
31 | final LayoutCallback onLayout; | 34 | final LayoutCallback onLayout; |
35 | + | ||
36 | + /// Callback used when calling Printing.convertHtml() | ||
32 | final Completer<Uint8List> onHtmlRendered; | 37 | final Completer<Uint8List> onHtmlRendered; |
38 | + | ||
39 | + /// Future triggered when the job is done | ||
33 | final Completer<bool> onCompleted; | 40 | final Completer<bool> onCompleted; |
41 | + | ||
42 | + /// Stream of rasterized pages | ||
34 | final StreamController<PdfRaster> onPageRasterized; | 43 | final StreamController<PdfRaster> onPageRasterized; |
35 | 44 | ||
45 | + /// The Job number | ||
36 | int index; | 46 | int index; |
37 | } | 47 | } |
@@ -36,6 +36,7 @@ import 'callback.dart'; | @@ -36,6 +36,7 @@ import 'callback.dart'; | ||
36 | import 'interface.dart'; | 36 | import 'interface.dart'; |
37 | import 'printing_info.dart'; | 37 | import 'printing_info.dart'; |
38 | 38 | ||
39 | +/// Print plugin targetting Flutter on the Web | ||
39 | class PrintingPlugin extends PrintingPlatform { | 40 | class PrintingPlugin extends PrintingPlatform { |
40 | /// Registers this class as the default instance of [PrintingPlugin]. | 41 | /// Registers this class as the default instance of [PrintingPlugin]. |
41 | static void registerWith(Registrar registrar) { | 42 | static void registerWith(Registrar registrar) { |
@@ -66,35 +67,34 @@ class PrintingPlugin extends PrintingPlatform { | @@ -66,35 +67,34 @@ class PrintingPlugin extends PrintingPlatform { | ||
66 | String name, | 67 | String name, |
67 | PdfPageFormat format, | 68 | PdfPageFormat format, |
68 | ) async { | 69 | ) async { |
69 | - final Uint8List result = await onLayout(format); | 70 | + final result = await onLayout(format); |
70 | 71 | ||
71 | if (result == null || result.isEmpty) { | 72 | if (result == null || result.isEmpty) { |
72 | return false; | 73 | return false; |
73 | } | 74 | } |
74 | 75 | ||
75 | - final bool isChrome = js.context['chrome'] != null; | ||
76 | - final bool isSafari = js.context['safari'] != null; | 76 | + final isChrome = js.context['chrome'] != null; |
77 | + final isSafari = js.context['safari'] != null; | ||
77 | // Maybe Firefox 75 will support iframe printing | 78 | // Maybe Firefox 75 will support iframe printing |
78 | // https://bugzilla.mozilla.org/show_bug.cgi?id=911444 | 79 | // https://bugzilla.mozilla.org/show_bug.cgi?id=911444 |
79 | 80 | ||
80 | if (!isChrome && !isSafari) { | 81 | if (!isChrome && !isSafari) { |
81 | - final String pr = 'data:application/pdf;base64,${base64.encode(result)}'; | 82 | + final pr = 'data:application/pdf;base64,${base64.encode(result)}'; |
82 | final html.Window win = js.context['window']; | 83 | final html.Window win = js.context['window']; |
83 | win.open(pr, name); | 84 | win.open(pr, name); |
84 | 85 | ||
85 | return true; | 86 | return true; |
86 | } | 87 | } |
87 | 88 | ||
88 | - final Completer<bool> completer = Completer<bool>(); | ||
89 | - final html.Blob pdfFile = html.Blob( | 89 | + final completer = Completer<bool>(); |
90 | + final pdfFile = html.Blob( | ||
90 | <Uint8List>[Uint8List.fromList(result)], | 91 | <Uint8List>[Uint8List.fromList(result)], |
91 | 'application/pdf', | 92 | 'application/pdf', |
92 | ); | 93 | ); |
93 | - final String pdfUrl = html.Url.createObjectUrl(pdfFile); | 94 | + final pdfUrl = html.Url.createObjectUrl(pdfFile); |
94 | final html.HtmlDocument doc = js.context['document']; | 95 | final html.HtmlDocument doc = js.context['document']; |
95 | 96 | ||
96 | - final html.Element frame = | ||
97 | - doc.getElementById(_frameId) ?? doc.createElement('iframe'); | 97 | + final frame = doc.getElementById(_frameId) ?? doc.createElement('iframe'); |
98 | frame.setAttribute( | 98 | frame.setAttribute( |
99 | 'style', | 99 | 'style', |
100 | 'visibility: hidden; height: 0; width: 0; position: absolute;', | 100 | 'visibility: hidden; height: 0; width: 0; position: absolute;', |
@@ -126,11 +126,11 @@ class PrintingPlugin extends PrintingPlatform { | @@ -126,11 +126,11 @@ class PrintingPlugin extends PrintingPlatform { | ||
126 | String filename, | 126 | String filename, |
127 | Rect bounds, | 127 | Rect bounds, |
128 | ) async { | 128 | ) async { |
129 | - final html.Blob pdfFile = html.Blob( | 129 | + final pdfFile = html.Blob( |
130 | <Uint8List>[Uint8List.fromList(bytes)], | 130 | <Uint8List>[Uint8List.fromList(bytes)], |
131 | 'application/pdf', | 131 | 'application/pdf', |
132 | ); | 132 | ); |
133 | - final String pdfUrl = html.Url.createObjectUrl(pdfFile); | 133 | + final pdfUrl = html.Url.createObjectUrl(pdfFile); |
134 | final html.HtmlDocument doc = js.context['document']; | 134 | final html.HtmlDocument doc = js.context['document']; |
135 | final html.AnchorElement link = doc.createElement('a'); | 135 | final html.AnchorElement link = doc.createElement('a'); |
136 | link.href = pdfUrl; | 136 | link.href = pdfUrl; |
@@ -171,23 +171,23 @@ class PrintingPlugin extends PrintingPlatform { | @@ -171,23 +171,23 @@ class PrintingPlugin extends PrintingPlatform { | ||
171 | List<int> pages, | 171 | List<int> pages, |
172 | double dpi, | 172 | double dpi, |
173 | ) async* { | 173 | ) async* { |
174 | - final PdfJsDocLoader t = PdfJs.getDocument(Settings()..data = document); | 174 | + final t = PdfJs.getDocument(Settings()..data = document); |
175 | 175 | ||
176 | - final PdfJsDoc d = await promiseToFuture(t.promise); | ||
177 | - final int numPages = d.numPages; | 176 | + final d = await promiseToFuture<PdfJsDoc>(t.promise); |
177 | + final numPages = d.numPages; | ||
178 | 178 | ||
179 | final html.CanvasElement canvas = | 179 | final html.CanvasElement canvas = |
180 | js.context['document'].createElement('canvas'); | 180 | js.context['document'].createElement('canvas'); |
181 | final html.CanvasRenderingContext2D context = canvas.getContext('2d'); | 181 | final html.CanvasRenderingContext2D context = canvas.getContext('2d'); |
182 | 182 | ||
183 | - for (int i = 0; i < numPages; i++) { | ||
184 | - final PdfJsPage page = await promiseToFuture(d.getPage(i + 1)); | ||
185 | - final PdfJsViewport viewport = page.getViewport(Settings()..scale = 1.5); | 183 | + for (var i = 0; i < numPages; i++) { |
184 | + final page = await promiseToFuture<PdfJsPage>(d.getPage(i + 1)); | ||
185 | + final viewport = page.getViewport(Settings()..scale = 1.5); | ||
186 | 186 | ||
187 | canvas.height = viewport.height.toInt(); | 187 | canvas.height = viewport.height.toInt(); |
188 | canvas.width = viewport.width.toInt(); | 188 | canvas.width = viewport.width.toInt(); |
189 | 189 | ||
190 | - final Settings renderContext = Settings() | 190 | + final renderContext = Settings() |
191 | ..canvasContext = context | 191 | ..canvasContext = context |
192 | ..viewport = viewport; | 192 | ..viewport = viewport; |
193 | 193 | ||
@@ -197,10 +197,10 @@ class PrintingPlugin extends PrintingPlatform { | @@ -197,10 +197,10 @@ class PrintingPlugin extends PrintingPlatform { | ||
197 | // context.getImageData(0, 0, canvas.width, canvas.height).data; | 197 | // context.getImageData(0, 0, canvas.width, canvas.height).data; |
198 | 198 | ||
199 | // Convert the image to PNG | 199 | // Convert the image to PNG |
200 | - final Completer<void> completer = Completer<void>(); | ||
201 | - final html.Blob blob = await canvas.toBlob(); | ||
202 | - final BytesBuilder data = BytesBuilder(); | ||
203 | - final html.FileReader r = FileReader(); | 200 | + final completer = Completer<void>(); |
201 | + final blob = await canvas.toBlob(); | ||
202 | + final data = BytesBuilder(); | ||
203 | + final r = FileReader(); | ||
204 | r.readAsArrayBuffer(blob); | 204 | r.readAsArrayBuffer(blob); |
205 | r.onLoadEnd.listen( | 205 | r.onLoadEnd.listen( |
206 | (ProgressEvent e) { | 206 | (ProgressEvent e) { |
@@ -233,7 +233,7 @@ class _WebPdfRaster extends PdfRaster { | @@ -233,7 +233,7 @@ class _WebPdfRaster extends PdfRaster { | ||
233 | @override | 233 | @override |
234 | Uint8List get pixels { | 234 | Uint8List get pixels { |
235 | if (_pixels == null) { | 235 | if (_pixels == null) { |
236 | - final im.Image img = asImage(); | 236 | + final img = asImage(); |
237 | _pixels = img.data.buffer.asUint8List(); | 237 | _pixels = img.data.buffer.asUint8List(); |
238 | } | 238 | } |
239 | 239 | ||
@@ -242,7 +242,7 @@ class _WebPdfRaster extends PdfRaster { | @@ -242,7 +242,7 @@ class _WebPdfRaster extends PdfRaster { | ||
242 | 242 | ||
243 | @override | 243 | @override |
244 | Future<Image> toImage() { | 244 | Future<Image> toImage() { |
245 | - final Completer<Image> comp = Completer<Image>(); | 245 | + final comp = Completer<Image>(); |
246 | decodeImageFromPixels( | 246 | decodeImageFromPixels( |
247 | png, | 247 | png, |
248 | width, | 248 | width, |
@@ -44,7 +44,7 @@ class PdfRaster { | @@ -44,7 +44,7 @@ class PdfRaster { | ||
44 | 44 | ||
45 | /// Decode RGBA raw image to dart:ui Image | 45 | /// Decode RGBA raw image to dart:ui Image |
46 | Future<ui.Image> toImage() { | 46 | Future<ui.Image> toImage() { |
47 | - final Completer<ui.Image> comp = Completer<ui.Image>(); | 47 | + final comp = Completer<ui.Image>(); |
48 | ui.decodeImageFromPixels( | 48 | ui.decodeImageFromPixels( |
49 | pixels, | 49 | pixels, |
50 | width, | 50 | width, |
@@ -57,9 +57,8 @@ class PdfRaster { | @@ -57,9 +57,8 @@ class PdfRaster { | ||
57 | 57 | ||
58 | /// Convert to a PNG image | 58 | /// Convert to a PNG image |
59 | Future<Uint8List> toPng() async { | 59 | Future<Uint8List> toPng() async { |
60 | - final ui.Image image = await toImage(); | ||
61 | - final ByteData data = | ||
62 | - await image.toByteData(format: ui.ImageByteFormat.png); | 60 | + final image = await toImage(); |
61 | + final data = await image.toByteData(format: ui.ImageByteFormat.png); | ||
63 | return data.buffer.asUint8List(); | 62 | return data.buffer.asUint8List(); |
64 | } | 63 | } |
65 | 64 | ||
@@ -78,7 +77,7 @@ class PdfRasterImage extends ImageProvider<PdfRaster> { | @@ -78,7 +77,7 @@ class PdfRasterImage extends ImageProvider<PdfRaster> { | ||
78 | final PdfRaster raster; | 77 | final PdfRaster raster; |
79 | 78 | ||
80 | Future<ImageInfo> _loadAsync() async { | 79 | Future<ImageInfo> _loadAsync() async { |
81 | - final ui.Image uiImage = await raster.toImage(); | 80 | + final uiImage = await raster.toImage(); |
82 | return ImageInfo(image: uiImage, scale: 1); | 81 | return ImageInfo(image: uiImage, scale: 1); |
83 | } | 82 | } |
84 | 83 |
@@ -15,7 +15,6 @@ | @@ -15,7 +15,6 @@ | ||
15 | */ | 15 | */ |
16 | 16 | ||
17 | import 'dart:async'; | 17 | import 'dart:async'; |
18 | -import 'dart:typed_data'; | ||
19 | import 'dart:ui' as ui; | 18 | import 'dart:ui' as ui; |
20 | 19 | ||
21 | import 'package:flutter/material.dart'; | 20 | import 'package:flutter/material.dart'; |
@@ -35,10 +34,9 @@ Future<PdfImage> wrapWidget( | @@ -35,10 +34,9 @@ Future<PdfImage> wrapWidget( | ||
35 | 34 | ||
36 | final RenderRepaintBoundary wrappedWidget = | 35 | final RenderRepaintBoundary wrappedWidget = |
37 | key.currentContext.findRenderObject(); | 36 | key.currentContext.findRenderObject(); |
38 | - final ui.Image image = await wrappedWidget.toImage(pixelRatio: pixelRatio); | ||
39 | - final ByteData byteData = | ||
40 | - await image.toByteData(format: ui.ImageByteFormat.rawRgba); | ||
41 | - final Uint8List imageData = byteData.buffer.asUint8List(); | 37 | + final image = await wrappedWidget.toImage(pixelRatio: pixelRatio); |
38 | + final byteData = await image.toByteData(format: ui.ImageByteFormat.rawRgba); | ||
39 | + final imageData = byteData.buffer.asUint8List(); | ||
42 | return PdfImage(document, | 40 | return PdfImage(document, |
43 | image: imageData, width: image.width, height: image.height); | 41 | image: imageData, width: image.width, height: image.height); |
44 | } | 42 | } |
@@ -15,12 +15,10 @@ | @@ -15,12 +15,10 @@ | ||
15 | */ | 15 | */ |
16 | 16 | ||
17 | import 'dart:io'; | 17 | import 'dart:io'; |
18 | -import 'dart:typed_data'; | ||
19 | 18 | ||
20 | import 'package:flutter/services.dart'; | 19 | import 'package:flutter/services.dart'; |
21 | import 'package:flutter/widgets.dart'; | 20 | import 'package:flutter/widgets.dart'; |
22 | import 'package:flutter_test/flutter_test.dart'; | 21 | import 'package:flutter_test/flutter_test.dart'; |
23 | -import 'package:pdf/pdf.dart'; | ||
24 | import 'package:pdf/widgets.dart' as pw; | 22 | import 'package:pdf/widgets.dart' as pw; |
25 | import 'package:printing/printing.dart'; | 23 | import 'package:printing/printing.dart'; |
26 | 24 | ||
@@ -28,9 +26,8 @@ pw.Document doc; | @@ -28,9 +26,8 @@ pw.Document doc; | ||
28 | pw.Font ttf; | 26 | pw.Font ttf; |
29 | 27 | ||
30 | void main() { | 28 | void main() { |
31 | - final String path = | ||
32 | - Directory.current.path.split('/').last == 'test' ? '..' : '.'; | ||
33 | - const MethodChannel channel = MethodChannel('net.nfet.printing'); | 29 | + final path = Directory.current.path.split('/').last == 'test' ? '..' : '.'; |
30 | + const channel = MethodChannel('net.nfet.printing'); | ||
34 | TestWidgetsFlutterBinding.ensureInitialized(); | 31 | TestWidgetsFlutterBinding.ensureInitialized(); |
35 | 32 | ||
36 | setUp(() { | 33 | setUp(() { |
@@ -49,7 +46,7 @@ void main() { | @@ -49,7 +46,7 @@ void main() { | ||
49 | }); | 46 | }); |
50 | 47 | ||
51 | test('pdfImageFromImageProvider(FileImage)', () async { | 48 | test('pdfImageFromImageProvider(FileImage)', () async { |
52 | - final PdfImage image = await pdfImageFromImageProvider( | 49 | + final image = await pdfImageFromImageProvider( |
53 | pdf: doc.document, image: FileImage(File('$path/example.png'))); | 50 | pdf: doc.document, image: FileImage(File('$path/example.png'))); |
54 | 51 | ||
55 | doc.addPage( | 52 | doc.addPage( |
@@ -66,14 +63,13 @@ void main() { | @@ -66,14 +63,13 @@ void main() { | ||
66 | setUpAll(() { | 63 | setUpAll(() { |
67 | pw.Document.debug = true; | 64 | pw.Document.debug = true; |
68 | pw.RichText.debug = true; | 65 | pw.RichText.debug = true; |
69 | - final Uint8List fontData = | ||
70 | - File('$path/../pdf/open-sans.ttf').readAsBytesSync(); | 66 | + final fontData = File('$path/../pdf/open-sans.ttf').readAsBytesSync(); |
71 | ttf = pw.Font.ttf(fontData.buffer.asByteData()); | 67 | ttf = pw.Font.ttf(fontData.buffer.asByteData()); |
72 | doc = pw.Document(); | 68 | doc = pw.Document(); |
73 | }); | 69 | }); |
74 | 70 | ||
75 | tearDownAll(() { | 71 | tearDownAll(() { |
76 | - final File file = File('printing.pdf'); | 72 | + final file = File('printing.pdf'); |
77 | file.writeAsBytesSync(doc.save()); | 73 | file.writeAsBytesSync(doc.save()); |
78 | }); | 74 | }); |
79 | } | 75 | } |
@@ -23,7 +23,7 @@ void main() { | @@ -23,7 +23,7 @@ void main() { | ||
23 | }); | 23 | }); |
24 | 24 | ||
25 | test('PrintingInfo', () async { | 25 | test('PrintingInfo', () async { |
26 | - const PrintingInfo info = PrintingInfo.unavailable; | 26 | + const info = PrintingInfo.unavailable; |
27 | expect(info.canConvertHtml, false); | 27 | expect(info.canConvertHtml, false); |
28 | expect(info.directPrint, false); | 28 | expect(info.directPrint, false); |
29 | expect(info.dynamicLayout, false); | 29 | expect(info.dynamicLayout, false); |
@@ -36,7 +36,7 @@ void main() { | @@ -36,7 +36,7 @@ void main() { | ||
36 | }); | 36 | }); |
37 | 37 | ||
38 | test('PrintingInfo.fromMap', () async { | 38 | test('PrintingInfo.fromMap', () async { |
39 | - final PrintingInfo info = PrintingInfo.fromMap( | 39 | + final info = PrintingInfo.fromMap( |
40 | <dynamic, dynamic>{ | 40 | <dynamic, dynamic>{ |
41 | 'canPrint': true, | 41 | 'canPrint': true, |
42 | }, | 42 | }, |
@@ -26,12 +26,12 @@ import 'package:printing/src/interface.dart'; | @@ -26,12 +26,12 @@ import 'package:printing/src/interface.dart'; | ||
26 | void main() { | 26 | void main() { |
27 | setUp(() { | 27 | setUp(() { |
28 | TestWidgetsFlutterBinding.ensureInitialized(); | 28 | TestWidgetsFlutterBinding.ensureInitialized(); |
29 | - final MockPrinting mock = MockPrinting(); | 29 | + final mock = MockPrinting(); |
30 | PrintingPlatform.instance = mock; | 30 | PrintingPlatform.instance = mock; |
31 | }); | 31 | }); |
32 | 32 | ||
33 | test('info', () async { | 33 | test('info', () async { |
34 | - final PrintingInfo info = await Printing.info(); | 34 | + final info = await Printing.info(); |
35 | expect(info, null); | 35 | expect(info, null); |
36 | }); | 36 | }); |
37 | 37 |
@@ -27,7 +27,7 @@ void main() { | @@ -27,7 +27,7 @@ void main() { | ||
27 | }); | 27 | }); |
28 | 28 | ||
29 | test('PdfRaster', () async { | 29 | test('PdfRaster', () async { |
30 | - final PdfRaster raster = | 30 | + final raster = |
31 | PdfRaster(10, 10, Uint8List.fromList(List<int>.filled(10 * 10 * 4, 0))); | 31 | PdfRaster(10, 10, Uint8List.fromList(List<int>.filled(10 * 10 * 4, 0))); |
32 | expect(raster.toString(), 'Image 10x10 400 bytes'); | 32 | expect(raster.toString(), 'Image 10x10 400 bytes'); |
33 | expect(await raster.toImage(), isA<ui.Image>()); | 33 | expect(await raster.toImage(), isA<ui.Image>()); |
@@ -35,7 +35,7 @@ void main() { | @@ -35,7 +35,7 @@ void main() { | ||
35 | }); | 35 | }); |
36 | 36 | ||
37 | testWidgets('PdfRasterImage', (WidgetTester tester) async { | 37 | testWidgets('PdfRasterImage', (WidgetTester tester) async { |
38 | - final PdfRaster raster = | 38 | + final raster = |
39 | PdfRaster(10, 10, Uint8List.fromList(List<int>.filled(10 * 10 * 4, 0))); | 39 | PdfRaster(10, 10, Uint8List.fromList(List<int>.filled(10 * 10 * 4, 0))); |
40 | 40 | ||
41 | await tester.pumpWidget(Image(image: PdfRasterImage(raster))); | 41 | await tester.pumpWidget(Image(image: PdfRasterImage(raster))); |
-
Please register or login to post a comment