Skip to content

Commit c36eb2e

Browse files
committed
Initial commit
0 parents  commit c36eb2e

14 files changed

+487
-0
lines changed

.gitattributes

+2
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,2 @@
1+
# Auto detect text files and perform LF normalization
2+
* text=auto

.gitignore

+75
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,75 @@
1+
# Miscellaneous
2+
*.class
3+
*.log
4+
*.pyc
5+
*.swp
6+
.DS_Store
7+
.atom/
8+
.buildlog/
9+
.history
10+
.svn/
11+
12+
# IntelliJ related
13+
*.iml
14+
*.ipr
15+
*.iws
16+
.idea/
17+
18+
# The .vscode folder contains launch configuration and tasks you configure in
19+
# VS Code which you may wish to be included in version control, so this line
20+
# is commented out by default.
21+
#.vscode/
22+
23+
# Flutter/Dart/Pub related
24+
**/doc/api/
25+
.dart_tool/
26+
.flutter-plugins
27+
.flutter-plugins-dependencies
28+
.packages
29+
.pub-cache/
30+
.pub/
31+
build/
32+
33+
# Android related
34+
**/android/**/gradle-wrapper.jar
35+
**/android/.gradle
36+
**/android/captures/
37+
**/android/gradlew
38+
**/android/gradlew.bat
39+
**/android/local.properties
40+
**/android/**/GeneratedPluginRegistrant.java
41+
42+
# iOS/XCode related
43+
**/ios/**/*.mode1v3
44+
**/ios/**/*.mode2v3
45+
**/ios/**/*.moved-aside
46+
**/ios/**/*.pbxuser
47+
**/ios/**/*.perspectivev3
48+
**/ios/**/*sync/
49+
**/ios/**/.sconsign.dblite
50+
**/ios/**/.tags*
51+
**/ios/**/.vagrant/
52+
**/ios/**/DerivedData/
53+
**/ios/**/Icon?
54+
**/ios/**/Pods/
55+
**/ios/**/.symlinks/
56+
**/ios/**/profile
57+
**/ios/**/xcuserdata
58+
**/ios/.generated/
59+
**/ios/Flutter/App.framework
60+
**/ios/Flutter/Flutter.framework
61+
**/ios/Flutter/Flutter.podspec
62+
**/ios/Flutter/Generated.xcconfig
63+
**/ios/Flutter/ephemeral
64+
**/ios/Flutter/app.flx
65+
**/ios/Flutter/app.zip
66+
**/ios/Flutter/flutter_assets/
67+
**/ios/Flutter/flutter_export_environment.sh
68+
**/ios/ServiceDefinitions.json
69+
**/ios/Runner/GeneratedPluginRegistrant.*
70+
71+
# Exceptions to above rules.
72+
!**/ios/**/default.mode1v3
73+
!**/ios/**/default.mode2v3
74+
!**/ios/**/default.pbxuser
75+
!**/ios/**/default.perspectivev3

.metadata

+10
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
# This file tracks properties of this Flutter project.
2+
# Used by Flutter tool to assess capabilities and perform upgrades etc.
3+
#
4+
# This file should be version controlled and should not be manually edited.
5+
6+
version:
7+
revision: 4cc385b4b84ac2f816d939a49ea1f328c4e0b48e
8+
channel: stable
9+
10+
project_type: package

CHANGELOG.md

+3
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
## 0.0.1
2+
3+
* TODO: Describe initial release.

LICENSE

+1
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
TODO: Add your license here.

README.md

+55
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
TODO: Put a short description of the package here that helps potential users
2+
know whether this package might be useful for them.
3+
4+
## Features
5+
6+
TODO: List what your package can do. Maybe include images, gifs, or videos.
7+
8+
## Getting started
9+
10+
TODO: List prerequisites and provide or point to information on how to
11+
start using the package.
12+
13+
## Usage
14+
15+
### Basic Usage
16+
17+
Define your view routes.
18+
19+
```dart
20+
import 'package:view_router/view_router.dart';
21+
22+
final Routes routes = {
23+
'/': (_) => HomePage(),
24+
'/profile': (_) => ProfilePage()
25+
};
26+
```
27+
28+
Create a `ViewRouter` and add to your `MaterialApp` as the `onGenerateRoute` callback.
29+
30+
```dart
31+
32+
class App extends StatelessWidget {
33+
// This widget is the root of your application.
34+
@override
35+
Widget build(BuildContext context) {
36+
return MaterialApp(
37+
title: 'My App',
38+
onGenerateRoute: ViewRouter(routes),
39+
initialRoute: '/',
40+
);
41+
}
42+
}
43+
```
44+
45+
Navigate using the navigator.
46+
47+
```dart
48+
Navigator.of(context).pushNamed('/profile');
49+
```
50+
51+
## Additional information
52+
53+
TODO: Tell users more about the package: where to find more information, how to
54+
contribute to the package, how to file issues, what response they can expect
55+
from the package authors, and more.

