ما هي AppBar؟
شريط علوي مادي (Material) يُعرض عادةً داخل:
Scaffold(appBar: AppBar(...))Dartيوفّر عنوان الصفحة، أزرار رجوع/قائمة، إجراءات (actions)، تبويبات… إلخ.
أهم الخصائص (مع الشرح السريع)
بنية المحتوى
leading: Widget?
العنصر في أقصى اليسار (Android) / أقصى اليمين (RTL). افتراضيًا:- زر رجوع إن وُجد مسار سابق في
Navigator. - زر قائمة (hamburger) إن كان هناك
Scaffold.drawerولا يوجد مسار سابق. - عيّنه يدويًا لتخصيصه (مثل شعار أو زر مخصص).
- زر رجوع إن وُجد مسار سابق في
automaticallyImplyLeading: bool(افتراضي true)
هل يُولِّد زر الرجوع/القائمة تلقائيًا؟ اجعلهfalseلإخفائه إن وضعتleadingمخصّصًا.title: Widget?
عادةText('العنوان'). يمكنك وضع أي ويدجت (حتى حقل بحث).actions: List<Widget>?
Widgets في الطرف المقابل لـleading(مثل أزرار البحث، الإشعارات، قائمة منسدلة).flexibleSpace: Widget?
طبقة خلف الـ AppBar (تحت العنوان والأزرار). ممتازة للخلفيات المتدرجة/الصور/الـ blur.bottom: PreferredSizeWidget?
شريط سفلي أسفل الـ AppBar (مثلTabBarأو أي ويدجت داخلPreferredSize).
الألوان والارتفاع والظل
backgroundColor: Color?
لون الخلفية.foregroundColor: Color?
يؤثر على لون النصوص/الأيقونات داخل الـ AppBar.elevation: double?
ظلّ الشريط (0 لإلغاء الظل).shadowColor: Color?
لون الظل.surfaceTintColor: Color?(Material 3)
صبغة على السطح؛ ألغِ تأثيراتها بـforceMaterialTransparency: true.scrolledUnderElevation: double?(Material 3)
ظل إضافي عندما يمرّ المحتوى أسفل الـ AppBar أثناء التمرير.
التخطيط والمحاذاة
centerTitle: bool?
محاذاة العنوان للوسط. (بعض المنصات تُوسّطه افتراضيًا؛ استخدمه للتثبيت).titleSpacing: double?
المسافة الأفقية حول العنوان. القيمة الافتراضية مناسبة غالبًا.toolbarHeight: double?
ارتفاع شريط الأدوات (الافتراضيkToolbarHeight = 56).leadingWidth: double?
عرض مساحةleading(مفيد لوضع شعار عريض).primary: bool(افتراضي true)
إن كانtrueيحترم مساحة شريط الحالة (status bar). اجعلهfalseإذا استخدمته بعيدًا عن أعلى الشاشة.
النصوص والأنماط
titleTextStyle,toolbarTextStyle
تخصيص نمط النصوص (يمكن أيضًا عبرAppBarTheme).iconTheme,actionsIconTheme
تخصيص نمط الأيقونات في الجهتين.
الشكل والقصّ والتراكب على النظام
shape: ShapeBorder?
حواف سفلية منحنية مثل:shape: RoundedRectangleBorder( borderRadius: BorderRadius.vertical(bottom: Radius.circular(24)), )clipBehavior: Clip
لقصّ المحتوى تبعًا للشكل.systemOverlayStyle: SystemUiOverlayStyle?
لتحديد لون/سطوع شريط الحالة (أيقونات بيضاء أو داكنة). مثال:systemOverlayStyle: SystemUiOverlayStyle.lightexcludeHeaderSemantics: bool
لحالات إمكانية الوصول (نادراً ما تغيّره).forceMaterialTransparency: bool(M3)
يجعل الخلفية شفافة ويعطّل طبقات الصبغة الافتراضية.
أمثلة عملية
1) أبسط AppBar
Scaffold(
appBar: AppBar(
title: Text('الرئيسية'),
),
)Dart2) AppBar مع actions وleading مخصص
AppBar(
leading: IconButton(
icon: Icon(Icons.arrow_back),
onPressed: () => Navigator.pop(context),
),
title: Text('الصفحة'),
actions: [
IconButton(icon: Icon(Icons.search), onPressed: () {}),
PopupMenuButton<String>(
onSelected: (v) {},
itemBuilder: (_) => [
PopupMenuItem(value: 's1', child: Text('إعدادات')),
PopupMenuItem(value: 's2', child: Text('حول')),
],
),
],
)Dart3) AppBar مع تبويبات (TabBar)
تحتاج
DefaultTabController.
DefaultTabController(
length: 3,
child: Scaffold(
appBar: AppBar(
title: Text('أقسام'),
bottom: TabBar(
tabs: [
Tab(text: 'الكل'),
Tab(text: 'المفضلة'),
Tab(text: 'حديث'),
],
),
),
body: TabBarView(
children: [/* Widgets */ Container(), Container(), Container()],
),
),
);Dart4) تدرّج لوني عبر flexibleSpace
AppBar(
title: Text('متدرّج'),
elevation: 0,
flexibleSpace: Container(
decoration: BoxDecoration(
gradient: LinearGradient(
begin: Alignment.topRight,
end: Alignment.bottomLeft,
colors: [Colors.teal, Colors.blue],
),
),
),
)Dart5) AppBar شفاف فوق صورة (Hero header)
مهم:
extendBodyBehindAppBar: trueوتهيئة التراكب.
Scaffold(
extendBodyBehindAppBar: true,
appBar: AppBar(
backgroundColor: Colors.transparent,
elevation: 0,
systemOverlayStyle: SystemUiOverlayStyle.light, // أيقونات بيضاء
),
body: Stack(
fit: StackFit.expand,
children: [
Image.network('https://picsum.photos/1200/800', fit: BoxFit.cover),
// محتوى…
],
),
);Dart6) AppBar مع Drawer تلقائي
Scaffold(
appBar: AppBar(title: Text('قائمة')),
drawer: Drawer(child: ListView(children: [ListTile(title: Text('عنصر'))])),
body: Container(),
);Dartعند إضافة
drawer، سيظهر زر القائمة تلقائيًا فيleading(ما لم تعيّنه يدويًا).
7) bottom مخصص بارتفاع معين
AppBar(
title: Text('ترويسة'),
bottom: PreferredSize(
preferredSize: Size.fromHeight(48),
child: Container(
height: 48,
alignment: Alignment.center,
child: Text('شريط سفلي مخصص'),
),
),
)
Dartتخصيص شامل عبر Theme
بدل تكرار الأنماط في كل صفحة، استخدم AppBarTheme:
MaterialApp(
theme: ThemeData(
useMaterial3: true, // اختياري
appBarTheme: AppBarTheme(
backgroundColor: Colors.white,
foregroundColor: Colors.black87,
elevation: 0,
centerTitle: true,
systemOverlayStyle: SystemUiOverlayStyle.dark,
titleTextStyle: TextStyle(fontSize: 18, fontWeight: FontWeight.w600),
iconTheme: IconThemeData(size: 22),
),
),
home: Scaffold(appBar: AppBar(title: Text('مثال'))),
);
Dartنصائح ذهبية ومحاذير
- ✅ Drawer: إذا لديك
Scaffold.drawerولم تضعleading، سيظهر زر الـ menu تلقائيًا. لـendDrawerلا يوجد زر تلقائي—أضِفه فيactionsأوleading:IconButton( icon: Icon(Icons.menu_open), onPressed: () => Scaffold.of(context).openEndDrawer(), )استخدمBuilderللحصول علىcontextالصحيح داخلAppBar. - ✅ عنوان طويل: استخدم
title: Text('عنوان طويل جدًا', overflow: TextOverflow.ellipsis)أو اجعل العنوان ويدجت مرنة. - ✅ شفافية تامة: اجمع بين
backgroundColor: Colors.transparent,elevation: 0, وقد تحتاجscrolledUnderElevation: 0مع M3. - ✅ التباين مع شريط الحالة: غيّر
systemOverlayStyleليتناسب لون أيقونات شريط الحالة مع الخلفية (فاتحة/داكنة). - ✅
primary: false
استخدمه عندما تضع AppBar داخل منطقة ليست أعلى الشاشة (داخلNestedScrollViewأو قسم داخلي). - ✅ TabBar: تأكد من وجود
DefaultTabControllerومواءمةlengthمع عدد التبويبات. - ⚠️ لا تخلط خصائص SliverAppBar هنا
خصائص مثلpinned/floating/snapتخصSliverAppBarضمنCustomScrollView/NestedScrollView.
إن احتجت سلوكًا مرنًا مع التمرير—فكّر باستخدامSliverAppBar. - ⚠️ M2 vs M3
عندuseMaterial3: trueقد تتغيّر بعض السلوكيات الافتراضية (ظلال، صبغات). استخدمforceMaterialTransparencyأو عدّلAppBarThemeلضبط المظهر.
أسئلة شائعة سريعة
- كيف أزيل خط الظل؟
elevation: 0(+scrolledUnderElevation: 0في M3). - كيف أوسّط العنوان دائمًا؟
centerTitle: true. - كيف أضع حقل بحث داخل AppBar؟
إمّا فيtitle:title: TextField( decoration: InputDecoration(hintText: 'ابحث...', border: InputBorder.none), )أو ضع شريط البحث فيbottom. - كيف أضع صورة/تدرّج؟
استخدمflexibleSpaceمعContainer+decoration.