I'm always excited to take on new projects and collaborate with innovative minds.

Phone

+20 115 052 9992

Website

https://ibrahimahmed.online/

Social Links

ازاي تحل مشكلة تهنيج تطبيق فلاتر (Flutter App Freezing) وتخلي الأداء صاروخ باستخدام Isolate Spawn

فئات المقال: Tutorials, Coding Challenges ازاي تحل مشكلة تهنيج تطبيق فلاتر (Flutter App Freezing) وتخلي الأداء صاروخ باستخدام Isolate Spawn يا هلا بيك يا صديقي

ازاي تحل مشكلة تهنيج تطبيق فلاتر (Flutter App Freezing) وتخلي الأداء صاروخ باستخدام Isolate Spawn
Reading Count: 3

فئات المقال: Tutorials, Coding Challenges

ازاي تحل مشكلة تهنيج تطبيق فلاتر (Flutter App Freezing) وتخلي الأداء صاروخ باستخدام Isolate Spawn

يا هلا بيك يا صديقي المبرمج! أكيد في يوم كنت شغال على تطبيق فلاتر (Flutter) وزي الفل، وفجأة قررت تعمل عملية حسابية ثقيلة، زي إنك تفك ضغط ملف كبير (File Decompression)، أو تعالج مصفوفة بيانات ضخمة (Large Data Arrays)، أو تعمل تحليل لصورة بحجم كبير. اللحظة اللي بتدوس فيها على الزرار، بتلاقي الشاشة جمدت تماماً (UI Freezing)، والـ Animation وقفت، والمستخدم حس إن التطبيق هنج أو هنيّك، و maybe التطبيق يقفل لوحده (ANR - Application Not Responding). الوجع ده كلنا عشناه!

السبب الرئيسي للمشكلة دي هو إن لغة دارت (Dart) لغة بتشتغل على خيط واحد أساسي (Single-threaded Execution Model)، والمعروف بالـ Main Isolate أو الـ UI Thread. الخيط ده بيعمل كل حاجة: بيبني الواجهات (UI Rendering)، وبينفذ الكود، وبيتفاعل مع المستخدم. فلما ترمي عليه عملية تاخد ثواني معدودة، التطبيق كله بيتقفل في وش المستخدم. الحل السحري هنا هو المعالجة المتعددة (Multithreading) باستخدام العزل أو ما يُعرف في فلاتر بالـ Isolate Spawn.

يعني إيه Isolate في دارت وليه بنحتاج Isolate.spawn؟

عشان نفهم الموضوع ببساطة، تخيل إن الـ Main Isolate ده هو شغال لوحده جوه مطعم، بياخد الطلبات، وبيجهز الأكل، ويحاسب الزباين. لو جه طلب "صعب" هياخد وقت، المطعم كله هيعطل. الحل؟ إننا نجيب شيف تاني خالص يشتغل في مطبخ لوحده (ده الـ Isolate الجديد)، ونديله المهمة الثقيلة يخلصها ويرجع لنا بالنتيجة، والمطبخ الأساسي (الواجهة) يفضل شغال ورايق ومستعد لأي مستخدم جديد.

الـ Isolate في دارت (Dart Isolate) هو عبارة عن خيط تنفيذ مستقل بذਾته (Independent Worker Thread)، عنده الذاكرة الخاصة بيه (Memory Heap)، ومش بيشارك الذاكرة مع الـ Main Isolate نهائياً. النقطة دي مهمة جداً عشان تفهم ليه الـ Isolates أمان، لأن مفيش حاجة اسمها Race Conditions أو تداخل في الذاكرة (Memory Corruption). التواصل بينهم بيتم عن طريق إرسال واستقبال الرسائل عبر قنوات اتصال (SendPort و ReceivePort).

إزاي تستخدم Isolate.spawn عملياً لمعالجة البيانات الثقيلة

دلوقتي هنشوف مثال عملي وكود حقيقي بوضح إزاي نعمل تفرع (Spawn) لـ Isolate جديد عشان ينفذ دالة ثقيلة بعيداً عن شاشة التطبيق. فرضا عندنا دالة بتحسب حسابات معقدة في مصفوفة ضخمة:


import 'dart:isolate';
import 'package:flutter/material.dart';

