1. مقدمة
تساعد المكونات المادية (MDC) المطورين على تنفيذ التصميم المتعدد الأبعاد. يضم مركز MDC، الذي أنشأه فريق من المهندسين ومصممي تجربة المستخدم في Google، عشرات من مكونات واجهة المستخدم الجميلة والعملية، وهو متاح لأجهزة Android وiOS والويب وFlutter.material.io/develop |
ما هو التصميم المتعدد الأبعاد والمكوّنات المادية لنظام Android؟
التصميم المتعدد الأبعاد هو نظام لتصميم منتجات رقمية جريئة وجميلة. من خلال توحيد الأسلوب والعلامات التجارية والتفاعل والحركة في ظل مجموعة متسقة من المبادئ والمكونات، يمكن لفرق المنتجات تحقيق أكبر إمكانات التصميم.
بالنسبة إلى تطبيقات Android، يدمج Material Components for Android (MDC Android) التصميم والهندسة مع مكتبة من المكونات لتحقيق اتساق في تطبيقك. ومع تطور نظام Material Design، يتم تحديث هذه المكونات لضمان تنفيذ وحدات بكسل متناسقة والالتزام بمعايير تطوير الواجهة الأمامية في Google. يتوفّر MDC أيضًا للويب وiOS وFlutter.
في هذا الدرس التطبيقي، ستُنشئ صفحة تسجيل دخول باستخدام العديد من مكونات MDC Android.
ما الذي ستنشئه
هذا الدرس التطبيقي هو الأول من بين 4 دروس تطبيقية حول الترميز سترشدك خلال إنشاء تطبيق باسم Shrine، وهو تطبيق للتجارة الإلكترونية على Android يبيع الملابس والسلع المنزلية. سيوضح لك هذا الدليل كيفية تخصيص المكوّنات لتعكس أي علامة تجارية أو نمط باستخدام MDC Android.
في هذا الدرس التطبيقي حول الترميز، ستنشئ صفحة تسجيل دخول إلى Shrine تحتوي على:
- حقلان نصيان، أحدهما لإدخال اسم مستخدم والآخر لإدخال كلمة مرور
- زران، أحدهما لـ "إلغاء" وواحدة لـ "التالي"
- اسم التطبيق (Shrine)
- صورة لشعار الضريح
مكونات MDC Android في هذا الدرس التطبيقي حول الترميز
- حقل نصي
- زرّ
المتطلبات
- معرفة أساسية بتطوير تطبيقات Android
- استوديو Android (يمكنك تنزيله من هنا إذا لم يكن متوفّرًا لديك)
- محاكي أو جهاز Android (متاح من خلال "استوديو Android")
- نموذج الرمز (انظر الخطوة التالية)
ما هو تقييمك لمستوى خبرتك في إنشاء تطبيقات Android؟
2. إعداد بيئة التطوير
بدء استخدام "استوديو Android"
عند فتح تطبيق Android Studio، من المفترض أن تظهر نافذة بعنوان "مرحبًا بك في Android Studio". ومع ذلك، إذا كانت هذه هي المرة الأولى التي تشغِّل فيها "استوديو Android"، يمكنك اتّباع خطوات معالج إعداد "استوديو Android" باستخدام القيم التلقائية. قد تستغرق هذه الخطوة عدة دقائق لتنزيل الملفات الضرورية وتثبيتها، لذا يمكنك ترك هذه الخطوة قيد التشغيل في الخلفية أثناء تنفيذ القسم التالي.
تنزيل تطبيق "الدرس التطبيقي حول الترميز" للمبتدئين
يتوفّر تطبيق إجراء التفعيل ضمن دليل material-components-android-codelabs-101-starter/kotlin
.
...أو استنساخها من GitHub
لاستنساخ هذا الدرس التطبيقي حول الترميز من GitHub، شغِّل الأوامر التالية:
git clone https://github.com/material-components/material-components-android-codelabs cd material-components-android-codelabs/ git checkout 101-starter
تحميل رمز إجراء التفعيل في "استوديو Android"
- بعد انتهاء معالج الإعداد وظهور نافذة مرحبًا بك في استوديو Android، انقر على فتح مشروع استوديو Android حالي. انتقل إلى الدليل الذي قمت فيه بتثبيت نموذج التعليمات البرمجية، وحدد kotlin ->. ضريح (أو ابحث عن كلمة ضريح في جهاز الكمبيوتر) لفتح مشروع الشحن.
- انتظِر قليلاً حتى ينشئ "استوديو Android" المشروع ويزامنه، كما هو موضّح من خلال مؤشرات النشاط أسفل نافذة "استوديو Android".
- في هذه المرحلة، قد يعرض "استوديو Android" بعض أخطاء الإصدار بسبب عدم توفُّر حزمة تطوير البرامج (SDK) لنظام التشغيل Android أو أدوات الإصدار، مثل الأداة الموضّحة أدناه. اتّبِع التعليمات الواردة في "استوديو Android" لتثبيت هذه العناصر أو تحديثها ومزامنة مشروعك.
إضافة تبعيات المشروع
يجب أن يعتمد المشروع على مكتبة دعم MDC Android. يُفترض أن يحتوي نموذج التعليمات البرمجية الذي نزّلته بالفعل على هذه التبعية، ولكن من الجيد القيام بالخطوات التالية للتأكد.
- انتقِل إلى ملف
build.gradle
في وحدةapp
وتأكَّد من أنّ الكتلةdependencies
تتضمن اعتمادًا على MDC Android:
api 'com.google.android.material:material:1.1.0-alpha06'
- (اختياري) إذا لزم الأمر، عدِّل ملف
build.gradle
لإضافة الاعتماديات التالية ومزامنة المشروع.
dependencies { api 'com.google.android.material:material:1.1.0-alpha06' implementation 'androidx.legacy:legacy-support-v4:1.0.0' implementation 'com.android.volley:volley:1.1.1' implementation 'com.google.code.gson:gson:2.8.5' implementation "org.jetbrains.kotlin:kotlin-stdlib-jdk7:1.3.21" testImplementation 'junit:junit:4.12' androidTestImplementation 'androidx.test:core:1.1.0' androidTestImplementation 'androidx.test.ext:junit:1.1.0' androidTestImplementation 'androidx.test:runner:1.2.0-alpha05' androidTestImplementation 'androidx.test.espresso:espresso-core:3.2.0-alpha05' }
تشغيل تطبيق إجراء التفعيل
|
اكتمال عملية النقل بنجاح يجب أن يكون رمز إجراء التفعيل لصفحة تسجيل الدخول إلى Shrine قيد التشغيل في المحاكي. من المفترض أن يظهر لك الاسم "Shrine" وشعار الضريح أسفله مباشرة.
لنلقِ نظرة على الرمز. لقد قدّمنا إطار عمل بسيطًا للتنقّل في Fragment
في نموذج الرمز البرمجي لعرض الأجزاء والتنقل بينها.
افتح MainActivity.kt
في دليل shrine -> app -> src -> main -> java -> com.google.codelabs.mdc.kotlin.shrine
. يجب أن يحتوي على ما يلي:
MainActivity.kt
package com.google.codelabs.mdc.kotlin.shrine
import android.os.Bundle
import androidx.appcompat.app.AppCompatActivity
import androidx.fragment.app.Fragment
class MainActivity : AppCompatActivity(), NavigationHost {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.shr_main_activity)
if (savedInstanceState == null) {
supportFragmentManager
.beginTransaction()
.add(R.id.container, LoginFragment())
.commit()
}
}
override fun navigateTo(fragment: Fragment, addToBackstack: Boolean) {
val transaction = supportFragmentManager
.beginTransaction()
.replace(R.id.container, fragment)
if (addToBackstack) {
transaction.addToBackStack(null)
}
transaction.commit()
}
}
يعرض هذا النشاط ملف تنسيق R.layout.shr_main_activity
، المحدّد في shr_main_activity.xml
.
في onCreate(),
، تبدأ MainActivity.kt
معاملة Fragment
لعرض LoginFragment
. في هذا الدرس التطبيقي حول الترميز، سنعمل على تعديل LoginFragment
. ينفِّذ النشاط أيضًا طريقة navigateTo(Fragment)
، محدّدة في NavigationHost
، ما يسمح لأي جزء بالانتقال إلى جزء مختلف.
Command + النقر (أو Control + Click) shr_main_activity
في ملف النشاط لفتح ملف التنسيق، أو انتقِل إلى ملف التنسيق في app -> res -> layout -> shr_main_activity.xml
.
shr_main_activity.xml
<?xml version="1.0" encoding="utf-8"?>
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:id="@+id/container"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity"/>
نلاحظ هنا رمز <FrameLayout>
بسيطًا يعمل كحاوية لأي أجزاء يعرضها النشاط.
بعد ذلك، سنفتح LoginFragment.kt
.
LoginFragment.kt
package com.google.codelabs.mdc.kotlin.shrine
import android.os.Bundle
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import androidx.fragment.app.Fragment
class LoginFragment : Fragment() {
override fun onCreateView(
inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
// Inflate the layout for this fragment
val view = inflater.inflate(R.layout.shr_login_fragment, container, false)
return view
}
}
يضخم LoginFragment
ملف التنسيق shr_login_fragment
ويعرضه في onCreateView()
.
والآن، لنلقِ نظرة على ملف تنسيق shr_login_fragment.xml
لمعرفة الشكل الذي تظهر به صفحة تسجيل الدخول.
shr_login_fragment.xml
<?xml version="1.0" encoding="utf-8"?>
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:background="@color/loginPageBackgroundColor"
tools:context=".LoginFragment">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:clipChildren="false"
android:clipToPadding="false"
android:orientation="vertical"
android:padding="24dp"
android:paddingTop="16dp">
<ImageView
android:layout_width="64dp"
android:layout_height="64dp"
android:layout_gravity="center_horizontal"
android:layout_marginTop="48dp"
android:layout_marginBottom="16dp"
app:srcCompat="@drawable/shr_logo" />
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:layout_marginBottom="132dp"
android:text="@string/shr_app_name"
android:textAllCaps="true"
android:textSize="16sp" />
</LinearLayout>
</ScrollView>
هنا، يمكننا رؤية <LinearLayout>
مع <ImageView>
في أعلى الصفحة، يمثل شعار الضريح.
بعد ذلك، ستظهر علامة <TextView>
تمثّل تصنيف الضريح تحت الشعار. نص هذا التصنيف هو مورد سلسلة باسم @string/shr_app_name
. إذا استخدمت Command + النقر (أو Control + Click) على اسم مورد السلسلة، أو فتحت app -> res -> values -> strings.xml
، يمكنك الاطّلاع على ملف strings.xml
الذي يتم فيه تحديد موارد السلسلة. عند إضافة المزيد من موارد السلسلة في المستقبل، سيتم تحديدها هنا. يجب أن يتضمّن كل مورد في هذا الملف بادئة shr_
للإشارة إلى أنّه جزء من تطبيق Shrine.
بعد أن تعرّفت على رمز إجراء التفعيل، لنبدأ بتنفيذ المكوّن الأول.
3- إضافة حقول نصية
للبدء، سنضيف حقلين نصيين إلى صفحة تسجيل الدخول ليتمكن الأشخاص من إدخال اسم المستخدم وكلمة المرور. سنستخدم مكوّن حقل النص بتنسيق MDC، الذي يتضمّن وظائف مضمَّنة تعرض تصنيفًا عائمًا ورسائل خطأ.
إضافة XML
في shr_login_fragment.xml
، أضِف عنصرَي TextInputLayout
مع العنصر TextInputEditText
الفرعي داخل <LinearLayout>
، أسفل "SHRINE" التصنيف <TextView>
:
shr_login_fragment.xml
<com.google.android.material.textfield.TextInputLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="4dp"
android:hint="@string/shr_hint_username">
<com.google.android.material.textfield.TextInputEditText
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</com.google.android.material.textfield.TextInputLayout>
<com.google.android.material.textfield.TextInputLayout
android:id="@+id/password_text_input"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="4dp"
android:hint="@string/shr_hint_password">
<com.google.android.material.textfield.TextInputEditText
android:id="@+id/password_edit_text"
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</com.google.android.material.textfield.TextInputLayout>
يمثّل المقتطف أعلاه حقلَين نصيَين، ويتألف كل منهما من عنصر <TextInputLayout>
وعنصر <TextInputEditText>
ثانوي. يتم تحديد نص التلميح لكل حقل نصي في السمة android:hint
.
لقد أدرجنا موردَي سلسلة جديدَين لحقل النص: @string/shr_hint_username
و@string/shr_hint_password
. افتح strings.xml
للاطّلاع على موارد السلسلة هذه.
strings.xml
<string name="shr_hint_username">Username</string>
<string name="shr_hint_password">Password</string>
إضافة التحقُّق من صحة الإدخال
توفّر مكوّنات TextInputLayout
وظيفة مدمجة للملاحظات على الأخطاء.
لعرض الملاحظات والآراء عن الأخطاء، يُرجى إجراء التغييرات التالية على "shr_login_fragment.xml
":
- اضبط السمة
app:errorEnabled
علىtrue
في عنصر كلمة المرورTextInputLayout
. سيؤدي ذلك إلى إضافة مساحة متروكة إضافية لرسالة الخطأ أسفل حقل النص. - ضبط السمة
android:inputType
على "textPassword
" في عنصر كلمة المرورTextInputEditText
. سيؤدي هذا الإجراء إلى إخفاء نص الإدخال في حقل كلمة المرور.
من خلال هذه التغييرات، من المفترض أن تظهر الحقول النصية في shr_login_fragment.xml
على النحو التالي:
shr_login_fragment.xml
<com.google.android.material.textfield.TextInputLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="4dp"
android:hint="@string/shr_hint_username">
<com.google.android.material.textfield.TextInputEditText
android:layout_width="match_parent"
android:layout_height="wrap_content" />
</com.google.android.material.textfield.TextInputLayout>
<com.google.android.material.textfield.TextInputLayout
android:id="@+id/password_text_input"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="4dp"
android:hint="@string/shr_hint_password"
app:errorEnabled="true">
<com.google.android.material.textfield.TextInputEditText
android:id="@+id/password_edit_text"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:inputType="textPassword" />
</com.google.android.material.textfield.TextInputLayout>
الآن حاول تشغيل التطبيق. من المفترض أن تظهر صفحة تحتوي على حقلين نصيين لـ "اسم المستخدم" و"كلمة المرور"!
اطلع على الرسوم المتحركة للتصنيف العائم:
4. إضافة أزرار
بعد ذلك، سنضيف زرَّين إلى صفحة تسجيل الدخول: "إلغاء" و"التالي". سنستخدم مكون زر MDC، الذي يأتي مع تأثير تمويج الحبر الرائع المدمج في التصميم المتعدد الأبعاد.
إضافة XML
في shr_login_fragment.xml
، أضِف <RelativeLayout>
إلى <LinearLayout>
، أسفل عناصر TextInputLayout
. بعد ذلك، أضِف عنصرَي <MaterialButton>
إلى <RelativeLayout>
.
من المفترض أن يظهر ملف XML الناتج على النحو التالي:
shr_login_fragment.xml
<RelativeLayout
android:layout_width="match_parent"
android:layout_height="wrap_content">
<com.google.android.material.button.MaterialButton
android:id="@+id/next_button"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignParentEnd="true"
android:layout_alignParentRight="true"
android:text="@string/shr_button_next" />
<com.google.android.material.button.MaterialButton
android:id="@+id/cancel_button"
style="@style/Widget.MaterialComponents.Button.TextButton"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginEnd="12dp"
android:layout_marginRight="12dp"
android:layout_toStartOf="@id/next_button"
android:layout_toLeftOf="@id/next_button"
android:text="@string/shr_button_cancel" />
</RelativeLayout>
هذا كل شيء! عند تشغيل التطبيق، ستظهر موجة الحبر عند النقر على كل زر.
5- الانتقال إلى الجزء التالي
وأخيرًا، سنضيف بعض رموز Kotlin إلى LoginFragment.kt
للربط بالعنوان "NEXT". للانتقال إلى جزء آخر.
لنضيف طريقة isPasswordValid
منطقية خاصة في LoginFragment.kt
ضمن onCreateView()
، مع تحديد ما إذا كانت كلمة المرور صالحة أم لا. لأغراض هذا العرض التوضيحي، سنتأكد فقط من أن كلمة المرور تتكون من 8 أحرف على الأقل:
LoginFragment.kt
private fun isPasswordValid(text: Editable?): Boolean {
return text != null && text.length >= 8
}
بعد ذلك، إضافة مستمع نقر إلى "التالي" الذي يحدّد الخطأ ويمحوه استنادًا إلى طريقة isPasswordValid()
التي أنشأناها للتو. في onCreateView()
، يجب وضع أداة معالجة النقرات هذه بين خط المنتفخ وخط return view
.
لنضيف الآن أداة معالجة أساسية رئيسية إلى كلمة المرور TextInputEditText
للاستماع إلى الأحداث الرئيسية التي من شأنها محو الخطأ. يجب أن يستخدم هذا المستمع أيضًا isPasswordValid()
للتحقّق مما إذا كانت كلمة المرور صالحة أم لا. يمكنك إضافة هذا النص مباشرةً تحت أداة معالجة الأحداث في "onCreateView()
".
يُفترض أن تبدو طريقة onCreateView() الآن على النحو التالي:
LoginFragment.kt
override fun onCreateView(
inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
// Inflate the layout for this fragment.
val view = inflater.inflate(R.layout.shr_login_fragment, container, false)
// Set an error if the password is less than 8 characters.
view.next_button.setOnClickListener({
if (!isPasswordValid(password_edit_text.text!!)) {
password_text_input.error = getString(R.string.shr_error_password)
} else {
// Clear the error.
password_text_input.error = null
}
})
// Clear the error once more than 8 characters are typed.
view.password_edit_text.setOnKeyListener({ _, _, _ ->
if (isPasswordValid(password_edit_text.text!!)) {
// Clear the error.
password_text_input.error = null
}
false
})
return view
}
}
الآن، يمكننا الانتقال إلى جزء آخر. في onCreateView()
، يمكنك تعديل OnClickListener
للانتقال إلى جزء آخر عند إتمام عملية التحقّق من الأخطاء بنجاح. من المفترض أن يظهر رمز clickListener
الآن على النحو التالي:
LoginFragment.kt
// Set an error if the password is less than 8 characters.
view.next_button.setOnClickListener({
if (!isPasswordValid(password_edit_text.text!!)) {
password_text_input.error = getString(R.string.shr_error_password)
} else {
// Clear the error.
password_text_input.error = null
// Navigate to the next Fragment.
(activity as NavigationHost).navigateTo(ProductGridFragment(), false)
}
})
لقد أضفنا السطر (
activity
as
NavigationHost).navigateTo(ProductGridFragment(),
false
)
إلى الحالة else
الخاصة بأداة معالجة النقرات. يستدعي هذا السطر الطريقة navigateTo()
من MainActivity
للانتقال إلى جزء جديد وهو ProductGridFragment
. هذه صفحة فارغة حاليًا يمكنك العمل عليها في MDC-102.
الآن، أنشئ التطبيق. استمر واضغط على زر التالي.
أحسنت. ستكون هذه الشاشة نقطة الانطلاق في الدروس التطبيقية التالية حول الترميز التي ستعمل عليها في MDC-102.
6- تم
باستخدام ترميز XML الأساسي وحوالي 30 سطرًا من Kotlin، ساعدتك مكتبة Material Components لمكتبة Android في إنشاء صفحة تسجيل دخول جميلة تتوافق مع إرشادات Material Design، وكذلك مظهر وتتصرف بشكل متسق عبر جميع الأجهزة.
الخطوات التالية
يعد الحقل النصي والزر مكونين أساسيين في مكتبة MDC لنظام التشغيل Android، ولكن هناك المزيد! يمكنك الاطّلاع على باقي المكوّنات في تطبيق MDC Android. يمكنك بدلاً من ذلك الانتقال إلى MDC 102: بنية التصميم المتعدد الأبعاد والتنسيق للتعرّف على شريط التطبيق العلوي وعرض البطاقة وتنسيق الشبكة. شكرًا لتجربة Material Components. نأمل أن تكون قد استفدت من هذا الدرس التطبيقي حول الترميز.