// Copyright 2014 The Flutter Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

import 'package:flutter/material.dart';
import 'package:flutter/scheduler.dart' show timeDilation;

final Map<int, Color> m2SwatchColors = <int, Color>{
  50: const Color(0xfff2e7fe),
  100: const Color(0xffd7b7fd),
  200: const Color(0xffbb86fc),
  300: const Color(0xff9e55fc),
  400: const Color(0xff7f22fd),
  500: const Color(0xff6200ee),
  600: const Color(0xff4b00d1),
  700: const Color(0xff3700b3),
  800: const Color(0xff270096),
  900: const Color(0xff270096),
};
final MaterialColor m2Swatch = MaterialColor(m2SwatchColors[500]!.value, m2SwatchColors);

void main() => runApp(const MyApp());

class MyApp extends StatelessWidget {
  const MyApp({super.key});

  static const String _title = 'Density Test';

  @override
  Widget build(BuildContext context) {
    return const MaterialApp(
      title: _title,
      home: MyHomePage(title: _title),
    );
  }
}

class MyHomePage extends StatefulWidget {
  const MyHomePage({super.key, required this.title});

  final String title;

  @override
  State<MyHomePage> createState() => _MyHomePageState();
}

class OptionModel extends ChangeNotifier {
  double get size => _size;
  double _size = 1.0;
  set size(double size) {
    if (size != _size) {
      _size = size;
      notifyListeners();
    }
  }

  VisualDensity get density => _density;
  VisualDensity _density = VisualDensity.standard;
  set density(VisualDensity density) {
    if (density != _density) {
      _density = density;
      notifyListeners();
    }
  }

  bool get enable => _enable;
  bool _enable = true;
  set enable(bool enable) {
    if (enable != _enable) {
      _enable = enable;
      notifyListeners();
    }
  }

  bool get slowAnimations => _slowAnimations;
  bool _slowAnimations = false;
  set slowAnimations(bool slowAnimations) {
    if (slowAnimations != _slowAnimations) {
      _slowAnimations = slowAnimations;
      notifyListeners();
    }
  }

  bool get rtl => _rtl;
  bool _rtl = false;
  set rtl(bool rtl) {
    if (rtl != _rtl) {
      _rtl = rtl;
      notifyListeners();
    }
  }

  bool get longText => _longText;
  bool _longText = false;
  set longText(bool longText) {
    if (longText != _longText) {
      _longText = longText;
      notifyListeners();
    }
  }

  void reset() {
    final OptionModel defaultModel = OptionModel();
    _size = defaultModel.size;
    _enable = defaultModel.enable;
    _slowAnimations = defaultModel.slowAnimations;
    _longText = defaultModel.longText;
    _density = defaultModel.density;
    _rtl = defaultModel.rtl;
    notifyListeners();
  }
}

class LabeledCheckbox extends StatelessWidget {
  const LabeledCheckbox({super.key, required this.label, this.onChanged, this.value});

  final String label;
  final ValueChanged<bool?>? onChanged;
  final bool? value;

  @override
  Widget build(BuildContext context) {
    return Row(
      mainAxisSize: MainAxisSize.min,
      children: <Widget>[
        Checkbox(
          onChanged: onChanged,
          value: value,
        ),
        Text(label),
      ],
    );
  }
}

class Options extends StatefulWidget {
  const Options(this.model, {super.key});

  final OptionModel model;

  @override
  State<Options> createState() => _OptionsState();
}

class _OptionsState extends State<Options> {
  @override
  void initState() {
    super.initState();
    widget.model.addListener(_modelChanged);
  }

  @override
  void didUpdateWidget(Options oldWidget) {
    super.didUpdateWidget(oldWidget);
    if (widget.model != oldWidget.model) {
      oldWidget.model.removeListener(_modelChanged);
      widget.model.addListener(_modelChanged);
    }
  }

  @override
  void dispose() {
    super.dispose();
    widget.model.removeListener(_modelChanged);
  }

  void _modelChanged() {
    setState(() {});
  }

  double sliderValue = 0.0;

  String _densityToProfile(VisualDensity density) {
    if (density == VisualDensity.standard) {
      return 'standard';
    } else if (density == VisualDensity.compact) {
      return 'compact';
    } else if (density == VisualDensity.comfortable) {
      return 'comfortable';
    }
    return 'custom';
  }

  VisualDensity _profileToDensity(String? profile) {
    switch (profile) {
      case 'standard':
        return VisualDensity.standard;
      case 'comfortable':
        return VisualDensity.comfortable;
      case 'compact':
        return VisualDensity.compact;
      case 'custom':
      default:
        return widget.model.density;
    }
  }

