AccessibilityDelegateCompat.java revision 0574ca37da4619afe4e26753f5a1b4de314b6565
1/* 2 * Copyright (C) 2011 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17package android.support.v4.view; 18 19import android.os.Build; 20import android.support.v4.view.accessibility.AccessibilityNodeInfoCompat; 21import android.view.View; 22import android.view.ViewGroup; 23import android.view.accessibility.AccessibilityEvent; 24 25/** 26 * Helper for accessing {@link View.AccessibilityDelegate} introduced after 27 * API level 4 in a backwards compatible fashion. 28 */ 29public class AccessibilityDelegateCompat { 30 31 static interface AccessibilityDelegateImpl { 32 public Object newAccessiblityDelegateDefaultImpl(); 33 public Object newAccessiblityDelegateBridge(AccessibilityDelegateCompat listener); 34 public boolean dispatchPopulateAccessibilityEvent(Object delegate, View host, 35 AccessibilityEvent event); 36 public void onInitializeAccessibilityEvent(Object delegate, View host, 37 AccessibilityEvent event); 38 public void onInitializeAccessibilityNodeInfo(Object delegate, View host, 39 AccessibilityNodeInfoCompat info); 40 public void onPopulateAccessibilityEvent(Object delegate, View host, 41 AccessibilityEvent event); 42 public boolean onRequestSendAccessibilityEvent(Object delegate, ViewGroup host, View child, 43 AccessibilityEvent event); 44 public void sendAccessibilityEvent(Object delegate, View host, int eventType); 45 public void sendAccessibilityEventUnchecked(Object delegate, View host, 46 AccessibilityEvent event); 47 } 48 49 static class AccessibilityDelegateStubImpl implements AccessibilityDelegateImpl { 50 public Object newAccessiblityDelegateDefaultImpl() { 51 return null; 52 } 53 54 public Object newAccessiblityDelegateBridge(AccessibilityDelegateCompat listener) { 55 return null; 56 } 57 58 public boolean dispatchPopulateAccessibilityEvent(Object delegate, View host, 59 AccessibilityEvent event) { 60 return false; 61 } 62 63 public void onInitializeAccessibilityEvent(Object delegate, View host, 64 AccessibilityEvent event) { 65 66 } 67 68 public void onInitializeAccessibilityNodeInfo(Object delegate, View host, 69 AccessibilityNodeInfoCompat info) { 70 71 } 72 73 public void onPopulateAccessibilityEvent(Object delegate, View host, 74 AccessibilityEvent event) { 75 76 } 77 78 public boolean onRequestSendAccessibilityEvent(Object delegate, ViewGroup host, View child, 79 AccessibilityEvent event) { 80 return true; 81 } 82 83 public void sendAccessibilityEvent(Object delegate, View host, int eventType) { 84 85 } 86 87 public void sendAccessibilityEventUnchecked(Object delegate, View host, 88 AccessibilityEvent event) { 89 90 } 91 } 92 93 static class AccessibilityDelegateIcsImpl extends AccessibilityDelegateStubImpl { 94 @Override 95 public Object newAccessiblityDelegateDefaultImpl() { 96 return AccessibilityDelegateCompatIcs.newAccessibilityDelegateDefaultImpl(); 97 } 98 99 @Override 100 public Object newAccessiblityDelegateBridge(final AccessibilityDelegateCompat compat) { 101 return AccessibilityDelegateCompatIcs.newAccessibilityDelegateBridge( 102 new AccessibilityDelegateCompatIcs.AccessibilityDelegateBridge() { 103 @Override 104 public boolean dispatchPopulateAccessibilityEvent(View host, 105 AccessibilityEvent event) { 106 return compat.dispatchPopulateAccessibilityEvent(host, event); 107 } 108 109 @Override 110 public void onInitializeAccessibilityEvent(View host, AccessibilityEvent event) { 111 compat.onInitializeAccessibilityEvent(host, event); 112 } 113 114 @Override 115 public void onInitializeAccessibilityNodeInfo(View host, Object info) { 116 compat.onInitializeAccessibilityNodeInfo(host, 117 new AccessibilityNodeInfoCompat(info)); 118 } 119 120 @Override 121 public void onPopulateAccessibilityEvent(View host, AccessibilityEvent event) { 122 compat.onPopulateAccessibilityEvent(host, event); 123 } 124 125 @Override 126 public boolean onRequestSendAccessibilityEvent(ViewGroup host, View child, 127 AccessibilityEvent event) { 128 return compat.onRequestSendAccessibilityEvent(host, child, event); 129 } 130 131 @Override 132 public void sendAccessibilityEvent(View host, int eventType) { 133 compat.sendAccessibilityEvent(host, eventType); 134 } 135 136 @Override 137 public void sendAccessibilityEventUnchecked(View host, AccessibilityEvent event) { 138 compat.sendAccessibilityEventUnchecked(host, event); 139 } 140 }); 141 } 142 143 @Override 144 public boolean dispatchPopulateAccessibilityEvent(Object delegate, View host, 145 AccessibilityEvent event) { 146 return AccessibilityDelegateCompatIcs.dispatchPopulateAccessibilityEvent(delegate, 147 host, event); 148 } 149 150 @Override 151 public void onInitializeAccessibilityEvent(Object delegate, View host, 152 AccessibilityEvent event) { 153 AccessibilityDelegateCompatIcs.onInitializeAccessibilityEvent(delegate, host, event); 154 } 155 156 @Override 157 public void onInitializeAccessibilityNodeInfo(Object delegate, View host, 158 AccessibilityNodeInfoCompat info) { 159 AccessibilityDelegateCompatIcs.onInitializeAccessibilityNodeInfo(delegate, host, 160 info.getImpl()); 161 } 162 163 @Override 164 public void onPopulateAccessibilityEvent(Object delegate, View host, 165 AccessibilityEvent event) { 166 AccessibilityDelegateCompatIcs.onPopulateAccessibilityEvent(delegate, host, event); 167 } 168 169 @Override 170 public boolean onRequestSendAccessibilityEvent(Object delegate, ViewGroup host, View child, 171 AccessibilityEvent event) { 172 return AccessibilityDelegateCompatIcs.onRequestSendAccessibilityEvent(delegate, host, 173 child, event); 174 } 175 176 @Override 177 public void sendAccessibilityEvent(Object delegate, View host, int eventType) { 178 AccessibilityDelegateCompatIcs.sendAccessibilityEvent(delegate, host, eventType); 179 } 180 181 @Override 182 public void sendAccessibilityEventUnchecked(Object delegate, View host, 183 AccessibilityEvent event) { 184 AccessibilityDelegateCompatIcs.sendAccessibilityEventUnchecked(delegate, host, event); 185 } 186 } 187 188 private static final AccessibilityDelegateImpl IMPL; 189 private static final Object DEFAULT_DELEGATE; 190 191 static { 192 if (Build.VERSION.SDK_INT >= 14) { // ICS 193 IMPL = new AccessibilityDelegateIcsImpl(); 194 } else { 195 IMPL = new AccessibilityDelegateStubImpl(); 196 } 197 DEFAULT_DELEGATE = IMPL.newAccessiblityDelegateDefaultImpl(); 198 } 199 200 final Object mBridge; 201 202 /** 203 * Creates a new instance. 204 */ 205 public AccessibilityDelegateCompat() { 206 mBridge = IMPL.newAccessiblityDelegateBridge(this); 207 } 208 209 /** 210 * @return The wrapped bridge implementation. 211 */ 212 Object getBridge() { 213 return mBridge; 214 } 215 216 /** 217 * Sends an accessibility event of the given type. If accessibility is not 218 * enabled this method has no effect. 219 * <p> 220 * The default implementation behaves as {@link View#sendAccessibilityEvent(int) 221 * View#sendAccessibilityEvent(int)} for the case of no accessibility delegate 222 * been set. 223 * </p> 224 * 225 * @param host The View hosting the delegate. 226 * @param eventType The type of the event to send. 227 * 228 * @see View#sendAccessibilityEvent(int) View#sendAccessibilityEvent(int) 229 */ 230 public void sendAccessibilityEvent(View host, int eventType) { 231 IMPL.sendAccessibilityEvent(DEFAULT_DELEGATE, host, eventType); 232 } 233 234 /** 235 * Sends an accessibility event. This method behaves exactly as 236 * {@link #sendAccessibilityEvent(View, int)} but takes as an argument an 237 * empty {@link AccessibilityEvent} and does not perform a check whether 238 * accessibility is enabled. 239 * <p> 240 * The default implementation behaves as 241 * {@link View#sendAccessibilityEventUnchecked(AccessibilityEvent) 242 * View#sendAccessibilityEventUnchecked(AccessibilityEvent)} for 243 * the case of no accessibility delegate been set. 244 * </p> 245 * 246 * @param host The View hosting the delegate. 247 * @param event The event to send. 248 * 249 * @see View#sendAccessibilityEventUnchecked(AccessibilityEvent) 250 * View#sendAccessibilityEventUnchecked(AccessibilityEvent) 251 */ 252 public void sendAccessibilityEventUnchecked(View host, AccessibilityEvent event) { 253 IMPL.sendAccessibilityEventUnchecked(DEFAULT_DELEGATE, host, event); 254 } 255 256 /** 257 * Dispatches an {@link AccessibilityEvent} to the host {@link View} first and then 258 * to its children for adding their text content to the event. 259 * <p> 260 * The default implementation behaves as 261 * {@link View#dispatchPopulateAccessibilityEvent(AccessibilityEvent) 262 * View#dispatchPopulateAccessibilityEvent(AccessibilityEvent)} for 263 * the case of no accessibility delegate been set. 264 * </p> 265 * 266 * @param host The View hosting the delegate. 267 * @param event The event. 268 * @return True if the event population was completed. 269 * 270 * @see View#dispatchPopulateAccessibilityEvent(AccessibilityEvent) 271 * View#dispatchPopulateAccessibilityEvent(AccessibilityEvent) 272 */ 273 public boolean dispatchPopulateAccessibilityEvent(View host, AccessibilityEvent event) { 274 return IMPL.dispatchPopulateAccessibilityEvent(DEFAULT_DELEGATE, host, event); 275 } 276 277 /** 278 * Gives a chance to the host View to populate the accessibility event with its 279 * text content. 280 * <p> 281 * The default implementation behaves as 282 * {@link ViewCompat#onPopulateAccessibilityEvent(View, AccessibilityEvent) 283 * ViewCompat#onPopulateAccessibilityEvent(AccessibilityEvent)} for 284 * the case of no accessibility delegate been set. 285 * </p> 286 * 287 * @param host The View hosting the delegate. 288 * @param event The accessibility event which to populate. 289 * 290 * @see ViewCompat#onPopulateAccessibilityEvent(View ,AccessibilityEvent) 291 * ViewCompat#onPopulateAccessibilityEvent(View, AccessibilityEvent) 292 */ 293 public void onPopulateAccessibilityEvent(View host, AccessibilityEvent event) { 294 IMPL.onPopulateAccessibilityEvent(DEFAULT_DELEGATE, host, event); 295 } 296 297 /** 298 * Initializes an {@link AccessibilityEvent} with information about the 299 * the host View which is the event source. 300 * <p> 301 * The default implementation behaves as 302 * {@link ViewCompat#onInitializeAccessibilityEvent(View v, AccessibilityEvent event) 303 * ViewCompat#onInitalizeAccessibilityEvent(View v, AccessibilityEvent event)} for 304 * the case of no accessibility delegate been set. 305 * </p> 306 * 307 * @param host The View hosting the delegate. 308 * @param event The event to initialize. 309 * 310 * @see ViewCompat#onInitializeAccessibilityEvent(View, AccessibilityEvent) 311 * ViewCompat#onInitializeAccessibilityEvent(View, AccessibilityEvent) 312 */ 313 public void onInitializeAccessibilityEvent(View host, AccessibilityEvent event) { 314 IMPL.onInitializeAccessibilityEvent(DEFAULT_DELEGATE, host, event); 315 } 316 317 /** 318 * Initializes an {@link AccessibilityNodeInfoCompat} with information about the host view. 319 * <p> 320 * The default implementation behaves as 321 * {@link ViewCompat#onInitializeAccessibilityNodeInfo(View, AccessibilityNodeInfoCompat) 322 * ViewCompat#onInitializeAccessibilityNodeInfo(View, AccessibilityNodeInfoCompat)} for 323 * the case of no accessibility delegate been set. 324 * </p> 325 * 326 * @param host The View hosting the delegate. 327 * @param info The instance to initialize. 328 * 329 * @see ViewCompat#onInitializeAccessibilityNodeInfo(View, AccessibilityNodeInfoCompat) 330 * ViewCompat#onInitializeAccessibilityNodeInfo(View, AccessibilityNodeInfoCompat) 331 */ 332 public void onInitializeAccessibilityNodeInfo(View host, AccessibilityNodeInfoCompat info) { 333 IMPL.onInitializeAccessibilityNodeInfo(DEFAULT_DELEGATE, host, info); 334 } 335 336 /** 337 * Called when a child of the host View has requested sending an 338 * {@link AccessibilityEvent} and gives an opportunity to the parent (the host) 339 * to augment the event. 340 * <p> 341 * The default implementation behaves as 342 * {@link ViewGroupCompat#onRequestSendAccessibilityEvent(ViewGroup, View, AccessibilityEvent) 343 * ViewGroupCompat#onRequestSendAccessibilityEvent(ViewGroup, View, AccessibilityEvent)} for 344 * the case of no accessibility delegate been set. 345 * </p> 346 * 347 * @param host The View hosting the delegate. 348 * @param child The child which requests sending the event. 349 * @param event The event to be sent. 350 * @return True if the event should be sent 351 * 352 * @see ViewGroupCompat#onRequestSendAccessibilityEvent(ViewGroup, View, AccessibilityEvent) 353 * ViewGroupCompat#onRequestSendAccessibilityEvent(ViewGroup, View, AccessibilityEvent) 354 */ 355 public boolean onRequestSendAccessibilityEvent(ViewGroup host, View child, 356 AccessibilityEvent event) { 357 return IMPL.onRequestSendAccessibilityEvent(DEFAULT_DELEGATE, host, child, event); 358 } 359} 360