Skip to content
GitLab
Menu
Projects
Groups
Snippets
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
Menu
Open sidebar
Hoàng Văn Đạt
mypoint_flutter_app
Commits
e41fc4fe
Commit
e41fc4fe
authored
Feb 27, 2025
by
DatHV
Browse files
init
parent
d87cb75e
Changes
104
Hide whitespace changes
Inline
Side-by-side
lib/splash_screen/splash_screen.dart
0 → 100644
View file @
e41fc4fe
import
'dart:io'
;
import
'package:flutter/material.dart'
;
import
'package:flutter/services.dart'
;
import
'package:get/get.dart'
;
import
'package:get/get_core/src/get_main.dart'
;
import
'package:mypoint_flutter_app/configs/api_paths.dart'
;
import
'package:mypoint_flutter_app/dio_http_service/api_helper.dart'
;
import
'package:mypoint_flutter_app/networking/api_service.dart'
;
import
'package:mypoint_flutter_app/splash_screen/splash_screen_view_model.dart'
;
import
'../model/check_update_response_model.dart'
;
import
'../onboading/onboarding_screen.dart'
;
class
SplashScreen
extends
StatefulWidget
{
const
SplashScreen
({
super
.
key
});
@override
State
<
SplashScreen
>
createState
()
=>
_SplashScreenState
();
}
class
_SplashScreenState
extends
State
<
SplashScreen
>
with
ApiHelper
{
final
SplashScreenViewModel
_viewModel
=
Get
.
put
(
SplashScreenViewModel
());
@override
void
initState
()
{
super
.
initState
();
initNetWork
(
APIPaths
.
baseUrl
);
_viewModel
.
checkUpdateApp
();
// ApiService().checkUpdateWithRequestManager().then((value) {
// if (value != null) {
// if (value!.status == UpdateStatus.force) {
// _showForceUpdateAlert();
// } else if (value!.status == UpdateStatus.suggest) {
// _showSuggestUpdateAlert();
// } else {
// _showForceUpdateAlert();
// // _navigateToHome();
// }
// } else {
// _showSuggestUpdateAlert();
// // _navigateToHome();
// }
// });
}
@override
Widget
build
(
BuildContext
context
)
{
return
Scaffold
(
backgroundColor:
Colors
.
blue
,
body:
Stack
(
children:
[
Container
(
width:
double
.
infinity
,
height:
double
.
infinity
,
decoration:
BoxDecoration
(
image:
DecorationImage
(
image:
AssetImage
(
"assets/images/splash_screen.png"
),
fit:
BoxFit
.
cover
),
),
),
Obx
(()
{
if
(
_viewModel
.
isLoading
.
value
)
{
return
Center
(
child:
CircularProgressIndicator
());
}
else
{
WidgetsBinding
.
instance
.
addPostFrameCallback
((
_
)
{
var
status
=
_viewModel
.
infoAppUpdate
.
value
?.
data
?.
data
?.
updateRequest
?.
first
?.
status
??
UpdateStatus
.
none
;
if
(
status
==
UpdateStatus
.
force
)
{
_showForceUpdateAlert
();
}
else
if
(
status
==
UpdateStatus
.
suggest
)
{
_showSuggestUpdateAlert
();
}
else
{
_showSuggestUpdateAlert
();
// _navigateToBeforCheckUpdate();
}
});
return
Container
(
width:
double
.
infinity
,
height:
double
.
infinity
,
color:
Colors
.
black
.
withOpacity
(
0.5
));
}
}),
],
),
);
}
void
_exitApp
()
{
if
(
Platform
.
isAndroid
)
{
SystemNavigator
.
pop
();
}
else
{
exit
(
0
);
}
}
void
_navigateToBeforCheckUpdate
()
{
Get
.
to
(
OnboardingScreen
());
}
void
_showForceUpdateAlert
()
{
showDialog
(
context:
context
,
barrierDismissible:
false
,
// Không cho dismiss ngoài Alert
builder:
(
context
)
{
return
AlertDialog
(
title:
Text
(
"Cập nhật bắt buộc"
),
content:
Text
(
"Phiên bản app của bạn đã cũ. Bạn phải cập nhật để tiếp tục sử dụng."
),
actions:
[
TextButton
(
onPressed:
()
async
{
// Sau khi nhấn update, bạn có thể đóng app nếu không cập nhật được.
_exitApp
();
},
child:
Text
(
"Cập nhật ngay"
),
),
TextButton
(
onPressed:
()
{
// Nếu người dùng không cập nhật, đóng app.
_exitApp
();
},
child:
Text
(
"Thoát"
),
),
],
);
},
);
}
void
_showSuggestUpdateAlert
()
{
showDialog
(
context:
context
,
barrierDismissible:
false
,
// Buộc người dùng chọn
builder:
(
context
)
{
return
AlertDialog
(
title:
Text
(
"Gợi ý cập nhật"
),
content:
Text
(
"Có phiên bản mới của app. Bạn có muốn cập nhật không?"
),
actions:
[
TextButton
(
onPressed:
()
async
{},
child:
Text
(
"Cập nhật ngay"
)),
TextButton
(
onPressed:
()
{
// Cho phép sử dụng app mà không cập nhật ngay
_navigateToBeforCheckUpdate
();
},
child:
Text
(
"Để sau"
),
),
],
);
},
);
}
Future
<
void
>
fetchCheckUpdate
()
async
{
final
response
=
await
ApiService
().
checkUpdateWithRequestManager
();
if
(
response
!=
null
)
{
if
(
response
.
status
==
UpdateStatus
.
force
)
{
_showForceUpdateAlert
();
}
else
if
(
response
.
status
==
UpdateStatus
.
suggest
)
{
_showSuggestUpdateAlert
();
}
else
{
_showForceUpdateAlert
();
// _navigateToHome();
}
}
else
{
_showSuggestUpdateAlert
();
// _navigateToHome();
}
}
}
lib/splash_screen/splash_screen_view_model.dart
0 → 100644
View file @
e41fc4fe
import
'package:get/get.dart'
;
import
'package:mypoint_flutter_app/base/restful_api_viewmodel.dart'
;
import
'package:mypoint_flutter_app/networking/restful_api_request.dart'
;
import
'../base/base_response_model.dart'
;
import
'../model/update_response_object.dart'
;
class
SplashScreenViewModel
extends
RestfulApiViewModel
{
var
infoAppUpdate
=
BaseResponseModel
<
UpdateResponseObject
>().
obs
;
var
isLoading
=
false
.
obs
;
void
checkUpdateApp
()
{
showLoading
();
isLoading
(
true
);
client
.
checkUpdateApp
().
then
((
value
)
{
infoAppUpdate
.
value
=
value
;
hideLoading
();
isLoading
(
false
);
});
}
}
class
EmptyCodable
{
EmptyCodable
.
fromJson
(
dynamic
json
);
Map
<
String
,
dynamic
>
toJson
()
{
return
{};
}
}
\ No newline at end of file
pubspec.yaml
0 → 100644
View file @
e41fc4fe
name
:
mypoint_flutter_app
description
:
"
A
new
Flutter
project."
# The following line prevents the package from being accidentally published to
# pub.dev using `flutter pub publish`. This is preferred for private packages.
publish_to
:
'
none'
# Remove this line if you wish to publish to pub.dev
# The following defines the version and build number for your application.
# A version number is three numbers separated by dots, like 1.2.43
# followed by an optional build number separated by a +.
# Both the version and the builder number may be overridden in flutter
# build by specifying --build-name and --build-number, respectively.
# In Android, build-name is used as versionName while build-number used as versionCode.
# Read more about Android versioning at https://developer.android.com/studio/publish/versioning
# In iOS, build-name is used as CFBundleShortVersionString while build-number is used as CFBundleVersion.
# Read more about iOS versioning at
# https://developer.apple.com/library/archive/documentation/General/Reference/InfoPlistKeyReference/Articles/CoreFoundationKeys.html
# In Windows, build-name is used as the major, minor, and patch parts
# of the product and file versions while build-number is used as the build suffix.
version
:
1.0.0+1
environment
:
sdk
:
^3.7.0
# Dependencies specify other packages that your package needs in order to work.
# To automatically upgrade your package dependencies to the latest versions
# consider running `flutter pub upgrade --major-versions`. Alternatively,
# dependencies can be manually updated by changing the version numbers below to
# the latest version available on pub.dev. To see which dependencies have newer
# versions available, run `flutter pub outdated`.
dependencies
:
flutter
:
sdk
:
flutter
dio
:
^5.8.0+1
# The following adds the Cupertino Icons font to your application.
# Use with the CupertinoIcons class for iOS style icons.
cupertino_icons
:
^1.0.8
shared_preferences
:
^2.5.2
json_annotation
:
^4.9.0
retrofit
:
get
:
^4.7.2
fluttertoast
:
8.2.12
logger
:
url_launcher
:
^6.3.1
dev_dependencies
:
flutter_test
:
sdk
:
flutter
build_runner
:
^2.4.15
json_serializable
:
^6.9.4
retrofit_generator
:
equatable
:
^2.0.7
# The "flutter_lints" package below contains a set of recommended lints to
# encourage good coding practices. The lint set provided by the package is
# activated in the `analysis_options.yaml` file located at the root of your
# package. See that file for information about deactivating specific lint
# rules and activating additional ones.
flutter_lints
:
^5.0.0
# For information on the generic Dart part of this file, see the
# following page: https://dart.dev/tools/pub/pubspec
# The following section is specific to Flutter packages.
flutter
:
# The following line ensures that the Material Icons font is
# included with your application, so that you can use the icons in
# the material Icons class.
uses-material-design
:
true
# To add assets to your application, add an assets section, like this:
assets
:
-
assets/images/splash_screen.png
-
assets/images/bg_onboarding.png
# - images/a_dot_burr.jpeg
# - images/a_dot_ham.jpeg
# An image asset can refer to one or more resolution-specific "variants", see
# https://flutter.dev/to/resolution-aware-images
# For details regarding adding assets from package dependencies, see
# https://flutter.dev/to/asset-from-package
# To add custom fonts to your application, add a fonts section here,
# in this "flutter" section. Each entry in this list should have a
# "family" key with the font family name, and a "fonts" key with a
# list giving the asset and other descriptors for the font. For
# example:
# fonts:
# - family: Schyler
# fonts:
# - asset: fonts/Schyler-Regular.ttf
# - asset: fonts/Schyler-Italic.ttf
# style: italic
# - family: Trajan Pro
# fonts:
# - asset: fonts/TrajanPro.ttf
# - asset: fonts/TrajanPro_Bold.ttf
# weight: 700
#
# For details regarding fonts from package dependencies,
# see https://flutter.dev/to/font-from-package
test/widget_test.dart
0 → 100644
View file @
e41fc4fe
// This is a basic Flutter widget test.
//
// To perform an interaction with a widget in your test, use the WidgetTester
// utility in the flutter_test package. For example, you can send tap and scroll
// gestures. You can also use WidgetTester to find child widgets in the widget
// tree, read text, and verify that the values of widget properties are correct.
import
'package:flutter/material.dart'
;
import
'package:flutter_test/flutter_test.dart'
;
import
'package:mypoint_flutter_app/main.dart'
;
void
main
(
)
{
testWidgets
(
'Counter increments smoke test'
,
(
WidgetTester
tester
)
async
{
// Build our app and trigger a frame.
await
tester
.
pumpWidget
(
const
MyApp
());
// Verify that our counter starts at 0.
expect
(
find
.
text
(
'0'
),
findsOneWidget
);
expect
(
find
.
text
(
'1'
),
findsNothing
);
// Tap the '+' icon and trigger a frame.
await
tester
.
tap
(
find
.
byIcon
(
Icons
.
add
));
await
tester
.
pump
();
// Verify that our counter has incremented.
expect
(
find
.
text
(
'0'
),
findsNothing
);
expect
(
find
.
text
(
'1'
),
findsOneWidget
);
});
}
Prev
1
2
3
4
5
6
Next
Write
Preview
Supports
Markdown
0%
Try again
or
attach a new file
.
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment