window_toolkit 0.1.1 window_toolkit: ^0.1.1 copied to clipboard
Toolkit simplifies customization of native user interface components for macOS applications.
import 'package:flutter/material.dart';
import 'package:window_toolkit/window_toolkit.dart';
Future<void> main() async {
WidgetsFlutterBinding.ensureInitialized();
WindowToolkit toolkit = WindowToolkit.instance;
await toolkit.initialize();
await toolkit.titlebar(Titlebar(style: TitlebarStyle.expand));
await toolkit.window(
Window(minimumSize: Size(800, 700), size: (Size(800, 700)), center: true),
);
runApp(App());
}
class App extends StatelessWidget {
const App({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(debugShowCheckedModeBanner: false, home: Home());
}
}
class Home extends StatefulWidget {
const Home({super.key});
@override
State<Home> createState() => _HomeState();
}
class _HomeState extends State<Home> {
final WindowToolkit _toolkit = WindowToolkit.instance;
double _opacity = 1.0;
TitlebarStyle _titlebarStyle = TitlebarStyle.expand;
@override
Widget build(BuildContext context) {
TextTheme texts = Theme.of(context).textTheme;
Size size = MediaQuery.sizeOf(context);
return Scaffold(
appBar: AppBar(),
body: Center(
child: ConstrainedBox(
constraints: BoxConstraints(maxWidth: size.width / 1.2),
child: Column(
children: [
_buildTitlebarSelector(texts),
_gap(gap: 60),
_buildWindowActions(texts),
_gap(gap: 60),
_buildWindowSettings(texts),
_gap(gap: 60),
_buildOpacitySlider(texts)
],
),
),
),
);
}
Widget _gap({double? gap}) => SizedBox(height: gap ?? 20);
Widget _buildTitlebarSelector(TextTheme texts) {
return Column(
children: [
Text("Title Bar Style", style: texts.headlineMedium),
_gap(),
Row(
mainAxisAlignment: MainAxisAlignment.center,
children: TitlebarStyle.values.map((style) {
return Padding(
padding: EdgeInsets.symmetric(horizontal: 10),
child: Row(
children: [
Radio<TitlebarStyle>(
value: style,
groupValue: _titlebarStyle,
onChanged: (style) async {
setState(() => _titlebarStyle = style!);
await _toolkit.titlebar(Titlebar(style: _titlebarStyle));
},
),
Text(
style.toString().split('.').last[0].toUpperCase() + style.toString().split('.').last.substring(1),
)
],
),
);
}).toList(),
),
],
);
}
Widget _buildWindowActions(TextTheme texts) {
return Column(
children: [
Text("Window Actions", style: texts.headlineMedium),
_gap(),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: [
_buildActionButton('Destroy', () => _toolkit.perform.destroy()),
_buildActionButton('Close', () => _toolkit.perform.close()),
_buildActionButton('Minimize', () => _toolkit.perform.minimize()),
_buildActionButton(
'Maximize',
() async {
bool isMaximized = await _toolkit.check.maximized();
isMaximized ? _toolkit.perform.unmaximize() : _toolkit.perform.maximize();
},
),
_buildActionButton('Fullscreen', () => _toolkit.perform.fullscreen()),
],
),
],
);
}
Widget _buildWindowSettings(TextTheme texts) {
return Column(
children: [
Text("Window Settings", style: texts.headlineMedium),
_gap(),
Row(
mainAxisAlignment: MainAxisAlignment.spaceEvenly,
children: [
_buildToggleActionButton('Movable', _toolkit.define.movable, _toolkit.check.movable),
_buildToggleActionButton('Closable', _toolkit.define.closable, _toolkit.check.closable),
_buildToggleActionButton('Minimizable', _toolkit.define.minimizable, _toolkit.check.minimizable),
_buildToggleActionButton('Maximizable', _toolkit.define.maximizable, _toolkit.check.maximizable),
],
),
],
);
}
Widget _buildActionButton(String text, VoidCallback onPressed) {
return TextButton(
onPressed: onPressed,
child: Text(text),
);
}
Widget _buildToggleActionButton(String text, Future<void> Function(bool) define, Future<bool> Function() check) {
return FutureBuilder<bool>(
future: check(),
builder: (context, snapshot) {
bool isEnabled = snapshot.data ?? false;
return TextButton(
onPressed: () async {
await define(!isEnabled);
setState(() {});
},
child: Text(isEnabled ? '$text: ON' : '$text: OFF'),
);
},
);
}
Widget _buildOpacitySlider(TextTheme texts) {
return Column(
children: [
Text("Window Opacity", style: texts.headlineMedium),
_gap(),
Slider(
value: _opacity,
min: 0.0,
max: 1.0,
divisions: 10,
label: "${(_opacity * 100).round()}%",
onChanged: (value) async {
setState(() => _opacity = value);
await _toolkit.define.opacity(value);
},
),
],
);
}
}
// import 'package:flutter/material.dart';
// import 'dart:async';
// import 'package:flutter/services.dart';
// import 'package:window_toolkit/window_toolkit.dart';
// void main() {
// runApp(const MyApp());
// }
// class MyApp extends StatefulWidget {
// const MyApp({super.key});
// @override
// State<MyApp> createState() => _MyAppState();
// }
// class _MyAppState extends State<MyApp> {
// String _platformVersion = 'Unknown';
// final _windowToolkitPlugin = WindowToolkit();
// @override
// void initState() {
// super.initState();
// initPlatformState();
// }
// // Platform messages are asynchronous, so we initialize in an async method.
// Future<void> initPlatformState() async {
// String platformVersion;
// // Platform messages may fail, so we use a try/catch PlatformException.
// // We also handle the message potentially returning null.
// try {
// platformVersion = await _windowToolkitPlugin.getPlatformVersion() ?? 'Unknown platform version';
// } on PlatformException {
// platformVersion = 'Failed to get platform version.';
// }
// // If the widget was removed from the tree while the asynchronous platform
// // message was in flight, we want to discard the reply rather than calling
// // setState to update our non-existent appearance.
// if (!mounted) return;
// setState(() {
// _platformVersion = platformVersion;
// });
// }
// @override
// Widget build(BuildContext context) {
// return MaterialApp(
// home: Scaffold(
// appBar: AppBar(
// title: const Text('Plugin example app'),
// ),
// body: Center(
// child: Text('Running on: $_platformVersion\n'),
// ),
// ),
// );
// }
// }