  @override
  Widget build(BuildContext context) {
    final SliderThemeData controlTheme = SliderTheme.of(context).copyWith(
      thumbColor: Colors.grey[50],
      activeTickMarkColor: Colors.deepPurple[200],
      activeTrackColor: Colors.deepPurple[300],
      inactiveTrackColor: Colors.grey[50],
    );

    return Padding(
      padding: const EdgeInsets.fromLTRB(5.0, 0.0, 5.0, 10.0),
      child: Builder(builder: (BuildContext context) {
        return DefaultTextStyle(
          style: TextStyle(color: Colors.grey[50]),
          child: Column(
            children: <Widget>[
              Padding(
                padding: const EdgeInsets.all(8.0),
                child: Row(
                  children: <Widget>[
                    const Text('Text Scale'),
                    Expanded(
                      child: SliderTheme(
                        data: controlTheme,
                        child: Slider(
                          label: '${widget.model.size}',
                          min: 0.5,
                          max: 3.0,
                          onChanged: (double value) {
                            widget.model.size = value;
                          },
                          value: widget.model.size,
                        ),
                      ),
                    ),
                    Text(
                      widget.model.size.toStringAsFixed(3),
                      style: TextStyle(color: Colors.grey[50]),
                    ),
                  ],
                ),
              ),
              Padding(
                padding: const EdgeInsets.all(8.0),
                child: Row(
                  children: <Widget>[
                    const Text('X Density'),
                    Expanded(
                      child: SliderTheme(
                        data: controlTheme,
                        child: Slider(
                          label: widget.model.density.horizontal.toStringAsFixed(1),
                          min: VisualDensity.minimumDensity,
                          max: VisualDensity.maximumDensity,
                          onChanged: (double value) {
                            widget.model.density = widget.model.density.copyWith(
                              horizontal: value,
                              vertical: widget.model.density.vertical,
                            );
                          },
                          value: widget.model.density.horizontal,
                        ),
                      ),
                    ),
                    Text(
                      widget.model.density.horizontal.toStringAsFixed(3),
                      style: TextStyle(color: Colors.grey[50]),
                    ),
                  ],
                ),
              ),
              Padding(
                padding: const EdgeInsets.all(8.0),
                child: Row(
                  children: <Widget>[
                    const Text('Y Density'),
                    Expanded(
                      child: SliderTheme(
                        data: controlTheme,
                        child: Slider(
                          label: widget.model.density.vertical.toStringAsFixed(1),
                          min: VisualDensity.minimumDensity,
                          max: VisualDensity.maximumDensity,
                          onChanged: (double value) {
                            widget.model.density = widget.model.density.copyWith(
                              horizontal: widget.model.density.horizontal,
                              vertical: value,
                            );
                          },
                          value: widget.model.density.vertical,
                        ),
                      ),
                    ),
                    Text(
                      widget.model.density.vertical.toStringAsFixed(3),
                      style: TextStyle(color: Colors.grey[50]),
                    ),
                  ],
                ),
              ),
              Wrap(
                alignment: WrapAlignment.center,
                crossAxisAlignment: WrapCrossAlignment.center,
                children: <Widget>[
                  Theme(
                    data: Theme.of(context).copyWith(canvasColor: Colors.grey[600]),
                    child: DropdownButton<String>(
                      style: TextStyle(color: Colors.grey[50]),
                      isDense: true,
                      onChanged: (String? value) {
                        widget.model.density = _profileToDensity(value);
                      },
                      items: const <DropdownMenuItem<String>>[
                        DropdownMenuItem<String>(
                          value: 'standard',
                          child: Text('Standard'),
                        ),
                        DropdownMenuItem<String>(value: 'comfortable', child: Text('Comfortable')),
                        DropdownMenuItem<String>(value: 'compact', child: Text('Compact')),
                        DropdownMenuItem<String>(value: 'custom', child: Text('Custom')),
                      ],
                      value: _densityToProfile(widget.model.density),
                    ),
                  ),
                  LabeledCheckbox(
                    label: 'Enabled',
                    onChanged: (bool? checked) {
                      widget.model.enable = checked ?? false;
                    },
                    value: widget.model.enable,
                  ),
                  LabeledCheckbox(
                    label: 'Slow',
                    onChanged: (bool? checked) {
                      widget.model.slowAnimations = checked ?? false;
                      Future<void>.delayed(const Duration(milliseconds: 150)).then((_) {
                        if (widget.model.slowAnimations) {
                          timeDilation = 20.0;
                        } else {
                          timeDilation = 1.0;
                        }
                      });
                    },
                    value: widget.model.slowAnimations,
                  ),
                  LabeledCheckbox(
                    label: 'RTL',
                    onChanged: (bool? checked) {
                      widget.model.rtl = checked ?? false;
                    },
                    value: widget.model.rtl,
                  ),
                  MaterialButton(
                    onPressed: () {
                      widget.model.reset();
                      sliderValue = 0.0;
                    },
                    child: Text('Reset', style: TextStyle(color: Colors.grey[50])),
                  ),
                ],
              ),
            ],
          ),
        );
      }),
    );
  }
}

