پشتیبانی از زبان‌ها و فرهنگ‌های مختلف

برنامه‌ها شامل منابعی هستند که می‌توانند مختص فرهنگ خاصی باشند. برای مثال، برنامه می‌تواند شامل رشته‌های مختص فرهنگ باشد که به زبان منطقه فعلی ترجمه شده‌اند.

بهتر است منابع مختص فرهنگ را از بقیه برنامه جدا نگه دارید. Android منابع مختص زبان و فرهنگ را براساس تنظیمات منطقه سیستم حل‌وفصل می‌کند. بااستفاده از فهرست راهنمای منابع در پروژه Android خود می‌توانید از زبان‌های مختلف پشتیبانی کنید.

می‌توانید منابعی را مشخص کنید که متناسب با فرهنگ افرادی باشد که از برنامه‌تان استفاده می‌کنند. می‌توانید هر نوع منبعی را که برای زبان و فرهنگ کاربرانتان مناسب است ارائه دهید. برای مثال، نماگرفت‌های زیر برنامه‌ای را نشان می‌دهد که منابع رشته‌ای و ترسیم‌شدنی را در en_US پیش‌فرض دستگاه و es_ES اسپانیایی نمایش می‌دهد.

برنامه بسته به منطقه زبانی فعلی، نوشتار و نماد متفاوتی را نشان می‌دهد

شکل ۱. برنامه بسته به منطقه فعلی از منابع مختلفی استفاده می‌کند.

وقتی پروژه‌ای را بااستفاده از ابزارهای کیت توسعه نرم‌افزار Android ایجاد می‌کنید، این ابزارها دایرکتوری res/ را در سطح بالای پروژه تولید می‌کنند. در این فهرست راهنمای res/، زیرفهرست‌های راهنمایی برای انواع مختلف منابع وجود دارد. همچنین چند فایل پیش‌فرض وجود دارد، مثل فایل res/values/strings.xml که مقادیر رشته‌ای شما را نگه می‌دارد.

پشتیبانی از زبان‌های مختلف فراتر از استفاده از منابع خاص منطقه است. برخی‌از کاربران زبانی را انتخاب می‌کنند که از نویسه‌های راست‌به‌چپ (RTL) استفاده می‌کند، مثل عربی یا عبری، برای زبان واسط کاربرشان. کاربران دیگری که زبان واسط کاربر خود را روی زبانی تنظیم کرده‌اند که از نوشتار چپ‌به‌راست استفاده می‌کند، مثل انگلیسی، ممکن است محتوا را به زبانی مشاهده یا تولید کنند که از نوشتار راست‌به‌چپ استفاده می‌کند. برای پشتیبانی از هر دو نوع کاربر، برنامه شما باید کارهای زیر را انجام دهد:

  • از چیدمان میانای کاربر راست‌به‌چپ برای زبان‌های راست‌به‌چپ استفاده کنید.
  • جهت داده‌های نوشتاری را که در پیام‌های قالب‌بندی‌شده نمایش داده می‌شود شناسایی و اعلام کنید. معمولاً می‌توانید روشی را فراخوانی کنید، همان‌طور که در این راهنما توضیح داده شده است، که جهت داده‌های نوشتاری را برای شما تعیین می‌کند.

ایجاد دایرکتوری‌های محلی و فایل‌های منبع

برای افزودن پشتیبانی از زبان‌های بیشتر، دایرکتوری‌های بیشتری در res/ ایجاد کنید. نام هر دایرکتوری باید از قالب زیر پیروی کند:

<resource type>-b+<language code>[+<country code>]

برای مثال، values-b+es/ حاوی منابع رشته‌ای برای مناطق زبانی با کد زبان es است. به‌طور مشابه، mipmap-b+es+ES/ حاوی نمادهایی برای زبان‌های محلی با کد زبان es و کد کشور ES است.

Android منابع مناسب را براساس تنظیمات منطقه زبانی دستگاه در زمان اجرا بار می‌کند. برای اطلاعات بیشتر، به ارائه منابع جایگزین مراجعه کنید.

پس‌از اینکه تصمیم گرفتید از کدام زبان‌ها پشتیبانی کنید، زیرفهرست‌های راهنما و فایل‌های منبع را ایجاد کنید. برای مثال:

MyProject/
    res/
       values/
           strings.xml
       values-b+es/
           strings.xml
       mipmap/
           country_flag.png
       mipmap-b+es+ES/
           country_flag.png

فایل‌های منبع را با منابع بومی‌سازی‌شده پر کنید. در زیر نمونه‌هایی از فایل‌های منبع تصویر و رشته بومی‌سازی‌شده آورده شده است:

رشته‌های انگلیسی (منطقه زبانی پیش‌فرض) در /values/strings.xml:

<resources>
    <string name="hello_world">Hello World!</string>
