<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0">
    <channel>
        <title>نوشته های حمیدرضا خواجه</title>
        <link>https://virgool.io/feed/@hamidkhajeh65</link>
        <description>توسعه دهنده نرم افزار</description>
        <language>fa</language>
        <pubDate>2026-06-17 07:15:02</pubDate>
        <image>
            <url>https://files.virgool.io/upload/users/26567/avatar/6ekbKq.png?height=120&amp;width=120</url>
            <title>حمیدرضا خواجه</title>
            <link>https://virgool.io/@hamidkhajeh65</link>
        </image>

                    <item>
                <title>معرفی اولیه ViewPager 2</title>
                <link>https://virgool.io/MobileLab/%D9%85%D8%B9%D8%B1%D9%81%DB%8C-%D8%A7%D9%88%D9%84%DB%8C%D9%87-viewpager-2-tmlir4fuopkd</link>
                <description>نمیدونم اطلاع دارید یا نه اما گوگل 7 فوریه (18 بهمن) نسخه جدید ViewPager رو با نام ViewPager 2 معرفی کرد و خب خالی از لطف نیست اگر بعضی از تغییرات این نسخه با نسخه قبلی رو با هم بررسی کنیممعرفی اولیه ViewPager 2 ویژگی های جدید- قابلیت راست به چپ کردن لایه ها- ساپورت کردن از Orientation عمودی- PageChangeListener بهترچه چیزایی تغییر کرده؟- PagerAdapter جایگزین شده با RecyclerView.Adapter (فوق العاده نیست؟!!!)- FragmentStatePagerAdapter هم جایگزین شده با FragmentStateAdapterنکته مهمViewPager 2 در واقع برای Android X معرفی شده و برای استفاده از اون باید پروژه تون رو با کامپونتت های Android X سازگار کنید؛ حالا چجوری باید به Android X مهاجرت کرد؟(کلیک کنید)نصببرای استفاده از ViewPager 2 باید ابتدا کتابخونه اون رو به فایل Build.gradle ماژول اپ وارد dependencies {
 implementation &quot;androidx.viewpager2:viewpager2:1.0.0-alpha01&quot;
}پروژه رو Sync کنید تا کتابخونه دانلود بشه(نیاز به VPN)پیاده سازی- ViewPager 2 رو به لایه xml صفحه ای که میخواید داخلش از اون استفاده کنید، اضافه کنید&lt;androidx.viewpager2.widget.ViewPager2
 android:id=&quot;@+id/viewPager2&quot;
 android:layout_width=&quot;match_parent&quot;
 android:layout_height=&quot;match_parent&quot;/&gt;- همونطوری که در بالا گفتم حالا میتونید برای اداپتر ViewPager 2 از RecyclerView استفاده کنید که یه چیز فوق العاده لذت بخشه! برای این کار باید اول لایوت هر آیتم ViewPager 2 رو بسازیم(مثلا نام لایه ما item_page.xml هستش) :&lt;?xml version=&quot;1.0&quot; encoding=&quot;utf-8&quot;?&gt;
&lt;RelativeLayout xmlns:android=&quot;http://schemas.android.com/apk/res/android&quot;
 xmlns:tools=&quot;http://schemas.android.com/tools&quot;
 android:id=&quot;@+id/container&quot;
 android:layout_width=&quot;match_parent&quot;
 android:layout_height=&quot;match_parent&quot;&gt;

 &lt;androidx.appcompat.widget.AppCompatTextView
 android:id=&quot;@+id/tvTitle&quot;
 android:textColor=&quot;@android:color/white&quot;
 android:layout_width=&quot;wrap_content&quot;
 android:layout_centerInParent=&quot;true&quot;
 tools:text= &quot;item&quot;
 android:textSize=&quot;32sp&quot;
 android:layout_height=&quot;wrap_content&quot; /&gt;

