Merge branch 'main' into dev
# Conflicts: # ln_jq_app/android/app/src/main/AndroidManifest.xml # ln_jq_app/pubspec.lock 同步线上
This commit is contained in:
@@ -1,9 +1,13 @@
|
||||
import 'dart:io';
|
||||
|
||||
import 'package:flutter/gestures.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/services.dart';
|
||||
import 'package:getx_scaffold/getx_scaffold.dart';
|
||||
import 'package:ln_jq_app/common/login_util.dart';
|
||||
import 'package:ln_jq_app/pages/b_page/reservation/controller.dart';
|
||||
import 'package:ln_jq_app/pages/c_page/message/view.dart';
|
||||
import 'package:ln_jq_app/pages/common/webview/view.dart';
|
||||
|
||||
class ReservationPage extends GetView<ReservationController> {
|
||||
const ReservationPage({super.key});
|
||||
@@ -36,6 +40,30 @@ class ReservationPage extends GetView<ReservationController> {
|
||||
_buildSystemTips(),
|
||||
SizedBox(height: 24),
|
||||
_buildLogoutButton(),
|
||||
SizedBox(height: 15.h),
|
||||
Text.rich(
|
||||
TextSpan(
|
||||
style: const TextStyle(color: Colors.grey, fontSize: 13),
|
||||
children: [
|
||||
TextSpan(
|
||||
text: '《用户协议》',
|
||||
style: TextStyle(color: Colors.blue, fontSize: 13),
|
||||
recognizer: TapGestureRecognizer()
|
||||
..onTap = () {
|
||||
openPage("用户协议", "https://lnh2e.com/user_agreement.html");
|
||||
},
|
||||
),
|
||||
TextSpan(
|
||||
text: '《隐私政策》',
|
||||
style: TextStyle(color: Colors.blue, fontSize: 13),
|
||||
recognizer: TapGestureRecognizer()
|
||||
..onTap = () {
|
||||
openPage("隐私政策", "https://lnh2e.com/privacy_agreement.html");
|
||||
},
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
SizedBox(height: 95.h),
|
||||
],
|
||||
),
|
||||
@@ -48,6 +76,14 @@ class ReservationPage extends GetView<ReservationController> {
|
||||
);
|
||||
}
|
||||
|
||||
void openPage(String title, String url) {
|
||||
if (Platform.isIOS) {
|
||||
openWebPage(url);
|
||||
return;
|
||||
}
|
||||
Get.to(() => const WebViewPage(), arguments: {'title': title, 'url': url});
|
||||
}
|
||||
|
||||
/// 1. 顶部个人信息及统计栏
|
||||
Widget _buildTopSection(BuildContext context) {
|
||||
return Container(
|
||||
|
||||
@@ -1,10 +1,15 @@
|
||||
import 'dart:io';
|
||||
|
||||
import 'package:flutter/gestures.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/services.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:getx_scaffold/common/index.dart';
|
||||
import 'package:getx_scaffold/common/widgets/index.dart';
|
||||
import 'package:ln_jq_app/common/login_util.dart';
|
||||
import 'package:ln_jq_app/common/styles/theme.dart';
|
||||
import 'package:ln_jq_app/pages/c_page/message/view.dart';
|
||||
import 'package:ln_jq_app/pages/common/webview/view.dart';
|
||||
import 'package:ln_jq_app/storage_service.dart';
|
||||
import 'controller.dart';
|
||||
|
||||
@@ -38,6 +43,30 @@ class MinePage extends GetView<MineController> {
|
||||
_buildSafetyReminderCard(),
|
||||
SizedBox(height: 24.h),
|
||||
_buildLogoutButton(),
|
||||
SizedBox(height: 15.h),
|
||||
Text.rich(
|
||||
TextSpan(
|
||||
style: const TextStyle(color: Colors.grey, fontSize: 13),
|
||||
children: [
|
||||
TextSpan(
|
||||
text: '《用户协议》',
|
||||
style: TextStyle(color: Colors.blue, fontSize: 13),
|
||||
recognizer: TapGestureRecognizer()
|
||||
..onTap = () {
|
||||
openPage("用户协议", "https://lnh2e.com/user_agreement.html");
|
||||
},
|
||||
),
|
||||
TextSpan(
|
||||
text: '《隐私政策》',
|
||||
style: TextStyle(color: Colors.blue, fontSize: 13),
|
||||
recognizer: TapGestureRecognizer()
|
||||
..onTap = () {
|
||||
openPage("隐私政策", "https://lnh2e.com/privacy_agreement.html");
|
||||
},
|
||||
),
|
||||
],
|
||||
),
|
||||
),
|
||||
SizedBox(height: 95.h),
|
||||
],
|
||||
),
|
||||
@@ -51,6 +80,15 @@ class MinePage extends GetView<MineController> {
|
||||
);
|
||||
}
|
||||
|
||||
void openPage(String title, String url) {
|
||||
if (Platform.isIOS) {
|
||||
openWebPage(url);
|
||||
return;
|
||||
}
|
||||
Get.to(() => const WebViewPage(), arguments: {'title': title, 'url': url});
|
||||
}
|
||||
|
||||
|
||||
/// 构建顶部用户信息卡片
|
||||
Widget _buildUserInfoCard() {
|
||||
return Card(
|
||||
|
||||
@@ -29,14 +29,6 @@ class HomeController extends GetxController with BaseControllerMixin {
|
||||
@override
|
||||
void onInit() {
|
||||
super.onInit();
|
||||
|
||||
// 检查是否同意过隐私政策,只有同意后才初始化推送
|
||||
if (StorageService.to.isPrivacyAgreed) {
|
||||
requestPermission();
|
||||
initAliyunPush();
|
||||
addPushCallback();
|
||||
}
|
||||
|
||||
FlutterNativeSplash.remove();
|
||||
log('page-init');
|
||||
|
||||
@@ -159,6 +151,13 @@ class HomeController extends GetxController with BaseControllerMixin {
|
||||
// 根据登录状态和登录渠道返回不同的首页
|
||||
Widget getHomePage() {
|
||||
if (StorageService.to.isLoggedIn) {
|
||||
// 检查是否同意过隐私政策,只有同意后才初始化推送
|
||||
if (StorageService.to.isPrivacyAgreed) {
|
||||
requestPermission();
|
||||
initAliyunPush();
|
||||
addPushCallback();
|
||||
}
|
||||
|
||||
if (StorageService.to.loginChannel == LoginChannel.station) {
|
||||
return B_BaseWidgetsPage();
|
||||
} else if (StorageService.to.loginChannel == LoginChannel.driver) {
|
||||
|
||||
@@ -140,9 +140,29 @@ class _LoginPageState extends State<LoginPage> with SingleTickerProviderStateMix
|
||||
children: [
|
||||
const SizedBox(height: 30),
|
||||
// 根据 Tab 显示不同的输入框
|
||||
_tabController.index == 0
|
||||
!_isAgreed
|
||||
? GestureDetector(
|
||||
onTap: () => _handleLogin(controller),
|
||||
behavior: HitTestBehavior.opaque,
|
||||
child: Container(
|
||||
width: double.infinity,
|
||||
height: 55.h,
|
||||
padding: const EdgeInsets.symmetric(
|
||||
horizontal: 24,
|
||||
),
|
||||
alignment: Alignment.centerLeft,
|
||||
child: Text(
|
||||
"请先阅读并同意用户协议和隐私政策",
|
||||
style: TextStyle(
|
||||
color: Colors.grey,
|
||||
fontSize: 16,
|
||||
),
|
||||
),
|
||||
),
|
||||
)
|
||||
: (_tabController.index == 0
|
||||
? _buildDriverInputFields(controller)
|
||||
: _buildStationInputFields(controller),
|
||||
: _buildStationInputFields(controller)),
|
||||
|
||||
const SizedBox(height: 30),
|
||||
// 统一登录按钮
|
||||
@@ -150,7 +170,8 @@ class _LoginPageState extends State<LoginPage> with SingleTickerProviderStateMix
|
||||
|
||||
const SizedBox(height: 10),
|
||||
buildAgreement(),
|
||||
const SizedBox(height: 40),
|
||||
const SizedBox(height: 80),
|
||||
_buildFooterSlogan(),
|
||||
],
|
||||
),
|
||||
),
|
||||
@@ -159,7 +180,6 @@ class _LoginPageState extends State<LoginPage> with SingleTickerProviderStateMix
|
||||
),
|
||||
),
|
||||
),
|
||||
Positioned(left: 0, right: 0, bottom: 33.h, child: _buildFooterSlogan()),
|
||||
if (AppTheme.is_show_host)
|
||||
Positioned(
|
||||
top: 40.h,
|
||||
@@ -475,7 +495,6 @@ class _LoginPageState extends State<LoginPage> with SingleTickerProviderStateMix
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
_processLoginResponse(responseData, "station", account);
|
||||
} catch (e) {
|
||||
dismissLoading();
|
||||
@@ -539,7 +558,6 @@ class _LoginPageState extends State<LoginPage> with SingleTickerProviderStateMix
|
||||
Logger.d("暂时不处理 查询车辆信息失败的情况");
|
||||
}
|
||||
|
||||
|
||||
dismissLoading();
|
||||
Get.offAll(() => BaseWidgetsPage());
|
||||
} else {
|
||||
@@ -596,9 +614,7 @@ class _LoginPageState extends State<LoginPage> with SingleTickerProviderStateMix
|
||||
}
|
||||
|
||||
// 添加推送回调
|
||||
_aliyunPush.addMessageReceiver(
|
||||
onNotificationOpened: _onNotificationOpened,
|
||||
);
|
||||
_aliyunPush.addMessageReceiver(onNotificationOpened: _onNotificationOpened);
|
||||
|
||||
isPushInitialized = true;
|
||||
Logger.d('推送服务初始化成功');
|
||||
|
||||
@@ -1,16 +1,103 @@
|
||||
import 'dart:io';
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter/services.dart';
|
||||
import 'package:flutter_native_splash/flutter_native_splash.dart';
|
||||
import 'package:get/get.dart';
|
||||
import 'package:getx_scaffold/common/components/index.dart';
|
||||
import 'package:getx_scaffold/common/widgets/rich_text_x.dart';
|
||||
import 'package:ln_jq_app/pages/home/view.dart';
|
||||
import 'package:ln_jq_app/pages/login/view.dart';
|
||||
import 'package:ln_jq_app/storage_service.dart';
|
||||
|
||||
import '../common/webview/view.dart';
|
||||
|
||||
class WelcomeController extends GetxController {
|
||||
@override
|
||||
void onReady() {
|
||||
super.onReady();
|
||||
// 移除原生闪屏页(如果有的话)
|
||||
FlutterNativeSplash.remove();
|
||||
_startTimer();
|
||||
|
||||
if (Platform.isAndroid) {
|
||||
if (StorageService.to.isPrivacyAgreed) {
|
||||
_startTimer();
|
||||
} else {
|
||||
showPrivacyDialog();
|
||||
}
|
||||
} else if (Platform.isIOS) {
|
||||
_startTimer();
|
||||
}
|
||||
}
|
||||
|
||||
void showPrivacyDialog() {
|
||||
DialogX.to.showConfirmDialog(
|
||||
title: "个人信息保护提示",
|
||||
content: _buildDialogContent(),
|
||||
confirmText: '同意',
|
||||
cancelText: '不同意',
|
||||
onConfirm: () async {
|
||||
await StorageService.to.savePrivacyAgreed(true);
|
||||
Get.offAll(() => const HomePage());
|
||||
},
|
||||
onCancel: () {
|
||||
DialogX.to.showConfirmDialog(
|
||||
title: "温馨提示",
|
||||
content: RichTextX(
|
||||
children: [
|
||||
TextSpanItem('如果您不同意'),
|
||||
TextSpanItem(
|
||||
'《隐私协议》',
|
||||
onTap: () => openPage("隐私政策", "https://lnh2e.com/privacy_agreement.html"),
|
||||
),
|
||||
TextSpanItem('和'),
|
||||
TextSpanItem(
|
||||
'《用户政策》',
|
||||
onTap: () => openPage("用户协议", "https://lnh2e.com/user_agreement.html"),
|
||||
),
|
||||
TextSpanItem(
|
||||
',很遗憾我们将无法为您提供服务。您需要同意以上协议后,才能使用本应用。\n\n我们将严格按照相关法律法规要求,坚决保护您的个人隐私和信息安全。',
|
||||
),
|
||||
TextSpanItem('\n点击“同意”按钮,表示您已知情并同意以上协议。'),
|
||||
],
|
||||
),
|
||||
confirmText: '同意并继续',
|
||||
cancelText: '不同意',
|
||||
onConfirm: () async {
|
||||
await StorageService.to.savePrivacyAgreed(true);
|
||||
Get.offAll(() => const HomePage());
|
||||
},
|
||||
onCancel: () {
|
||||
SystemNavigator.pop();
|
||||
},
|
||||
);
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
Widget _buildDialogContent() {
|
||||
return RichTextX(
|
||||
children: [
|
||||
TextSpanItem('欢迎使用小羚羚!\n我们将通过'),
|
||||
TextSpanItem(
|
||||
'《隐私协议》',
|
||||
onTap: () => openPage("隐私政策", "https://lnh2e.com/privacy_agreement.html"),
|
||||
),
|
||||
TextSpanItem('和'),
|
||||
TextSpanItem(
|
||||
'《用户政策》',
|
||||
onTap: () => openPage("用户协议", "https://lnh2e.com/user_agreement.html"),
|
||||
),
|
||||
TextSpanItem(
|
||||
',帮助您了解我们为您提供的服务、我们如何处理个人信息以及您享有的权利。我们会严格按照相关法律法规要求,采取各种安全措施来保护您的个人信息。',
|
||||
),
|
||||
TextSpanItem('\n点击“同意”按钮,表示您已知情并同意以上协议。'),
|
||||
],
|
||||
);
|
||||
}
|
||||
|
||||
void openPage(String title, String url) {
|
||||
Get.to(() => const WebViewPage(), arguments: {'title': title, 'url': url});
|
||||
}
|
||||
|
||||
void _startTimer() {
|
||||
|
||||
Reference in New Issue
Block a user