التنقل بين شاشات التطبيق باستخدام الـ Intents في أندرويد
يُعدّ التنقل بين الشاشات في تطبيقات أندرويد أحد الجوانب الأساسية التي تحدد تجربة المستخدم. تقوم التطبيقات عادة بتقسيم الوظائف والمحتوى إلى واجهات متعددة (Activities أو Fragments)، مما يجعل من الضروري وجود آلية فعالة للتنقل بينها. تُستخدم Intents كآلية رسمية ومرنة لهذا الغرض ضمن بنية نظام أندرويد، حيث توفر وسيلة معيارية للتواصل بين مكونات التطبيق أو حتى بين التطبيقات المختلفة.
يتناول هذا المقال شرحًا معمقًا لمفهوم Intents في أندرويد، وكيفية استخدامها في التنقل بين الأنشطة المختلفة (Activities)، مع التوسع في عرض الأنواع المختلفة من الـ Intent، والفرق بين Explicit Intent و Implicit Intent، بالإضافة إلى تفاصيل عملية تشمل إرسال البيانات بين الشاشات، واستقبال النتائج، وإدارة دورة حياة الأنشطة ذات الصلة بالتنقل.
ما هو الـ Intent في أندرويد؟
الـ Intent في أندرويد هو كائن يُستخدم للتواصل بين مكونات التطبيق المختلفة مثل Activities، Services، وBroadcast Receivers. يُمكن تعريف الـ Intent على أنه رسالة تحتوي على نوايا أو طلبات من مكون معين إلى مكون آخر، حيث تُشير إلى ما يرغب النظام أو المطور بتنفيذه.
بشكل عام، يستخدم المطورون الـ Intents لعدة أغراض، أهمها:
-
إطلاق نشاط جديد (Activity)
-
بدء خدمة (Service)
-
إرسال بث (Broadcast)
-
إطلاق نشاط خارجي (مثل فتح المتصفح أو الاتصال الهاتفي)
أنواع الـ Intent في أندرويد
1. Intents صريحة (Explicit Intents)
تُستخدم هذه الأنواع من الـ Intent للتنقل إلى نشاط معين داخل نفس التطبيق. يكون هذا النوع من النوايا محددًا باسم الفئة (Class Name) للنشاط الهدف.
javaIntent intent = new Intent(CurrentActivity.this, TargetActivity.class);
startActivity(intent);
2. Intents ضمنية (Implicit Intents)
تُستخدم للتعامل مع الأنشطة التي لا تنتمي بالضرورة لنفس التطبيق، ويتم تحديدها من خلال وصف الإجراء (Action) والمحتوى (Data). النظام يقرر النشاط المناسب لتنفيذ هذا الـ Intent.
javaIntent intent = new Intent(Intent.ACTION_VIEW);
intent.setData(Uri.parse("https://www.google.com"));
startActivity(intent);
التنقل بين الأنشطة (Activities) باستخدام Explicit Intents
للتنقل من شاشة إلى أخرى داخل تطبيق معين، يتم إنشاء كائن من فئة Intent وتحديد النشاط الهدف، ومن ثم استدعاء startActivity().
خطوات أساسية:
-
تعريف النشاط الهدف في ملف
AndroidManifest.xml:
xml<activity android:name=".SecondActivity" />
-
إنشاء الـ Intent داخل النشاط الحالي:
javaIntent intent = new Intent(MainActivity.this, SecondActivity.class);
startActivity(intent);
بهذا الشكل، يتم الانتقال من MainActivity إلى SecondActivity.
تمرير البيانات بين الأنشطة
غالبًا ما يحتاج المطورون إلى تمرير معلومات من نشاط إلى آخر. يتم ذلك باستخدام دوال putExtra() وgetIntent().
مثال على إرسال البيانات:
javaIntent intent = new Intent(MainActivity.this, SecondActivity.class);
intent.putExtra("username", "Ahmed");
startActivity(intent);
مثال على استقبال البيانات في النشاط الهدف:
javaIntent intent = getIntent();
String username = intent.getStringExtra("username");
يمكن تمرير أنواع بيانات مختلفة مثل int, String, boolean, Parcelable, Serializable وغيرها.
استخدام Bundle لتمرير مجموعة من البيانات
في حال الحاجة إلى تمرير أكثر من متغير، يمكن استخدام كائن من نوع Bundle.
javaBundle bundle = new Bundle();
bundle.putString("name", "Sara");
bundle.putInt("age", 28);
Intent intent = new Intent(MainActivity.this, ProfileActivity.class);
intent.putExtras(bundle);
startActivity(intent);
وفي النشاط المستقبل:
javaBundle bundle = getIntent().getExtras();
if (bundle != null) {
String name = bundle.getString("name");
int age = bundle.getInt("age");
}
استلام نتائج من نشاط آخر باستخدام startActivityForResult
في بعض الحالات، تحتاج الشاشة الحالية إلى نتيجة من الشاشة التي تم الانتقال إليها. لهذا الغرض، تُستخدم الدالة startActivityForResult() والتي تم استبدالها في الإصدارات الحديثة بـ registerForActivityResult().
باستخدام الأسلوب القديم:
javaIntent intent = new Intent(MainActivity.this, SecondActivity.class);
startActivityForResult(intent, 1);
ثم استقبال النتيجة في:
java@Override
protected void onActivityResult(int requestCode, int resultCode, Intent data) {
super.onActivityResult(requestCode, resultCode, data);
if (requestCode == 1 && resultCode == RESULT_OK) {
String result = data.getStringExtra("resultKey");
}
}
باستخدام الأسلوب الحديث:
javaActivityResultLauncher launcher = registerForActivityResult(
new ActivityResultContracts.StartActivityForResult(),
result -> {
if (result.getResultCode() == Activity.RESULT_OK) {
Intent data = result.getData();
String returnedData = data.getStringExtra("resultKey");
}
}
);
Intent intent = new Intent(MainActivity.this, SecondActivity.class);
launcher.launch(intent);
التنقل بين الأنشطة مع خيارات خاصة
يمكن تخصيص عملية التنقل بين الأنشطة بإضافة مؤثرات انتقالية أو إعدادات خاصة مثل:
1. مؤثرات انتقال:
javaoverridePendingTransition(android.R.anim.fade_in, android.R.anim.fade_out);
2. إغلاق النشاط الحالي بعد التنقل:
javastartActivity(intent); finish();
3. تقييد العودة للنشاط السابق:
يُستخدم finish() لمنع المستخدم من العودة إلى النشاط السابق باستخدام زر الرجوع.
إرسال البيانات إلى تطبيقات خارجية باستخدام Implicit Intents
أحيانًا يُراد فتح كاميرا، أو إرسال بريد إلكتروني، أو مشاركة محتوى عبر تطبيق خارجي.
مثال: فتح الكاميرا
javaIntent intent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
startActivity(intent);
مثال: مشاركة نص
javaIntent intent = new Intent(Intent.ACTION_SEND);
intent.setType("text/plain");
intent.putExtra(Intent.EXTRA_TEXT, "مرحبًا بك في مواضيع");
startActivity(Intent.createChooser(intent, "اختر تطبيقًا"));
مقارنة بين Explicit و Implicit Intents
| المقارنة | Explicit Intent | Implicit Intent |
|---|---|---|
| الوجهة | معرفة مسبقًا (داخل التطبيق) | غير محددة (قد تكون تطبيق خارجي) |
| الاستخدام الشائع | التنقل بين الأنشطة | التفاعل مع وظائف النظام أو تطبيقات أخرى |
| الحاجة للتصريح | لا، إذا كان النشاط داخليًا | نعم، يحتاج لفحص Intent Filters |
| الأمان | أكثر أمانًا | أقل أمانًا (قد تتدخل تطبيقات أخرى) |
التعامل مع Intent Filters
للسماح للنظام باكتشاف نشاط ما عند استخدام Implicit Intent، يجب تعريف Intent Filters في AndroidManifest.xml.
xml<activity android:name=".WebActivity">
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<data android:scheme="https" android:host="www.moadee3.com" />
intent-filter>
activity>
دورة حياة النشاط عند التنقل باستخدام Intents
عند استخدام startActivity(), يتم تنفيذ دورة حياة كاملة للنشاط الهدف. النشاط الجديد يمر بالمراحل التالية:
-
onCreate()
-
onStart()
-
onResume()
بينما يمر النشاط الحالي بـ:
-
onPause()
-
onStop()
إذا تم استخدام finish(), يمر النشاط الحالي بـ onDestroy() أيضًا.
من الضروري معرفة هذه المراحل من أجل إدارة الموارد بشكل فعّال وتجنب تسرب الذاكرة.
حالات استخدام عملية للتنقل بين الأنشطة
1. شاشة تسجيل دخول إلى الشاشة الرئيسية
بعد التحقق من بيانات الاعتماد، يمكن التنقل إلى الشاشة الرئيسية.
javaIntent intent = new Intent(LoginActivity.this, HomeActivity.class);
intent.putExtra("userId", user.getId());
startActivity(intent);
finish(); // لمنع العودة إلى شاشة الدخول
2. شاشة إعدادات من الشاشة الرئيسية
javaIntent intent = new Intent(HomeActivity.this, SettingsActivity.class);
startActivity(intent);
الاستخدام الأمثل للـ Intents في التطبيقات الكبيرة
في التطبيقات المعقدة، يمكن أن يؤدي الاعتماد المباشر على Intent إلى تكرار غير مرغوب فيه في الكود. يُنصح بتغليف عمليات التنقل داخل طبقات خاصة بالتوجيه (Navigation Layer)، أو باستخدام أدوات حديثة مثل Navigation Component في مكتبة Jetpack، ما يوفر تحكمًا أكثر تنظيمًا.
الخلاصة
تُعد Intents في أندرويد من الركائز الأساسية لبناء تطبيقات متعددة الشاشات ومرنة في التعامل مع وظائف النظام والمكونات الخارجية. يسمح هذا النظام المفتوح بتصميم تدفقات تنقل متقدمة، وإرسال البيانات بسلاسة، وتنفيذ وظائف عبر التطبيقات. ومع تعقيد التطبيقات الحديثة، تزداد أهمية الاستخدام المنظم والمنهجي للـ Intents مع مراعاة دورة حياة الأنشطة، وكفاءة الأداء، وتجربة المستخدم.
المراجع:

