Implemented Null Safety.

This commit is contained in:
Phani Pavan K
2021-02-18 15:41:13 +05:30
parent 56f5210712
commit 0e792ea48f
10 changed files with 402 additions and 39 deletions

View File

@@ -1,3 +1,7 @@
##0.1.0-nullsafety-0
- Implemented Sound Null Safety 💪
## 0.0.1 ## 0.0.1
* TODO: Describe initial release. - Inported code from the parent package, https://github.com/mmcc007/modal_progress_hud

149
README.md
View File

@@ -1,15 +1,144 @@
# modal_progress_hud_nsn # modal_progress_hud
A new flutter plugin project. A simple widget wrapper to enable modal progress HUD (a modal progress indicator, HUD = Heads Up Display)
## Getting Started [![pub package](https://img.shields.io/pub/v/modal_progress_hud_nsn.svg)](https://pub.dartlang.org/packages/modal_progress_hud_nsn)
This project is a starting point for a Flutter Inspired by [this](https://codingwithjoe.com/flutter-how-to-build-a-modal-progress-indicator/) article.
[plug-in package](https://flutter.dev/developing-packages/),
a specialized package that includes platform-specific implementation code for
Android and/or iOS.
For help getting started with Flutter, view our A fork of [this](https://github.com/mmcc007/modal_progress_hud) with support for Null Safety.
[online documentation](https://flutter.dev/docs), which offers tutorials,
samples, guidance on mobile development, and a full API reference.
## Demo
![Demo](https://raw.githubusercontent.com/mmcc007/modal_progress_hud/master/modal_progress_hud.gif)
_See example for details_
## Usage
Add the package to your `pubspec.yml` file.
```yml
dependencies:
modal_progress_hud_nsn: ^0.1.0-nullsafety-0
```
Next, import the library into your widget.
```dart
import 'package:modal_progress_hud/modal_progress_hud.dart';
```
Now, all you have to do is simply wrap your widget as a child of `ModalProgressHUD`, typically a form, together with a boolean that is maintained in local state.
```dart
...
bool _saving = false
...
@override
Widget build(BuildContext context) {
return Scaffold(
body: ModalProgressHUD(child: Container(
Form(...)
), inAsyncCall: _saving),
);
}
```
## Options
The current parameters are customizable in the constructor
```dart
ModalProgressHUD(
@required inAsyncCall: bool,
@required child: Widget,
opacity: double,
color: Color,
progressIndicator: CircularProgressIndicator,
offset: double
dismissible: bool,
);
```
## Example
Here is an example app that demonstrates the usage.
1. On initial load, `_saving` is false which causes your child widget to display
2. When the form is submitted, `_saving` is set to true, which will display the modal
3. Once the async call is complete, `_saving` is set back to false, hiding the modal
```dart
class SettingsPage extends StatefulWidget {
@override
_SettingsPageState createState() => new _SettingsPageState();
}
class _SettingsPageState extends State<SettingsPage> {
bool _saving = false;
void _submit() {
setState(() {
_saving = true;
});
//Simulate a service call
print('submitting to backend...');
new Future.delayed(new Duration(seconds: 4), () {
setState(() {
_saving = false;
});
});
}
Widget _buildWidget() {
return new Form(
child: new Column(
children: [
new SwitchListTile(
title: const Text('Bedroom'),
value: _bedroom,
onChanged: (bool value) {
setState(() {
_bedroom = value;
});
},
secondary: const Icon(Icons.hotel),
),
new RaisedButton(
onPressed: _submit,
child: new Text('Save'),
),
],
),
);
}
@override
Widget build(BuildContext context) {
return new Scaffold(
appBar: new AppBar(
title: new Text('Flutter Progress Indicator Demo'),
backgroundColor: Colors.blue,
),
body: ModalProgressHUD(child: _buildWidget(), inAsyncCall: _saving),
);
}
}
```
Update: See this [article](https://medium.com/@nocnoc/the-secret-to-async-validation-on-flutter-forms-4b273c667c03) on Medium about async form validation
See the [example application](https://github.com/kphanipavan/modal_progress_hud_nsn/tree/master/example) source
for a complete sample app using the modal progress HUD. Included in the
example is a method for using a form's validators while making async
calls (see [flutter/issues/9688](https://github.com/flutter/flutter/issues/9688) for details).
### Issues and feedback
Please file [issues](https://github.com/kphanipavan/modal_progress_hud_nsn/issues/new)
to send feedback or report a bug. Thank you!

View File

@@ -22,7 +22,7 @@ class MyApp extends StatelessWidget {
class LoginPage extends StatefulWidget { class LoginPage extends StatefulWidget {
final VoidCallback _onSignIn; final VoidCallback _onSignIn;
LoginPage({@required onSignIn}) LoginPage({required onSignIn})
: assert(onSignIn != null), : assert(onSignIn != null),
_onSignIn = onSignIn; _onSignIn = onSignIn;
@@ -40,13 +40,13 @@ class _LoginPageState extends State<LoginPage> {
bool _isInvalidAsyncUser = false; // managed after response from server bool _isInvalidAsyncUser = false; // managed after response from server
bool _isInvalidAsyncPass = false; // managed after response from server bool _isInvalidAsyncPass = false; // managed after response from server
String _username; String? _username;
String _password; String? _password;
bool _isLoggedIn = false; bool _isLoggedIn = false;
// validate user name // validate user name
String _validateUserName(String userName) { String? _validateUserName(String? userName) {
if (userName.length < 8) { if (userName!.length < 8) {
return 'Username must be at least 8 characters'; return 'Username must be at least 8 characters';
} }
@@ -60,8 +60,8 @@ class _LoginPageState extends State<LoginPage> {
} }
// validate password // validate password
String _validatePassword(String password) { String? _validatePassword(String? password) {
if (password.length < 8) { if (password!.length < 8) {
return 'Password must be at least 8 characters'; return 'Password must be at least 8 characters';
} }
@@ -75,8 +75,8 @@ class _LoginPageState extends State<LoginPage> {
} }
void _submit() { void _submit() {
if (_loginFormKey.currentState.validate()) { if (_loginFormKey.currentState!.validate()) {
_loginFormKey.currentState.save(); _loginFormKey.currentState!.save();
// dismiss keyboard during async call // dismiss keyboard during async call
FocusScope.of(context).requestFocus(new FocusNode()); FocusScope.of(context).requestFocus(new FocusNode());
@@ -154,7 +154,7 @@ class _LoginPageState extends State<LoginPage> {
key: Key('username'), key: Key('username'),
decoration: InputDecoration( decoration: InputDecoration(
hintText: 'enter username', labelText: 'User Name'), hintText: 'enter username', labelText: 'User Name'),
style: TextStyle(fontSize: 20.0, color: textTheme.button.color), style: TextStyle(fontSize: 20.0, color: textTheme.button!.color),
validator: _validateUserName, validator: _validateUserName,
onSaved: (value) => _username = value, onSaved: (value) => _username = value,
), ),
@@ -166,7 +166,7 @@ class _LoginPageState extends State<LoginPage> {
obscureText: true, obscureText: true,
decoration: InputDecoration( decoration: InputDecoration(
hintText: 'enter password', labelText: 'Password'), hintText: 'enter password', labelText: 'Password'),
style: TextStyle(fontSize: 20.0, color: textTheme.button.color), style: TextStyle(fontSize: 20.0, color: textTheme.button!.color),
validator: _validatePassword, validator: _validatePassword,
onSaved: (value) => _password = value, onSaved: (value) => _password = value,
), ),

View File

@@ -157,5 +157,5 @@ packages:
source: hosted source: hosted
version: "2.1.0" version: "2.1.0"
sdks: sdks:
dart: ">=2.12.0-0.0 <3.0.0" dart: ">=2.12.0 <3.0.0"
flutter: ">=1.20.0" flutter: ">=1.20.0"

View File

@@ -6,7 +6,7 @@ description: Demonstrates how to use the modal_progress_hud_nsn plugin.
publish_to: 'none' # Remove this line if you wish to publish to pub.dev publish_to: 'none' # Remove this line if you wish to publish to pub.dev
environment: environment:
sdk: ">=2.7.0 <3.0.0" sdk: '>=2.12.0 <3.0.0'
dependencies: dependencies:
flutter: flutter:

View File

@@ -19,7 +19,7 @@ void main() {
expect( expect(
find.byWidgetPredicate( find.byWidgetPredicate(
(Widget widget) => widget is Text && (Widget widget) => widget is Text &&
widget.data.startsWith('Running on:'), widget.data!.startsWith('Running on:'),
), ),
findsOneWidget, findsOneWidget,
); );

View File

@@ -27,22 +27,20 @@ class ModalProgressHUD extends StatelessWidget {
final double opacity; final double opacity;
final Color color; final Color color;
final Widget progressIndicator; final Widget progressIndicator;
final Offset offset; final Offset? offset;
final bool dismissible; final bool dismissible;
final Widget child; final Widget child;
ModalProgressHUD({ ModalProgressHUD({
Key key, Key? key,
@required this.inAsyncCall, required this.inAsyncCall,
this.opacity = 0.3, this.opacity = 0.3,
this.color = Colors.grey, this.color = Colors.grey,
this.progressIndicator = const CircularProgressIndicator(), this.progressIndicator = const CircularProgressIndicator(),
this.offset, this.offset,
this.dismissible = false, this.dismissible = false,
@required this.child, required this.child,
}) : assert(child != null), }) : super(key: key);
assert(inAsyncCall != null),
super(key: key);
@override @override
Widget build(BuildContext context) { Widget build(BuildContext context) {
@@ -54,8 +52,8 @@ class ModalProgressHUD extends StatelessWidget {
else { else {
layOutProgressIndicator = Positioned( layOutProgressIndicator = Positioned(
child: progressIndicator, child: progressIndicator,
left: offset.dx, left: offset!.dx,
top: offset.dy, top: offset!.dy,
); );
} }

View File

@@ -1,6 +1,27 @@
# Generated by pub # Generated by pub
# See https://dart.dev/tools/pub/glossary#lockfile # See https://dart.dev/tools/pub/glossary#lockfile
packages: packages:
_fe_analyzer_shared:
dependency: transitive
description:
name: _fe_analyzer_shared
url: "https://pub.dartlang.org"
source: hosted
version: "16.0.0"
analyzer:
dependency: transitive
description:
name: analyzer
url: "https://pub.dartlang.org"
source: hosted
version: "1.0.0"
args:
dependency: transitive
description:
name: args
url: "https://pub.dartlang.org"
source: hosted
version: "2.0.0"
async: async:
dependency: transitive dependency: transitive
description: description:
@@ -29,6 +50,13 @@ packages:
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "1.2.0" version: "1.2.0"
cli_util:
dependency: transitive
description:
name: cli_util
url: "https://pub.dartlang.org"
source: hosted
version: "0.3.0"
clock: clock:
dependency: transitive dependency: transitive
description: description:
@@ -43,6 +71,27 @@ packages:
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "1.15.0" version: "1.15.0"
convert:
dependency: transitive
description:
name: convert
url: "https://pub.dartlang.org"
source: hosted
version: "3.0.0"
coverage:
dependency: transitive
description:
name: coverage
url: "https://pub.dartlang.org"
source: hosted
version: "0.15.2"
crypto:
dependency: transitive
description:
name: crypto
url: "https://pub.dartlang.org"
source: hosted
version: "3.0.0"
fake_async: fake_async:
dependency: transitive dependency: transitive
description: description:
@@ -50,6 +99,13 @@ packages:
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "1.2.0" version: "1.2.0"
file:
dependency: transitive
description:
name: file
url: "https://pub.dartlang.org"
source: hosted
version: "6.1.0"
flutter: flutter:
dependency: "direct main" dependency: "direct main"
description: flutter description: flutter
@@ -60,6 +116,48 @@ packages:
description: flutter description: flutter
source: sdk source: sdk
version: "0.0.0" version: "0.0.0"
glob:
dependency: transitive
description:
name: glob
url: "https://pub.dartlang.org"
source: hosted
version: "2.0.0"
http_multi_server:
dependency: transitive
description:
name: http_multi_server
url: "https://pub.dartlang.org"
source: hosted
version: "2.2.0"
http_parser:
dependency: transitive
description:
name: http_parser
url: "https://pub.dartlang.org"
source: hosted
version: "4.0.0"
io:
dependency: transitive
description:
name: io
url: "https://pub.dartlang.org"
source: hosted
version: "0.3.4"
js:
dependency: transitive
description:
name: js
url: "https://pub.dartlang.org"
source: hosted
version: "0.6.3"
logging:
dependency: transitive
description:
name: logging
url: "https://pub.dartlang.org"
source: hosted
version: "1.0.0"
matcher: matcher:
dependency: transitive dependency: transitive
description: description:
@@ -74,6 +172,27 @@ packages:
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "1.3.0" version: "1.3.0"
mime:
dependency: transitive
description:
name: mime
url: "https://pub.dartlang.org"
source: hosted
version: "1.0.0"
node_preamble:
dependency: transitive
description:
name: node_preamble
url: "https://pub.dartlang.org"
source: hosted
version: "1.4.13"
package_config:
dependency: transitive
description:
name: package_config
url: "https://pub.dartlang.org"
source: hosted
version: "2.0.0"
path: path:
dependency: transitive dependency: transitive
description: description:
@@ -81,11 +200,74 @@ packages:
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "1.8.0" version: "1.8.0"
pedantic:
dependency: transitive
description:
name: pedantic
url: "https://pub.dartlang.org"
source: hosted
version: "1.10.0"
pool:
dependency: transitive
description:
name: pool
url: "https://pub.dartlang.org"
source: hosted
version: "1.5.0"
pub_semver:
dependency: transitive
description:
name: pub_semver
url: "https://pub.dartlang.org"
source: hosted
version: "2.0.0"
shelf:
dependency: transitive
description:
name: shelf
url: "https://pub.dartlang.org"
source: hosted
version: "1.0.0"
shelf_packages_handler:
dependency: transitive
description:
name: shelf_packages_handler
url: "https://pub.dartlang.org"
source: hosted
version: "2.0.1"
shelf_static:
dependency: transitive
description:
name: shelf_static
url: "https://pub.dartlang.org"
source: hosted
version: "0.2.9+2"
shelf_web_socket:
dependency: transitive
description:
name: shelf_web_socket
url: "https://pub.dartlang.org"
source: hosted
version: "0.2.4"
sky_engine: sky_engine:
dependency: transitive dependency: transitive
description: flutter description: flutter
source: sdk source: sdk
version: "0.0.99" version: "0.0.99"
source_map_stack_trace:
dependency: transitive
description:
name: source_map_stack_trace
url: "https://pub.dartlang.org"
source: hosted
version: "2.1.0"
source_maps:
dependency: transitive
description:
name: source_maps
url: "https://pub.dartlang.org"
source: hosted
version: "0.10.10"
source_span: source_span:
dependency: transitive dependency: transitive
description: description:
@@ -121,6 +303,13 @@ packages:
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "1.2.0" version: "1.2.0"
test:
dependency: "direct dev"
description:
name: test
url: "https://pub.dartlang.org"
source: hosted
version: "1.16.2"
test_api: test_api:
dependency: transitive dependency: transitive
description: description:
@@ -128,6 +317,13 @@ packages:
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "0.2.19" version: "0.2.19"
test_core:
dependency: transitive
description:
name: test_core
url: "https://pub.dartlang.org"
source: hosted
version: "0.3.13"
typed_data: typed_data:
dependency: transitive dependency: transitive
description: description:
@@ -142,6 +338,41 @@ packages:
url: "https://pub.dartlang.org" url: "https://pub.dartlang.org"
source: hosted source: hosted
version: "2.1.0" version: "2.1.0"
vm_service:
dependency: transitive
description:
name: vm_service
url: "https://pub.dartlang.org"
source: hosted
version: "6.0.1"
watcher:
dependency: transitive
description:
name: watcher
url: "https://pub.dartlang.org"
source: hosted
version: "1.0.0"
web_socket_channel:
dependency: transitive
description:
name: web_socket_channel
url: "https://pub.dartlang.org"
source: hosted
version: "1.2.0"
webkit_inspection_protocol:
dependency: transitive
description:
name: webkit_inspection_protocol
url: "https://pub.dartlang.org"
source: hosted
version: "0.7.5"
yaml:
dependency: transitive
description:
name: yaml
url: "https://pub.dartlang.org"
source: hosted
version: "3.0.0"
sdks: sdks:
dart: ">=2.12.0-0.0 <3.0.0" dart: ">=2.12.0 <3.0.0"
flutter: ">=1.20.0" flutter: ">=1.20.0"

View File

@@ -1,11 +1,11 @@
name: modal_progress_hud_nsn name: modal_progress_hud_nsn
description: A modal progress indicator widget with Sound Null Safety. A fork of https://github.com/mmcc007/modal_progress_hud description: A modal progress indicator widget with Sound Null Safety. A fork of https://github.com/mmcc007/modal_progress_hud
version: 0.1.0-nullsafety-0 version: 0.1.0-nullsafety-0
author: Phani Pavan K #author: Phani Pavan K
homepage: homepage: https://github.com/kphanipavan/modal_progress_hud_nsn
environment: environment:
sdk: ">=2.7.0 <3.0.0" sdk: '>=2.12.0 <3.0.0'
flutter: ">=1.20.0" flutter: ">=1.20.0"
dependencies: dependencies:
@@ -15,6 +15,7 @@ dependencies:
dev_dependencies: dev_dependencies:
flutter_test: flutter_test:
sdk: flutter sdk: flutter
test: ^1.16.2
flutter: flutter:
plugin: plugin:

View File

@@ -5,7 +5,7 @@ import 'package:modal_progress_hud_nsn/modal_progress_hud_nsn.dart';
void main() { void main() {
group('Modal Progress HUD', () { group('Modal Progress HUD', () {
Widget sut(bool inAsyncCall, Offset offset) { Widget sut(bool inAsyncCall, Offset? offset) {
return MaterialApp( return MaterialApp(
home: new ModalProgressHUD( home: new ModalProgressHUD(
inAsyncCall: inAsyncCall, inAsyncCall: inAsyncCall,