</resources>

رشته‌های اسپانیایی (منطقه زبانی es) در /values-b+es/strings.xml:

<resources>
    <string name="hello_world">¡Hola Mundo!</string>
</resources>

نماد پرچم ایالات متحده (منطقه زبانی پیش‌فرض) در /mipmap/country_flag.png:

نماد پرچم ایالات متحده

شکل ۲. نماد مورداستفاده برای منطقه زبانی پیش‌فرض (en_US).

نماد پرچم اسپانیا (منطقه زبانی es_ES) در /mipmap-b+es+ES/country_flag.png:

نماد پرچم
اسپانیا

شکل ۳. نماد استفاده‌شده برای منطقه زبانی es_ES.

توجه: می‌توانید از توصیف‌گرهای پیکربندی، مثل توصیف‌گر زبان، در هر نوع منبعی استفاده کنید. برای مثال، ممکن است بخواهید نسخه‌های بومی‌سازی‌شده‌ای از نقشه بیتی قابل‌رسم خود ارائه دهید. برای اطلاعات بیشتر، بومی‌سازی برنامه را ببینید.

استفاده از منابع در برنامه

بااستفاده از ویژگی name هر منبع، به منابع موجود در کد منبع و سایر فایل‌های XML ارجاع دهید: R.<resource type>.<resource name>. روش‌های مختلفی وجود دارد که منبع را به این روش می‌پذیرند، همان‌طور که در مثال‌های زیر نشان داده شده است:

کاتلین

// Get a string resource
val hello = resources.getString(R.string.hello_world)

// Or supply a string resource to a method that requires a string
TextView(this).apply {
    setText(R.string.hello_world)
}

جاوا

// Get a string resource
String hello = getResources().getString(R.string.hello_world);

// Or supply a string resource to a method that requires a string
TextView textView = new TextView(this);
textView.setText(R.string.hello_world);

در فایل‌های XML، هرگاه مشخصه XML مقدار سازگاری را بپذیرد، می‌توانید با نحو @<resource type>/<resource name> به منبعی ارجاع دهید، همان‌طور که در مثال زیر نشان داده شده است:

<ImageView
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:src="@mipmap/country_flag" />

توجه: برای اطمینان از اینکه تنظیمات زبان کاربر به‌درستی اولویت‌بندی شده است، زبان‌هایی را که برنامه‌تان پشتیبانی می‌کند بااستفاده از ویژگی resConfigs مشخص کنید. برای اطلاعات بیشتر، به مشخص کردن زبان‌هایی که برنامه‌تان پشتیبانی می‌کند مراجعه کنید.

قالب‌بندی نوشتار در پیام‌ها

یکی از رایج‌ترین کارها در برنامه، قالب‌بندی نوشتار است. پیام‌های بومی‌سازی‌شده با درج نوشتار و داده‌های عددی در جایگاه‌های مناسب قالب‌بندی می‌شوند. متأسفانه، هنگام کار با واسط کاربر راست‌به‌چپ یا داده‌های راست‌به‌چپ، قالب‌بندی ساده می‌تواند خروجی نوشتاری نادرست یا حتی ناخوانا نمایش دهد.

زبان‌هایی مانند عربی، عبری، فارسی، و اردو از راست به چپ نوشته می‌شوند. بااین‌حال، برخی عناصر، مانند اعداد و نوشتار جاسازی‌شده چپ‌به‌راست، به‌صورت چپ‌به‌راست در نوشتار راست‌به‌چپ نوشته می‌شوند. زبان‌هایی که از نویسه‌های چپ به راست استفاده می‌کنند، ازجمله انگلیسی، نیز دوجهته هستند، زیرا می‌توانند حاوی نویسه‌های راست به چپ جاسازی‌شده باشند که باید به‌صورت راست به چپ نمایش داده شوند.

برنامه‌ها اغلب نمونه‌هایی از این نوع نوشتار جاسازی‌شده در جهت مخالف را تولید می‌کنند، مثلاً با درج داده‌های نوشتاری از یک زبان دلخواه و جهت نوشتار دلخواه در پیام‌های بومی‌سازی‌شده. این ترکیب جهت‌ها اغلب شامل نشانگر واضحی از محل شروع و پایان نوشتار جهت مخالف نیست، بنابراین نوشتار تولیدشده توسط برنامه می‌تواند باعث تجربه کاربری ضعیف شود.