analysis_options.yaml

+4
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,4 @@
1+
include: package:flutter_lints/flutter.yaml
2+
3+
# Additional information about this file can be found at
4+
# https://dart.dev/guides/language/analysis-options

lib/parse_route_uri.dart

+78
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
import 'package:flutter/material.dart';
2+
import 'package:view_router/routes.dart';
3+
4+
/// Extract query parameters from a named route and generate
5+
/// the page route, supplying the parameters as arguments.
6+
///
7+
/// Example:
8+
///
9+
/// Initial route settings:
10+
///
11+
/// name: `/profile?id=123`,
12+
/// arguments: `null`
13+
///
14+
/// After:
15+
///
16+
/// name: `/profile`,
17+
/// arguments: `{ id: '123' }`
18+
Route<dynamic>? parseRouteUri(Routes routes, RouteSettings settings) {
19+
final Uri uri = Uri.parse(settings.name ?? '/');
20+
final Map<String, String> params = uri.queryParameters;
21+
22+
final String path = uri.path;
23+
24+
if (routes.containsKey(path)) {
25+
// If the path can be immediately found, return it.
26+
return MaterialPageRoute(
27+
builder: routes[path]!,
28+
settings: settings.copyWith(arguments: params, name: path));
29+
} else {
30+
// Otherwise, the route may not have been found due
31+
// to it containing dynamic parameters. Figure that out here.
32+
33+
// Only get routes that have named parameters.
34+
final routesWithNamedParams = routes.keys
35+
.where((element) => RegExp(r":\w{1,}").hasMatch(element))
36+
.toList();
37+
38+
routesWithNamedParams.sort((a, b) => a.length.compareTo(b.length));
39+
40+
// RegExp(r"^:\w{1,}") for finding named parameters in paths.
41+
final segments = path.split('/').toList();
42+
43+
for (var route in routesWithNamedParams) {
44+
final parts = route.split('/');
45+
46+
if (parts.length != segments.length) {
47+
// Lengths do not match.
48+
continue;
49+
}
50+
51+
bool? matches;
52+
final Map<String, String> namedParams = {};
53+
54+
for (var i in segments.asMap().keys) {
55+
if (matches == false) continue;
56+
57+
final isDynamic = RegExp(r":\w{1,}").hasMatch(parts[i]);
58+
59+
matches = segments[i] == parts[i] || isDynamic;
60+
61+
if (matches && isDynamic) {
62+
final name = parts[i].substring(1);
63+
final value = segments[i];
64+
namedParams[name] = value;
65+
}
66+
67+
if (i == parts.length - 1 && matches == true) {
68+
// at last segment and fully matched
69+
params.addAll(namedParams);
70+
71+
return MaterialPageRoute(
72+
builder: routes[route]!,
73+
settings: settings.copyWith(arguments: params, name: route));
74+
}
75+
}
76+
}
77+
}
78+
}

lib/routes.dart

+3
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
import 'package:flutter/material.dart';
2+
3+
typedef Routes = Map<String, Widget Function(BuildContext)>;

lib/view.dart

+18
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
import 'package:flutter/material.dart';
2+
3+
/// Build a widget using the given builder which is supplied
4+
/// with the query parameters parsed from the current named route.
5+
///
6+
/// Example:
7+
///
8+
/// ```
9+
/// static MyViewWidget route(BuildContext context) {
10+
/// return view(context, (args) => MyViewWidget(id: args['id']));
11+
/// }
12+
/// ```
13+
Widget view(
14+
BuildContext context, Widget Function(Map<String, String>) builder) {
15+
final args =
16+
ModalRoute.of(context)!.settings.arguments as Map<String, String>;
17+
return builder.call(args);
18+
}

lib/view_router.dart

+18
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
library view_router;
2+
3+
import 'package:flutter/material.dart';
4+
import 'package:view_router/parse_route_uri.dart';
5+
import 'package:view_router/routes.dart';
6+
7+
export 'package:view_router/routes.dart';
8+
export 'package:view_router/view.dart';
9+
10+
/// A view router that parses named routes as URIs, supplying
11+
/// any query parameters as arguments.
12+
class ViewRouter {
13+
final Routes routes;
14+
15+
ViewRouter({required this.routes});
16+
17+
call(RouteSettings settings) => parseRouteUri(routes, settings);
18+
}

0 commit comments

Comments
 (0)