1 /* 2 * Copyright (C) 2008 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 17 package android.widget.cts; 18 19 import android.test.UiThreadTest; 20 import com.android.cts.widget.R; 21 22 23 import android.app.Activity; 24 import android.app.Instrumentation; 25 import android.app.PendingIntent; 26 import android.app.Instrumentation.ActivityMonitor; 27 import android.content.Intent; 28 import android.content.res.ColorStateList; 29 import android.cts.util.WidgetTestUtils; 30 import android.graphics.Bitmap; 31 import android.graphics.BitmapFactory; 32 import android.graphics.drawable.BitmapDrawable; 33 import android.net.Uri; 34 import android.os.Parcel; 35 import android.test.ActivityInstrumentationTestCase2; 36 import android.view.View; 37 import android.widget.AbsoluteLayout; 38 import android.widget.Chronometer; 39 import android.widget.EditText; 40 import android.widget.FrameLayout; 41 import android.widget.GridView; 42 import android.widget.ImageView; 43 import android.widget.LinearLayout; 44 import android.widget.ListView; 45 import android.widget.ProgressBar; 46 import android.widget.RelativeLayout; 47 import android.widget.RemoteViews; 48 import android.widget.TextView; 49 import android.widget.RemoteViews.ActionException; 50 51 import java.io.File; 52 import java.io.FileOutputStream; 53 import java.io.IOException; 54 import java.io.InputStream; 55 import java.io.OutputStream; 56 57 /** 58 * Test {@link RemoteViews}. 59 */ 60 public class RemoteViewsTest extends ActivityInstrumentationTestCase2<RemoteViewsCtsActivity> { 61 private static final String PACKAGE_NAME = "com.android.cts.widget"; 62 63 private static final int INVALD_ID = -1; 64 65 private static final long TEST_TIMEOUT = 5000; 66 67 private RemoteViews mRemoteViews; 68 69 private View mResult; 70 71 private Activity mActivity; 72 73 public RemoteViewsTest() { 74 super(PACKAGE_NAME, RemoteViewsCtsActivity.class); 75 } 76 77 @Override 78 protected void setUp() throws Exception { 79 super.setUp(); 80 mActivity = getActivity(); 81 getInstrumentation().runOnMainSync(new Runnable() { 82 @Override 83 public void run() { 84 mRemoteViews = new RemoteViews(PACKAGE_NAME, R.layout.remoteviews_good); 85 mResult = mRemoteViews.apply(mActivity, null); 86 } 87 }); 88 } 89 90 public void testConstructor() { 91 new RemoteViews(PACKAGE_NAME, R.layout.remoteviews_good); 92 93 new RemoteViews(Parcel.obtain()); 94 } 95 96 public void testGetPackage() { 97 assertEquals(PACKAGE_NAME, mRemoteViews.getPackage()); 98 99 mRemoteViews = new RemoteViews(null, R.layout.remoteviews_good); 100 assertNull(mRemoteViews.getPackage()); 101 } 102 103 public void testGetLayoutId() { 104 assertEquals(R.layout.remoteviews_good, mRemoteViews.getLayoutId()); 105 106 mRemoteViews = new RemoteViews(PACKAGE_NAME, R.layout.listview_layout); 107 assertEquals(R.layout.listview_layout, mRemoteViews.getLayoutId()); 108 109 mRemoteViews = new RemoteViews(PACKAGE_NAME, INVALD_ID); 110 assertEquals(INVALD_ID, mRemoteViews.getLayoutId()); 111 112 mRemoteViews = new RemoteViews(PACKAGE_NAME, 0); 113 assertEquals(0, mRemoteViews.getLayoutId()); 114 } 115 116 public void testSetViewVisibility() { 117 View view = mResult.findViewById(R.id.remoteView_chronometer); 118 assertEquals(View.VISIBLE, view.getVisibility()); 119 120 mRemoteViews.setViewVisibility(R.id.remoteView_chronometer, View.INVISIBLE); 121 mRemoteViews.reapply(mActivity, mResult); 122 assertEquals(View.INVISIBLE, view.getVisibility()); 123 124 mRemoteViews.setViewVisibility(R.id.remoteView_chronometer, View.GONE); 125 mRemoteViews.reapply(mActivity, mResult); 126 assertEquals(View.GONE, view.getVisibility()); 127 128 mRemoteViews.setViewVisibility(R.id.remoteView_chronometer, View.VISIBLE); 129 mRemoteViews.reapply(mActivity, mResult); 130 assertEquals(View.VISIBLE, view.getVisibility()); 131 } 132 133 public void testSetTextViewText() { 134 TextView textView = (TextView) mResult.findViewById(R.id.remoteView_text); 135 assertEquals("", textView.getText().toString()); 136 137 String expected = "This is content"; 138 mRemoteViews.setTextViewText(R.id.remoteView_text, expected); 139 mRemoteViews.reapply(mActivity, mResult); 140 assertEquals(expected, textView.getText().toString()); 141 142 mRemoteViews.setTextViewText(R.id.remoteView_text, null); 143 mRemoteViews.reapply(mActivity, mResult); 144 assertEquals("", textView.getText().toString()); 145 146 mRemoteViews.setTextViewText(R.id.remoteView_absolute, ""); 147 try { 148 mRemoteViews.reapply(mActivity, mResult); 149 fail("Should throw ActionException"); 150 } catch (ActionException e) { 151 // expected 152 } 153 } 154 155 public void testSetImageViewResource() { 156 ImageView image = (ImageView) mResult.findViewById(R.id.remoteView_image); 157 assertNull(image.getDrawable()); 158 159 mRemoteViews.setImageViewResource(R.id.remoteView_image, R.drawable.testimage); 160 mRemoteViews.reapply(mActivity, mResult); 161 assertNotNull(image.getDrawable()); 162 BitmapDrawable d = (BitmapDrawable) mActivity 163 .getResources().getDrawable(R.drawable.testimage); 164 WidgetTestUtils.assertEquals(d.getBitmap(), 165 ((BitmapDrawable) image.getDrawable()).getBitmap()); 166 167 mRemoteViews.setImageViewResource(R.id.remoteView_absolute, R.drawable.testimage); 168 try { 169 mRemoteViews.reapply(mActivity, mResult); 170 fail("Should throw ActionException"); 171 } catch (ActionException e) { 172 // expected 173 } 174 } 175 176 public void testSetImageViewUri() throws IOException { 177 String path = getTestImagePath(); 178 File imageFile = new File(path); 179 180 try { 181 createSampleImage(imageFile, R.raw.testimage); 182 183 Uri uri = Uri.parse(path); 184 ImageView image = (ImageView) mResult.findViewById(R.id.remoteView_image); 185 assertNull(image.getDrawable()); 186 187 mRemoteViews.setImageViewUri(R.id.remoteView_image, uri); 188 mRemoteViews.reapply(mActivity, mResult); 189 190 Bitmap imageViewBitmap = ((BitmapDrawable) image.getDrawable()).getBitmap(); 191 Bitmap expectedBitmap = WidgetTestUtils.getUnscaledAndDitheredBitmap( 192 mActivity.getResources(), R.raw.testimage, imageViewBitmap.getConfig()); 193 WidgetTestUtils.assertEquals(expectedBitmap, imageViewBitmap); 194 } finally { 195 imageFile.delete(); 196 } 197 } 198 199 /** 200 * Returns absolute file path of location where test image should be stored 201 */ 202 private String getTestImagePath() { 203 return getInstrumentation().getTargetContext().getFilesDir() + "/test.jpg"; 204 } 205 206 public void testSetChronometer() { 207 long base1 = 50; 208 long base2 = -50; 209 Chronometer chronometer = (Chronometer) mResult.findViewById(R.id.remoteView_chronometer); 210 211 mRemoteViews.setChronometer(R.id.remoteView_chronometer, base1, "HH:MM:SS", 212 false); 213 mRemoteViews.reapply(mActivity, mResult); 214 assertEquals(base1, chronometer.getBase()); 215 assertEquals("HH:MM:SS", chronometer.getFormat()); 216 217 mRemoteViews.setChronometer(R.id.remoteView_chronometer, base2, "HH:MM:SS", 218 false); 219 mRemoteViews.reapply(mActivity, mResult); 220 assertEquals(base2, chronometer.getBase()); 221 assertEquals("HH:MM:SS", chronometer.getFormat()); 222 223 mRemoteViews.setChronometer(R.id.remoteView_chronometer, base1, "invalid", 224 true); 225 mRemoteViews.reapply(mActivity, mResult); 226 assertEquals(base1, chronometer.getBase()); 227 assertEquals("invalid", chronometer.getFormat()); 228 229 mRemoteViews.setChronometer(R.id.remoteView_absolute, base1, "invalid", true); 230 try { 231 mRemoteViews.reapply(mActivity, mResult); 232 fail("Should throw ActionException"); 233 } catch (ActionException e) { 234 // expected 235 } 236 } 237 238 public void testSetProgressBar() { 239 ProgressBar progress = (ProgressBar) mResult.findViewById(R.id.remoteView_progress); 240 assertEquals(100, progress.getMax()); 241 assertEquals(0, progress.getProgress()); 242 // the view uses style progressBarHorizontal, so the default is false 243 assertFalse(progress.isIndeterminate()); 244 245 mRemoteViews.setProgressBar(R.id.remoteView_progress, 80, 50, true); 246 mRemoteViews.reapply(mActivity, mResult); 247 // make the bar indeterminate will not affect max and progress 248 assertEquals(100, progress.getMax()); 249 assertEquals(0, progress.getProgress()); 250 assertTrue(progress.isIndeterminate()); 251 252 mRemoteViews.setProgressBar(R.id.remoteView_progress, 60, 50, false); 253 mRemoteViews.reapply(mActivity, mResult); 254 assertEquals(60, progress.getMax()); 255 assertEquals(50, progress.getProgress()); 256 assertFalse(progress.isIndeterminate()); 257 258 mRemoteViews.setProgressBar(R.id.remoteView_relative, 60, 50, false); 259 try { 260 mRemoteViews.reapply(mActivity, mResult); 261 fail("Should throw ActionException"); 262 } catch (ActionException e) { 263 // expected 264 } 265 } 266 267 public void testApply() { 268 assertNotNull(mResult); 269 assertNotNull(mResult.findViewById(R.id.remoteViews_good)); 270 assertNotNull(mResult.findViewById(R.id.remoteView_absolute)); 271 assertNotNull(mResult.findViewById(R.id.remoteView_chronometer)); 272 assertNotNull(mResult.findViewById(R.id.remoteView_frame)); 273 assertNotNull(mResult.findViewById(R.id.remoteView_image)); 274 assertNotNull(mResult.findViewById(R.id.remoteView_linear)); 275 assertNotNull(mResult.findViewById(R.id.remoteView_progress)); 276 assertNotNull(mResult.findViewById(R.id.remoteView_relative)); 277 assertNotNull(mResult.findViewById(R.id.remoteView_text)); 278 } 279 280 public void testReapply() { 281 TextView text = new TextView(mActivity); 282 ImageView image = (ImageView) mResult.findViewById(R.id.remoteView_image); 283 assertNull(image.getDrawable()); 284 285 mRemoteViews.setImageViewResource(R.id.remoteView_image, R.drawable.testimage); 286 mRemoteViews.reapply(mActivity, image); 287 assertNotNull(image.getDrawable()); 288 BitmapDrawable d = (BitmapDrawable) mActivity 289 .getResources().getDrawable(R.drawable.testimage); 290 WidgetTestUtils.assertEquals(d.getBitmap(), 291 ((BitmapDrawable) image.getDrawable()).getBitmap()); 292 } 293 294 public void testOnLoadClass() { 295 mRemoteViews = new RemoteViews(Parcel.obtain()); 296 297 assertTrue(mRemoteViews.onLoadClass(RelativeLayout.class)); 298 assertTrue(mRemoteViews.onLoadClass(FrameLayout.class)); 299 assertTrue(mRemoteViews.onLoadClass(AbsoluteLayout.class)); 300 assertTrue(mRemoteViews.onLoadClass(LinearLayout.class)); 301 assertTrue(mRemoteViews.onLoadClass(TextView.class)); 302 assertTrue(mRemoteViews.onLoadClass(ImageView.class)); 303 assertTrue(mRemoteViews.onLoadClass(ProgressBar.class)); 304 assertTrue(mRemoteViews.onLoadClass(Chronometer.class)); 305 assertTrue(mRemoteViews.onLoadClass(ListView.class)); 306 assertTrue(mRemoteViews.onLoadClass(GridView.class)); 307 308 // those classes without annotation @RemoteView 309 assertFalse(mRemoteViews.onLoadClass(EditText.class)); 310 } 311 312 public void testDescribeContents() { 313 mRemoteViews = new RemoteViews(Parcel.obtain()); 314 mRemoteViews.describeContents(); 315 } 316 317 @UiThreadTest 318 public void testWriteToParcel() { 319 mRemoteViews.setTextViewText(R.id.remoteView_text, "This is content"); 320 mRemoteViews.setViewVisibility(R.id.remoteView_frame, View.GONE); 321 Parcel p = Parcel.obtain(); 322 mRemoteViews.writeToParcel(p, 0); 323 p.setDataPosition(0); 324 325 // the package and layout are successfully written into parcel 326 mRemoteViews = RemoteViews.CREATOR.createFromParcel(p); 327 View result = mRemoteViews.apply(mActivity, null); 328 assertEquals(PACKAGE_NAME, mRemoteViews.getPackage()); 329 assertEquals(R.layout.remoteviews_good, mRemoteViews.getLayoutId()); 330 assertEquals("This is content", ((TextView) result.findViewById(R.id.remoteView_text)) 331 .getText().toString()); 332 assertEquals(View.GONE, result.findViewById(R.id.remoteView_frame).getVisibility()); 333 334 p = Parcel.obtain(); 335 try { 336 mRemoteViews.writeToParcel(null, 0); 337 fail("Should throw NullPointerException"); 338 } catch (NullPointerException e) { 339 // expected 340 } 341 342 // currently the flag is not used 343 mRemoteViews.writeToParcel(p, -1); 344 345 p.recycle(); 346 347 RemoteViews[] remote = RemoteViews.CREATOR.newArray(1); 348 assertNotNull(remote); 349 assertEquals(1, remote.length); 350 351 try { 352 RemoteViews.CREATOR.newArray(-1); 353 fail("should throw NegativeArraySizeException"); 354 } catch (NegativeArraySizeException e) { 355 // expected 356 } 357 } 358 359 public void testSetImageViewBitmap() { 360 ImageView image = (ImageView) mResult.findViewById(R.id.remoteView_image); 361 assertNull(image.getDrawable()); 362 363 Bitmap bitmap = 364 BitmapFactory.decodeResource(mActivity.getResources(), R.drawable.testimage); 365 mRemoteViews.setImageViewBitmap(R.id.remoteView_image, bitmap); 366 mRemoteViews.reapply(mActivity, mResult); 367 assertNotNull(image.getDrawable()); 368 WidgetTestUtils.assertEquals(bitmap, ((BitmapDrawable) image.getDrawable()).getBitmap()); 369 370 mRemoteViews.setImageViewBitmap(R.id.remoteView_absolute, bitmap); 371 try { 372 mRemoteViews.reapply(mActivity, mResult); 373 fail("Should throw ActionException"); 374 } catch (ActionException e) { 375 // expected 376 } 377 } 378 379 public void testSetBitmap() { 380 ImageView image = (ImageView) mResult.findViewById(R.id.remoteView_image); 381 assertNull(image.getDrawable()); 382 383 Bitmap bitmap = 384 BitmapFactory.decodeResource(mActivity.getResources(), R.drawable.testimage); 385 mRemoteViews.setBitmap(R.id.remoteView_image, "setImageBitmap", bitmap); 386 mRemoteViews.reapply(mActivity, mResult); 387 assertNotNull(image.getDrawable()); 388 WidgetTestUtils.assertEquals(bitmap, ((BitmapDrawable) image.getDrawable()).getBitmap()); 389 390 mRemoteViews.setBitmap(R.id.remoteView_absolute, "setImageBitmap", bitmap); 391 try { 392 mRemoteViews.reapply(mActivity, mResult); 393 fail("Should throw ActionException"); 394 } catch (ActionException e) { 395 // expected 396 } 397 } 398 399 public void testSetBoolean() { 400 ProgressBar progress = (ProgressBar) mResult.findViewById(R.id.remoteView_progress); 401 // the view uses style progressBarHorizontal, so the default is false 402 assertFalse(progress.isIndeterminate()); 403 404 mRemoteViews.setBoolean(R.id.remoteView_progress, "setIndeterminate", true); 405 mRemoteViews.reapply(mActivity, mResult); 406 assertTrue(progress.isIndeterminate()); 407 408 mRemoteViews.setBoolean(R.id.remoteView_relative, "setIndeterminate", false); 409 try { 410 mRemoteViews.reapply(mActivity, mResult); 411 fail("Should throw ActionException"); 412 } catch (ActionException e) { 413 // expected 414 } 415 } 416 417 public void testSetCharSequence() { 418 TextView textView = (TextView) mResult.findViewById(R.id.remoteView_text); 419 assertEquals("", textView.getText().toString()); 420 421 String expected = "test setCharSequence"; 422 mRemoteViews.setCharSequence(R.id.remoteView_text, "setText", expected); 423 mRemoteViews.reapply(mActivity, mResult); 424 assertEquals(expected, textView.getText().toString()); 425 426 mRemoteViews.setCharSequence(R.id.remoteView_text, "setText", null); 427 mRemoteViews.reapply(mActivity, mResult); 428 assertEquals("", textView.getText().toString()); 429 430 mRemoteViews.setCharSequence(R.id.remoteView_absolute, "setText", ""); 431 try { 432 mRemoteViews.reapply(mActivity, mResult); 433 fail("Should throw ActionException"); 434 } catch (ActionException e) { 435 // expected 436 } 437 } 438 439 public void testSetInt() { 440 View view = mResult.findViewById(R.id.remoteView_chronometer); 441 assertEquals(View.VISIBLE, view.getVisibility()); 442 443 mRemoteViews.setInt(R.id.remoteView_chronometer, "setVisibility", View.INVISIBLE); 444 mRemoteViews.reapply(mActivity, mResult); 445 assertEquals(View.INVISIBLE, view.getVisibility()); 446 447 mRemoteViews.setInt(R.id.remoteView_chronometer, "setVisibility", View.GONE); 448 mRemoteViews.reapply(mActivity, mResult); 449 assertEquals(View.GONE, view.getVisibility()); 450 451 mRemoteViews.setInt(R.id.remoteView_chronometer, "setVisibility", View.VISIBLE); 452 mRemoteViews.reapply(mActivity, mResult); 453 assertEquals(View.VISIBLE, view.getVisibility()); 454 } 455 456 public void testSetString() { 457 String format = "HH:MM:SS"; 458 Chronometer chronometer = (Chronometer) mResult.findViewById(R.id.remoteView_chronometer); 459 assertNull(chronometer.getFormat()); 460 461 mRemoteViews.setString(R.id.remoteView_chronometer, "setFormat", format); 462 mRemoteViews.reapply(mActivity, mResult); 463 assertEquals(format, chronometer.getFormat()); 464 465 mRemoteViews.setString(R.id.remoteView_image, "setFormat", format); 466 try { 467 mRemoteViews.reapply(mActivity, mResult); 468 fail("Should throw ActionException"); 469 } catch (ActionException e) { 470 // expected 471 } 472 } 473 474 public void testSetUri() throws IOException { 475 String path = getTestImagePath(); 476 File imagefile = new File(path); 477 478 try { 479 createSampleImage(imagefile, R.raw.testimage); 480 481 Uri uri = Uri.parse(path); 482 ImageView image = (ImageView) mResult.findViewById(R.id.remoteView_image); 483 assertNull(image.getDrawable()); 484 485 mRemoteViews.setUri(R.id.remoteView_image, "setImageURI", uri); 486 mRemoteViews.reapply(mActivity, mResult); 487 488 Bitmap imageViewBitmap = ((BitmapDrawable) image.getDrawable()).getBitmap(); 489 Bitmap expectedBitmap = WidgetTestUtils.getUnscaledAndDitheredBitmap( 490 mActivity.getResources(), R.raw.testimage, imageViewBitmap.getConfig()); 491 WidgetTestUtils.assertEquals(expectedBitmap, imageViewBitmap); 492 493 mRemoteViews.setUri(R.id.remoteView_absolute, "setImageURI", uri); 494 try { 495 mRemoteViews.reapply(mActivity, mResult); 496 fail("Should throw ActionException"); 497 } catch (ActionException e) { 498 // expected 499 } 500 } finally { 501 // remove the test image file 502 imagefile.delete(); 503 } 504 } 505 506 public void testSetTextColor() { 507 TextView textView = (TextView) mResult.findViewById(R.id.remoteView_text); 508 509 mRemoteViews.setTextColor(R.id.remoteView_text, R.color.testcolor1); 510 mRemoteViews.reapply(mActivity, mResult); 511 assertSame(ColorStateList.valueOf(R.color.testcolor1), textView.getTextColors()); 512 513 mRemoteViews.setTextColor(R.id.remoteView_text, R.color.testcolor2); 514 mRemoteViews.reapply(mActivity, mResult); 515 assertSame(ColorStateList.valueOf(R.color.testcolor2), textView.getTextColors()); 516 517 mRemoteViews.setTextColor(R.id.remoteView_absolute, R.color.testcolor1); 518 try { 519 mRemoteViews.reapply(mActivity, mResult); 520 fail("Should throw ActionException"); 521 } catch (ActionException e) { 522 // expected 523 } 524 } 525 526 public void testSetOnClickPendingIntent() { 527 Uri uri = Uri.parse("ctstest://RemoteView/test"); 528 Instrumentation instrumentation = getInstrumentation(); 529 ActivityMonitor am = instrumentation.addMonitor(MockURLSpanTestActivity.class.getName(), 530 null, false); 531 View view = mResult.findViewById(R.id.remoteView_image); 532 view.performClick(); 533 Activity newActivity = am.waitForActivityWithTimeout(TEST_TIMEOUT); 534 assertNull(newActivity); 535 536 Intent intent = new Intent(Intent.ACTION_VIEW, uri); 537 PendingIntent pendingIntent = PendingIntent.getActivity(mActivity, 0, intent, 0); 538 mRemoteViews.setOnClickPendingIntent(R.id.remoteView_image, pendingIntent); 539 mRemoteViews.reapply(mActivity, mResult); 540 view.performClick(); 541 newActivity = am.waitForActivityWithTimeout(TEST_TIMEOUT); 542 assertNotNull(newActivity); 543 newActivity.finish(); 544 } 545 546 public void testSetLong() { 547 long base1 = 50; 548 long base2 = -50; 549 Chronometer chronometer = (Chronometer) mResult.findViewById(R.id.remoteView_chronometer); 550 551 mRemoteViews.setLong(R.id.remoteView_chronometer, "setBase", base1); 552 mRemoteViews.reapply(mActivity, mResult); 553 assertEquals(base1, chronometer.getBase()); 554 555 mRemoteViews.setLong(R.id.remoteView_chronometer, "setBase", base2); 556 mRemoteViews.reapply(mActivity, mResult); 557 assertEquals(base2, chronometer.getBase()); 558 559 mRemoteViews.setLong(R.id.remoteView_absolute, "setBase", base1); 560 try { 561 mRemoteViews.reapply(mActivity, mResult); 562 fail("Should throw ActionException"); 563 } catch (ActionException e) { 564 // expected 565 } 566 } 567 568 public void testSetFloat() { 569 LinearLayout linearLayout = (LinearLayout) mResult.findViewById(R.id.remoteView_linear); 570 assertTrue(linearLayout.getWeightSum() <= 0.0f); 571 572 mRemoteViews.setFloat(R.id.remoteView_linear, "setWeightSum", 0.5f); 573 mRemoteViews.reapply(mActivity, mResult); 574 assertEquals(0.5f, linearLayout.getWeightSum()); 575 576 mRemoteViews.setFloat(R.id.remoteView_absolute, "setWeightSum", 1.0f); 577 try { 578 mRemoteViews.reapply(mActivity, mResult); 579 fail("Should throw ActionException"); 580 } catch (ActionException e) { 581 // expected 582 } 583 } 584 585 public void testNotFeasibleSetters() { 586 // there is no RemotableViewMethods to use them, how to test? 587 } 588 589 private void createSampleImage(File imagefile, int resid) throws IOException { 590 InputStream source = null; 591 OutputStream target = null; 592 593 try { 594 source = mActivity.getResources().openRawResource(resid); 595 target = new FileOutputStream(imagefile); 596 597 byte[] buffer = new byte[1024]; 598 for (int len = source.read(buffer); len > 0; len = source.read(buffer)) { 599 target.write(buffer, 0, len); 600 } 601 } finally { 602 try { 603 if (source != null) { 604 source.close(); 605 } 606 if (target != null) { 607 target.close(); 608 } 609 } catch (IOException _) { 610 // Ignore the IOException. 611 } 612 } 613 } 614 } 615