اگرچه مدیریت پیش‌فرض سیستم برای نوشتار دوجهته معمولاً نوشتار را طبق انتظار ارائه می‌کند، اما ممکن است وقتی برنامه‌تان نوشتار را در پیام بومی‌سازی‌شده درج می‌کند، نوشتار به‌درستی ارائه نشود. در نمونه‌های زیر، نوشتار احتمالاً به‌درستی نشان داده نمی‌شود:

  • نوشتار درج‌شده در ابتدای پیام:

    ‫PERSON_NAME درحال تماس با شما است

  • نوشتاری که با عدد شروع می‌شود، مثل نشانی یا شماره تلفن:

    987 654-3210

  • نوشتاری که با علائم نگارشی شروع می‌شود، مثل شماره تلفن:

    ‎+19876543210

  • نوشتاری که با علائم نگارشی تمام می‌شود:

    مطمئنید؟

  • نوشتاری که ازقبل حاوی هر دو جهت است:

    کلمه בננה در زبان عبری به‌معنی موز است.

مثال

فرض کنید برنامه‌ای گاهی اوقات باید پیام «منظورتان %s بود؟» را نمایش دهد و نشانی‌ای در زمان اجرا به‌جای %s درج شود. برنامه از زبان‌های مختلف واسط کاربر پشتیبانی می‌کند، بنابراین پیام از منبعی خاص زبان می‌آید و وقتی دستگاه روی زبان راست‌به‌چپ تنظیم شده باشد، از جهت راست‌به‌چپ استفاده می‌کند. برای مثال، برای واسط کاربر عبری، پیام به‌صورت زیر نشان داده می‌شود:

האם התכוונת ל %s?

اما نشانی پیشنهادی ممکن است از پایگاه داده‌ای باشد که نوشتار به زبان منطقه را ندارد. برای مثال، اگر نشانی مربوط به مکانی در کالیفرنیا باشد، بااستفاده از نوشتار انگلیسی در پایگاه داده نشان داده می‌شود. اگر نشانی «15 Bay Street, Laurel, CA» را بدون ارائه هیچ‌گونه راهنمایی درباره جهت نوشتار در پیام راست‌به‌چپ درج کنید، نتیجه موردانتظار یا صحیح نخواهد بود:

האם התכוונת ל 15 Bay Street, Laurel, CA?

شماره خانه در سمت راست نشانی نشان داده می‌شود، نه در سمت چپ که مدنظر است. این باعث می‌شود شماره خانه بیشتر شبیه کد پستی عجیب‌وغریبی به‌نظر برسد. اگر نوشتار راست‌به‌چپ را در پیامی که از جهت نوشتار چپ‌به‌راست استفاده می‌کند قرار دهید، ممکن است همین مشکل رخ دهد.

توضیح و راه‌حل

مشکل در این مثال به این دلیل رخ می‌دهد که قالب‌بندی نوشتار مشخص نمی‌کند که «۱۵» بخشی از نشانی است، بنابراین سیستم نمی‌تواند تعیین کند که آیا «۱۵» بخشی از نوشتار راست‌به‌چپ است که قبل‌از آن می‌آید یا نوشتار چپ‌به‌راست که بعداز آن می‌آید.

برای حل این مشکل، از روش unicodeWrap() از کلاس BidiFormatter استفاده کنید. این روش جهت رشته را تشخیص می‌دهد و آن را در نویسه‌های قالب‌بندی Unicode که آن جهت را اعلام می‌کنند می‌پیچد.

تکه‌کد زیر نحوه استفاده از unicodeWrap() را نشان می‌دهد:

کاتلین

val mySuggestion = "15 Bay Street, Laurel, CA"
val myBidiFormatter: BidiFormatter = BidiFormatter.getInstance()

// The "did_you_mean" localized string resource includes
// a "%s" placeholder for the suggestion.
String.format(getString(R.string.did_you_mean), myBidiFormatter.unicodeWrap(mySuggestion))

جاوا

String mySuggestion = "15 Bay Street, Laurel, CA";
BidiFormatter myBidiFormatter = BidiFormatter.getInstance();

// The "did_you_mean" localized string resource includes
// a "%s" placeholder for the suggestion.
String.format(getString(R.string.did_you_mean),
        myBidiFormatter.unicodeWrap(mySuggestion));

چون «۱۵» اکنون در داخل نوشتاری ظاهر می‌شود که به‌عنوان «چپ به راست» اعلام شده است، در جایگاه درست نمایش داده می‌شود:

האם התכוונת ל 15 Bay Street, Laurel, CA?

از روش unicodeWrap() برای هر قطعه نوشتاری که در پیام بومی‌سازی‌شده درج می‌کنید استفاده کنید، مگراینکه یکی از موارد زیر اعمال شود:

  • نوشتار درحال درج شدن در رشته‌ای ماشین‌خوانا، مثل URI یا پرسمان SQL، است.
  • می‌دانید که آن بخش از نوشتار ازقبل به‌درستی پیچیده شده است.

توجه: اگر برنامه شما Android 4.3 (سطح میانای برنامه‌سازی کاربردی ۱۸) یا بالاتر را هدف قرار می‌دهد، از نسخه BidiFormatter موجود در چارچوب Android استفاده کنید. درغیراین‌صورت، از نسخه BidiFormatter موجود در «کتابخانه پشتیبانی» استفاده کنید.

