كيفية اضافة بيانات داخل Sqlflite في Flutter والتعامل مع الData
في هذا الكود سوف نتعرف معكم على كيفية التعامل مع البيانات في فلاتر وكيفية اضافة بيانات اي عمل insert لها داخل القوائم وهذا الدرس من سلسلة تعلم Sqlflite بشكل مبسط لا تنساه وايضا سوف نقوم في نهاية الدوره على تكوين تطبيق رائع تستطيع من خلاله التعامل مع البيانات بشكل اوفلاين واضافة والتعديل وحذف بيانات وكل هذا سوف نتعرف عليه في المقالات القادمه بإذن الله تعالى .
تعتبر لغة dart مخصصه ل flutter و فلاتر مخصصة لتطوير و صناعة تطبيقات اندرويد او الايفون ونحن نعمل على تقديم شرح لكل من يريد تعلم دارت و برمجة و تطوير التطبيقات ios , android , web او غيرها ويمكنك تحميل حزمة sdk من خلال الانتقال الى الموقع الخاص بهم وعمل download وتثبيته والبدء في انشاء اول app او برنامج لك وسوف نعمل على تقديم دورة لعمل العديد من أفضل التطبيقات وكل شيئ تقريبا حول هذة اللغه وتقديم لكم كتاب في الدارت لتطوير من نفسك حيث يوجد الكثير من كتب development ولكن سوف نقدم لكم افضل كتاب عربي في تعلم الدارت والفلاتر
ما المميز في إطار العمل الخاص بفلاتر
يمكنك عمل تطبيق خاص بك و الـ apps التي يتم كتابها باستخدام language dart تعمل على مختلف المنصات ويمكنك البحث في جوجل عن طريق الانتقال الى google والبحث لماذا بناء التبيطقات بفلاتر ويوجد شركة او العديد من الشركات تهتم ب كيفية العمل بفلاتر وال ui لانه تستطيع من خلال flutter تطوير العديد من التطبيقات بكود واحد بالعربي او الانجليزي لكي تكون البداية لديك قوية ويمكنك الاستعانه بي المصدر ال مستخدم من موقع فلاتر .
انشاء ميثود لعمل insert للبيانات داخل Database
سوف تقوم بعمل دالة تستقبل بيانات مستقبليه بمعنى ان البيانات سوف تحصل عليها فيما بعد ولهذا سوف تكون الداله من نوع Future وليس void وايضا سوف نضع العناصر التي نريد اضافتها واماكنية التعامل معها والتعديل عليها ونقوم بعمل database.transaction وناخذ منه عنصر وهو txn وهذا العنصر سوف نحتاج منه الامر insert لامكانية الاضافة وايضا نقوم بكتابة الامر الموجود بين ' ' وهو الذي يحوي العملية حيث ان tasks هو اسم الجدول وبعدها تدخل البيانات التي توجد في هذا الجدول وبعدها تضع البيانات التي يستقبلها منك .واخيرا تقوم بوضع catchError بحيث اذا ظهر ايرور يظهر لك السبب .
database.code
Future insert_database({
required String title,
required String time,
required String date,
}) async {
await database.transaction((txn) {
return txn
.rawInsert(
'INSERT INTO tasks(title , time , date , status) VALUES( "$title" , "$time" , "$date" , "active" )')
.then((value) {
print('done $value');
}).catchError((onError){
print('Error ${onError.toString()}');
});
});
}
المتغيرات المستخدمه لاضافة البيانات
في هذا الجزء سوف نرجع الى اول المشروع ونقوم بوضع البيانات التي نقوم بتمريرها وهي عباره عن العنوان والوقت والتاريخ .
variables of database
var scaffoldKey = GlobalKey<ScaffoldState>();
var formKey = GlobalKey<FormState>();
bool isBottomSheetShow = false;
IconData iconDate = Icons.edit;
var title_controller = TextEditingController();
var time_controller = TextEditingController();
var date_controller = TextEditingController();
فتح واغلاق ال floatingActionButton وتغيير الicon لكل وضعيه واضافة البيانات اذا غير فارغه .
الان نقوم بعمل العمليه على العناصر النصيه التي نقوم بإدخالها وهي scaffoldKey ونضع الشرط الخاص بها داخل floatingActionButton للتاكد من ان الشرط تم تحقيقه ولم يحدث اي مشاكل اثناء عملية التنفيذ .
key: scaffoldKey,
appBar: AppBar(
title: Text(appbar[currentIndex]),
),
body: screen[currentIndex],
floatingActionButton: FloatingActionButton(
onPressed: () async {
if (isBottomSheetShow) {
if (formKey.currentState!.validate()) {
insert_database(
title: title_controller.text,
time: time_controller.text,
date: date_controller.text)
.then((value) {
Navigator.pop(context);
isBottomSheetShow = false;
setState(() {
iconDate = Icons.edit;
});
});
}
اضافة FormField لاضافة بيانات داخل BottomSheet
الان سوف نقوم بعمل بيانات نصية وهذه البيانات سبق وقمنا بوضعها داخل الReusable Components ولذلك لن نحتاج الى كتابتها من اول وجديد بل نقوم بكل بساطة بإستدعائها بسهوله من الReusable Components والتعديل على بعض المحتويات والشروط التي تحتاجها منا فقط وليس إلا .
floatingActionButton: FloatingActionButton(
onPressed: () async {
if (isBottomSheetShow) {
if (formKey.currentState!.validate()) {
insert_database(
title: title_controller.text,
time: time_controller.text,
date: date_controller.text)
.then((value) {
Navigator.pop(context);
isBottomSheetShow = false;
setState(() {
iconDate = Icons.edit;
});
});
}
} else {
scaffoldKey.currentState!.showBottomSheet(
(context) => Padding(
padding: const EdgeInsets.all(15.0),
child: Form(
key: formKey,
child: Column(
mainAxisSize: MainAxisSize.min,
children: [
defaultFormField(controller: title_controller,
type: TextInputType.text,
validate: (String? value){
if (value!.isEmpty) {
return 'title is null';
}
return null;
},
label: 'Task Title',
prefix: Icons.title),
SizedBox(height: 5,),
defaultFormField(controller: time_controller,
type: TextInputType.datetime,
onTap: (){
showTimePicker(context: context,
initialTime: TimeOfDay.now())
.then((value) {
setState(() {
time_controller.text = value!.format(context);
});
print(value.toString());
});
},
validate: (String? value){
if (value!.isEmpty) {
return 'time is null';
}
return null;
},
label: 'Task Time',
prefix: Icons.timer_sharp),
SizedBox(height: 5,),
defaultFormField(controller: date_controller,
type: TextInputType.datetime,
onTap: (){
showDatePicker(context: context,
initialDate: DateTime.now(),
firstDate: DateTime(2018),
lastDate: DateTime(2025)).then((value) {
date_controller.text = DateFormat.yMMMd().format(value!);
print(value.toString());
});
},
validate: (String? value){
if (value!.isEmpty) {
return 'time is null';
}
return null;
},
label: 'Task Time',
prefix: Icons.timer_sharp),
],
),
),
),
elevation: 20.0,
);
isBottomSheetShow = true;
setState(() {
iconDate = Icons.add;
});
}
},
child: Icon(iconDate),
),
كلاس componant الذي يحتوي على التصاميم
في هذا الكلاس يوجد التصميمات التي تستخدم بكثرة بدلا من تصميم الشكل في كل مره يمكنك تصتيمه واعادة استخدامه في اي ماكن مع تغيير المتغيرات التي ترغب بها , وهنا كنت استخدم بشكل كبير الTextFormField وهذا سوف نستخدمه في اكثر من مكان لذلك قمنا بوضعه في كلاس خارجي وهذا ما يدعى بالReusable Components والتي سبق وشرحناها لكم في الدروس السابقة .
Widget defaultFormField({
required TextEditingController controller,
required TextInputType type,
Function(String)? onSubmit,
Function(String)? onChange,
Function()? onTap,
bool isPassword = false,
required String? Function(String?)? validate,
required String label,
required IconData prefix,
IconData? suffix,
Function()? suffixPressed,
bool isClickable = true,
}) =>
Padding(
padding: const EdgeInsets.all(15.0),
child: TextFormField(
controller: controller,
keyboardType: type,
obscureText: isPassword,
enabled: isClickable,
onFieldSubmitted: onSubmit,
onChanged: onChange,
onTap: onTap,
validator: validate,
decoration: InputDecoration(
labelText: label,
prefixIcon: Icon(
prefix,
),
suffixIcon: suffix != null ? IconButton( onPressed: suffixPressed , icon: Icon( suffix,),) : null,
border: OutlineInputBorder(),
),
),
);
تثبيت مكتبة عمل format للتاريخ
الان تمت العملية بنجاح وتم تشغيل التطبيق بدون اي مشاكل والبيانات تظهر بشكل نصي في الprint وسوف نتعلم كيف نظهرها في الاماكان الاخرى في الدروس المقبلة