flutter_autoscaler 0.0.3
flutter_autoscaler: ^0.0.3 copied to clipboard
A responsive layout and typography scaling solution for Flutter applications across mobile, desktop, and web.
import 'package:flutter/material.dart';
import 'package:flutter_autoscaler/flutter_autoscaler.dart';
void main() {
runApp(const ExampleApp());
}
class ExampleApp extends StatelessWidget {
const ExampleApp({super.key});
@override
Widget build(BuildContext context) {
return AutoScale(
designWidth: 390,
designHeight: 844,
minFontScale: 0.8,
maxFontScale: 1.6,
clampFontScale: true,
fontScaleMode: FontScaleMode.width,
child: MaterialApp(
title: 'AutoScale Demo',
debugShowCheckedModeBanner: false,
theme: ThemeData(
brightness: Brightness.dark,
scaffoldBackgroundColor: const Color(0xFF0F172A),
colorScheme: const ColorScheme.dark(
primary: Color(0xFF6366F1),
secondary: Color(0xFF38BDF8),
surface: Color(0xFF1E293B),
),
useMaterial3: true,
),
home: const DemoHomeScreen(),
),
);
}
}
class DemoHomeScreen extends StatefulWidget {
const DemoHomeScreen({super.key});
@override
State<DemoHomeScreen> createState() => _DemoHomeScreenState();
}
class _DemoHomeScreenState extends State<DemoHomeScreen> {
@override
Widget build(BuildContext context) {
final metrics = AutoScale.of(context);
return Scaffold(
appBar: AppBar(
backgroundColor: const Color(0xFF1E293B),
elevation: 0,
title: const Text('Flutter AutoScale macOS Demo'),
),
body: SingleChildScrollView(
padding: 24.autoPadAll,
child: Center(
child: ConstrainedBox(
constraints: const BoxConstraints(maxWidth: 800),
child: Column(
crossAxisAlignment: CrossAxisAlignment.stretch,
children: [
// Info header card
Container(
padding: 20.autoPadAll,
decoration: BoxDecoration(
color: const Color(0xFF1E293B),
borderRadius: 16.autoCircular,
border: Border.all(color: const Color(0xFF334155)),
),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
const Text(
'Live AutoScale Metrics',
style: TextStyle(
fontSize: 20,
fontWeight: FontWeight.bold,
color: Color(0xFFF8FAFC),
),
),
8.autoGapY,
const Text(
'Resize the macOS window to see responsive metrics update automatically.',
style: TextStyle(color: Color(0xFF94A3B8)),
),
16.autoGapY,
Wrap(
spacing: 12.sx,
runSpacing: 12.sy,
children: [
_MetricChip(
label: 'Screen Size',
value:
'${metrics.screenWidth.toStringAsFixed(0)} x ${metrics.screenHeight.toStringAsFixed(0)}',
),
_MetricChip(
label: 'Design Base',
value:
'${metrics.config.designWidth.toInt()} x ${metrics.config.designHeight.toInt()}',
),
_MetricChip(
label: 'Scale X (.sx)',
value: '${metrics.scaleWidth.toStringAsFixed(2)}x',
),
_MetricChip(
label: 'Scale Y (.sy)',
value: '${metrics.scaleHeight.toStringAsFixed(2)}x',
),
_MetricChip(
label: 'Scale Font (.sf)',
value: '${metrics.scaleFont.toStringAsFixed(2)}x',
),
_MetricChip(
label: 'Scale Radius (.sr)',
value: '${metrics.scaleRadius.toStringAsFixed(2)}x',
),
],
),
],
),
),
24.autoGapY,
// Demonstration Card
Container(
padding: 24.autoPadAll,
decoration: BoxDecoration(
color: const Color(0xFF1E293B),
borderRadius: 16.autoCircular,
border: Border.all(color: const Color(0xFF334155)),
),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
const Text(
'Extension Showcase',
style: TextStyle(
fontSize: 18,
fontWeight: FontWeight.bold,
color: Color(0xFFF8FAFC),
),
),
16.autoGapY,
// Horizontal scale demo
const Text(
'1. Width scaling (.sx):',
style: TextStyle(color: Color(0xFFCBD5E1)),
),
8.autoGapY,
Container(
height: 36.sy,
width: 250.sx,
padding: 12.autoPadX,
alignment: Alignment.centerLeft,
decoration: BoxDecoration(
color: const Color(0xFF6366F1).withValues(alpha: 0.2),
borderRadius: 8.autoCircular,
border: Border.all(color: const Color(0xFF6366F1)),
),
child: Text(
'Width: 250.sx (${250.sx.toStringAsFixed(1)}px)',
style: const TextStyle(color: Color(0xFFE0E7FF)),
),
),
16.autoGapY,
// Vertical scale demo
const Text(
'2. Height & Padding (.sy, .autoPadY):',
style: TextStyle(color: Color(0xFFCBD5E1)),
),
8.autoGapY,
Container(
width: double.infinity,
height: 50.sy,
padding: 14.autoPadY,
alignment: Alignment.center,
decoration: BoxDecoration(
color: const Color(0xFF38BDF8).withValues(alpha: 0.2),
borderRadius: 8.autoCircular,
border: Border.all(color: const Color(0xFF38BDF8)),
),
child: Text(
'Height: 50.sy (${50.sy.toStringAsFixed(1)}px) with 14.autoPadY',
style: const TextStyle(color: Color(0xFFE0F2FE)),
),
),
16.autoGapY,
// Font scaling demo
const Text(
'3. Font scaling (automatic via wrapper + .sf):',
style: TextStyle(color: Color(0xFFCBD5E1)),
),
8.autoGapY,
Container(
padding: 16.autoPadAll,
width: double.infinity,
decoration: BoxDecoration(
color: const Color(0xFF0F172A),
borderRadius: 12.autoCircular,
),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: [
const Text(
'Automatic child text scaling (22px)',
style: TextStyle(
fontSize: 22,
fontWeight: FontWeight.bold,
),
),
6.autoGapY,
Text(
'Explicit font scale via TextStyle: 14.sf',
style: const TextStyle(
color: Color(0xFF94A3B8),
).copyWith(fontSize: 14.sf),
),
],
),
),
20.autoGapY,
// Subtree wrapper demo
const Text(
'4. Isolated Subtree with .autoScale():',
style: TextStyle(color: Color(0xFFCBD5E1)),
),
8.autoGapY,
Container(
padding: 16.autoPadAll,
decoration: BoxDecoration(
color: const Color(0xFF14532D).withValues(alpha: 0.3),
borderRadius: 12.autoCircular,
border: Border.all(color: const Color(0xFF22C55E)),
),
child: const Row(
children: [
Icon(Icons.tune, color: Color(0xFF4ADE80)),
SizedBox(width: 12),
Expanded(
child: Text(
'This card is wrapped in its own .autoScale(minFontScale: 1.1) scope!',
style: TextStyle(color: Color(0xFFDCFCE7)),
),
),
],
),
).autoScale(minFontScale: 1.1, maxFontScale: 1.8),
],
),
),
],
),
),
),
),
);
}
}
class _MetricChip extends StatelessWidget {
const _MetricChip({
required this.label,
required this.value,
});
final String label;
final String value;
@override
Widget build(BuildContext context) {
return Container(
padding: const EdgeInsets.symmetric(horizontal: 12, vertical: 8),
decoration: BoxDecoration(
color: const Color(0xFF0F172A),
borderRadius: BorderRadius.circular(8),
border: Border.all(color: const Color(0xFF334155)),
),
child: Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisSize: MainAxisSize.min,
children: [
Text(
label,
style: const TextStyle(
fontSize: 11,
color: Color(0xFF94A3B8),
),
),
const SizedBox(height: 2),
Text(
value,
style: const TextStyle(
fontSize: 14,
fontWeight: FontWeight.bold,
color: Color(0xFFF8FAFC),
),
),
],
),
);
}
}