class _ControlTile extends StatelessWidget {
  const _ControlTile({required this.label, required this.child});

  final String label;
  final Widget child;

  @override
  Widget build(BuildContext context) {
    return Center(
      child: Padding(
        padding: const EdgeInsets.all(8.0),
        child: Column(
          children: <Widget>[
            Align(
              alignment: AlignmentDirectional.topStart,
              child: Text(
                label,
                textAlign: TextAlign.start,
              ),
            ),
            child,
          ],
        ),
      ),
    );
  }
}

class _MyHomePageState extends State<MyHomePage> {
  static final GlobalKey<ScaffoldState> scaffoldKey = GlobalKey<ScaffoldState>();
  final OptionModel _model = OptionModel();
  final TextEditingController textController = TextEditingController();

  @override
  void initState() {
    super.initState();
    _model.addListener(_modelChanged);
  }

  @override
  void dispose() {
    super.dispose();
    _model.removeListener(_modelChanged);
  }

  void _modelChanged() {
    setState(() {});
  }

  double sliderValue = 0.0;
  List<bool> checkboxValues = <bool>[false, false, false, false];
  List<IconData> iconValues = <IconData>[Icons.arrow_back, Icons.play_arrow, Icons.arrow_forward];
  List<String> chipValues = <String>['Potato', 'Computer'];
  int radioValue = 0;

