اگر برنامه شما به یک مؤلفه نمای سفارشی نیاز دارد، باید نما را در دسترس تر کنید. مراحل زیر می تواند دسترسی نمای سفارشی شما را، همانطور که در این صفحه توضیح داده شده است، بهبود بخشد:
- کنترل کلیک های کنترل کننده جهت دار
- پیاده سازی روش های دسترسی به API.
- اشیاء
AccessibilityEvent
مخصوص نمای سفارشی شما را ارسال کنید. -
AccessibilityEvent
وAccessibilityNodeInfo
را برای نمای خود پر کنید.
کنترل کلیک های کنترل کننده جهت دار
در اکثر دستگاهها، کلیک کردن روی یک نما با استفاده از یک کنترلکننده جهت، یک KeyEvent
با KEYCODE_DPAD_CENTER
به نمای فعلی در فوکوس ارسال میکند. همه نماهای استاندارد Android KEYCODE_DPAD_CENTER
به درستی مدیریت می کنند. هنگام ساختن یک کنترل View
سفارشی، مطمئن شوید که این رویداد همان اثر ضربه زدن به نمای روی صفحه لمسی را دارد.
کنترل سفارشی شما باید با رویداد KEYCODE_ENTER
مانند KEYCODE_DPAD_CENTER
رفتار کند. این کار تعامل با صفحه کلید کامل را برای کاربران آسان تر می کند.
پیاده سازی روش های دسترسی به API
رویدادهای دسترسپذیری پیامهایی درباره تعامل کاربران با اجزای رابط بصری برنامه شما هستند. این پیامها توسط سرویسهای دسترسپذیری مدیریت میشوند که از اطلاعات این رویدادها برای تولید بازخورد و درخواستهای تکمیلی استفاده میکنند. متدهای دسترسی بخشی از کلاس های View
و View.AccessibilityDelegate
هستند. روش ها به شرح زیر است:
dispatchPopulateAccessibilityEvent()
onPopulateAccessibilityEvent()
برای این view و سپس متد dispatchPopulateAccessibilityEvent()
برای هر فرزند این view فراخوانی میکند.onInitializeAccessibilityEvent()
TextView
یا Button
ساده ارائه میکند، این روش را نادیده بگیرید و اطلاعات اضافی در مورد نمای خود را تنظیم کنید - مانند نوع فیلد رمز عبور، نوع کادر انتخاب یا حالتهایی که تعامل یا بازخورد کاربر را برای رویداد ارائه میدهند - با استفاده از این روش. . اگر این متد را لغو کردید، اجرای super آن را فراخوانی کنید و فقط ویژگی هایی را تغییر دهید که توسط کلاس super تنظیم نشده اند.onInitializeAccessibilityNodeInfo()
View
پیشفرض دارای یک مجموعه استاندارد از ویژگیهای view است، اما اگر نمای سفارشی شما کنترل تعاملی فراتر از یک TextView
یا Button
ساده ارائه میکند، این روش را لغو کنید و اطلاعات اضافی درباره نمای خود را در شی AccessibilityNodeInfo
که توسط این روش مدیریت میشود، تنظیم کنید.onPopulateAccessibilityEvent()
AccessibilityEvent
را برای نمای شما تنظیم می کند. همچنین اگر نمای فرزند نمای است که یک رویداد دسترسپذیری ایجاد میکند، نامیده میشود.onRequestSendAccessibilityEvent()
AccessibilityEvent
ایجاد کند. این مرحله به نمای والدین امکان میدهد رویداد دسترسپذیری را با اطلاعات اضافی اصلاح کند. این روش را فقط در صورتی اجرا کنید که نمای سفارشی شما بتواند نماهای فرزند داشته باشد و اگر نمای والد بتواند اطلاعات زمینه را برای رویداد دسترسپذیری ارائه دهد که برای سرویسهای دسترسپذیری مفید است.-
sendAccessibilityEvent()
- سیستم زمانی این روش را فراخوانی می کند که کاربر روی یک view اقدام کند. رویداد با یک نوع اقدام کاربر، مانند
TYPE_VIEW_CLICKED
طبقهبندی میشود. به طور کلی، هر زمان که محتوای نمای سفارشی شما تغییر کرد، باید یکAccessibilityEvent
ارسال کنید. -
sendAccessibilityEventUnchecked()
- این روش زمانی استفاده میشود که کد فراخوانی نیاز به کنترل مستقیم بررسی دسترسپذیری در دستگاه دارد (
AccessibilityManager.isEnabled()
). اگر این روش را اجرا می کنید، بدون توجه به تنظیمات سیستم، تماس را طوری انجام دهید که گویی دسترسی فعال است. شما معمولاً برای یک نمای سفارشی نیازی به پیاده سازی این روش ندارید. -
dispatchPopulateAccessibilityEvent()
-
onInitializeAccessibilityEvent()
-
onInitializeAccessibilityNodeInfo()
-
onPopulateAccessibilityEvent()
-
TYPE_VIEW_CLICKED
-
TYPE_VIEW_FOCUSED
-
TYPE_VIEW_HOVER_ENTER
-
TYPE_VIEW_HOVER_EXIT
-
TYPE_VIEW_LONG_CLICKED
-
TYPE_VIEW_SCROLLED
- یک
AccessibilityEvent
مناسب برای عمل کلیک تفسیر شده ایجاد کنید. - خدمات دسترسپذیری را فعال کنید تا عملکرد کلیک سفارشی را برای کاربرانی که قادر به استفاده از صفحه لمسی نیستند، انجام دهند.
برای پشتیبانی از دسترسپذیری، روشهای دسترسپذیری قبلی را مستقیماً در کلاس view سفارشی خود لغو و پیادهسازی کنید.
حداقل، روشهای دسترسی زیر را برای کلاس view سفارشی خود پیادهسازی کنید:
برای اطلاعات بیشتر در مورد اجرای این روشها، بخش مربوط به پر کردن رویدادهای دسترسی را ببینید.
رویدادهای دسترسی را ارسال کنید
بسته به مشخصات نمای سفارشی شما، ممکن است نیاز باشد که اشیاء AccessibilityEvent
در زمانهای مختلف یا برای رویدادهایی که توسط پیادهسازی پیشفرض مدیریت نمیشوند ارسال شود. کلاس View
یک پیاده سازی پیش فرض برای این انواع رویداد ارائه می دهد:
به طور کلی، هر زمان که محتوای نمای سفارشی شما تغییر کرد، باید یک AccessibilityEvent
ارسال کنید. برای مثال، اگر یک نوار لغزنده سفارشی را پیادهسازی میکنید که به کاربر امکان میدهد با فشار دادن کلید پیکان چپ یا راست، یک مقدار عددی را انتخاب کند، نمای سفارشی شما باید هر زمان که مقدار لغزنده تغییر کرد، یک رویداد TYPE_VIEW_TEXT_CHANGED
منتشر کند. نمونه کد زیر استفاده از متد sendAccessibilityEvent()
برای گزارش این رویداد نشان می دهد.
کاتلین
override fun onKeyUp(keyCode: Int, event: KeyEvent): Boolean { return when(keyCode) { KeyEvent.KEYCODE_DPAD_LEFT -> { currentValue-- sendAccessibilityEvent(AccessibilityEvent.TYPE_VIEW_TEXT_CHANGED) true } ... } }
جاوا
@Override public boolean onKeyUp (int keyCode, KeyEvent event) { if (keyCode == KeyEvent.KEYCODE_DPAD_LEFT) { currentValue--; sendAccessibilityEvent(AccessibilityEvent.TYPE_VIEW_TEXT_CHANGED); return true; } ... }
رویدادهای دسترسی را پر کنید
هر AccessibilityEvent
دارای مجموعه ای از ویژگی های مورد نیاز است که وضعیت فعلی نما را توصیف می کند. این ویژگی ها شامل مواردی مانند نام کلاس view، توضیحات محتوا و وضعیت علامت گذاری شده است. ویژگی های خاص مورد نیاز برای هر نوع رویداد در مستندات مرجع AccessibilityEvent
توضیح داده شده است.
پیاده سازی View
مقادیر پیش فرض را برای این ویژگی های مورد نیاز ارائه می دهد. بسیاری از این مقادیر، از جمله نام کلاس و مهر زمانی رویداد، به صورت خودکار ارائه می شوند. اگر در حال ایجاد یک کامپوننت نمای سفارشی هستید، باید اطلاعاتی در مورد محتوا و ویژگی های نما ارائه دهید. این اطلاعات می تواند به سادگی یک برچسب دکمه باشد و می تواند شامل اطلاعات وضعیت اضافی باشد که می خواهید به رویداد اضافه کنید.
از متدهای onPopulateAccessibilityEvent()
و onInitializeAccessibilityEvent()
برای پر کردن یا تغییر اطلاعات در AccessibilityEvent
استفاده کنید. از روش onPopulateAccessibilityEvent()
به طور خاص برای افزودن یا اصلاح محتوای متنی رویداد استفاده کنید، که توسط سرویسهای دسترسپذیری مانند TalkBack به پیامهای شنیداری تبدیل میشود. از متد onInitializeAccessibilityEvent()
برای پر کردن اطلاعات اضافی درباره رویداد، مانند حالت انتخاب view استفاده کنید.
علاوه بر این، متد onInitializeAccessibilityNodeInfo()
را پیاده سازی کنید. سرویسهای دسترسپذیری از اشیاء AccessibilityNodeInfo
پر شده توسط این روش برای بررسی سلسلهمراتب view استفاده میکنند که یک رویداد دسترسی را پس از دریافت آن ایجاد میکند و بازخورد مناسب را برای کاربران ارائه میکند.
مثال کد زیر نشان می دهد که چگونه می توان این سه روش را در نمای خود نادیده گرفت:
کاتلین
override fun onPopulateAccessibilityEvent(event: AccessibilityEvent?) { super.onPopulateAccessibilityEvent(event) // Call the super implementation to populate its text for the // event. Then, add text not present in a super class. // You typically only need to add the text for the custom view. if (text?.isNotEmpty() == true) { event?.text?.add(text) } } override fun onInitializeAccessibilityEvent(event: AccessibilityEvent?) { super.onInitializeAccessibilityEvent(event) // Call the super implementation to let super classes // set appropriate event properties. Then, add the new checked // property that is not supported by a super class. event?.isChecked = isChecked() } override fun onInitializeAccessibilityNodeInfo(info: AccessibilityNodeInfo?) { super.onInitializeAccessibilityNodeInfo(info) // Call the super implementation to let super classes set // appropriate info properties. Then, add the checkable and checked // properties that are not supported by a super class. info?.isCheckable = true info?.isChecked = isChecked() // You typically only need to add the text for the custom view. if (text?.isNotEmpty() == true) { info?.text = text } }
جاوا
@Override public void onPopulateAccessibilityEvent(AccessibilityEvent event) { super.onPopulateAccessibilityEvent(event); // Call the super implementation to populate its text for the // event. Then, add the text not present in a super class. // You typically only need to add the text for the custom view. CharSequence text = getText(); if (!TextUtils.isEmpty(text)) { event.getText().add(text); } } @Override public void onInitializeAccessibilityEvent(AccessibilityEvent event) { super.onInitializeAccessibilityEvent(event); // Call the super implementation to let super classes // set appropriate event properties. Then, add the new checked // property that is not supported by a super class. event.setChecked(isChecked()); } @Override public void onInitializeAccessibilityNodeInfo(AccessibilityNodeInfo info) { super.onInitializeAccessibilityNodeInfo(info); // Call the super implementation to let super classes set // appropriate info properties. Then, add the checkable and checked // properties that are not supported by a super class. info.setCheckable(true); info.setChecked(isChecked()); // You typically only need to add the text for the custom view. CharSequence text = getText(); if (!TextUtils.isEmpty(text)) { info.setText(text); } }
می توانید این متدها را مستقیماً در کلاس view سفارشی خود پیاده سازی کنید.
زمینه دسترسی سفارشی شده را ارائه دهید
سرویسهای دسترسپذیری میتوانند سلسلهمراتب نمای یک مؤلفه رابط کاربری را که یک رویداد دسترسپذیری ایجاد میکند، بررسی کنند. این به خدمات دسترسی امکان می دهد اطلاعات متنی غنی تری را برای کمک به کاربران ارائه دهند.
مواردی وجود دارد که سرویسهای دسترسی نمیتوانند اطلاعات کافی را از سلسله مراتب مشاهده دریافت کنند. یک مثال از این یک کنترل رابط سفارشی است که دارای دو یا چند ناحیه جداگانه قابل کلیک است، مانند یک کنترل تقویم. در این حالت، سرویسها نمیتوانند اطلاعات کافی را دریافت کنند زیرا بخشهای فرعی قابل کلیک بخشی از سلسله مراتب مشاهده نیستند.
![](https://developer.android.com/static/guide/topics/ui/accessibility/calendar.png?hl=fa)
شکل 1. نمای تقویم سفارشی با عناصر روز قابل انتخاب.
در مثال شکل 1، کل تقویم به صورت یک نمای واحد پیادهسازی شده است، بنابراین سرویسهای دسترسپذیری اطلاعات کافی در مورد محتوای نما و انتخاب کاربر در نما دریافت نمیکنند، مگر اینکه توسعهدهنده اطلاعات اضافی ارائه دهد. به عنوان مثال، اگر کاربر روی روزی که دارای برچسب 17 است کلیک کند، چارچوب دسترسپذیری فقط اطلاعات توضیحات را برای کل کنترل تقویم دریافت میکند. در این مورد، سرویس دسترسپذیری TalkBack «تقویم» یا «تقویم آوریل» را اعلام میکند و کاربر نمیداند چه روزی انتخاب شده است.
برای ارائه اطلاعات زمینه کافی برای خدمات دسترسی در شرایطی مانند این، چارچوب راهی برای تعیین سلسله مراتب نمای مجازی ارائه می دهد. سلسله مراتب نمای مجازی راهی برای توسعه دهندگان برنامه است تا سلسله مراتب نمای تکمیلی را برای سرویس های دسترسی ارائه کنند که بیشتر با اطلاعات روی صفحه مطابقت دارد. این رویکرد به خدمات دسترس پذیری اجازه می دهد تا اطلاعات زمینه مفیدتری را به کاربران ارائه دهند.
موقعیت دیگری که در آن ممکن است به یک سلسله مراتب نمای مجازی نیاز باشد، یک رابط کاربری حاوی مجموعه ای از کنترل های View
است که عملکردهای نزدیک به هم دارند، جایی که یک عمل بر روی یک کنترل بر محتویات یک یا چند عنصر تأثیر می گذارد - مانند جمع کننده اعداد با جدا کردن و دکمه های پایین در این مورد، سرویسهای دسترسپذیری نمیتوانند اطلاعات کافی را دریافت کنند، زیرا یک عملکرد روی یک کنترل، محتوا را در کنترل دیگر تغییر میدهد و ممکن است ارتباط آن کنترلها برای سرویس آشکار نباشد.
برای رسیدگی به این وضعیت، کنترلهای مرتبط را با یک نمای شامل گروهبندی کنید و یک سلسلهمراتب نمای مجازی از این کانتینر ارائه کنید تا اطلاعات و رفتار ارائهشده توسط کنترلها را به وضوح نشان دهد.
برای ارائه یک سلسله مراتب نمای مجازی برای یک view، متد getAccessibilityNodeProvider()
را در نمای سفارشی یا گروه view خود لغو کنید و پیاده سازی AccessibilityNodeProvider
را برگردانید. شما می توانید یک سلسله مراتب نمای مجازی را با استفاده از کتابخانه پشتیبانی با متد ViewCompat.getAccessibilityNodeProvider()
پیاده سازی کنید و یک پیاده سازی با AccessibilityNodeProviderCompat
ارائه دهید.
برای ساده کردن کار ارائه اطلاعات به سرویسهای دسترسپذیری و مدیریت تمرکز دسترسپذیری، میتوانید در عوض ExploreByTouchHelper
پیادهسازی کنید. این یک AccessibilityNodeProviderCompat
را ارائه میکند و میتواند با فراخوانی setAccessibilityDelegate
به عنوان AccessibilityDelegateCompat
یک View پیوست شود. برای مثال، ExploreByTouchHelperActivity
را ببینید. ExploreByTouchHelper
همچنین توسط ویجت های چارچوب مانند CalendarView
از طریق نمای فرزند SimpleMonthView
استفاده می شود.
رویدادهای لمسی سفارشی را مدیریت کنید
کنترلهای نمای سفارشی ممکن است به رفتار رویداد لمسی غیر استاندارد نیاز داشته باشند، همانطور که در مثالهای زیر نشان داده شده است.
اقدامات مبتنی بر کلیک را تعریف کنید
اگر ویجت شما از رابط OnClickListener
یا OnLongClickListener
استفاده می کند، سیستم عملکردهای ACTION_CLICK
و ACTION_LONG_CLICK
را برای شما انجام می دهد. اگر برنامه شما از ویجت سفارشیسازیشدهتری استفاده میکند که به رابط OnTouchListener
متکی است، کنترلکنندههای سفارشی را برای اقدامات دسترسی مبتنی بر کلیک تعریف کنید. برای انجام این کار، همانطور که در قطعه کد زیر نشان داده شده است، متد replaceAccessibilityAction()
را برای هر عمل فراخوانی کنید:
کاتلین
override fun onCreate(savedInstanceState: Bundle?) { ... // Assumes that the widget is designed to select text when tapped, and selects // all text when tapped and held. In its strings.xml file, this app sets // "select" to "Select" and "select_all" to "Select all". ViewCompat.replaceAccessibilityAction( binding.textSelectWidget, ACTION_CLICK, getString(R.string.select) ) { view, commandArguments -> selectText() } ViewCompat.replaceAccessibilityAction( binding.textSelectWidget, ACTION_LONG_CLICK, getString(R.string.select_all) ) { view, commandArguments -> selectAllText() } }
جاوا
@Override protected void onCreate(Bundle savedInstanceState) { ... // Assumes that the widget is designed to select text when tapped, and select // all text when tapped and held. In its strings.xml file, this app sets // "select" to "Select" and "select_all" to "Select all". ViewCompat.replaceAccessibilityAction( binding.textSelectWidget, ACTION_CLICK, getString(R.string.select), (view, commandArguments) -> selectText()); ViewCompat.replaceAccessibilityAction( binding.textSelectWidget, ACTION_LONG_CLICK, getString(R.string.select_all), (view, commandArguments) -> selectAllText()); }
رویدادهای کلیک سفارشی ایجاد کنید
یک کنترل سفارشی میتواند از روش شنونده onTouchEvent(MotionEvent)
برای شناسایی رویدادهای ACTION_DOWN
و ACTION_UP
و راهاندازی رویداد کلیک ویژه استفاده کند. برای حفظ سازگاری با سرویسهای دسترسی، کدی که این رویداد کلیک سفارشی را مدیریت میکند باید موارد زیر را انجام دهد:
برای رسیدگی موثر به این الزامات، کد شما باید متد performClick()
را لغو کند، که باید اجرای فوق العاده این متد را فراخوانی کند و سپس هر اقدامی را که توسط رویداد کلیک مورد نیاز است را اجرا کند. وقتی عمل کلیک سفارشی شناسایی شد، آن کد باید متد performClick()
شما را فراخوانی کند. مثال کد زیر این الگو را نشان می دهد.
کاتلین
class CustomTouchView(context: Context) : View(context) { var downTouch = false override fun onTouchEvent(event: MotionEvent): Boolean { super.onTouchEvent(event) // Listening for the down and up touch events. return when (event.action) { MotionEvent.ACTION_DOWN -> { downTouch = true true } MotionEvent.ACTION_UP -> if (downTouch) { downTouch = false performClick() // Call this method to handle the response and // enable accessibility services to // perform this action for a user who can't // tap the touchscreen. true } else { false } else -> false // Return false for other touch events. } } override fun performClick(): Boolean { // Calls the super implementation, which generates an AccessibilityEvent // and calls the onClick() listener on the view, if any. super.performClick() // Handle the action for the custom click here. return true } }
جاوا
class CustomTouchView extends View { public CustomTouchView(Context context) { super(context); } boolean downTouch = false; @Override public boolean onTouchEvent(MotionEvent event) { super.onTouchEvent(event); // Listening for the down and up touch events switch (event.getAction()) { case MotionEvent.ACTION_DOWN: downTouch = true; return true; case MotionEvent.ACTION_UP: if (downTouch) { downTouch = false; performClick(); // Call this method to handle the response and // enable accessibility services to // perform this action for a user who can't // tap the touchscreen. return true; } } return false; // Return false for other touch events. } @Override public boolean performClick() { // Calls the super implementation, which generates an AccessibilityEvent // and calls the onClick() listener on the view, if any. super.performClick(); // Handle the action for the custom click here. return true; } }
الگوی قبلی کمک میکند تا اطمینان حاصل شود که رویداد کلیک سفارشی با سرویسهای دسترسپذیری سازگار است، با استفاده از روش performClick()
برای ایجاد یک رویداد دسترسپذیری و ارائه یک نقطه ورودی برای سرویسهای دسترسپذیری که از طرف کاربری که رویداد کلیک سفارشی را انجام میدهد، عمل کنند.