Features
- Reduce 28% of chars in writing code & lines breaks.
- Get ride of RenderFlex overflowed by pixels.
- Basics ui widget with extra feature not found at normal widget. Example widget:
- PageFastor, TextFastor, ImageFastor, RowFastor, ColumnFastor, TextFieldFastor ..etc
- Can Write Widget Type Fastor Inside Regular Widget Flutter and vise versa:
- Example : can use "ColumnFastor()" inside "Column()" regular and vise versa
- Example : can use "TextFastor()" inside "Column()" regular or inside "ColumnFastor"
- Don't Worry About Using Widget Type Fastor With Regular Widget
- Helping make coding faster by use Utils. Example Classes:
- NetworkManager, LanguageTools, ... etc.
Get Start
1- import dependence in yaml file:
fastor_app_ui_widget:
2- at any class must import
import 'package:fastor_app_ui_widget/fastor_app_ui_widget.dart';
3- In main() write
void main() async {
WidgetsFlutterBinding.ensureInitialized();
await Fastor.initializeApp( );
runApp(const MyApp());
}
Reference
documentation
https://pub.dev/documentation/fastor_app_ui_widget/latest/index.html
Tutorial Content
Content: Widget
Page Shapes | TextView | Button | ImageView |
Row | Column | TextField | CheckboxFastor |
Content: Classes Helper Tools
Start Your Tutorial
PageFastor
Scroll Screen
- Get ride of RenderFlex overflowed by pixels.
- Simple Example Create "PageFastor"
@override
Widget build(BuildContext context) {
return PageFastor(this,
content: getContent() );
}
- Example For Content Long Data
Widget getContent() {
return Column( children: getLongDataForTestScroll() ,);
}
List<Widget> getLongDataForTestScroll() {
List<Widget> data = [];
for (int i = 1; i <= 70; i++) {
var w = TextFastor(
"Get ride of RenderFlex, data number $i",
fontSize: 15,
width: 300,
color: Colors.yellow,
margin: EdgeInsets.all(5),
);
data.add(w);
}
return data;
}
Toolbar Custom Shape
Create any shape of Toolbar you want in Custom shape then put it at page template by using parameter "toolbar"
@override
Widget build(BuildContext context) {
return PageFastor(this,
toolbar: ToolbarSimpleFastor( context, "Page Shapes"),
toolbar_height : 70,
content: getContent() );
}
- The Default height of toolbar is 70
- When the toolbar you draw different than 70 you can set height of toolbar by using "toolbar_height"
Background Feature
Asset
set Image png to background, to make all content scrolling while the background image still hold at background
Asset with Opacity
@override
Widget build(BuildContext context) {
return PageFastor(this,
toolbar: ToolbarSimpleFastor( context, "Page Shapes"),
toolbar_height : 70,
//background
assetBackground: const AssetImage("assets/images/background.png"),
assetBackgroundOpacity: 0.3,
content: getContent() );
}
Custom Widget
set Custom Widget hold at background, to make all content scrolling while the background widget still holding while scrolling
@override
Widget build(BuildContext context) {
return PageFastor(this,
toolbar: ToolbarSimpleFastor( context, "Page Shapes"),
toolbar_height : 70,
//background
widgetBackground: CustomWidgetBackground(),
content: getContent() );
}
Navigation Bottom
Custom Shape Navigation
set Custom Widget hold at bottom of screen to navigate between multi screens
@override
Widget build(BuildContext context) {
return PageFastor(this,
//toolbar
toolbar: ToolbarSimpleFastor( context, "Page Shapes"),
toolbar_height : 70,
//navigation bottom
navigationBottom: NavigationFastor( context, 0),
navigationBottom_height: 70,
homeButtonsBackgroundColor: HexColor( "#1593bc"), //color background for home buttons
content: getContent() );
}
Change color
Color of Home Buttons Android Device
By using parameter "homeButtonsBackgroundColor" you can write hexcode color
@override
Widget build(BuildContext context) {
return PageFastor(this,
homeButtonsBackgroundColor: HexColor( "#1593bc"), //color background for home buttons
content: getContent() );
}
Color of Status Bar
By using parameter "statusBarColorCustome" you can write hexcode color
@override
Widget build(BuildContext context) {
return PageFastor(this,
statusBarColorCustome: HexColor( "#595629"),
content: getContent() );
}
ScaffoldFastor
Navigation To Transparent Page
- To Navigate Need to User class "NavigationTools" found in fastor helper classes.
- Just Call for navigation push
NavigationTools.pushTransparent( SimpleScreen() );
- or for animation navigation
NavigationTools.pushTransparentAnimateFade( SimpleScreen() );
- In Your Screen Page set "shapeTransparent: true "
@override
Widget build(BuildContext context) {
return ScaffoldFastor(
shapeTransparent: true,
body: directionWithPageBlocState(),
);
}
- to change transparent color dialog use parameter "shapeTransparentColor"
Tutorial : TextFastor
Why use Fastor widget ?
- Reduce 28% of chars in writing code
- Reduce 28% of lines breaks
Feature Fastor
- Margin without use Container
- Padding without use Container
- Decoration background without use Container
- Text Align without use Style
- Text Decoration without use Style
- Font size without use Style
- Font family without use Style
- On tap without use GestureDetector
Table Result : Percentage of code writing reduction
Using Fastor widget reduce writing code by 28% chars when you compare with normal flutter widget
See source code compare between Fastor and Normal at this page
Get Start
Full Example
TextFastor(
"Text Fastor Simple" ,
textAlign: TextAlign.center,
textDecoration: TextDecoration.underline,
color: Colors.blue,
fontSize: 25,
fontFamily: FontProject.marina,
margin: EdgeInsets.all( 25 ),
padding: EdgeInsets.all( 10),
decoration: BoarderHelper.cardView(
colorLine: Colors.red,
colorBackground: Colors.yellow,
radiusSize: 15
),
// backgroundColor: Colors.green,
maxLines: 2,
onPressed: (){
Log.i( "click on fastor widget");
},
);
Compare Text() Normal Vs TextFastor()
Widget getContent() {
return Column( children: [
textview_normal(),
textview_fastor()
],);
}
Widget textview_normal() {
return GestureDetector( child: Container(
child: Text(
"Text Normal" ,
textAlign: TextAlign.center,
maxLines: 2,
style: TextStyle(
decoration: TextDecoration.underline,
decorationColor: Colors.blue,
color: Colors.blue,
fontSize: 25,
fontFamily: FontProject.marina
),
),
margin: EdgeInsets.all( 25 ),
padding: EdgeInsets.all( 10),
decoration: BoxDecoration(
border: Border.all(color: Colors.red ) ,
borderRadius: BorderRadius.all(
Radius.circular( 15 )
) ,
color: Colors.yellow //background color
),
// color: Colors.green,
),
onTap: (){
Log.i( "click on Normal");
},
);
}
Widget textview_fastor() {
return TextFastor(
"Text Fastor" ,
textAlign: TextAlign.center,
textDecoration: TextDecoration.underline,
color: Colors.blue,
fontSize: 25,
fontFamily: FontProject.marina,
margin: EdgeInsets.all( 25 ),
padding: EdgeInsets.all( 10),
decoration: BoarderHelper.cardView(
colorLine: Colors.red,
colorBackground: Colors.yellow,
radiusSize: 15
),
// backgroundColor: Colors.green,
maxLines: 2,
onPressed: (){
Log.i( "click on fastor widget");
},
);
}
Tutorial : ButtonFastor
Feature Fastor
- Margin without use Container
- Padding without use Container
- Decoration background without use Container
- Text Align without use Style
- Text Decoration without use Style
- Font size without use Style
- Font family without use Style
- On tap without use GestureDetector
Get Start
See source code compare between Fastor and Normal at this page
Full Example
ButtonFastor(
"Button Fastor",
() {
print("click on btn type fastor");
},
margin: EdgeInsets.symmetric( vertical: 40),
textColor: Colors.blue,
background: Colors.black,
fontFamily: FontProject.marina,
textFontSize: 15,
borderLine: Colors.blue,
borderRadius: 15,
);
}
Compare Text() Normal Vs TextFastor()
EdgeInsets.symmetric( vertical: 30),
child: ElevatedButton(
onPressed: () {
print("click on btn type normal");
},
style: ElevatedButton.styleFrom(
backgroundColor: Colors.black,
shape: RoundedRectangleBorder (
borderRadius: BorderRadius.circular(15),
side: BorderSide(width: 1,color: Colors.blue)
)),
child: Text(
"Button Normal",
textAlign: TextAlign.center,
maxLines: 2,
style: TextStyle(
color: Colors.blue,
fontSize: 15,
fontFamily: FontProject.marina
),
)
),
// color: Colors.green,
);
- progress of button controle by:
bool? showProgress;
double? sizeProgress;
Color? colorProgress;
Tutorial : ImageFastor
Feature Fastor
- Background color/image without use Container
- Padding without use Container
- Aspect Ratio Image
- Radius Corner for Image
- On tap without use GestureDetector
Set Image type url + Corner Radius + Background color + opacity + onPressed + margin
ImageFastor(
context: context,
width: 278,
height: 181,
margin: EdgeInsets.all( 10),
radius_all: 25,
boxFit_background: BoxFit.cover,
urlBackground: square_url_image_example,
colorBackground: Colors.amber,
opacity: 0.7,
onPressed: (){
print("click on image");
},
);
}
Set Image type assets + Corner Radius
return ImageFastor(
context: context,
width: 300,
height: 600,
radius_all: 25,
assetAspectRatio: AssetImage("assets/images/background.png"),
);
Set Image auto-responsive between website screen desktop, website screen mobile and mobile real device
same code working in all platform with save the aspect ratio size of image with all screen size of any device.
Screen Size : Website Desktop
Screen Size : Website Browser Mobile Chrome
Screen Size : Android Mobile
ImageFastor(
context: context,
width: 300,
height: 300,
radius_all: 25,
assetAspectRatio: AssetImage("assets/images/logo_example.png"),
responsive_auto: true,
);
Tutorial : RowFastor
Feature Fastor
- "RowScrollFastor" Scroll Horizontal for get ride of RenderFlex overflowed by pixels
RowScrollFastor
Using Fastor widget Scroll Horizontal for get ride of RenderFlex overflowed by pixels
See source code compare between Fastor and Normal at this page
RowScrollFastor( children: getChildren() );
Tutorial : ColumnFastor
Feature Fastor
- Have Decoration
- Have Space : Margin, Padding
- Have Alignment
- Can Set Fixed size width/height
ColumnFastor
Using Fastor widget Scroll Horizontal for get ride of RenderFlex overflowed by pixels
See source code compare between Fastor and Normal at this page
ColumnFastor(
children: getChildren(),
margin: EdgeInsets.only(top: 20, bottom: 20, left: 60, right: 60),
padding: EdgeInsets.all(5),
decoration: BoxDecoration(
border: Border.all(color: Colors.red),
borderRadius: BorderRadius.all(Radius.circular(15)),
color: Colors.yellow //background color
),
);
Tutorial : TextFieldFastor
Feature Fastor
- Call from constructor of class
// validate
this.validator,
this.autovalidateMode,
//text and hint
this.hint_text,
this.text_color,
this.fontSize,
this.hint_color,
//boarder and underline
this.isRemoveUnderline = false,
this.isShowBoarder,
//background
this.background_color,
this.decoration, //at the Container
//spaces
this.padding,
this.margin,
//controller
this.controller,
this.onChanged,
//input content type
this.keyboardType,
this.obscureText = false,
//size and max/min
this.width,
this.maxLength,
this.maxLines,
this.minLines,
//other
this.textAlign ,
this.focusNode,
this.prefixIcon
Get Start
Tutorial : Without Use Any State Management
- use "setState()"
- Create Variable at class
var email_txt = "";
var email_valid = AutovalidateMode.disabled;
- Create Widget
return TextFieldFastor(
autovalidateMode: email_valid,
margin: EdgeInsets.only( top: 10 ),
padding: EdgeInsets.all( 5),
background_color: Colors.white,
validator: ValidatorTemplate.email( ),
keyboardType: TextInputType.emailAddress,
onChanged: (s){
email_txt = s;
Log.i( "tf_email() - change s: $s ");
}
);
- Validate Form after click of button
if(validateEmailAfterClick()) {
///TO-DO : After success success field
}
bool validateEmailAfterClick() {
var result = true; //default good
//email
if ( ToolsValidation.isEmail( email_txt ) == false ){
Log.i( "missed email");
result = false;
setState(() {
email_valid = AutovalidateMode.always;
});
}
return result;
}
Tutorial : Use State Management Type "Cubit" like using "BLoc"
-
Using "Cubit" it similar as Using "BLoc"
-
Create Cubit
class AuthCubit extends Cubit<AuthState> {
final LogInUseCase logInUseCase;
AuthCubit( ) : super(AuthInitialState()) {}
static AuthCubit get(context) => BlocProvider.of(context);
AuthResponse authResponse = AuthResponse();
Future login(String email_txt, String pass_txt) async {
//....
}
void resetError() {
emit( AuthInitialState() );
}
}
- Create Cubit State
abstract class AuthState {}
class AuthInitialState extends AuthState {}
class AuthLoadingState extends AuthState {}
class AuthSuccessState extends AuthState {
//.....
}
class AuthErrorState extends AuthState
{
//.....
}
- Declare Variable at class
AuthState? stateCurrent;
var emailValid = AutovalidateMode.disabled;
var emailController = TextEditingController();
var passValid = AutovalidateMode.disabled;
var passController = TextEditingController();
- This Way You Can Set Error Message To UI
void setErrorToInputFields() {
//email
if (ToolsValidation.isEmail(emailController.text) == false) {
Log.i("missed email");
emailValid = AutovalidateMode.always;
}
//pass
if (ToolsValidation.isPasswordValid(passController.text) == false) {
Log.i("missed pass");
passValid = AutovalidateMode.always;
}
}
- Listener Cubit State
Widget getContent() {
return BlocConsumer<AuthCubit, AuthState>(
listener: (context, state) {
stateCurrent = state;
if (state is AuthSuccessState) {
RouterPage.home(context);
}
},
builder: (context, state) {
if (state is AuthErrorState) {
setErrorToInputFields();
printMessageError();
}
return Column(children: [
tfEmail(),
tfPass(),
]);
);
}
- Create Widget TextFieldFastor
Widget tfEmail() {
return TextFieldFastor(
hint_text: "Email",
controller: emailController,
autovalidateMode: emailValid,
margin: EdgeInsets.only(top: 10),
padding: EdgeInsets.all(5),
background_color: Colors.white,
validator: ValidatorTemplate.email(),
keyboardType: TextInputType.emailAddress,
onChanged: (s) {
// Log.i("tfEmail() - change s: $s ");
bool isNotInit = stateCurrent! is AuthInitialState;
if (isNotInit) {
AuthCubit.get(context).resetError();
}
});
}
Widget tfPass() {
return TextFieldFastor(
hint_text: "Password",
controller: passController,
autovalidateMode: passValid,
margin: EdgeInsets.only(top: 10),
padding: EdgeInsets.all(5),
background_color: Colors.white,
validator: ValidatorTemplate.pass(),
keyboardType: TextInputType.number,
onChanged: (s) {
// Log.i("tf_pass() - change s: $s ");
});
}
Class Utils For TextField
- class ValidatorTemplate : This have methods utils used at parameter "validator"
Class "TextFieldBackendErrorFastor" :
- This Class used for handle error from backend for every input fields.
- Example error array backend response :
{
"errors": {
"email": [
"The email provided is incorrect."
]
}
}
Handle Error Array
-
We need in UI to handle every error array and to show to message error under every textfields
-
Example :
return TextFieldFastor(
hint_text: "Email",
controller: emailController,
autovalidateMode: emailValid,
validatorCustom: ValidatorTemplate.email(),
errorBackendJson: errorState?.errors,
errorBackendKeyJson: "email",
// errorBackendKeyJson2: "role",
margin: EdgeInsets.only(top: 10),
padding: EdgeInsets.all(5),
background_color: Colors.white,
keyboardType: TextInputType.emailAddress,
onChanged: (s) {
// Log.i("tfEmail() - change s: $s ");
bool isNotInit = stateCurrent! is AuthInitialState;
if (isNotInit) {
AuthCubit.get(context).resetError();
}
});
Tutorial : CheckboxFastor
Feature Fastor
- set color from constructor for active/inactive: color_inactive, color_active
- Set Text Style : color, font size, weight.
- Remove default padding found when use normal checkbox widget.
Get Start
Simple Example
- Create Variable at class
bool isAgree = false;
- Create Widget
return CheckboxFastor( context: context, value: isAgree,
margin: EdgeInsets.only(top: 10),
text: "Are you agree to terms and condition.",
text_color: Colors.brown,
text_dimen: 20,
color_inactive : Colors.brown,
color_active: Colors.green,
onChanged: (updatedValue) {
setState(() {
isAgree = updatedValue!;
});
}
);
SwitchFastor
- Feature Padding, Margin.
- Feature send "TextStyle" in parameter constructor.
- Feature Color action active and dis-active in parameter constructor.
Example Using with "Cubit" StateManagment
- ui :
Widget _switchVipButton(){
return SwitchFastor(defaultValue: cubit!.createReservation.isVip,
onChange: (updateStatus){
Log.i( "_switchVipButton() updateStatus: $updateStatus");
cubit!.switchVipStatus(updateStatus);
});
}
- Save the last updated status of change in variable
- when calling
cubit!.createReservation.isVip
it just boolean varaible to carry data of switch status
bool isVip = false;
- create new state for class Cubit state
class ReservationCreateVipStatusChangeState extends ReservationState {}
- call the change of switch value by calling "State Cubit"
void switchVipStatus(bool updateStatus) {
createReservation.isVip = updateStatus;
emit(ReservationCreateVipStatusChangeState());
}
ScrollFastor
Example
@override
Widget build(BuildContext context) {
return Scaffold(
body: createUI()
);
}
Widget createUI() {
var scrollPage = ScrollFastor( child: contentFormColumn() );
var cont = Container(
padding: EdgeInsets.only(top: ToolbarCustom.heigh),
margin: EdgeInsets.only( left: 16, right: 16, bottom: 16),
child: scrollPage ,
);
return Stack(
children: [
cont,
ToolbarCustom(pageContext: context, title: "Add Reservation"),
],
);
}
Widget contentFormColumn(){
return Column(
crossAxisAlignment: CrossAxisAlignment.start,
mainAxisAlignment: MainAxisAlignment.start,
children: [
Text("input field 1"),
Text("input field 2"),
Text("input field 3"),
Text("input field 4"),
Text("input field 5"),
Text("input field 6"),
Text("input field 7"),
],
);
}
TableFastor
- feature scroll both horizontal and vertical axis
Progress
TableFastor( { required this.listRow,
this.showProgress,
this.sizeProgress,
this.colorProgress,
} ){
Progress
- shape Circle
ProgressCircleFastor( {
this.color,
this.size
})
- shape Spin Plugin "package:flutter_spinkit"
ProgressSpinFastor( {
this.color,
this.size
})
PageViewFastor
Features
- easy to set colors of indicator selected and unselcted
- set frame width / height.
- indicator points clicked to navigate to child widget.
Example
Widget pageView(){
return PageViewFastor(
widht: DeviceTools.isLandscape(context)? ResponsiveConstant.widthChangeInCaseLandscape: DeviceTools.getWidth(context) ,
height: 400,
colorIndicatorOn: ColorProject.primary,
colorIndicatorOff: ColorProject.black,
children: [
firstBoarder(),
secondBoarder()
],
onChangePage: (p){
Log.i( "change p : " + p.toString() );
},);
}
TimerCountDownFastor
- count down text to shape format: mm:ss
- easy to use with callback when timer complete.
- change font size, font family, text color.
TimerCountDownFastor(
contextPage: context ,
second: 7,
callBack: () {
///TO-DO when complete timer
}
)
DropdownFastor
Simple Example :
- simple string[] array
return DropdownFastor(
width: widget.width - 16 -16 ,
names: HelperEumCrypto.getListNameEnumCrypto(), //string[] array
hintText: "select one",
previousSelectedText: selectedCrypto?.name,
listener: (name, position ) {
setState(() {
selectedCrypto = HelperEumCrypto.mapNameToEnum(name);
Log.i("dropdownCrypto() - currentCryptoReading: $selectedCrypto /position: $position");
widget.listener(selectedCrypto);
});
},
);
Set previous selected name
previousSelectedText: selectedCrypto?.name,
to remove the selected item from dropdown programmatically
- example dropdown
Widget dropdownFastor(){
return DropdownFastor(
width: 150,
names: ["male", "female", "prefer not answer"],
iconSize: 24,
previousPosition: previousPosition,
listener: (name, position){
Log.i( "dropdownFastor() - name: " + name.toString() + " /position: $position" );
previousPosition = position;
},
onRemoveSelected: (){
Log.i( "dropdownFastor() - onRemoveSelected " );
removeSelectedDropdown();
});
}
- After "onRemoveSelected" called, means you need to remove old selected :
removeSelectedDropdown(){
setState(() {
previousPosition = null;
});
}
Handle Direction ltr or rtl :
return DropdownFastor(
textDirection: getTextDirection(),
Show Progress View Will Loading Data
this.showProgress,
this.sizeProgress,
this.colorProgress,
OTPTextFieldFastor
- you can listener when user complete write "OTP CODE"
- Listener while user still writing the OTP Code
- write how many fields otp needed 4 or 5 or 6. maximue is 6 otp code
- choose style from constructor
//size
double? widthOTP ;
double? heightByPadding ;
double? margin ;
//color
Color? colorText;
Color? colorHint;
String? fontFamily;
double? fontSize;
Decoration? decoration;
- example
var otpWidget = OTPTextFieldFastor(
countNumber: 5,
decoration: BoarderHelper.box(
colorLine: ColorApp.black,
colorBackground: Colors.transparent
),
fontFamily: ProjectFonts.DarkerGrotesque_Black_900,
fontSize: 13,
// colorHint: ColorApp.gray,
colorText: ColorApp.black,
onComplete: ( isComplete ){
Log.i("otpFields() - isComplete: $isComplete");
},
onChangeCode: (codeUpdate ) {
Log.i("otpFields() - onChangeCode: $codeUpdate");
},
);
DateTextFieldFastor
- simple date picker one day in shape textfield boarder
return DateTextFieldFastor(
width: DeviceTools.getHalfWidth(context),
boarderColor: Colors.transparent,
boarderRadius: 0,
fontSize: 12,
iconColor: HexColor(ColorProject.blue_fish_front),
callback: (date){
dateSearchSelected = date;
});
- add "previousSelectedText" parameter in class "DateTextFieldFastor"
return DateTextFieldFastor(
previousSelectedText: "2024-01-20",
});
DateRangeTextFieldFastor
- simple date picker for range between two days in shape textfield boarder
- class "DateRangePickerResult" to handle callback listener of date picker range
return DateRangeTextFieldFastor(
width: DeviceTools.getWidth(context),
boarderRadius: 0,
dateStart : dateRangeSelected?.start,
dateEnd : dateRangeSelected?.end,
callback: (dateSelected){
dateRangeSelected = dateSelected;
});
MobileCountryFastor
- widget TextField "MobileCountryFastor" use plugin "country_code_picker" with some customization in phone
return MobileCountryFastor(
width: getWidthOfInputField(),
colorUnderlineInputField: ColorApp.underlineInputField,
textStyle: TextStyle(
color: ColorApp.black,
fontSize: 13,
fontFamily: ProjectFonts.DarkerGrotesque_Regular_400
),
controller: phoneController,
title: "ENTER PHONE NUMBER",
callback: (String country_code, String phone) {
cubit!.requestRegister.countryCode = country_code;
cubit!.requestRegister.phoneNumber = phone;
}
);
- feature
MobileCountryFastor( {
required this.width,
required this.callback,
this.widthCountryCode,
this.textStyle,
this.controller,
this.decoration,
this.textInputType,
this.padding,
this.title,
this.hint,
this.hint_color,
this.colorUnderlineInputField,
this.favoriteCountryCodeArray,
this.initialSelection,
this.suffixIcon,
this.isHideCountryPicker
}) {
TextFieldEmailOrPhoneFastor
- widget "TextFieldEmailOrPhoneFastor" use plugin "country_code_picker" with some customization in phone
- allow user to enter both email format or phone, the country code picker auto hide/show when user write phone character or not.
Widget emailOrPhone(){
var imageEmail = Image.asset( "assets/images/email.png", width: 28, height: 28,);
var iconEmail = Padding(child: imageEmail , padding: EdgeInsets.only(bottom: 18, right: 8) );
var mobile = TextFieldEmailOrPhoneFastor(
width: ProjectDimen.allDeviceWidthMinesMarginLeftRight(context),
colorUnderlineInputField: ColorApp.underlineInputField,
textStyle: TextStyle(
color: ColorApp.black,
fontSize: 13,
fontFamily: ProjectFonts.DarkerGrotesque_Regular_400
),
// countryCodeDefault: ConstantEnvironment.isTestEnvironment?"+20":"+966",
controller: emailOrPhoneController,
title: "ENTER EMAIL ADDRESS OR PHONE NUMBER",
hint: "Email address or phone number",
iconCaseEmail : iconEmail,
callbackEmail: ( email ) {
Log.i("callbackEmail - s: $email");
cubit!.loginRequest.emailOrPhone = email ;
// cubit!.emitToInitialState( );
},
callbackPhone: (String country_code, String phone) {
Log.i("callbackPhone - s: $phone");
cubit!.loginRequest.countryCode = country_code;
cubit!.loginRequest.emailOrPhone = phone ;
// cubit!.emitToInitialState() ;
},
);
return Container(
child: mobile,
margin: EdgeInsets.symmetric(horizontal: ProjectDimen.leftRightPageContent),
);
}
Example Arabic Change Icon Direction
- code use "textDirection"
var mobile = TextFieldEmailOrPhoneFastor(
textDirection : LanguageHelper.getTextDirection(),
....
);
- user any class helper to return direction
- you can also used helper fastor langauge class. "LangFastor.getTextDirection()"
class LanguageHelper {
static TextDirection getTextDirection() {
var lang = translator.activeLanguageCode;
var isArabic = lang == "ar";
if (isArabic) {
return TextDirection.rtl;
} else {
return TextDirection.ltr;
}
}
}
TextFieldPasswordFastor
- icon password click to show/hide password
- can custom iconWidget for show/hide
- title text optional to set above TextField
- Can send custom Title Widget
- optional validator fourm
- optional set type of AutoValidateMode
Example Simple : Not Used Custom Icon
return TextFieldPasswordFastor(
title: "ENTER PASSWORD",
hint_text: "Enter password",
iconPasswordShow: Icon(), //optional: this custom icon
iconPasswordShow: Icon(), //optional: this custom icon
passwordController: passwordController,
margin: EdgeInsets.only(top: 10 ), //optional:
validatorCustom: ValidatorTemplate.pass(error_text: "*Enter password at least 8 char." ), //optional
autoValidateMode: AutovalidateMode.onUserInteraction,
onChanged: (s) {
},
);
Example Use Custom Icon
@override
Widget build(BuildContext context) {
return TextFieldPasswordFastor(
titleWidget: title(),
hint: "Enter password".trf(),
iconPasswordShow: iconEyeShow(),
iconPasswordHidden: iconEyeHide(),
passwordController: widget.passwordController,
margin: EdgeInsets.symmetric(horizontal: ProjectDimen.leftRightPageContent),
validatorCustom: ValidatorTemplate.pass(error_text: "*Enter password at least 8 char.".trf()),
autovalidateMode: AutovalidateMode.onUserInteraction,
onChanged: widget.onChanged,
colorIconEyePassword: ColorApp.pink,
);
}
Widget iconEyeShow(){
var img = Image.asset(
"assets/images/eye_show.png",
width: 14,
height: 14,
color: ColorApp.primary,
);
return Container(
child: img,
color: Colors.transparent,
padding: EdgeInsets.only( right: 10, left: 10),
);
}
Widget iconEyeHide(){
var img = Image.asset(
"assets/images/eye_hide.png",
width: 14,
height: 14,
color: ColorApp.primary,
);
return Container(
child: img,
color: Colors.transparent,
padding: EdgeInsets.only( right: 10, left: 10),
);
}
title() {
return Container(
child: TextCustomBold("ENTER PASSWORD".trf(), fontSize: 15 ),
margin: EdgeInsets.only(bottom: 20),
);
}
TabBarFastor
example simple
int selectedTabPosition = 0 ;
Widget tabBarFastor(){
return TabBarFastor(
width: DeviceTools.getWidth(context),
height: 50,
names: ['UPCOMING'.trf() , 'COMPLETED'.trf(), 'CANCELLED'.trf()],
indicatorColor: ColorApp.primaryByVip(),
unselectedLabelColor: ColorApp.blackOpacity,
fontSize: 16,
fontFamily: ProjectFonts.DarkerGrotesque_Medium_500,
spaceBetweenLabelAndUnderline : 10,
decorationTabBar: BoarderHelper.box(
colorBackground: Colors.grey[200],
colorLine: Colors.transparent
),
pressed: (int index , String title ) {
Log.i("tabBarFastor() - pressed - index: $index /title: $title");
setState(() {
selectedTabPosition = index;
});
});
}
- to show the content ui for each tab item, just use if condition to show the view you want below tabbar
Some Features
- feature show underline in all item tabs
return TabBarFastor(
underlineShownBelowAllTabs : true,
CalenderFastor
Feature :
- title is optional
- decoration background optional
- types calender "CalenderTypeFastor.birthday" for handle picker birthday logic
- "height" parameter to resize to specific fixed height.
- style of font: colorTextTitle, colorTextSelected, colorTextUnSelected, fontFamily, fontSize
Example :
- example type birthday picker
var calender = CalenderFastor(
title: "ENTER DOB" ,
decoration: BoarderHelper.cardView(
colorLine: ColorApp.grayOpacity,
radiusSize: 3,
colorBackground: ColorApp.pinkOpacity
),
calenderTypeFastor: CalenderTypeFastor.birthday,
dateSelected: cubit!.requestRegister.birthday,
colorTextTitle: ColorApp.black,
colorTextSelected: ColorApp.black,
colorTextUnSelected: ColorApp.gray,
fontFamily: ProjectFonts.DarkerGrotesque_Bold_700,
callback: ( dateTime, ddMMyyyy ) {
cubit!.requestRegister.birthday = ddMMyyyy;
},
);
Types
- type of calender "CalenderTypeFastor" see Enum
enum CalenderTypeFastor { dateStartFromToday, birthday }
BoarderHelper
- BoxDecoration easy to use in Container( decoration: )
- BoxDecoration utils to be used in "Container()"
Container(
decoration: BoarderHelper.cardViewBlur(
colorBackground: ColorApp.greyDarkButton,
colorBlur: ColorApp.greyOpacity,
radiusSize: 30,
widthShadow: 5,
blurStyle: BlurStyle.normal,
makeBlurColorDark: true,
)
);
Classes Helper Tools
NetworkManager
Feature
- Fix Error "XMLHttpRequest" found in platform Web.
- Feature "CallBack()" return value like interface.
- Feature NetworkType.file : to upload file in all platform( Android/IPhone/Web).
- Class "NetworkHeaderTools" to generate "bearerToken()" and "basicAuth_usernameAndPassword()" easily.
Simple Example
- There is many steps to call API, you need to prepare: Body, Url, Header, token.
- Here is guide
1- Generate Body
Map<String, dynamic> bodyParameter = Map();
bodyParameter[ "payment_method"] = "cash";
bodyParameter[ "price"] = "123";
2- Call Class "NetworkManagerDio.dart"
We will return the response in format JSON
Response response = await NetworkManagerDio().post( url , body: bodyParameter );
if (response.statusCode == 200) {
var result = CityResponse.fromJson( response.data);
return result;
}
NetworkConfigDio
- This class responsible for add "BaseUrl" to all EndPoint apis.
var config = NetworkConfigDio( baseUrl: "http://example.com");
NetworkManagerDio( { config: config})
- This Class responsible for add header in all apis like token
var config = NetworkConfigDio(
baseUrl: "http://example.com",
headers : myHeader
);
NetworkManagerDio( { config: config})
NetworkType
NetworkManagerDio().get();
NetworkManagerDio().post();
NetworkManagerDio().put();
NetworkManagerDio().delete();
NetworkManagerDio().file();
Enum of Network type
enum NetworkTypeDio{
get,
post,
put,
delete,
file
}
Time Out
NetworkManagerDio().get( timeOutSecond: 50 );
Handler Errors
- Handler Error XMLHttpRequest by using "NetworkManagerDio" set parameter "handleErrorXMLHttpRequest = true"
Upload File
- What is class "xFile" it's famous used by plugin "cross_file".
- Generate XFile used by image picker
class "NetworkRequestFile"
this class used to set the path of file of "xFile" and set the key/value of file
Example upload file type "xFile"
Future _startAPI() async {
//body request
Map<String, dynamic> body = Map();
body[ "payment_method"] = "cash";
body[ "price"] = "123";
//set type requestFile
NetworkRequestFile? requestFile = NetworkRequestFile.fromXFileAndBody( xFile!, body );
//header
var token = await UserSingleTone.instance().getToken();
Map<String, String> header = NetworkHeaderTools.bearerToken( token );
NetworkManagerDio().file(urlApiLink,
requestFile: requestFile,
headers: header,
callback: (status, msg, json){
parseJson(json );
});
- You Can Make Type Method PUT by call method
requestFile.setTypeMethodPut();
Types Of Webservice Network Dependence
- dio : use class "NetworkManagerDio.dart"
- http : use class "NetworkManagerHttp.dart"
LangFastor
Get Start Setup
- from main method call:
await LangFastor.setupFromMainMethod();
- from MyApp() class inside build() method write :
class MyApp extends StatelessWidget {
// This widget is the root of your application.
@override
Widget build(BuildContext context) {
LangFastor.setupFromBuildMethod(context);
.....
}
}
- in yaml add path of assets
assets:
- assets/lang/
- create new json file named "ar.json" in path : assets/lang/ar.json
Section: How To Change Language Direction
Arabic right-to-left "RTL" Layout Direction
How to auto change direction from ( English => Arabic ) left/right
@override
Widget build(BuildContext context) {
return Scaffold(
body: SafeArea(child: getDirection()),
resizeToAvoidBottomInset: true,
);
}
Widget getDirection() {
return Directionality(
textDirection: LangFastor.getTextDirection(),
child: Builder(
builder: (BuildContext context) {
return MediaQuery(
data: MediaQuery.of(context).copyWith(
textScaleFactor: 1.0,
),
child: blocConsumer(),
);
},
),
);
}
Method Handle Arabic/English
Set/Get Arabic Value
- How To Set Arabic or English
LangFastor.setArabic(context);
LangFastor.setEnglish(context);
- How to check anywhere lang is arabic
- this return boolean
LangFastor.isArabic
Dropdown Handle Direction Arabic
DropdownFastor(
textDirection: LangFastor.getTextDirection(),
Handle Stack Direction Left/Right Arabic
PositionFastor.directional(
textDirection: TextDirection.rtl,
child: Text(""),
top: 0,
start: 0 ,
)
- use "PositionedFastor.langFastor()" auto choose which langauge use used when use LangFastor plugin
PositionedFastor.langFastor(
child: Text(""),
top: 0,
start: 0 ,
)
Handle The Container Alignment Left/Right Arabic
- Fix Arabic Alignment of the "Container" by using "LangFastor.getAlignmentGeometry()" return left alignment
Container(
width: DeviceTools.getWidth(contextPage),
alignment: LangFastor.getAlignmentGeometry(),// Alignment.topRight in arabic, while in english Alignment.topLeft
child: menuFrameUI(),
);
-
add methods "getAlignmentGeometryStart()" it's return left Container( alignment ) in english, while in arabic return right Container( alignment )
-
add methods "getAlignmentGeometryEnd()" it's return right Container( alignment ) in english, while in arabic return left Container( alignment )
Section: Arabic Translation
- There is Many Ways To Translate English text to Arabic Text :
- First One Using json file to save english text as key while save arabic transalation as value
- Second One Is Translate english to arabic In One Line.
First Way : Using Json File To Save Translation
- write json with key/value for each english word
- in path project : assets/lang/ar.json
{
"Login" : "تسجيل الدخول" ,
"" : ""
}
- In Widget Text or Button-Text
- Use "english-world".trf()
- where .trf() means translate by fastor, where used to translate any string Object
Text( "Login".trf() )
Second Way : Write To Arabic In One Line
- Use "ENGLISH-WORD".arf("ARABIC-WORD")
- where arf() means arabic by fastor, where used to translate any string Object
Text( "Login".arf("تسجيل دخول" ) )
How To Add In Network Header The Lang Value
- Add in "NetworkHeaderTools" the "LangFastor" new method "bearerTokenAndLang()" return header with "lang" = ar or en
- the plugin code will do this step when used method "bearerTokenAndLang()" :
header[ "Authorization"] = "Bearer " + token;
header[ "lang"] = LangFastor.isArabic ? "ar" : "en";
- Example Can Use This Method NetworkHeaderTools.bearerTokenAndLang()
//header
Map<String, String> header = NetworkHeaderTools.bearerTokenAndLang( tokenFromCache );
//webservice
var responseDio = NetworkManagerDio().get(url, headers: header );
Dropdown:
- Handle Direction ltr/rtl
return DropdownFastor(
textDirection: LangFastor.getTextDirection(),
SaveFastor
-
Save In Cache By Using Plugin SharedPreference
-
Can Save Single Map() object
-
Can Save List of Map() Object
-
Setup
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
Fastor.initializeApp(context); //init Fastor Plugin here
}
- methods to save
SaveFastor.setMap( );
SaveFastor.setMapList( );
SaveFastor.setInt();
SaveFastor.setString();
SaveFastor.setBool();
- methods to get
SaveFastor.getMap( );
SaveFastor.getMapList( );
SaveFastor.getInt();
SaveFastor.getString();
SaveFastor.getBool();
- Example Get Username From Cache In Text Widget
Widget loginContentUI(){
return ColumnFastor(children: [
TextFastor( "Test get username: " + SaveFastor.getString( "username"))
]);
}
ClipboardFastor
- save and get to clipboard of mobile
class ClipboardFastor {
static Future save(String valueToSave ) async {
....
}
static Future<String> get() async{
...
}
}
DeviceTools
Size
- get device width/height with some feature methods
- method for calculate percentage of device size
double d = DeviceTools.getWidth(context);
double d = DeviceTools.getHeight(context);
double half = DeviceTools.getPercentageWidth(context, 0.5);
double d = DeviceTools.getHeightInsideSafeArea(context);
- method get platform of this device "android/ios/browser/mobile"
- method get orientation partial/landscape
PlatFrom
- check type platform
- check is mobile browser or mobile application
bool b = isPlatformWeb();
bool b = isMobile();
bool b = isAndroid();
bool b = isIOS();
bool b = isBrowserMobile();
bool b = isBrowserAndroid(); // any type of platform mobile like: ios or android
bool b = isBrowserIOS();
bool b = isIOS();
Orientation
bool b = isPortrait();
bool b = isLandscape();
bool b = isPortraitMobile();
bool b = isLandscapeMobile();
NavigationTools
- Transparent View
- can make animation fade while push easily
- add class "NavigationTools" for push() or pushAndRemove()
- can use "resume" plugin to pushWithResumeLifecycle
Navigate To Transparent Screens
NavigationTools.pushTransparentAnimateFade( SimpleScreen() ) ;
NavigationTools.pushTransparent( SimpleScreen() ) ;
Navigate With Animation Fade
NavigationTools.pushAnimateFade( SimpleScreen() ) ;
Navigate With Using Plugin "resume"
NavigationTools.pushResumeAnimateFade( SimpleScreen(), this ) ;
NavigationTools.pushResume( SimpleScreen() , this) ;
- Where "this" is screen that extends "ResumableState" when using plugin "resume"
Normal Push
- Push Second Screen Above First Screen
NavigationTools.push( SimpleScreen() );
- Push New Screen Will Clear All Previous Screen Opening
NavigationTools.pushAndRemoveUntil( SimpleScreen() );
ToolsWait
- Make any action after waiting some time. Juse method "ToolsWait.waitToDo()"
//wait to remove cache
ToolsWait.waitToDo(100, () {
GoTo.splashApp( context);
});
ToolsPhone
- add method "ToolsPhone.fixEgyptAndSaudiNumber()" fix egyption people ways of enter mobile number.
- add method "ToolsPhone.fixEgyptAndSaudiNumber()" fix saudi people ways of enter mobile number.
bool status = await InternetTools.isConnected();
ZoneTools
- method "ZoneTools.getZoneCountryDialCode()"
- method "ZoneTools.getCountryISOCode()"
InternetTools
- class "InternetTools" for check for internet connection.
bool status = await InternetTools.isConnected();
ToolsValidation
Phone Number Checker
- this check it's like "0101234568" to be return true, if it hase any abc it will return false
ToolsValidation.checkTextIsPhoneNumberCharsOnlyWithoutAbc( text);
- Valid Mobile
ToolsValidation.isPhoneMobileValid( text);
- Egyptian Phone Number
ToolsValidation.egyptionCodeCountry_returnByPlus( text);
- Validate Not To Write Arabic Phone Number like ١٢٣٤٥٦٧٨٩٠
ToolsValidation.isStringContainArabicNumber( text);
ToolsValidation.isPhoneMobileValidAndEnglishLetter( text );
Password
- password greater than 8 character
ToolsValidation.isPasswordValid( text);
Valid Text
ToolsValidation.isValid( text);
ToolsValidation.isEmpty( text);
ToolsValidation.isMoreThan2( text);
Name / Email
ToolsValidation.isNameFull( text);
ToolsValidation.isName( text);
ToolsValidation.isEmail( text);
List
ToolsValidation.isValidList( listString );
ToolsValidation.isEmptyList( listString );
ToolsValidation.isEmptyListInteger( listInteger);
ToolsValidation.isValidListInteger( listInteger );
Zero Checker
ToolsValidation.isZero( numString );
ToolsValidation.isNotZeroInt( numInteger );
ToolsValidation.isZeroInt( numInteger );
ToolsValidation.isValidInteger( numInteger );
ApiParserFastor
- Parse json in dynamic.
- example some integer return from backend as "1" or 1 this issue cause exception in parse json.
- Convert 0 and 1 to boolean variable
Parse Zero And One to Boolean
static bool isSuccess(int? n) {
....
}
static bool isTrue(int? n) {
....
}
static bool isFalse(int? n) {
....
}
static bool isFailed(int? n) {
....
}
static bool parseBoolean_int(int? n) {
....
}
static bool parseBoolean(String? n) {
...
}
Parse Boolean to Zero And One
int i = ApiParserFastor.convertBooleanToZeroAndOne( booleanValue );
Parse Double Or Integer to String
- fix when api return value someTime in "Int" and sometimes in "Double" like: { "data": 15 } or some times return { "data": 13.5 } remove command "," if found in at big numbers come from backend
static double parseDoubleOrInt(dynamic data) {
......
}
Parse Integer Any Shape to String
- In Api Json Return in integer like 1 or some time in string double qoutaiton like "1". to fix
static int parseIntDynamic(dynamic data) {
....
}
Check Pagination End
- This Working when using pagingate with backend PHP Laravel
*1- example totalBar record is 100, while pagiantor is 10
* current page is 9
* "to" is 10
* >> result false
*
*2- example totalBar record is 100, while pagiantor is 10
* current page is 10
* "to" is 10
* >> result true "there is no next pages"
*3- example totalBar record is 0 zero, while pagiantor is 10
* current page is 1
* "to" is 0
* >> result true "there is no next pages"
*/
static bool isPaginateLaravelEnd(int? currentPage, int? last_page) {
...
}
ValidateResponse
Handle Status Code
- status code of request is between 200 - 210
Response response = await http.get(url);
if( ValidateResponse.isStatusFrom200To210Code( response.statusCode ) ) {
///To-Do after success request
}
Using Dio Network
- method check invalid token
//dio response
Response response = await dio.get(url);
if( ValidateResponse.isResponseStatusCodeInvalidToken(response) ) {
///To-Do token expire or invalid, now do action for clear cache and ask user to login again
}
- example method success request
//dio response
Response response = await dio.get(url);
if( ValidateResponse.isStatusFrom200To210(response) ) {
///To-Do after success request
}
- method to check the string return from api network is json or html to avoid crash in parsing json
//dio response
Response response = await dio.get(url);
if( ValidateResponse.isValidJson(response.data) ) {
///To-Do
}
- method the response type data not found or url not found or bad request. where status code is 400
//dio response
Response response = await dio.get(url);
if( ValidateResponse.isStatusBadRequest(response.data) ) {
///To-Do
}
ResponsiveFastor
-
Choice what view will be shown here in ui, for tablet or iphone.
-
Decide the view will be show for orientation: portrait and landscape
-
each method will return boolean value
Methods
ResponsiveFastor.isTabletPortraitOrIsPhoneNormalSize( context );
ResponsiveFastor.isTabletLandscape( context );
ResponsiveFastor.isTabletPortrait( context );
ResponsiveFastor.isTablet( context );
ResponsiveFastor.isPhoneNormalSize( context );
ResponsiveFastor.isPhoneSmall( context );
PaginateBarFastor
- Used in Admin Panel for pagingate the list of data.
- button: show current page
- text: show total records - items in database - .
- button GoTo to any page
- button next and previous page
constructor
PaginateBarFastor( {
required this.currentPage,
required this.itemTotal,
required this.limitPerPage,
required this.progress,
required this.paginateNumberChange,
required this.colorPrimary,
required this.colorSecondary
}){
- example:
Widget getPaginateBar(){
return PaginateBarFastor(
currentPage: 1, //come from response of paginate backend
itemTotal: 100, //come from response of paginate backend
limitPerPage: 10,
progress: progressStatus,
colorPrimary: Colors.blue,
colorSecondary: Colors.green,
paginateNumberChange: (newPage){
Log.i("PaginateBarFastor() - paginateNumberChange() - newPage: $newPage ");
provider?.tasksRefreshOrDownloadNextPage(context: context, isResetPage: false, newPage: newPage);
},
);
}
At The End
About Developer
• 7 Years of experience build +20 App.
• Mobile Developer: Flutter & Native Android IOS.
• Skills: Dart, Java, Kotlin, Swift UIKit, SwiftUI
• OCA, Oracle Certified Associate.
Follow my Project on Instagram :
How to contribute
Want to contribute to the project? We will be proud to highlight you as one of our collaborators. Here are some points where you can contribute and make Fastor (and Flutter) even better.
Write articles or make videos teaching how to use Fastor (they will be inserted in the Readme and in the future in our Wiki). Offering PRs for code/tests. Including new functions. Any contribution is welcome!
Contact for contribute:
License BSD 3
Copyright (c) 2022, Abdallah Mahmoud Ahmed Shehata
All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are met:
* Redistributions of source code must retain the above copyright notice,
this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above copyright
notice, this list of conditions and the following disclaimer in the
documentation and/or other materials provided with the distribution.
* Neither the name of fastor-app.com nor the names of its contributors
may be used to endorse or promote products derived from this software
without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
POSSIBILITY OF SUCH DAMAGE.
Libraries
- fastor_app_ui_widget
- resource/resources/boarder/BaseBoarderHelper
- resource/resources/boarder/BoarderHelper
- resource/resources/boarder/BorderRadiusTools
- resource/resources/color/ResourceColor
- resource/resources/dimen/DimenResource
- resource/resources/ds/DesignSystemColor
- resource/resources/ds/DesignSystemDimen
- resource/resources/ds/DesignSystemFont
- resource/resources/ds/DesignSystemTools
- resource/resources/ds/DSElevationTools
- resource/resources/ds/LevelDS
- resource/template/AppBarFastor/AppBarFastor
- resource/template/button/ButtonFastor
- resource/template/button/ButtonTemplate
- resource/template/calendar/CalendarTemplate
- resource/template/calendar/offical_sdk/CalenderFastor
- resource/template/calendar/plugin_not_support/flutter_clean_calendar/calendar_tile
- resource/template/calendar/plugin_not_support/flutter_clean_calendar/clean_calendar_event
- resource/template/calendar/plugin_not_support/flutter_clean_calendar/date_utils
- resource/template/calendar/plugin_not_support/flutter_clean_calendar/flutter_clean_calendar
- resource/template/calendar/plugin_not_support/flutter_clean_calendar/simple_gesture_detector
- resource/template/cardview/fixedSize/BaseCardViewTemplate
- resource/template/cardview/fixedSize/CardViewTemplate
- resource/template/chart/multiline/ChartMultiLineFastor
- resource/template/checkbox/CheckboxFastor
- resource/template/checkbox/CheckboxTemplate
- resource/template/click/GestureDetectorTemplate
- resource/template/column/ColumnFastor
- resource/template/column/ColumnTemplate
- resource/template/constants/TemplateSize
- resource/template/container/ContainerTemplate
- resource/template/crop/CropTemplate
- resource/template/date/range/DatePickerHelper
- resource/template/date/range/DateRangePickerResult
- resource/template/date/range/DateRangeTextFieldFastor
- resource/template/date/textfield/DateTextFieldFastor
- resource/template/EdgeInsets/EdgeInsetsTools
- resource/template/elevation/ElevationTemplate
- resource/template/elevation/ShadowContainer
- resource/template/emptyView/EmptyView
- resource/template/image/ImageCircleView
- resource/template/image/ImageFastor
- resource/template/image/ImageView
- resource/template/image/ImageViewTemplate
- resource/template/listview/gridview/GridViewFastor
- resource/template/listview/ItemList/ItemListController
- resource/template/listview/ListViewTemplate
- resource/template/material_app/FastorMaterialApp
- resource/template/page/base/BasePageTemplateProgrees
- resource/template/page/PageFastor
- resource/template/page/PageTemplate
- resource/template/page/ScaffoldFastor
- resource/template/pager_view/PageViewFastor
- resource/template/placeholder/PlaceholderTemplate
- resource/template/progressView/ProgressCircle
- resource/template/progressView/ProgressCircleFastor
- resource/template/progressView/ProgressSpinFastor
- resource/template/progressView/ProgressSpinkit
- resource/template/radio/RadioFastor
- resource/template/radio/RadioTemplate
- resource/template/row/RowScrollFastor
- resource/template/row/RowTemplate
- resource/template/scrollview/ScrollFastor
- resource/template/scrollview/ScrollSpeed
- resource/template/scrollview/ScrollViewPage
- resource/template/scrollview/SingleChildScrollViewTemplate
- resource/template/select/extend_dropdow/ExtendDropdownButton
- resource/template/select/fastor/DropdownFastor
- resource/template/select/fastor/widget/DropdownContent
- resource/template/select/fastor/widget/PreviousSelected
- resource/template/select/fastor/widget/ProgressDropdown
- resource/template/select/template/SpinnerTemplate
- resource/template/select/view/SpinnerView
- resource/template/stack/positioned/PositionedTools
- resource/template/stack/StackTemplate
- resource/template/switch/SwitchFastor
- resource/template/switch/SwitchTemplate
- resource/template/TabBar/simple/ItemTabBarFastor
- resource/template/TabBar/simple/logic/TabBarController
- resource/template/TabBar/simple/TabBarFastor
- resource/template/table/TableFastor
- resource/template/table/TableView
- resource/template/text/BaseTextTemplate
- resource/template/text/style/TextStyleTemplate
- resource/template/text/TextFastor
- resource/template/text/TextTemplate
- resource/template/textfield/email_or_phone/TextFieldEmailOrPhoneFastor
- resource/template/textfield/form/TextFormFieldTemplate
- resource/template/textfield/mobile/MobileCountryFastor
- resource/template/textfield/otp/OTPTextFieldFastor
- resource/template/textfield/otp/TextFieldsOtp
- resource/template/textfield/password/TextFieldPasswordFastor
- resource/template/textfield/stateless/TextFieldFastor
- resource/template/textfield/template/TextFieldTemplate
- resource/template/textfield/TextFieldTemplateBase
- resource/template/textfield/validator/MapValidatorTypeToForm
- resource/template/textfield/validator/ValidatorTemplate
- resource/template/textfield/validator/ValidatorType
- resource/template/timer/logic/TimerLogic
- resource/template/timer/TimerCountDownFastor
- resource/template/toolbar/simple/ToolbarSimpleFastor
- resource/toolsFastor/cache/ClipboardFastor
- resource/toolsFastor/cache/Save
- resource/toolsFastor/cache/SaveFastor
- resource/toolsFastor/device/deviceChangeSize/DeviceSizeChangeBase
- resource/toolsFastor/device/deviceChangeSize/ListenerChangeDeviceSize
- resource/toolsFastor/device/DeviceTools
- resource/toolsFastor/fix_bugs_web/fake_register/fake_platform_view_registry
- resource/toolsFastor/fix_bugs_web/fake_register/platform_view_registry
- resource/toolsFastor/fix_bugs_web/html_fake
- resource/toolsFastor/initialize_app/Fastor
- resource/toolsFastor/lang/LangFastor
- resource/toolsFastor/lang/PositionDirectionFastor
- resource/toolsFastor/lang/PositionedFastor
- resource/toolsFastor/lang/PositionFastor
- resource/toolsFastor/log/Log
- resource/toolsFastor/log/log_debug
- resource/toolsFastor/log/LogDeveloperInfo
- resource/toolsFastor/network/dio/DioParameter
- resource/toolsFastor/network/dio/DioServiceFastor
- resource/toolsFastor/network/dio/NetworkConfigDio
- resource/toolsFastor/network/dio/NetworkManagerDio
- resource/toolsFastor/network/http/NetworkManagerHttp
- resource/toolsFastor/network/internet/InternetTools
- resource/toolsFastor/network/NetworkHeaderTools
- resource/toolsFastor/network/NetworkRequestFile
- resource/toolsFastor/network/NetworkTypeDio
- resource/toolsFastor/network/parse/ApiParserFastor
- resource/toolsFastor/network/parse/ApiTools
- resource/toolsFastor/network/ValidateResponse
- resource/toolsFastor/size/TextWidthCalculatorFastor
- resource/toolsFastor/state/FastorStateManagement
- resource/toolsFastor/timer/ToolsWait
- resource/toolsFastor/values/PriceTools
- resource/toolsFastor/values/ToolsPhone
- resource/toolsFastor/values/ToolsString
- resource/toolsFastor/values/ToolsValidation
- resource/toolsFastor/values/UniqueIdTools
- resource/toolsFastor/zone/ZoneTools
- resource/uiFastor/admin/paginate_number/logic/ButtonNextPreviousController
- resource/uiFastor/admin/paginate_number/logic/NumberController
- resource/uiFastor/admin/paginate_number/PaginateBarFastor
- resource/uiFastor/admin/paginate_number/widget/boxNumberItem
- resource/uiFastor/admin/paginate_number/widget/ButtonBarPaginate
- resource/uiFastor/admin/paginate_number/widget/NumberViewPaginate
- resource/uiFastor/admin/paginate_number/widget/TotalInformationBarPaginate
- resource/uiFastor/iphoneNotchBar/NotchBarConstant
- resource/uiFastor/language/DirectionLanguage
- resource/uiFastor/language/LanguageTools
- resource/uiFastor/responsive_views/helper/PortraitToLandscapeUtilsResponsiveFastor
- resource/uiFastor/responsive_views/helper/ResponsiveFastor
- resource/uiFastor/responsive_views/helper/ResponsiveFastorConstant
- resource/uiFastor/responsive_views/landscape/shape_content_center_top/PortraitBodyToCenterPageInLandscapeResponsiveFastor
- resource/uiFastor/responsive_views/landscape/shape_fourm_submit/ForumPortraitToLandscapeResponsiveFastor
- resource/uiFastor/scroll/FastorScrollTheme
- resource/uiFastor/statusBar/StatusBarConstant