  @override
  Widget build(BuildContext context) {
    final ThemeData theme = ThemeData(
      primarySwatch: m2Swatch,
    );
    final Widget label = Text(_model.rtl ? 'اضغط علي' : 'Press Me');
    textController.text = _model.rtl
        ? 'يعتمد القرار الجيد على المعرفة وليس على الأرقام.'
        : 'A good decision is based on knowledge and not on numbers.';

    final List<Widget> tiles = <Widget>[
      _ControlTile(
        label: _model.rtl ? 'حقل النص' : 'List Tile',
        child: SizedBox(
          width: 400,
          child: Column(
            mainAxisAlignment: MainAxisAlignment.center,
            children: <Widget>[
              ListTile(
                title: Text(_model.rtl ? 'هذا عنوان طويل نسبيا' : 'This is a relatively long title'),
                onTap: () {},
              ),
              ListTile(
                title: Text(_model.rtl ? 'هذا عنوان قصير' : 'This is a short title'),
                subtitle:
                    Text(_model.rtl ? 'هذا عنوان فرعي مناسب.' : 'This is an appropriate subtitle.'),
                trailing: const Icon(Icons.check_box),
                onTap: () {},
              ),
              ListTile(
                title: Text(_model.rtl ? 'هذا عنوان قصير' : 'This is a short title'),
                subtitle:
                    Text(_model.rtl ? 'هذا عنوان فرعي مناسب.' : 'This is an appropriate subtitle.'),
                leading: const Icon(Icons.check_box),
                dense: true,
                onTap: () {},
              ),
              ListTile(
                title: Text(_model.rtl ? 'هذا عنوان قصير' : 'This is a short title'),
                subtitle:
                    Text(_model.rtl ? 'هذا عنوان فرعي مناسب.' : 'This is an appropriate subtitle.'),
                dense: true,
                leading: const Icon(Icons.add_box),
                trailing: const Icon(Icons.check_box),
                onTap: () {},
              ),
              ListTile(
                title: Text(_model.rtl ? 'هذا عنوان قصير' : 'This is a short title'),
                subtitle:
                    Text(_model.rtl ? 'هذا عنوان فرعي مناسب.' : 'This is an appropriate subtitle.'),
                isThreeLine: true,
                leading: const Icon(Icons.add_box),
                trailing: const Icon(Icons.check_box),
                onTap: () {},
              ),
            ],
          ),
        ),
      ),
      _ControlTile(
        label: _model.rtl ? 'حقل النص' : 'Text Field',
        child: SizedBox(
          width: 300,
          child: Column(
            mainAxisAlignment: MainAxisAlignment.center,
            children: <Widget>[
              TextField(
                controller: textController,
                decoration: const InputDecoration(
                  hintText: 'Hint',
                  helperText: 'Helper',
                  labelText: 'Label',
                  border: OutlineInputBorder(),
                ),
              ),
              TextField(
                controller: textController,
              ),
              TextField(
                controller: textController,
                maxLines: 3,
              ),
            ],
          ),
        ),
      ),
      _ControlTile(
        label: _model.rtl ? 'رقائق' : 'Chips',
        child: Column(
          mainAxisAlignment: MainAxisAlignment.center,
          children: List<Widget>.generate(chipValues.length, (int index) {
            return InputChip(
              onPressed: _model.enable ? () {} : null,
              onDeleted: _model.enable ? () {} : null,
              label: Text(chipValues[index]),
              deleteIcon: const Icon(Icons.delete),
              avatar: const Icon(Icons.play_arrow),
            );
          }),
        ),
      ),
      _ControlTile(
        label: _model.rtl ? 'زر المواد' : 'Material Button',
        child: MaterialButton(
          color: m2Swatch[200],
          onPressed: _model.enable ? () {} : null,
          child: label,
        ),
      ),
      _ControlTile(
        label: _model.rtl ? 'زر مسطح' : 'Text Button',
        child: TextButton(
          style: TextButton.styleFrom(
            foregroundColor: Colors.white,
            backgroundColor: m2Swatch[200]
          ),
          onPressed: _model.enable ? () {} : null,
          child: label,
        ),
      ),
      _ControlTile(
        label: _model.rtl ? 'أثارت زر' : 'Elevated Button',
        child: ElevatedButton(
          style: TextButton.styleFrom(backgroundColor: m2Swatch[200]),
          onPressed: _model.enable ? () {} : null,
          child: label,
        ),
      ),
      _ControlTile(
        label: _model.rtl ? 'زر المخطط التفصيلي' : 'Outlined Button',
        child: OutlinedButton(
          onPressed: _model.enable ? () {} : null,
          child: label,
        ),
      ),
      _ControlTile(
        label: _model.rtl ? 'خانات الاختيار' : 'Checkboxes',
        child: Row(
          mainAxisAlignment: MainAxisAlignment.center,
          children: List<Widget>.generate(checkboxValues.length, (int index) {
            return Checkbox(
              onChanged: _model.enable
                  ? (bool? value) {
                      setState(() {
                        checkboxValues[index] = value ?? false;
                      });
                    }
                  : null,
              value: checkboxValues[index],
            );
          }),
        ),
      ),
      _ControlTile(
        label: _model.rtl ? 'زر الراديو' : 'Radio Button',
        child: Row(
          mainAxisAlignment: MainAxisAlignment.center,
          children: List<Widget>.generate(4, (int index) {
            return Radio<int>(
              onChanged: _model.enable
                  ? (int? value) {
                      setState(() {
                        radioValue = value!;
                      });
                    }
                  : null,
              groupValue: radioValue,
              value: index,
            );
          }),
        ),
      ),
      _ControlTile(
        label: _model.rtl ? 'زر الأيقونة' : 'Icon Button',
        child: Row(
          mainAxisAlignment: MainAxisAlignment.center,
          children: List<Widget>.generate(iconValues.length, (int index) {
            return IconButton(
              onPressed: _model.enable ? () {} : null,
              icon: Icon(iconValues[index]),
            );
          }),
        ),
      ),
    ];

    return SafeArea(
      child: Theme(
        data: theme,
        child: Scaffold(
          key: scaffoldKey,
          appBar: AppBar(
            title: const Text('Density'),
            bottom: PreferredSize(
              preferredSize: const Size.fromHeight(220.0),
              child: Options(_model),
            ),
            backgroundColor: const Color(0xff323232),
          ),
          body: DefaultTextStyle(
            style: const TextStyle(
              color: Colors.black,
              fontSize: 14.0,
              fontFamily: 'Roboto',
              fontStyle: FontStyle.normal,
            ),
            child: Theme(
              data: Theme.of(context).copyWith(visualDensity: _model.density),
              child: Directionality(
                textDirection: _model.rtl ? TextDirection.rtl : TextDirection.ltr,
                child: MediaQuery(
                  data: MediaQuery.of(context).copyWith(textScaleFactor: _model.size),
                  child: SizedBox.expand(
                    child: ListView(
                      children: tiles,
                    ),
                  ),
                ),
              ),
            ),
          ),
        ),
      ),
    );
  }
}