// الدالة الثقيلة اللي هتشتغل في الخلفية
// ملاحظة: لازم تكون دالة مستقلة (Top-level function أو Static method)
void heavyComputationTask(SendPort sendPort) {
  int sum = 0;
  // محاكاة عملية حسابية ثقيلة بتخد وقت
  for (int i = 0; i < 1000000000; i++) {
    sum += i;
  }
  // نبعث النتيجة للـ Main Isolate
  sendPort.send(sum);
}

// دالة لتشغيل الـ Isolate من الـ UI
Future<void> runHeavyTaskInBackground() async {
  // 1. إنشاء بواب استقبال للرسائل
  ReceivePort receivePort = ReceivePort();

  // 2. إطلاق الـ Isolate الجديد وربطه بالدالة
  await Isolate.spawn(heavyComputationTask, receivePort.sendPort);

  // 3. انتظار استقبال النتيجة من الـ Isolate
  var result = await receivePort.first;
  
  print("النتيجة وصلت يا معلم: $result");
}

الكود اللي فوق ده بيوضح البساطة والجمال في استخدام Isolate.spawn. إحنا فتحنا قناة اتصال (ReceivePort)، وبعثنا الـ SendPort بتاعها كمدخل لدالة الـ Isolate. الـ Isolate اشتغل مع نفسه، وخلص الشغلانة، وبعت النتيجة في الـ SendPort، والـ Main Isolate استقبلها وعرضها من غير ما الشاشة تحس بحاجة أصلاً.

نقاط مهمة لازم تاخد بالك منها وأنت شغال مع الـ Isolates

عشان تكون مبرمج شاطر ومحتك بالمشاكل الحقيقية، فيه قواعد ذهبية لازم تحطها في ذهنك وأنت بتستخدم الـ Concurrency في فلاتر:

  • الدوال المستقلة (Top-level Functions): ممنوع تبعت ميثอด جوه Class (Instance Method) عادية لـ Isolate.spawn، لازم الدالة تكون Top-level أو Static عشان الـ Dart Compiler يقدر يعزلها تماماً.
  • نقل الذاكرة (Memory Transfer): بما إن الـ Isolates مش بتشارك نفس الذاكرة، فكل البيانات اللي بتتنقل بينهم بيتعملها Copy (نسخ). تجنب نقل بيانات بحجم ميجابايتات ضخمة جداً في كل رسالة إلا للضرورة القصوى، ولو البيانات كبيرة جداً، فكر في استخدام الـ TypedData.
  • إصدارات دارت الحديثة (Dart 2.15+): وفرت تحسينات خرافية في التعامل مع الـ Isolates وتسهيل نقل البيانات (Send and Receive ports)، فدائماً تأكد إنك شغال على نسخة دارت حديثة في مشروعك.

خاتمة ونصيحة من أخ

يا صديقي، الأداء الجيد (Performance Optimization) هو الفيصل بين تطبيق عادي وتطبيق احترافي المستخدمين بيعشقوه. استخدام الـ Isolate Spawn مش مجرد ميزة رفاهية، ده أداة أساسية لو تطبيقك بيتعامل مع صور، ملفات PDF، شبكات محلية ثقيلة، أو قواعد بيانات ضخمة. متستناش لحد ما المستخدمين يشتكوا من التهنيج، وابدأ طبق مبادئ المعالجة المتعددة (Multithreading) في مشاريعك من دلوقتي. بالتوفيق، ودايماً اكتب كود نضيف ونظيف!


Share

Related posts

Aug 03, 2026 • 1 min read
Reading Count: 2
عنوان تلقائي

يا هلا بيك يا بشمهندس! لو بتطور تطبيق موبايل بـ فلاتر (Flutter)، أكيد في لحظة معينة جالِك أكلينت أو...

Aug 02, 2026 • 1 min read
Reading Count: 6
دليلك الشامل لربط تطبيقات فلاتر (Flutter) بأجهزة إنترنت الأشياء (IoT) عن طريق البلوتوث منخفض الطاقة (BLE)

معرفات الأقسام: 3 دليلك الشامل لربط تطبيقات فلاتر (Flutter) بأجهزة إنترنت الأشياء (IoT) عن طريق البل...

Aug 02, 2026 • 1 min read
Reading Count: 4
عنوان تلقائي

يا هلا بيك يا صاحبي في عالم البرمجة! لو إنت مطور فلاتر (Flutter Developer) وبتشتغل باستمتاع عشان تبن...