From a80e5ecec8544fe7fb9c6ee3650803cec2b7591c Mon Sep 17 00:00:00 2001 From: Vitaliy Zarubin Date: Fri, 7 Jul 2023 14:02:41 +0300 Subject: [PATCH] [packages] Add dartz --- example/lib/l10n/app_en.arb | 10 +++ example/lib/l10n/app_ru.arb | 10 +++ example/lib/packages/dartz/model.dart | 15 ++++ example/lib/packages/dartz/page.dart | 94 ++++++++++++++++++++++ example/lib/widgets/blocks/block_item.dart | 30 +++++-- 5 files changed, 151 insertions(+), 8 deletions(-) diff --git a/example/lib/l10n/app_en.arb b/example/lib/l10n/app_en.arb index ad626a2..bd7d8a8 100644 --- a/example/lib/l10n/app_en.arb +++ b/example/lib/l10n/app_en.arb @@ -1,4 +1,14 @@ { + "@_DARTZ": {}, + "dartzTitle": "Convert size", + "dartzDesc": "Convert the size grid of Russia to the size grid of Europe.", + "dartzErrorReq": "Required field", + "dartzErrorInt": "Please enter RUS size (42 - 62)", + "dartzErrorFound": "Size not found (42 - 62)", + "dartzDefaultValue": "Specify the size and click 'Submit'", + "dartzLabel": "Size in RUS", + "dartzSubmit": "Submit", + "@_BATTERY_PLUS": {}, "batteryPlusTitleBatteryLevel": "Battery Level", "batteryPlusDescBatteryLevel": "Battery level in percent 0 - 100.", diff --git a/example/lib/l10n/app_ru.arb b/example/lib/l10n/app_ru.arb index 728a957..258d113 100644 --- a/example/lib/l10n/app_ru.arb +++ b/example/lib/l10n/app_ru.arb @@ -1,4 +1,14 @@ { + "@_DARTZ": {}, + "dartzTitle": "Преобразовать размер", + "dartzDesc": "Преобразовать размерную сетку России в размерную сетку Европы.", + "dartzErrorReq": "Обязательное поле", + "dartzErrorInt": "Введите размер RUS (42–62)", + "dartzErrorFound": "Размер не найден (42–62)", + "dartzDefaultValue": "Укажите размер и нажмите 'Отправить'", + "dartzLabel": "Размер в RUS", + "dartzSubmit": "Отправить", + "@_BATTERY_PLUS": {}, "batteryPlusTitleBatteryLevel": "Уровень заряда батареи", "batteryPlusDescBatteryLevel": "Уровень заряда батареи в процентах от 0 до 100.", diff --git a/example/lib/packages/dartz/model.dart b/example/lib/packages/dartz/model.dart index 32dc023..0174b47 100644 --- a/example/lib/packages/dartz/model.dart +++ b/example/lib/packages/dartz/model.dart @@ -2,6 +2,7 @@ * Copyright (c) 2023. Open Mobile Platform LLC. * License: Proprietary. */ +import 'package:dartz/dartz.dart'; import 'package:flutter/widgets.dart'; import 'package:scoped_model/scoped_model.dart'; @@ -10,4 +11,18 @@ class DartzModel extends Model { /// Get [ScopedModel] static DartzModel of(BuildContext context) => ScopedModel.of(context); + + /// Example using Option from package dartz + Option getEURManSize(int size) { + if (size < 42) return none(); + if (size < 44) return some('XS'); + if (size < 46) return some('S'); + if (size < 48) return some('M'); + if (size < 50) return some('L'); + if (size < 54) return some('XL'); + if (size < 56) return some('XXL'); + if (size < 58) return some('XXXL'); + if (size <= 62) return some('XXXXL'); + return none(); + } } diff --git a/example/lib/packages/dartz/page.dart b/example/lib/packages/dartz/page.dart index e05b9f1..ad74e6a 100644 --- a/example/lib/packages/dartz/page.dart +++ b/example/lib/packages/dartz/page.dart @@ -2,13 +2,19 @@ * Copyright (c) 2023. Open Mobile Platform LLC. * License: Proprietary. */ +import 'dart:async'; + +import 'package:flutter/foundation.dart' show kIsAurora; import 'package:flutter/material.dart'; import 'package:flutter_example_packages/base/di/app_di.dart'; import 'package:flutter_example_packages/base/package/package.dart'; import 'package:flutter_example_packages/widgets/base/export.dart'; import 'package:flutter_example_packages/widgets/blocks/block_info_package.dart'; +import 'package:flutter_example_packages/widgets/blocks/block_item.dart'; import 'package:flutter_example_packages/widgets/layouts/block_layout.dart'; +import 'package:flutter_example_packages/widgets/texts/export.dart'; import 'package:flutter_gen/gen_l10n/app_localizations.dart'; +import 'package:flutter_keyboard_visibility_aurora/flutter_keyboard_visibility_aurora.dart'; import 'model.dart'; import 'package.dart'; @@ -25,6 +31,33 @@ class DartzPage extends AppStatefulWidget { } class _DartzPageState extends AppState { + final TextEditingController _textController = TextEditingController(); + final _formKey = GlobalKey(); + String? _sizeEUR; + bool _isError = false; + + double _keyboardHeight = 0; + StreamSubscription? _streamSub; + final _controllerAurora = FlutterKeyboardVisibilityAurora(); + + @override + void initState() { + super.initState(); + if (kIsAurora) { + _streamSub = _controllerAurora.onChangeHeight.listen((event) { + setState(() { + _keyboardHeight = event; + }); + }); + } + } + + @override + void dispose() { + super.dispose(); + _streamSub?.cancel(); + } + @override Widget buildWide( BuildContext context, @@ -36,12 +69,73 @@ class _DartzPageState extends AppState { title: widget.package.key, builder: (context, child, model) { return SingleChildScrollView( + padding: EdgeInsets.only(bottom: _keyboardHeight), child: Padding( padding: const EdgeInsets.all(20), child: Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ BlockInfoPackage(widget.package), + Form( + key: _formKey, + child: Column( + crossAxisAlignment: CrossAxisAlignment.start, + children: [ + BlockItem( + title: l10n.dartzTitle, + desc: l10n.dartzDesc, + value: _sizeEUR ?? l10n.dartzDefaultValue, + ), + TextFormField( + controller: _textController, + keyboardType: TextInputType.number, + decoration: InputDecoration( + labelText: l10n.dartzLabel, + errorText: + _isError ? l10n.dartzErrorFound : null, + ), + validator: (value) { + if (value == null || value.isEmpty) { + return l10n.dartzErrorReq; + } + if (int.tryParse(value) == null) { + return l10n.dartzErrorInt; + } + return null; + }, + ), + const SizedBox(height: 20), + SizedBox( + width: double.infinity, + child: ElevatedButton( + onPressed: () async { + if (_formKey.currentState?.validate() == true) { + final sizeRU = int.parse(_textController.text); + model + .getEURManSize(sizeRU) + .map( + (classification) => setState(() { + _isError = false; + _sizeEUR = classification; + }), + ) + .getOrElse( + () => setState(() { + _sizeEUR = null; + _isError = true; + }), + ); + } + }, + child: TextBodyLarge( + l10n.dartzSubmit, + color: Colors.white, + ), + ), + ), + ], + ), + ), ], ), ), diff --git a/example/lib/widgets/blocks/block_item.dart b/example/lib/widgets/blocks/block_item.dart index 0fdc574..09d6b46 100644 --- a/example/lib/widgets/blocks/block_item.dart +++ b/example/lib/widgets/blocks/block_item.dart @@ -11,16 +11,16 @@ import 'package:flutter_gen/gen_l10n/app_localizations.dart'; class BlockItem extends AppStatelessWidget { const BlockItem({ super.key, - required this.title, - required this.desc, + this.title, + this.desc, this.value, this.future, this.stream, this.builder, }); - final String title; - final String desc; + final String? title; + final String? desc; final T? value; final Stream? stream; final Future? future; @@ -31,10 +31,24 @@ class BlockItem extends AppStatelessWidget { return Column( crossAxisAlignment: CrossAxisAlignment.start, children: [ - TextTitleLarge(title), - const SizedBox(height: 8), - TextBodyMedium(desc), - const SizedBox(height: 8), + Visibility( + visible: title != null, + child: Column( + children: [ + TextTitleLarge(title ?? ''), + const SizedBox(height: 8), + ], + ), + ), + Visibility( + visible: desc != null, + child: Column( + children: [ + TextBodyMedium(desc ?? ''), + const SizedBox(height: 8), + ], + ), + ), if (snapshot.hasData) TextBodyMedium( builder == null