mirror of
https://github.com/lollipopkit/flutter_server_box.git
synced 2025-12-17 07:14:28 +01:00
New UI.
This commit is contained in:
@@ -1,13 +1,16 @@
|
||||
import 'package:after_layout/after_layout.dart';
|
||||
import 'package:flutter/material.dart';
|
||||
import 'package:flutter_advanced_drawer/flutter_advanced_drawer.dart';
|
||||
import 'package:get_it/get_it.dart';
|
||||
import 'package:toolbox/core/analysis.dart';
|
||||
import 'package:toolbox/core/build_mode.dart';
|
||||
import 'package:toolbox/core/route.dart';
|
||||
import 'package:toolbox/core/update.dart';
|
||||
import 'package:toolbox/core/utils.dart';
|
||||
import 'package:toolbox/data/model/app/navigation_item.dart';
|
||||
import 'package:toolbox/data/provider/server.dart';
|
||||
import 'package:toolbox/data/res/build_data.dart';
|
||||
import 'package:toolbox/data/res/color.dart';
|
||||
import 'package:toolbox/data/res/icon/common.dart';
|
||||
import 'package:toolbox/data/res/tab.dart';
|
||||
import 'package:toolbox/data/res/url.dart';
|
||||
@@ -36,23 +39,26 @@ class _MyHomePageState extends State<MyHomePage>
|
||||
SingleTickerProviderStateMixin,
|
||||
AfterLayoutMixin,
|
||||
WidgetsBindingObserver {
|
||||
late final TabController _tabController;
|
||||
late final ServerProvider _serverProvider;
|
||||
late final PageController _pageController;
|
||||
late final AdvancedDrawerController _advancedDrawerController;
|
||||
late int _selectIndex;
|
||||
late double _width;
|
||||
|
||||
@override
|
||||
void initState() {
|
||||
super.initState();
|
||||
_serverProvider = locator<ServerProvider>();
|
||||
WidgetsBinding.instance?.addObserver(this);
|
||||
_tabController = TabController(
|
||||
initialIndex: locator<SettingStore>().launchPage.fetch()!,
|
||||
length: tabs.length,
|
||||
vsync: this);
|
||||
_tabController.addListener(() {
|
||||
if (_tabController.index == 0) {
|
||||
FocusScope.of(context).unfocus();
|
||||
}
|
||||
});
|
||||
_selectIndex = locator<SettingStore>().launchPage.fetch()!;
|
||||
_pageController = PageController(initialPage: _selectIndex);
|
||||
_advancedDrawerController = AdvancedDrawerController();
|
||||
}
|
||||
|
||||
@override
|
||||
void didChangeDependencies() {
|
||||
super.didChangeDependencies();
|
||||
_width = MediaQuery.of(context).size.width;
|
||||
}
|
||||
|
||||
@override
|
||||
@@ -77,37 +83,123 @@ class _MyHomePageState extends State<MyHomePage>
|
||||
Widget build(BuildContext context) {
|
||||
setTransparentNavigationBar(context);
|
||||
super.build(context);
|
||||
return Scaffold(
|
||||
appBar: AppBar(
|
||||
title: GestureDetector(
|
||||
onLongPress: () =>
|
||||
AppRoute(const DebugPage(), 'Debug Page').go(context),
|
||||
child: const Text(BuildData.name),
|
||||
),
|
||||
bottom: TabBar(
|
||||
indicatorColor: widget.primaryColor,
|
||||
tabs: tabs.map((e) => Tab(text: e)).toList(),
|
||||
controller: _tabController,
|
||||
return AdvancedDrawer(
|
||||
controller: _advancedDrawerController,
|
||||
animationCurve: Curves.easeInOutCirc,
|
||||
animationDuration: const Duration(milliseconds: 300),
|
||||
animateChildDecoration: true,
|
||||
rtlOpening: false,
|
||||
disabledGestures: true,
|
||||
childDecoration: const BoxDecoration(
|
||||
// NOTICE: Uncomment if you want to add shadow behind the page.
|
||||
// Keep in mind that it may cause animation jerks.
|
||||
boxShadow: <BoxShadow>[
|
||||
BoxShadow(
|
||||
color: Colors.black12,
|
||||
blurRadius: 0.0,
|
||||
),
|
||||
],
|
||||
borderRadius: BorderRadius.all(Radius.circular(16)),
|
||||
),
|
||||
drawer: _buildDrawer(),
|
||||
child: Scaffold(
|
||||
appBar: AppBar(
|
||||
title: Text(tabItems[_selectIndex].title),
|
||||
actions: [
|
||||
IconButton(
|
||||
icon: const Icon(Icons.developer_mode, size: 23),
|
||||
tooltip: 'Debug',
|
||||
onPressed: () =>
|
||||
AppRoute(const DebugPage(), 'Debug Page').go(context),
|
||||
),
|
||||
],
|
||||
leading: IconButton(
|
||||
onPressed: () => _advancedDrawerController.showDrawer(),
|
||||
icon: ValueListenableBuilder<AdvancedDrawerValue>(
|
||||
valueListenable: _advancedDrawerController,
|
||||
builder: (_, value, __) {
|
||||
return AnimatedSwitcher(
|
||||
duration: const Duration(milliseconds: 250),
|
||||
child: Icon(
|
||||
value.visible ? Icons.clear : Icons.menu,
|
||||
key: ValueKey<bool>(value.visible),
|
||||
),
|
||||
);
|
||||
},
|
||||
),
|
||||
),
|
||||
),
|
||||
body: PageView(
|
||||
physics: const ClampingScrollPhysics(),
|
||||
controller: _pageController,
|
||||
onPageChanged: (i) {
|
||||
FocusScope.of(context).unfocus();
|
||||
_selectIndex = i;
|
||||
setState(() {});
|
||||
},
|
||||
children: const [ServerPage(), ConvertPage(), PingPage()],
|
||||
),
|
||||
bottomNavigationBar: _buildBottom(context),
|
||||
));
|
||||
}
|
||||
|
||||
Widget _buildItem(int idx, NavigationItem item, bool isSelected) {
|
||||
bool isDarkMode = Theme.of(context).brightness == Brightness.dark;
|
||||
final width = _width / tabItems.length;
|
||||
return AnimatedContainer(
|
||||
duration: const Duration(milliseconds: 377),
|
||||
curve: Curves.fastOutSlowIn,
|
||||
height: 50,
|
||||
width: isSelected ? width : width - 17,
|
||||
decoration: BoxDecoration(
|
||||
color: isSelected
|
||||
? isDarkMode
|
||||
? Colors.white12
|
||||
: Colors.black.withOpacity(0.07)
|
||||
: Colors.transparent,
|
||||
borderRadius: const BorderRadius.all(Radius.circular(50))),
|
||||
child: IconButton(
|
||||
icon: Icon(item.icon),
|
||||
tooltip: item.title,
|
||||
splashRadius: width / 3.3,
|
||||
padding: const EdgeInsets.only(left: 17, right: 17),
|
||||
onPressed: () {
|
||||
setState(() {
|
||||
_pageController.animateToPage(idx,
|
||||
duration: const Duration(milliseconds: 677),
|
||||
curve: Curves.fastLinearToSlowEaseIn);
|
||||
});
|
||||
},
|
||||
),
|
||||
drawer: _buildDrawer(),
|
||||
body: TabBarView(controller: _tabController, children: [
|
||||
ServerPage(_tabController),
|
||||
const ConvertPage(),
|
||||
const PingPage()
|
||||
]),
|
||||
);
|
||||
}
|
||||
|
||||
Widget _buildBottom(BuildContext context) {
|
||||
return SafeArea(
|
||||
child: Container(
|
||||
height: 56,
|
||||
padding: const EdgeInsets.only(left: 8, top: 4, bottom: 4, right: 8),
|
||||
width: _width,
|
||||
child: Row(
|
||||
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
|
||||
children: tabItems.map((item) {
|
||||
int itemIndex = tabItems.indexOf(item);
|
||||
return _buildItem(itemIndex, item, _selectIndex == itemIndex);
|
||||
}).toList(),
|
||||
),
|
||||
));
|
||||
}
|
||||
|
||||
Widget _buildDrawer() {
|
||||
return Drawer(
|
||||
child: ListView(
|
||||
padding: EdgeInsets.zero,
|
||||
return SafeArea(
|
||||
child: Column(
|
||||
mainAxisAlignment: MainAxisAlignment.center,
|
||||
children: [
|
||||
UserAccountsDrawerHeader(
|
||||
accountName: const Text(BuildData.name),
|
||||
accountEmail: Text(_buildVersionStr()),
|
||||
currentAccountPicture: _buildIcon(),
|
||||
_buildIcon(),
|
||||
const Text(BuildData.name),
|
||||
Text(_buildVersionStr()),
|
||||
SizedBox(
|
||||
height: MediaQuery.of(context).size.height * 0.07,
|
||||
),
|
||||
ListTile(
|
||||
leading: const Icon(Icons.settings),
|
||||
@@ -149,9 +241,19 @@ class _MyHomePageState extends State<MyHomePage>
|
||||
}
|
||||
|
||||
Widget _buildIcon() {
|
||||
return ConstrainedBox(
|
||||
constraints: const BoxConstraints(maxHeight: 60, maxWidth: 60),
|
||||
child: appIcon,
|
||||
return Stack(
|
||||
alignment: Alignment.center,
|
||||
children: [
|
||||
ConstrainedBox(
|
||||
constraints: const BoxConstraints(maxHeight: 53, maxWidth: 53),
|
||||
child: Container(
|
||||
color: primaryColor,
|
||||
)),
|
||||
ConstrainedBox(
|
||||
constraints: const BoxConstraints(maxHeight: 83, maxWidth: 83),
|
||||
child: appIcon,
|
||||
)
|
||||
],
|
||||
);
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user