FilterShowActivity.java revision 0addfc7f6342184a67cdd8b5cc3872c6a5c87e55
1 2package com.android.gallery3d.filtershow; 3 4import android.annotation.TargetApi; 5import android.app.ActionBar; 6import android.app.Activity; 7import android.app.ProgressDialog; 8import android.content.ContentValues; 9import android.content.Context; 10import android.content.Intent; 11import android.content.res.Resources; 12import android.graphics.Bitmap; 13import android.graphics.BitmapFactory; 14import android.graphics.Color; 15import android.graphics.Point; 16import android.graphics.drawable.Drawable; 17import android.net.Uri; 18import android.os.Bundle; 19import android.util.DisplayMetrics; 20import android.util.Log; 21import android.util.TypedValue; 22import android.view.Display; 23import android.view.Menu; 24import android.view.MenuItem; 25import android.view.View; 26import android.view.View.OnClickListener; 27import android.widget.AdapterView; 28import android.widget.AdapterView.OnItemClickListener; 29import android.widget.ImageButton; 30import android.widget.LinearLayout; 31import android.widget.ListView; 32import android.widget.SeekBar; 33import android.widget.ShareActionProvider; 34import android.widget.ShareActionProvider.OnShareTargetSelectedListener; 35import android.widget.Toast; 36 37import com.android.gallery3d.R; 38import com.android.gallery3d.data.LocalAlbum; 39import com.android.gallery3d.filtershow.cache.ImageLoader; 40import com.android.gallery3d.filtershow.filters.ImageFilter; 41import com.android.gallery3d.filtershow.filters.ImageFilterBorder; 42import com.android.gallery3d.filtershow.filters.ImageFilterContrast; 43import com.android.gallery3d.filtershow.filters.ImageFilterExposure; 44import com.android.gallery3d.filtershow.filters.ImageFilterFx; 45import com.android.gallery3d.filtershow.filters.ImageFilterHue; 46import com.android.gallery3d.filtershow.filters.ImageFilterParametricBorder; 47import com.android.gallery3d.filtershow.filters.ImageFilterRS; 48import com.android.gallery3d.filtershow.filters.ImageFilterSaturated; 49import com.android.gallery3d.filtershow.filters.ImageFilterShadows; 50import com.android.gallery3d.filtershow.filters.ImageFilterVibrance; 51import com.android.gallery3d.filtershow.filters.ImageFilterVignette; 52import com.android.gallery3d.filtershow.filters.ImageFilterWBalance; 53import com.android.gallery3d.filtershow.imageshow.ImageBorder; 54import com.android.gallery3d.filtershow.imageshow.ImageCrop; 55import com.android.gallery3d.filtershow.imageshow.ImageFlip; 56import com.android.gallery3d.filtershow.imageshow.ImageRotate; 57import com.android.gallery3d.filtershow.imageshow.ImageShow; 58import com.android.gallery3d.filtershow.imageshow.ImageSmallBorder; 59import com.android.gallery3d.filtershow.imageshow.ImageSmallFilter; 60import com.android.gallery3d.filtershow.imageshow.ImageStraighten; 61import com.android.gallery3d.filtershow.imageshow.ImageWithIcon; 62import com.android.gallery3d.filtershow.imageshow.ImageZoom; 63import com.android.gallery3d.filtershow.presets.ImagePreset; 64import com.android.gallery3d.filtershow.provider.SharedImageProvider; 65import com.android.gallery3d.filtershow.tools.SaveCopyTask; 66import com.android.gallery3d.filtershow.ui.ImageButtonTitle; 67import com.android.gallery3d.filtershow.ui.ImageCurves; 68import com.android.gallery3d.filtershow.ui.Spline; 69import com.android.gallery3d.util.GalleryUtils; 70 71import java.io.File; 72import java.lang.ref.WeakReference; 73import java.util.Vector; 74 75@TargetApi(16) 76public class FilterShowActivity extends Activity implements OnItemClickListener, 77 OnShareTargetSelectedListener { 78 79 public static final String CROP_ACTION = "com.android.camera.action.CROP"; 80 private final PanelController mPanelController = new PanelController(); 81 private ImageLoader mImageLoader = null; 82 private ImageShow mImageShow = null; 83 private ImageCurves mImageCurves = null; 84 private ImageBorder mImageBorders = null; 85 private ImageStraighten mImageStraighten = null; 86 private ImageZoom mImageZoom = null; 87 private ImageCrop mImageCrop = null; 88 private ImageRotate mImageRotate = null; 89 private ImageFlip mImageFlip = null; 90 91 private View mListFx = null; 92 private View mListBorders = null; 93 private View mListGeometry = null; 94 private View mListColors = null; 95 private View mListFilterButtons = null; 96 97 private ImageButton mFxButton = null; 98 private ImageButton mBorderButton = null; 99 private ImageButton mGeometryButton = null; 100 private ImageButton mColorsButton = null; 101 102 private ImageSmallFilter mCurrentImageSmallFilter = null; 103 private static final int SELECT_PICTURE = 1; 104 private static final String LOGTAG = "FilterShowActivity"; 105 protected static final boolean ANIMATE_PANELS = true; 106 private static int mImageBorderSize = 40; 107 108 private boolean mShowingHistoryPanel = false; 109 private boolean mShowingImageStatePanel = false; 110 111 private final Vector<ImageShow> mImageViews = new Vector<ImageShow>(); 112 private final Vector<View> mListViews = new Vector<View>(); 113 private final Vector<ImageButton> mBottomPanelButtons = new Vector<ImageButton>(); 114 115 private ShareActionProvider mShareActionProvider; 116 private File mSharedOutputFile = null; 117 118 private boolean mSharingImage = false; 119 120 private WeakReference<ProgressDialog> mSavingProgressDialog; 121 private static final int SEEK_BAR_MAX = 600; 122 123 @Override 124 public void onCreate(Bundle savedInstanceState) { 125 super.onCreate(savedInstanceState); 126 127 ImageFilterRS.setRenderScriptContext(this); 128 129 ImageShow.setDefaultBackgroundColor(getResources().getColor(R.color.background_screen)); 130 // TODO: get those values from XML. 131 ImageShow.setTextSize((int) getPixelsFromDip(12)); 132 ImageShow.setTextPadding((int) getPixelsFromDip(10)); 133 ImageButtonTitle.setTextSize((int) getPixelsFromDip(12)); 134 ImageButtonTitle.setTextPadding((int) getPixelsFromDip(10)); 135 ImageSmallFilter.setMargin((int) getPixelsFromDip(3)); 136 ImageSmallFilter.setTextMargin((int) getPixelsFromDip(4)); 137 mImageBorderSize = (int) getPixelsFromDip(20); 138 Drawable curveHandle = getResources().getDrawable(R.drawable.camera_crop_holo); 139 int curveHandleSize = (int) getResources().getDimension(R.dimen.crop_indicator_size); 140 Spline.setCurveHandle(curveHandle, curveHandleSize); 141 Spline.setCurveWidth((int) getPixelsFromDip(3)); 142 143 setContentView(R.layout.filtershow_activity); 144 ActionBar actionBar = getActionBar(); 145 actionBar.setDisplayOptions(ActionBar.DISPLAY_SHOW_CUSTOM); 146 actionBar.setCustomView(R.layout.filtershow_actionbar); 147 148 actionBar.getCustomView().setOnClickListener(new OnClickListener() { 149 @Override 150 public void onClick(View view) { 151 saveImage(); 152 } 153 }); 154 155 mImageLoader = new ImageLoader(this, getApplicationContext()); 156 157 LinearLayout listFilters = (LinearLayout) findViewById(R.id.listFilters); 158 LinearLayout listBorders = (LinearLayout) findViewById(R.id.listBorders); 159 LinearLayout listColors = (LinearLayout) findViewById(R.id.listColorsFx); 160 161 mImageShow = (ImageShow) findViewById(R.id.imageShow); 162 mImageCurves = (ImageCurves) findViewById(R.id.imageCurves); 163 mImageBorders = (ImageBorder) findViewById(R.id.imageBorder); 164 mImageStraighten = (ImageStraighten) findViewById(R.id.imageStraighten); 165 mImageZoom = (ImageZoom) findViewById(R.id.imageZoom); 166 mImageCrop = (ImageCrop) findViewById(R.id.imageCrop); 167 mImageRotate = (ImageRotate) findViewById(R.id.imageRotate); 168 mImageFlip = (ImageFlip) findViewById(R.id.imageFlip); 169 170 mImageViews.add(mImageShow); 171 mImageViews.add(mImageCurves); 172 mImageViews.add(mImageBorders); 173 mImageViews.add(mImageStraighten); 174 mImageViews.add(mImageZoom); 175 mImageViews.add(mImageCrop); 176 mImageViews.add(mImageRotate); 177 mImageViews.add(mImageFlip); 178 179 mListFx = findViewById(R.id.fxList); 180 mListBorders = findViewById(R.id.bordersList); 181 mListGeometry = findViewById(R.id.geometryList); 182 mListFilterButtons = findViewById(R.id.filterButtonsList); 183 mListColors = findViewById(R.id.colorsFxList); 184 mListViews.add(mListFx); 185 mListViews.add(mListBorders); 186 mListViews.add(mListGeometry); 187 mListViews.add(mListFilterButtons); 188 mListViews.add(mListColors); 189 190 mFxButton = (ImageButton) findViewById(R.id.fxButton); 191 mBorderButton = (ImageButton) findViewById(R.id.borderButton); 192 mGeometryButton = (ImageButton) findViewById(R.id.geometryButton); 193 mColorsButton = (ImageButton) findViewById(R.id.colorsButton); 194 195 mImageShow.setImageLoader(mImageLoader); 196 mImageCurves.setImageLoader(mImageLoader); 197 mImageCurves.setMaster(mImageShow); 198 mImageBorders.setImageLoader(mImageLoader); 199 mImageBorders.setMaster(mImageShow); 200 mImageStraighten.setImageLoader(mImageLoader); 201 mImageStraighten.setMaster(mImageShow); 202 mImageZoom.setImageLoader(mImageLoader); 203 mImageZoom.setMaster(mImageShow); 204 mImageCrop.setImageLoader(mImageLoader); 205 mImageCrop.setMaster(mImageShow); 206 mImageRotate.setImageLoader(mImageLoader); 207 mImageRotate.setMaster(mImageShow); 208 mImageFlip.setImageLoader(mImageLoader); 209 mImageFlip.setMaster(mImageShow); 210 211 mPanelController.addImageView(findViewById(R.id.imageShow)); 212 mPanelController.addImageView(findViewById(R.id.imageCurves)); 213 mPanelController.addImageView(findViewById(R.id.imageBorder)); 214 mPanelController.addImageView(findViewById(R.id.imageStraighten)); 215 mPanelController.addImageView(findViewById(R.id.imageCrop)); 216 mPanelController.addImageView(findViewById(R.id.imageRotate)); 217 mPanelController.addImageView(findViewById(R.id.imageFlip)); 218 mPanelController.addImageView(findViewById(R.id.imageZoom)); 219 220 mPanelController.addPanel(mFxButton, mListFx, 0); 221 mPanelController.addPanel(mBorderButton, mListBorders, 1); 222 223 mPanelController.addPanel(mGeometryButton, mListGeometry, 2); 224 mPanelController.addComponent(mGeometryButton, findViewById(R.id.straightenButton)); 225 mPanelController.addComponent(mGeometryButton, findViewById(R.id.cropButton)); 226 mPanelController.addComponent(mGeometryButton, findViewById(R.id.rotateButton)); 227 mPanelController.addComponent(mGeometryButton, findViewById(R.id.flipButton)); 228 229 mPanelController.addPanel(mColorsButton, mListColors, 3); 230 231 int[] recastIDs = { 232 R.id.vignetteButton, 233 R.id.vibranceButton, 234 R.id.contrastButton, 235 R.id.saturationButton, 236 R.id.wbalanceButton, 237 R.id.hueButton, 238 R.id.exposureButton, 239 R.id.shadowRecoveryButton 240 }; 241 ImageFilter[] filters = { 242 new ImageFilterVignette(), 243 new ImageFilterVibrance(), 244 new ImageFilterContrast(), 245 new ImageFilterSaturated(), 246 new ImageFilterWBalance(), 247 new ImageFilterHue(), 248 new ImageFilterExposure(), 249 new ImageFilterShadows() 250 }; 251 252 for (int i = 0; i < filters.length; i++) { 253 254 ImageSmallFilter fView = new ImageSmallFilter(this); 255 View v = listColors.findViewById(recastIDs[i]); 256 int pos = listColors.indexOfChild(v); 257 listColors.removeView(v); 258 259 filters[i].setParameter(100); 260 if(v instanceof ImageButtonTitle) 261 filters[i].setName(((ImageButtonTitle) v).getText()); 262 fView.setImageFilter(filters[i]); 263 fView.setController(this); 264 fView.setImageLoader(mImageLoader); 265 fView.setId(recastIDs[i]); 266 mPanelController.addComponent(mColorsButton, fView); 267 listColors.addView(fView, pos); 268 } 269 270 int[] overlayIDs = { 271 R.id.sharpenButton, 272 R.id.curvesButtonRGB 273 }; 274 int[] overlayBitmaps = { 275 R.drawable.filtershow_button_colors_sharpen, 276 R.drawable.filtershow_button_colors_curve 277 }; 278 int []overlayNames = { 279 R.string.sharpness, 280 R.string.curvesRGB 281 }; 282 283 for (int i = 0; i < overlayIDs.length; i++) { 284 ImageWithIcon fView = new ImageWithIcon(this); 285 View v = listColors.findViewById(overlayIDs[i]); 286 int pos = listColors.indexOfChild(v); 287 listColors.removeView(v); 288 final int sid = overlayNames[i]; 289 ImageFilterExposure efilter = new ImageFilterExposure() { 290 { 291 mName = getString(sid); 292 } 293 }; 294 efilter.setParameter(-300); 295 Bitmap bitmap = BitmapFactory.decodeResource(getResources(), 296 overlayBitmaps[i]); 297 298 fView.setIcon(bitmap); 299 fView.setImageFilter(efilter); 300 fView.setController(this); 301 fView.setImageLoader(mImageLoader); 302 fView.setId(overlayIDs[i]); 303 mPanelController.addComponent(mColorsButton, fView); 304 listColors.addView(fView, pos); 305 } 306 307 mPanelController.addComponent(mColorsButton, findViewById(R.id.curvesButtonRGB)); 308 mPanelController.addComponent(mColorsButton, findViewById(R.id.sharpenButton)); 309 mPanelController.addComponent(mColorsButton, findViewById(R.id.vibranceButton)); 310 mPanelController.addComponent(mColorsButton, findViewById(R.id.contrastButton)); 311 mPanelController.addComponent(mColorsButton, findViewById(R.id.saturationButton)); 312 mPanelController.addComponent(mColorsButton, findViewById(R.id.wbalanceButton)); 313 mPanelController.addComponent(mColorsButton, findViewById(R.id.hueButton)); 314 mPanelController.addComponent(mColorsButton, findViewById(R.id.exposureButton)); 315 mPanelController.addComponent(mColorsButton, findViewById(R.id.shadowRecoveryButton)); 316 317 mPanelController.addView(findViewById(R.id.applyEffect)); 318 mPanelController.addView(findViewById(R.id.pickCurvesChannel)); 319 mPanelController.addView(findViewById(R.id.aspect)); 320 findViewById(R.id.resetOperationsButton).setOnClickListener( 321 createOnClickResetOperationsButton()); 322 323 ListView operationsList = (ListView) findViewById(R.id.operationsList); 324 operationsList.setAdapter(mImageShow.getHistoryAdapter()); 325 operationsList.setOnItemClickListener(this); 326 ListView imageStateList = (ListView) findViewById(R.id.imageStateList); 327 imageStateList.setAdapter(mImageShow.getImageStateAdapter()); 328 mImageLoader.setAdapter((HistoryAdapter) mImageShow.getHistoryAdapter()); 329 330 fillListImages(listFilters); 331 fillListBorders(listBorders); 332 333 SeekBar seekBar = (SeekBar) findViewById(R.id.filterSeekBar); 334 seekBar.setMax(SEEK_BAR_MAX); 335 336 mImageShow.setSeekBar(seekBar); 337 mImageZoom.setSeekBar(seekBar); 338 mPanelController.setRowPanel(findViewById(R.id.secondRowPanel)); 339 mPanelController.setUtilityPanel(this, findViewById(R.id.filterButtonsList), 340 findViewById(R.id.applyEffect), findViewById(R.id.aspect)); 341 mPanelController.setMasterImage(mImageShow); 342 mPanelController.setCurrentPanel(mFxButton); 343 Intent intent = getIntent(); 344 String data = intent.getDataString(); 345 if (data != null) { 346 Uri uri = Uri.parse(data); 347 mImageLoader.loadBitmap(uri, getScreenImageSize()); 348 } else { 349 pickImage(); 350 } 351 352 String action = intent.getAction(); 353 if (action == CROP_ACTION){ 354 mPanelController.showComponent(findViewById(R.id.cropButton)); 355 } 356 357 } 358 359 private int getScreenImageSize() { 360 DisplayMetrics metrics = new DisplayMetrics(); 361 Display display = getWindowManager().getDefaultDisplay(); 362 Point size = new Point(); 363 display.getSize(size); 364 display.getMetrics(metrics); 365 int msize = Math.min(size.x, size.y); 366 return (133 * msize) / metrics.densityDpi; 367 } 368 369 private void showSavingProgress(String albumName) { 370 ProgressDialog progress; 371 if (mSavingProgressDialog != null) { 372 progress = mSavingProgressDialog.get(); 373 if (progress != null) { 374 progress.show(); 375 return; 376 } 377 } 378 // TODO: Allow cancellation of the saving process 379 String progressText; 380 if (albumName == null) { 381 progressText = getString(R.string.saving_image); 382 } else { 383 progressText = getString(R.string.filtershow_saving_image, albumName); 384 } 385 progress = ProgressDialog.show(this, "", progressText, true, false); 386 mSavingProgressDialog = new WeakReference<ProgressDialog>(progress); 387 } 388 389 private void hideSavingProgress() { 390 if (mSavingProgressDialog != null) { 391 ProgressDialog progress = mSavingProgressDialog.get(); 392 if (progress != null) 393 progress.dismiss(); 394 } 395 } 396 397 public void completeSaveImage(Uri saveUri) { 398 if (mSharingImage && mSharedOutputFile != null) { 399 // Image saved, we unblock the content provider 400 Uri uri = Uri.withAppendedPath(SharedImageProvider.CONTENT_URI, 401 Uri.encode(mSharedOutputFile.getAbsolutePath())); 402 ContentValues values = new ContentValues(); 403 values.put(SharedImageProvider.PREPARE, false); 404 getContentResolver().insert(uri, values); 405 } 406 setResult(RESULT_OK, new Intent().setData(saveUri)); 407 hideSavingProgress(); 408 finish(); 409 } 410 411 @Override 412 public boolean onShareTargetSelected(ShareActionProvider arg0, Intent arg1) { 413 // First, let's tell the SharedImageProvider that it will need to wait 414 // for the image 415 Uri uri = Uri.withAppendedPath(SharedImageProvider.CONTENT_URI, 416 Uri.encode(mSharedOutputFile.getAbsolutePath())); 417 ContentValues values = new ContentValues(); 418 values.put(SharedImageProvider.PREPARE, true); 419 getContentResolver().insert(uri, values); 420 mSharingImage = true; 421 422 // Process and save the image in the background. 423 showSavingProgress(null); 424 mImageShow.saveImage(this, mSharedOutputFile); 425 return true; 426 } 427 428 private Intent getDefaultShareIntent() { 429 Intent intent = new Intent(Intent.ACTION_SEND); 430 intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_WHEN_TASK_RESET); 431 intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION); 432 intent.setType(SharedImageProvider.MIME_TYPE); 433 mSharedOutputFile = SaveCopyTask.getNewFile(this, mImageLoader.getUri()); 434 Uri uri = Uri.withAppendedPath(SharedImageProvider.CONTENT_URI, 435 Uri.encode(mSharedOutputFile.getAbsolutePath())); 436 intent.putExtra(Intent.EXTRA_STREAM, uri); 437 return intent; 438 } 439 440 @Override 441 public boolean onCreateOptionsMenu(Menu menu) { 442 getMenuInflater().inflate(R.menu.filtershow_activity_menu, menu); 443 MenuItem showHistory = menu.findItem(R.id.operationsButton); 444 if (mShowingHistoryPanel) { 445 showHistory.setTitle(R.string.hide_history_panel); 446 } else { 447 showHistory.setTitle(R.string.show_history_panel); 448 } 449 MenuItem showState = menu.findItem(R.id.showImageStateButton); 450 if (mShowingImageStatePanel) { 451 showState.setTitle(R.string.hide_imagestate_panel); 452 } else { 453 showState.setTitle(R.string.show_imagestate_panel); 454 } 455 mShareActionProvider = (ShareActionProvider) menu.findItem(R.id.menu_share) 456 .getActionProvider(); 457 mShareActionProvider.setShareIntent(getDefaultShareIntent()); 458 mShareActionProvider.setOnShareTargetSelectedListener(this); 459 return true; 460 } 461 462 @Override 463 public void onPause() { 464 super.onPause(); 465 if (mShareActionProvider != null) { 466 mShareActionProvider.setOnShareTargetSelectedListener(null); 467 } 468 } 469 470 @Override 471 public void onResume() { 472 super.onResume(); 473 if (mShareActionProvider != null) { 474 mShareActionProvider.setOnShareTargetSelectedListener(this); 475 } 476 } 477 478 @Override 479 public boolean onOptionsItemSelected(MenuItem item) { 480 switch (item.getItemId()) { 481 case R.id.undoButton: { 482 HistoryAdapter adapter = (HistoryAdapter) mImageShow 483 .getHistoryAdapter(); 484 int position = adapter.undo(); 485 mImageShow.onItemClick(position); 486 mImageShow.showToast("Undo"); 487 invalidateViews(); 488 return true; 489 } 490 case R.id.redoButton: { 491 HistoryAdapter adapter = (HistoryAdapter) mImageShow 492 .getHistoryAdapter(); 493 int position = adapter.redo(); 494 mImageShow.onItemClick(position); 495 mImageShow.showToast("Redo"); 496 invalidateViews(); 497 return true; 498 } 499 case R.id.resetHistoryButton: { 500 resetHistory(); 501 return true; 502 } 503 case R.id.showImageStateButton: { 504 toggleImageStatePanel(); 505 return true; 506 } 507 case R.id.operationsButton: { 508 toggleHistoryPanel(); 509 return true; 510 } 511 case android.R.id.home: { 512 saveImage(); 513 return true; 514 } 515 } 516 return false; 517 } 518 519 private void fillListImages(LinearLayout listFilters) { 520 // TODO: use listview 521 // TODO: load the filters straight from the filesystem 522 523 ImageFilterFx[] fxArray = new ImageFilterFx[18]; 524 int p = 0; 525 526 int[] drawid = { 527 R.drawable.filtershow_fx_0005_punch, 528 R.drawable.filtershow_fx_0000_vintage, 529 R.drawable.filtershow_fx_0004_bw_contrast, 530 R.drawable.filtershow_fx_0002_bleach, 531 R.drawable.filtershow_fx_0001_instant, 532 R.drawable.filtershow_fx_0007_washout, 533 R.drawable.filtershow_fx_0003_blue_crush, 534 R.drawable.filtershow_fx_0008_washout_color, 535 R.drawable.filtershow_fx_0006_x_process 536 }; 537 538 int[] fxNameid = { 539 R.string.ffx_punch, 540 R.string.ffx_vintage, 541 R.string.ffx_bw_contrast, 542 R.string.ffx_bleach, 543 R.string.ffx_instant, 544 R.string.ffx_washout, 545 R.string.ffx_blue_crush, 546 R.string.ffx_washout_color, 547 R.string.ffx_x_process 548 }; 549 550 ImagePreset preset = new ImagePreset(); // empty 551 ImageSmallFilter filter = new ImageSmallFilter(this); 552 553 filter.setSelected(true); 554 mCurrentImageSmallFilter = filter; 555 556 filter.setImageFilter(new ImageFilterFx(null,getString(R.string.none))); 557 558 filter.setController(this); 559 filter.setImageLoader(mImageLoader); 560 listFilters.addView(filter); 561 ImageSmallFilter previousFilter = filter; 562 563 BitmapFactory.Options o = new BitmapFactory.Options(); 564 o.inScaled = false; 565 566 for (int i = 0; i < drawid.length; i++) { 567 Bitmap b = BitmapFactory.decodeResource(getResources(), drawid[i], o); 568 fxArray[p++] = new ImageFilterFx(b, getString(fxNameid[i])); 569 } 570 571 for (int i = 0; i < p; i++) { 572 filter = new ImageSmallFilter(this); 573 filter.setImageFilter(fxArray[i]); 574 filter.setController(this); 575 filter.setImageLoader(mImageLoader); 576 listFilters.addView(filter); 577 previousFilter = filter; 578 } 579 580 // Default preset (original) 581 mImageShow.setImagePreset(preset); 582 } 583 584 private void fillListBorders(LinearLayout listBorders) { 585 // TODO: use listview 586 // TODO: load the borders straight from the filesystem 587 int p = 0; 588 ImageFilter[] borders = new ImageFilter[7]; 589 borders[p++] = new ImageFilterBorder(null); 590 591 Drawable npd1 = getResources().getDrawable(R.drawable.filtershow_border_4x5); 592 borders[p++] = new ImageFilterBorder(npd1); 593 Drawable npd2 = getResources().getDrawable(R.drawable.filtershow_border_brush); 594 borders[p++] = new ImageFilterBorder(npd2); 595 borders[p++] = new ImageFilterParametricBorder(Color.BLACK, mImageBorderSize, 0); 596 borders[p++] = new ImageFilterParametricBorder(Color.BLACK, mImageBorderSize, 597 mImageBorderSize); 598 borders[p++] = new ImageFilterParametricBorder(Color.WHITE, mImageBorderSize, 0); 599 borders[p++] = new ImageFilterParametricBorder(Color.WHITE, mImageBorderSize, 600 mImageBorderSize); 601 602 ImageSmallFilter previousFilter = null; 603 for (int i = 0; i < p; i++) { 604 ImageSmallBorder filter = new ImageSmallBorder(this); 605 filter.setImageFilter(borders[i]); 606 filter.setController(this); 607 filter.setBorder(true); 608 filter.setImageLoader(mImageLoader); 609 filter.setShowTitle(false); 610 listBorders.addView(filter); 611 previousFilter = filter; 612 } 613 } 614 615 // ////////////////////////////////////////////////////////////////////////////// 616 // Some utility functions 617 // TODO: finish the cleanup. 618 619 public void showOriginalViews(boolean value) { 620 for (ImageShow views : mImageViews) { 621 views.showOriginal(value); 622 } 623 } 624 625 public void invalidateViews() { 626 for (ImageShow views : mImageViews) { 627 views.invalidate(); 628 views.updateImage(); 629 } 630 } 631 632 public void hideListViews() { 633 for (View view : mListViews) { 634 view.setVisibility(View.GONE); 635 } 636 } 637 638 public void hideImageViews() { 639 mImageShow.setShowControls(false); // reset 640 for (View view : mImageViews) { 641 view.setVisibility(View.GONE); 642 } 643 } 644 645 public void unselectBottomPanelButtons() { 646 for (ImageButton button : mBottomPanelButtons) { 647 button.setSelected(false); 648 } 649 } 650 651 public void unselectPanelButtons(Vector<ImageButton> buttons) { 652 for (ImageButton button : buttons) { 653 button.setSelected(false); 654 } 655 } 656 657 // ////////////////////////////////////////////////////////////////////////////// 658 // imageState panel... 659 660 private void toggleImageStatePanel() { 661 final View view = findViewById(R.id.mainPanel); 662 final View viewList = findViewById(R.id.imageStatePanel); 663 664 if (mShowingHistoryPanel) { 665 findViewById(R.id.historyPanel).setVisibility(View.INVISIBLE); 666 mShowingHistoryPanel = false; 667 } 668 669 if (!mShowingImageStatePanel) { 670 mShowingImageStatePanel = true; 671 view.animate().setDuration(200).x(-viewList.getWidth()) 672 .withLayer().withEndAction(new Runnable() { 673 @Override 674 public void run() { 675 viewList.setAlpha(0); 676 viewList.setVisibility(View.VISIBLE); 677 viewList.animate().setDuration(100) 678 .alpha(1.0f).start(); 679 } 680 }).start(); 681 } else { 682 mShowingImageStatePanel = false; 683 viewList.setVisibility(View.INVISIBLE); 684 view.animate().setDuration(200).x(0).withLayer() 685 .start(); 686 } 687 invalidateOptionsMenu(); 688 } 689 690 // ////////////////////////////////////////////////////////////////////////////// 691 // history panel... 692 693 private void toggleHistoryPanel() { 694 final View view = findViewById(R.id.mainPanel); 695 final View viewList = findViewById(R.id.historyPanel); 696 697 if (mShowingImageStatePanel) { 698 findViewById(R.id.imageStatePanel).setVisibility(View.INVISIBLE); 699 mShowingImageStatePanel = false; 700 } 701 702 if (!mShowingHistoryPanel) { 703 mShowingHistoryPanel = true; 704 view.animate().setDuration(200).x(-viewList.getWidth()) 705 .withLayer().withEndAction(new Runnable() { 706 @Override 707 public void run() { 708 viewList.setAlpha(0); 709 viewList.setVisibility(View.VISIBLE); 710 viewList.animate().setDuration(100) 711 .alpha(1.0f).start(); 712 } 713 }).start(); 714 } else { 715 mShowingHistoryPanel = false; 716 viewList.setVisibility(View.INVISIBLE); 717 view.animate().setDuration(200).x(0).withLayer() 718 .start(); 719 } 720 invalidateOptionsMenu(); 721 } 722 723 private void resetHistory() { 724 HistoryAdapter adapter = (HistoryAdapter) mImageShow 725 .getHistoryAdapter(); 726 adapter.reset(); 727 ImagePreset original = new ImagePreset(adapter.getItem(0)); 728 mImageShow.setImagePreset(original); 729 mPanelController.resetParameters(); 730 invalidateViews(); 731 } 732 733 // reset button in the history panel. 734 private OnClickListener createOnClickResetOperationsButton() { 735 return new View.OnClickListener() { 736 @Override 737 public void onClick(View v) { 738 resetHistory(); 739 } 740 }; 741 } 742 743 @Override 744 public void onBackPressed() { 745 if (mPanelController.onBackPressed()) { 746 saveImage(); 747 } 748 } 749 750 public void cannotLoadImage() { 751 CharSequence text = getString(R.string.cannot_load_image); 752 Toast toast = Toast.makeText(this, text, Toast.LENGTH_SHORT); 753 toast.show(); 754 finish(); 755 } 756 757 // ////////////////////////////////////////////////////////////////////////////// 758 759 public float getPixelsFromDip(float value) { 760 Resources r = getResources(); 761 return TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, value, 762 r.getDisplayMetrics()); 763 } 764 765 public void useImagePreset(ImageSmallFilter imageSmallFilter, ImagePreset preset) { 766 if (preset == null) { 767 return; 768 } 769 770 if (mCurrentImageSmallFilter != null) { 771 mCurrentImageSmallFilter.setSelected(false); 772 } 773 mCurrentImageSmallFilter = imageSmallFilter; 774 mCurrentImageSmallFilter.setSelected(true); 775 776 ImagePreset copy = new ImagePreset(preset); 777 mImageShow.setImagePreset(copy); 778 if (preset.isFx()) { 779 // if it's an FX we rest the curve adjustment too 780 mImageCurves.resetCurve(); 781 } 782 invalidateViews(); 783 } 784 785 public void useImageFilter(ImageSmallFilter imageSmallFilter, ImageFilter imageFilter, 786 boolean setBorder) { 787 if (imageFilter == null) { 788 return; 789 } 790 791 if (mCurrentImageSmallFilter != null) { 792 mCurrentImageSmallFilter.setSelected(false); 793 } 794 mCurrentImageSmallFilter = imageSmallFilter; 795 mCurrentImageSmallFilter.setSelected(true); 796 797 ImagePreset oldPreset = mImageShow.getImagePreset(); 798 ImagePreset copy = new ImagePreset(oldPreset); 799 // TODO: use a numerical constant instead. 800 801 copy.add(imageFilter); 802 803 mImageShow.setImagePreset(copy); 804 invalidateViews(); 805 } 806 807 @Override 808 public void onItemClick(AdapterView<?> parent, View view, int position, 809 long id) { 810 mImageShow.onItemClick(position); 811 invalidateViews(); 812 } 813 814 public void pickImage() { 815 Intent intent = new Intent(); 816 intent.setType("image/*"); 817 intent.setAction(Intent.ACTION_GET_CONTENT); 818 startActivityForResult(Intent.createChooser(intent, getString(R.string.select_image)), 819 SELECT_PICTURE); 820 } 821 822 @Override 823 public void onActivityResult(int requestCode, int resultCode, Intent data) { 824 Log.v(LOGTAG, "onActivityResult"); 825 if (resultCode == RESULT_OK) { 826 if (requestCode == SELECT_PICTURE) { 827 Uri selectedImageUri = data.getData(); 828 mImageLoader.loadBitmap(selectedImageUri, getScreenImageSize()); 829 } 830 } 831 } 832 833 public void saveImage() { 834 if (mImageShow.hasModifications()) { 835 // Get the name of the album, to which the image will be saved 836 File saveDir = SaveCopyTask.getFinalSaveDirectory(this, mImageLoader.getUri()); 837 int bucketId = GalleryUtils.getBucketId(saveDir.getPath()); 838 String albumName = LocalAlbum.getLocalizedName(getResources(), bucketId, null); 839 showSavingProgress(albumName); 840 mImageShow.saveImage(this, null); 841 } else { 842 finish(); 843 } 844 } 845 846 static { 847 System.loadLibrary("jni_filtershow_filters"); 848 } 849 850} 851