قالب‌بندی اعداد

برای تبدیل اعداد به رشته در منطق برنامه‌تان، از رشته‌های قالب استفاده کنید، نه فراخوانی روش:

کاتلین

var myIntAsString = "$myInt"

جاوا

String myIntAsString = String.format("%d", myInt);

این کار شماره‌ها را به‌طور مناسب برای منطقه شما قالب‌بندی می‌کند، که ممکن است شامل استفاده از مجموعه متفاوتی از ارقام باشد.

وقتی از String.format() برای ایجاد پُرسمان SQL در دستگاهی استفاده می‌کنید که روی منطقه‌ای تنظیم شده است که از مجموعه ارقام خودش استفاده می‌کند، مانند فارسی و اکثر مناطق عربی، اگر هرکدام از پارامترهای پُرسمان عدد باشد، مشکلاتی رخ می‌دهد. دلیلش این است که عدد با ارقام منطقه زبانی قالب‌بندی شده است و این ارقام در SQL نامعتبر است.

برای حفظ اعداد با قالب ASCII و معتبر نگه داشتن پُرسمان SQL، باید از نسخه سربارگذاری‌شده String.format() استفاده کنید که شامل یک زبان به‌عنوان پارامتر اول است. از آرگومان محلی Locale.US استفاده کنید.

پشتیبانی از قرینه‌سازی چیدمان

افرادی که از نویسه‌های راست‌به‌چپ استفاده می‌کنند، میانای کاربر راست‌به‌چپ را ترجیح می‌دهند که شامل منوهای راست‌چین، نوشتار راست‌چین، و پیکان‌های روبه‌جلو است که به چپ اشاره می‌کنند.

شکل ۴ تضاد بین نسخه چپ‌به‌راست صفحه‌ای در برنامه «تنظیمات» و همتای راست‌به‌چپ آن را نشان می‌دهد:

ناحیه اعلان در نزدیکی گوشه بالا سمت چپ راست‌چین شده است،
           دکمه منو در نوار برنامه در نزدیکی گوشه بالا سمت راست قرار دارد،
           محتوای بخش اصلی صفحه چپ‌چین شده است و به‌صورت
           چپ به راست نشان داده می‌شود، و دکمه برگشت در نزدیکی گوشه پایین سمت راست قرار دارد و
           به سمت چپ اشاره می‌کند. ناحیه اعلان در نزدیکی گوشه بالا سمت چپ تراز شده است، دکمه منو در نوار برنامه در نزدیکی گوشه بالا سمت راست قرار دارد، محتوا در بخش اصلی صفحه تراز شده است و به‌صورت راست‌به‌چپ نمایش داده می‌شود، و دکمه برگشت در نزدیکی گوشه پایین سمت راست قرار دارد و به سمت راست اشاره می‌کند
شکل ۴. انواع چپ‌به‌راست و راست‌به‌چپ صفحه تنظیمات.

هنگام افزودن پشتیبانی از راست‌به‌چپ به برنامه‌تان، نکات زیر را به‌خاطر داشته باشید:

  • قرینه‌سازی نوشتار راست به چپ فقط در برنامه‌هایی پشتیبانی می‌شود که در دستگاه‌های دارای Android 4.2 (سطح میانای برنامه‌سازی کاربردی ۱۷) یا بالاتر استفاده می‌شوند. برای آشنایی با نحوه پشتیبانی از قرینه‌سازی نوشتار در دستگاه‌های قدیمی‌تر، به ارائه پشتیبانی برای برنامه‌های قدیمی در این راهنما مراجعه کنید.
  • برای آزمایش اینکه آیا برنامه‌تان از جهت نوشتار راست‌به‌چپ پشتیبانی می‌کند یا نه، بااستفاده از گزینه‌های توسعه‌دهندگان آزمایش کنید (همان‌طور که در این راهنما شرح داده شده است) و از افرادی که از خط‌های راست‌به‌چپ استفاده می‌کنند دعوت کنید از برنامه‌تان استفاده کنند.

توجه: برای مشاهده دستورالعمل‌های طراحی بیشتر مربوط به قرینه‌سازی چیدمان، ازجمله فهرستی از عناصری که برای قرینه‌سازی مناسب هستند و نیستند، به دستورالعمل‌های طراحی مواد دوجهتی مراجعه کنید.

برای قرینه‌سازی چیدمان میانای کاربر در برنامه‌تان به‌طوری‌که در زبان‌های راست‌به‌چپ به‌صورت راست‌به‌چپ نشان داده شود، مراحل بخش‌های زیر را تکمیل کنید.

فایل‌های مانیفست و ساخت را اصلاح کنید

