Skip to content
Toggle navigation
Toggle navigation
This project
Loading...
Sign in
ethan
/
appframe
Go to a project
Toggle navigation
Toggle navigation pinning
Projects
Groups
Snippets
Help
Project
Activity
Repository
Pipelines
Graphs
Issues
0
Merge Requests
0
Wiki
Network
Create a new issue
Jobs
Commits
Issue Boards
Files
Commits
Network
Compare
Branches
Tags
Commit 5a44fc5c
authored
2026-01-27 15:43:04 +0800
by
tanghuan
Browse Files
Options
Browse Files
Tag
Download
Email Patches
Plain Diff
调整打开设置界面的方式
1 parent
1f29d37d
Show whitespace changes
Inline
Side-by-side
Showing
5 changed files
with
453 additions
and
396 deletions
lib/bloc/setting/setting_cubit.dart
lib/bloc/web_cubit.dart
lib/config/routes.dart
lib/ui/pages/setting/setting_page.dart
lib/ui/pages/web_page.dart
lib/bloc/setting/setting_cubit.dart
0 → 100644
View file @
5a44fc5
import
'dart:io'
;
import
'package:appframe/config/constant.dart'
;
import
'package:appframe/config/locator.dart'
;
import
'package:appframe/config/routes.dart'
;
import
'package:equatable/equatable.dart'
;
import
'package:flutter_bloc/flutter_bloc.dart'
;
import
'package:fluwx/fluwx.dart'
;
import
'package:path_provider/path_provider.dart'
;
import
'package:shared_preferences/shared_preferences.dart'
;
class
SettingState
extends
Equatable
{
final
String
h5Version
;
const
SettingState
({
this
.
h5Version
=
''
,
});
SettingState
copyWith
({
String
?
h5Version
,
})
{
return
SettingState
(
h5Version:
h5Version
??
this
.
h5Version
,
);
}
@override
List
<
Object
?>
get
props
=>
[
h5Version
];
}
class
SettingCubit
extends
Cubit
<
SettingState
>
{
final
SharedPreferences
_prefs
=
getIt
.
get
<
SharedPreferences
>();
final
Fluwx
_fluwx
=
getIt
.
get
<
Fluwx
>();
SettingCubit
()
:
super
(
const
SettingState
())
{
_init
();
}
void
_init
()
{
_readH5ShowVersion
();
}
void
_readH5ShowVersion
()
{
var
h5Version
=
_prefs
.
getString
(
Constant
.
h5ShowVersionKey
)
??
'unknown'
;
emit
(
state
.
copyWith
(
h5Version:
h5Version
));
}
/// 跳转客服(微信小程序)
void
goCs
()
{
_fluwx
.
open
(
target:
MiniProgram
(
username:
'gh_0ed02e873abc'
,
path:
'/pages/agentChat/index?showAuthDirectly=1&agentId=eiXH0MAJmjgl'
,
miniProgramType:
WXMiniProgramType
.
release
,
),
);
}
/// 退出登录
Future
<
void
>
logout
()
async
{
// 删除所有auth_开头的key
_prefs
.
getKeys
().
forEach
((
key
)
{
if
(
key
.
startsWith
(
'auth_'
))
{
_prefs
.
remove
(
key
);
}
});
// IM 登出
// await getIt.get<ImService>().logout();
router
.
go
(
'/loginMain'
);
}
/// 切换日志模式
Future
<
void
>
handleToggleDebug
()
async
{
var
debug
=
_prefs
.
getInt
(
'debug'
)
??
0
;
debug
=
(
debug
==
0
?
1
:
0
);
_prefs
.
setInt
(
'debug'
,
debug
);
// 通知 WebCubit 更新 H5 状态
WebCubitHolder
.
instance
?.
notifyDebugStatus
(
debug
);
}
/// 清理缓存
Future
<
void
>
clearStorage
()
async
{
// 1 清理 WebView 相关缓存
WebCubitHolder
.
instance
?.
clearWebCache
();
// 2 清理非 h5_version 的缓存
_prefs
.
getKeys
().
forEach
((
key
)
async
{
if
(!
key
.
startsWith
(
'h5'
))
{
await
_prefs
.
remove
(
key
);
}
});
// 3 清理 http_dist_assets 下的非当前版本号的文件和目录
var
dir
=
await
getApplicationSupportDirectory
();
var
httpDir
=
Directory
(
'
${dir.path}
/
${Constant.h5DistDir}
'
);
if
(
httpDir
.
existsSync
())
{
var
version
=
_prefs
.
getString
(
Constant
.
h5VersionKey
)
??
Constant
.
h5Version
;
await
for
(
final
entity
in
httpDir
.
list
())
{
if
(
entity
is
Directory
)
{
if
(!
entity
.
path
.
endsWith
(
version
))
{
await
entity
.
delete
(
recursive:
true
);
}
}
else
if
(
entity
is
File
)
{
if
(!
entity
.
path
.
endsWith
(
'
$version
.zip'
))
{
await
entity
.
delete
();
}
}
}
}
// 4 清理临时目录下的所有文件和目录
var
tempDir
=
await
getTemporaryDirectory
();
if
(
tempDir
.
existsSync
())
{
await
for
(
final
entity
in
tempDir
.
list
())
{
if
(
entity
is
Directory
)
{
await
entity
.
delete
(
recursive:
true
);
}
else
{
await
entity
.
delete
();
}
}
}
}
}
lib/bloc/web_cubit.dart
View file @
5a44fc5
...
@@ -67,8 +67,6 @@ class WebState extends Equatable {
...
@@ -67,8 +67,6 @@ class WebState extends Equatable {
final
bool
chooseVideoCmdFlag
;
final
bool
chooseVideoCmdFlag
;
final
String
chooseVideoCmdMessage
;
final
String
chooseVideoCmdMessage
;
final
String
h5Version
;
/// 用于测试监测问题
/// 用于测试监测问题
final
String
testMsg
;
final
String
testMsg
;
...
@@ -96,7 +94,6 @@ class WebState extends Equatable {
...
@@ -96,7 +94,6 @@ class WebState extends Equatable {
this
.
chooseImageCmdMessage
=
''
,
this
.
chooseImageCmdMessage
=
''
,
this
.
chooseVideoCmdFlag
=
false
,
this
.
chooseVideoCmdFlag
=
false
,
this
.
chooseVideoCmdMessage
=
''
,
this
.
chooseVideoCmdMessage
=
''
,
this
.
h5Version
=
''
,
this
.
testMsg
=
''
,
this
.
testMsg
=
''
,
});
});
...
@@ -125,7 +122,6 @@ class WebState extends Equatable {
...
@@ -125,7 +122,6 @@ class WebState extends Equatable {
String
?
chooseImageCmdMessage
,
String
?
chooseImageCmdMessage
,
bool
?
chooseVideoCmdFlag
,
bool
?
chooseVideoCmdFlag
,
String
?
chooseVideoCmdMessage
,
String
?
chooseVideoCmdMessage
,
String
?
h5Version
,
String
?
testMsg
,
String
?
testMsg
,
})
{
})
{
return
WebState
(
return
WebState
(
...
@@ -152,7 +148,6 @@ class WebState extends Equatable {
...
@@ -152,7 +148,6 @@ class WebState extends Equatable {
chooseImageCmdMessage:
chooseImageCmdMessage
??
this
.
chooseImageCmdMessage
,
chooseImageCmdMessage:
chooseImageCmdMessage
??
this
.
chooseImageCmdMessage
,
chooseVideoCmdFlag:
chooseVideoCmdFlag
??
this
.
chooseVideoCmdFlag
,
chooseVideoCmdFlag:
chooseVideoCmdFlag
??
this
.
chooseVideoCmdFlag
,
chooseVideoCmdMessage:
chooseVideoCmdMessage
??
this
.
chooseVideoCmdMessage
,
chooseVideoCmdMessage:
chooseVideoCmdMessage
??
this
.
chooseVideoCmdMessage
,
h5Version:
h5Version
??
this
.
h5Version
,
testMsg:
testMsg
??
this
.
testMsg
,
testMsg:
testMsg
??
this
.
testMsg
,
);
);
}
}
...
@@ -181,7 +176,6 @@ class WebState extends Equatable {
...
@@ -181,7 +176,6 @@ class WebState extends Equatable {
chooseImageCmdMessage
,
chooseImageCmdMessage
,
chooseVideoCmdFlag
,
chooseVideoCmdFlag
,
chooseVideoCmdMessage
,
chooseVideoCmdMessage
,
h5Version
,
testMsg
,
testMsg
,
];
];
}
}
...
@@ -189,7 +183,6 @@ class WebState extends Equatable {
...
@@ -189,7 +183,6 @@ class WebState extends Equatable {
class
WebCubit
extends
Cubit
<
WebState
>
with
WidgetsBindingObserver
{
class
WebCubit
extends
Cubit
<
WebState
>
with
WidgetsBindingObserver
{
late
final
MessageDispatcher
_dispatcher
;
late
final
MessageDispatcher
_dispatcher
;
late
final
WebViewController
_controller
;
late
final
WebViewController
_controller
;
late
final
Fluwx
_fluwx
;
HttpServer
?
_server
;
HttpServer
?
_server
;
PlayerService
?
_playerService
;
PlayerService
?
_playerService
;
RecorderService
?
_recorderService
;
RecorderService
?
_recorderService
;
...
@@ -259,11 +252,7 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
...
@@ -259,11 +252,7 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
// 加载H5页面
// 加载H5页面
_loadHtml
();
_loadHtml
();
// 读取 h5 版本号
_readH5ShowVersion
();
// 初始化其它一些属性
// 初始化其它一些属性
_fluwx
=
getIt
.
get
<
Fluwx
>();
_playerService
=
getIt
.
get
<
PlayerService
>();
_playerService
=
getIt
.
get
<
PlayerService
>();
_playerService
?.
sendResponse
=
_sendResponse
;
_playerService
?.
sendResponse
=
_sendResponse
;
_recorderService
=
getIt
.
get
<
RecorderService
>();
_recorderService
=
getIt
.
get
<
RecorderService
>();
...
@@ -271,11 +260,9 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
...
@@ -271,11 +260,9 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
// 登录IM
// 登录IM
_loginIM
();
_loginIM
();
// 针对ios系统,处理侧滑返回
// 注册 WebCubit 实例,供其它页面使用
if
(
Platform
.
isIOS
)
{
WebCubitHolder
.
register
(
this
);
WebCubitHolder
.
register
(
this
);
}
}
}
Future
<
Map
<
String
,
String
>>
_getVersionConfig
()
async
{
Future
<
Map
<
String
,
String
>>
_getVersionConfig
()
async
{
Dio
dio
=
Dio
();
Dio
dio
=
Dio
();
...
@@ -385,11 +372,6 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
...
@@ -385,11 +372,6 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
_controller
.
loadRequest
(
Uri
.
parse
(
serverUrl
));
_controller
.
loadRequest
(
Uri
.
parse
(
serverUrl
));
}
}
void
_readH5ShowVersion
()
{
var
h5Version
=
getIt
.
get
<
SharedPreferences
>().
getString
(
Constant
.
h5ShowVersionKey
)
??
'unknown'
;
emit
(
state
.
copyWith
(
h5Version:
h5Version
));
}
Future
<
void
>
_loginIM
()
async
{
Future
<
void
>
_loginIM
()
async
{
if
(
Constant
.
needIM
)
{
if
(
Constant
.
needIM
)
{
var
imService
=
getIt
.
get
<
ImService
>();
var
imService
=
getIt
.
get
<
ImService
>();
...
@@ -476,16 +458,24 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
...
@@ -476,16 +458,24 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
}
}
///
///
///
跳转客服(微信小程序)
///
清理 WebView 缓存
///
///
void
goCs
()
{
Future
<
void
>
clearWebCache
()
async
{
_fluwx
.
open
(
_controller
.
clearLocalStorage
();
target:
MiniProgram
(
_controller
.
clearCache
();
username:
'gh_0ed02e873abc'
,
}
path:
'/pages/agentChat/index?showAuthDirectly=1&agentId=eiXH0MAJmjgl'
,
miniProgramType:
WXMiniProgramType
.
release
,
///
),
/// 通知 H5 更新调试模式
);
///
void
notifyDebugStatus
(
int
debug
)
{
var
resp
=
{
'unique'
:
''
,
'cmd'
:
'toggleDebug'
,
'data'
:
{
'debug'
:
debug
},
'errMsg'
:
''
};
_sendResponse
(
resp
);
}
}
void
goLogin
()
{
void
goLogin
()
{
...
@@ -525,21 +515,6 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
...
@@ -525,21 +515,6 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
_sendResponse
(
resp
);
_sendResponse
(
resp
);
}
}
Future
<
void
>
handleToggleDebug
()
async
{
var
sharedPreferences
=
getIt
.
get
<
SharedPreferences
>();
var
debug
=
sharedPreferences
.
getInt
(
'debug'
)
??
0
;
debug
=
(
debug
==
0
?
1
:
0
);
sharedPreferences
.
setInt
(
'debug'
,
debug
);
var
resp
=
{
'unique'
:
''
,
'cmd'
:
'toggleDebug'
,
'data'
:
{
'debug'
:
debug
},
'errMsg'
:
''
};
_sendResponse
(
resp
);
}
bool
setTitleBar
(
String
title
,
String
color
,
String
bgColor
,
String
icon
)
{
bool
setTitleBar
(
String
title
,
String
color
,
String
bgColor
,
String
icon
)
{
int
parsedTitleColor
=
_hexStringToInt
(
color
);
int
parsedTitleColor
=
_hexStringToInt
(
color
);
int
parsedBgColor
=
_hexStringToInt
(
bgColor
);
int
parsedBgColor
=
_hexStringToInt
(
bgColor
);
...
@@ -573,68 +548,6 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
...
@@ -573,68 +548,6 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
router
.
push
(
'/account'
);
router
.
push
(
'/account'
);
}
}
Future
<
void
>
clearStorage
()
async
{
// 1 清理 localStorage
_controller
.
clearLocalStorage
();
_controller
.
clearCache
();
// 2 清理非 h5_version 的缓存
var
sharedPreferences
=
getIt
.
get
<
SharedPreferences
>();
sharedPreferences
.
getKeys
().
forEach
((
key
)
async
{
if
(!
key
.
startsWith
(
'h5'
))
{
await
sharedPreferences
.
remove
(
key
);
}
});
// 3 清理 http_dist_assets 下的非当前版本号的文件和目录
var
dir
=
await
getApplicationSupportDirectory
();
var
httpDir
=
Directory
(
'
${dir.path}
/
${Constant.h5DistDir}
'
);
if
(
httpDir
.
existsSync
())
{
var
version
=
sharedPreferences
.
getString
(
Constant
.
h5VersionKey
)
??
Constant
.
h5Version
;
await
for
(
final
FileSystemEntity
entity
in
httpDir
.
list
())
{
if
(
entity
is
Directory
)
{
// 删除目录
if
(!
entity
.
path
.
endsWith
(
version
))
{
await
entity
.
delete
(
recursive:
true
);
}
}
else
if
(
entity
is
File
)
{
// 删除文件
if
(!
entity
.
path
.
endsWith
(
'
$version
.zip'
))
{
await
entity
.
delete
();
}
}
}
}
// 4 清理临时目录下的所有文件和目录
var
tempDir
=
await
getTemporaryDirectory
();
if
(
tempDir
.
existsSync
())
{
await
for
(
final
FileSystemEntity
entity
in
tempDir
.
list
())
{
if
(
entity
is
Directory
)
{
await
entity
.
delete
(
recursive:
true
);
}
else
{
await
entity
.
delete
();
}
}
}
}
Future
<
void
>
logout
()
async
{
// 删除所有auth_开头的key
var
sharedPreferences
=
getIt
.
get
<
SharedPreferences
>();
sharedPreferences
.
getKeys
().
forEach
((
key
)
{
if
(
key
.
startsWith
(
'auth_'
))
{
sharedPreferences
.
remove
(
key
);
}
});
// IM 登出
// await getIt.get<ImService>().logout();
goLogin
();
}
void
updateSelectedIndex
(
int
index
)
{
void
updateSelectedIndex
(
int
index
)
{
emit
(
state
.
copyWith
(
selectedIndex:
index
));
emit
(
state
.
copyWith
(
selectedIndex:
index
));
}
}
...
@@ -1221,9 +1134,7 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
...
@@ -1221,9 +1134,7 @@ class WebCubit extends Cubit<WebState> with WidgetsBindingObserver {
await
_playerService
?.
close
();
await
_playerService
?.
close
();
await
_recorderService
?.
close
();
await
_recorderService
?.
close
();
if
(
Platform
.
isIOS
)
{
WebCubitHolder
.
unregister
();
WebCubitHolder
.
unregister
();
}
// 移除观察者
// 移除观察者
WidgetsBinding
.
instance
.
removeObserver
(
this
);
WidgetsBinding
.
instance
.
removeObserver
(
this
);
...
...
lib/config/routes.dart
View file @
5a44fc5
...
@@ -13,6 +13,7 @@ import 'package:appframe/ui/pages/setting/account_logoff_page.dart';
...
@@ -13,6 +13,7 @@ import 'package:appframe/ui/pages/setting/account_logoff_page.dart';
import
'package:appframe/ui/pages/setting/account_page.dart'
;
import
'package:appframe/ui/pages/setting/account_page.dart'
;
import
'package:appframe/ui/pages/setting/account_phone_page.dart'
;
import
'package:appframe/ui/pages/setting/account_phone_page.dart'
;
import
'package:appframe/ui/pages/setting/account_user_page.dart'
;
import
'package:appframe/ui/pages/setting/account_user_page.dart'
;
import
'package:appframe/ui/pages/setting/setting_page.dart'
;
import
'package:appframe/ui/pages/web_page.dart'
;
import
'package:appframe/ui/pages/web_page.dart'
;
import
'package:appframe/ui/widgets/ios_edge_swipe_detector.dart'
;
import
'package:appframe/ui/widgets/ios_edge_swipe_detector.dart'
;
import
'package:flutter/material.dart'
;
import
'package:flutter/material.dart'
;
...
@@ -25,7 +26,7 @@ final GoRouter router = GoRouter(
...
@@ -25,7 +26,7 @@ final GoRouter router = GoRouter(
GoRoute
(
GoRoute
(
path:
'/web'
,
path:
'/web'
,
builder:
(
BuildContext
context
,
GoRouterState
state
)
{
builder:
(
BuildContext
context
,
GoRouterState
state
)
{
return
WebPage
();
return
const
WebPage
();
},
},
),
),
GoRoute
(
GoRoute
(
...
@@ -100,6 +101,12 @@ final GoRouter router = GoRouter(
...
@@ -100,6 +101,12 @@ final GoRouter router = GoRouter(
return
const
ReloadPage
();
return
const
ReloadPage
();
},
},
),
),
GoRoute
(
path:
'/setting'
,
builder:
(
BuildContext
context
,
GoRouterState
state
)
{
return
const
SettingPage
();
},
),
],
],
);
);
...
@@ -158,7 +165,7 @@ class AppRouteObserver extends NavigatorObserver {
...
@@ -158,7 +165,7 @@ class AppRouteObserver extends NavigatorObserver {
}
}
///
///
///
只针对iOS使用
///
用于全局访问 WebCubit 实例
///
///
class
WebCubitHolder
{
class
WebCubitHolder
{
static
WebCubit
?
instance
;
static
WebCubit
?
instance
;
...
...
lib/ui/pages/setting/setting_page.dart
0 → 100644
View file @
5a44fc5
import
'package:appframe/bloc/setting/setting_cubit.dart'
;
import
'package:appframe/config/constant.dart'
;
import
'package:appframe/config/env_config.dart'
;
import
'package:appframe/config/routes.dart'
;
import
'package:flutter/material.dart'
;
import
'package:flutter_bloc/flutter_bloc.dart'
;
class
SettingPage
extends
StatelessWidget
{
const
SettingPage
({
super
.
key
});
@override
Widget
build
(
BuildContext
context
)
{
return
BlocProvider
(
create:
(
context
)
=>
SettingCubit
(),
child:
BlocBuilder
<
SettingCubit
,
SettingState
>(
builder:
(
context
,
state
)
{
final
settingCubit
=
context
.
read
<
SettingCubit
>();
return
Scaffold
(
appBar:
AppBar
(
title:
const
Text
(
'设置'
,
style:
TextStyle
(
color:
Colors
.
white
,
fontSize:
18
)),
centerTitle:
true
,
backgroundColor:
const
Color
(
0xFF7691FA
),
iconTheme:
const
IconThemeData
(
color:
Colors
.
white
),
),
body:
Column
(
children:
[
Expanded
(
child:
SingleChildScrollView
(
child:
Column
(
crossAxisAlignment:
CrossAxisAlignment
.
stretch
,
children:
[
const
SizedBox
(
height:
16
),
Card
(
margin:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
2
),
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
6
),
),
child:
Column
(
children:
[
ListTile
(
leading:
const
Icon
(
Icons
.
lock
,
size:
20
),
title:
const
Text
(
'账号与安全'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
router
.
push
(
'/account'
);
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
trailing:
const
Icon
(
Icons
.
arrow_forward_ios
,
size:
14
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
],
),
),
const
SizedBox
(
height:
8
),
Card
(
margin:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
2
),
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
6
),
),
child:
Column
(
children:
[
ListTile
(
leading:
const
Icon
(
Icons
.
book_outlined
,
size:
20
),
title:
const
Text
(
'版本记录'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
router
.
push
(
'/link'
,
extra:
{
'url'
:
'https://bxr.banxiaoer.net/apps/versions.html'
,
'title'
:
'版本记录'
},
);
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
trailing:
const
Icon
(
Icons
.
arrow_forward_ios
,
size:
14
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
const
Divider
(
height:
1
,
thickness:
0.5
,
indent:
16
,
endIndent:
16
),
ListTile
(
leading:
const
Icon
(
Icons
.
book_outlined
,
size:
20
),
title:
const
Text
(
'用户协议'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
router
.
push
(
'/link'
,
extra:
{
'url'
:
'https://bxr.banxiaoer.net/apps/useragreement.html'
,
'title'
:
'用户协议'
},
);
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
trailing:
const
Icon
(
Icons
.
arrow_forward_ios
,
size:
14
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
const
Divider
(
height:
1
,
thickness:
0.5
,
indent:
16
,
endIndent:
16
),
ListTile
(
leading:
const
Icon
(
Icons
.
book_outlined
,
size:
20
),
title:
const
Text
(
'隐私设置'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
router
.
push
(
'/link'
,
extra:
{
'url'
:
'https://bxr.banxiaoer.net/apps/privacysettings.html'
,
'title'
:
'隐私设置'
},
);
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
trailing:
const
Icon
(
Icons
.
arrow_forward_ios
,
size:
14
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
const
Divider
(
height:
1
,
thickness:
0.5
,
indent:
16
,
endIndent:
16
),
ListTile
(
leading:
const
Icon
(
Icons
.
book_outlined
,
size:
20
),
title:
const
Text
(
'关于'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
router
.
push
(
'/link'
,
extra:
{
'url'
:
'https://bxr.banxiaoer.net/apps/produce.html'
,
'title'
:
'关于'
},
);
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
trailing:
const
Icon
(
Icons
.
arrow_forward_ios
,
size:
14
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
],
),
),
const
SizedBox
(
height:
8
),
Card
(
margin:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
2
),
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
6
),
),
child:
Column
(
children:
[
ListTile
(
leading:
const
Icon
(
Icons
.
headset_mic
,
size:
20
),
title:
const
Text
(
'在线客服'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
settingCubit
.
goCs
();
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
trailing:
const
Icon
(
Icons
.
arrow_forward_ios
,
size:
14
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
],
),
),
const
SizedBox
(
height:
8
),
Card
(
margin:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
2
),
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
6
),
),
child:
Column
(
children:
[
ListTile
(
leading:
const
Icon
(
Icons
.
cleaning_services
,
size:
20
),
title:
const
Text
(
'清理缓存'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
_showClearCacheDialog
(
context
,
settingCubit
);
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
const
Divider
(
height:
1
,
thickness:
0.5
,
indent:
16
,
endIndent:
16
),
ListTile
(
leading:
const
Icon
(
Icons
.
logout
,
size:
20
),
title:
const
Text
(
'退出登录'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
settingCubit
.
logout
();
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
],
),
),
const
SizedBox
(
height:
8
),
EnvConfig
.
isDev
()
?
Card
(
margin:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
2
),
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
6
),
),
child:
Column
(
children:
[
ListTile
(
leading:
const
Icon
(
Icons
.
timeline
,
size:
20
),
title:
const
Text
(
'切换日志模式'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
settingCubit
.
handleToggleDebug
();
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
],
),
)
:
const
SizedBox
(),
],
),
),
),
const
Divider
(),
Container
(
width:
double
.
infinity
,
padding:
const
EdgeInsets
.
all
(
16
),
child:
Center
(
child:
Column
(
children:
[
if
(
EnvConfig
.
isDev
())
...[
const
Text
(
'开发版'
,
style:
TextStyle
(
color:
Colors
.
grey
,
fontSize:
14
,
),
),
const
SizedBox
(
height:
4
),
],
const
Text
(
'V1.0'
,
style:
TextStyle
(
color:
Colors
.
grey
,
fontSize:
12
,
),
),
const
SizedBox
(
height:
8
),
const
Text
(
'粤ICP备2025475184号-15A'
,
style:
TextStyle
(
color:
Colors
.
grey
,
fontSize:
12
),
),
const
SizedBox
(
height:
8
),
const
Text
(
'Copyright © 中山班小二科技有限公司'
,
style:
TextStyle
(
color:
Colors
.
grey
,
fontSize:
12
),
),
const
SizedBox
(
height:
8
),
Text
(
'
${Constant.appVersion}
-
${state.h5Version}
'
,
style:
const
TextStyle
(
color:
Colors
.
grey
,
fontSize:
12
,
),
),
const
SizedBox
(
height:
10
),
],
),
),
),
],
),
);
},
),
);
}
void
_showClearCacheDialog
(
BuildContext
context
,
SettingCubit
settingCubit
)
{
showDialog
(
context:
context
,
builder:
(
BuildContext
ctx
)
{
return
AlertDialog
(
title:
const
Text
(
'清理缓存'
),
content:
const
Text
(
'清理缓存后将需要重新登录,是否继续?'
),
actions:
<
Widget
>[
TextButton
(
child:
const
Text
(
'取消'
),
onPressed:
()
{
Navigator
.
of
(
ctx
).
pop
();
},
),
TextButton
(
child:
const
Text
(
'确认'
),
onPressed:
()
{
Navigator
.
of
(
ctx
).
pop
();
settingCubit
.
clearStorage
();
settingCubit
.
logout
();
},
),
],
);
},
);
}
}
lib/ui/pages/web_page.dart
View file @
5a44fc5
import
'dart:io'
;
import
'dart:io'
;
import
'package:appframe/bloc/web_cubit.dart'
;
import
'package:appframe/bloc/web_cubit.dart'
;
import
'package:appframe/config/constant.dart'
;
import
'package:appframe/config/env_config.dart'
;
import
'package:appframe/config/env_config.dart'
;
import
'package:appframe/config/locator.dart'
;
import
'package:appframe/config/locator.dart'
;
import
'package:appframe/config/routes.dart'
;
import
'package:appframe/config/routes.dart'
;
...
@@ -12,9 +11,7 @@ import 'package:shared_preferences/shared_preferences.dart';
...
@@ -12,9 +11,7 @@ import 'package:shared_preferences/shared_preferences.dart';
import
'package:webview_flutter/webview_flutter.dart'
;
import
'package:webview_flutter/webview_flutter.dart'
;
class
WebPage
extends
StatelessWidget
{
class
WebPage
extends
StatelessWidget
{
WebPage
({
super
.
key
});
const
WebPage
({
super
.
key
});
final
GlobalKey
<
ScaffoldState
>
_scaffoldKey
=
GlobalKey
<
ScaffoldState
>();
@override
@override
Widget
build
(
BuildContext
buildContext
)
{
Widget
build
(
BuildContext
buildContext
)
{
...
@@ -56,9 +53,7 @@ class WebPage extends StatelessWidget {
...
@@ -56,9 +53,7 @@ class WebPage extends StatelessWidget {
child:
BlocConsumer
<
WebCubit
,
WebState
>(
child:
BlocConsumer
<
WebCubit
,
WebState
>(
builder:
(
ctx
,
state
)
{
builder:
(
ctx
,
state
)
{
final
scaffold
=
Scaffold
(
final
scaffold
=
Scaffold
(
key:
_scaffoldKey
,
appBar:
_buildAppBar
(
ctx
,
state
),
appBar:
_buildAppBar
(
ctx
,
state
),
endDrawer:
_buildDrawer
(
ctx
,
state
),
body:
Stack
(
body:
Stack
(
children:
[
children:
[
state
.
loaded
state
.
loaded
...
@@ -183,291 +178,14 @@ class WebPage extends StatelessWidget {
...
@@ -183,291 +178,14 @@ class WebPage extends StatelessWidget {
},
},
)
)
:
null
),
:
null
),
);
actions:
[
}
IconButton
(
icon:
const
Icon
(
Icons
.
settings
),
Drawer
_buildDrawer
(
BuildContext
ctx
,
WebState
state
)
{
final
screenSize
=
MediaQuery
.
of
(
ctx
).
size
;
return
Drawer
(
width:
screenSize
.
width
>
600
?
400
:
screenSize
.
width
*
0.8
,
// Pad 上给一个固定最大宽度
child:
Column
(
children:
[
DrawerHeader
(
decoration:
BoxDecoration
(
color:
Color
(
0xFF7691FA
),
),
child:
Align
(
alignment:
Alignment
.
centerLeft
,
child:
Text
(
'设置'
,
style:
TextStyle
(
// color: Theme.of(ctx).colorScheme.onPrimary,
fontSize:
24
,
color:
Colors
.
white
,
),
),
),
),
Expanded
(
child:
SingleChildScrollView
(
child:
Column
(
crossAxisAlignment:
CrossAxisAlignment
.
stretch
,
children:
[
Card
(
margin:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
2
),
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
6
),
),
child:
Column
(
children:
[
ListTile
(
leading:
const
Icon
(
Icons
.
lock
,
size:
20
),
title:
const
Text
(
'账号与安全'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
Navigator
.
pop
(
ctx
);
ctx
.
read
<
WebCubit
>().
goAccount
();
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
trailing:
Icon
(
Icons
.
arrow_forward_ios
,
size:
14
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
],
),
),
SizedBox
(
height:
8
),
Card
(
margin:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
2
),
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
6
),
),
child:
Column
(
children:
[
ListTile
(
leading:
const
Icon
(
Icons
.
book_outlined
,
size:
20
),
title:
const
Text
(
'版本记录'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
Navigator
.
pop
(
ctx
);
router
.
push
(
'/link'
,
extra:
{
'url'
:
'https://bxr.banxiaoer.net/apps/versions.html'
,
'title'
:
'版本记录'
},
);
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
trailing:
Icon
(
Icons
.
arrow_forward_ios
,
size:
14
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
Divider
(
height:
1
,
thickness:
0.5
,
indent:
16
,
endIndent:
16
),
ListTile
(
leading:
const
Icon
(
Icons
.
book_outlined
,
size:
20
),
title:
const
Text
(
'用户协议'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
Navigator
.
pop
(
ctx
);
router
.
push
(
'/link'
,
extra:
{
'url'
:
'https://bxr.banxiaoer.net/apps/useragreement.html'
,
'title'
:
'用户协议'
},
);
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
trailing:
Icon
(
Icons
.
arrow_forward_ios
,
size:
14
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
Divider
(
height:
1
,
thickness:
0.5
,
indent:
16
,
endIndent:
16
),
ListTile
(
leading:
const
Icon
(
Icons
.
book_outlined
,
size:
20
),
title:
const
Text
(
'隐私设置'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
Navigator
.
pop
(
ctx
);
router
.
push
(
'/link'
,
extra:
{
'url'
:
'https://bxr.banxiaoer.net/apps/privacysettings.html'
,
'title'
:
'隐私设置'
},
);
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
trailing:
Icon
(
Icons
.
arrow_forward_ios
,
size:
14
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
Divider
(
height:
1
,
thickness:
0.5
,
indent:
16
,
endIndent:
16
),
ListTile
(
leading:
const
Icon
(
Icons
.
book_outlined
,
size:
20
),
title:
const
Text
(
'关于'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
Navigator
.
pop
(
ctx
);
router
.
push
(
'/link'
,
extra:
{
'url'
:
'https://bxr.banxiaoer.net/apps/produce.html'
,
'title'
:
'关于'
},
);
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
trailing:
Icon
(
Icons
.
arrow_forward_ios
,
size:
14
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
],
),
),
SizedBox
(
height:
8
),
Card
(
margin:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
2
),
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
6
),
),
child:
Column
(
children:
[
ListTile
(
leading:
const
Icon
(
Icons
.
headset_mic
,
size:
20
),
title:
const
Text
(
'在线客服'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
Navigator
.
pop
(
ctx
);
ctx
.
read
<
WebCubit
>().
goCs
();
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
trailing:
Icon
(
Icons
.
arrow_forward_ios
,
size:
14
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
],
),
),
SizedBox
(
height:
8
),
Card
(
margin:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
2
),
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
6
),
),
child:
Column
(
children:
[
ListTile
(
leading:
const
Icon
(
Icons
.
cleaning_services
,
size:
20
),
title:
const
Text
(
'清理缓存'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
Navigator
.
pop
(
ctx
);
_showClearCacheDialog
(
ctx
);
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
Divider
(
height:
1
,
thickness:
0.5
,
indent:
16
,
endIndent:
16
),
ListTile
(
leading:
const
Icon
(
Icons
.
logout
,
size:
20
),
title:
const
Text
(
'退出登录'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
Navigator
.
pop
(
ctx
);
ctx
.
read
<
WebCubit
>().
logout
();
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
),
],
),
),
SizedBox
(
height:
8
),
EnvConfig
.
isDev
()
?
Card
(
margin:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
2
),
shape:
RoundedRectangleBorder
(
borderRadius:
BorderRadius
.
circular
(
6
),
),
child:
Column
(
children:
[
ListTile
(
leading:
const
Icon
(
Icons
.
timeline
,
size:
20
),
title:
const
Text
(
'切换日志模式'
,
style:
TextStyle
(
fontSize:
14
)),
onTap:
()
{
Navigator
.
pop
(
ctx
);
ctx
.
read
<
WebCubit
>().
handleToggleDebug
();
},
contentPadding:
const
EdgeInsets
.
symmetric
(
horizontal:
16
,
vertical:
4
),
// trailing: Icon(Icons.arrow_forward_ios, size: 14),
dense:
true
,
visualDensity:
VisualDensity
.
compact
,
// 视觉密度设为紧凑
),
],
),
)
:
SizedBox
(),
],
),
),
),
const
Divider
(),
Container
(
width:
double
.
infinity
,
padding:
const
EdgeInsets
.
all
(
1
),
child:
Center
(
child:
Column
(
children:
[
if
(
EnvConfig
.
isDev
())
...[
Text
(
'开发版'
,
style:
TextStyle
(
color:
Colors
.
grey
,
fontSize:
14
,
),
),
SizedBox
(
height:
4
),
],
Text
(
'V1.0'
,
style:
TextStyle
(
color:
Colors
.
grey
,
fontSize:
12
,
),
),
SizedBox
(
height:
8
),
Text
(
'粤ICP备2025475184号-15A'
,
),
SizedBox
(
height:
8
),
Text
(
'Copyright © 中山班小二科技有限公司'
,
),
SizedBox
(
height:
8
),
Text
(
'
${Constant.appVersion}
-
${state.h5Version}
'
,
style:
TextStyle
(
color:
Colors
.
grey
,
fontSize:
12
,
),
),
SizedBox
(
height:
10
),
],
),
),
),
]));
}
void
_showClearCacheDialog
(
BuildContext
ctx
)
{
showDialog
(
context:
ctx
,
builder:
(
BuildContext
context
)
{
return
AlertDialog
(
title:
Text
(
'清理缓存'
),
content:
Text
(
'清理缓存后将需要重新登录,是否继续?'
),
actions:
<
Widget
>[
TextButton
(
child:
Text
(
'取消'
),
onPressed:
()
{
onPressed:
()
{
Navigator
.
of
(
context
).
pop
();
router
.
push
(
'/setting'
);
},
),
TextButton
(
child:
Text
(
'确认'
),
onPressed:
()
{
Navigator
.
of
(
context
).
pop
();
var
webCubit
=
ctx
.
read
<
WebCubit
>();
webCubit
.
clearStorage
();
webCubit
.
goLogin
();
},
},
),
),
],
],
);
);
},
);
}
}
}
}
Write
Preview
Styling with
Markdown
is supported
Attach a file
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 post a comment