&lt;/RelativeLayout&gt;- حالا ما نیاز داریم یک آداپتر برای ویو پیجرمون بسازیم (دقیقا مثل RecyclerView)؛ کلاس آداپترمون ViewPagerAdapter.kt:class ViewPagerAdapter : RecyclerView.Adapter&lt;PagerVH&gt;() {

 privateval colors = intArrayOf(
 android.R.color.black,
 android.R.color.holo_red_light,
 android.R.color.holo_blue_dark,
 android.R.color.holo_purple
 )

 override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): PagerVH =
 PagerVH(LayoutInflater.from(parent.context).inflate(R.layout.item_page, parent, false))

 override fun getItemCount(): Int = colors.size

 override fun onBindViewHolder(holder: PagerVH, position: Int) = holder.itemView.run {
 tvTitle.text = &quot;item $position&quot;
 container.setBackgroundResource(colors[position])
 }
}

class PagerVH(itemView: View) : RecyclerView.ViewHolder(itemView)- حالا در مرحله آخر کافیه آداپترمون رو روی ViewPager ــی که در لایوت صفحه اصلیمون اضافه کردیم ست بکنیم.class MainActivity : AppCompatActivity() {

 override fun onCreate(savedInstanceState: Bundle?) {
 super.onCreate(savedInstanceState)
 setContentView(R.layout.activity_main) viewPager2.adapter = ViewPagerAdapter()
 }
}و در نهایت خروجی کار به این صورت خواهد بود:نتیجه کاراسکرول عمودیحالا میرسیم به قسمت جدید و کاربردی اسکرول عمودی در ViewPagerviewPager2.orientation = ViewPager2.ORIENTATION_VERTICALنتیجه به این شکل خواهد بود:نتیجه اسکرول عمودیاستفاده از FragmentStateAdapterشما همچنین میتونید فرگمنت هارو با روش قدیمی ViewPager هم بسازید؛ برای این کار باید از FragmentStateAdapter استفاده کنیم:- ابتدا فرگمنت رو میسازیم:class PagerFragment : Fragment() {

 override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
 return inflater.inflate(R.layout.item_page, container, false)
 }

 override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
 arguments?.let {
 container.setBackgroundResource(it.getInt(&quot;color&quot;))
 tvTitle.text = &quot;Item ${it.getInt(&quot;position&quot;)}&quot;
 }
 }
}- حالا باید یک آداپتر برای مدیریت فرگمنت (ها) مون بسازیم: class ViewPagerFragmentStateAdapter(fm: FragmentManager) : FragmentStateAdapter(fm){

    privateval colors = intArrayOf(
        android.R.color.black,
        android.R.color.holo_red_light,
        android.R.color.holo_blue_dark,
        android.R.color.holo_purple
    )

    override fun getItem(position: Int): Fragment = PagerFragment().apply {
        arguments = bundleOf(
            &quot;color&quot; to colors[position],
            &quot;position&quot; to position
        )
    }

    override fun getItemCount(): Int = colors.size
}- و در مرحله آخر باید آداپترمون رو روی ViewPager ست کنیم:viewPager2.adapter = ViewPagerFragmentStateAdapter(supportFragmentManager)متد ChangeCallback خیلی آساندر ViewPager نسخه قبل ما با استفاده از متد ChangeListener کار های مثل تغییرات Page یا Event های Scroll شدن رو مدیریت می کردیم این کار مشکلاتی داشت مثلا ما مجبور بودیم همه متد های ScrollStateChanged، dScrolled و Selected رو پیاده سازی می کردیم فارغ از اینکه با کدومشون کار داریم!! مثل زیر:oldViewPager.addChangeListener(object:ViewPager.ChangeListener{
 override fun ScrollStateChanged(state: Int) {
 // useless
 }

 override fun Scrolled(position: Int, positionOffset: Float, positionOffsetPixels: Int) {
 // useless too
 }

 override fun Selected(position: Int) {
 // useful
 }
})خبر خوب اینه که این روزا رفتن و دیگه نیازی به این کار نیست :) ما حالا با استفاده از ViewPager 2 و با متد ChangeCallback که یک abstract class هستش و البته شامل متد های non-abstract هست.یعنی چی؟ یعنی اینکه ما فقط متدی رو پیاده سازی میکنیم که نیاز داریم:viewPager2.registerChangeCallback(object : ViewPager2.ChangeCallback() {
 override fun Selected(position: Int) {
 super.Selected(position)
 // No boilerplate, only useful
 }
})هشدارکتابخونه ViewPager 2 هنوز در نسخه alpha(غیر stable) هستش؛ بعضی از ویژگی های نسخه قبلی در نسخه جدید به درستی کار نمیکنن یا ناقص هستند و خب بزودی و در نسخه Stable احتمالا این مشکلات برطرف میشن؛ خود داکیومنت گوگل این موارد رو معرفی کرده:- ClipToPadding- No implementation for integrating with TabLayout- no offscreen limit control- (no pageWidth setter (forced 100%/100%اطلاعات بیشتر در اینجامنبع</description>
                <category>حمیدرضا خواجه</category>
                <author>حمیدرضا خواجه</author>
                <pubDate>Thu, 28 Feb 2019 14:37:05 +0330</pubDate>
            </item>
                    <item>
                <title>پیاده سازی Data Binding در اندروید</title>
                <link>https://virgool.io/@hamidkhajeh65/%D9%BE%DB%8C%D8%A7%D8%AF%D9%87-%D8%B3%D8%A7%D8%B2%DB%8C-data-binding-%D8%AF%D8%B1-%D8%A7%D9%86%D8%AF%D8%B1%D9%88%DB%8C%D8%AF-xjfjo3xvmvn3</link>
                <description>مدیریت کد و معماری اون در برنامه نویسی یکی از مهمترین موضوعاتیه که هر توسعه دهنده با اون روبرو هست و خب برنامه نویسان اندروید هم از این قاعده مستثنا نیستن؛ Data Binding یکی از موارد مهمی هستش که اگر به اون مسلط بشید میتونید ارتباط ViewModel(داده هاتون) رو با View به بهترین شکل ممکن و با کمترین خط کد برقرار کنید.Data Binding In Androidدر قسمت قبلی از سری مقالاتم در مورد اهمیت استفاده از معماری و همینطور اهمیت کد نویسی تمیز صحبت کردم؛ اگر برنامه نویس اندروید باشید میدونید که یک برنامه ساده از تعداد زیادی View ساخته میشه؛ برای مثال TextView که متن رو شامل میشه یک View هستش یا همینطور ImageView که شامل عکس های پروژه میشه یا... همونطوری که میدونید برای ساخت ظاهر برنامه در اندروید از زبان xml استفاده میشه، در واقع ما المنت های رابط کاربری مون رو در xml میسازیم(مثل همون مثالای بالا) و سپس ویو هایی که ساختیم رو در سمت Java معرفی میکنیم تا بتونیم باهاش منطق برنامه رو بسازیم.خب این یک فرایند ساده ساخت رابط کاربری توی اندروید بود، اما چرا باید از Data Binding استفاده کنیم؟بصورت سنتی با متد findViewById ما هر بار میاییم و یک View میسازیم و بعد از اون میاییم Data رو بر روی این View ست میکنیم(یا حالا هرکاری که بخوایم با اون View انجام میدیم)؛ اما این کار همونطوری که مطلع هستید خیلی وقت گیر و زمان بر هستش؛ Data Binding اومده تا این فرایند رو کوتاه تر کنه تا هم حوصله ما برنامه نویسای اندروید کمتر سر بره و هم خوانایی کد بهتر میشه؛ به این صورت که میتونیم Data Model مون رو بصورت مستقیم به لایه xml  پاس بدیم و دیگه نیازی به معرفی ویو در Java و ست کردن مقدار اونجا نیست؛ یعنی شما با حذف کردن حدودی ست کردن دیتا روی View در جاوا، دیتا رو مستقیما به رابط کاربری توی xml میفرستید و از اونجا داده مستقیما روی View شما ست میشه! یعنی شما عملا دارید میانبر میزنید! به همین راحتی!خب دیگه توضیحاتمون زیاد شد، بهتره بریم توی کار ببینیم چجوریه؛ برای درک بهتر من یک مینی پروژه خیلی ساده رو پیاده سازی میکنم تا بخوبی با مطالب آشنا بشید.و اما منطق برنامه: برنامه ای که میخوایم پیاده سازی کنیم دارای دو صفحه هست، در صفحه اول  که LoginActivity نام داره، چهار مقدار name, Last Name, gender, Job رو از کاربر دریافت میکنیم و به محض دریافت کردن اطلاعات اونارو پاس میدیم به صفحه دوم که ProfileActivity اسمش هست و این صفحه هم دریافتی رو با استفاده از Data Binding روی View هامون ست میکنه.1- آغاز کار: بعد از ساختن دو تا صفحه مورد نیازمون، میریم سراغ کانفیگ پروژه(کلیک کنید)مهمترین قسمت صفحه Build.gradle ما در واقع این دستور هستش:با دستور dataBinding و Enable کردن اون در واقع پروژه شما تنظیمات مربوط به Data Binding رو دانلود و نصب میکنه.2-حالا بریم سراغ ساخت کلاس دیتا مدل Person(کلیک کنید)بعد از ساختن دیتا مدل و با دانش به اینکه دوتا صفحه(اکتیویتی Profile و Login) رو ساختید میریم سراغ کامل کردن اون قسمت ها؛ اول از همه صفحه لاگین توی نرم افزار اجرا میشه که لایه های xml صفحه activity_login به این شکل میشن(کلیک کنید)؛ در واقع تو این صفحه کاربر اطلاعات خودش اعم از اسم، نام خانوادگی، شغل و جنسیت خودش رو انتخاب میکنه، بعد از کلیک روی دکمه Login به صفحه Profile میره تا اطلاعات نهایی خودش رو ببینه؛ این هم کد های کلاس LoginActivity (کلیک کنید)3-حالا میرسیم به قسمت جالب ماجرا :)خب قسمت مهم اینه که اگر قراره از Data Binding استفاده کنید ساختار لایه xml صفحه تون باید همچین ساختاری داشته باشه:ساختار لایه در زمان استفاده از Data Bindingصفحه تون باید حتما با layout شروع بشه، و بعد از اون data باشه. data در واقع Data Binding مارو یه جورایی کانفیگ میکنه، چجوری؟ ما به عنوان مقدار type به اون آدرس کلاس person رو میدیم(com.hrkhajeh.databindingsample.Person) و تو قسمت name هم میگیم آقا در صفحه ای که الان درش هستیم(لایوت activity_profile) با اسم person، به همون Data Model اصلی که به این صفحه پاس داده میشه(از طریق Data Binding) دسترسی پیدا کن و اونو شناسایی کن.پیاده سازی Data Binding در xml صفحه profileحالا نوبت میرسه به ربط دادن هر کدوم از متغییر هایی که هنگام ساخت کلاس person ساختیم به ویو هامون(اینجا TextView)؛ با این تیکه کد  &quot;{android:text=&quot;@{person.personName میگیم آقا متغییر personName دیتا مدل Person هرچی که بود، بیا روی این TextView ستش بکن! یعنی اگر ما در صفحه لاگین قسمت اسم رو با Hamid پر کردیم، اون مقدار رو روی personName یک نمونه از Person ست میکنیم و اونو اینجوری به TextView مون پاس میدیم! کد های تکمیلی xml صفحه activity_profile اینجا(کلیک کنید) نکته مهم: حتما بعد از تکمیل کردن صفحه activity_profile پروژه رو یک بار ReBuild کنید تا کلاس های مخصوص Data Binding مثل ActivityProfileBinding و متد Binding در سمت جاوا از این صفحه ساخته شوند.4-بعد از اینکه لایه مون ساخته شد باید تنظیمات صفحه پروفایل رو انجام بدیم؛ روال کار اینجوریه که اول مقادیری که از صفحه لاگین به صفحه پروفایل فرستاده شده(با intent)رو دریافت میکنیم، و سپس اون هارو توی یک نمونه از کلاس person میریزیم(مثلا اسمی که وارد شده رو توی متغییر personName کلاس person میریزیم و باقی موارد نیز به همین منوال)، سپس با استفاده از کد زیر ابتدا لایه xml اکتیویتی پروفایل رو به متد bind کننده مون میدیم، سپس همون person ــی که داریم رو با متد binding و setPerson میدیم به لایه xml(که در نتیجه اون هر مقداری که توی person ست شده میره و داخل View های xml ریخته میشه)کد های کامل صفحه پروفایل و پیاده سازی Data Binding در ProfileActivity(کلیک کنید)پیاده سازی Data Binding تبریک میگم ! شما موفق شدید در صفحه ProfileActivity بدون حتی یک بار فراخوانی View ها در جاوا، تمامی مقادیرتون رو روی View هاتون ست کنید... نمای کلی از پروژه رو در زیر میبینید:صفحه لاگینصفحه پروفایلهمچنین کد های کامل این پروژه رو میتونید توی GitHub مشاهده کنید. https://github.com/hamidrezakhajeh/DataBindingSample </description>
                <category>حمیدرضا خواجه</category>
                <author>حمیدرضا خواجه</author>
                <pubDate>Mon, 18 Feb 2019 00:27:31 +0330</pubDate>
            </item>
                    <item>
                <title>فواید استفاده از معماری در برنامه نویسی</title>
                <link>https://virgool.io/MobileLab/1-czpa8jbuke4a</link>
                <description>فک کنم این اواخر زیاد اسم معماری های مختلف در طراحی اپلیکیشن ها رو شنیدید و خب الان با توجه به بالا رفتن اهمیت کار های تیمی، نگهداری بهتر از کد ها و همچنین توسعه نرم افزار، معماری ها ارزش خودشونو بیشتر بهمون نشون میدن، بهتره با من همراه باشید تا با هم بررسی کنیم که چرا باید از معماری در توسعه اپلیکیشن هامون استفاده کنیم.دو معماری معروف MVC و MVP که احتمالا از اون ها شنیدید!اما معماری در توسعه و ساخت نرم افزار چی هست؟ خب دوست عزیزمون ویکی پدیا بهمون کمک میکنه:&quot;معماری نرم‌افزار یعنی ساختار و سازمان یک سیستم نرم‌افزاری که به منظور پشتیبانی از عملیات مشخص، بر روی سازماندهی اجزاء متمرکز می‌باشد. در واقع اجزاء را در حوزه‌های مرتبط به هم گروه بندی می‌کند. دیگر حوزه‌های مرتبط به هم، بر روی تبادل و تعامل با این حوزه متمرکز می‌شوند.&quot;خب بزارید راحت تر بهتون بگم؛ معماری نرم افزار یعنی اینکه ما با رعایت یک سری استاندارد ها و قواعد، جوری کد بنویسیم که بشه پروژه رو به قسمت های مختلف، مستقل و بزرگ تقسیم بندی کرد؛ در آخر با مرتبط کردن و ارتباط این قسمت ها با هم، نرم افزارمون ساخته میشه! پس بصورت خلاصه معماری در برنامه نویسی یعنی تقسیم بندی پروژه و کد ها به قسمت های بزرگ و مشخص!اما خب چرا از معماری در برنامه نویسی استفاده میکنیم؟ببینید پروژه های نرم افزاری روز به روز دارن بزرگتر میشن و خب این بزرگ شدن گروه ها یا شرکت های نرم افزاری رو مجاب کرده که پروژه هاشون رو بصورت گروهی اداره کنن، اهمیت کار گروهی روز به روز داره مهم تر میشه و در نهایت اون نگهداری از کد ها هم مهم تر؛ استفاده از معماری به نرم افزار و سیستم شما ساختار میده و خوانایی کد رو بالاتر میبره، میتونه لایه های مختلف نرم افزارتون رو از هم جدا بکنه و هرکدوم از اونا رو مستقل از یکدیگر کنه؛ با این کار شما میتونید یه نرم افزاری بسازید که همه چیزش تفکیک شده است یعنی لایه View(نمایش) شما از لایه منطق و مدل هاتون جدا بشه و خب این خوانایی کد رو فوق العاده بالاتر میبره و نگهداری از کد ها رو خیلی بهتر میکنه.اگر بخوام رو راست تر بگم درسته که میشه بدون معماری خاصی نرم افزار های زیادی رو ساخت، اما مطمئن باشید نمیتونید اونارو خوب مدیریت کنید و طبیعتا برای بروزرسانی نرم افزار یا... به مشکل میخورید، چرا؟ چون اون نرم افزار ها ساختار خاصی ندارند اگر بخوام بهتر بگم ما توی اون ها گم هستیم!!!فرض کنید یه نرم افزاری رو ساختید که معماری خاصی نداره و اونو میدید به همکارتون که گسترشش بده، خب اگر دیدید فردا همکارتون باهاتون صمیمی نیست زیاد تعجب نکنید! چون سورس کدی که از شما به اون رسیده خیلی در هم ور هم بوده و خب خوندن و فهمیدن همچین سورس کد نرم افزاری خیلی خیلی وقت گیر و اعصاب خورد کن هست در ضمن احتمال بوجود اومدن باگ رو هم بیشتر میکنه، ولی تصور کنید نرم افزار شما کاملا لایه بندی شده باشه، منطق ها در پکیجی جدا، ویو ها و مدل ها هم در پکیج های جدا و بعد با استفاده از یه سری ارتباط این کامپوننت ها به هم وصل بشن خیلی خیلی خوانایی کد رو بالاتر میبره و نرم افزار رو برای توسعه، بسیار سریع تر، بهینه تر و بهتر میکنه!یه مثال جالب: فرض کنید دارید یک اپلیکیشن اندروید رو توسعه میدید، خب همونطوری مطلع هستید دستگاه های اندرویدی در سایز های مختلف وجود دارن(موبایل، فبلت، تبلت و...) و شما میخواید برای هرکدوم از این ها UI یا رابط کاربری خاص خودشونو بسازید! مثلا میخواید داخل تبلت  دکمه ای بزرگ باشه و در داخل موبایل همون دکمه مثلا کوچک تر باشه! با استفاده از معماری شما لایه منطق هاتونو از لایه ویو(نمایش) جدا کردید، یک منطق نوشتید و حالا میخواید در دو صفحه اون منطق رو پیاده سازی کنید! میبینید که چقدر جالب میتونید یک منطق خاص رو به چندین و چند ویو یا صفحه در اندروید وصل کنید. خلاصه اینکه حتما حتما سعی کنید معماری های نرم افزاری رو خوب یاد بگیرید و بسته به نیازتون از اون ها در نرم افزار هاتون استفاده کنید تا یک سیستم استاندارد با قابلیت نگهداری و توسعه بسیار عالی داشته باشید.از معماری های مهم نرم افزاری میشه به موارد زیر اشاره کرد:MVC: Model, View, ControllerMVP: Model, View, PresenterMVVM: Model, View, ViewModelAnd...</description>
                <category>حمیدرضا خواجه</category>
                <author>حمیدرضا خواجه</author>
                <pubDate>Sun, 13 Jan 2019 23:04:31 +0330</pubDate>
            </item>
            </channel>
</rss>