فایل build.gradle واحد برنامه و فایل مانیفست برنامه را به‌صورت زیر اصلاح کنید:

build.gradle (Module: app)

شیک

android {
    ...
    defaultConfig {
        targetSdkVersion 17 // Or higher
        ...
    }
}

کاتلین

android {
    ...
    defaultConfig {
        targetSdkVersion(17) // Or higher
        ...
    }
}

AndroidManifest.xml

<manifest ... >
    ...
    <application ...
        android:supportsRtl="true">
    </application>
</manifest>

توجه: اگر برنامه شما Android 4.1.1 (سطح API‏ ۱۶) یا پایین‌تر را هدف قرار دهد، ویژگی android:supportsRtl نادیده گرفته می‌شود، همراه با هر مقدار ویژگی start و end که در فایل‌های چیدمان برنامه شما ظاهر می‌شود. در این حالت، قرینه‌سازی چیدمان راست‌به‌چپ به‌طور خودکار در برنامه‌تان اتفاق نمی‌افتد.

به‌روزرسانی منابع موجود

‫left و right را به‌ترتیب به start و end در فایل‌های منبع چیدمان موجود تبدیل کنید. این کار به چارچوب اجازه می‌دهد عناصر میانای کاربر برنامه‌تان را براساس تنظیمات زبان کاربر تراز کند.

توجه: پیش‌از به‌روزرسانی منابع، با نحوه ارائه پشتیبانی برای برنامه‌های قدیمی، یا برنامه‌هایی که Android نسخه ۴.۱.۱ (سطح میانای برنامه‌سازی کاربردی ۱۶) و پایین‌تر را هدف قرار می‌دهند آشنا شوید.

برای استفاده از قابلیت‌های تراز راست‌به‌چپ چارچوب، مشخصه‌های موجود در فایل‌های چیدمانتان را که در جدول ۱ نشان داده شده است تغییر دهید.

جدول ۱. مشخصه‌هایی که باید استفاده شود وقتی برنامه‌تان از چند جهت نوشتار پشتیبانی می‌کند

مشخصه فقط از چپ‌به‌راست پشتیبانی می‌کند مشخصه پشتیبانی از راست‌به‌چپ و چپ‌به‌راست
android:gravity="left" android:gravity="start"
android:gravity="right" android:gravity="end"
android:layout_gravity="left" android:layout_gravity="start"
android:layout_gravity="right" android:layout_gravity="end"
android:paddingLeft android:paddingStart
android:paddingRight android:paddingEnd
android:drawableLeft android:drawableStart
android:drawableRight android:drawableEnd
android:layout_alignLeft android:layout_alignStart
android:layout_alignRight android:layout_alignEnd
android:layout_marginLeft android:layout_marginStart
android:layout_marginRight android:layout_marginEnd
android:layout_alignParentLeft android:layout_alignParentStart
android:layout_alignParentRight android:layout_alignParentEnd
android:layout_toLeftOf android:layout_toStartOf
android:layout_toRightOf android:layout_toEndOf

جدول ۲ نشان می‌دهد که سیستم چگونه مشخصه‌های تراز میانای کاربری را براساس نسخه SDK هدف، تعریف شدن یا نشدن مشخصه‌های left و right، و تعریف شدن یا نشدن مشخصه‌های start و end مدیریت می‌کند.

جدول ۲. رفتار تراز کردن عنصر میانای کاربر براساس نسخه کیت توسعه نرم‌افزار هدف و مشخصه‌های تعریف‌شده

Android 4.2
(سطح میانای برنامه‌سازی کاربردی ۱۷) یا بالاتر را هدف قرار می‌دهید؟
چپ و راست تعریف شده است؟ شروع و پایان تعریف شده است؟ نتیجه
بله بله بله از start و end استفاده می‌شود، left و right لغو می‌شود
بله بله نه از left و right استفاده شده است
بله نه بله از start و end استفاده شده است
نه بله بله از left و right استفاده می‌شود (start و end نادیده گرفته می‌شوند)
نه بله نه از left و right استفاده شده است
نه نه بله ‫start و end به left و right تبدیل می‌شوند

افزودن منابع مختص جهت و زبان

این مرحله شامل افزودن نسخه‌های خاصی از چیدمان، موارد قابل‌ترسیم، و فایل‌های منبع مقادیر است که حاوی مقادیر سفارشی‌شده برای زبان‌ها و جهت‌های نوشتار مختلف است.

در Android 4.2 (سطح میانای برنامه کاربردی ۱۷) و بالاتر، می‌توانید از توصیف‌گرهای منبع -ldrtl (layout-direction-right-to-left) و -ldltr (layout-direction-left-to-right) استفاده کنید. برای حفظ سازگاری با نسخه‌های قدیمی با منابع موجود، نسخه‌های قدیمی‌تر Android از توصیف‌گرهای زبان منبع برای استنباط جهت صحیح نوشتار استفاده می‌کنند.

فرض کنید می‌خواهید فایل چیدمان خاصی را برای پشتیبانی از خط‌های راست‌به‌چپ، مثل زبان‌های عبری، عربی، و فارسی اضافه کنید. برای انجام این کار، یک دایرکتوری layout-ldrtl/ در دایرکتوری res/ خود اضافه کنید، همان‌طور که در مثال زیر نشان داده شده است:

res/
    layout/
        main.xml This layout file is loaded by default.
    layout-ldrtl/
        main.xml This layout file is loaded for languages using an
                 RTL text direction, including Arabic, Persian, and Hebrew.

اگر می‌خواهید نسخه خاصی از چیدمان را که فقط برای نوشتار عربی طراحی شده است اضافه کنید، ساختار دایرکتوری شما به‌صورت زیر خواهد بود:

res/
    layout/
        main.xml This layout file is loaded by default.
    layout-ar/
        main.xml This layout file is loaded for Arabic text.
    layout-ldrtl/
        main.xml This layout file is loaded only for non-Arabic
                 languages that use an RTL text direction.

توجه: منابع مختص زبان بر منابع مختص جهت چیدمان اولویت دارند و منابع مختص جهت چیدمان بر منابع پیش‌فرض اولویت دارند.

استفاده از ابزاره‌های پشتیبانی‌شده

از Android 4.2 (سطح API‏ ۱۷)، اکثر عناصر میانای کاربر چارچوب به‌طور خودکار از جهت نوشتار راست‌به‌چپ پشتیبانی می‌کنند. بااین‌حال، چندین عنصر چارچوب، مانند ViewPager، از جهت نوشتار راست‌به‌چپ پشتیبانی نمی‌کنند.

ابزارک‌های صفحه اصلی از جهت نوشتار راست به چپ پشتیبانی می‌کنند، به‌شرطی که فایل‌های مانیفست مربوطه آن‌ها شامل تخصیص ویژگی android:supportsRtl="true" باشد.

ارائه پشتیبانی برای برنامه‌های قدیمی

اگر برنامه شما Android 4.1.1 (سطح میانای برنامه‌سازی کاربردی ۱۶) یا پایین‌تر را هدف قرار می‌دهد، علاوه‌بر start و end، ویژگی‌های left و right را نیز اضافه کنید.

برای بررسی اینکه آیا چیدمان شما باید از جهت نوشتار راست به چپ استفاده کند یا نه، از منطق زیر استفاده کنید:

کاتلین

private fun shouldUseLayoutRtl(): Boolean {
    return if (android.os.Build.VERSION.SDK_INT >= android.os.Build.VERSION_CODES.JELLY_BEAN_MR1) {
        View.LAYOUT_DIRECTION_RTL == layoutDirection
    } else {
        false
    }
}

جاوا

private boolean shouldUseLayoutRtl() {
    if (android.os.Build.VERSION.SDK_INT >=
            android.os.Build.VERSION_CODES.JELLY_BEAN_MR1) {
        return View.LAYOUT_DIRECTION_RTL == getLayoutDirection();
    } else {
        return false;
    }
}

توجه: برای جلوگیری از مشکلات سازگاری، از نسخه ۲۳.۰.۱ یا بالاتر ابزارهای ساخت کیت توسعه نرم‌افزار Android استفاده کنید.

آزمایش بااستفاده از گزینه‌های توسعه‌دهندگان

در دستگاه‌های دارای Android نسخه ۴.۴ (سطح میانای برنامه‌سازی کاربردی ۱۹) یا بالاتر، می‌توانید اجباری کردن جهت چیدمان راست‌به‌چپ را در گزینه‌های توسعه‌دهندگان درون دستگاه فعال کنید. این تنظیم به شما امکان می‌دهد نوشتاری را که از خط‌های چپ‌به‌راست استفاده می‌کند (مثل نوشتار انگلیسی) در حالت راست‌به‌چپ ببینید.

به‌روزرسانی منطق برنامه

این بخش جنبه‌های خاصی از منطق برنامه شما را برای به‌روزرسانی هنگام تطبیق برنامه شما برای مدیریت چندین جهت نوشتار توصیف می‌کند.

تغییرات دارایی

برای مدیریت تغییر در هر ویژگی مرتبط با راست‌به‌چپ (مانند جهت چیدمان، پارامترهای چیدمان، حاشیه داخلی، جهت نوشتار، تراز نوشتار، یا موقعیت قابل‌ترسیم)، از فراخوانی برگشتی onRtlPropertiesChanged() استفاده کنید. این فراخوانی برگشتی به شما امکان می‌دهد جهت چیدمان فعلی را دریافت کنید و اشیاء View فعالیت را براساس آن به‌روز کنید.

بازدیدها

اگر ابزاره UI ایجاد می‌کنید که مستقیماً بخشی از سلسله‌مراتب نمای فعالیت نیست، مانند کادر گفتگو یا عنصر UI شبیه به پیام موقت، جهت چیدمان صحیح را بسته به بافت تنظیم کنید. تکه‌کد زیر نحوه تکمیل این فرایند را نشان می‌دهد:

کاتلین

val config: Configuration = context.resources.configuration
view.layoutDirection = config.layoutDirection

جاوا

final Configuration config =
    getContext().getResources().getConfiguration();
view.setLayoutDirection(config.getLayoutDirection());

چند روش از کلاس View به ملاحظات بیشتری نیاز دارد:

onMeasure()
اندازه‌های نما ممکن است بسته به جهت نوشتار متفاوت باشد.
onLayout()
اگر پیاده‌سازی چیدمان خودتان را ایجاد می‌کنید، باید super() را در نسخه onLayout() خودتان فراخوانی کنید و منطق سفارشی‌تان را برای پشتیبانی از نوشتارهای راست‌به‌چپ تطبیق دهید.
onDraw()
اگر درحال پیاده‌سازی نمای سفارشی یا افزودن عملکرد پیشرفته به طرح هستید، باید کدتان را به‌روز کنید تا از نوشتار راست‌به‌چپ پشتیبانی کند. از کد زیر برای تعیین اینکه ابزاره شما در حالت «راست به چپ» است یا نه استفاده کنید:

کاتلین

// On devices running Android 4.1.1 (API level 16) and lower,
// you can call the isLayoutRtl() system method directly.
fun isLayoutRtl(): Boolean = layoutDirection == LAYOUT_DIRECTION_RTL

جاوا

// On devices running Android 4.1.1 (API level 16) and lower,
// you can call the isLayoutRtl() system method directly.
public boolean isLayoutRtl() {
    return (getLayoutDirection() == LAYOUT_DIRECTION_RTL);
}

ترسیم‌شدنی‌ها

اگر ترسیم‌پذیری دارید که باید برای چیدمان راست‌به‌چپ قرینه‌سازی شود، یکی از این مراحل را براساس نسخه Android درحال اجرا در دستگاه تکمیل کنید:

  • در دستگاه‌هایی که از Android 4.3 (میانای برنامه کاربردی سطح ۱۸) و پایین‌تر استفاده می‌کنند، فایل‌های منبع -ldrtl را اضافه و تعریف کنید.
  • در Android نسخه ۴.۴ (سطح میانای برنامه‌سازی کاربردی ۱۹) و بالاتر، از android:autoMirrored="true" هنگام تعریف کردن drawable استفاده کنید، که به سیستم اجازه می‌دهد قرینه‌سازی چیدمان راست‌به‌چپ را برای شما انجام دهد.

    توجه: مشخصه android:autoMirrored فقط برای ترسیم‌پذیرهای ساده‌ای کار می‌کند که قرینه‌سازی دوسویه آن‌ها صرفاً قرینه‌سازی گرافیکی کل ترسیم‌پذیر است. اگر drawable شما شامل چندین عنصر باشد، یا اگر بازتاب drawable شما تفسیر آن را تغییر دهد، می‌توانید قرینه‌سازی را خودتان انجام دهید. هرزمان که ممکن بود، با یک کارشناس دوسویه بررسی کنید تا مشخص شود آیا ترسیم‌شدنی‌های قرینه‌شده شما برای کاربران منطقی است یا نه.

گرانش

اگر کد چیدمان برنامه‌تان از Gravity.LEFT یا Gravity.RIGHT استفاده می‌کند، این مقادیر را به‌ترتیب به Gravity.START و Gravity.END تغییر دهید.

اگر کد Kotlin یا Java دارید که به ویژگی‌های Gravity.LEFT یا Gravity.RIGHT بستگی دارد، می‌توانید آن را با تنظیم absoluteGravity برای مطابقت با layoutDirection با این تغییر سازگار کنید.

برای مثال، اگر از کد زیر استفاده می‌کنید:

کاتلین

when (gravity and Gravity.HORIZONTAL_GRAVITY_MASK) {
    Gravity.LEFT -> {
        // Handle objects that are left-aligned.
    }
    Gravity.RIGHT -> {
        // Handle objects that are right-aligned.
    }
}

جاوا

switch (gravity & Gravity.HORIZONTAL_GRAVITY_MASK) {
    case Gravity.LEFT:
        // Handle objects that are left-aligned.
        break;
    case Gravity.RIGHT:
        // Handle objects that are right-aligned.
        break;
}

آن را به این مورد تغییر دهید:

کاتلین

val absoluteGravity: Int = Gravity.getAbsoluteGravity(gravity, layoutDirection)
when (absoluteGravity and Gravity.HORIZONTAL_GRAVITY_MASK) {
    Gravity.LEFT -> {
        // Handle objects that are left-aligned.
    }
    Gravity.RIGHT -> {
        // Handle objects that are right-aligned.
    }
}

جاوا

final int layoutDirection = getLayoutDirection();
final int absoluteGravity =
        Gravity.getAbsoluteGravity(gravity, layoutDirection);
switch (absoluteGravity & Gravity.HORIZONTAL_GRAVITY_MASK) {
    case Gravity.LEFT:
        // Handle objects that are left-aligned.
        break;
    case Gravity.RIGHT:
        // Handle objects that are right-aligned.
        break;
}

این یعنی می‌توانید کد موجودتان را که مقادیر چپ‌چین و راست‌چین را مدیریت می‌کند حفظ کنید، حتی اگر از start و end برای مقادیر ثقل استفاده می‌کنید.

توجه: هنگام اعمال تنظیمات گرانش، از نسخه سربارگذاری‌شده Gravity.apply() که شامل آرگومان layoutDirection است استفاده کنید.

حاشیه‌ها و فاصله‌گذاری‌ها

برای پشتیبانی از نوشتارهای راست‌به‌چپ در برنامه‌تان، این روال‌های مطلوب مربوط به مقادیر حاشیه و لایه را دنبال کنید:

  • به‌جای مشخصه‌های معادل جهت‌دار leftMargin و rightMargin، از getMarginStart() و getMarginEnd() استفاده کنید.
  • هنگام استفاده از setMargins()، اگر برنامه‌تان نوشتار راست‌به‌چپ را شناسایی کرد، مقادیر آرگومان‌های left و right را جابه‌جا کنید.
  • اگر برنامه‌تان منطق لایه داخلی سفارشی دارد، setPadding() و setPaddingRelative() را لغو کنید.

پشتیبانی از اولویت‌های زبان هر برنامه

در بسیاری از موارد، کاربران چندزبانه زبان سیستم خود را روی یک زبان (مثلاً انگلیسی) تنظیم می‌کنند، اما می‌خواهند زبان‌های دیگری مثل هلندی، چینی، یا هندی را برای برنامه‌های خاصی انتخاب کنند. برای کمک به برنامه‌ها در ارائه تجربه بهتر به این کاربران، Android 13 ویژگی‌های زیر را برای برنامه‌هایی که از چند زبان پشتیبانی می‌کنند معرفی می‌کند:

  • تنظیمات سیستم: مکانی متمرکز که کاربران می‌توانند زبان ترجیحی را برای هر برنامه انتخاب کنند.

    برنامه‌تان باید مشخصه android:localeConfig را در مانیفست خود اعلام کند تا به سیستم اطلاع دهد که از چند زبان پشتیبانی می‌کند. برای کسب اطلاعات بیشتر، دستورالعمل‌های ایجاد فایل منبع و اعلام آن در فایل مانیفست برنامه را ببینید.

  • میاناهای برنامه‌سازی کاربردی اضافی: این میاناهای برنامه‌سازی کاربردی عمومی، مثل روش‌های setApplicationLocales() و getApplicationLocales() در LocaleManager، به برنامه‌ها اجازه می‌دهند در زمان اجرا زبانی متفاوت از زبان سیستم تنظیم کنند.

    برنامه‌هایی که از انتخابگرهای سفارشی زبان درون‌برنامه استفاده می‌کنند می‌توانند از این میاناهای برنامه‌سازی کاربردی استفاده کنند تا تجربه کاربری ثابتی را بدون توجه به جایی که اولویت‌های زبانشان را انتخاب می‌کنند به کاربران ارائه دهند. میاناهای برنامه‌سازی کاربردی عمومی همچنین به شما کمک می‌کنند مقدار کد متن استاندارد را کاهش دهید و از APK جداشده پشتیبانی می‌کنند. همچنین از پشتیبان‌گیری خودکار برای برنامه‌ها برای ذخیره کردن تنظیمات زبان کاربر در سطح برنامه پشتیبانی می‌کنند.

    برای سازگاری با نسخه‌های قدیمی‌تر Android، میاناهای برنامه‌سازی کاربردی معادل نیز در AndroidX دردسترس است. توصیه می‌کنیم از Appcompat 1.6.0-beta01 یا نسخه بالاتر استفاده کنید.

    برای کسب اطلاعات بیشتر، دستورالعمل‌های پیاده‌سازی میاناهای برنامه‌سازی کاربردی جدید را ببینید.

همچنین مراجعه کنید به

منابع بیشتر

برای کسب اطلاعات بیشتر درباره پشتیبانی از دستگاه‌های قدیمی‌تر، منابع زیر را مشاهده کنید:

پست‌های وبلاگ