summaryrefslogtreecommitdiffstats
path: root/src/com/android/gallery3d
diff options
context:
space:
mode:
authorSascha Haeberling <haeberling@google.com>2013-08-06 11:43:02 -0700
committerSascha Haeberling <haeberling@google.com>2013-08-06 11:43:02 -0700
commit8e963a5a6016d246184ed65906f9d103e92b17e2 (patch)
tree02eb244ea4a20d9aa8e43916a40b876be8935d11 /src/com/android/gallery3d
parent4fc90b07dcf316c7ce6c5313af8202e84bc85603 (diff)
downloadandroid_packages_apps_Snap-8e963a5a6016d246184ed65906f9d103e92b17e2.tar.gz
android_packages_apps_Snap-8e963a5a6016d246184ed65906f9d103e92b17e2.tar.bz2
android_packages_apps_Snap-8e963a5a6016d246184ed65906f9d103e92b17e2.zip
This removes all non-Camera stuff from Camera2.
Note: Camera2 is a clone of Gallery2 right now. Note 2: I will bring .mk files back later. Change-Id: Ida958654296f5ebaacb6bb0ff59d52a7c37ce6fc
Diffstat (limited to 'src/com/android/gallery3d')
-rw-r--r--src/com/android/gallery3d/anim/AlphaAnimation.java48
-rw-r--r--src/com/android/gallery3d/anim/Animation.java92
-rw-r--r--src/com/android/gallery3d/anim/CanvasAnimation.java25
-rw-r--r--src/com/android/gallery3d/anim/FloatAnimation.java40
-rw-r--r--src/com/android/gallery3d/anim/StateTransitionAnimation.java180
-rw-r--r--src/com/android/gallery3d/app/AbstractGalleryActivity.java343
-rw-r--r--src/com/android/gallery3d/app/ActivityState.java276
-rw-r--r--src/com/android/gallery3d/app/AlbumDataLoader.java397
-rw-r--r--src/com/android/gallery3d/app/AlbumPage.java786
-rw-r--r--src/com/android/gallery3d/app/AlbumPicker.java40
-rw-r--r--src/com/android/gallery3d/app/AlbumSetDataLoader.java393
-rw-r--r--src/com/android/gallery3d/app/AlbumSetPage.java764
-rw-r--r--src/com/android/gallery3d/app/AppBridge.java72
-rw-r--r--src/com/android/gallery3d/app/BatchService.java48
-rw-r--r--src/com/android/gallery3d/app/CommonControllerOverlay.java346
-rw-r--r--src/com/android/gallery3d/app/Config.java127
-rw-r--r--src/com/android/gallery3d/app/ControllerOverlay.java56
-rw-r--r--src/com/android/gallery3d/app/DialogPicker.java41
-rw-r--r--src/com/android/gallery3d/app/EyePosition.java226
-rw-r--r--src/com/android/gallery3d/app/FilmstripPage.java21
-rw-r--r--src/com/android/gallery3d/app/FilterUtils.java257
-rw-r--r--src/com/android/gallery3d/app/Gallery.java274
-rw-r--r--src/com/android/gallery3d/app/GalleryActionBar.java438
-rw-r--r--src/com/android/gallery3d/app/GalleryApp.java41
-rw-r--r--src/com/android/gallery3d/app/GalleryAppImpl.java127
-rw-r--r--src/com/android/gallery3d/app/GalleryContext.java34
-rw-r--r--src/com/android/gallery3d/app/LoadingListener.java27
-rw-r--r--src/com/android/gallery3d/app/Log.java53
-rw-r--r--src/com/android/gallery3d/app/ManageCachePage.java419
-rw-r--r--src/com/android/gallery3d/app/MovieActivity.java263
-rw-r--r--src/com/android/gallery3d/app/MovieControllerOverlay.java185
-rw-r--r--src/com/android/gallery3d/app/MoviePlayer.java525
-rw-r--r--src/com/android/gallery3d/app/MuteVideo.java104
-rw-r--r--src/com/android/gallery3d/app/NotificationIds.java22
-rw-r--r--src/com/android/gallery3d/app/OrientationManager.java166
-rw-r--r--src/com/android/gallery3d/app/PackagesMonitor.java71
-rw-r--r--src/com/android/gallery3d/app/PanoramaMetadataSupport.java93
-rw-r--r--src/com/android/gallery3d/app/PhotoDataAdapter.java1133
-rw-r--r--src/com/android/gallery3d/app/PhotoPage.java1571
-rw-r--r--src/com/android/gallery3d/app/PhotoPageBottomControls.java137
-rw-r--r--src/com/android/gallery3d/app/PhotoPageProgressBar.java50
-rw-r--r--src/com/android/gallery3d/app/PickerActivity.java83
-rw-r--r--src/com/android/gallery3d/app/SinglePhotoDataAdapter.java263
-rw-r--r--src/com/android/gallery3d/app/SinglePhotoPage.java21
-rw-r--r--src/com/android/gallery3d/app/SlideshowDataAdapter.java204
-rw-r--r--src/com/android/gallery3d/app/SlideshowPage.java366
-rw-r--r--src/com/android/gallery3d/app/StateManager.java339
-rw-r--r--src/com/android/gallery3d/app/StitchingChangeListener.java27
-rw-r--r--src/com/android/gallery3d/app/TimeBar.java266
-rw-r--r--src/com/android/gallery3d/app/TransitionStore.java46
-rw-r--r--src/com/android/gallery3d/app/TrimControllerOverlay.java111
-rw-r--r--src/com/android/gallery3d/app/TrimTimeBar.java339
-rw-r--r--src/com/android/gallery3d/app/TrimVideo.java337
-rw-r--r--src/com/android/gallery3d/app/VideoUtils.java328
-rw-r--r--src/com/android/gallery3d/app/Wallpaper.java135
-rw-r--r--src/com/android/gallery3d/data/ActionImage.java103
-rw-r--r--src/com/android/gallery3d/data/BucketHelper.java241
-rw-r--r--src/com/android/gallery3d/data/BytesBufferPool.java91
-rw-r--r--src/com/android/gallery3d/data/CameraShortcutImage.java34
-rw-r--r--src/com/android/gallery3d/data/ChangeNotifier.java57
-rw-r--r--src/com/android/gallery3d/data/ClusterAlbum.java143
-rw-r--r--src/com/android/gallery3d/data/ClusterAlbumSet.java159
-rw-r--r--src/com/android/gallery3d/data/ClusterSource.java86
-rw-r--r--src/com/android/gallery3d/data/Clustering.java29
-rw-r--r--src/com/android/gallery3d/data/ComboAlbum.java103
-rw-r--r--src/com/android/gallery3d/data/ComboAlbumSet.java96
-rw-r--r--src/com/android/gallery3d/data/ComboSource.java55
-rw-r--r--src/com/android/gallery3d/data/ContentListener.java21
-rw-r--r--src/com/android/gallery3d/data/DataManager.java371
-rw-r--r--src/com/android/gallery3d/data/DataSourceType.java45
-rw-r--r--src/com/android/gallery3d/data/DecodeUtils.java312
-rw-r--r--src/com/android/gallery3d/data/DownloadCache.java370
-rw-r--r--src/com/android/gallery3d/data/DownloadEntry.java72
-rw-r--r--src/com/android/gallery3d/data/DownloadUtils.java79
-rw-r--r--src/com/android/gallery3d/data/EmptyAlbumImage.java34
-rw-r--r--src/com/android/gallery3d/data/Exif.java48
-rw-r--r--src/com/android/gallery3d/data/Face.java65
-rw-r--r--src/com/android/gallery3d/data/FaceClustering.java142
-rw-r--r--src/com/android/gallery3d/data/FilterDeleteSet.java256
-rw-r--r--src/com/android/gallery3d/data/FilterEmptyPromptSet.java82
-rw-r--r--src/com/android/gallery3d/data/FilterSource.java94
-rw-r--r--src/com/android/gallery3d/data/FilterTypeSet.java137
-rw-r--r--src/com/android/gallery3d/data/ImageCacheRequest.java102
-rw-r--r--src/com/android/gallery3d/data/ImageCacheService.java123
-rw-r--r--src/com/android/gallery3d/data/LocalAlbum.java325
-rw-r--r--src/com/android/gallery3d/data/LocalAlbumSet.java211
-rw-r--r--src/com/android/gallery3d/data/LocalImage.java355
-rw-r--r--src/com/android/gallery3d/data/LocalMediaItem.java109
-rw-r--r--src/com/android/gallery3d/data/LocalMergeAlbum.java257
-rw-r--r--src/com/android/gallery3d/data/LocalSource.java275
-rw-r--r--src/com/android/gallery3d/data/LocalVideo.java242
-rw-r--r--src/com/android/gallery3d/data/LocationClustering.java316
-rw-r--r--src/com/android/gallery3d/data/Log.java53
-rw-r--r--src/com/android/gallery3d/data/MediaDetails.java170
-rw-r--r--src/com/android/gallery3d/data/MediaItem.java134
-rw-r--r--src/com/android/gallery3d/data/MediaObject.java166
-rw-r--r--src/com/android/gallery3d/data/MediaSet.java348
-rw-r--r--src/com/android/gallery3d/data/MediaSource.java96
-rw-r--r--src/com/android/gallery3d/data/MtpClient.java443
-rw-r--r--src/com/android/gallery3d/data/PanoramaMetadataJob.java40
-rw-r--r--src/com/android/gallery3d/data/Path.java241
-rw-r--r--src/com/android/gallery3d/data/PathMatcher.java102
-rw-r--r--src/com/android/gallery3d/data/SecureAlbum.java206
-rw-r--r--src/com/android/gallery3d/data/SecureSource.java56
-rw-r--r--src/com/android/gallery3d/data/SingleItemAlbum.java68
-rw-r--r--src/com/android/gallery3d/data/SizeClustering.java141
-rw-r--r--src/com/android/gallery3d/data/SnailAlbum.java44
-rw-r--r--src/com/android/gallery3d/data/SnailItem.java95
-rw-r--r--src/com/android/gallery3d/data/SnailSource.java70
-rw-r--r--src/com/android/gallery3d/data/TagClustering.java95
-rw-r--r--src/com/android/gallery3d/data/TimeClustering.java439
-rw-r--r--src/com/android/gallery3d/data/UnlockImage.java34
-rw-r--r--src/com/android/gallery3d/data/UriImage.java298
-rw-r--r--src/com/android/gallery3d/data/UriSource.java95
-rw-r--r--src/com/android/gallery3d/filtershow/CenteredLinearLayout.java51
-rw-r--r--src/com/android/gallery3d/filtershow/EditorPlaceHolder.java82
-rw-r--r--src/com/android/gallery3d/filtershow/FilterShowActivity.java1121
-rw-r--r--src/com/android/gallery3d/filtershow/cache/ImageLoader.java502
-rw-r--r--src/com/android/gallery3d/filtershow/category/Action.java186
-rw-r--r--src/com/android/gallery3d/filtershow/category/CategoryAdapter.java182
-rw-r--r--src/com/android/gallery3d/filtershow/category/CategoryPanel.java108
-rw-r--r--src/com/android/gallery3d/filtershow/category/CategoryTrack.java77
-rw-r--r--src/com/android/gallery3d/filtershow/category/CategoryView.java176
-rw-r--r--src/com/android/gallery3d/filtershow/category/MainPanel.java239
-rw-r--r--src/com/android/gallery3d/filtershow/colorpicker/ColorGridDialog.java100
-rw-r--r--src/com/android/gallery3d/filtershow/colorpicker/ColorListener.java21
-rw-r--r--src/com/android/gallery3d/filtershow/colorpicker/ColorOpacityView.java197
-rw-r--r--src/com/android/gallery3d/filtershow/colorpicker/ColorPickerDialog.java123
-rw-r--r--src/com/android/gallery3d/filtershow/colorpicker/ColorRectView.java225
-rw-r--r--src/com/android/gallery3d/filtershow/colorpicker/ColorValueView.java180
-rw-r--r--src/com/android/gallery3d/filtershow/colorpicker/RGBListener.java21
-rw-r--r--src/com/android/gallery3d/filtershow/controller/ActionSlider.java71
-rw-r--r--src/com/android/gallery3d/filtershow/controller/BasicParameterInt.java113
-rw-r--r--src/com/android/gallery3d/filtershow/controller/BasicParameterStyle.java111
-rw-r--r--src/com/android/gallery3d/filtershow/controller/BasicSlider.java87
-rw-r--r--src/com/android/gallery3d/filtershow/controller/Control.java32
-rw-r--r--src/com/android/gallery3d/filtershow/controller/FilterView.java25
-rw-r--r--src/com/android/gallery3d/filtershow/controller/Parameter.java33
-rw-r--r--src/com/android/gallery3d/filtershow/controller/ParameterActionAndInt.java29
-rw-r--r--src/com/android/gallery3d/filtershow/controller/ParameterInteger.java31
-rw-r--r--src/com/android/gallery3d/filtershow/controller/ParameterSet.java23
-rw-r--r--src/com/android/gallery3d/filtershow/controller/ParameterStyles.java37
-rw-r--r--src/com/android/gallery3d/filtershow/controller/StyleChooser.java88
-rw-r--r--src/com/android/gallery3d/filtershow/controller/TitledSlider.java106
-rw-r--r--src/com/android/gallery3d/filtershow/crop/BoundedRect.java368
-rw-r--r--src/com/android/gallery3d/filtershow/crop/CropActivity.java697
-rw-r--r--src/com/android/gallery3d/filtershow/crop/CropDrawingUtils.java168
-rw-r--r--src/com/android/gallery3d/filtershow/crop/CropExtras.java121
-rw-r--r--src/com/android/gallery3d/filtershow/crop/CropMath.java260
-rw-r--r--src/com/android/gallery3d/filtershow/crop/CropObject.java330
-rw-r--r--src/com/android/gallery3d/filtershow/crop/CropView.java378
-rw-r--r--src/com/android/gallery3d/filtershow/data/FilterStackDBHelper.java101
-rw-r--r--src/com/android/gallery3d/filtershow/data/FilterStackSource.java197
-rw-r--r--src/com/android/gallery3d/filtershow/data/UserPresetsManager.java149
-rw-r--r--src/com/android/gallery3d/filtershow/editors/BasicEditor.java138
-rw-r--r--src/com/android/gallery3d/filtershow/editors/Editor.java330
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorChanSat.java227
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorCrop.java168
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorCurves.java56
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorDraw.java158
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorGrad.java315
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorInfo.java23
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorMirror.java109
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorPanel.java143
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorRedEye.java65
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorRotate.java112
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorStraighten.java103
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorTinyPlanet.java58
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorVignette.java53
-rw-r--r--src/com/android/gallery3d/filtershow/editors/EditorZoom.java27
-rw-r--r--src/com/android/gallery3d/filtershow/editors/ImageOnlyEditor.java50
-rw-r--r--src/com/android/gallery3d/filtershow/editors/ParametricEditor.java206
-rw-r--r--src/com/android/gallery3d/filtershow/editors/SwapButton.java111
-rw-r--r--src/com/android/gallery3d/filtershow/filters/BaseFiltersManager.java296
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ColorSpaceMatrix.java225
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterBasicRepresentation.java196
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterChanSatRepresentation.java211
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterColorBorderRepresentation.java113
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterCropRepresentation.java179
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterCurvesRepresentation.java170
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterDirectRepresentation.java38
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterDrawRepresentation.java171
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterFxRepresentation.java112
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterGradRepresentation.java497
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterImageBorderRepresentation.java91
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterMirrorRepresentation.java190
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterPoint.java21
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterPointRepresentation.java88
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterRedEyeRepresentation.java67
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterRepresentation.java262
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterRotateRepresentation.java190
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterStraightenRepresentation.java154
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterTinyPlanetRepresentation.java101
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterUserPresetRepresentation.java53
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FilterVignetteRepresentation.java173
-rw-r--r--src/com/android/gallery3d/filtershow/filters/FiltersManagerInterface.java21
-rw-r--r--src/com/android/gallery3d/filtershow/filters/IconUtilities.java75
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilter.java109
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterBorder.java92
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterBwFilter.java64
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterChanSat.java161
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterContrast.java58
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterCurves.java112
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterDownsample.java83
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterDraw.java278
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterEdge.java53
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterExposure.java56
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterFx.java111
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterGrad.java190
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterHighlights.java74
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterHue.java64
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterKMeans.java95
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterNegative.java39
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterParametricBorder.java69
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterRS.java260
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterRedEye.java79
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterSaturated.java58
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterShadows.java58
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterSharpen.java107
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterTinyPlanet.java158
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterVibrance.java57
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterVignette.java98
-rw-r--r--src/com/android/gallery3d/filtershow/filters/ImageFilterWBalance.java59
-rw-r--r--src/com/android/gallery3d/filtershow/filters/RedEyeCandidate.java50
-rw-r--r--src/com/android/gallery3d/filtershow/filters/SimpleImageFilter.java37
-rw-r--r--src/com/android/gallery3d/filtershow/filters/SplineMath.java166
-rw-r--r--src/com/android/gallery3d/filtershow/filters/convolve3x3.rs67
-rw-r--r--src/com/android/gallery3d/filtershow/filters/grad.rs121
-rw-r--r--src/com/android/gallery3d/filtershow/filters/grey.rs22
-rw-r--r--src/com/android/gallery3d/filtershow/filters/saturation.rs161
-rw-r--r--src/com/android/gallery3d/filtershow/history/HistoryItem.java53
-rw-r--r--src/com/android/gallery3d/filtershow/history/HistoryManager.java172
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/ControlPoint.java64
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/EclipseControl.java302
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/GeometryMathUtils.java416
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/GradControl.java274
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/ImageCrop.java307
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/ImageCurves.java445
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/ImageDraw.java139
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/ImageGrad.java215
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/ImageMirror.java78
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/ImagePoint.java89
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/ImageRedEye.java137
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/ImageRotate.java81
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/ImageShow.java578
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/ImageStraighten.java260
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/ImageTinyPlanet.java174
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/ImageVignette.java165
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/Line.java26
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/MasterImage.java581
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/Oval.java29
-rw-r--r--src/com/android/gallery3d/filtershow/imageshow/Spline.java450
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/Buffer.java74
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/CacheProcessing.java193
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/CachingPipeline.java469
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/FilterEnvironment.java178
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/HighresRenderingRequestTask.java90
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/ImagePreset.java694
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/ImageSavingTask.java125
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/PipelineInterface.java31
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/ProcessingService.java283
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/ProcessingTask.java88
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/ProcessingTaskController.java97
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/RenderingRequest.java174
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/RenderingRequestCaller.java21
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/RenderingRequestTask.java81
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/SharedBuffer.java77
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/SharedPreset.java42
-rw-r--r--src/com/android/gallery3d/filtershow/pipeline/UpdatePreviewTask.java79
-rw-r--r--src/com/android/gallery3d/filtershow/presets/PresetManagementDialog.java69
-rw-r--r--src/com/android/gallery3d/filtershow/presets/UserPresetsAdapter.java171
-rw-r--r--src/com/android/gallery3d/filtershow/provider/SharedImageProvider.java137
-rw-r--r--src/com/android/gallery3d/filtershow/state/DragListener.java110
-rw-r--r--src/com/android/gallery3d/filtershow/state/PanelTrack.java37
-rw-r--r--src/com/android/gallery3d/filtershow/state/State.java78
-rw-r--r--src/com/android/gallery3d/filtershow/state/StateAdapter.java115
-rw-r--r--src/com/android/gallery3d/filtershow/state/StatePanel.java44
-rw-r--r--src/com/android/gallery3d/filtershow/state/StatePanelTrack.java351
-rw-r--r--src/com/android/gallery3d/filtershow/state/StateView.java291
-rw-r--r--src/com/android/gallery3d/filtershow/tools/IconFactory.java108
-rw-r--r--src/com/android/gallery3d/filtershow/tools/MatrixFit.java200
-rw-r--r--src/com/android/gallery3d/filtershow/tools/SaveImage.java632
-rw-r--r--src/com/android/gallery3d/filtershow/tools/XmpPresets.java133
-rw-r--r--src/com/android/gallery3d/filtershow/ui/ExportDialog.java90
-rw-r--r--src/com/android/gallery3d/filtershow/ui/FramedTextButton.java137
-rw-r--r--src/com/android/gallery3d/filtershow/ui/SelectionRenderer.java48
-rw-r--r--src/com/android/gallery3d/gadget/LocalPhotoSource.java205
-rw-r--r--src/com/android/gallery3d/gadget/MediaSetSource.java233
-rw-r--r--src/com/android/gallery3d/gadget/PhotoAppWidgetProvider.java139
-rw-r--r--src/com/android/gallery3d/gadget/WidgetClickHandler.java77
-rw-r--r--src/com/android/gallery3d/gadget/WidgetConfigure.java209
-rw-r--r--src/com/android/gallery3d/gadget/WidgetDatabaseHelper.java309
-rw-r--r--src/com/android/gallery3d/gadget/WidgetService.java143
-rw-r--r--src/com/android/gallery3d/gadget/WidgetSource.java31
-rw-r--r--src/com/android/gallery3d/gadget/WidgetTypeChooser.java59
-rw-r--r--src/com/android/gallery3d/gadget/WidgetUtils.java80
-rw-r--r--src/com/android/gallery3d/glrenderer/BasicTexture.java212
-rw-r--r--src/com/android/gallery3d/glrenderer/BitmapTexture.java54
-rw-r--r--src/com/android/gallery3d/glrenderer/CanvasTexture.java52
-rw-r--r--src/com/android/gallery3d/glrenderer/ColorTexture.java63
-rw-r--r--src/com/android/gallery3d/glrenderer/ExtTexture.java60
-rw-r--r--src/com/android/gallery3d/glrenderer/FadeInTexture.java43
-rw-r--r--src/com/android/gallery3d/glrenderer/FadeOutTexture.java42
-rw-r--r--src/com/android/gallery3d/glrenderer/FadeTexture.java81
-rw-r--r--src/com/android/gallery3d/glrenderer/GLCanvas.java217
-rw-r--r--src/com/android/gallery3d/glrenderer/GLES11Canvas.java997
-rw-r--r--src/com/android/gallery3d/glrenderer/GLES11IdImpl.java68
-rw-r--r--src/com/android/gallery3d/glrenderer/GLES20Canvas.java1009
-rw-r--r--src/com/android/gallery3d/glrenderer/GLES20IdImpl.java42
-rw-r--r--src/com/android/gallery3d/glrenderer/GLId.java33
-rw-r--r--src/com/android/gallery3d/glrenderer/GLPaint.java41
-rw-r--r--src/com/android/gallery3d/glrenderer/MultiLineTexture.java52
-rw-r--r--src/com/android/gallery3d/glrenderer/NinePatchChunk.java82
-rw-r--r--src/com/android/gallery3d/glrenderer/NinePatchTexture.java424
-rw-r--r--src/com/android/gallery3d/glrenderer/RawTexture.java73
-rw-r--r--src/com/android/gallery3d/glrenderer/ResourceTexture.java53
-rw-r--r--src/com/android/gallery3d/glrenderer/StringTexture.java88
-rw-r--r--src/com/android/gallery3d/glrenderer/Texture.java44
-rw-r--r--src/com/android/gallery3d/glrenderer/TextureUploader.java105
-rw-r--r--src/com/android/gallery3d/glrenderer/TiledTexture.java349
-rw-r--r--src/com/android/gallery3d/glrenderer/UploadedTexture.java298
-rw-r--r--src/com/android/gallery3d/ingest/ImportTask.java95
-rw-r--r--src/com/android/gallery3d/ingest/IngestActivity.java570
-rw-r--r--src/com/android/gallery3d/ingest/IngestService.java320
-rw-r--r--src/com/android/gallery3d/ingest/MtpDeviceIndex.java596
-rw-r--r--src/com/android/gallery3d/ingest/SimpleDate.java114
-rw-r--r--src/com/android/gallery3d/ingest/adapter/CheckBroker.java56
-rw-r--r--src/com/android/gallery3d/ingest/adapter/MtpAdapter.java192
-rw-r--r--src/com/android/gallery3d/ingest/adapter/MtpPagerAdapter.java102
-rw-r--r--src/com/android/gallery3d/ingest/data/BitmapWithMetadata.java29
-rw-r--r--src/com/android/gallery3d/ingest/data/MtpBitmapFetch.java106
-rw-r--r--src/com/android/gallery3d/ingest/ui/DateTileView.java107
-rw-r--r--src/com/android/gallery3d/ingest/ui/IngestGridView.java58
-rw-r--r--src/com/android/gallery3d/ingest/ui/MtpFullscreenView.java115
-rw-r--r--src/com/android/gallery3d/ingest/ui/MtpImageView.java280
-rw-r--r--src/com/android/gallery3d/ingest/ui/MtpThumbnailTileView.java106
-rw-r--r--src/com/android/gallery3d/onetimeinitializer/GalleryWidgetMigrator.java169
-rw-r--r--src/com/android/gallery3d/provider/GalleryProvider.java228
-rw-r--r--src/com/android/gallery3d/ui/AbstractSlotRenderer.java119
-rw-r--r--src/com/android/gallery3d/ui/ActionModeHandler.java501
-rw-r--r--src/com/android/gallery3d/ui/AlbumLabelMaker.java206
-rw-r--r--src/com/android/gallery3d/ui/AlbumSetSlidingWindow.java549
-rw-r--r--src/com/android/gallery3d/ui/AlbumSetSlotRenderer.java242
-rw-r--r--src/com/android/gallery3d/ui/AlbumSlidingWindow.java365
-rw-r--r--src/com/android/gallery3d/ui/AlbumSlotRenderer.java201
-rw-r--r--src/com/android/gallery3d/ui/AnimationTime.java45
-rw-r--r--src/com/android/gallery3d/ui/BitmapLoader.java108
-rw-r--r--src/com/android/gallery3d/ui/BitmapScreenNail.java61
-rw-r--r--src/com/android/gallery3d/ui/BitmapTileProvider.java103
-rw-r--r--src/com/android/gallery3d/ui/CacheStorageUsageInfo.java90
-rw-r--r--src/com/android/gallery3d/ui/CaptureAnimation.java56
-rw-r--r--src/com/android/gallery3d/ui/DetailsAddressResolver.java118
-rw-r--r--src/com/android/gallery3d/ui/DetailsHelper.java148
-rw-r--r--src/com/android/gallery3d/ui/DialogDetailsView.java288
-rw-r--r--src/com/android/gallery3d/ui/DownUpDetector.java61
-rw-r--r--src/com/android/gallery3d/ui/EdgeEffect.java443
-rw-r--r--src/com/android/gallery3d/ui/EdgeView.java132
-rw-r--r--src/com/android/gallery3d/ui/FlingScroller.java141
-rw-r--r--src/com/android/gallery3d/ui/GLRoot.java53
-rw-r--r--src/com/android/gallery3d/ui/GLRootView.java630
-rw-r--r--src/com/android/gallery3d/ui/GLView.java465
-rw-r--r--src/com/android/gallery3d/ui/GestureRecognizer.java132
-rw-r--r--src/com/android/gallery3d/ui/Log.java54
-rw-r--r--src/com/android/gallery3d/ui/ManageCacheDrawer.java116
-rw-r--r--src/com/android/gallery3d/ui/MeasureHelper.java65
-rw-r--r--src/com/android/gallery3d/ui/MenuExecutor.java448
-rw-r--r--src/com/android/gallery3d/ui/OrientationSource.java22
-rw-r--r--src/com/android/gallery3d/ui/Paper.java183
-rw-r--r--src/com/android/gallery3d/ui/PhotoFallbackEffect.java179
-rw-r--r--src/com/android/gallery3d/ui/PhotoView.java1858
-rw-r--r--src/com/android/gallery3d/ui/PopupList.java206
-rw-r--r--src/com/android/gallery3d/ui/PositionController.java1821
-rw-r--r--src/com/android/gallery3d/ui/PreparePageFadeoutTexture.java85
-rw-r--r--src/com/android/gallery3d/ui/ProgressSpinner.java80
-rw-r--r--src/com/android/gallery3d/ui/RelativePosition.java42
-rw-r--r--src/com/android/gallery3d/ui/ScreenNail.java35
-rw-r--r--src/com/android/gallery3d/ui/ScrollBarView.java97
-rw-r--r--src/com/android/gallery3d/ui/ScrollerHelper.java97
-rw-r--r--src/com/android/gallery3d/ui/SelectionManager.java251
-rw-r--r--src/com/android/gallery3d/ui/SelectionMenu.java61
-rw-r--r--src/com/android/gallery3d/ui/SlideshowView.java163
-rw-r--r--src/com/android/gallery3d/ui/SlotView.java788
-rw-r--r--src/com/android/gallery3d/ui/SurfaceTextureScreenNail.java142
-rw-r--r--src/com/android/gallery3d/ui/SynchronizedHandler.java41
-rw-r--r--src/com/android/gallery3d/ui/TileImageView.java786
-rw-r--r--src/com/android/gallery3d/ui/TileImageViewAdapter.java200
-rw-r--r--src/com/android/gallery3d/ui/TiledScreenNail.java218
-rw-r--r--src/com/android/gallery3d/ui/UndoBarView.java211
-rw-r--r--src/com/android/gallery3d/ui/UserInteractionListener.java26
-rw-r--r--src/com/android/gallery3d/ui/WakeLockHoldingProgressListener.java66
-rw-r--r--src/com/android/gallery3d/util/AccessibilityUtils.java54
-rw-r--r--src/com/android/gallery3d/util/BucketNames.java29
-rw-r--r--src/com/android/gallery3d/util/CacheManager.java82
-rw-r--r--src/com/android/gallery3d/util/GalleryUtils.java404
-rw-r--r--src/com/android/gallery3d/util/Holder.java29
-rw-r--r--src/com/android/gallery3d/util/IdentityCache.java78
-rw-r--r--src/com/android/gallery3d/util/IntArray.java60
-rw-r--r--src/com/android/gallery3d/util/InterruptableOutputStream.java67
-rw-r--r--src/com/android/gallery3d/util/JobLimiter.java159
-rw-r--r--src/com/android/gallery3d/util/LinkedNode.java71
-rw-r--r--src/com/android/gallery3d/util/Log.java53
-rw-r--r--src/com/android/gallery3d/util/MediaSetUtils.java66
-rw-r--r--src/com/android/gallery3d/util/MotionEventHelper.java120
-rw-r--r--src/com/android/gallery3d/util/Profile.java226
-rw-r--r--src/com/android/gallery3d/util/ProfileData.java168
-rw-r--r--src/com/android/gallery3d/util/RangeArray.java52
-rw-r--r--src/com/android/gallery3d/util/RangeBoolArray.java49
-rw-r--r--src/com/android/gallery3d/util/RangeIntArray.java49
-rw-r--r--src/com/android/gallery3d/util/ReverseGeocoder.java418
-rw-r--r--src/com/android/gallery3d/util/SaveVideoFileInfo.java29
-rw-r--r--src/com/android/gallery3d/util/SaveVideoFileUtils.java154
-rw-r--r--src/com/android/gallery3d/util/UpdateHelper.java59
412 files changed, 0 insertions, 74774 deletions
diff --git a/src/com/android/gallery3d/anim/AlphaAnimation.java b/src/com/android/gallery3d/anim/AlphaAnimation.java
deleted file mode 100644
index f9f4cbd2c..000000000
--- a/src/com/android/gallery3d/anim/AlphaAnimation.java
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.anim;
-
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.glrenderer.GLCanvas;
-
-public class AlphaAnimation extends CanvasAnimation {
- private final float mStartAlpha;
- private final float mEndAlpha;
- private float mCurrentAlpha;
-
- public AlphaAnimation(float from, float to) {
- mStartAlpha = from;
- mEndAlpha = to;
- mCurrentAlpha = from;
- }
-
- @Override
- public void apply(GLCanvas canvas) {
- canvas.multiplyAlpha(mCurrentAlpha);
- }
-
- @Override
- public int getCanvasSaveFlags() {
- return GLCanvas.SAVE_FLAG_ALPHA;
- }
-
- @Override
- protected void onCalculate(float progress) {
- mCurrentAlpha = Utils.clamp(mStartAlpha
- + (mEndAlpha - mStartAlpha) * progress, 0f, 1f);
- }
-}
diff --git a/src/com/android/gallery3d/anim/Animation.java b/src/com/android/gallery3d/anim/Animation.java
deleted file mode 100644
index cc117bbce..000000000
--- a/src/com/android/gallery3d/anim/Animation.java
+++ /dev/null
@@ -1,92 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.anim;
-
-import android.view.animation.Interpolator;
-
-import com.android.gallery3d.common.Utils;
-
-// Animation calculates a value according to the current input time.
-//
-// 1. First we need to use setDuration(int) to set the duration of the
-// animation. The duration is in milliseconds.
-// 2. Then we should call start(). The actual start time is the first value
-// passed to calculate(long).
-// 3. Each time we want to get an animation value, we call
-// calculate(long currentTimeMillis) to ask the Animation to calculate it.
-// The parameter passed to calculate(long) should be nonnegative.
-// 4. Use get() to get that value.
-//
-// In step 3, onCalculate(float progress) is called so subclasses can calculate
-// the value according to progress (progress is a value in [0,1]).
-//
-// Before onCalculate(float) is called, There is an optional interpolator which
-// can change the progress value. The interpolator can be set by
-// setInterpolator(Interpolator). If the interpolator is used, the value passed
-// to onCalculate may be (for example, the overshoot effect).
-//
-// The isActive() method returns true after the animation start() is called and
-// before calculate is passed a value which reaches the duration of the
-// animation.
-//
-// The start() method can be called again to restart the Animation.
-//
-abstract public class Animation {
- private static final long ANIMATION_START = -1;
- private static final long NO_ANIMATION = -2;
-
- private long mStartTime = NO_ANIMATION;
- private int mDuration;
- private Interpolator mInterpolator;
-
- public void setInterpolator(Interpolator interpolator) {
- mInterpolator = interpolator;
- }
-
- public void setDuration(int duration) {
- mDuration = duration;
- }
-
- public void start() {
- mStartTime = ANIMATION_START;
- }
-
- public void setStartTime(long time) {
- mStartTime = time;
- }
-
- public boolean isActive() {
- return mStartTime != NO_ANIMATION;
- }
-
- public void forceStop() {
- mStartTime = NO_ANIMATION;
- }
-
- public boolean calculate(long currentTimeMillis) {
- if (mStartTime == NO_ANIMATION) return false;
- if (mStartTime == ANIMATION_START) mStartTime = currentTimeMillis;
- int elapse = (int) (currentTimeMillis - mStartTime);
- float x = Utils.clamp((float) elapse / mDuration, 0f, 1f);
- Interpolator i = mInterpolator;
- onCalculate(i != null ? i.getInterpolation(x) : x);
- if (elapse >= mDuration) mStartTime = NO_ANIMATION;
- return mStartTime != NO_ANIMATION;
- }
-
- abstract protected void onCalculate(float progress);
-}
diff --git a/src/com/android/gallery3d/anim/CanvasAnimation.java b/src/com/android/gallery3d/anim/CanvasAnimation.java
deleted file mode 100644
index cdc66c6ba..000000000
--- a/src/com/android/gallery3d/anim/CanvasAnimation.java
+++ /dev/null
@@ -1,25 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.anim;
-
-import com.android.gallery3d.glrenderer.GLCanvas;
-
-public abstract class CanvasAnimation extends Animation {
-
- public abstract int getCanvasSaveFlags();
- public abstract void apply(GLCanvas canvas);
-}
diff --git a/src/com/android/gallery3d/anim/FloatAnimation.java b/src/com/android/gallery3d/anim/FloatAnimation.java
deleted file mode 100644
index 1294ec2f4..000000000
--- a/src/com/android/gallery3d/anim/FloatAnimation.java
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.anim;
-
-public class FloatAnimation extends Animation {
-
- private final float mFrom;
- private final float mTo;
- private float mCurrent;
-
- public FloatAnimation(float from, float to, int duration) {
- mFrom = from;
- mTo = to;
- mCurrent = from;
- setDuration(duration);
- }
-
- @Override
- protected void onCalculate(float progress) {
- mCurrent = mFrom + (mTo - mFrom) * progress;
- }
-
- public float get() {
- return mCurrent;
- }
-}
diff --git a/src/com/android/gallery3d/anim/StateTransitionAnimation.java b/src/com/android/gallery3d/anim/StateTransitionAnimation.java
deleted file mode 100644
index bf8a54405..000000000
--- a/src/com/android/gallery3d/anim/StateTransitionAnimation.java
+++ /dev/null
@@ -1,180 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.anim;
-
-import android.view.animation.AccelerateInterpolator;
-import android.view.animation.DecelerateInterpolator;
-import android.view.animation.Interpolator;
-
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.RawTexture;
-import com.android.gallery3d.ui.GLView;
-import com.android.gallery3d.ui.TiledScreenNail;
-
-public class StateTransitionAnimation extends Animation {
-
- public static class Spec {
- public static final Spec OUTGOING;
- public static final Spec INCOMING;
- public static final Spec PHOTO_INCOMING;
-
- private static final Interpolator DEFAULT_INTERPOLATOR =
- new DecelerateInterpolator();
-
- public int duration = 330;
- public float backgroundAlphaFrom = 0;
- public float backgroundAlphaTo = 0;
- public float backgroundScaleFrom = 0;
- public float backgroundScaleTo = 0;
- public float contentAlphaFrom = 1;
- public float contentAlphaTo = 1;
- public float contentScaleFrom = 1;
- public float contentScaleTo = 1;
- public float overlayAlphaFrom = 0;
- public float overlayAlphaTo = 0;
- public float overlayScaleFrom = 0;
- public float overlayScaleTo = 0;
- public Interpolator interpolator = DEFAULT_INTERPOLATOR;
-
- static {
- OUTGOING = new Spec();
- OUTGOING.backgroundAlphaFrom = 0.5f;
- OUTGOING.backgroundAlphaTo = 0f;
- OUTGOING.backgroundScaleFrom = 1f;
- OUTGOING.backgroundScaleTo = 0f;
- OUTGOING.contentAlphaFrom = 0.5f;
- OUTGOING.contentAlphaTo = 1f;
- OUTGOING.contentScaleFrom = 3f;
- OUTGOING.contentScaleTo = 1f;
-
- INCOMING = new Spec();
- INCOMING.overlayAlphaFrom = 1f;
- INCOMING.overlayAlphaTo = 0f;
- INCOMING.overlayScaleFrom = 1f;
- INCOMING.overlayScaleTo = 3f;
- INCOMING.contentAlphaFrom = 0f;
- INCOMING.contentAlphaTo = 1f;
- INCOMING.contentScaleFrom = 0.25f;
- INCOMING.contentScaleTo = 1f;
-
- PHOTO_INCOMING = INCOMING;
- }
-
- private static Spec specForTransition(Transition t) {
- switch (t) {
- case Outgoing:
- return Spec.OUTGOING;
- case Incoming:
- return Spec.INCOMING;
- case PhotoIncoming:
- return Spec.PHOTO_INCOMING;
- case None:
- default:
- return null;
- }
- }
- }
-
- public static enum Transition { None, Outgoing, Incoming, PhotoIncoming }
-
- private final Spec mTransitionSpec;
- private float mCurrentContentScale;
- private float mCurrentContentAlpha;
- private float mCurrentBackgroundScale;
- private float mCurrentBackgroundAlpha;
- private float mCurrentOverlayScale;
- private float mCurrentOverlayAlpha;
- private RawTexture mOldScreenTexture;
-
- public StateTransitionAnimation(Transition t, RawTexture oldScreen) {
- this(Spec.specForTransition(t), oldScreen);
- }
-
- public StateTransitionAnimation(Spec spec, RawTexture oldScreen) {
- mTransitionSpec = spec != null ? spec : Spec.OUTGOING;
- setDuration(mTransitionSpec.duration);
- setInterpolator(mTransitionSpec.interpolator);
- mOldScreenTexture = oldScreen;
- TiledScreenNail.disableDrawPlaceholder();
- }
-
- @Override
- public boolean calculate(long currentTimeMillis) {
- boolean retval = super.calculate(currentTimeMillis);
- if (!isActive()) {
- if (mOldScreenTexture != null) {
- mOldScreenTexture.recycle();
- mOldScreenTexture = null;
- }
- TiledScreenNail.enableDrawPlaceholder();
- }
- return retval;
- }
-
- @Override
- protected void onCalculate(float progress) {
- mCurrentContentScale = mTransitionSpec.contentScaleFrom
- + (mTransitionSpec.contentScaleTo - mTransitionSpec.contentScaleFrom) * progress;
- mCurrentContentAlpha = mTransitionSpec.contentAlphaFrom
- + (mTransitionSpec.contentAlphaTo - mTransitionSpec.contentAlphaFrom) * progress;
- mCurrentBackgroundAlpha = mTransitionSpec.backgroundAlphaFrom
- + (mTransitionSpec.backgroundAlphaTo - mTransitionSpec.backgroundAlphaFrom)
- * progress;
- mCurrentBackgroundScale = mTransitionSpec.backgroundScaleFrom
- + (mTransitionSpec.backgroundScaleTo - mTransitionSpec.backgroundScaleFrom)
- * progress;
- mCurrentOverlayScale = mTransitionSpec.overlayScaleFrom
- + (mTransitionSpec.overlayScaleTo - mTransitionSpec.overlayScaleFrom) * progress;
- mCurrentOverlayAlpha = mTransitionSpec.overlayAlphaFrom
- + (mTransitionSpec.overlayAlphaTo - mTransitionSpec.overlayAlphaFrom) * progress;
- }
-
- private void applyOldTexture(GLView view, GLCanvas canvas, float alpha, float scale, boolean clear) {
- if (mOldScreenTexture == null)
- return;
- if (clear) canvas.clearBuffer(view.getBackgroundColor());
- canvas.save();
- canvas.setAlpha(alpha);
- int xOffset = view.getWidth() / 2;
- int yOffset = view.getHeight() / 2;
- canvas.translate(xOffset, yOffset);
- canvas.scale(scale, scale, 1);
- mOldScreenTexture.draw(canvas, -xOffset, -yOffset);
- canvas.restore();
- }
-
- public void applyBackground(GLView view, GLCanvas canvas) {
- if (mCurrentBackgroundAlpha > 0f) {
- applyOldTexture(view, canvas, mCurrentBackgroundAlpha, mCurrentBackgroundScale, true);
- }
- }
-
- public void applyContentTransform(GLView view, GLCanvas canvas) {
- int xOffset = view.getWidth() / 2;
- int yOffset = view.getHeight() / 2;
- canvas.translate(xOffset, yOffset);
- canvas.scale(mCurrentContentScale, mCurrentContentScale, 1);
- canvas.translate(-xOffset, -yOffset);
- canvas.setAlpha(mCurrentContentAlpha);
- }
-
- public void applyOverlay(GLView view, GLCanvas canvas) {
- if (mCurrentOverlayAlpha > 0f) {
- applyOldTexture(view, canvas, mCurrentOverlayAlpha, mCurrentOverlayScale, false);
- }
- }
-}
diff --git a/src/com/android/gallery3d/app/AbstractGalleryActivity.java b/src/com/android/gallery3d/app/AbstractGalleryActivity.java
deleted file mode 100644
index ac39aa560..000000000
--- a/src/com/android/gallery3d/app/AbstractGalleryActivity.java
+++ /dev/null
@@ -1,343 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.annotation.TargetApi;
-import android.app.Activity;
-import android.app.AlertDialog;
-import android.content.BroadcastReceiver;
-import android.content.ComponentName;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.content.DialogInterface.OnCancelListener;
-import android.content.DialogInterface.OnClickListener;
-import android.content.Intent;
-import android.content.IntentFilter;
-import android.content.ServiceConnection;
-import android.content.res.Configuration;
-import android.os.Bundle;
-import android.os.IBinder;
-import android.view.Menu;
-import android.view.MenuItem;
-import android.view.Window;
-import android.view.WindowManager;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.ui.GLRoot;
-import com.android.gallery3d.ui.GLRootView;
-import com.android.gallery3d.util.LightCycleHelper.PanoramaViewHelper;
-import com.android.gallery3d.util.ThreadPool;
-import com.android.photos.data.GalleryBitmapPool;
-
-public class AbstractGalleryActivity extends Activity implements GalleryContext {
- @SuppressWarnings("unused")
- private static final String TAG = "AbstractGalleryActivity";
- private GLRootView mGLRootView;
- private StateManager mStateManager;
- private GalleryActionBar mActionBar;
- private OrientationManager mOrientationManager;
- private TransitionStore mTransitionStore = new TransitionStore();
- private boolean mDisableToggleStatusBar;
- private PanoramaViewHelper mPanoramaViewHelper;
-
- private AlertDialog mAlertDialog = null;
- private BroadcastReceiver mMountReceiver = new BroadcastReceiver() {
- @Override
- public void onReceive(Context context, Intent intent) {
- if (getExternalCacheDir() != null) onStorageReady();
- }
- };
- private IntentFilter mMountFilter = new IntentFilter(Intent.ACTION_MEDIA_MOUNTED);
-
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- mOrientationManager = new OrientationManager(this);
- toggleStatusBarByOrientation();
- getWindow().setBackgroundDrawable(null);
- mPanoramaViewHelper = new PanoramaViewHelper(this);
- mPanoramaViewHelper.onCreate();
- doBindBatchService();
- }
-
- @Override
- protected void onSaveInstanceState(Bundle outState) {
- mGLRootView.lockRenderThread();
- try {
- super.onSaveInstanceState(outState);
- getStateManager().saveState(outState);
- } finally {
- mGLRootView.unlockRenderThread();
- }
- }
-
- @Override
- public void onConfigurationChanged(Configuration config) {
- super.onConfigurationChanged(config);
- mStateManager.onConfigurationChange(config);
- getGalleryActionBar().onConfigurationChanged();
- invalidateOptionsMenu();
- toggleStatusBarByOrientation();
- }
-
- @Override
- public boolean onCreateOptionsMenu(Menu menu) {
- super.onCreateOptionsMenu(menu);
- return getStateManager().createOptionsMenu(menu);
- }
-
- @Override
- public Context getAndroidContext() {
- return this;
- }
-
- @Override
- public DataManager getDataManager() {
- return ((GalleryApp) getApplication()).getDataManager();
- }
-
- @Override
- public ThreadPool getThreadPool() {
- return ((GalleryApp) getApplication()).getThreadPool();
- }
-
- public synchronized StateManager getStateManager() {
- if (mStateManager == null) {
- mStateManager = new StateManager(this);
- }
- return mStateManager;
- }
-
- public GLRoot getGLRoot() {
- return mGLRootView;
- }
-
- public OrientationManager getOrientationManager() {
- return mOrientationManager;
- }
-
- @Override
- public void setContentView(int resId) {
- super.setContentView(resId);
- mGLRootView = (GLRootView) findViewById(R.id.gl_root_view);
- }
-
- protected void onStorageReady() {
- if (mAlertDialog != null) {
- mAlertDialog.dismiss();
- mAlertDialog = null;
- unregisterReceiver(mMountReceiver);
- }
- }
-
- @Override
- protected void onStart() {
- super.onStart();
- if (getExternalCacheDir() == null) {
- OnCancelListener onCancel = new OnCancelListener() {
- @Override
- public void onCancel(DialogInterface dialog) {
- finish();
- }
- };
- OnClickListener onClick = new OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int which) {
- dialog.cancel();
- }
- };
- AlertDialog.Builder builder = new AlertDialog.Builder(this)
- .setTitle(R.string.no_external_storage_title)
- .setMessage(R.string.no_external_storage)
- .setNegativeButton(android.R.string.cancel, onClick)
- .setOnCancelListener(onCancel);
- if (ApiHelper.HAS_SET_ICON_ATTRIBUTE) {
- setAlertDialogIconAttribute(builder);
- } else {
- builder.setIcon(android.R.drawable.ic_dialog_alert);
- }
- mAlertDialog = builder.show();
- registerReceiver(mMountReceiver, mMountFilter);
- }
- mPanoramaViewHelper.onStart();
- }
-
- @TargetApi(ApiHelper.VERSION_CODES.HONEYCOMB)
- private static void setAlertDialogIconAttribute(
- AlertDialog.Builder builder) {
- builder.setIconAttribute(android.R.attr.alertDialogIcon);
- }
-
- @Override
- protected void onStop() {
- super.onStop();
- if (mAlertDialog != null) {
- unregisterReceiver(mMountReceiver);
- mAlertDialog.dismiss();
- mAlertDialog = null;
- }
- mPanoramaViewHelper.onStop();
- }
-
- @Override
- protected void onResume() {
- super.onResume();
- mGLRootView.lockRenderThread();
- try {
- getStateManager().resume();
- getDataManager().resume();
- } finally {
- mGLRootView.unlockRenderThread();
- }
- mGLRootView.onResume();
- mOrientationManager.resume();
- }
-
- @Override
- protected void onPause() {
- super.onPause();
- mOrientationManager.pause();
- mGLRootView.onPause();
- mGLRootView.lockRenderThread();
- try {
- getStateManager().pause();
- getDataManager().pause();
- } finally {
- mGLRootView.unlockRenderThread();
- }
- GalleryBitmapPool.getInstance().clear();
- MediaItem.getBytesBufferPool().clear();
- }
-
- @Override
- protected void onDestroy() {
- super.onDestroy();
- mGLRootView.lockRenderThread();
- try {
- getStateManager().destroy();
- } finally {
- mGLRootView.unlockRenderThread();
- }
- doUnbindBatchService();
- }
-
- @Override
- protected void onActivityResult(int requestCode, int resultCode, Intent data) {
- mGLRootView.lockRenderThread();
- try {
- getStateManager().notifyActivityResult(
- requestCode, resultCode, data);
- } finally {
- mGLRootView.unlockRenderThread();
- }
- }
-
- @Override
- public void onBackPressed() {
- // send the back event to the top sub-state
- GLRoot root = getGLRoot();
- root.lockRenderThread();
- try {
- getStateManager().onBackPressed();
- } finally {
- root.unlockRenderThread();
- }
- }
-
- public GalleryActionBar getGalleryActionBar() {
- if (mActionBar == null) {
- mActionBar = new GalleryActionBar(this);
- }
- return mActionBar;
- }
-
- @Override
- public boolean onOptionsItemSelected(MenuItem item) {
- GLRoot root = getGLRoot();
- root.lockRenderThread();
- try {
- return getStateManager().itemSelected(item);
- } finally {
- root.unlockRenderThread();
- }
- }
-
- protected void disableToggleStatusBar() {
- mDisableToggleStatusBar = true;
- }
-
- // Shows status bar in portrait view, hide in landscape view
- private void toggleStatusBarByOrientation() {
- if (mDisableToggleStatusBar) return;
-
- Window win = getWindow();
- if (getResources().getConfiguration().orientation == Configuration.ORIENTATION_PORTRAIT) {
- win.clearFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
- } else {
- win.addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
- }
- }
-
- public TransitionStore getTransitionStore() {
- return mTransitionStore;
- }
-
- public PanoramaViewHelper getPanoramaViewHelper() {
- return mPanoramaViewHelper;
- }
-
- protected boolean isFullscreen() {
- return (getWindow().getAttributes().flags
- & WindowManager.LayoutParams.FLAG_FULLSCREEN) != 0;
- }
-
- private BatchService mBatchService;
- private boolean mBatchServiceIsBound = false;
- private ServiceConnection mBatchServiceConnection = new ServiceConnection() {
- public void onServiceConnected(ComponentName className, IBinder service) {
- mBatchService = ((BatchService.LocalBinder)service).getService();
- }
-
- public void onServiceDisconnected(ComponentName className) {
- mBatchService = null;
- }
- };
-
- private void doBindBatchService() {
- bindService(new Intent(this, BatchService.class), mBatchServiceConnection, Context.BIND_AUTO_CREATE);
- mBatchServiceIsBound = true;
- }
-
- private void doUnbindBatchService() {
- if (mBatchServiceIsBound) {
- // Detach our existing connection.
- unbindService(mBatchServiceConnection);
- mBatchServiceIsBound = false;
- }
- }
-
- public ThreadPool getBatchServiceThreadPoolIfAvailable() {
- if (mBatchServiceIsBound && mBatchService != null) {
- return mBatchService.getThreadPool();
- } else {
- throw new RuntimeException("Batch service unavailable");
- }
- }
-}
diff --git a/src/com/android/gallery3d/app/ActivityState.java b/src/com/android/gallery3d/app/ActivityState.java
deleted file mode 100644
index 2f1e0c9d9..000000000
--- a/src/com/android/gallery3d/app/ActivityState.java
+++ /dev/null
@@ -1,276 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.app.ActionBar;
-import android.app.Activity;
-import android.content.BroadcastReceiver;
-import android.content.Context;
-import android.content.Intent;
-import android.content.IntentFilter;
-import android.content.res.Configuration;
-import android.os.BatteryManager;
-import android.os.Bundle;
-import android.view.HapticFeedbackConstants;
-import android.view.Menu;
-import android.view.MenuInflater;
-import android.view.MenuItem;
-import android.view.Window;
-import android.view.WindowManager;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.anim.StateTransitionAnimation;
-import com.android.gallery3d.glrenderer.RawTexture;
-import com.android.gallery3d.ui.GLView;
-import com.android.gallery3d.ui.PreparePageFadeoutTexture;
-import com.android.gallery3d.util.GalleryUtils;
-
-abstract public class ActivityState {
- protected static final int FLAG_HIDE_ACTION_BAR = 1;
- protected static final int FLAG_HIDE_STATUS_BAR = 2;
- protected static final int FLAG_SCREEN_ON_WHEN_PLUGGED = 4;
- protected static final int FLAG_SCREEN_ON_ALWAYS = 8;
- protected static final int FLAG_ALLOW_LOCK_WHILE_SCREEN_ON = 16;
- protected static final int FLAG_SHOW_WHEN_LOCKED = 32;
-
- protected AbstractGalleryActivity mActivity;
- protected Bundle mData;
- protected int mFlags;
-
- protected ResultEntry mReceivedResults;
- protected ResultEntry mResult;
-
- protected static class ResultEntry {
- public int requestCode;
- public int resultCode = Activity.RESULT_CANCELED;
- public Intent resultData;
- }
-
- private boolean mDestroyed = false;
- private boolean mPlugged = false;
- boolean mIsFinishing = false;
-
- private static final String KEY_TRANSITION_IN = "transition-in";
-
- private StateTransitionAnimation.Transition mNextTransition =
- StateTransitionAnimation.Transition.None;
- private StateTransitionAnimation mIntroAnimation;
- private GLView mContentPane;
-
- protected ActivityState() {
- }
-
- protected void setContentPane(GLView content) {
- mContentPane = content;
- if (mIntroAnimation != null) {
- mContentPane.setIntroAnimation(mIntroAnimation);
- mIntroAnimation = null;
- }
- mContentPane.setBackgroundColor(getBackgroundColor());
- mActivity.getGLRoot().setContentPane(mContentPane);
- }
-
- void initialize(AbstractGalleryActivity activity, Bundle data) {
- mActivity = activity;
- mData = data;
- }
-
- public Bundle getData() {
- return mData;
- }
-
- protected void onBackPressed() {
- mActivity.getStateManager().finishState(this);
- }
-
- protected void setStateResult(int resultCode, Intent data) {
- if (mResult == null) return;
- mResult.resultCode = resultCode;
- mResult.resultData = data;
- }
-
- protected void onConfigurationChanged(Configuration config) {
- }
-
- protected void onSaveState(Bundle outState) {
- }
-
- protected void onStateResult(int requestCode, int resultCode, Intent data) {
- }
-
- protected float[] mBackgroundColor;
-
- protected int getBackgroundColorId() {
- return R.color.default_background;
- }
-
- protected float[] getBackgroundColor() {
- return mBackgroundColor;
- }
-
- protected void onCreate(Bundle data, Bundle storedState) {
- mBackgroundColor = GalleryUtils.intColorToFloatARGBArray(
- mActivity.getResources().getColor(getBackgroundColorId()));
- }
-
- protected void clearStateResult() {
- }
-
- BroadcastReceiver mPowerIntentReceiver = new BroadcastReceiver() {
- @Override
- public void onReceive(Context context, Intent intent) {
- final String action = intent.getAction();
- if (Intent.ACTION_BATTERY_CHANGED.equals(action)) {
- boolean plugged = (0 != intent.getIntExtra(BatteryManager.EXTRA_PLUGGED, 0));
-
- if (plugged != mPlugged) {
- mPlugged = plugged;
- setScreenFlags();
- }
- }
- }
- };
-
- private void setScreenFlags() {
- final Window win = mActivity.getWindow();
- final WindowManager.LayoutParams params = win.getAttributes();
- if ((0 != (mFlags & FLAG_SCREEN_ON_ALWAYS)) ||
- (mPlugged && 0 != (mFlags & FLAG_SCREEN_ON_WHEN_PLUGGED))) {
- params.flags |= WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON;
- } else {
- params.flags &= ~WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON;
- }
- if (0 != (mFlags & FLAG_ALLOW_LOCK_WHILE_SCREEN_ON)) {
- params.flags |= WindowManager.LayoutParams.FLAG_ALLOW_LOCK_WHILE_SCREEN_ON;
- } else {
- params.flags &= ~WindowManager.LayoutParams.FLAG_ALLOW_LOCK_WHILE_SCREEN_ON;
- }
- if (0 != (mFlags & FLAG_SHOW_WHEN_LOCKED)) {
- params.flags |= WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED;
- } else {
- params.flags &= ~WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED;
- }
- win.setAttributes(params);
- }
-
- protected void transitionOnNextPause(Class<? extends ActivityState> outgoing,
- Class<? extends ActivityState> incoming, StateTransitionAnimation.Transition hint) {
- if (outgoing == SinglePhotoPage.class && incoming == AlbumPage.class) {
- mNextTransition = StateTransitionAnimation.Transition.Outgoing;
- } else if (outgoing == AlbumPage.class && incoming == SinglePhotoPage.class) {
- mNextTransition = StateTransitionAnimation.Transition.PhotoIncoming;
- } else {
- mNextTransition = hint;
- }
- }
-
- protected void performHapticFeedback(int feedbackConstant) {
- mActivity.getWindow().getDecorView().performHapticFeedback(feedbackConstant,
- HapticFeedbackConstants.FLAG_IGNORE_VIEW_SETTING);
- }
-
- protected void onPause() {
- if (0 != (mFlags & FLAG_SCREEN_ON_WHEN_PLUGGED)) {
- ((Activity) mActivity).unregisterReceiver(mPowerIntentReceiver);
- }
- if (mNextTransition != StateTransitionAnimation.Transition.None) {
- mActivity.getTransitionStore().put(KEY_TRANSITION_IN, mNextTransition);
- PreparePageFadeoutTexture.prepareFadeOutTexture(mActivity, mContentPane);
- mNextTransition = StateTransitionAnimation.Transition.None;
- }
- }
-
- // should only be called by StateManager
- void resume() {
- AbstractGalleryActivity activity = mActivity;
- ActionBar actionBar = activity.getActionBar();
- if (actionBar != null) {
- if ((mFlags & FLAG_HIDE_ACTION_BAR) != 0) {
- actionBar.hide();
- } else {
- actionBar.show();
- }
- int stateCount = mActivity.getStateManager().getStateCount();
- mActivity.getGalleryActionBar().setDisplayOptions(stateCount > 1, true);
- // Default behavior, this can be overridden in ActivityState's onResume.
- actionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD);
- }
-
- activity.invalidateOptionsMenu();
-
- setScreenFlags();
-
- boolean lightsOut = ((mFlags & FLAG_HIDE_STATUS_BAR) != 0);
- mActivity.getGLRoot().setLightsOutMode(lightsOut);
-
- ResultEntry entry = mReceivedResults;
- if (entry != null) {
- mReceivedResults = null;
- onStateResult(entry.requestCode, entry.resultCode, entry.resultData);
- }
-
- if (0 != (mFlags & FLAG_SCREEN_ON_WHEN_PLUGGED)) {
- // we need to know whether the device is plugged in to do this correctly
- final IntentFilter filter = new IntentFilter();
- filter.addAction(Intent.ACTION_BATTERY_CHANGED);
- activity.registerReceiver(mPowerIntentReceiver, filter);
- }
-
- onResume();
-
- // the transition store should be cleared after resume;
- mActivity.getTransitionStore().clear();
- }
-
- // a subclass of ActivityState should override the method to resume itself
- protected void onResume() {
- RawTexture fade = mActivity.getTransitionStore().get(
- PreparePageFadeoutTexture.KEY_FADE_TEXTURE);
- mNextTransition = mActivity.getTransitionStore().get(
- KEY_TRANSITION_IN, StateTransitionAnimation.Transition.None);
- if (mNextTransition != StateTransitionAnimation.Transition.None) {
- mIntroAnimation = new StateTransitionAnimation(mNextTransition, fade);
- mNextTransition = StateTransitionAnimation.Transition.None;
- }
- }
-
- protected boolean onCreateActionBar(Menu menu) {
- // TODO: we should return false if there is no menu to show
- // this is a workaround for a bug in system
- return true;
- }
-
- protected boolean onItemSelected(MenuItem item) {
- return false;
- }
-
- protected void onDestroy() {
- mDestroyed = true;
- }
-
- boolean isDestroyed() {
- return mDestroyed;
- }
-
- public boolean isFinishing() {
- return mIsFinishing;
- }
-
- protected MenuInflater getSupportMenuInflater() {
- return mActivity.getMenuInflater();
- }
-}
diff --git a/src/com/android/gallery3d/app/AlbumDataLoader.java b/src/com/android/gallery3d/app/AlbumDataLoader.java
deleted file mode 100644
index 28a822830..000000000
--- a/src/com/android/gallery3d/app/AlbumDataLoader.java
+++ /dev/null
@@ -1,397 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.os.Handler;
-import android.os.Message;
-import android.os.Process;
-
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.ContentListener;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.ui.SynchronizedHandler;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.concurrent.Callable;
-import java.util.concurrent.ExecutionException;
-import java.util.concurrent.FutureTask;
-
-public class AlbumDataLoader {
- @SuppressWarnings("unused")
- private static final String TAG = "AlbumDataAdapter";
- private static final int DATA_CACHE_SIZE = 1000;
-
- private static final int MSG_LOAD_START = 1;
- private static final int MSG_LOAD_FINISH = 2;
- private static final int MSG_RUN_OBJECT = 3;
-
- private static final int MIN_LOAD_COUNT = 32;
- private static final int MAX_LOAD_COUNT = 64;
-
- private final MediaItem[] mData;
- private final long[] mItemVersion;
- private final long[] mSetVersion;
-
- public static interface DataListener {
- public void onContentChanged(int index);
- public void onSizeChanged(int size);
- }
-
- private int mActiveStart = 0;
- private int mActiveEnd = 0;
-
- private int mContentStart = 0;
- private int mContentEnd = 0;
-
- private final MediaSet mSource;
- private long mSourceVersion = MediaObject.INVALID_DATA_VERSION;
-
- private final Handler mMainHandler;
- private int mSize = 0;
-
- private DataListener mDataListener;
- private MySourceListener mSourceListener = new MySourceListener();
- private LoadingListener mLoadingListener;
-
- private ReloadTask mReloadTask;
- // the data version on which last loading failed
- private long mFailedVersion = MediaObject.INVALID_DATA_VERSION;
-
- public AlbumDataLoader(AbstractGalleryActivity context, MediaSet mediaSet) {
- mSource = mediaSet;
-
- mData = new MediaItem[DATA_CACHE_SIZE];
- mItemVersion = new long[DATA_CACHE_SIZE];
- mSetVersion = new long[DATA_CACHE_SIZE];
- Arrays.fill(mItemVersion, MediaObject.INVALID_DATA_VERSION);
- Arrays.fill(mSetVersion, MediaObject.INVALID_DATA_VERSION);
-
- mMainHandler = new SynchronizedHandler(context.getGLRoot()) {
- @Override
- public void handleMessage(Message message) {
- switch (message.what) {
- case MSG_RUN_OBJECT:
- ((Runnable) message.obj).run();
- return;
- case MSG_LOAD_START:
- if (mLoadingListener != null) mLoadingListener.onLoadingStarted();
- return;
- case MSG_LOAD_FINISH:
- if (mLoadingListener != null) {
- boolean loadingFailed =
- (mFailedVersion != MediaObject.INVALID_DATA_VERSION);
- mLoadingListener.onLoadingFinished(loadingFailed);
- }
- return;
- }
- }
- };
- }
-
- public void resume() {
- mSource.addContentListener(mSourceListener);
- mReloadTask = new ReloadTask();
- mReloadTask.start();
- }
-
- public void pause() {
- mReloadTask.terminate();
- mReloadTask = null;
- mSource.removeContentListener(mSourceListener);
- }
-
- public MediaItem get(int index) {
- if (!isActive(index)) {
- return mSource.getMediaItem(index, 1).get(0);
- }
- return mData[index % mData.length];
- }
-
- public int getActiveStart() {
- return mActiveStart;
- }
-
- public boolean isActive(int index) {
- return index >= mActiveStart && index < mActiveEnd;
- }
-
- public int size() {
- return mSize;
- }
-
- // Returns the index of the MediaItem with the given path or
- // -1 if the path is not cached
- public int findItem(Path id) {
- for (int i = mContentStart; i < mContentEnd; i++) {
- MediaItem item = mData[i % DATA_CACHE_SIZE];
- if (item != null && id == item.getPath()) {
- return i;
- }
- }
- return -1;
- }
-
- private void clearSlot(int slotIndex) {
- mData[slotIndex] = null;
- mItemVersion[slotIndex] = MediaObject.INVALID_DATA_VERSION;
- mSetVersion[slotIndex] = MediaObject.INVALID_DATA_VERSION;
- }
-
- private void setContentWindow(int contentStart, int contentEnd) {
- if (contentStart == mContentStart && contentEnd == mContentEnd) return;
- int end = mContentEnd;
- int start = mContentStart;
-
- // We need change the content window before calling reloadData(...)
- synchronized (this) {
- mContentStart = contentStart;
- mContentEnd = contentEnd;
- }
- long[] itemVersion = mItemVersion;
- long[] setVersion = mSetVersion;
- if (contentStart >= end || start >= contentEnd) {
- for (int i = start, n = end; i < n; ++i) {
- clearSlot(i % DATA_CACHE_SIZE);
- }
- } else {
- for (int i = start; i < contentStart; ++i) {
- clearSlot(i % DATA_CACHE_SIZE);
- }
- for (int i = contentEnd, n = end; i < n; ++i) {
- clearSlot(i % DATA_CACHE_SIZE);
- }
- }
- if (mReloadTask != null) mReloadTask.notifyDirty();
- }
-
- public void setActiveWindow(int start, int end) {
- if (start == mActiveStart && end == mActiveEnd) return;
-
- Utils.assertTrue(start <= end
- && end - start <= mData.length && end <= mSize);
-
- int length = mData.length;
- mActiveStart = start;
- mActiveEnd = end;
-
- // If no data is visible, keep the cache content
- if (start == end) return;
-
- int contentStart = Utils.clamp((start + end) / 2 - length / 2,
- 0, Math.max(0, mSize - length));
- int contentEnd = Math.min(contentStart + length, mSize);
- if (mContentStart > start || mContentEnd < end
- || Math.abs(contentStart - mContentStart) > MIN_LOAD_COUNT) {
- setContentWindow(contentStart, contentEnd);
- }
- }
-
- private class MySourceListener implements ContentListener {
- @Override
- public void onContentDirty() {
- if (mReloadTask != null) mReloadTask.notifyDirty();
- }
- }
-
- public void setDataListener(DataListener listener) {
- mDataListener = listener;
- }
-
- public void setLoadingListener(LoadingListener listener) {
- mLoadingListener = listener;
- }
-
- private <T> T executeAndWait(Callable<T> callable) {
- FutureTask<T> task = new FutureTask<T>(callable);
- mMainHandler.sendMessage(
- mMainHandler.obtainMessage(MSG_RUN_OBJECT, task));
- try {
- return task.get();
- } catch (InterruptedException e) {
- return null;
- } catch (ExecutionException e) {
- throw new RuntimeException(e);
- }
- }
-
- private static class UpdateInfo {
- public long version;
- public int reloadStart;
- public int reloadCount;
-
- public int size;
- public ArrayList<MediaItem> items;
- }
-
- private class GetUpdateInfo implements Callable<UpdateInfo> {
- private final long mVersion;
-
- public GetUpdateInfo(long version) {
- mVersion = version;
- }
-
- @Override
- public UpdateInfo call() throws Exception {
- if (mFailedVersion == mVersion) {
- // previous loading failed, return null to pause loading
- return null;
- }
- UpdateInfo info = new UpdateInfo();
- long version = mVersion;
- info.version = mSourceVersion;
- info.size = mSize;
- long setVersion[] = mSetVersion;
- for (int i = mContentStart, n = mContentEnd; i < n; ++i) {
- int index = i % DATA_CACHE_SIZE;
- if (setVersion[index] != version) {
- info.reloadStart = i;
- info.reloadCount = Math.min(MAX_LOAD_COUNT, n - i);
- return info;
- }
- }
- return mSourceVersion == mVersion ? null : info;
- }
- }
-
- private class UpdateContent implements Callable<Void> {
-
- private UpdateInfo mUpdateInfo;
-
- public UpdateContent(UpdateInfo info) {
- mUpdateInfo = info;
- }
-
- @Override
- public Void call() throws Exception {
- UpdateInfo info = mUpdateInfo;
- mSourceVersion = info.version;
- if (mSize != info.size) {
- mSize = info.size;
- if (mDataListener != null) mDataListener.onSizeChanged(mSize);
- if (mContentEnd > mSize) mContentEnd = mSize;
- if (mActiveEnd > mSize) mActiveEnd = mSize;
- }
-
- ArrayList<MediaItem> items = info.items;
-
- mFailedVersion = MediaObject.INVALID_DATA_VERSION;
- if ((items == null) || items.isEmpty()) {
- if (info.reloadCount > 0) {
- mFailedVersion = info.version;
- Log.d(TAG, "loading failed: " + mFailedVersion);
- }
- return null;
- }
- int start = Math.max(info.reloadStart, mContentStart);
- int end = Math.min(info.reloadStart + items.size(), mContentEnd);
-
- for (int i = start; i < end; ++i) {
- int index = i % DATA_CACHE_SIZE;
- mSetVersion[index] = info.version;
- MediaItem updateItem = items.get(i - info.reloadStart);
- long itemVersion = updateItem.getDataVersion();
- if (mItemVersion[index] != itemVersion) {
- mItemVersion[index] = itemVersion;
- mData[index] = updateItem;
- if (mDataListener != null && i >= mActiveStart && i < mActiveEnd) {
- mDataListener.onContentChanged(i);
- }
- }
- }
- return null;
- }
- }
-
- /*
- * The thread model of ReloadTask
- * *
- * [Reload Task] [Main Thread]
- * | |
- * getUpdateInfo() --> | (synchronous call)
- * (wait) <---- getUpdateInfo()
- * | |
- * Load Data |
- * | |
- * updateContent() --> | (synchronous call)
- * (wait) updateContent()
- * | |
- * | |
- */
- private class ReloadTask extends Thread {
-
- private volatile boolean mActive = true;
- private volatile boolean mDirty = true;
- private boolean mIsLoading = false;
-
- private void updateLoading(boolean loading) {
- if (mIsLoading == loading) return;
- mIsLoading = loading;
- mMainHandler.sendEmptyMessage(loading ? MSG_LOAD_START : MSG_LOAD_FINISH);
- }
-
- @Override
- public void run() {
- Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
-
- boolean updateComplete = false;
- while (mActive) {
- synchronized (this) {
- if (mActive && !mDirty && updateComplete) {
- updateLoading(false);
- if (mFailedVersion != MediaObject.INVALID_DATA_VERSION) {
- Log.d(TAG, "reload pause");
- }
- Utils.waitWithoutInterrupt(this);
- if (mActive && (mFailedVersion != MediaObject.INVALID_DATA_VERSION)) {
- Log.d(TAG, "reload resume");
- }
- continue;
- }
- mDirty = false;
- }
- updateLoading(true);
- long version = mSource.reload();
- UpdateInfo info = executeAndWait(new GetUpdateInfo(version));
- updateComplete = info == null;
- if (updateComplete) continue;
- if (info.version != version) {
- info.size = mSource.getMediaItemCount();
- info.version = version;
- }
- if (info.reloadCount > 0) {
- info.items = mSource.getMediaItem(info.reloadStart, info.reloadCount);
- }
- executeAndWait(new UpdateContent(info));
- }
- updateLoading(false);
- }
-
- public synchronized void notifyDirty() {
- mDirty = true;
- notifyAll();
- }
-
- public synchronized void terminate() {
- mActive = false;
- notifyAll();
- }
- }
-}
diff --git a/src/com/android/gallery3d/app/AlbumPage.java b/src/com/android/gallery3d/app/AlbumPage.java
deleted file mode 100644
index 658abbbd4..000000000
--- a/src/com/android/gallery3d/app/AlbumPage.java
+++ /dev/null
@@ -1,786 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.app.Activity;
-import android.content.Context;
-import android.content.Intent;
-import android.graphics.Rect;
-import android.net.Uri;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.Message;
-import android.provider.MediaStore;
-import android.view.HapticFeedbackConstants;
-import android.view.Menu;
-import android.view.MenuInflater;
-import android.view.MenuItem;
-import android.widget.Toast;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.MediaDetails;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.filtershow.crop.CropActivity;
-import com.android.gallery3d.filtershow.crop.CropExtras;
-import com.android.gallery3d.glrenderer.FadeTexture;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.ui.ActionModeHandler;
-import com.android.gallery3d.ui.ActionModeHandler.ActionModeListener;
-import com.android.gallery3d.ui.AlbumSlotRenderer;
-import com.android.gallery3d.ui.DetailsHelper;
-import com.android.gallery3d.ui.DetailsHelper.CloseListener;
-import com.android.gallery3d.ui.GLRoot;
-import com.android.gallery3d.ui.GLView;
-import com.android.gallery3d.ui.PhotoFallbackEffect;
-import com.android.gallery3d.ui.RelativePosition;
-import com.android.gallery3d.ui.SelectionManager;
-import com.android.gallery3d.ui.SlotView;
-import com.android.gallery3d.ui.SynchronizedHandler;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.MediaSetUtils;
-
-
-public class AlbumPage extends ActivityState implements GalleryActionBar.ClusterRunner,
- SelectionManager.SelectionListener, MediaSet.SyncListener, GalleryActionBar.OnAlbumModeSelectedListener {
- @SuppressWarnings("unused")
- private static final String TAG = "AlbumPage";
-
- public static final String KEY_MEDIA_PATH = "media-path";
- public static final String KEY_PARENT_MEDIA_PATH = "parent-media-path";
- public static final String KEY_SET_CENTER = "set-center";
- public static final String KEY_AUTO_SELECT_ALL = "auto-select-all";
- public static final String KEY_SHOW_CLUSTER_MENU = "cluster-menu";
- public static final String KEY_EMPTY_ALBUM = "empty-album";
- public static final String KEY_RESUME_ANIMATION = "resume_animation";
-
- private static final int REQUEST_SLIDESHOW = 1;
- public static final int REQUEST_PHOTO = 2;
- private static final int REQUEST_DO_ANIMATION = 3;
-
- private static final int BIT_LOADING_RELOAD = 1;
- private static final int BIT_LOADING_SYNC = 2;
-
- private static final float USER_DISTANCE_METER = 0.3f;
-
- private boolean mIsActive = false;
- private AlbumSlotRenderer mAlbumView;
- private Path mMediaSetPath;
- private String mParentMediaSetString;
- private SlotView mSlotView;
-
- private AlbumDataLoader mAlbumDataAdapter;
-
- protected SelectionManager mSelectionManager;
-
- private boolean mGetContent;
- private boolean mShowClusterMenu;
-
- private ActionModeHandler mActionModeHandler;
- private int mFocusIndex = 0;
- private DetailsHelper mDetailsHelper;
- private MyDetailsSource mDetailsSource;
- private MediaSet mMediaSet;
- private boolean mShowDetails;
- private float mUserDistance; // in pixel
- private Future<Integer> mSyncTask = null;
- private boolean mLaunchedFromPhotoPage;
- private boolean mInCameraApp;
- private boolean mInCameraAndWantQuitOnPause;
-
- private int mLoadingBits = 0;
- private boolean mInitialSynced = false;
- private int mSyncResult;
- private boolean mLoadingFailed;
- private RelativePosition mOpenCenter = new RelativePosition();
-
- private Handler mHandler;
- private static final int MSG_PICK_PHOTO = 0;
-
- private PhotoFallbackEffect mResumeEffect;
- private PhotoFallbackEffect.PositionProvider mPositionProvider =
- new PhotoFallbackEffect.PositionProvider() {
- @Override
- public Rect getPosition(int index) {
- Rect rect = mSlotView.getSlotRect(index);
- Rect bounds = mSlotView.bounds();
- rect.offset(bounds.left - mSlotView.getScrollX(),
- bounds.top - mSlotView.getScrollY());
- return rect;
- }
-
- @Override
- public int getItemIndex(Path path) {
- int start = mSlotView.getVisibleStart();
- int end = mSlotView.getVisibleEnd();
- for (int i = start; i < end; ++i) {
- MediaItem item = mAlbumDataAdapter.get(i);
- if (item != null && item.getPath() == path) return i;
- }
- return -1;
- }
- };
-
- @Override
- protected int getBackgroundColorId() {
- return R.color.album_background;
- }
-
- private final GLView mRootPane = new GLView() {
- private final float mMatrix[] = new float[16];
-
- @Override
- protected void onLayout(
- boolean changed, int left, int top, int right, int bottom) {
-
- int slotViewTop = mActivity.getGalleryActionBar().getHeight();
- int slotViewBottom = bottom - top;
- int slotViewRight = right - left;
-
- if (mShowDetails) {
- mDetailsHelper.layout(left, slotViewTop, right, bottom);
- } else {
- mAlbumView.setHighlightItemPath(null);
- }
-
- // Set the mSlotView as a reference point to the open animation
- mOpenCenter.setReferencePosition(0, slotViewTop);
- mSlotView.layout(0, slotViewTop, slotViewRight, slotViewBottom);
- GalleryUtils.setViewPointMatrix(mMatrix,
- (right - left) / 2, (bottom - top) / 2, -mUserDistance);
- }
-
- @Override
- protected void render(GLCanvas canvas) {
- canvas.save(GLCanvas.SAVE_FLAG_MATRIX);
- canvas.multiplyMatrix(mMatrix, 0);
- super.render(canvas);
-
- if (mResumeEffect != null) {
- boolean more = mResumeEffect.draw(canvas);
- if (!more) {
- mResumeEffect = null;
- mAlbumView.setSlotFilter(null);
- }
- // We want to render one more time even when no more effect
- // required. So that the animated thumbnails could be draw
- // with declarations in super.render().
- invalidate();
- }
- canvas.restore();
- }
- };
-
- // This are the transitions we want:
- //
- // +--------+ +------------+ +-------+ +----------+
- // | Camera |---------->| Fullscreen |--->| Album |--->| AlbumSet |
- // | View | thumbnail | Photo | up | Page | up | Page |
- // +--------+ +------------+ +-------+ +----------+
- // ^ | | ^ |
- // | | | | | close
- // +----------back--------+ +----back----+ +--back-> app
- //
- @Override
- protected void onBackPressed() {
- if (mShowDetails) {
- hideDetails();
- } else if (mSelectionManager.inSelectionMode()) {
- mSelectionManager.leaveSelectionMode();
- } else {
- if(mLaunchedFromPhotoPage) {
- mActivity.getTransitionStore().putIfNotPresent(
- PhotoPage.KEY_ALBUMPAGE_TRANSITION,
- PhotoPage.MSG_ALBUMPAGE_RESUMED);
- }
- // TODO: fix this regression
- // mAlbumView.savePositions(PositionRepository.getInstance(mActivity));
- if (mInCameraApp) {
- super.onBackPressed();
- } else {
- onUpPressed();
- }
- }
- }
-
- private void onUpPressed() {
- if (mInCameraApp) {
- GalleryUtils.startGalleryActivity(mActivity);
- } else if (mActivity.getStateManager().getStateCount() > 1) {
- super.onBackPressed();
- } else if (mParentMediaSetString != null) {
- Bundle data = new Bundle(getData());
- data.putString(AlbumSetPage.KEY_MEDIA_PATH, mParentMediaSetString);
- mActivity.getStateManager().switchState(
- this, AlbumSetPage.class, data);
- }
- }
-
- private void onDown(int index) {
- mAlbumView.setPressedIndex(index);
- }
-
- private void onUp(boolean followedByLongPress) {
- if (followedByLongPress) {
- // Avoid showing press-up animations for long-press.
- mAlbumView.setPressedIndex(-1);
- } else {
- mAlbumView.setPressedUp();
- }
- }
-
- private void onSingleTapUp(int slotIndex) {
- if (!mIsActive) return;
-
- if (mSelectionManager.inSelectionMode()) {
- MediaItem item = mAlbumDataAdapter.get(slotIndex);
- if (item == null) return; // Item not ready yet, ignore the click
- mSelectionManager.toggle(item.getPath());
- mSlotView.invalidate();
- } else {
- // Render transition in pressed state
- mAlbumView.setPressedIndex(slotIndex);
- mAlbumView.setPressedUp();
- mHandler.sendMessageDelayed(mHandler.obtainMessage(MSG_PICK_PHOTO, slotIndex, 0),
- FadeTexture.DURATION);
- }
- }
-
- private void pickPhoto(int slotIndex) {
- pickPhoto(slotIndex, false);
- }
-
- private void pickPhoto(int slotIndex, boolean startInFilmstrip) {
- if (!mIsActive) return;
-
- if (!startInFilmstrip) {
- // Launch photos in lights out mode
- mActivity.getGLRoot().setLightsOutMode(true);
- }
-
- MediaItem item = mAlbumDataAdapter.get(slotIndex);
- if (item == null) return; // Item not ready yet, ignore the click
- if (mGetContent) {
- onGetContent(item);
- } else if (mLaunchedFromPhotoPage) {
- TransitionStore transitions = mActivity.getTransitionStore();
- transitions.put(
- PhotoPage.KEY_ALBUMPAGE_TRANSITION,
- PhotoPage.MSG_ALBUMPAGE_PICKED);
- transitions.put(PhotoPage.KEY_INDEX_HINT, slotIndex);
- onBackPressed();
- } else {
- // Get into the PhotoPage.
- // mAlbumView.savePositions(PositionRepository.getInstance(mActivity));
- Bundle data = new Bundle();
- data.putInt(PhotoPage.KEY_INDEX_HINT, slotIndex);
- data.putParcelable(PhotoPage.KEY_OPEN_ANIMATION_RECT,
- mSlotView.getSlotRect(slotIndex, mRootPane));
- data.putString(PhotoPage.KEY_MEDIA_SET_PATH,
- mMediaSetPath.toString());
- data.putString(PhotoPage.KEY_MEDIA_ITEM_PATH,
- item.getPath().toString());
- data.putInt(PhotoPage.KEY_ALBUMPAGE_TRANSITION,
- PhotoPage.MSG_ALBUMPAGE_STARTED);
- data.putBoolean(PhotoPage.KEY_START_IN_FILMSTRIP,
- startInFilmstrip);
- data.putBoolean(PhotoPage.KEY_IN_CAMERA_ROLL, mMediaSet.isCameraRoll());
- if (startInFilmstrip) {
- mActivity.getStateManager().switchState(this, FilmstripPage.class, data);
- } else {
- mActivity.getStateManager().startStateForResult(
- SinglePhotoPage.class, REQUEST_PHOTO, data);
- }
- }
- }
-
- private void onGetContent(final MediaItem item) {
- DataManager dm = mActivity.getDataManager();
- Activity activity = mActivity;
- if (mData.getString(Gallery.EXTRA_CROP) != null) {
- Uri uri = dm.getContentUri(item.getPath());
- Intent intent = new Intent(CropActivity.CROP_ACTION, uri)
- .addFlags(Intent.FLAG_ACTIVITY_FORWARD_RESULT)
- .putExtras(getData());
- if (mData.getParcelable(MediaStore.EXTRA_OUTPUT) == null) {
- intent.putExtra(CropExtras.KEY_RETURN_DATA, true);
- }
- activity.startActivity(intent);
- activity.finish();
- } else {
- Intent intent = new Intent(null, item.getContentUri())
- .addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
- activity.setResult(Activity.RESULT_OK, intent);
- activity.finish();
- }
- }
-
- public void onLongTap(int slotIndex) {
- if (mGetContent) return;
- MediaItem item = mAlbumDataAdapter.get(slotIndex);
- if (item == null) return;
- mSelectionManager.setAutoLeaveSelectionMode(true);
- mSelectionManager.toggle(item.getPath());
- mSlotView.invalidate();
- }
-
- @Override
- public void doCluster(int clusterType) {
- String basePath = mMediaSet.getPath().toString();
- String newPath = FilterUtils.newClusterPath(basePath, clusterType);
- Bundle data = new Bundle(getData());
- data.putString(AlbumSetPage.KEY_MEDIA_PATH, newPath);
- if (mShowClusterMenu) {
- Context context = mActivity.getAndroidContext();
- data.putString(AlbumSetPage.KEY_SET_TITLE, mMediaSet.getName());
- data.putString(AlbumSetPage.KEY_SET_SUBTITLE,
- GalleryActionBar.getClusterByTypeString(context, clusterType));
- }
-
- // mAlbumView.savePositions(PositionRepository.getInstance(mActivity));
- mActivity.getStateManager().startStateForResult(
- AlbumSetPage.class, REQUEST_DO_ANIMATION, data);
- }
-
- @Override
- protected void onCreate(Bundle data, Bundle restoreState) {
- super.onCreate(data, restoreState);
- mUserDistance = GalleryUtils.meterToPixel(USER_DISTANCE_METER);
- initializeViews();
- initializeData(data);
- mGetContent = data.getBoolean(Gallery.KEY_GET_CONTENT, false);
- mShowClusterMenu = data.getBoolean(KEY_SHOW_CLUSTER_MENU, false);
- mDetailsSource = new MyDetailsSource();
- Context context = mActivity.getAndroidContext();
-
- if (data.getBoolean(KEY_AUTO_SELECT_ALL)) {
- mSelectionManager.selectAll();
- }
-
- mLaunchedFromPhotoPage =
- mActivity.getStateManager().hasStateClass(FilmstripPage.class);
- mInCameraApp = data.getBoolean(PhotoPage.KEY_APP_BRIDGE, false);
-
- mHandler = new SynchronizedHandler(mActivity.getGLRoot()) {
- @Override
- public void handleMessage(Message message) {
- switch (message.what) {
- case MSG_PICK_PHOTO: {
- pickPhoto(message.arg1);
- break;
- }
- default:
- throw new AssertionError(message.what);
- }
- }
- };
- }
-
- @Override
- protected void onResume() {
- super.onResume();
- mIsActive = true;
-
- mResumeEffect = mActivity.getTransitionStore().get(KEY_RESUME_ANIMATION);
- if (mResumeEffect != null) {
- mAlbumView.setSlotFilter(mResumeEffect);
- mResumeEffect.setPositionProvider(mPositionProvider);
- mResumeEffect.start();
- }
-
- setContentPane(mRootPane);
-
- boolean enableHomeButton = (mActivity.getStateManager().getStateCount() > 1) |
- mParentMediaSetString != null;
- GalleryActionBar actionBar = mActivity.getGalleryActionBar();
- actionBar.setDisplayOptions(enableHomeButton, false);
- if (!mGetContent) {
- actionBar.enableAlbumModeMenu(GalleryActionBar.ALBUM_GRID_MODE_SELECTED, this);
- }
-
- // Set the reload bit here to prevent it exit this page in clearLoadingBit().
- setLoadingBit(BIT_LOADING_RELOAD);
- mLoadingFailed = false;
- mAlbumDataAdapter.resume();
-
- mAlbumView.resume();
- mAlbumView.setPressedIndex(-1);
- mActionModeHandler.resume();
- if (!mInitialSynced) {
- setLoadingBit(BIT_LOADING_SYNC);
- mSyncTask = mMediaSet.requestSync(this);
- }
- mInCameraAndWantQuitOnPause = mInCameraApp;
- }
-
- @Override
- protected void onPause() {
- super.onPause();
- mIsActive = false;
-
- if (mSelectionManager.inSelectionMode()) {
- mSelectionManager.leaveSelectionMode();
- }
- mAlbumView.setSlotFilter(null);
- mActionModeHandler.pause();
- mAlbumDataAdapter.pause();
- mAlbumView.pause();
- DetailsHelper.pause();
- if (!mGetContent) {
- mActivity.getGalleryActionBar().disableAlbumModeMenu(true);
- }
-
- if (mSyncTask != null) {
- mSyncTask.cancel();
- mSyncTask = null;
- clearLoadingBit(BIT_LOADING_SYNC);
- }
- }
-
- @Override
- protected void onDestroy() {
- super.onDestroy();
- if (mAlbumDataAdapter != null) {
- mAlbumDataAdapter.setLoadingListener(null);
- }
- mActionModeHandler.destroy();
- }
-
- private void initializeViews() {
- mSelectionManager = new SelectionManager(mActivity, false);
- mSelectionManager.setSelectionListener(this);
- Config.AlbumPage config = Config.AlbumPage.get(mActivity);
- mSlotView = new SlotView(mActivity, config.slotViewSpec);
- mAlbumView = new AlbumSlotRenderer(mActivity, mSlotView,
- mSelectionManager, config.placeholderColor);
- mSlotView.setSlotRenderer(mAlbumView);
- mRootPane.addComponent(mSlotView);
- mSlotView.setListener(new SlotView.SimpleListener() {
- @Override
- public void onDown(int index) {
- AlbumPage.this.onDown(index);
- }
-
- @Override
- public void onUp(boolean followedByLongPress) {
- AlbumPage.this.onUp(followedByLongPress);
- }
-
- @Override
- public void onSingleTapUp(int slotIndex) {
- AlbumPage.this.onSingleTapUp(slotIndex);
- }
-
- @Override
- public void onLongTap(int slotIndex) {
- AlbumPage.this.onLongTap(slotIndex);
- }
- });
- mActionModeHandler = new ActionModeHandler(mActivity, mSelectionManager);
- mActionModeHandler.setActionModeListener(new ActionModeListener() {
- @Override
- public boolean onActionItemClicked(MenuItem item) {
- return onItemSelected(item);
- }
- });
- }
-
- private void initializeData(Bundle data) {
- mMediaSetPath = Path.fromString(data.getString(KEY_MEDIA_PATH));
- mParentMediaSetString = data.getString(KEY_PARENT_MEDIA_PATH);
- mMediaSet = mActivity.getDataManager().getMediaSet(mMediaSetPath);
- if (mMediaSet == null) {
- Utils.fail("MediaSet is null. Path = %s", mMediaSetPath);
- }
- mSelectionManager.setSourceMediaSet(mMediaSet);
- mAlbumDataAdapter = new AlbumDataLoader(mActivity, mMediaSet);
- mAlbumDataAdapter.setLoadingListener(new MyLoadingListener());
- mAlbumView.setModel(mAlbumDataAdapter);
- }
-
- private void showDetails() {
- mShowDetails = true;
- if (mDetailsHelper == null) {
- mDetailsHelper = new DetailsHelper(mActivity, mRootPane, mDetailsSource);
- mDetailsHelper.setCloseListener(new CloseListener() {
- @Override
- public void onClose() {
- hideDetails();
- }
- });
- }
- mDetailsHelper.show();
- }
-
- private void hideDetails() {
- mShowDetails = false;
- mDetailsHelper.hide();
- mAlbumView.setHighlightItemPath(null);
- mSlotView.invalidate();
- }
-
- @Override
- protected boolean onCreateActionBar(Menu menu) {
- GalleryActionBar actionBar = mActivity.getGalleryActionBar();
- MenuInflater inflator = getSupportMenuInflater();
- if (mGetContent) {
- inflator.inflate(R.menu.pickup, menu);
- int typeBits = mData.getInt(Gallery.KEY_TYPE_BITS,
- DataManager.INCLUDE_IMAGE);
- actionBar.setTitle(GalleryUtils.getSelectionModePrompt(typeBits));
- } else {
- inflator.inflate(R.menu.album, menu);
- actionBar.setTitle(mMediaSet.getName());
-
- FilterUtils.setupMenuItems(actionBar, mMediaSetPath, true);
-
- menu.findItem(R.id.action_group_by).setVisible(mShowClusterMenu);
- menu.findItem(R.id.action_camera).setVisible(
- MediaSetUtils.isCameraSource(mMediaSetPath)
- && GalleryUtils.isCameraAvailable(mActivity));
-
- }
- actionBar.setSubtitle(null);
- return true;
- }
-
- private void prepareAnimationBackToFilmstrip(int slotIndex) {
- if (mAlbumDataAdapter == null || !mAlbumDataAdapter.isActive(slotIndex)) return;
- MediaItem item = mAlbumDataAdapter.get(slotIndex);
- if (item == null) return;
- TransitionStore transitions = mActivity.getTransitionStore();
- transitions.put(PhotoPage.KEY_INDEX_HINT, slotIndex);
- transitions.put(PhotoPage.KEY_OPEN_ANIMATION_RECT,
- mSlotView.getSlotRect(slotIndex, mRootPane));
- }
-
- private void switchToFilmstrip() {
- if (mAlbumDataAdapter.size() < 1) return;
- int targetPhoto = mSlotView.getVisibleStart();
- prepareAnimationBackToFilmstrip(targetPhoto);
- if(mLaunchedFromPhotoPage) {
- onBackPressed();
- } else {
- pickPhoto(targetPhoto, true);
- }
- }
-
- @Override
- protected boolean onItemSelected(MenuItem item) {
- switch (item.getItemId()) {
- case android.R.id.home: {
- onUpPressed();
- return true;
- }
- case R.id.action_cancel:
- mActivity.getStateManager().finishState(this);
- return true;
- case R.id.action_select:
- mSelectionManager.setAutoLeaveSelectionMode(false);
- mSelectionManager.enterSelectionMode();
- return true;
- case R.id.action_group_by: {
- mActivity.getGalleryActionBar().showClusterDialog(this);
- return true;
- }
- case R.id.action_slideshow: {
- mInCameraAndWantQuitOnPause = false;
- Bundle data = new Bundle();
- data.putString(SlideshowPage.KEY_SET_PATH,
- mMediaSetPath.toString());
- data.putBoolean(SlideshowPage.KEY_REPEAT, true);
- mActivity.getStateManager().startStateForResult(
- SlideshowPage.class, REQUEST_SLIDESHOW, data);
- return true;
- }
- case R.id.action_details: {
- if (mShowDetails) {
- hideDetails();
- } else {
- showDetails();
- }
- return true;
- }
- case R.id.action_camera: {
- GalleryUtils.startCameraActivity(mActivity);
- return true;
- }
- default:
- return false;
- }
- }
-
- @Override
- protected void onStateResult(int request, int result, Intent data) {
- switch (request) {
- case REQUEST_SLIDESHOW: {
- // data could be null, if there is no images in the album
- if (data == null) return;
- mFocusIndex = data.getIntExtra(SlideshowPage.KEY_PHOTO_INDEX, 0);
- mSlotView.setCenterIndex(mFocusIndex);
- break;
- }
- case REQUEST_PHOTO: {
- if (data == null) return;
- mFocusIndex = data.getIntExtra(PhotoPage.KEY_RETURN_INDEX_HINT, 0);
- mSlotView.makeSlotVisible(mFocusIndex);
- break;
- }
- case REQUEST_DO_ANIMATION: {
- mSlotView.startRisingAnimation();
- break;
- }
- }
- }
-
- @Override
- public void onSelectionModeChange(int mode) {
- switch (mode) {
- case SelectionManager.ENTER_SELECTION_MODE: {
- mActionModeHandler.startActionMode();
- performHapticFeedback(HapticFeedbackConstants.LONG_PRESS);
- break;
- }
- case SelectionManager.LEAVE_SELECTION_MODE: {
- mActionModeHandler.finishActionMode();
- mRootPane.invalidate();
- break;
- }
- case SelectionManager.SELECT_ALL_MODE: {
- mActionModeHandler.updateSupportedOperation();
- mRootPane.invalidate();
- break;
- }
- }
- }
-
- @Override
- public void onSelectionChange(Path path, boolean selected) {
- int count = mSelectionManager.getSelectedCount();
- String format = mActivity.getResources().getQuantityString(
- R.plurals.number_of_items_selected, count);
- mActionModeHandler.setTitle(String.format(format, count));
- mActionModeHandler.updateSupportedOperation(path, selected);
- }
-
- @Override
- public void onSyncDone(final MediaSet mediaSet, final int resultCode) {
- Log.d(TAG, "onSyncDone: " + Utils.maskDebugInfo(mediaSet.getName()) + " result="
- + resultCode);
- ((Activity) mActivity).runOnUiThread(new Runnable() {
- @Override
- public void run() {
- GLRoot root = mActivity.getGLRoot();
- root.lockRenderThread();
- mSyncResult = resultCode;
- try {
- if (resultCode == MediaSet.SYNC_RESULT_SUCCESS) {
- mInitialSynced = true;
- }
- clearLoadingBit(BIT_LOADING_SYNC);
- showSyncErrorIfNecessary(mLoadingFailed);
- } finally {
- root.unlockRenderThread();
- }
- }
- });
- }
-
- // Show sync error toast when all the following conditions are met:
- // (1) both loading and sync are done,
- // (2) sync result is error,
- // (3) the page is still active, and
- // (4) no photo is shown or loading fails.
- private void showSyncErrorIfNecessary(boolean loadingFailed) {
- if ((mLoadingBits == 0) && (mSyncResult == MediaSet.SYNC_RESULT_ERROR) && mIsActive
- && (loadingFailed || (mAlbumDataAdapter.size() == 0))) {
- Toast.makeText(mActivity, R.string.sync_album_error,
- Toast.LENGTH_LONG).show();
- }
- }
-
- private void setLoadingBit(int loadTaskBit) {
- mLoadingBits |= loadTaskBit;
- }
-
- private void clearLoadingBit(int loadTaskBit) {
- mLoadingBits &= ~loadTaskBit;
- if (mLoadingBits == 0 && mIsActive) {
- if (mAlbumDataAdapter.size() == 0) {
- Intent result = new Intent();
- result.putExtra(KEY_EMPTY_ALBUM, true);
- setStateResult(Activity.RESULT_OK, result);
- mActivity.getStateManager().finishState(this);
- }
- }
- }
-
- private class MyLoadingListener implements LoadingListener {
- @Override
- public void onLoadingStarted() {
- setLoadingBit(BIT_LOADING_RELOAD);
- mLoadingFailed = false;
- }
-
- @Override
- public void onLoadingFinished(boolean loadingFailed) {
- clearLoadingBit(BIT_LOADING_RELOAD);
- mLoadingFailed = loadingFailed;
- showSyncErrorIfNecessary(loadingFailed);
- }
- }
-
- private class MyDetailsSource implements DetailsHelper.DetailsSource {
- private int mIndex;
-
- @Override
- public int size() {
- return mAlbumDataAdapter.size();
- }
-
- @Override
- public int setIndex() {
- Path id = mSelectionManager.getSelected(false).get(0);
- mIndex = mAlbumDataAdapter.findItem(id);
- return mIndex;
- }
-
- @Override
- public MediaDetails getDetails() {
- // this relies on setIndex() being called beforehand
- MediaObject item = mAlbumDataAdapter.get(mIndex);
- if (item != null) {
- mAlbumView.setHighlightItemPath(item.getPath());
- return item.getDetails();
- } else {
- return null;
- }
- }
- }
-
- @Override
- public void onAlbumModeSelected(int mode) {
- if (mode == GalleryActionBar.ALBUM_FILMSTRIP_MODE_SELECTED) {
- switchToFilmstrip();
- }
- }
-}
diff --git a/src/com/android/gallery3d/app/AlbumPicker.java b/src/com/android/gallery3d/app/AlbumPicker.java
deleted file mode 100644
index 65eb77291..000000000
--- a/src/com/android/gallery3d/app/AlbumPicker.java
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.content.Intent;
-import android.os.Bundle;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.data.DataManager;
-
-public class AlbumPicker extends PickerActivity {
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- setTitle(R.string.select_album);
- Intent intent = getIntent();
- Bundle extras = intent.getExtras();
- Bundle data = extras == null ? new Bundle() : new Bundle(extras);
-
- data.putBoolean(Gallery.KEY_GET_ALBUM, true);
- data.putString(AlbumSetPage.KEY_MEDIA_PATH,
- getDataManager().getTopSetPath(DataManager.INCLUDE_IMAGE));
- getStateManager().startState(AlbumSetPage.class, data);
- }
-}
diff --git a/src/com/android/gallery3d/app/AlbumSetDataLoader.java b/src/com/android/gallery3d/app/AlbumSetDataLoader.java
deleted file mode 100644
index cf380f812..000000000
--- a/src/com/android/gallery3d/app/AlbumSetDataLoader.java
+++ /dev/null
@@ -1,393 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.os.Handler;
-import android.os.Message;
-import android.os.Process;
-
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.ContentListener;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.ui.SynchronizedHandler;
-
-import java.util.Arrays;
-import java.util.concurrent.Callable;
-import java.util.concurrent.ExecutionException;
-import java.util.concurrent.FutureTask;
-
-public class AlbumSetDataLoader {
- @SuppressWarnings("unused")
- private static final String TAG = "AlbumSetDataAdapter";
-
- private static final int INDEX_NONE = -1;
-
- private static final int MIN_LOAD_COUNT = 4;
-
- private static final int MSG_LOAD_START = 1;
- private static final int MSG_LOAD_FINISH = 2;
- private static final int MSG_RUN_OBJECT = 3;
-
- public static interface DataListener {
- public void onContentChanged(int index);
- public void onSizeChanged(int size);
- }
-
- private final MediaSet[] mData;
- private final MediaItem[] mCoverItem;
- private final int[] mTotalCount;
- private final long[] mItemVersion;
- private final long[] mSetVersion;
-
- private int mActiveStart = 0;
- private int mActiveEnd = 0;
-
- private int mContentStart = 0;
- private int mContentEnd = 0;
-
- private final MediaSet mSource;
- private long mSourceVersion = MediaObject.INVALID_DATA_VERSION;
- private int mSize;
-
- private DataListener mDataListener;
- private LoadingListener mLoadingListener;
- private ReloadTask mReloadTask;
-
- private final Handler mMainHandler;
-
- private final MySourceListener mSourceListener = new MySourceListener();
-
- public AlbumSetDataLoader(AbstractGalleryActivity activity, MediaSet albumSet, int cacheSize) {
- mSource = Utils.checkNotNull(albumSet);
- mCoverItem = new MediaItem[cacheSize];
- mData = new MediaSet[cacheSize];
- mTotalCount = new int[cacheSize];
- mItemVersion = new long[cacheSize];
- mSetVersion = new long[cacheSize];
- Arrays.fill(mItemVersion, MediaObject.INVALID_DATA_VERSION);
- Arrays.fill(mSetVersion, MediaObject.INVALID_DATA_VERSION);
-
- mMainHandler = new SynchronizedHandler(activity.getGLRoot()) {
- @Override
- public void handleMessage(Message message) {
- switch (message.what) {
- case MSG_RUN_OBJECT:
- ((Runnable) message.obj).run();
- return;
- case MSG_LOAD_START:
- if (mLoadingListener != null) mLoadingListener.onLoadingStarted();
- return;
- case MSG_LOAD_FINISH:
- if (mLoadingListener != null) mLoadingListener.onLoadingFinished(false);
- return;
- }
- }
- };
- }
-
- public void pause() {
- mReloadTask.terminate();
- mReloadTask = null;
- mSource.removeContentListener(mSourceListener);
- }
-
- public void resume() {
- mSource.addContentListener(mSourceListener);
- mReloadTask = new ReloadTask();
- mReloadTask.start();
- }
-
- private void assertIsActive(int index) {
- if (index < mActiveStart && index >= mActiveEnd) {
- throw new IllegalArgumentException(String.format(
- "%s not in (%s, %s)", index, mActiveStart, mActiveEnd));
- }
- }
-
- public MediaSet getMediaSet(int index) {
- assertIsActive(index);
- return mData[index % mData.length];
- }
-
- public MediaItem getCoverItem(int index) {
- assertIsActive(index);
- return mCoverItem[index % mCoverItem.length];
- }
-
- public int getTotalCount(int index) {
- assertIsActive(index);
- return mTotalCount[index % mTotalCount.length];
- }
-
- public int getActiveStart() {
- return mActiveStart;
- }
-
- public boolean isActive(int index) {
- return index >= mActiveStart && index < mActiveEnd;
- }
-
- public int size() {
- return mSize;
- }
-
- // Returns the index of the MediaSet with the given path or
- // -1 if the path is not cached
- public int findSet(Path id) {
- int length = mData.length;
- for (int i = mContentStart; i < mContentEnd; i++) {
- MediaSet set = mData[i % length];
- if (set != null && id == set.getPath()) {
- return i;
- }
- }
- return -1;
- }
-
- private void clearSlot(int slotIndex) {
- mData[slotIndex] = null;
- mCoverItem[slotIndex] = null;
- mTotalCount[slotIndex] = 0;
- mItemVersion[slotIndex] = MediaObject.INVALID_DATA_VERSION;
- mSetVersion[slotIndex] = MediaObject.INVALID_DATA_VERSION;
- }
-
- private void setContentWindow(int contentStart, int contentEnd) {
- if (contentStart == mContentStart && contentEnd == mContentEnd) return;
- int length = mCoverItem.length;
-
- int start = this.mContentStart;
- int end = this.mContentEnd;
-
- mContentStart = contentStart;
- mContentEnd = contentEnd;
-
- if (contentStart >= end || start >= contentEnd) {
- for (int i = start, n = end; i < n; ++i) {
- clearSlot(i % length);
- }
- } else {
- for (int i = start; i < contentStart; ++i) {
- clearSlot(i % length);
- }
- for (int i = contentEnd, n = end; i < n; ++i) {
- clearSlot(i % length);
- }
- }
- mReloadTask.notifyDirty();
- }
-
- public void setActiveWindow(int start, int end) {
- if (start == mActiveStart && end == mActiveEnd) return;
-
- Utils.assertTrue(start <= end
- && end - start <= mCoverItem.length && end <= mSize);
-
- mActiveStart = start;
- mActiveEnd = end;
-
- int length = mCoverItem.length;
- // If no data is visible, keep the cache content
- if (start == end) return;
-
- int contentStart = Utils.clamp((start + end) / 2 - length / 2,
- 0, Math.max(0, mSize - length));
- int contentEnd = Math.min(contentStart + length, mSize);
- if (mContentStart > start || mContentEnd < end
- || Math.abs(contentStart - mContentStart) > MIN_LOAD_COUNT) {
- setContentWindow(contentStart, contentEnd);
- }
- }
-
- private class MySourceListener implements ContentListener {
- @Override
- public void onContentDirty() {
- mReloadTask.notifyDirty();
- }
- }
-
- public void setModelListener(DataListener listener) {
- mDataListener = listener;
- }
-
- public void setLoadingListener(LoadingListener listener) {
- mLoadingListener = listener;
- }
-
- private static class UpdateInfo {
- public long version;
- public int index;
-
- public int size;
- public MediaSet item;
- public MediaItem cover;
- public int totalCount;
- }
-
- private class GetUpdateInfo implements Callable<UpdateInfo> {
-
- private final long mVersion;
-
- public GetUpdateInfo(long version) {
- mVersion = version;
- }
-
- private int getInvalidIndex(long version) {
- long setVersion[] = mSetVersion;
- int length = setVersion.length;
- for (int i = mContentStart, n = mContentEnd; i < n; ++i) {
- int index = i % length;
- if (setVersion[i % length] != version) return i;
- }
- return INDEX_NONE;
- }
-
- @Override
- public UpdateInfo call() throws Exception {
- int index = getInvalidIndex(mVersion);
- if (index == INDEX_NONE && mSourceVersion == mVersion) return null;
- UpdateInfo info = new UpdateInfo();
- info.version = mSourceVersion;
- info.index = index;
- info.size = mSize;
- return info;
- }
- }
-
- private class UpdateContent implements Callable<Void> {
- private final UpdateInfo mUpdateInfo;
-
- public UpdateContent(UpdateInfo info) {
- mUpdateInfo = info;
- }
-
- @Override
- public Void call() {
- // Avoid notifying listeners of status change after pause
- // Otherwise gallery will be in inconsistent state after resume.
- if (mReloadTask == null) return null;
- UpdateInfo info = mUpdateInfo;
- mSourceVersion = info.version;
- if (mSize != info.size) {
- mSize = info.size;
- if (mDataListener != null) mDataListener.onSizeChanged(mSize);
- if (mContentEnd > mSize) mContentEnd = mSize;
- if (mActiveEnd > mSize) mActiveEnd = mSize;
- }
- // Note: info.index could be INDEX_NONE, i.e., -1
- if (info.index >= mContentStart && info.index < mContentEnd) {
- int pos = info.index % mCoverItem.length;
- mSetVersion[pos] = info.version;
- long itemVersion = info.item.getDataVersion();
- if (mItemVersion[pos] == itemVersion) return null;
- mItemVersion[pos] = itemVersion;
- mData[pos] = info.item;
- mCoverItem[pos] = info.cover;
- mTotalCount[pos] = info.totalCount;
- if (mDataListener != null
- && info.index >= mActiveStart && info.index < mActiveEnd) {
- mDataListener.onContentChanged(info.index);
- }
- }
- return null;
- }
- }
-
- private <T> T executeAndWait(Callable<T> callable) {
- FutureTask<T> task = new FutureTask<T>(callable);
- mMainHandler.sendMessage(
- mMainHandler.obtainMessage(MSG_RUN_OBJECT, task));
- try {
- return task.get();
- } catch (InterruptedException e) {
- return null;
- } catch (ExecutionException e) {
- throw new RuntimeException(e);
- }
- }
-
- // TODO: load active range first
- private class ReloadTask extends Thread {
- private volatile boolean mActive = true;
- private volatile boolean mDirty = true;
- private volatile boolean mIsLoading = false;
-
- private void updateLoading(boolean loading) {
- if (mIsLoading == loading) return;
- mIsLoading = loading;
- mMainHandler.sendEmptyMessage(loading ? MSG_LOAD_START : MSG_LOAD_FINISH);
- }
-
- @Override
- public void run() {
- Process.setThreadPriority(Process.THREAD_PRIORITY_BACKGROUND);
-
- boolean updateComplete = false;
- while (mActive) {
- synchronized (this) {
- if (mActive && !mDirty && updateComplete) {
- if (!mSource.isLoading()) updateLoading(false);
- Utils.waitWithoutInterrupt(this);
- continue;
- }
- }
- mDirty = false;
- updateLoading(true);
-
- long version = mSource.reload();
- UpdateInfo info = executeAndWait(new GetUpdateInfo(version));
- updateComplete = info == null;
- if (updateComplete) continue;
- if (info.version != version) {
- info.version = version;
- info.size = mSource.getSubMediaSetCount();
-
- // If the size becomes smaller after reload(), we may
- // receive from GetUpdateInfo an index which is too
- // big. Because the main thread is not aware of the size
- // change until we call UpdateContent.
- if (info.index >= info.size) {
- info.index = INDEX_NONE;
- }
- }
- if (info.index != INDEX_NONE) {
- info.item = mSource.getSubMediaSet(info.index);
- if (info.item == null) continue;
- info.cover = info.item.getCoverMediaItem();
- info.totalCount = info.item.getTotalMediaItemCount();
- }
- executeAndWait(new UpdateContent(info));
- }
- updateLoading(false);
- }
-
- public synchronized void notifyDirty() {
- mDirty = true;
- notifyAll();
- }
-
- public synchronized void terminate() {
- mActive = false;
- notifyAll();
- }
- }
-}
-
-
diff --git a/src/com/android/gallery3d/app/AlbumSetPage.java b/src/com/android/gallery3d/app/AlbumSetPage.java
deleted file mode 100644
index dd9d8ec41..000000000
--- a/src/com/android/gallery3d/app/AlbumSetPage.java
+++ /dev/null
@@ -1,764 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.app.Activity;
-import android.content.Context;
-import android.content.Intent;
-import android.graphics.Rect;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.Message;
-import android.view.HapticFeedbackConstants;
-import android.view.Menu;
-import android.view.MenuInflater;
-import android.view.MenuItem;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.widget.Button;
-import android.widget.RelativeLayout;
-import android.widget.Toast;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.MediaDetails;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.glrenderer.FadeTexture;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.picasasource.PicasaSource;
-import com.android.gallery3d.settings.GallerySettings;
-import com.android.gallery3d.ui.ActionModeHandler;
-import com.android.gallery3d.ui.ActionModeHandler.ActionModeListener;
-import com.android.gallery3d.ui.AlbumSetSlotRenderer;
-import com.android.gallery3d.ui.DetailsHelper;
-import com.android.gallery3d.ui.DetailsHelper.CloseListener;
-import com.android.gallery3d.ui.GLRoot;
-import com.android.gallery3d.ui.GLView;
-import com.android.gallery3d.ui.SelectionManager;
-import com.android.gallery3d.ui.SlotView;
-import com.android.gallery3d.ui.SynchronizedHandler;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.HelpUtils;
-
-import java.lang.ref.WeakReference;
-import java.util.ArrayList;
-
-public class AlbumSetPage extends ActivityState implements
- SelectionManager.SelectionListener, GalleryActionBar.ClusterRunner,
- EyePosition.EyePositionListener, MediaSet.SyncListener {
- @SuppressWarnings("unused")
- private static final String TAG = "AlbumSetPage";
-
- private static final int MSG_PICK_ALBUM = 1;
-
- public static final String KEY_MEDIA_PATH = "media-path";
- public static final String KEY_SET_TITLE = "set-title";
- public static final String KEY_SET_SUBTITLE = "set-subtitle";
- public static final String KEY_SELECTED_CLUSTER_TYPE = "selected-cluster";
-
- private static final int DATA_CACHE_SIZE = 256;
- private static final int REQUEST_DO_ANIMATION = 1;
-
- private static final int BIT_LOADING_RELOAD = 1;
- private static final int BIT_LOADING_SYNC = 2;
-
- private boolean mIsActive = false;
- private SlotView mSlotView;
- private AlbumSetSlotRenderer mAlbumSetView;
- private Config.AlbumSetPage mConfig;
-
- private MediaSet mMediaSet;
- private String mTitle;
- private String mSubtitle;
- private boolean mShowClusterMenu;
- private GalleryActionBar mActionBar;
- private int mSelectedAction;
-
- protected SelectionManager mSelectionManager;
- private AlbumSetDataLoader mAlbumSetDataAdapter;
-
- private boolean mGetContent;
- private boolean mGetAlbum;
- private ActionModeHandler mActionModeHandler;
- private DetailsHelper mDetailsHelper;
- private MyDetailsSource mDetailsSource;
- private boolean mShowDetails;
- private EyePosition mEyePosition;
- private Handler mHandler;
-
- // The eyes' position of the user, the origin is at the center of the
- // device and the unit is in pixels.
- private float mX;
- private float mY;
- private float mZ;
-
- private Future<Integer> mSyncTask = null;
-
- private int mLoadingBits = 0;
- private boolean mInitialSynced = false;
-
- private Button mCameraButton;
- private boolean mShowedEmptyToastForSelf = false;
-
- @Override
- protected int getBackgroundColorId() {
- return R.color.albumset_background;
- }
-
- private final GLView mRootPane = new GLView() {
- private final float mMatrix[] = new float[16];
-
- @Override
- protected void onLayout(
- boolean changed, int left, int top, int right, int bottom) {
- mEyePosition.resetPosition();
-
- int slotViewTop = mActionBar.getHeight() + mConfig.paddingTop;
- int slotViewBottom = bottom - top - mConfig.paddingBottom;
- int slotViewRight = right - left;
-
- if (mShowDetails) {
- mDetailsHelper.layout(left, slotViewTop, right, bottom);
- } else {
- mAlbumSetView.setHighlightItemPath(null);
- }
-
- mSlotView.layout(0, slotViewTop, slotViewRight, slotViewBottom);
- }
-
- @Override
- protected void render(GLCanvas canvas) {
- canvas.save(GLCanvas.SAVE_FLAG_MATRIX);
- GalleryUtils.setViewPointMatrix(mMatrix,
- getWidth() / 2 + mX, getHeight() / 2 + mY, mZ);
- canvas.multiplyMatrix(mMatrix, 0);
- super.render(canvas);
- canvas.restore();
- }
- };
-
- @Override
- public void onEyePositionChanged(float x, float y, float z) {
- mRootPane.lockRendering();
- mX = x;
- mY = y;
- mZ = z;
- mRootPane.unlockRendering();
- mRootPane.invalidate();
- }
-
- @Override
- public void onBackPressed() {
- if (mShowDetails) {
- hideDetails();
- } else if (mSelectionManager.inSelectionMode()) {
- mSelectionManager.leaveSelectionMode();
- } else {
- super.onBackPressed();
- }
- }
-
- private void getSlotCenter(int slotIndex, int center[]) {
- Rect offset = new Rect();
- mRootPane.getBoundsOf(mSlotView, offset);
- Rect r = mSlotView.getSlotRect(slotIndex);
- int scrollX = mSlotView.getScrollX();
- int scrollY = mSlotView.getScrollY();
- center[0] = offset.left + (r.left + r.right) / 2 - scrollX;
- center[1] = offset.top + (r.top + r.bottom) / 2 - scrollY;
- }
-
- public void onSingleTapUp(int slotIndex) {
- if (!mIsActive) return;
-
- if (mSelectionManager.inSelectionMode()) {
- MediaSet targetSet = mAlbumSetDataAdapter.getMediaSet(slotIndex);
- if (targetSet == null) return; // Content is dirty, we shall reload soon
- mSelectionManager.toggle(targetSet.getPath());
- mSlotView.invalidate();
- } else {
- // Show pressed-up animation for the single-tap.
- mAlbumSetView.setPressedIndex(slotIndex);
- mAlbumSetView.setPressedUp();
- mHandler.sendMessageDelayed(mHandler.obtainMessage(MSG_PICK_ALBUM, slotIndex, 0),
- FadeTexture.DURATION);
- }
- }
-
- private static boolean albumShouldOpenInFilmstrip(MediaSet album) {
- int itemCount = album.getMediaItemCount();
- ArrayList<MediaItem> list = (itemCount == 1) ? album.getMediaItem(0, 1) : null;
- // open in film strip only if there's one item in the album and the item exists
- return (list != null && !list.isEmpty());
- }
-
- WeakReference<Toast> mEmptyAlbumToast = null;
-
- private void showEmptyAlbumToast(int toastLength) {
- Toast toast;
- if (mEmptyAlbumToast != null) {
- toast = mEmptyAlbumToast.get();
- if (toast != null) {
- toast.show();
- return;
- }
- }
- toast = Toast.makeText(mActivity, R.string.empty_album, toastLength);
- mEmptyAlbumToast = new WeakReference<Toast>(toast);
- toast.show();
- }
-
- private void hideEmptyAlbumToast() {
- if (mEmptyAlbumToast != null) {
- Toast toast = mEmptyAlbumToast.get();
- if (toast != null) toast.cancel();
- }
- }
-
- private void pickAlbum(int slotIndex) {
- if (!mIsActive) return;
-
- MediaSet targetSet = mAlbumSetDataAdapter.getMediaSet(slotIndex);
- if (targetSet == null) return; // Content is dirty, we shall reload soon
- if (targetSet.getTotalMediaItemCount() == 0) {
- showEmptyAlbumToast(Toast.LENGTH_SHORT);
- return;
- }
- hideEmptyAlbumToast();
-
- String mediaPath = targetSet.getPath().toString();
-
- Bundle data = new Bundle(getData());
- int[] center = new int[2];
- getSlotCenter(slotIndex, center);
- data.putIntArray(AlbumPage.KEY_SET_CENTER, center);
- if (mGetAlbum && targetSet.isLeafAlbum()) {
- Activity activity = mActivity;
- Intent result = new Intent()
- .putExtra(AlbumPicker.KEY_ALBUM_PATH, targetSet.getPath().toString());
- activity.setResult(Activity.RESULT_OK, result);
- activity.finish();
- } else if (targetSet.getSubMediaSetCount() > 0) {
- data.putString(AlbumSetPage.KEY_MEDIA_PATH, mediaPath);
- mActivity.getStateManager().startStateForResult(
- AlbumSetPage.class, REQUEST_DO_ANIMATION, data);
- } else {
- if (!mGetContent && albumShouldOpenInFilmstrip(targetSet)) {
- data.putParcelable(PhotoPage.KEY_OPEN_ANIMATION_RECT,
- mSlotView.getSlotRect(slotIndex, mRootPane));
- data.putInt(PhotoPage.KEY_INDEX_HINT, 0);
- data.putString(PhotoPage.KEY_MEDIA_SET_PATH,
- mediaPath);
- data.putBoolean(PhotoPage.KEY_START_IN_FILMSTRIP, true);
- data.putBoolean(PhotoPage.KEY_IN_CAMERA_ROLL, targetSet.isCameraRoll());
- mActivity.getStateManager().startStateForResult(
- FilmstripPage.class, AlbumPage.REQUEST_PHOTO, data);
- return;
- }
- data.putString(AlbumPage.KEY_MEDIA_PATH, mediaPath);
-
- // We only show cluster menu in the first AlbumPage in stack
- boolean inAlbum = mActivity.getStateManager().hasStateClass(AlbumPage.class);
- data.putBoolean(AlbumPage.KEY_SHOW_CLUSTER_MENU, !inAlbum);
- mActivity.getStateManager().startStateForResult(
- AlbumPage.class, REQUEST_DO_ANIMATION, data);
- }
- }
-
- private void onDown(int index) {
- mAlbumSetView.setPressedIndex(index);
- }
-
- private void onUp(boolean followedByLongPress) {
- if (followedByLongPress) {
- // Avoid showing press-up animations for long-press.
- mAlbumSetView.setPressedIndex(-1);
- } else {
- mAlbumSetView.setPressedUp();
- }
- }
-
- public void onLongTap(int slotIndex) {
- if (mGetContent || mGetAlbum) return;
- MediaSet set = mAlbumSetDataAdapter.getMediaSet(slotIndex);
- if (set == null) return;
- mSelectionManager.setAutoLeaveSelectionMode(true);
- mSelectionManager.toggle(set.getPath());
- mSlotView.invalidate();
- }
-
- @Override
- public void doCluster(int clusterType) {
- String basePath = mMediaSet.getPath().toString();
- String newPath = FilterUtils.switchClusterPath(basePath, clusterType);
- Bundle data = new Bundle(getData());
- data.putString(AlbumSetPage.KEY_MEDIA_PATH, newPath);
- data.putInt(KEY_SELECTED_CLUSTER_TYPE, clusterType);
- mActivity.getStateManager().switchState(this, AlbumSetPage.class, data);
- }
-
- @Override
- public void onCreate(Bundle data, Bundle restoreState) {
- super.onCreate(data, restoreState);
- initializeViews();
- initializeData(data);
- Context context = mActivity.getAndroidContext();
- mGetContent = data.getBoolean(Gallery.KEY_GET_CONTENT, false);
- mGetAlbum = data.getBoolean(Gallery.KEY_GET_ALBUM, false);
- mTitle = data.getString(AlbumSetPage.KEY_SET_TITLE);
- mSubtitle = data.getString(AlbumSetPage.KEY_SET_SUBTITLE);
- mEyePosition = new EyePosition(context, this);
- mDetailsSource = new MyDetailsSource();
- mActionBar = mActivity.getGalleryActionBar();
- mSelectedAction = data.getInt(AlbumSetPage.KEY_SELECTED_CLUSTER_TYPE,
- FilterUtils.CLUSTER_BY_ALBUM);
-
- mHandler = new SynchronizedHandler(mActivity.getGLRoot()) {
- @Override
- public void handleMessage(Message message) {
- switch (message.what) {
- case MSG_PICK_ALBUM: {
- pickAlbum(message.arg1);
- break;
- }
- default: throw new AssertionError(message.what);
- }
- }
- };
- }
-
- @Override
- public void onDestroy() {
- super.onDestroy();
- cleanupCameraButton();
- mActionModeHandler.destroy();
- }
-
- private boolean setupCameraButton() {
- if (!GalleryUtils.isCameraAvailable(mActivity)) return false;
- RelativeLayout galleryRoot = (RelativeLayout) ((Activity) mActivity)
- .findViewById(R.id.gallery_root);
- if (galleryRoot == null) return false;
-
- mCameraButton = new Button(mActivity);
- mCameraButton.setText(R.string.camera_label);
- mCameraButton.setCompoundDrawablesWithIntrinsicBounds(0, R.drawable.frame_overlay_gallery_camera, 0, 0);
- mCameraButton.setOnClickListener(new OnClickListener() {
- @Override
- public void onClick(View arg0) {
- GalleryUtils.startCameraActivity(mActivity);
- }
- });
- RelativeLayout.LayoutParams lp = new RelativeLayout.LayoutParams(
- RelativeLayout.LayoutParams.WRAP_CONTENT,
- RelativeLayout.LayoutParams.WRAP_CONTENT);
- lp.addRule(RelativeLayout.CENTER_IN_PARENT);
- galleryRoot.addView(mCameraButton, lp);
- return true;
- }
-
- private void cleanupCameraButton() {
- if (mCameraButton == null) return;
- RelativeLayout galleryRoot = (RelativeLayout) ((Activity) mActivity)
- .findViewById(R.id.gallery_root);
- if (galleryRoot == null) return;
- galleryRoot.removeView(mCameraButton);
- mCameraButton = null;
- }
-
- private void showCameraButton() {
- if (mCameraButton == null && !setupCameraButton()) return;
- mCameraButton.setVisibility(View.VISIBLE);
- }
-
- private void hideCameraButton() {
- if (mCameraButton == null) return;
- mCameraButton.setVisibility(View.GONE);
- }
-
- private void clearLoadingBit(int loadingBit) {
- mLoadingBits &= ~loadingBit;
- if (mLoadingBits == 0 && mIsActive) {
- if (mAlbumSetDataAdapter.size() == 0) {
- // If this is not the top of the gallery folder hierarchy,
- // tell the parent AlbumSetPage instance to handle displaying
- // the empty album toast, otherwise show it within this
- // instance
- if (mActivity.getStateManager().getStateCount() > 1) {
- Intent result = new Intent();
- result.putExtra(AlbumPage.KEY_EMPTY_ALBUM, true);
- setStateResult(Activity.RESULT_OK, result);
- mActivity.getStateManager().finishState(this);
- } else {
- mShowedEmptyToastForSelf = true;
- showEmptyAlbumToast(Toast.LENGTH_LONG);
- mSlotView.invalidate();
- showCameraButton();
- }
- return;
- }
- }
- // Hide the empty album toast if we are in the root instance of
- // AlbumSetPage and the album is no longer empty (for instance,
- // after a sync is completed and web albums have been synced)
- if (mShowedEmptyToastForSelf) {
- mShowedEmptyToastForSelf = false;
- hideEmptyAlbumToast();
- hideCameraButton();
- }
- }
-
- private void setLoadingBit(int loadingBit) {
- mLoadingBits |= loadingBit;
- }
-
- @Override
- public void onPause() {
- super.onPause();
- mIsActive = false;
- mAlbumSetDataAdapter.pause();
- mAlbumSetView.pause();
- mActionModeHandler.pause();
- mEyePosition.pause();
- DetailsHelper.pause();
- // Call disableClusterMenu to avoid receiving callback after paused.
- // Don't hide menu here otherwise the list menu will disappear earlier than
- // the action bar, which is janky and unwanted behavior.
- mActionBar.disableClusterMenu(false);
- if (mSyncTask != null) {
- mSyncTask.cancel();
- mSyncTask = null;
- clearLoadingBit(BIT_LOADING_SYNC);
- }
- }
-
- @Override
- public void onResume() {
- super.onResume();
- mIsActive = true;
- setContentPane(mRootPane);
-
- // Set the reload bit here to prevent it exit this page in clearLoadingBit().
- setLoadingBit(BIT_LOADING_RELOAD);
- mAlbumSetDataAdapter.resume();
-
- mAlbumSetView.resume();
- mEyePosition.resume();
- mActionModeHandler.resume();
- if (mShowClusterMenu) {
- mActionBar.enableClusterMenu(mSelectedAction, this);
- }
- if (!mInitialSynced) {
- setLoadingBit(BIT_LOADING_SYNC);
- mSyncTask = mMediaSet.requestSync(AlbumSetPage.this);
- }
- }
-
- private void initializeData(Bundle data) {
- String mediaPath = data.getString(AlbumSetPage.KEY_MEDIA_PATH);
- mMediaSet = mActivity.getDataManager().getMediaSet(mediaPath);
- mSelectionManager.setSourceMediaSet(mMediaSet);
- mAlbumSetDataAdapter = new AlbumSetDataLoader(
- mActivity, mMediaSet, DATA_CACHE_SIZE);
- mAlbumSetDataAdapter.setLoadingListener(new MyLoadingListener());
- mAlbumSetView.setModel(mAlbumSetDataAdapter);
- }
-
- private void initializeViews() {
- mSelectionManager = new SelectionManager(mActivity, true);
- mSelectionManager.setSelectionListener(this);
-
- mConfig = Config.AlbumSetPage.get(mActivity);
- mSlotView = new SlotView(mActivity, mConfig.slotViewSpec);
- mAlbumSetView = new AlbumSetSlotRenderer(
- mActivity, mSelectionManager, mSlotView, mConfig.labelSpec,
- mConfig.placeholderColor);
- mSlotView.setSlotRenderer(mAlbumSetView);
- mSlotView.setListener(new SlotView.SimpleListener() {
- @Override
- public void onDown(int index) {
- AlbumSetPage.this.onDown(index);
- }
-
- @Override
- public void onUp(boolean followedByLongPress) {
- AlbumSetPage.this.onUp(followedByLongPress);
- }
-
- @Override
- public void onSingleTapUp(int slotIndex) {
- AlbumSetPage.this.onSingleTapUp(slotIndex);
- }
-
- @Override
- public void onLongTap(int slotIndex) {
- AlbumSetPage.this.onLongTap(slotIndex);
- }
- });
-
- mActionModeHandler = new ActionModeHandler(mActivity, mSelectionManager);
- mActionModeHandler.setActionModeListener(new ActionModeListener() {
- @Override
- public boolean onActionItemClicked(MenuItem item) {
- return onItemSelected(item);
- }
- });
- mRootPane.addComponent(mSlotView);
- }
-
- @Override
- protected boolean onCreateActionBar(Menu menu) {
- Activity activity = mActivity;
- final boolean inAlbum = mActivity.getStateManager().hasStateClass(AlbumPage.class);
- MenuInflater inflater = getSupportMenuInflater();
-
- if (mGetContent) {
- inflater.inflate(R.menu.pickup, menu);
- int typeBits = mData.getInt(
- Gallery.KEY_TYPE_BITS, DataManager.INCLUDE_IMAGE);
- mActionBar.setTitle(GalleryUtils.getSelectionModePrompt(typeBits));
- } else if (mGetAlbum) {
- inflater.inflate(R.menu.pickup, menu);
- mActionBar.setTitle(R.string.select_album);
- } else {
- inflater.inflate(R.menu.albumset, menu);
- boolean wasShowingClusterMenu = mShowClusterMenu;
- mShowClusterMenu = !inAlbum;
- boolean selectAlbums = !inAlbum &&
- mActionBar.getClusterTypeAction() == FilterUtils.CLUSTER_BY_ALBUM;
- MenuItem selectItem = menu.findItem(R.id.action_select);
- selectItem.setTitle(activity.getString(
- selectAlbums ? R.string.select_album : R.string.select_group));
-
- MenuItem cameraItem = menu.findItem(R.id.action_camera);
- cameraItem.setVisible(GalleryUtils.isCameraAvailable(activity));
-
- FilterUtils.setupMenuItems(mActionBar, mMediaSet.getPath(), false);
-
- Intent helpIntent = HelpUtils.getHelpIntent(activity);
-
- MenuItem helpItem = menu.findItem(R.id.action_general_help);
- helpItem.setVisible(helpIntent != null);
- if (helpIntent != null) helpItem.setIntent(helpIntent);
-
- mActionBar.setTitle(mTitle);
- mActionBar.setSubtitle(mSubtitle);
- if (mShowClusterMenu != wasShowingClusterMenu) {
- if (mShowClusterMenu) {
- mActionBar.enableClusterMenu(mSelectedAction, this);
- } else {
- mActionBar.disableClusterMenu(true);
- }
- }
- }
- return true;
- }
-
- @Override
- protected boolean onItemSelected(MenuItem item) {
- Activity activity = mActivity;
- switch (item.getItemId()) {
- case R.id.action_cancel:
- activity.setResult(Activity.RESULT_CANCELED);
- activity.finish();
- return true;
- case R.id.action_select:
- mSelectionManager.setAutoLeaveSelectionMode(false);
- mSelectionManager.enterSelectionMode();
- return true;
- case R.id.action_details:
- if (mAlbumSetDataAdapter.size() != 0) {
- if (mShowDetails) {
- hideDetails();
- } else {
- showDetails();
- }
- } else {
- Toast.makeText(activity,
- activity.getText(R.string.no_albums_alert),
- Toast.LENGTH_SHORT).show();
- }
- return true;
- case R.id.action_camera: {
- GalleryUtils.startCameraActivity(activity);
- return true;
- }
- case R.id.action_manage_offline: {
- Bundle data = new Bundle();
- String mediaPath = mActivity.getDataManager().getTopSetPath(
- DataManager.INCLUDE_ALL);
- data.putString(AlbumSetPage.KEY_MEDIA_PATH, mediaPath);
- mActivity.getStateManager().startState(ManageCachePage.class, data);
- return true;
- }
- case R.id.action_sync_picasa_albums: {
- PicasaSource.requestSync(activity);
- return true;
- }
- case R.id.action_settings: {
- activity.startActivity(new Intent(activity, GallerySettings.class));
- return true;
- }
- default:
- return false;
- }
- }
-
- @Override
- protected void onStateResult(int requestCode, int resultCode, Intent data) {
- if (data != null && data.getBooleanExtra(AlbumPage.KEY_EMPTY_ALBUM, false)) {
- showEmptyAlbumToast(Toast.LENGTH_SHORT);
- }
- switch (requestCode) {
- case REQUEST_DO_ANIMATION: {
- mSlotView.startRisingAnimation();
- }
- }
- }
-
- private String getSelectedString() {
- int count = mSelectionManager.getSelectedCount();
- int action = mActionBar.getClusterTypeAction();
- int string = action == FilterUtils.CLUSTER_BY_ALBUM
- ? R.plurals.number_of_albums_selected
- : R.plurals.number_of_groups_selected;
- String format = mActivity.getResources().getQuantityString(string, count);
- return String.format(format, count);
- }
-
- @Override
- public void onSelectionModeChange(int mode) {
- switch (mode) {
- case SelectionManager.ENTER_SELECTION_MODE: {
- mActionBar.disableClusterMenu(true);
- mActionModeHandler.startActionMode();
- performHapticFeedback(HapticFeedbackConstants.LONG_PRESS);
- break;
- }
- case SelectionManager.LEAVE_SELECTION_MODE: {
- mActionModeHandler.finishActionMode();
- if (mShowClusterMenu) {
- mActionBar.enableClusterMenu(mSelectedAction, this);
- }
- mRootPane.invalidate();
- break;
- }
- case SelectionManager.SELECT_ALL_MODE: {
- mActionModeHandler.updateSupportedOperation();
- mRootPane.invalidate();
- break;
- }
- }
- }
-
- @Override
- public void onSelectionChange(Path path, boolean selected) {
- mActionModeHandler.setTitle(getSelectedString());
- mActionModeHandler.updateSupportedOperation(path, selected);
- }
-
- private void hideDetails() {
- mShowDetails = false;
- mDetailsHelper.hide();
- mAlbumSetView.setHighlightItemPath(null);
- mSlotView.invalidate();
- }
-
- private void showDetails() {
- mShowDetails = true;
- if (mDetailsHelper == null) {
- mDetailsHelper = new DetailsHelper(mActivity, mRootPane, mDetailsSource);
- mDetailsHelper.setCloseListener(new CloseListener() {
- @Override
- public void onClose() {
- hideDetails();
- }
- });
- }
- mDetailsHelper.show();
- }
-
- @Override
- public void onSyncDone(final MediaSet mediaSet, final int resultCode) {
- if (resultCode == MediaSet.SYNC_RESULT_ERROR) {
- Log.d(TAG, "onSyncDone: " + Utils.maskDebugInfo(mediaSet.getName()) + " result="
- + resultCode);
- }
- ((Activity) mActivity).runOnUiThread(new Runnable() {
- @Override
- public void run() {
- GLRoot root = mActivity.getGLRoot();
- root.lockRenderThread();
- try {
- if (resultCode == MediaSet.SYNC_RESULT_SUCCESS) {
- mInitialSynced = true;
- }
- clearLoadingBit(BIT_LOADING_SYNC);
- if (resultCode == MediaSet.SYNC_RESULT_ERROR && mIsActive) {
- Log.w(TAG, "failed to load album set");
- }
- } finally {
- root.unlockRenderThread();
- }
- }
- });
- }
-
- private class MyLoadingListener implements LoadingListener {
- @Override
- public void onLoadingStarted() {
- setLoadingBit(BIT_LOADING_RELOAD);
- }
-
- @Override
- public void onLoadingFinished(boolean loadingFailed) {
- clearLoadingBit(BIT_LOADING_RELOAD);
- }
- }
-
- private class MyDetailsSource implements DetailsHelper.DetailsSource {
- private int mIndex;
-
- @Override
- public int size() {
- return mAlbumSetDataAdapter.size();
- }
-
- @Override
- public int setIndex() {
- Path id = mSelectionManager.getSelected(false).get(0);
- mIndex = mAlbumSetDataAdapter.findSet(id);
- return mIndex;
- }
-
- @Override
- public MediaDetails getDetails() {
- MediaObject item = mAlbumSetDataAdapter.getMediaSet(mIndex);
- if (item != null) {
- mAlbumSetView.setHighlightItemPath(item.getPath());
- return item.getDetails();
- } else {
- return null;
- }
- }
- }
-}
diff --git a/src/com/android/gallery3d/app/AppBridge.java b/src/com/android/gallery3d/app/AppBridge.java
deleted file mode 100644
index ee55fa6db..000000000
--- a/src/com/android/gallery3d/app/AppBridge.java
+++ /dev/null
@@ -1,72 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.app;
-
-import android.graphics.Rect;
-import android.os.Parcel;
-import android.os.Parcelable;
-
-import com.android.gallery3d.ui.ScreenNail;
-
-// This is the bridge to connect a PhotoPage to the external environment.
-public abstract class AppBridge implements Parcelable {
- @Override
- public int describeContents() {
- return 0;
- }
-
- @Override
- public void writeToParcel(Parcel dest, int flags) {
- }
-
- //////////////////////////////////////////////////////////////////////////
- // These are requests sent from PhotoPage to the app
- //////////////////////////////////////////////////////////////////////////
-
- public abstract boolean isPanorama();
- public abstract boolean isStaticCamera();
- public abstract ScreenNail attachScreenNail();
- public abstract void detachScreenNail();
-
- // Return true if the tap is consumed.
- public abstract boolean onSingleTapUp(int x, int y);
-
- // This is used to notify that the screen nail will be drawn in full screen
- // or not in next draw() call.
- public abstract void onFullScreenChanged(boolean full);
-
- //////////////////////////////////////////////////////////////////////////
- // These are requests send from app to PhotoPage
- //////////////////////////////////////////////////////////////////////////
-
- public interface Server {
- // Set the camera frame relative to GLRootView.
- public void setCameraRelativeFrame(Rect frame);
- // Switch to the previous or next picture using the capture animation.
- // The offset is -1 to switch to the previous picture, 1 to switch to
- // the next picture.
- public boolean switchWithCaptureAnimation(int offset);
- // Enable or disable the swiping gestures (the default is enabled).
- public void setSwipingEnabled(boolean enabled);
- // Notify that the ScreenNail is changed.
- public void notifyScreenNailChanged();
- // Add a new media item to the secure album.
- public void addSecureAlbumItem(boolean isVideo, int id);
- }
-
- // If server is null, the services are not available.
- public abstract void setServer(Server server);
-}
diff --git a/src/com/android/gallery3d/app/BatchService.java b/src/com/android/gallery3d/app/BatchService.java
deleted file mode 100644
index 564001d5b..000000000
--- a/src/com/android/gallery3d/app/BatchService.java
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.app.Service;
-import android.content.Intent;
-import android.os.Binder;
-import android.os.IBinder;
-
-import com.android.gallery3d.util.ThreadPool;
-
-public class BatchService extends Service {
-
- public class LocalBinder extends Binder {
- BatchService getService() {
- return BatchService.this;
- }
- }
-
- private final IBinder mBinder = new LocalBinder();
- private ThreadPool mThreadPool = new ThreadPool(1, 1);
-
- @Override
- public IBinder onBind(Intent intent) {
- return mBinder;
- }
-
- // The threadpool returned by getThreadPool must have only 1 thread
- // running at a time, as MenuExecutor (atrociously) depends on this
- // guarantee for synchronization.
- public ThreadPool getThreadPool() {
- return mThreadPool;
- }
-}
diff --git a/src/com/android/gallery3d/app/CommonControllerOverlay.java b/src/com/android/gallery3d/app/CommonControllerOverlay.java
deleted file mode 100644
index 9adb4e7a8..000000000
--- a/src/com/android/gallery3d/app/CommonControllerOverlay.java
+++ /dev/null
@@ -1,346 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.Rect;
-import android.view.Gravity;
-import android.view.KeyEvent;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.widget.FrameLayout;
-import android.widget.ImageView;
-import android.widget.ImageView.ScaleType;
-import android.widget.LinearLayout;
-import android.widget.ProgressBar;
-import android.widget.RelativeLayout;
-import android.widget.TextView;
-
-import com.android.gallery3d.R;
-
-/**
- * The common playback controller for the Movie Player or Video Trimming.
- */
-public abstract class CommonControllerOverlay extends FrameLayout implements
- ControllerOverlay,
- OnClickListener,
- TimeBar.Listener {
-
- protected enum State {
- PLAYING,
- PAUSED,
- ENDED,
- ERROR,
- LOADING
- }
-
- private static final float ERROR_MESSAGE_RELATIVE_PADDING = 1.0f / 6;
-
- protected Listener mListener;
-
- protected final View mBackground;
- protected TimeBar mTimeBar;
-
- protected View mMainView;
- protected final LinearLayout mLoadingView;
- protected final TextView mErrorView;
- protected final ImageView mPlayPauseReplayView;
-
- protected State mState;
-
- protected boolean mCanReplay = true;
-
- public void setSeekable(boolean canSeek) {
- mTimeBar.setSeekable(canSeek);
- }
-
- public CommonControllerOverlay(Context context) {
- super(context);
-
- mState = State.LOADING;
- // TODO: Move the following layout code into xml file.
- LayoutParams wrapContent =
- new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
- LayoutParams matchParent =
- new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
-
- mBackground = new View(context);
- mBackground.setBackgroundColor(context.getResources().getColor(R.color.darker_transparent));
- addView(mBackground, matchParent);
-
- // Depending on the usage, the timeBar can show a single scrubber, or
- // multiple ones for trimming.
- createTimeBar(context);
- addView(mTimeBar, wrapContent);
- mTimeBar.setContentDescription(
- context.getResources().getString(R.string.accessibility_time_bar));
- mLoadingView = new LinearLayout(context);
- mLoadingView.setOrientation(LinearLayout.VERTICAL);
- mLoadingView.setGravity(Gravity.CENTER_HORIZONTAL);
- ProgressBar spinner = new ProgressBar(context);
- spinner.setIndeterminate(true);
- mLoadingView.addView(spinner, wrapContent);
- TextView loadingText = createOverlayTextView(context);
- loadingText.setText(R.string.loading_video);
- mLoadingView.addView(loadingText, wrapContent);
- addView(mLoadingView, wrapContent);
-
- mPlayPauseReplayView = new ImageView(context);
- mPlayPauseReplayView.setImageResource(R.drawable.ic_vidcontrol_play);
- mPlayPauseReplayView.setContentDescription(
- context.getResources().getString(R.string.accessibility_play_video));
- mPlayPauseReplayView.setBackgroundResource(R.drawable.bg_vidcontrol);
- mPlayPauseReplayView.setScaleType(ScaleType.CENTER);
- mPlayPauseReplayView.setFocusable(true);
- mPlayPauseReplayView.setClickable(true);
- mPlayPauseReplayView.setOnClickListener(this);
- addView(mPlayPauseReplayView, wrapContent);
-
- mErrorView = createOverlayTextView(context);
- addView(mErrorView, matchParent);
-
- RelativeLayout.LayoutParams params =
- new RelativeLayout.LayoutParams(
- LayoutParams.MATCH_PARENT, LayoutParams.MATCH_PARENT);
- setLayoutParams(params);
- hide();
- }
-
- abstract protected void createTimeBar(Context context);
-
- private TextView createOverlayTextView(Context context) {
- TextView view = new TextView(context);
- view.setGravity(Gravity.CENTER);
- view.setTextColor(0xFFFFFFFF);
- view.setPadding(0, 15, 0, 15);
- return view;
- }
-
- @Override
- public void setListener(Listener listener) {
- this.mListener = listener;
- }
-
- @Override
- public void setCanReplay(boolean canReplay) {
- this.mCanReplay = canReplay;
- }
-
- @Override
- public View getView() {
- return this;
- }
-
- @Override
- public void showPlaying() {
- mState = State.PLAYING;
- showMainView(mPlayPauseReplayView);
- }
-
- @Override
- public void showPaused() {
- mState = State.PAUSED;
- showMainView(mPlayPauseReplayView);
- }
-
- @Override
- public void showEnded() {
- mState = State.ENDED;
- if (mCanReplay) showMainView(mPlayPauseReplayView);
- }
-
- @Override
- public void showLoading() {
- mState = State.LOADING;
- showMainView(mLoadingView);
- }
-
- @Override
- public void showErrorMessage(String message) {
- mState = State.ERROR;
- int padding = (int) (getMeasuredWidth() * ERROR_MESSAGE_RELATIVE_PADDING);
- mErrorView.setPadding(
- padding, mErrorView.getPaddingTop(), padding, mErrorView.getPaddingBottom());
- mErrorView.setText(message);
- showMainView(mErrorView);
- }
-
- @Override
- public void setTimes(int currentTime, int totalTime,
- int trimStartTime, int trimEndTime) {
- mTimeBar.setTime(currentTime, totalTime, trimStartTime, trimEndTime);
- }
-
- public void hide() {
- mPlayPauseReplayView.setVisibility(View.INVISIBLE);
- mLoadingView.setVisibility(View.INVISIBLE);
- mBackground.setVisibility(View.INVISIBLE);
- mTimeBar.setVisibility(View.INVISIBLE);
- setVisibility(View.INVISIBLE);
- setFocusable(true);
- requestFocus();
- }
-
- private void showMainView(View view) {
- mMainView = view;
- mErrorView.setVisibility(mMainView == mErrorView ? View.VISIBLE : View.INVISIBLE);
- mLoadingView.setVisibility(mMainView == mLoadingView ? View.VISIBLE : View.INVISIBLE);
- mPlayPauseReplayView.setVisibility(
- mMainView == mPlayPauseReplayView ? View.VISIBLE : View.INVISIBLE);
- show();
- }
-
- @Override
- public void show() {
- updateViews();
- setVisibility(View.VISIBLE);
- setFocusable(false);
- }
-
- @Override
- public void onClick(View view) {
- if (mListener != null) {
- if (view == mPlayPauseReplayView) {
- if (mState == State.ENDED) {
- if (mCanReplay) {
- mListener.onReplay();
- }
- } else if (mState == State.PAUSED || mState == State.PLAYING) {
- mListener.onPlayPause();
- }
- }
- }
- }
-
- @Override
- public boolean onKeyDown(int keyCode, KeyEvent event) {
- return super.onKeyDown(keyCode, event);
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- if (super.onTouchEvent(event)) {
- return true;
- }
- return false;
- }
-
- // The paddings of 4 sides which covered by system components. E.g.
- // +-----------------+\
- // | Action Bar | insets.top
- // +-----------------+/
- // | |
- // | Content Area | insets.right = insets.left = 0
- // | |
- // +-----------------+\
- // | Navigation Bar | insets.bottom
- // +-----------------+/
- // Please see View.fitSystemWindows() for more details.
- private final Rect mWindowInsets = new Rect();
-
- @Override
- protected boolean fitSystemWindows(Rect insets) {
- // We don't set the paddings of this View, otherwise,
- // the content will get cropped outside window
- mWindowInsets.set(insets);
- return true;
- }
-
- @Override
- protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
- Rect insets = mWindowInsets;
- int pl = insets.left; // the left paddings
- int pr = insets.right;
- int pt = insets.top;
- int pb = insets.bottom;
-
- int h = bottom - top;
- int w = right - left;
- boolean error = mErrorView.getVisibility() == View.VISIBLE;
-
- int y = h - pb;
- // Put both TimeBar and Background just above the bottom system
- // component.
- // But extend the background to the width of the screen, since we don't
- // care if it will be covered by a system component and it looks better.
- mBackground.layout(0, y - mTimeBar.getBarHeight(), w, y);
- mTimeBar.layout(pl, y - mTimeBar.getPreferredHeight(), w - pr, y);
-
- // Put the play/pause/next/ previous button in the center of the screen
- layoutCenteredView(mPlayPauseReplayView, 0, 0, w, h);
-
- if (mMainView != null) {
- layoutCenteredView(mMainView, 0, 0, w, h);
- }
- }
-
- private void layoutCenteredView(View view, int l, int t, int r, int b) {
- int cw = view.getMeasuredWidth();
- int ch = view.getMeasuredHeight();
- int cl = (r - l - cw) / 2;
- int ct = (b - t - ch) / 2;
- view.layout(cl, ct, cl + cw, ct + ch);
- }
-
- @Override
- protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
- super.onMeasure(widthMeasureSpec, heightMeasureSpec);
- measureChildren(widthMeasureSpec, heightMeasureSpec);
- }
-
- protected void updateViews() {
- mBackground.setVisibility(View.VISIBLE);
- mTimeBar.setVisibility(View.VISIBLE);
- Resources resources = getContext().getResources();
- int imageResource = R.drawable.ic_vidcontrol_reload;
- String contentDescription = resources.getString(R.string.accessibility_reload_video);
- if (mState == State.PAUSED) {
- imageResource = R.drawable.ic_vidcontrol_play;
- contentDescription = resources.getString(R.string.accessibility_play_video);
- } else if (mState == State.PLAYING) {
- imageResource = R.drawable.ic_vidcontrol_pause;
- contentDescription = resources.getString(R.string.accessibility_pause_video);
- }
-
- mPlayPauseReplayView.setImageResource(imageResource);
- mPlayPauseReplayView.setContentDescription(contentDescription);
- mPlayPauseReplayView.setVisibility(
- (mState != State.LOADING && mState != State.ERROR &&
- !(mState == State.ENDED && !mCanReplay))
- ? View.VISIBLE : View.GONE);
- requestLayout();
- }
-
- // TimeBar listener
-
- @Override
- public void onScrubbingStart() {
- mListener.onSeekStart();
- }
-
- @Override
- public void onScrubbingMove(int time) {
- mListener.onSeekMove(time);
- }
-
- @Override
- public void onScrubbingEnd(int time, int trimStartTime, int trimEndTime) {
- mListener.onSeekEnd(time, trimStartTime, trimEndTime);
- }
-}
diff --git a/src/com/android/gallery3d/app/Config.java b/src/com/android/gallery3d/app/Config.java
deleted file mode 100644
index 7183acc33..000000000
--- a/src/com/android/gallery3d/app/Config.java
+++ /dev/null
@@ -1,127 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.content.Context;
-import android.content.res.Resources;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.ui.AlbumSetSlotRenderer;
-import com.android.gallery3d.ui.SlotView;
-
-final class Config {
- public static class AlbumSetPage {
- private static AlbumSetPage sInstance;
-
- public SlotView.Spec slotViewSpec;
- public AlbumSetSlotRenderer.LabelSpec labelSpec;
- public int paddingTop;
- public int paddingBottom;
- public int placeholderColor;
-
- public static synchronized AlbumSetPage get(Context context) {
- if (sInstance == null) {
- sInstance = new AlbumSetPage(context);
- }
- return sInstance;
- }
-
- private AlbumSetPage(Context context) {
- Resources r = context.getResources();
-
- placeholderColor = r.getColor(R.color.albumset_placeholder);
-
- slotViewSpec = new SlotView.Spec();
- slotViewSpec.rowsLand = r.getInteger(R.integer.albumset_rows_land);
- slotViewSpec.rowsPort = r.getInteger(R.integer.albumset_rows_port);
- slotViewSpec.slotGap = r.getDimensionPixelSize(R.dimen.albumset_slot_gap);
- slotViewSpec.slotHeightAdditional = 0;
-
- paddingTop = r.getDimensionPixelSize(R.dimen.albumset_padding_top);
- paddingBottom = r.getDimensionPixelSize(R.dimen.albumset_padding_bottom);
-
- labelSpec = new AlbumSetSlotRenderer.LabelSpec();
- labelSpec.labelBackgroundHeight = r.getDimensionPixelSize(
- R.dimen.albumset_label_background_height);
- labelSpec.titleOffset = r.getDimensionPixelSize(
- R.dimen.albumset_title_offset);
- labelSpec.countOffset = r.getDimensionPixelSize(
- R.dimen.albumset_count_offset);
- labelSpec.titleFontSize = r.getDimensionPixelSize(
- R.dimen.albumset_title_font_size);
- labelSpec.countFontSize = r.getDimensionPixelSize(
- R.dimen.albumset_count_font_size);
- labelSpec.leftMargin = r.getDimensionPixelSize(
- R.dimen.albumset_left_margin);
- labelSpec.titleRightMargin = r.getDimensionPixelSize(
- R.dimen.albumset_title_right_margin);
- labelSpec.iconSize = r.getDimensionPixelSize(
- R.dimen.albumset_icon_size);
- labelSpec.backgroundColor = r.getColor(
- R.color.albumset_label_background);
- labelSpec.titleColor = r.getColor(R.color.albumset_label_title);
- labelSpec.countColor = r.getColor(R.color.albumset_label_count);
- }
- }
-
- public static class AlbumPage {
- private static AlbumPage sInstance;
-
- public SlotView.Spec slotViewSpec;
- public int placeholderColor;
-
- public static synchronized AlbumPage get(Context context) {
- if (sInstance == null) {
- sInstance = new AlbumPage(context);
- }
- return sInstance;
- }
-
- private AlbumPage(Context context) {
- Resources r = context.getResources();
-
- placeholderColor = r.getColor(R.color.album_placeholder);
-
- slotViewSpec = new SlotView.Spec();
- slotViewSpec.rowsLand = r.getInteger(R.integer.album_rows_land);
- slotViewSpec.rowsPort = r.getInteger(R.integer.album_rows_port);
- slotViewSpec.slotGap = r.getDimensionPixelSize(R.dimen.album_slot_gap);
- }
- }
-
- public static class ManageCachePage extends AlbumSetPage {
- private static ManageCachePage sInstance;
-
- public final int cachePinSize;
- public final int cachePinMargin;
-
- public static synchronized ManageCachePage get(Context context) {
- if (sInstance == null) {
- sInstance = new ManageCachePage(context);
- }
- return sInstance;
- }
-
- public ManageCachePage(Context context) {
- super(context);
- Resources r = context.getResources();
- cachePinSize = r.getDimensionPixelSize(R.dimen.cache_pin_size);
- cachePinMargin = r.getDimensionPixelSize(R.dimen.cache_pin_margin);
- }
- }
-}
-
diff --git a/src/com/android/gallery3d/app/ControllerOverlay.java b/src/com/android/gallery3d/app/ControllerOverlay.java
deleted file mode 100644
index 078f59e28..000000000
--- a/src/com/android/gallery3d/app/ControllerOverlay.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.view.View;
-
-public interface ControllerOverlay {
-
- interface Listener {
- void onPlayPause();
- void onSeekStart();
- void onSeekMove(int time);
- void onSeekEnd(int time, int trimStartTime, int trimEndTime);
- void onShown();
- void onHidden();
- void onReplay();
- }
-
- void setListener(Listener listener);
-
- void setCanReplay(boolean canReplay);
-
- /**
- * @return The overlay view that should be added to the player.
- */
- View getView();
-
- void show();
-
- void showPlaying();
-
- void showPaused();
-
- void showEnded();
-
- void showLoading();
-
- void showErrorMessage(String message);
-
- void setTimes(int currentTime, int totalTime,
- int trimStartTime, int trimEndTime);
-}
diff --git a/src/com/android/gallery3d/app/DialogPicker.java b/src/com/android/gallery3d/app/DialogPicker.java
deleted file mode 100644
index 7ca86e5b4..000000000
--- a/src/com/android/gallery3d/app/DialogPicker.java
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.content.Intent;
-import android.os.Bundle;
-
-import com.android.gallery3d.util.GalleryUtils;
-
-public class DialogPicker extends PickerActivity {
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
-
- int typeBits = GalleryUtils.determineTypeBits(this, getIntent());
- setTitle(GalleryUtils.getSelectionModePrompt(typeBits));
- Intent intent = getIntent();
- Bundle extras = intent.getExtras();
- Bundle data = extras == null ? new Bundle() : new Bundle(extras);
-
- data.putBoolean(Gallery.KEY_GET_CONTENT, true);
- data.putString(AlbumSetPage.KEY_MEDIA_PATH,
- getDataManager().getTopSetPath(typeBits));
- getStateManager().startState(AlbumSetPage.class, data);
- }
-}
diff --git a/src/com/android/gallery3d/app/EyePosition.java b/src/com/android/gallery3d/app/EyePosition.java
deleted file mode 100644
index d99d97b0e..000000000
--- a/src/com/android/gallery3d/app/EyePosition.java
+++ /dev/null
@@ -1,226 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.content.Context;
-import android.hardware.Sensor;
-import android.hardware.SensorEvent;
-import android.hardware.SensorEventListener;
-import android.hardware.SensorManager;
-import android.os.SystemClock;
-import android.util.FloatMath;
-import android.view.Display;
-import android.view.Surface;
-import android.view.WindowManager;
-
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.util.GalleryUtils;
-
-public class EyePosition {
- @SuppressWarnings("unused")
- private static final String TAG = "EyePosition";
-
- public interface EyePositionListener {
- public void onEyePositionChanged(float x, float y, float z);
- }
-
- private static final float GYROSCOPE_THRESHOLD = 0.15f;
- private static final float GYROSCOPE_LIMIT = 10f;
- private static final int GYROSCOPE_SETTLE_DOWN = 15;
- private static final float GYROSCOPE_RESTORE_FACTOR = 0.995f;
-
- private static final float USER_ANGEL = (float) Math.toRadians(10);
- private static final float USER_ANGEL_COS = FloatMath.cos(USER_ANGEL);
- private static final float USER_ANGEL_SIN = FloatMath.sin(USER_ANGEL);
- private static final float MAX_VIEW_RANGE = (float) 0.5;
- private static final int NOT_STARTED = -1;
-
- private static final float USER_DISTANCE_METER = 0.3f;
-
- private Context mContext;
- private EyePositionListener mListener;
- private Display mDisplay;
- // The eyes' position of the user, the origin is at the center of the
- // device and the unit is in pixels.
- private float mX;
- private float mY;
- private float mZ;
-
- private final float mUserDistance; // in pixel
- private final float mLimit;
- private long mStartTime = NOT_STARTED;
- private Sensor mSensor;
- private PositionListener mPositionListener = new PositionListener();
-
- private int mGyroscopeCountdown = 0;
-
- public EyePosition(Context context, EyePositionListener listener) {
- mContext = context;
- mListener = listener;
- mUserDistance = GalleryUtils.meterToPixel(USER_DISTANCE_METER);
- mLimit = mUserDistance * MAX_VIEW_RANGE;
-
- WindowManager wManager = (WindowManager) mContext
- .getSystemService(Context.WINDOW_SERVICE);
- mDisplay = wManager.getDefaultDisplay();
-
- // The 3D effect where the photo albums fan out in 3D based on angle
- // of device tilt is currently disabled.
-/*
- SensorManager sManager = (SensorManager) mContext
- .getSystemService(Context.SENSOR_SERVICE);
- mSensor = sManager.getDefaultSensor(Sensor.TYPE_GYROSCOPE);
- if (mSensor == null) {
- Log.w(TAG, "no gyroscope, use accelerometer instead");
- mSensor = sManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER);
- }
- if (mSensor == null) {
- Log.w(TAG, "no sensor available");
- }
-*/
- }
-
- public void resetPosition() {
- mStartTime = NOT_STARTED;
- mX = mY = 0;
- mZ = -mUserDistance;
- mListener.onEyePositionChanged(mX, mY, mZ);
- }
-
- /*
- * We assume the user is at the following position
- *
- * /|\ user's eye
- * | /
- * -G(gravity) | /
- * |_/
- * / |/_____\ -Y (-y direction of device)
- * user angel
- */
- private void onAccelerometerChanged(float gx, float gy, float gz) {
-
- float x = gx, y = gy, z = gz;
-
- switch (mDisplay.getRotation()) {
- case Surface.ROTATION_90: x = -gy; y= gx; break;
- case Surface.ROTATION_180: x = -gx; y = -gy; break;
- case Surface.ROTATION_270: x = gy; y = -gx; break;
- }
-
- float temp = x * x + y * y + z * z;
- float t = -y /temp;
-
- float tx = t * x;
- float ty = -1 + t * y;
- float tz = t * z;
-
- float length = FloatMath.sqrt(tx * tx + ty * ty + tz * tz);
- float glength = FloatMath.sqrt(temp);
-
- mX = Utils.clamp((x * USER_ANGEL_COS / glength
- + tx * USER_ANGEL_SIN / length) * mUserDistance,
- -mLimit, mLimit);
- mY = -Utils.clamp((y * USER_ANGEL_COS / glength
- + ty * USER_ANGEL_SIN / length) * mUserDistance,
- -mLimit, mLimit);
- mZ = -FloatMath.sqrt(
- mUserDistance * mUserDistance - mX * mX - mY * mY);
- mListener.onEyePositionChanged(mX, mY, mZ);
- }
-
- private void onGyroscopeChanged(float gx, float gy, float gz) {
- long now = SystemClock.elapsedRealtime();
- float distance = (gx > 0 ? gx : -gx) + (gy > 0 ? gy : - gy);
- if (distance < GYROSCOPE_THRESHOLD
- || distance > GYROSCOPE_LIMIT || mGyroscopeCountdown > 0) {
- --mGyroscopeCountdown;
- mStartTime = now;
- float limit = mUserDistance / 20f;
- if (mX > limit || mX < -limit || mY > limit || mY < -limit) {
- mX *= GYROSCOPE_RESTORE_FACTOR;
- mY *= GYROSCOPE_RESTORE_FACTOR;
- mZ = (float) -Math.sqrt(
- mUserDistance * mUserDistance - mX * mX - mY * mY);
- mListener.onEyePositionChanged(mX, mY, mZ);
- }
- return;
- }
-
- float t = (now - mStartTime) / 1000f * mUserDistance * (-mZ);
- mStartTime = now;
-
- float x = -gy, y = -gx;
- switch (mDisplay.getRotation()) {
- case Surface.ROTATION_90: x = -gx; y= gy; break;
- case Surface.ROTATION_180: x = gy; y = gx; break;
- case Surface.ROTATION_270: x = gx; y = -gy; break;
- }
-
- mX = Utils.clamp((float) (mX + x * t / Math.hypot(mZ, mX)),
- -mLimit, mLimit) * GYROSCOPE_RESTORE_FACTOR;
- mY = Utils.clamp((float) (mY + y * t / Math.hypot(mZ, mY)),
- -mLimit, mLimit) * GYROSCOPE_RESTORE_FACTOR;
-
- mZ = -FloatMath.sqrt(
- mUserDistance * mUserDistance - mX * mX - mY * mY);
- mListener.onEyePositionChanged(mX, mY, mZ);
- }
-
- private class PositionListener implements SensorEventListener {
- @Override
- public void onAccuracyChanged(Sensor sensor, int accuracy) {
- }
-
- @Override
- public void onSensorChanged(SensorEvent event) {
- switch (event.sensor.getType()) {
- case Sensor.TYPE_GYROSCOPE: {
- onGyroscopeChanged(
- event.values[0], event.values[1], event.values[2]);
- break;
- }
- case Sensor.TYPE_ACCELEROMETER: {
- onAccelerometerChanged(
- event.values[0], event.values[1], event.values[2]);
- }
- }
- }
- }
-
- public void pause() {
- if (mSensor != null) {
- SensorManager sManager = (SensorManager) mContext
- .getSystemService(Context.SENSOR_SERVICE);
- sManager.unregisterListener(mPositionListener);
- }
- }
-
- public void resume() {
- if (mSensor != null) {
- SensorManager sManager = (SensorManager) mContext
- .getSystemService(Context.SENSOR_SERVICE);
- sManager.registerListener(mPositionListener,
- mSensor, SensorManager.SENSOR_DELAY_GAME);
- }
-
- mStartTime = NOT_STARTED;
- mGyroscopeCountdown = GYROSCOPE_SETTLE_DOWN;
- mX = mY = 0;
- mZ = -mUserDistance;
- mListener.onEyePositionChanged(mX, mY, mZ);
- }
-}
diff --git a/src/com/android/gallery3d/app/FilmstripPage.java b/src/com/android/gallery3d/app/FilmstripPage.java
deleted file mode 100644
index a9726cdc9..000000000
--- a/src/com/android/gallery3d/app/FilmstripPage.java
+++ /dev/null
@@ -1,21 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-public class FilmstripPage extends PhotoPage {
-
-}
diff --git a/src/com/android/gallery3d/app/FilterUtils.java b/src/com/android/gallery3d/app/FilterUtils.java
deleted file mode 100644
index bc28a9cc1..000000000
--- a/src/com/android/gallery3d/app/FilterUtils.java
+++ /dev/null
@@ -1,257 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.Path;
-
-// This class handles filtering and clustering.
-//
-// We allow at most only one filter operation at a time (Currently it
-// doesn't make sense to use more than one). Also each clustering operation
-// can be applied at most once. In addition, there is one more constraint
-// ("fixed set constraint") described below.
-//
-// A clustered album (not including album set) and its base sets are fixed.
-// For example,
-//
-// /cluster/{base_set}/time/7
-//
-// This set and all sets inside base_set (recursively) are fixed because
-// 1. We can not change this set to use another clustering condition (like
-// changing "time" to "location").
-// 2. Neither can we change any set in the base_set.
-// The reason is in both cases the 7th set may not exist in the new clustering.
-// ---------------------
-// newPath operation: create a new path based on a source path and put an extra
-// condition on top of it:
-//
-// T = newFilterPath(S, filterType);
-// T = newClusterPath(S, clusterType);
-//
-// Similar functions can be used to replace the current condition (if there is one).
-//
-// T = switchFilterPath(S, filterType);
-// T = switchClusterPath(S, clusterType);
-//
-// For all fixed set in the path defined above, if some clusterType and
-// filterType are already used, they cannot not be used as parameter for these
-// functions. setupMenuItems() makes sure those types cannot be selected.
-//
-public class FilterUtils {
- @SuppressWarnings("unused")
- private static final String TAG = "FilterUtils";
-
- public static final int CLUSTER_BY_ALBUM = 1;
- public static final int CLUSTER_BY_TIME = 2;
- public static final int CLUSTER_BY_LOCATION = 4;
- public static final int CLUSTER_BY_TAG = 8;
- public static final int CLUSTER_BY_SIZE = 16;
- public static final int CLUSTER_BY_FACE = 32;
-
- public static final int FILTER_IMAGE_ONLY = 1;
- public static final int FILTER_VIDEO_ONLY = 2;
- public static final int FILTER_ALL = 4;
-
- // These are indices of the return values of getAppliedFilters().
- // The _F suffix means "fixed".
- private static final int CLUSTER_TYPE = 0;
- private static final int FILTER_TYPE = 1;
- private static final int CLUSTER_TYPE_F = 2;
- private static final int FILTER_TYPE_F = 3;
- private static final int CLUSTER_CURRENT_TYPE = 4;
- private static final int FILTER_CURRENT_TYPE = 5;
-
- public static void setupMenuItems(GalleryActionBar actionBar, Path path, boolean inAlbum) {
- int[] result = new int[6];
- getAppliedFilters(path, result);
- int ctype = result[CLUSTER_TYPE];
- int ftype = result[FILTER_TYPE];
- int ftypef = result[FILTER_TYPE_F];
- int ccurrent = result[CLUSTER_CURRENT_TYPE];
- int fcurrent = result[FILTER_CURRENT_TYPE];
-
- setMenuItemApplied(actionBar, CLUSTER_BY_TIME,
- (ctype & CLUSTER_BY_TIME) != 0, (ccurrent & CLUSTER_BY_TIME) != 0);
- setMenuItemApplied(actionBar, CLUSTER_BY_LOCATION,
- (ctype & CLUSTER_BY_LOCATION) != 0, (ccurrent & CLUSTER_BY_LOCATION) != 0);
- setMenuItemApplied(actionBar, CLUSTER_BY_TAG,
- (ctype & CLUSTER_BY_TAG) != 0, (ccurrent & CLUSTER_BY_TAG) != 0);
- setMenuItemApplied(actionBar, CLUSTER_BY_FACE,
- (ctype & CLUSTER_BY_FACE) != 0, (ccurrent & CLUSTER_BY_FACE) != 0);
-
- actionBar.setClusterItemVisibility(CLUSTER_BY_ALBUM, !inAlbum || ctype == 0);
-
- setMenuItemApplied(actionBar, R.id.action_cluster_album, ctype == 0,
- ccurrent == 0);
-
- // A filtering is available if it's not applied, and the old filtering
- // (if any) is not fixed.
- setMenuItemAppliedEnabled(actionBar, R.string.show_images_only,
- (ftype & FILTER_IMAGE_ONLY) != 0,
- (ftype & FILTER_IMAGE_ONLY) == 0 && ftypef == 0,
- (fcurrent & FILTER_IMAGE_ONLY) != 0);
- setMenuItemAppliedEnabled(actionBar, R.string.show_videos_only,
- (ftype & FILTER_VIDEO_ONLY) != 0,
- (ftype & FILTER_VIDEO_ONLY) == 0 && ftypef == 0,
- (fcurrent & FILTER_VIDEO_ONLY) != 0);
- setMenuItemAppliedEnabled(actionBar, R.string.show_all,
- ftype == 0, ftype != 0 && ftypef == 0, fcurrent == 0);
- }
-
- // Gets the filters applied in the path.
- private static void getAppliedFilters(Path path, int[] result) {
- getAppliedFilters(path, result, false);
- }
-
- private static void getAppliedFilters(Path path, int[] result, boolean underCluster) {
- String[] segments = path.split();
- // Recurse into sub media sets.
- for (int i = 0; i < segments.length; i++) {
- if (segments[i].startsWith("{")) {
- String[] sets = Path.splitSequence(segments[i]);
- for (int j = 0; j < sets.length; j++) {
- Path sub = Path.fromString(sets[j]);
- getAppliedFilters(sub, result, underCluster);
- }
- }
- }
-
- // update current selection
- if (segments[0].equals("cluster")) {
- // if this is a clustered album, set underCluster to true.
- if (segments.length == 4) {
- underCluster = true;
- }
-
- int ctype = toClusterType(segments[2]);
- result[CLUSTER_TYPE] |= ctype;
- result[CLUSTER_CURRENT_TYPE] = ctype;
- if (underCluster) {
- result[CLUSTER_TYPE_F] |= ctype;
- }
- }
- }
-
- private static int toClusterType(String s) {
- if (s.equals("time")) {
- return CLUSTER_BY_TIME;
- } else if (s.equals("location")) {
- return CLUSTER_BY_LOCATION;
- } else if (s.equals("tag")) {
- return CLUSTER_BY_TAG;
- } else if (s.equals("size")) {
- return CLUSTER_BY_SIZE;
- } else if (s.equals("face")) {
- return CLUSTER_BY_FACE;
- }
- return 0;
- }
-
- private static void setMenuItemApplied(
- GalleryActionBar model, int id, boolean applied, boolean updateTitle) {
- model.setClusterItemEnabled(id, !applied);
- }
-
- private static void setMenuItemAppliedEnabled(GalleryActionBar model, int id, boolean applied, boolean enabled, boolean updateTitle) {
- model.setClusterItemEnabled(id, enabled);
- }
-
- // Add a specified filter to the path.
- public static String newFilterPath(String base, int filterType) {
- int mediaType;
- switch (filterType) {
- case FILTER_IMAGE_ONLY:
- mediaType = MediaObject.MEDIA_TYPE_IMAGE;
- break;
- case FILTER_VIDEO_ONLY:
- mediaType = MediaObject.MEDIA_TYPE_VIDEO;
- break;
- default: /* FILTER_ALL */
- return base;
- }
-
- return "/filter/mediatype/" + mediaType + "/{" + base + "}";
- }
-
- // Add a specified clustering to the path.
- public static String newClusterPath(String base, int clusterType) {
- String kind;
- switch (clusterType) {
- case CLUSTER_BY_TIME:
- kind = "time";
- break;
- case CLUSTER_BY_LOCATION:
- kind = "location";
- break;
- case CLUSTER_BY_TAG:
- kind = "tag";
- break;
- case CLUSTER_BY_SIZE:
- kind = "size";
- break;
- case CLUSTER_BY_FACE:
- kind = "face";
- break;
- default: /* CLUSTER_BY_ALBUM */
- return base;
- }
-
- return "/cluster/{" + base + "}/" + kind;
- }
-
- // Change the topmost clustering to the specified type.
- public static String switchClusterPath(String base, int clusterType) {
- return newClusterPath(removeOneClusterFromPath(base), clusterType);
- }
-
- // Remove the topmost clustering (if any) from the path.
- private static String removeOneClusterFromPath(String base) {
- boolean[] done = new boolean[1];
- return removeOneClusterFromPath(base, done);
- }
-
- private static String removeOneClusterFromPath(String base, boolean[] done) {
- if (done[0]) return base;
-
- String[] segments = Path.split(base);
- if (segments[0].equals("cluster")) {
- done[0] = true;
- return Path.splitSequence(segments[1])[0];
- }
-
- StringBuilder sb = new StringBuilder();
- for (int i = 0; i < segments.length; i++) {
- sb.append("/");
- if (segments[i].startsWith("{")) {
- sb.append("{");
- String[] sets = Path.splitSequence(segments[i]);
- for (int j = 0; j < sets.length; j++) {
- if (j > 0) {
- sb.append(",");
- }
- sb.append(removeOneClusterFromPath(sets[j], done));
- }
- sb.append("}");
- } else {
- sb.append(segments[i]);
- }
- }
- return sb.toString();
- }
-}
diff --git a/src/com/android/gallery3d/app/Gallery.java b/src/com/android/gallery3d/app/Gallery.java
deleted file mode 100644
index baef56b44..000000000
--- a/src/com/android/gallery3d/app/Gallery.java
+++ /dev/null
@@ -1,274 +0,0 @@
-/*
- * Copyright (C) 2009 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.app.Dialog;
-import android.content.ContentResolver;
-import android.content.DialogInterface;
-import android.content.DialogInterface.OnCancelListener;
-import android.content.Intent;
-import android.net.Uri;
-import android.os.Bundle;
-import android.view.InputDevice;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.Window;
-import android.view.WindowManager;
-import android.widget.Toast;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.picasasource.PicasaSource;
-import com.android.gallery3d.util.GalleryUtils;
-
-public final class Gallery extends AbstractGalleryActivity implements OnCancelListener {
- public static final String EXTRA_SLIDESHOW = "slideshow";
- public static final String EXTRA_DREAM = "dream";
- public static final String EXTRA_CROP = "crop";
-
- public static final String ACTION_REVIEW = "com.android.camera.action.REVIEW";
- public static final String KEY_GET_CONTENT = "get-content";
- public static final String KEY_GET_ALBUM = "get-album";
- public static final String KEY_TYPE_BITS = "type-bits";
- public static final String KEY_MEDIA_TYPES = "mediaTypes";
- public static final String KEY_DISMISS_KEYGUARD = "dismiss-keyguard";
-
- private static final String TAG = "Gallery";
- private Dialog mVersionCheckDialog;
-
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- requestWindowFeature(Window.FEATURE_ACTION_BAR);
- requestWindowFeature(Window.FEATURE_ACTION_BAR_OVERLAY);
-
- if (getIntent().getBooleanExtra(KEY_DISMISS_KEYGUARD, false)) {
- getWindow().addFlags(
- WindowManager.LayoutParams.FLAG_DISMISS_KEYGUARD);
- }
-
- setContentView(R.layout.main);
-
- if (savedInstanceState != null) {
- getStateManager().restoreFromState(savedInstanceState);
- } else {
- initializeByIntent();
- }
- }
-
- private void initializeByIntent() {
- Intent intent = getIntent();
- String action = intent.getAction();
-
- if (Intent.ACTION_GET_CONTENT.equalsIgnoreCase(action)) {
- startGetContent(intent);
- } else if (Intent.ACTION_PICK.equalsIgnoreCase(action)) {
- // We do NOT really support the PICK intent. Handle it as
- // the GET_CONTENT. However, we need to translate the type
- // in the intent here.
- Log.w(TAG, "action PICK is not supported");
- String type = Utils.ensureNotNull(intent.getType());
- if (type.startsWith("vnd.android.cursor.dir/")) {
- if (type.endsWith("/image")) intent.setType("image/*");
- if (type.endsWith("/video")) intent.setType("video/*");
- }
- startGetContent(intent);
- } else if (Intent.ACTION_VIEW.equalsIgnoreCase(action)
- || ACTION_REVIEW.equalsIgnoreCase(action)){
- startViewAction(intent);
- } else {
- startDefaultPage();
- }
- }
-
- public void startDefaultPage() {
- PicasaSource.showSignInReminder(this);
- Bundle data = new Bundle();
- data.putString(AlbumSetPage.KEY_MEDIA_PATH,
- getDataManager().getTopSetPath(DataManager.INCLUDE_ALL));
- getStateManager().startState(AlbumSetPage.class, data);
- mVersionCheckDialog = PicasaSource.getVersionCheckDialog(this);
- if (mVersionCheckDialog != null) {
- mVersionCheckDialog.setOnCancelListener(this);
- }
- }
-
- private void startGetContent(Intent intent) {
- Bundle data = intent.getExtras() != null
- ? new Bundle(intent.getExtras())
- : new Bundle();
- data.putBoolean(KEY_GET_CONTENT, true);
- int typeBits = GalleryUtils.determineTypeBits(this, intent);
- data.putInt(KEY_TYPE_BITS, typeBits);
- data.putString(AlbumSetPage.KEY_MEDIA_PATH,
- getDataManager().getTopSetPath(typeBits));
- getStateManager().startState(AlbumSetPage.class, data);
- }
-
- private String getContentType(Intent intent) {
- String type = intent.getType();
- if (type != null) {
- return GalleryUtils.MIME_TYPE_PANORAMA360.equals(type)
- ? MediaItem.MIME_TYPE_JPEG : type;
- }
-
- Uri uri = intent.getData();
- try {
- return getContentResolver().getType(uri);
- } catch (Throwable t) {
- Log.w(TAG, "get type fail", t);
- return null;
- }
- }
-
- private void startViewAction(Intent intent) {
- Boolean slideshow = intent.getBooleanExtra(EXTRA_SLIDESHOW, false);
- if (slideshow) {
- getActionBar().hide();
- DataManager manager = getDataManager();
- Path path = manager.findPathByUri(intent.getData(), intent.getType());
- if (path == null || manager.getMediaObject(path)
- instanceof MediaItem) {
- path = Path.fromString(
- manager.getTopSetPath(DataManager.INCLUDE_IMAGE));
- }
- Bundle data = new Bundle();
- data.putString(SlideshowPage.KEY_SET_PATH, path.toString());
- data.putBoolean(SlideshowPage.KEY_RANDOM_ORDER, true);
- data.putBoolean(SlideshowPage.KEY_REPEAT, true);
- if (intent.getBooleanExtra(EXTRA_DREAM, false)) {
- data.putBoolean(SlideshowPage.KEY_DREAM, true);
- }
- getStateManager().startState(SlideshowPage.class, data);
- } else {
- Bundle data = new Bundle();
- DataManager dm = getDataManager();
- Uri uri = intent.getData();
- String contentType = getContentType(intent);
- if (contentType == null) {
- Toast.makeText(this,
- R.string.no_such_item, Toast.LENGTH_LONG).show();
- finish();
- return;
- }
- if (uri == null) {
- int typeBits = GalleryUtils.determineTypeBits(this, intent);
- data.putInt(KEY_TYPE_BITS, typeBits);
- data.putString(AlbumSetPage.KEY_MEDIA_PATH,
- getDataManager().getTopSetPath(typeBits));
- getStateManager().startState(AlbumSetPage.class, data);
- } else if (contentType.startsWith(
- ContentResolver.CURSOR_DIR_BASE_TYPE)) {
- int mediaType = intent.getIntExtra(KEY_MEDIA_TYPES, 0);
- if (mediaType != 0) {
- uri = uri.buildUpon().appendQueryParameter(
- KEY_MEDIA_TYPES, String.valueOf(mediaType))
- .build();
- }
- Path setPath = dm.findPathByUri(uri, null);
- MediaSet mediaSet = null;
- if (setPath != null) {
- mediaSet = (MediaSet) dm.getMediaObject(setPath);
- }
- if (mediaSet != null) {
- if (mediaSet.isLeafAlbum()) {
- data.putString(AlbumPage.KEY_MEDIA_PATH, setPath.toString());
- data.putString(AlbumPage.KEY_PARENT_MEDIA_PATH,
- dm.getTopSetPath(DataManager.INCLUDE_ALL));
- getStateManager().startState(AlbumPage.class, data);
- } else {
- data.putString(AlbumSetPage.KEY_MEDIA_PATH, setPath.toString());
- getStateManager().startState(AlbumSetPage.class, data);
- }
- } else {
- startDefaultPage();
- }
- } else {
- Path itemPath = dm.findPathByUri(uri, contentType);
- Path albumPath = dm.getDefaultSetOf(itemPath);
-
- data.putString(PhotoPage.KEY_MEDIA_ITEM_PATH, itemPath.toString());
-
- // TODO: Make the parameter "SingleItemOnly" public so other
- // activities can reference it.
- boolean singleItemOnly = (albumPath == null)
- || intent.getBooleanExtra("SingleItemOnly", false);
- if (!singleItemOnly) {
- data.putString(PhotoPage.KEY_MEDIA_SET_PATH, albumPath.toString());
- // when FLAG_ACTIVITY_NEW_TASK is set, (e.g. when intent is fired
- // from notification), back button should behave the same as up button
- // rather than taking users back to the home screen
- if (intent.getBooleanExtra(PhotoPage.KEY_TREAT_BACK_AS_UP, false)
- || ((intent.getFlags() & Intent.FLAG_ACTIVITY_NEW_TASK) != 0)) {
- data.putBoolean(PhotoPage.KEY_TREAT_BACK_AS_UP, true);
- }
- }
-
- getStateManager().startState(SinglePhotoPage.class, data);
- }
- }
- }
-
- @Override
- protected void onResume() {
- Utils.assertTrue(getStateManager().getStateCount() > 0);
- super.onResume();
- if (mVersionCheckDialog != null) {
- mVersionCheckDialog.show();
- }
- }
-
- @Override
- protected void onPause() {
- super.onPause();
- if (mVersionCheckDialog != null) {
- mVersionCheckDialog.dismiss();
- }
- }
-
- @Override
- public void onCancel(DialogInterface dialog) {
- if (dialog == mVersionCheckDialog) {
- mVersionCheckDialog = null;
- }
- }
-
- @Override
- public boolean onGenericMotionEvent(MotionEvent event) {
- final boolean isTouchPad = (event.getSource()
- & InputDevice.SOURCE_CLASS_POSITION) != 0;
- if (isTouchPad) {
- float maxX = event.getDevice().getMotionRange(MotionEvent.AXIS_X).getMax();
- float maxY = event.getDevice().getMotionRange(MotionEvent.AXIS_Y).getMax();
- View decor = getWindow().getDecorView();
- float scaleX = decor.getWidth() / maxX;
- float scaleY = decor.getHeight() / maxY;
- float x = event.getX() * scaleX;
- //x = decor.getWidth() - x; // invert x
- float y = event.getY() * scaleY;
- //y = decor.getHeight() - y; // invert y
- MotionEvent touchEvent = MotionEvent.obtain(event.getDownTime(),
- event.getEventTime(), event.getAction(), x, y, event.getMetaState());
- return dispatchTouchEvent(touchEvent);
- }
- return super.onGenericMotionEvent(event);
- }
-}
diff --git a/src/com/android/gallery3d/app/GalleryActionBar.java b/src/com/android/gallery3d/app/GalleryActionBar.java
deleted file mode 100644
index 588f5842a..000000000
--- a/src/com/android/gallery3d/app/GalleryActionBar.java
+++ /dev/null
@@ -1,438 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.annotation.TargetApi;
-import android.app.ActionBar;
-import android.app.ActionBar.OnMenuVisibilityListener;
-import android.app.ActionBar.OnNavigationListener;
-import android.app.Activity;
-import android.app.AlertDialog;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.content.Intent;
-import android.content.res.Resources;
-import android.view.LayoutInflater;
-import android.view.Menu;
-import android.view.MenuItem;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.BaseAdapter;
-import android.widget.ShareActionProvider;
-import android.widget.TextView;
-import android.widget.TwoLineListItem;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.ApiHelper;
-
-import java.util.ArrayList;
-
-public class GalleryActionBar implements OnNavigationListener {
- @SuppressWarnings("unused")
- private static final String TAG = "GalleryActionBar";
-
- private ClusterRunner mClusterRunner;
- private CharSequence[] mTitles;
- private ArrayList<Integer> mActions;
- private Context mContext;
- private LayoutInflater mInflater;
- private AbstractGalleryActivity mActivity;
- private ActionBar mActionBar;
- private int mCurrentIndex;
- private ClusterAdapter mAdapter = new ClusterAdapter();
-
- private AlbumModeAdapter mAlbumModeAdapter;
- private OnAlbumModeSelectedListener mAlbumModeListener;
- private int mLastAlbumModeSelected;
- private CharSequence [] mAlbumModes;
- public static final int ALBUM_FILMSTRIP_MODE_SELECTED = 0;
- public static final int ALBUM_GRID_MODE_SELECTED = 1;
-
- public interface ClusterRunner {
- public void doCluster(int id);
- }
-
- public interface OnAlbumModeSelectedListener {
- public void onAlbumModeSelected(int mode);
- }
-
- private static class ActionItem {
- public int action;
- public boolean enabled;
- public boolean visible;
- public int spinnerTitle;
- public int dialogTitle;
- public int clusterBy;
-
- public ActionItem(int action, boolean applied, boolean enabled, int title,
- int clusterBy) {
- this(action, applied, enabled, title, title, clusterBy);
- }
-
- public ActionItem(int action, boolean applied, boolean enabled, int spinnerTitle,
- int dialogTitle, int clusterBy) {
- this.action = action;
- this.enabled = enabled;
- this.spinnerTitle = spinnerTitle;
- this.dialogTitle = dialogTitle;
- this.clusterBy = clusterBy;
- this.visible = true;
- }
- }
-
- private static final ActionItem[] sClusterItems = new ActionItem[] {
- new ActionItem(FilterUtils.CLUSTER_BY_ALBUM, true, false, R.string.albums,
- R.string.group_by_album),
- new ActionItem(FilterUtils.CLUSTER_BY_LOCATION, true, false,
- R.string.locations, R.string.location, R.string.group_by_location),
- new ActionItem(FilterUtils.CLUSTER_BY_TIME, true, false, R.string.times,
- R.string.time, R.string.group_by_time),
- new ActionItem(FilterUtils.CLUSTER_BY_FACE, true, false, R.string.people,
- R.string.group_by_faces),
- new ActionItem(FilterUtils.CLUSTER_BY_TAG, true, false, R.string.tags,
- R.string.group_by_tags)
- };
-
- private class ClusterAdapter extends BaseAdapter {
-
- @Override
- public int getCount() {
- return sClusterItems.length;
- }
-
- @Override
- public Object getItem(int position) {
- return sClusterItems[position];
- }
-
- @Override
- public long getItemId(int position) {
- return sClusterItems[position].action;
- }
-
- @Override
- public View getView(int position, View convertView, ViewGroup parent) {
- if (convertView == null) {
- convertView = mInflater.inflate(R.layout.action_bar_text,
- parent, false);
- }
- TextView view = (TextView) convertView;
- view.setText(sClusterItems[position].spinnerTitle);
- return convertView;
- }
- }
-
- private class AlbumModeAdapter extends BaseAdapter {
- @Override
- public int getCount() {
- return mAlbumModes.length;
- }
-
- @Override
- public Object getItem(int position) {
- return mAlbumModes[position];
- }
-
- @Override
- public long getItemId(int position) {
- return position;
- }
-
- @Override
- public View getView(int position, View convertView, ViewGroup parent) {
- if (convertView == null) {
- convertView = mInflater.inflate(R.layout.action_bar_two_line_text,
- parent, false);
- }
- TwoLineListItem view = (TwoLineListItem) convertView;
- view.getText1().setText(mActionBar.getTitle());
- view.getText2().setText((CharSequence) getItem(position));
- return convertView;
- }
-
- @Override
- public View getDropDownView(int position, View convertView, ViewGroup parent) {
- if (convertView == null) {
- convertView = mInflater.inflate(R.layout.action_bar_text,
- parent, false);
- }
- TextView view = (TextView) convertView;
- view.setText((CharSequence) getItem(position));
- return convertView;
- }
- }
-
- public static String getClusterByTypeString(Context context, int type) {
- for (ActionItem item : sClusterItems) {
- if (item.action == type) {
- return context.getString(item.clusterBy);
- }
- }
- return null;
- }
-
- public GalleryActionBar(AbstractGalleryActivity activity) {
- mActionBar = activity.getActionBar();
- mContext = activity.getAndroidContext();
- mActivity = activity;
- mInflater = ((Activity) mActivity).getLayoutInflater();
- mCurrentIndex = 0;
- }
-
- private void createDialogData() {
- ArrayList<CharSequence> titles = new ArrayList<CharSequence>();
- mActions = new ArrayList<Integer>();
- for (ActionItem item : sClusterItems) {
- if (item.enabled && item.visible) {
- titles.add(mContext.getString(item.dialogTitle));
- mActions.add(item.action);
- }
- }
- mTitles = new CharSequence[titles.size()];
- titles.toArray(mTitles);
- }
-
- public int getHeight() {
- return mActionBar != null ? mActionBar.getHeight() : 0;
- }
-
- public void setClusterItemEnabled(int id, boolean enabled) {
- for (ActionItem item : sClusterItems) {
- if (item.action == id) {
- item.enabled = enabled;
- return;
- }
- }
- }
-
- public void setClusterItemVisibility(int id, boolean visible) {
- for (ActionItem item : sClusterItems) {
- if (item.action == id) {
- item.visible = visible;
- return;
- }
- }
- }
-
- public int getClusterTypeAction() {
- return sClusterItems[mCurrentIndex].action;
- }
-
- public void enableClusterMenu(int action, ClusterRunner runner) {
- if (mActionBar != null) {
- // Don't set cluster runner until action bar is ready.
- mClusterRunner = null;
- mActionBar.setListNavigationCallbacks(mAdapter, this);
- mActionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_LIST);
- setSelectedAction(action);
- mClusterRunner = runner;
- }
- }
-
- // The only use case not to hideMenu in this method is to ensure
- // all elements disappear at the same time when exiting gallery.
- // hideMenu should always be true in all other cases.
- public void disableClusterMenu(boolean hideMenu) {
- if (mActionBar != null) {
- mClusterRunner = null;
- if (hideMenu) {
- mActionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD);
- }
- }
- }
-
- public void onConfigurationChanged() {
- if (mActionBar != null && mAlbumModeListener != null) {
- OnAlbumModeSelectedListener listener = mAlbumModeListener;
- enableAlbumModeMenu(mLastAlbumModeSelected, listener);
- }
- }
-
- public void enableAlbumModeMenu(int selected, OnAlbumModeSelectedListener listener) {
- if (mActionBar != null) {
- if (mAlbumModeAdapter == null) {
- // Initialize the album mode options if they haven't been already
- Resources res = mActivity.getResources();
- mAlbumModes = new CharSequence[] {
- res.getString(R.string.switch_photo_filmstrip),
- res.getString(R.string.switch_photo_grid)};
- mAlbumModeAdapter = new AlbumModeAdapter();
- }
- mAlbumModeListener = null;
- mLastAlbumModeSelected = selected;
- mActionBar.setListNavigationCallbacks(mAlbumModeAdapter, this);
- mActionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_LIST);
- mActionBar.setSelectedNavigationItem(selected);
- mAlbumModeListener = listener;
- }
- }
-
- public void disableAlbumModeMenu(boolean hideMenu) {
- if (mActionBar != null) {
- mAlbumModeListener = null;
- if (hideMenu) {
- mActionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD);
- }
- }
- }
-
- public void showClusterDialog(final ClusterRunner clusterRunner) {
- createDialogData();
- final ArrayList<Integer> actions = mActions;
- new AlertDialog.Builder(mContext).setTitle(R.string.group_by).setItems(
- mTitles, new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int which) {
- // Need to lock rendering when operations invoked by system UI (main thread) are
- // modifying slot data used in GL thread for rendering.
- mActivity.getGLRoot().lockRenderThread();
- try {
- clusterRunner.doCluster(actions.get(which).intValue());
- } finally {
- mActivity.getGLRoot().unlockRenderThread();
- }
- }
- }).create().show();
- }
-
- @TargetApi(ApiHelper.VERSION_CODES.ICE_CREAM_SANDWICH)
- private void setHomeButtonEnabled(boolean enabled) {
- if (mActionBar != null) mActionBar.setHomeButtonEnabled(enabled);
- }
-
- public void setDisplayOptions(boolean displayHomeAsUp, boolean showTitle) {
- if (mActionBar == null) return;
- int options = 0;
- if (displayHomeAsUp) options |= ActionBar.DISPLAY_HOME_AS_UP;
- if (showTitle) options |= ActionBar.DISPLAY_SHOW_TITLE;
-
- mActionBar.setDisplayOptions(options,
- ActionBar.DISPLAY_HOME_AS_UP | ActionBar.DISPLAY_SHOW_TITLE);
- mActionBar.setHomeButtonEnabled(displayHomeAsUp);
- }
-
- public void setTitle(String title) {
- if (mActionBar != null) mActionBar.setTitle(title);
- }
-
- public void setTitle(int titleId) {
- if (mActionBar != null) {
- mActionBar.setTitle(mContext.getString(titleId));
- }
- }
-
- public void setSubtitle(String title) {
- if (mActionBar != null) mActionBar.setSubtitle(title);
- }
-
- public void show() {
- if (mActionBar != null) mActionBar.show();
- }
-
- public void hide() {
- if (mActionBar != null) mActionBar.hide();
- }
-
- public void addOnMenuVisibilityListener(OnMenuVisibilityListener listener) {
- if (mActionBar != null) mActionBar.addOnMenuVisibilityListener(listener);
- }
-
- public void removeOnMenuVisibilityListener(OnMenuVisibilityListener listener) {
- if (mActionBar != null) mActionBar.removeOnMenuVisibilityListener(listener);
- }
-
- public boolean setSelectedAction(int type) {
- if (mActionBar == null) return false;
-
- for (int i = 0, n = sClusterItems.length; i < n; i++) {
- ActionItem item = sClusterItems[i];
- if (item.action == type) {
- mActionBar.setSelectedNavigationItem(i);
- mCurrentIndex = i;
- return true;
- }
- }
- return false;
- }
-
- @Override
- public boolean onNavigationItemSelected(int itemPosition, long itemId) {
- if (itemPosition != mCurrentIndex && mClusterRunner != null
- || mAlbumModeListener != null) {
- // Need to lock rendering when operations invoked by system UI (main thread) are
- // modifying slot data used in GL thread for rendering.
- mActivity.getGLRoot().lockRenderThread();
- try {
- if (mAlbumModeListener != null) {
- mAlbumModeListener.onAlbumModeSelected(itemPosition);
- } else {
- mClusterRunner.doCluster(sClusterItems[itemPosition].action);
- }
- } finally {
- mActivity.getGLRoot().unlockRenderThread();
- }
- }
- return false;
- }
-
- private Menu mActionBarMenu;
- private ShareActionProvider mSharePanoramaActionProvider;
- private ShareActionProvider mShareActionProvider;
- private Intent mSharePanoramaIntent;
- private Intent mShareIntent;
-
- public void createActionBarMenu(int menuRes, Menu menu) {
- mActivity.getMenuInflater().inflate(menuRes, menu);
- mActionBarMenu = menu;
-
- MenuItem item = menu.findItem(R.id.action_share_panorama);
- if (item != null) {
- mSharePanoramaActionProvider = (ShareActionProvider)
- item.getActionProvider();
- mSharePanoramaActionProvider
- .setShareHistoryFileName("panorama_share_history.xml");
- mSharePanoramaActionProvider.setShareIntent(mSharePanoramaIntent);
- }
-
- item = menu.findItem(R.id.action_share);
- if (item != null) {
- mShareActionProvider = (ShareActionProvider)
- item.getActionProvider();
- mShareActionProvider
- .setShareHistoryFileName("share_history.xml");
- mShareActionProvider.setShareIntent(mShareIntent);
- }
- }
-
- public Menu getMenu() {
- return mActionBarMenu;
- }
-
- public void setShareIntents(Intent sharePanoramaIntent, Intent shareIntent,
- ShareActionProvider.OnShareTargetSelectedListener onShareListener) {
- mSharePanoramaIntent = sharePanoramaIntent;
- if (mSharePanoramaActionProvider != null) {
- mSharePanoramaActionProvider.setShareIntent(sharePanoramaIntent);
- }
- mShareIntent = shareIntent;
- if (mShareActionProvider != null) {
- mShareActionProvider.setShareIntent(shareIntent);
- mShareActionProvider.setOnShareTargetSelectedListener(
- onShareListener);
- }
- }
-}
diff --git a/src/com/android/gallery3d/app/GalleryApp.java b/src/com/android/gallery3d/app/GalleryApp.java
deleted file mode 100644
index b56b8a82c..000000000
--- a/src/com/android/gallery3d/app/GalleryApp.java
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.content.ContentResolver;
-import android.content.Context;
-import android.content.res.Resources;
-import android.os.Looper;
-
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.DownloadCache;
-import com.android.gallery3d.data.ImageCacheService;
-import com.android.gallery3d.util.ThreadPool;
-
-public interface GalleryApp {
- public DataManager getDataManager();
-
- public StitchingProgressManager getStitchingProgressManager();
- public ImageCacheService getImageCacheService();
- public DownloadCache getDownloadCache();
- public ThreadPool getThreadPool();
-
- public Context getAndroidContext();
- public Looper getMainLooper();
- public ContentResolver getContentResolver();
- public Resources getResources();
-}
diff --git a/src/com/android/gallery3d/app/GalleryAppImpl.java b/src/com/android/gallery3d/app/GalleryAppImpl.java
deleted file mode 100644
index 2abdaa0c1..000000000
--- a/src/com/android/gallery3d/app/GalleryAppImpl.java
+++ /dev/null
@@ -1,127 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.app.Application;
-import android.content.Context;
-import android.os.AsyncTask;
-
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.DownloadCache;
-import com.android.gallery3d.data.ImageCacheService;
-import com.android.gallery3d.gadget.WidgetUtils;
-import com.android.gallery3d.picasasource.PicasaSource;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.LightCycleHelper;
-import com.android.gallery3d.util.ThreadPool;
-import com.android.gallery3d.util.UsageStatistics;
-import com.android.photos.data.MediaCache;
-
-import java.io.File;
-
-public class GalleryAppImpl extends Application implements GalleryApp {
-
- private static final String DOWNLOAD_FOLDER = "download";
- private static final long DOWNLOAD_CAPACITY = 64 * 1024 * 1024; // 64M
-
- private ImageCacheService mImageCacheService;
- private Object mLock = new Object();
- private DataManager mDataManager;
- private ThreadPool mThreadPool;
- private DownloadCache mDownloadCache;
- private StitchingProgressManager mStitchingProgressManager;
-
- @Override
- public void onCreate() {
- super.onCreate();
- com.android.camera.Util.initialize(this);
- initializeAsyncTask();
- GalleryUtils.initialize(this);
- WidgetUtils.initialize(this);
- PicasaSource.initialize(this);
- UsageStatistics.initialize(this);
- MediaCache.initialize(this);
-
- mStitchingProgressManager = LightCycleHelper.createStitchingManagerInstance(this);
- if (mStitchingProgressManager != null) {
- mStitchingProgressManager.addChangeListener(getDataManager());
- }
- }
-
- @Override
- public Context getAndroidContext() {
- return this;
- }
-
- @Override
- public synchronized DataManager getDataManager() {
- if (mDataManager == null) {
- mDataManager = new DataManager(this);
- mDataManager.initializeSourceMap();
- }
- return mDataManager;
- }
-
- @Override
- public StitchingProgressManager getStitchingProgressManager() {
- return mStitchingProgressManager;
- }
-
- @Override
- public ImageCacheService getImageCacheService() {
- // This method may block on file I/O so a dedicated lock is needed here.
- synchronized (mLock) {
- if (mImageCacheService == null) {
- mImageCacheService = new ImageCacheService(getAndroidContext());
- }
- return mImageCacheService;
- }
- }
-
- @Override
- public synchronized ThreadPool getThreadPool() {
- if (mThreadPool == null) {
- mThreadPool = new ThreadPool();
- }
- return mThreadPool;
- }
-
- @Override
- public synchronized DownloadCache getDownloadCache() {
- if (mDownloadCache == null) {
- File cacheDir = new File(getExternalCacheDir(), DOWNLOAD_FOLDER);
-
- if (!cacheDir.isDirectory()) cacheDir.mkdirs();
-
- if (!cacheDir.isDirectory()) {
- throw new RuntimeException(
- "fail to create: " + cacheDir.getAbsolutePath());
- }
- mDownloadCache = new DownloadCache(this, cacheDir, DOWNLOAD_CAPACITY);
- }
- return mDownloadCache;
- }
-
- private void initializeAsyncTask() {
- // AsyncTask class needs to be loaded in UI thread.
- // So we load it here to comply the rule.
- try {
- Class.forName(AsyncTask.class.getName());
- } catch (ClassNotFoundException e) {
- }
- }
-}
diff --git a/src/com/android/gallery3d/app/GalleryContext.java b/src/com/android/gallery3d/app/GalleryContext.java
deleted file mode 100644
index 06f4fe4d1..000000000
--- a/src/com/android/gallery3d/app/GalleryContext.java
+++ /dev/null
@@ -1,34 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.os.Looper;
-
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.util.ThreadPool;
-
-public interface GalleryContext {
- public DataManager getDataManager();
-
- public Context getAndroidContext();
-
- public Looper getMainLooper();
- public Resources getResources();
- public ThreadPool getThreadPool();
-}
diff --git a/src/com/android/gallery3d/app/LoadingListener.java b/src/com/android/gallery3d/app/LoadingListener.java
deleted file mode 100644
index e94df9307..000000000
--- a/src/com/android/gallery3d/app/LoadingListener.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-public interface LoadingListener {
- public void onLoadingStarted();
- /**
- * Called when loading is complete or no further progress can be made.
- *
- * @param loadingFailed true if data source cannot provide requested data
- */
- public void onLoadingFinished(boolean loadingFailed);
-}
diff --git a/src/com/android/gallery3d/app/Log.java b/src/com/android/gallery3d/app/Log.java
deleted file mode 100644
index 07a8ea588..000000000
--- a/src/com/android/gallery3d/app/Log.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-public class Log {
- public static int v(String tag, String msg) {
- return android.util.Log.v(tag, msg);
- }
- public static int v(String tag, String msg, Throwable tr) {
- return android.util.Log.v(tag, msg, tr);
- }
- public static int d(String tag, String msg) {
- return android.util.Log.d(tag, msg);
- }
- public static int d(String tag, String msg, Throwable tr) {
- return android.util.Log.d(tag, msg, tr);
- }
- public static int i(String tag, String msg) {
- return android.util.Log.i(tag, msg);
- }
- public static int i(String tag, String msg, Throwable tr) {
- return android.util.Log.i(tag, msg, tr);
- }
- public static int w(String tag, String msg) {
- return android.util.Log.w(tag, msg);
- }
- public static int w(String tag, String msg, Throwable tr) {
- return android.util.Log.w(tag, msg, tr);
- }
- public static int w(String tag, Throwable tr) {
- return android.util.Log.w(tag, tr);
- }
- public static int e(String tag, String msg) {
- return android.util.Log.e(tag, msg);
- }
- public static int e(String tag, String msg, Throwable tr) {
- return android.util.Log.e(tag, msg, tr);
- }
-}
diff --git a/src/com/android/gallery3d/app/ManageCachePage.java b/src/com/android/gallery3d/app/ManageCachePage.java
deleted file mode 100644
index 4f5c35819..000000000
--- a/src/com/android/gallery3d/app/ManageCachePage.java
+++ /dev/null
@@ -1,419 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.app.Activity;
-import android.content.res.Configuration;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.Message;
-import android.text.format.Formatter;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.widget.FrameLayout;
-import android.widget.ProgressBar;
-import android.widget.TextView;
-import android.widget.Toast;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.ui.CacheStorageUsageInfo;
-import com.android.gallery3d.ui.GLRoot;
-import com.android.gallery3d.ui.GLView;
-import com.android.gallery3d.ui.ManageCacheDrawer;
-import com.android.gallery3d.ui.MenuExecutor;
-import com.android.gallery3d.ui.SelectionManager;
-import com.android.gallery3d.ui.SlotView;
-import com.android.gallery3d.ui.SynchronizedHandler;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.util.ArrayList;
-
-public class ManageCachePage extends ActivityState implements
- SelectionManager.SelectionListener, MenuExecutor.ProgressListener,
- EyePosition.EyePositionListener, OnClickListener {
- public static final String KEY_MEDIA_PATH = "media-path";
-
- @SuppressWarnings("unused")
- private static final String TAG = "ManageCachePage";
-
- private static final int DATA_CACHE_SIZE = 256;
- private static final int MSG_REFRESH_STORAGE_INFO = 1;
- private static final int MSG_REQUEST_LAYOUT = 2;
- private static final int PROGRESS_BAR_MAX = 10000;
-
- private SlotView mSlotView;
- private MediaSet mMediaSet;
-
- protected SelectionManager mSelectionManager;
- protected ManageCacheDrawer mSelectionDrawer;
- private AlbumSetDataLoader mAlbumSetDataAdapter;
-
- private EyePosition mEyePosition;
-
- // The eyes' position of the user, the origin is at the center of the
- // device and the unit is in pixels.
- private float mX;
- private float mY;
- private float mZ;
-
- private int mAlbumCountToMakeAvailableOffline;
- private View mFooterContent;
- private CacheStorageUsageInfo mCacheStorageInfo;
- private Future<Void> mUpdateStorageInfo;
- private Handler mHandler;
- private boolean mLayoutReady = false;
-
- @Override
- protected int getBackgroundColorId() {
- return R.color.cache_background;
- }
-
- private GLView mRootPane = new GLView() {
- private float mMatrix[] = new float[16];
-
- @Override
- protected void renderBackground(GLCanvas view) {
- view.clearBuffer(getBackgroundColor());
- }
-
- @Override
- protected void onLayout(
- boolean changed, int left, int top, int right, int bottom) {
- // Hack: our layout depends on other components on the screen.
- // We assume the other components will complete before we get a change
- // to run a message in main thread.
- if (!mLayoutReady) {
- mHandler.sendEmptyMessage(MSG_REQUEST_LAYOUT);
- return;
- }
- mLayoutReady = false;
-
- mEyePosition.resetPosition();
- int slotViewTop = mActivity.getGalleryActionBar().getHeight();
- int slotViewBottom = bottom - top;
-
- View footer = mActivity.findViewById(R.id.footer);
- if (footer != null) {
- int location[] = {0, 0};
- footer.getLocationOnScreen(location);
- slotViewBottom = location[1];
- }
-
- mSlotView.layout(0, slotViewTop, right - left, slotViewBottom);
- }
-
- @Override
- protected void render(GLCanvas canvas) {
- canvas.save(GLCanvas.SAVE_FLAG_MATRIX);
- GalleryUtils.setViewPointMatrix(mMatrix,
- getWidth() / 2 + mX, getHeight() / 2 + mY, mZ);
- canvas.multiplyMatrix(mMatrix, 0);
- super.render(canvas);
- canvas.restore();
- }
- };
-
- @Override
- public void onEyePositionChanged(float x, float y, float z) {
- mRootPane.lockRendering();
- mX = x;
- mY = y;
- mZ = z;
- mRootPane.unlockRendering();
- mRootPane.invalidate();
- }
-
- private void onDown(int index) {
- mSelectionDrawer.setPressedIndex(index);
- }
-
- private void onUp() {
- mSelectionDrawer.setPressedIndex(-1);
- }
-
- public void onSingleTapUp(int slotIndex) {
- MediaSet targetSet = mAlbumSetDataAdapter.getMediaSet(slotIndex);
- if (targetSet == null) return; // Content is dirty, we shall reload soon
-
- // ignore selection action if the target set does not support cache
- // operation (like a local album).
- if ((targetSet.getSupportedOperations()
- & MediaSet.SUPPORT_CACHE) == 0) {
- showToastForLocalAlbum();
- return;
- }
-
- Path path = targetSet.getPath();
- boolean isFullyCached =
- (targetSet.getCacheFlag() == MediaObject.CACHE_FLAG_FULL);
- boolean isSelected = mSelectionManager.isItemSelected(path);
-
- if (!isFullyCached) {
- // We only count the media sets that will be made available offline
- // in this session.
- if (isSelected) {
- --mAlbumCountToMakeAvailableOffline;
- } else {
- ++mAlbumCountToMakeAvailableOffline;
- }
- }
-
- long sizeOfTarget = targetSet.getCacheSize();
- mCacheStorageInfo.increaseTargetCacheSize(
- (isFullyCached ^ isSelected) ? -sizeOfTarget : sizeOfTarget);
- refreshCacheStorageInfo();
-
- mSelectionManager.toggle(path);
- mSlotView.invalidate();
- }
-
- @Override
- public void onCreate(Bundle data, Bundle restoreState) {
- super.onCreate(data, restoreState);
- mCacheStorageInfo = new CacheStorageUsageInfo(mActivity);
- initializeViews();
- initializeData(data);
- mEyePosition = new EyePosition(mActivity.getAndroidContext(), this);
- mHandler = new SynchronizedHandler(mActivity.getGLRoot()) {
- @Override
- public void handleMessage(Message message) {
- switch (message.what) {
- case MSG_REFRESH_STORAGE_INFO:
- refreshCacheStorageInfo();
- break;
- case MSG_REQUEST_LAYOUT: {
- mLayoutReady = true;
- removeMessages(MSG_REQUEST_LAYOUT);
- mRootPane.requestLayout();
- break;
- }
- }
- }
- };
- }
-
- @Override
- public void onConfigurationChanged(Configuration config) {
- // We use different layout resources for different configs
- initializeFooterViews();
- FrameLayout layout = (FrameLayout) ((Activity) mActivity).findViewById(R.id.footer);
- if (layout.getVisibility() == View.VISIBLE) {
- layout.removeAllViews();
- layout.addView(mFooterContent);
- }
- }
-
- @Override
- public void onPause() {
- super.onPause();
- mAlbumSetDataAdapter.pause();
- mSelectionDrawer.pause();
- mEyePosition.pause();
-
- if (mUpdateStorageInfo != null) {
- mUpdateStorageInfo.cancel();
- mUpdateStorageInfo = null;
- }
- mHandler.removeMessages(MSG_REFRESH_STORAGE_INFO);
-
- FrameLayout layout = (FrameLayout) ((Activity) mActivity).findViewById(R.id.footer);
- layout.removeAllViews();
- layout.setVisibility(View.INVISIBLE);
- }
-
- private Job<Void> mUpdateStorageInfoJob = new Job<Void>() {
- @Override
- public Void run(JobContext jc) {
- mCacheStorageInfo.loadStorageInfo(jc);
- if (!jc.isCancelled()) {
- mHandler.sendEmptyMessage(MSG_REFRESH_STORAGE_INFO);
- }
- return null;
- }
- };
-
- @Override
- public void onResume() {
- super.onResume();
- setContentPane(mRootPane);
- mAlbumSetDataAdapter.resume();
- mSelectionDrawer.resume();
- mEyePosition.resume();
- mUpdateStorageInfo = mActivity.getThreadPool().submit(mUpdateStorageInfoJob);
- FrameLayout layout = (FrameLayout) ((Activity) mActivity).findViewById(R.id.footer);
- layout.addView(mFooterContent);
- layout.setVisibility(View.VISIBLE);
- }
-
- private void initializeData(Bundle data) {
- String mediaPath = data.getString(ManageCachePage.KEY_MEDIA_PATH);
- mMediaSet = mActivity.getDataManager().getMediaSet(mediaPath);
- mSelectionManager.setSourceMediaSet(mMediaSet);
-
- // We will always be in selection mode in this page.
- mSelectionManager.setAutoLeaveSelectionMode(false);
- mSelectionManager.enterSelectionMode();
-
- mAlbumSetDataAdapter = new AlbumSetDataLoader(
- mActivity, mMediaSet, DATA_CACHE_SIZE);
- mSelectionDrawer.setModel(mAlbumSetDataAdapter);
- }
-
- private void initializeViews() {
- Activity activity = mActivity;
-
- mSelectionManager = new SelectionManager(mActivity, true);
- mSelectionManager.setSelectionListener(this);
-
- Config.ManageCachePage config = Config.ManageCachePage.get(activity);
- mSlotView = new SlotView(mActivity, config.slotViewSpec);
- mSelectionDrawer = new ManageCacheDrawer(mActivity, mSelectionManager, mSlotView,
- config.labelSpec, config.cachePinSize, config.cachePinMargin);
- mSlotView.setSlotRenderer(mSelectionDrawer);
- mSlotView.setListener(new SlotView.SimpleListener() {
- @Override
- public void onDown(int index) {
- ManageCachePage.this.onDown(index);
- }
-
- @Override
- public void onUp(boolean followedByLongPress) {
- ManageCachePage.this.onUp();
- }
-
- @Override
- public void onSingleTapUp(int slotIndex) {
- ManageCachePage.this.onSingleTapUp(slotIndex);
- }
- });
- mRootPane.addComponent(mSlotView);
- initializeFooterViews();
- }
-
- private void initializeFooterViews() {
- Activity activity = mActivity;
-
- LayoutInflater inflater = activity.getLayoutInflater();
- mFooterContent = inflater.inflate(R.layout.manage_offline_bar, null);
-
- mFooterContent.findViewById(R.id.done).setOnClickListener(this);
- refreshCacheStorageInfo();
- }
-
- @Override
- public void onClick(View view) {
- Utils.assertTrue(view.getId() == R.id.done);
- GLRoot root = mActivity.getGLRoot();
- root.lockRenderThread();
- try {
- ArrayList<Path> ids = mSelectionManager.getSelected(false);
- if (ids.size() == 0) {
- onBackPressed();
- return;
- }
- showToast();
-
- MenuExecutor menuExecutor = new MenuExecutor(mActivity, mSelectionManager);
- menuExecutor.startAction(R.id.action_toggle_full_caching,
- R.string.process_caching_requests, this);
- } finally {
- root.unlockRenderThread();
- }
- }
-
- private void showToast() {
- if (mAlbumCountToMakeAvailableOffline > 0) {
- Activity activity = mActivity;
- Toast.makeText(activity, activity.getResources().getQuantityString(
- R.plurals.make_albums_available_offline,
- mAlbumCountToMakeAvailableOffline),
- Toast.LENGTH_SHORT).show();
- }
- }
-
- private void showToastForLocalAlbum() {
- Activity activity = mActivity;
- Toast.makeText(activity, activity.getResources().getString(
- R.string.try_to_set_local_album_available_offline),
- Toast.LENGTH_SHORT).show();
- }
-
- private void refreshCacheStorageInfo() {
- ProgressBar progressBar = (ProgressBar) mFooterContent.findViewById(R.id.progress);
- TextView status = (TextView) mFooterContent.findViewById(R.id.status);
- progressBar.setMax(PROGRESS_BAR_MAX);
- long totalBytes = mCacheStorageInfo.getTotalBytes();
- long usedBytes = mCacheStorageInfo.getUsedBytes();
- long expectedBytes = mCacheStorageInfo.getExpectedUsedBytes();
- long freeBytes = mCacheStorageInfo.getFreeBytes();
-
- Activity activity = mActivity;
- if (totalBytes == 0) {
- progressBar.setProgress(0);
- progressBar.setSecondaryProgress(0);
-
- // TODO: get the string translated
- String label = activity.getString(R.string.free_space_format, "-");
- status.setText(label);
- } else {
- progressBar.setProgress((int) (usedBytes * PROGRESS_BAR_MAX / totalBytes));
- progressBar.setSecondaryProgress(
- (int) (expectedBytes * PROGRESS_BAR_MAX / totalBytes));
- String label = activity.getString(R.string.free_space_format,
- Formatter.formatFileSize(activity, freeBytes));
- status.setText(label);
- }
- }
-
- @Override
- public void onProgressComplete(int result) {
- onBackPressed();
- }
-
- @Override
- public void onProgressUpdate(int index) {
- }
-
- @Override
- public void onSelectionModeChange(int mode) {
- }
-
- @Override
- public void onSelectionChange(Path path, boolean selected) {
- }
-
- @Override
- public void onConfirmDialogDismissed(boolean confirmed) {
- }
-
- @Override
- public void onConfirmDialogShown() {
- }
-
- @Override
- public void onProgressStart() {
- }
-}
diff --git a/src/com/android/gallery3d/app/MovieActivity.java b/src/com/android/gallery3d/app/MovieActivity.java
deleted file mode 100644
index 40edbbe4d..000000000
--- a/src/com/android/gallery3d/app/MovieActivity.java
+++ /dev/null
@@ -1,263 +0,0 @@
-/*
- * Copyright (C) 2007 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.annotation.TargetApi;
-import android.app.ActionBar;
-import android.app.Activity;
-import android.content.AsyncQueryHandler;
-import android.content.ContentResolver;
-import android.content.Intent;
-import android.content.pm.ActivityInfo;
-import android.database.Cursor;
-import android.graphics.Bitmap;
-import android.graphics.drawable.BitmapDrawable;
-import android.media.AudioManager;
-import android.net.Uri;
-import android.os.Build;
-import android.os.Bundle;
-import android.provider.MediaStore;
-import android.provider.OpenableColumns;
-import android.view.KeyEvent;
-import android.view.Menu;
-import android.view.MenuItem;
-import android.view.View;
-import android.view.Window;
-import android.view.WindowManager;
-import android.widget.ShareActionProvider;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.common.Utils;
-
-/**
- * This activity plays a video from a specified URI.
- *
- * The client of this activity can pass a logo bitmap in the intent (KEY_LOGO_BITMAP)
- * to set the action bar logo so the playback process looks more seamlessly integrated with
- * the original activity.
- */
-public class MovieActivity extends Activity {
- @SuppressWarnings("unused")
- private static final String TAG = "MovieActivity";
- public static final String KEY_LOGO_BITMAP = "logo-bitmap";
- public static final String KEY_TREAT_UP_AS_BACK = "treat-up-as-back";
-
- private MoviePlayer mPlayer;
- private boolean mFinishOnCompletion;
- private Uri mUri;
- private boolean mTreatUpAsBack;
-
- @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
- private void setSystemUiVisibility(View rootView) {
- if (ApiHelper.HAS_VIEW_SYSTEM_UI_FLAG_LAYOUT_STABLE) {
- rootView.setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_STABLE
- | View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
- | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION);
- }
- }
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
-
- requestWindowFeature(Window.FEATURE_ACTION_BAR);
- requestWindowFeature(Window.FEATURE_ACTION_BAR_OVERLAY);
-
- setContentView(R.layout.movie_view);
- View rootView = findViewById(R.id.movie_view_root);
-
- setSystemUiVisibility(rootView);
-
- Intent intent = getIntent();
- initializeActionBar(intent);
- mFinishOnCompletion = intent.getBooleanExtra(
- MediaStore.EXTRA_FINISH_ON_COMPLETION, true);
- mTreatUpAsBack = intent.getBooleanExtra(KEY_TREAT_UP_AS_BACK, false);
- mPlayer = new MoviePlayer(rootView, this, intent.getData(), savedInstanceState,
- !mFinishOnCompletion) {
- @Override
- public void onCompletion() {
- if (mFinishOnCompletion) {
- finish();
- }
- }
- };
- if (intent.hasExtra(MediaStore.EXTRA_SCREEN_ORIENTATION)) {
- int orientation = intent.getIntExtra(
- MediaStore.EXTRA_SCREEN_ORIENTATION,
- ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED);
- if (orientation != getRequestedOrientation()) {
- setRequestedOrientation(orientation);
- }
- }
- Window win = getWindow();
- WindowManager.LayoutParams winParams = win.getAttributes();
- winParams.buttonBrightness = WindowManager.LayoutParams.BRIGHTNESS_OVERRIDE_OFF;
- winParams.flags |= WindowManager.LayoutParams.FLAG_FULLSCREEN;
- win.setAttributes(winParams);
-
- // We set the background in the theme to have the launching animation.
- // But for the performance (and battery), we remove the background here.
- win.setBackgroundDrawable(null);
- }
-
- private void setActionBarLogoFromIntent(Intent intent) {
- Bitmap logo = intent.getParcelableExtra(KEY_LOGO_BITMAP);
- if (logo != null) {
- getActionBar().setLogo(
- new BitmapDrawable(getResources(), logo));
- }
- }
-
- private void initializeActionBar(Intent intent) {
- mUri = intent.getData();
- final ActionBar actionBar = getActionBar();
- if (actionBar == null) {
- return;
- }
- setActionBarLogoFromIntent(intent);
- actionBar.setDisplayOptions(
- ActionBar.DISPLAY_HOME_AS_UP,
- ActionBar.DISPLAY_HOME_AS_UP);
-
- String title = intent.getStringExtra(Intent.EXTRA_TITLE);
- if (title != null) {
- actionBar.setTitle(title);
- } else {
- // Displays the filename as title, reading the filename from the
- // interface: {@link android.provider.OpenableColumns#DISPLAY_NAME}.
- AsyncQueryHandler queryHandler =
- new AsyncQueryHandler(getContentResolver()) {
- @Override
- protected void onQueryComplete(int token, Object cookie,
- Cursor cursor) {
- try {
- if ((cursor != null) && cursor.moveToFirst()) {
- String displayName = cursor.getString(0);
-
- // Just show empty title if other apps don't set
- // DISPLAY_NAME
- actionBar.setTitle((displayName == null) ? "" :
- displayName);
- }
- } finally {
- Utils.closeSilently(cursor);
- }
- }
- };
- queryHandler.startQuery(0, null, mUri,
- new String[] {OpenableColumns.DISPLAY_NAME}, null, null,
- null);
- }
- }
-
- @Override
- public boolean onCreateOptionsMenu(Menu menu) {
- super.onCreateOptionsMenu(menu);
- getMenuInflater().inflate(R.menu.movie, menu);
-
- // Document says EXTRA_STREAM should be a content: Uri
- // So, we only share the video if it's "content:".
- MenuItem shareItem = menu.findItem(R.id.action_share);
- if (ContentResolver.SCHEME_CONTENT.equals(mUri.getScheme())) {
- shareItem.setVisible(true);
- ((ShareActionProvider) shareItem.getActionProvider())
- .setShareIntent(createShareIntent());
- } else {
- shareItem.setVisible(false);
- }
- return true;
- }
-
- private Intent createShareIntent() {
- Intent intent = new Intent(Intent.ACTION_SEND);
- intent.setType("video/*");
- intent.putExtra(Intent.EXTRA_STREAM, mUri);
- return intent;
- }
-
- @Override
- public boolean onOptionsItemSelected(MenuItem item) {
- int id = item.getItemId();
- if (id == android.R.id.home) {
- if (mTreatUpAsBack) {
- finish();
- } else {
- startActivity(new Intent(this, Gallery.class));
- finish();
- }
- return true;
- } else if (id == R.id.action_share) {
- startActivity(Intent.createChooser(createShareIntent(),
- getString(R.string.share)));
- return true;
- }
- return false;
- }
-
- @Override
- public void onStart() {
- ((AudioManager) getSystemService(AUDIO_SERVICE))
- .requestAudioFocus(null, AudioManager.STREAM_MUSIC,
- AudioManager.AUDIOFOCUS_GAIN_TRANSIENT);
- super.onStart();
- }
-
- @Override
- protected void onStop() {
- ((AudioManager) getSystemService(AUDIO_SERVICE))
- .abandonAudioFocus(null);
- super.onStop();
- }
-
- @Override
- public void onPause() {
- mPlayer.onPause();
- super.onPause();
- }
-
- @Override
- public void onResume() {
- mPlayer.onResume();
- super.onResume();
- }
-
- @Override
- public void onSaveInstanceState(Bundle outState) {
- super.onSaveInstanceState(outState);
- mPlayer.onSaveInstanceState(outState);
- }
-
- @Override
- public void onDestroy() {
- mPlayer.onDestroy();
- super.onDestroy();
- }
-
- @Override
- public boolean onKeyDown(int keyCode, KeyEvent event) {
- return mPlayer.onKeyDown(keyCode, event)
- || super.onKeyDown(keyCode, event);
- }
-
- @Override
- public boolean onKeyUp(int keyCode, KeyEvent event) {
- return mPlayer.onKeyUp(keyCode, event)
- || super.onKeyUp(keyCode, event);
- }
-}
diff --git a/src/com/android/gallery3d/app/MovieControllerOverlay.java b/src/com/android/gallery3d/app/MovieControllerOverlay.java
deleted file mode 100644
index f01e619c6..000000000
--- a/src/com/android/gallery3d/app/MovieControllerOverlay.java
+++ /dev/null
@@ -1,185 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.content.Context;
-import android.os.Handler;
-import android.view.KeyEvent;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.animation.Animation;
-import android.view.animation.Animation.AnimationListener;
-import android.view.animation.AnimationUtils;
-import com.android.gallery3d.R;
-
-/**
- * The playback controller for the Movie Player.
- */
-public class MovieControllerOverlay extends CommonControllerOverlay implements
- AnimationListener {
-
- private boolean hidden;
-
- private final Handler handler;
- private final Runnable startHidingRunnable;
- private final Animation hideAnimation;
-
- public MovieControllerOverlay(Context context) {
- super(context);
-
- handler = new Handler();
- startHidingRunnable = new Runnable() {
- @Override
- public void run() {
- startHiding();
- }
- };
-
- hideAnimation = AnimationUtils.loadAnimation(context, R.anim.player_out);
- hideAnimation.setAnimationListener(this);
-
- hide();
- }
-
- @Override
- protected void createTimeBar(Context context) {
- mTimeBar = new TimeBar(context, this);
- }
-
- @Override
- public void hide() {
- boolean wasHidden = hidden;
- hidden = true;
- super.hide();
- if (mListener != null && wasHidden != hidden) {
- mListener.onHidden();
- }
- }
-
-
- @Override
- public void show() {
- boolean wasHidden = hidden;
- hidden = false;
- super.show();
- if (mListener != null && wasHidden != hidden) {
- mListener.onShown();
- }
- maybeStartHiding();
- }
-
- private void maybeStartHiding() {
- cancelHiding();
- if (mState == State.PLAYING) {
- handler.postDelayed(startHidingRunnable, 2500);
- }
- }
-
- private void startHiding() {
- startHideAnimation(mBackground);
- startHideAnimation(mTimeBar);
- startHideAnimation(mPlayPauseReplayView);
- }
-
- private void startHideAnimation(View view) {
- if (view.getVisibility() == View.VISIBLE) {
- view.startAnimation(hideAnimation);
- }
- }
-
- private void cancelHiding() {
- handler.removeCallbacks(startHidingRunnable);
- mBackground.setAnimation(null);
- mTimeBar.setAnimation(null);
- mPlayPauseReplayView.setAnimation(null);
- }
-
- @Override
- public void onAnimationStart(Animation animation) {
- // Do nothing.
- }
-
- @Override
- public void onAnimationRepeat(Animation animation) {
- // Do nothing.
- }
-
- @Override
- public void onAnimationEnd(Animation animation) {
- hide();
- }
-
- @Override
- public boolean onKeyDown(int keyCode, KeyEvent event) {
- if (hidden) {
- show();
- }
- return super.onKeyDown(keyCode, event);
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- if (super.onTouchEvent(event)) {
- return true;
- }
-
- if (hidden) {
- show();
- return true;
- }
- switch (event.getAction()) {
- case MotionEvent.ACTION_DOWN:
- cancelHiding();
- if (mState == State.PLAYING || mState == State.PAUSED) {
- mListener.onPlayPause();
- }
- break;
- case MotionEvent.ACTION_UP:
- maybeStartHiding();
- break;
- }
- return true;
- }
-
- @Override
- protected void updateViews() {
- if (hidden) {
- return;
- }
- super.updateViews();
- }
-
- // TimeBar listener
-
- @Override
- public void onScrubbingStart() {
- cancelHiding();
- super.onScrubbingStart();
- }
-
- @Override
- public void onScrubbingMove(int time) {
- cancelHiding();
- super.onScrubbingMove(time);
- }
-
- @Override
- public void onScrubbingEnd(int time, int trimStartTime, int trimEndTime) {
- maybeStartHiding();
- super.onScrubbingEnd(time, trimStartTime, trimEndTime);
- }
-}
diff --git a/src/com/android/gallery3d/app/MoviePlayer.java b/src/com/android/gallery3d/app/MoviePlayer.java
deleted file mode 100644
index ce9183483..000000000
--- a/src/com/android/gallery3d/app/MoviePlayer.java
+++ /dev/null
@@ -1,525 +0,0 @@
-/*
- * Copyright (C) 2009 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.annotation.TargetApi;
-import android.app.AlertDialog;
-import android.content.BroadcastReceiver;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.content.DialogInterface.OnCancelListener;
-import android.content.DialogInterface.OnClickListener;
-import android.content.Intent;
-import android.content.IntentFilter;
-import android.media.AudioManager;
-import android.media.MediaPlayer;
-import android.net.Uri;
-import android.os.Build;
-import android.os.Bundle;
-import android.os.Handler;
-import android.view.KeyEvent;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.VideoView;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.common.BlobCache;
-import com.android.gallery3d.util.CacheManager;
-import com.android.gallery3d.util.GalleryUtils;
-
-import java.io.ByteArrayInputStream;
-import java.io.ByteArrayOutputStream;
-import java.io.DataInputStream;
-import java.io.DataOutputStream;
-
-public class MoviePlayer implements
- MediaPlayer.OnErrorListener, MediaPlayer.OnCompletionListener,
- ControllerOverlay.Listener {
- @SuppressWarnings("unused")
- private static final String TAG = "MoviePlayer";
-
- private static final String KEY_VIDEO_POSITION = "video-position";
- private static final String KEY_RESUMEABLE_TIME = "resumeable-timeout";
-
- // These are constants in KeyEvent, appearing on API level 11.
- private static final int KEYCODE_MEDIA_PLAY = 126;
- private static final int KEYCODE_MEDIA_PAUSE = 127;
-
- // Copied from MediaPlaybackService in the Music Player app.
- private static final String SERVICECMD = "com.android.music.musicservicecommand";
- private static final String CMDNAME = "command";
- private static final String CMDPAUSE = "pause";
-
- private static final long BLACK_TIMEOUT = 500;
-
- // If we resume the acitivty with in RESUMEABLE_TIMEOUT, we will keep playing.
- // Otherwise, we pause the player.
- private static final long RESUMEABLE_TIMEOUT = 3 * 60 * 1000; // 3 mins
-
- private Context mContext;
- private final VideoView mVideoView;
- private final View mRootView;
- private final Bookmarker mBookmarker;
- private final Uri mUri;
- private final Handler mHandler = new Handler();
- private final AudioBecomingNoisyReceiver mAudioBecomingNoisyReceiver;
- private final MovieControllerOverlay mController;
-
- private long mResumeableTime = Long.MAX_VALUE;
- private int mVideoPosition = 0;
- private boolean mHasPaused = false;
- private int mLastSystemUiVis = 0;
-
- // If the time bar is being dragged.
- private boolean mDragging;
-
- // If the time bar is visible.
- private boolean mShowing;
-
- private final Runnable mPlayingChecker = new Runnable() {
- @Override
- public void run() {
- if (mVideoView.isPlaying()) {
- mController.showPlaying();
- } else {
- mHandler.postDelayed(mPlayingChecker, 250);
- }
- }
- };
-
- private final Runnable mProgressChecker = new Runnable() {
- @Override
- public void run() {
- int pos = setProgress();
- mHandler.postDelayed(mProgressChecker, 1000 - (pos % 1000));
- }
- };
-
- public MoviePlayer(View rootView, final MovieActivity movieActivity,
- Uri videoUri, Bundle savedInstance, boolean canReplay) {
- mContext = movieActivity.getApplicationContext();
- mRootView = rootView;
- mVideoView = (VideoView) rootView.findViewById(R.id.surface_view);
- mBookmarker = new Bookmarker(movieActivity);
- mUri = videoUri;
-
- mController = new MovieControllerOverlay(mContext);
- ((ViewGroup)rootView).addView(mController.getView());
- mController.setListener(this);
- mController.setCanReplay(canReplay);
-
- mVideoView.setOnErrorListener(this);
- mVideoView.setOnCompletionListener(this);
- mVideoView.setVideoURI(mUri);
- mVideoView.setOnTouchListener(new View.OnTouchListener() {
- @Override
- public boolean onTouch(View v, MotionEvent event) {
- mController.show();
- return true;
- }
- });
- mVideoView.setOnPreparedListener(new MediaPlayer.OnPreparedListener() {
- @Override
- public void onPrepared(MediaPlayer player) {
- if (!mVideoView.canSeekForward() || !mVideoView.canSeekBackward()) {
- mController.setSeekable(false);
- } else {
- mController.setSeekable(true);
- }
- setProgress();
- }
- });
-
- // The SurfaceView is transparent before drawing the first frame.
- // This makes the UI flashing when open a video. (black -> old screen
- // -> video) However, we have no way to know the timing of the first
- // frame. So, we hide the VideoView for a while to make sure the
- // video has been drawn on it.
- mVideoView.postDelayed(new Runnable() {
- @Override
- public void run() {
- mVideoView.setVisibility(View.VISIBLE);
- }
- }, BLACK_TIMEOUT);
-
- setOnSystemUiVisibilityChangeListener();
- // Hide system UI by default
- showSystemUi(false);
-
- mAudioBecomingNoisyReceiver = new AudioBecomingNoisyReceiver();
- mAudioBecomingNoisyReceiver.register();
-
- Intent i = new Intent(SERVICECMD);
- i.putExtra(CMDNAME, CMDPAUSE);
- movieActivity.sendBroadcast(i);
-
- if (savedInstance != null) { // this is a resumed activity
- mVideoPosition = savedInstance.getInt(KEY_VIDEO_POSITION, 0);
- mResumeableTime = savedInstance.getLong(KEY_RESUMEABLE_TIME, Long.MAX_VALUE);
- mVideoView.start();
- mVideoView.suspend();
- mHasPaused = true;
- } else {
- final Integer bookmark = mBookmarker.getBookmark(mUri);
- if (bookmark != null) {
- showResumeDialog(movieActivity, bookmark);
- } else {
- startVideo();
- }
- }
- }
-
- @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
- private void setOnSystemUiVisibilityChangeListener() {
- if (!ApiHelper.HAS_VIEW_SYSTEM_UI_FLAG_HIDE_NAVIGATION) return;
-
- // When the user touches the screen or uses some hard key, the framework
- // will change system ui visibility from invisible to visible. We show
- // the media control and enable system UI (e.g. ActionBar) to be visible at this point
- mVideoView.setOnSystemUiVisibilityChangeListener(
- new View.OnSystemUiVisibilityChangeListener() {
- @Override
- public void onSystemUiVisibilityChange(int visibility) {
- int diff = mLastSystemUiVis ^ visibility;
- mLastSystemUiVis = visibility;
- if ((diff & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) != 0
- && (visibility & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) == 0) {
- mController.show();
- }
- }
- });
- }
-
- @SuppressWarnings("deprecation")
- @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
- private void showSystemUi(boolean visible) {
- if (!ApiHelper.HAS_VIEW_SYSTEM_UI_FLAG_LAYOUT_STABLE) return;
-
- int flag = View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
- | View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
- | View.SYSTEM_UI_FLAG_LAYOUT_STABLE;
- if (!visible) {
- // We used the deprecated "STATUS_BAR_HIDDEN" for unbundling
- flag |= View.STATUS_BAR_HIDDEN | View.SYSTEM_UI_FLAG_FULLSCREEN
- | View.SYSTEM_UI_FLAG_HIDE_NAVIGATION;
- }
- mVideoView.setSystemUiVisibility(flag);
- }
-
- public void onSaveInstanceState(Bundle outState) {
- outState.putInt(KEY_VIDEO_POSITION, mVideoPosition);
- outState.putLong(KEY_RESUMEABLE_TIME, mResumeableTime);
- }
-
- private void showResumeDialog(Context context, final int bookmark) {
- AlertDialog.Builder builder = new AlertDialog.Builder(context);
- builder.setTitle(R.string.resume_playing_title);
- builder.setMessage(String.format(
- context.getString(R.string.resume_playing_message),
- GalleryUtils.formatDuration(context, bookmark / 1000)));
- builder.setOnCancelListener(new OnCancelListener() {
- @Override
- public void onCancel(DialogInterface dialog) {
- onCompletion();
- }
- });
- builder.setPositiveButton(
- R.string.resume_playing_resume, new OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int which) {
- mVideoView.seekTo(bookmark);
- startVideo();
- }
- });
- builder.setNegativeButton(
- R.string.resume_playing_restart, new OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int which) {
- startVideo();
- }
- });
- builder.show();
- }
-
- public void onPause() {
- mHasPaused = true;
- mHandler.removeCallbacksAndMessages(null);
- mVideoPosition = mVideoView.getCurrentPosition();
- mBookmarker.setBookmark(mUri, mVideoPosition, mVideoView.getDuration());
- mVideoView.suspend();
- mResumeableTime = System.currentTimeMillis() + RESUMEABLE_TIMEOUT;
- }
-
- public void onResume() {
- if (mHasPaused) {
- mVideoView.seekTo(mVideoPosition);
- mVideoView.resume();
-
- // If we have slept for too long, pause the play
- if (System.currentTimeMillis() > mResumeableTime) {
- pauseVideo();
- }
- }
- mHandler.post(mProgressChecker);
- }
-
- public void onDestroy() {
- mVideoView.stopPlayback();
- mAudioBecomingNoisyReceiver.unregister();
- }
-
- // This updates the time bar display (if necessary). It is called every
- // second by mProgressChecker and also from places where the time bar needs
- // to be updated immediately.
- private int setProgress() {
- if (mDragging || !mShowing) {
- return 0;
- }
- int position = mVideoView.getCurrentPosition();
- int duration = mVideoView.getDuration();
- mController.setTimes(position, duration, 0, 0);
- return position;
- }
-
- private void startVideo() {
- // For streams that we expect to be slow to start up, show a
- // progress spinner until playback starts.
- String scheme = mUri.getScheme();
- if ("http".equalsIgnoreCase(scheme) || "rtsp".equalsIgnoreCase(scheme)) {
- mController.showLoading();
- mHandler.removeCallbacks(mPlayingChecker);
- mHandler.postDelayed(mPlayingChecker, 250);
- } else {
- mController.showPlaying();
- mController.hide();
- }
-
- mVideoView.start();
- setProgress();
- }
-
- private void playVideo() {
- mVideoView.start();
- mController.showPlaying();
- setProgress();
- }
-
- private void pauseVideo() {
- mVideoView.pause();
- mController.showPaused();
- }
-
- // Below are notifications from VideoView
- @Override
- public boolean onError(MediaPlayer player, int arg1, int arg2) {
- mHandler.removeCallbacksAndMessages(null);
- // VideoView will show an error dialog if we return false, so no need
- // to show more message.
- mController.showErrorMessage("");
- return false;
- }
-
- @Override
- public void onCompletion(MediaPlayer mp) {
- mController.showEnded();
- onCompletion();
- }
-
- public void onCompletion() {
- }
-
- // Below are notifications from ControllerOverlay
- @Override
- public void onPlayPause() {
- if (mVideoView.isPlaying()) {
- pauseVideo();
- } else {
- playVideo();
- }
- }
-
- @Override
- public void onSeekStart() {
- mDragging = true;
- }
-
- @Override
- public void onSeekMove(int time) {
- mVideoView.seekTo(time);
- }
-
- @Override
- public void onSeekEnd(int time, int start, int end) {
- mDragging = false;
- mVideoView.seekTo(time);
- setProgress();
- }
-
- @Override
- public void onShown() {
- mShowing = true;
- setProgress();
- showSystemUi(true);
- }
-
- @Override
- public void onHidden() {
- mShowing = false;
- showSystemUi(false);
- }
-
- @Override
- public void onReplay() {
- startVideo();
- }
-
- // Below are key events passed from MovieActivity.
- public boolean onKeyDown(int keyCode, KeyEvent event) {
-
- // Some headsets will fire off 7-10 events on a single click
- if (event.getRepeatCount() > 0) {
- return isMediaKey(keyCode);
- }
-
- switch (keyCode) {
- case KeyEvent.KEYCODE_HEADSETHOOK:
- case KeyEvent.KEYCODE_MEDIA_PLAY_PAUSE:
- if (mVideoView.isPlaying()) {
- pauseVideo();
- } else {
- playVideo();
- }
- return true;
- case KEYCODE_MEDIA_PAUSE:
- if (mVideoView.isPlaying()) {
- pauseVideo();
- }
- return true;
- case KEYCODE_MEDIA_PLAY:
- if (!mVideoView.isPlaying()) {
- playVideo();
- }
- return true;
- case KeyEvent.KEYCODE_MEDIA_PREVIOUS:
- case KeyEvent.KEYCODE_MEDIA_NEXT:
- // TODO: Handle next / previous accordingly, for now we're
- // just consuming the events.
- return true;
- }
- return false;
- }
-
- public boolean onKeyUp(int keyCode, KeyEvent event) {
- return isMediaKey(keyCode);
- }
-
- private static boolean isMediaKey(int keyCode) {
- return keyCode == KeyEvent.KEYCODE_HEADSETHOOK
- || keyCode == KeyEvent.KEYCODE_MEDIA_PREVIOUS
- || keyCode == KeyEvent.KEYCODE_MEDIA_NEXT
- || keyCode == KeyEvent.KEYCODE_MEDIA_PLAY_PAUSE
- || keyCode == KeyEvent.KEYCODE_MEDIA_PLAY
- || keyCode == KeyEvent.KEYCODE_MEDIA_PAUSE;
- }
-
- // We want to pause when the headset is unplugged.
- private class AudioBecomingNoisyReceiver extends BroadcastReceiver {
-
- public void register() {
- mContext.registerReceiver(this,
- new IntentFilter(AudioManager.ACTION_AUDIO_BECOMING_NOISY));
- }
-
- public void unregister() {
- mContext.unregisterReceiver(this);
- }
-
- @Override
- public void onReceive(Context context, Intent intent) {
- if (mVideoView.isPlaying()) pauseVideo();
- }
- }
-}
-
-class Bookmarker {
- private static final String TAG = "Bookmarker";
-
- private static final String BOOKMARK_CACHE_FILE = "bookmark";
- private static final int BOOKMARK_CACHE_MAX_ENTRIES = 100;
- private static final int BOOKMARK_CACHE_MAX_BYTES = 10 * 1024;
- private static final int BOOKMARK_CACHE_VERSION = 1;
-
- private static final int HALF_MINUTE = 30 * 1000;
- private static final int TWO_MINUTES = 4 * HALF_MINUTE;
-
- private final Context mContext;
-
- public Bookmarker(Context context) {
- mContext = context;
- }
-
- public void setBookmark(Uri uri, int bookmark, int duration) {
- try {
- BlobCache cache = CacheManager.getCache(mContext,
- BOOKMARK_CACHE_FILE, BOOKMARK_CACHE_MAX_ENTRIES,
- BOOKMARK_CACHE_MAX_BYTES, BOOKMARK_CACHE_VERSION);
-
- ByteArrayOutputStream bos = new ByteArrayOutputStream();
- DataOutputStream dos = new DataOutputStream(bos);
- dos.writeUTF(uri.toString());
- dos.writeInt(bookmark);
- dos.writeInt(duration);
- dos.flush();
- cache.insert(uri.hashCode(), bos.toByteArray());
- } catch (Throwable t) {
- Log.w(TAG, "setBookmark failed", t);
- }
- }
-
- public Integer getBookmark(Uri uri) {
- try {
- BlobCache cache = CacheManager.getCache(mContext,
- BOOKMARK_CACHE_FILE, BOOKMARK_CACHE_MAX_ENTRIES,
- BOOKMARK_CACHE_MAX_BYTES, BOOKMARK_CACHE_VERSION);
-
- byte[] data = cache.lookup(uri.hashCode());
- if (data == null) return null;
-
- DataInputStream dis = new DataInputStream(
- new ByteArrayInputStream(data));
-
- String uriString = DataInputStream.readUTF(dis);
- int bookmark = dis.readInt();
- int duration = dis.readInt();
-
- if (!uriString.equals(uri.toString())) {
- return null;
- }
-
- if ((bookmark < HALF_MINUTE) || (duration < TWO_MINUTES)
- || (bookmark > (duration - HALF_MINUTE))) {
- return null;
- }
- return Integer.valueOf(bookmark);
- } catch (Throwable t) {
- Log.w(TAG, "getBookmark failed", t);
- }
- return null;
- }
-}
diff --git a/src/com/android/gallery3d/app/MuteVideo.java b/src/com/android/gallery3d/app/MuteVideo.java
deleted file mode 100644
index d3f3aa594..000000000
--- a/src/com/android/gallery3d/app/MuteVideo.java
+++ /dev/null
@@ -1,104 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.app.Activity;
-import android.app.ProgressDialog;
-import android.content.Intent;
-import android.net.Uri;
-import android.os.Handler;
-import android.provider.MediaStore;
-import android.widget.Toast;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.util.SaveVideoFileInfo;
-import com.android.gallery3d.util.SaveVideoFileUtils;
-
-import java.io.IOException;
-
-public class MuteVideo {
-
- private ProgressDialog mMuteProgress;
-
- private String mFilePath = null;
- private Uri mUri = null;
- private SaveVideoFileInfo mDstFileInfo = null;
- private Activity mActivity = null;
- private final Handler mHandler = new Handler();
-
- final String TIME_STAMP_NAME = "'MUTE'_yyyyMMdd_HHmmss";
-
- public MuteVideo(String filePath, Uri uri, Activity activity) {
- mUri = uri;
- mFilePath = filePath;
- mActivity = activity;
- }
-
- public void muteInBackground() {
- mDstFileInfo = SaveVideoFileUtils.getDstMp4FileInfo(TIME_STAMP_NAME,
- mActivity.getContentResolver(), mUri,
- mActivity.getString(R.string.folder_download));
-
- showProgressDialog();
- new Thread(new Runnable() {
- @Override
- public void run() {
- try {
- VideoUtils.startMute(mFilePath, mDstFileInfo);
- SaveVideoFileUtils.insertContent(
- mDstFileInfo, mActivity.getContentResolver(), mUri);
- } catch (IOException e) {
- Toast.makeText(mActivity, mActivity.getString(R.string.video_mute_err),
- Toast.LENGTH_SHORT).show();
- }
- // After muting is done, trigger the UI changed.
- mHandler.post(new Runnable() {
- @Override
- public void run() {
- Toast.makeText(mActivity.getApplicationContext(),
- mActivity.getString(R.string.save_into,
- mDstFileInfo.mFolderName),
- Toast.LENGTH_SHORT)
- .show();
-
- if (mMuteProgress != null) {
- mMuteProgress.dismiss();
- mMuteProgress = null;
-
- // Show the result only when the activity not
- // stopped.
- Intent intent = new Intent(android.content.Intent.ACTION_VIEW);
- intent.setDataAndType(Uri.fromFile(mDstFileInfo.mFile), "video/*");
- intent.putExtra(MediaStore.EXTRA_FINISH_ON_COMPLETION, false);
- mActivity.startActivity(intent);
- }
- }
- });
- }
- }).start();
- }
-
- private void showProgressDialog() {
- mMuteProgress = new ProgressDialog(mActivity);
- mMuteProgress.setTitle(mActivity.getString(R.string.muting));
- mMuteProgress.setMessage(mActivity.getString(R.string.please_wait));
- mMuteProgress.setCancelable(false);
- mMuteProgress.setCanceledOnTouchOutside(false);
- mMuteProgress.show();
- }
-}
diff --git a/src/com/android/gallery3d/app/NotificationIds.java b/src/com/android/gallery3d/app/NotificationIds.java
deleted file mode 100644
index d697d854b..000000000
--- a/src/com/android/gallery3d/app/NotificationIds.java
+++ /dev/null
@@ -1,22 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-public class NotificationIds {
- public static final int INGEST_NOTIFICATION_SCANNING = 10;
- public static final int INGEST_NOTIFICATION_IMPORTING = 11;
-}
diff --git a/src/com/android/gallery3d/app/OrientationManager.java b/src/com/android/gallery3d/app/OrientationManager.java
deleted file mode 100644
index f2f632c9f..000000000
--- a/src/com/android/gallery3d/app/OrientationManager.java
+++ /dev/null
@@ -1,166 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.app.Activity;
-import android.content.ContentResolver;
-import android.content.Context;
-import android.content.pm.ActivityInfo;
-import android.content.res.Configuration;
-import android.provider.Settings;
-import android.view.OrientationEventListener;
-import android.view.Surface;
-
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.ui.OrientationSource;
-
-public class OrientationManager implements OrientationSource {
- private static final String TAG = "OrientationManager";
-
- // Orientation hysteresis amount used in rounding, in degrees
- private static final int ORIENTATION_HYSTERESIS = 5;
-
- private Activity mActivity;
- private MyOrientationEventListener mOrientationListener;
- // If the framework orientation is locked.
- private boolean mOrientationLocked = false;
-
- // This is true if "Settings -> Display -> Rotation Lock" is checked. We
- // don't allow the orientation to be unlocked if the value is true.
- private boolean mRotationLockedSetting = false;
-
- public OrientationManager(Activity activity) {
- mActivity = activity;
- mOrientationListener = new MyOrientationEventListener(activity);
- }
-
- public void resume() {
- ContentResolver resolver = mActivity.getContentResolver();
- mRotationLockedSetting = Settings.System.getInt(
- resolver, Settings.System.ACCELEROMETER_ROTATION, 0) != 1;
- mOrientationListener.enable();
- }
-
- public void pause() {
- mOrientationListener.disable();
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Orientation handling
- //
- // We can choose to lock the framework orientation or not. If we lock the
- // framework orientation, we calculate a a compensation value according to
- // current device orientation and send it to listeners. If we don't lock
- // the framework orientation, we always set the compensation value to 0.
- ////////////////////////////////////////////////////////////////////////////
-
- // Lock the framework orientation to the current device orientation
- public void lockOrientation() {
- if (mOrientationLocked) return;
- mOrientationLocked = true;
- if (ApiHelper.HAS_ORIENTATION_LOCK) {
- mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_LOCKED);
- } else {
- mActivity.setRequestedOrientation(calculateCurrentScreenOrientation());
- }
- }
-
- // Unlock the framework orientation, so it can change when the device
- // rotates.
- public void unlockOrientation() {
- if (!mOrientationLocked) return;
- mOrientationLocked = false;
- Log.d(TAG, "unlock orientation");
- mActivity.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_FULL_SENSOR);
- }
-
- private int calculateCurrentScreenOrientation() {
- int displayRotation = getDisplayRotation();
- // Display rotation >= 180 means we need to use the REVERSE landscape/portrait
- boolean standard = displayRotation < 180;
- if (mActivity.getResources().getConfiguration().orientation
- == Configuration.ORIENTATION_LANDSCAPE) {
- return standard
- ? ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE
- : ActivityInfo.SCREEN_ORIENTATION_REVERSE_LANDSCAPE;
- } else {
- if (displayRotation == 90 || displayRotation == 270) {
- // If displayRotation = 90 or 270 then we are on a landscape
- // device. On landscape devices, portrait is a 90 degree
- // clockwise rotation from landscape, so we need
- // to flip which portrait we pick as display rotation is counter clockwise
- standard = !standard;
- }
- return standard
- ? ActivityInfo.SCREEN_ORIENTATION_PORTRAIT
- : ActivityInfo.SCREEN_ORIENTATION_REVERSE_PORTRAIT;
- }
- }
-
- // This listens to the device orientation, so we can update the compensation.
- private class MyOrientationEventListener extends OrientationEventListener {
- public MyOrientationEventListener(Context context) {
- super(context);
- }
-
- @Override
- public void onOrientationChanged(int orientation) {
- // We keep the last known orientation. So if the user first orient
- // the camera then point the camera to floor or sky, we still have
- // the correct orientation.
- if (orientation == ORIENTATION_UNKNOWN) return;
- orientation = roundOrientation(orientation, 0);
- }
- }
-
- @Override
- public int getDisplayRotation() {
- return getDisplayRotation(mActivity);
- }
-
- @Override
- public int getCompensation() {
- return 0;
- }
-
- private static int roundOrientation(int orientation, int orientationHistory) {
- boolean changeOrientation = false;
- if (orientationHistory == OrientationEventListener.ORIENTATION_UNKNOWN) {
- changeOrientation = true;
- } else {
- int dist = Math.abs(orientation - orientationHistory);
- dist = Math.min(dist, 360 - dist);
- changeOrientation = (dist >= 45 + ORIENTATION_HYSTERESIS);
- }
- if (changeOrientation) {
- return ((orientation + 45) / 90 * 90) % 360;
- }
- return orientationHistory;
- }
-
- private static int getDisplayRotation(Activity activity) {
- int rotation = activity.getWindowManager().getDefaultDisplay()
- .getRotation();
- switch (rotation) {
- case Surface.ROTATION_0: return 0;
- case Surface.ROTATION_90: return 90;
- case Surface.ROTATION_180: return 180;
- case Surface.ROTATION_270: return 270;
- }
- return 0;
- }
-}
diff --git a/src/com/android/gallery3d/app/PackagesMonitor.java b/src/com/android/gallery3d/app/PackagesMonitor.java
deleted file mode 100644
index 9b2412f1b..000000000
--- a/src/com/android/gallery3d/app/PackagesMonitor.java
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.app.IntentService;
-import android.content.BroadcastReceiver;
-import android.content.Context;
-import android.content.Intent;
-import android.content.SharedPreferences;
-import android.preference.PreferenceManager;
-
-import com.android.gallery3d.picasasource.PicasaSource;
-import com.android.gallery3d.util.LightCycleHelper;
-
-public class PackagesMonitor extends BroadcastReceiver {
- public static final String KEY_PACKAGES_VERSION = "packages-version";
-
- public synchronized static int getPackagesVersion(Context context) {
- SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
- return prefs.getInt(KEY_PACKAGES_VERSION, 1);
- }
-
- @Override
- public void onReceive(final Context context, final Intent intent) {
- intent.setClass(context, AsyncService.class);
- context.startService(intent);
- }
-
- public static class AsyncService extends IntentService {
- public AsyncService() {
- super("GalleryPackagesMonitorAsync");
- }
-
- @Override
- protected void onHandleIntent(Intent intent) {
- onReceiveAsync(this, intent);
- }
- }
-
- // Runs in a background thread.
- private static void onReceiveAsync(Context context, Intent intent) {
- SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
-
- int version = prefs.getInt(KEY_PACKAGES_VERSION, 1);
- prefs.edit().putInt(KEY_PACKAGES_VERSION, version + 1).commit();
-
- String action = intent.getAction();
- String packageName = intent.getData().getSchemeSpecificPart();
- if (Intent.ACTION_PACKAGE_ADDED.equals(action)) {
- PicasaSource.onPackageAdded(context, packageName);
- } else if (Intent.ACTION_PACKAGE_REMOVED.equals(action)) {
- PicasaSource.onPackageRemoved(context, packageName);
- } else if (Intent.ACTION_PACKAGE_CHANGED.equals(action)) {
- PicasaSource.onPackageChanged(context, packageName);
- }
- }
-}
diff --git a/src/com/android/gallery3d/app/PanoramaMetadataSupport.java b/src/com/android/gallery3d/app/PanoramaMetadataSupport.java
deleted file mode 100644
index ba0c9e71a..000000000
--- a/src/com/android/gallery3d/app/PanoramaMetadataSupport.java
+++ /dev/null
@@ -1,93 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.app;
-
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.MediaObject.PanoramaSupportCallback;
-import com.android.gallery3d.data.PanoramaMetadataJob;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.FutureListener;
-import com.android.gallery3d.util.LightCycleHelper;
-import com.android.gallery3d.util.LightCycleHelper.PanoramaMetadata;
-
-import java.util.ArrayList;
-
-/**
- * This class breaks out the off-thread panorama support checks so that the
- * complexity can be shared between UriImage and LocalImage, which need to
- * support panoramas.
- */
-public class PanoramaMetadataSupport implements FutureListener<PanoramaMetadata> {
- private Object mLock = new Object();
- private Future<PanoramaMetadata> mGetPanoMetadataTask;
- private PanoramaMetadata mPanoramaMetadata;
- private ArrayList<PanoramaSupportCallback> mCallbacksWaiting;
- private MediaObject mMediaObject;
-
- public PanoramaMetadataSupport(MediaObject mediaObject) {
- mMediaObject = mediaObject;
- }
-
- public void getPanoramaSupport(GalleryApp app, PanoramaSupportCallback callback) {
- synchronized (mLock) {
- if (mPanoramaMetadata != null) {
- callback.panoramaInfoAvailable(mMediaObject, mPanoramaMetadata.mUsePanoramaViewer,
- mPanoramaMetadata.mIsPanorama360);
- } else {
- if (mCallbacksWaiting == null) {
- mCallbacksWaiting = new ArrayList<PanoramaSupportCallback>();
- mGetPanoMetadataTask = app.getThreadPool().submit(
- new PanoramaMetadataJob(app.getAndroidContext(),
- mMediaObject.getContentUri()), this);
-
- }
- mCallbacksWaiting.add(callback);
- }
- }
- }
-
- public void clearCachedValues() {
- synchronized (mLock) {
- if (mPanoramaMetadata != null) {
- mPanoramaMetadata = null;
- } else if (mGetPanoMetadataTask != null) {
- mGetPanoMetadataTask.cancel();
- for (PanoramaSupportCallback cb : mCallbacksWaiting) {
- cb.panoramaInfoAvailable(mMediaObject, false, false);
- }
- mGetPanoMetadataTask = null;
- mCallbacksWaiting = null;
- }
- }
- }
-
- @Override
- public void onFutureDone(Future<PanoramaMetadata> future) {
- synchronized (mLock) {
- mPanoramaMetadata = future.get();
- if (mPanoramaMetadata == null) {
- // Error getting panorama data from file. Treat as not panorama.
- mPanoramaMetadata = LightCycleHelper.NOT_PANORAMA;
- }
- for (PanoramaSupportCallback cb : mCallbacksWaiting) {
- cb.panoramaInfoAvailable(mMediaObject, mPanoramaMetadata.mUsePanoramaViewer,
- mPanoramaMetadata.mIsPanorama360);
- }
- mGetPanoMetadataTask = null;
- mCallbacksWaiting = null;
- }
- }
-}
diff --git a/src/com/android/gallery3d/app/PhotoDataAdapter.java b/src/com/android/gallery3d/app/PhotoDataAdapter.java
deleted file mode 100644
index fd3a7cf73..000000000
--- a/src/com/android/gallery3d/app/PhotoDataAdapter.java
+++ /dev/null
@@ -1,1133 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.graphics.Bitmap;
-import android.graphics.BitmapRegionDecoder;
-import android.os.Handler;
-import android.os.Message;
-
-import com.android.gallery3d.common.BitmapUtils;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.ContentListener;
-import com.android.gallery3d.data.LocalMediaItem;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.glrenderer.TiledTexture;
-import com.android.gallery3d.ui.PhotoView;
-import com.android.gallery3d.ui.ScreenNail;
-import com.android.gallery3d.ui.SynchronizedHandler;
-import com.android.gallery3d.ui.TileImageViewAdapter;
-import com.android.gallery3d.ui.TiledScreenNail;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.FutureListener;
-import com.android.gallery3d.util.MediaSetUtils;
-import com.android.gallery3d.util.ThreadPool;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.concurrent.Callable;
-import java.util.concurrent.ExecutionException;
-import java.util.concurrent.FutureTask;
-
-public class PhotoDataAdapter implements PhotoPage.Model {
- @SuppressWarnings("unused")
- private static final String TAG = "PhotoDataAdapter";
-
- private static final int MSG_LOAD_START = 1;
- private static final int MSG_LOAD_FINISH = 2;
- private static final int MSG_RUN_OBJECT = 3;
- private static final int MSG_UPDATE_IMAGE_REQUESTS = 4;
-
- private static final int MIN_LOAD_COUNT = 16;
- private static final int DATA_CACHE_SIZE = 256;
- private static final int SCREEN_NAIL_MAX = PhotoView.SCREEN_NAIL_MAX;
- private static final int IMAGE_CACHE_SIZE = 2 * SCREEN_NAIL_MAX + 1;
-
- private static final int BIT_SCREEN_NAIL = 1;
- private static final int BIT_FULL_IMAGE = 2;
-
- // sImageFetchSeq is the fetching sequence for images.
- // We want to fetch the current screennail first (offset = 0), the next
- // screennail (offset = +1), then the previous screennail (offset = -1) etc.
- // After all the screennail are fetched, we fetch the full images (only some
- // of them because of we don't want to use too much memory).
- private static ImageFetch[] sImageFetchSeq;
-
- private static class ImageFetch {
- int indexOffset;
- int imageBit;
- public ImageFetch(int offset, int bit) {
- indexOffset = offset;
- imageBit = bit;
- }
- }
-
- static {
- int k = 0;
- sImageFetchSeq = new ImageFetch[1 + (IMAGE_CACHE_SIZE - 1) * 2 + 3];
- sImageFetchSeq[k++] = new ImageFetch(0, BIT_SCREEN_NAIL);
-
- for (int i = 1; i < IMAGE_CACHE_SIZE; ++i) {
- sImageFetchSeq[k++] = new ImageFetch(i, BIT_SCREEN_NAIL);
- sImageFetchSeq[k++] = new ImageFetch(-i, BIT_SCREEN_NAIL);
- }
-
- sImageFetchSeq[k++] = new ImageFetch(0, BIT_FULL_IMAGE);
- sImageFetchSeq[k++] = new ImageFetch(1, BIT_FULL_IMAGE);
- sImageFetchSeq[k++] = new ImageFetch(-1, BIT_FULL_IMAGE);
- }
-
- private final TileImageViewAdapter mTileProvider = new TileImageViewAdapter();
-
- // PhotoDataAdapter caches MediaItems (data) and ImageEntries (image).
- //
- // The MediaItems are stored in the mData array, which has DATA_CACHE_SIZE
- // entries. The valid index range are [mContentStart, mContentEnd). We keep
- // mContentEnd - mContentStart <= DATA_CACHE_SIZE, so we can use
- // (i % DATA_CACHE_SIZE) as index to the array.
- //
- // The valid MediaItem window size (mContentEnd - mContentStart) may be
- // smaller than DATA_CACHE_SIZE because we only update the window and reload
- // the MediaItems when there are significant changes to the window position
- // (>= MIN_LOAD_COUNT).
- private final MediaItem mData[] = new MediaItem[DATA_CACHE_SIZE];
- private int mContentStart = 0;
- private int mContentEnd = 0;
-
- // The ImageCache is a Path-to-ImageEntry map. It only holds the
- // ImageEntries in the range of [mActiveStart, mActiveEnd). We also keep
- // mActiveEnd - mActiveStart <= IMAGE_CACHE_SIZE. Besides, the
- // [mActiveStart, mActiveEnd) range must be contained within
- // the [mContentStart, mContentEnd) range.
- private HashMap<Path, ImageEntry> mImageCache =
- new HashMap<Path, ImageEntry>();
- private int mActiveStart = 0;
- private int mActiveEnd = 0;
-
- // mCurrentIndex is the "center" image the user is viewing. The change of
- // mCurrentIndex triggers the data loading and image loading.
- private int mCurrentIndex;
-
- // mChanges keeps the version number (of MediaItem) about the images. If any
- // of the version number changes, we notify the view. This is used after a
- // database reload or mCurrentIndex changes.
- private final long mChanges[] = new long[IMAGE_CACHE_SIZE];
- // mPaths keeps the corresponding Path (of MediaItem) for the images. This
- // is used to determine the item movement.
- private final Path mPaths[] = new Path[IMAGE_CACHE_SIZE];
-
- private final Handler mMainHandler;
- private final ThreadPool mThreadPool;
-
- private final PhotoView mPhotoView;
- private final MediaSet mSource;
- private ReloadTask mReloadTask;
-
- private long mSourceVersion = MediaObject.INVALID_DATA_VERSION;
- private int mSize = 0;
- private Path mItemPath;
- private int mCameraIndex;
- private boolean mIsPanorama;
- private boolean mIsStaticCamera;
- private boolean mIsActive;
- private boolean mNeedFullImage;
- private int mFocusHintDirection = FOCUS_HINT_NEXT;
- private Path mFocusHintPath = null;
-
- public interface DataListener extends LoadingListener {
- public void onPhotoChanged(int index, Path item);
- }
-
- private DataListener mDataListener;
-
- private final SourceListener mSourceListener = new SourceListener();
- private final TiledTexture.Uploader mUploader;
-
- // The path of the current viewing item will be stored in mItemPath.
- // If mItemPath is not null, mCurrentIndex is only a hint for where we
- // can find the item. If mItemPath is null, then we use the mCurrentIndex to
- // find the image being viewed. cameraIndex is the index of the camera
- // preview. If cameraIndex < 0, there is no camera preview.
- public PhotoDataAdapter(AbstractGalleryActivity activity, PhotoView view,
- MediaSet mediaSet, Path itemPath, int indexHint, int cameraIndex,
- boolean isPanorama, boolean isStaticCamera) {
- mSource = Utils.checkNotNull(mediaSet);
- mPhotoView = Utils.checkNotNull(view);
- mItemPath = Utils.checkNotNull(itemPath);
- mCurrentIndex = indexHint;
- mCameraIndex = cameraIndex;
- mIsPanorama = isPanorama;
- mIsStaticCamera = isStaticCamera;
- mThreadPool = activity.getThreadPool();
- mNeedFullImage = true;
-
- Arrays.fill(mChanges, MediaObject.INVALID_DATA_VERSION);
-
- mUploader = new TiledTexture.Uploader(activity.getGLRoot());
-
- mMainHandler = new SynchronizedHandler(activity.getGLRoot()) {
- @SuppressWarnings("unchecked")
- @Override
- public void handleMessage(Message message) {
- switch (message.what) {
- case MSG_RUN_OBJECT:
- ((Runnable) message.obj).run();
- return;
- case MSG_LOAD_START: {
- if (mDataListener != null) {
- mDataListener.onLoadingStarted();
- }
- return;
- }
- case MSG_LOAD_FINISH: {
- if (mDataListener != null) {
- mDataListener.onLoadingFinished(false);
- }
- return;
- }
- case MSG_UPDATE_IMAGE_REQUESTS: {
- updateImageRequests();
- return;
- }
- default: throw new AssertionError();
- }
- }
- };
-
- updateSlidingWindow();
- }
-
- private MediaItem getItemInternal(int index) {
- if (index < 0 || index >= mSize) return null;
- if (index >= mContentStart && index < mContentEnd) {
- return mData[index % DATA_CACHE_SIZE];
- }
- return null;
- }
-
- private long getVersion(int index) {
- MediaItem item = getItemInternal(index);
- if (item == null) return MediaObject.INVALID_DATA_VERSION;
- return item.getDataVersion();
- }
-
- private Path getPath(int index) {
- MediaItem item = getItemInternal(index);
- if (item == null) return null;
- return item.getPath();
- }
-
- private void fireDataChange() {
- // First check if data actually changed.
- boolean changed = false;
- for (int i = -SCREEN_NAIL_MAX; i <= SCREEN_NAIL_MAX; ++i) {
- long newVersion = getVersion(mCurrentIndex + i);
- if (mChanges[i + SCREEN_NAIL_MAX] != newVersion) {
- mChanges[i + SCREEN_NAIL_MAX] = newVersion;
- changed = true;
- }
- }
-
- if (!changed) return;
-
- // Now calculate the fromIndex array. fromIndex represents the item
- // movement. It records the index where the picture come from. The
- // special value Integer.MAX_VALUE means it's a new picture.
- final int N = IMAGE_CACHE_SIZE;
- int fromIndex[] = new int[N];
-
- // Remember the old path array.
- Path oldPaths[] = new Path[N];
- System.arraycopy(mPaths, 0, oldPaths, 0, N);
-
- // Update the mPaths array.
- for (int i = 0; i < N; ++i) {
- mPaths[i] = getPath(mCurrentIndex + i - SCREEN_NAIL_MAX);
- }
-
- // Calculate the fromIndex array.
- for (int i = 0; i < N; i++) {
- Path p = mPaths[i];
- if (p == null) {
- fromIndex[i] = Integer.MAX_VALUE;
- continue;
- }
-
- // Try to find the same path in the old array
- int j;
- for (j = 0; j < N; j++) {
- if (oldPaths[j] == p) {
- break;
- }
- }
- fromIndex[i] = (j < N) ? j - SCREEN_NAIL_MAX : Integer.MAX_VALUE;
- }
-
- mPhotoView.notifyDataChange(fromIndex, -mCurrentIndex,
- mSize - 1 - mCurrentIndex);
- }
-
- public void setDataListener(DataListener listener) {
- mDataListener = listener;
- }
-
- private void updateScreenNail(Path path, Future<ScreenNail> future) {
- ImageEntry entry = mImageCache.get(path);
- ScreenNail screenNail = future.get();
-
- if (entry == null || entry.screenNailTask != future) {
- if (screenNail != null) screenNail.recycle();
- return;
- }
-
- entry.screenNailTask = null;
-
- // Combine the ScreenNails if we already have a BitmapScreenNail
- if (entry.screenNail instanceof TiledScreenNail) {
- TiledScreenNail original = (TiledScreenNail) entry.screenNail;
- screenNail = original.combine(screenNail);
- }
-
- if (screenNail == null) {
- entry.failToLoad = true;
- } else {
- entry.failToLoad = false;
- entry.screenNail = screenNail;
- }
-
- for (int i = -SCREEN_NAIL_MAX; i <= SCREEN_NAIL_MAX; ++i) {
- if (path == getPath(mCurrentIndex + i)) {
- if (i == 0) updateTileProvider(entry);
- mPhotoView.notifyImageChange(i);
- break;
- }
- }
- updateImageRequests();
- updateScreenNailUploadQueue();
- }
-
- private void updateFullImage(Path path, Future<BitmapRegionDecoder> future) {
- ImageEntry entry = mImageCache.get(path);
- if (entry == null || entry.fullImageTask != future) {
- BitmapRegionDecoder fullImage = future.get();
- if (fullImage != null) fullImage.recycle();
- return;
- }
-
- entry.fullImageTask = null;
- entry.fullImage = future.get();
- if (entry.fullImage != null) {
- if (path == getPath(mCurrentIndex)) {
- updateTileProvider(entry);
- mPhotoView.notifyImageChange(0);
- }
- }
- updateImageRequests();
- }
-
- @Override
- public void resume() {
- mIsActive = true;
- TiledTexture.prepareResources();
-
- mSource.addContentListener(mSourceListener);
- updateImageCache();
- updateImageRequests();
-
- mReloadTask = new ReloadTask();
- mReloadTask.start();
-
- fireDataChange();
- }
-
- @Override
- public void pause() {
- mIsActive = false;
-
- mReloadTask.terminate();
- mReloadTask = null;
-
- mSource.removeContentListener(mSourceListener);
-
- for (ImageEntry entry : mImageCache.values()) {
- if (entry.fullImageTask != null) entry.fullImageTask.cancel();
- if (entry.screenNailTask != null) entry.screenNailTask.cancel();
- if (entry.screenNail != null) entry.screenNail.recycle();
- }
- mImageCache.clear();
- mTileProvider.clear();
-
- mUploader.clear();
- TiledTexture.freeResources();
- }
-
- private MediaItem getItem(int index) {
- if (index < 0 || index >= mSize || !mIsActive) return null;
- Utils.assertTrue(index >= mActiveStart && index < mActiveEnd);
-
- if (index >= mContentStart && index < mContentEnd) {
- return mData[index % DATA_CACHE_SIZE];
- }
- return null;
- }
-
- private void updateCurrentIndex(int index) {
- if (mCurrentIndex == index) return;
- mCurrentIndex = index;
- updateSlidingWindow();
-
- MediaItem item = mData[index % DATA_CACHE_SIZE];
- mItemPath = item == null ? null : item.getPath();
-
- updateImageCache();
- updateImageRequests();
- updateTileProvider();
-
- if (mDataListener != null) {
- mDataListener.onPhotoChanged(index, mItemPath);
- }
-
- fireDataChange();
- }
-
- private void uploadScreenNail(int offset) {
- int index = mCurrentIndex + offset;
- if (index < mActiveStart || index >= mActiveEnd) return;
-
- MediaItem item = getItem(index);
- if (item == null) return;
-
- ImageEntry e = mImageCache.get(item.getPath());
- if (e == null) return;
-
- ScreenNail s = e.screenNail;
- if (s instanceof TiledScreenNail) {
- TiledTexture t = ((TiledScreenNail) s).getTexture();
- if (t != null && !t.isReady()) mUploader.addTexture(t);
- }
- }
-
- private void updateScreenNailUploadQueue() {
- mUploader.clear();
- uploadScreenNail(0);
- for (int i = 1; i < IMAGE_CACHE_SIZE; ++i) {
- uploadScreenNail(i);
- uploadScreenNail(-i);
- }
- }
-
- @Override
- public void moveTo(int index) {
- updateCurrentIndex(index);
- }
-
- @Override
- public ScreenNail getScreenNail(int offset) {
- int index = mCurrentIndex + offset;
- if (index < 0 || index >= mSize || !mIsActive) return null;
- Utils.assertTrue(index >= mActiveStart && index < mActiveEnd);
-
- MediaItem item = getItem(index);
- if (item == null) return null;
-
- ImageEntry entry = mImageCache.get(item.getPath());
- if (entry == null) return null;
-
- // Create a default ScreenNail if the real one is not available yet,
- // except for camera that a black screen is better than a gray tile.
- if (entry.screenNail == null && !isCamera(offset)) {
- entry.screenNail = newPlaceholderScreenNail(item);
- if (offset == 0) updateTileProvider(entry);
- }
-
- return entry.screenNail;
- }
-
- @Override
- public void getImageSize(int offset, PhotoView.Size size) {
- MediaItem item = getItem(mCurrentIndex + offset);
- if (item == null) {
- size.width = 0;
- size.height = 0;
- } else {
- size.width = item.getWidth();
- size.height = item.getHeight();
- }
- }
-
- @Override
- public int getImageRotation(int offset) {
- MediaItem item = getItem(mCurrentIndex + offset);
- return (item == null) ? 0 : item.getFullImageRotation();
- }
-
- @Override
- public void setNeedFullImage(boolean enabled) {
- mNeedFullImage = enabled;
- mMainHandler.sendEmptyMessage(MSG_UPDATE_IMAGE_REQUESTS);
- }
-
- @Override
- public boolean isCamera(int offset) {
- return mCurrentIndex + offset == mCameraIndex;
- }
-
- @Override
- public boolean isPanorama(int offset) {
- return isCamera(offset) && mIsPanorama;
- }
-
- @Override
- public boolean isStaticCamera(int offset) {
- return isCamera(offset) && mIsStaticCamera;
- }
-
- @Override
- public boolean isVideo(int offset) {
- MediaItem item = getItem(mCurrentIndex + offset);
- return (item == null)
- ? false
- : item.getMediaType() == MediaItem.MEDIA_TYPE_VIDEO;
- }
-
- @Override
- public boolean isDeletable(int offset) {
- MediaItem item = getItem(mCurrentIndex + offset);
- return (item == null)
- ? false
- : (item.getSupportedOperations() & MediaItem.SUPPORT_DELETE) != 0;
- }
-
- @Override
- public int getLoadingState(int offset) {
- ImageEntry entry = mImageCache.get(getPath(mCurrentIndex + offset));
- if (entry == null) return LOADING_INIT;
- if (entry.failToLoad) return LOADING_FAIL;
- if (entry.screenNail != null) return LOADING_COMPLETE;
- return LOADING_INIT;
- }
-
- @Override
- public ScreenNail getScreenNail() {
- return getScreenNail(0);
- }
-
- @Override
- public int getImageHeight() {
- return mTileProvider.getImageHeight();
- }
-
- @Override
- public int getImageWidth() {
- return mTileProvider.getImageWidth();
- }
-
- @Override
- public int getLevelCount() {
- return mTileProvider.getLevelCount();
- }
-
- @Override
- public Bitmap getTile(int level, int x, int y, int tileSize) {
- return mTileProvider.getTile(level, x, y, tileSize);
- }
-
- @Override
- public boolean isEmpty() {
- return mSize == 0;
- }
-
- @Override
- public int getCurrentIndex() {
- return mCurrentIndex;
- }
-
- @Override
- public MediaItem getMediaItem(int offset) {
- int index = mCurrentIndex + offset;
- if (index >= mContentStart && index < mContentEnd) {
- return mData[index % DATA_CACHE_SIZE];
- }
- return null;
- }
-
- @Override
- public void setCurrentPhoto(Path path, int indexHint) {
- if (mItemPath == path) return;
- mItemPath = path;
- mCurrentIndex = indexHint;
- updateSlidingWindow();
- updateImageCache();
- fireDataChange();
-
- // We need to reload content if the path doesn't match.
- MediaItem item = getMediaItem(0);
- if (item != null && item.getPath() != path) {
- if (mReloadTask != null) mReloadTask.notifyDirty();
- }
- }
-
- @Override
- public void setFocusHintDirection(int direction) {
- mFocusHintDirection = direction;
- }
-
- @Override
- public void setFocusHintPath(Path path) {
- mFocusHintPath = path;
- }
-
- private void updateTileProvider() {
- ImageEntry entry = mImageCache.get(getPath(mCurrentIndex));
- if (entry == null) { // in loading
- mTileProvider.clear();
- } else {
- updateTileProvider(entry);
- }
- }
-
- private void updateTileProvider(ImageEntry entry) {
- ScreenNail screenNail = entry.screenNail;
- BitmapRegionDecoder fullImage = entry.fullImage;
- if (screenNail != null) {
- if (fullImage != null) {
- mTileProvider.setScreenNail(screenNail,
- fullImage.getWidth(), fullImage.getHeight());
- mTileProvider.setRegionDecoder(fullImage);
- } else {
- int width = screenNail.getWidth();
- int height = screenNail.getHeight();
- mTileProvider.setScreenNail(screenNail, width, height);
- }
- } else {
- mTileProvider.clear();
- }
- }
-
- private void updateSlidingWindow() {
- // 1. Update the image window
- int start = Utils.clamp(mCurrentIndex - IMAGE_CACHE_SIZE / 2,
- 0, Math.max(0, mSize - IMAGE_CACHE_SIZE));
- int end = Math.min(mSize, start + IMAGE_CACHE_SIZE);
-
- if (mActiveStart == start && mActiveEnd == end) return;
-
- mActiveStart = start;
- mActiveEnd = end;
-
- // 2. Update the data window
- start = Utils.clamp(mCurrentIndex - DATA_CACHE_SIZE / 2,
- 0, Math.max(0, mSize - DATA_CACHE_SIZE));
- end = Math.min(mSize, start + DATA_CACHE_SIZE);
- if (mContentStart > mActiveStart || mContentEnd < mActiveEnd
- || Math.abs(start - mContentStart) > MIN_LOAD_COUNT) {
- for (int i = mContentStart; i < mContentEnd; ++i) {
- if (i < start || i >= end) {
- mData[i % DATA_CACHE_SIZE] = null;
- }
- }
- mContentStart = start;
- mContentEnd = end;
- if (mReloadTask != null) mReloadTask.notifyDirty();
- }
- }
-
- private void updateImageRequests() {
- if (!mIsActive) return;
-
- int currentIndex = mCurrentIndex;
- MediaItem item = mData[currentIndex % DATA_CACHE_SIZE];
- if (item == null || item.getPath() != mItemPath) {
- // current item mismatch - don't request image
- return;
- }
-
- // 1. Find the most wanted request and start it (if not already started).
- Future<?> task = null;
- for (int i = 0; i < sImageFetchSeq.length; i++) {
- int offset = sImageFetchSeq[i].indexOffset;
- int bit = sImageFetchSeq[i].imageBit;
- if (bit == BIT_FULL_IMAGE && !mNeedFullImage) continue;
- task = startTaskIfNeeded(currentIndex + offset, bit);
- if (task != null) break;
- }
-
- // 2. Cancel everything else.
- for (ImageEntry entry : mImageCache.values()) {
- if (entry.screenNailTask != null && entry.screenNailTask != task) {
- entry.screenNailTask.cancel();
- entry.screenNailTask = null;
- entry.requestedScreenNail = MediaObject.INVALID_DATA_VERSION;
- }
- if (entry.fullImageTask != null && entry.fullImageTask != task) {
- entry.fullImageTask.cancel();
- entry.fullImageTask = null;
- entry.requestedFullImage = MediaObject.INVALID_DATA_VERSION;
- }
- }
- }
-
- private class ScreenNailJob implements Job<ScreenNail> {
- private MediaItem mItem;
-
- public ScreenNailJob(MediaItem item) {
- mItem = item;
- }
-
- @Override
- public ScreenNail run(JobContext jc) {
- // We try to get a ScreenNail first, if it fails, we fallback to get
- // a Bitmap and then wrap it in a BitmapScreenNail instead.
- ScreenNail s = mItem.getScreenNail();
- if (s != null) return s;
-
- // If this is a temporary item, don't try to get its bitmap because
- // it won't be available. We will get its bitmap after a data reload.
- if (isTemporaryItem(mItem)) {
- return newPlaceholderScreenNail(mItem);
- }
-
- Bitmap bitmap = mItem.requestImage(MediaItem.TYPE_THUMBNAIL).run(jc);
- if (jc.isCancelled()) return null;
- if (bitmap != null) {
- bitmap = BitmapUtils.rotateBitmap(bitmap,
- mItem.getRotation() - mItem.getFullImageRotation(), true);
- }
- return bitmap == null ? null : new TiledScreenNail(bitmap);
- }
- }
-
- private class FullImageJob implements Job<BitmapRegionDecoder> {
- private MediaItem mItem;
-
- public FullImageJob(MediaItem item) {
- mItem = item;
- }
-
- @Override
- public BitmapRegionDecoder run(JobContext jc) {
- if (isTemporaryItem(mItem)) {
- return null;
- }
- return mItem.requestLargeImage().run(jc);
- }
- }
-
- // Returns true if we think this is a temporary item created by Camera. A
- // temporary item is an image or a video whose data is still being
- // processed, but an incomplete entry is created first in MediaProvider, so
- // we can display them (in grey tile) even if they are not saved to disk
- // yet. When the image or video data is actually saved, we will get
- // notification from MediaProvider, reload data, and show the actual image
- // or video data.
- private boolean isTemporaryItem(MediaItem mediaItem) {
- // Must have camera to create a temporary item.
- if (mCameraIndex < 0) return false;
- // Must be an item in camera roll.
- if (!(mediaItem instanceof LocalMediaItem)) return false;
- LocalMediaItem item = (LocalMediaItem) mediaItem;
- if (item.getBucketId() != MediaSetUtils.CAMERA_BUCKET_ID) return false;
- // Must have no size, but must have width and height information
- if (item.getSize() != 0) return false;
- if (item.getWidth() == 0) return false;
- if (item.getHeight() == 0) return false;
- // Must be created in the last 10 seconds.
- if (item.getDateInMs() - System.currentTimeMillis() > 10000) return false;
- return true;
- }
-
- // Create a default ScreenNail when a ScreenNail is needed, but we don't yet
- // have one available (because the image data is still being saved, or the
- // Bitmap is still being loaded.
- private ScreenNail newPlaceholderScreenNail(MediaItem item) {
- int width = item.getWidth();
- int height = item.getHeight();
- return new TiledScreenNail(width, height);
- }
-
- // Returns the task if we started the task or the task is already started.
- private Future<?> startTaskIfNeeded(int index, int which) {
- if (index < mActiveStart || index >= mActiveEnd) return null;
-
- ImageEntry entry = mImageCache.get(getPath(index));
- if (entry == null) return null;
- MediaItem item = mData[index % DATA_CACHE_SIZE];
- Utils.assertTrue(item != null);
- long version = item.getDataVersion();
-
- if (which == BIT_SCREEN_NAIL && entry.screenNailTask != null
- && entry.requestedScreenNail == version) {
- return entry.screenNailTask;
- } else if (which == BIT_FULL_IMAGE && entry.fullImageTask != null
- && entry.requestedFullImage == version) {
- return entry.fullImageTask;
- }
-
- if (which == BIT_SCREEN_NAIL && entry.requestedScreenNail != version) {
- entry.requestedScreenNail = version;
- entry.screenNailTask = mThreadPool.submit(
- new ScreenNailJob(item),
- new ScreenNailListener(item));
- // request screen nail
- return entry.screenNailTask;
- }
- if (which == BIT_FULL_IMAGE && entry.requestedFullImage != version
- && (item.getSupportedOperations()
- & MediaItem.SUPPORT_FULL_IMAGE) != 0) {
- entry.requestedFullImage = version;
- entry.fullImageTask = mThreadPool.submit(
- new FullImageJob(item),
- new FullImageListener(item));
- // request full image
- return entry.fullImageTask;
- }
- return null;
- }
-
- private void updateImageCache() {
- HashSet<Path> toBeRemoved = new HashSet<Path>(mImageCache.keySet());
- for (int i = mActiveStart; i < mActiveEnd; ++i) {
- MediaItem item = mData[i % DATA_CACHE_SIZE];
- if (item == null) continue;
- Path path = item.getPath();
- ImageEntry entry = mImageCache.get(path);
- toBeRemoved.remove(path);
- if (entry != null) {
- if (Math.abs(i - mCurrentIndex) > 1) {
- if (entry.fullImageTask != null) {
- entry.fullImageTask.cancel();
- entry.fullImageTask = null;
- }
- entry.fullImage = null;
- entry.requestedFullImage = MediaObject.INVALID_DATA_VERSION;
- }
- if (entry.requestedScreenNail != item.getDataVersion()) {
- // This ScreenNail is outdated, we want to update it if it's
- // still a placeholder.
- if (entry.screenNail instanceof TiledScreenNail) {
- TiledScreenNail s = (TiledScreenNail) entry.screenNail;
- s.updatePlaceholderSize(
- item.getWidth(), item.getHeight());
- }
- }
- } else {
- entry = new ImageEntry();
- mImageCache.put(path, entry);
- }
- }
-
- // Clear the data and requests for ImageEntries outside the new window.
- for (Path path : toBeRemoved) {
- ImageEntry entry = mImageCache.remove(path);
- if (entry.fullImageTask != null) entry.fullImageTask.cancel();
- if (entry.screenNailTask != null) entry.screenNailTask.cancel();
- if (entry.screenNail != null) entry.screenNail.recycle();
- }
-
- updateScreenNailUploadQueue();
- }
-
- private class FullImageListener
- implements Runnable, FutureListener<BitmapRegionDecoder> {
- private final Path mPath;
- private Future<BitmapRegionDecoder> mFuture;
-
- public FullImageListener(MediaItem item) {
- mPath = item.getPath();
- }
-
- @Override
- public void onFutureDone(Future<BitmapRegionDecoder> future) {
- mFuture = future;
- mMainHandler.sendMessage(
- mMainHandler.obtainMessage(MSG_RUN_OBJECT, this));
- }
-
- @Override
- public void run() {
- updateFullImage(mPath, mFuture);
- }
- }
-
- private class ScreenNailListener
- implements Runnable, FutureListener<ScreenNail> {
- private final Path mPath;
- private Future<ScreenNail> mFuture;
-
- public ScreenNailListener(MediaItem item) {
- mPath = item.getPath();
- }
-
- @Override
- public void onFutureDone(Future<ScreenNail> future) {
- mFuture = future;
- mMainHandler.sendMessage(
- mMainHandler.obtainMessage(MSG_RUN_OBJECT, this));
- }
-
- @Override
- public void run() {
- updateScreenNail(mPath, mFuture);
- }
- }
-
- private static class ImageEntry {
- public BitmapRegionDecoder fullImage;
- public ScreenNail screenNail;
- public Future<ScreenNail> screenNailTask;
- public Future<BitmapRegionDecoder> fullImageTask;
- public long requestedScreenNail = MediaObject.INVALID_DATA_VERSION;
- public long requestedFullImage = MediaObject.INVALID_DATA_VERSION;
- public boolean failToLoad = false;
- }
-
- private class SourceListener implements ContentListener {
- @Override
- public void onContentDirty() {
- if (mReloadTask != null) mReloadTask.notifyDirty();
- }
- }
-
- private <T> T executeAndWait(Callable<T> callable) {
- FutureTask<T> task = new FutureTask<T>(callable);
- mMainHandler.sendMessage(
- mMainHandler.obtainMessage(MSG_RUN_OBJECT, task));
- try {
- return task.get();
- } catch (InterruptedException e) {
- return null;
- } catch (ExecutionException e) {
- throw new RuntimeException(e);
- }
- }
-
- private static class UpdateInfo {
- public long version;
- public boolean reloadContent;
- public Path target;
- public int indexHint;
- public int contentStart;
- public int contentEnd;
-
- public int size;
- public ArrayList<MediaItem> items;
- }
-
- private class GetUpdateInfo implements Callable<UpdateInfo> {
-
- private boolean needContentReload() {
- for (int i = mContentStart, n = mContentEnd; i < n; ++i) {
- if (mData[i % DATA_CACHE_SIZE] == null) return true;
- }
- MediaItem current = mData[mCurrentIndex % DATA_CACHE_SIZE];
- return current == null || current.getPath() != mItemPath;
- }
-
- @Override
- public UpdateInfo call() throws Exception {
- // TODO: Try to load some data in first update
- UpdateInfo info = new UpdateInfo();
- info.version = mSourceVersion;
- info.reloadContent = needContentReload();
- info.target = mItemPath;
- info.indexHint = mCurrentIndex;
- info.contentStart = mContentStart;
- info.contentEnd = mContentEnd;
- info.size = mSize;
- return info;
- }
- }
-
- private class UpdateContent implements Callable<Void> {
- UpdateInfo mUpdateInfo;
-
- public UpdateContent(UpdateInfo updateInfo) {
- mUpdateInfo = updateInfo;
- }
-
- @Override
- public Void call() throws Exception {
- UpdateInfo info = mUpdateInfo;
- mSourceVersion = info.version;
-
- if (info.size != mSize) {
- mSize = info.size;
- if (mContentEnd > mSize) mContentEnd = mSize;
- if (mActiveEnd > mSize) mActiveEnd = mSize;
- }
-
- mCurrentIndex = info.indexHint;
- updateSlidingWindow();
-
- if (info.items != null) {
- int start = Math.max(info.contentStart, mContentStart);
- int end = Math.min(info.contentStart + info.items.size(), mContentEnd);
- int dataIndex = start % DATA_CACHE_SIZE;
- for (int i = start; i < end; ++i) {
- mData[dataIndex] = info.items.get(i - info.contentStart);
- if (++dataIndex == DATA_CACHE_SIZE) dataIndex = 0;
- }
- }
-
- // update mItemPath
- MediaItem current = mData[mCurrentIndex % DATA_CACHE_SIZE];
- mItemPath = current == null ? null : current.getPath();
-
- updateImageCache();
- updateTileProvider();
- updateImageRequests();
-
- if (mDataListener != null) {
- mDataListener.onPhotoChanged(mCurrentIndex, mItemPath);
- }
-
- fireDataChange();
- return null;
- }
- }
-
- private class ReloadTask extends Thread {
- private volatile boolean mActive = true;
- private volatile boolean mDirty = true;
-
- private boolean mIsLoading = false;
-
- private void updateLoading(boolean loading) {
- if (mIsLoading == loading) return;
- mIsLoading = loading;
- mMainHandler.sendEmptyMessage(loading ? MSG_LOAD_START : MSG_LOAD_FINISH);
- }
-
- @Override
- public void run() {
- while (mActive) {
- synchronized (this) {
- if (!mDirty && mActive) {
- updateLoading(false);
- Utils.waitWithoutInterrupt(this);
- continue;
- }
- }
- mDirty = false;
- UpdateInfo info = executeAndWait(new GetUpdateInfo());
- updateLoading(true);
- long version = mSource.reload();
- if (info.version != version) {
- info.reloadContent = true;
- info.size = mSource.getMediaItemCount();
- }
- if (!info.reloadContent) continue;
- info.items = mSource.getMediaItem(
- info.contentStart, info.contentEnd);
-
- int index = MediaSet.INDEX_NOT_FOUND;
-
- // First try to focus on the given hint path if there is one.
- if (mFocusHintPath != null) {
- index = findIndexOfPathInCache(info, mFocusHintPath);
- mFocusHintPath = null;
- }
-
- // Otherwise try to see if the currently focused item can be found.
- if (index == MediaSet.INDEX_NOT_FOUND) {
- MediaItem item = findCurrentMediaItem(info);
- if (item != null && item.getPath() == info.target) {
- index = info.indexHint;
- } else {
- index = findIndexOfTarget(info);
- }
- }
-
- // The image has been deleted. Focus on the next image (keep
- // mCurrentIndex unchanged) or the previous image (decrease
- // mCurrentIndex by 1). In page mode we want to see the next
- // image, so we focus on the next one. In film mode we want the
- // later images to shift left to fill the empty space, so we
- // focus on the previous image (so it will not move). In any
- // case the index needs to be limited to [0, mSize).
- if (index == MediaSet.INDEX_NOT_FOUND) {
- index = info.indexHint;
- int focusHintDirection = mFocusHintDirection;
- if (index == (mCameraIndex + 1)) {
- focusHintDirection = FOCUS_HINT_NEXT;
- }
- if (focusHintDirection == FOCUS_HINT_PREVIOUS
- && index > 0) {
- index--;
- }
- }
-
- // Don't change index if mSize == 0
- if (mSize > 0) {
- if (index >= mSize) index = mSize - 1;
- }
-
- info.indexHint = index;
-
- executeAndWait(new UpdateContent(info));
- }
- }
-
- public synchronized void notifyDirty() {
- mDirty = true;
- notifyAll();
- }
-
- public synchronized void terminate() {
- mActive = false;
- notifyAll();
- }
-
- private MediaItem findCurrentMediaItem(UpdateInfo info) {
- ArrayList<MediaItem> items = info.items;
- int index = info.indexHint - info.contentStart;
- return index < 0 || index >= items.size() ? null : items.get(index);
- }
-
- private int findIndexOfTarget(UpdateInfo info) {
- if (info.target == null) return info.indexHint;
- ArrayList<MediaItem> items = info.items;
-
- // First, try to find the item in the data just loaded
- if (items != null) {
- int i = findIndexOfPathInCache(info, info.target);
- if (i != MediaSet.INDEX_NOT_FOUND) return i;
- }
-
- // Not found, find it in mSource.
- return mSource.getIndexOfItem(info.target, info.indexHint);
- }
-
- private int findIndexOfPathInCache(UpdateInfo info, Path path) {
- ArrayList<MediaItem> items = info.items;
- for (int i = 0, n = items.size(); i < n; ++i) {
- MediaItem item = items.get(i);
- if (item != null && item.getPath() == path) {
- return i + info.contentStart;
- }
- }
- return MediaSet.INDEX_NOT_FOUND;
- }
- }
-}
diff --git a/src/com/android/gallery3d/app/PhotoPage.java b/src/com/android/gallery3d/app/PhotoPage.java
deleted file mode 100644
index 7a71e9109..000000000
--- a/src/com/android/gallery3d/app/PhotoPage.java
+++ /dev/null
@@ -1,1571 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.annotation.TargetApi;
-import android.app.ActionBar.OnMenuVisibilityListener;
-import android.app.Activity;
-import android.content.ActivityNotFoundException;
-import android.content.Context;
-import android.content.Intent;
-import android.content.pm.PackageManager;
-import android.content.res.Configuration;
-import android.graphics.Rect;
-import android.net.Uri;
-import android.nfc.NfcAdapter;
-import android.nfc.NfcAdapter.CreateBeamUrisCallback;
-import android.nfc.NfcEvent;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.Message;
-import android.os.SystemClock;
-import android.view.Menu;
-import android.view.MenuItem;
-import android.widget.RelativeLayout;
-import android.widget.ShareActionProvider;
-import android.widget.Toast;
-
-import com.android.camera.CameraActivity;
-import com.android.camera.ProxyLauncher;
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.data.ComboAlbum;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.FilterDeleteSet;
-import com.android.gallery3d.data.FilterSource;
-import com.android.gallery3d.data.LocalImage;
-import com.android.gallery3d.data.MediaDetails;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.MediaObject.PanoramaSupportCallback;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.data.SecureAlbum;
-import com.android.gallery3d.data.SecureSource;
-import com.android.gallery3d.data.SnailAlbum;
-import com.android.gallery3d.data.SnailItem;
-import com.android.gallery3d.data.SnailSource;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.crop.CropActivity;
-import com.android.gallery3d.picasasource.PicasaSource;
-import com.android.gallery3d.ui.DetailsHelper;
-import com.android.gallery3d.ui.DetailsHelper.CloseListener;
-import com.android.gallery3d.ui.DetailsHelper.DetailsSource;
-import com.android.gallery3d.ui.GLView;
-import com.android.gallery3d.ui.MenuExecutor;
-import com.android.gallery3d.ui.PhotoView;
-import com.android.gallery3d.ui.SelectionManager;
-import com.android.gallery3d.ui.SynchronizedHandler;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.UsageStatistics;
-
-public abstract class PhotoPage extends ActivityState implements
- PhotoView.Listener, AppBridge.Server, ShareActionProvider.OnShareTargetSelectedListener,
- PhotoPageBottomControls.Delegate, GalleryActionBar.OnAlbumModeSelectedListener {
- private static final String TAG = "PhotoPage";
-
- private static final int MSG_HIDE_BARS = 1;
- private static final int MSG_ON_FULL_SCREEN_CHANGED = 4;
- private static final int MSG_UPDATE_ACTION_BAR = 5;
- private static final int MSG_UNFREEZE_GLROOT = 6;
- private static final int MSG_WANT_BARS = 7;
- private static final int MSG_REFRESH_BOTTOM_CONTROLS = 8;
- private static final int MSG_ON_CAMERA_CENTER = 9;
- private static final int MSG_ON_PICTURE_CENTER = 10;
- private static final int MSG_REFRESH_IMAGE = 11;
- private static final int MSG_UPDATE_PHOTO_UI = 12;
- private static final int MSG_UPDATE_PROGRESS = 13;
- private static final int MSG_UPDATE_DEFERRED = 14;
- private static final int MSG_UPDATE_SHARE_URI = 15;
- private static final int MSG_UPDATE_PANORAMA_UI = 16;
-
- private static final int HIDE_BARS_TIMEOUT = 3500;
- private static final int UNFREEZE_GLROOT_TIMEOUT = 250;
-
- private static final int REQUEST_SLIDESHOW = 1;
- private static final int REQUEST_CROP = 2;
- private static final int REQUEST_CROP_PICASA = 3;
- private static final int REQUEST_EDIT = 4;
- private static final int REQUEST_PLAY_VIDEO = 5;
- private static final int REQUEST_TRIM = 6;
-
- public static final String KEY_MEDIA_SET_PATH = "media-set-path";
- public static final String KEY_MEDIA_ITEM_PATH = "media-item-path";
- public static final String KEY_INDEX_HINT = "index-hint";
- public static final String KEY_OPEN_ANIMATION_RECT = "open-animation-rect";
- public static final String KEY_APP_BRIDGE = "app-bridge";
- public static final String KEY_TREAT_BACK_AS_UP = "treat-back-as-up";
- public static final String KEY_START_IN_FILMSTRIP = "start-in-filmstrip";
- public static final String KEY_RETURN_INDEX_HINT = "return-index-hint";
- public static final String KEY_SHOW_WHEN_LOCKED = "show_when_locked";
- public static final String KEY_IN_CAMERA_ROLL = "in_camera_roll";
-
- public static final String KEY_ALBUMPAGE_TRANSITION = "albumpage-transition";
- public static final int MSG_ALBUMPAGE_NONE = 0;
- public static final int MSG_ALBUMPAGE_STARTED = 1;
- public static final int MSG_ALBUMPAGE_RESUMED = 2;
- public static final int MSG_ALBUMPAGE_PICKED = 4;
-
- public static final String ACTION_NEXTGEN_EDIT = "action_nextgen_edit";
- public static final String ACTION_SIMPLE_EDIT = "action_simple_edit";
-
- private GalleryApp mApplication;
- private SelectionManager mSelectionManager;
-
- private PhotoView mPhotoView;
- private PhotoPage.Model mModel;
- private DetailsHelper mDetailsHelper;
- private boolean mShowDetails;
-
- // mMediaSet could be null if there is no KEY_MEDIA_SET_PATH supplied.
- // E.g., viewing a photo in gmail attachment
- private FilterDeleteSet mMediaSet;
-
- // The mediaset used by camera launched from secure lock screen.
- private SecureAlbum mSecureAlbum;
-
- private int mCurrentIndex = 0;
- private Handler mHandler;
- private boolean mShowBars = true;
- private volatile boolean mActionBarAllowed = true;
- private GalleryActionBar mActionBar;
- private boolean mIsMenuVisible;
- private boolean mHaveImageEditor;
- private PhotoPageBottomControls mBottomControls;
- private PhotoPageProgressBar mProgressBar;
- private MediaItem mCurrentPhoto = null;
- private MenuExecutor mMenuExecutor;
- private boolean mIsActive;
- private boolean mShowSpinner;
- private String mSetPathString;
- // This is the original mSetPathString before adding the camera preview item.
- private String mOriginalSetPathString;
- private AppBridge mAppBridge;
- private SnailItem mScreenNailItem;
- private SnailAlbum mScreenNailSet;
- private OrientationManager mOrientationManager;
- private boolean mTreatBackAsUp;
- private boolean mStartInFilmstrip;
- private boolean mHasCameraScreennailOrPlaceholder = false;
- private boolean mRecenterCameraOnResume = true;
-
- // These are only valid after the panorama callback
- private boolean mIsPanorama;
- private boolean mIsPanorama360;
-
- private long mCameraSwitchCutoff = 0;
- private boolean mSkipUpdateCurrentPhoto = false;
- private static final long CAMERA_SWITCH_CUTOFF_THRESHOLD_MS = 300;
-
- private static final long DEFERRED_UPDATE_MS = 250;
- private boolean mDeferredUpdateWaiting = false;
- private long mDeferUpdateUntil = Long.MAX_VALUE;
-
- // The item that is deleted (but it can still be undeleted before commiting)
- private Path mDeletePath;
- private boolean mDeleteIsFocus; // whether the deleted item was in focus
-
- private Uri[] mNfcPushUris = new Uri[1];
-
- private final MyMenuVisibilityListener mMenuVisibilityListener =
- new MyMenuVisibilityListener();
- private UpdateProgressListener mProgressListener;
-
- private final PanoramaSupportCallback mUpdatePanoramaMenuItemsCallback = new PanoramaSupportCallback() {
- @Override
- public void panoramaInfoAvailable(MediaObject mediaObject, boolean isPanorama,
- boolean isPanorama360) {
- if (mediaObject == mCurrentPhoto) {
- mHandler.obtainMessage(MSG_UPDATE_PANORAMA_UI, isPanorama360 ? 1 : 0, 0,
- mediaObject).sendToTarget();
- }
- }
- };
-
- private final PanoramaSupportCallback mRefreshBottomControlsCallback = new PanoramaSupportCallback() {
- @Override
- public void panoramaInfoAvailable(MediaObject mediaObject, boolean isPanorama,
- boolean isPanorama360) {
- if (mediaObject == mCurrentPhoto) {
- mHandler.obtainMessage(MSG_REFRESH_BOTTOM_CONTROLS, isPanorama ? 1 : 0, isPanorama360 ? 1 : 0,
- mediaObject).sendToTarget();
- }
- }
- };
-
- private final PanoramaSupportCallback mUpdateShareURICallback = new PanoramaSupportCallback() {
- @Override
- public void panoramaInfoAvailable(MediaObject mediaObject, boolean isPanorama,
- boolean isPanorama360) {
- if (mediaObject == mCurrentPhoto) {
- mHandler.obtainMessage(MSG_UPDATE_SHARE_URI, isPanorama360 ? 1 : 0, 0, mediaObject)
- .sendToTarget();
- }
- }
- };
-
- public static interface Model extends PhotoView.Model {
- public void resume();
- public void pause();
- public boolean isEmpty();
- public void setCurrentPhoto(Path path, int indexHint);
- }
-
- private class MyMenuVisibilityListener implements OnMenuVisibilityListener {
- @Override
- public void onMenuVisibilityChanged(boolean isVisible) {
- mIsMenuVisible = isVisible;
- refreshHidingMessage();
- }
- }
-
- private class UpdateProgressListener implements StitchingChangeListener {
-
- @Override
- public void onStitchingResult(Uri uri) {
- sendUpdate(uri, MSG_REFRESH_IMAGE);
- }
-
- @Override
- public void onStitchingQueued(Uri uri) {
- sendUpdate(uri, MSG_UPDATE_PROGRESS);
- }
-
- @Override
- public void onStitchingProgress(Uri uri, final int progress) {
- sendUpdate(uri, MSG_UPDATE_PROGRESS);
- }
-
- private void sendUpdate(Uri uri, int message) {
- MediaObject currentPhoto = mCurrentPhoto;
- boolean isCurrentPhoto = currentPhoto instanceof LocalImage
- && currentPhoto.getContentUri().equals(uri);
- if (isCurrentPhoto) {
- mHandler.sendEmptyMessage(message);
- }
- }
- };
-
- @Override
- protected int getBackgroundColorId() {
- return R.color.photo_background;
- }
-
- private final GLView mRootPane = new GLView() {
- @Override
- protected void onLayout(
- boolean changed, int left, int top, int right, int bottom) {
- mPhotoView.layout(0, 0, right - left, bottom - top);
- if (mShowDetails) {
- mDetailsHelper.layout(left, mActionBar.getHeight(), right, bottom);
- }
- }
- };
-
- @Override
- public void onCreate(Bundle data, Bundle restoreState) {
- super.onCreate(data, restoreState);
- mActionBar = mActivity.getGalleryActionBar();
- mSelectionManager = new SelectionManager(mActivity, false);
- mMenuExecutor = new MenuExecutor(mActivity, mSelectionManager);
-
- mPhotoView = new PhotoView(mActivity);
- mPhotoView.setListener(this);
- mRootPane.addComponent(mPhotoView);
- mApplication = (GalleryApp) ((Activity) mActivity).getApplication();
- mOrientationManager = mActivity.getOrientationManager();
- mActivity.getGLRoot().setOrientationSource(mOrientationManager);
-
- mHandler = new SynchronizedHandler(mActivity.getGLRoot()) {
- @Override
- public void handleMessage(Message message) {
- switch (message.what) {
- case MSG_HIDE_BARS: {
- hideBars();
- break;
- }
- case MSG_REFRESH_BOTTOM_CONTROLS: {
- if (mCurrentPhoto == message.obj && mBottomControls != null) {
- mIsPanorama = message.arg1 == 1;
- mIsPanorama360 = message.arg2 == 1;
- mBottomControls.refresh();
- }
- break;
- }
- case MSG_ON_FULL_SCREEN_CHANGED: {
- if (mAppBridge != null) {
- mAppBridge.onFullScreenChanged(message.arg1 == 1);
- }
- break;
- }
- case MSG_UPDATE_ACTION_BAR: {
- updateBars();
- break;
- }
- case MSG_WANT_BARS: {
- wantBars();
- break;
- }
- case MSG_UNFREEZE_GLROOT: {
- mActivity.getGLRoot().unfreeze();
- break;
- }
- case MSG_UPDATE_DEFERRED: {
- long nextUpdate = mDeferUpdateUntil - SystemClock.uptimeMillis();
- if (nextUpdate <= 0) {
- mDeferredUpdateWaiting = false;
- updateUIForCurrentPhoto();
- } else {
- mHandler.sendEmptyMessageDelayed(MSG_UPDATE_DEFERRED, nextUpdate);
- }
- break;
- }
- case MSG_ON_CAMERA_CENTER: {
- mSkipUpdateCurrentPhoto = false;
- boolean stayedOnCamera = false;
- if (!mPhotoView.getFilmMode()) {
- stayedOnCamera = true;
- } else if (SystemClock.uptimeMillis() < mCameraSwitchCutoff &&
- mMediaSet.getMediaItemCount() > 1) {
- mPhotoView.switchToImage(1);
- } else {
- if (mAppBridge != null) mPhotoView.setFilmMode(false);
- stayedOnCamera = true;
- }
-
- if (stayedOnCamera) {
- if (mAppBridge == null && mMediaSet.getTotalMediaItemCount() > 1) {
- launchCamera();
- /* We got here by swiping from photo 1 to the
- placeholder, so make it be the thing that
- is in focus when the user presses back from
- the camera app */
- mPhotoView.switchToImage(1);
- } else {
- updateBars();
- updateCurrentPhoto(mModel.getMediaItem(0));
- }
- }
- break;
- }
- case MSG_ON_PICTURE_CENTER: {
- if (!mPhotoView.getFilmMode() && mCurrentPhoto != null
- && (mCurrentPhoto.getSupportedOperations() & MediaObject.SUPPORT_ACTION) != 0) {
- mPhotoView.setFilmMode(true);
- }
- break;
- }
- case MSG_REFRESH_IMAGE: {
- final MediaItem photo = mCurrentPhoto;
- mCurrentPhoto = null;
- updateCurrentPhoto(photo);
- break;
- }
- case MSG_UPDATE_PHOTO_UI: {
- updateUIForCurrentPhoto();
- break;
- }
- case MSG_UPDATE_PROGRESS: {
- updateProgressBar();
- break;
- }
- case MSG_UPDATE_SHARE_URI: {
- if (mCurrentPhoto == message.obj) {
- boolean isPanorama360 = message.arg1 != 0;
- Uri contentUri = mCurrentPhoto.getContentUri();
- Intent panoramaIntent = null;
- if (isPanorama360) {
- panoramaIntent = createSharePanoramaIntent(contentUri);
- }
- Intent shareIntent = createShareIntent(mCurrentPhoto);
-
- mActionBar.setShareIntents(panoramaIntent, shareIntent, PhotoPage.this);
- setNfcBeamPushUri(contentUri);
- }
- break;
- }
- case MSG_UPDATE_PANORAMA_UI: {
- if (mCurrentPhoto == message.obj) {
- boolean isPanorama360 = message.arg1 != 0;
- updatePanoramaUI(isPanorama360);
- }
- break;
- }
- default: throw new AssertionError(message.what);
- }
- }
- };
-
- mSetPathString = data.getString(KEY_MEDIA_SET_PATH);
- mOriginalSetPathString = mSetPathString;
- setupNfcBeamPush();
- String itemPathString = data.getString(KEY_MEDIA_ITEM_PATH);
- Path itemPath = itemPathString != null ?
- Path.fromString(data.getString(KEY_MEDIA_ITEM_PATH)) :
- null;
- mTreatBackAsUp = data.getBoolean(KEY_TREAT_BACK_AS_UP, false);
- mStartInFilmstrip = data.getBoolean(KEY_START_IN_FILMSTRIP, false);
- boolean inCameraRoll = data.getBoolean(KEY_IN_CAMERA_ROLL, false);
- mCurrentIndex = data.getInt(KEY_INDEX_HINT, 0);
- if (mSetPathString != null) {
- mShowSpinner = true;
- mAppBridge = (AppBridge) data.getParcelable(KEY_APP_BRIDGE);
- if (mAppBridge != null) {
- mShowBars = false;
- mHasCameraScreennailOrPlaceholder = true;
- mAppBridge.setServer(this);
-
- // Get the ScreenNail from AppBridge and register it.
- int id = SnailSource.newId();
- Path screenNailSetPath = SnailSource.getSetPath(id);
- Path screenNailItemPath = SnailSource.getItemPath(id);
- mScreenNailSet = (SnailAlbum) mActivity.getDataManager()
- .getMediaObject(screenNailSetPath);
- mScreenNailItem = (SnailItem) mActivity.getDataManager()
- .getMediaObject(screenNailItemPath);
- mScreenNailItem.setScreenNail(mAppBridge.attachScreenNail());
-
- if (data.getBoolean(KEY_SHOW_WHEN_LOCKED, false)) {
- // Set the flag to be on top of the lock screen.
- mFlags |= FLAG_SHOW_WHEN_LOCKED;
- }
-
- // Don't display "empty album" action item for capture intents.
- if (!mSetPathString.equals("/local/all/0")) {
- // Check if the path is a secure album.
- if (SecureSource.isSecurePath(mSetPathString)) {
- mSecureAlbum = (SecureAlbum) mActivity.getDataManager()
- .getMediaSet(mSetPathString);
- mShowSpinner = false;
- }
- mSetPathString = "/filter/empty/{"+mSetPathString+"}";
- }
-
- // Combine the original MediaSet with the one for ScreenNail
- // from AppBridge.
- mSetPathString = "/combo/item/{" + screenNailSetPath +
- "," + mSetPathString + "}";
-
- // Start from the screen nail.
- itemPath = screenNailItemPath;
- } else if (inCameraRoll && GalleryUtils.isCameraAvailable(mActivity)) {
- mSetPathString = "/combo/item/{" + FilterSource.FILTER_CAMERA_SHORTCUT +
- "," + mSetPathString + "}";
- mCurrentIndex++;
- mHasCameraScreennailOrPlaceholder = true;
- }
-
- MediaSet originalSet = mActivity.getDataManager()
- .getMediaSet(mSetPathString);
- if (mHasCameraScreennailOrPlaceholder && originalSet instanceof ComboAlbum) {
- // Use the name of the camera album rather than the default
- // ComboAlbum behavior
- ((ComboAlbum) originalSet).useNameOfChild(1);
- }
- mSelectionManager.setSourceMediaSet(originalSet);
- mSetPathString = "/filter/delete/{" + mSetPathString + "}";
- mMediaSet = (FilterDeleteSet) mActivity.getDataManager()
- .getMediaSet(mSetPathString);
- if (mMediaSet == null) {
- Log.w(TAG, "failed to restore " + mSetPathString);
- }
- if (itemPath == null) {
- int mediaItemCount = mMediaSet.getMediaItemCount();
- if (mediaItemCount > 0) {
- if (mCurrentIndex >= mediaItemCount) mCurrentIndex = 0;
- itemPath = mMediaSet.getMediaItem(mCurrentIndex, 1)
- .get(0).getPath();
- } else {
- // Bail out, PhotoPage can't load on an empty album
- return;
- }
- }
- PhotoDataAdapter pda = new PhotoDataAdapter(
- mActivity, mPhotoView, mMediaSet, itemPath, mCurrentIndex,
- mAppBridge == null ? -1 : 0,
- mAppBridge == null ? false : mAppBridge.isPanorama(),
- mAppBridge == null ? false : mAppBridge.isStaticCamera());
- mModel = pda;
- mPhotoView.setModel(mModel);
-
- pda.setDataListener(new PhotoDataAdapter.DataListener() {
-
- @Override
- public void onPhotoChanged(int index, Path item) {
- int oldIndex = mCurrentIndex;
- mCurrentIndex = index;
-
- if (mHasCameraScreennailOrPlaceholder) {
- if (mCurrentIndex > 0) {
- mSkipUpdateCurrentPhoto = false;
- }
-
- if (oldIndex == 0 && mCurrentIndex > 0
- && !mPhotoView.getFilmMode()) {
- mPhotoView.setFilmMode(true);
- if (mAppBridge != null) {
- UsageStatistics.onEvent("CameraToFilmstrip",
- UsageStatistics.TRANSITION_SWIPE, null);
- }
- } else if (oldIndex == 2 && mCurrentIndex == 1) {
- mCameraSwitchCutoff = SystemClock.uptimeMillis() +
- CAMERA_SWITCH_CUTOFF_THRESHOLD_MS;
- mPhotoView.stopScrolling();
- } else if (oldIndex >= 1 && mCurrentIndex == 0) {
- mPhotoView.setWantPictureCenterCallbacks(true);
- mSkipUpdateCurrentPhoto = true;
- }
- }
- if (!mSkipUpdateCurrentPhoto) {
- if (item != null) {
- MediaItem photo = mModel.getMediaItem(0);
- if (photo != null) updateCurrentPhoto(photo);
- }
- updateBars();
- }
- // Reset the timeout for the bars after a swipe
- refreshHidingMessage();
- }
-
- @Override
- public void onLoadingFinished(boolean loadingFailed) {
- if (!mModel.isEmpty()) {
- MediaItem photo = mModel.getMediaItem(0);
- if (photo != null) updateCurrentPhoto(photo);
- } else if (mIsActive) {
- // We only want to finish the PhotoPage if there is no
- // deletion that the user can undo.
- if (mMediaSet.getNumberOfDeletions() == 0) {
- mActivity.getStateManager().finishState(
- PhotoPage.this);
- }
- }
- }
-
- @Override
- public void onLoadingStarted() {
- }
- });
- } else {
- // Get default media set by the URI
- MediaItem mediaItem = (MediaItem)
- mActivity.getDataManager().getMediaObject(itemPath);
- mModel = new SinglePhotoDataAdapter(mActivity, mPhotoView, mediaItem);
- mPhotoView.setModel(mModel);
- updateCurrentPhoto(mediaItem);
- mShowSpinner = false;
- }
-
- mPhotoView.setFilmMode(mStartInFilmstrip && mMediaSet.getMediaItemCount() > 1);
- RelativeLayout galleryRoot = (RelativeLayout) ((Activity) mActivity)
- .findViewById(mAppBridge != null ? R.id.content : R.id.gallery_root);
- if (galleryRoot != null) {
- if (mSecureAlbum == null) {
- mBottomControls = new PhotoPageBottomControls(this, mActivity, galleryRoot);
- }
- StitchingProgressManager progressManager = mApplication.getStitchingProgressManager();
- if (progressManager != null) {
- mProgressBar = new PhotoPageProgressBar(mActivity, galleryRoot);
- mProgressListener = new UpdateProgressListener();
- progressManager.addChangeListener(mProgressListener);
- if (mSecureAlbum != null) {
- progressManager.addChangeListener(mSecureAlbum);
- }
- }
- }
- }
-
- @Override
- public void onPictureCenter(boolean isCamera) {
- isCamera = isCamera || (mHasCameraScreennailOrPlaceholder && mAppBridge == null);
- mPhotoView.setWantPictureCenterCallbacks(false);
- mHandler.removeMessages(MSG_ON_CAMERA_CENTER);
- mHandler.removeMessages(MSG_ON_PICTURE_CENTER);
- mHandler.sendEmptyMessage(isCamera ? MSG_ON_CAMERA_CENTER : MSG_ON_PICTURE_CENTER);
- }
-
- @Override
- public boolean canDisplayBottomControls() {
- return mIsActive && !mPhotoView.canUndo();
- }
-
- @Override
- public boolean canDisplayBottomControl(int control) {
- if (mCurrentPhoto == null) {
- return false;
- }
- switch(control) {
- case R.id.photopage_bottom_control_edit:
- return mHaveImageEditor && mShowBars
- && !mPhotoView.getFilmMode()
- && (mCurrentPhoto.getSupportedOperations() & MediaItem.SUPPORT_EDIT) != 0
- && mCurrentPhoto.getMediaType() == MediaObject.MEDIA_TYPE_IMAGE;
- case R.id.photopage_bottom_control_panorama:
- return mIsPanorama;
- case R.id.photopage_bottom_control_tiny_planet:
- return mHaveImageEditor && mShowBars
- && mIsPanorama360 && !mPhotoView.getFilmMode();
- default:
- return false;
- }
- }
-
- @Override
- public void onBottomControlClicked(int control) {
- switch(control) {
- case R.id.photopage_bottom_control_edit:
- launchPhotoEditor();
- return;
- case R.id.photopage_bottom_control_panorama:
- mActivity.getPanoramaViewHelper()
- .showPanorama(mCurrentPhoto.getContentUri());
- return;
- case R.id.photopage_bottom_control_tiny_planet:
- launchTinyPlanet();
- return;
- default:
- return;
- }
- }
-
- @TargetApi(ApiHelper.VERSION_CODES.JELLY_BEAN)
- private void setupNfcBeamPush() {
- if (!ApiHelper.HAS_SET_BEAM_PUSH_URIS) return;
-
- NfcAdapter adapter = NfcAdapter.getDefaultAdapter(mActivity);
- if (adapter != null) {
- adapter.setBeamPushUris(null, mActivity);
- adapter.setBeamPushUrisCallback(new CreateBeamUrisCallback() {
- @Override
- public Uri[] createBeamUris(NfcEvent event) {
- return mNfcPushUris;
- }
- }, mActivity);
- }
- }
-
- private void setNfcBeamPushUri(Uri uri) {
- mNfcPushUris[0] = uri;
- }
-
- private static Intent createShareIntent(MediaObject mediaObject) {
- int type = mediaObject.getMediaType();
- return new Intent(Intent.ACTION_SEND)
- .setType(MenuExecutor.getMimeType(type))
- .putExtra(Intent.EXTRA_STREAM, mediaObject.getContentUri())
- .addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
- }
-
- private static Intent createSharePanoramaIntent(Uri contentUri) {
- return new Intent(Intent.ACTION_SEND)
- .setType(GalleryUtils.MIME_TYPE_PANORAMA360)
- .putExtra(Intent.EXTRA_STREAM, contentUri)
- .addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
- }
-
- private void overrideTransitionToEditor() {
- ((Activity) mActivity).overridePendingTransition(android.R.anim.fade_in,
- android.R.anim.fade_out);
- }
-
- private void launchTinyPlanet() {
- // Deep link into tiny planet
- MediaItem current = mModel.getMediaItem(0);
- Intent intent = new Intent(FilterShowActivity.TINY_PLANET_ACTION);
- intent.setClass(mActivity, FilterShowActivity.class);
- intent.setDataAndType(current.getContentUri(), current.getMimeType())
- .setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
- intent.putExtra(FilterShowActivity.LAUNCH_FULLSCREEN,
- mActivity.isFullscreen());
- mActivity.startActivityForResult(intent, REQUEST_EDIT);
- overrideTransitionToEditor();
- }
-
- private void launchCamera() {
- Intent intent = new Intent(mActivity, CameraActivity.class)
- .addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
- mRecenterCameraOnResume = false;
- mActivity.startActivity(intent);
- }
-
- private void launchPhotoEditor() {
- MediaItem current = mModel.getMediaItem(0);
- if (current == null || (current.getSupportedOperations()
- & MediaObject.SUPPORT_EDIT) == 0) {
- return;
- }
-
- Intent intent = new Intent(ACTION_NEXTGEN_EDIT);
-
- intent.setDataAndType(current.getContentUri(), current.getMimeType())
- .setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
- if (mActivity.getPackageManager()
- .queryIntentActivities(intent, PackageManager.MATCH_DEFAULT_ONLY).size() == 0) {
- intent.setAction(Intent.ACTION_EDIT);
- }
- intent.putExtra(FilterShowActivity.LAUNCH_FULLSCREEN,
- mActivity.isFullscreen());
- ((Activity) mActivity).startActivityForResult(Intent.createChooser(intent, null),
- REQUEST_EDIT);
- overrideTransitionToEditor();
- }
-
- private void launchSimpleEditor() {
- MediaItem current = mModel.getMediaItem(0);
- if (current == null || (current.getSupportedOperations()
- & MediaObject.SUPPORT_EDIT) == 0) {
- return;
- }
-
- Intent intent = new Intent(ACTION_SIMPLE_EDIT);
-
- intent.setDataAndType(current.getContentUri(), current.getMimeType())
- .setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
- if (mActivity.getPackageManager()
- .queryIntentActivities(intent, PackageManager.MATCH_DEFAULT_ONLY).size() == 0) {
- intent.setAction(Intent.ACTION_EDIT);
- }
- intent.putExtra(FilterShowActivity.LAUNCH_FULLSCREEN,
- mActivity.isFullscreen());
- ((Activity) mActivity).startActivityForResult(Intent.createChooser(intent, null),
- REQUEST_EDIT);
- overrideTransitionToEditor();
- }
-
- private void requestDeferredUpdate() {
- mDeferUpdateUntil = SystemClock.uptimeMillis() + DEFERRED_UPDATE_MS;
- if (!mDeferredUpdateWaiting) {
- mDeferredUpdateWaiting = true;
- mHandler.sendEmptyMessageDelayed(MSG_UPDATE_DEFERRED, DEFERRED_UPDATE_MS);
- }
- }
-
- private void updateUIForCurrentPhoto() {
- if (mCurrentPhoto == null) return;
-
- // If by swiping or deletion the user ends up on an action item
- // and zoomed in, zoom out so that the context of the action is
- // more clear
- if ((mCurrentPhoto.getSupportedOperations() & MediaObject.SUPPORT_ACTION) != 0
- && !mPhotoView.getFilmMode()) {
- mPhotoView.setWantPictureCenterCallbacks(true);
- }
-
- updateMenuOperations();
- refreshBottomControlsWhenReady();
- if (mShowDetails) {
- mDetailsHelper.reloadDetails();
- }
- if ((mSecureAlbum == null)
- && (mCurrentPhoto.getSupportedOperations() & MediaItem.SUPPORT_SHARE) != 0) {
- mCurrentPhoto.getPanoramaSupport(mUpdateShareURICallback);
- }
- updateProgressBar();
- }
-
- private void updateCurrentPhoto(MediaItem photo) {
- if (mCurrentPhoto == photo) return;
- mCurrentPhoto = photo;
- if (mPhotoView.getFilmMode()) {
- requestDeferredUpdate();
- } else {
- updateUIForCurrentPhoto();
- }
- }
-
- private void updateProgressBar() {
- if (mProgressBar != null) {
- mProgressBar.hideProgress();
- StitchingProgressManager progressManager = mApplication.getStitchingProgressManager();
- if (progressManager != null && mCurrentPhoto instanceof LocalImage) {
- Integer progress = progressManager.getProgress(mCurrentPhoto.getContentUri());
- if (progress != null) {
- mProgressBar.setProgress(progress);
- }
- }
- }
- }
-
- private void updateMenuOperations() {
- Menu menu = mActionBar.getMenu();
-
- // it could be null if onCreateActionBar has not been called yet
- if (menu == null) return;
-
- MenuItem item = menu.findItem(R.id.action_slideshow);
- if (item != null) {
- item.setVisible((mSecureAlbum == null) && canDoSlideShow());
- }
- if (mCurrentPhoto == null) return;
-
- int supportedOperations = mCurrentPhoto.getSupportedOperations();
- if (mSecureAlbum != null) {
- supportedOperations &= MediaObject.SUPPORT_DELETE;
- } else {
- mCurrentPhoto.getPanoramaSupport(mUpdatePanoramaMenuItemsCallback);
- if (!mHaveImageEditor) {
- supportedOperations &= ~MediaObject.SUPPORT_EDIT;
- }
- }
- MenuExecutor.updateMenuOperation(menu, supportedOperations);
- }
-
- private boolean canDoSlideShow() {
- if (mMediaSet == null || mCurrentPhoto == null) {
- return false;
- }
- if (mCurrentPhoto.getMediaType() != MediaObject.MEDIA_TYPE_IMAGE) {
- return false;
- }
- return true;
- }
-
- //////////////////////////////////////////////////////////////////////////
- // Action Bar show/hide management
- //////////////////////////////////////////////////////////////////////////
-
- private void showBars() {
- if (mShowBars) return;
- mShowBars = true;
- mOrientationManager.unlockOrientation();
- mActionBar.show();
- mActivity.getGLRoot().setLightsOutMode(false);
- refreshHidingMessage();
- refreshBottomControlsWhenReady();
- }
-
- private void hideBars() {
- if (!mShowBars) return;
- mShowBars = false;
- mActionBar.hide();
- mActivity.getGLRoot().setLightsOutMode(true);
- mHandler.removeMessages(MSG_HIDE_BARS);
- refreshBottomControlsWhenReady();
- }
-
- private void refreshHidingMessage() {
- mHandler.removeMessages(MSG_HIDE_BARS);
- if (!mIsMenuVisible && !mPhotoView.getFilmMode()) {
- mHandler.sendEmptyMessageDelayed(MSG_HIDE_BARS, HIDE_BARS_TIMEOUT);
- }
- }
-
- private boolean canShowBars() {
- // No bars if we are showing camera preview.
- if (mAppBridge != null && mCurrentIndex == 0
- && !mPhotoView.getFilmMode()) return false;
-
- // No bars if it's not allowed.
- if (!mActionBarAllowed) return false;
-
- Configuration config = mActivity.getResources().getConfiguration();
- if (config.touchscreen == Configuration.TOUCHSCREEN_NOTOUCH) {
- return false;
- }
-
- return true;
- }
-
- private void wantBars() {
- if (canShowBars()) showBars();
- }
-
- private void toggleBars() {
- if (mShowBars) {
- hideBars();
- } else {
- if (canShowBars()) showBars();
- }
- }
-
- private void updateBars() {
- if (!canShowBars()) {
- hideBars();
- }
- }
-
- @Override
- protected void onBackPressed() {
- if (mShowDetails) {
- hideDetails();
- } else if (mAppBridge == null || !switchWithCaptureAnimation(-1)) {
- // We are leaving this page. Set the result now.
- setResult();
- if (mStartInFilmstrip && !mPhotoView.getFilmMode()) {
- mPhotoView.setFilmMode(true);
- } else if (mTreatBackAsUp) {
- onUpPressed();
- } else {
- super.onBackPressed();
- }
- }
- }
-
- private void onUpPressed() {
- if ((mStartInFilmstrip || mAppBridge != null)
- && !mPhotoView.getFilmMode()) {
- mPhotoView.setFilmMode(true);
- return;
- }
-
- if (mActivity.getStateManager().getStateCount() > 1) {
- setResult();
- super.onBackPressed();
- return;
- }
-
- if (mOriginalSetPathString == null) return;
-
- if (mAppBridge == null) {
- // We're in view mode so set up the stacks on our own.
- Bundle data = new Bundle(getData());
- data.putString(AlbumPage.KEY_MEDIA_PATH, mOriginalSetPathString);
- data.putString(AlbumPage.KEY_PARENT_MEDIA_PATH,
- mActivity.getDataManager().getTopSetPath(
- DataManager.INCLUDE_ALL));
- mActivity.getStateManager().switchState(this, AlbumPage.class, data);
- } else {
- GalleryUtils.startGalleryActivity(mActivity);
- }
- }
-
- private void setResult() {
- Intent result = null;
- result = new Intent();
- result.putExtra(KEY_RETURN_INDEX_HINT, mCurrentIndex);
- setStateResult(Activity.RESULT_OK, result);
- }
-
- //////////////////////////////////////////////////////////////////////////
- // AppBridge.Server interface
- //////////////////////////////////////////////////////////////////////////
-
- @Override
- public void setCameraRelativeFrame(Rect frame) {
- mPhotoView.setCameraRelativeFrame(frame);
- }
-
- @Override
- public boolean switchWithCaptureAnimation(int offset) {
- return mPhotoView.switchWithCaptureAnimation(offset);
- }
-
- @Override
- public void setSwipingEnabled(boolean enabled) {
- mPhotoView.setSwipingEnabled(enabled);
- }
-
- @Override
- public void notifyScreenNailChanged() {
- mScreenNailItem.setScreenNail(mAppBridge.attachScreenNail());
- mScreenNailSet.notifyChange();
- }
-
- @Override
- public void addSecureAlbumItem(boolean isVideo, int id) {
- mSecureAlbum.addMediaItem(isVideo, id);
- }
-
- @Override
- protected boolean onCreateActionBar(Menu menu) {
- mActionBar.createActionBarMenu(R.menu.photo, menu);
- mHaveImageEditor = GalleryUtils.isEditorAvailable(mActivity, "image/*");
- updateMenuOperations();
- mActionBar.setTitle(mMediaSet != null ? mMediaSet.getName() : "");
- return true;
- }
-
- private MenuExecutor.ProgressListener mConfirmDialogListener =
- new MenuExecutor.ProgressListener() {
- @Override
- public void onProgressUpdate(int index) {}
-
- @Override
- public void onProgressComplete(int result) {}
-
- @Override
- public void onConfirmDialogShown() {
- mHandler.removeMessages(MSG_HIDE_BARS);
- }
-
- @Override
- public void onConfirmDialogDismissed(boolean confirmed) {
- refreshHidingMessage();
- }
-
- @Override
- public void onProgressStart() {}
- };
-
- private void switchToGrid() {
- if (mActivity.getStateManager().hasStateClass(AlbumPage.class)) {
- onUpPressed();
- } else {
- if (mOriginalSetPathString == null) return;
- if (mProgressBar != null) {
- updateCurrentPhoto(null);
- mProgressBar.hideProgress();
- }
- Bundle data = new Bundle(getData());
- data.putString(AlbumPage.KEY_MEDIA_PATH, mOriginalSetPathString);
- data.putString(AlbumPage.KEY_PARENT_MEDIA_PATH,
- mActivity.getDataManager().getTopSetPath(
- DataManager.INCLUDE_ALL));
-
- // We only show cluster menu in the first AlbumPage in stack
- // TODO: Enable this when running from the camera app
- boolean inAlbum = mActivity.getStateManager().hasStateClass(AlbumPage.class);
- data.putBoolean(AlbumPage.KEY_SHOW_CLUSTER_MENU, !inAlbum
- && mAppBridge == null);
-
- data.putBoolean(PhotoPage.KEY_APP_BRIDGE, mAppBridge != null);
-
- // Account for live preview being first item
- mActivity.getTransitionStore().put(KEY_RETURN_INDEX_HINT,
- mAppBridge != null ? mCurrentIndex - 1 : mCurrentIndex);
-
- if (mHasCameraScreennailOrPlaceholder && mAppBridge != null) {
- mActivity.getStateManager().startState(AlbumPage.class, data);
- } else {
- mActivity.getStateManager().switchState(this, AlbumPage.class, data);
- }
- }
- }
-
- @Override
- protected boolean onItemSelected(MenuItem item) {
- if (mModel == null) return true;
- refreshHidingMessage();
- MediaItem current = mModel.getMediaItem(0);
-
- // This is a shield for monkey when it clicks the action bar
- // menu when transitioning from filmstrip to camera
- if (current instanceof SnailItem) return true;
- // TODO: We should check the current photo against the MediaItem
- // that the menu was initially created for. We need to fix this
- // after PhotoPage being refactored.
- if (current == null) {
- // item is not ready, ignore
- return true;
- }
- int currentIndex = mModel.getCurrentIndex();
- Path path = current.getPath();
-
- DataManager manager = mActivity.getDataManager();
- int action = item.getItemId();
- String confirmMsg = null;
- switch (action) {
- case android.R.id.home: {
- onUpPressed();
- return true;
- }
- case R.id.action_slideshow: {
- Bundle data = new Bundle();
- data.putString(SlideshowPage.KEY_SET_PATH, mMediaSet.getPath().toString());
- data.putString(SlideshowPage.KEY_ITEM_PATH, path.toString());
- data.putInt(SlideshowPage.KEY_PHOTO_INDEX, currentIndex);
- data.putBoolean(SlideshowPage.KEY_REPEAT, true);
- mActivity.getStateManager().startStateForResult(
- SlideshowPage.class, REQUEST_SLIDESHOW, data);
- return true;
- }
- case R.id.action_crop: {
- Activity activity = mActivity;
- Intent intent = new Intent(CropActivity.CROP_ACTION);
- intent.setClass(activity, CropActivity.class);
- intent.setDataAndType(manager.getContentUri(path), current.getMimeType())
- .setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
- activity.startActivityForResult(intent, PicasaSource.isPicasaImage(current)
- ? REQUEST_CROP_PICASA
- : REQUEST_CROP);
- return true;
- }
- case R.id.action_trim: {
- Intent intent = new Intent(mActivity, TrimVideo.class);
- intent.setData(manager.getContentUri(path));
- // We need the file path to wrap this into a RandomAccessFile.
- intent.putExtra(KEY_MEDIA_ITEM_PATH, current.getFilePath());
- mActivity.startActivityForResult(intent, REQUEST_TRIM);
- return true;
- }
- case R.id.action_mute: {
- MuteVideo muteVideo = new MuteVideo(current.getFilePath(),
- manager.getContentUri(path), mActivity);
- muteVideo.muteInBackground();
- return true;
- }
- case R.id.action_edit: {
- launchPhotoEditor();
- return true;
- }
- case R.id.action_simple_edit: {
- launchSimpleEditor();
- return true;
- }
- case R.id.action_details: {
- if (mShowDetails) {
- hideDetails();
- } else {
- showDetails();
- }
- return true;
- }
- case R.id.action_delete:
- confirmMsg = mActivity.getResources().getQuantityString(
- R.plurals.delete_selection, 1);
- case R.id.action_setas:
- case R.id.action_rotate_ccw:
- case R.id.action_rotate_cw:
- case R.id.action_show_on_map:
- mSelectionManager.deSelectAll();
- mSelectionManager.toggle(path);
- mMenuExecutor.onMenuClicked(item, confirmMsg, mConfirmDialogListener);
- return true;
- default :
- return false;
- }
- }
-
- private void hideDetails() {
- mShowDetails = false;
- mDetailsHelper.hide();
- }
-
- private void showDetails() {
- mShowDetails = true;
- if (mDetailsHelper == null) {
- mDetailsHelper = new DetailsHelper(mActivity, mRootPane, new MyDetailsSource());
- mDetailsHelper.setCloseListener(new CloseListener() {
- @Override
- public void onClose() {
- hideDetails();
- }
- });
- }
- mDetailsHelper.show();
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Callbacks from PhotoView
- ////////////////////////////////////////////////////////////////////////////
- @Override
- public void onSingleTapUp(int x, int y) {
- if (mAppBridge != null) {
- if (mAppBridge.onSingleTapUp(x, y)) return;
- }
-
- MediaItem item = mModel.getMediaItem(0);
- if (item == null || item == mScreenNailItem) {
- // item is not ready or it is camera preview, ignore
- return;
- }
-
- int supported = item.getSupportedOperations();
- boolean playVideo = ((supported & MediaItem.SUPPORT_PLAY) != 0);
- boolean unlock = ((supported & MediaItem.SUPPORT_UNLOCK) != 0);
- boolean goBack = ((supported & MediaItem.SUPPORT_BACK) != 0);
- boolean launchCamera = ((supported & MediaItem.SUPPORT_CAMERA_SHORTCUT) != 0);
-
- if (playVideo) {
- // determine if the point is at center (1/6) of the photo view.
- // (The position of the "play" icon is at center (1/6) of the photo)
- int w = mPhotoView.getWidth();
- int h = mPhotoView.getHeight();
- playVideo = (Math.abs(x - w / 2) * 12 <= w)
- && (Math.abs(y - h / 2) * 12 <= h);
- }
-
- if (playVideo) {
- if (mSecureAlbum == null) {
- playVideo(mActivity, item.getPlayUri(), item.getName());
- } else {
- mActivity.getStateManager().finishState(this);
- }
- } else if (goBack) {
- onBackPressed();
- } else if (unlock) {
- Intent intent = new Intent(mActivity, Gallery.class);
- intent.putExtra(Gallery.KEY_DISMISS_KEYGUARD, true);
- mActivity.startActivity(intent);
- } else if (launchCamera) {
- launchCamera();
- } else {
- toggleBars();
- }
- }
-
- @Override
- public void onActionBarAllowed(boolean allowed) {
- mActionBarAllowed = allowed;
- mHandler.sendEmptyMessage(MSG_UPDATE_ACTION_BAR);
- }
-
- @Override
- public void onActionBarWanted() {
- mHandler.sendEmptyMessage(MSG_WANT_BARS);
- }
-
- @Override
- public void onFullScreenChanged(boolean full) {
- Message m = mHandler.obtainMessage(
- MSG_ON_FULL_SCREEN_CHANGED, full ? 1 : 0, 0);
- m.sendToTarget();
- }
-
- // How we do delete/undo:
- //
- // When the user choose to delete a media item, we just tell the
- // FilterDeleteSet to hide that item. If the user choose to undo it, we
- // again tell FilterDeleteSet not to hide it. If the user choose to commit
- // the deletion, we then actually delete the media item.
- @Override
- public void onDeleteImage(Path path, int offset) {
- onCommitDeleteImage(); // commit the previous deletion
- mDeletePath = path;
- mDeleteIsFocus = (offset == 0);
- mMediaSet.addDeletion(path, mCurrentIndex + offset);
- }
-
- @Override
- public void onUndoDeleteImage() {
- if (mDeletePath == null) return;
- // If the deletion was done on the focused item, we want the model to
- // focus on it when it is undeleted.
- if (mDeleteIsFocus) mModel.setFocusHintPath(mDeletePath);
- mMediaSet.removeDeletion(mDeletePath);
- mDeletePath = null;
- }
-
- @Override
- public void onCommitDeleteImage() {
- if (mDeletePath == null) return;
- mMenuExecutor.startSingleItemAction(R.id.action_delete, mDeletePath);
- mDeletePath = null;
- }
-
- public void playVideo(Activity activity, Uri uri, String title) {
- try {
- Intent intent = new Intent(Intent.ACTION_VIEW)
- .setDataAndType(uri, "video/*")
- .putExtra(Intent.EXTRA_TITLE, title)
- .putExtra(MovieActivity.KEY_TREAT_UP_AS_BACK, true);
- activity.startActivityForResult(intent, REQUEST_PLAY_VIDEO);
- } catch (ActivityNotFoundException e) {
- Toast.makeText(activity, activity.getString(R.string.video_err),
- Toast.LENGTH_SHORT).show();
- }
- }
-
- private void setCurrentPhotoByIntent(Intent intent) {
- if (intent == null) return;
- Path path = mApplication.getDataManager()
- .findPathByUri(intent.getData(), intent.getType());
- if (path != null) {
- Path albumPath = mApplication.getDataManager().getDefaultSetOf(path);
- if (!albumPath.equalsIgnoreCase(mOriginalSetPathString)) {
- // If the edited image is stored in a different album, we need
- // to start a new activity state to show the new image
- Bundle data = new Bundle(getData());
- data.putString(KEY_MEDIA_SET_PATH, albumPath.toString());
- data.putString(PhotoPage.KEY_MEDIA_ITEM_PATH, path.toString());
- mActivity.getStateManager().startState(SinglePhotoPage.class, data);
- return;
- }
- mModel.setCurrentPhoto(path, mCurrentIndex);
- }
- }
-
- @Override
- protected void onStateResult(int requestCode, int resultCode, Intent data) {
- if (resultCode == Activity.RESULT_CANCELED) {
- // This is a reset, not a canceled
- return;
- }
- if (resultCode == ProxyLauncher.RESULT_USER_CANCELED) {
- // Unmap reset vs. canceled
- resultCode = Activity.RESULT_CANCELED;
- }
- mRecenterCameraOnResume = false;
- switch (requestCode) {
- case REQUEST_EDIT:
- setCurrentPhotoByIntent(data);
- break;
- case REQUEST_CROP:
- if (resultCode == Activity.RESULT_OK) {
- setCurrentPhotoByIntent(data);
- }
- break;
- case REQUEST_CROP_PICASA: {
- if (resultCode == Activity.RESULT_OK) {
- Context context = mActivity.getAndroidContext();
- String message = context.getString(R.string.crop_saved,
- context.getString(R.string.folder_edited_online_photos));
- Toast.makeText(context, message, Toast.LENGTH_SHORT).show();
- }
- break;
- }
- case REQUEST_SLIDESHOW: {
- if (data == null) break;
- String path = data.getStringExtra(SlideshowPage.KEY_ITEM_PATH);
- int index = data.getIntExtra(SlideshowPage.KEY_PHOTO_INDEX, 0);
- if (path != null) {
- mModel.setCurrentPhoto(Path.fromString(path), index);
- }
- }
- }
- }
-
- @Override
- public void onPause() {
- super.onPause();
- mIsActive = false;
-
- mActivity.getGLRoot().unfreeze();
- mHandler.removeMessages(MSG_UNFREEZE_GLROOT);
-
- DetailsHelper.pause();
- // Hide the detail dialog on exit
- if (mShowDetails) hideDetails();
- if (mModel != null) {
- mModel.pause();
- }
- mPhotoView.pause();
- mHandler.removeMessages(MSG_HIDE_BARS);
- mHandler.removeMessages(MSG_REFRESH_BOTTOM_CONTROLS);
- refreshBottomControlsWhenReady();
- mActionBar.removeOnMenuVisibilityListener(mMenuVisibilityListener);
- if (mShowSpinner) {
- mActionBar.disableAlbumModeMenu(true);
- }
- onCommitDeleteImage();
- mMenuExecutor.pause();
- if (mMediaSet != null) mMediaSet.clearDeletion();
- }
-
- @Override
- public void onCurrentImageUpdated() {
- mActivity.getGLRoot().unfreeze();
- }
-
- @Override
- public void onFilmModeChanged(boolean enabled) {
- refreshBottomControlsWhenReady();
- if (mShowSpinner) {
- if (enabled) {
- mActionBar.enableAlbumModeMenu(
- GalleryActionBar.ALBUM_FILMSTRIP_MODE_SELECTED, this);
- } else {
- mActionBar.disableAlbumModeMenu(true);
- }
- }
- if (enabled) {
- mHandler.removeMessages(MSG_HIDE_BARS);
- UsageStatistics.onContentViewChanged(
- UsageStatistics.COMPONENT_GALLERY, "FilmstripPage");
- } else {
- refreshHidingMessage();
- if (mAppBridge == null || mCurrentIndex > 0) {
- UsageStatistics.onContentViewChanged(
- UsageStatistics.COMPONENT_GALLERY, "SinglePhotoPage");
- } else {
- UsageStatistics.onContentViewChanged(
- UsageStatistics.COMPONENT_CAMERA, "Unknown"); // TODO
- }
- }
- }
-
- private void transitionFromAlbumPageIfNeeded() {
- TransitionStore transitions = mActivity.getTransitionStore();
-
- int albumPageTransition = transitions.get(
- KEY_ALBUMPAGE_TRANSITION, MSG_ALBUMPAGE_NONE);
-
- if (albumPageTransition == MSG_ALBUMPAGE_NONE && mAppBridge != null
- && mRecenterCameraOnResume) {
- // Generally, resuming the PhotoPage when in Camera should
- // reset to the capture mode to allow quick photo taking
- mCurrentIndex = 0;
- mPhotoView.resetToFirstPicture();
- } else {
- int resumeIndex = transitions.get(KEY_INDEX_HINT, -1);
- if (resumeIndex >= 0) {
- if (mHasCameraScreennailOrPlaceholder) {
- // Account for preview/placeholder being the first item
- resumeIndex++;
- }
- if (resumeIndex < mMediaSet.getMediaItemCount()) {
- mCurrentIndex = resumeIndex;
- mModel.moveTo(mCurrentIndex);
- }
- }
- }
-
- if (albumPageTransition == MSG_ALBUMPAGE_RESUMED) {
- mPhotoView.setFilmMode(mStartInFilmstrip || mAppBridge != null);
- } else if (albumPageTransition == MSG_ALBUMPAGE_PICKED) {
- mPhotoView.setFilmMode(false);
- }
- }
-
- @Override
- protected void onResume() {
- super.onResume();
-
- if (mModel == null) {
- mActivity.getStateManager().finishState(this);
- return;
- }
- transitionFromAlbumPageIfNeeded();
-
- mActivity.getGLRoot().freeze();
- mIsActive = true;
- setContentPane(mRootPane);
-
- mModel.resume();
- mPhotoView.resume();
- mActionBar.setDisplayOptions(
- ((mSecureAlbum == null) && (mSetPathString != null)), false);
- mActionBar.addOnMenuVisibilityListener(mMenuVisibilityListener);
- refreshBottomControlsWhenReady();
- if (mShowSpinner && mPhotoView.getFilmMode()) {
- mActionBar.enableAlbumModeMenu(
- GalleryActionBar.ALBUM_FILMSTRIP_MODE_SELECTED, this);
- }
- if (!mShowBars) {
- mActionBar.hide();
- mActivity.getGLRoot().setLightsOutMode(true);
- }
- boolean haveImageEditor = GalleryUtils.isEditorAvailable(mActivity, "image/*");
- if (haveImageEditor != mHaveImageEditor) {
- mHaveImageEditor = haveImageEditor;
- updateMenuOperations();
- }
-
- mRecenterCameraOnResume = true;
- mHandler.sendEmptyMessageDelayed(MSG_UNFREEZE_GLROOT, UNFREEZE_GLROOT_TIMEOUT);
- }
-
- @Override
- protected void onDestroy() {
- if (mAppBridge != null) {
- mAppBridge.setServer(null);
- mScreenNailItem.setScreenNail(null);
- mAppBridge.detachScreenNail();
- mAppBridge = null;
- mScreenNailSet = null;
- mScreenNailItem = null;
- }
- mActivity.getGLRoot().setOrientationSource(null);
- if (mBottomControls != null) mBottomControls.cleanup();
-
- // Remove all pending messages.
- mHandler.removeCallbacksAndMessages(null);
- super.onDestroy();
- }
-
- private class MyDetailsSource implements DetailsSource {
-
- @Override
- public MediaDetails getDetails() {
- return mModel.getMediaItem(0).getDetails();
- }
-
- @Override
- public int size() {
- return mMediaSet != null ? mMediaSet.getMediaItemCount() : 1;
- }
-
- @Override
- public int setIndex() {
- return mModel.getCurrentIndex();
- }
- }
-
- @Override
- public void onAlbumModeSelected(int mode) {
- if (mode == GalleryActionBar.ALBUM_GRID_MODE_SELECTED) {
- switchToGrid();
- }
- }
-
- @Override
- public void refreshBottomControlsWhenReady() {
- if (mBottomControls == null) {
- return;
- }
- MediaObject currentPhoto = mCurrentPhoto;
- if (currentPhoto == null) {
- mHandler.obtainMessage(MSG_REFRESH_BOTTOM_CONTROLS, 0, 0, currentPhoto).sendToTarget();
- } else {
- currentPhoto.getPanoramaSupport(mRefreshBottomControlsCallback);
- }
- }
-
- private void updatePanoramaUI(boolean isPanorama360) {
- Menu menu = mActionBar.getMenu();
-
- // it could be null if onCreateActionBar has not been called yet
- if (menu == null) {
- return;
- }
-
- MenuExecutor.updateMenuForPanorama(menu, isPanorama360, isPanorama360);
-
- if (isPanorama360) {
- MenuItem item = menu.findItem(R.id.action_share);
- if (item != null) {
- item.setShowAsAction(MenuItem.SHOW_AS_ACTION_NEVER);
- item.setTitle(mActivity.getResources().getString(R.string.share_as_photo));
- }
- } else if ((mCurrentPhoto.getSupportedOperations() & MediaObject.SUPPORT_SHARE) != 0) {
- MenuItem item = menu.findItem(R.id.action_share);
- if (item != null) {
- item.setShowAsAction(MenuItem.SHOW_AS_ACTION_IF_ROOM);
- item.setTitle(mActivity.getResources().getString(R.string.share));
- }
- }
- }
-
- @Override
- public void onUndoBarVisibilityChanged(boolean visible) {
- refreshBottomControlsWhenReady();
- }
-
- @Override
- public boolean onShareTargetSelected(ShareActionProvider source, Intent intent) {
- final long timestampMillis = mCurrentPhoto.getDateInMs();
- final String mediaType = getMediaTypeString(mCurrentPhoto);
- UsageStatistics.onEvent(UsageStatistics.COMPONENT_GALLERY,
- UsageStatistics.ACTION_SHARE,
- mediaType,
- timestampMillis > 0
- ? System.currentTimeMillis() - timestampMillis
- : -1);
- return false;
- }
-
- private static String getMediaTypeString(MediaItem item) {
- if (item.getMediaType() == MediaObject.MEDIA_TYPE_VIDEO) {
- return "Video";
- } else if (item.getMediaType() == MediaObject.MEDIA_TYPE_IMAGE) {
- return "Photo";
- } else {
- return "Unknown:" + item.getMediaType();
- }
- }
-
-}
diff --git a/src/com/android/gallery3d/app/PhotoPageBottomControls.java b/src/com/android/gallery3d/app/PhotoPageBottomControls.java
deleted file mode 100644
index 24b8ceb7e..000000000
--- a/src/com/android/gallery3d/app/PhotoPageBottomControls.java
+++ /dev/null
@@ -1,137 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.content.Context;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.view.ViewGroup;
-import android.view.animation.AlphaAnimation;
-import android.view.animation.Animation;
-import android.widget.RelativeLayout;
-
-import com.android.gallery3d.R;
-
-import java.util.HashMap;
-import java.util.Map;
-
-public class PhotoPageBottomControls implements OnClickListener {
- public interface Delegate {
- public boolean canDisplayBottomControls();
- public boolean canDisplayBottomControl(int control);
- public void onBottomControlClicked(int control);
- public void refreshBottomControlsWhenReady();
- }
-
- private Delegate mDelegate;
- private ViewGroup mParentLayout;
- private ViewGroup mContainer;
-
- private boolean mContainerVisible = false;
- private Map<View, Boolean> mControlsVisible = new HashMap<View, Boolean>();
-
- private Animation mContainerAnimIn = new AlphaAnimation(0f, 1f);
- private Animation mContainerAnimOut = new AlphaAnimation(1f, 0f);
- private static final int CONTAINER_ANIM_DURATION_MS = 200;
-
- private static final int CONTROL_ANIM_DURATION_MS = 150;
- private static Animation getControlAnimForVisibility(boolean visible) {
- Animation anim = visible ? new AlphaAnimation(0f, 1f)
- : new AlphaAnimation(1f, 0f);
- anim.setDuration(CONTROL_ANIM_DURATION_MS);
- return anim;
- }
-
- public PhotoPageBottomControls(Delegate delegate, Context context, RelativeLayout layout) {
- mDelegate = delegate;
- mParentLayout = layout;
-
- LayoutInflater inflater = (LayoutInflater) context
- .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
- mContainer = (ViewGroup) inflater
- .inflate(R.layout.photopage_bottom_controls, mParentLayout, false);
- mParentLayout.addView(mContainer);
-
- for (int i = mContainer.getChildCount() - 1; i >= 0; i--) {
- View child = mContainer.getChildAt(i);
- child.setOnClickListener(this);
- mControlsVisible.put(child, false);
- }
-
- mContainerAnimIn.setDuration(CONTAINER_ANIM_DURATION_MS);
- mContainerAnimOut.setDuration(CONTAINER_ANIM_DURATION_MS);
-
- mDelegate.refreshBottomControlsWhenReady();
- }
-
- private void hide() {
- mContainer.clearAnimation();
- mContainerAnimOut.reset();
- mContainer.startAnimation(mContainerAnimOut);
- mContainer.setVisibility(View.INVISIBLE);
- }
-
- private void show() {
- mContainer.clearAnimation();
- mContainerAnimIn.reset();
- mContainer.startAnimation(mContainerAnimIn);
- mContainer.setVisibility(View.VISIBLE);
- }
-
- public void refresh() {
- boolean visible = mDelegate.canDisplayBottomControls();
- boolean containerVisibilityChanged = (visible != mContainerVisible);
- if (containerVisibilityChanged) {
- if (visible) {
- show();
- } else {
- hide();
- }
- mContainerVisible = visible;
- }
- if (!mContainerVisible) {
- return;
- }
- for (View control : mControlsVisible.keySet()) {
- Boolean prevVisibility = mControlsVisible.get(control);
- boolean curVisibility = mDelegate.canDisplayBottomControl(control.getId());
- if (prevVisibility.booleanValue() != curVisibility) {
- if (!containerVisibilityChanged) {
- control.clearAnimation();
- control.startAnimation(getControlAnimForVisibility(curVisibility));
- }
- control.setVisibility(curVisibility ? View.VISIBLE : View.INVISIBLE);
- mControlsVisible.put(control, curVisibility);
- }
- }
- // Force a layout change
- mContainer.requestLayout(); // Kick framework to draw the control.
- }
-
- public void cleanup() {
- mParentLayout.removeView(mContainer);
- mControlsVisible.clear();
- }
-
- @Override
- public void onClick(View view) {
- if (mContainerVisible && mControlsVisible.get(view).booleanValue()) {
- mDelegate.onBottomControlClicked(view.getId());
- }
- }
-}
diff --git a/src/com/android/gallery3d/app/PhotoPageProgressBar.java b/src/com/android/gallery3d/app/PhotoPageProgressBar.java
deleted file mode 100644
index 141fea698..000000000
--- a/src/com/android/gallery3d/app/PhotoPageProgressBar.java
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.app;
-
-import android.content.Context;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewGroup.LayoutParams;
-import android.widget.RelativeLayout;
-
-import com.android.gallery3d.R;
-
-public class PhotoPageProgressBar {
- private ViewGroup mContainer;
- private View mProgress;
-
- public PhotoPageProgressBar(Context context, RelativeLayout parentLayout) {
- LayoutInflater inflater = (LayoutInflater) context
- .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
- mContainer = (ViewGroup) inflater.inflate(R.layout.photopage_progress_bar, parentLayout,
- false);
- parentLayout.addView(mContainer);
- mProgress = mContainer.findViewById(R.id.photopage_progress_foreground);
- }
-
- public void setProgress(int progressPercent) {
- mContainer.setVisibility(View.VISIBLE);
- LayoutParams layoutParams = mProgress.getLayoutParams();
- layoutParams.width = mContainer.getWidth() * progressPercent / 100;
- mProgress.setLayoutParams(layoutParams);
- }
-
- public void hideProgress() {
- mContainer.setVisibility(View.INVISIBLE);
- }
-}
diff --git a/src/com/android/gallery3d/app/PickerActivity.java b/src/com/android/gallery3d/app/PickerActivity.java
deleted file mode 100644
index d5bb218ea..000000000
--- a/src/com/android/gallery3d/app/PickerActivity.java
+++ /dev/null
@@ -1,83 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.os.Bundle;
-import android.view.Menu;
-import android.view.MenuInflater;
-import android.view.MenuItem;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.view.Window;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.ui.GLRootView;
-
-public class PickerActivity extends AbstractGalleryActivity
- implements OnClickListener {
-
- public static final String KEY_ALBUM_PATH = "album-path";
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
-
- // We show the picker in two ways. One smaller screen we use a full
- // screen window with an action bar. On larger screen we use a dialog.
- boolean isDialog = getResources().getBoolean(R.bool.picker_is_dialog);
-
- if (!isDialog) {
- requestWindowFeature(Window.FEATURE_ACTION_BAR);
- requestWindowFeature(Window.FEATURE_ACTION_BAR_OVERLAY);
- }
-
- setContentView(R.layout.dialog_picker);
-
- if (isDialog) {
- // In dialog mode, we don't have the action bar to show the
- // "cancel" action, so we show an additional "cancel" button.
- View view = findViewById(R.id.cancel);
- view.setOnClickListener(this);
- view.setVisibility(View.VISIBLE);
-
- // We need this, otherwise the view will be dimmed because it
- // is "behind" the dialog.
- ((GLRootView) findViewById(R.id.gl_root_view)).setZOrderOnTop(true);
- }
- }
-
- @Override
- public boolean onCreateOptionsMenu(Menu menu) {
- MenuInflater inflater = getMenuInflater();
- inflater.inflate(R.menu.pickup, menu);
- return true;
- }
-
- @Override
- public boolean onOptionsItemSelected(MenuItem item) {
- if (item.getItemId() == R.id.action_cancel) {
- finish();
- return true;
- }
- return super.onOptionsItemSelected(item);
- }
-
- @Override
- public void onClick(View v) {
- if (v.getId() == R.id.cancel) finish();
- }
-}
diff --git a/src/com/android/gallery3d/app/SinglePhotoDataAdapter.java b/src/com/android/gallery3d/app/SinglePhotoDataAdapter.java
deleted file mode 100644
index 00f2fe78f..000000000
--- a/src/com/android/gallery3d/app/SinglePhotoDataAdapter.java
+++ /dev/null
@@ -1,263 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.BitmapRegionDecoder;
-import android.graphics.Rect;
-import android.os.Handler;
-import android.os.Message;
-
-import com.android.gallery3d.common.BitmapUtils;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.ui.BitmapScreenNail;
-import com.android.gallery3d.ui.PhotoView;
-import com.android.gallery3d.ui.ScreenNail;
-import com.android.gallery3d.ui.SynchronizedHandler;
-import com.android.gallery3d.ui.TileImageViewAdapter;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.FutureListener;
-import com.android.gallery3d.util.ThreadPool;
-
-public class SinglePhotoDataAdapter extends TileImageViewAdapter
- implements PhotoPage.Model {
-
- private static final String TAG = "SinglePhotoDataAdapter";
- private static final int SIZE_BACKUP = 1024;
- private static final int MSG_UPDATE_IMAGE = 1;
-
- private MediaItem mItem;
- private boolean mHasFullImage;
- private Future<?> mTask;
- private Handler mHandler;
-
- private PhotoView mPhotoView;
- private ThreadPool mThreadPool;
- private int mLoadingState = LOADING_INIT;
- private BitmapScreenNail mBitmapScreenNail;
-
- public SinglePhotoDataAdapter(
- AbstractGalleryActivity activity, PhotoView view, MediaItem item) {
- mItem = Utils.checkNotNull(item);
- mHasFullImage = (item.getSupportedOperations() &
- MediaItem.SUPPORT_FULL_IMAGE) != 0;
- mPhotoView = Utils.checkNotNull(view);
- mHandler = new SynchronizedHandler(activity.getGLRoot()) {
- @Override
- @SuppressWarnings("unchecked")
- public void handleMessage(Message message) {
- Utils.assertTrue(message.what == MSG_UPDATE_IMAGE);
- if (mHasFullImage) {
- onDecodeLargeComplete((ImageBundle) message.obj);
- } else {
- onDecodeThumbComplete((Future<Bitmap>) message.obj);
- }
- }
- };
- mThreadPool = activity.getThreadPool();
- }
-
- private static class ImageBundle {
- public final BitmapRegionDecoder decoder;
- public final Bitmap backupImage;
-
- public ImageBundle(BitmapRegionDecoder decoder, Bitmap backupImage) {
- this.decoder = decoder;
- this.backupImage = backupImage;
- }
- }
-
- private FutureListener<BitmapRegionDecoder> mLargeListener =
- new FutureListener<BitmapRegionDecoder>() {
- @Override
- public void onFutureDone(Future<BitmapRegionDecoder> future) {
- BitmapRegionDecoder decoder = future.get();
- if (decoder == null) return;
- int width = decoder.getWidth();
- int height = decoder.getHeight();
- BitmapFactory.Options options = new BitmapFactory.Options();
- options.inSampleSize = BitmapUtils.computeSampleSize(
- (float) SIZE_BACKUP / Math.max(width, height));
- Bitmap bitmap = decoder.decodeRegion(new Rect(0, 0, width, height), options);
- mHandler.sendMessage(mHandler.obtainMessage(
- MSG_UPDATE_IMAGE, new ImageBundle(decoder, bitmap)));
- }
- };
-
- private FutureListener<Bitmap> mThumbListener =
- new FutureListener<Bitmap>() {
- @Override
- public void onFutureDone(Future<Bitmap> future) {
- mHandler.sendMessage(
- mHandler.obtainMessage(MSG_UPDATE_IMAGE, future));
- }
- };
-
- @Override
- public boolean isEmpty() {
- return false;
- }
-
- private void setScreenNail(Bitmap bitmap, int width, int height) {
- mBitmapScreenNail = new BitmapScreenNail(bitmap);
- setScreenNail(mBitmapScreenNail, width, height);
- }
-
- private void onDecodeLargeComplete(ImageBundle bundle) {
- try {
- setScreenNail(bundle.backupImage,
- bundle.decoder.getWidth(), bundle.decoder.getHeight());
- setRegionDecoder(bundle.decoder);
- mPhotoView.notifyImageChange(0);
- } catch (Throwable t) {
- Log.w(TAG, "fail to decode large", t);
- }
- }
-
- private void onDecodeThumbComplete(Future<Bitmap> future) {
- try {
- Bitmap backup = future.get();
- if (backup == null) {
- mLoadingState = LOADING_FAIL;
- return;
- } else {
- mLoadingState = LOADING_COMPLETE;
- }
- setScreenNail(backup, backup.getWidth(), backup.getHeight());
- mPhotoView.notifyImageChange(0);
- } catch (Throwable t) {
- Log.w(TAG, "fail to decode thumb", t);
- }
- }
-
- @Override
- public void resume() {
- if (mTask == null) {
- if (mHasFullImage) {
- mTask = mThreadPool.submit(
- mItem.requestLargeImage(), mLargeListener);
- } else {
- mTask = mThreadPool.submit(
- mItem.requestImage(MediaItem.TYPE_THUMBNAIL),
- mThumbListener);
- }
- }
- }
-
- @Override
- public void pause() {
- Future<?> task = mTask;
- task.cancel();
- task.waitDone();
- if (task.get() == null) {
- mTask = null;
- }
- if (mBitmapScreenNail != null) {
- mBitmapScreenNail.recycle();
- mBitmapScreenNail = null;
- }
- }
-
- @Override
- public void moveTo(int index) {
- throw new UnsupportedOperationException();
- }
-
- @Override
- public void getImageSize(int offset, PhotoView.Size size) {
- if (offset == 0) {
- size.width = mItem.getWidth();
- size.height = mItem.getHeight();
- } else {
- size.width = 0;
- size.height = 0;
- }
- }
-
- @Override
- public int getImageRotation(int offset) {
- return (offset == 0) ? mItem.getFullImageRotation() : 0;
- }
-
- @Override
- public ScreenNail getScreenNail(int offset) {
- return (offset == 0) ? getScreenNail() : null;
- }
-
- @Override
- public void setNeedFullImage(boolean enabled) {
- // currently not necessary.
- }
-
- @Override
- public boolean isCamera(int offset) {
- return false;
- }
-
- @Override
- public boolean isPanorama(int offset) {
- return false;
- }
-
- @Override
- public boolean isStaticCamera(int offset) {
- return false;
- }
-
- @Override
- public boolean isVideo(int offset) {
- return mItem.getMediaType() == MediaItem.MEDIA_TYPE_VIDEO;
- }
-
- @Override
- public boolean isDeletable(int offset) {
- return (mItem.getSupportedOperations() & MediaItem.SUPPORT_DELETE) != 0;
- }
-
- @Override
- public MediaItem getMediaItem(int offset) {
- return offset == 0 ? mItem : null;
- }
-
- @Override
- public int getCurrentIndex() {
- return 0;
- }
-
- @Override
- public void setCurrentPhoto(Path path, int indexHint) {
- // ignore
- }
-
- @Override
- public void setFocusHintDirection(int direction) {
- // ignore
- }
-
- @Override
- public void setFocusHintPath(Path path) {
- // ignore
- }
-
- @Override
- public int getLoadingState(int offset) {
- return mLoadingState;
- }
-}
diff --git a/src/com/android/gallery3d/app/SinglePhotoPage.java b/src/com/android/gallery3d/app/SinglePhotoPage.java
deleted file mode 100644
index beb87d358..000000000
--- a/src/com/android/gallery3d/app/SinglePhotoPage.java
+++ /dev/null
@@ -1,21 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-public class SinglePhotoPage extends PhotoPage {
-
-}
diff --git a/src/com/android/gallery3d/app/SlideshowDataAdapter.java b/src/com/android/gallery3d/app/SlideshowDataAdapter.java
deleted file mode 100644
index 7a0fba5fb..000000000
--- a/src/com/android/gallery3d/app/SlideshowDataAdapter.java
+++ /dev/null
@@ -1,204 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.graphics.Bitmap;
-
-import com.android.gallery3d.app.SlideshowPage.Slide;
-import com.android.gallery3d.data.ContentListener;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.FutureListener;
-import com.android.gallery3d.util.ThreadPool;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.util.LinkedList;
-import java.util.concurrent.atomic.AtomicBoolean;
-
-public class SlideshowDataAdapter implements SlideshowPage.Model {
- @SuppressWarnings("unused")
- private static final String TAG = "SlideshowDataAdapter";
-
- private static final int IMAGE_QUEUE_CAPACITY = 3;
-
- public interface SlideshowSource {
- public void addContentListener(ContentListener listener);
- public void removeContentListener(ContentListener listener);
- public long reload();
- public MediaItem getMediaItem(int index);
- public int findItemIndex(Path path, int hint);
- }
-
- private final SlideshowSource mSource;
-
- private int mLoadIndex = 0;
- private int mNextOutput = 0;
- private boolean mIsActive = false;
- private boolean mNeedReset;
- private boolean mDataReady;
- private Path mInitialPath;
-
- private final LinkedList<Slide> mImageQueue = new LinkedList<Slide>();
-
- private Future<Void> mReloadTask;
- private final ThreadPool mThreadPool;
-
- private long mDataVersion = MediaObject.INVALID_DATA_VERSION;
- private final AtomicBoolean mNeedReload = new AtomicBoolean(false);
- private final SourceListener mSourceListener = new SourceListener();
-
- // The index is just a hint if initialPath is set
- public SlideshowDataAdapter(GalleryContext context, SlideshowSource source, int index,
- Path initialPath) {
- mSource = source;
- mInitialPath = initialPath;
- mLoadIndex = index;
- mNextOutput = index;
- mThreadPool = context.getThreadPool();
- }
-
- private MediaItem loadItem() {
- if (mNeedReload.compareAndSet(true, false)) {
- long v = mSource.reload();
- if (v != mDataVersion) {
- mDataVersion = v;
- mNeedReset = true;
- return null;
- }
- }
- int index = mLoadIndex;
- if (mInitialPath != null) {
- index = mSource.findItemIndex(mInitialPath, index);
- mInitialPath = null;
- }
- return mSource.getMediaItem(index);
- }
-
- private class ReloadTask implements Job<Void> {
- @Override
- public Void run(JobContext jc) {
- while (true) {
- synchronized (SlideshowDataAdapter.this) {
- while (mIsActive && (!mDataReady
- || mImageQueue.size() >= IMAGE_QUEUE_CAPACITY)) {
- try {
- SlideshowDataAdapter.this.wait();
- } catch (InterruptedException ex) {
- // ignored.
- }
- continue;
- }
- }
- if (!mIsActive) return null;
- mNeedReset = false;
-
- MediaItem item = loadItem();
-
- if (mNeedReset) {
- synchronized (SlideshowDataAdapter.this) {
- mImageQueue.clear();
- mLoadIndex = mNextOutput;
- }
- continue;
- }
-
- if (item == null) {
- synchronized (SlideshowDataAdapter.this) {
- if (!mNeedReload.get()) mDataReady = false;
- SlideshowDataAdapter.this.notifyAll();
- }
- continue;
- }
-
- Bitmap bitmap = item
- .requestImage(MediaItem.TYPE_THUMBNAIL)
- .run(jc);
-
- if (bitmap != null) {
- synchronized (SlideshowDataAdapter.this) {
- mImageQueue.addLast(
- new Slide(item, mLoadIndex, bitmap));
- if (mImageQueue.size() == 1) {
- SlideshowDataAdapter.this.notifyAll();
- }
- }
- }
- ++mLoadIndex;
- }
- }
- }
-
- private class SourceListener implements ContentListener {
- @Override
- public void onContentDirty() {
- synchronized (SlideshowDataAdapter.this) {
- mNeedReload.set(true);
- mDataReady = true;
- SlideshowDataAdapter.this.notifyAll();
- }
- }
- }
-
- private synchronized Slide innerNextBitmap() {
- while (mIsActive && mDataReady && mImageQueue.isEmpty()) {
- try {
- wait();
- } catch (InterruptedException t) {
- throw new AssertionError();
- }
- }
- if (mImageQueue.isEmpty()) return null;
- mNextOutput++;
- this.notifyAll();
- return mImageQueue.removeFirst();
- }
-
- @Override
- public Future<Slide> nextSlide(FutureListener<Slide> listener) {
- return mThreadPool.submit(new Job<Slide>() {
- @Override
- public Slide run(JobContext jc) {
- jc.setMode(ThreadPool.MODE_NONE);
- return innerNextBitmap();
- }
- }, listener);
- }
-
- @Override
- public void pause() {
- synchronized (this) {
- mIsActive = false;
- notifyAll();
- }
- mSource.removeContentListener(mSourceListener);
- mReloadTask.cancel();
- mReloadTask.waitDone();
- mReloadTask = null;
- }
-
- @Override
- public synchronized void resume() {
- mIsActive = true;
- mSource.addContentListener(mSourceListener);
- mNeedReload.set(true);
- mDataReady = true;
- mReloadTask = mThreadPool.submit(new ReloadTask());
- }
-}
diff --git a/src/com/android/gallery3d/app/SlideshowPage.java b/src/com/android/gallery3d/app/SlideshowPage.java
deleted file mode 100644
index 174058dc8..000000000
--- a/src/com/android/gallery3d/app/SlideshowPage.java
+++ /dev/null
@@ -1,366 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.app.Activity;
-import android.content.Intent;
-import android.graphics.Bitmap;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.Message;
-import android.view.MotionEvent;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.ContentListener;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.ui.GLView;
-import com.android.gallery3d.ui.SlideshowView;
-import com.android.gallery3d.ui.SynchronizedHandler;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.FutureListener;
-
-import java.util.ArrayList;
-import java.util.Random;
-
-public class SlideshowPage extends ActivityState {
- private static final String TAG = "SlideshowPage";
-
- public static final String KEY_SET_PATH = "media-set-path";
- public static final String KEY_ITEM_PATH = "media-item-path";
- public static final String KEY_PHOTO_INDEX = "photo-index";
- public static final String KEY_RANDOM_ORDER = "random-order";
- public static final String KEY_REPEAT = "repeat";
- public static final String KEY_DREAM = "dream";
-
- private static final long SLIDESHOW_DELAY = 3000; // 3 seconds
-
- private static final int MSG_LOAD_NEXT_BITMAP = 1;
- private static final int MSG_SHOW_PENDING_BITMAP = 2;
-
- public static interface Model {
- public void pause();
-
- public void resume();
-
- public Future<Slide> nextSlide(FutureListener<Slide> listener);
- }
-
- public static class Slide {
- public Bitmap bitmap;
- public MediaItem item;
- public int index;
-
- public Slide(MediaItem item, int index, Bitmap bitmap) {
- this.bitmap = bitmap;
- this.item = item;
- this.index = index;
- }
- }
-
- private Handler mHandler;
- private Model mModel;
- private SlideshowView mSlideshowView;
-
- private Slide mPendingSlide = null;
- private boolean mIsActive = false;
- private final Intent mResultIntent = new Intent();
-
- @Override
- protected int getBackgroundColorId() {
- return R.color.slideshow_background;
- }
-
- private final GLView mRootPane = new GLView() {
- @Override
- protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
- mSlideshowView.layout(0, 0, right - left, bottom - top);
- }
-
- @Override
- protected boolean onTouch(MotionEvent event) {
- if (event.getAction() == MotionEvent.ACTION_UP) {
- onBackPressed();
- }
- return true;
- }
-
- @Override
- protected void renderBackground(GLCanvas canvas) {
- canvas.clearBuffer(getBackgroundColor());
- }
- };
-
- @Override
- public void onCreate(Bundle data, Bundle restoreState) {
- super.onCreate(data, restoreState);
- mFlags |= (FLAG_HIDE_ACTION_BAR | FLAG_HIDE_STATUS_BAR);
- if (data.getBoolean(KEY_DREAM)) {
- // Dream screensaver only keeps screen on for plugged devices.
- mFlags |= FLAG_SCREEN_ON_WHEN_PLUGGED | FLAG_SHOW_WHEN_LOCKED;
- } else {
- // User-initiated slideshow would always keep screen on.
- mFlags |= FLAG_SCREEN_ON_ALWAYS;
- }
-
- mHandler = new SynchronizedHandler(mActivity.getGLRoot()) {
- @Override
- public void handleMessage(Message message) {
- switch (message.what) {
- case MSG_SHOW_PENDING_BITMAP:
- showPendingBitmap();
- break;
- case MSG_LOAD_NEXT_BITMAP:
- loadNextBitmap();
- break;
- default: throw new AssertionError();
- }
- }
- };
- initializeViews();
- initializeData(data);
- }
-
- private void loadNextBitmap() {
- mModel.nextSlide(new FutureListener<Slide>() {
- @Override
- public void onFutureDone(Future<Slide> future) {
- mPendingSlide = future.get();
- mHandler.sendEmptyMessage(MSG_SHOW_PENDING_BITMAP);
- }
- });
- }
-
- private void showPendingBitmap() {
- // mPendingBitmap could be null, if
- // 1.) there is no more items
- // 2.) mModel is paused
- Slide slide = mPendingSlide;
- if (slide == null) {
- if (mIsActive) {
- mActivity.getStateManager().finishState(SlideshowPage.this);
- }
- return;
- }
-
- mSlideshowView.next(slide.bitmap, slide.item.getRotation());
-
- setStateResult(Activity.RESULT_OK, mResultIntent
- .putExtra(KEY_ITEM_PATH, slide.item.getPath().toString())
- .putExtra(KEY_PHOTO_INDEX, slide.index));
- mHandler.sendEmptyMessageDelayed(MSG_LOAD_NEXT_BITMAP, SLIDESHOW_DELAY);
- }
-
- @Override
- public void onPause() {
- super.onPause();
- mIsActive = false;
- mModel.pause();
- mSlideshowView.release();
-
- mHandler.removeMessages(MSG_LOAD_NEXT_BITMAP);
- mHandler.removeMessages(MSG_SHOW_PENDING_BITMAP);
- }
-
- @Override
- public void onResume() {
- super.onResume();
- mIsActive = true;
- mModel.resume();
-
- if (mPendingSlide != null) {
- showPendingBitmap();
- } else {
- loadNextBitmap();
- }
- }
-
- private void initializeData(Bundle data) {
- boolean random = data.getBoolean(KEY_RANDOM_ORDER, false);
-
- // We only want to show slideshow for images only, not videos.
- String mediaPath = data.getString(KEY_SET_PATH);
- mediaPath = FilterUtils.newFilterPath(mediaPath, FilterUtils.FILTER_IMAGE_ONLY);
- MediaSet mediaSet = mActivity.getDataManager().getMediaSet(mediaPath);
-
- if (random) {
- boolean repeat = data.getBoolean(KEY_REPEAT);
- mModel = new SlideshowDataAdapter(mActivity,
- new ShuffleSource(mediaSet, repeat), 0, null);
- setStateResult(Activity.RESULT_OK, mResultIntent.putExtra(KEY_PHOTO_INDEX, 0));
- } else {
- int index = data.getInt(KEY_PHOTO_INDEX);
- String itemPath = data.getString(KEY_ITEM_PATH);
- Path path = itemPath != null ? Path.fromString(itemPath) : null;
- boolean repeat = data.getBoolean(KEY_REPEAT);
- mModel = new SlideshowDataAdapter(mActivity, new SequentialSource(mediaSet, repeat),
- index, path);
- setStateResult(Activity.RESULT_OK, mResultIntent.putExtra(KEY_PHOTO_INDEX, index));
- }
- }
-
- private void initializeViews() {
- mSlideshowView = new SlideshowView();
- mRootPane.addComponent(mSlideshowView);
- setContentPane(mRootPane);
- }
-
- private static MediaItem findMediaItem(MediaSet mediaSet, int index) {
- for (int i = 0, n = mediaSet.getSubMediaSetCount(); i < n; ++i) {
- MediaSet subset = mediaSet.getSubMediaSet(i);
- int count = subset.getTotalMediaItemCount();
- if (index < count) {
- return findMediaItem(subset, index);
- }
- index -= count;
- }
- ArrayList<MediaItem> list = mediaSet.getMediaItem(index, 1);
- return list.isEmpty() ? null : list.get(0);
- }
-
- private static class ShuffleSource implements SlideshowDataAdapter.SlideshowSource {
- private static final int RETRY_COUNT = 5;
- private final MediaSet mMediaSet;
- private final Random mRandom = new Random();
- private int mOrder[] = new int[0];
- private final boolean mRepeat;
- private long mSourceVersion = MediaSet.INVALID_DATA_VERSION;
- private int mLastIndex = -1;
-
- public ShuffleSource(MediaSet mediaSet, boolean repeat) {
- mMediaSet = Utils.checkNotNull(mediaSet);
- mRepeat = repeat;
- }
-
- @Override
- public int findItemIndex(Path path, int hint) {
- return hint;
- }
-
- @Override
- public MediaItem getMediaItem(int index) {
- if (!mRepeat && index >= mOrder.length) return null;
- if (mOrder.length == 0) return null;
- mLastIndex = mOrder[index % mOrder.length];
- MediaItem item = findMediaItem(mMediaSet, mLastIndex);
- for (int i = 0; i < RETRY_COUNT && item == null; ++i) {
- Log.w(TAG, "fail to find image: " + mLastIndex);
- mLastIndex = mRandom.nextInt(mOrder.length);
- item = findMediaItem(mMediaSet, mLastIndex);
- }
- return item;
- }
-
- @Override
- public long reload() {
- long version = mMediaSet.reload();
- if (version != mSourceVersion) {
- mSourceVersion = version;
- int count = mMediaSet.getTotalMediaItemCount();
- if (count != mOrder.length) generateOrderArray(count);
- }
- return version;
- }
-
- private void generateOrderArray(int totalCount) {
- if (mOrder.length != totalCount) {
- mOrder = new int[totalCount];
- for (int i = 0; i < totalCount; ++i) {
- mOrder[i] = i;
- }
- }
- for (int i = totalCount - 1; i > 0; --i) {
- Utils.swap(mOrder, i, mRandom.nextInt(i + 1));
- }
- if (mOrder[0] == mLastIndex && totalCount > 1) {
- Utils.swap(mOrder, 0, mRandom.nextInt(totalCount - 1) + 1);
- }
- }
-
- @Override
- public void addContentListener(ContentListener listener) {
- mMediaSet.addContentListener(listener);
- }
-
- @Override
- public void removeContentListener(ContentListener listener) {
- mMediaSet.removeContentListener(listener);
- }
- }
-
- private static class SequentialSource implements SlideshowDataAdapter.SlideshowSource {
- private static final int DATA_SIZE = 32;
-
- private ArrayList<MediaItem> mData = new ArrayList<MediaItem>();
- private int mDataStart = 0;
- private long mDataVersion = MediaObject.INVALID_DATA_VERSION;
- private final MediaSet mMediaSet;
- private final boolean mRepeat;
-
- public SequentialSource(MediaSet mediaSet, boolean repeat) {
- mMediaSet = mediaSet;
- mRepeat = repeat;
- }
-
- @Override
- public int findItemIndex(Path path, int hint) {
- return mMediaSet.getIndexOfItem(path, hint);
- }
-
- @Override
- public MediaItem getMediaItem(int index) {
- int dataEnd = mDataStart + mData.size();
-
- if (mRepeat) {
- int count = mMediaSet.getMediaItemCount();
- if (count == 0) return null;
- index = index % count;
- }
- if (index < mDataStart || index >= dataEnd) {
- mData = mMediaSet.getMediaItem(index, DATA_SIZE);
- mDataStart = index;
- dataEnd = index + mData.size();
- }
-
- return (index < mDataStart || index >= dataEnd) ? null : mData.get(index - mDataStart);
- }
-
- @Override
- public long reload() {
- long version = mMediaSet.reload();
- if (version != mDataVersion) {
- mDataVersion = version;
- mData.clear();
- }
- return mDataVersion;
- }
-
- @Override
- public void addContentListener(ContentListener listener) {
- mMediaSet.addContentListener(listener);
- }
-
- @Override
- public void removeContentListener(ContentListener listener) {
- mMediaSet.removeContentListener(listener);
- }
- }
-}
diff --git a/src/com/android/gallery3d/app/StateManager.java b/src/com/android/gallery3d/app/StateManager.java
deleted file mode 100644
index 53c3fc228..000000000
--- a/src/com/android/gallery3d/app/StateManager.java
+++ /dev/null
@@ -1,339 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.app.Activity;
-import android.content.Intent;
-import android.content.res.Configuration;
-import android.os.Bundle;
-import android.os.Parcelable;
-import android.view.Menu;
-import android.view.MenuItem;
-
-import com.android.camera.CameraActivity;
-import com.android.gallery3d.anim.StateTransitionAnimation;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.util.UsageStatistics;
-
-import java.util.Stack;
-
-public class StateManager {
- @SuppressWarnings("unused")
- private static final String TAG = "StateManager";
- private boolean mIsResumed = false;
-
- private static final String KEY_MAIN = "activity-state";
- private static final String KEY_DATA = "data";
- private static final String KEY_STATE = "bundle";
- private static final String KEY_CLASS = "class";
-
- private AbstractGalleryActivity mActivity;
- private Stack<StateEntry> mStack = new Stack<StateEntry>();
- private ActivityState.ResultEntry mResult;
-
- public StateManager(AbstractGalleryActivity activity) {
- mActivity = activity;
- }
-
- public void startState(Class<? extends ActivityState> klass,
- Bundle data) {
- Log.v(TAG, "startState " + klass);
- ActivityState state = null;
- try {
- state = klass.newInstance();
- } catch (Exception e) {
- throw new AssertionError(e);
- }
- if (!mStack.isEmpty()) {
- ActivityState top = getTopState();
- top.transitionOnNextPause(top.getClass(), klass,
- StateTransitionAnimation.Transition.Incoming);
- if (mIsResumed) top.onPause();
- }
-
- UsageStatistics.onContentViewChanged(
- UsageStatistics.COMPONENT_GALLERY,
- klass.getSimpleName());
- state.initialize(mActivity, data);
-
- mStack.push(new StateEntry(data, state));
- state.onCreate(data, null);
- if (mIsResumed) state.resume();
- }
-
- public void startStateForResult(Class<? extends ActivityState> klass,
- int requestCode, Bundle data) {
- Log.v(TAG, "startStateForResult " + klass + ", " + requestCode);
- ActivityState state = null;
- try {
- state = klass.newInstance();
- } catch (Exception e) {
- throw new AssertionError(e);
- }
- state.initialize(mActivity, data);
- state.mResult = new ActivityState.ResultEntry();
- state.mResult.requestCode = requestCode;
-
- if (!mStack.isEmpty()) {
- ActivityState as = getTopState();
- as.transitionOnNextPause(as.getClass(), klass,
- StateTransitionAnimation.Transition.Incoming);
- as.mReceivedResults = state.mResult;
- if (mIsResumed) as.onPause();
- } else {
- mResult = state.mResult;
- }
- UsageStatistics.onContentViewChanged(UsageStatistics.COMPONENT_GALLERY,
- klass.getSimpleName());
- mStack.push(new StateEntry(data, state));
- state.onCreate(data, null);
- if (mIsResumed) state.resume();
- }
-
- public boolean createOptionsMenu(Menu menu) {
- if (mStack.isEmpty()) {
- return false;
- } else {
- return getTopState().onCreateActionBar(menu);
- }
- }
-
- public void onConfigurationChange(Configuration config) {
- for (StateEntry entry : mStack) {
- entry.activityState.onConfigurationChanged(config);
- }
- }
-
- public void resume() {
- if (mIsResumed) return;
- mIsResumed = true;
- if (!mStack.isEmpty()) getTopState().resume();
- }
-
- public void pause() {
- if (!mIsResumed) return;
- mIsResumed = false;
- if (!mStack.isEmpty()) getTopState().onPause();
- }
-
- public void notifyActivityResult(int requestCode, int resultCode, Intent data) {
- getTopState().onStateResult(requestCode, resultCode, data);
- }
-
- public void clearActivityResult() {
- if (!mStack.isEmpty()) {
- getTopState().clearStateResult();
- }
- }
-
- public int getStateCount() {
- return mStack.size();
- }
-
- public boolean itemSelected(MenuItem item) {
- if (!mStack.isEmpty()) {
- if (getTopState().onItemSelected(item)) return true;
- if (item.getItemId() == android.R.id.home) {
- if (mStack.size() > 1) {
- getTopState().onBackPressed();
- }
- return true;
- }
- }
- return false;
- }
-
- public void onBackPressed() {
- if (!mStack.isEmpty()) {
- getTopState().onBackPressed();
- }
- }
-
- void finishState(ActivityState state) {
- finishState(state, true);
- }
-
- public void clearTasks() {
- // Remove all the states that are on top of the bottom PhotoPage state
- while (mStack.size() > 1) {
- mStack.pop().activityState.onDestroy();
- }
- }
-
- void finishState(ActivityState state, boolean fireOnPause) {
- // The finish() request could be rejected (only happens under Monkey),
- // If it is rejected, we won't close the last page.
- if (mStack.size() == 1) {
- Activity activity = (Activity) mActivity.getAndroidContext();
- if (mResult != null) {
- activity.setResult(mResult.resultCode, mResult.resultData);
- }
- activity.finish();
- if (!activity.isFinishing()) {
- Log.w(TAG, "finish is rejected, keep the last state");
- return;
- }
- Log.v(TAG, "no more state, finish activity");
- }
-
- Log.v(TAG, "finishState " + state);
- if (state != mStack.peek().activityState) {
- if (state.isDestroyed()) {
- Log.d(TAG, "The state is already destroyed");
- return;
- } else {
- throw new IllegalArgumentException("The stateview to be finished"
- + " is not at the top of the stack: " + state + ", "
- + mStack.peek().activityState);
- }
- }
-
- // Remove the top state.
- mStack.pop();
- state.mIsFinishing = true;
- ActivityState top = !mStack.isEmpty() ? mStack.peek().activityState : null;
- if (mIsResumed && fireOnPause) {
- if (top != null) {
- state.transitionOnNextPause(state.getClass(), top.getClass(),
- StateTransitionAnimation.Transition.Outgoing);
- }
- state.onPause();
- }
- mActivity.getGLRoot().setContentPane(null);
- state.onDestroy();
-
- if (top != null && mIsResumed) top.resume();
- if (top != null) {
- UsageStatistics.onContentViewChanged(UsageStatistics.COMPONENT_GALLERY,
- top.getClass().getSimpleName());
- }
- }
-
- public void switchState(ActivityState oldState,
- Class<? extends ActivityState> klass, Bundle data) {
- Log.v(TAG, "switchState " + oldState + ", " + klass);
- if (oldState != mStack.peek().activityState) {
- throw new IllegalArgumentException("The stateview to be finished"
- + " is not at the top of the stack: " + oldState + ", "
- + mStack.peek().activityState);
- }
- // Remove the top state.
- mStack.pop();
- if (!data.containsKey(PhotoPage.KEY_APP_BRIDGE)) {
- // Do not do the fade out stuff when we are switching camera modes
- oldState.transitionOnNextPause(oldState.getClass(), klass,
- StateTransitionAnimation.Transition.Incoming);
- }
- if (mIsResumed) oldState.onPause();
- oldState.onDestroy();
-
- // Create new state.
- ActivityState state = null;
- try {
- state = klass.newInstance();
- } catch (Exception e) {
- throw new AssertionError(e);
- }
- state.initialize(mActivity, data);
- mStack.push(new StateEntry(data, state));
- state.onCreate(data, null);
- if (mIsResumed) state.resume();
- UsageStatistics.onContentViewChanged(UsageStatistics.COMPONENT_GALLERY,
- klass.getSimpleName());
- }
-
- public void destroy() {
- Log.v(TAG, "destroy");
- while (!mStack.isEmpty()) {
- mStack.pop().activityState.onDestroy();
- }
- mStack.clear();
- }
-
- @SuppressWarnings("unchecked")
- public void restoreFromState(Bundle inState) {
- Log.v(TAG, "restoreFromState");
- Parcelable list[] = inState.getParcelableArray(KEY_MAIN);
- ActivityState topState = null;
- for (Parcelable parcelable : list) {
- Bundle bundle = (Bundle) parcelable;
- Class<? extends ActivityState> klass =
- (Class<? extends ActivityState>) bundle.getSerializable(KEY_CLASS);
-
- Bundle data = bundle.getBundle(KEY_DATA);
- Bundle state = bundle.getBundle(KEY_STATE);
-
- ActivityState activityState;
- try {
- Log.v(TAG, "restoreFromState " + klass);
- activityState = klass.newInstance();
- } catch (Exception e) {
- throw new AssertionError(e);
- }
- activityState.initialize(mActivity, data);
- activityState.onCreate(data, state);
- mStack.push(new StateEntry(data, activityState));
- topState = activityState;
- }
- if (topState != null) {
- UsageStatistics.onContentViewChanged(UsageStatistics.COMPONENT_GALLERY,
- topState.getClass().getSimpleName());
- }
- }
-
- public void saveState(Bundle outState) {
- Log.v(TAG, "saveState");
-
- Parcelable list[] = new Parcelable[mStack.size()];
- int i = 0;
- for (StateEntry entry : mStack) {
- Bundle bundle = new Bundle();
- bundle.putSerializable(KEY_CLASS, entry.activityState.getClass());
- bundle.putBundle(KEY_DATA, entry.data);
- Bundle state = new Bundle();
- entry.activityState.onSaveState(state);
- bundle.putBundle(KEY_STATE, state);
- Log.v(TAG, "saveState " + entry.activityState.getClass());
- list[i++] = bundle;
- }
- outState.putParcelableArray(KEY_MAIN, list);
- }
-
- public boolean hasStateClass(Class<? extends ActivityState> klass) {
- for (StateEntry entry : mStack) {
- if (klass.isInstance(entry.activityState)) {
- return true;
- }
- }
- return false;
- }
-
- public ActivityState getTopState() {
- Utils.assertTrue(!mStack.isEmpty());
- return mStack.peek().activityState;
- }
-
- private static class StateEntry {
- public Bundle data;
- public ActivityState activityState;
-
- public StateEntry(Bundle data, ActivityState state) {
- this.data = data;
- this.activityState = state;
- }
- }
-}
diff --git a/src/com/android/gallery3d/app/StitchingChangeListener.java b/src/com/android/gallery3d/app/StitchingChangeListener.java
deleted file mode 100644
index 0b8c2d6d6..000000000
--- a/src/com/android/gallery3d/app/StitchingChangeListener.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.net.Uri;
-
-public interface StitchingChangeListener {
- public void onStitchingQueued(Uri uri);
-
- public void onStitchingResult(Uri uri);
-
- public void onStitchingProgress(Uri uri, int progress);
-}
diff --git a/src/com/android/gallery3d/app/TimeBar.java b/src/com/android/gallery3d/app/TimeBar.java
deleted file mode 100644
index 246346a56..000000000
--- a/src/com/android/gallery3d/app/TimeBar.java
+++ /dev/null
@@ -1,266 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.graphics.Rect;
-import android.util.DisplayMetrics;
-import android.view.MotionEvent;
-import android.view.View;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.Utils;
-
-/**
- * The time bar view, which includes the current and total time, the progress
- * bar, and the scrubber.
- */
-public class TimeBar extends View {
-
- public interface Listener {
- void onScrubbingStart();
-
- void onScrubbingMove(int time);
-
- void onScrubbingEnd(int time, int start, int end);
- }
-
- // Padding around the scrubber to increase its touch target
- private static final int SCRUBBER_PADDING_IN_DP = 10;
-
- // The total padding, top plus bottom
- private static final int V_PADDING_IN_DP = 30;
-
- private static final int TEXT_SIZE_IN_DP = 14;
-
- protected final Listener mListener;
-
- // the bars we use for displaying the progress
- protected final Rect mProgressBar;
- protected final Rect mPlayedBar;
-
- protected final Paint mProgressPaint;
- protected final Paint mPlayedPaint;
- protected final Paint mTimeTextPaint;
-
- protected final Bitmap mScrubber;
- protected int mScrubberPadding; // adds some touch tolerance around the
- // scrubber
-
- protected int mScrubberLeft;
- protected int mScrubberTop;
- protected int mScrubberCorrection;
- protected boolean mScrubbing;
- protected boolean mShowTimes;
- protected boolean mShowScrubber;
-
- protected int mTotalTime;
- protected int mCurrentTime;
-
- protected final Rect mTimeBounds;
-
- protected int mVPaddingInPx;
-
- public TimeBar(Context context, Listener listener) {
- super(context);
- mListener = Utils.checkNotNull(listener);
-
- mShowTimes = true;
- mShowScrubber = true;
-
- mProgressBar = new Rect();
- mPlayedBar = new Rect();
-
- mProgressPaint = new Paint();
- mProgressPaint.setColor(0xFF808080);
- mPlayedPaint = new Paint();
- mPlayedPaint.setColor(0xFFFFFFFF);
-
- DisplayMetrics metrics = context.getResources().getDisplayMetrics();
- float textSizeInPx = metrics.density * TEXT_SIZE_IN_DP;
- mTimeTextPaint = new Paint(Paint.ANTI_ALIAS_FLAG);
- mTimeTextPaint.setColor(0xFFCECECE);
- mTimeTextPaint.setTextSize(textSizeInPx);
- mTimeTextPaint.setTextAlign(Paint.Align.CENTER);
-
- mTimeBounds = new Rect();
- mTimeTextPaint.getTextBounds("0:00:00", 0, 7, mTimeBounds);
-
- mScrubber = BitmapFactory.decodeResource(getResources(), R.drawable.scrubber_knob);
- mScrubberPadding = (int) (metrics.density * SCRUBBER_PADDING_IN_DP);
-
- mVPaddingInPx = (int) (metrics.density * V_PADDING_IN_DP);
- }
-
- private void update() {
- mPlayedBar.set(mProgressBar);
-
- if (mTotalTime > 0) {
- mPlayedBar.right =
- mPlayedBar.left + (int) ((mProgressBar.width() * (long) mCurrentTime) / mTotalTime);
- } else {
- mPlayedBar.right = mProgressBar.left;
- }
-
- if (!mScrubbing) {
- mScrubberLeft = mPlayedBar.right - mScrubber.getWidth() / 2;
- }
- invalidate();
- }
-
- /**
- * @return the preferred height of this view, including invisible padding
- */
- public int getPreferredHeight() {
- return mTimeBounds.height() + mVPaddingInPx + mScrubberPadding;
- }
-
- /**
- * @return the height of the time bar, excluding invisible padding
- */
- public int getBarHeight() {
- return mTimeBounds.height() + mVPaddingInPx;
- }
-
- public void setTime(int currentTime, int totalTime,
- int trimStartTime, int trimEndTime) {
- if (mCurrentTime == currentTime && mTotalTime == totalTime) {
- return;
- }
- mCurrentTime = currentTime;
- mTotalTime = totalTime;
- update();
- }
-
- private boolean inScrubber(float x, float y) {
- int scrubberRight = mScrubberLeft + mScrubber.getWidth();
- int scrubberBottom = mScrubberTop + mScrubber.getHeight();
- return mScrubberLeft - mScrubberPadding < x && x < scrubberRight + mScrubberPadding
- && mScrubberTop - mScrubberPadding < y && y < scrubberBottom + mScrubberPadding;
- }
-
- private void clampScrubber() {
- int half = mScrubber.getWidth() / 2;
- int max = mProgressBar.right - half;
- int min = mProgressBar.left - half;
- mScrubberLeft = Math.min(max, Math.max(min, mScrubberLeft));
- }
-
- private int getScrubberTime() {
- return (int) ((long) (mScrubberLeft + mScrubber.getWidth() / 2 - mProgressBar.left)
- * mTotalTime / mProgressBar.width());
- }
-
- @Override
- protected void onLayout(boolean changed, int l, int t, int r, int b) {
- int w = r - l;
- int h = b - t;
- if (!mShowTimes && !mShowScrubber) {
- mProgressBar.set(0, 0, w, h);
- } else {
- int margin = mScrubber.getWidth() / 3;
- if (mShowTimes) {
- margin += mTimeBounds.width();
- }
- int progressY = (h + mScrubberPadding) / 2;
- mScrubberTop = progressY - mScrubber.getHeight() / 2 + 1;
- mProgressBar.set(
- getPaddingLeft() + margin, progressY,
- w - getPaddingRight() - margin, progressY + 4);
- }
- update();
- }
-
- @Override
- protected void onDraw(Canvas canvas) {
- // draw progress bars
- canvas.drawRect(mProgressBar, mProgressPaint);
- canvas.drawRect(mPlayedBar, mPlayedPaint);
-
- // draw scrubber and timers
- if (mShowScrubber) {
- canvas.drawBitmap(mScrubber, mScrubberLeft, mScrubberTop, null);
- }
- if (mShowTimes) {
- canvas.drawText(
- stringForTime(mCurrentTime),
- mTimeBounds.width() / 2 + getPaddingLeft(),
- mTimeBounds.height() + mVPaddingInPx / 2 + mScrubberPadding + 1,
- mTimeTextPaint);
- canvas.drawText(
- stringForTime(mTotalTime),
- getWidth() - getPaddingRight() - mTimeBounds.width() / 2,
- mTimeBounds.height() + mVPaddingInPx / 2 + mScrubberPadding + 1,
- mTimeTextPaint);
- }
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- if (mShowScrubber) {
- int x = (int) event.getX();
- int y = (int) event.getY();
-
- switch (event.getAction()) {
- case MotionEvent.ACTION_DOWN: {
- mScrubberCorrection = inScrubber(x, y)
- ? x - mScrubberLeft
- : mScrubber.getWidth() / 2;
- mScrubbing = true;
- mListener.onScrubbingStart();
- }
- // fall-through
- case MotionEvent.ACTION_MOVE: {
- mScrubberLeft = x - mScrubberCorrection;
- clampScrubber();
- mCurrentTime = getScrubberTime();
- mListener.onScrubbingMove(mCurrentTime);
- invalidate();
- return true;
- }
- case MotionEvent.ACTION_CANCEL:
- case MotionEvent.ACTION_UP: {
- mListener.onScrubbingEnd(getScrubberTime(), 0, 0);
- mScrubbing = false;
- return true;
- }
- }
- }
- return false;
- }
-
- protected String stringForTime(long millis) {
- int totalSeconds = (int) millis / 1000;
- int seconds = totalSeconds % 60;
- int minutes = (totalSeconds / 60) % 60;
- int hours = totalSeconds / 3600;
- if (hours > 0) {
- return String.format("%d:%02d:%02d", hours, minutes, seconds).toString();
- } else {
- return String.format("%02d:%02d", minutes, seconds).toString();
- }
- }
-
- public void setSeekable(boolean canSeek) {
- mShowScrubber = canSeek;
- }
-
-}
diff --git a/src/com/android/gallery3d/app/TransitionStore.java b/src/com/android/gallery3d/app/TransitionStore.java
deleted file mode 100644
index aa38ed77e..000000000
--- a/src/com/android/gallery3d/app/TransitionStore.java
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import java.util.HashMap;
-
-public class TransitionStore {
- private HashMap<Object, Object> mStorage = new HashMap<Object, Object>();
-
- public void put(Object key, Object value) {
- mStorage.put(key, value);
- }
-
- public <T> void putIfNotPresent(Object key, T valueIfNull) {
- mStorage.put(key, get(key, valueIfNull));
- }
-
- @SuppressWarnings("unchecked")
- public <T> T get(Object key) {
- return (T) mStorage.get(key);
- }
-
- @SuppressWarnings("unchecked")
- public <T> T get(Object key, T valueIfNull) {
- T value = (T) mStorage.get(key);
- return value == null ? valueIfNull : value;
- }
-
- public void clear() {
- mStorage.clear();
- }
-}
diff --git a/src/com/android/gallery3d/app/TrimControllerOverlay.java b/src/com/android/gallery3d/app/TrimControllerOverlay.java
deleted file mode 100644
index cae016626..000000000
--- a/src/com/android/gallery3d/app/TrimControllerOverlay.java
+++ /dev/null
@@ -1,111 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.animation.Animator;
-import android.animation.Animator.AnimatorListener;
-import android.animation.ObjectAnimator;
-import android.content.Context;
-import android.view.MotionEvent;
-import android.view.View;
-
-import com.android.gallery3d.common.ApiHelper;
-
-/**
- * The controller for the Trimming Video.
- */
-public class TrimControllerOverlay extends CommonControllerOverlay {
-
- public TrimControllerOverlay(Context context) {
- super(context);
- }
-
- @Override
- protected void createTimeBar(Context context) {
- mTimeBar = new TrimTimeBar(context, this);
- }
-
- private void hidePlayButtonIfPlaying() {
- if (mState == State.PLAYING) {
- mPlayPauseReplayView.setVisibility(View.INVISIBLE);
- }
- if (ApiHelper.HAS_OBJECT_ANIMATION) {
- mPlayPauseReplayView.setAlpha(1f);
- }
- }
-
- @Override
- public void showPlaying() {
- super.showPlaying();
- if (ApiHelper.HAS_OBJECT_ANIMATION) {
- // Add animation to hide the play button while playing.
- ObjectAnimator anim = ObjectAnimator.ofFloat(mPlayPauseReplayView, "alpha", 1f, 0f);
- anim.setDuration(200);
- anim.start();
- anim.addListener(new AnimatorListener() {
- @Override
- public void onAnimationStart(Animator animation) {
- }
-
- @Override
- public void onAnimationEnd(Animator animation) {
- hidePlayButtonIfPlaying();
- }
-
- @Override
- public void onAnimationCancel(Animator animation) {
- hidePlayButtonIfPlaying();
- }
-
- @Override
- public void onAnimationRepeat(Animator animation) {
- }
- });
- } else {
- hidePlayButtonIfPlaying();
- }
- }
-
- @Override
- public void setTimes(int currentTime, int totalTime, int trimStartTime, int trimEndTime) {
- mTimeBar.setTime(currentTime, totalTime, trimStartTime, trimEndTime);
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- if (super.onTouchEvent(event)) {
- return true;
- }
-
- // The special thing here is that the State.ENDED include both cases of
- // the video completed and current == trimEnd. Both request a replay.
- switch (event.getAction()) {
- case MotionEvent.ACTION_DOWN:
- if (mState == State.PLAYING || mState == State.PAUSED) {
- mListener.onPlayPause();
- } else if (mState == State.ENDED) {
- if (mCanReplay) {
- mListener.onReplay();
- }
- }
- break;
- case MotionEvent.ACTION_UP:
- break;
- }
- return true;
- }
-}
diff --git a/src/com/android/gallery3d/app/TrimTimeBar.java b/src/com/android/gallery3d/app/TrimTimeBar.java
deleted file mode 100644
index f8dbc749e..000000000
--- a/src/com/android/gallery3d/app/TrimTimeBar.java
+++ /dev/null
@@ -1,339 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.Canvas;
-import android.view.MotionEvent;
-
-import com.android.gallery3d.R;
-
-/**
- * The trim time bar view, which includes the current and total time, the progress
- * bar, and the scrubbers for current time, start and end time for trimming.
- */
-public class TrimTimeBar extends TimeBar {
-
- public static final int SCRUBBER_NONE = 0;
- public static final int SCRUBBER_START = 1;
- public static final int SCRUBBER_CURRENT = 2;
- public static final int SCRUBBER_END = 3;
-
- private int mPressedThumb = SCRUBBER_NONE;
-
- // On touch event, the setting order is Scrubber Position -> Time ->
- // PlayedBar. At the setTimes(), activity can update the Time directly, then
- // PlayedBar will be updated too.
- private int mTrimStartScrubberLeft;
- private int mTrimEndScrubberLeft;
-
- private int mTrimStartScrubberTop;
- private int mTrimEndScrubberTop;
-
- private int mTrimStartTime;
- private int mTrimEndTime;
-
- private final Bitmap mTrimStartScrubber;
- private final Bitmap mTrimEndScrubber;
- public TrimTimeBar(Context context, Listener listener) {
- super(context, listener);
-
- mTrimStartTime = 0;
- mTrimEndTime = 0;
- mTrimStartScrubberLeft = 0;
- mTrimEndScrubberLeft = 0;
- mTrimStartScrubberTop = 0;
- mTrimEndScrubberTop = 0;
-
- mTrimStartScrubber = BitmapFactory.decodeResource(getResources(),
- R.drawable.text_select_handle_left);
- mTrimEndScrubber = BitmapFactory.decodeResource(getResources(),
- R.drawable.text_select_handle_right);
- // Increase the size of this trimTimeBar, but minimize the scrubber
- // touch padding since we have 3 scrubbers now.
- mScrubberPadding = 0;
- mVPaddingInPx = mVPaddingInPx * 3 / 2;
- }
-
- private int getBarPosFromTime(int time) {
- return mProgressBar.left +
- (int) ((mProgressBar.width() * (long) time) / mTotalTime);
- }
-
- private int trimStartScrubberTipOffset() {
- return mTrimStartScrubber.getWidth() * 3 / 4;
- }
-
- private int trimEndScrubberTipOffset() {
- return mTrimEndScrubber.getWidth() / 4;
- }
-
- // Based on all the time info (current, total, trimStart, trimEnd), we
- // decide the playedBar size.
- private void updatePlayedBarAndScrubberFromTime() {
- // According to the Time, update the Played Bar
- mPlayedBar.set(mProgressBar);
- if (mTotalTime > 0) {
- // set playedBar according to the trim time.
- mPlayedBar.left = getBarPosFromTime(mTrimStartTime);
- mPlayedBar.right = getBarPosFromTime(mCurrentTime);
- if (!mScrubbing) {
- mScrubberLeft = mPlayedBar.right - mScrubber.getWidth() / 2;
- mTrimStartScrubberLeft = mPlayedBar.left - trimStartScrubberTipOffset();
- mTrimEndScrubberLeft = getBarPosFromTime(mTrimEndTime)
- - trimEndScrubberTipOffset();
- }
- } else {
- // If the video is not prepared, just show the scrubber at the end
- // of progressBar
- mPlayedBar.right = mProgressBar.left;
- mScrubberLeft = mProgressBar.left - mScrubber.getWidth() / 2;
- mTrimStartScrubberLeft = mProgressBar.left - trimStartScrubberTipOffset();
- mTrimEndScrubberLeft = mProgressBar.right - trimEndScrubberTipOffset();
- }
- }
-
- private void initTrimTimeIfNeeded() {
- if (mTotalTime > 0 && mTrimEndTime == 0) {
- mTrimEndTime = mTotalTime;
- }
- }
-
- private void update() {
- initTrimTimeIfNeeded();
- updatePlayedBarAndScrubberFromTime();
- invalidate();
- }
-
- @Override
- public void setTime(int currentTime, int totalTime,
- int trimStartTime, int trimEndTime) {
- if (mCurrentTime == currentTime && mTotalTime == totalTime
- && mTrimStartTime == trimStartTime && mTrimEndTime == trimEndTime) {
- return;
- }
- mCurrentTime = currentTime;
- mTotalTime = totalTime;
- mTrimStartTime = trimStartTime;
- mTrimEndTime = trimEndTime;
- update();
- }
-
- private int whichScrubber(float x, float y) {
- if (inScrubber(x, y, mTrimStartScrubberLeft, mTrimStartScrubberTop, mTrimStartScrubber)) {
- return SCRUBBER_START;
- } else if (inScrubber(x, y, mTrimEndScrubberLeft, mTrimEndScrubberTop, mTrimEndScrubber)) {
- return SCRUBBER_END;
- } else if (inScrubber(x, y, mScrubberLeft, mScrubberTop, mScrubber)) {
- return SCRUBBER_CURRENT;
- }
- return SCRUBBER_NONE;
- }
-
- private boolean inScrubber(float x, float y, int startX, int startY, Bitmap scrubber) {
- int scrubberRight = startX + scrubber.getWidth();
- int scrubberBottom = startY + scrubber.getHeight();
- return startX < x && x < scrubberRight && startY < y && y < scrubberBottom;
- }
-
- private int clampScrubber(int scrubberLeft, int offset, int lowerBound, int upperBound) {
- int max = upperBound - offset;
- int min = lowerBound - offset;
- return Math.min(max, Math.max(min, scrubberLeft));
- }
-
- private int getScrubberTime(int scrubberLeft, int offset) {
- return (int) ((long) (scrubberLeft + offset - mProgressBar.left)
- * mTotalTime / mProgressBar.width());
- }
-
- @Override
- protected void onLayout(boolean changed, int l, int t, int r, int b) {
- int w = r - l;
- int h = b - t;
- if (!mShowTimes && !mShowScrubber) {
- mProgressBar.set(0, 0, w, h);
- } else {
- int margin = mScrubber.getWidth() / 3;
- if (mShowTimes) {
- margin += mTimeBounds.width();
- }
- int progressY = h / 4;
- int scrubberY = progressY - mScrubber.getHeight() / 2 + 1;
- mScrubberTop = scrubberY;
- mTrimStartScrubberTop = progressY;
- mTrimEndScrubberTop = progressY;
- mProgressBar.set(
- getPaddingLeft() + margin, progressY,
- w - getPaddingRight() - margin, progressY + 4);
- }
- update();
- }
-
- @Override
- protected void onDraw(Canvas canvas) {
- // draw progress bars
- canvas.drawRect(mProgressBar, mProgressPaint);
- canvas.drawRect(mPlayedBar, mPlayedPaint);
-
- if (mShowTimes) {
- canvas.drawText(
- stringForTime(mCurrentTime),
- mTimeBounds.width() / 2 + getPaddingLeft(),
- mTimeBounds.height() / 2 + mTrimStartScrubberTop,
- mTimeTextPaint);
- canvas.drawText(
- stringForTime(mTotalTime),
- getWidth() - getPaddingRight() - mTimeBounds.width() / 2,
- mTimeBounds.height() / 2 + mTrimStartScrubberTop,
- mTimeTextPaint);
- }
-
- // draw extra scrubbers
- if (mShowScrubber) {
- canvas.drawBitmap(mScrubber, mScrubberLeft, mScrubberTop, null);
- canvas.drawBitmap(mTrimStartScrubber, mTrimStartScrubberLeft,
- mTrimStartScrubberTop, null);
- canvas.drawBitmap(mTrimEndScrubber, mTrimEndScrubberLeft,
- mTrimEndScrubberTop, null);
- }
- }
-
- private void updateTimeFromPos() {
- mCurrentTime = getScrubberTime(mScrubberLeft, mScrubber.getWidth() / 2);
- mTrimStartTime = getScrubberTime(mTrimStartScrubberLeft, trimStartScrubberTipOffset());
- mTrimEndTime = getScrubberTime(mTrimEndScrubberLeft, trimEndScrubberTipOffset());
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- if (mShowScrubber) {
- int x = (int) event.getX();
- int y = (int) event.getY();
-
- switch (event.getAction()) {
- case MotionEvent.ACTION_DOWN:
- mPressedThumb = whichScrubber(x, y);
- switch (mPressedThumb) {
- case SCRUBBER_NONE:
- break;
- case SCRUBBER_CURRENT:
- mScrubbing = true;
- mScrubberCorrection = x - mScrubberLeft;
- break;
- case SCRUBBER_START:
- mScrubbing = true;
- mScrubberCorrection = x - mTrimStartScrubberLeft;
- break;
- case SCRUBBER_END:
- mScrubbing = true;
- mScrubberCorrection = x - mTrimEndScrubberLeft;
- break;
- }
- if (mScrubbing == true) {
- mListener.onScrubbingStart();
- return true;
- }
- break;
- case MotionEvent.ACTION_MOVE:
- if (mScrubbing) {
- int seekToTime = -1;
- int lowerBound = mTrimStartScrubberLeft + trimStartScrubberTipOffset();
- int upperBound = mTrimEndScrubberLeft + trimEndScrubberTipOffset();
- switch (mPressedThumb) {
- case SCRUBBER_CURRENT:
- mScrubberLeft = x - mScrubberCorrection;
- mScrubberLeft =
- clampScrubber(mScrubberLeft,
- mScrubber.getWidth() / 2,
- lowerBound, upperBound);
- seekToTime = getScrubberTime(mScrubberLeft,
- mScrubber.getWidth() / 2);
- break;
- case SCRUBBER_START:
- mTrimStartScrubberLeft = x - mScrubberCorrection;
- // Limit start <= end
- if (mTrimStartScrubberLeft > mTrimEndScrubberLeft) {
- mTrimStartScrubberLeft = mTrimEndScrubberLeft;
- }
- lowerBound = mProgressBar.left;
- mTrimStartScrubberLeft =
- clampScrubber(mTrimStartScrubberLeft,
- trimStartScrubberTipOffset(),
- lowerBound, upperBound);
- seekToTime = getScrubberTime(mTrimStartScrubberLeft,
- trimStartScrubberTipOffset());
- break;
- case SCRUBBER_END:
- mTrimEndScrubberLeft = x - mScrubberCorrection;
- upperBound = mProgressBar.right;
- mTrimEndScrubberLeft =
- clampScrubber(mTrimEndScrubberLeft,
- trimEndScrubberTipOffset(),
- lowerBound, upperBound);
- seekToTime = getScrubberTime(mTrimEndScrubberLeft,
- trimEndScrubberTipOffset());
- break;
- }
- updateTimeFromPos();
- updatePlayedBarAndScrubberFromTime();
- if (seekToTime != -1) {
- mListener.onScrubbingMove(seekToTime);
- }
- invalidate();
- return true;
- }
- break;
- case MotionEvent.ACTION_CANCEL:
- case MotionEvent.ACTION_UP:
- if (mScrubbing) {
- int seekToTime = 0;
- switch (mPressedThumb) {
- case SCRUBBER_CURRENT:
- seekToTime = getScrubberTime(mScrubberLeft,
- mScrubber.getWidth() / 2);
- break;
- case SCRUBBER_START:
- seekToTime = getScrubberTime(mTrimStartScrubberLeft,
- trimStartScrubberTipOffset());
- mScrubberLeft = mTrimStartScrubberLeft +
- trimStartScrubberTipOffset() - mScrubber.getWidth() / 2;
- break;
- case SCRUBBER_END:
- seekToTime = getScrubberTime(mTrimEndScrubberLeft,
- trimEndScrubberTipOffset());
- mScrubberLeft = mTrimEndScrubberLeft +
- trimEndScrubberTipOffset() - mScrubber.getWidth() / 2;
- break;
- }
- updateTimeFromPos();
- mListener.onScrubbingEnd(seekToTime,
- getScrubberTime(mTrimStartScrubberLeft,
- trimStartScrubberTipOffset()),
- getScrubberTime(mTrimEndScrubberLeft, trimEndScrubberTipOffset()));
- mScrubbing = false;
- mPressedThumb = SCRUBBER_NONE;
- return true;
- }
- break;
- }
- }
- return false;
- }
-}
diff --git a/src/com/android/gallery3d/app/TrimVideo.java b/src/com/android/gallery3d/app/TrimVideo.java
deleted file mode 100644
index 1e7728162..000000000
--- a/src/com/android/gallery3d/app/TrimVideo.java
+++ /dev/null
@@ -1,337 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.app.ActionBar;
-import android.app.Activity;
-import android.app.ProgressDialog;
-import android.content.Context;
-import android.content.Intent;
-import android.media.MediaPlayer;
-import android.net.Uri;
-import android.os.Bundle;
-import android.os.Handler;
-import android.provider.MediaStore;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.Window;
-import android.widget.TextView;
-import android.widget.Toast;
-import android.widget.VideoView;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.util.SaveVideoFileInfo;
-import com.android.gallery3d.util.SaveVideoFileUtils;
-
-import java.io.File;
-import java.io.IOException;
-
-public class TrimVideo extends Activity implements
- MediaPlayer.OnErrorListener,
- MediaPlayer.OnCompletionListener,
- ControllerOverlay.Listener {
-
- private VideoView mVideoView;
- private TextView mSaveVideoTextView;
- private TrimControllerOverlay mController;
- private Context mContext;
- private Uri mUri;
- private final Handler mHandler = new Handler();
- public static final String TRIM_ACTION = "com.android.camera.action.TRIM";
-
- public ProgressDialog mProgress;
-
- private int mTrimStartTime = 0;
- private int mTrimEndTime = 0;
- private int mVideoPosition = 0;
- public static final String KEY_TRIM_START = "trim_start";
- public static final String KEY_TRIM_END = "trim_end";
- public static final String KEY_VIDEO_POSITION = "video_pos";
- private boolean mHasPaused = false;
-
- private String mSrcVideoPath = null;
- private static final String TIME_STAMP_NAME = "'TRIM'_yyyyMMdd_HHmmss";
- private SaveVideoFileInfo mDstFileInfo = null;
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- mContext = getApplicationContext();
- super.onCreate(savedInstanceState);
-
- requestWindowFeature(Window.FEATURE_ACTION_BAR);
- requestWindowFeature(Window.FEATURE_ACTION_BAR_OVERLAY);
-
- ActionBar actionBar = getActionBar();
- int displayOptions = ActionBar.DISPLAY_SHOW_HOME;
- actionBar.setDisplayOptions(0, displayOptions);
- displayOptions = ActionBar.DISPLAY_SHOW_CUSTOM;
- actionBar.setDisplayOptions(displayOptions, displayOptions);
- actionBar.setCustomView(R.layout.trim_menu);
-
- mSaveVideoTextView = (TextView) findViewById(R.id.start_trim);
- mSaveVideoTextView.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View arg0) {
- trimVideo();
- }
- });
- mSaveVideoTextView.setEnabled(false);
-
- Intent intent = getIntent();
- mUri = intent.getData();
- mSrcVideoPath = intent.getStringExtra(PhotoPage.KEY_MEDIA_ITEM_PATH);
- setContentView(R.layout.trim_view);
- View rootView = findViewById(R.id.trim_view_root);
-
- mVideoView = (VideoView) rootView.findViewById(R.id.surface_view);
-
- mController = new TrimControllerOverlay(mContext);
- ((ViewGroup) rootView).addView(mController.getView());
- mController.setListener(this);
- mController.setCanReplay(true);
-
- mVideoView.setOnErrorListener(this);
- mVideoView.setOnCompletionListener(this);
- mVideoView.setVideoURI(mUri);
-
- playVideo();
- }
-
- @Override
- public void onResume() {
- super.onResume();
- if (mHasPaused) {
- mVideoView.seekTo(mVideoPosition);
- mVideoView.resume();
- mHasPaused = false;
- }
- mHandler.post(mProgressChecker);
- }
-
- @Override
- public void onPause() {
- mHasPaused = true;
- mHandler.removeCallbacksAndMessages(null);
- mVideoPosition = mVideoView.getCurrentPosition();
- mVideoView.suspend();
- super.onPause();
- }
-
- @Override
- public void onStop() {
- if (mProgress != null) {
- mProgress.dismiss();
- mProgress = null;
- }
- super.onStop();
- }
-
- @Override
- public void onDestroy() {
- mVideoView.stopPlayback();
- super.onDestroy();
- }
-
- private final Runnable mProgressChecker = new Runnable() {
- @Override
- public void run() {
- int pos = setProgress();
- mHandler.postDelayed(mProgressChecker, 200 - (pos % 200));
- }
- };
-
- @Override
- public void onSaveInstanceState(Bundle savedInstanceState) {
- savedInstanceState.putInt(KEY_TRIM_START, mTrimStartTime);
- savedInstanceState.putInt(KEY_TRIM_END, mTrimEndTime);
- savedInstanceState.putInt(KEY_VIDEO_POSITION, mVideoPosition);
- super.onSaveInstanceState(savedInstanceState);
- }
-
- @Override
- public void onRestoreInstanceState(Bundle savedInstanceState) {
- super.onRestoreInstanceState(savedInstanceState);
- mTrimStartTime = savedInstanceState.getInt(KEY_TRIM_START, 0);
- mTrimEndTime = savedInstanceState.getInt(KEY_TRIM_END, 0);
- mVideoPosition = savedInstanceState.getInt(KEY_VIDEO_POSITION, 0);
- }
-
- // This updates the time bar display (if necessary). It is called by
- // mProgressChecker and also from places where the time bar needs
- // to be updated immediately.
- private int setProgress() {
- mVideoPosition = mVideoView.getCurrentPosition();
- // If the video position is smaller than the starting point of trimming,
- // correct it.
- if (mVideoPosition < mTrimStartTime) {
- mVideoView.seekTo(mTrimStartTime);
- mVideoPosition = mTrimStartTime;
- }
- // If the position is bigger than the end point of trimming, show the
- // replay button and pause.
- if (mVideoPosition >= mTrimEndTime && mTrimEndTime > 0) {
- if (mVideoPosition > mTrimEndTime) {
- mVideoView.seekTo(mTrimEndTime);
- mVideoPosition = mTrimEndTime;
- }
- mController.showEnded();
- mVideoView.pause();
- }
-
- int duration = mVideoView.getDuration();
- if (duration > 0 && mTrimEndTime == 0) {
- mTrimEndTime = duration;
- }
- mController.setTimes(mVideoPosition, duration, mTrimStartTime, mTrimEndTime);
- return mVideoPosition;
- }
-
- private void playVideo() {
- mVideoView.start();
- mController.showPlaying();
- setProgress();
- }
-
- private void pauseVideo() {
- mVideoView.pause();
- mController.showPaused();
- }
-
-
- private boolean isModified() {
- int delta = mTrimEndTime - mTrimStartTime;
-
- // Considering that we only trim at sync frame, we don't want to trim
- // when the time interval is too short or too close to the origin.
- if (delta < 100 || Math.abs(mVideoView.getDuration() - delta) < 100) {
- return false;
- } else {
- return true;
- }
- }
-
- private void trimVideo() {
-
- mDstFileInfo = SaveVideoFileUtils.getDstMp4FileInfo(TIME_STAMP_NAME,
- getContentResolver(), mUri, getString(R.string.folder_download));
- final File mSrcFile = new File(mSrcVideoPath);
-
- showProgressDialog();
-
- new Thread(new Runnable() {
- @Override
- public void run() {
- try {
- VideoUtils.startTrim(mSrcFile, mDstFileInfo.mFile,
- mTrimStartTime, mTrimEndTime);
- // Update the database for adding a new video file.
- SaveVideoFileUtils.insertContent(mDstFileInfo,
- getContentResolver(), mUri);
- } catch (IOException e) {
- e.printStackTrace();
- }
- // After trimming is done, trigger the UI changed.
- mHandler.post(new Runnable() {
- @Override
- public void run() {
- Toast.makeText(getApplicationContext(),
- getString(R.string.save_into, mDstFileInfo.mFolderName),
- Toast.LENGTH_SHORT)
- .show();
- // TODO: change trimming into a service to avoid
- // this progressDialog and add notification properly.
- if (mProgress != null) {
- mProgress.dismiss();
- mProgress = null;
- // Show the result only when the activity not stopped.
- Intent intent = new Intent(android.content.Intent.ACTION_VIEW);
- intent.setDataAndType(Uri.fromFile(mDstFileInfo.mFile), "video/*");
- intent.putExtra(MediaStore.EXTRA_FINISH_ON_COMPLETION, false);
- startActivity(intent);
- finish();
- }
- }
- });
- }
- }).start();
- }
-
- private void showProgressDialog() {
- // create a background thread to trim the video.
- // and show the progress.
- mProgress = new ProgressDialog(this);
- mProgress.setTitle(getString(R.string.trimming));
- mProgress.setMessage(getString(R.string.please_wait));
- // TODO: make this cancelable.
- mProgress.setCancelable(false);
- mProgress.setCanceledOnTouchOutside(false);
- mProgress.show();
- }
-
- @Override
- public void onPlayPause() {
- if (mVideoView.isPlaying()) {
- pauseVideo();
- } else {
- playVideo();
- }
- }
-
- @Override
- public void onSeekStart() {
- pauseVideo();
- }
-
- @Override
- public void onSeekMove(int time) {
- mVideoView.seekTo(time);
- }
-
- @Override
- public void onSeekEnd(int time, int start, int end) {
- mVideoView.seekTo(time);
- mTrimStartTime = start;
- mTrimEndTime = end;
- setProgress();
- // Enable save if there's modifications
- mSaveVideoTextView.setEnabled(isModified());
- }
-
- @Override
- public void onShown() {
- }
-
- @Override
- public void onHidden() {
- }
-
- @Override
- public void onReplay() {
- mVideoView.seekTo(mTrimStartTime);
- playVideo();
- }
-
- @Override
- public void onCompletion(MediaPlayer mp) {
- mController.showEnded();
- }
-
- @Override
- public boolean onError(MediaPlayer mp, int what, int extra) {
- return false;
- }
-}
diff --git a/src/com/android/gallery3d/app/VideoUtils.java b/src/com/android/gallery3d/app/VideoUtils.java
deleted file mode 100644
index a3c3ef273..000000000
--- a/src/com/android/gallery3d/app/VideoUtils.java
+++ /dev/null
@@ -1,328 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Modified example based on mp4parser google code open source project.
-// http://code.google.com/p/mp4parser/source/browse/trunk/examples/src/main/java/com/googlecode/mp4parser/ShortenExample.java
-
-package com.android.gallery3d.app;
-
-import android.media.MediaCodec.BufferInfo;
-import android.media.MediaExtractor;
-import android.media.MediaFormat;
-import android.media.MediaMetadataRetriever;
-import android.media.MediaMuxer;
-import android.util.Log;
-
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.util.SaveVideoFileInfo;
-import com.coremedia.iso.IsoFile;
-import com.coremedia.iso.boxes.TimeToSampleBox;
-import com.googlecode.mp4parser.authoring.Movie;
-import com.googlecode.mp4parser.authoring.Track;
-import com.googlecode.mp4parser.authoring.builder.DefaultMp4Builder;
-import com.googlecode.mp4parser.authoring.container.mp4.MovieCreator;
-import com.googlecode.mp4parser.authoring.tracks.CroppedTrack;
-
-import java.io.File;
-import java.io.FileNotFoundException;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.RandomAccessFile;
-import java.nio.ByteBuffer;
-import java.nio.channels.FileChannel;
-import java.util.Arrays;
-import java.util.HashMap;
-import java.util.LinkedList;
-import java.util.List;
-
-public class VideoUtils {
- private static final String LOGTAG = "VideoUtils";
- private static final int DEFAULT_BUFFER_SIZE = 1 * 1024 * 1024;
-
- /**
- * Remove the sound track.
- */
- public static void startMute(String filePath, SaveVideoFileInfo dstFileInfo)
- throws IOException {
- if (ApiHelper.HAS_MEDIA_MUXER) {
- genVideoUsingMuxer(filePath, dstFileInfo.mFile.getPath(), -1, -1,
- false, true);
- } else {
- startMuteUsingMp4Parser(filePath, dstFileInfo);
- }
- }
-
- /**
- * Shortens/Crops tracks
- */
- public static void startTrim(File src, File dst, int startMs, int endMs)
- throws IOException {
- if (ApiHelper.HAS_MEDIA_MUXER) {
- genVideoUsingMuxer(src.getPath(), dst.getPath(), startMs, endMs,
- true, true);
- } else {
- trimUsingMp4Parser(src, dst, startMs, endMs);
- }
- }
-
- private static void startMuteUsingMp4Parser(String filePath,
- SaveVideoFileInfo dstFileInfo) throws FileNotFoundException, IOException {
- File dst = dstFileInfo.mFile;
- File src = new File(filePath);
- RandomAccessFile randomAccessFile = new RandomAccessFile(src, "r");
- Movie movie = MovieCreator.build(randomAccessFile.getChannel());
-
- // remove all tracks we will create new tracks from the old
- List<Track> tracks = movie.getTracks();
- movie.setTracks(new LinkedList<Track>());
-
- for (Track track : tracks) {
- if (track.getHandler().equals("vide")) {
- movie.addTrack(track);
- }
- }
- writeMovieIntoFile(dst, movie);
- randomAccessFile.close();
- }
-
- private static void writeMovieIntoFile(File dst, Movie movie)
- throws IOException {
- if (!dst.exists()) {
- dst.createNewFile();
- }
-
- IsoFile out = new DefaultMp4Builder().build(movie);
- FileOutputStream fos = new FileOutputStream(dst);
- FileChannel fc = fos.getChannel();
- out.getBox(fc); // This one build up the memory.
-
- fc.close();
- fos.close();
- }
-
- /**
- * @param srcPath the path of source video file.
- * @param dstPath the path of destination video file.
- * @param startMs starting time in milliseconds for trimming. Set to
- * negative if starting from beginning.
- * @param endMs end time for trimming in milliseconds. Set to negative if
- * no trimming at the end.
- * @param useAudio true if keep the audio track from the source.
- * @param useVideo true if keep the video track from the source.
- * @throws IOException
- */
- private static void genVideoUsingMuxer(String srcPath, String dstPath,
- int startMs, int endMs, boolean useAudio, boolean useVideo)
- throws IOException {
- // Set up MediaExtractor to read from the source.
- MediaExtractor extractor = new MediaExtractor();
- extractor.setDataSource(srcPath);
-
- int trackCount = extractor.getTrackCount();
-
- // Set up MediaMuxer for the destination.
- MediaMuxer muxer;
- muxer = new MediaMuxer(dstPath, MediaMuxer.OutputFormat.MUXER_OUTPUT_MPEG_4);
-
- // Set up the tracks and retrieve the max buffer size for selected
- // tracks.
- HashMap<Integer, Integer> indexMap = new HashMap<Integer,
- Integer>(trackCount);
- int bufferSize = -1;
- for (int i = 0; i < trackCount; i++) {
- MediaFormat format = extractor.getTrackFormat(i);
- String mime = format.getString(MediaFormat.KEY_MIME);
-
- boolean selectCurrentTrack = false;
-
- if (mime.startsWith("audio/") && useAudio) {
- selectCurrentTrack = true;
- } else if (mime.startsWith("video/") && useVideo) {
- selectCurrentTrack = true;
- }
-
- if (selectCurrentTrack) {
- extractor.selectTrack(i);
- int dstIndex = muxer.addTrack(format);
- indexMap.put(i, dstIndex);
- if (format.containsKey(MediaFormat.KEY_MAX_INPUT_SIZE)) {
- int newSize = format.getInteger(MediaFormat.KEY_MAX_INPUT_SIZE);
- bufferSize = newSize > bufferSize ? newSize : bufferSize;
- }
- }
- }
-
- if (bufferSize < 0) {
- bufferSize = DEFAULT_BUFFER_SIZE;
- }
-
- // Set up the orientation and starting time for extractor.
- MediaMetadataRetriever retrieverSrc = new MediaMetadataRetriever();
- retrieverSrc.setDataSource(srcPath);
- String degreesString = retrieverSrc.extractMetadata(
- MediaMetadataRetriever.METADATA_KEY_VIDEO_ROTATION);
- if (degreesString != null) {
- int degrees = Integer.parseInt(degreesString);
- if (degrees >= 0) {
- muxer.setOrientationHint(degrees);
- }
- }
-
- if (startMs > 0) {
- extractor.seekTo(startMs * 1000, MediaExtractor.SEEK_TO_CLOSEST_SYNC);
- }
-
- // Copy the samples from MediaExtractor to MediaMuxer. We will loop
- // for copying each sample and stop when we get to the end of the source
- // file or exceed the end time of the trimming.
- int offset = 0;
- int trackIndex = -1;
- ByteBuffer dstBuf = ByteBuffer.allocate(bufferSize);
- BufferInfo bufferInfo = new BufferInfo();
-
- muxer.start();
- while (true) {
- bufferInfo.offset = offset;
- bufferInfo.size = extractor.readSampleData(dstBuf, offset);
- if (bufferInfo.size < 0) {
- Log.d(LOGTAG, "Saw input EOS.");
- bufferInfo.size = 0;
- break;
- } else {
- bufferInfo.presentationTimeUs = extractor.getSampleTime();
- if (endMs > 0 && bufferInfo.presentationTimeUs > (endMs * 1000)) {
- Log.d(LOGTAG, "The current sample is over the trim end time.");
- break;
- } else {
- bufferInfo.flags = extractor.getSampleFlags();
- trackIndex = extractor.getSampleTrackIndex();
-
- muxer.writeSampleData(indexMap.get(trackIndex), dstBuf,
- bufferInfo);
- extractor.advance();
- }
- }
- }
-
- muxer.stop();
- muxer.release();
- return;
- }
-
- private static void trimUsingMp4Parser(File src, File dst, int startMs, int endMs)
- throws FileNotFoundException, IOException {
- RandomAccessFile randomAccessFile = new RandomAccessFile(src, "r");
- Movie movie = MovieCreator.build(randomAccessFile.getChannel());
-
- // remove all tracks we will create new tracks from the old
- List<Track> tracks = movie.getTracks();
- movie.setTracks(new LinkedList<Track>());
-
- double startTime = startMs / 1000;
- double endTime = endMs / 1000;
-
- boolean timeCorrected = false;
-
- // Here we try to find a track that has sync samples. Since we can only
- // start decoding at such a sample we SHOULD make sure that the start of
- // the new fragment is exactly such a frame.
- for (Track track : tracks) {
- if (track.getSyncSamples() != null && track.getSyncSamples().length > 0) {
- if (timeCorrected) {
- // This exception here could be a false positive in case we
- // have multiple tracks with sync samples at exactly the
- // same positions. E.g. a single movie containing multiple
- // qualities of the same video (Microsoft Smooth Streaming
- // file)
- throw new RuntimeException(
- "The startTime has already been corrected by" +
- " another track with SyncSample. Not Supported.");
- }
- startTime = correctTimeToSyncSample(track, startTime, false);
- endTime = correctTimeToSyncSample(track, endTime, true);
- timeCorrected = true;
- }
- }
-
- for (Track track : tracks) {
- long currentSample = 0;
- double currentTime = 0;
- long startSample = -1;
- long endSample = -1;
-
- for (int i = 0; i < track.getDecodingTimeEntries().size(); i++) {
- TimeToSampleBox.Entry entry = track.getDecodingTimeEntries().get(i);
- for (int j = 0; j < entry.getCount(); j++) {
- // entry.getDelta() is the amount of time the current sample
- // covers.
-
- if (currentTime <= startTime) {
- // current sample is still before the new starttime
- startSample = currentSample;
- }
- if (currentTime <= endTime) {
- // current sample is after the new start time and still
- // before the new endtime
- endSample = currentSample;
- } else {
- // current sample is after the end of the cropped video
- break;
- }
- currentTime += (double) entry.getDelta()
- / (double) track.getTrackMetaData().getTimescale();
- currentSample++;
- }
- }
- movie.addTrack(new CroppedTrack(track, startSample, endSample));
- }
- writeMovieIntoFile(dst, movie);
- randomAccessFile.close();
- }
-
- private static double correctTimeToSyncSample(Track track, double cutHere,
- boolean next) {
- double[] timeOfSyncSamples = new double[track.getSyncSamples().length];
- long currentSample = 0;
- double currentTime = 0;
- for (int i = 0; i < track.getDecodingTimeEntries().size(); i++) {
- TimeToSampleBox.Entry entry = track.getDecodingTimeEntries().get(i);
- for (int j = 0; j < entry.getCount(); j++) {
- if (Arrays.binarySearch(track.getSyncSamples(), currentSample + 1) >= 0) {
- // samples always start with 1 but we start with zero
- // therefore +1
- timeOfSyncSamples[Arrays.binarySearch(
- track.getSyncSamples(), currentSample + 1)] = currentTime;
- }
- currentTime += (double) entry.getDelta()
- / (double) track.getTrackMetaData().getTimescale();
- currentSample++;
- }
- }
- double previous = 0;
- for (double timeOfSyncSample : timeOfSyncSamples) {
- if (timeOfSyncSample > cutHere) {
- if (next) {
- return timeOfSyncSample;
- } else {
- return previous;
- }
- }
- previous = timeOfSyncSample;
- }
- return timeOfSyncSamples[timeOfSyncSamples.length - 1];
- }
-
-}
diff --git a/src/com/android/gallery3d/app/Wallpaper.java b/src/com/android/gallery3d/app/Wallpaper.java
deleted file mode 100644
index b0a26c236..000000000
--- a/src/com/android/gallery3d/app/Wallpaper.java
+++ /dev/null
@@ -1,135 +0,0 @@
-/*
- * Copyright (C) 2007 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.app;
-
-import android.annotation.TargetApi;
-import android.app.Activity;
-import android.content.Intent;
-import android.graphics.Point;
-import android.net.Uri;
-import android.os.Build;
-import android.os.Bundle;
-import android.view.Display;
-
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.filtershow.crop.CropActivity;
-import com.android.gallery3d.filtershow.crop.CropExtras;
-
-/**
- * Wallpaper picker for the gallery application. This just redirects to the
- * standard pick action.
- */
-public class Wallpaper extends Activity {
- @SuppressWarnings("unused")
- private static final String TAG = "Wallpaper";
-
- private static final String IMAGE_TYPE = "image/*";
- private static final String KEY_STATE = "activity-state";
- private static final String KEY_PICKED_ITEM = "picked-item";
-
- private static final int STATE_INIT = 0;
- private static final int STATE_PHOTO_PICKED = 1;
-
- private int mState = STATE_INIT;
- private Uri mPickedItem;
-
- @Override
- protected void onCreate(Bundle bundle) {
- super.onCreate(bundle);
- if (bundle != null) {
- mState = bundle.getInt(KEY_STATE);
- mPickedItem = (Uri) bundle.getParcelable(KEY_PICKED_ITEM);
- }
- }
-
- @Override
- protected void onSaveInstanceState(Bundle saveState) {
- saveState.putInt(KEY_STATE, mState);
- if (mPickedItem != null) {
- saveState.putParcelable(KEY_PICKED_ITEM, mPickedItem);
- }
- }
-
- @SuppressWarnings("deprecation")
- @TargetApi(Build.VERSION_CODES.HONEYCOMB_MR2)
- private Point getDefaultDisplaySize(Point size) {
- Display d = getWindowManager().getDefaultDisplay();
- if (Build.VERSION.SDK_INT >= ApiHelper.VERSION_CODES.HONEYCOMB_MR2) {
- d.getSize(size);
- } else {
- size.set(d.getWidth(), d.getHeight());
- }
- return size;
- }
-
- @SuppressWarnings("fallthrough")
- @Override
- protected void onResume() {
- super.onResume();
- Intent intent = getIntent();
- switch (mState) {
- case STATE_INIT: {
- mPickedItem = intent.getData();
- if (mPickedItem == null) {
- Intent request = new Intent(Intent.ACTION_GET_CONTENT)
- .setClass(this, DialogPicker.class)
- .setType(IMAGE_TYPE);
- startActivityForResult(request, STATE_PHOTO_PICKED);
- return;
- }
- mState = STATE_PHOTO_PICKED;
- // fall-through
- }
- case STATE_PHOTO_PICKED: {
- int width = getWallpaperDesiredMinimumWidth();
- int height = getWallpaperDesiredMinimumHeight();
- Point size = getDefaultDisplaySize(new Point());
- float spotlightX = (float) size.x / width;
- float spotlightY = (float) size.y / height;
- Intent request = new Intent(CropActivity.CROP_ACTION)
- .setDataAndType(mPickedItem, IMAGE_TYPE)
- .addFlags(Intent.FLAG_ACTIVITY_FORWARD_RESULT)
- .putExtra(CropExtras.KEY_OUTPUT_X, width)
- .putExtra(CropExtras.KEY_OUTPUT_Y, height)
- .putExtra(CropExtras.KEY_ASPECT_X, width)
- .putExtra(CropExtras.KEY_ASPECT_Y, height)
- .putExtra(CropExtras.KEY_SPOTLIGHT_X, spotlightX)
- .putExtra(CropExtras.KEY_SPOTLIGHT_Y, spotlightY)
- .putExtra(CropExtras.KEY_SCALE, true)
- .putExtra(CropExtras.KEY_SCALE_UP_IF_NEEDED, true)
- .putExtra(CropExtras.KEY_SET_AS_WALLPAPER, true);
- startActivity(request);
- finish();
- }
- }
- }
-
- @Override
- protected void onActivityResult(int requestCode, int resultCode, Intent data) {
- if (resultCode != RESULT_OK) {
- setResult(resultCode);
- finish();
- return;
- }
- mState = requestCode;
- if (mState == STATE_PHOTO_PICKED) {
- mPickedItem = data.getData();
- }
-
- // onResume() would be called next
- }
-}
diff --git a/src/com/android/gallery3d/data/ActionImage.java b/src/com/android/gallery3d/data/ActionImage.java
deleted file mode 100644
index 58e30b146..000000000
--- a/src/com/android/gallery3d/data/ActionImage.java
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.BitmapRegionDecoder;
-import android.net.Uri;
-
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.common.BitmapUtils;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-public class ActionImage extends MediaItem {
- @SuppressWarnings("unused")
- private static final String TAG = "ActionImage";
- private GalleryApp mApplication;
- private int mResourceId;
-
- public ActionImage(Path path, GalleryApp application, int resourceId) {
- super(path, nextVersionNumber());
- mApplication = Utils.checkNotNull(application);
- mResourceId = resourceId;
- }
-
- @Override
- public Job<Bitmap> requestImage(int type) {
- return new BitmapJob(type);
- }
-
- @Override
- public Job<BitmapRegionDecoder> requestLargeImage() {
- return null;
- }
-
- private class BitmapJob implements Job<Bitmap> {
- private int mType;
-
- protected BitmapJob(int type) {
- mType = type;
- }
-
- @Override
- public Bitmap run(JobContext jc) {
- int targetSize = MediaItem.getTargetSize(mType);
- Bitmap bitmap = BitmapFactory.decodeResource(mApplication.getResources(),
- mResourceId);
-
- if (mType == MediaItem.TYPE_MICROTHUMBNAIL) {
- bitmap = BitmapUtils.resizeAndCropCenter(bitmap, targetSize, true);
- } else {
- bitmap = BitmapUtils.resizeDownBySideLength(bitmap, targetSize, true);
- }
- return bitmap;
- }
- }
-
- @Override
- public int getSupportedOperations() {
- return SUPPORT_ACTION;
- }
-
- @Override
- public int getMediaType() {
- return MEDIA_TYPE_UNKNOWN;
- }
-
- @Override
- public Uri getContentUri() {
- return null;
- }
-
- @Override
- public String getMimeType() {
- return "";
- }
-
- @Override
- public int getWidth() {
- return 0;
- }
-
- @Override
- public int getHeight() {
- return 0;
- }
-}
diff --git a/src/com/android/gallery3d/data/BucketHelper.java b/src/com/android/gallery3d/data/BucketHelper.java
deleted file mode 100644
index 3418dafb7..000000000
--- a/src/com/android/gallery3d/data/BucketHelper.java
+++ /dev/null
@@ -1,241 +0,0 @@
-package com.android.gallery3d.data;
-
-import android.annotation.TargetApi;
-import android.content.ContentResolver;
-import android.database.Cursor;
-import android.net.Uri;
-import android.provider.MediaStore.Files;
-import android.provider.MediaStore.Files.FileColumns;
-import android.provider.MediaStore.Images;
-import android.provider.MediaStore.Images.ImageColumns;
-import android.provider.MediaStore.Video;
-import android.util.Log;
-
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Comparator;
-import java.util.HashMap;
-
-class BucketHelper {
-
- private static final String TAG = "BucketHelper";
- private static final String EXTERNAL_MEDIA = "external";
-
- // BUCKET_DISPLAY_NAME is a string like "Camera" which is the directory
- // name of where an image or video is in. BUCKET_ID is a hash of the path
- // name of that directory (see computeBucketValues() in MediaProvider for
- // details). MEDIA_TYPE is video, image, audio, etc.
- //
- // The "albums" are not explicitly recorded in the database, but each image
- // or video has the two columns (BUCKET_ID, MEDIA_TYPE). We define an
- // "album" to be the collection of images/videos which have the same value
- // for the two columns.
- //
- // The goal of the query (used in loadSubMediaSetsFromFilesTable()) is to
- // find all albums, that is, all unique values for (BUCKET_ID, MEDIA_TYPE).
- // In the meantime sort them by the timestamp of the latest image/video in
- // each of the album.
- //
- // The order of columns below is important: it must match to the index in
- // MediaStore.
- private static final String[] PROJECTION_BUCKET = {
- ImageColumns.BUCKET_ID,
- FileColumns.MEDIA_TYPE,
- ImageColumns.BUCKET_DISPLAY_NAME};
-
- // The indices should match the above projections.
- private static final int INDEX_BUCKET_ID = 0;
- private static final int INDEX_MEDIA_TYPE = 1;
- private static final int INDEX_BUCKET_NAME = 2;
-
- // We want to order the albums by reverse chronological order. We abuse the
- // "WHERE" parameter to insert a "GROUP BY" clause into the SQL statement.
- // The template for "WHERE" parameter is like:
- // SELECT ... FROM ... WHERE (%s)
- // and we make it look like:
- // SELECT ... FROM ... WHERE (1) GROUP BY 1,(2)
- // The "(1)" means true. The "1,(2)" means the first two columns specified
- // after SELECT. Note that because there is a ")" in the template, we use
- // "(2" to match it.
- private static final String BUCKET_GROUP_BY = "1) GROUP BY 1,(2";
-
- private static final String BUCKET_ORDER_BY = "MAX(datetaken) DESC";
-
- // Before HoneyComb there is no Files table. Thus, we need to query the
- // bucket info from the Images and Video tables and then merge them
- // together.
- //
- // A bucket can exist in both tables. In this case, we need to find the
- // latest timestamp from the two tables and sort ourselves. So we add the
- // MAX(date_taken) to the projection and remove the media_type since we
- // already know the media type from the table we query from.
- private static final String[] PROJECTION_BUCKET_IN_ONE_TABLE = {
- ImageColumns.BUCKET_ID,
- "MAX(datetaken)",
- ImageColumns.BUCKET_DISPLAY_NAME};
-
- // We keep the INDEX_BUCKET_ID and INDEX_BUCKET_NAME the same as
- // PROJECTION_BUCKET so we can reuse the values defined before.
- private static final int INDEX_DATE_TAKEN = 1;
-
- // When query from the Images or Video tables, we only need to group by BUCKET_ID.
- private static final String BUCKET_GROUP_BY_IN_ONE_TABLE = "1) GROUP BY (1";
-
- public static BucketEntry[] loadBucketEntries(
- JobContext jc, ContentResolver resolver, int type) {
- if (ApiHelper.HAS_MEDIA_PROVIDER_FILES_TABLE) {
- return loadBucketEntriesFromFilesTable(jc, resolver, type);
- } else {
- return loadBucketEntriesFromImagesAndVideoTable(jc, resolver, type);
- }
- }
-
- private static void updateBucketEntriesFromTable(JobContext jc,
- ContentResolver resolver, Uri tableUri, HashMap<Integer, BucketEntry> buckets) {
- Cursor cursor = resolver.query(tableUri, PROJECTION_BUCKET_IN_ONE_TABLE,
- BUCKET_GROUP_BY_IN_ONE_TABLE, null, null);
- if (cursor == null) {
- Log.w(TAG, "cannot open media database: " + tableUri);
- return;
- }
- try {
- while (cursor.moveToNext()) {
- int bucketId = cursor.getInt(INDEX_BUCKET_ID);
- int dateTaken = cursor.getInt(INDEX_DATE_TAKEN);
- BucketEntry entry = buckets.get(bucketId);
- if (entry == null) {
- entry = new BucketEntry(bucketId, cursor.getString(INDEX_BUCKET_NAME));
- buckets.put(bucketId, entry);
- entry.dateTaken = dateTaken;
- } else {
- entry.dateTaken = Math.max(entry.dateTaken, dateTaken);
- }
- }
- } finally {
- Utils.closeSilently(cursor);
- }
- }
-
- private static BucketEntry[] loadBucketEntriesFromImagesAndVideoTable(
- JobContext jc, ContentResolver resolver, int type) {
- HashMap<Integer, BucketEntry> buckets = new HashMap<Integer, BucketEntry>(64);
- if ((type & MediaObject.MEDIA_TYPE_IMAGE) != 0) {
- updateBucketEntriesFromTable(
- jc, resolver, Images.Media.EXTERNAL_CONTENT_URI, buckets);
- }
- if ((type & MediaObject.MEDIA_TYPE_VIDEO) != 0) {
- updateBucketEntriesFromTable(
- jc, resolver, Video.Media.EXTERNAL_CONTENT_URI, buckets);
- }
- BucketEntry[] entries = buckets.values().toArray(new BucketEntry[buckets.size()]);
- Arrays.sort(entries, new Comparator<BucketEntry>() {
- @Override
- public int compare(BucketEntry a, BucketEntry b) {
- // sorted by dateTaken in descending order
- return b.dateTaken - a.dateTaken;
- }
- });
- return entries;
- }
-
- private static BucketEntry[] loadBucketEntriesFromFilesTable(
- JobContext jc, ContentResolver resolver, int type) {
- Uri uri = getFilesContentUri();
-
- Cursor cursor = resolver.query(uri,
- PROJECTION_BUCKET, BUCKET_GROUP_BY,
- null, BUCKET_ORDER_BY);
- if (cursor == null) {
- Log.w(TAG, "cannot open local database: " + uri);
- return new BucketEntry[0];
- }
- ArrayList<BucketEntry> buffer = new ArrayList<BucketEntry>();
- int typeBits = 0;
- if ((type & MediaObject.MEDIA_TYPE_IMAGE) != 0) {
- typeBits |= (1 << FileColumns.MEDIA_TYPE_IMAGE);
- }
- if ((type & MediaObject.MEDIA_TYPE_VIDEO) != 0) {
- typeBits |= (1 << FileColumns.MEDIA_TYPE_VIDEO);
- }
- try {
- while (cursor.moveToNext()) {
- if ((typeBits & (1 << cursor.getInt(INDEX_MEDIA_TYPE))) != 0) {
- BucketEntry entry = new BucketEntry(
- cursor.getInt(INDEX_BUCKET_ID),
- cursor.getString(INDEX_BUCKET_NAME));
- if (!buffer.contains(entry)) {
- buffer.add(entry);
- }
- }
- if (jc.isCancelled()) return null;
- }
- } finally {
- Utils.closeSilently(cursor);
- }
- return buffer.toArray(new BucketEntry[buffer.size()]);
- }
-
- private static String getBucketNameInTable(
- ContentResolver resolver, Uri tableUri, int bucketId) {
- String selectionArgs[] = new String[] {String.valueOf(bucketId)};
- Uri uri = tableUri.buildUpon()
- .appendQueryParameter("limit", "1")
- .build();
- Cursor cursor = resolver.query(uri, PROJECTION_BUCKET_IN_ONE_TABLE,
- "bucket_id = ?", selectionArgs, null);
- try {
- if (cursor != null && cursor.moveToNext()) {
- return cursor.getString(INDEX_BUCKET_NAME);
- }
- } finally {
- Utils.closeSilently(cursor);
- }
- return null;
- }
-
- @TargetApi(ApiHelper.VERSION_CODES.HONEYCOMB)
- private static Uri getFilesContentUri() {
- return Files.getContentUri(EXTERNAL_MEDIA);
- }
-
- public static String getBucketName(ContentResolver resolver, int bucketId) {
- if (ApiHelper.HAS_MEDIA_PROVIDER_FILES_TABLE) {
- String result = getBucketNameInTable(resolver, getFilesContentUri(), bucketId);
- return result == null ? "" : result;
- } else {
- String result = getBucketNameInTable(
- resolver, Images.Media.EXTERNAL_CONTENT_URI, bucketId);
- if (result != null) return result;
- result = getBucketNameInTable(
- resolver, Video.Media.EXTERNAL_CONTENT_URI, bucketId);
- return result == null ? "" : result;
- }
- }
-
- public static class BucketEntry {
- public String bucketName;
- public int bucketId;
- public int dateTaken;
-
- public BucketEntry(int id, String name) {
- bucketId = id;
- bucketName = Utils.ensureNotNull(name);
- }
-
- @Override
- public int hashCode() {
- return bucketId;
- }
-
- @Override
- public boolean equals(Object object) {
- if (!(object instanceof BucketEntry)) return false;
- BucketEntry entry = (BucketEntry) object;
- return bucketId == entry.bucketId;
- }
- }
-}
diff --git a/src/com/android/gallery3d/data/BytesBufferPool.java b/src/com/android/gallery3d/data/BytesBufferPool.java
deleted file mode 100644
index d2da323fc..000000000
--- a/src/com/android/gallery3d/data/BytesBufferPool.java
+++ /dev/null
@@ -1,91 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.io.FileDescriptor;
-import java.io.FileInputStream;
-import java.io.IOException;
-import java.util.ArrayList;
-
-public class BytesBufferPool {
-
- private static final int READ_STEP = 4096;
-
- public static class BytesBuffer {
- public byte[] data;
- public int offset;
- public int length;
-
- private BytesBuffer(int capacity) {
- this.data = new byte[capacity];
- }
-
- // an helper function to read content from FileDescriptor
- public void readFrom(JobContext jc, FileDescriptor fd) throws IOException {
- FileInputStream fis = new FileInputStream(fd);
- length = 0;
- try {
- int capacity = data.length;
- while (true) {
- int step = Math.min(READ_STEP, capacity - length);
- int rc = fis.read(data, length, step);
- if (rc < 0 || jc.isCancelled()) return;
- length += rc;
-
- if (length == capacity) {
- byte[] newData = new byte[data.length * 2];
- System.arraycopy(data, 0, newData, 0, data.length);
- data = newData;
- capacity = data.length;
- }
- }
- } finally {
- fis.close();
- }
- }
- }
-
- private final int mPoolSize;
- private final int mBufferSize;
- private final ArrayList<BytesBuffer> mList;
-
- public BytesBufferPool(int poolSize, int bufferSize) {
- mList = new ArrayList<BytesBuffer>(poolSize);
- mPoolSize = poolSize;
- mBufferSize = bufferSize;
- }
-
- public synchronized BytesBuffer get() {
- int n = mList.size();
- return n > 0 ? mList.remove(n - 1) : new BytesBuffer(mBufferSize);
- }
-
- public synchronized void recycle(BytesBuffer buffer) {
- if (buffer.data.length != mBufferSize) return;
- if (mList.size() < mPoolSize) {
- buffer.offset = 0;
- buffer.length = 0;
- mList.add(buffer);
- }
- }
-
- public synchronized void clear() {
- mList.clear();
- }
-}
diff --git a/src/com/android/gallery3d/data/CameraShortcutImage.java b/src/com/android/gallery3d/data/CameraShortcutImage.java
deleted file mode 100644
index 865270b4c..000000000
--- a/src/com/android/gallery3d/data/CameraShortcutImage.java
+++ /dev/null
@@ -1,34 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.GalleryApp;
-
-public class CameraShortcutImage extends ActionImage {
- @SuppressWarnings("unused")
- private static final String TAG = "CameraShortcutImage";
-
- public CameraShortcutImage(Path path, GalleryApp application) {
- super(path, application, R.drawable.placeholder_camera);
- }
-
- @Override
- public int getSupportedOperations() {
- return super.getSupportedOperations() | SUPPORT_CAMERA_SHORTCUT;
- }
-}
diff --git a/src/com/android/gallery3d/data/ChangeNotifier.java b/src/com/android/gallery3d/data/ChangeNotifier.java
deleted file mode 100644
index 558a8648e..000000000
--- a/src/com/android/gallery3d/data/ChangeNotifier.java
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.net.Uri;
-
-import com.android.gallery3d.app.GalleryApp;
-
-import java.util.concurrent.atomic.AtomicBoolean;
-
-// This handles change notification for media sets.
-public class ChangeNotifier {
-
- private MediaSet mMediaSet;
- private AtomicBoolean mContentDirty = new AtomicBoolean(true);
-
- public ChangeNotifier(MediaSet set, Uri uri, GalleryApp application) {
- mMediaSet = set;
- application.getDataManager().registerChangeNotifier(uri, this);
- }
-
- public ChangeNotifier(MediaSet set, Uri[] uris, GalleryApp application) {
- mMediaSet = set;
- for (int i = 0; i < uris.length; i++) {
- application.getDataManager().registerChangeNotifier(uris[i], this);
- }
- }
-
- // Returns the dirty flag and clear it.
- public boolean isDirty() {
- return mContentDirty.compareAndSet(true, false);
- }
-
- public void fakeChange() {
- onChange(false);
- }
-
- protected void onChange(boolean selfChange) {
- if (mContentDirty.compareAndSet(false, true)) {
- mMediaSet.notifyContentChanged();
- }
- }
-} \ No newline at end of file
diff --git a/src/com/android/gallery3d/data/ClusterAlbum.java b/src/com/android/gallery3d/data/ClusterAlbum.java
deleted file mode 100644
index 8681952bf..000000000
--- a/src/com/android/gallery3d/data/ClusterAlbum.java
+++ /dev/null
@@ -1,143 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import java.util.ArrayList;
-
-public class ClusterAlbum extends MediaSet implements ContentListener {
- @SuppressWarnings("unused")
- private static final String TAG = "ClusterAlbum";
- private ArrayList<Path> mPaths = new ArrayList<Path>();
- private String mName = "";
- private DataManager mDataManager;
- private MediaSet mClusterAlbumSet;
- private MediaItem mCover;
-
- public ClusterAlbum(Path path, DataManager dataManager,
- MediaSet clusterAlbumSet) {
- super(path, nextVersionNumber());
- mDataManager = dataManager;
- mClusterAlbumSet = clusterAlbumSet;
- mClusterAlbumSet.addContentListener(this);
- }
-
- public void setCoverMediaItem(MediaItem cover) {
- mCover = cover;
- }
-
- @Override
- public MediaItem getCoverMediaItem() {
- return mCover != null ? mCover : super.getCoverMediaItem();
- }
-
- void setMediaItems(ArrayList<Path> paths) {
- mPaths = paths;
- }
-
- ArrayList<Path> getMediaItems() {
- return mPaths;
- }
-
- public void setName(String name) {
- mName = name;
- }
-
- @Override
- public String getName() {
- return mName;
- }
-
- @Override
- public int getMediaItemCount() {
- return mPaths.size();
- }
-
- @Override
- public ArrayList<MediaItem> getMediaItem(int start, int count) {
- return getMediaItemFromPath(mPaths, start, count, mDataManager);
- }
-
- public static ArrayList<MediaItem> getMediaItemFromPath(
- ArrayList<Path> paths, int start, int count,
- DataManager dataManager) {
- if (start >= paths.size()) {
- return new ArrayList<MediaItem>();
- }
- int end = Math.min(start + count, paths.size());
- ArrayList<Path> subset = new ArrayList<Path>(paths.subList(start, end));
- final MediaItem[] buf = new MediaItem[end - start];
- ItemConsumer consumer = new ItemConsumer() {
- @Override
- public void consume(int index, MediaItem item) {
- buf[index] = item;
- }
- };
- dataManager.mapMediaItems(subset, consumer, 0);
- ArrayList<MediaItem> result = new ArrayList<MediaItem>(end - start);
- for (int i = 0; i < buf.length; i++) {
- result.add(buf[i]);
- }
- return result;
- }
-
- @Override
- protected int enumerateMediaItems(ItemConsumer consumer, int startIndex) {
- mDataManager.mapMediaItems(mPaths, consumer, startIndex);
- return mPaths.size();
- }
-
- @Override
- public int getTotalMediaItemCount() {
- return mPaths.size();
- }
-
- @Override
- public long reload() {
- if (mClusterAlbumSet.reload() > mDataVersion) {
- mDataVersion = nextVersionNumber();
- }
- return mDataVersion;
- }
-
- @Override
- public void onContentDirty() {
- notifyContentChanged();
- }
-
- @Override
- public int getSupportedOperations() {
- return SUPPORT_SHARE | SUPPORT_DELETE | SUPPORT_INFO;
- }
-
- @Override
- public void delete() {
- ItemConsumer consumer = new ItemConsumer() {
- @Override
- public void consume(int index, MediaItem item) {
- if ((item.getSupportedOperations() & SUPPORT_DELETE) != 0) {
- item.delete();
- }
- }
- };
- mDataManager.mapMediaItems(mPaths, consumer, 0);
- }
-
- @Override
- public boolean isLeafAlbum() {
- return true;
- }
-}
diff --git a/src/com/android/gallery3d/data/ClusterAlbumSet.java b/src/com/android/gallery3d/data/ClusterAlbumSet.java
deleted file mode 100644
index cb212ba36..000000000
--- a/src/com/android/gallery3d/data/ClusterAlbumSet.java
+++ /dev/null
@@ -1,159 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.Context;
-import android.net.Uri;
-
-import com.android.gallery3d.app.GalleryApp;
-
-import java.util.ArrayList;
-import java.util.HashSet;
-
-public class ClusterAlbumSet extends MediaSet implements ContentListener {
- @SuppressWarnings("unused")
- private static final String TAG = "ClusterAlbumSet";
- private GalleryApp mApplication;
- private MediaSet mBaseSet;
- private int mKind;
- private ArrayList<ClusterAlbum> mAlbums = new ArrayList<ClusterAlbum>();
- private boolean mFirstReloadDone;
-
- public ClusterAlbumSet(Path path, GalleryApp application,
- MediaSet baseSet, int kind) {
- super(path, INVALID_DATA_VERSION);
- mApplication = application;
- mBaseSet = baseSet;
- mKind = kind;
- baseSet.addContentListener(this);
- }
-
- @Override
- public MediaSet getSubMediaSet(int index) {
- return mAlbums.get(index);
- }
-
- @Override
- public int getSubMediaSetCount() {
- return mAlbums.size();
- }
-
- @Override
- public String getName() {
- return mBaseSet.getName();
- }
-
- @Override
- public long reload() {
- if (mBaseSet.reload() > mDataVersion) {
- if (mFirstReloadDone) {
- updateClustersContents();
- } else {
- updateClusters();
- mFirstReloadDone = true;
- }
- mDataVersion = nextVersionNumber();
- }
- return mDataVersion;
- }
-
- @Override
- public void onContentDirty() {
- notifyContentChanged();
- }
-
- private void updateClusters() {
- mAlbums.clear();
- Clustering clustering;
- Context context = mApplication.getAndroidContext();
- switch (mKind) {
- case ClusterSource.CLUSTER_ALBUMSET_TIME:
- clustering = new TimeClustering(context);
- break;
- case ClusterSource.CLUSTER_ALBUMSET_LOCATION:
- clustering = new LocationClustering(context);
- break;
- case ClusterSource.CLUSTER_ALBUMSET_TAG:
- clustering = new TagClustering(context);
- break;
- case ClusterSource.CLUSTER_ALBUMSET_FACE:
- clustering = new FaceClustering(context);
- break;
- default: /* CLUSTER_ALBUMSET_SIZE */
- clustering = new SizeClustering(context);
- break;
- }
-
- clustering.run(mBaseSet);
- int n = clustering.getNumberOfClusters();
- DataManager dataManager = mApplication.getDataManager();
- for (int i = 0; i < n; i++) {
- Path childPath;
- String childName = clustering.getClusterName(i);
- if (mKind == ClusterSource.CLUSTER_ALBUMSET_TAG) {
- childPath = mPath.getChild(Uri.encode(childName));
- } else if (mKind == ClusterSource.CLUSTER_ALBUMSET_SIZE) {
- long minSize = ((SizeClustering) clustering).getMinSize(i);
- childPath = mPath.getChild(minSize);
- } else {
- childPath = mPath.getChild(i);
- }
-
- ClusterAlbum album;
- synchronized (DataManager.LOCK) {
- album = (ClusterAlbum) dataManager.peekMediaObject(childPath);
- if (album == null) {
- album = new ClusterAlbum(childPath, dataManager, this);
- }
- }
- album.setMediaItems(clustering.getCluster(i));
- album.setName(childName);
- album.setCoverMediaItem(clustering.getClusterCover(i));
- mAlbums.add(album);
- }
- }
-
- private void updateClustersContents() {
- final HashSet<Path> existing = new HashSet<Path>();
- mBaseSet.enumerateTotalMediaItems(new MediaSet.ItemConsumer() {
- @Override
- public void consume(int index, MediaItem item) {
- existing.add(item.getPath());
- }
- });
-
- int n = mAlbums.size();
-
- // The loop goes backwards because we may remove empty albums from
- // mAlbums.
- for (int i = n - 1; i >= 0; i--) {
- ArrayList<Path> oldPaths = mAlbums.get(i).getMediaItems();
- ArrayList<Path> newPaths = new ArrayList<Path>();
- int m = oldPaths.size();
- for (int j = 0; j < m; j++) {
- Path p = oldPaths.get(j);
- if (existing.contains(p)) {
- newPaths.add(p);
- }
- }
- mAlbums.get(i).setMediaItems(newPaths);
- if (newPaths.isEmpty()) {
- mAlbums.remove(i);
- }
- }
- }
-}
diff --git a/src/com/android/gallery3d/data/ClusterSource.java b/src/com/android/gallery3d/data/ClusterSource.java
deleted file mode 100644
index a1f22e57a..000000000
--- a/src/com/android/gallery3d/data/ClusterSource.java
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.app.GalleryApp;
-
-class ClusterSource extends MediaSource {
- static final int CLUSTER_ALBUMSET_TIME = 0;
- static final int CLUSTER_ALBUMSET_LOCATION = 1;
- static final int CLUSTER_ALBUMSET_TAG = 2;
- static final int CLUSTER_ALBUMSET_SIZE = 3;
- static final int CLUSTER_ALBUMSET_FACE = 4;
-
- static final int CLUSTER_ALBUM_TIME = 0x100;
- static final int CLUSTER_ALBUM_LOCATION = 0x101;
- static final int CLUSTER_ALBUM_TAG = 0x102;
- static final int CLUSTER_ALBUM_SIZE = 0x103;
- static final int CLUSTER_ALBUM_FACE = 0x104;
-
- GalleryApp mApplication;
- PathMatcher mMatcher;
-
- public ClusterSource(GalleryApp application) {
- super("cluster");
- mApplication = application;
- mMatcher = new PathMatcher();
- mMatcher.add("/cluster/*/time", CLUSTER_ALBUMSET_TIME);
- mMatcher.add("/cluster/*/location", CLUSTER_ALBUMSET_LOCATION);
- mMatcher.add("/cluster/*/tag", CLUSTER_ALBUMSET_TAG);
- mMatcher.add("/cluster/*/size", CLUSTER_ALBUMSET_SIZE);
- mMatcher.add("/cluster/*/face", CLUSTER_ALBUMSET_FACE);
-
- mMatcher.add("/cluster/*/time/*", CLUSTER_ALBUM_TIME);
- mMatcher.add("/cluster/*/location/*", CLUSTER_ALBUM_LOCATION);
- mMatcher.add("/cluster/*/tag/*", CLUSTER_ALBUM_TAG);
- mMatcher.add("/cluster/*/size/*", CLUSTER_ALBUM_SIZE);
- mMatcher.add("/cluster/*/face/*", CLUSTER_ALBUM_FACE);
- }
-
- // The names we accept are:
- // /cluster/{set}/time /cluster/{set}/time/k
- // /cluster/{set}/location /cluster/{set}/location/k
- // /cluster/{set}/tag /cluster/{set}/tag/encoded_tag
- // /cluster/{set}/size /cluster/{set}/size/min_size
- @Override
- public MediaObject createMediaObject(Path path) {
- int matchType = mMatcher.match(path);
- String setsName = mMatcher.getVar(0);
- DataManager dataManager = mApplication.getDataManager();
- MediaSet[] sets = dataManager.getMediaSetsFromString(setsName);
- switch (matchType) {
- case CLUSTER_ALBUMSET_TIME:
- case CLUSTER_ALBUMSET_LOCATION:
- case CLUSTER_ALBUMSET_TAG:
- case CLUSTER_ALBUMSET_SIZE:
- case CLUSTER_ALBUMSET_FACE:
- return new ClusterAlbumSet(path, mApplication, sets[0], matchType);
- case CLUSTER_ALBUM_TIME:
- case CLUSTER_ALBUM_LOCATION:
- case CLUSTER_ALBUM_TAG:
- case CLUSTER_ALBUM_SIZE:
- case CLUSTER_ALBUM_FACE: {
- MediaSet parent = dataManager.getMediaSet(path.getParent());
- // The actual content in the ClusterAlbum will be filled later
- // when the reload() method in the parent is run.
- return new ClusterAlbum(path, dataManager, parent);
- }
- default:
- throw new RuntimeException("bad path: " + path);
- }
- }
-}
diff --git a/src/com/android/gallery3d/data/Clustering.java b/src/com/android/gallery3d/data/Clustering.java
deleted file mode 100644
index 4072bf57b..000000000
--- a/src/com/android/gallery3d/data/Clustering.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import java.util.ArrayList;
-
-public abstract class Clustering {
- public abstract void run(MediaSet baseSet);
- public abstract int getNumberOfClusters();
- public abstract ArrayList<Path> getCluster(int index);
- public abstract String getClusterName(int index);
- public MediaItem getClusterCover(int index) {
- return null;
- }
-}
diff --git a/src/com/android/gallery3d/data/ComboAlbum.java b/src/com/android/gallery3d/data/ComboAlbum.java
deleted file mode 100644
index cadd9f8af..000000000
--- a/src/com/android/gallery3d/data/ComboAlbum.java
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.util.Future;
-
-import java.util.ArrayList;
-
-// ComboAlbum combines multiple media sets into one. It lists all media items
-// from the input albums.
-// This only handles SubMediaSets, not MediaItems. (That's all we need now)
-public class ComboAlbum extends MediaSet implements ContentListener {
- @SuppressWarnings("unused")
- private static final String TAG = "ComboAlbum";
- private final MediaSet[] mSets;
- private String mName;
-
- public ComboAlbum(Path path, MediaSet[] mediaSets, String name) {
- super(path, nextVersionNumber());
- mSets = mediaSets;
- for (MediaSet set : mSets) {
- set.addContentListener(this);
- }
- mName = name;
- }
-
- @Override
- public ArrayList<MediaItem> getMediaItem(int start, int count) {
- ArrayList<MediaItem> items = new ArrayList<MediaItem>();
- for (MediaSet set : mSets) {
- int size = set.getMediaItemCount();
- if (count < 1) break;
- if (start < size) {
- int fetchCount = (start + count <= size) ? count : size - start;
- ArrayList<MediaItem> fetchItems = set.getMediaItem(start, fetchCount);
- items.addAll(fetchItems);
- count -= fetchItems.size();
- start = 0;
- } else {
- start -= size;
- }
- }
- return items;
- }
-
- @Override
- public int getMediaItemCount() {
- int count = 0;
- for (MediaSet set : mSets) {
- count += set.getMediaItemCount();
- }
- return count;
- }
-
- @Override
- public boolean isLeafAlbum() {
- return true;
- }
-
- @Override
- public String getName() {
- return mName;
- }
-
- public void useNameOfChild(int i) {
- if (i < mSets.length) mName = mSets[i].getName();
- }
-
- @Override
- public long reload() {
- boolean changed = false;
- for (int i = 0, n = mSets.length; i < n; ++i) {
- long version = mSets[i].reload();
- if (version > mDataVersion) changed = true;
- }
- if (changed) mDataVersion = nextVersionNumber();
- return mDataVersion;
- }
-
- @Override
- public void onContentDirty() {
- notifyContentChanged();
- }
-
- @Override
- public Future<Integer> requestSync(SyncListener listener) {
- return requestSyncOnMultipleSets(mSets, listener);
- }
-}
diff --git a/src/com/android/gallery3d/data/ComboAlbumSet.java b/src/com/android/gallery3d/data/ComboAlbumSet.java
deleted file mode 100644
index 3f3674500..000000000
--- a/src/com/android/gallery3d/data/ComboAlbumSet.java
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.util.Future;
-
-// ComboAlbumSet combines multiple media sets into one. It lists all sub
-// media sets from the input album sets.
-// This only handles SubMediaSets, not MediaItems. (That's all we need now)
-public class ComboAlbumSet extends MediaSet implements ContentListener {
- @SuppressWarnings("unused")
- private static final String TAG = "ComboAlbumSet";
- private final MediaSet[] mSets;
- private final String mName;
-
- public ComboAlbumSet(Path path, GalleryApp application, MediaSet[] mediaSets) {
- super(path, nextVersionNumber());
- mSets = mediaSets;
- for (MediaSet set : mSets) {
- set.addContentListener(this);
- }
- mName = application.getResources().getString(
- R.string.set_label_all_albums);
- }
-
- @Override
- public MediaSet getSubMediaSet(int index) {
- for (MediaSet set : mSets) {
- int size = set.getSubMediaSetCount();
- if (index < size) {
- return set.getSubMediaSet(index);
- }
- index -= size;
- }
- return null;
- }
-
- @Override
- public int getSubMediaSetCount() {
- int count = 0;
- for (MediaSet set : mSets) {
- count += set.getSubMediaSetCount();
- }
- return count;
- }
-
- @Override
- public String getName() {
- return mName;
- }
-
- @Override
- public boolean isLoading() {
- for (int i = 0, n = mSets.length; i < n; ++i) {
- if (mSets[i].isLoading()) return true;
- }
- return false;
- }
-
- @Override
- public long reload() {
- boolean changed = false;
- for (int i = 0, n = mSets.length; i < n; ++i) {
- long version = mSets[i].reload();
- if (version > mDataVersion) changed = true;
- }
- if (changed) mDataVersion = nextVersionNumber();
- return mDataVersion;
- }
-
- @Override
- public void onContentDirty() {
- notifyContentChanged();
- }
-
- @Override
- public Future<Integer> requestSync(SyncListener listener) {
- return requestSyncOnMultipleSets(mSets, listener);
- }
-}
diff --git a/src/com/android/gallery3d/data/ComboSource.java b/src/com/android/gallery3d/data/ComboSource.java
deleted file mode 100644
index 867d47e64..000000000
--- a/src/com/android/gallery3d/data/ComboSource.java
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.app.GalleryApp;
-
-class ComboSource extends MediaSource {
- private static final int COMBO_ALBUMSET = 0;
- private static final int COMBO_ALBUM = 1;
- private GalleryApp mApplication;
- private PathMatcher mMatcher;
-
- public ComboSource(GalleryApp application) {
- super("combo");
- mApplication = application;
- mMatcher = new PathMatcher();
- mMatcher.add("/combo/*", COMBO_ALBUMSET);
- mMatcher.add("/combo/*/*", COMBO_ALBUM);
- }
-
- // The only path we accept is "/combo/{set1, set2, ...} and /combo/item/{set1, set2, ...}"
- @Override
- public MediaObject createMediaObject(Path path) {
- String[] segments = path.split();
- if (segments.length < 2) {
- throw new RuntimeException("bad path: " + path);
- }
-
- DataManager dataManager = mApplication.getDataManager();
- switch (mMatcher.match(path)) {
- case COMBO_ALBUMSET:
- return new ComboAlbumSet(path, mApplication,
- dataManager.getMediaSetsFromString(segments[1]));
-
- case COMBO_ALBUM:
- return new ComboAlbum(path,
- dataManager.getMediaSetsFromString(segments[2]), segments[1]);
- }
- return null;
- }
-}
diff --git a/src/com/android/gallery3d/data/ContentListener.java b/src/com/android/gallery3d/data/ContentListener.java
deleted file mode 100644
index 5e2952685..000000000
--- a/src/com/android/gallery3d/data/ContentListener.java
+++ /dev/null
@@ -1,21 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-public interface ContentListener {
- public void onContentDirty();
-} \ No newline at end of file
diff --git a/src/com/android/gallery3d/data/DataManager.java b/src/com/android/gallery3d/data/DataManager.java
deleted file mode 100644
index 38865e9f1..000000000
--- a/src/com/android/gallery3d/data/DataManager.java
+++ /dev/null
@@ -1,371 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.Context;
-import android.database.ContentObserver;
-import android.net.Uri;
-import android.os.Handler;
-
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.app.StitchingChangeListener;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.MediaObject.PanoramaSupportCallback;
-import com.android.gallery3d.data.MediaSet.ItemConsumer;
-import com.android.gallery3d.data.MediaSource.PathId;
-import com.android.gallery3d.picasasource.PicasaSource;
-
-import java.util.ArrayList;
-import java.util.Comparator;
-import java.util.HashMap;
-import java.util.LinkedHashMap;
-import java.util.Map.Entry;
-import java.util.WeakHashMap;
-
-// DataManager manages all media sets and media items in the system.
-//
-// Each MediaSet and MediaItem has a unique 64 bits id. The most significant
-// 32 bits represents its parent, and the least significant 32 bits represents
-// the self id. For MediaSet the self id is is globally unique, but for
-// MediaItem it's unique only relative to its parent.
-//
-// To make sure the id is the same when the MediaSet is re-created, a child key
-// is provided to obtainSetId() to make sure the same self id will be used as
-// when the parent and key are the same. A sequence of child keys is called a
-// path. And it's used to identify a specific media set even if the process is
-// killed and re-created, so child keys should be stable identifiers.
-
-public class DataManager implements StitchingChangeListener {
- public static final int INCLUDE_IMAGE = 1;
- public static final int INCLUDE_VIDEO = 2;
- public static final int INCLUDE_ALL = INCLUDE_IMAGE | INCLUDE_VIDEO;
- public static final int INCLUDE_LOCAL_ONLY = 4;
- public static final int INCLUDE_LOCAL_IMAGE_ONLY =
- INCLUDE_LOCAL_ONLY | INCLUDE_IMAGE;
- public static final int INCLUDE_LOCAL_VIDEO_ONLY =
- INCLUDE_LOCAL_ONLY | INCLUDE_VIDEO;
- public static final int INCLUDE_LOCAL_ALL_ONLY =
- INCLUDE_LOCAL_ONLY | INCLUDE_IMAGE | INCLUDE_VIDEO;
-
- // Any one who would like to access data should require this lock
- // to prevent concurrency issue.
- public static final Object LOCK = new Object();
-
- public static DataManager from(Context context) {
- GalleryApp app = (GalleryApp) context.getApplicationContext();
- return app.getDataManager();
- }
-
- private static final String TAG = "DataManager";
-
- // This is the path for the media set seen by the user at top level.
- private static final String TOP_SET_PATH = "/combo/{/local/all,/picasa/all}";
-
- private static final String TOP_IMAGE_SET_PATH = "/combo/{/local/image,/picasa/image}";
-
- private static final String TOP_VIDEO_SET_PATH =
- "/combo/{/local/video,/picasa/video}";
-
- private static final String TOP_LOCAL_SET_PATH = "/local/all";
-
- private static final String TOP_LOCAL_IMAGE_SET_PATH = "/local/image";
-
- private static final String TOP_LOCAL_VIDEO_SET_PATH = "/local/video";
-
- public static final Comparator<MediaItem> sDateTakenComparator =
- new DateTakenComparator();
-
- private static class DateTakenComparator implements Comparator<MediaItem> {
- @Override
- public int compare(MediaItem item1, MediaItem item2) {
- return -Utils.compare(item1.getDateInMs(), item2.getDateInMs());
- }
- }
-
- private final Handler mDefaultMainHandler;
-
- private GalleryApp mApplication;
- private int mActiveCount = 0;
-
- private HashMap<Uri, NotifyBroker> mNotifierMap =
- new HashMap<Uri, NotifyBroker>();
-
-
- private HashMap<String, MediaSource> mSourceMap =
- new LinkedHashMap<String, MediaSource>();
-
- public DataManager(GalleryApp application) {
- mApplication = application;
- mDefaultMainHandler = new Handler(application.getMainLooper());
- }
-
- public synchronized void initializeSourceMap() {
- if (!mSourceMap.isEmpty()) return;
-
- // the order matters, the UriSource must come last
- addSource(new LocalSource(mApplication));
- addSource(new PicasaSource(mApplication));
- addSource(new ComboSource(mApplication));
- addSource(new ClusterSource(mApplication));
- addSource(new FilterSource(mApplication));
- addSource(new SecureSource(mApplication));
- addSource(new UriSource(mApplication));
- addSource(new SnailSource(mApplication));
-
- if (mActiveCount > 0) {
- for (MediaSource source : mSourceMap.values()) {
- source.resume();
- }
- }
- }
-
- public String getTopSetPath(int typeBits) {
-
- switch (typeBits) {
- case INCLUDE_IMAGE: return TOP_IMAGE_SET_PATH;
- case INCLUDE_VIDEO: return TOP_VIDEO_SET_PATH;
- case INCLUDE_ALL: return TOP_SET_PATH;
- case INCLUDE_LOCAL_IMAGE_ONLY: return TOP_LOCAL_IMAGE_SET_PATH;
- case INCLUDE_LOCAL_VIDEO_ONLY: return TOP_LOCAL_VIDEO_SET_PATH;
- case INCLUDE_LOCAL_ALL_ONLY: return TOP_LOCAL_SET_PATH;
- default: throw new IllegalArgumentException();
- }
- }
-
- // open for debug
- void addSource(MediaSource source) {
- if (source == null) return;
- mSourceMap.put(source.getPrefix(), source);
- }
-
- // A common usage of this method is:
- // synchronized (DataManager.LOCK) {
- // MediaObject object = peekMediaObject(path);
- // if (object == null) {
- // object = createMediaObject(...);
- // }
- // }
- public MediaObject peekMediaObject(Path path) {
- return path.getObject();
- }
-
- public MediaObject getMediaObject(Path path) {
- synchronized (LOCK) {
- MediaObject obj = path.getObject();
- if (obj != null) return obj;
-
- MediaSource source = mSourceMap.get(path.getPrefix());
- if (source == null) {
- Log.w(TAG, "cannot find media source for path: " + path);
- return null;
- }
-
- try {
- MediaObject object = source.createMediaObject(path);
- if (object == null) {
- Log.w(TAG, "cannot create media object: " + path);
- }
- return object;
- } catch (Throwable t) {
- Log.w(TAG, "exception in creating media object: " + path, t);
- return null;
- }
- }
- }
-
- public MediaObject getMediaObject(String s) {
- return getMediaObject(Path.fromString(s));
- }
-
- public MediaSet getMediaSet(Path path) {
- return (MediaSet) getMediaObject(path);
- }
-
- public MediaSet getMediaSet(String s) {
- return (MediaSet) getMediaObject(s);
- }
-
- public MediaSet[] getMediaSetsFromString(String segment) {
- String[] seq = Path.splitSequence(segment);
- int n = seq.length;
- MediaSet[] sets = new MediaSet[n];
- for (int i = 0; i < n; i++) {
- sets[i] = getMediaSet(seq[i]);
- }
- return sets;
- }
-
- // Maps a list of Paths to MediaItems, and invoke consumer.consume()
- // for each MediaItem (may not be in the same order as the input list).
- // An index number is also passed to consumer.consume() to identify
- // the original position in the input list of the corresponding Path (plus
- // startIndex).
- public void mapMediaItems(ArrayList<Path> list, ItemConsumer consumer,
- int startIndex) {
- HashMap<String, ArrayList<PathId>> map =
- new HashMap<String, ArrayList<PathId>>();
-
- // Group the path by the prefix.
- int n = list.size();
- for (int i = 0; i < n; i++) {
- Path path = list.get(i);
- String prefix = path.getPrefix();
- ArrayList<PathId> group = map.get(prefix);
- if (group == null) {
- group = new ArrayList<PathId>();
- map.put(prefix, group);
- }
- group.add(new PathId(path, i + startIndex));
- }
-
- // For each group, ask the corresponding media source to map it.
- for (Entry<String, ArrayList<PathId>> entry : map.entrySet()) {
- String prefix = entry.getKey();
- MediaSource source = mSourceMap.get(prefix);
- source.mapMediaItems(entry.getValue(), consumer);
- }
- }
-
- // The following methods forward the request to the proper object.
- public int getSupportedOperations(Path path) {
- return getMediaObject(path).getSupportedOperations();
- }
-
- public void getPanoramaSupport(Path path, PanoramaSupportCallback callback) {
- getMediaObject(path).getPanoramaSupport(callback);
- }
-
- public void delete(Path path) {
- getMediaObject(path).delete();
- }
-
- public void rotate(Path path, int degrees) {
- getMediaObject(path).rotate(degrees);
- }
-
- public Uri getContentUri(Path path) {
- return getMediaObject(path).getContentUri();
- }
-
- public int getMediaType(Path path) {
- return getMediaObject(path).getMediaType();
- }
-
- public Path findPathByUri(Uri uri, String type) {
- if (uri == null) return null;
- for (MediaSource source : mSourceMap.values()) {
- Path path = source.findPathByUri(uri, type);
- if (path != null) return path;
- }
- return null;
- }
-
- public Path getDefaultSetOf(Path item) {
- MediaSource source = mSourceMap.get(item.getPrefix());
- return source == null ? null : source.getDefaultSetOf(item);
- }
-
- // Returns number of bytes used by cached pictures currently downloaded.
- public long getTotalUsedCacheSize() {
- long sum = 0;
- for (MediaSource source : mSourceMap.values()) {
- sum += source.getTotalUsedCacheSize();
- }
- return sum;
- }
-
- // Returns number of bytes used by cached pictures if all pending
- // downloads and removals are completed.
- public long getTotalTargetCacheSize() {
- long sum = 0;
- for (MediaSource source : mSourceMap.values()) {
- sum += source.getTotalTargetCacheSize();
- }
- return sum;
- }
-
- public void registerChangeNotifier(Uri uri, ChangeNotifier notifier) {
- NotifyBroker broker = null;
- synchronized (mNotifierMap) {
- broker = mNotifierMap.get(uri);
- if (broker == null) {
- broker = new NotifyBroker(mDefaultMainHandler);
- mApplication.getContentResolver()
- .registerContentObserver(uri, true, broker);
- mNotifierMap.put(uri, broker);
- }
- }
- broker.registerNotifier(notifier);
- }
-
- public void resume() {
- if (++mActiveCount == 1) {
- for (MediaSource source : mSourceMap.values()) {
- source.resume();
- }
- }
- }
-
- public void pause() {
- if (--mActiveCount == 0) {
- for (MediaSource source : mSourceMap.values()) {
- source.pause();
- }
- }
- }
-
- private static class NotifyBroker extends ContentObserver {
- private WeakHashMap<ChangeNotifier, Object> mNotifiers =
- new WeakHashMap<ChangeNotifier, Object>();
-
- public NotifyBroker(Handler handler) {
- super(handler);
- }
-
- public synchronized void registerNotifier(ChangeNotifier notifier) {
- mNotifiers.put(notifier, null);
- }
-
- @Override
- public synchronized void onChange(boolean selfChange) {
- for(ChangeNotifier notifier : mNotifiers.keySet()) {
- notifier.onChange(selfChange);
- }
- }
- }
-
- @Override
- public void onStitchingQueued(Uri uri) {
- // Do nothing.
- }
-
- @Override
- public void onStitchingResult(Uri uri) {
- Path path = findPathByUri(uri, null);
- if (path != null) {
- MediaObject mediaObject = getMediaObject(path);
- if (mediaObject != null) {
- mediaObject.clearCachedPanoramaSupport();
- }
- }
- }
-
- @Override
- public void onStitchingProgress(Uri uri, int progress) {
- // Do nothing.
- }
-}
diff --git a/src/com/android/gallery3d/data/DataSourceType.java b/src/com/android/gallery3d/data/DataSourceType.java
deleted file mode 100644
index ab534d0c3..000000000
--- a/src/com/android/gallery3d/data/DataSourceType.java
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.util.MediaSetUtils;
-
-public final class DataSourceType {
- public static final int TYPE_NOT_CATEGORIZED = 0;
- public static final int TYPE_LOCAL = 1;
- public static final int TYPE_PICASA = 2;
- public static final int TYPE_CAMERA = 3;
-
- private static final Path PICASA_ROOT = Path.fromString("/picasa");
- private static final Path LOCAL_ROOT = Path.fromString("/local");
-
- public static int identifySourceType(MediaSet set) {
- if (set == null) {
- return TYPE_NOT_CATEGORIZED;
- }
-
- Path path = set.getPath();
- if (MediaSetUtils.isCameraSource(path)) return TYPE_CAMERA;
-
- Path prefix = path.getPrefixPath();
-
- if (prefix == PICASA_ROOT) return TYPE_PICASA;
- if (prefix == LOCAL_ROOT) return TYPE_LOCAL;
-
- return TYPE_NOT_CATEGORIZED;
- }
-}
diff --git a/src/com/android/gallery3d/data/DecodeUtils.java b/src/com/android/gallery3d/data/DecodeUtils.java
deleted file mode 100644
index fa709157d..000000000
--- a/src/com/android/gallery3d/data/DecodeUtils.java
+++ /dev/null
@@ -1,312 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.annotation.TargetApi;
-import android.graphics.Bitmap;
-import android.graphics.Bitmap.Config;
-import android.graphics.BitmapFactory;
-import android.graphics.BitmapFactory.Options;
-import android.graphics.BitmapRegionDecoder;
-import android.os.Build;
-import android.util.FloatMath;
-
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.common.BitmapUtils;
-import com.android.gallery3d.common.Utils;
-import com.android.photos.data.GalleryBitmapPool;
-import com.android.gallery3d.ui.Log;
-import com.android.gallery3d.util.ThreadPool.CancelListener;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.io.FileDescriptor;
-import java.io.FileInputStream;
-import java.io.InputStream;
-
-public class DecodeUtils {
- private static final String TAG = "DecodeUtils";
-
- private static class DecodeCanceller implements CancelListener {
- Options mOptions;
-
- public DecodeCanceller(Options options) {
- mOptions = options;
- }
-
- @Override
- public void onCancel() {
- mOptions.requestCancelDecode();
- }
- }
-
- @TargetApi(ApiHelper.VERSION_CODES.HONEYCOMB)
- public static void setOptionsMutable(Options options) {
- if (ApiHelper.HAS_OPTIONS_IN_MUTABLE) options.inMutable = true;
- }
-
- public static Bitmap decode(JobContext jc, FileDescriptor fd, Options options) {
- if (options == null) options = new Options();
- jc.setCancelListener(new DecodeCanceller(options));
- setOptionsMutable(options);
- return ensureGLCompatibleBitmap(
- BitmapFactory.decodeFileDescriptor(fd, null, options));
- }
-
- public static void decodeBounds(JobContext jc, FileDescriptor fd,
- Options options) {
- Utils.assertTrue(options != null);
- options.inJustDecodeBounds = true;
- jc.setCancelListener(new DecodeCanceller(options));
- BitmapFactory.decodeFileDescriptor(fd, null, options);
- options.inJustDecodeBounds = false;
- }
-
- public static Bitmap decode(JobContext jc, byte[] bytes, Options options) {
- return decode(jc, bytes, 0, bytes.length, options);
- }
-
- public static Bitmap decode(JobContext jc, byte[] bytes, int offset,
- int length, Options options) {
- if (options == null) options = new Options();
- jc.setCancelListener(new DecodeCanceller(options));
- setOptionsMutable(options);
- return ensureGLCompatibleBitmap(
- BitmapFactory.decodeByteArray(bytes, offset, length, options));
- }
-
- public static void decodeBounds(JobContext jc, byte[] bytes, int offset,
- int length, Options options) {
- Utils.assertTrue(options != null);
- options.inJustDecodeBounds = true;
- jc.setCancelListener(new DecodeCanceller(options));
- BitmapFactory.decodeByteArray(bytes, offset, length, options);
- options.inJustDecodeBounds = false;
- }
-
- public static Bitmap decodeThumbnail(
- JobContext jc, String filePath, Options options, int targetSize, int type) {
- FileInputStream fis = null;
- try {
- fis = new FileInputStream(filePath);
- FileDescriptor fd = fis.getFD();
- return decodeThumbnail(jc, fd, options, targetSize, type);
- } catch (Exception ex) {
- Log.w(TAG, ex);
- return null;
- } finally {
- Utils.closeSilently(fis);
- }
- }
-
- public static Bitmap decodeThumbnail(
- JobContext jc, FileDescriptor fd, Options options, int targetSize, int type) {
- if (options == null) options = new Options();
- jc.setCancelListener(new DecodeCanceller(options));
-
- options.inJustDecodeBounds = true;
- BitmapFactory.decodeFileDescriptor(fd, null, options);
- if (jc.isCancelled()) return null;
-
- int w = options.outWidth;
- int h = options.outHeight;
-
- if (type == MediaItem.TYPE_MICROTHUMBNAIL) {
- // We center-crop the original image as it's micro thumbnail. In this case,
- // we want to make sure the shorter side >= "targetSize".
- float scale = (float) targetSize / Math.min(w, h);
- options.inSampleSize = BitmapUtils.computeSampleSizeLarger(scale);
-
- // For an extremely wide image, e.g. 300x30000, we may got OOM when decoding
- // it for TYPE_MICROTHUMBNAIL. So we add a max number of pixels limit here.
- final int MAX_PIXEL_COUNT = 640000; // 400 x 1600
- if ((w / options.inSampleSize) * (h / options.inSampleSize) > MAX_PIXEL_COUNT) {
- options.inSampleSize = BitmapUtils.computeSampleSize(
- FloatMath.sqrt((float) MAX_PIXEL_COUNT / (w * h)));
- }
- } else {
- // For screen nail, we only want to keep the longer side >= targetSize.
- float scale = (float) targetSize / Math.max(w, h);
- options.inSampleSize = BitmapUtils.computeSampleSizeLarger(scale);
- }
-
- options.inJustDecodeBounds = false;
- setOptionsMutable(options);
-
- Bitmap result = BitmapFactory.decodeFileDescriptor(fd, null, options);
- if (result == null) return null;
-
- // We need to resize down if the decoder does not support inSampleSize
- // (For example, GIF images)
- float scale = (float) targetSize / (type == MediaItem.TYPE_MICROTHUMBNAIL
- ? Math.min(result.getWidth(), result.getHeight())
- : Math.max(result.getWidth(), result.getHeight()));
-
- if (scale <= 0.5) result = BitmapUtils.resizeBitmapByScale(result, scale, true);
- return ensureGLCompatibleBitmap(result);
- }
-
- /**
- * Decodes the bitmap from the given byte array if the image size is larger than the given
- * requirement.
- *
- * Note: The returned image may be resized down. However, both width and height must be
- * larger than the <code>targetSize</code>.
- */
- public static Bitmap decodeIfBigEnough(JobContext jc, byte[] data,
- Options options, int targetSize) {
- if (options == null) options = new Options();
- jc.setCancelListener(new DecodeCanceller(options));
-
- options.inJustDecodeBounds = true;
- BitmapFactory.decodeByteArray(data, 0, data.length, options);
- if (jc.isCancelled()) return null;
- if (options.outWidth < targetSize || options.outHeight < targetSize) {
- return null;
- }
- options.inSampleSize = BitmapUtils.computeSampleSizeLarger(
- options.outWidth, options.outHeight, targetSize);
- options.inJustDecodeBounds = false;
- setOptionsMutable(options);
-
- return ensureGLCompatibleBitmap(
- BitmapFactory.decodeByteArray(data, 0, data.length, options));
- }
-
- // TODO: This function should not be called directly from
- // DecodeUtils.requestDecode(...), since we don't have the knowledge
- // if the bitmap will be uploaded to GL.
- public static Bitmap ensureGLCompatibleBitmap(Bitmap bitmap) {
- if (bitmap == null || bitmap.getConfig() != null) return bitmap;
- Bitmap newBitmap = bitmap.copy(Config.ARGB_8888, false);
- bitmap.recycle();
- return newBitmap;
- }
-
- public static BitmapRegionDecoder createBitmapRegionDecoder(
- JobContext jc, byte[] bytes, int offset, int length,
- boolean shareable) {
- if (offset < 0 || length <= 0 || offset + length > bytes.length) {
- throw new IllegalArgumentException(String.format(
- "offset = %s, length = %s, bytes = %s",
- offset, length, bytes.length));
- }
-
- try {
- return BitmapRegionDecoder.newInstance(
- bytes, offset, length, shareable);
- } catch (Throwable t) {
- Log.w(TAG, t);
- return null;
- }
- }
-
- public static BitmapRegionDecoder createBitmapRegionDecoder(
- JobContext jc, String filePath, boolean shareable) {
- try {
- return BitmapRegionDecoder.newInstance(filePath, shareable);
- } catch (Throwable t) {
- Log.w(TAG, t);
- return null;
- }
- }
-
- public static BitmapRegionDecoder createBitmapRegionDecoder(
- JobContext jc, FileDescriptor fd, boolean shareable) {
- try {
- return BitmapRegionDecoder.newInstance(fd, shareable);
- } catch (Throwable t) {
- Log.w(TAG, t);
- return null;
- }
- }
-
- public static BitmapRegionDecoder createBitmapRegionDecoder(
- JobContext jc, InputStream is, boolean shareable) {
- try {
- return BitmapRegionDecoder.newInstance(is, shareable);
- } catch (Throwable t) {
- // We often cancel the creating of bitmap region decoder,
- // so just log one line.
- Log.w(TAG, "requestCreateBitmapRegionDecoder: " + t);
- return null;
- }
- }
-
- @TargetApi(Build.VERSION_CODES.HONEYCOMB)
- public static Bitmap decodeUsingPool(JobContext jc, byte[] data, int offset,
- int length, BitmapFactory.Options options) {
- if (options == null) options = new BitmapFactory.Options();
- if (options.inSampleSize < 1) options.inSampleSize = 1;
- options.inPreferredConfig = Bitmap.Config.ARGB_8888;
- options.inBitmap = (options.inSampleSize == 1)
- ? findCachedBitmap(jc, data, offset, length, options) : null;
- try {
- Bitmap bitmap = decode(jc, data, offset, length, options);
- if (options.inBitmap != null && options.inBitmap != bitmap) {
- GalleryBitmapPool.getInstance().put(options.inBitmap);
- options.inBitmap = null;
- }
- return bitmap;
- } catch (IllegalArgumentException e) {
- if (options.inBitmap == null) throw e;
-
- Log.w(TAG, "decode fail with a given bitmap, try decode to a new bitmap");
- GalleryBitmapPool.getInstance().put(options.inBitmap);
- options.inBitmap = null;
- return decode(jc, data, offset, length, options);
- }
- }
-
- // This is the same as the method above except the source data comes
- // from a file descriptor instead of a byte array.
- @TargetApi(Build.VERSION_CODES.HONEYCOMB)
- public static Bitmap decodeUsingPool(JobContext jc,
- FileDescriptor fileDescriptor, Options options) {
- if (options == null) options = new BitmapFactory.Options();
- if (options.inSampleSize < 1) options.inSampleSize = 1;
- options.inPreferredConfig = Bitmap.Config.ARGB_8888;
- options.inBitmap = (options.inSampleSize == 1)
- ? findCachedBitmap(jc, fileDescriptor, options) : null;
- try {
- Bitmap bitmap = DecodeUtils.decode(jc, fileDescriptor, options);
- if (options.inBitmap != null && options.inBitmap != bitmap) {
- GalleryBitmapPool.getInstance().put(options.inBitmap);
- options.inBitmap = null;
- }
- return bitmap;
- } catch (IllegalArgumentException e) {
- if (options.inBitmap == null) throw e;
-
- Log.w(TAG, "decode fail with a given bitmap, try decode to a new bitmap");
- GalleryBitmapPool.getInstance().put(options.inBitmap);
- options.inBitmap = null;
- return decode(jc, fileDescriptor, options);
- }
- }
-
- private static Bitmap findCachedBitmap(JobContext jc, byte[] data,
- int offset, int length, Options options) {
- decodeBounds(jc, data, offset, length, options);
- return GalleryBitmapPool.getInstance().get(options.outWidth, options.outHeight);
- }
-
- private static Bitmap findCachedBitmap(JobContext jc, FileDescriptor fileDescriptor,
- Options options) {
- decodeBounds(jc, fileDescriptor, options);
- return GalleryBitmapPool.getInstance().get(options.outWidth, options.outHeight);
- }
-}
diff --git a/src/com/android/gallery3d/data/DownloadCache.java b/src/com/android/gallery3d/data/DownloadCache.java
deleted file mode 100644
index be7820b01..000000000
--- a/src/com/android/gallery3d/data/DownloadCache.java
+++ /dev/null
@@ -1,370 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.ContentValues;
-import android.content.Context;
-import android.database.Cursor;
-import android.database.sqlite.SQLiteDatabase;
-import android.database.sqlite.SQLiteOpenHelper;
-
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.common.LruCache;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.DownloadEntry.Columns;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.FutureListener;
-import com.android.gallery3d.util.ThreadPool;
-import com.android.gallery3d.util.ThreadPool.CancelListener;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.io.File;
-import java.net.URL;
-import java.util.HashMap;
-import java.util.HashSet;
-
-public class DownloadCache {
- private static final String TAG = "DownloadCache";
- private static final int MAX_DELETE_COUNT = 16;
- private static final int LRU_CAPACITY = 4;
-
- private static final String TABLE_NAME = DownloadEntry.SCHEMA.getTableName();
-
- private static final String QUERY_PROJECTION[] = {Columns.ID, Columns.DATA};
- private static final String WHERE_HASH_AND_URL = String.format(
- "%s = ? AND %s = ?", Columns.HASH_CODE, Columns.CONTENT_URL);
- private static final int QUERY_INDEX_ID = 0;
- private static final int QUERY_INDEX_DATA = 1;
-
- private static final String FREESPACE_PROJECTION[] = {
- Columns.ID, Columns.DATA, Columns.CONTENT_URL, Columns.CONTENT_SIZE};
- private static final String FREESPACE_ORDER_BY =
- String.format("%s ASC", Columns.LAST_ACCESS);
- private static final int FREESPACE_IDNEX_ID = 0;
- private static final int FREESPACE_IDNEX_DATA = 1;
- private static final int FREESPACE_INDEX_CONTENT_URL = 2;
- private static final int FREESPACE_INDEX_CONTENT_SIZE = 3;
-
- private static final String ID_WHERE = Columns.ID + " = ?";
-
- private static final String SUM_PROJECTION[] =
- {String.format("sum(%s)", Columns.CONTENT_SIZE)};
- private static final int SUM_INDEX_SUM = 0;
-
- private final LruCache<String, Entry> mEntryMap =
- new LruCache<String, Entry>(LRU_CAPACITY);
- private final HashMap<String, DownloadTask> mTaskMap =
- new HashMap<String, DownloadTask>();
- private final File mRoot;
- private final GalleryApp mApplication;
- private final SQLiteDatabase mDatabase;
- private final long mCapacity;
-
- private long mTotalBytes = 0;
- private boolean mInitialized = false;
-
- public DownloadCache(GalleryApp application, File root, long capacity) {
- mRoot = Utils.checkNotNull(root);
- mApplication = Utils.checkNotNull(application);
- mCapacity = capacity;
- mDatabase = new DatabaseHelper(application.getAndroidContext())
- .getWritableDatabase();
- }
-
- private Entry findEntryInDatabase(String stringUrl) {
- long hash = Utils.crc64Long(stringUrl);
- String whereArgs[] = {String.valueOf(hash), stringUrl};
- Cursor cursor = mDatabase.query(TABLE_NAME, QUERY_PROJECTION,
- WHERE_HASH_AND_URL, whereArgs, null, null, null);
- try {
- if (cursor.moveToNext()) {
- File file = new File(cursor.getString(QUERY_INDEX_DATA));
- long id = cursor.getInt(QUERY_INDEX_ID);
- Entry entry = null;
- synchronized (mEntryMap) {
- entry = mEntryMap.get(stringUrl);
- if (entry == null) {
- entry = new Entry(id, file);
- mEntryMap.put(stringUrl, entry);
- }
- }
- return entry;
- }
- } finally {
- cursor.close();
- }
- return null;
- }
-
- public Entry download(JobContext jc, URL url) {
- if (!mInitialized) initialize();
-
- String stringUrl = url.toString();
-
- // First find in the entry-pool
- synchronized (mEntryMap) {
- Entry entry = mEntryMap.get(stringUrl);
- if (entry != null) {
- updateLastAccess(entry.mId);
- return entry;
- }
- }
-
- // Then, find it in database
- TaskProxy proxy = new TaskProxy();
- synchronized (mTaskMap) {
- Entry entry = findEntryInDatabase(stringUrl);
- if (entry != null) {
- updateLastAccess(entry.mId);
- return entry;
- }
-
- // Finally, we need to download the file ....
- // First check if we are downloading it now ...
- DownloadTask task = mTaskMap.get(stringUrl);
- if (task == null) { // if not, start the download task now
- task = new DownloadTask(stringUrl);
- mTaskMap.put(stringUrl, task);
- task.mFuture = mApplication.getThreadPool().submit(task, task);
- }
- task.addProxy(proxy);
- }
-
- return proxy.get(jc);
- }
-
- private void updateLastAccess(long id) {
- ContentValues values = new ContentValues();
- values.put(Columns.LAST_ACCESS, System.currentTimeMillis());
- mDatabase.update(TABLE_NAME, values,
- ID_WHERE, new String[] {String.valueOf(id)});
- }
-
- private synchronized void freeSomeSpaceIfNeed(int maxDeleteFileCount) {
- if (mTotalBytes <= mCapacity) return;
- Cursor cursor = mDatabase.query(TABLE_NAME,
- FREESPACE_PROJECTION, null, null, null, null, FREESPACE_ORDER_BY);
- try {
- while (maxDeleteFileCount > 0
- && mTotalBytes > mCapacity && cursor.moveToNext()) {
- long id = cursor.getLong(FREESPACE_IDNEX_ID);
- String url = cursor.getString(FREESPACE_INDEX_CONTENT_URL);
- long size = cursor.getLong(FREESPACE_INDEX_CONTENT_SIZE);
- String path = cursor.getString(FREESPACE_IDNEX_DATA);
- boolean containsKey;
- synchronized (mEntryMap) {
- containsKey = mEntryMap.containsKey(url);
- }
- if (!containsKey) {
- --maxDeleteFileCount;
- mTotalBytes -= size;
- new File(path).delete();
- mDatabase.delete(TABLE_NAME,
- ID_WHERE, new String[]{String.valueOf(id)});
- } else {
- // skip delete, since it is being used
- }
- }
- } finally {
- cursor.close();
- }
- }
-
- private synchronized long insertEntry(String url, File file) {
- long size = file.length();
- mTotalBytes += size;
-
- ContentValues values = new ContentValues();
- String hashCode = String.valueOf(Utils.crc64Long(url));
- values.put(Columns.DATA, file.getAbsolutePath());
- values.put(Columns.HASH_CODE, hashCode);
- values.put(Columns.CONTENT_URL, url);
- values.put(Columns.CONTENT_SIZE, size);
- values.put(Columns.LAST_UPDATED, System.currentTimeMillis());
- return mDatabase.insert(TABLE_NAME, "", values);
- }
-
- private synchronized void initialize() {
- if (mInitialized) return;
- mInitialized = true;
- if (!mRoot.isDirectory()) mRoot.mkdirs();
- if (!mRoot.isDirectory()) {
- throw new RuntimeException("cannot create " + mRoot.getAbsolutePath());
- }
-
- Cursor cursor = mDatabase.query(
- TABLE_NAME, SUM_PROJECTION, null, null, null, null, null);
- mTotalBytes = 0;
- try {
- if (cursor.moveToNext()) {
- mTotalBytes = cursor.getLong(SUM_INDEX_SUM);
- }
- } finally {
- cursor.close();
- }
- if (mTotalBytes > mCapacity) freeSomeSpaceIfNeed(MAX_DELETE_COUNT);
- }
-
- private final class DatabaseHelper extends SQLiteOpenHelper {
- public static final String DATABASE_NAME = "download.db";
- public static final int DATABASE_VERSION = 2;
-
- public DatabaseHelper(Context context) {
- super(context, DATABASE_NAME, null, DATABASE_VERSION);
- }
-
- @Override
- public void onCreate(SQLiteDatabase db) {
- DownloadEntry.SCHEMA.createTables(db);
- // Delete old files
- for (File file : mRoot.listFiles()) {
- if (!file.delete()) {
- Log.w(TAG, "fail to remove: " + file.getAbsolutePath());
- }
- }
- }
-
- @Override
- public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
- //reset everything
- DownloadEntry.SCHEMA.dropTables(db);
- onCreate(db);
- }
- }
-
- public class Entry {
- public File cacheFile;
- protected long mId;
-
- Entry(long id, File cacheFile) {
- mId = id;
- this.cacheFile = Utils.checkNotNull(cacheFile);
- }
- }
-
- private class DownloadTask implements Job<File>, FutureListener<File> {
- private HashSet<TaskProxy> mProxySet = new HashSet<TaskProxy>();
- private Future<File> mFuture;
- private final String mUrl;
-
- public DownloadTask(String url) {
- mUrl = Utils.checkNotNull(url);
- }
-
- public void removeProxy(TaskProxy proxy) {
- synchronized (mTaskMap) {
- Utils.assertTrue(mProxySet.remove(proxy));
- if (mProxySet.isEmpty()) {
- mFuture.cancel();
- mTaskMap.remove(mUrl);
- }
- }
- }
-
- // should be used in synchronized block of mDatabase
- public void addProxy(TaskProxy proxy) {
- proxy.mTask = this;
- mProxySet.add(proxy);
- }
-
- @Override
- public void onFutureDone(Future<File> future) {
- File file = future.get();
- long id = 0;
- if (file != null) { // insert to database
- id = insertEntry(mUrl, file);
- }
-
- if (future.isCancelled()) {
- Utils.assertTrue(mProxySet.isEmpty());
- return;
- }
-
- synchronized (mTaskMap) {
- Entry entry = null;
- synchronized (mEntryMap) {
- if (file != null) {
- entry = new Entry(id, file);
- Utils.assertTrue(mEntryMap.put(mUrl, entry) == null);
- }
- }
- for (TaskProxy proxy : mProxySet) {
- proxy.setResult(entry);
- }
- mTaskMap.remove(mUrl);
- freeSomeSpaceIfNeed(MAX_DELETE_COUNT);
- }
- }
-
- @Override
- public File run(JobContext jc) {
- // TODO: utilize etag
- jc.setMode(ThreadPool.MODE_NETWORK);
- File tempFile = null;
- try {
- URL url = new URL(mUrl);
- tempFile = File.createTempFile("cache", ".tmp", mRoot);
- // download from url to tempFile
- jc.setMode(ThreadPool.MODE_NETWORK);
- boolean downloaded = DownloadUtils.requestDownload(jc, url, tempFile);
- jc.setMode(ThreadPool.MODE_NONE);
- if (downloaded) return tempFile;
- } catch (Exception e) {
- Log.e(TAG, String.format("fail to download %s", mUrl), e);
- } finally {
- jc.setMode(ThreadPool.MODE_NONE);
- }
- if (tempFile != null) tempFile.delete();
- return null;
- }
- }
-
- public static class TaskProxy {
- private DownloadTask mTask;
- private boolean mIsCancelled = false;
- private Entry mEntry;
-
- synchronized void setResult(Entry entry) {
- if (mIsCancelled) return;
- mEntry = entry;
- notifyAll();
- }
-
- public synchronized Entry get(JobContext jc) {
- jc.setCancelListener(new CancelListener() {
- @Override
- public void onCancel() {
- mTask.removeProxy(TaskProxy.this);
- synchronized (TaskProxy.this) {
- mIsCancelled = true;
- TaskProxy.this.notifyAll();
- }
- }
- });
- while (!mIsCancelled && mEntry == null) {
- try {
- wait();
- } catch (InterruptedException e) {
- Log.w(TAG, "ignore interrupt", e);
- }
- }
- jc.setCancelListener(null);
- return mEntry;
- }
- }
-}
diff --git a/src/com/android/gallery3d/data/DownloadEntry.java b/src/com/android/gallery3d/data/DownloadEntry.java
deleted file mode 100644
index 578523f73..000000000
--- a/src/com/android/gallery3d/data/DownloadEntry.java
+++ /dev/null
@@ -1,72 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.common.Entry;
-import com.android.gallery3d.common.EntrySchema;
-
-
-@Entry.Table("download")
-public class DownloadEntry extends Entry {
- public static final EntrySchema SCHEMA = new EntrySchema(DownloadEntry.class);
-
- public static interface Columns extends Entry.Columns {
- public static final String HASH_CODE = "hash_code";
- public static final String CONTENT_URL = "content_url";
- public static final String CONTENT_SIZE = "_size";
- public static final String ETAG = "etag";
- public static final String LAST_ACCESS = "last_access";
- public static final String LAST_UPDATED = "last_updated";
- public static final String DATA = "_data";
- }
-
- @Column(value = "hash_code", indexed = true)
- public long hashCode;
-
- @Column("content_url")
- public String contentUrl;
-
- @Column("_size")
- public long contentSize;
-
- @Column("etag")
- public String eTag;
-
- @Column(value = "last_access", indexed = true)
- public long lastAccessTime;
-
- @Column(value = "last_updated")
- public long lastUpdatedTime;
-
- @Column("_data")
- public String path;
-
- @Override
- public String toString() {
- // Note: THIS IS REQUIRED. We used all the fields here. Otherwise,
- // ProGuard will remove these UNUSED fields. However, these
- // fields are needed to generate database.
- return new StringBuilder()
- .append("hash_code: ").append(hashCode).append(", ")
- .append("content_url").append(contentUrl).append(", ")
- .append("_size").append(contentSize).append(", ")
- .append("etag").append(eTag).append(", ")
- .append("last_access").append(lastAccessTime).append(", ")
- .append("last_updated").append(lastUpdatedTime).append(",")
- .append("_data").append(path)
- .toString();
- }
-}
diff --git a/src/com/android/gallery3d/data/DownloadUtils.java b/src/com/android/gallery3d/data/DownloadUtils.java
deleted file mode 100644
index 137898e91..000000000
--- a/src/com/android/gallery3d/data/DownloadUtils.java
+++ /dev/null
@@ -1,79 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.util.ThreadPool.CancelListener;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.io.File;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.InterruptedIOException;
-import java.io.OutputStream;
-import java.net.URL;
-
-public class DownloadUtils {
- private static final String TAG = "DownloadService";
-
- public static boolean requestDownload(JobContext jc, URL url, File file) {
- FileOutputStream fos = null;
- try {
- fos = new FileOutputStream(file);
- return download(jc, url, fos);
- } catch (Throwable t) {
- return false;
- } finally {
- Utils.closeSilently(fos);
- }
- }
-
- public static void dump(JobContext jc, InputStream is, OutputStream os)
- throws IOException {
- byte buffer[] = new byte[4096];
- int rc = is.read(buffer, 0, buffer.length);
- final Thread thread = Thread.currentThread();
- jc.setCancelListener(new CancelListener() {
- @Override
- public void onCancel() {
- thread.interrupt();
- }
- });
- while (rc > 0) {
- if (jc.isCancelled()) throw new InterruptedIOException();
- os.write(buffer, 0, rc);
- rc = is.read(buffer, 0, buffer.length);
- }
- jc.setCancelListener(null);
- Thread.interrupted(); // consume the interrupt signal
- }
-
- public static boolean download(JobContext jc, URL url, OutputStream output) {
- InputStream input = null;
- try {
- input = url.openStream();
- dump(jc, input, output);
- return true;
- } catch (Throwable t) {
- Log.w(TAG, "fail to download", t);
- return false;
- } finally {
- Utils.closeSilently(input);
- }
- }
-} \ No newline at end of file
diff --git a/src/com/android/gallery3d/data/EmptyAlbumImage.java b/src/com/android/gallery3d/data/EmptyAlbumImage.java
deleted file mode 100644
index 6f8c37c6b..000000000
--- a/src/com/android/gallery3d/data/EmptyAlbumImage.java
+++ /dev/null
@@ -1,34 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.GalleryApp;
-
-public class EmptyAlbumImage extends ActionImage {
- @SuppressWarnings("unused")
- private static final String TAG = "EmptyAlbumImage";
-
- public EmptyAlbumImage(Path path, GalleryApp application) {
- super(path, application, R.drawable.placeholder_empty);
- }
-
- @Override
- public int getSupportedOperations() {
- return super.getSupportedOperations() | SUPPORT_BACK;
- }
-}
diff --git a/src/com/android/gallery3d/data/Exif.java b/src/com/android/gallery3d/data/Exif.java
deleted file mode 100644
index 950e7de18..000000000
--- a/src/com/android/gallery3d/data/Exif.java
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.util.Log;
-
-import com.android.gallery3d.exif.ExifInterface;
-
-import java.io.IOException;
-import java.io.InputStream;
-
-public class Exif {
- private static final String TAG = "CameraExif";
-
- // Returns the degrees in clockwise. Values are 0, 90, 180, or 270.
- public static int getOrientation(InputStream is) {
- if (is == null) {
- return 0;
- }
- ExifInterface exif = new ExifInterface();
- try {
- exif.readExif(is);
- Integer val = exif.getTagIntValue(ExifInterface.TAG_ORIENTATION);
- if (val == null) {
- return 0;
- } else {
- return ExifInterface.getRotationForOrientationValue(val.shortValue());
- }
- } catch (IOException e) {
- Log.w(TAG, "Failed to read EXIF orientation", e);
- return 0;
- }
- }
-}
diff --git a/src/com/android/gallery3d/data/Face.java b/src/com/android/gallery3d/data/Face.java
deleted file mode 100644
index d2dc22bfc..000000000
--- a/src/com/android/gallery3d/data/Face.java
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.graphics.Rect;
-
-import com.android.gallery3d.common.Utils;
-
-import java.util.StringTokenizer;
-
-public class Face implements Comparable<Face> {
- private String mName;
- private String mPersonId;
- private Rect mPosition;
-
- public Face(String name, String personId, String rect) {
- mName = name;
- mPersonId = personId;
- Utils.assertTrue(mName != null && mPersonId != null && rect != null);
- StringTokenizer tokenizer = new StringTokenizer(rect);
- mPosition = new Rect();
- while (tokenizer.hasMoreElements()) {
- mPosition.left = Integer.parseInt(tokenizer.nextToken());
- mPosition.top = Integer.parseInt(tokenizer.nextToken());
- mPosition.right = Integer.parseInt(tokenizer.nextToken());
- mPosition.bottom = Integer.parseInt(tokenizer.nextToken());
- }
- }
-
- public Rect getPosition() {
- return mPosition;
- }
-
- public String getName() {
- return mName;
- }
-
- @Override
- public boolean equals(Object obj) {
- if (obj instanceof Face) {
- Face face = (Face) obj;
- return mPersonId.equals(face.mPersonId);
- }
- return false;
- }
-
- @Override
- public int compareTo(Face another) {
- return mName.compareTo(another.mName);
- }
-}
diff --git a/src/com/android/gallery3d/data/FaceClustering.java b/src/com/android/gallery3d/data/FaceClustering.java
deleted file mode 100644
index 819915edb..000000000
--- a/src/com/android/gallery3d/data/FaceClustering.java
+++ /dev/null
@@ -1,142 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.Context;
-import android.graphics.Rect;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.picasasource.PicasaSource;
-
-import java.util.ArrayList;
-import java.util.TreeMap;
-
-public class FaceClustering extends Clustering {
- @SuppressWarnings("unused")
- private static final String TAG = "FaceClustering";
-
- private FaceCluster[] mClusters;
- private String mUntaggedString;
- private Context mContext;
-
- private class FaceCluster {
- ArrayList<Path> mPaths = new ArrayList<Path>();
- String mName;
- MediaItem mCoverItem;
- Rect mCoverRegion;
- int mCoverFaceIndex;
-
- public FaceCluster(String name) {
- mName = name;
- }
-
- public void add(MediaItem item, int faceIndex) {
- Path path = item.getPath();
- mPaths.add(path);
- Face[] faces = item.getFaces();
- if (faces != null) {
- Face face = faces[faceIndex];
- if (mCoverItem == null) {
- mCoverItem = item;
- mCoverRegion = face.getPosition();
- mCoverFaceIndex = faceIndex;
- } else {
- Rect region = face.getPosition();
- if (mCoverRegion.width() < region.width() &&
- mCoverRegion.height() < region.height()) {
- mCoverItem = item;
- mCoverRegion = face.getPosition();
- mCoverFaceIndex = faceIndex;
- }
- }
- }
- }
-
- public int size() {
- return mPaths.size();
- }
-
- public MediaItem getCover() {
- if (mCoverItem != null) {
- if (PicasaSource.isPicasaImage(mCoverItem)) {
- return PicasaSource.getFaceItem(mContext, mCoverItem, mCoverFaceIndex);
- } else {
- return mCoverItem;
- }
- }
- return null;
- }
- }
-
- public FaceClustering(Context context) {
- mUntaggedString = context.getResources().getString(R.string.untagged);
- mContext = context;
- }
-
- @Override
- public void run(MediaSet baseSet) {
- final TreeMap<Face, FaceCluster> map =
- new TreeMap<Face, FaceCluster>();
- final FaceCluster untagged = new FaceCluster(mUntaggedString);
-
- baseSet.enumerateTotalMediaItems(new MediaSet.ItemConsumer() {
- @Override
- public void consume(int index, MediaItem item) {
- Face[] faces = item.getFaces();
- if (faces == null || faces.length == 0) {
- untagged.add(item, -1);
- return;
- }
- for (int j = 0; j < faces.length; j++) {
- Face face = faces[j];
- FaceCluster cluster = map.get(face);
- if (cluster == null) {
- cluster = new FaceCluster(face.getName());
- map.put(face, cluster);
- }
- cluster.add(item, j);
- }
- }
- });
-
- int m = map.size();
- mClusters = map.values().toArray(new FaceCluster[m + ((untagged.size() > 0) ? 1 : 0)]);
- if (untagged.size() > 0) {
- mClusters[m] = untagged;
- }
- }
-
- @Override
- public int getNumberOfClusters() {
- return mClusters.length;
- }
-
- @Override
- public ArrayList<Path> getCluster(int index) {
- return mClusters[index].mPaths;
- }
-
- @Override
- public String getClusterName(int index) {
- return mClusters[index].mName;
- }
-
- @Override
- public MediaItem getClusterCover(int index) {
- return mClusters[index].getCover();
- }
-}
diff --git a/src/com/android/gallery3d/data/FilterDeleteSet.java b/src/com/android/gallery3d/data/FilterDeleteSet.java
deleted file mode 100644
index c76412ff8..000000000
--- a/src/com/android/gallery3d/data/FilterDeleteSet.java
+++ /dev/null
@@ -1,256 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import java.util.ArrayList;
-
-// FilterDeleteSet filters a base MediaSet to remove some deletion items (we
-// expect the number to be small). The user can use the following methods to
-// add/remove deletion items:
-//
-// void addDeletion(Path path, int index);
-// void removeDelection(Path path);
-// void clearDeletion();
-// int getNumberOfDeletions();
-//
-public class FilterDeleteSet extends MediaSet implements ContentListener {
- @SuppressWarnings("unused")
- private static final String TAG = "FilterDeleteSet";
-
- private static final int REQUEST_ADD = 1;
- private static final int REQUEST_REMOVE = 2;
- private static final int REQUEST_CLEAR = 3;
-
- private static class Request {
- int type; // one of the REQUEST_* constants
- Path path;
- int indexHint;
- public Request(int type, Path path, int indexHint) {
- this.type = type;
- this.path = path;
- this.indexHint = indexHint;
- }
- }
-
- private static class Deletion {
- Path path;
- int index;
- public Deletion(Path path, int index) {
- this.path = path;
- this.index = index;
- }
- }
-
- // The underlying MediaSet
- private final MediaSet mBaseSet;
-
- // Pending Requests
- private ArrayList<Request> mRequests = new ArrayList<Request>();
-
- // Deletions currently in effect, ordered by index
- private ArrayList<Deletion> mCurrent = new ArrayList<Deletion>();
-
- public FilterDeleteSet(Path path, MediaSet baseSet) {
- super(path, INVALID_DATA_VERSION);
- mBaseSet = baseSet;
- mBaseSet.addContentListener(this);
- }
-
- @Override
- public boolean isCameraRoll() {
- return mBaseSet.isCameraRoll();
- }
-
- @Override
- public String getName() {
- return mBaseSet.getName();
- }
-
- @Override
- public int getMediaItemCount() {
- return mBaseSet.getMediaItemCount() - mCurrent.size();
- }
-
- // Gets the MediaItems whose (post-deletion) index are in the range [start,
- // start + count). Because we remove some of the MediaItems, the index need
- // to be adjusted.
- //
- // For example, if there are 12 items in total. The deleted items are 3, 5,
- // 10, and the the requested range is [3, 7]:
- //
- // The original index: 0 1 2 3 4 5 6 7 8 9 A B C
- // The deleted items: X X X
- // The new index: 0 1 2 3 4 5 6 7 8 9
- // Requested: * * * * *
- //
- // We need to figure out the [3, 7] actually maps to the original index 4,
- // 6, 7, 8, 9.
- //
- // We can break the MediaItems into segments, each segment other than the
- // last one ends in a deleted item. The difference between the new index and
- // the original index increases with each segment:
- //
- // 0 1 2 X (new index = old index)
- // 4 X (new index = old index - 1)
- // 6 7 8 9 X (new index = old index - 2)
- // B C (new index = old index - 3)
- //
- @Override
- public ArrayList<MediaItem> getMediaItem(int start, int count) {
- if (count <= 0) return new ArrayList<MediaItem>();
-
- int end = start + count - 1;
- int n = mCurrent.size();
- // Find the segment that "start" falls into. Count the number of items
- // not yet deleted until it reaches "start".
- int i = 0;
- for (i = 0; i < n; i++) {
- Deletion d = mCurrent.get(i);
- if (d.index - i > start) break;
- }
- // Find the segment that "end" falls into.
- int j = i;
- for (; j < n; j++) {
- Deletion d = mCurrent.get(j);
- if (d.index - j > end) break;
- }
-
- // Now get enough to cover deleted items in [start, end]
- ArrayList<MediaItem> base = mBaseSet.getMediaItem(start + i, count + (j - i));
-
- // Remove the deleted items.
- for (int m = j - 1; m >= i; m--) {
- Deletion d = mCurrent.get(m);
- int k = d.index - (start + i);
- base.remove(k);
- }
- return base;
- }
-
- // We apply the pending requests in the mRequests to construct mCurrent in reload().
- @Override
- public long reload() {
- boolean newData = mBaseSet.reload() > mDataVersion;
- synchronized (mRequests) {
- if (!newData && mRequests.isEmpty()) {
- return mDataVersion;
- }
- for (int i = 0; i < mRequests.size(); i++) {
- Request r = mRequests.get(i);
- switch (r.type) {
- case REQUEST_ADD: {
- // Add the path into mCurrent if there is no duplicate.
- int n = mCurrent.size();
- int j;
- for (j = 0; j < n; j++) {
- if (mCurrent.get(j).path == r.path) break;
- }
- if (j == n) {
- mCurrent.add(new Deletion(r.path, r.indexHint));
- }
- break;
- }
- case REQUEST_REMOVE: {
- // Remove the path from mCurrent.
- int n = mCurrent.size();
- for (int j = 0; j < n; j++) {
- if (mCurrent.get(j).path == r.path) {
- mCurrent.remove(j);
- break;
- }
- }
- break;
- }
- case REQUEST_CLEAR: {
- mCurrent.clear();
- break;
- }
- }
- }
- mRequests.clear();
- }
-
- if (!mCurrent.isEmpty()) {
- // See if the elements in mCurrent can be found in the MediaSet. We
- // don't want to search the whole mBaseSet, so we just search a
- // small window that contains the index hints (plus some margin).
- int minIndex = mCurrent.get(0).index;
- int maxIndex = minIndex;
- for (int i = 1; i < mCurrent.size(); i++) {
- Deletion d = mCurrent.get(i);
- minIndex = Math.min(d.index, minIndex);
- maxIndex = Math.max(d.index, maxIndex);
- }
-
- int n = mBaseSet.getMediaItemCount();
- int from = Math.max(minIndex - 5, 0);
- int to = Math.min(maxIndex + 5, n);
- ArrayList<MediaItem> items = mBaseSet.getMediaItem(from, to - from);
- ArrayList<Deletion> result = new ArrayList<Deletion>();
- for (int i = 0; i < items.size(); i++) {
- MediaItem item = items.get(i);
- if (item == null) continue;
- Path p = item.getPath();
- // Find the matching path in mCurrent, if found move it to result
- for (int j = 0; j < mCurrent.size(); j++) {
- Deletion d = mCurrent.get(j);
- if (d.path == p) {
- d.index = from + i;
- result.add(d);
- mCurrent.remove(j);
- break;
- }
- }
- }
- mCurrent = result;
- }
-
- mDataVersion = nextVersionNumber();
- return mDataVersion;
- }
-
- private void sendRequest(int type, Path path, int indexHint) {
- Request r = new Request(type, path, indexHint);
- synchronized (mRequests) {
- mRequests.add(r);
- }
- notifyContentChanged();
- }
-
- @Override
- public void onContentDirty() {
- notifyContentChanged();
- }
-
- public void addDeletion(Path path, int indexHint) {
- sendRequest(REQUEST_ADD, path, indexHint);
- }
-
- public void removeDeletion(Path path) {
- sendRequest(REQUEST_REMOVE, path, 0 /* unused */);
- }
-
- public void clearDeletion() {
- sendRequest(REQUEST_CLEAR, null /* unused */ , 0 /* unused */);
- }
-
- // Returns number of deletions _in effect_ (the number will only gets
- // updated after a reload()).
- public int getNumberOfDeletions() {
- return mCurrent.size();
- }
-}
diff --git a/src/com/android/gallery3d/data/FilterEmptyPromptSet.java b/src/com/android/gallery3d/data/FilterEmptyPromptSet.java
deleted file mode 100644
index b576e06d4..000000000
--- a/src/com/android/gallery3d/data/FilterEmptyPromptSet.java
+++ /dev/null
@@ -1,82 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import java.util.ArrayList;
-
-public class FilterEmptyPromptSet extends MediaSet implements ContentListener {
- @SuppressWarnings("unused")
- private static final String TAG = "FilterEmptyPromptSet";
-
- private ArrayList<MediaItem> mEmptyItem;
- private MediaSet mBaseSet;
-
- public FilterEmptyPromptSet(Path path, MediaSet baseSet, MediaItem emptyItem) {
- super(path, INVALID_DATA_VERSION);
- mEmptyItem = new ArrayList<MediaItem>(1);
- mEmptyItem.add(emptyItem);
- mBaseSet = baseSet;
- mBaseSet.addContentListener(this);
- }
-
- @Override
- public int getMediaItemCount() {
- int itemCount = mBaseSet.getMediaItemCount();
- if (itemCount > 0) {
- return itemCount;
- } else {
- return 1;
- }
- }
-
- @Override
- public ArrayList<MediaItem> getMediaItem(int start, int count) {
- int itemCount = mBaseSet.getMediaItemCount();
- if (itemCount > 0) {
- return mBaseSet.getMediaItem(start, count);
- } else if (start == 0 && count == 1) {
- return mEmptyItem;
- } else {
- throw new ArrayIndexOutOfBoundsException();
- }
- }
-
- @Override
- public void onContentDirty() {
- notifyContentChanged();
- }
-
- @Override
- public boolean isLeafAlbum() {
- return true;
- }
-
- @Override
- public boolean isCameraRoll() {
- return mBaseSet.isCameraRoll();
- }
-
- @Override
- public long reload() {
- return mBaseSet.reload();
- }
-
- @Override
- public String getName() {
- return mBaseSet.getName();
- }
-}
diff --git a/src/com/android/gallery3d/data/FilterSource.java b/src/com/android/gallery3d/data/FilterSource.java
deleted file mode 100644
index d689fe336..000000000
--- a/src/com/android/gallery3d/data/FilterSource.java
+++ /dev/null
@@ -1,94 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.app.GalleryApp;
-
-public class FilterSource extends MediaSource {
- @SuppressWarnings("unused")
- private static final String TAG = "FilterSource";
- private static final int FILTER_BY_MEDIATYPE = 0;
- private static final int FILTER_BY_DELETE = 1;
- private static final int FILTER_BY_EMPTY = 2;
- private static final int FILTER_BY_EMPTY_ITEM = 3;
- private static final int FILTER_BY_CAMERA_SHORTCUT = 4;
- private static final int FILTER_BY_CAMERA_SHORTCUT_ITEM = 5;
-
- public static final String FILTER_EMPTY_ITEM = "/filter/empty_prompt";
- public static final String FILTER_CAMERA_SHORTCUT = "/filter/camera_shortcut";
- private static final String FILTER_CAMERA_SHORTCUT_ITEM = "/filter/camera_shortcut_item";
-
- private GalleryApp mApplication;
- private PathMatcher mMatcher;
- private MediaItem mEmptyItem;
- private MediaItem mCameraShortcutItem;
-
- public FilterSource(GalleryApp application) {
- super("filter");
- mApplication = application;
- mMatcher = new PathMatcher();
- mMatcher.add("/filter/mediatype/*/*", FILTER_BY_MEDIATYPE);
- mMatcher.add("/filter/delete/*", FILTER_BY_DELETE);
- mMatcher.add("/filter/empty/*", FILTER_BY_EMPTY);
- mMatcher.add(FILTER_EMPTY_ITEM, FILTER_BY_EMPTY_ITEM);
- mMatcher.add(FILTER_CAMERA_SHORTCUT, FILTER_BY_CAMERA_SHORTCUT);
- mMatcher.add(FILTER_CAMERA_SHORTCUT_ITEM, FILTER_BY_CAMERA_SHORTCUT_ITEM);
-
- mEmptyItem = new EmptyAlbumImage(Path.fromString(FILTER_EMPTY_ITEM),
- mApplication);
- mCameraShortcutItem = new CameraShortcutImage(
- Path.fromString(FILTER_CAMERA_SHORTCUT_ITEM), mApplication);
- }
-
- // The name we accept are:
- // /filter/mediatype/k/{set} where k is the media type we want.
- // /filter/delete/{set}
- @Override
- public MediaObject createMediaObject(Path path) {
- int matchType = mMatcher.match(path);
- DataManager dataManager = mApplication.getDataManager();
- switch (matchType) {
- case FILTER_BY_MEDIATYPE: {
- int mediaType = mMatcher.getIntVar(0);
- String setsName = mMatcher.getVar(1);
- MediaSet[] sets = dataManager.getMediaSetsFromString(setsName);
- return new FilterTypeSet(path, dataManager, sets[0], mediaType);
- }
- case FILTER_BY_DELETE: {
- String setsName = mMatcher.getVar(0);
- MediaSet[] sets = dataManager.getMediaSetsFromString(setsName);
- return new FilterDeleteSet(path, sets[0]);
- }
- case FILTER_BY_EMPTY: {
- String setsName = mMatcher.getVar(0);
- MediaSet[] sets = dataManager.getMediaSetsFromString(setsName);
- return new FilterEmptyPromptSet(path, sets[0], mEmptyItem);
- }
- case FILTER_BY_EMPTY_ITEM: {
- return mEmptyItem;
- }
- case FILTER_BY_CAMERA_SHORTCUT: {
- return new SingleItemAlbum(path, mCameraShortcutItem);
- }
- case FILTER_BY_CAMERA_SHORTCUT_ITEM: {
- return mCameraShortcutItem;
- }
- default:
- throw new RuntimeException("bad path: " + path);
- }
- }
-}
diff --git a/src/com/android/gallery3d/data/FilterTypeSet.java b/src/com/android/gallery3d/data/FilterTypeSet.java
deleted file mode 100644
index 477ef73ad..000000000
--- a/src/com/android/gallery3d/data/FilterTypeSet.java
+++ /dev/null
@@ -1,137 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import java.util.ArrayList;
-
-// FilterTypeSet filters a base MediaSet according to a matching media type.
-public class FilterTypeSet extends MediaSet implements ContentListener {
- @SuppressWarnings("unused")
- private static final String TAG = "FilterTypeSet";
-
- private final DataManager mDataManager;
- private final MediaSet mBaseSet;
- private final int mMediaType;
- private final ArrayList<Path> mPaths = new ArrayList<Path>();
- private final ArrayList<MediaSet> mAlbums = new ArrayList<MediaSet>();
-
- public FilterTypeSet(Path path, DataManager dataManager, MediaSet baseSet,
- int mediaType) {
- super(path, INVALID_DATA_VERSION);
- mDataManager = dataManager;
- mBaseSet = baseSet;
- mMediaType = mediaType;
- mBaseSet.addContentListener(this);
- }
-
- @Override
- public String getName() {
- return mBaseSet.getName();
- }
-
- @Override
- public MediaSet getSubMediaSet(int index) {
- return mAlbums.get(index);
- }
-
- @Override
- public int getSubMediaSetCount() {
- return mAlbums.size();
- }
-
- @Override
- public int getMediaItemCount() {
- return mPaths.size();
- }
-
- @Override
- public ArrayList<MediaItem> getMediaItem(int start, int count) {
- return ClusterAlbum.getMediaItemFromPath(
- mPaths, start, count, mDataManager);
- }
-
- @Override
- public long reload() {
- if (mBaseSet.reload() > mDataVersion) {
- updateData();
- mDataVersion = nextVersionNumber();
- }
- return mDataVersion;
- }
-
- @Override
- public void onContentDirty() {
- notifyContentChanged();
- }
-
- private void updateData() {
- // Albums
- mAlbums.clear();
- String basePath = "/filter/mediatype/" + mMediaType;
-
- for (int i = 0, n = mBaseSet.getSubMediaSetCount(); i < n; i++) {
- MediaSet set = mBaseSet.getSubMediaSet(i);
- String filteredPath = basePath + "/{" + set.getPath().toString() + "}";
- MediaSet filteredSet = mDataManager.getMediaSet(filteredPath);
- filteredSet.reload();
- if (filteredSet.getMediaItemCount() > 0
- || filteredSet.getSubMediaSetCount() > 0) {
- mAlbums.add(filteredSet);
- }
- }
-
- // Items
- mPaths.clear();
- final int total = mBaseSet.getMediaItemCount();
- final Path[] buf = new Path[total];
-
- mBaseSet.enumerateMediaItems(new MediaSet.ItemConsumer() {
- @Override
- public void consume(int index, MediaItem item) {
- if (item.getMediaType() == mMediaType) {
- if (index < 0 || index >= total) return;
- Path path = item.getPath();
- buf[index] = path;
- }
- }
- });
-
- for (int i = 0; i < total; i++) {
- if (buf[i] != null) {
- mPaths.add(buf[i]);
- }
- }
- }
-
- @Override
- public int getSupportedOperations() {
- return SUPPORT_SHARE | SUPPORT_DELETE;
- }
-
- @Override
- public void delete() {
- ItemConsumer consumer = new ItemConsumer() {
- @Override
- public void consume(int index, MediaItem item) {
- if ((item.getSupportedOperations() & SUPPORT_DELETE) != 0) {
- item.delete();
- }
- }
- };
- mDataManager.mapMediaItems(mPaths, consumer, 0);
- }
-}
diff --git a/src/com/android/gallery3d/data/ImageCacheRequest.java b/src/com/android/gallery3d/data/ImageCacheRequest.java
deleted file mode 100644
index 6cbc5c5ea..000000000
--- a/src/com/android/gallery3d/data/ImageCacheRequest.java
+++ /dev/null
@@ -1,102 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.common.BitmapUtils;
-import com.android.gallery3d.data.BytesBufferPool.BytesBuffer;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-abstract class ImageCacheRequest implements Job<Bitmap> {
- private static final String TAG = "ImageCacheRequest";
-
- protected GalleryApp mApplication;
- private Path mPath;
- private int mType;
- private int mTargetSize;
- private long mTimeModified;
-
- public ImageCacheRequest(GalleryApp application,
- Path path, long timeModified, int type, int targetSize) {
- mApplication = application;
- mPath = path;
- mType = type;
- mTargetSize = targetSize;
- mTimeModified = timeModified;
- }
-
- private String debugTag() {
- return mPath + "," + mTimeModified + "," +
- ((mType == MediaItem.TYPE_THUMBNAIL) ? "THUMB" :
- (mType == MediaItem.TYPE_MICROTHUMBNAIL) ? "MICROTHUMB" : "?");
- }
-
- @Override
- public Bitmap run(JobContext jc) {
- ImageCacheService cacheService = mApplication.getImageCacheService();
-
- BytesBuffer buffer = MediaItem.getBytesBufferPool().get();
- try {
- boolean found = cacheService.getImageData(mPath, mTimeModified, mType, buffer);
- if (jc.isCancelled()) return null;
- if (found) {
- BitmapFactory.Options options = new BitmapFactory.Options();
- options.inPreferredConfig = Bitmap.Config.ARGB_8888;
- Bitmap bitmap;
- if (mType == MediaItem.TYPE_MICROTHUMBNAIL) {
- bitmap = DecodeUtils.decodeUsingPool(jc,
- buffer.data, buffer.offset, buffer.length, options);
- } else {
- bitmap = DecodeUtils.decodeUsingPool(jc,
- buffer.data, buffer.offset, buffer.length, options);
- }
- if (bitmap == null && !jc.isCancelled()) {
- Log.w(TAG, "decode cached failed " + debugTag());
- }
- return bitmap;
- }
- } finally {
- MediaItem.getBytesBufferPool().recycle(buffer);
- }
- Bitmap bitmap = onDecodeOriginal(jc, mType);
- if (jc.isCancelled()) return null;
-
- if (bitmap == null) {
- Log.w(TAG, "decode orig failed " + debugTag());
- return null;
- }
-
- if (mType == MediaItem.TYPE_MICROTHUMBNAIL) {
- bitmap = BitmapUtils.resizeAndCropCenter(bitmap, mTargetSize, true);
- } else {
- bitmap = BitmapUtils.resizeDownBySideLength(bitmap, mTargetSize, true);
- }
- if (jc.isCancelled()) return null;
-
- byte[] array = BitmapUtils.compressToBytes(bitmap);
- if (jc.isCancelled()) return null;
-
- cacheService.putImageData(mPath, mTimeModified, mType, array);
- return bitmap;
- }
-
- public abstract Bitmap onDecodeOriginal(JobContext jc, int targetSize);
-}
diff --git a/src/com/android/gallery3d/data/ImageCacheService.java b/src/com/android/gallery3d/data/ImageCacheService.java
deleted file mode 100644
index 1c7cb8c5e..000000000
--- a/src/com/android/gallery3d/data/ImageCacheService.java
+++ /dev/null
@@ -1,123 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.Context;
-
-import com.android.gallery3d.common.BlobCache;
-import com.android.gallery3d.common.BlobCache.LookupRequest;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.BytesBufferPool.BytesBuffer;
-import com.android.gallery3d.util.CacheManager;
-import com.android.gallery3d.util.GalleryUtils;
-
-import java.io.IOException;
-import java.nio.ByteBuffer;
-
-public class ImageCacheService {
- @SuppressWarnings("unused")
- private static final String TAG = "ImageCacheService";
-
- private static final String IMAGE_CACHE_FILE = "imgcache";
- private static final int IMAGE_CACHE_MAX_ENTRIES = 5000;
- private static final int IMAGE_CACHE_MAX_BYTES = 200 * 1024 * 1024;
- private static final int IMAGE_CACHE_VERSION = 7;
-
- private BlobCache mCache;
-
- public ImageCacheService(Context context) {
- mCache = CacheManager.getCache(context, IMAGE_CACHE_FILE,
- IMAGE_CACHE_MAX_ENTRIES, IMAGE_CACHE_MAX_BYTES,
- IMAGE_CACHE_VERSION);
- }
-
- /**
- * Gets the cached image data for the given <code>path</code>,
- * <code>timeModified</code> and <code>type</code>.
- *
- * The image data will be stored in <code>buffer.data</code>, started from
- * <code>buffer.offset</code> for <code>buffer.length</code> bytes. If the
- * buffer.data is not big enough, a new byte array will be allocated and returned.
- *
- * @return true if the image data is found; false if not found.
- */
- public boolean getImageData(Path path, long timeModified, int type, BytesBuffer buffer) {
- byte[] key = makeKey(path, timeModified, type);
- long cacheKey = Utils.crc64Long(key);
- try {
- LookupRequest request = new LookupRequest();
- request.key = cacheKey;
- request.buffer = buffer.data;
- synchronized (mCache) {
- if (!mCache.lookup(request)) return false;
- }
- if (isSameKey(key, request.buffer)) {
- buffer.data = request.buffer;
- buffer.offset = key.length;
- buffer.length = request.length - buffer.offset;
- return true;
- }
- } catch (IOException ex) {
- // ignore.
- }
- return false;
- }
-
- public void putImageData(Path path, long timeModified, int type, byte[] value) {
- byte[] key = makeKey(path, timeModified, type);
- long cacheKey = Utils.crc64Long(key);
- ByteBuffer buffer = ByteBuffer.allocate(key.length + value.length);
- buffer.put(key);
- buffer.put(value);
- synchronized (mCache) {
- try {
- mCache.insert(cacheKey, buffer.array());
- } catch (IOException ex) {
- // ignore.
- }
- }
- }
-
- public void clearImageData(Path path, long timeModified, int type) {
- byte[] key = makeKey(path, timeModified, type);
- long cacheKey = Utils.crc64Long(key);
- synchronized (mCache) {
- try {
- mCache.clearEntry(cacheKey);
- } catch (IOException ex) {
- // ignore.
- }
- }
- }
-
- private static byte[] makeKey(Path path, long timeModified, int type) {
- return GalleryUtils.getBytes(path.toString() + "+" + timeModified + "+" + type);
- }
-
- private static boolean isSameKey(byte[] key, byte[] buffer) {
- int n = key.length;
- if (buffer.length < n) {
- return false;
- }
- for (int i = 0; i < n; ++i) {
- if (key[i] != buffer[i]) {
- return false;
- }
- }
- return true;
- }
-}
diff --git a/src/com/android/gallery3d/data/LocalAlbum.java b/src/com/android/gallery3d/data/LocalAlbum.java
deleted file mode 100644
index 7b7015af6..000000000
--- a/src/com/android/gallery3d/data/LocalAlbum.java
+++ /dev/null
@@ -1,325 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.ContentResolver;
-import android.content.res.Resources;
-import android.database.Cursor;
-import android.net.Uri;
-import android.os.Environment;
-import android.provider.MediaStore;
-import android.provider.MediaStore.Images;
-import android.provider.MediaStore.Images.ImageColumns;
-import android.provider.MediaStore.Video;
-import android.provider.MediaStore.Video.VideoColumns;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.util.BucketNames;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.MediaSetUtils;
-
-import java.io.File;
-import java.util.ArrayList;
-
-// LocalAlbumSet lists all media items in one bucket on local storage.
-// The media items need to be all images or all videos, but not both.
-public class LocalAlbum extends MediaSet {
- private static final String TAG = "LocalAlbum";
- private static final String[] COUNT_PROJECTION = { "count(*)" };
-
- private static final int INVALID_COUNT = -1;
- private final String mWhereClause;
- private final String mOrderClause;
- private final Uri mBaseUri;
- private final String[] mProjection;
-
- private final GalleryApp mApplication;
- private final ContentResolver mResolver;
- private final int mBucketId;
- private final String mName;
- private final boolean mIsImage;
- private final ChangeNotifier mNotifier;
- private final Path mItemPath;
- private int mCachedCount = INVALID_COUNT;
-
- public LocalAlbum(Path path, GalleryApp application, int bucketId,
- boolean isImage, String name) {
- super(path, nextVersionNumber());
- mApplication = application;
- mResolver = application.getContentResolver();
- mBucketId = bucketId;
- mName = name;
- mIsImage = isImage;
-
- if (isImage) {
- mWhereClause = ImageColumns.BUCKET_ID + " = ?";
- mOrderClause = ImageColumns.DATE_TAKEN + " DESC, "
- + ImageColumns._ID + " DESC";
- mBaseUri = Images.Media.EXTERNAL_CONTENT_URI;
- mProjection = LocalImage.PROJECTION;
- mItemPath = LocalImage.ITEM_PATH;
- } else {
- mWhereClause = VideoColumns.BUCKET_ID + " = ?";
- mOrderClause = VideoColumns.DATE_TAKEN + " DESC, "
- + VideoColumns._ID + " DESC";
- mBaseUri = Video.Media.EXTERNAL_CONTENT_URI;
- mProjection = LocalVideo.PROJECTION;
- mItemPath = LocalVideo.ITEM_PATH;
- }
-
- mNotifier = new ChangeNotifier(this, mBaseUri, application);
- }
-
- public LocalAlbum(Path path, GalleryApp application, int bucketId,
- boolean isImage) {
- this(path, application, bucketId, isImage,
- BucketHelper.getBucketName(
- application.getContentResolver(), bucketId));
- }
-
- @Override
- public boolean isCameraRoll() {
- return mBucketId == MediaSetUtils.CAMERA_BUCKET_ID;
- }
-
- @Override
- public Uri getContentUri() {
- if (mIsImage) {
- return MediaStore.Images.Media.EXTERNAL_CONTENT_URI.buildUpon()
- .appendQueryParameter(LocalSource.KEY_BUCKET_ID,
- String.valueOf(mBucketId)).build();
- } else {
- return MediaStore.Video.Media.EXTERNAL_CONTENT_URI.buildUpon()
- .appendQueryParameter(LocalSource.KEY_BUCKET_ID,
- String.valueOf(mBucketId)).build();
- }
- }
-
- @Override
- public ArrayList<MediaItem> getMediaItem(int start, int count) {
- DataManager dataManager = mApplication.getDataManager();
- Uri uri = mBaseUri.buildUpon()
- .appendQueryParameter("limit", start + "," + count).build();
- ArrayList<MediaItem> list = new ArrayList<MediaItem>();
- GalleryUtils.assertNotInRenderThread();
- Cursor cursor = mResolver.query(
- uri, mProjection, mWhereClause,
- new String[]{String.valueOf(mBucketId)},
- mOrderClause);
- if (cursor == null) {
- Log.w(TAG, "query fail: " + uri);
- return list;
- }
-
- try {
- while (cursor.moveToNext()) {
- int id = cursor.getInt(0); // _id must be in the first column
- Path childPath = mItemPath.getChild(id);
- MediaItem item = loadOrUpdateItem(childPath, cursor,
- dataManager, mApplication, mIsImage);
- list.add(item);
- }
- } finally {
- cursor.close();
- }
- return list;
- }
-
- private static MediaItem loadOrUpdateItem(Path path, Cursor cursor,
- DataManager dataManager, GalleryApp app, boolean isImage) {
- synchronized (DataManager.LOCK) {
- LocalMediaItem item = (LocalMediaItem) dataManager.peekMediaObject(path);
- if (item == null) {
- if (isImage) {
- item = new LocalImage(path, app, cursor);
- } else {
- item = new LocalVideo(path, app, cursor);
- }
- } else {
- item.updateContent(cursor);
- }
- return item;
- }
- }
-
- // The pids array are sorted by the (path) id.
- public static MediaItem[] getMediaItemById(
- GalleryApp application, boolean isImage, ArrayList<Integer> ids) {
- // get the lower and upper bound of (path) id
- MediaItem[] result = new MediaItem[ids.size()];
- if (ids.isEmpty()) return result;
- int idLow = ids.get(0);
- int idHigh = ids.get(ids.size() - 1);
-
- // prepare the query parameters
- Uri baseUri;
- String[] projection;
- Path itemPath;
- if (isImage) {
- baseUri = Images.Media.EXTERNAL_CONTENT_URI;
- projection = LocalImage.PROJECTION;
- itemPath = LocalImage.ITEM_PATH;
- } else {
- baseUri = Video.Media.EXTERNAL_CONTENT_URI;
- projection = LocalVideo.PROJECTION;
- itemPath = LocalVideo.ITEM_PATH;
- }
-
- ContentResolver resolver = application.getContentResolver();
- DataManager dataManager = application.getDataManager();
- Cursor cursor = resolver.query(baseUri, projection, "_id BETWEEN ? AND ?",
- new String[]{String.valueOf(idLow), String.valueOf(idHigh)},
- "_id");
- if (cursor == null) {
- Log.w(TAG, "query fail" + baseUri);
- return result;
- }
- try {
- int n = ids.size();
- int i = 0;
-
- while (i < n && cursor.moveToNext()) {
- int id = cursor.getInt(0); // _id must be in the first column
-
- // Match id with the one on the ids list.
- if (ids.get(i) > id) {
- continue;
- }
-
- while (ids.get(i) < id) {
- if (++i >= n) {
- return result;
- }
- }
-
- Path childPath = itemPath.getChild(id);
- MediaItem item = loadOrUpdateItem(childPath, cursor, dataManager,
- application, isImage);
- result[i] = item;
- ++i;
- }
- return result;
- } finally {
- cursor.close();
- }
- }
-
- public static Cursor getItemCursor(ContentResolver resolver, Uri uri,
- String[] projection, int id) {
- return resolver.query(uri, projection, "_id=?",
- new String[]{String.valueOf(id)}, null);
- }
-
- @Override
- public int getMediaItemCount() {
- if (mCachedCount == INVALID_COUNT) {
- Cursor cursor = mResolver.query(
- mBaseUri, COUNT_PROJECTION, mWhereClause,
- new String[]{String.valueOf(mBucketId)}, null);
- if (cursor == null) {
- Log.w(TAG, "query fail");
- return 0;
- }
- try {
- Utils.assertTrue(cursor.moveToNext());
- mCachedCount = cursor.getInt(0);
- } finally {
- cursor.close();
- }
- }
- return mCachedCount;
- }
-
- @Override
- public String getName() {
- return getLocalizedName(mApplication.getResources(), mBucketId, mName);
- }
-
- @Override
- public long reload() {
- if (mNotifier.isDirty()) {
- mDataVersion = nextVersionNumber();
- mCachedCount = INVALID_COUNT;
- }
- return mDataVersion;
- }
-
- @Override
- public int getSupportedOperations() {
- return SUPPORT_DELETE | SUPPORT_SHARE | SUPPORT_INFO;
- }
-
- @Override
- public void delete() {
- GalleryUtils.assertNotInRenderThread();
- mResolver.delete(mBaseUri, mWhereClause,
- new String[]{String.valueOf(mBucketId)});
- }
-
- @Override
- public boolean isLeafAlbum() {
- return true;
- }
-
- public static String getLocalizedName(Resources res, int bucketId,
- String name) {
- if (bucketId == MediaSetUtils.CAMERA_BUCKET_ID) {
- return res.getString(R.string.folder_camera);
- } else if (bucketId == MediaSetUtils.DOWNLOAD_BUCKET_ID) {
- return res.getString(R.string.folder_download);
- } else if (bucketId == MediaSetUtils.IMPORTED_BUCKET_ID) {
- return res.getString(R.string.folder_imported);
- } else if (bucketId == MediaSetUtils.SNAPSHOT_BUCKET_ID) {
- return res.getString(R.string.folder_screenshot);
- } else if (bucketId == MediaSetUtils.EDITED_ONLINE_PHOTOS_BUCKET_ID) {
- return res.getString(R.string.folder_edited_online_photos);
- } else {
- return name;
- }
- }
-
- // Relative path is the absolute path minus external storage path
- public static String getRelativePath(int bucketId) {
- String relativePath = "/";
- if (bucketId == MediaSetUtils.CAMERA_BUCKET_ID) {
- relativePath += BucketNames.CAMERA;
- } else if (bucketId == MediaSetUtils.DOWNLOAD_BUCKET_ID) {
- relativePath += BucketNames.DOWNLOAD;
- } else if (bucketId == MediaSetUtils.IMPORTED_BUCKET_ID) {
- relativePath += BucketNames.IMPORTED;
- } else if (bucketId == MediaSetUtils.SNAPSHOT_BUCKET_ID) {
- relativePath += BucketNames.SCREENSHOTS;
- } else if (bucketId == MediaSetUtils.EDITED_ONLINE_PHOTOS_BUCKET_ID) {
- relativePath += BucketNames.EDITED_ONLINE_PHOTOS;
- } else {
- // If the first few cases didn't hit the matching path, do a
- // thorough search in the local directories.
- File extStorage = Environment.getExternalStorageDirectory();
- String path = GalleryUtils.searchDirForPath(extStorage, bucketId);
- if (path == null) {
- Log.w(TAG, "Relative path for bucket id: " + bucketId + " is not found.");
- relativePath = null;
- } else {
- relativePath = path.substring(extStorage.getAbsolutePath().length());
- }
- }
- return relativePath;
- }
-
-}
diff --git a/src/com/android/gallery3d/data/LocalAlbumSet.java b/src/com/android/gallery3d/data/LocalAlbumSet.java
deleted file mode 100644
index b2b4b8c5d..000000000
--- a/src/com/android/gallery3d/data/LocalAlbumSet.java
+++ /dev/null
@@ -1,211 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.net.Uri;
-import android.os.Handler;
-import android.provider.MediaStore.Images;
-import android.provider.MediaStore.Video;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.data.BucketHelper.BucketEntry;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.FutureListener;
-import com.android.gallery3d.util.MediaSetUtils;
-import com.android.gallery3d.util.ThreadPool;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.util.ArrayList;
-import java.util.Comparator;
-
-// LocalAlbumSet lists all image or video albums in the local storage.
-// The path should be "/local/image", "local/video" or "/local/all"
-public class LocalAlbumSet extends MediaSet
- implements FutureListener<ArrayList<MediaSet>> {
- @SuppressWarnings("unused")
- private static final String TAG = "LocalAlbumSet";
-
- public static final Path PATH_ALL = Path.fromString("/local/all");
- public static final Path PATH_IMAGE = Path.fromString("/local/image");
- public static final Path PATH_VIDEO = Path.fromString("/local/video");
-
- private static final Uri[] mWatchUris =
- {Images.Media.EXTERNAL_CONTENT_URI, Video.Media.EXTERNAL_CONTENT_URI};
-
- private final GalleryApp mApplication;
- private final int mType;
- private ArrayList<MediaSet> mAlbums = new ArrayList<MediaSet>();
- private final ChangeNotifier mNotifier;
- private final String mName;
- private final Handler mHandler;
- private boolean mIsLoading;
-
- private Future<ArrayList<MediaSet>> mLoadTask;
- private ArrayList<MediaSet> mLoadBuffer;
-
- public LocalAlbumSet(Path path, GalleryApp application) {
- super(path, nextVersionNumber());
- mApplication = application;
- mHandler = new Handler(application.getMainLooper());
- mType = getTypeFromPath(path);
- mNotifier = new ChangeNotifier(this, mWatchUris, application);
- mName = application.getResources().getString(
- R.string.set_label_local_albums);
- }
-
- private static int getTypeFromPath(Path path) {
- String name[] = path.split();
- if (name.length < 2) {
- throw new IllegalArgumentException(path.toString());
- }
- return getTypeFromString(name[1]);
- }
-
- @Override
- public MediaSet getSubMediaSet(int index) {
- return mAlbums.get(index);
- }
-
- @Override
- public int getSubMediaSetCount() {
- return mAlbums.size();
- }
-
- @Override
- public String getName() {
- return mName;
- }
-
- private static int findBucket(BucketEntry entries[], int bucketId) {
- for (int i = 0, n = entries.length; i < n; ++i) {
- if (entries[i].bucketId == bucketId) return i;
- }
- return -1;
- }
-
- private class AlbumsLoader implements ThreadPool.Job<ArrayList<MediaSet>> {
-
- @Override
- @SuppressWarnings("unchecked")
- public ArrayList<MediaSet> run(JobContext jc) {
- // Note: it will be faster if we only select media_type and bucket_id.
- // need to test the performance if that is worth
- BucketEntry[] entries = BucketHelper.loadBucketEntries(
- jc, mApplication.getContentResolver(), mType);
-
- if (jc.isCancelled()) return null;
-
- int offset = 0;
- // Move camera and download bucket to the front, while keeping the
- // order of others.
- int index = findBucket(entries, MediaSetUtils.CAMERA_BUCKET_ID);
- if (index != -1) {
- circularShiftRight(entries, offset++, index);
- }
- index = findBucket(entries, MediaSetUtils.DOWNLOAD_BUCKET_ID);
- if (index != -1) {
- circularShiftRight(entries, offset++, index);
- }
-
- ArrayList<MediaSet> albums = new ArrayList<MediaSet>();
- DataManager dataManager = mApplication.getDataManager();
- for (BucketEntry entry : entries) {
- MediaSet album = getLocalAlbum(dataManager,
- mType, mPath, entry.bucketId, entry.bucketName);
- albums.add(album);
- }
- return albums;
- }
- }
-
- private MediaSet getLocalAlbum(
- DataManager manager, int type, Path parent, int id, String name) {
- synchronized (DataManager.LOCK) {
- Path path = parent.getChild(id);
- MediaObject object = manager.peekMediaObject(path);
- if (object != null) return (MediaSet) object;
- switch (type) {
- case MEDIA_TYPE_IMAGE:
- return new LocalAlbum(path, mApplication, id, true, name);
- case MEDIA_TYPE_VIDEO:
- return new LocalAlbum(path, mApplication, id, false, name);
- case MEDIA_TYPE_ALL:
- Comparator<MediaItem> comp = DataManager.sDateTakenComparator;
- return new LocalMergeAlbum(path, comp, new MediaSet[] {
- getLocalAlbum(manager, MEDIA_TYPE_IMAGE, PATH_IMAGE, id, name),
- getLocalAlbum(manager, MEDIA_TYPE_VIDEO, PATH_VIDEO, id, name)}, id);
- }
- throw new IllegalArgumentException(String.valueOf(type));
- }
- }
-
- @Override
- public synchronized boolean isLoading() {
- return mIsLoading;
- }
-
- @Override
- // synchronized on this function for
- // 1. Prevent calling reload() concurrently.
- // 2. Prevent calling onFutureDone() and reload() concurrently
- public synchronized long reload() {
- if (mNotifier.isDirty()) {
- if (mLoadTask != null) mLoadTask.cancel();
- mIsLoading = true;
- mLoadTask = mApplication.getThreadPool().submit(new AlbumsLoader(), this);
- }
- if (mLoadBuffer != null) {
- mAlbums = mLoadBuffer;
- mLoadBuffer = null;
- for (MediaSet album : mAlbums) {
- album.reload();
- }
- mDataVersion = nextVersionNumber();
- }
- return mDataVersion;
- }
-
- @Override
- public synchronized void onFutureDone(Future<ArrayList<MediaSet>> future) {
- if (mLoadTask != future) return; // ignore, wait for the latest task
- mLoadBuffer = future.get();
- mIsLoading = false;
- if (mLoadBuffer == null) mLoadBuffer = new ArrayList<MediaSet>();
- mHandler.post(new Runnable() {
- @Override
- public void run() {
- notifyContentChanged();
- }
- });
- }
-
- // For debug only. Fake there is a ContentObserver.onChange() event.
- void fakeChange() {
- mNotifier.fakeChange();
- }
-
- // Circular shift the array range from a[i] to a[j] (inclusive). That is,
- // a[i] -> a[i+1] -> a[i+2] -> ... -> a[j], and a[j] -> a[i]
- private static <T> void circularShiftRight(T[] array, int i, int j) {
- T temp = array[j];
- for (int k = j; k > i; k--) {
- array[k] = array[k - 1];
- }
- array[i] = temp;
- }
-}
diff --git a/src/com/android/gallery3d/data/LocalImage.java b/src/com/android/gallery3d/data/LocalImage.java
deleted file mode 100644
index cc70dd457..000000000
--- a/src/com/android/gallery3d/data/LocalImage.java
+++ /dev/null
@@ -1,355 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.annotation.TargetApi;
-import android.content.ContentResolver;
-import android.content.ContentValues;
-import android.database.Cursor;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.BitmapRegionDecoder;
-import android.net.Uri;
-import android.os.Build;
-import android.provider.MediaStore.Images;
-import android.provider.MediaStore.Images.ImageColumns;
-import android.provider.MediaStore.MediaColumns;
-import android.util.Log;
-
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.app.PanoramaMetadataSupport;
-import com.android.gallery3d.app.StitchingProgressManager;
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.common.BitmapUtils;
-import com.android.gallery3d.exif.ExifInterface;
-import com.android.gallery3d.exif.ExifTag;
-import com.android.gallery3d.filtershow.tools.SaveImage;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-import com.android.gallery3d.util.UpdateHelper;
-
-import java.io.File;
-import java.io.FileNotFoundException;
-import java.io.IOException;
-
-// LocalImage represents an image in the local storage.
-public class LocalImage extends LocalMediaItem {
- private static final String TAG = "LocalImage";
-
- static final Path ITEM_PATH = Path.fromString("/local/image/item");
-
- // Must preserve order between these indices and the order of the terms in
- // the following PROJECTION array.
- private static final int INDEX_ID = 0;
- private static final int INDEX_CAPTION = 1;
- private static final int INDEX_MIME_TYPE = 2;
- private static final int INDEX_LATITUDE = 3;
- private static final int INDEX_LONGITUDE = 4;
- private static final int INDEX_DATE_TAKEN = 5;
- private static final int INDEX_DATE_ADDED = 6;
- private static final int INDEX_DATE_MODIFIED = 7;
- private static final int INDEX_DATA = 8;
- private static final int INDEX_ORIENTATION = 9;
- private static final int INDEX_BUCKET_ID = 10;
- private static final int INDEX_SIZE = 11;
- private static final int INDEX_WIDTH = 12;
- private static final int INDEX_HEIGHT = 13;
-
- static final String[] PROJECTION = {
- ImageColumns._ID, // 0
- ImageColumns.TITLE, // 1
- ImageColumns.MIME_TYPE, // 2
- ImageColumns.LATITUDE, // 3
- ImageColumns.LONGITUDE, // 4
- ImageColumns.DATE_TAKEN, // 5
- ImageColumns.DATE_ADDED, // 6
- ImageColumns.DATE_MODIFIED, // 7
- ImageColumns.DATA, // 8
- ImageColumns.ORIENTATION, // 9
- ImageColumns.BUCKET_ID, // 10
- ImageColumns.SIZE, // 11
- "0", // 12
- "0" // 13
- };
-
- static {
- updateWidthAndHeightProjection();
- }
-
- @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
- private static void updateWidthAndHeightProjection() {
- if (ApiHelper.HAS_MEDIA_COLUMNS_WIDTH_AND_HEIGHT) {
- PROJECTION[INDEX_WIDTH] = MediaColumns.WIDTH;
- PROJECTION[INDEX_HEIGHT] = MediaColumns.HEIGHT;
- }
- }
-
- private final GalleryApp mApplication;
-
- public int rotation;
-
- private PanoramaMetadataSupport mPanoramaMetadata = new PanoramaMetadataSupport(this);
-
- public LocalImage(Path path, GalleryApp application, Cursor cursor) {
- super(path, nextVersionNumber());
- mApplication = application;
- loadFromCursor(cursor);
- }
-
- public LocalImage(Path path, GalleryApp application, int id) {
- super(path, nextVersionNumber());
- mApplication = application;
- ContentResolver resolver = mApplication.getContentResolver();
- Uri uri = Images.Media.EXTERNAL_CONTENT_URI;
- Cursor cursor = LocalAlbum.getItemCursor(resolver, uri, PROJECTION, id);
- if (cursor == null) {
- throw new RuntimeException("cannot get cursor for: " + path);
- }
- try {
- if (cursor.moveToNext()) {
- loadFromCursor(cursor);
- } else {
- throw new RuntimeException("cannot find data for: " + path);
- }
- } finally {
- cursor.close();
- }
- }
-
- private void loadFromCursor(Cursor cursor) {
- id = cursor.getInt(INDEX_ID);
- caption = cursor.getString(INDEX_CAPTION);
- mimeType = cursor.getString(INDEX_MIME_TYPE);
- latitude = cursor.getDouble(INDEX_LATITUDE);
- longitude = cursor.getDouble(INDEX_LONGITUDE);
- dateTakenInMs = cursor.getLong(INDEX_DATE_TAKEN);
- dateAddedInSec = cursor.getLong(INDEX_DATE_ADDED);
- dateModifiedInSec = cursor.getLong(INDEX_DATE_MODIFIED);
- filePath = cursor.getString(INDEX_DATA);
- rotation = cursor.getInt(INDEX_ORIENTATION);
- bucketId = cursor.getInt(INDEX_BUCKET_ID);
- fileSize = cursor.getLong(INDEX_SIZE);
- width = cursor.getInt(INDEX_WIDTH);
- height = cursor.getInt(INDEX_HEIGHT);
- }
-
- @Override
- protected boolean updateFromCursor(Cursor cursor) {
- UpdateHelper uh = new UpdateHelper();
- id = uh.update(id, cursor.getInt(INDEX_ID));
- caption = uh.update(caption, cursor.getString(INDEX_CAPTION));
- mimeType = uh.update(mimeType, cursor.getString(INDEX_MIME_TYPE));
- latitude = uh.update(latitude, cursor.getDouble(INDEX_LATITUDE));
- longitude = uh.update(longitude, cursor.getDouble(INDEX_LONGITUDE));
- dateTakenInMs = uh.update(
- dateTakenInMs, cursor.getLong(INDEX_DATE_TAKEN));
- dateAddedInSec = uh.update(
- dateAddedInSec, cursor.getLong(INDEX_DATE_ADDED));
- dateModifiedInSec = uh.update(
- dateModifiedInSec, cursor.getLong(INDEX_DATE_MODIFIED));
- filePath = uh.update(filePath, cursor.getString(INDEX_DATA));
- rotation = uh.update(rotation, cursor.getInt(INDEX_ORIENTATION));
- bucketId = uh.update(bucketId, cursor.getInt(INDEX_BUCKET_ID));
- fileSize = uh.update(fileSize, cursor.getLong(INDEX_SIZE));
- width = uh.update(width, cursor.getInt(INDEX_WIDTH));
- height = uh.update(height, cursor.getInt(INDEX_HEIGHT));
- return uh.isUpdated();
- }
-
- @Override
- public Job<Bitmap> requestImage(int type) {
- return new LocalImageRequest(mApplication, mPath, dateModifiedInSec,
- type, filePath);
- }
-
- public static class LocalImageRequest extends ImageCacheRequest {
- private String mLocalFilePath;
-
- LocalImageRequest(GalleryApp application, Path path, long timeModified,
- int type, String localFilePath) {
- super(application, path, timeModified, type,
- MediaItem.getTargetSize(type));
- mLocalFilePath = localFilePath;
- }
-
- @Override
- public Bitmap onDecodeOriginal(JobContext jc, final int type) {
- BitmapFactory.Options options = new BitmapFactory.Options();
- options.inPreferredConfig = Bitmap.Config.ARGB_8888;
- int targetSize = MediaItem.getTargetSize(type);
-
- // try to decode from JPEG EXIF
- if (type == MediaItem.TYPE_MICROTHUMBNAIL) {
- ExifInterface exif = new ExifInterface();
- byte[] thumbData = null;
- try {
- exif.readExif(mLocalFilePath);
- thumbData = exif.getThumbnail();
- } catch (FileNotFoundException e) {
- Log.w(TAG, "failed to find file to read thumbnail: " + mLocalFilePath);
- } catch (IOException e) {
- Log.w(TAG, "failed to get thumbnail from: " + mLocalFilePath);
- }
- if (thumbData != null) {
- Bitmap bitmap = DecodeUtils.decodeIfBigEnough(
- jc, thumbData, options, targetSize);
- if (bitmap != null) return bitmap;
- }
- }
-
- return DecodeUtils.decodeThumbnail(jc, mLocalFilePath, options, targetSize, type);
- }
- }
-
- @Override
- public Job<BitmapRegionDecoder> requestLargeImage() {
- return new LocalLargeImageRequest(filePath);
- }
-
- public static class LocalLargeImageRequest
- implements Job<BitmapRegionDecoder> {
- String mLocalFilePath;
-
- public LocalLargeImageRequest(String localFilePath) {
- mLocalFilePath = localFilePath;
- }
-
- @Override
- public BitmapRegionDecoder run(JobContext jc) {
- return DecodeUtils.createBitmapRegionDecoder(jc, mLocalFilePath, false);
- }
- }
-
- @Override
- public int getSupportedOperations() {
- StitchingProgressManager progressManager = mApplication.getStitchingProgressManager();
- if (progressManager != null && progressManager.getProgress(getContentUri()) != null) {
- return 0; // doesn't support anything while stitching!
- }
- int operation = SUPPORT_DELETE | SUPPORT_SHARE | SUPPORT_CROP
- | SUPPORT_SETAS | SUPPORT_EDIT | SUPPORT_INFO;
- if (BitmapUtils.isSupportedByRegionDecoder(mimeType)) {
- operation |= SUPPORT_FULL_IMAGE;
- }
-
- if (BitmapUtils.isRotationSupported(mimeType)) {
- operation |= SUPPORT_ROTATE;
- }
-
- if (GalleryUtils.isValidLocation(latitude, longitude)) {
- operation |= SUPPORT_SHOW_ON_MAP;
- }
- return operation;
- }
-
- @Override
- public void getPanoramaSupport(PanoramaSupportCallback callback) {
- mPanoramaMetadata.getPanoramaSupport(mApplication, callback);
- }
-
- @Override
- public void clearCachedPanoramaSupport() {
- mPanoramaMetadata.clearCachedValues();
- }
-
- @Override
- public void delete() {
- GalleryUtils.assertNotInRenderThread();
- Uri baseUri = Images.Media.EXTERNAL_CONTENT_URI;
- ContentResolver contentResolver = mApplication.getContentResolver();
- SaveImage.deleteAuxFiles(contentResolver, getContentUri());
- contentResolver.delete(baseUri, "_id=?",
- new String[]{String.valueOf(id)});
- }
-
- @Override
- public void rotate(int degrees) {
- GalleryUtils.assertNotInRenderThread();
- Uri baseUri = Images.Media.EXTERNAL_CONTENT_URI;
- ContentValues values = new ContentValues();
- int rotation = (this.rotation + degrees) % 360;
- if (rotation < 0) rotation += 360;
-
- if (mimeType.equalsIgnoreCase("image/jpeg")) {
- ExifInterface exifInterface = new ExifInterface();
- ExifTag tag = exifInterface.buildTag(ExifInterface.TAG_ORIENTATION,
- ExifInterface.getOrientationValueForRotation(rotation));
- if(tag != null) {
- exifInterface.setTag(tag);
- try {
- exifInterface.forceRewriteExif(filePath);
- fileSize = new File(filePath).length();
- values.put(Images.Media.SIZE, fileSize);
- } catch (FileNotFoundException e) {
- Log.w(TAG, "cannot find file to set exif: " + filePath);
- } catch (IOException e) {
- Log.w(TAG, "cannot set exif data: " + filePath);
- }
- } else {
- Log.w(TAG, "Could not build tag: " + ExifInterface.TAG_ORIENTATION);
- }
- }
-
- values.put(Images.Media.ORIENTATION, rotation);
- mApplication.getContentResolver().update(baseUri, values, "_id=?",
- new String[]{String.valueOf(id)});
- }
-
- @Override
- public Uri getContentUri() {
- Uri baseUri = Images.Media.EXTERNAL_CONTENT_URI;
- return baseUri.buildUpon().appendPath(String.valueOf(id)).build();
- }
-
- @Override
- public int getMediaType() {
- return MEDIA_TYPE_IMAGE;
- }
-
- @Override
- public MediaDetails getDetails() {
- MediaDetails details = super.getDetails();
- details.addDetail(MediaDetails.INDEX_ORIENTATION, Integer.valueOf(rotation));
- if (MIME_TYPE_JPEG.equals(mimeType)) {
- // ExifInterface returns incorrect values for photos in other format.
- // For example, the width and height of an webp images is always '0'.
- MediaDetails.extractExifInfo(details, filePath);
- }
- return details;
- }
-
- @Override
- public int getRotation() {
- return rotation;
- }
-
- @Override
- public int getWidth() {
- return width;
- }
-
- @Override
- public int getHeight() {
- return height;
- }
-
- @Override
- public String getFilePath() {
- return filePath;
- }
-}
diff --git a/src/com/android/gallery3d/data/LocalMediaItem.java b/src/com/android/gallery3d/data/LocalMediaItem.java
deleted file mode 100644
index 7e003cd3a..000000000
--- a/src/com/android/gallery3d/data/LocalMediaItem.java
+++ /dev/null
@@ -1,109 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.database.Cursor;
-
-import com.android.gallery3d.util.GalleryUtils;
-
-import java.text.DateFormat;
-import java.util.Date;
-
-//
-// LocalMediaItem is an abstract class captures those common fields
-// in LocalImage and LocalVideo.
-//
-public abstract class LocalMediaItem extends MediaItem {
-
- @SuppressWarnings("unused")
- private static final String TAG = "LocalMediaItem";
-
- // database fields
- public int id;
- public String caption;
- public String mimeType;
- public long fileSize;
- public double latitude = INVALID_LATLNG;
- public double longitude = INVALID_LATLNG;
- public long dateTakenInMs;
- public long dateAddedInSec;
- public long dateModifiedInSec;
- public String filePath;
- public int bucketId;
- public int width;
- public int height;
-
- public LocalMediaItem(Path path, long version) {
- super(path, version);
- }
-
- @Override
- public long getDateInMs() {
- return dateTakenInMs;
- }
-
- @Override
- public String getName() {
- return caption;
- }
-
- @Override
- public void getLatLong(double[] latLong) {
- latLong[0] = latitude;
- latLong[1] = longitude;
- }
-
- abstract protected boolean updateFromCursor(Cursor cursor);
-
- public int getBucketId() {
- return bucketId;
- }
-
- protected void updateContent(Cursor cursor) {
- if (updateFromCursor(cursor)) {
- mDataVersion = nextVersionNumber();
- }
- }
-
- @Override
- public MediaDetails getDetails() {
- MediaDetails details = super.getDetails();
- details.addDetail(MediaDetails.INDEX_PATH, filePath);
- details.addDetail(MediaDetails.INDEX_TITLE, caption);
- DateFormat formater = DateFormat.getDateTimeInstance();
- details.addDetail(MediaDetails.INDEX_DATETIME,
- formater.format(new Date(dateModifiedInSec * 1000)));
- details.addDetail(MediaDetails.INDEX_WIDTH, width);
- details.addDetail(MediaDetails.INDEX_HEIGHT, height);
-
- if (GalleryUtils.isValidLocation(latitude, longitude)) {
- details.addDetail(MediaDetails.INDEX_LOCATION, new double[] {latitude, longitude});
- }
- if (fileSize > 0) details.addDetail(MediaDetails.INDEX_SIZE, fileSize);
- return details;
- }
-
- @Override
- public String getMimeType() {
- return mimeType;
- }
-
- @Override
- public long getSize() {
- return fileSize;
- }
-}
diff --git a/src/com/android/gallery3d/data/LocalMergeAlbum.java b/src/com/android/gallery3d/data/LocalMergeAlbum.java
deleted file mode 100644
index f0b5e5726..000000000
--- a/src/com/android/gallery3d/data/LocalMergeAlbum.java
+++ /dev/null
@@ -1,257 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.net.Uri;
-import android.provider.MediaStore;
-
-import com.android.gallery3d.common.ApiHelper;
-
-import java.lang.ref.SoftReference;
-import java.util.ArrayList;
-import java.util.Comparator;
-import java.util.NoSuchElementException;
-import java.util.SortedMap;
-import java.util.TreeMap;
-
-// MergeAlbum merges items from two or more MediaSets. It uses a Comparator to
-// determine the order of items. The items are assumed to be sorted in the input
-// media sets (with the same order that the Comparator uses).
-//
-// This only handles MediaItems, not SubMediaSets.
-public class LocalMergeAlbum extends MediaSet implements ContentListener {
- @SuppressWarnings("unused")
- private static final String TAG = "LocalMergeAlbum";
- private static final int PAGE_SIZE = 64;
-
- private final Comparator<MediaItem> mComparator;
- private final MediaSet[] mSources;
-
- private FetchCache[] mFetcher;
- private int mSupportedOperation;
- private int mBucketId;
-
- // mIndex maps global position to the position of each underlying media sets.
- private TreeMap<Integer, int[]> mIndex = new TreeMap<Integer, int[]>();
-
- public LocalMergeAlbum(
- Path path, Comparator<MediaItem> comparator, MediaSet[] sources, int bucketId) {
- super(path, INVALID_DATA_VERSION);
- mComparator = comparator;
- mSources = sources;
- mBucketId = bucketId;
- for (MediaSet set : mSources) {
- set.addContentListener(this);
- }
- reload();
- }
-
- @Override
- public boolean isCameraRoll() {
- if (mSources.length == 0) return false;
- for(MediaSet set : mSources) {
- if (!set.isCameraRoll()) return false;
- }
- return true;
- }
-
- private void updateData() {
- ArrayList<MediaSet> matches = new ArrayList<MediaSet>();
- int supported = mSources.length == 0 ? 0 : MediaItem.SUPPORT_ALL;
- mFetcher = new FetchCache[mSources.length];
- for (int i = 0, n = mSources.length; i < n; ++i) {
- mFetcher[i] = new FetchCache(mSources[i]);
- supported &= mSources[i].getSupportedOperations();
- }
- mSupportedOperation = supported;
- mIndex.clear();
- mIndex.put(0, new int[mSources.length]);
- }
-
- private void invalidateCache() {
- for (int i = 0, n = mSources.length; i < n; i++) {
- mFetcher[i].invalidate();
- }
- mIndex.clear();
- mIndex.put(0, new int[mSources.length]);
- }
-
- @Override
- public Uri getContentUri() {
- String bucketId = String.valueOf(mBucketId);
- if (ApiHelper.HAS_MEDIA_PROVIDER_FILES_TABLE) {
- return MediaStore.Files.getContentUri("external").buildUpon()
- .appendQueryParameter(LocalSource.KEY_BUCKET_ID, bucketId)
- .build();
- } else {
- // We don't have a single URL for a merged image before ICS
- // So we used the image's URL as a substitute.
- return MediaStore.Images.Media.EXTERNAL_CONTENT_URI.buildUpon()
- .appendQueryParameter(LocalSource.KEY_BUCKET_ID, bucketId)
- .build();
- }
- }
-
- @Override
- public String getName() {
- return mSources.length == 0 ? "" : mSources[0].getName();
- }
-
- @Override
- public int getMediaItemCount() {
- return getTotalMediaItemCount();
- }
-
- @Override
- public ArrayList<MediaItem> getMediaItem(int start, int count) {
-
- // First find the nearest mark position <= start.
- SortedMap<Integer, int[]> head = mIndex.headMap(start + 1);
- int markPos = head.lastKey();
- int[] subPos = head.get(markPos).clone();
- MediaItem[] slot = new MediaItem[mSources.length];
-
- int size = mSources.length;
-
- // fill all slots
- for (int i = 0; i < size; i++) {
- slot[i] = mFetcher[i].getItem(subPos[i]);
- }
-
- ArrayList<MediaItem> result = new ArrayList<MediaItem>();
-
- for (int i = markPos; i < start + count; i++) {
- int k = -1; // k points to the best slot up to now.
- for (int j = 0; j < size; j++) {
- if (slot[j] != null) {
- if (k == -1 || mComparator.compare(slot[j], slot[k]) < 0) {
- k = j;
- }
- }
- }
-
- // If we don't have anything, all streams are exhausted.
- if (k == -1) break;
-
- // Pick the best slot and refill it.
- subPos[k]++;
- if (i >= start) {
- result.add(slot[k]);
- }
- slot[k] = mFetcher[k].getItem(subPos[k]);
-
- // Periodically leave a mark in the index, so we can come back later.
- if ((i + 1) % PAGE_SIZE == 0) {
- mIndex.put(i + 1, subPos.clone());
- }
- }
-
- return result;
- }
-
- @Override
- public int getTotalMediaItemCount() {
- int count = 0;
- for (MediaSet set : mSources) {
- count += set.getTotalMediaItemCount();
- }
- return count;
- }
-
- @Override
- public long reload() {
- boolean changed = false;
- for (int i = 0, n = mSources.length; i < n; ++i) {
- if (mSources[i].reload() > mDataVersion) changed = true;
- }
- if (changed) {
- mDataVersion = nextVersionNumber();
- updateData();
- invalidateCache();
- }
- return mDataVersion;
- }
-
- @Override
- public void onContentDirty() {
- notifyContentChanged();
- }
-
- @Override
- public int getSupportedOperations() {
- return mSupportedOperation;
- }
-
- @Override
- public void delete() {
- for (MediaSet set : mSources) {
- set.delete();
- }
- }
-
- @Override
- public void rotate(int degrees) {
- for (MediaSet set : mSources) {
- set.rotate(degrees);
- }
- }
-
- private static class FetchCache {
- private MediaSet mBaseSet;
- private SoftReference<ArrayList<MediaItem>> mCacheRef;
- private int mStartPos;
-
- public FetchCache(MediaSet baseSet) {
- mBaseSet = baseSet;
- }
-
- public void invalidate() {
- mCacheRef = null;
- }
-
- public MediaItem getItem(int index) {
- boolean needLoading = false;
- ArrayList<MediaItem> cache = null;
- if (mCacheRef == null
- || index < mStartPos || index >= mStartPos + PAGE_SIZE) {
- needLoading = true;
- } else {
- cache = mCacheRef.get();
- if (cache == null) {
- needLoading = true;
- }
- }
-
- if (needLoading) {
- cache = mBaseSet.getMediaItem(index, PAGE_SIZE);
- mCacheRef = new SoftReference<ArrayList<MediaItem>>(cache);
- mStartPos = index;
- }
-
- if (index < mStartPos || index >= mStartPos + cache.size()) {
- return null;
- }
-
- return cache.get(index - mStartPos);
- }
- }
-
- @Override
- public boolean isLeafAlbum() {
- return true;
- }
-}
diff --git a/src/com/android/gallery3d/data/LocalSource.java b/src/com/android/gallery3d/data/LocalSource.java
deleted file mode 100644
index a2e3d1443..000000000
--- a/src/com/android/gallery3d/data/LocalSource.java
+++ /dev/null
@@ -1,275 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.ContentProviderClient;
-import android.content.ContentUris;
-import android.content.UriMatcher;
-import android.net.Uri;
-import android.provider.MediaStore;
-
-import com.android.gallery3d.app.Gallery;
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.data.MediaSet.ItemConsumer;
-
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.Comparator;
-
-class LocalSource extends MediaSource {
-
- public static final String KEY_BUCKET_ID = "bucketId";
-
- private GalleryApp mApplication;
- private PathMatcher mMatcher;
- private static final int NO_MATCH = -1;
- private final UriMatcher mUriMatcher = new UriMatcher(NO_MATCH);
- public static final Comparator<PathId> sIdComparator = new IdComparator();
-
- private static final int LOCAL_IMAGE_ALBUMSET = 0;
- private static final int LOCAL_VIDEO_ALBUMSET = 1;
- private static final int LOCAL_IMAGE_ALBUM = 2;
- private static final int LOCAL_VIDEO_ALBUM = 3;
- private static final int LOCAL_IMAGE_ITEM = 4;
- private static final int LOCAL_VIDEO_ITEM = 5;
- private static final int LOCAL_ALL_ALBUMSET = 6;
- private static final int LOCAL_ALL_ALBUM = 7;
-
- private static final String TAG = "LocalSource";
-
- private ContentProviderClient mClient;
-
- public LocalSource(GalleryApp context) {
- super("local");
- mApplication = context;
- mMatcher = new PathMatcher();
- mMatcher.add("/local/image", LOCAL_IMAGE_ALBUMSET);
- mMatcher.add("/local/video", LOCAL_VIDEO_ALBUMSET);
- mMatcher.add("/local/all", LOCAL_ALL_ALBUMSET);
-
- mMatcher.add("/local/image/*", LOCAL_IMAGE_ALBUM);
- mMatcher.add("/local/video/*", LOCAL_VIDEO_ALBUM);
- mMatcher.add("/local/all/*", LOCAL_ALL_ALBUM);
- mMatcher.add("/local/image/item/*", LOCAL_IMAGE_ITEM);
- mMatcher.add("/local/video/item/*", LOCAL_VIDEO_ITEM);
-
- mUriMatcher.addURI(MediaStore.AUTHORITY,
- "external/images/media/#", LOCAL_IMAGE_ITEM);
- mUriMatcher.addURI(MediaStore.AUTHORITY,
- "external/video/media/#", LOCAL_VIDEO_ITEM);
- mUriMatcher.addURI(MediaStore.AUTHORITY,
- "external/images/media", LOCAL_IMAGE_ALBUM);
- mUriMatcher.addURI(MediaStore.AUTHORITY,
- "external/video/media", LOCAL_VIDEO_ALBUM);
- mUriMatcher.addURI(MediaStore.AUTHORITY,
- "external/file", LOCAL_ALL_ALBUM);
- }
-
- @Override
- public MediaObject createMediaObject(Path path) {
- GalleryApp app = mApplication;
- switch (mMatcher.match(path)) {
- case LOCAL_ALL_ALBUMSET:
- case LOCAL_IMAGE_ALBUMSET:
- case LOCAL_VIDEO_ALBUMSET:
- return new LocalAlbumSet(path, mApplication);
- case LOCAL_IMAGE_ALBUM:
- return new LocalAlbum(path, app, mMatcher.getIntVar(0), true);
- case LOCAL_VIDEO_ALBUM:
- return new LocalAlbum(path, app, mMatcher.getIntVar(0), false);
- case LOCAL_ALL_ALBUM: {
- int bucketId = mMatcher.getIntVar(0);
- DataManager dataManager = app.getDataManager();
- MediaSet imageSet = (MediaSet) dataManager.getMediaObject(
- LocalAlbumSet.PATH_IMAGE.getChild(bucketId));
- MediaSet videoSet = (MediaSet) dataManager.getMediaObject(
- LocalAlbumSet.PATH_VIDEO.getChild(bucketId));
- Comparator<MediaItem> comp = DataManager.sDateTakenComparator;
- return new LocalMergeAlbum(
- path, comp, new MediaSet[] {imageSet, videoSet}, bucketId);
- }
- case LOCAL_IMAGE_ITEM:
- return new LocalImage(path, mApplication, mMatcher.getIntVar(0));
- case LOCAL_VIDEO_ITEM:
- return new LocalVideo(path, mApplication, mMatcher.getIntVar(0));
- default:
- throw new RuntimeException("bad path: " + path);
- }
- }
-
- private static int getMediaType(String type, int defaultType) {
- if (type == null) return defaultType;
- try {
- int value = Integer.parseInt(type);
- if ((value & (MEDIA_TYPE_IMAGE
- | MEDIA_TYPE_VIDEO)) != 0) return value;
- } catch (NumberFormatException e) {
- Log.w(TAG, "invalid type: " + type, e);
- }
- return defaultType;
- }
-
- // The media type bit passed by the intent
- private static final int MEDIA_TYPE_ALL = 0;
- private static final int MEDIA_TYPE_IMAGE = 1;
- private static final int MEDIA_TYPE_VIDEO = 4;
-
- private Path getAlbumPath(Uri uri, int defaultType) {
- int mediaType = getMediaType(
- uri.getQueryParameter(Gallery.KEY_MEDIA_TYPES),
- defaultType);
- String bucketId = uri.getQueryParameter(KEY_BUCKET_ID);
- int id = 0;
- try {
- id = Integer.parseInt(bucketId);
- } catch (NumberFormatException e) {
- Log.w(TAG, "invalid bucket id: " + bucketId, e);
- return null;
- }
- switch (mediaType) {
- case MEDIA_TYPE_IMAGE:
- return Path.fromString("/local/image").getChild(id);
- case MEDIA_TYPE_VIDEO:
- return Path.fromString("/local/video").getChild(id);
- default:
- return Path.fromString("/local/all").getChild(id);
- }
- }
-
- @Override
- public Path findPathByUri(Uri uri, String type) {
- try {
- switch (mUriMatcher.match(uri)) {
- case LOCAL_IMAGE_ITEM: {
- long id = ContentUris.parseId(uri);
- return id >= 0 ? LocalImage.ITEM_PATH.getChild(id) : null;
- }
- case LOCAL_VIDEO_ITEM: {
- long id = ContentUris.parseId(uri);
- return id >= 0 ? LocalVideo.ITEM_PATH.getChild(id) : null;
- }
- case LOCAL_IMAGE_ALBUM: {
- return getAlbumPath(uri, MEDIA_TYPE_IMAGE);
- }
- case LOCAL_VIDEO_ALBUM: {
- return getAlbumPath(uri, MEDIA_TYPE_VIDEO);
- }
- case LOCAL_ALL_ALBUM: {
- return getAlbumPath(uri, MEDIA_TYPE_ALL);
- }
- }
- } catch (NumberFormatException e) {
- Log.w(TAG, "uri: " + uri.toString(), e);
- }
- return null;
- }
-
- @Override
- public Path getDefaultSetOf(Path item) {
- MediaObject object = mApplication.getDataManager().getMediaObject(item);
- if (object instanceof LocalMediaItem) {
- return Path.fromString("/local/all").getChild(
- String.valueOf(((LocalMediaItem) object).getBucketId()));
- }
- return null;
- }
-
- @Override
- public void mapMediaItems(ArrayList<PathId> list, ItemConsumer consumer) {
- ArrayList<PathId> imageList = new ArrayList<PathId>();
- ArrayList<PathId> videoList = new ArrayList<PathId>();
- int n = list.size();
- for (int i = 0; i < n; i++) {
- PathId pid = list.get(i);
- // We assume the form is: "/local/{image,video}/item/#"
- // We don't use mMatcher for efficiency's reason.
- Path parent = pid.path.getParent();
- if (parent == LocalImage.ITEM_PATH) {
- imageList.add(pid);
- } else if (parent == LocalVideo.ITEM_PATH) {
- videoList.add(pid);
- }
- }
- // TODO: use "files" table so we can merge the two cases.
- processMapMediaItems(imageList, consumer, true);
- processMapMediaItems(videoList, consumer, false);
- }
-
- private void processMapMediaItems(ArrayList<PathId> list,
- ItemConsumer consumer, boolean isImage) {
- // Sort path by path id
- Collections.sort(list, sIdComparator);
- int n = list.size();
- for (int i = 0; i < n; ) {
- PathId pid = list.get(i);
-
- // Find a range of items.
- ArrayList<Integer> ids = new ArrayList<Integer>();
- int startId = Integer.parseInt(pid.path.getSuffix());
- ids.add(startId);
-
- int j;
- for (j = i + 1; j < n; j++) {
- PathId pid2 = list.get(j);
- int curId = Integer.parseInt(pid2.path.getSuffix());
- if (curId - startId >= MediaSet.MEDIAITEM_BATCH_FETCH_COUNT) {
- break;
- }
- ids.add(curId);
- }
-
- MediaItem[] items = LocalAlbum.getMediaItemById(
- mApplication, isImage, ids);
- for(int k = i ; k < j; k++) {
- PathId pid2 = list.get(k);
- consumer.consume(pid2.id, items[k - i]);
- }
-
- i = j;
- }
- }
-
- // This is a comparator which compares the suffix number in two Paths.
- private static class IdComparator implements Comparator<PathId> {
- @Override
- public int compare(PathId p1, PathId p2) {
- String s1 = p1.path.getSuffix();
- String s2 = p2.path.getSuffix();
- int len1 = s1.length();
- int len2 = s2.length();
- if (len1 < len2) {
- return -1;
- } else if (len1 > len2) {
- return 1;
- } else {
- return s1.compareTo(s2);
- }
- }
- }
-
- @Override
- public void resume() {
- mClient = mApplication.getContentResolver()
- .acquireContentProviderClient(MediaStore.AUTHORITY);
- }
-
- @Override
- public void pause() {
- mClient.release();
- mClient = null;
- }
-}
diff --git a/src/com/android/gallery3d/data/LocalVideo.java b/src/com/android/gallery3d/data/LocalVideo.java
deleted file mode 100644
index 4b8774ca4..000000000
--- a/src/com/android/gallery3d/data/LocalVideo.java
+++ /dev/null
@@ -1,242 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.ContentResolver;
-import android.database.Cursor;
-import android.graphics.Bitmap;
-import android.graphics.BitmapRegionDecoder;
-import android.net.Uri;
-import android.provider.MediaStore.Video;
-import android.provider.MediaStore.Video.VideoColumns;
-
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.common.BitmapUtils;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-import com.android.gallery3d.util.UpdateHelper;
-
-// LocalVideo represents a video in the local storage.
-public class LocalVideo extends LocalMediaItem {
- private static final String TAG = "LocalVideo";
- static final Path ITEM_PATH = Path.fromString("/local/video/item");
-
- // Must preserve order between these indices and the order of the terms in
- // the following PROJECTION array.
- private static final int INDEX_ID = 0;
- private static final int INDEX_CAPTION = 1;
- private static final int INDEX_MIME_TYPE = 2;
- private static final int INDEX_LATITUDE = 3;
- private static final int INDEX_LONGITUDE = 4;
- private static final int INDEX_DATE_TAKEN = 5;
- private static final int INDEX_DATE_ADDED = 6;
- private static final int INDEX_DATE_MODIFIED = 7;
- private static final int INDEX_DATA = 8;
- private static final int INDEX_DURATION = 9;
- private static final int INDEX_BUCKET_ID = 10;
- private static final int INDEX_SIZE = 11;
- private static final int INDEX_RESOLUTION = 12;
-
- static final String[] PROJECTION = new String[] {
- VideoColumns._ID,
- VideoColumns.TITLE,
- VideoColumns.MIME_TYPE,
- VideoColumns.LATITUDE,
- VideoColumns.LONGITUDE,
- VideoColumns.DATE_TAKEN,
- VideoColumns.DATE_ADDED,
- VideoColumns.DATE_MODIFIED,
- VideoColumns.DATA,
- VideoColumns.DURATION,
- VideoColumns.BUCKET_ID,
- VideoColumns.SIZE,
- VideoColumns.RESOLUTION,
- };
-
- private final GalleryApp mApplication;
-
- public int durationInSec;
-
- public LocalVideo(Path path, GalleryApp application, Cursor cursor) {
- super(path, nextVersionNumber());
- mApplication = application;
- loadFromCursor(cursor);
- }
-
- public LocalVideo(Path path, GalleryApp context, int id) {
- super(path, nextVersionNumber());
- mApplication = context;
- ContentResolver resolver = mApplication.getContentResolver();
- Uri uri = Video.Media.EXTERNAL_CONTENT_URI;
- Cursor cursor = LocalAlbum.getItemCursor(resolver, uri, PROJECTION, id);
- if (cursor == null) {
- throw new RuntimeException("cannot get cursor for: " + path);
- }
- try {
- if (cursor.moveToNext()) {
- loadFromCursor(cursor);
- } else {
- throw new RuntimeException("cannot find data for: " + path);
- }
- } finally {
- cursor.close();
- }
- }
-
- private void loadFromCursor(Cursor cursor) {
- id = cursor.getInt(INDEX_ID);
- caption = cursor.getString(INDEX_CAPTION);
- mimeType = cursor.getString(INDEX_MIME_TYPE);
- latitude = cursor.getDouble(INDEX_LATITUDE);
- longitude = cursor.getDouble(INDEX_LONGITUDE);
- dateTakenInMs = cursor.getLong(INDEX_DATE_TAKEN);
- dateAddedInSec = cursor.getLong(INDEX_DATE_ADDED);
- dateModifiedInSec = cursor.getLong(INDEX_DATE_MODIFIED);
- filePath = cursor.getString(INDEX_DATA);
- durationInSec = cursor.getInt(INDEX_DURATION) / 1000;
- bucketId = cursor.getInt(INDEX_BUCKET_ID);
- fileSize = cursor.getLong(INDEX_SIZE);
- parseResolution(cursor.getString(INDEX_RESOLUTION));
- }
-
- private void parseResolution(String resolution) {
- if (resolution == null) return;
- int m = resolution.indexOf('x');
- if (m == -1) return;
- try {
- int w = Integer.parseInt(resolution.substring(0, m));
- int h = Integer.parseInt(resolution.substring(m + 1));
- width = w;
- height = h;
- } catch (Throwable t) {
- Log.w(TAG, t);
- }
- }
-
- @Override
- protected boolean updateFromCursor(Cursor cursor) {
- UpdateHelper uh = new UpdateHelper();
- id = uh.update(id, cursor.getInt(INDEX_ID));
- caption = uh.update(caption, cursor.getString(INDEX_CAPTION));
- mimeType = uh.update(mimeType, cursor.getString(INDEX_MIME_TYPE));
- latitude = uh.update(latitude, cursor.getDouble(INDEX_LATITUDE));
- longitude = uh.update(longitude, cursor.getDouble(INDEX_LONGITUDE));
- dateTakenInMs = uh.update(
- dateTakenInMs, cursor.getLong(INDEX_DATE_TAKEN));
- dateAddedInSec = uh.update(
- dateAddedInSec, cursor.getLong(INDEX_DATE_ADDED));
- dateModifiedInSec = uh.update(
- dateModifiedInSec, cursor.getLong(INDEX_DATE_MODIFIED));
- filePath = uh.update(filePath, cursor.getString(INDEX_DATA));
- durationInSec = uh.update(
- durationInSec, cursor.getInt(INDEX_DURATION) / 1000);
- bucketId = uh.update(bucketId, cursor.getInt(INDEX_BUCKET_ID));
- fileSize = uh.update(fileSize, cursor.getLong(INDEX_SIZE));
- return uh.isUpdated();
- }
-
- @Override
- public Job<Bitmap> requestImage(int type) {
- return new LocalVideoRequest(mApplication, getPath(), dateModifiedInSec,
- type, filePath);
- }
-
- public static class LocalVideoRequest extends ImageCacheRequest {
- private String mLocalFilePath;
-
- LocalVideoRequest(GalleryApp application, Path path, long timeModified,
- int type, String localFilePath) {
- super(application, path, timeModified, type,
- MediaItem.getTargetSize(type));
- mLocalFilePath = localFilePath;
- }
-
- @Override
- public Bitmap onDecodeOriginal(JobContext jc, int type) {
- Bitmap bitmap = BitmapUtils.createVideoThumbnail(mLocalFilePath);
- if (bitmap == null || jc.isCancelled()) return null;
- return bitmap;
- }
- }
-
- @Override
- public Job<BitmapRegionDecoder> requestLargeImage() {
- throw new UnsupportedOperationException("Cannot regquest a large image"
- + " to a local video!");
- }
-
- @Override
- public int getSupportedOperations() {
- return SUPPORT_DELETE | SUPPORT_SHARE | SUPPORT_PLAY | SUPPORT_INFO | SUPPORT_TRIM | SUPPORT_MUTE;
- }
-
- @Override
- public void delete() {
- GalleryUtils.assertNotInRenderThread();
- Uri baseUri = Video.Media.EXTERNAL_CONTENT_URI;
- mApplication.getContentResolver().delete(baseUri, "_id=?",
- new String[]{String.valueOf(id)});
- }
-
- @Override
- public void rotate(int degrees) {
- // TODO
- }
-
- @Override
- public Uri getContentUri() {
- Uri baseUri = Video.Media.EXTERNAL_CONTENT_URI;
- return baseUri.buildUpon().appendPath(String.valueOf(id)).build();
- }
-
- @Override
- public Uri getPlayUri() {
- return getContentUri();
- }
-
- @Override
- public int getMediaType() {
- return MEDIA_TYPE_VIDEO;
- }
-
- @Override
- public MediaDetails getDetails() {
- MediaDetails details = super.getDetails();
- int s = durationInSec;
- if (s > 0) {
- details.addDetail(MediaDetails.INDEX_DURATION, GalleryUtils.formatDuration(
- mApplication.getAndroidContext(), durationInSec));
- }
- return details;
- }
-
- @Override
- public int getWidth() {
- return width;
- }
-
- @Override
- public int getHeight() {
- return height;
- }
-
- @Override
- public String getFilePath() {
- return filePath;
- }
-}
diff --git a/src/com/android/gallery3d/data/LocationClustering.java b/src/com/android/gallery3d/data/LocationClustering.java
deleted file mode 100644
index 540322a33..000000000
--- a/src/com/android/gallery3d/data/LocationClustering.java
+++ /dev/null
@@ -1,316 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.Context;
-import android.os.Handler;
-import android.os.Looper;
-import android.util.FloatMath;
-import android.widget.Toast;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.ReverseGeocoder;
-
-import java.util.ArrayList;
-
-class LocationClustering extends Clustering {
- @SuppressWarnings("unused")
- private static final String TAG = "LocationClustering";
-
- private static final int MIN_GROUPS = 1;
- private static final int MAX_GROUPS = 20;
- private static final int MAX_ITERATIONS = 30;
-
- // If the total distance change is less than this ratio, stop iterating.
- private static final float STOP_CHANGE_RATIO = 0.01f;
- private Context mContext;
- private ArrayList<ArrayList<SmallItem>> mClusters;
- private ArrayList<String> mNames;
- private String mNoLocationString;
- private Handler mHandler;
-
- private static class Point {
- public Point(double lat, double lng) {
- latRad = Math.toRadians(lat);
- lngRad = Math.toRadians(lng);
- }
- public Point() {}
- public double latRad, lngRad;
- }
-
- private static class SmallItem {
- Path path;
- double lat, lng;
- }
-
- public LocationClustering(Context context) {
- mContext = context;
- mNoLocationString = mContext.getResources().getString(R.string.no_location);
- mHandler = new Handler(Looper.getMainLooper());
- }
-
- @Override
- public void run(MediaSet baseSet) {
- final int total = baseSet.getTotalMediaItemCount();
- final SmallItem[] buf = new SmallItem[total];
- // Separate items to two sets: with or without lat-long.
- final double[] latLong = new double[2];
- baseSet.enumerateTotalMediaItems(new MediaSet.ItemConsumer() {
- @Override
- public void consume(int index, MediaItem item) {
- if (index < 0 || index >= total) return;
- SmallItem s = new SmallItem();
- s.path = item.getPath();
- item.getLatLong(latLong);
- s.lat = latLong[0];
- s.lng = latLong[1];
- buf[index] = s;
- }
- });
-
- final ArrayList<SmallItem> withLatLong = new ArrayList<SmallItem>();
- final ArrayList<SmallItem> withoutLatLong = new ArrayList<SmallItem>();
- final ArrayList<Point> points = new ArrayList<Point>();
- for (int i = 0; i < total; i++) {
- SmallItem s = buf[i];
- if (s == null) continue;
- if (GalleryUtils.isValidLocation(s.lat, s.lng)) {
- withLatLong.add(s);
- points.add(new Point(s.lat, s.lng));
- } else {
- withoutLatLong.add(s);
- }
- }
-
- ArrayList<ArrayList<SmallItem>> clusters = new ArrayList<ArrayList<SmallItem>>();
-
- int m = withLatLong.size();
- if (m > 0) {
- // cluster the items with lat-long
- Point[] pointsArray = new Point[m];
- pointsArray = points.toArray(pointsArray);
- int[] bestK = new int[1];
- int[] index = kMeans(pointsArray, bestK);
-
- for (int i = 0; i < bestK[0]; i++) {
- clusters.add(new ArrayList<SmallItem>());
- }
-
- for (int i = 0; i < m; i++) {
- clusters.get(index[i]).add(withLatLong.get(i));
- }
- }
-
- ReverseGeocoder geocoder = new ReverseGeocoder(mContext);
- mNames = new ArrayList<String>();
- boolean hasUnresolvedAddress = false;
- mClusters = new ArrayList<ArrayList<SmallItem>>();
- for (ArrayList<SmallItem> cluster : clusters) {
- String name = generateName(cluster, geocoder);
- if (name != null) {
- mNames.add(name);
- mClusters.add(cluster);
- } else {
- // move cluster-i to no location cluster
- withoutLatLong.addAll(cluster);
- hasUnresolvedAddress = true;
- }
- }
-
- if (withoutLatLong.size() > 0) {
- mNames.add(mNoLocationString);
- mClusters.add(withoutLatLong);
- }
-
- if (hasUnresolvedAddress) {
- mHandler.post(new Runnable() {
- @Override
- public void run() {
- Toast.makeText(mContext, R.string.no_connectivity,
- Toast.LENGTH_LONG).show();
- }
- });
- }
- }
-
- private static String generateName(ArrayList<SmallItem> items,
- ReverseGeocoder geocoder) {
- ReverseGeocoder.SetLatLong set = new ReverseGeocoder.SetLatLong();
-
- int n = items.size();
- for (int i = 0; i < n; i++) {
- SmallItem item = items.get(i);
- double itemLatitude = item.lat;
- double itemLongitude = item.lng;
-
- if (set.mMinLatLatitude > itemLatitude) {
- set.mMinLatLatitude = itemLatitude;
- set.mMinLatLongitude = itemLongitude;
- }
- if (set.mMaxLatLatitude < itemLatitude) {
- set.mMaxLatLatitude = itemLatitude;
- set.mMaxLatLongitude = itemLongitude;
- }
- if (set.mMinLonLongitude > itemLongitude) {
- set.mMinLonLatitude = itemLatitude;
- set.mMinLonLongitude = itemLongitude;
- }
- if (set.mMaxLonLongitude < itemLongitude) {
- set.mMaxLonLatitude = itemLatitude;
- set.mMaxLonLongitude = itemLongitude;
- }
- }
-
- return geocoder.computeAddress(set);
- }
-
- @Override
- public int getNumberOfClusters() {
- return mClusters.size();
- }
-
- @Override
- public ArrayList<Path> getCluster(int index) {
- ArrayList<SmallItem> items = mClusters.get(index);
- ArrayList<Path> result = new ArrayList<Path>(items.size());
- for (int i = 0, n = items.size(); i < n; i++) {
- result.add(items.get(i).path);
- }
- return result;
- }
-
- @Override
- public String getClusterName(int index) {
- return mNames.get(index);
- }
-
- // Input: n points
- // Output: the best k is stored in bestK[0], and the return value is the
- // an array which specifies the group that each point belongs (0 to k - 1).
- private static int[] kMeans(Point points[], int[] bestK) {
- int n = points.length;
-
- // min and max number of groups wanted
- int minK = Math.min(n, MIN_GROUPS);
- int maxK = Math.min(n, MAX_GROUPS);
-
- Point[] center = new Point[maxK]; // center of each group.
- Point[] groupSum = new Point[maxK]; // sum of points in each group.
- int[] groupCount = new int[maxK]; // number of points in each group.
- int[] grouping = new int[n]; // The group assignment for each point.
-
- for (int i = 0; i < maxK; i++) {
- center[i] = new Point();
- groupSum[i] = new Point();
- }
-
- // The score we want to minimize is:
- // (sum of distance from each point to its group center) * sqrt(k).
- float bestScore = Float.MAX_VALUE;
- // The best group assignment up to now.
- int[] bestGrouping = new int[n];
- // The best K up to now.
- bestK[0] = 1;
-
- float lastDistance = 0;
- float totalDistance = 0;
-
- for (int k = minK; k <= maxK; k++) {
- // step 1: (arbitrarily) pick k points as the initial centers.
- int delta = n / k;
- for (int i = 0; i < k; i++) {
- Point p = points[i * delta];
- center[i].latRad = p.latRad;
- center[i].lngRad = p.lngRad;
- }
-
- for (int iter = 0; iter < MAX_ITERATIONS; iter++) {
- // step 2: assign each point to the nearest center.
- for (int i = 0; i < k; i++) {
- groupSum[i].latRad = 0;
- groupSum[i].lngRad = 0;
- groupCount[i] = 0;
- }
- totalDistance = 0;
-
- for (int i = 0; i < n; i++) {
- Point p = points[i];
- float bestDistance = Float.MAX_VALUE;
- int bestIndex = 0;
- for (int j = 0; j < k; j++) {
- float distance = (float) GalleryUtils.fastDistanceMeters(
- p.latRad, p.lngRad, center[j].latRad, center[j].lngRad);
- // We may have small non-zero distance introduced by
- // floating point calculation, so zero out small
- // distances less than 1 meter.
- if (distance < 1) {
- distance = 0;
- }
- if (distance < bestDistance) {
- bestDistance = distance;
- bestIndex = j;
- }
- }
- grouping[i] = bestIndex;
- groupCount[bestIndex]++;
- groupSum[bestIndex].latRad += p.latRad;
- groupSum[bestIndex].lngRad += p.lngRad;
- totalDistance += bestDistance;
- }
-
- // step 3: calculate new centers
- for (int i = 0; i < k; i++) {
- if (groupCount[i] > 0) {
- center[i].latRad = groupSum[i].latRad / groupCount[i];
- center[i].lngRad = groupSum[i].lngRad / groupCount[i];
- }
- }
-
- if (totalDistance == 0 || (Math.abs(lastDistance - totalDistance)
- / totalDistance) < STOP_CHANGE_RATIO) {
- break;
- }
- lastDistance = totalDistance;
- }
-
- // step 4: remove empty groups and reassign group number
- int reassign[] = new int[k];
- int realK = 0;
- for (int i = 0; i < k; i++) {
- if (groupCount[i] > 0) {
- reassign[i] = realK++;
- }
- }
-
- // step 5: calculate the final score
- float score = totalDistance * FloatMath.sqrt(realK);
-
- if (score < bestScore) {
- bestScore = score;
- bestK[0] = realK;
- for (int i = 0; i < n; i++) {
- bestGrouping[i] = reassign[grouping[i]];
- }
- if (score == 0) {
- break;
- }
- }
- }
- return bestGrouping;
- }
-}
diff --git a/src/com/android/gallery3d/data/Log.java b/src/com/android/gallery3d/data/Log.java
deleted file mode 100644
index 3384eb66c..000000000
--- a/src/com/android/gallery3d/data/Log.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-public class Log {
- public static int v(String tag, String msg) {
- return android.util.Log.v(tag, msg);
- }
- public static int v(String tag, String msg, Throwable tr) {
- return android.util.Log.v(tag, msg, tr);
- }
- public static int d(String tag, String msg) {
- return android.util.Log.d(tag, msg);
- }
- public static int d(String tag, String msg, Throwable tr) {
- return android.util.Log.d(tag, msg, tr);
- }
- public static int i(String tag, String msg) {
- return android.util.Log.i(tag, msg);
- }
- public static int i(String tag, String msg, Throwable tr) {
- return android.util.Log.i(tag, msg, tr);
- }
- public static int w(String tag, String msg) {
- return android.util.Log.w(tag, msg);
- }
- public static int w(String tag, String msg, Throwable tr) {
- return android.util.Log.w(tag, msg, tr);
- }
- public static int w(String tag, Throwable tr) {
- return android.util.Log.w(tag, tr);
- }
- public static int e(String tag, String msg) {
- return android.util.Log.e(tag, msg);
- }
- public static int e(String tag, String msg, Throwable tr) {
- return android.util.Log.e(tag, msg, tr);
- }
-}
diff --git a/src/com/android/gallery3d/data/MediaDetails.java b/src/com/android/gallery3d/data/MediaDetails.java
deleted file mode 100644
index cac524b88..000000000
--- a/src/com/android/gallery3d/data/MediaDetails.java
+++ /dev/null
@@ -1,170 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.exif.ExifInterface;
-import com.android.gallery3d.exif.ExifTag;
-import com.android.gallery3d.exif.Rational;
-
-import java.io.FileInputStream;
-import java.io.FileNotFoundException;
-import java.io.IOException;
-import java.io.InputStream;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.Map.Entry;
-import java.util.TreeMap;
-
-public class MediaDetails implements Iterable<Entry<Integer, Object>> {
- @SuppressWarnings("unused")
- private static final String TAG = "MediaDetails";
-
- private TreeMap<Integer, Object> mDetails = new TreeMap<Integer, Object>();
- private HashMap<Integer, Integer> mUnits = new HashMap<Integer, Integer>();
-
- public static final int INDEX_TITLE = 1;
- public static final int INDEX_DESCRIPTION = 2;
- public static final int INDEX_DATETIME = 3;
- public static final int INDEX_LOCATION = 4;
- public static final int INDEX_WIDTH = 5;
- public static final int INDEX_HEIGHT = 6;
- public static final int INDEX_ORIENTATION = 7;
- public static final int INDEX_DURATION = 8;
- public static final int INDEX_MIMETYPE = 9;
- public static final int INDEX_SIZE = 10;
-
- // for EXIF
- public static final int INDEX_MAKE = 100;
- public static final int INDEX_MODEL = 101;
- public static final int INDEX_FLASH = 102;
- public static final int INDEX_FOCAL_LENGTH = 103;
- public static final int INDEX_WHITE_BALANCE = 104;
- public static final int INDEX_APERTURE = 105;
- public static final int INDEX_SHUTTER_SPEED = 106;
- public static final int INDEX_EXPOSURE_TIME = 107;
- public static final int INDEX_ISO = 108;
-
- // Put this last because it may be long.
- public static final int INDEX_PATH = 200;
-
- public static class FlashState {
- private static int FLASH_FIRED_MASK = 1;
- private static int FLASH_RETURN_MASK = 2 | 4;
- private static int FLASH_MODE_MASK = 8 | 16;
- private static int FLASH_FUNCTION_MASK = 32;
- private static int FLASH_RED_EYE_MASK = 64;
- private int mState;
-
- public FlashState(int state) {
- mState = state;
- }
-
- public boolean isFlashFired() {
- return (mState & FLASH_FIRED_MASK) != 0;
- }
- }
-
- public void addDetail(int index, Object value) {
- mDetails.put(index, value);
- }
-
- public Object getDetail(int index) {
- return mDetails.get(index);
- }
-
- public int size() {
- return mDetails.size();
- }
-
- @Override
- public Iterator<Entry<Integer, Object>> iterator() {
- return mDetails.entrySet().iterator();
- }
-
- public void setUnit(int index, int unit) {
- mUnits.put(index, unit);
- }
-
- public boolean hasUnit(int index) {
- return mUnits.containsKey(index);
- }
-
- public int getUnit(int index) {
- return mUnits.get(index);
- }
-
- private static void setExifData(MediaDetails details, ExifTag tag,
- int key) {
- if (tag != null) {
- String value = null;
- int type = tag.getDataType();
- if (type == ExifTag.TYPE_UNSIGNED_RATIONAL || type == ExifTag.TYPE_RATIONAL) {
- value = String.valueOf(tag.getValueAsRational(0).toDouble());
- } else if (type == ExifTag.TYPE_ASCII) {
- value = tag.getValueAsString();
- } else {
- value = String.valueOf(tag.forceGetValueAsLong(0));
- }
- if (key == MediaDetails.INDEX_FLASH) {
- MediaDetails.FlashState state = new MediaDetails.FlashState(
- Integer.valueOf(value.toString()));
- details.addDetail(key, state);
- } else {
- details.addDetail(key, value);
- }
- }
- }
-
- public static void extractExifInfo(MediaDetails details, String filePath) {
-
- ExifInterface exif = new ExifInterface();
- try {
- exif.readExif(filePath);
- } catch (FileNotFoundException e) {
- Log.w(TAG, "Could not find file to read exif: " + filePath, e);
- } catch (IOException e) {
- Log.w(TAG, "Could not read exif from file: " + filePath, e);
- }
-
- setExifData(details, exif.getTag(ExifInterface.TAG_FLASH),
- MediaDetails.INDEX_FLASH);
- setExifData(details, exif.getTag(ExifInterface.TAG_IMAGE_WIDTH),
- MediaDetails.INDEX_WIDTH);
- setExifData(details, exif.getTag(ExifInterface.TAG_IMAGE_LENGTH),
- MediaDetails.INDEX_HEIGHT);
- setExifData(details, exif.getTag(ExifInterface.TAG_MAKE),
- MediaDetails.INDEX_MAKE);
- setExifData(details, exif.getTag(ExifInterface.TAG_MODEL),
- MediaDetails.INDEX_MODEL);
- setExifData(details, exif.getTag(ExifInterface.TAG_APERTURE_VALUE),
- MediaDetails.INDEX_APERTURE);
- setExifData(details, exif.getTag(ExifInterface.TAG_ISO_SPEED_RATINGS),
- MediaDetails.INDEX_ISO);
- setExifData(details, exif.getTag(ExifInterface.TAG_WHITE_BALANCE),
- MediaDetails.INDEX_WHITE_BALANCE);
- setExifData(details, exif.getTag(ExifInterface.TAG_EXPOSURE_TIME),
- MediaDetails.INDEX_EXPOSURE_TIME);
- ExifTag focalTag = exif.getTag(ExifInterface.TAG_FOCAL_LENGTH);
- if (focalTag != null) {
- details.addDetail(MediaDetails.INDEX_FOCAL_LENGTH,
- focalTag.getValueAsRational(0).toDouble());
- details.setUnit(MediaDetails.INDEX_FOCAL_LENGTH, R.string.unit_mm);
- }
- }
-}
diff --git a/src/com/android/gallery3d/data/MediaItem.java b/src/com/android/gallery3d/data/MediaItem.java
deleted file mode 100644
index 59ea86551..000000000
--- a/src/com/android/gallery3d/data/MediaItem.java
+++ /dev/null
@@ -1,134 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.graphics.Bitmap;
-import android.graphics.BitmapRegionDecoder;
-
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.ui.ScreenNail;
-import com.android.gallery3d.util.ThreadPool.Job;
-
-// MediaItem represents an image or a video item.
-public abstract class MediaItem extends MediaObject {
- // NOTE: These type numbers are stored in the image cache, so it should not
- // not be changed without resetting the cache.
- public static final int TYPE_THUMBNAIL = 1;
- public static final int TYPE_MICROTHUMBNAIL = 2;
-
- public static final int CACHED_IMAGE_QUALITY = 95;
-
- public static final int IMAGE_READY = 0;
- public static final int IMAGE_WAIT = 1;
- public static final int IMAGE_ERROR = -1;
-
- public static final String MIME_TYPE_JPEG = "image/jpeg";
-
- private static final int BYTESBUFFE_POOL_SIZE = 4;
- private static final int BYTESBUFFER_SIZE = 200 * 1024;
-
- private static int sMicrothumbnailTargetSize = 200;
- private static final BytesBufferPool sMicroThumbBufferPool =
- new BytesBufferPool(BYTESBUFFE_POOL_SIZE, BYTESBUFFER_SIZE);
-
- private static int sThumbnailTargetSize = 640;
-
- // TODO: fix default value for latlng and change this.
- public static final double INVALID_LATLNG = 0f;
-
- public abstract Job<Bitmap> requestImage(int type);
- public abstract Job<BitmapRegionDecoder> requestLargeImage();
-
- public MediaItem(Path path, long version) {
- super(path, version);
- }
-
- public long getDateInMs() {
- return 0;
- }
-
- public String getName() {
- return null;
- }
-
- public void getLatLong(double[] latLong) {
- latLong[0] = INVALID_LATLNG;
- latLong[1] = INVALID_LATLNG;
- }
-
- public String[] getTags() {
- return null;
- }
-
- public Face[] getFaces() {
- return null;
- }
-
- // The rotation of the full-resolution image. By default, it returns the value of
- // getRotation().
- public int getFullImageRotation() {
- return getRotation();
- }
-
- public int getRotation() {
- return 0;
- }
-
- public long getSize() {
- return 0;
- }
-
- public abstract String getMimeType();
-
- public String getFilePath() {
- return "";
- }
-
- // Returns width and height of the media item.
- // Returns 0, 0 if the information is not available.
- public abstract int getWidth();
- public abstract int getHeight();
-
- // This is an alternative for requestImage() in PhotoPage. If this
- // is implemented, you don't need to implement requestImage().
- public ScreenNail getScreenNail() {
- return null;
- }
-
- public static int getTargetSize(int type) {
- switch (type) {
- case TYPE_THUMBNAIL:
- return sThumbnailTargetSize;
- case TYPE_MICROTHUMBNAIL:
- return sMicrothumbnailTargetSize;
- default:
- throw new RuntimeException(
- "should only request thumb/microthumb from cache");
- }
- }
-
- public static BytesBufferPool getBytesBufferPool() {
- return sMicroThumbBufferPool;
- }
-
- public static void setThumbnailSizes(int size, int microSize) {
- sThumbnailTargetSize = size;
- if (sMicrothumbnailTargetSize != microSize) {
- sMicrothumbnailTargetSize = microSize;
- }
- }
-}
diff --git a/src/com/android/gallery3d/data/MediaObject.java b/src/com/android/gallery3d/data/MediaObject.java
deleted file mode 100644
index 270d4cf0b..000000000
--- a/src/com/android/gallery3d/data/MediaObject.java
+++ /dev/null
@@ -1,166 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.net.Uri;
-
-public abstract class MediaObject {
- @SuppressWarnings("unused")
- private static final String TAG = "MediaObject";
- public static final long INVALID_DATA_VERSION = -1;
-
- // These are the bits returned from getSupportedOperations():
- public static final int SUPPORT_DELETE = 1 << 0;
- public static final int SUPPORT_ROTATE = 1 << 1;
- public static final int SUPPORT_SHARE = 1 << 2;
- public static final int SUPPORT_CROP = 1 << 3;
- public static final int SUPPORT_SHOW_ON_MAP = 1 << 4;
- public static final int SUPPORT_SETAS = 1 << 5;
- public static final int SUPPORT_FULL_IMAGE = 1 << 6;
- public static final int SUPPORT_PLAY = 1 << 7;
- public static final int SUPPORT_CACHE = 1 << 8;
- public static final int SUPPORT_EDIT = 1 << 9;
- public static final int SUPPORT_INFO = 1 << 10;
- public static final int SUPPORT_TRIM = 1 << 11;
- public static final int SUPPORT_UNLOCK = 1 << 12;
- public static final int SUPPORT_BACK = 1 << 13;
- public static final int SUPPORT_ACTION = 1 << 14;
- public static final int SUPPORT_CAMERA_SHORTCUT = 1 << 15;
- public static final int SUPPORT_MUTE = 1 << 16;
- public static final int SUPPORT_ALL = 0xffffffff;
-
- // These are the bits returned from getMediaType():
- public static final int MEDIA_TYPE_UNKNOWN = 1;
- public static final int MEDIA_TYPE_IMAGE = 2;
- public static final int MEDIA_TYPE_VIDEO = 4;
- public static final int MEDIA_TYPE_ALL = MEDIA_TYPE_IMAGE | MEDIA_TYPE_VIDEO;
-
- public static final String MEDIA_TYPE_IMAGE_STRING = "image";
- public static final String MEDIA_TYPE_VIDEO_STRING = "video";
- public static final String MEDIA_TYPE_ALL_STRING = "all";
-
- // These are flags for cache() and return values for getCacheFlag():
- public static final int CACHE_FLAG_NO = 0;
- public static final int CACHE_FLAG_SCREENNAIL = 1;
- public static final int CACHE_FLAG_FULL = 2;
-
- // These are return values for getCacheStatus():
- public static final int CACHE_STATUS_NOT_CACHED = 0;
- public static final int CACHE_STATUS_CACHING = 1;
- public static final int CACHE_STATUS_CACHED_SCREENNAIL = 2;
- public static final int CACHE_STATUS_CACHED_FULL = 3;
-
- private static long sVersionSerial = 0;
-
- protected long mDataVersion;
-
- protected final Path mPath;
-
- public interface PanoramaSupportCallback {
- void panoramaInfoAvailable(MediaObject mediaObject, boolean isPanorama,
- boolean isPanorama360);
- }
-
- public MediaObject(Path path, long version) {
- path.setObject(this);
- mPath = path;
- mDataVersion = version;
- }
-
- public Path getPath() {
- return mPath;
- }
-
- public int getSupportedOperations() {
- return 0;
- }
-
- public void getPanoramaSupport(PanoramaSupportCallback callback) {
- callback.panoramaInfoAvailable(this, false, false);
- }
-
- public void clearCachedPanoramaSupport() {
- }
-
- public void delete() {
- throw new UnsupportedOperationException();
- }
-
- public void rotate(int degrees) {
- throw new UnsupportedOperationException();
- }
-
- public Uri getContentUri() {
- String className = getClass().getName();
- Log.e(TAG, "Class " + className + "should implement getContentUri.");
- Log.e(TAG, "The object was created from path: " + getPath());
- throw new UnsupportedOperationException();
- }
-
- public Uri getPlayUri() {
- throw new UnsupportedOperationException();
- }
-
- public int getMediaType() {
- return MEDIA_TYPE_UNKNOWN;
- }
-
- public MediaDetails getDetails() {
- MediaDetails details = new MediaDetails();
- return details;
- }
-
- public long getDataVersion() {
- return mDataVersion;
- }
-
- public int getCacheFlag() {
- return CACHE_FLAG_NO;
- }
-
- public int getCacheStatus() {
- throw new UnsupportedOperationException();
- }
-
- public long getCacheSize() {
- throw new UnsupportedOperationException();
- }
-
- public void cache(int flag) {
- throw new UnsupportedOperationException();
- }
-
- public static synchronized long nextVersionNumber() {
- return ++MediaObject.sVersionSerial;
- }
-
- public static int getTypeFromString(String s) {
- if (MEDIA_TYPE_ALL_STRING.equals(s)) return MediaObject.MEDIA_TYPE_ALL;
- if (MEDIA_TYPE_IMAGE_STRING.equals(s)) return MediaObject.MEDIA_TYPE_IMAGE;
- if (MEDIA_TYPE_VIDEO_STRING.equals(s)) return MediaObject.MEDIA_TYPE_VIDEO;
- throw new IllegalArgumentException(s);
- }
-
- public static String getTypeString(int type) {
- switch (type) {
- case MEDIA_TYPE_IMAGE: return MEDIA_TYPE_IMAGE_STRING;
- case MEDIA_TYPE_VIDEO: return MEDIA_TYPE_VIDEO_STRING;
- case MEDIA_TYPE_ALL: return MEDIA_TYPE_ALL_STRING;
- }
- throw new IllegalArgumentException();
- }
-}
diff --git a/src/com/android/gallery3d/data/MediaSet.java b/src/com/android/gallery3d/data/MediaSet.java
deleted file mode 100644
index 683aa6b32..000000000
--- a/src/com/android/gallery3d/data/MediaSet.java
+++ /dev/null
@@ -1,348 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.util.Future;
-
-import java.util.ArrayList;
-import java.util.WeakHashMap;
-
-// MediaSet is a directory-like data structure.
-// It contains MediaItems and sub-MediaSets.
-//
-// The primary interface are:
-// getMediaItemCount(), getMediaItem() and
-// getSubMediaSetCount(), getSubMediaSet().
-//
-// getTotalMediaItemCount() returns the number of all MediaItems, including
-// those in sub-MediaSets.
-public abstract class MediaSet extends MediaObject {
- @SuppressWarnings("unused")
- private static final String TAG = "MediaSet";
-
- public static final int MEDIAITEM_BATCH_FETCH_COUNT = 500;
- public static final int INDEX_NOT_FOUND = -1;
-
- public static final int SYNC_RESULT_SUCCESS = 0;
- public static final int SYNC_RESULT_CANCELLED = 1;
- public static final int SYNC_RESULT_ERROR = 2;
-
- /** Listener to be used with requestSync(SyncListener). */
- public static interface SyncListener {
- /**
- * Called when the sync task completed. Completion may be due to normal termination,
- * an exception, or cancellation.
- *
- * @param mediaSet the MediaSet that's done with sync
- * @param resultCode one of the SYNC_RESULT_* constants
- */
- void onSyncDone(MediaSet mediaSet, int resultCode);
- }
-
- public MediaSet(Path path, long version) {
- super(path, version);
- }
-
- public int getMediaItemCount() {
- return 0;
- }
-
- // Returns the media items in the range [start, start + count).
- //
- // The number of media items returned may be less than the specified count
- // if there are not enough media items available. The number of
- // media items available may not be consistent with the return value of
- // getMediaItemCount() because the contents of database may have already
- // changed.
- public ArrayList<MediaItem> getMediaItem(int start, int count) {
- return new ArrayList<MediaItem>();
- }
-
- public MediaItem getCoverMediaItem() {
- ArrayList<MediaItem> items = getMediaItem(0, 1);
- if (items.size() > 0) return items.get(0);
- for (int i = 0, n = getSubMediaSetCount(); i < n; i++) {
- MediaItem cover = getSubMediaSet(i).getCoverMediaItem();
- if (cover != null) return cover;
- }
- return null;
- }
-
- public int getSubMediaSetCount() {
- return 0;
- }
-
- public MediaSet getSubMediaSet(int index) {
- throw new IndexOutOfBoundsException();
- }
-
- public boolean isLeafAlbum() {
- return false;
- }
-
- public boolean isCameraRoll() {
- return false;
- }
-
- /**
- * Method {@link #reload()} may process the loading task in background, this method tells
- * its client whether the loading is still in process or not.
- */
- public boolean isLoading() {
- return false;
- }
-
- public int getTotalMediaItemCount() {
- int total = getMediaItemCount();
- for (int i = 0, n = getSubMediaSetCount(); i < n; i++) {
- total += getSubMediaSet(i).getTotalMediaItemCount();
- }
- return total;
- }
-
- // TODO: we should have better implementation of sub classes
- public int getIndexOfItem(Path path, int hint) {
- // hint < 0 is handled below
- // first, try to find it around the hint
- int start = Math.max(0,
- hint - MEDIAITEM_BATCH_FETCH_COUNT / 2);
- ArrayList<MediaItem> list = getMediaItem(
- start, MEDIAITEM_BATCH_FETCH_COUNT);
- int index = getIndexOf(path, list);
- if (index != INDEX_NOT_FOUND) return start + index;
-
- // try to find it globally
- start = start == 0 ? MEDIAITEM_BATCH_FETCH_COUNT : 0;
- list = getMediaItem(start, MEDIAITEM_BATCH_FETCH_COUNT);
- while (true) {
- index = getIndexOf(path, list);
- if (index != INDEX_NOT_FOUND) return start + index;
- if (list.size() < MEDIAITEM_BATCH_FETCH_COUNT) return INDEX_NOT_FOUND;
- start += MEDIAITEM_BATCH_FETCH_COUNT;
- list = getMediaItem(start, MEDIAITEM_BATCH_FETCH_COUNT);
- }
- }
-
- protected int getIndexOf(Path path, ArrayList<MediaItem> list) {
- for (int i = 0, n = list.size(); i < n; ++i) {
- // item could be null only in ClusterAlbum
- MediaObject item = list.get(i);
- if (item != null && item.mPath == path) return i;
- }
- return INDEX_NOT_FOUND;
- }
-
- public abstract String getName();
-
- private WeakHashMap<ContentListener, Object> mListeners =
- new WeakHashMap<ContentListener, Object>();
-
- // NOTE: The MediaSet only keeps a weak reference to the listener. The
- // listener is automatically removed when there is no other reference to
- // the listener.
- public void addContentListener(ContentListener listener) {
- mListeners.put(listener, null);
- }
-
- public void removeContentListener(ContentListener listener) {
- mListeners.remove(listener);
- }
-
- // This should be called by subclasses when the content is changed.
- public void notifyContentChanged() {
- for (ContentListener listener : mListeners.keySet()) {
- listener.onContentDirty();
- }
- }
-
- // Reload the content. Return the current data version. reload() should be called
- // in the same thread as getMediaItem(int, int) and getSubMediaSet(int).
- public abstract long reload();
-
- @Override
- public MediaDetails getDetails() {
- MediaDetails details = super.getDetails();
- details.addDetail(MediaDetails.INDEX_TITLE, getName());
- return details;
- }
-
- // Enumerate all media items in this media set (including the ones in sub
- // media sets), in an efficient order. ItemConsumer.consumer() will be
- // called for each media item with its index.
- public void enumerateMediaItems(ItemConsumer consumer) {
- enumerateMediaItems(consumer, 0);
- }
-
- public void enumerateTotalMediaItems(ItemConsumer consumer) {
- enumerateTotalMediaItems(consumer, 0);
- }
-
- public static interface ItemConsumer {
- void consume(int index, MediaItem item);
- }
-
- // The default implementation uses getMediaItem() for enumerateMediaItems().
- // Subclasses may override this and use more efficient implementations.
- // Returns the number of items enumerated.
- protected int enumerateMediaItems(ItemConsumer consumer, int startIndex) {
- int total = getMediaItemCount();
- int start = 0;
- while (start < total) {
- int count = Math.min(MEDIAITEM_BATCH_FETCH_COUNT, total - start);
- ArrayList<MediaItem> items = getMediaItem(start, count);
- for (int i = 0, n = items.size(); i < n; i++) {
- MediaItem item = items.get(i);
- consumer.consume(startIndex + start + i, item);
- }
- start += count;
- }
- return total;
- }
-
- // Recursively enumerate all media items under this set.
- // Returns the number of items enumerated.
- protected int enumerateTotalMediaItems(
- ItemConsumer consumer, int startIndex) {
- int start = 0;
- start += enumerateMediaItems(consumer, startIndex);
- int m = getSubMediaSetCount();
- for (int i = 0; i < m; i++) {
- start += getSubMediaSet(i).enumerateTotalMediaItems(
- consumer, startIndex + start);
- }
- return start;
- }
-
- /**
- * Requests sync on this MediaSet. It returns a Future object that can be used by the caller
- * to query the status of the sync. The sync result code is one of the SYNC_RESULT_* constants
- * defined in this class and can be obtained by Future.get().
- *
- * Subclasses should perform sync on a different thread.
- *
- * The default implementation here returns a Future stub that does nothing and returns
- * SYNC_RESULT_SUCCESS by get().
- */
- public Future<Integer> requestSync(SyncListener listener) {
- listener.onSyncDone(this, SYNC_RESULT_SUCCESS);
- return FUTURE_STUB;
- }
-
- private static final Future<Integer> FUTURE_STUB = new Future<Integer>() {
- @Override
- public void cancel() {}
-
- @Override
- public boolean isCancelled() {
- return false;
- }
-
- @Override
- public boolean isDone() {
- return true;
- }
-
- @Override
- public Integer get() {
- return SYNC_RESULT_SUCCESS;
- }
-
- @Override
- public void waitDone() {}
- };
-
- protected Future<Integer> requestSyncOnMultipleSets(MediaSet[] sets, SyncListener listener) {
- return new MultiSetSyncFuture(sets, listener);
- }
-
- private class MultiSetSyncFuture implements Future<Integer>, SyncListener {
- @SuppressWarnings("hiding")
- private static final String TAG = "Gallery.MultiSetSync";
-
- private final SyncListener mListener;
- private final Future<Integer> mFutures[];
-
- private boolean mIsCancelled = false;
- private int mResult = -1;
- private int mPendingCount;
-
- @SuppressWarnings("unchecked")
- MultiSetSyncFuture(MediaSet[] sets, SyncListener listener) {
- mListener = listener;
- mPendingCount = sets.length;
- mFutures = new Future[sets.length];
-
- synchronized (this) {
- for (int i = 0, n = sets.length; i < n; ++i) {
- mFutures[i] = sets[i].requestSync(this);
- Log.d(TAG, " request sync: " + Utils.maskDebugInfo(sets[i].getName()));
- }
- }
- }
-
- @Override
- public synchronized void cancel() {
- if (mIsCancelled) return;
- mIsCancelled = true;
- for (Future<Integer> future : mFutures) future.cancel();
- if (mResult < 0) mResult = SYNC_RESULT_CANCELLED;
- }
-
- @Override
- public synchronized boolean isCancelled() {
- return mIsCancelled;
- }
-
- @Override
- public synchronized boolean isDone() {
- return mPendingCount == 0;
- }
-
- @Override
- public synchronized Integer get() {
- waitDone();
- return mResult;
- }
-
- @Override
- public synchronized void waitDone() {
- try {
- while (!isDone()) wait();
- } catch (InterruptedException e) {
- Log.d(TAG, "waitDone() interrupted");
- }
- }
-
- // SyncListener callback
- @Override
- public void onSyncDone(MediaSet mediaSet, int resultCode) {
- SyncListener listener = null;
- synchronized (this) {
- if (resultCode == SYNC_RESULT_ERROR) mResult = SYNC_RESULT_ERROR;
- --mPendingCount;
- if (mPendingCount == 0) {
- listener = mListener;
- notifyAll();
- }
- Log.d(TAG, "onSyncDone: " + Utils.maskDebugInfo(mediaSet.getName())
- + " #pending=" + mPendingCount);
- }
- if (listener != null) listener.onSyncDone(MediaSet.this, mResult);
- }
- }
-}
diff --git a/src/com/android/gallery3d/data/MediaSource.java b/src/com/android/gallery3d/data/MediaSource.java
deleted file mode 100644
index 95901283b..000000000
--- a/src/com/android/gallery3d/data/MediaSource.java
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.net.Uri;
-
-import com.android.gallery3d.data.MediaSet.ItemConsumer;
-
-import java.util.ArrayList;
-
-public abstract class MediaSource {
- private static final String TAG = "MediaSource";
- private String mPrefix;
-
- protected MediaSource(String prefix) {
- mPrefix = prefix;
- }
-
- public String getPrefix() {
- return mPrefix;
- }
-
- public Path findPathByUri(Uri uri, String type) {
- return null;
- }
-
- public abstract MediaObject createMediaObject(Path path);
-
- public void pause() {
- }
-
- public void resume() {
- }
-
- public Path getDefaultSetOf(Path item) {
- return null;
- }
-
- public long getTotalUsedCacheSize() {
- return 0;
- }
-
- public long getTotalTargetCacheSize() {
- return 0;
- }
-
- public static class PathId {
- public PathId(Path path, int id) {
- this.path = path;
- this.id = id;
- }
- public Path path;
- public int id;
- }
-
- // Maps a list of Paths (all belong to this MediaSource) to MediaItems,
- // and invoke consumer.consume() for each MediaItem with the given id.
- //
- // This default implementation uses getMediaObject for each Path. Subclasses
- // may override this and provide more efficient implementation (like
- // batching the database query).
- public void mapMediaItems(ArrayList<PathId> list, ItemConsumer consumer) {
- int n = list.size();
- for (int i = 0; i < n; i++) {
- PathId pid = list.get(i);
- MediaObject obj;
- synchronized (DataManager.LOCK) {
- obj = pid.path.getObject();
- if (obj == null) {
- try {
- obj = createMediaObject(pid.path);
- } catch (Throwable th) {
- Log.w(TAG, "cannot create media object: " + pid.path, th);
- }
- }
- }
- if (obj != null) {
- consumer.consume(pid.id, (MediaItem) obj);
- }
- }
- }
-}
diff --git a/src/com/android/gallery3d/data/MtpClient.java b/src/com/android/gallery3d/data/MtpClient.java
deleted file mode 100644
index 737b5b60d..000000000
--- a/src/com/android/gallery3d/data/MtpClient.java
+++ /dev/null
@@ -1,443 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.annotation.TargetApi;
-import android.app.PendingIntent;
-import android.content.BroadcastReceiver;
-import android.content.Context;
-import android.content.Intent;
-import android.content.IntentFilter;
-import android.hardware.usb.UsbConstants;
-import android.hardware.usb.UsbDevice;
-import android.hardware.usb.UsbDeviceConnection;
-import android.hardware.usb.UsbInterface;
-import android.hardware.usb.UsbManager;
-import android.mtp.MtpDevice;
-import android.mtp.MtpObjectInfo;
-import android.mtp.MtpStorageInfo;
-import android.util.Log;
-
-import com.android.gallery3d.common.ApiHelper;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.List;
-
-/**
- * This class helps an application manage a list of connected MTP or PTP devices.
- * It listens for MTP devices being attached and removed from the USB host bus
- * and notifies the application when the MTP device list changes.
- */
-@TargetApi(ApiHelper.VERSION_CODES.HONEYCOMB_MR1)
-public class MtpClient {
-
- private static final String TAG = "MtpClient";
-
- private static final String ACTION_USB_PERMISSION =
- "android.mtp.MtpClient.action.USB_PERMISSION";
-
- private final Context mContext;
- private final UsbManager mUsbManager;
- private final ArrayList<Listener> mListeners = new ArrayList<Listener>();
- // mDevices contains all MtpDevices that have been seen by our client,
- // so we can inform when the device has been detached.
- // mDevices is also used for synchronization in this class.
- private final HashMap<String, MtpDevice> mDevices = new HashMap<String, MtpDevice>();
- // List of MTP devices we should not try to open for which we are currently
- // asking for permission to open.
- private final ArrayList<String> mRequestPermissionDevices = new ArrayList<String>();
- // List of MTP devices we should not try to open.
- // We add devices to this list if the user canceled a permission request or we were
- // unable to open the device.
- private final ArrayList<String> mIgnoredDevices = new ArrayList<String>();
-
- private final PendingIntent mPermissionIntent;
-
- private final BroadcastReceiver mUsbReceiver = new BroadcastReceiver() {
- @Override
- public void onReceive(Context context, Intent intent) {
- String action = intent.getAction();
- UsbDevice usbDevice = (UsbDevice)intent.getParcelableExtra(UsbManager.EXTRA_DEVICE);
- String deviceName = usbDevice.getDeviceName();
-
- synchronized (mDevices) {
- MtpDevice mtpDevice = mDevices.get(deviceName);
-
- if (UsbManager.ACTION_USB_DEVICE_ATTACHED.equals(action)) {
- if (mtpDevice == null) {
- mtpDevice = openDeviceLocked(usbDevice);
- }
- if (mtpDevice != null) {
- for (Listener listener : mListeners) {
- listener.deviceAdded(mtpDevice);
- }
- }
- } else if (UsbManager.ACTION_USB_DEVICE_DETACHED.equals(action)) {
- if (mtpDevice != null) {
- mDevices.remove(deviceName);
- mRequestPermissionDevices.remove(deviceName);
- mIgnoredDevices.remove(deviceName);
- for (Listener listener : mListeners) {
- listener.deviceRemoved(mtpDevice);
- }
- }
- } else if (ACTION_USB_PERMISSION.equals(action)) {
- mRequestPermissionDevices.remove(deviceName);
- boolean permission = intent.getBooleanExtra(UsbManager.EXTRA_PERMISSION_GRANTED,
- false);
- Log.d(TAG, "ACTION_USB_PERMISSION: " + permission);
- if (permission) {
- if (mtpDevice == null) {
- mtpDevice = openDeviceLocked(usbDevice);
- }
- if (mtpDevice != null) {
- for (Listener listener : mListeners) {
- listener.deviceAdded(mtpDevice);
- }
- }
- } else {
- // so we don't ask for permission again
- mIgnoredDevices.add(deviceName);
- }
- }
- }
- }
- };
-
- /**
- * An interface for being notified when MTP or PTP devices are attached
- * or removed. In the current implementation, only PTP devices are supported.
- */
- public interface Listener {
- /**
- * Called when a new device has been added
- *
- * @param device the new device that was added
- */
- public void deviceAdded(MtpDevice device);
-
- /**
- * Called when a new device has been removed
- *
- * @param device the device that was removed
- */
- public void deviceRemoved(MtpDevice device);
- }
-
- /**
- * Tests to see if a {@link android.hardware.usb.UsbDevice}
- * supports the PTP protocol (typically used by digital cameras)
- *
- * @param device the device to test
- * @return true if the device is a PTP device.
- */
- static public boolean isCamera(UsbDevice device) {
- int count = device.getInterfaceCount();
- for (int i = 0; i < count; i++) {
- UsbInterface intf = device.getInterface(i);
- if (intf.getInterfaceClass() == UsbConstants.USB_CLASS_STILL_IMAGE &&
- intf.getInterfaceSubclass() == 1 &&
- intf.getInterfaceProtocol() == 1) {
- return true;
- }
- }
- return false;
- }
-
- /**
- * MtpClient constructor
- *
- * @param context the {@link android.content.Context} to use for the MtpClient
- */
- public MtpClient(Context context) {
- mContext = context;
- mUsbManager = (UsbManager)context.getSystemService(Context.USB_SERVICE);
- mPermissionIntent = PendingIntent.getBroadcast(mContext, 0, new Intent(ACTION_USB_PERMISSION), 0);
- IntentFilter filter = new IntentFilter();
- filter.addAction(UsbManager.ACTION_USB_DEVICE_ATTACHED);
- filter.addAction(UsbManager.ACTION_USB_DEVICE_DETACHED);
- filter.addAction(ACTION_USB_PERMISSION);
- context.registerReceiver(mUsbReceiver, filter);
- }
-
- /**
- * Opens the {@link android.hardware.usb.UsbDevice} for an MTP or PTP
- * device and return an {@link android.mtp.MtpDevice} for it.
- *
- * @param usbDevice the device to open
- * @return an MtpDevice for the device.
- */
- private MtpDevice openDeviceLocked(UsbDevice usbDevice) {
- String deviceName = usbDevice.getDeviceName();
-
- // don't try to open devices that we have decided to ignore
- // or are currently asking permission for
- if (isCamera(usbDevice) && !mIgnoredDevices.contains(deviceName)
- && !mRequestPermissionDevices.contains(deviceName)) {
- if (!mUsbManager.hasPermission(usbDevice)) {
- mUsbManager.requestPermission(usbDevice, mPermissionIntent);
- mRequestPermissionDevices.add(deviceName);
- } else {
- UsbDeviceConnection connection = mUsbManager.openDevice(usbDevice);
- if (connection != null) {
- MtpDevice mtpDevice = new MtpDevice(usbDevice);
- if (mtpDevice.open(connection)) {
- mDevices.put(usbDevice.getDeviceName(), mtpDevice);
- return mtpDevice;
- } else {
- // so we don't try to open it again
- mIgnoredDevices.add(deviceName);
- }
- } else {
- // so we don't try to open it again
- mIgnoredDevices.add(deviceName);
- }
- }
- }
- return null;
- }
-
- /**
- * Closes all resources related to the MtpClient object
- */
- public void close() {
- mContext.unregisterReceiver(mUsbReceiver);
- }
-
- /**
- * Registers a {@link com.android.gallery3d.data.MtpClient.Listener} interface to receive
- * notifications when MTP or PTP devices are added or removed.
- *
- * @param listener the listener to register
- */
- public void addListener(Listener listener) {
- synchronized (mDevices) {
- if (!mListeners.contains(listener)) {
- mListeners.add(listener);
- }
- }
- }
-
- /**
- * Unregisters a {@link com.android.gallery3d.data.MtpClient.Listener} interface.
- *
- * @param listener the listener to unregister
- */
- public void removeListener(Listener listener) {
- synchronized (mDevices) {
- mListeners.remove(listener);
- }
- }
-
- /**
- * Retrieves an {@link android.mtp.MtpDevice} object for the USB device
- * with the given name.
- *
- * @param deviceName the name of the USB device
- * @return the MtpDevice, or null if it does not exist
- */
- public MtpDevice getDevice(String deviceName) {
- synchronized (mDevices) {
- return mDevices.get(deviceName);
- }
- }
-
- /**
- * Retrieves an {@link android.mtp.MtpDevice} object for the USB device
- * with the given ID.
- *
- * @param id the ID of the USB device
- * @return the MtpDevice, or null if it does not exist
- */
- public MtpDevice getDevice(int id) {
- synchronized (mDevices) {
- return mDevices.get(UsbDevice.getDeviceName(id));
- }
- }
-
- /**
- * Retrieves a list of all currently connected {@link android.mtp.MtpDevice}.
- *
- * @return the list of MtpDevices
- */
- public List<MtpDevice> getDeviceList() {
- synchronized (mDevices) {
- // Query the USB manager since devices might have attached
- // before we added our listener.
- for (UsbDevice usbDevice : mUsbManager.getDeviceList().values()) {
- if (mDevices.get(usbDevice.getDeviceName()) == null) {
- openDeviceLocked(usbDevice);
- }
- }
-
- return new ArrayList<MtpDevice>(mDevices.values());
- }
- }
-
- /**
- * Retrieves a list of all {@link android.mtp.MtpStorageInfo}
- * for the MTP or PTP device with the given USB device name
- *
- * @param deviceName the name of the USB device
- * @return the list of MtpStorageInfo
- */
- public List<MtpStorageInfo> getStorageList(String deviceName) {
- MtpDevice device = getDevice(deviceName);
- if (device == null) {
- return null;
- }
- int[] storageIds = device.getStorageIds();
- if (storageIds == null) {
- return null;
- }
-
- int length = storageIds.length;
- ArrayList<MtpStorageInfo> storageList = new ArrayList<MtpStorageInfo>(length);
- for (int i = 0; i < length; i++) {
- MtpStorageInfo info = device.getStorageInfo(storageIds[i]);
- if (info == null) {
- Log.w(TAG, "getStorageInfo failed");
- } else {
- storageList.add(info);
- }
- }
- return storageList;
- }
-
- /**
- * Retrieves the {@link android.mtp.MtpObjectInfo} for an object on
- * the MTP or PTP device with the given USB device name with the given
- * object handle
- *
- * @param deviceName the name of the USB device
- * @param objectHandle handle of the object to query
- * @return the MtpObjectInfo
- */
- public MtpObjectInfo getObjectInfo(String deviceName, int objectHandle) {
- MtpDevice device = getDevice(deviceName);
- if (device == null) {
- return null;
- }
- return device.getObjectInfo(objectHandle);
- }
-
- /**
- * Deletes an object on the MTP or PTP device with the given USB device name.
- *
- * @param deviceName the name of the USB device
- * @param objectHandle handle of the object to delete
- * @return true if the deletion succeeds
- */
- public boolean deleteObject(String deviceName, int objectHandle) {
- MtpDevice device = getDevice(deviceName);
- if (device == null) {
- return false;
- }
- return device.deleteObject(objectHandle);
- }
-
- /**
- * Retrieves a list of {@link android.mtp.MtpObjectInfo} for all objects
- * on the MTP or PTP device with the given USB device name and given storage ID
- * and/or object handle.
- * If the object handle is zero, then all objects in the root of the storage unit
- * will be returned. Otherwise, all immediate children of the object will be returned.
- * If the storage ID is also zero, then all objects on all storage units will be returned.
- *
- * @param deviceName the name of the USB device
- * @param storageId the ID of the storage unit to query, or zero for all
- * @param objectHandle the handle of the parent object to query, or zero for the storage root
- * @return the list of MtpObjectInfo
- */
- public List<MtpObjectInfo> getObjectList(String deviceName, int storageId, int objectHandle) {
- MtpDevice device = getDevice(deviceName);
- if (device == null) {
- return null;
- }
- if (objectHandle == 0) {
- // all objects in root of storage
- objectHandle = 0xFFFFFFFF;
- }
- int[] handles = device.getObjectHandles(storageId, 0, objectHandle);
- if (handles == null) {
- return null;
- }
-
- int length = handles.length;
- ArrayList<MtpObjectInfo> objectList = new ArrayList<MtpObjectInfo>(length);
- for (int i = 0; i < length; i++) {
- MtpObjectInfo info = device.getObjectInfo(handles[i]);
- if (info == null) {
- Log.w(TAG, "getObjectInfo failed");
- } else {
- objectList.add(info);
- }
- }
- return objectList;
- }
-
- /**
- * Returns the data for an object as a byte array.
- *
- * @param deviceName the name of the USB device containing the object
- * @param objectHandle handle of the object to read
- * @param objectSize the size of the object (this should match
- * {@link android.mtp.MtpObjectInfo#getCompressedSize}
- * @return the object's data, or null if reading fails
- */
- public byte[] getObject(String deviceName, int objectHandle, int objectSize) {
- MtpDevice device = getDevice(deviceName);
- if (device == null) {
- return null;
- }
- return device.getObject(objectHandle, objectSize);
- }
-
- /**
- * Returns the thumbnail data for an object as a byte array.
- *
- * @param deviceName the name of the USB device containing the object
- * @param objectHandle handle of the object to read
- * @return the object's thumbnail, or null if reading fails
- */
- public byte[] getThumbnail(String deviceName, int objectHandle) {
- MtpDevice device = getDevice(deviceName);
- if (device == null) {
- return null;
- }
- return device.getThumbnail(objectHandle);
- }
-
- /**
- * Copies the data for an object to a file in external storage.
- *
- * @param deviceName the name of the USB device containing the object
- * @param objectHandle handle of the object to read
- * @param destPath path to destination for the file transfer.
- * This path should be in the external storage as defined by
- * {@link android.os.Environment#getExternalStorageDirectory}
- * @return true if the file transfer succeeds
- */
- public boolean importFile(String deviceName, int objectHandle, String destPath) {
- MtpDevice device = getDevice(deviceName);
- if (device == null) {
- return false;
- }
- return device.importFile(objectHandle, destPath);
- }
-}
diff --git a/src/com/android/gallery3d/data/PanoramaMetadataJob.java b/src/com/android/gallery3d/data/PanoramaMetadataJob.java
deleted file mode 100644
index ab99d6a81..000000000
--- a/src/com/android/gallery3d/data/PanoramaMetadataJob.java
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.Context;
-import android.net.Uri;
-
-import com.android.gallery3d.util.LightCycleHelper;
-import com.android.gallery3d.util.LightCycleHelper.PanoramaMetadata;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-public class PanoramaMetadataJob implements Job<PanoramaMetadata> {
- Context mContext;
- Uri mUri;
-
- public PanoramaMetadataJob(Context context, Uri uri) {
- mContext = context;
- mUri = uri;
- }
-
- @Override
- public PanoramaMetadata run(JobContext jc) {
- return LightCycleHelper.getPanoramaMetadata(mContext, mUri);
- }
-}
diff --git a/src/com/android/gallery3d/data/Path.java b/src/com/android/gallery3d/data/Path.java
deleted file mode 100644
index fcae65e66..000000000
--- a/src/com/android/gallery3d/data/Path.java
+++ /dev/null
@@ -1,241 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.util.IdentityCache;
-
-import java.lang.ref.WeakReference;
-import java.util.ArrayList;
-
-public class Path {
- private static final String TAG = "Path";
- private static Path sRoot = new Path(null, "ROOT");
-
- private final Path mParent;
- private final String mSegment;
- private WeakReference<MediaObject> mObject;
- private IdentityCache<String, Path> mChildren;
-
- private Path(Path parent, String segment) {
- mParent = parent;
- mSegment = segment;
- }
-
- public Path getChild(String segment) {
- synchronized (Path.class) {
- if (mChildren == null) {
- mChildren = new IdentityCache<String, Path>();
- } else {
- Path p = mChildren.get(segment);
- if (p != null) return p;
- }
-
- Path p = new Path(this, segment);
- mChildren.put(segment, p);
- return p;
- }
- }
-
- public Path getParent() {
- synchronized (Path.class) {
- return mParent;
- }
- }
-
- public Path getChild(int segment) {
- return getChild(String.valueOf(segment));
- }
-
- public Path getChild(long segment) {
- return getChild(String.valueOf(segment));
- }
-
- public void setObject(MediaObject object) {
- synchronized (Path.class) {
- Utils.assertTrue(mObject == null || mObject.get() == null);
- mObject = new WeakReference<MediaObject>(object);
- }
- }
-
- MediaObject getObject() {
- synchronized (Path.class) {
- return (mObject == null) ? null : mObject.get();
- }
- }
-
- @Override
- // TODO: toString() should be more efficient, will fix it later
- public String toString() {
- synchronized (Path.class) {
- StringBuilder sb = new StringBuilder();
- String[] segments = split();
- for (int i = 0; i < segments.length; i++) {
- sb.append("/");
- sb.append(segments[i]);
- }
- return sb.toString();
- }
- }
-
- public boolean equalsIgnoreCase (String p) {
- String path = toString();
- return path.equalsIgnoreCase(p);
- }
-
- public static Path fromString(String s) {
- synchronized (Path.class) {
- String[] segments = split(s);
- Path current = sRoot;
- for (int i = 0; i < segments.length; i++) {
- current = current.getChild(segments[i]);
- }
- return current;
- }
- }
-
- public String[] split() {
- synchronized (Path.class) {
- int n = 0;
- for (Path p = this; p != sRoot; p = p.mParent) {
- n++;
- }
- String[] segments = new String[n];
- int i = n - 1;
- for (Path p = this; p != sRoot; p = p.mParent) {
- segments[i--] = p.mSegment;
- }
- return segments;
- }
- }
-
- public static String[] split(String s) {
- int n = s.length();
- if (n == 0) return new String[0];
- if (s.charAt(0) != '/') {
- throw new RuntimeException("malformed path:" + s);
- }
- ArrayList<String> segments = new ArrayList<String>();
- int i = 1;
- while (i < n) {
- int brace = 0;
- int j;
- for (j = i; j < n; j++) {
- char c = s.charAt(j);
- if (c == '{') ++brace;
- else if (c == '}') --brace;
- else if (brace == 0 && c == '/') break;
- }
- if (brace != 0) {
- throw new RuntimeException("unbalanced brace in path:" + s);
- }
- segments.add(s.substring(i, j));
- i = j + 1;
- }
- String[] result = new String[segments.size()];
- segments.toArray(result);
- return result;
- }
-
- // Splits a string to an array of strings.
- // For example, "{foo,bar,baz}" -> {"foo","bar","baz"}.
- public static String[] splitSequence(String s) {
- int n = s.length();
- if (s.charAt(0) != '{' || s.charAt(n-1) != '}') {
- throw new RuntimeException("bad sequence: " + s);
- }
- ArrayList<String> segments = new ArrayList<String>();
- int i = 1;
- while (i < n - 1) {
- int brace = 0;
- int j;
- for (j = i; j < n - 1; j++) {
- char c = s.charAt(j);
- if (c == '{') ++brace;
- else if (c == '}') --brace;
- else if (brace == 0 && c == ',') break;
- }
- if (brace != 0) {
- throw new RuntimeException("unbalanced brace in path:" + s);
- }
- segments.add(s.substring(i, j));
- i = j + 1;
- }
- String[] result = new String[segments.size()];
- segments.toArray(result);
- return result;
- }
-
- public String getPrefix() {
- if (this == sRoot) return "";
- return getPrefixPath().mSegment;
- }
-
- public Path getPrefixPath() {
- synchronized (Path.class) {
- Path current = this;
- if (current == sRoot) {
- throw new IllegalStateException();
- }
- while (current.mParent != sRoot) {
- current = current.mParent;
- }
- return current;
- }
- }
-
- public String getSuffix() {
- // We don't need lock because mSegment is final.
- return mSegment;
- }
-
- // Below are for testing/debugging only
- static void clearAll() {
- synchronized (Path.class) {
- sRoot = new Path(null, "");
- }
- }
-
- static void dumpAll() {
- dumpAll(sRoot, "", "");
- }
-
- static void dumpAll(Path p, String prefix1, String prefix2) {
- synchronized (Path.class) {
- MediaObject obj = p.getObject();
- Log.d(TAG, prefix1 + p.mSegment + ":"
- + (obj == null ? "null" : obj.getClass().getSimpleName()));
- if (p.mChildren != null) {
- ArrayList<String> childrenKeys = p.mChildren.keys();
- int i = 0, n = childrenKeys.size();
- for (String key : childrenKeys) {
- Path child = p.mChildren.get(key);
- if (child == null) {
- ++i;
- continue;
- }
- Log.d(TAG, prefix2 + "|");
- if (++i < n) {
- dumpAll(child, prefix2 + "+-- ", prefix2 + "| ");
- } else {
- dumpAll(child, prefix2 + "+-- ", prefix2 + " ");
- }
- }
- }
- }
- }
-}
diff --git a/src/com/android/gallery3d/data/PathMatcher.java b/src/com/android/gallery3d/data/PathMatcher.java
deleted file mode 100644
index 9c6b840d5..000000000
--- a/src/com/android/gallery3d/data/PathMatcher.java
+++ /dev/null
@@ -1,102 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-
-public class PathMatcher {
- public static final int NOT_FOUND = -1;
-
- private ArrayList<String> mVariables = new ArrayList<String>();
- private Node mRoot = new Node();
-
- public PathMatcher() {
- mRoot = new Node();
- }
-
- public void add(String pattern, int kind) {
- String[] segments = Path.split(pattern);
- Node current = mRoot;
- for (int i = 0; i < segments.length; i++) {
- current = current.addChild(segments[i]);
- }
- current.setKind(kind);
- }
-
- public int match(Path path) {
- String[] segments = path.split();
- mVariables.clear();
- Node current = mRoot;
- for (int i = 0; i < segments.length; i++) {
- Node next = current.getChild(segments[i]);
- if (next == null) {
- next = current.getChild("*");
- if (next != null) {
- mVariables.add(segments[i]);
- } else {
- return NOT_FOUND;
- }
- }
- current = next;
- }
- return current.getKind();
- }
-
- public String getVar(int index) {
- return mVariables.get(index);
- }
-
- public int getIntVar(int index) {
- return Integer.parseInt(mVariables.get(index));
- }
-
- public long getLongVar(int index) {
- return Long.parseLong(mVariables.get(index));
- }
-
- private static class Node {
- private HashMap<String, Node> mMap;
- private int mKind = NOT_FOUND;
-
- Node addChild(String segment) {
- if (mMap == null) {
- mMap = new HashMap<String, Node>();
- } else {
- Node node = mMap.get(segment);
- if (node != null) return node;
- }
-
- Node n = new Node();
- mMap.put(segment, n);
- return n;
- }
-
- Node getChild(String segment) {
- if (mMap == null) return null;
- return mMap.get(segment);
- }
-
- void setKind(int kind) {
- mKind = kind;
- }
-
- int getKind() {
- return mKind;
- }
- }
-}
diff --git a/src/com/android/gallery3d/data/SecureAlbum.java b/src/com/android/gallery3d/data/SecureAlbum.java
deleted file mode 100644
index 204f848f8..000000000
--- a/src/com/android/gallery3d/data/SecureAlbum.java
+++ /dev/null
@@ -1,206 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.Context;
-import android.database.Cursor;
-import android.net.Uri;
-import android.provider.MediaStore.Images;
-import android.provider.MediaStore.MediaColumns;
-import android.provider.MediaStore.Video;
-
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.app.StitchingChangeListener;
-import com.android.gallery3d.util.MediaSetUtils;
-
-import java.util.ArrayList;
-
-// This class lists all media items added by the client.
-public class SecureAlbum extends MediaSet implements StitchingChangeListener {
- @SuppressWarnings("unused")
- private static final String TAG = "SecureAlbum";
- private static final String[] PROJECTION = {MediaColumns._ID};
- private int mMinImageId = Integer.MAX_VALUE; // the smallest id of images
- private int mMaxImageId = Integer.MIN_VALUE; // the biggest id in images
- private int mMinVideoId = Integer.MAX_VALUE; // the smallest id of videos
- private int mMaxVideoId = Integer.MIN_VALUE; // the biggest id of videos
- // All the media items added by the client.
- private ArrayList<Path> mAllItems = new ArrayList<Path>();
- // The types of items in mAllItems. True is video and false is image.
- private ArrayList<Boolean> mAllItemTypes = new ArrayList<Boolean>();
- private ArrayList<Path> mExistingItems = new ArrayList<Path>();
- private Context mContext;
- private DataManager mDataManager;
- private static final Uri[] mWatchUris =
- {Images.Media.EXTERNAL_CONTENT_URI, Video.Media.EXTERNAL_CONTENT_URI};
- private final ChangeNotifier mNotifier;
- // A placeholder image in the end of secure album. When it is tapped, it
- // will take the user to the lock screen.
- private MediaItem mUnlockItem;
- private boolean mShowUnlockItem;
-
- public SecureAlbum(Path path, GalleryApp application, MediaItem unlock) {
- super(path, nextVersionNumber());
- mContext = application.getAndroidContext();
- mDataManager = application.getDataManager();
- mNotifier = new ChangeNotifier(this, mWatchUris, application);
- mUnlockItem = unlock;
- mShowUnlockItem = (!isCameraBucketEmpty(Images.Media.EXTERNAL_CONTENT_URI)
- || !isCameraBucketEmpty(Video.Media.EXTERNAL_CONTENT_URI));
- }
-
- public void addMediaItem(boolean isVideo, int id) {
- Path pathBase;
- if (isVideo) {
- pathBase = LocalVideo.ITEM_PATH;
- mMinVideoId = Math.min(mMinVideoId, id);
- mMaxVideoId = Math.max(mMaxVideoId, id);
- } else {
- pathBase = LocalImage.ITEM_PATH;
- mMinImageId = Math.min(mMinImageId, id);
- mMaxImageId = Math.max(mMaxImageId, id);
- }
- Path path = pathBase.getChild(id);
- if (!mAllItems.contains(path)) {
- mAllItems.add(path);
- mAllItemTypes.add(isVideo);
- mNotifier.fakeChange();
- }
- }
-
- // The sequence is stitching items, local media items, and unlock image.
- @Override
- public ArrayList<MediaItem> getMediaItem(int start, int count) {
- int existingCount = mExistingItems.size();
- if (start >= existingCount + 1) {
- return new ArrayList<MediaItem>();
- }
-
- // Add paths of requested stitching items.
- int end = Math.min(start + count, existingCount);
- ArrayList<Path> subset = new ArrayList<Path>(mExistingItems.subList(start, end));
-
- // Convert paths to media items.
- final MediaItem[] buf = new MediaItem[end - start];
- ItemConsumer consumer = new ItemConsumer() {
- @Override
- public void consume(int index, MediaItem item) {
- buf[index] = item;
- }
- };
- mDataManager.mapMediaItems(subset, consumer, 0);
- ArrayList<MediaItem> result = new ArrayList<MediaItem>(end - start);
- for (int i = 0; i < buf.length; i++) {
- result.add(buf[i]);
- }
- if (mShowUnlockItem) result.add(mUnlockItem);
- return result;
- }
-
- @Override
- public int getMediaItemCount() {
- return (mExistingItems.size() + (mShowUnlockItem ? 1 : 0));
- }
-
- @Override
- public String getName() {
- return "secure";
- }
-
- @Override
- public long reload() {
- if (mNotifier.isDirty()) {
- mDataVersion = nextVersionNumber();
- updateExistingItems();
- }
- return mDataVersion;
- }
-
- private ArrayList<Integer> queryExistingIds(Uri uri, int minId, int maxId) {
- ArrayList<Integer> ids = new ArrayList<Integer>();
- if (minId == Integer.MAX_VALUE || maxId == Integer.MIN_VALUE) return ids;
-
- String[] selectionArgs = {String.valueOf(minId), String.valueOf(maxId)};
- Cursor cursor = mContext.getContentResolver().query(uri, PROJECTION,
- "_id BETWEEN ? AND ?", selectionArgs, null);
- if (cursor == null) return ids;
- try {
- while (cursor.moveToNext()) {
- ids.add(cursor.getInt(0));
- }
- } finally {
- cursor.close();
- }
- return ids;
- }
-
- private boolean isCameraBucketEmpty(Uri baseUri) {
- Uri uri = baseUri.buildUpon()
- .appendQueryParameter("limit", "1").build();
- String[] selection = {String.valueOf(MediaSetUtils.CAMERA_BUCKET_ID)};
- Cursor cursor = mContext.getContentResolver().query(uri, PROJECTION,
- "bucket_id = ?", selection, null);
- if (cursor == null) return true;
- try {
- return (cursor.getCount() == 0);
- } finally {
- cursor.close();
- }
- }
-
- private void updateExistingItems() {
- if (mAllItems.size() == 0) return;
-
- // Query existing ids.
- ArrayList<Integer> imageIds = queryExistingIds(
- Images.Media.EXTERNAL_CONTENT_URI, mMinImageId, mMaxImageId);
- ArrayList<Integer> videoIds = queryExistingIds(
- Video.Media.EXTERNAL_CONTENT_URI, mMinVideoId, mMaxVideoId);
-
- // Construct the existing items list.
- mExistingItems.clear();
- for (int i = mAllItems.size() - 1; i >= 0; i--) {
- Path path = mAllItems.get(i);
- boolean isVideo = mAllItemTypes.get(i);
- int id = Integer.parseInt(path.getSuffix());
- if (isVideo) {
- if (videoIds.contains(id)) mExistingItems.add(path);
- } else {
- if (imageIds.contains(id)) mExistingItems.add(path);
- }
- }
- }
-
- @Override
- public boolean isLeafAlbum() {
- return true;
- }
-
- @Override
- public void onStitchingQueued(Uri uri) {
- int id = Integer.parseInt(uri.getLastPathSegment());
- addMediaItem(false, id);
- }
-
- @Override
- public void onStitchingResult(Uri uri) {
- }
-
- @Override
- public void onStitchingProgress(Uri uri, final int progress) {
- }
-}
diff --git a/src/com/android/gallery3d/data/SecureSource.java b/src/com/android/gallery3d/data/SecureSource.java
deleted file mode 100644
index 6bc8cc295..000000000
--- a/src/com/android/gallery3d/data/SecureSource.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.app.GalleryApp;
-
-public class SecureSource extends MediaSource {
- private GalleryApp mApplication;
- private static PathMatcher mMatcher = new PathMatcher();
- private static final int SECURE_ALBUM = 0;
- private static final int SECURE_UNLOCK = 1;
-
- static {
- mMatcher.add("/secure/all/*", SECURE_ALBUM);
- mMatcher.add("/secure/unlock", SECURE_UNLOCK);
- }
-
- public SecureSource(GalleryApp context) {
- super("secure");
- mApplication = context;
- }
-
- public static boolean isSecurePath(String path) {
- return (SECURE_ALBUM == mMatcher.match(Path.fromString(path)));
- }
-
- @Override
- public MediaObject createMediaObject(Path path) {
- switch (mMatcher.match(path)) {
- case SECURE_ALBUM: {
- DataManager dataManager = mApplication.getDataManager();
- MediaItem unlock = (MediaItem) dataManager.getMediaObject(
- "/secure/unlock");
- return new SecureAlbum(path, mApplication, unlock);
- }
- case SECURE_UNLOCK:
- return new UnlockImage(path, mApplication);
- default:
- throw new RuntimeException("bad path: " + path);
- }
- }
-}
diff --git a/src/com/android/gallery3d/data/SingleItemAlbum.java b/src/com/android/gallery3d/data/SingleItemAlbum.java
deleted file mode 100644
index a0093e0c3..000000000
--- a/src/com/android/gallery3d/data/SingleItemAlbum.java
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import java.util.ArrayList;
-
-public class SingleItemAlbum extends MediaSet {
- @SuppressWarnings("unused")
- private static final String TAG = "SingleItemAlbum";
- private final MediaItem mItem;
- private final String mName;
-
- public SingleItemAlbum(Path path, MediaItem item) {
- super(path, nextVersionNumber());
- mItem = item;
- mName = "SingleItemAlbum("+mItem.getClass().getSimpleName()+")";
- }
-
- @Override
- public int getMediaItemCount() {
- return 1;
- }
-
- @Override
- public ArrayList<MediaItem> getMediaItem(int start, int count) {
- ArrayList<MediaItem> result = new ArrayList<MediaItem>();
-
- // If [start, start+count) contains the index 0, return the item.
- if (start <= 0 && start + count > 0) {
- result.add(mItem);
- }
-
- return result;
- }
-
- public MediaItem getItem() {
- return mItem;
- }
-
- @Override
- public boolean isLeafAlbum() {
- return true;
- }
-
- @Override
- public String getName() {
- return mName;
- }
-
- @Override
- public long reload() {
- return mDataVersion;
- }
-}
diff --git a/src/com/android/gallery3d/data/SizeClustering.java b/src/com/android/gallery3d/data/SizeClustering.java
deleted file mode 100644
index b809c841b..000000000
--- a/src/com/android/gallery3d/data/SizeClustering.java
+++ /dev/null
@@ -1,141 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.Context;
-import android.content.res.Resources;
-
-import com.android.gallery3d.R;
-
-import java.util.ArrayList;
-
-public class SizeClustering extends Clustering {
- @SuppressWarnings("unused")
- private static final String TAG = "SizeClustering";
-
- private Context mContext;
- private ArrayList<Path>[] mClusters;
- private String[] mNames;
- private long mMinSizes[];
-
- private static final long MEGA_BYTES = 1024L*1024;
- private static final long GIGA_BYTES = 1024L*1024*1024;
-
- private static final long[] SIZE_LEVELS = {
- 0,
- 1 * MEGA_BYTES,
- 10 * MEGA_BYTES,
- 100 * MEGA_BYTES,
- 1 * GIGA_BYTES,
- 2 * GIGA_BYTES,
- 4 * GIGA_BYTES,
- };
-
- public SizeClustering(Context context) {
- mContext = context;
- }
-
- @SuppressWarnings("unchecked")
- @Override
- public void run(MediaSet baseSet) {
- @SuppressWarnings("unchecked")
- final ArrayList<Path>[] group = new ArrayList[SIZE_LEVELS.length];
- baseSet.enumerateTotalMediaItems(new MediaSet.ItemConsumer() {
- @Override
- public void consume(int index, MediaItem item) {
- // Find the cluster this item belongs to.
- long size = item.getSize();
- int i;
- for (i = 0; i < SIZE_LEVELS.length - 1; i++) {
- if (size < SIZE_LEVELS[i + 1]) {
- break;
- }
- }
-
- ArrayList<Path> list = group[i];
- if (list == null) {
- list = new ArrayList<Path>();
- group[i] = list;
- }
- list.add(item.getPath());
- }
- });
-
- int count = 0;
- for (int i = 0; i < group.length; i++) {
- if (group[i] != null) {
- count++;
- }
- }
-
- mClusters = new ArrayList[count];
- mNames = new String[count];
- mMinSizes = new long[count];
-
- Resources res = mContext.getResources();
- int k = 0;
- // Go through group in the reverse order, so the group with the largest
- // size will show first.
- for (int i = group.length - 1; i >= 0; i--) {
- if (group[i] == null) continue;
-
- mClusters[k] = group[i];
- if (i == 0) {
- mNames[k] = String.format(
- res.getString(R.string.size_below), getSizeString(i + 1));
- } else if (i == group.length - 1) {
- mNames[k] = String.format(
- res.getString(R.string.size_above), getSizeString(i));
- } else {
- String minSize = getSizeString(i);
- String maxSize = getSizeString(i + 1);
- mNames[k] = String.format(
- res.getString(R.string.size_between), minSize, maxSize);
- }
- mMinSizes[k] = SIZE_LEVELS[i];
- k++;
- }
- }
-
- private String getSizeString(int index) {
- long bytes = SIZE_LEVELS[index];
- if (bytes >= GIGA_BYTES) {
- return (bytes / GIGA_BYTES) + "GB";
- } else {
- return (bytes / MEGA_BYTES) + "MB";
- }
- }
-
- @Override
- public int getNumberOfClusters() {
- return mClusters.length;
- }
-
- @Override
- public ArrayList<Path> getCluster(int index) {
- return mClusters[index];
- }
-
- @Override
- public String getClusterName(int index) {
- return mNames[index];
- }
-
- public long getMinSize(int index) {
- return mMinSizes[index];
- }
-}
diff --git a/src/com/android/gallery3d/data/SnailAlbum.java b/src/com/android/gallery3d/data/SnailAlbum.java
deleted file mode 100644
index 7bce7a695..000000000
--- a/src/com/android/gallery3d/data/SnailAlbum.java
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import java.util.concurrent.atomic.AtomicBoolean;
-
-// This is a simple MediaSet which contains only one MediaItem -- a SnailItem.
-public class SnailAlbum extends SingleItemAlbum {
- @SuppressWarnings("unused")
- private static final String TAG = "SnailAlbum";
- private AtomicBoolean mDirty = new AtomicBoolean(false);
-
- public SnailAlbum(Path path, SnailItem item) {
- super(path, item);
- }
-
- @Override
- public long reload() {
- if (mDirty.compareAndSet(true, false)) {
- ((SnailItem) getItem()).updateVersion();
- mDataVersion = nextVersionNumber();
- }
- return mDataVersion;
- }
-
- public void notifyChange() {
- mDirty.set(true);
- notifyContentChanged();
- }
-}
diff --git a/src/com/android/gallery3d/data/SnailItem.java b/src/com/android/gallery3d/data/SnailItem.java
deleted file mode 100644
index 3586d2cab..000000000
--- a/src/com/android/gallery3d/data/SnailItem.java
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.graphics.Bitmap;
-import android.graphics.BitmapRegionDecoder;
-
-import com.android.gallery3d.ui.ScreenNail;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-// SnailItem is a MediaItem which can provide a ScreenNail. This is
-// used so we can show an foreign component (like an
-// android.view.View) instead of a Bitmap.
-public class SnailItem extends MediaItem {
- @SuppressWarnings("unused")
- private static final String TAG = "SnailItem";
- private ScreenNail mScreenNail;
-
- public SnailItem(Path path) {
- super(path, nextVersionNumber());
- }
-
- @Override
- public Job<Bitmap> requestImage(int type) {
- // nothing to return
- return new Job<Bitmap>() {
- @Override
- public Bitmap run(JobContext jc) {
- return null;
- }
- };
- }
-
- @Override
- public Job<BitmapRegionDecoder> requestLargeImage() {
- // nothing to return
- return new Job<BitmapRegionDecoder>() {
- @Override
- public BitmapRegionDecoder run(JobContext jc) {
- return null;
- }
- };
- }
-
- // We do not provide requestImage or requestLargeImage, instead we
- // provide a ScreenNail.
- @Override
- public ScreenNail getScreenNail() {
- return mScreenNail;
- }
-
- @Override
- public String getMimeType() {
- return "";
- }
-
- // Returns width and height of the media item.
- // Returns 0, 0 if the information is not available.
- @Override
- public int getWidth() {
- return 0;
- }
-
- @Override
- public int getHeight() {
- return 0;
- }
-
- //////////////////////////////////////////////////////////////////////////
- // Extra methods for SnailItem
- //////////////////////////////////////////////////////////////////////////
-
- public void setScreenNail(ScreenNail screenNail) {
- mScreenNail = screenNail;
- }
-
- public void updateVersion() {
- mDataVersion = nextVersionNumber();
- }
-}
diff --git a/src/com/android/gallery3d/data/SnailSource.java b/src/com/android/gallery3d/data/SnailSource.java
deleted file mode 100644
index 5c690ccdb..000000000
--- a/src/com/android/gallery3d/data/SnailSource.java
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.app.GalleryApp;
-
-public class SnailSource extends MediaSource {
- @SuppressWarnings("unused")
- private static final String TAG = "SnailSource";
- private static final int SNAIL_ALBUM = 0;
- private static final int SNAIL_ITEM = 1;
-
- private GalleryApp mApplication;
- private PathMatcher mMatcher;
- private static int sNextId;
-
- public SnailSource(GalleryApp application) {
- super("snail");
- mApplication = application;
- mMatcher = new PathMatcher();
- mMatcher.add("/snail/set/*", SNAIL_ALBUM);
- mMatcher.add("/snail/item/*", SNAIL_ITEM);
- }
-
- // The only path we accept is "/snail/set/id" and "/snail/item/id"
- @Override
- public MediaObject createMediaObject(Path path) {
- DataManager dataManager = mApplication.getDataManager();
- switch (mMatcher.match(path)) {
- case SNAIL_ALBUM:
- String itemPath = "/snail/item/" + mMatcher.getVar(0);
- SnailItem item =
- (SnailItem) dataManager.getMediaObject(itemPath);
- return new SnailAlbum(path, item);
- case SNAIL_ITEM: {
- int id = mMatcher.getIntVar(0);
- return new SnailItem(path);
- }
- }
- return null;
- }
-
- // Registers a new SnailAlbum containing a SnailItem and returns the id of
- // them. You can obtain the Path of the SnailAlbum and SnailItem associated
- // with the id by getSetPath and getItemPath().
- public static synchronized int newId() {
- return sNextId++;
- }
-
- public static Path getSetPath(int id) {
- return Path.fromString("/snail/set").getChild(id);
- }
-
- public static Path getItemPath(int id) {
- return Path.fromString("/snail/item").getChild(id);
- }
-}
diff --git a/src/com/android/gallery3d/data/TagClustering.java b/src/com/android/gallery3d/data/TagClustering.java
deleted file mode 100644
index 407ca84c4..000000000
--- a/src/com/android/gallery3d/data/TagClustering.java
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.Context;
-
-import com.android.gallery3d.R;
-
-import java.util.ArrayList;
-import java.util.Map;
-import java.util.TreeMap;
-
-public class TagClustering extends Clustering {
- @SuppressWarnings("unused")
- private static final String TAG = "TagClustering";
-
- private ArrayList<ArrayList<Path>> mClusters;
- private String[] mNames;
- private String mUntaggedString;
-
- public TagClustering(Context context) {
- mUntaggedString = context.getResources().getString(R.string.untagged);
- }
-
- @Override
- public void run(MediaSet baseSet) {
- final TreeMap<String, ArrayList<Path>> map =
- new TreeMap<String, ArrayList<Path>>();
- final ArrayList<Path> untagged = new ArrayList<Path>();
-
- baseSet.enumerateTotalMediaItems(new MediaSet.ItemConsumer() {
- @Override
- public void consume(int index, MediaItem item) {
- Path path = item.getPath();
-
- String[] tags = item.getTags();
- if (tags == null || tags.length == 0) {
- untagged.add(path);
- return;
- }
- for (int j = 0; j < tags.length; j++) {
- String key = tags[j];
- ArrayList<Path> list = map.get(key);
- if (list == null) {
- list = new ArrayList<Path>();
- map.put(key, list);
- }
- list.add(path);
- }
- }
- });
-
- int m = map.size();
- mClusters = new ArrayList<ArrayList<Path>>();
- mNames = new String[m + ((untagged.size() > 0) ? 1 : 0)];
- int i = 0;
- for (Map.Entry<String, ArrayList<Path>> entry : map.entrySet()) {
- mNames[i++] = entry.getKey();
- mClusters.add(entry.getValue());
- }
- if (untagged.size() > 0) {
- mNames[i++] = mUntaggedString;
- mClusters.add(untagged);
- }
- }
-
- @Override
- public int getNumberOfClusters() {
- return mClusters.size();
- }
-
- @Override
- public ArrayList<Path> getCluster(int index) {
- return mClusters.get(index);
- }
-
- @Override
- public String getClusterName(int index) {
- return mNames[index];
- }
-}
diff --git a/src/com/android/gallery3d/data/TimeClustering.java b/src/com/android/gallery3d/data/TimeClustering.java
deleted file mode 100644
index 35cbab1ee..000000000
--- a/src/com/android/gallery3d/data/TimeClustering.java
+++ /dev/null
@@ -1,439 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.Context;
-import android.text.format.DateFormat;
-import android.text.format.DateUtils;
-
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.util.GalleryUtils;
-
-import java.util.ArrayList;
-import java.util.Collections;
-import java.util.Comparator;
-
-public class TimeClustering extends Clustering {
- @SuppressWarnings("unused")
- private static final String TAG = "TimeClustering";
-
- // If 2 items are greater than 25 miles apart, they will be in different
- // clusters.
- private static final int GEOGRAPHIC_DISTANCE_CUTOFF_IN_MILES = 20;
-
- // Do not want to split based on anything under 1 min.
- private static final long MIN_CLUSTER_SPLIT_TIME_IN_MS = 60000L;
-
- // Disregard a cluster split time of anything over 2 hours.
- private static final long MAX_CLUSTER_SPLIT_TIME_IN_MS = 7200000L;
-
- // Try and get around 9 clusters (best-effort for the common case).
- private static final int NUM_CLUSTERS_TARGETED = 9;
-
- // Try and merge 2 clusters if they are both smaller than min cluster size.
- // The min cluster size can range from 8 to 15.
- private static final int MIN_MIN_CLUSTER_SIZE = 8;
- private static final int MAX_MIN_CLUSTER_SIZE = 15;
-
- // Try and split a cluster if it is bigger than max cluster size.
- // The max cluster size can range from 20 to 50.
- private static final int MIN_MAX_CLUSTER_SIZE = 20;
- private static final int MAX_MAX_CLUSTER_SIZE = 50;
-
- // Initially put 2 items in the same cluster as long as they are within
- // 3 cluster frequencies of each other.
- private static int CLUSTER_SPLIT_MULTIPLIER = 3;
-
- // The minimum change factor in the time between items to consider a
- // partition.
- // Example: (Item 3 - Item 2) / (Item 2 - Item 1).
- private static final int MIN_PARTITION_CHANGE_FACTOR = 2;
-
- // Make the cluster split time of a large cluster half that of a regular
- // cluster.
- private static final int PARTITION_CLUSTER_SPLIT_TIME_FACTOR = 2;
-
- private Context mContext;
- private ArrayList<Cluster> mClusters;
- private String[] mNames;
- private Cluster mCurrCluster;
-
- private long mClusterSplitTime =
- (MIN_CLUSTER_SPLIT_TIME_IN_MS + MAX_CLUSTER_SPLIT_TIME_IN_MS) / 2;
- private long mLargeClusterSplitTime =
- mClusterSplitTime / PARTITION_CLUSTER_SPLIT_TIME_FACTOR;
- private int mMinClusterSize = (MIN_MIN_CLUSTER_SIZE + MAX_MIN_CLUSTER_SIZE) / 2;
- private int mMaxClusterSize = (MIN_MAX_CLUSTER_SIZE + MAX_MAX_CLUSTER_SIZE) / 2;
-
-
- private static final Comparator<SmallItem> sDateComparator =
- new DateComparator();
-
- private static class DateComparator implements Comparator<SmallItem> {
- @Override
- public int compare(SmallItem item1, SmallItem item2) {
- return -Utils.compare(item1.dateInMs, item2.dateInMs);
- }
- }
-
- public TimeClustering(Context context) {
- mContext = context;
- mClusters = new ArrayList<Cluster>();
- mCurrCluster = new Cluster();
- }
-
- @Override
- public void run(MediaSet baseSet) {
- final int total = baseSet.getTotalMediaItemCount();
- final SmallItem[] buf = new SmallItem[total];
- final double[] latLng = new double[2];
-
- baseSet.enumerateTotalMediaItems(new MediaSet.ItemConsumer() {
- @Override
- public void consume(int index, MediaItem item) {
- if (index < 0 || index >= total) return;
- SmallItem s = new SmallItem();
- s.path = item.getPath();
- s.dateInMs = item.getDateInMs();
- item.getLatLong(latLng);
- s.lat = latLng[0];
- s.lng = latLng[1];
- buf[index] = s;
- }
- });
-
- ArrayList<SmallItem> items = new ArrayList<SmallItem>(total);
- for (int i = 0; i < total; i++) {
- if (buf[i] != null) {
- items.add(buf[i]);
- }
- }
-
- Collections.sort(items, sDateComparator);
-
- int n = items.size();
- long minTime = 0;
- long maxTime = 0;
- for (int i = 0; i < n; i++) {
- long t = items.get(i).dateInMs;
- if (t == 0) continue;
- if (minTime == 0) {
- minTime = maxTime = t;
- } else {
- minTime = Math.min(minTime, t);
- maxTime = Math.max(maxTime, t);
- }
- }
-
- setTimeRange(maxTime - minTime, n);
-
- for (int i = 0; i < n; i++) {
- compute(items.get(i));
- }
-
- compute(null);
-
- int m = mClusters.size();
- mNames = new String[m];
- for (int i = 0; i < m; i++) {
- mNames[i] = mClusters.get(i).generateCaption(mContext);
- }
- }
-
- @Override
- public int getNumberOfClusters() {
- return mClusters.size();
- }
-
- @Override
- public ArrayList<Path> getCluster(int index) {
- ArrayList<SmallItem> items = mClusters.get(index).getItems();
- ArrayList<Path> result = new ArrayList<Path>(items.size());
- for (int i = 0, n = items.size(); i < n; i++) {
- result.add(items.get(i).path);
- }
- return result;
- }
-
- @Override
- public String getClusterName(int index) {
- return mNames[index];
- }
-
- private void setTimeRange(long timeRange, int numItems) {
- if (numItems != 0) {
- int meanItemsPerCluster = numItems / NUM_CLUSTERS_TARGETED;
- // Heuristic to get min and max cluster size - half and double the
- // desired items per cluster.
- mMinClusterSize = meanItemsPerCluster / 2;
- mMaxClusterSize = meanItemsPerCluster * 2;
- mClusterSplitTime = timeRange / numItems * CLUSTER_SPLIT_MULTIPLIER;
- }
- mClusterSplitTime = Utils.clamp(mClusterSplitTime, MIN_CLUSTER_SPLIT_TIME_IN_MS, MAX_CLUSTER_SPLIT_TIME_IN_MS);
- mLargeClusterSplitTime = mClusterSplitTime / PARTITION_CLUSTER_SPLIT_TIME_FACTOR;
- mMinClusterSize = Utils.clamp(mMinClusterSize, MIN_MIN_CLUSTER_SIZE, MAX_MIN_CLUSTER_SIZE);
- mMaxClusterSize = Utils.clamp(mMaxClusterSize, MIN_MAX_CLUSTER_SIZE, MAX_MAX_CLUSTER_SIZE);
- }
-
- private void compute(SmallItem currentItem) {
- if (currentItem != null) {
- int numClusters = mClusters.size();
- int numCurrClusterItems = mCurrCluster.size();
- boolean geographicallySeparateItem = false;
- boolean itemAddedToCurrentCluster = false;
-
- // Determine if this item should go in the current cluster or be the
- // start of a new cluster.
- if (numCurrClusterItems == 0) {
- mCurrCluster.addItem(currentItem);
- } else {
- SmallItem prevItem = mCurrCluster.getLastItem();
- if (isGeographicallySeparated(prevItem, currentItem)) {
- mClusters.add(mCurrCluster);
- geographicallySeparateItem = true;
- } else if (numCurrClusterItems > mMaxClusterSize) {
- splitAndAddCurrentCluster();
- } else if (timeDistance(prevItem, currentItem) < mClusterSplitTime) {
- mCurrCluster.addItem(currentItem);
- itemAddedToCurrentCluster = true;
- } else if (numClusters > 0 && numCurrClusterItems < mMinClusterSize
- && !mCurrCluster.mGeographicallySeparatedFromPrevCluster) {
- mergeAndAddCurrentCluster();
- } else {
- mClusters.add(mCurrCluster);
- }
-
- // Creating a new cluster and adding the current item to it.
- if (!itemAddedToCurrentCluster) {
- mCurrCluster = new Cluster();
- if (geographicallySeparateItem) {
- mCurrCluster.mGeographicallySeparatedFromPrevCluster = true;
- }
- mCurrCluster.addItem(currentItem);
- }
- }
- } else {
- if (mCurrCluster.size() > 0) {
- int numClusters = mClusters.size();
- int numCurrClusterItems = mCurrCluster.size();
-
- // The last cluster may potentially be too big or too small.
- if (numCurrClusterItems > mMaxClusterSize) {
- splitAndAddCurrentCluster();
- } else if (numClusters > 0 && numCurrClusterItems < mMinClusterSize
- && !mCurrCluster.mGeographicallySeparatedFromPrevCluster) {
- mergeAndAddCurrentCluster();
- } else {
- mClusters.add(mCurrCluster);
- }
- mCurrCluster = new Cluster();
- }
- }
- }
-
- private void splitAndAddCurrentCluster() {
- ArrayList<SmallItem> currClusterItems = mCurrCluster.getItems();
- int numCurrClusterItems = mCurrCluster.size();
- int secondPartitionStartIndex = getPartitionIndexForCurrentCluster();
- if (secondPartitionStartIndex != -1) {
- Cluster partitionedCluster = new Cluster();
- for (int j = 0; j < secondPartitionStartIndex; j++) {
- partitionedCluster.addItem(currClusterItems.get(j));
- }
- mClusters.add(partitionedCluster);
- partitionedCluster = new Cluster();
- for (int j = secondPartitionStartIndex; j < numCurrClusterItems; j++) {
- partitionedCluster.addItem(currClusterItems.get(j));
- }
- mClusters.add(partitionedCluster);
- } else {
- mClusters.add(mCurrCluster);
- }
- }
-
- private int getPartitionIndexForCurrentCluster() {
- int partitionIndex = -1;
- float largestChange = MIN_PARTITION_CHANGE_FACTOR;
- ArrayList<SmallItem> currClusterItems = mCurrCluster.getItems();
- int numCurrClusterItems = mCurrCluster.size();
- int minClusterSize = mMinClusterSize;
-
- // Could be slightly more efficient here but this code seems cleaner.
- if (numCurrClusterItems > minClusterSize + 1) {
- for (int i = minClusterSize; i < numCurrClusterItems - minClusterSize; i++) {
- SmallItem prevItem = currClusterItems.get(i - 1);
- SmallItem currItem = currClusterItems.get(i);
- SmallItem nextItem = currClusterItems.get(i + 1);
-
- long timeNext = nextItem.dateInMs;
- long timeCurr = currItem.dateInMs;
- long timePrev = prevItem.dateInMs;
-
- if (timeNext == 0 || timeCurr == 0 || timePrev == 0) continue;
-
- long diff1 = Math.abs(timeNext - timeCurr);
- long diff2 = Math.abs(timeCurr - timePrev);
-
- float change = Math.max(diff1 / (diff2 + 0.01f), diff2 / (diff1 + 0.01f));
- if (change > largestChange) {
- if (timeDistance(currItem, prevItem) > mLargeClusterSplitTime) {
- partitionIndex = i;
- largestChange = change;
- } else if (timeDistance(nextItem, currItem) > mLargeClusterSplitTime) {
- partitionIndex = i + 1;
- largestChange = change;
- }
- }
- }
- }
- return partitionIndex;
- }
-
- private void mergeAndAddCurrentCluster() {
- int numClusters = mClusters.size();
- Cluster prevCluster = mClusters.get(numClusters - 1);
- ArrayList<SmallItem> currClusterItems = mCurrCluster.getItems();
- int numCurrClusterItems = mCurrCluster.size();
- if (prevCluster.size() < mMinClusterSize) {
- for (int i = 0; i < numCurrClusterItems; i++) {
- prevCluster.addItem(currClusterItems.get(i));
- }
- mClusters.set(numClusters - 1, prevCluster);
- } else {
- mClusters.add(mCurrCluster);
- }
- }
-
- // Returns true if a, b are sufficiently geographically separated.
- private static boolean isGeographicallySeparated(SmallItem itemA, SmallItem itemB) {
- if (!GalleryUtils.isValidLocation(itemA.lat, itemA.lng)
- || !GalleryUtils.isValidLocation(itemB.lat, itemB.lng)) {
- return false;
- }
-
- double distance = GalleryUtils.fastDistanceMeters(
- Math.toRadians(itemA.lat),
- Math.toRadians(itemA.lng),
- Math.toRadians(itemB.lat),
- Math.toRadians(itemB.lng));
- return (GalleryUtils.toMile(distance) > GEOGRAPHIC_DISTANCE_CUTOFF_IN_MILES);
- }
-
- // Returns the time interval between the two items in milliseconds.
- private static long timeDistance(SmallItem a, SmallItem b) {
- return Math.abs(a.dateInMs - b.dateInMs);
- }
-}
-
-class SmallItem {
- Path path;
- long dateInMs;
- double lat, lng;
-}
-
-class Cluster {
- @SuppressWarnings("unused")
- private static final String TAG = "Cluster";
- private static final String MMDDYY_FORMAT = "MMddyy";
-
- // This is for TimeClustering only.
- public boolean mGeographicallySeparatedFromPrevCluster = false;
-
- private ArrayList<SmallItem> mItems = new ArrayList<SmallItem>();
-
- public Cluster() {
- }
-
- public void addItem(SmallItem item) {
- mItems.add(item);
- }
-
- public int size() {
- return mItems.size();
- }
-
- public SmallItem getLastItem() {
- int n = mItems.size();
- return (n == 0) ? null : mItems.get(n - 1);
- }
-
- public ArrayList<SmallItem> getItems() {
- return mItems;
- }
-
- public String generateCaption(Context context) {
- int n = mItems.size();
- long minTimestamp = 0;
- long maxTimestamp = 0;
-
- for (int i = 0; i < n; i++) {
- long t = mItems.get(i).dateInMs;
- if (t == 0) continue;
- if (minTimestamp == 0) {
- minTimestamp = maxTimestamp = t;
- } else {
- minTimestamp = Math.min(minTimestamp, t);
- maxTimestamp = Math.max(maxTimestamp, t);
- }
- }
- if (minTimestamp == 0) return "";
-
- String caption;
- String minDay = DateFormat.format(MMDDYY_FORMAT, minTimestamp)
- .toString();
- String maxDay = DateFormat.format(MMDDYY_FORMAT, maxTimestamp)
- .toString();
-
- if (minDay.substring(4).equals(maxDay.substring(4))) {
- // The items are from the same year - show at least as
- // much granularity as abbrev_all allows.
- caption = DateUtils.formatDateRange(context, minTimestamp,
- maxTimestamp, DateUtils.FORMAT_ABBREV_ALL);
-
- // Get a more granular date range string if the min and
- // max timestamp are on the same day and from the
- // current year.
- if (minDay.equals(maxDay)) {
- int flags = DateUtils.FORMAT_ABBREV_MONTH | DateUtils.FORMAT_SHOW_DATE;
- // Contains the year only if the date does not
- // correspond to the current year.
- String dateRangeWithOptionalYear = DateUtils.formatDateTime(
- context, minTimestamp, flags);
- String dateRangeWithYear = DateUtils.formatDateTime(
- context, minTimestamp, flags | DateUtils.FORMAT_SHOW_YEAR);
- if (!dateRangeWithOptionalYear.equals(dateRangeWithYear)) {
- // This means both dates are from the same year
- // - show the time.
- // Not enough room to display the time range.
- // Pick the mid-point.
- long midTimestamp = (minTimestamp + maxTimestamp) / 2;
- caption = DateUtils.formatDateRange(context, midTimestamp,
- midTimestamp, DateUtils.FORMAT_SHOW_TIME | flags);
- }
- }
- } else {
- // The items are not from the same year - only show
- // month and year.
- int flags = DateUtils.FORMAT_NO_MONTH_DAY
- | DateUtils.FORMAT_ABBREV_MONTH | DateUtils.FORMAT_SHOW_DATE;
- caption = DateUtils.formatDateRange(context, minTimestamp,
- maxTimestamp, flags);
- }
-
- return caption;
- }
-}
diff --git a/src/com/android/gallery3d/data/UnlockImage.java b/src/com/android/gallery3d/data/UnlockImage.java
deleted file mode 100644
index ed3b485c4..000000000
--- a/src/com/android/gallery3d/data/UnlockImage.java
+++ /dev/null
@@ -1,34 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.GalleryApp;
-
-public class UnlockImage extends ActionImage {
- @SuppressWarnings("unused")
- private static final String TAG = "UnlockImage";
-
- public UnlockImage(Path path, GalleryApp application) {
- super(path, application, R.drawable.placeholder_locked);
- }
-
- @Override
- public int getSupportedOperations() {
- return super.getSupportedOperations() | SUPPORT_UNLOCK;
- }
-}
diff --git a/src/com/android/gallery3d/data/UriImage.java b/src/com/android/gallery3d/data/UriImage.java
deleted file mode 100644
index e8875b572..000000000
--- a/src/com/android/gallery3d/data/UriImage.java
+++ /dev/null
@@ -1,298 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.ContentResolver;
-import android.graphics.Bitmap;
-import android.graphics.Bitmap.Config;
-import android.graphics.BitmapFactory.Options;
-import android.graphics.BitmapRegionDecoder;
-import android.net.Uri;
-import android.os.ParcelFileDescriptor;
-
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.app.PanoramaMetadataSupport;
-import com.android.gallery3d.common.BitmapUtils;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.util.ThreadPool.CancelListener;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.io.FileInputStream;
-import java.io.FileNotFoundException;
-import java.io.InputStream;
-import java.net.URI;
-import java.net.URL;
-
-public class UriImage extends MediaItem {
- private static final String TAG = "UriImage";
-
- private static final int STATE_INIT = 0;
- private static final int STATE_DOWNLOADING = 1;
- private static final int STATE_DOWNLOADED = 2;
- private static final int STATE_ERROR = -1;
-
- private final Uri mUri;
- private final String mContentType;
-
- private DownloadCache.Entry mCacheEntry;
- private ParcelFileDescriptor mFileDescriptor;
- private int mState = STATE_INIT;
- private int mWidth;
- private int mHeight;
- private int mRotation;
- private PanoramaMetadataSupport mPanoramaMetadata = new PanoramaMetadataSupport(this);
-
- private GalleryApp mApplication;
-
- public UriImage(GalleryApp application, Path path, Uri uri, String contentType) {
- super(path, nextVersionNumber());
- mUri = uri;
- mApplication = Utils.checkNotNull(application);
- mContentType = contentType;
- }
-
- @Override
- public Job<Bitmap> requestImage(int type) {
- return new BitmapJob(type);
- }
-
- @Override
- public Job<BitmapRegionDecoder> requestLargeImage() {
- return new RegionDecoderJob();
- }
-
- private void openFileOrDownloadTempFile(JobContext jc) {
- int state = openOrDownloadInner(jc);
- synchronized (this) {
- mState = state;
- if (mState != STATE_DOWNLOADED) {
- if (mFileDescriptor != null) {
- Utils.closeSilently(mFileDescriptor);
- mFileDescriptor = null;
- }
- }
- notifyAll();
- }
- }
-
- private int openOrDownloadInner(JobContext jc) {
- String scheme = mUri.getScheme();
- if (ContentResolver.SCHEME_CONTENT.equals(scheme)
- || ContentResolver.SCHEME_ANDROID_RESOURCE.equals(scheme)
- || ContentResolver.SCHEME_FILE.equals(scheme)) {
- try {
- if (MIME_TYPE_JPEG.equalsIgnoreCase(mContentType)) {
- InputStream is = mApplication.getContentResolver()
- .openInputStream(mUri);
- mRotation = Exif.getOrientation(is);
- Utils.closeSilently(is);
- }
- mFileDescriptor = mApplication.getContentResolver()
- .openFileDescriptor(mUri, "r");
- if (jc.isCancelled()) return STATE_INIT;
- return STATE_DOWNLOADED;
- } catch (FileNotFoundException e) {
- Log.w(TAG, "fail to open: " + mUri, e);
- return STATE_ERROR;
- }
- } else {
- try {
- URL url = new URI(mUri.toString()).toURL();
- mCacheEntry = mApplication.getDownloadCache().download(jc, url);
- if (jc.isCancelled()) return STATE_INIT;
- if (mCacheEntry == null) {
- Log.w(TAG, "download failed " + url);
- return STATE_ERROR;
- }
- if (MIME_TYPE_JPEG.equalsIgnoreCase(mContentType)) {
- InputStream is = new FileInputStream(mCacheEntry.cacheFile);
- mRotation = Exif.getOrientation(is);
- Utils.closeSilently(is);
- }
- mFileDescriptor = ParcelFileDescriptor.open(
- mCacheEntry.cacheFile, ParcelFileDescriptor.MODE_READ_ONLY);
- return STATE_DOWNLOADED;
- } catch (Throwable t) {
- Log.w(TAG, "download error", t);
- return STATE_ERROR;
- }
- }
- }
-
- private boolean prepareInputFile(JobContext jc) {
- jc.setCancelListener(new CancelListener() {
- @Override
- public void onCancel() {
- synchronized (this) {
- notifyAll();
- }
- }
- });
-
- while (true) {
- synchronized (this) {
- if (jc.isCancelled()) return false;
- if (mState == STATE_INIT) {
- mState = STATE_DOWNLOADING;
- // Then leave the synchronized block and continue.
- } else if (mState == STATE_ERROR) {
- return false;
- } else if (mState == STATE_DOWNLOADED) {
- return true;
- } else /* if (mState == STATE_DOWNLOADING) */ {
- try {
- wait();
- } catch (InterruptedException ex) {
- // ignored.
- }
- continue;
- }
- }
- // This is only reached for STATE_INIT->STATE_DOWNLOADING
- openFileOrDownloadTempFile(jc);
- }
- }
-
- private class RegionDecoderJob implements Job<BitmapRegionDecoder> {
- @Override
- public BitmapRegionDecoder run(JobContext jc) {
- if (!prepareInputFile(jc)) return null;
- BitmapRegionDecoder decoder = DecodeUtils.createBitmapRegionDecoder(
- jc, mFileDescriptor.getFileDescriptor(), false);
- mWidth = decoder.getWidth();
- mHeight = decoder.getHeight();
- return decoder;
- }
- }
-
- private class BitmapJob implements Job<Bitmap> {
- private int mType;
-
- protected BitmapJob(int type) {
- mType = type;
- }
-
- @Override
- public Bitmap run(JobContext jc) {
- if (!prepareInputFile(jc)) return null;
- int targetSize = MediaItem.getTargetSize(mType);
- Options options = new Options();
- options.inPreferredConfig = Config.ARGB_8888;
- Bitmap bitmap = DecodeUtils.decodeThumbnail(jc,
- mFileDescriptor.getFileDescriptor(), options, targetSize, mType);
-
- if (jc.isCancelled() || bitmap == null) {
- return null;
- }
-
- if (mType == MediaItem.TYPE_MICROTHUMBNAIL) {
- bitmap = BitmapUtils.resizeAndCropCenter(bitmap, targetSize, true);
- } else {
- bitmap = BitmapUtils.resizeDownBySideLength(bitmap, targetSize, true);
- }
- return bitmap;
- }
- }
-
- @Override
- public int getSupportedOperations() {
- int supported = SUPPORT_EDIT | SUPPORT_SETAS;
- if (isSharable()) supported |= SUPPORT_SHARE;
- if (BitmapUtils.isSupportedByRegionDecoder(mContentType)) {
- supported |= SUPPORT_FULL_IMAGE;
- }
- return supported;
- }
-
- @Override
- public void getPanoramaSupport(PanoramaSupportCallback callback) {
- mPanoramaMetadata.getPanoramaSupport(mApplication, callback);
- }
-
- @Override
- public void clearCachedPanoramaSupport() {
- mPanoramaMetadata.clearCachedValues();
- }
-
- private boolean isSharable() {
- // We cannot grant read permission to the receiver since we put
- // the data URI in EXTRA_STREAM instead of the data part of an intent
- // And there are issues in MediaUploader and Bluetooth file sender to
- // share a general image data. So, we only share for local file.
- return ContentResolver.SCHEME_FILE.equals(mUri.getScheme());
- }
-
- @Override
- public int getMediaType() {
- return MEDIA_TYPE_IMAGE;
- }
-
- @Override
- public Uri getContentUri() {
- return mUri;
- }
-
- @Override
- public MediaDetails getDetails() {
- MediaDetails details = super.getDetails();
- if (mWidth != 0 && mHeight != 0) {
- details.addDetail(MediaDetails.INDEX_WIDTH, mWidth);
- details.addDetail(MediaDetails.INDEX_HEIGHT, mHeight);
- }
- if (mContentType != null) {
- details.addDetail(MediaDetails.INDEX_MIMETYPE, mContentType);
- }
- if (ContentResolver.SCHEME_FILE.equals(mUri.getScheme())) {
- String filePath = mUri.getPath();
- details.addDetail(MediaDetails.INDEX_PATH, filePath);
- MediaDetails.extractExifInfo(details, filePath);
- }
- return details;
- }
-
- @Override
- public String getMimeType() {
- return mContentType;
- }
-
- @Override
- protected void finalize() throws Throwable {
- try {
- if (mFileDescriptor != null) {
- Utils.closeSilently(mFileDescriptor);
- }
- } finally {
- super.finalize();
- }
- }
-
- @Override
- public int getWidth() {
- return 0;
- }
-
- @Override
- public int getHeight() {
- return 0;
- }
-
- @Override
- public int getRotation() {
- return mRotation;
- }
-}
diff --git a/src/com/android/gallery3d/data/UriSource.java b/src/com/android/gallery3d/data/UriSource.java
deleted file mode 100644
index f66bacd7b..000000000
--- a/src/com/android/gallery3d/data/UriSource.java
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.data;
-
-import android.content.ContentResolver;
-import android.net.Uri;
-import android.webkit.MimeTypeMap;
-
-import com.android.gallery3d.app.GalleryApp;
-
-import java.io.UnsupportedEncodingException;
-import java.net.URLDecoder;
-import java.net.URLEncoder;
-
-class UriSource extends MediaSource {
- @SuppressWarnings("unused")
- private static final String TAG = "UriSource";
- private static final String IMAGE_TYPE_PREFIX = "image/";
- private static final String IMAGE_TYPE_ANY = "image/*";
- private static final String CHARSET_UTF_8 = "utf-8";
-
- private GalleryApp mApplication;
-
- public UriSource(GalleryApp context) {
- super("uri");
- mApplication = context;
- }
-
- @Override
- public MediaObject createMediaObject(Path path) {
- String segment[] = path.split();
- if (segment.length != 3) {
- throw new RuntimeException("bad path: " + path);
- }
- try {
- String uri = URLDecoder.decode(segment[1], CHARSET_UTF_8);
- String type = URLDecoder.decode(segment[2], CHARSET_UTF_8);
- return new UriImage(mApplication, path, Uri.parse(uri), type);
- } catch (UnsupportedEncodingException e) {
- throw new AssertionError(e);
- }
- }
-
- private String getMimeType(Uri uri) {
- if (ContentResolver.SCHEME_FILE.equals(uri.getScheme())) {
- String extension =
- MimeTypeMap.getFileExtensionFromUrl(uri.toString());
- String type = MimeTypeMap.getSingleton()
- .getMimeTypeFromExtension(extension.toLowerCase());
- if (type != null) return type;
- }
- // Assume the type is image if the type cannot be resolved
- // This could happen for "http" URI.
- String type = mApplication.getContentResolver().getType(uri);
- if (type == null) type = "image/*";
- return type;
- }
-
- @Override
- public Path findPathByUri(Uri uri, String type) {
- String mimeType = getMimeType(uri);
-
- // Try to find a most specific type but it has to be started with "image/"
- if ((type == null) || (IMAGE_TYPE_ANY.equals(type)
- && mimeType.startsWith(IMAGE_TYPE_PREFIX))) {
- type = mimeType;
- }
-
- if (type.startsWith(IMAGE_TYPE_PREFIX)) {
- try {
- return Path.fromString("/uri/"
- + URLEncoder.encode(uri.toString(), CHARSET_UTF_8)
- + "/" +URLEncoder.encode(type, CHARSET_UTF_8));
- } catch (UnsupportedEncodingException e) {
- throw new AssertionError(e);
- }
- }
- // We have no clues that it is an image
- return null;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/CenteredLinearLayout.java b/src/com/android/gallery3d/filtershow/CenteredLinearLayout.java
deleted file mode 100644
index bc9342d6f..000000000
--- a/src/com/android/gallery3d/filtershow/CenteredLinearLayout.java
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.content.res.TypedArray;
-import android.util.AttributeSet;
-import android.util.TypedValue;
-import android.widget.LinearLayout;
-
-import com.android.gallery3d.R;
-
-public class CenteredLinearLayout extends LinearLayout {
- private final int mMaxWidth;
-
- public CenteredLinearLayout(Context context, AttributeSet attrs) {
- super(context, attrs);
- TypedArray a = getContext().obtainStyledAttributes(attrs, R.styleable.CenteredLinearLayout);
- mMaxWidth = a.getDimensionPixelSize(R.styleable.CenteredLinearLayout_max_width, 0);
- }
-
- @Override
- protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
- int parentWidth = MeasureSpec.getSize(widthMeasureSpec);
- int parentHeight = MeasureSpec.getSize(heightMeasureSpec);
- Resources r = getContext().getResources();
- float value = TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, parentWidth,
- r.getDisplayMetrics());
- if (mMaxWidth > 0 && parentWidth > mMaxWidth) {
- int measureMode = MeasureSpec.getMode(widthMeasureSpec);
- widthMeasureSpec = MeasureSpec.makeMeasureSpec(mMaxWidth, measureMode);
- }
- super.onMeasure(widthMeasureSpec, heightMeasureSpec);
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/EditorPlaceHolder.java b/src/com/android/gallery3d/filtershow/EditorPlaceHolder.java
deleted file mode 100644
index 95abce114..000000000
--- a/src/com/android/gallery3d/filtershow/EditorPlaceHolder.java
+++ /dev/null
@@ -1,82 +0,0 @@
-package com.android.gallery3d.filtershow;
-
-import android.view.View;
-import android.view.ViewParent;
-import android.widget.FrameLayout;
-
-import com.android.gallery3d.filtershow.cache.ImageLoader;
-import com.android.gallery3d.filtershow.editors.Editor;
-import com.android.gallery3d.filtershow.imageshow.ImageShow;
-
-import java.util.HashMap;
-import java.util.Vector;
-
-public class EditorPlaceHolder {
- private static final String LOGTAG = "EditorPlaceHolder";
-
- private FilterShowActivity mActivity = null;
- private FrameLayout mContainer = null;
- private HashMap<Integer, Editor> mEditors = new HashMap<Integer, Editor>();
- private Vector<ImageShow> mOldViews = new Vector<ImageShow>();
-
- public EditorPlaceHolder(FilterShowActivity activity) {
- mActivity = activity;
- }
-
- public void setContainer(FrameLayout container) {
- mContainer = container;
- }
-
- public void addEditor(Editor c) {
- mEditors.put(c.getID(), c);
- }
-
- public boolean contains(int type) {
- if (mEditors.get(type) != null) {
- return true;
- }
- return false;
- }
-
- public Editor showEditor(int type) {
- Editor editor = mEditors.get(type);
- if (editor == null) {
- return null;
- }
-
- editor.createEditor(mActivity, mContainer);
- editor.getImageShow().bindAsImageLoadListener();
- mContainer.setVisibility(View.VISIBLE);
- mContainer.removeAllViews();
- View eview = editor.getTopLevelView();
- ViewParent parent = eview.getParent();
-
- if (parent != null && parent instanceof FrameLayout) {
- ((FrameLayout) parent).removeAllViews();
- }
-
- mContainer.addView(eview);
- hideOldViews();
- editor.setVisibility(View.VISIBLE);
- return editor;
- }
-
- public void setOldViews(Vector<ImageShow> views) {
- mOldViews = views;
- }
-
- public void hide() {
- mContainer.setVisibility(View.GONE);
- }
-
- public void hideOldViews() {
- for (View view : mOldViews) {
- view.setVisibility(View.GONE);
- }
- }
-
- public Editor getEditor(int editorId) {
- return mEditors.get(editorId);
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/FilterShowActivity.java b/src/com/android/gallery3d/filtershow/FilterShowActivity.java
deleted file mode 100644
index 4700fccfe..000000000
--- a/src/com/android/gallery3d/filtershow/FilterShowActivity.java
+++ /dev/null
@@ -1,1121 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow;
-
-import android.app.ActionBar;
-import android.app.AlertDialog;
-import android.app.ProgressDialog;
-import android.content.ComponentName;
-import android.content.ContentValues;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.content.Intent;
-import android.content.ServiceConnection;
-import android.content.pm.ActivityInfo;
-import android.content.res.Configuration;
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.Rect;
-import android.graphics.drawable.Drawable;
-import android.net.Uri;
-import android.os.AsyncTask;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.IBinder;
-import android.support.v4.app.DialogFragment;
-import android.support.v4.app.Fragment;
-import android.support.v4.app.FragmentActivity;
-import android.support.v4.app.FragmentTransaction;
-import android.util.DisplayMetrics;
-import android.util.Log;
-import android.util.TypedValue;
-import android.view.Menu;
-import android.view.MenuItem;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.view.ViewPropertyAnimator;
-import android.view.WindowManager;
-import android.widget.AdapterView;
-import android.widget.AdapterView.OnItemClickListener;
-import android.widget.FrameLayout;
-import android.widget.ShareActionProvider;
-import android.widget.ShareActionProvider.OnShareTargetSelectedListener;
-import android.widget.Toast;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.PhotoPage;
-import com.android.gallery3d.data.LocalAlbum;
-import com.android.gallery3d.filtershow.cache.ImageLoader;
-import com.android.gallery3d.filtershow.category.Action;
-import com.android.gallery3d.filtershow.category.CategoryAdapter;
-import com.android.gallery3d.filtershow.category.MainPanel;
-import com.android.gallery3d.filtershow.data.UserPresetsManager;
-import com.android.gallery3d.filtershow.editors.BasicEditor;
-import com.android.gallery3d.filtershow.editors.Editor;
-import com.android.gallery3d.filtershow.editors.EditorChanSat;
-import com.android.gallery3d.filtershow.editors.EditorCrop;
-import com.android.gallery3d.filtershow.editors.EditorDraw;
-import com.android.gallery3d.filtershow.editors.EditorGrad;
-import com.android.gallery3d.filtershow.editors.EditorManager;
-import com.android.gallery3d.filtershow.editors.EditorMirror;
-import com.android.gallery3d.filtershow.editors.EditorPanel;
-import com.android.gallery3d.filtershow.editors.EditorRedEye;
-import com.android.gallery3d.filtershow.editors.EditorRotate;
-import com.android.gallery3d.filtershow.editors.EditorStraighten;
-import com.android.gallery3d.filtershow.editors.EditorTinyPlanet;
-import com.android.gallery3d.filtershow.editors.ImageOnlyEditor;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterUserPresetRepresentation;
-import com.android.gallery3d.filtershow.filters.FiltersManager;
-import com.android.gallery3d.filtershow.filters.ImageFilter;
-import com.android.gallery3d.filtershow.history.HistoryItem;
-import com.android.gallery3d.filtershow.history.HistoryManager;
-import com.android.gallery3d.filtershow.imageshow.ImageShow;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.imageshow.Spline;
-import com.android.gallery3d.filtershow.pipeline.CachingPipeline;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-import com.android.gallery3d.filtershow.pipeline.ProcessingService;
-import com.android.gallery3d.filtershow.presets.PresetManagementDialog;
-import com.android.gallery3d.filtershow.presets.UserPresetsAdapter;
-import com.android.gallery3d.filtershow.provider.SharedImageProvider;
-import com.android.gallery3d.filtershow.state.StateAdapter;
-import com.android.gallery3d.filtershow.tools.SaveImage;
-import com.android.gallery3d.filtershow.tools.XmpPresets;
-import com.android.gallery3d.filtershow.tools.XmpPresets.XMresults;
-import com.android.gallery3d.filtershow.ui.ExportDialog;
-import com.android.gallery3d.filtershow.ui.FramedTextButton;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.UsageStatistics;
-import com.android.photos.data.GalleryBitmapPool;
-
-import java.io.File;
-import java.lang.ref.WeakReference;
-import java.util.ArrayList;
-import java.util.Vector;
-
-public class FilterShowActivity extends FragmentActivity implements OnItemClickListener,
- OnShareTargetSelectedListener {
-
- private String mAction = "";
- MasterImage mMasterImage = null;
-
- private static final long LIMIT_SUPPORTS_HIGHRES = 134217728; // 128Mb
-
- public static final String TINY_PLANET_ACTION = "com.android.camera.action.TINY_PLANET";
- public static final String LAUNCH_FULLSCREEN = "launch-fullscreen";
- private ImageShow mImageShow = null;
-
- private View mSaveButton = null;
-
- private EditorPlaceHolder mEditorPlaceHolder = new EditorPlaceHolder(this);
-
- private static final int SELECT_PICTURE = 1;
- private static final String LOGTAG = "FilterShowActivity";
-
- private boolean mShowingTinyPlanet = false;
- private boolean mShowingImageStatePanel = false;
-
- private final Vector<ImageShow> mImageViews = new Vector<ImageShow>();
-
- private ShareActionProvider mShareActionProvider;
- private File mSharedOutputFile = null;
-
- private boolean mSharingImage = false;
-
- private WeakReference<ProgressDialog> mSavingProgressDialog;
-
- private LoadBitmapTask mLoadBitmapTask;
-
- private Uri mOriginalImageUri = null;
- private ImagePreset mOriginalPreset = null;
-
- private Uri mSelectedImageUri = null;
-
- private UserPresetsManager mUserPresetsManager = null;
- private UserPresetsAdapter mUserPresetsAdapter = null;
- private CategoryAdapter mCategoryLooksAdapter = null;
- private CategoryAdapter mCategoryBordersAdapter = null;
- private CategoryAdapter mCategoryGeometryAdapter = null;
- private CategoryAdapter mCategoryFiltersAdapter = null;
- private int mCurrentPanel = MainPanel.LOOKS;
-
- private ProcessingService mBoundService;
- private boolean mIsBound = false;
-
- public ProcessingService getProcessingService() {
- return mBoundService;
- }
-
- public boolean isSimpleEditAction() {
- return !PhotoPage.ACTION_NEXTGEN_EDIT.equalsIgnoreCase(mAction);
- }
-
- private ServiceConnection mConnection = new ServiceConnection() {
- public void onServiceConnected(ComponentName className, IBinder service) {
- /*
- * This is called when the connection with the service has been
- * established, giving us the service object we can use to
- * interact with the service. Because we have bound to a explicit
- * service that we know is running in our own process, we can
- * cast its IBinder to a concrete class and directly access it.
- */
- mBoundService = ((ProcessingService.LocalBinder)service).getService();
- mBoundService.setFiltershowActivity(FilterShowActivity.this);
- mBoundService.onStart();
- }
-
- public void onServiceDisconnected(ComponentName className) {
- /*
- * This is called when the connection with the service has been
- * unexpectedly disconnected -- that is, its process crashed.
- * Because it is running in our same process, we should never
- * see this happen.
- */
- mBoundService = null;
- }
- };
-
- void doBindService() {
- /*
- * Establish a connection with the service. We use an explicit
- * class name because we want a specific service implementation that
- * we know will be running in our own process (and thus won't be
- * supporting component replacement by other applications).
- */
- bindService(new Intent(FilterShowActivity.this, ProcessingService.class),
- mConnection, Context.BIND_AUTO_CREATE);
- mIsBound = true;
- }
-
- void doUnbindService() {
- if (mIsBound) {
- // Detach our existing connection.
- unbindService(mConnection);
- mIsBound = false;
- }
- }
-
- private void setupPipeline() {
- doBindService();
- ImageFilter.setActivityForMemoryToasts(this);
- mUserPresetsManager = new UserPresetsManager(this);
- mUserPresetsAdapter = new UserPresetsAdapter(this);
- mCategoryLooksAdapter = new CategoryAdapter(this);
- }
-
- public void updateUIAfterServiceStarted() {
- fillCategories();
- loadMainPanel();
- setDefaultPreset();
- extractXMPData();
- processIntent();
- }
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
-
- boolean onlyUsePortrait = getResources().getBoolean(R.bool.only_use_portrait);
- if (onlyUsePortrait) {
- setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
- }
- MasterImage.setMaster(mMasterImage);
-
- clearGalleryBitmapPool();
- setupPipeline();
-
- setupMasterImage();
- setDefaultValues();
- fillEditors();
-
- loadXML();
- UsageStatistics.onContentViewChanged(UsageStatistics.COMPONENT_EDITOR, "Main");
- UsageStatistics.onEvent(UsageStatistics.COMPONENT_EDITOR,
- UsageStatistics.CATEGORY_LIFECYCLE, UsageStatistics.LIFECYCLE_START);
- }
-
- public boolean isShowingImageStatePanel() {
- return mShowingImageStatePanel;
- }
-
- public void loadMainPanel() {
- if (findViewById(R.id.main_panel_container) == null) {
- return;
- }
- MainPanel panel = new MainPanel();
- FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
- transaction.replace(R.id.main_panel_container, panel, MainPanel.FRAGMENT_TAG);
- transaction.commit();
- }
-
- public void loadEditorPanel(FilterRepresentation representation,
- final Editor currentEditor) {
- if (representation.getEditorId() == ImageOnlyEditor.ID) {
- currentEditor.reflectCurrentFilter();
- return;
- }
- final int currentId = currentEditor.getID();
- Runnable showEditor = new Runnable() {
- @Override
- public void run() {
- EditorPanel panel = new EditorPanel();
- panel.setEditor(currentId);
- FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
- transaction.remove(getSupportFragmentManager().findFragmentByTag(MainPanel.FRAGMENT_TAG));
- transaction.replace(R.id.main_panel_container, panel, MainPanel.FRAGMENT_TAG);
- transaction.commit();
- }
- };
- Fragment main = getSupportFragmentManager().findFragmentByTag(MainPanel.FRAGMENT_TAG);
- boolean doAnimation = false;
- if (mShowingImageStatePanel
- && getResources().getConfiguration().orientation == Configuration.ORIENTATION_PORTRAIT) {
- doAnimation = true;
- }
- if (doAnimation && main != null && main instanceof MainPanel) {
- MainPanel mainPanel = (MainPanel) main;
- View container = mainPanel.getView().findViewById(R.id.category_panel_container);
- View bottom = mainPanel.getView().findViewById(R.id.bottom_panel);
- int panelHeight = container.getHeight() + bottom.getHeight();
- ViewPropertyAnimator anim = mainPanel.getView().animate();
- anim.translationY(panelHeight).start();
- final Handler handler = new Handler();
- handler.postDelayed(showEditor, anim.getDuration());
- } else {
- showEditor.run();
- }
- }
-
- private void loadXML() {
- setContentView(R.layout.filtershow_activity);
-
- ActionBar actionBar = getActionBar();
- actionBar.setDisplayOptions(ActionBar.DISPLAY_SHOW_CUSTOM);
- actionBar.setCustomView(R.layout.filtershow_actionbar);
-
- mSaveButton = actionBar.getCustomView();
- mSaveButton.setOnClickListener(new OnClickListener() {
- @Override
- public void onClick(View view) {
- saveImage();
- }
- });
-
- mImageShow = (ImageShow) findViewById(R.id.imageShow);
- mImageViews.add(mImageShow);
-
- setupEditors();
-
- mEditorPlaceHolder.hide();
- mImageShow.bindAsImageLoadListener();
-
- setupStatePanel();
- }
-
- public void fillCategories() {
- fillLooks();
- loadUserPresets();
- fillBorders();
- fillTools();
- fillEffects();
- }
-
- public void setupStatePanel() {
- MasterImage.getImage().setHistoryManager(mMasterImage.getHistory());
- }
-
- private void fillEffects() {
- FiltersManager filtersManager = FiltersManager.getManager();
- ArrayList<FilterRepresentation> filtersRepresentations = filtersManager.getEffects();
- mCategoryFiltersAdapter = new CategoryAdapter(this);
- for (FilterRepresentation representation : filtersRepresentations) {
- if (representation.getTextId() != 0) {
- representation.setName(getString(representation.getTextId()));
- }
- mCategoryFiltersAdapter.add(new Action(this, representation));
- }
- }
-
- private void fillTools() {
- FiltersManager filtersManager = FiltersManager.getManager();
- ArrayList<FilterRepresentation> filtersRepresentations = filtersManager.getTools();
- mCategoryGeometryAdapter = new CategoryAdapter(this);
- for (FilterRepresentation representation : filtersRepresentations) {
- mCategoryGeometryAdapter.add(new Action(this, representation));
- }
- }
-
- private void processIntent() {
- Intent intent = getIntent();
- if (intent.getBooleanExtra(LAUNCH_FULLSCREEN, false)) {
- getWindow().addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
- }
-
- mAction = intent.getAction();
- mSelectedImageUri = intent.getData();
- Uri loadUri = mSelectedImageUri;
- if (mOriginalImageUri != null) {
- loadUri = mOriginalImageUri;
- }
- if (loadUri != null) {
- startLoadBitmap(loadUri);
- } else {
- pickImage();
- }
- }
-
- private void setupEditors() {
- mEditorPlaceHolder.setContainer((FrameLayout) findViewById(R.id.editorContainer));
- EditorManager.addEditors(mEditorPlaceHolder);
- mEditorPlaceHolder.setOldViews(mImageViews);
- }
-
- private void fillEditors() {
- mEditorPlaceHolder.addEditor(new EditorChanSat());
- mEditorPlaceHolder.addEditor(new EditorGrad());
- mEditorPlaceHolder.addEditor(new EditorDraw());
- mEditorPlaceHolder.addEditor(new BasicEditor());
- mEditorPlaceHolder.addEditor(new ImageOnlyEditor());
- mEditorPlaceHolder.addEditor(new EditorTinyPlanet());
- mEditorPlaceHolder.addEditor(new EditorRedEye());
- mEditorPlaceHolder.addEditor(new EditorCrop());
- mEditorPlaceHolder.addEditor(new EditorMirror());
- mEditorPlaceHolder.addEditor(new EditorRotate());
- mEditorPlaceHolder.addEditor(new EditorStraighten());
- }
-
- private void setDefaultValues() {
- Resources res = getResources();
-
- // TODO: get those values from XML.
- FramedTextButton.setTextSize((int) getPixelsFromDip(14));
- FramedTextButton.setTrianglePadding((int) getPixelsFromDip(4));
- FramedTextButton.setTriangleSize((int) getPixelsFromDip(10));
-
- Drawable curveHandle = res.getDrawable(R.drawable.camera_crop);
- int curveHandleSize = (int) res.getDimension(R.dimen.crop_indicator_size);
- Spline.setCurveHandle(curveHandle, curveHandleSize);
- Spline.setCurveWidth((int) getPixelsFromDip(3));
- }
-
- private void startLoadBitmap(Uri uri) {
- final View loading = findViewById(R.id.loading);
- final View imageShow = findViewById(R.id.imageShow);
- imageShow.setVisibility(View.INVISIBLE);
- loading.setVisibility(View.VISIBLE);
- mShowingTinyPlanet = false;
- mLoadBitmapTask = new LoadBitmapTask();
- mLoadBitmapTask.execute(uri);
- }
-
- private void fillBorders() {
- FiltersManager filtersManager = FiltersManager.getManager();
- ArrayList<FilterRepresentation> borders = filtersManager.getBorders();
-
- for (int i = 0; i < borders.size(); i++) {
- FilterRepresentation filter = borders.get(i);
- filter.setName(getString(R.string.borders));
- if (i == 0) {
- filter.setName(getString(R.string.none));
- }
- }
-
- mCategoryBordersAdapter = new CategoryAdapter(this);
- for (FilterRepresentation representation : borders) {
- if (representation.getTextId() != 0) {
- representation.setName(getString(representation.getTextId()));
- }
- mCategoryBordersAdapter.add(new Action(this, representation, Action.FULL_VIEW));
- }
- }
-
- public UserPresetsAdapter getUserPresetsAdapter() {
- return mUserPresetsAdapter;
- }
-
- public CategoryAdapter getCategoryLooksAdapter() {
- return mCategoryLooksAdapter;
- }
-
- public CategoryAdapter getCategoryBordersAdapter() {
- return mCategoryBordersAdapter;
- }
-
- public CategoryAdapter getCategoryGeometryAdapter() {
- return mCategoryGeometryAdapter;
- }
-
- public CategoryAdapter getCategoryFiltersAdapter() {
- return mCategoryFiltersAdapter;
- }
-
- public void removeFilterRepresentation(FilterRepresentation filterRepresentation) {
- if (filterRepresentation == null) {
- return;
- }
- ImagePreset oldPreset = MasterImage.getImage().getPreset();
- ImagePreset copy = new ImagePreset(oldPreset);
- copy.removeFilter(filterRepresentation);
- MasterImage.getImage().setPreset(copy, copy.getLastRepresentation(), true);
- if (MasterImage.getImage().getCurrentFilterRepresentation() == filterRepresentation) {
- FilterRepresentation lastRepresentation = copy.getLastRepresentation();
- MasterImage.getImage().setCurrentFilterRepresentation(lastRepresentation);
- }
- }
-
- public void useFilterRepresentation(FilterRepresentation filterRepresentation) {
- if (filterRepresentation == null) {
- return;
- }
- if (MasterImage.getImage().getCurrentFilterRepresentation() == filterRepresentation) {
- return;
- }
- ImagePreset oldPreset = MasterImage.getImage().getPreset();
- ImagePreset copy = new ImagePreset(oldPreset);
- FilterRepresentation representation = copy.getRepresentation(filterRepresentation);
- if (representation == null) {
- copy.addFilter(filterRepresentation);
- } else if (filterRepresentation.getFilterType() == FilterRepresentation.TYPE_GEOMETRY) {
- filterRepresentation = representation;
- } else {
- if (filterRepresentation.allowsSingleInstanceOnly()) {
- // Don't just update the filter representation. Centralize the
- // logic in the addFilter(), such that we can keep "None" as
- // null.
- copy.removeFilter(representation);
- copy.addFilter(filterRepresentation);
- }
- }
- MasterImage.getImage().setPreset(copy, filterRepresentation, true);
- MasterImage.getImage().setCurrentFilterRepresentation(filterRepresentation);
- }
-
- public void showRepresentation(FilterRepresentation representation) {
- if (representation == null) {
- return;
- }
-
- useFilterRepresentation(representation);
-
- // show representation
- Editor mCurrentEditor = mEditorPlaceHolder.showEditor(representation.getEditorId());
- loadEditorPanel(representation, mCurrentEditor);
- }
-
- public Editor getEditor(int editorID) {
- return mEditorPlaceHolder.getEditor(editorID);
- }
-
- public void setCurrentPanel(int currentPanel) {
- mCurrentPanel = currentPanel;
- }
-
- public int getCurrentPanel() {
- return mCurrentPanel;
- }
-
- public void updateCategories() {
- ImagePreset preset = mMasterImage.getPreset();
- mCategoryLooksAdapter.reflectImagePreset(preset);
- mCategoryBordersAdapter.reflectImagePreset(preset);
- }
-
- private class LoadHighresBitmapTask extends AsyncTask<Void, Void, Boolean> {
- @Override
- protected Boolean doInBackground(Void... params) {
- MasterImage master = MasterImage.getImage();
- Rect originalBounds = master.getOriginalBounds();
- if (master.supportsHighRes()) {
- int highresPreviewSize = master.getOriginalBitmapLarge().getWidth() * 2;
- if (highresPreviewSize > originalBounds.width()) {
- highresPreviewSize = originalBounds.width();
- }
- Rect bounds = new Rect();
- Bitmap originalHires = ImageLoader.loadOrientedConstrainedBitmap(master.getUri(),
- master.getActivity(), highresPreviewSize,
- master.getOrientation(), bounds);
- master.setOriginalBounds(bounds);
- master.setOriginalBitmapHighres(originalHires);
- mBoundService.setOriginalBitmapHighres(originalHires);
- master.warnListeners();
- }
- return true;
- }
-
- @Override
- protected void onPostExecute(Boolean result) {
- Bitmap highresBitmap = MasterImage.getImage().getOriginalBitmapHighres();
- if (highresBitmap != null) {
- float highResPreviewScale = (float) highresBitmap.getWidth()
- / (float) MasterImage.getImage().getOriginalBounds().width();
- mBoundService.setHighresPreviewScaleFactor(highResPreviewScale);
- }
- }
- }
-
- private class LoadBitmapTask extends AsyncTask<Uri, Boolean, Boolean> {
- int mBitmapSize;
-
- public LoadBitmapTask() {
- mBitmapSize = getScreenImageSize();
- }
-
- @Override
- protected Boolean doInBackground(Uri... params) {
- if (!MasterImage.getImage().loadBitmap(params[0], mBitmapSize)) {
- return false;
- }
- publishProgress(ImageLoader.queryLightCycle360(MasterImage.getImage().getActivity()));
- return true;
- }
-
- @Override
- protected void onProgressUpdate(Boolean... values) {
- super.onProgressUpdate(values);
- if (isCancelled()) {
- return;
- }
- if (values[0]) {
- mShowingTinyPlanet = true;
- }
- }
-
- @Override
- protected void onPostExecute(Boolean result) {
- MasterImage.setMaster(mMasterImage);
- if (isCancelled()) {
- return;
- }
-
- if (!result) {
- cannotLoadImage();
- }
-
- if (null == CachingPipeline.getRenderScriptContext()){
- Log.v(LOGTAG,"RenderScript context destroyed during load");
- return;
- }
- final View loading = findViewById(R.id.loading);
- loading.setVisibility(View.GONE);
- final View imageShow = findViewById(R.id.imageShow);
- imageShow.setVisibility(View.VISIBLE);
-
- Bitmap largeBitmap = MasterImage.getImage().getOriginalBitmapLarge();
- mBoundService.setOriginalBitmap(largeBitmap);
-
- float previewScale = (float) largeBitmap.getWidth()
- / (float) MasterImage.getImage().getOriginalBounds().width();
- mBoundService.setPreviewScaleFactor(previewScale);
- if (!mShowingTinyPlanet) {
- mCategoryFiltersAdapter.removeTinyPlanet();
- }
- mCategoryLooksAdapter.imageLoaded();
- mCategoryBordersAdapter.imageLoaded();
- mCategoryGeometryAdapter.imageLoaded();
- mCategoryFiltersAdapter.imageLoaded();
- mLoadBitmapTask = null;
-
- if (mOriginalPreset != null) {
- MasterImage.getImage().setLoadedPreset(mOriginalPreset);
- MasterImage.getImage().setPreset(mOriginalPreset,
- mOriginalPreset.getLastRepresentation(), true);
- mOriginalPreset = null;
- }
-
- if (mAction == TINY_PLANET_ACTION) {
- showRepresentation(mCategoryFiltersAdapter.getTinyPlanet());
- }
- LoadHighresBitmapTask highresLoad = new LoadHighresBitmapTask();
- highresLoad.execute();
- super.onPostExecute(result);
- }
-
- }
-
- private void clearGalleryBitmapPool() {
- (new AsyncTask<Void, Void, Void>() {
- @Override
- protected Void doInBackground(Void... params) {
- // Free memory held in Gallery's Bitmap pool. May be O(n) for n bitmaps.
- GalleryBitmapPool.getInstance().clear();
- return null;
- }
- }).execute();
- }
-
- @Override
- protected void onDestroy() {
- if (mLoadBitmapTask != null) {
- mLoadBitmapTask.cancel(false);
- }
- mUserPresetsManager.close();
- doUnbindService();
- super.onDestroy();
- }
-
- // TODO: find a more robust way of handling image size selection
- // for high screen densities.
- private int getScreenImageSize() {
- DisplayMetrics outMetrics = new DisplayMetrics();
- getWindowManager().getDefaultDisplay().getMetrics(outMetrics);
- return (int) Math.max(outMetrics.heightPixels, outMetrics.widthPixels);
- }
-
- private void showSavingProgress(String albumName) {
- ProgressDialog progress;
- if (mSavingProgressDialog != null) {
- progress = mSavingProgressDialog.get();
- if (progress != null) {
- progress.show();
- return;
- }
- }
- // TODO: Allow cancellation of the saving process
- String progressText;
- if (albumName == null) {
- progressText = getString(R.string.saving_image);
- } else {
- progressText = getString(R.string.filtershow_saving_image, albumName);
- }
- progress = ProgressDialog.show(this, "", progressText, true, false);
- mSavingProgressDialog = new WeakReference<ProgressDialog>(progress);
- }
-
- private void hideSavingProgress() {
- if (mSavingProgressDialog != null) {
- ProgressDialog progress = mSavingProgressDialog.get();
- if (progress != null)
- progress.dismiss();
- }
- }
-
- public void completeSaveImage(Uri saveUri) {
- if (mSharingImage && mSharedOutputFile != null) {
- // Image saved, we unblock the content provider
- Uri uri = Uri.withAppendedPath(SharedImageProvider.CONTENT_URI,
- Uri.encode(mSharedOutputFile.getAbsolutePath()));
- ContentValues values = new ContentValues();
- values.put(SharedImageProvider.PREPARE, false);
- getContentResolver().insert(uri, values);
- }
- setResult(RESULT_OK, new Intent().setData(saveUri));
- hideSavingProgress();
- finish();
- }
-
- @Override
- public boolean onShareTargetSelected(ShareActionProvider arg0, Intent arg1) {
- // First, let's tell the SharedImageProvider that it will need to wait
- // for the image
- Uri uri = Uri.withAppendedPath(SharedImageProvider.CONTENT_URI,
- Uri.encode(mSharedOutputFile.getAbsolutePath()));
- ContentValues values = new ContentValues();
- values.put(SharedImageProvider.PREPARE, true);
- getContentResolver().insert(uri, values);
- mSharingImage = true;
-
- // Process and save the image in the background.
- showSavingProgress(null);
- mImageShow.saveImage(this, mSharedOutputFile);
- return true;
- }
-
- private Intent getDefaultShareIntent() {
- Intent intent = new Intent(Intent.ACTION_SEND);
- intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_WHEN_TASK_RESET);
- intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
- intent.setType(SharedImageProvider.MIME_TYPE);
- mSharedOutputFile = SaveImage.getNewFile(this, MasterImage.getImage().getUri());
- Uri uri = Uri.withAppendedPath(SharedImageProvider.CONTENT_URI,
- Uri.encode(mSharedOutputFile.getAbsolutePath()));
- intent.putExtra(Intent.EXTRA_STREAM, uri);
- return intent;
- }
-
- @Override
- public boolean onCreateOptionsMenu(Menu menu) {
- getMenuInflater().inflate(R.menu.filtershow_activity_menu, menu);
- MenuItem showState = menu.findItem(R.id.showImageStateButton);
- if (mShowingImageStatePanel) {
- showState.setTitle(R.string.hide_imagestate_panel);
- } else {
- showState.setTitle(R.string.show_imagestate_panel);
- }
- mShareActionProvider = (ShareActionProvider) menu.findItem(R.id.menu_share)
- .getActionProvider();
- mShareActionProvider.setShareIntent(getDefaultShareIntent());
- mShareActionProvider.setOnShareTargetSelectedListener(this);
-
- MenuItem undoItem = menu.findItem(R.id.undoButton);
- MenuItem redoItem = menu.findItem(R.id.redoButton);
- MenuItem resetItem = menu.findItem(R.id.resetHistoryButton);
- mMasterImage.getHistory().setMenuItems(undoItem, redoItem, resetItem);
- return true;
- }
-
- @Override
- public void onPause() {
- super.onPause();
- if (mShareActionProvider != null) {
- mShareActionProvider.setOnShareTargetSelectedListener(null);
- }
- }
-
- @Override
- public void onResume() {
- super.onResume();
- if (mShareActionProvider != null) {
- mShareActionProvider.setOnShareTargetSelectedListener(this);
- }
- }
-
- @Override
- public boolean onOptionsItemSelected(MenuItem item) {
- switch (item.getItemId()) {
- case R.id.undoButton: {
- HistoryManager adapter = mMasterImage.getHistory();
- int position = adapter.undo();
- mMasterImage.onHistoryItemClick(position);
- backToMain();
- invalidateViews();
- UsageStatistics.onEvent(UsageStatistics.COMPONENT_EDITOR,
- UsageStatistics.CATEGORY_BUTTON_PRESS, "Undo");
- return true;
- }
- case R.id.redoButton: {
- HistoryManager adapter = mMasterImage.getHistory();
- int position = adapter.redo();
- mMasterImage.onHistoryItemClick(position);
- invalidateViews();
- UsageStatistics.onEvent(UsageStatistics.COMPONENT_EDITOR,
- UsageStatistics.CATEGORY_BUTTON_PRESS, "Redo");
- return true;
- }
- case R.id.resetHistoryButton: {
- resetHistory();
- UsageStatistics.onEvent(UsageStatistics.COMPONENT_EDITOR,
- UsageStatistics.CATEGORY_BUTTON_PRESS, "ResetHistory");
- return true;
- }
- case R.id.showImageStateButton: {
- toggleImageStatePanel();
- UsageStatistics.onEvent(UsageStatistics.COMPONENT_EDITOR,
- UsageStatistics.CATEGORY_BUTTON_PRESS,
- mShowingImageStatePanel ? "ShowPanel" : "HidePanel");
- return true;
- }
- case R.id.exportFlattenButton: {
- showExportOptionsDialog();
- return true;
- }
- case android.R.id.home: {
- saveImage();
- return true;
- }
- case R.id.manageUserPresets: {
- manageUserPresets();
- return true;
- }
- }
- return false;
- }
-
- private void manageUserPresets() {
- DialogFragment dialog = new PresetManagementDialog();
- dialog.show(getSupportFragmentManager(), "NoticeDialogFragment");
- }
-
- private void showExportOptionsDialog() {
- DialogFragment dialog = new ExportDialog();
- dialog.show(getSupportFragmentManager(), "ExportDialogFragment");
- }
-
- public void updateUserPresetsFromAdapter(UserPresetsAdapter adapter) {
- ArrayList<FilterUserPresetRepresentation> representations =
- adapter.getDeletedRepresentations();
- for (FilterUserPresetRepresentation representation : representations) {
- deletePreset(representation.getId());
- }
- ArrayList<FilterUserPresetRepresentation> changedRepresentations =
- adapter.getChangedRepresentations();
- for (FilterUserPresetRepresentation representation : changedRepresentations) {
- updatePreset(representation);
- }
- adapter.clearDeletedRepresentations();
- adapter.clearChangedRepresentations();
- loadUserPresets();
- }
-
- public void loadUserPresets() {
- mUserPresetsManager.load();
- }
-
- public void updateUserPresetsFromManager() {
- ArrayList<FilterUserPresetRepresentation> presets = mUserPresetsManager.getRepresentations();
- if (presets == null) {
- return;
- }
- if (mCategoryLooksAdapter != null) {
- fillLooks();
- }
- mUserPresetsAdapter.clear();
- for (int i = 0; i < presets.size(); i++) {
- FilterUserPresetRepresentation representation = presets.get(i);
- mCategoryLooksAdapter.add(
- new Action(this, representation, Action.FULL_VIEW));
- mUserPresetsAdapter.add(new Action(this, representation, Action.FULL_VIEW));
- }
- mCategoryLooksAdapter.notifyDataSetInvalidated();
-
- }
-
- public void saveCurrentImagePreset() {
- mUserPresetsManager.save(MasterImage.getImage().getPreset());
- }
-
- private void deletePreset(int id) {
- mUserPresetsManager.delete(id);
- }
-
- private void updatePreset(FilterUserPresetRepresentation representation) {
- mUserPresetsManager.update(representation);
- }
-
- public void enableSave(boolean enable) {
- if (mSaveButton != null) {
- mSaveButton.setEnabled(enable);
- }
- }
-
- private void fillLooks() {
- FiltersManager filtersManager = FiltersManager.getManager();
- ArrayList<FilterRepresentation> filtersRepresentations = filtersManager.getLooks();
-
- mCategoryLooksAdapter.clear();
- int verticalItemHeight = (int) getResources().getDimension(R.dimen.action_item_height);
- mCategoryLooksAdapter.setItemHeight(verticalItemHeight);
- for (FilterRepresentation representation : filtersRepresentations) {
- mCategoryLooksAdapter.add(new Action(this, representation, Action.FULL_VIEW));
- }
- }
-
- public void setDefaultPreset() {
- // Default preset (original)
- ImagePreset preset = new ImagePreset(); // empty
- mMasterImage.setPreset(preset, preset.getLastRepresentation(), true);
- }
-
- // //////////////////////////////////////////////////////////////////////////////
- // Some utility functions
- // TODO: finish the cleanup.
-
- public void invalidateViews() {
- for (ImageShow views : mImageViews) {
- views.updateImage();
- }
- }
-
- public void hideImageViews() {
- for (View view : mImageViews) {
- view.setVisibility(View.GONE);
- }
- mEditorPlaceHolder.hide();
- }
-
- // //////////////////////////////////////////////////////////////////////////////
- // imageState panel...
-
- public void toggleImageStatePanel() {
- invalidateOptionsMenu();
- mShowingImageStatePanel = !mShowingImageStatePanel;
- Fragment panel = getSupportFragmentManager().findFragmentByTag(MainPanel.FRAGMENT_TAG);
- if (panel != null) {
- if (panel instanceof EditorPanel) {
- EditorPanel editorPanel = (EditorPanel) panel;
- editorPanel.showImageStatePanel(mShowingImageStatePanel);
- } else if (panel instanceof MainPanel) {
- MainPanel mainPanel = (MainPanel) panel;
- mainPanel.showImageStatePanel(mShowingImageStatePanel);
- }
- }
- }
-
- @Override
- public void onConfigurationChanged(Configuration newConfig)
- {
- super.onConfigurationChanged(newConfig);
- setDefaultValues();
- loadXML();
- fillCategories();
- loadMainPanel();
-
- // mLoadBitmapTask==null implies you have looked at the intent
- if (!mShowingTinyPlanet && (mLoadBitmapTask == null)) {
- mCategoryFiltersAdapter.removeTinyPlanet();
- }
- final View loading = findViewById(R.id.loading);
- loading.setVisibility(View.GONE);
- }
-
- public void setupMasterImage() {
-
- HistoryManager historyManager = new HistoryManager();
- StateAdapter imageStateAdapter = new StateAdapter(this, 0);
- MasterImage.reset();
- mMasterImage = MasterImage.getImage();
- mMasterImage.setHistoryManager(historyManager);
- mMasterImage.setStateAdapter(imageStateAdapter);
- mMasterImage.setActivity(this);
-
- if (Runtime.getRuntime().maxMemory() > LIMIT_SUPPORTS_HIGHRES) {
- mMasterImage.setSupportsHighRes(true);
- } else {
- mMasterImage.setSupportsHighRes(false);
- }
- }
-
- void resetHistory() {
- HistoryManager adapter = mMasterImage.getHistory();
- adapter.reset();
- HistoryItem historyItem = adapter.getItem(0);
- ImagePreset original = new ImagePreset(historyItem.getImagePreset());
- mMasterImage.setPreset(original, historyItem.getFilterRepresentation(), true);
- invalidateViews();
- backToMain();
- }
-
- public void showDefaultImageView() {
- mEditorPlaceHolder.hide();
- mImageShow.setVisibility(View.VISIBLE);
- MasterImage.getImage().setCurrentFilter(null);
- MasterImage.getImage().setCurrentFilterRepresentation(null);
- }
-
- public void backToMain() {
- Fragment currentPanel = getSupportFragmentManager().findFragmentByTag(MainPanel.FRAGMENT_TAG);
- if (currentPanel instanceof MainPanel) {
- return;
- }
- loadMainPanel();
- showDefaultImageView();
- }
-
- @Override
- public void onBackPressed() {
- Fragment currentPanel = getSupportFragmentManager().findFragmentByTag(MainPanel.FRAGMENT_TAG);
- if (currentPanel instanceof MainPanel) {
- if (!mImageShow.hasModifications()) {
- done();
- } else {
- AlertDialog.Builder builder = new AlertDialog.Builder(this);
- builder.setMessage(R.string.unsaved).setTitle(R.string.save_before_exit);
- builder.setPositiveButton(R.string.save_and_exit, new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int id) {
- saveImage();
- }
- });
- builder.setNegativeButton(R.string.exit, new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int id) {
- done();
- }
- });
- builder.show();
- }
- } else {
- backToMain();
- }
- }
-
- public void cannotLoadImage() {
- Toast.makeText(this, R.string.cannot_load_image, Toast.LENGTH_SHORT).show();
- finish();
- }
-
- // //////////////////////////////////////////////////////////////////////////////
-
- public float getPixelsFromDip(float value) {
- Resources r = getResources();
- return TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP, value,
- r.getDisplayMetrics());
- }
-
- @Override
- public void onItemClick(AdapterView<?> parent, View view, int position,
- long id) {
- mMasterImage.onHistoryItemClick(position);
- invalidateViews();
- }
-
- public void pickImage() {
- Intent intent = new Intent();
- intent.setType("image/*");
- intent.setAction(Intent.ACTION_GET_CONTENT);
- startActivityForResult(Intent.createChooser(intent, getString(R.string.select_image)),
- SELECT_PICTURE);
- }
-
- @Override
- public void onActivityResult(int requestCode, int resultCode, Intent data) {
- if (resultCode == RESULT_OK) {
- if (requestCode == SELECT_PICTURE) {
- Uri selectedImageUri = data.getData();
- startLoadBitmap(selectedImageUri);
- }
- }
- }
-
-
- public void saveImage() {
- if (mImageShow.hasModifications()) {
- // Get the name of the album, to which the image will be saved
- File saveDir = SaveImage.getFinalSaveDirectory(this, mSelectedImageUri);
- int bucketId = GalleryUtils.getBucketId(saveDir.getPath());
- String albumName = LocalAlbum.getLocalizedName(getResources(), bucketId, null);
- showSavingProgress(albumName);
- mImageShow.saveImage(this, null);
- } else {
- done();
- }
- }
-
-
- public void done() {
- hideSavingProgress();
- if (mLoadBitmapTask != null) {
- mLoadBitmapTask.cancel(false);
- }
- finish();
- }
-
- private void extractXMPData() {
- XMresults res = XmpPresets.extractXMPData(
- getBaseContext(), mMasterImage, getIntent().getData());
- if (res == null)
- return;
-
- mOriginalImageUri = res.originalimage;
- mOriginalPreset = res.preset;
- }
-
- public Uri getSelectedImageUri() {
- return mSelectedImageUri;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/cache/ImageLoader.java b/src/com/android/gallery3d/filtershow/cache/ImageLoader.java
deleted file mode 100644
index b6c72fd9d..000000000
--- a/src/com/android/gallery3d/filtershow/cache/ImageLoader.java
+++ /dev/null
@@ -1,502 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.cache;
-
-import android.content.ContentResolver;
-import android.content.Context;
-import android.content.Intent;
-import android.content.res.Resources;
-import android.database.Cursor;
-import android.database.sqlite.SQLiteException;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.BitmapRegionDecoder;
-import android.graphics.Matrix;
-import android.graphics.Rect;
-import android.net.Uri;
-import android.provider.MediaStore;
-import android.util.Log;
-import android.webkit.MimeTypeMap;
-
-import com.adobe.xmp.XMPException;
-import com.adobe.xmp.XMPMeta;
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.exif.ExifInterface;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.util.XmpUtilHelper;
-
-import java.io.FileNotFoundException;
-import java.io.IOException;
-import java.io.InputStream;
-
-public final class ImageLoader {
-
- private static final String LOGTAG = "ImageLoader";
-
- public static final String JPEG_MIME_TYPE = "image/jpeg";
- public static final int DEFAULT_COMPRESS_QUALITY = 95;
-
- public static final int ORI_NORMAL = ExifInterface.Orientation.TOP_LEFT;
- public static final int ORI_ROTATE_90 = ExifInterface.Orientation.RIGHT_TOP;
- public static final int ORI_ROTATE_180 = ExifInterface.Orientation.BOTTOM_LEFT;
- public static final int ORI_ROTATE_270 = ExifInterface.Orientation.RIGHT_BOTTOM;
- public static final int ORI_FLIP_HOR = ExifInterface.Orientation.TOP_RIGHT;
- public static final int ORI_FLIP_VERT = ExifInterface.Orientation.BOTTOM_RIGHT;
- public static final int ORI_TRANSPOSE = ExifInterface.Orientation.LEFT_TOP;
- public static final int ORI_TRANSVERSE = ExifInterface.Orientation.LEFT_BOTTOM;
-
- private static final int BITMAP_LOAD_BACKOUT_ATTEMPTS = 5;
-
- private ImageLoader() {}
-
- /**
- * Returns the Mime type for a Url. Safe to use with Urls that do not
- * come from Gallery's content provider.
- */
- public static String getMimeType(Uri src) {
- String postfix = MimeTypeMap.getFileExtensionFromUrl(src.toString());
- String ret = null;
- if (postfix != null) {
- ret = MimeTypeMap.getSingleton().getMimeTypeFromExtension(postfix);
- }
- return ret;
- }
-
- /**
- * Returns the image's orientation flag. Defaults to ORI_NORMAL if no valid
- * orientation was found.
- */
- public static int getMetadataOrientation(Context context, Uri uri) {
- if (uri == null || context == null) {
- throw new IllegalArgumentException("bad argument to getOrientation");
- }
-
- // First try to find orientation data in Gallery's ContentProvider.
- Cursor cursor = null;
- try {
- cursor = context.getContentResolver().query(uri,
- new String[] { MediaStore.Images.ImageColumns.ORIENTATION },
- null, null, null);
- if (cursor != null && cursor.moveToNext()) {
- int ori = cursor.getInt(0);
- switch (ori) {
- case 90:
- return ORI_ROTATE_90;
- case 270:
- return ORI_ROTATE_270;
- case 180:
- return ORI_ROTATE_180;
- default:
- return ORI_NORMAL;
- }
- }
- } catch (SQLiteException e) {
- // Do nothing
- } catch (IllegalArgumentException e) {
- // Do nothing
- } finally {
- Utils.closeSilently(cursor);
- }
-
- // Fall back to checking EXIF tags in file.
- if (ContentResolver.SCHEME_FILE.equals(uri.getScheme())) {
- String mimeType = getMimeType(uri);
- if (!JPEG_MIME_TYPE.equals(mimeType)) {
- return ORI_NORMAL;
- }
- String path = uri.getPath();
- ExifInterface exif = new ExifInterface();
- try {
- exif.readExif(path);
- Integer tagval = exif.getTagIntValue(ExifInterface.TAG_ORIENTATION);
- if (tagval != null) {
- int orientation = tagval;
- switch(orientation) {
- case ORI_NORMAL:
- case ORI_ROTATE_90:
- case ORI_ROTATE_180:
- case ORI_ROTATE_270:
- case ORI_FLIP_HOR:
- case ORI_FLIP_VERT:
- case ORI_TRANSPOSE:
- case ORI_TRANSVERSE:
- return orientation;
- default:
- return ORI_NORMAL;
- }
- }
- } catch (IOException e) {
- Log.w(LOGTAG, "Failed to read EXIF orientation", e);
- }
- }
- return ORI_NORMAL;
- }
-
- /**
- * Returns the rotation of image at the given URI as one of 0, 90, 180,
- * 270. Defaults to 0.
- */
- public static int getMetadataRotation(Context context, Uri uri) {
- int orientation = getMetadataOrientation(context, uri);
- switch(orientation) {
- case ORI_ROTATE_90:
- return 90;
- case ORI_ROTATE_180:
- return 180;
- case ORI_ROTATE_270:
- return 270;
- default:
- return 0;
- }
- }
-
- /**
- * Takes an orientation and a bitmap, and returns the bitmap transformed
- * to that orientation.
- */
- public static Bitmap orientBitmap(Bitmap bitmap, int ori) {
- Matrix matrix = new Matrix();
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- if (ori == ORI_ROTATE_90 ||
- ori == ORI_ROTATE_270 ||
- ori == ORI_TRANSPOSE ||
- ori == ORI_TRANSVERSE) {
- int tmp = w;
- w = h;
- h = tmp;
- }
- switch (ori) {
- case ORI_ROTATE_90:
- matrix.setRotate(90, w / 2f, h / 2f);
- break;
- case ORI_ROTATE_180:
- matrix.setRotate(180, w / 2f, h / 2f);
- break;
- case ORI_ROTATE_270:
- matrix.setRotate(270, w / 2f, h / 2f);
- break;
- case ORI_FLIP_HOR:
- matrix.preScale(-1, 1);
- break;
- case ORI_FLIP_VERT:
- matrix.preScale(1, -1);
- break;
- case ORI_TRANSPOSE:
- matrix.setRotate(90, w / 2f, h / 2f);
- matrix.preScale(1, -1);
- break;
- case ORI_TRANSVERSE:
- matrix.setRotate(270, w / 2f, h / 2f);
- matrix.preScale(1, -1);
- break;
- case ORI_NORMAL:
- default:
- return bitmap;
- }
- return Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(),
- bitmap.getHeight(), matrix, true);
- }
-
- /**
- * Returns the bitmap for the rectangular region given by "bounds"
- * if it is a subset of the bitmap stored at uri. Otherwise returns
- * null.
- */
- public static Bitmap loadRegionBitmap(Context context, Uri uri, BitmapFactory.Options options,
- Rect bounds) {
- InputStream is = null;
- try {
- is = context.getContentResolver().openInputStream(uri);
- BitmapRegionDecoder decoder = BitmapRegionDecoder.newInstance(is, false);
- Rect r = new Rect(0, 0, decoder.getWidth(), decoder.getHeight());
- // return null if bounds are not entirely within the bitmap
- if (!r.contains(bounds)) {
- return null;
- }
- return decoder.decodeRegion(bounds, options);
- } catch (FileNotFoundException e) {
- Log.e(LOGTAG, "FileNotFoundException for " + uri, e);
- } catch (IOException e) {
- Log.e(LOGTAG, "FileNotFoundException for " + uri, e);
- } finally {
- Utils.closeSilently(is);
- }
- return null;
- }
-
- /**
- * Returns the bounds of the bitmap stored at a given Url.
- */
- public static Rect loadBitmapBounds(Context context, Uri uri) {
- BitmapFactory.Options o = new BitmapFactory.Options();
- loadBitmap(context, uri, o);
- return new Rect(0, 0, o.outWidth, o.outHeight);
- }
-
- /**
- * Loads a bitmap that has been downsampled using sampleSize from a given url.
- */
- public static Bitmap loadDownsampledBitmap(Context context, Uri uri, int sampleSize) {
- BitmapFactory.Options options = new BitmapFactory.Options();
- options.inMutable = true;
- options.inSampleSize = sampleSize;
- return loadBitmap(context, uri, options);
- }
-
-
- /**
- * Returns the bitmap from the given uri loaded using the given options.
- * Returns null on failure.
- */
- public static Bitmap loadBitmap(Context context, Uri uri, BitmapFactory.Options o) {
- if (uri == null || context == null) {
- throw new IllegalArgumentException("bad argument to loadBitmap");
- }
- InputStream is = null;
- try {
- is = context.getContentResolver().openInputStream(uri);
- return BitmapFactory.decodeStream(is, null, o);
- } catch (FileNotFoundException e) {
- Log.e(LOGTAG, "FileNotFoundException for " + uri, e);
- } finally {
- Utils.closeSilently(is);
- }
- return null;
- }
-
- /**
- * Loads a bitmap at a given URI that is downsampled so that both sides are
- * smaller than maxSideLength. The Bitmap's original dimensions are stored
- * in the rect originalBounds.
- *
- * @param uri URI of image to open.
- * @param context context whose ContentResolver to use.
- * @param maxSideLength max side length of returned bitmap.
- * @param originalBounds If not null, set to the actual bounds of the stored bitmap.
- * @param useMin use min or max side of the original image
- * @return downsampled bitmap or null if this operation failed.
- */
- public static Bitmap loadConstrainedBitmap(Uri uri, Context context, int maxSideLength,
- Rect originalBounds, boolean useMin) {
- if (maxSideLength <= 0 || uri == null || context == null) {
- throw new IllegalArgumentException("bad argument to getScaledBitmap");
- }
- // Get width and height of stored bitmap
- Rect storedBounds = loadBitmapBounds(context, uri);
- if (originalBounds != null) {
- originalBounds.set(storedBounds);
- }
- int w = storedBounds.width();
- int h = storedBounds.height();
-
- // If bitmap cannot be decoded, return null
- if (w <= 0 || h <= 0) {
- return null;
- }
-
- // Find best downsampling size
- int imageSide = 0;
- if (useMin) {
- imageSide = Math.min(w, h);
- } else {
- imageSide = Math.max(w, h);
- }
- int sampleSize = 1;
- while (imageSide > maxSideLength) {
- imageSide >>>= 1;
- sampleSize <<= 1;
- }
-
- // Make sure sample size is reasonable
- if (sampleSize <= 0 ||
- 0 >= (int) (Math.min(w, h) / sampleSize)) {
- return null;
- }
- return loadDownsampledBitmap(context, uri, sampleSize);
- }
-
- /**
- * Loads a bitmap at a given URI that is downsampled so that both sides are
- * smaller than maxSideLength. The Bitmap's original dimensions are stored
- * in the rect originalBounds. The output is also transformed to the given
- * orientation.
- *
- * @param uri URI of image to open.
- * @param context context whose ContentResolver to use.
- * @param maxSideLength max side length of returned bitmap.
- * @param orientation the orientation to transform the bitmap to.
- * @param originalBounds set to the actual bounds of the stored bitmap.
- * @return downsampled bitmap or null if this operation failed.
- */
- public static Bitmap loadOrientedConstrainedBitmap(Uri uri, Context context, int maxSideLength,
- int orientation, Rect originalBounds) {
- Bitmap bmap = loadConstrainedBitmap(uri, context, maxSideLength, originalBounds, false);
- if (bmap != null) {
- bmap = orientBitmap(bmap, orientation);
- }
- return bmap;
- }
-
- public static Bitmap getScaleOneImageForPreset(Context context, Uri uri, Rect bounds,
- Rect destination) {
- BitmapFactory.Options options = new BitmapFactory.Options();
- options.inMutable = true;
- if (destination != null) {
- if (bounds.width() > destination.width()) {
- int sampleSize = 1;
- int w = bounds.width();
- while (w > destination.width()) {
- sampleSize *= 2;
- w /= sampleSize;
- }
- options.inSampleSize = sampleSize;
- }
- }
- Bitmap bmp = loadRegionBitmap(context, uri, options, bounds);
- return bmp;
- }
-
- /**
- * Loads a bitmap that is downsampled by at least the input sample size. In
- * low-memory situations, the bitmap may be downsampled further.
- */
- public static Bitmap loadBitmapWithBackouts(Context context, Uri sourceUri, int sampleSize) {
- boolean noBitmap = true;
- int num_tries = 0;
- if (sampleSize <= 0) {
- sampleSize = 1;
- }
- Bitmap bmap = null;
- while (noBitmap) {
- try {
- // Try to decode, downsample if low-memory.
- bmap = loadDownsampledBitmap(context, sourceUri, sampleSize);
- noBitmap = false;
- } catch (java.lang.OutOfMemoryError e) {
- // Try with more downsampling before failing for good.
- if (++num_tries >= BITMAP_LOAD_BACKOUT_ATTEMPTS) {
- throw e;
- }
- bmap = null;
- System.gc();
- sampleSize *= 2;
- }
- }
- return bmap;
- }
-
- /**
- * Loads an oriented bitmap that is downsampled by at least the input sample
- * size. In low-memory situations, the bitmap may be downsampled further.
- */
- public static Bitmap loadOrientedBitmapWithBackouts(Context context, Uri sourceUri,
- int sampleSize) {
- Bitmap bitmap = loadBitmapWithBackouts(context, sourceUri, sampleSize);
- if (bitmap == null) {
- return null;
- }
- int orientation = getMetadataOrientation(context, sourceUri);
- bitmap = orientBitmap(bitmap, orientation);
- return bitmap;
- }
-
- /**
- * Loads bitmap from a resource that may be downsampled in low-memory situations.
- */
- public static Bitmap decodeResourceWithBackouts(Resources res, BitmapFactory.Options options,
- int id) {
- boolean noBitmap = true;
- int num_tries = 0;
- if (options.inSampleSize < 1) {
- options.inSampleSize = 1;
- }
- // Stopgap fix for low-memory devices.
- Bitmap bmap = null;
- while (noBitmap) {
- try {
- // Try to decode, downsample if low-memory.
- bmap = BitmapFactory.decodeResource(
- res, id, options);
- noBitmap = false;
- } catch (java.lang.OutOfMemoryError e) {
- // Retry before failing for good.
- if (++num_tries >= BITMAP_LOAD_BACKOUT_ATTEMPTS) {
- throw e;
- }
- bmap = null;
- System.gc();
- options.inSampleSize *= 2;
- }
- }
- return bmap;
- }
-
- public static XMPMeta getXmpObject(Context context) {
- try {
- InputStream is = context.getContentResolver().openInputStream(
- MasterImage.getImage().getUri());
- return XmpUtilHelper.extractXMPMeta(is);
- } catch (FileNotFoundException e) {
- return null;
- }
- }
-
- /**
- * Determine if this is a light cycle 360 image
- *
- * @return true if it is a light Cycle image that is full 360
- */
- public static boolean queryLightCycle360(Context context) {
- InputStream is = null;
- try {
- is = context.getContentResolver().openInputStream(MasterImage.getImage().getUri());
- XMPMeta meta = XmpUtilHelper.extractXMPMeta(is);
- if (meta == null) {
- return false;
- }
- String namespace = "http://ns.google.com/photos/1.0/panorama/";
- String cropWidthName = "GPano:CroppedAreaImageWidthPixels";
- String fullWidthName = "GPano:FullPanoWidthPixels";
-
- if (!meta.doesPropertyExist(namespace, cropWidthName)) {
- return false;
- }
- if (!meta.doesPropertyExist(namespace, fullWidthName)) {
- return false;
- }
-
- Integer cropValue = meta.getPropertyInteger(namespace, cropWidthName);
- Integer fullValue = meta.getPropertyInteger(namespace, fullWidthName);
-
- // Definition of a 360:
- // GFullPanoWidthPixels == CroppedAreaImageWidthPixels
- if (cropValue != null && fullValue != null) {
- return cropValue.equals(fullValue);
- }
-
- return false;
- } catch (FileNotFoundException e) {
- return false;
- } catch (XMPException e) {
- return false;
- } finally {
- Utils.closeSilently(is);
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/category/Action.java b/src/com/android/gallery3d/filtershow/category/Action.java
deleted file mode 100644
index 332ca18b0..000000000
--- a/src/com/android/gallery3d/filtershow/category/Action.java
+++ /dev/null
@@ -1,186 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.category;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.Canvas;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.widget.ArrayAdapter;
-import android.widget.ListAdapter;
-import com.android.gallery3d.filtershow.filters.FilterUserPresetRepresentation;
-import com.android.gallery3d.filtershow.pipeline.RenderingRequest;
-import com.android.gallery3d.filtershow.pipeline.RenderingRequestCaller;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-
-public class Action implements RenderingRequestCaller {
-
- private static final String LOGTAG = "Action";
- private FilterRepresentation mRepresentation;
- private String mName;
- private Rect mImageFrame;
- private Bitmap mImage;
- private ArrayAdapter mAdapter;
- public static final int FULL_VIEW = 0;
- public static final int CROP_VIEW = 1;
- private int mType = CROP_VIEW;
- private Bitmap mPortraitImage;
- private Bitmap mOverlayBitmap;
- private Context mContext;
-
- public Action(Context context, FilterRepresentation representation, int type) {
- mContext = context;
- setRepresentation(representation);
- setType(type);
- }
-
- public Action(Context context, FilterRepresentation representation) {
- this(context, representation, CROP_VIEW);
- }
-
- public FilterRepresentation getRepresentation() {
- return mRepresentation;
- }
-
- public void setRepresentation(FilterRepresentation representation) {
- mRepresentation = representation;
- mName = representation.getName();
- }
-
- public String getName() {
- return mName;
- }
-
- public void setName(String name) {
- mName = name;
- }
-
- public void setImageFrame(Rect imageFrame, int orientation) {
- if (mImageFrame != null && mImageFrame.equals(imageFrame)) {
- return;
- }
- Bitmap bitmap = MasterImage.getImage().getLargeThumbnailBitmap();
- if (bitmap != null) {
- mImageFrame = imageFrame;
- int w = mImageFrame.width();
- int h = mImageFrame.height();
- if (orientation == CategoryView.VERTICAL
- && mType == CROP_VIEW) {
- w /= 2;
- }
- Bitmap bitmapCrop = Bitmap.createBitmap(w, h, Bitmap.Config.ARGB_8888);
- drawCenteredImage(bitmap, bitmapCrop, true);
-
- postNewIconRenderRequest(bitmapCrop);
- }
- }
-
- public Bitmap getImage() {
- return mImage;
- }
-
- public void setImage(Bitmap image) {
- mImage = image;
- }
-
- public void setAdapter(ArrayAdapter adapter) {
- mAdapter = adapter;
- }
-
- public void setType(int type) {
- mType = type;
- }
-
- private void postNewIconRenderRequest(Bitmap bitmap) {
- if (bitmap != null && mRepresentation != null) {
- ImagePreset preset = new ImagePreset();
- preset.addFilter(mRepresentation);
- RenderingRequest.post(mContext, bitmap,
- preset, RenderingRequest.ICON_RENDERING, this);
- }
- }
-
- private void drawCenteredImage(Bitmap source, Bitmap destination, boolean scale) {
- RectF image = new RectF(0, 0, source.getWidth(), source.getHeight());
- int border = 0;
- if (!scale) {
- border = destination.getWidth() - destination.getHeight();
- if (border < 0) {
- border = 0;
- }
- }
- RectF frame = new RectF(border, 0,
- destination.getWidth() - border,
- destination.getHeight());
- Matrix m = new Matrix();
- m.setRectToRect(frame, image, Matrix.ScaleToFit.CENTER);
- image.set(frame);
- m.mapRect(image);
- m.setRectToRect(image, frame, Matrix.ScaleToFit.FILL);
- Canvas canvas = new Canvas(destination);
- canvas.drawBitmap(source, m, new Paint(Paint.FILTER_BITMAP_FLAG));
- }
-
- @Override
- public void available(RenderingRequest request) {
- mImage = request.getBitmap();
- if (mImage == null) {
- return;
- }
- if (mRepresentation.getOverlayId() != 0 && mOverlayBitmap == null) {
- mOverlayBitmap = BitmapFactory.decodeResource(
- mContext.getResources(),
- mRepresentation.getOverlayId());
- }
- if (mOverlayBitmap != null) {
- if (getRepresentation().getFilterType() == FilterRepresentation.TYPE_BORDER) {
- Canvas canvas = new Canvas(mImage);
- canvas.drawBitmap(mOverlayBitmap, new Rect(0, 0, mOverlayBitmap.getWidth(), mOverlayBitmap.getHeight()),
- new Rect(0, 0, mImage.getWidth(), mImage.getHeight()), new Paint());
- } else {
- Canvas canvas = new Canvas(mImage);
- canvas.drawARGB(128, 0, 0, 0);
- drawCenteredImage(mOverlayBitmap, mImage, false);
- }
- }
- if (mAdapter != null) {
- mAdapter.notifyDataSetChanged();
- }
- }
-
- public void setPortraitImage(Bitmap portraitImage) {
- mPortraitImage = portraitImage;
- }
-
- public Bitmap getPortraitImage() {
- return mPortraitImage;
- }
-
- public Bitmap getOverlayBitmap() {
- return mOverlayBitmap;
- }
-
- public void setOverlayBitmap(Bitmap overlayBitmap) {
- mOverlayBitmap = overlayBitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/category/CategoryAdapter.java b/src/com/android/gallery3d/filtershow/category/CategoryAdapter.java
deleted file mode 100644
index 6451c39df..000000000
--- a/src/com/android/gallery3d/filtershow/category/CategoryAdapter.java
+++ /dev/null
@@ -1,182 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.category;
-
-import android.content.Context;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.ArrayAdapter;
-import android.widget.ListView;
-
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterTinyPlanetRepresentation;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-
-public class CategoryAdapter extends ArrayAdapter<Action> {
-
- private static final String LOGTAG = "CategoryAdapter";
- private int mItemHeight;
- private View mContainer;
- private int mItemWidth = ListView.LayoutParams.MATCH_PARENT;
- private int mSelectedPosition;
- int mCategory;
- private int mOrientation;
-
- public CategoryAdapter(Context context, int textViewResourceId) {
- super(context, textViewResourceId);
- mItemHeight = (int) (context.getResources().getDisplayMetrics().density * 100);
- }
-
- public CategoryAdapter(Context context) {
- this(context, 0);
- }
-
- public void setItemHeight(int height) {
- mItemHeight = height;
- }
-
- public void setItemWidth(int width) {
- mItemWidth = width;
- }
-
- @Override
- public void add(Action action) {
- super.add(action);
- action.setAdapter(this);
- }
-
- public void initializeSelection(int category) {
- mCategory = category;
- mSelectedPosition = -1;
- if (category == MainPanel.LOOKS) {
- mSelectedPosition = 0;
- }
- if (category == MainPanel.BORDERS) {
- mSelectedPosition = 0;
- }
- }
-
- @Override
- public View getView(int position, View convertView, ViewGroup parent) {
- if (convertView == null) {
- convertView = new CategoryView(getContext());
- }
- CategoryView view = (CategoryView) convertView;
- view.setOrientation(mOrientation);
- view.setAction(getItem(position), this);
- view.setLayoutParams(
- new ListView.LayoutParams(mItemWidth, mItemHeight));
- view.setTag(position);
- view.invalidate();
- return view;
- }
-
- public void setSelected(View v) {
- int old = mSelectedPosition;
- mSelectedPosition = (Integer) v.getTag();
- if (old != -1) {
- invalidateView(old);
- }
- invalidateView(mSelectedPosition);
- }
-
- public boolean isSelected(View v) {
- return (Integer) v.getTag() == mSelectedPosition;
- }
-
- private void invalidateView(int position) {
- View child = null;
- if (mContainer instanceof ListView) {
- ListView lv = (ListView) mContainer;
- child = lv.getChildAt(position - lv.getFirstVisiblePosition());
- } else {
- CategoryTrack ct = (CategoryTrack) mContainer;
- child = ct.getChildAt(position);
- }
- if (child != null) {
- child.invalidate();
- }
- }
-
- public void setContainer(View container) {
- mContainer = container;
- }
-
- public void imageLoaded() {
- notifyDataSetChanged();
- }
-
- public FilterRepresentation getTinyPlanet() {
- for (int i = 0; i < getCount(); i++) {
- Action action = getItem(i);
- if (action.getRepresentation() != null
- && action.getRepresentation()
- instanceof FilterTinyPlanetRepresentation) {
- return action.getRepresentation();
- }
- }
- return null;
- }
-
- public void removeTinyPlanet() {
- for (int i = 0; i < getCount(); i++) {
- Action action = getItem(i);
- if (action.getRepresentation() != null
- && action.getRepresentation()
- instanceof FilterTinyPlanetRepresentation) {
- remove(action);
- return;
- }
- }
- }
-
- public void setOrientation(int orientation) {
- mOrientation = orientation;
- }
-
- public void reflectImagePreset(ImagePreset preset) {
- if (preset == null) {
- return;
- }
- int selected = 0; // if nothing found, select "none" (first element)
- FilterRepresentation rep = null;
- if (mCategory == MainPanel.LOOKS) {
- int pos = preset.getPositionForType(FilterRepresentation.TYPE_FX);
- if (pos != -1) {
- rep = preset.getFilterRepresentation(pos);
- }
- } else if (mCategory == MainPanel.BORDERS) {
- int pos = preset.getPositionForType(FilterRepresentation.TYPE_BORDER);
- if (pos != -1) {
- rep = preset.getFilterRepresentation(pos);
- }
- }
- if (rep != null) {
- for (int i = 0; i < getCount(); i++) {
- if (rep.getName().equalsIgnoreCase(
- getItem(i).getRepresentation().getName())) {
- selected = i;
- break;
- }
- }
- }
- if (mSelectedPosition != selected) {
- mSelectedPosition = selected;
- this.notifyDataSetChanged();
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/category/CategoryPanel.java b/src/com/android/gallery3d/filtershow/category/CategoryPanel.java
deleted file mode 100644
index de2481f3f..000000000
--- a/src/com/android/gallery3d/filtershow/category/CategoryPanel.java
+++ /dev/null
@@ -1,108 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.category;
-
-import android.app.Activity;
-import android.os.Bundle;
-import android.support.v4.app.Fragment;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.LinearLayout;
-import android.widget.ListView;
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-
-public class CategoryPanel extends Fragment {
-
- public static final String FRAGMENT_TAG = "CategoryPanel";
- private static final String PARAMETER_TAG = "currentPanel";
-
- private int mCurrentAdapter = MainPanel.LOOKS;
- private CategoryAdapter mAdapter;
-
- public void setAdapter(int value) {
- mCurrentAdapter = value;
- }
-
- @Override
- public void onAttach(Activity activity) {
- super.onAttach(activity);
- loadAdapter(mCurrentAdapter);
- }
-
- private void loadAdapter(int adapter) {
- FilterShowActivity activity = (FilterShowActivity) getActivity();
- switch (adapter) {
- case MainPanel.LOOKS: {
- mAdapter = activity.getCategoryLooksAdapter();
- mAdapter.initializeSelection(MainPanel.LOOKS);
- activity.updateCategories();
- break;
- }
- case MainPanel.BORDERS: {
- mAdapter = activity.getCategoryBordersAdapter();
- mAdapter.initializeSelection(MainPanel.BORDERS);
- activity.updateCategories();
- break;
- }
- case MainPanel.GEOMETRY: {
- mAdapter = activity.getCategoryGeometryAdapter();
- mAdapter.initializeSelection(MainPanel.GEOMETRY);
- break;
- }
- case MainPanel.FILTERS: {
- mAdapter = activity.getCategoryFiltersAdapter();
- mAdapter.initializeSelection(MainPanel.FILTERS);
- break;
- }
- }
- }
-
- @Override
- public void onSaveInstanceState(Bundle state) {
- super.onSaveInstanceState(state);
- state.putInt(PARAMETER_TAG, mCurrentAdapter);
- }
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
- LinearLayout main = (LinearLayout) inflater.inflate(
- R.layout.filtershow_category_panel_new, container,
- false);
-
- if (savedInstanceState != null) {
- int selectedPanel = savedInstanceState.getInt(PARAMETER_TAG);
- loadAdapter(selectedPanel);
- }
-
- View panelView = main.findViewById(R.id.listItems);
- if (panelView instanceof CategoryTrack) {
- CategoryTrack panel = (CategoryTrack) panelView;
- mAdapter.setOrientation(CategoryView.HORIZONTAL);
- panel.setAdapter(mAdapter);
- mAdapter.setContainer(panel);
- } else {
- ListView panel = (ListView) main.findViewById(R.id.listItems);
- panel.setAdapter(mAdapter);
- mAdapter.setContainer(panel);
- }
- return main;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/category/CategoryTrack.java b/src/com/android/gallery3d/filtershow/category/CategoryTrack.java
deleted file mode 100644
index ac8245a3b..000000000
--- a/src/com/android/gallery3d/filtershow/category/CategoryTrack.java
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.category;
-
-import android.content.Context;
-import android.content.res.TypedArray;
-import android.database.DataSetObserver;
-import android.util.AttributeSet;
-import android.util.Log;
-import android.view.View;
-import android.widget.LinearLayout;
-import com.android.gallery3d.R;
-
-public class CategoryTrack extends LinearLayout {
-
- private CategoryAdapter mAdapter;
- private int mElemSize;
- private DataSetObserver mDataSetObserver = new DataSetObserver() {
- @Override
- public void onChanged() {
- super.onChanged();
- invalidate();
- }
- @Override
- public void onInvalidated() {
- super.onInvalidated();
- fillContent();
- }
- };
-
- public CategoryTrack(Context context, AttributeSet attrs) {
- super(context, attrs);
- TypedArray a = getContext().obtainStyledAttributes(attrs, R.styleable.CategoryTrack);
- mElemSize = a.getDimensionPixelSize(R.styleable.CategoryTrack_iconSize, 0);
- }
-
- public void setAdapter(CategoryAdapter adapter) {
- mAdapter = adapter;
- mAdapter.registerDataSetObserver(mDataSetObserver);
- fillContent();
- }
-
- public void fillContent() {
- removeAllViews();
- mAdapter.setItemWidth(mElemSize);
- mAdapter.setItemHeight(LayoutParams.MATCH_PARENT);
- int n = mAdapter.getCount();
- for (int i = 0; i < n; i++) {
- View view = mAdapter.getView(i, null, this);
- addView(view, i);
- }
- requestLayout();
- }
-
- @Override
- public void invalidate() {
- for (int i = 0; i < this.getChildCount(); i++) {
- View child = getChildAt(i);
- child.invalidate();
- }
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/category/CategoryView.java b/src/com/android/gallery3d/filtershow/category/CategoryView.java
deleted file mode 100644
index c456dc207..000000000
--- a/src/com/android/gallery3d/filtershow/category/CategoryView.java
+++ /dev/null
@@ -1,176 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.category;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.Rect;
-import android.graphics.Typeface;
-import android.view.View;
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.ui.SelectionRenderer;
-
-public class CategoryView extends View implements View.OnClickListener {
-
- private static final String LOGTAG = "CategoryView";
- public static final int VERTICAL = 0;
- public static final int HORIZONTAL = 1;
- private Paint mPaint = new Paint();
- private Action mAction;
- private Rect mTextBounds = new Rect();
- private int mMargin = 16;
- private int mTextSize = 32;
- private int mTextColor;
- private int mBackgroundColor;
- private Paint mSelectPaint;
- CategoryAdapter mAdapter;
- private int mSelectionStroke;
- private Paint mBorderPaint;
- private int mBorderStroke;
- private int mOrientation = VERTICAL;
-
- public CategoryView(Context context) {
- super(context);
- setOnClickListener(this);
- Resources res = getResources();
- mBackgroundColor = res.getColor(R.color.filtershow_categoryview_background);
- mTextColor = res.getColor(R.color.filtershow_categoryview_text);
- mSelectionStroke = res.getDimensionPixelSize(R.dimen.thumbnail_margin);
- mTextSize = res.getDimensionPixelSize(R.dimen.category_panel_text_size);
- mMargin = res.getDimensionPixelOffset(R.dimen.category_panel_margin);
- mSelectPaint = new Paint();
- mSelectPaint.setStyle(Paint.Style.FILL);
- mSelectPaint.setColor(res.getColor(R.color.filtershow_category_selection));
- mBorderPaint = new Paint(mSelectPaint);
- mBorderPaint.setColor(Color.BLACK);
- mBorderStroke = mSelectionStroke / 3;
- }
-
- private void computeTextPosition(String text) {
- if (text == null) {
- return;
- }
- mPaint.setTextSize(mTextSize);
- if (mOrientation == VERTICAL) {
- text = text.toUpperCase();
- // TODO: set this in xml
- mPaint.setTypeface(Typeface.DEFAULT_BOLD);
- }
- mPaint.getTextBounds(text, 0, text.length(), mTextBounds);
- }
-
- public void drawText(Canvas canvas, String text) {
- if (text == null) {
- return;
- }
- float textWidth = mPaint.measureText(text);
- int x = (int) (canvas.getWidth() - textWidth - mMargin);
- if (mOrientation == HORIZONTAL) {
- x = (int) ((canvas.getWidth() - textWidth) / 2.0f);
- }
- if (x < 0) {
- // If the text takes more than the view width,
- // justify to the left.
- x = mMargin;
- }
- int y = canvas.getHeight() - mMargin;
- canvas.drawText(text, x, y, mPaint);
- }
-
- @Override
- public CharSequence getContentDescription () {
- if (mAction != null) {
- return mAction.getName();
- }
- return null;
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- canvas.drawColor(mBackgroundColor);
- if (mAction != null) {
- mPaint.reset();
- mPaint.setAntiAlias(true);
- computeTextPosition(mAction.getName());
- if (mAction.getImage() == null) {
- mAction.setImageFrame(new Rect(0, 0, getWidth(), getHeight()), mOrientation);
- } else {
- Bitmap bitmap = mAction.getImage();
- canvas.save();
- Rect clipRect = new Rect(mSelectionStroke, mSelectionStroke,
- getWidth() - mSelectionStroke,
- getHeight() - 2* mMargin - mTextSize);
- int offsetx = 0;
- int offsety = 0;
- if (mOrientation == HORIZONTAL) {
- canvas.clipRect(clipRect);
- offsetx = - (bitmap.getWidth() - clipRect.width()) / 2;
- offsety = - (bitmap.getHeight() - clipRect.height()) / 2;
- }
- canvas.drawBitmap(bitmap, offsetx, offsety, mPaint);
- canvas.restore();
- if (mAdapter.isSelected(this)) {
- if (mOrientation == HORIZONTAL) {
- SelectionRenderer.drawSelection(canvas, 0, 0,
- getWidth(), getHeight() - mMargin - mTextSize,
- mSelectionStroke, mSelectPaint, mBorderStroke, mBorderPaint);
- } else {
- SelectionRenderer.drawSelection(canvas, 0, 0,
- Math.min(bitmap.getWidth(), getWidth()),
- Math.min(bitmap.getHeight(), getHeight()),
- mSelectionStroke, mSelectPaint, mBorderStroke, mBorderPaint);
- }
- }
- }
- mPaint.setColor(mBackgroundColor);
- mPaint.setStyle(Paint.Style.STROKE);
- mPaint.setStrokeWidth(3);
- drawText(canvas, mAction.getName());
- mPaint.setColor(mTextColor);
- mPaint.setStyle(Paint.Style.FILL);
- mPaint.setStrokeWidth(1);
- drawText(canvas, mAction.getName());
- }
- }
-
- public void setAction(Action action, CategoryAdapter adapter) {
- mAction = action;
- mAdapter = adapter;
- invalidate();
- }
-
- public FilterRepresentation getRepresentation() {
- return mAction.getRepresentation();
- }
-
- @Override
- public void onClick(View view) {
- FilterShowActivity activity = (FilterShowActivity) getContext();
- activity.showRepresentation(mAction.getRepresentation());
- mAdapter.setSelected(this);
- }
-
- public void setOrientation(int orientation) {
- mOrientation = orientation;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/category/MainPanel.java b/src/com/android/gallery3d/filtershow/category/MainPanel.java
deleted file mode 100644
index 9a64ffbf3..000000000
--- a/src/com/android/gallery3d/filtershow/category/MainPanel.java
+++ /dev/null
@@ -1,239 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.category;
-
-import android.os.Bundle;
-import android.support.v4.app.Fragment;
-import android.support.v4.app.FragmentTransaction;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.ImageButton;
-import android.widget.LinearLayout;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.state.StatePanel;
-
-public class MainPanel extends Fragment {
-
- private static final String LOGTAG = "MainPanel";
-
- private LinearLayout mMainView;
- private ImageButton looksButton;
- private ImageButton bordersButton;
- private ImageButton geometryButton;
- private ImageButton filtersButton;
-
- public static final String FRAGMENT_TAG = "MainPanel";
- public static final int LOOKS = 0;
- public static final int BORDERS = 1;
- public static final int GEOMETRY = 2;
- public static final int FILTERS = 3;
-
- private int mCurrentSelected = -1;
-
- private void selection(int position, boolean value) {
- if (value) {
- FilterShowActivity activity = (FilterShowActivity) getActivity();
- activity.setCurrentPanel(position);
- }
- switch (position) {
- case LOOKS: {
- looksButton.setSelected(value);
- break;
- }
- case BORDERS: {
- bordersButton.setSelected(value);
- break;
- }
- case GEOMETRY: {
- geometryButton.setSelected(value);
- break;
- }
- case FILTERS: {
- filtersButton.setSelected(value);
- break;
- }
- }
- }
-
- @Override
- public void onDestroyView() {
- super.onDestroyView();
- if (mMainView != null) {
- if (mMainView.getParent() != null) {
- ViewGroup parent = (ViewGroup) mMainView.getParent();
- parent.removeView(mMainView);
- }
- }
- }
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
-
- mMainView = (LinearLayout) inflater.inflate(
- R.layout.filtershow_main_panel, null, false);
-
- looksButton = (ImageButton) mMainView.findViewById(R.id.fxButton);
- bordersButton = (ImageButton) mMainView.findViewById(R.id.borderButton);
- geometryButton = (ImageButton) mMainView.findViewById(R.id.geometryButton);
- filtersButton = (ImageButton) mMainView.findViewById(R.id.colorsButton);
-
- looksButton.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- showPanel(LOOKS);
- }
- });
- bordersButton.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- showPanel(BORDERS);
- }
- });
- geometryButton.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- showPanel(GEOMETRY);
- }
- });
- filtersButton.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- showPanel(FILTERS);
- }
- });
-
- FilterShowActivity activity = (FilterShowActivity) getActivity();
- showImageStatePanel(activity.isShowingImageStatePanel());
- showPanel(activity.getCurrentPanel());
- return mMainView;
- }
-
- private boolean isRightAnimation(int newPos) {
- if (newPos < mCurrentSelected) {
- return false;
- }
- return true;
- }
-
- private void setCategoryFragment(CategoryPanel category, boolean fromRight) {
- FragmentTransaction transaction = getChildFragmentManager().beginTransaction();
- if (fromRight) {
- transaction.setCustomAnimations(R.anim.slide_in_right, R.anim.slide_out_right);
- } else {
- transaction.setCustomAnimations(R.anim.slide_in_left, R.anim.slide_out_left);
- }
- transaction.replace(R.id.category_panel_container, category, CategoryPanel.FRAGMENT_TAG);
- transaction.commit();
- }
-
- public void loadCategoryLookPanel() {
- if (mCurrentSelected == LOOKS) {
- return;
- }
- boolean fromRight = isRightAnimation(LOOKS);
- selection(mCurrentSelected, false);
- CategoryPanel categoryPanel = new CategoryPanel();
- categoryPanel.setAdapter(LOOKS);
- setCategoryFragment(categoryPanel, fromRight);
- mCurrentSelected = LOOKS;
- selection(mCurrentSelected, true);
- }
-
- public void loadCategoryBorderPanel() {
- if (mCurrentSelected == BORDERS) {
- return;
- }
- boolean fromRight = isRightAnimation(BORDERS);
- selection(mCurrentSelected, false);
- CategoryPanel categoryPanel = new CategoryPanel();
- categoryPanel.setAdapter(BORDERS);
- setCategoryFragment(categoryPanel, fromRight);
- mCurrentSelected = BORDERS;
- selection(mCurrentSelected, true);
- }
-
- public void loadCategoryGeometryPanel() {
- if (mCurrentSelected == GEOMETRY) {
- return;
- }
- boolean fromRight = isRightAnimation(GEOMETRY);
- selection(mCurrentSelected, false);
- CategoryPanel categoryPanel = new CategoryPanel();
- categoryPanel.setAdapter(GEOMETRY);
- setCategoryFragment(categoryPanel, fromRight);
- mCurrentSelected = GEOMETRY;
- selection(mCurrentSelected, true);
- }
-
- public void loadCategoryFiltersPanel() {
- if (mCurrentSelected == FILTERS) {
- return;
- }
- boolean fromRight = isRightAnimation(FILTERS);
- selection(mCurrentSelected, false);
- CategoryPanel categoryPanel = new CategoryPanel();
- categoryPanel.setAdapter(FILTERS);
- setCategoryFragment(categoryPanel, fromRight);
- mCurrentSelected = FILTERS;
- selection(mCurrentSelected, true);
- }
-
- public void showPanel(int currentPanel) {
- switch (currentPanel) {
- case LOOKS: {
- loadCategoryLookPanel();
- break;
- }
- case BORDERS: {
- loadCategoryBorderPanel();
- break;
- }
- case GEOMETRY: {
- loadCategoryGeometryPanel();
- break;
- }
- case FILTERS: {
- loadCategoryFiltersPanel();
- break;
- }
- }
- }
-
- public void showImageStatePanel(boolean show) {
- if (mMainView.findViewById(R.id.state_panel_container) == null) {
- return;
- }
- FragmentTransaction transaction = getChildFragmentManager().beginTransaction();
- final View container = mMainView.findViewById(R.id.state_panel_container);
- if (show) {
- container.setVisibility(View.VISIBLE);
- StatePanel statePanel = new StatePanel();
- transaction.replace(R.id.state_panel_container, statePanel, StatePanel.FRAGMENT_TAG);
- } else {
- container.setVisibility(View.GONE);
- Fragment statePanel = getChildFragmentManager().findFragmentByTag(StatePanel.FRAGMENT_TAG);
- if (statePanel != null) {
- transaction.remove(statePanel);
- }
- }
- transaction.commit();
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/colorpicker/ColorGridDialog.java b/src/com/android/gallery3d/filtershow/colorpicker/ColorGridDialog.java
deleted file mode 100644
index dd4df7dc8..000000000
--- a/src/com/android/gallery3d/filtershow/colorpicker/ColorGridDialog.java
+++ /dev/null
@@ -1,100 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.colorpicker;
-
-import android.app.Dialog;
-import android.content.Context;
-import android.graphics.Color;
-import android.graphics.drawable.GradientDrawable;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.Button;
-
-import com.android.gallery3d.R;
-
-import java.util.ArrayList;
-
-public class ColorGridDialog extends Dialog {
- RGBListener mCallback;
- private static final String LOGTAG = "ColorGridDialog";
-
- public ColorGridDialog(Context context, final RGBListener cl) {
- super(context);
- mCallback = cl;
- setTitle(R.string.color_pick_title);
- setContentView(R.layout.filtershow_color_gird);
- Button sel = (Button) findViewById(R.id.filtershow_cp_custom);
- ArrayList<Button> b = getButtons((ViewGroup) getWindow().getDecorView());
- int k = 0;
- float[] hsv = new float[3];
-
- for (Button button : b) {
- if (!button.equals(sel)){
- hsv[0] = (k % 5) * 360 / 5;
- hsv[1] = (k / 5) / 3.0f;
- hsv[2] = (k < 5) ? (k / 4f) : 1;
- final int c = (Color.HSVToColor(hsv) & 0x00FFFFFF) | 0xAA000000;
- GradientDrawable sd = ((GradientDrawable) button.getBackground());
- button.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- mCallback.setColor(c);
- dismiss();
- }
- });
- sd.setColor(c);
- k++;
- }
-
- }
- sel.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- showColorPicker();
- ColorGridDialog.this.dismiss();
- }
- });
- }
-
- private ArrayList<Button> getButtons(ViewGroup vg) {
- ArrayList<Button> list = new ArrayList<Button>();
- for (int i = 0; i < vg.getChildCount(); i++) {
- View v = vg.getChildAt(i);
- if (v instanceof Button) {
- list.add((Button) v);
- } else if (v instanceof ViewGroup) {
- list.addAll(getButtons((ViewGroup) v));
- }
- }
- return list;
- }
-
- public void showColorPicker() {
- ColorListener cl = new ColorListener() {
- @Override
- public void setColor(float[] hsvo) {
- int c = Color.HSVToColor(hsvo) & 0xFFFFFF;
- int alpha = (int) (hsvo[3] * 255);
- c |= alpha << 24;
- mCallback.setColor(c);
- }
- };
- ColorPickerDialog cpd = new ColorPickerDialog(this.getContext(), cl);
- cpd.show();
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/colorpicker/ColorListener.java b/src/com/android/gallery3d/filtershow/colorpicker/ColorListener.java
deleted file mode 100644
index 5127dad26..000000000
--- a/src/com/android/gallery3d/filtershow/colorpicker/ColorListener.java
+++ /dev/null
@@ -1,21 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.colorpicker;
-
-public interface ColorListener {
- void setColor(float[] hsvo);
-}
diff --git a/src/com/android/gallery3d/filtershow/colorpicker/ColorOpacityView.java b/src/com/android/gallery3d/filtershow/colorpicker/ColorOpacityView.java
deleted file mode 100644
index 2bff501f7..000000000
--- a/src/com/android/gallery3d/filtershow/colorpicker/ColorOpacityView.java
+++ /dev/null
@@ -1,197 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.colorpicker;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.BitmapShader;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.LinearGradient;
-import android.graphics.Paint;
-import android.graphics.RadialGradient;
-import android.graphics.Shader;
-import android.util.AttributeSet;
-import android.util.DisplayMetrics;
-import android.view.MotionEvent;
-import android.view.View;
-
-import com.android.gallery3d.R;
-
-import java.util.ArrayList;
-
-public class ColorOpacityView extends View implements ColorListener {
-
- private float mRadius;
- private float mWidth;
- private Paint mBarPaint1;
- private Paint mLinePaint1;
- private Paint mLinePaint2;
- private Paint mCheckPaint;
-
- private float mHeight;
- private Paint mDotPaint;
- private int mBgcolor = 0;
-
- private float mDotRadius;
- private float mBorder;
-
- private float[] mHSVO = new float[4];
- private int mSliderColor;
- private float mDotX = mBorder;
- private float mDotY = mBorder;
- private final static float DOT_SIZE = ColorRectView.DOT_SIZE;
- public final static float BORDER_SIZE = 20;;
-
- public ColorOpacityView(Context ctx, AttributeSet attrs) {
- super(ctx, attrs);
- DisplayMetrics metrics = ctx.getResources().getDisplayMetrics();
- float mDpToPix = metrics.density;
- mDotRadius = DOT_SIZE * mDpToPix;
- mBorder = BORDER_SIZE * mDpToPix;
- mBarPaint1 = new Paint();
-
- mDotPaint = new Paint();
-
- mDotPaint.setStyle(Paint.Style.FILL);
- mDotPaint.setColor(ctx.getResources().getColor(R.color.slider_dot_color));
- mSliderColor = ctx.getResources().getColor(R.color.slider_line_color);
-
- mBarPaint1.setStyle(Paint.Style.FILL);
-
- mLinePaint1 = new Paint();
- mLinePaint1.setColor(Color.GRAY);
- mLinePaint2 = new Paint();
- mLinePaint2.setColor(mSliderColor);
- mLinePaint2.setStrokeWidth(4);
-
- int[] colors = new int[16 * 16];
- for (int i = 0; i < colors.length; i++) {
- int y = i / (16 * 8);
- int x = (i / 8) % 2;
- colors[i] = (x == y) ? 0xFFAAAAAA : 0xFF444444;
- }
- Bitmap bitmap = Bitmap.createBitmap(colors, 16, 16, Bitmap.Config.ARGB_8888);
- BitmapShader bs = new BitmapShader(bitmap, Shader.TileMode.REPEAT, Shader.TileMode.REPEAT);
- mCheckPaint = new Paint();
- mCheckPaint.setShader(bs);
- }
-
- public boolean onDown(MotionEvent e) {
- return true;
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- float ox = mDotX;
- float oy = mDotY;
-
- float x = event.getX();
- float y = event.getY();
-
- mDotX = x;
-
- if (mDotX < mBorder) {
- mDotX = mBorder;
- }
-
- if (mDotX > mWidth - mBorder) {
- mDotX = mWidth - mBorder;
- }
- mHSVO[3] = (mDotX - mBorder) / (mWidth - mBorder * 2);
- notifyColorListeners(mHSVO);
- setupButton();
- invalidate((int) (ox - mDotRadius), (int) (oy - mDotRadius), (int) (ox + mDotRadius),
- (int) (oy + mDotRadius));
- invalidate(
- (int) (mDotX - mDotRadius), (int) (mDotY - mDotRadius), (int) (mDotX + mDotRadius),
- (int) (mDotY + mDotRadius));
-
- return true;
- }
-
- private void setupButton() {
- float pos = mHSVO[3] * (mWidth - mBorder * 2);
- mDotX = pos + mBorder;
-
- int[] colors3 = new int[] {
- mSliderColor, mSliderColor, 0x66000000, 0 };
- RadialGradient g = new RadialGradient(mDotX, mDotY, mDotRadius, colors3, new float[] {
- 0, .3f, .31f, 1 }, Shader.TileMode.CLAMP);
- mDotPaint.setShader(g);
- }
-
- @Override
- protected void onSizeChanged(int w, int h, int oldw, int oldh) {
- mWidth = w;
- mHeight = h;
- mDotY = mHeight / 2;
- updatePaint();
- setupButton();
- }
-
- private void updatePaint() {
-
- int color2 = Color.HSVToColor(mHSVO);
- int color1 = color2 & 0xFFFFFF;
-
- Shader sg = new LinearGradient(
- mBorder, mBorder, mWidth - mBorder, mBorder, color1, color2, Shader.TileMode.CLAMP);
- mBarPaint1.setShader(sg);
-
- }
-
- @Override
- protected void onDraw(Canvas canvas) {
- super.onDraw(canvas);
- canvas.drawColor(mBgcolor);
- canvas.drawRect(mBorder, mBorder, mWidth - mBorder, mHeight - mBorder, mCheckPaint);
- canvas.drawRect(mBorder, mBorder, mWidth - mBorder, mHeight - mBorder, mBarPaint1);
- canvas.drawLine(mDotX, mDotY, mWidth - mBorder, mDotY, mLinePaint1);
- canvas.drawLine(mBorder, mDotY, mDotX, mDotY, mLinePaint2);
- if (mDotX != Float.NaN) {
- canvas.drawCircle(mDotX, mDotY, mDotRadius, mDotPaint);
- }
- }
-
- @Override
- public void setColor(float[] hsv) {
- System.arraycopy(hsv, 0, mHSVO, 0, mHSVO.length);
-
- float oy = mDotY;
-
- updatePaint();
- setupButton();
- invalidate();
- }
-
- ArrayList<ColorListener> mColorListeners = new ArrayList<ColorListener>();
-
- public void notifyColorListeners(float[] hsvo) {
- for (ColorListener l : mColorListeners) {
- l.setColor(hsvo);
- }
- }
-
- public void addColorListener(ColorListener l) {
- mColorListeners.add(l);
- }
-
- public void removeColorListener(ColorListener l) {
- mColorListeners.remove(l);
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/colorpicker/ColorPickerDialog.java b/src/com/android/gallery3d/filtershow/colorpicker/ColorPickerDialog.java
deleted file mode 100644
index 73a5c907c..000000000
--- a/src/com/android/gallery3d/filtershow/colorpicker/ColorPickerDialog.java
+++ /dev/null
@@ -1,123 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.colorpicker;
-
-import android.app.Dialog;
-import android.content.Context;
-import android.graphics.Color;
-import android.graphics.drawable.GradientDrawable;
-import android.view.View;
-import android.widget.Button;
-import android.widget.ToggleButton;
-
-import com.android.gallery3d.R;
-
-public class ColorPickerDialog extends Dialog implements ColorListener {
- ToggleButton mSelectedButton;
- GradientDrawable mSelectRect;
-
- float[] mHSVO = new float[4];
-
- public ColorPickerDialog(Context context, final ColorListener cl) {
- super(context);
-
- setContentView(R.layout.filtershow_color_picker);
- ColorValueView csv = (ColorValueView) findViewById(R.id.colorValueView);
- ColorRectView cwv = (ColorRectView) findViewById(R.id.colorRectView);
- ColorOpacityView cvv = (ColorOpacityView) findViewById(R.id.colorOpacityView);
- float[] hsvo = new float[] {
- 123, .9f, 1, 1 };
-
- mSelectRect = (GradientDrawable) getContext()
- .getResources().getDrawable(R.drawable.filtershow_color_picker_roundrect);
- Button selButton = (Button) findViewById(R.id.btnSelect);
- selButton.setCompoundDrawablesWithIntrinsicBounds(null, null, mSelectRect, null);
- Button sel = (Button) findViewById(R.id.btnSelect);
-
- sel.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- ColorPickerDialog.this.dismiss();
- if (cl != null) {
- cl.setColor(mHSVO);
- }
- }
- });
-
- cwv.setColor(hsvo);
- cvv.setColor(hsvo);
- csv.setColor(hsvo);
- csv.addColorListener(cwv);
- cwv.addColorListener(csv);
- csv.addColorListener(cvv);
- cwv.addColorListener(cvv);
- cvv.addColorListener(cwv);
- cvv.addColorListener(csv);
- cvv.addColorListener(this);
- csv.addColorListener(this);
- cwv.addColorListener(this);
-
- }
-
- void toggleClick(ToggleButton v, int[] buttons, boolean isChecked) {
- int id = v.getId();
- if (!isChecked) {
- mSelectedButton = null;
- return;
- }
- for (int i = 0; i < buttons.length; i++) {
- if (id != buttons[i]) {
- ToggleButton b = (ToggleButton) findViewById(buttons[i]);
- b.setChecked(false);
- }
- }
- mSelectedButton = v;
-
- float[] hsv = (float[]) v.getTag();
-
- ColorValueView csv = (ColorValueView) findViewById(R.id.colorValueView);
- ColorRectView cwv = (ColorRectView) findViewById(R.id.colorRectView);
- ColorOpacityView cvv = (ColorOpacityView) findViewById(R.id.colorOpacityView);
- cwv.setColor(hsv);
- cvv.setColor(hsv);
- csv.setColor(hsv);
- }
-
- @Override
- public void setColor(float[] hsvo) {
- System.arraycopy(hsvo, 0, mHSVO, 0, mHSVO.length);
- int color = Color.HSVToColor(hsvo);
- mSelectRect.setColor(color);
- setButtonColor(mSelectedButton, hsvo);
- }
-
- private void setButtonColor(ToggleButton button, float[] hsv) {
- if (button == null) {
- return;
- }
- int color = Color.HSVToColor(hsv);
- button.setBackgroundColor(color);
- float[] fg = new float[] {
- (hsv[0] + 180) % 360,
- hsv[1],
- (hsv[2] > .5f) ? .1f : .9f
- };
- button.setTextColor(Color.HSVToColor(fg));
- button.setTag(hsv);
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/colorpicker/ColorRectView.java b/src/com/android/gallery3d/filtershow/colorpicker/ColorRectView.java
deleted file mode 100644
index 07d7c7126..000000000
--- a/src/com/android/gallery3d/filtershow/colorpicker/ColorRectView.java
+++ /dev/null
@@ -1,225 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.colorpicker;
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.LinearGradient;
-import android.graphics.Paint;
-import android.graphics.RadialGradient;
-import android.graphics.RectF;
-import android.graphics.Shader;
-import android.graphics.SweepGradient;
-import android.util.AttributeSet;
-import android.util.DisplayMetrics;
-import android.view.MotionEvent;
-import android.view.View;
-
-import com.android.gallery3d.R;
-
-import java.util.ArrayList;
-
-public class ColorRectView extends View implements ColorListener {
- private float mDpToPix;
- private float mRadius = 80;
- private float mCtrY = 100;
- private Paint mWheelPaint1;
- private Paint mWheelPaint2;
- private Paint mWheelPaint3;
- private float mCtrX = 100;
- private Paint mDotPaint;
- private float mDotRadus;
- private float mBorder;
- private int mBgcolor = 0;
- private float mDotX = Float.NaN;
- private float mDotY;
- private int mSliderColor = 0xFF33B5E5;
- private float[] mHSVO = new float[4];
- private int[] mColors = new int[] {
- 0xFFFF0000,// red
- 0xFFFFFF00,// yellow
- 0xFF00FF00,// green
- 0xFF00FFFF,// cyan
- 0xFF0000FF,// blue
- 0xFFFF00FF,// magenta
- 0xFFFF0000,// red
- };
- private int mWidth;
- private int mHeight;
- public final static float DOT_SIZE = 20;
- public final static float BORDER_SIZE = 10;
-
- public ColorRectView(Context ctx, AttributeSet attrs) {
- super(ctx, attrs);
-
- DisplayMetrics metrics = ctx.getResources().getDisplayMetrics();
- mDpToPix = metrics.density;
- mDotRadus = DOT_SIZE * mDpToPix;
- mBorder = BORDER_SIZE * mDpToPix;
-
- mWheelPaint1 = new Paint();
- mWheelPaint2 = new Paint();
- mWheelPaint3 = new Paint();
- mDotPaint = new Paint();
-
- mDotPaint.setStyle(Paint.Style.FILL);
- mDotPaint.setColor(ctx.getResources().getColor(R.color.slider_dot_color));
- mSliderColor = ctx.getResources().getColor(R.color.slider_line_color);
- mWheelPaint1.setStyle(Paint.Style.FILL);
- mWheelPaint2.setStyle(Paint.Style.FILL);
- mWheelPaint3.setStyle(Paint.Style.FILL);
- }
-
- public boolean onDown(MotionEvent e) {
- return true;
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
-
- invalidate((int) (mDotX - mDotRadus), (int) (mDotY - mDotRadus), (int) (mDotX + mDotRadus),
- (int) (mDotY + mDotRadus));
- float x = event.getX();
- float y = event.getY();
-
- x = Math.max(Math.min(x, mWidth - mBorder), mBorder);
- y = Math.max(Math.min(y, mHeight - mBorder), mBorder);
- mDotX = x;
- mDotY = y;
- float sat = 1 - (mDotY - mBorder) / (mHeight - 2 * mBorder);
- if (sat > 1) {
- sat = 1;
- }
-
- double hue = Math.PI * 2 * (mDotX - mBorder) / (mHeight - 2 * mBorder);
- mHSVO[0] = ((float) Math.toDegrees(hue) + 360) % 360;
- mHSVO[1] = sat;
- notifyColorListeners(mHSVO);
- updateDotPaint();
- invalidate((int) (mDotX - mDotRadus), (int) (mDotY - mDotRadus), (int) (mDotX + mDotRadus),
- (int) (mDotY + mDotRadus));
-
- return true;
- }
-
- @Override
- protected void onSizeChanged(int w, int h, int oldw, int oldh) {
- mWidth = w;
- mHeight = h;
- mCtrY = h / 2f;
- mCtrX = w / 2f;
- mRadius = Math.min(mCtrY, mCtrX) - 2 * mBorder;
- setUpColorPanel();
- }
-
- private void setUpColorPanel() {
- float val = mHSVO[2];
- int v = 0xFF000000 | 0x10101 * (int) (val * 0xFF);
- int[] colors = new int[] {
- 0x0000000, v };
- int[] colors2 = new int[] {
- 0x0000000, 0xFF000000 };
- int[] wheelColor = new int[mColors.length];
- float[] hsv = new float[3];
- for (int i = 0; i < wheelColor.length; i++) {
- Color.colorToHSV(mColors[i], hsv);
- hsv[2] = mHSVO[2];
- wheelColor[i] = Color.HSVToColor(hsv);
- }
- updateDot();
- updateDotPaint();
- SweepGradient sg = new SweepGradient(mCtrX, mCtrY, wheelColor, null);
- LinearGradient lg = new LinearGradient(
- mBorder, 0, mWidth - mBorder, 0, wheelColor, null, Shader.TileMode.CLAMP);
-
- mWheelPaint1.setShader(lg);
- LinearGradient rg = new LinearGradient(
- 0, mBorder, 0, mHeight - mBorder, colors, null, Shader.TileMode.CLAMP);
- mWheelPaint2.setShader(rg);
- LinearGradient rg2 = new LinearGradient(
- 0, mBorder, 0, mHeight - mBorder, colors2, null, Shader.TileMode.CLAMP);
- mWheelPaint3.setShader(rg2);
- }
-
- @Override
- protected void onDraw(Canvas canvas) {
- super.onDraw(canvas);
- canvas.drawColor(mBgcolor);
- RectF rect = new RectF();
- rect.left = mBorder;
- rect.right = mWidth - mBorder;
- rect.top = mBorder;
- rect.bottom = mHeight - mBorder;
-
- canvas.drawRect(rect, mWheelPaint1);
- canvas.drawRect(rect, mWheelPaint3);
- canvas.drawRect(rect, mWheelPaint2);
-
- if (mDotX != Float.NaN) {
-
- canvas.drawCircle(mDotX, mDotY, mDotRadus, mDotPaint);
- }
- }
-
- private void updateDot() {
-
- double hue = mHSVO[0];
- double sat = mHSVO[1];
-
- mDotX = (float) (mBorder + (mHeight - 2 * mBorder) * Math.toRadians(hue) / (Math.PI * 2));
- mDotY = (float) ((1 - sat) * (mHeight - 2 * mBorder) + mBorder);
-
- }
-
- private void updateDotPaint() {
- int[] colors3 = new int[] {
- mSliderColor, mSliderColor, 0x66000000, 0 };
- RadialGradient g = new RadialGradient(mDotX, mDotY, mDotRadus, colors3, new float[] {
- 0, .3f, .31f, 1 }, Shader.TileMode.CLAMP);
- mDotPaint.setShader(g);
-
- }
-
- @Override
- public void setColor(float[] hsvo) {
- System.arraycopy(hsvo, 0, mHSVO, 0, mHSVO.length);
-
- setUpColorPanel();
- invalidate();
-
- updateDot();
- updateDotPaint();
-
- }
-
- ArrayList<ColorListener> mColorListeners = new ArrayList<ColorListener>();
-
- public void notifyColorListeners(float[] hsv) {
- for (ColorListener l : mColorListeners) {
- l.setColor(hsv);
- }
- }
-
- public void addColorListener(ColorListener l) {
- mColorListeners.add(l);
- }
-
- public void removeColorListener(ColorListener l) {
- mColorListeners.remove(l);
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/colorpicker/ColorValueView.java b/src/com/android/gallery3d/filtershow/colorpicker/ColorValueView.java
deleted file mode 100644
index 13cb44bad..000000000
--- a/src/com/android/gallery3d/filtershow/colorpicker/ColorValueView.java
+++ /dev/null
@@ -1,180 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.colorpicker;
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.LinearGradient;
-import android.graphics.Paint;
-import android.graphics.RadialGradient;
-import android.graphics.Shader;
-import android.util.AttributeSet;
-import android.util.DisplayMetrics;
-import android.view.MotionEvent;
-import android.view.View;
-
-import com.android.gallery3d.R;
-
-import java.util.ArrayList;
-
-public class ColorValueView extends View implements ColorListener {
-
- private float mRadius;
- private float mWidth;
- private Paint mBarPaint1;
- private Paint mLinePaint1;
- private Paint mLinePaint2;
- private float mHeight;
- private int mBgcolor = 0;
- private Paint mDotPaint;
- private float dotRadus;
- private float mBorder;
-
- private float[] mHSVO = new float[4];
- private int mSliderColor;
- private float mDotX;
- private float mDotY = mBorder;
- private final static float DOT_SIZE = ColorRectView.DOT_SIZE;
- private final static float BORDER_SIZE = ColorRectView.DOT_SIZE;
-
- public ColorValueView(Context ctx, AttributeSet attrs) {
- super(ctx, attrs);
- DisplayMetrics metrics = ctx.getResources().getDisplayMetrics();
- float mDpToPix = metrics.density;
- dotRadus = DOT_SIZE * mDpToPix;
- mBorder = BORDER_SIZE * mDpToPix;
-
- mBarPaint1 = new Paint();
-
- mDotPaint = new Paint();
-
- mDotPaint.setStyle(Paint.Style.FILL);
- mDotPaint.setColor(ctx.getResources().getColor(R.color.slider_dot_color));
-
- mBarPaint1.setStyle(Paint.Style.FILL);
-
- mLinePaint1 = new Paint();
- mLinePaint1.setColor(Color.GRAY);
- mLinePaint2 = new Paint();
- mSliderColor = ctx.getResources().getColor(R.color.slider_line_color);
- mLinePaint2.setColor(mSliderColor);
- mLinePaint2.setStrokeWidth(4);
- }
-
- public boolean onDown(MotionEvent e) {
- return true;
- }
-
- public boolean onTouchEvent(MotionEvent event) {
- float ox = mDotX;
- float oy = mDotY;
-
- float x = event.getX();
- float y = event.getY();
-
- mDotY = y;
-
- if (mDotY < mBorder) {
- mDotY = mBorder;
- }
-
- if (mDotY > mHeight - mBorder) {
- mDotY = mHeight - mBorder;
- }
- mHSVO[2] = (mDotY - mBorder) / (mHeight - mBorder * 2);
- notifyColorListeners(mHSVO);
- setupButton();
- invalidate((int) (ox - dotRadus), (int) (oy - dotRadus), (int) (ox + dotRadus),
- (int) (oy + dotRadus));
- invalidate((int) (mDotX - dotRadus), (int) (mDotY - dotRadus), (int) (mDotX + dotRadus),
- (int) (mDotY + dotRadus));
-
- return true;
- }
-
- private void setupButton() {
- float pos = mHSVO[2] * (mHeight - mBorder * 2);
- mDotY = pos + mBorder;
-
- int[] colors3 = new int[] {
- mSliderColor, mSliderColor, 0x66000000, 0 };
- RadialGradient g = new RadialGradient(mDotX, mDotY, dotRadus, colors3, new float[] {
- 0, .3f, .31f, 1 }, Shader.TileMode.CLAMP);
- mDotPaint.setShader(g);
- }
-
- @Override
- protected void onSizeChanged(int w, int h, int oldw, int oldh) {
- mWidth = w;
- mHeight = h;
- mDotX = mWidth / 2;
- updatePaint();
- setupButton();
- }
-
- private void updatePaint() {
- float[] hsv = new float[] {
- mHSVO[0], mHSVO[1], 0f };
- int color1 = Color.HSVToColor(hsv);
- hsv[2] = 1;
- int color2 = Color.HSVToColor(hsv);
-
- Shader sg = new LinearGradient(mBorder, mBorder, mBorder, mHeight - mBorder, color1, color2,
- Shader.TileMode.CLAMP);
- mBarPaint1.setShader(sg);
- }
-
- @Override
- protected void onDraw(Canvas canvas) {
- super.onDraw(canvas);
- canvas.drawColor(mBgcolor);
- canvas.drawRect(mBorder, mBorder, mWidth - mBorder, mHeight - mBorder, mBarPaint1);
- canvas.drawLine(mDotX, mDotY, mDotX, mHeight - mBorder, mLinePaint2);
- canvas.drawLine(mDotX, mBorder, mDotX, mDotY, mLinePaint1);
- if (mDotX != Float.NaN) {
- canvas.drawCircle(mDotX, mDotY, dotRadus, mDotPaint);
- }
- }
-
- @Override
- public void setColor(float[] hsvo) {
- System.arraycopy(hsvo, 0, mHSVO, 0, mHSVO.length);
-
- float oy = mDotY;
- updatePaint();
- setupButton();
- invalidate();
-
- }
-
- ArrayList<ColorListener> mColorListeners = new ArrayList<ColorListener>();
-
- public void notifyColorListeners(float[] hsv) {
- for (ColorListener l : mColorListeners) {
- l.setColor(hsv);
- }
- }
-
- public void addColorListener(ColorListener l) {
- mColorListeners.add(l);
- }
-
- public void removeColorListener(ColorListener l) {
- mColorListeners.remove(l);
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/colorpicker/RGBListener.java b/src/com/android/gallery3d/filtershow/colorpicker/RGBListener.java
deleted file mode 100644
index 147fb91a4..000000000
--- a/src/com/android/gallery3d/filtershow/colorpicker/RGBListener.java
+++ /dev/null
@@ -1,21 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.colorpicker;
-
-public interface RGBListener {
- void setColor(int hsv);
-}
diff --git a/src/com/android/gallery3d/filtershow/controller/ActionSlider.java b/src/com/android/gallery3d/filtershow/controller/ActionSlider.java
deleted file mode 100644
index f80a1cacb..000000000
--- a/src/com/android/gallery3d/filtershow/controller/ActionSlider.java
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.controller;
-
-import android.util.Log;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.view.ViewGroup;
-import android.widget.ImageButton;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.Editor;
-
-public class ActionSlider extends TitledSlider {
- private static final String LOGTAG = "ActionSlider";
- ImageButton mLeftButton;
- ImageButton mRightButton;
- public ActionSlider() {
- mLayoutID = R.layout.filtershow_control_action_slider;
- }
-
- @Override
- public void setUp(ViewGroup container, Parameter parameter, Editor editor) {
- super.setUp(container, parameter, editor);
- mLeftButton = (ImageButton) mTopView.findViewById(R.id.leftActionButton);
- mLeftButton.setOnClickListener(new OnClickListener() {
-
- @Override
- public void onClick(View v) {
- ((ParameterActionAndInt) mParameter).fireLeftAction();
- }
- });
-
- mRightButton = (ImageButton) mTopView.findViewById(R.id.rightActionButton);
- mRightButton.setOnClickListener(new OnClickListener() {
-
- @Override
- public void onClick(View v) {
- ((ParameterActionAndInt) mParameter).fireRightAction();
- }
- });
- updateUI();
- }
-
- @Override
- public void updateUI() {
- super.updateUI();
- if (mLeftButton != null) {
- int iconId = ((ParameterActionAndInt) mParameter).getLeftIcon();
- mLeftButton.setImageResource(iconId);
- }
- if (mRightButton != null) {
- int iconId = ((ParameterActionAndInt) mParameter).getRightIcon();
- mRightButton.setImageResource(iconId);
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/controller/BasicParameterInt.java b/src/com/android/gallery3d/filtershow/controller/BasicParameterInt.java
deleted file mode 100644
index 92145e9be..000000000
--- a/src/com/android/gallery3d/filtershow/controller/BasicParameterInt.java
+++ /dev/null
@@ -1,113 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.controller;
-
-import android.util.Log;
-
-public class BasicParameterInt implements ParameterInteger {
- protected String mParameterName;
- protected Control mControl;
- protected int mMaximum = 100;
- protected int mMinimum = 0;
- protected int mDefaultValue;
- protected int mValue;
- public final int ID;
- protected FilterView mEditor;
- private final String LOGTAG = "BasicParameterInt";
-
- @Override
- public void copyFrom(Parameter src) {
- if (!(src instanceof BasicParameterInt)) {
- throw new IllegalArgumentException(src.getClass().getName());
- }
- BasicParameterInt p = (BasicParameterInt) src;
- mMaximum = p.mMaximum;
- mMinimum = p.mMinimum;
- mDefaultValue = p.mDefaultValue;
- mValue = p.mValue;
- }
-
- public BasicParameterInt(int id, int value) {
- ID = id;
- mValue = value;
- }
-
- public BasicParameterInt(int id, int value, int min, int max) {
- ID = id;
- mValue = value;
- mMinimum = min;
- mMaximum = max;
- }
-
- @Override
- public String getParameterName() {
- return mParameterName;
- }
-
- @Override
- public String getParameterType() {
- return sParameterType;
- }
-
- @Override
- public String getValueString() {
- return mParameterName + mValue;
- }
-
- @Override
- public void setController(Control control) {
- mControl = control;
- }
-
- @Override
- public int getMaximum() {
- return mMaximum;
- }
-
- @Override
- public int getMinimum() {
- return mMinimum;
- }
-
- @Override
- public int getDefaultValue() {
- return mDefaultValue;
- }
-
- @Override
- public int getValue() {
- return mValue;
- }
-
- @Override
- public void setValue(int value) {
- mValue = value;
- if (mEditor != null) {
- mEditor.commitLocalRepresentation();
- }
- }
-
- @Override
- public String toString() {
- return getValueString();
- }
-
- @Override
- public void setFilterView(FilterView editor) {
- mEditor = editor;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/controller/BasicParameterStyle.java b/src/com/android/gallery3d/filtershow/controller/BasicParameterStyle.java
deleted file mode 100644
index fb9f95e97..000000000
--- a/src/com/android/gallery3d/filtershow/controller/BasicParameterStyle.java
+++ /dev/null
@@ -1,111 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.controller;
-
-import android.content.Context;
-
-import com.android.gallery3d.filtershow.pipeline.RenderingRequestCaller;
-
-public class BasicParameterStyle implements ParameterStyles {
- protected String mParameterName;
- protected int mSelectedStyle;
- protected int mNumberOfStyles;
- protected int mDefaultStyle = 0;
- protected Control mControl;
- protected FilterView mEditor;
- public final int ID;
- private final String LOGTAG = "BasicParameterStyle";
-
- @Override
- public void copyFrom(Parameter src) {
- if (!(src instanceof BasicParameterStyle)) {
- throw new IllegalArgumentException(src.getClass().getName());
- }
- BasicParameterStyle p = (BasicParameterStyle) src;
- mNumberOfStyles = p.mNumberOfStyles;
- mSelectedStyle = p.mSelectedStyle;
- mDefaultStyle = p.mDefaultStyle;
- }
-
- public BasicParameterStyle(int id, int numberOfStyles) {
- ID = id;
- mNumberOfStyles = numberOfStyles;
- }
-
- @Override
- public String getParameterName() {
- return mParameterName;
- }
-
- @Override
- public String getParameterType() {
- return sParameterType;
- }
-
- @Override
- public String getValueString() {
- return mParameterName + mSelectedStyle;
- }
-
- @Override
- public void setController(Control control) {
- mControl = control;
- }
-
- @Override
- public int getNumberOfStyles() {
- return mNumberOfStyles;
- }
-
- @Override
- public int getDefaultSelected() {
- return mDefaultStyle;
- }
-
- @Override
- public int getSelected() {
- return mSelectedStyle;
- }
-
- @Override
- public void setSelected(int selectedStyle) {
- mSelectedStyle = selectedStyle;
- if (mEditor != null) {
- mEditor.commitLocalRepresentation();
- }
- }
-
- @Override
- public void getIcon(int index, RenderingRequestCaller caller) {
- mEditor.computeIcon(index, caller);
- }
-
- @Override
- public String getStyleTitle(int index, Context context) {
- return "";
- }
-
- @Override
- public String toString() {
- return getValueString();
- }
-
- @Override
- public void setFilterView(FilterView editor) {
- mEditor = editor;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/controller/BasicSlider.java b/src/com/android/gallery3d/filtershow/controller/BasicSlider.java
deleted file mode 100644
index 9d8278d52..000000000
--- a/src/com/android/gallery3d/filtershow/controller/BasicSlider.java
+++ /dev/null
@@ -1,87 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.controller;
-
-import android.content.Context;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.LinearLayout;
-import android.widget.SeekBar;
-import android.widget.SeekBar.OnSeekBarChangeListener;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.Editor;
-
-public class BasicSlider implements Control {
- private SeekBar mSeekBar;
- private ParameterInteger mParameter;
- Editor mEditor;
-
- @Override
- public void setUp(ViewGroup container, Parameter parameter, Editor editor) {
- container.removeAllViews();
- mEditor = editor;
- Context context = container.getContext();
- mParameter = (ParameterInteger) parameter;
- LayoutInflater inflater =
- (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
- LinearLayout lp = (LinearLayout) inflater.inflate(
- R.layout.filtershow_seekbar, container, true);
- mSeekBar = (SeekBar) lp.findViewById(R.id.primarySeekBar);
-
- updateUI();
- mSeekBar.setOnSeekBarChangeListener(new OnSeekBarChangeListener() {
-
- @Override
- public void onStopTrackingTouch(SeekBar seekBar) {
- }
-
- @Override
- public void onStartTrackingTouch(SeekBar seekBar) {
- }
-
- @Override
- public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
- if (mParameter != null) {
- mParameter.setValue(progress + mParameter.getMinimum());
- mEditor.commitLocalRepresentation();
-
- }
- }
- });
- }
-
- @Override
- public View getTopView() {
- return mSeekBar;
- }
-
- @Override
- public void setPrameter(Parameter parameter) {
- mParameter = (ParameterInteger) parameter;
- if (mSeekBar != null) {
- updateUI();
- }
- }
-
- @Override
- public void updateUI() {
- mSeekBar.setMax(mParameter.getMaximum() - mParameter.getMinimum());
- mSeekBar.setProgress(mParameter.getValue() - mParameter.getMinimum());
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/controller/Control.java b/src/com/android/gallery3d/filtershow/controller/Control.java
deleted file mode 100644
index 43422904c..000000000
--- a/src/com/android/gallery3d/filtershow/controller/Control.java
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.controller;
-
-import android.view.View;
-import android.view.ViewGroup;
-
-import com.android.gallery3d.filtershow.editors.Editor;
-
-public interface Control {
- public void setUp(ViewGroup container, Parameter parameter, Editor editor);
-
- public View getTopView();
-
- public void setPrameter(Parameter parameter);
-
- public void updateUI();
-}
diff --git a/src/com/android/gallery3d/filtershow/controller/FilterView.java b/src/com/android/gallery3d/filtershow/controller/FilterView.java
deleted file mode 100644
index 9ca81dc35..000000000
--- a/src/com/android/gallery3d/filtershow/controller/FilterView.java
+++ /dev/null
@@ -1,25 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.controller;
-
-import com.android.gallery3d.filtershow.pipeline.RenderingRequestCaller;
-
-public interface FilterView {
- public void computeIcon(int index, RenderingRequestCaller caller);
-
- public void commitLocalRepresentation();
-}
diff --git a/src/com/android/gallery3d/filtershow/controller/Parameter.java b/src/com/android/gallery3d/filtershow/controller/Parameter.java
deleted file mode 100644
index 8f4d5c0a5..000000000
--- a/src/com/android/gallery3d/filtershow/controller/Parameter.java
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.controller;
-
-import com.android.gallery3d.filtershow.editors.Editor;
-
-public interface Parameter {
- String getParameterName();
-
- String getParameterType();
-
- String getValueString();
-
- public void setController(Control c);
-
- public void setFilterView(FilterView editor);
-
- public void copyFrom(Parameter src);
-}
diff --git a/src/com/android/gallery3d/filtershow/controller/ParameterActionAndInt.java b/src/com/android/gallery3d/filtershow/controller/ParameterActionAndInt.java
deleted file mode 100644
index 8a05c3aa6..000000000
--- a/src/com/android/gallery3d/filtershow/controller/ParameterActionAndInt.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.controller;
-
-public interface ParameterActionAndInt extends ParameterInteger {
- static String sParameterType = "ParameterActionAndInt";
-
- public void fireLeftAction();
-
- public int getLeftIcon();
-
- public void fireRightAction();
-
- public int getRightIcon();
-}
diff --git a/src/com/android/gallery3d/filtershow/controller/ParameterInteger.java b/src/com/android/gallery3d/filtershow/controller/ParameterInteger.java
deleted file mode 100644
index 0bfd20135..000000000
--- a/src/com/android/gallery3d/filtershow/controller/ParameterInteger.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.controller;
-
-public interface ParameterInteger extends Parameter {
- static String sParameterType = "ParameterInteger";
-
- int getMaximum();
-
- int getMinimum();
-
- int getDefaultValue();
-
- int getValue();
-
- void setValue(int value);
-}
diff --git a/src/com/android/gallery3d/filtershow/controller/ParameterSet.java b/src/com/android/gallery3d/filtershow/controller/ParameterSet.java
deleted file mode 100644
index 6b50a4d0b..000000000
--- a/src/com/android/gallery3d/filtershow/controller/ParameterSet.java
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.controller;
-
-public interface ParameterSet {
- int getNumberOfParameters();
-
- Parameter getFilterParameter(int index);
-}
diff --git a/src/com/android/gallery3d/filtershow/controller/ParameterStyles.java b/src/com/android/gallery3d/filtershow/controller/ParameterStyles.java
deleted file mode 100644
index 7d250a0bf..000000000
--- a/src/com/android/gallery3d/filtershow/controller/ParameterStyles.java
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.controller;
-
-import android.content.Context;
-
-import com.android.gallery3d.filtershow.pipeline.RenderingRequestCaller;
-
-public interface ParameterStyles extends Parameter {
- public static String sParameterType = "ParameterStyles";
-
- int getNumberOfStyles();
-
- int getDefaultSelected();
-
- int getSelected();
-
- void setSelected(int value);
-
- void getIcon(int index, RenderingRequestCaller caller);
-
- String getStyleTitle(int index, Context context);
-}
diff --git a/src/com/android/gallery3d/filtershow/controller/StyleChooser.java b/src/com/android/gallery3d/filtershow/controller/StyleChooser.java
deleted file mode 100644
index fb613abc7..000000000
--- a/src/com/android/gallery3d/filtershow/controller/StyleChooser.java
+++ /dev/null
@@ -1,88 +0,0 @@
-package com.android.gallery3d.filtershow.controller;
-
-import android.app.ActionBar.LayoutParams;
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.ImageButton;
-import android.widget.ImageView.ScaleType;
-import android.widget.LinearLayout;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.pipeline.RenderingRequest;
-import com.android.gallery3d.filtershow.pipeline.RenderingRequestCaller;
-import com.android.gallery3d.filtershow.editors.Editor;
-
-import java.util.Vector;
-
-public class StyleChooser implements Control {
- private final String LOGTAG = "StyleChooser";
- protected ParameterStyles mParameter;
- protected LinearLayout mLinearLayout;
- protected Editor mEditor;
- private View mTopView;
- private Vector<ImageButton> mIconButton = new Vector<ImageButton>();
- protected int mLayoutID = R.layout.filtershow_control_style_chooser;
-
- @Override
- public void setUp(ViewGroup container, Parameter parameter, Editor editor) {
- container.removeAllViews();
- mEditor = editor;
- Context context = container.getContext();
- mParameter = (ParameterStyles) parameter;
- LayoutInflater inflater =
- (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
- mTopView = inflater.inflate(mLayoutID, container, true);
- mLinearLayout = (LinearLayout) mTopView.findViewById(R.id.listStyles);
- mTopView.setVisibility(View.VISIBLE);
- int n = mParameter.getNumberOfStyles();
- mIconButton.clear();
- LayoutParams lp = new LayoutParams(120, 120);
- for (int i = 0; i < n; i++) {
- final ImageButton button = new ImageButton(context);
- button.setScaleType(ScaleType.CENTER_CROP);
- button.setLayoutParams(lp);
- button.setBackgroundResource(android.R.color.transparent);
- mIconButton.add(button);
- final int buttonNo = i;
- button.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View arg0) {
- mParameter.setSelected(buttonNo);
- }
- });
- mLinearLayout.addView(button);
- mParameter.getIcon(i, new RenderingRequestCaller() {
- @Override
- public void available(RenderingRequest request) {
- Bitmap bmap = request.getBitmap();
- if (bmap == null) {
- return;
- }
- button.setImageBitmap(bmap);
- }
- });
- }
- }
-
- @Override
- public View getTopView() {
- return mTopView;
- }
-
- @Override
- public void setPrameter(Parameter parameter) {
- mParameter = (ParameterStyles) parameter;
- updateUI();
- }
-
- @Override
- public void updateUI() {
- if (mParameter == null) {
- return;
- }
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/controller/TitledSlider.java b/src/com/android/gallery3d/filtershow/controller/TitledSlider.java
deleted file mode 100644
index f29442bb9..000000000
--- a/src/com/android/gallery3d/filtershow/controller/TitledSlider.java
+++ /dev/null
@@ -1,106 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.controller;
-
-import android.content.Context;
-import android.util.Log;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.SeekBar;
-import android.widget.SeekBar.OnSeekBarChangeListener;
-import android.widget.TextView;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.Editor;
-
-public class TitledSlider implements Control {
- private final String LOGTAG = "ParametricEditor";
- private SeekBar mSeekBar;
- private TextView mControlName;
- private TextView mControlValue;
- protected ParameterInteger mParameter;
- Editor mEditor;
- View mTopView;
- protected int mLayoutID = R.layout.filtershow_control_title_slider;
-
- @Override
- public void setUp(ViewGroup container, Parameter parameter, Editor editor) {
- container.removeAllViews();
- mEditor = editor;
- Context context = container.getContext();
- mParameter = (ParameterInteger) parameter;
- LayoutInflater inflater =
- (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
- mTopView = inflater.inflate(mLayoutID, container, true);
- mTopView.setVisibility(View.VISIBLE);
- mSeekBar = (SeekBar) mTopView.findViewById(R.id.controlValueSeekBar);
- mControlName = (TextView) mTopView.findViewById(R.id.controlName);
- mControlValue = (TextView) mTopView.findViewById(R.id.controlValue);
- updateUI();
- mSeekBar.setOnSeekBarChangeListener(new OnSeekBarChangeListener() {
-
- @Override
- public void onStopTrackingTouch(SeekBar seekBar) {
- }
-
- @Override
- public void onStartTrackingTouch(SeekBar seekBar) {
- }
-
- @Override
- public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
- if (mParameter != null) {
- mParameter.setValue(progress + mParameter.getMinimum());
- if (mControlName != null) {
- mControlName.setText(mParameter.getParameterName());
- }
- if (mControlValue != null) {
- mControlValue.setText(Integer.toString(mParameter.getValue()));
- }
- mEditor.commitLocalRepresentation();
- }
- }
- });
- }
-
- @Override
- public void setPrameter(Parameter parameter) {
- mParameter = (ParameterInteger) parameter;
- if (mSeekBar != null)
- updateUI();
- }
-
- @Override
- public void updateUI() {
- if (mControlName != null && mParameter.getParameterName() != null) {
- mControlName.setText(mParameter.getParameterName().toUpperCase());
- }
- if (mControlValue != null) {
- mControlValue.setText(
- Integer.toString(mParameter.getValue()));
- }
- mSeekBar.setMax(mParameter.getMaximum() - mParameter.getMinimum());
- mSeekBar.setProgress(mParameter.getValue() - mParameter.getMinimum());
- mEditor.commitLocalRepresentation();
- }
-
- @Override
- public View getTopView() {
- return mTopView;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/crop/BoundedRect.java b/src/com/android/gallery3d/filtershow/crop/BoundedRect.java
deleted file mode 100644
index 13b8d6de1..000000000
--- a/src/com/android/gallery3d/filtershow/crop/BoundedRect.java
+++ /dev/null
@@ -1,368 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.filtershow.crop;
-
-import android.graphics.Matrix;
-import android.graphics.Rect;
-import android.graphics.RectF;
-
-import com.android.gallery3d.filtershow.imageshow.GeometryMathUtils;
-
-import java.util.Arrays;
-
-/**
- * Maintains invariant that inner rectangle is constrained to be within the
- * outer, rotated rectangle.
- */
-public class BoundedRect {
- private float rot;
- private RectF outer;
- private RectF inner;
- private float[] innerRotated;
-
- public BoundedRect(float rotation, Rect outerRect, Rect innerRect) {
- rot = rotation;
- outer = new RectF(outerRect);
- inner = new RectF(innerRect);
- innerRotated = CropMath.getCornersFromRect(inner);
- rotateInner();
- if (!isConstrained())
- reconstrain();
- }
-
- public BoundedRect(float rotation, RectF outerRect, RectF innerRect) {
- rot = rotation;
- outer = new RectF(outerRect);
- inner = new RectF(innerRect);
- innerRotated = CropMath.getCornersFromRect(inner);
- rotateInner();
- if (!isConstrained())
- reconstrain();
- }
-
- public void resetTo(float rotation, RectF outerRect, RectF innerRect) {
- rot = rotation;
- outer.set(outerRect);
- inner.set(innerRect);
- innerRotated = CropMath.getCornersFromRect(inner);
- rotateInner();
- if (!isConstrained())
- reconstrain();
- }
-
- /**
- * Sets inner, and re-constrains it to fit within the rotated bounding rect.
- */
- public void setInner(RectF newInner) {
- if (inner.equals(newInner))
- return;
- inner = newInner;
- innerRotated = CropMath.getCornersFromRect(inner);
- rotateInner();
- if (!isConstrained())
- reconstrain();
- }
-
- /**
- * Sets rotation, and re-constrains inner to fit within the rotated bounding rect.
- */
- public void setRotation(float rotation) {
- if (rotation == rot)
- return;
- rot = rotation;
- innerRotated = CropMath.getCornersFromRect(inner);
- rotateInner();
- if (!isConstrained())
- reconstrain();
- }
-
- public void setToInner(RectF r) {
- r.set(inner);
- }
-
- public void setToOuter(RectF r) {
- r.set(outer);
- }
-
- public RectF getInner() {
- return new RectF(inner);
- }
-
- public RectF getOuter() {
- return new RectF(outer);
- }
-
- /**
- * Tries to move the inner rectangle by (dx, dy). If this would cause it to leave
- * the bounding rectangle, snaps the inner rectangle to the edge of the bounding
- * rectangle.
- */
- public void moveInner(float dx, float dy) {
- Matrix m0 = getInverseRotMatrix();
-
- RectF translatedInner = new RectF(inner);
- translatedInner.offset(dx, dy);
-
- float[] translatedInnerCorners = CropMath.getCornersFromRect(translatedInner);
- float[] outerCorners = CropMath.getCornersFromRect(outer);
-
- m0.mapPoints(translatedInnerCorners);
- float[] correction = {
- 0, 0
- };
-
- // find correction vectors for corners that have moved out of bounds
- for (int i = 0; i < translatedInnerCorners.length; i += 2) {
- float correctedInnerX = translatedInnerCorners[i] + correction[0];
- float correctedInnerY = translatedInnerCorners[i + 1] + correction[1];
- if (!CropMath.inclusiveContains(outer, correctedInnerX, correctedInnerY)) {
- float[] badCorner = {
- correctedInnerX, correctedInnerY
- };
- float[] nearestSide = CropMath.closestSide(badCorner, outerCorners);
- float[] correctionVec =
- GeometryMathUtils.shortestVectorFromPointToLine(badCorner, nearestSide);
- correction[0] += correctionVec[0];
- correction[1] += correctionVec[1];
- }
- }
-
- for (int i = 0; i < translatedInnerCorners.length; i += 2) {
- float correctedInnerX = translatedInnerCorners[i] + correction[0];
- float correctedInnerY = translatedInnerCorners[i + 1] + correction[1];
- if (!CropMath.inclusiveContains(outer, correctedInnerX, correctedInnerY)) {
- float[] correctionVec = {
- correctedInnerX, correctedInnerY
- };
- CropMath.getEdgePoints(outer, correctionVec);
- correctionVec[0] -= correctedInnerX;
- correctionVec[1] -= correctedInnerY;
- correction[0] += correctionVec[0];
- correction[1] += correctionVec[1];
- }
- }
-
- // Set correction
- for (int i = 0; i < translatedInnerCorners.length; i += 2) {
- float correctedInnerX = translatedInnerCorners[i] + correction[0];
- float correctedInnerY = translatedInnerCorners[i + 1] + correction[1];
- // update translated corners with correction vectors
- translatedInnerCorners[i] = correctedInnerX;
- translatedInnerCorners[i + 1] = correctedInnerY;
- }
-
- innerRotated = translatedInnerCorners;
- // reconstrain to update inner
- reconstrain();
- }
-
- /**
- * Attempts to resize the inner rectangle. If this would cause it to leave
- * the bounding rect, clips the inner rectangle to fit.
- */
- public void resizeInner(RectF newInner) {
- Matrix m = getRotMatrix();
- Matrix m0 = getInverseRotMatrix();
-
- float[] outerCorners = CropMath.getCornersFromRect(outer);
- m.mapPoints(outerCorners);
- float[] oldInnerCorners = CropMath.getCornersFromRect(inner);
- float[] newInnerCorners = CropMath.getCornersFromRect(newInner);
- RectF ret = new RectF(newInner);
-
- for (int i = 0; i < newInnerCorners.length; i += 2) {
- float[] c = {
- newInnerCorners[i], newInnerCorners[i + 1]
- };
- float[] c0 = Arrays.copyOf(c, 2);
- m0.mapPoints(c0);
- if (!CropMath.inclusiveContains(outer, c0[0], c0[1])) {
- float[] outerSide = CropMath.closestSide(c, outerCorners);
- float[] pathOfCorner = {
- newInnerCorners[i], newInnerCorners[i + 1],
- oldInnerCorners[i], oldInnerCorners[i + 1]
- };
- float[] p = GeometryMathUtils.lineIntersect(pathOfCorner, outerSide);
- if (p == null) {
- // lines are parallel or not well defined, so don't resize
- p = new float[2];
- p[0] = oldInnerCorners[i];
- p[1] = oldInnerCorners[i + 1];
- }
- // relies on corners being in same order as method
- // getCornersFromRect
- switch (i) {
- case 0:
- case 1:
- ret.left = (p[0] > ret.left) ? p[0] : ret.left;
- ret.top = (p[1] > ret.top) ? p[1] : ret.top;
- break;
- case 2:
- case 3:
- ret.right = (p[0] < ret.right) ? p[0] : ret.right;
- ret.top = (p[1] > ret.top) ? p[1] : ret.top;
- break;
- case 4:
- case 5:
- ret.right = (p[0] < ret.right) ? p[0] : ret.right;
- ret.bottom = (p[1] < ret.bottom) ? p[1] : ret.bottom;
- break;
- case 6:
- case 7:
- ret.left = (p[0] > ret.left) ? p[0] : ret.left;
- ret.bottom = (p[1] < ret.bottom) ? p[1] : ret.bottom;
- break;
- default:
- break;
- }
- }
- }
- float[] retCorners = CropMath.getCornersFromRect(ret);
- m0.mapPoints(retCorners);
- innerRotated = retCorners;
- // reconstrain to update inner
- reconstrain();
- }
-
- /**
- * Attempts to resize the inner rectangle. If this would cause it to leave
- * the bounding rect, clips the inner rectangle to fit while maintaining
- * aspect ratio.
- */
- public void fixedAspectResizeInner(RectF newInner) {
- Matrix m = getRotMatrix();
- Matrix m0 = getInverseRotMatrix();
-
- float aspectW = inner.width();
- float aspectH = inner.height();
- float aspRatio = aspectW / aspectH;
- float[] corners = CropMath.getCornersFromRect(outer);
-
- m.mapPoints(corners);
- float[] oldInnerCorners = CropMath.getCornersFromRect(inner);
- float[] newInnerCorners = CropMath.getCornersFromRect(newInner);
-
- // find fixed corner
- int fixed = -1;
- if (inner.top == newInner.top) {
- if (inner.left == newInner.left)
- fixed = 0; // top left
- else if (inner.right == newInner.right)
- fixed = 2; // top right
- } else if (inner.bottom == newInner.bottom) {
- if (inner.right == newInner.right)
- fixed = 4; // bottom right
- else if (inner.left == newInner.left)
- fixed = 6; // bottom left
- }
- // no fixed corner, return without update
- if (fixed == -1)
- return;
- float widthSoFar = newInner.width();
- int moved = -1;
- for (int i = 0; i < newInnerCorners.length; i += 2) {
- float[] c = {
- newInnerCorners[i], newInnerCorners[i + 1]
- };
- float[] c0 = Arrays.copyOf(c, 2);
- m0.mapPoints(c0);
- if (!CropMath.inclusiveContains(outer, c0[0], c0[1])) {
- moved = i;
- if (moved == fixed)
- continue;
- float[] l2 = CropMath.closestSide(c, corners);
- float[] l1 = {
- newInnerCorners[i], newInnerCorners[i + 1],
- oldInnerCorners[i], oldInnerCorners[i + 1]
- };
- float[] p = GeometryMathUtils.lineIntersect(l1, l2);
- if (p == null) {
- // lines are parallel or not well defined, so set to old
- // corner
- p = new float[2];
- p[0] = oldInnerCorners[i];
- p[1] = oldInnerCorners[i + 1];
- }
- // relies on corners being in same order as method
- // getCornersFromRect
- float fixed_x = oldInnerCorners[fixed];
- float fixed_y = oldInnerCorners[fixed + 1];
- float newWidth = Math.abs(fixed_x - p[0]);
- float newHeight = Math.abs(fixed_y - p[1]);
- newWidth = Math.max(newWidth, aspRatio * newHeight);
- if (newWidth < widthSoFar)
- widthSoFar = newWidth;
- }
- }
-
- float heightSoFar = widthSoFar / aspRatio;
- RectF ret = new RectF(inner);
- if (fixed == 0) {
- ret.right = ret.left + widthSoFar;
- ret.bottom = ret.top + heightSoFar;
- } else if (fixed == 2) {
- ret.left = ret.right - widthSoFar;
- ret.bottom = ret.top + heightSoFar;
- } else if (fixed == 4) {
- ret.left = ret.right - widthSoFar;
- ret.top = ret.bottom - heightSoFar;
- } else if (fixed == 6) {
- ret.right = ret.left + widthSoFar;
- ret.top = ret.bottom - heightSoFar;
- }
- float[] retCorners = CropMath.getCornersFromRect(ret);
- m0.mapPoints(retCorners);
- innerRotated = retCorners;
- // reconstrain to update inner
- reconstrain();
- }
-
- // internal methods
-
- private boolean isConstrained() {
- for (int i = 0; i < 8; i += 2) {
- if (!CropMath.inclusiveContains(outer, innerRotated[i], innerRotated[i + 1]))
- return false;
- }
- return true;
- }
-
- private void reconstrain() {
- // innerRotated has been changed to have incorrect values
- CropMath.getEdgePoints(outer, innerRotated);
- Matrix m = getRotMatrix();
- float[] unrotated = Arrays.copyOf(innerRotated, 8);
- m.mapPoints(unrotated);
- inner = CropMath.trapToRect(unrotated);
- }
-
- private void rotateInner() {
- Matrix m = getInverseRotMatrix();
- m.mapPoints(innerRotated);
- }
-
- private Matrix getRotMatrix() {
- Matrix m = new Matrix();
- m.setRotate(rot, outer.centerX(), outer.centerY());
- return m;
- }
-
- private Matrix getInverseRotMatrix() {
- Matrix m = new Matrix();
- m.setRotate(-rot, outer.centerX(), outer.centerY());
- return m;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/crop/CropActivity.java b/src/com/android/gallery3d/filtershow/crop/CropActivity.java
deleted file mode 100644
index 0a0c36703..000000000
--- a/src/com/android/gallery3d/filtershow/crop/CropActivity.java
+++ /dev/null
@@ -1,697 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.crop;
-
-import android.app.ActionBar;
-import android.app.Activity;
-import android.app.WallpaperManager;
-import android.content.Context;
-import android.content.Intent;
-import android.content.res.Configuration;
-import android.graphics.Bitmap;
-import android.graphics.Bitmap.CompressFormat;
-import android.graphics.BitmapFactory;
-import android.graphics.BitmapRegionDecoder;
-import android.graphics.Canvas;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.net.Uri;
-import android.os.AsyncTask;
-import android.os.Bundle;
-import android.provider.MediaStore;
-import android.util.DisplayMetrics;
-import android.util.Log;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.view.WindowManager;
-import android.widget.Toast;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.filtershow.cache.ImageLoader;
-import com.android.gallery3d.filtershow.tools.SaveImage;
-
-import java.io.ByteArrayInputStream;
-import java.io.ByteArrayOutputStream;
-import java.io.FileNotFoundException;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.OutputStream;
-
-/**
- * Activity for cropping an image.
- */
-public class CropActivity extends Activity {
- private static final String LOGTAG = "CropActivity";
- public static final String CROP_ACTION = "com.android.camera.action.CROP";
- private CropExtras mCropExtras = null;
- private LoadBitmapTask mLoadBitmapTask = null;
-
- private int mOutputX = 0;
- private int mOutputY = 0;
- private Bitmap mOriginalBitmap = null;
- private RectF mOriginalBounds = null;
- private int mOriginalRotation = 0;
- private Uri mSourceUri = null;
- private CropView mCropView = null;
- private View mSaveButton = null;
- private boolean finalIOGuard = false;
-
- private static final int SELECT_PICTURE = 1; // request code for picker
-
- private static final int DEFAULT_COMPRESS_QUALITY = 90;
- /**
- * The maximum bitmap size we allow to be returned through the intent.
- * Intents have a maximum of 1MB in total size. However, the Bitmap seems to
- * have some overhead to hit so that we go way below the limit here to make
- * sure the intent stays below 1MB.We should consider just returning a byte
- * array instead of a Bitmap instance to avoid overhead.
- */
- public static final int MAX_BMAP_IN_INTENT = 750000;
-
- // Flags
- private static final int DO_SET_WALLPAPER = 1;
- private static final int DO_RETURN_DATA = 1 << 1;
- private static final int DO_EXTRA_OUTPUT = 1 << 2;
-
- private static final int FLAG_CHECK = DO_SET_WALLPAPER | DO_RETURN_DATA | DO_EXTRA_OUTPUT;
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- Intent intent = getIntent();
- setResult(RESULT_CANCELED, new Intent());
- mCropExtras = getExtrasFromIntent(intent);
- if (mCropExtras != null && mCropExtras.getShowWhenLocked()) {
- getWindow().addFlags(WindowManager.LayoutParams.FLAG_SHOW_WHEN_LOCKED);
- }
-
- setContentView(R.layout.crop_activity);
- mCropView = (CropView) findViewById(R.id.cropView);
-
- ActionBar actionBar = getActionBar();
- actionBar.setDisplayOptions(ActionBar.DISPLAY_SHOW_CUSTOM);
- actionBar.setCustomView(R.layout.filtershow_actionbar);
-
- View mSaveButton = actionBar.getCustomView();
- mSaveButton.setOnClickListener(new OnClickListener() {
- @Override
- public void onClick(View view) {
- startFinishOutput();
- }
- });
-
- if (intent.getData() != null) {
- mSourceUri = intent.getData();
- startLoadBitmap(mSourceUri);
- } else {
- pickImage();
- }
- }
-
- private void enableSave(boolean enable) {
- if (mSaveButton != null) {
- mSaveButton.setEnabled(enable);
- }
- }
-
- @Override
- protected void onDestroy() {
- if (mLoadBitmapTask != null) {
- mLoadBitmapTask.cancel(false);
- }
- super.onDestroy();
- }
-
- @Override
- public void onConfigurationChanged (Configuration newConfig) {
- super.onConfigurationChanged(newConfig);
- mCropView.configChanged();
- }
-
- /**
- * Opens a selector in Gallery to chose an image for use when none was given
- * in the CROP intent.
- */
- private void pickImage() {
- Intent intent = new Intent();
- intent.setType("image/*");
- intent.setAction(Intent.ACTION_GET_CONTENT);
- startActivityForResult(Intent.createChooser(intent, getString(R.string.select_image)),
- SELECT_PICTURE);
- }
-
- /**
- * Callback for pickImage().
- */
- @Override
- public void onActivityResult(int requestCode, int resultCode, Intent data) {
- if (resultCode == RESULT_OK && requestCode == SELECT_PICTURE) {
- mSourceUri = data.getData();
- startLoadBitmap(mSourceUri);
- }
- }
-
- /**
- * Gets screen size metric.
- */
- private int getScreenImageSize() {
- DisplayMetrics outMetrics = new DisplayMetrics();
- getWindowManager().getDefaultDisplay().getMetrics(outMetrics);
- return (int) Math.max(outMetrics.heightPixels, outMetrics.widthPixels);
- }
-
- /**
- * Method that loads a bitmap in an async task.
- */
- private void startLoadBitmap(Uri uri) {
- if (uri != null) {
- enableSave(false);
- final View loading = findViewById(R.id.loading);
- loading.setVisibility(View.VISIBLE);
- mLoadBitmapTask = new LoadBitmapTask();
- mLoadBitmapTask.execute(uri);
- } else {
- cannotLoadImage();
- done();
- }
- }
-
- /**
- * Method called on UI thread with loaded bitmap.
- */
- private void doneLoadBitmap(Bitmap bitmap, RectF bounds, int orientation) {
- final View loading = findViewById(R.id.loading);
- loading.setVisibility(View.GONE);
- mOriginalBitmap = bitmap;
- mOriginalBounds = bounds;
- mOriginalRotation = orientation;
- if (bitmap != null && bitmap.getWidth() != 0 && bitmap.getHeight() != 0) {
- RectF imgBounds = new RectF(0, 0, bitmap.getWidth(), bitmap.getHeight());
- mCropView.initialize(bitmap, imgBounds, imgBounds, orientation);
- if (mCropExtras != null) {
- int aspectX = mCropExtras.getAspectX();
- int aspectY = mCropExtras.getAspectY();
- mOutputX = mCropExtras.getOutputX();
- mOutputY = mCropExtras.getOutputY();
- if (mOutputX > 0 && mOutputY > 0) {
- mCropView.applyAspect(mOutputX, mOutputY);
-
- }
- float spotX = mCropExtras.getSpotlightX();
- float spotY = mCropExtras.getSpotlightY();
- if (spotX > 0 && spotY > 0) {
- mCropView.setWallpaperSpotlight(spotX, spotY);
- }
- if (aspectX > 0 && aspectY > 0) {
- mCropView.applyAspect(aspectX, aspectY);
- }
- }
- enableSave(true);
- } else {
- Log.w(LOGTAG, "could not load image for cropping");
- cannotLoadImage();
- setResult(RESULT_CANCELED, new Intent());
- done();
- }
- }
-
- /**
- * Display toast for image loading failure.
- */
- private void cannotLoadImage() {
- CharSequence text = getString(R.string.cannot_load_image);
- Toast toast = Toast.makeText(this, text, Toast.LENGTH_SHORT);
- toast.show();
- }
-
- /**
- * AsyncTask for loading a bitmap into memory.
- *
- * @see #startLoadBitmap(Uri)
- * @see #doneLoadBitmap(Bitmap)
- */
- private class LoadBitmapTask extends AsyncTask<Uri, Void, Bitmap> {
- int mBitmapSize;
- Context mContext;
- Rect mOriginalBounds;
- int mOrientation;
-
- public LoadBitmapTask() {
- mBitmapSize = getScreenImageSize();
- mContext = getApplicationContext();
- mOriginalBounds = new Rect();
- mOrientation = 0;
- }
-
- @Override
- protected Bitmap doInBackground(Uri... params) {
- Uri uri = params[0];
- Bitmap bmap = ImageLoader.loadConstrainedBitmap(uri, mContext, mBitmapSize,
- mOriginalBounds, false);
- mOrientation = ImageLoader.getMetadataRotation(mContext, uri);
- return bmap;
- }
-
- @Override
- protected void onPostExecute(Bitmap result) {
- doneLoadBitmap(result, new RectF(mOriginalBounds), mOrientation);
- }
- }
-
- private void startFinishOutput() {
- if (finalIOGuard) {
- return;
- } else {
- finalIOGuard = true;
- }
- enableSave(false);
- Uri destinationUri = null;
- int flags = 0;
- if (mOriginalBitmap != null && mCropExtras != null) {
- if (mCropExtras.getExtraOutput() != null) {
- destinationUri = mCropExtras.getExtraOutput();
- if (destinationUri != null) {
- flags |= DO_EXTRA_OUTPUT;
- }
- }
- if (mCropExtras.getSetAsWallpaper()) {
- flags |= DO_SET_WALLPAPER;
- }
- if (mCropExtras.getReturnData()) {
- flags |= DO_RETURN_DATA;
- }
- }
- if (flags == 0) {
- destinationUri = SaveImage.makeAndInsertUri(this, mSourceUri);
- if (destinationUri != null) {
- flags |= DO_EXTRA_OUTPUT;
- }
- }
- if ((flags & FLAG_CHECK) != 0 && mOriginalBitmap != null) {
- RectF photo = new RectF(0, 0, mOriginalBitmap.getWidth(), mOriginalBitmap.getHeight());
- RectF crop = getBitmapCrop(photo);
- startBitmapIO(flags, mOriginalBitmap, mSourceUri, destinationUri, crop,
- photo, mOriginalBounds,
- (mCropExtras == null) ? null : mCropExtras.getOutputFormat(), mOriginalRotation);
- return;
- }
- setResult(RESULT_CANCELED, new Intent());
- done();
- return;
- }
-
- private void startBitmapIO(int flags, Bitmap currentBitmap, Uri sourceUri, Uri destUri,
- RectF cropBounds, RectF photoBounds, RectF currentBitmapBounds, String format,
- int rotation) {
- if (cropBounds == null || photoBounds == null || currentBitmap == null
- || currentBitmap.getWidth() == 0 || currentBitmap.getHeight() == 0
- || cropBounds.width() == 0 || cropBounds.height() == 0 || photoBounds.width() == 0
- || photoBounds.height() == 0) {
- return; // fail fast
- }
- if ((flags & FLAG_CHECK) == 0) {
- return; // no output options
- }
- if ((flags & DO_SET_WALLPAPER) != 0) {
- Toast.makeText(this, R.string.setting_wallpaper, Toast.LENGTH_LONG).show();
- }
-
- final View loading = findViewById(R.id.loading);
- loading.setVisibility(View.VISIBLE);
- BitmapIOTask ioTask = new BitmapIOTask(sourceUri, destUri, format, flags, cropBounds,
- photoBounds, currentBitmapBounds, rotation, mOutputX, mOutputY);
- ioTask.execute(currentBitmap);
- }
-
- private void doneBitmapIO(boolean success, Intent intent) {
- final View loading = findViewById(R.id.loading);
- loading.setVisibility(View.GONE);
- if (success) {
- setResult(RESULT_OK, intent);
- } else {
- setResult(RESULT_CANCELED, intent);
- }
- done();
- }
-
- private class BitmapIOTask extends AsyncTask<Bitmap, Void, Boolean> {
-
- private final WallpaperManager mWPManager;
- InputStream mInStream = null;
- OutputStream mOutStream = null;
- String mOutputFormat = null;
- Uri mOutUri = null;
- Uri mInUri = null;
- int mFlags = 0;
- RectF mCrop = null;
- RectF mPhoto = null;
- RectF mOrig = null;
- Intent mResultIntent = null;
- int mRotation = 0;
-
- // Helper to setup input stream
- private void regenerateInputStream() {
- if (mInUri == null) {
- Log.w(LOGTAG, "cannot read original file, no input URI given");
- } else {
- Utils.closeSilently(mInStream);
- try {
- mInStream = getContentResolver().openInputStream(mInUri);
- } catch (FileNotFoundException e) {
- Log.w(LOGTAG, "cannot read file: " + mInUri.toString(), e);
- }
- }
- }
-
- public BitmapIOTask(Uri sourceUri, Uri destUri, String outputFormat, int flags,
- RectF cropBounds, RectF photoBounds, RectF originalBitmapBounds, int rotation,
- int outputX, int outputY) {
- mOutputFormat = outputFormat;
- mOutStream = null;
- mOutUri = destUri;
- mInUri = sourceUri;
- mFlags = flags;
- mCrop = cropBounds;
- mPhoto = photoBounds;
- mOrig = originalBitmapBounds;
- mWPManager = WallpaperManager.getInstance(getApplicationContext());
- mResultIntent = new Intent();
- mRotation = (rotation < 0) ? -rotation : rotation;
- mRotation %= 360;
- mRotation = 90 * (int) (mRotation / 90); // now mRotation is a multiple of 90
- mOutputX = outputX;
- mOutputY = outputY;
-
- if ((flags & DO_EXTRA_OUTPUT) != 0) {
- if (mOutUri == null) {
- Log.w(LOGTAG, "cannot write file, no output URI given");
- } else {
- try {
- mOutStream = getContentResolver().openOutputStream(mOutUri);
- } catch (FileNotFoundException e) {
- Log.w(LOGTAG, "cannot write file: " + mOutUri.toString(), e);
- }
- }
- }
-
- if ((flags & (DO_EXTRA_OUTPUT | DO_SET_WALLPAPER)) != 0) {
- regenerateInputStream();
- }
- }
-
- @Override
- protected Boolean doInBackground(Bitmap... params) {
- boolean failure = false;
- Bitmap img = params[0];
-
- // Set extra for crop bounds
- if (mCrop != null && mPhoto != null && mOrig != null) {
- RectF trueCrop = CropMath.getScaledCropBounds(mCrop, mPhoto, mOrig);
- Matrix m = new Matrix();
- m.setRotate(mRotation);
- m.mapRect(trueCrop);
- if (trueCrop != null) {
- Rect rounded = new Rect();
- trueCrop.roundOut(rounded);
- mResultIntent.putExtra(CropExtras.KEY_CROPPED_RECT, rounded);
- }
- }
-
- // Find the small cropped bitmap that is returned in the intent
- if ((mFlags & DO_RETURN_DATA) != 0) {
- assert (img != null);
- Bitmap ret = getCroppedImage(img, mCrop, mPhoto);
- if (ret != null) {
- ret = getDownsampledBitmap(ret, MAX_BMAP_IN_INTENT);
- }
- if (ret == null) {
- Log.w(LOGTAG, "could not downsample bitmap to return in data");
- failure = true;
- } else {
- if (mRotation > 0) {
- Matrix m = new Matrix();
- m.setRotate(mRotation);
- Bitmap tmp = Bitmap.createBitmap(ret, 0, 0, ret.getWidth(),
- ret.getHeight(), m, true);
- if (tmp != null) {
- ret = tmp;
- }
- }
- mResultIntent.putExtra(CropExtras.KEY_DATA, ret);
- }
- }
-
- // Do the large cropped bitmap and/or set the wallpaper
- if ((mFlags & (DO_EXTRA_OUTPUT | DO_SET_WALLPAPER)) != 0 && mInStream != null) {
- // Find crop bounds (scaled to original image size)
- RectF trueCrop = CropMath.getScaledCropBounds(mCrop, mPhoto, mOrig);
- if (trueCrop == null) {
- Log.w(LOGTAG, "cannot find crop for full size image");
- failure = true;
- return false;
- }
- Rect roundedTrueCrop = new Rect();
- trueCrop.roundOut(roundedTrueCrop);
-
- if (roundedTrueCrop.width() <= 0 || roundedTrueCrop.height() <= 0) {
- Log.w(LOGTAG, "crop has bad values for full size image");
- failure = true;
- return false;
- }
-
- // Attempt to open a region decoder
- BitmapRegionDecoder decoder = null;
- try {
- decoder = BitmapRegionDecoder.newInstance(mInStream, true);
- } catch (IOException e) {
- Log.w(LOGTAG, "cannot open region decoder for file: " + mInUri.toString(), e);
- }
-
- Bitmap crop = null;
- if (decoder != null) {
- // Do region decoding to get crop bitmap
- BitmapFactory.Options options = new BitmapFactory.Options();
- options.inMutable = true;
- crop = decoder.decodeRegion(roundedTrueCrop, options);
- decoder.recycle();
- }
-
- if (crop == null) {
- // BitmapRegionDecoder has failed, try to crop in-memory
- regenerateInputStream();
- Bitmap fullSize = null;
- if (mInStream != null) {
- fullSize = BitmapFactory.decodeStream(mInStream);
- }
- if (fullSize != null) {
- crop = Bitmap.createBitmap(fullSize, roundedTrueCrop.left,
- roundedTrueCrop.top, roundedTrueCrop.width(),
- roundedTrueCrop.height());
- }
- }
-
- if (crop == null) {
- Log.w(LOGTAG, "cannot decode file: " + mInUri.toString());
- failure = true;
- return false;
- }
- if (mOutputX > 0 && mOutputY > 0) {
- Matrix m = new Matrix();
- RectF cropRect = new RectF(0, 0, crop.getWidth(), crop.getHeight());
- if (mRotation > 0) {
- m.setRotate(mRotation);
- m.mapRect(cropRect);
- }
- RectF returnRect = new RectF(0, 0, mOutputX, mOutputY);
- m.setRectToRect(cropRect, returnRect, Matrix.ScaleToFit.FILL);
- m.preRotate(mRotation);
- Bitmap tmp = Bitmap.createBitmap((int) returnRect.width(),
- (int) returnRect.height(), Bitmap.Config.ARGB_8888);
- if (tmp != null) {
- Canvas c = new Canvas(tmp);
- c.drawBitmap(crop, m, new Paint());
- crop = tmp;
- }
- } else if (mRotation > 0) {
- Matrix m = new Matrix();
- m.setRotate(mRotation);
- Bitmap tmp = Bitmap.createBitmap(crop, 0, 0, crop.getWidth(),
- crop.getHeight(), m, true);
- if (tmp != null) {
- crop = tmp;
- }
- }
- // Get output compression format
- CompressFormat cf =
- convertExtensionToCompressFormat(getFileExtension(mOutputFormat));
-
- // If we only need to output to a URI, compress straight to file
- if (mFlags == DO_EXTRA_OUTPUT) {
- if (mOutStream == null
- || !crop.compress(cf, DEFAULT_COMPRESS_QUALITY, mOutStream)) {
- Log.w(LOGTAG, "failed to compress bitmap to file: " + mOutUri.toString());
- failure = true;
- } else {
- mResultIntent.setData(mOutUri);
- }
- } else {
- // Compress to byte array
- ByteArrayOutputStream tmpOut = new ByteArrayOutputStream(2048);
- if (crop.compress(cf, DEFAULT_COMPRESS_QUALITY, tmpOut)) {
-
- // If we need to output to a Uri, write compressed
- // bitmap out
- if ((mFlags & DO_EXTRA_OUTPUT) != 0) {
- if (mOutStream == null) {
- Log.w(LOGTAG,
- "failed to compress bitmap to file: " + mOutUri.toString());
- failure = true;
- } else {
- try {
- mOutStream.write(tmpOut.toByteArray());
- mResultIntent.setData(mOutUri);
- } catch (IOException e) {
- Log.w(LOGTAG,
- "failed to compress bitmap to file: "
- + mOutUri.toString(), e);
- failure = true;
- }
- }
- }
-
- // If we need to set to the wallpaper, set it
- if ((mFlags & DO_SET_WALLPAPER) != 0 && mWPManager != null) {
- if (mWPManager == null) {
- Log.w(LOGTAG, "no wallpaper manager");
- failure = true;
- } else {
- try {
- mWPManager.setStream(new ByteArrayInputStream(tmpOut
- .toByteArray()));
- } catch (IOException e) {
- Log.w(LOGTAG, "cannot write stream to wallpaper", e);
- failure = true;
- }
- }
- }
- } else {
- Log.w(LOGTAG, "cannot compress bitmap");
- failure = true;
- }
- }
- }
- return !failure; // True if any of the operations failed
- }
-
- @Override
- protected void onPostExecute(Boolean result) {
- Utils.closeSilently(mOutStream);
- Utils.closeSilently(mInStream);
- doneBitmapIO(result.booleanValue(), mResultIntent);
- }
-
- }
-
- private void done() {
- finish();
- }
-
- protected static Bitmap getCroppedImage(Bitmap image, RectF cropBounds, RectF photoBounds) {
- RectF imageBounds = new RectF(0, 0, image.getWidth(), image.getHeight());
- RectF crop = CropMath.getScaledCropBounds(cropBounds, photoBounds, imageBounds);
- if (crop == null) {
- return null;
- }
- Rect intCrop = new Rect();
- crop.roundOut(intCrop);
- return Bitmap.createBitmap(image, intCrop.left, intCrop.top, intCrop.width(),
- intCrop.height());
- }
-
- protected static Bitmap getDownsampledBitmap(Bitmap image, int max_size) {
- if (image == null || image.getWidth() == 0 || image.getHeight() == 0 || max_size < 16) {
- throw new IllegalArgumentException("Bad argument to getDownsampledBitmap()");
- }
- int shifts = 0;
- int size = CropMath.getBitmapSize(image);
- while (size > max_size) {
- shifts++;
- size /= 4;
- }
- Bitmap ret = Bitmap.createScaledBitmap(image, image.getWidth() >> shifts,
- image.getHeight() >> shifts, true);
- if (ret == null) {
- return null;
- }
- // Handle edge case for rounding.
- if (CropMath.getBitmapSize(ret) > max_size) {
- return Bitmap.createScaledBitmap(ret, ret.getWidth() >> 1, ret.getHeight() >> 1, true);
- }
- return ret;
- }
-
- /**
- * Gets the crop extras from the intent, or null if none exist.
- */
- protected static CropExtras getExtrasFromIntent(Intent intent) {
- Bundle extras = intent.getExtras();
- if (extras != null) {
- return new CropExtras(extras.getInt(CropExtras.KEY_OUTPUT_X, 0),
- extras.getInt(CropExtras.KEY_OUTPUT_Y, 0),
- extras.getBoolean(CropExtras.KEY_SCALE, true) &&
- extras.getBoolean(CropExtras.KEY_SCALE_UP_IF_NEEDED, false),
- extras.getInt(CropExtras.KEY_ASPECT_X, 0),
- extras.getInt(CropExtras.KEY_ASPECT_Y, 0),
- extras.getBoolean(CropExtras.KEY_SET_AS_WALLPAPER, false),
- extras.getBoolean(CropExtras.KEY_RETURN_DATA, false),
- (Uri) extras.getParcelable(MediaStore.EXTRA_OUTPUT),
- extras.getString(CropExtras.KEY_OUTPUT_FORMAT),
- extras.getBoolean(CropExtras.KEY_SHOW_WHEN_LOCKED, false),
- extras.getFloat(CropExtras.KEY_SPOTLIGHT_X),
- extras.getFloat(CropExtras.KEY_SPOTLIGHT_Y));
- }
- return null;
- }
-
- protected static CompressFormat convertExtensionToCompressFormat(String extension) {
- return extension.equals("png") ? CompressFormat.PNG : CompressFormat.JPEG;
- }
-
- protected static String getFileExtension(String requestFormat) {
- String outputFormat = (requestFormat == null)
- ? "jpg"
- : requestFormat;
- outputFormat = outputFormat.toLowerCase();
- return (outputFormat.equals("png") || outputFormat.equals("gif"))
- ? "png" // We don't support gif compression.
- : "jpg";
- }
-
- private RectF getBitmapCrop(RectF imageBounds) {
- RectF crop = mCropView.getCrop();
- RectF photo = mCropView.getPhoto();
- if (crop == null || photo == null) {
- Log.w(LOGTAG, "could not get crop");
- return null;
- }
- RectF scaledCrop = CropMath.getScaledCropBounds(crop, photo, imageBounds);
- return scaledCrop;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/crop/CropDrawingUtils.java b/src/com/android/gallery3d/filtershow/crop/CropDrawingUtils.java
deleted file mode 100644
index b0d324cbb..000000000
--- a/src/com/android/gallery3d/filtershow/crop/CropDrawingUtils.java
+++ /dev/null
@@ -1,168 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.crop;
-
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.Path;
-import android.graphics.RectF;
-import android.graphics.Region;
-import android.graphics.drawable.Drawable;
-
-public abstract class CropDrawingUtils {
-
- public static void drawRuleOfThird(Canvas canvas, RectF bounds) {
- Paint p = new Paint();
- p.setStyle(Paint.Style.STROKE);
- p.setColor(Color.argb(128, 255, 255, 255));
- p.setStrokeWidth(2);
- float stepX = bounds.width() / 3.0f;
- float stepY = bounds.height() / 3.0f;
- float x = bounds.left + stepX;
- float y = bounds.top + stepY;
- for (int i = 0; i < 2; i++) {
- canvas.drawLine(x, bounds.top, x, bounds.bottom, p);
- x += stepX;
- }
- for (int j = 0; j < 2; j++) {
- canvas.drawLine(bounds.left, y, bounds.right, y, p);
- y += stepY;
- }
- }
-
- public static void drawCropRect(Canvas canvas, RectF bounds) {
- Paint p = new Paint();
- p.setStyle(Paint.Style.STROKE);
- p.setColor(Color.WHITE);
- p.setStrokeWidth(3);
- canvas.drawRect(bounds, p);
- }
-
- public static void drawIndicator(Canvas canvas, Drawable indicator, int indicatorSize,
- float centerX, float centerY) {
- int left = (int) centerX - indicatorSize / 2;
- int top = (int) centerY - indicatorSize / 2;
- indicator.setBounds(left, top, left + indicatorSize, top + indicatorSize);
- indicator.draw(canvas);
- }
-
- public static void drawIndicators(Canvas canvas, Drawable cropIndicator, int indicatorSize,
- RectF bounds, boolean fixedAspect, int selection) {
- boolean notMoving = (selection == CropObject.MOVE_NONE);
- if (fixedAspect) {
- if ((selection == CropObject.TOP_LEFT) || notMoving) {
- drawIndicator(canvas, cropIndicator, indicatorSize, bounds.left, bounds.top);
- }
- if ((selection == CropObject.TOP_RIGHT) || notMoving) {
- drawIndicator(canvas, cropIndicator, indicatorSize, bounds.right, bounds.top);
- }
- if ((selection == CropObject.BOTTOM_LEFT) || notMoving) {
- drawIndicator(canvas, cropIndicator, indicatorSize, bounds.left, bounds.bottom);
- }
- if ((selection == CropObject.BOTTOM_RIGHT) || notMoving) {
- drawIndicator(canvas, cropIndicator, indicatorSize, bounds.right, bounds.bottom);
- }
- } else {
- if (((selection & CropObject.MOVE_TOP) != 0) || notMoving) {
- drawIndicator(canvas, cropIndicator, indicatorSize, bounds.centerX(), bounds.top);
- }
- if (((selection & CropObject.MOVE_BOTTOM) != 0) || notMoving) {
- drawIndicator(canvas, cropIndicator, indicatorSize, bounds.centerX(), bounds.bottom);
- }
- if (((selection & CropObject.MOVE_LEFT) != 0) || notMoving) {
- drawIndicator(canvas, cropIndicator, indicatorSize, bounds.left, bounds.centerY());
- }
- if (((selection & CropObject.MOVE_RIGHT) != 0) || notMoving) {
- drawIndicator(canvas, cropIndicator, indicatorSize, bounds.right, bounds.centerY());
- }
- }
- }
-
- public static void drawWallpaperSelectionFrame(Canvas canvas, RectF cropBounds, float spotX,
- float spotY, Paint p, Paint shadowPaint) {
- float sx = cropBounds.width() * spotX;
- float sy = cropBounds.height() * spotY;
- float cx = cropBounds.centerX();
- float cy = cropBounds.centerY();
- RectF r1 = new RectF(cx - sx / 2, cy - sy / 2, cx + sx / 2, cy + sy / 2);
- float temp = sx;
- sx = sy;
- sy = temp;
- RectF r2 = new RectF(cx - sx / 2, cy - sy / 2, cx + sx / 2, cy + sy / 2);
- canvas.save();
- canvas.clipRect(cropBounds);
- canvas.clipRect(r1, Region.Op.DIFFERENCE);
- canvas.clipRect(r2, Region.Op.DIFFERENCE);
- canvas.drawPaint(shadowPaint);
- canvas.restore();
- Path path = new Path();
- path.moveTo(r1.left, r1.top);
- path.lineTo(r1.right, r1.top);
- path.moveTo(r1.left, r1.top);
- path.lineTo(r1.left, r1.bottom);
- path.moveTo(r1.left, r1.bottom);
- path.lineTo(r1.right, r1.bottom);
- path.moveTo(r1.right, r1.top);
- path.lineTo(r1.right, r1.bottom);
- path.moveTo(r2.left, r2.top);
- path.lineTo(r2.right, r2.top);
- path.moveTo(r2.right, r2.top);
- path.lineTo(r2.right, r2.bottom);
- path.moveTo(r2.left, r2.bottom);
- path.lineTo(r2.right, r2.bottom);
- path.moveTo(r2.left, r2.top);
- path.lineTo(r2.left, r2.bottom);
- canvas.drawPath(path, p);
- }
-
- public static void drawShadows(Canvas canvas, Paint p, RectF innerBounds, RectF outerBounds) {
- canvas.drawRect(outerBounds.left, outerBounds.top, innerBounds.right, innerBounds.top, p);
- canvas.drawRect(innerBounds.right, outerBounds.top, outerBounds.right, innerBounds.bottom,
- p);
- canvas.drawRect(innerBounds.left, innerBounds.bottom, outerBounds.right,
- outerBounds.bottom, p);
- canvas.drawRect(outerBounds.left, innerBounds.top, innerBounds.left, outerBounds.bottom, p);
- }
-
- public static Matrix getBitmapToDisplayMatrix(RectF imageBounds, RectF displayBounds) {
- Matrix m = new Matrix();
- CropDrawingUtils.setBitmapToDisplayMatrix(m, imageBounds, displayBounds);
- return m;
- }
-
- public static boolean setBitmapToDisplayMatrix(Matrix m, RectF imageBounds,
- RectF displayBounds) {
- m.reset();
- return m.setRectToRect(imageBounds, displayBounds, Matrix.ScaleToFit.CENTER);
- }
-
- public static boolean setImageToScreenMatrix(Matrix dst, RectF image,
- RectF screen, int rotation) {
- RectF rotatedImage = new RectF();
- dst.setRotate(rotation, image.centerX(), image.centerY());
- if (!dst.mapRect(rotatedImage, image)) {
- return false; // fails for rotations that are not multiples of 90
- // degrees
- }
- boolean rToR = dst.setRectToRect(rotatedImage, screen, Matrix.ScaleToFit.CENTER);
- boolean rot = dst.preRotate(rotation, image.centerX(), image.centerY());
- return rToR && rot;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/crop/CropExtras.java b/src/com/android/gallery3d/filtershow/crop/CropExtras.java
deleted file mode 100644
index 60fe9af53..000000000
--- a/src/com/android/gallery3d/filtershow/crop/CropExtras.java
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.crop;
-
-import android.net.Uri;
-
-public class CropExtras {
-
- public static final String KEY_CROPPED_RECT = "cropped-rect";
- public static final String KEY_OUTPUT_X = "outputX";
- public static final String KEY_OUTPUT_Y = "outputY";
- public static final String KEY_SCALE = "scale";
- public static final String KEY_SCALE_UP_IF_NEEDED = "scaleUpIfNeeded";
- public static final String KEY_ASPECT_X = "aspectX";
- public static final String KEY_ASPECT_Y = "aspectY";
- public static final String KEY_SET_AS_WALLPAPER = "set-as-wallpaper";
- public static final String KEY_RETURN_DATA = "return-data";
- public static final String KEY_DATA = "data";
- public static final String KEY_SPOTLIGHT_X = "spotlightX";
- public static final String KEY_SPOTLIGHT_Y = "spotlightY";
- public static final String KEY_SHOW_WHEN_LOCKED = "showWhenLocked";
- public static final String KEY_OUTPUT_FORMAT = "outputFormat";
-
- private int mOutputX = 0;
- private int mOutputY = 0;
- private boolean mScaleUp = true;
- private int mAspectX = 0;
- private int mAspectY = 0;
- private boolean mSetAsWallpaper = false;
- private boolean mReturnData = false;
- private Uri mExtraOutput = null;
- private String mOutputFormat = null;
- private boolean mShowWhenLocked = false;
- private float mSpotlightX = 0;
- private float mSpotlightY = 0;
-
- public CropExtras(int outputX, int outputY, boolean scaleUp, int aspectX, int aspectY,
- boolean setAsWallpaper, boolean returnData, Uri extraOutput, String outputFormat,
- boolean showWhenLocked, float spotlightX, float spotlightY) {
- mOutputX = outputX;
- mOutputY = outputY;
- mScaleUp = scaleUp;
- mAspectX = aspectX;
- mAspectY = aspectY;
- mSetAsWallpaper = setAsWallpaper;
- mReturnData = returnData;
- mExtraOutput = extraOutput;
- mOutputFormat = outputFormat;
- mShowWhenLocked = showWhenLocked;
- mSpotlightX = spotlightX;
- mSpotlightY = spotlightY;
- }
-
- public CropExtras(CropExtras c) {
- this(c.mOutputX, c.mOutputY, c.mScaleUp, c.mAspectX, c.mAspectY, c.mSetAsWallpaper,
- c.mReturnData, c.mExtraOutput, c.mOutputFormat, c.mShowWhenLocked,
- c.mSpotlightX, c.mSpotlightY);
- }
-
- public int getOutputX() {
- return mOutputX;
- }
-
- public int getOutputY() {
- return mOutputY;
- }
-
- public boolean getScaleUp() {
- return mScaleUp;
- }
-
- public int getAspectX() {
- return mAspectX;
- }
-
- public int getAspectY() {
- return mAspectY;
- }
-
- public boolean getSetAsWallpaper() {
- return mSetAsWallpaper;
- }
-
- public boolean getReturnData() {
- return mReturnData;
- }
-
- public Uri getExtraOutput() {
- return mExtraOutput;
- }
-
- public String getOutputFormat() {
- return mOutputFormat;
- }
-
- public boolean getShowWhenLocked() {
- return mShowWhenLocked;
- }
-
- public float getSpotlightX() {
- return mSpotlightX;
- }
-
- public float getSpotlightY() {
- return mSpotlightY;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/crop/CropMath.java b/src/com/android/gallery3d/filtershow/crop/CropMath.java
deleted file mode 100644
index 02c65310e..000000000
--- a/src/com/android/gallery3d/filtershow/crop/CropMath.java
+++ /dev/null
@@ -1,260 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.crop;
-
-import android.graphics.Bitmap;
-import android.graphics.Matrix;
-import android.graphics.RectF;
-
-import com.android.gallery3d.filtershow.imageshow.GeometryMathUtils;
-
-import java.util.Arrays;
-
-public class CropMath {
-
- /**
- * Gets a float array of the 2D coordinates representing a rectangles
- * corners.
- * The order of the corners in the float array is:
- * 0------->1
- * ^ |
- * | v
- * 3<-------2
- *
- * @param r the rectangle to get the corners of
- * @return the float array of corners (8 floats)
- */
-
- public static float[] getCornersFromRect(RectF r) {
- float[] corners = {
- r.left, r.top,
- r.right, r.top,
- r.right, r.bottom,
- r.left, r.bottom
- };
- return corners;
- }
-
- /**
- * Returns true iff point (x, y) is within or on the rectangle's bounds.
- * RectF's "contains" function treats points on the bottom and right bound
- * as not being contained.
- *
- * @param r the rectangle
- * @param x the x value of the point
- * @param y the y value of the point
- * @return
- */
- public static boolean inclusiveContains(RectF r, float x, float y) {
- return !(x > r.right || x < r.left || y > r.bottom || y < r.top);
- }
-
- /**
- * Takes an array of 2D coordinates representing corners and returns the
- * smallest rectangle containing those coordinates.
- *
- * @param array array of 2D coordinates
- * @return smallest rectangle containing coordinates
- */
- public static RectF trapToRect(float[] array) {
- RectF r = new RectF(Float.POSITIVE_INFINITY, Float.POSITIVE_INFINITY,
- Float.NEGATIVE_INFINITY, Float.NEGATIVE_INFINITY);
- for (int i = 1; i < array.length; i += 2) {
- float x = array[i - 1];
- float y = array[i];
- r.left = (x < r.left) ? x : r.left;
- r.top = (y < r.top) ? y : r.top;
- r.right = (x > r.right) ? x : r.right;
- r.bottom = (y > r.bottom) ? y : r.bottom;
- }
- r.sort();
- return r;
- }
-
- /**
- * If edge point [x, y] in array [x0, y0, x1, y1, ...] is outside of the
- * image bound rectangle, clamps it to the edge of the rectangle.
- *
- * @param imageBound the rectangle to clamp edge points to.
- * @param array an array of points to clamp to the rectangle, gets set to
- * the clamped values.
- */
- public static void getEdgePoints(RectF imageBound, float[] array) {
- if (array.length < 2)
- return;
- for (int x = 0; x < array.length; x += 2) {
- array[x] = GeometryMathUtils.clamp(array[x], imageBound.left, imageBound.right);
- array[x + 1] = GeometryMathUtils.clamp(array[x + 1], imageBound.top, imageBound.bottom);
- }
- }
-
- /**
- * Takes a point and the corners of a rectangle and returns the two corners
- * representing the side of the rectangle closest to the point.
- *
- * @param point the point which is being checked
- * @param corners the corners of the rectangle
- * @return two corners representing the side of the rectangle
- */
- public static float[] closestSide(float[] point, float[] corners) {
- int len = corners.length;
- float oldMag = Float.POSITIVE_INFINITY;
- float[] bestLine = null;
- for (int i = 0; i < len; i += 2) {
- float[] line = {
- corners[i], corners[(i + 1) % len],
- corners[(i + 2) % len], corners[(i + 3) % len]
- };
- float mag = GeometryMathUtils.vectorLength(
- GeometryMathUtils.shortestVectorFromPointToLine(point, line));
- if (mag < oldMag) {
- oldMag = mag;
- bestLine = line;
- }
- }
- return bestLine;
- }
-
- /**
- * Checks if a given point is within a rotated rectangle.
- *
- * @param point 2D point to check
- * @param bound rectangle to rotate
- * @param rot angle of rotation about rectangle center
- * @return true if point is within rotated rectangle
- */
- public static boolean pointInRotatedRect(float[] point, RectF bound, float rot) {
- Matrix m = new Matrix();
- float[] p = Arrays.copyOf(point, 2);
- m.setRotate(rot, bound.centerX(), bound.centerY());
- Matrix m0 = new Matrix();
- if (!m.invert(m0))
- return false;
- m0.mapPoints(p);
- return inclusiveContains(bound, p[0], p[1]);
- }
-
- /**
- * Checks if a given point is within a rotated rectangle.
- *
- * @param point 2D point to check
- * @param rotatedRect corners of a rotated rectangle
- * @param center center of the rotated rectangle
- * @return true if point is within rotated rectangle
- */
- public static boolean pointInRotatedRect(float[] point, float[] rotatedRect, float[] center) {
- RectF unrotated = new RectF();
- float angle = getUnrotated(rotatedRect, center, unrotated);
- return pointInRotatedRect(point, unrotated, angle);
- }
-
- /**
- * Resizes rectangle to have a certain aspect ratio (center remains
- * stationary).
- *
- * @param r rectangle to resize
- * @param w new width aspect
- * @param h new height aspect
- */
- public static void fixAspectRatio(RectF r, float w, float h) {
- float scale = Math.min(r.width() / w, r.height() / h);
- float centX = r.centerX();
- float centY = r.centerY();
- float hw = scale * w / 2;
- float hh = scale * h / 2;
- r.set(centX - hw, centY - hh, centX + hw, centY + hh);
- }
-
- /**
- * Resizes rectangle to have a certain aspect ratio (center remains
- * stationary) while constraining it to remain within the original rect.
- *
- * @param r rectangle to resize
- * @param w new width aspect
- * @param h new height aspect
- */
- public static void fixAspectRatioContained(RectF r, float w, float h) {
- float origW = r.width();
- float origH = r.height();
- float origA = origW / origH;
- float a = w / h;
- float finalW = origW;
- float finalH = origH;
- if (origA < a) {
- finalH = origW / a;
- r.top = r.centerY() - finalH / 2;
- r.bottom = r.top + finalH;
- } else {
- finalW = origH * a;
- r.left = r.centerX() - finalW / 2;
- r.right = r.left + finalW;
- }
- }
-
- /**
- * Stretches/Scales/Translates photoBounds to match displayBounds, and
- * and returns an equivalent stretched/scaled/translated cropBounds or null
- * if the mapping is invalid.
- * @param cropBounds cropBounds to transform
- * @param photoBounds original bounds containing crop bounds
- * @param displayBounds final bounds for crop
- * @return the stretched/scaled/translated crop bounds that fit within displayBounds
- */
- public static RectF getScaledCropBounds(RectF cropBounds, RectF photoBounds,
- RectF displayBounds) {
- Matrix m = new Matrix();
- m.setRectToRect(photoBounds, displayBounds, Matrix.ScaleToFit.FILL);
- RectF trueCrop = new RectF(cropBounds);
- if (!m.mapRect(trueCrop)) {
- return null;
- }
- return trueCrop;
- }
-
- /**
- * Returns the size of a bitmap in bytes.
- * @param bmap bitmap whose size to check
- * @return bitmap size in bytes
- */
- public static int getBitmapSize(Bitmap bmap) {
- return bmap.getRowBytes() * bmap.getHeight();
- }
-
- /**
- * Constrains rotation to be in [0, 90, 180, 270] rounding down.
- * @param rotation any rotation value, in degrees
- * @return integer rotation in [0, 90, 180, 270]
- */
- public static int constrainedRotation(float rotation) {
- int r = (int) ((rotation % 360) / 90);
- r = (r < 0) ? (r + 4) : r;
- return r * 90;
- }
-
- private static float getUnrotated(float[] rotatedRect, float[] center, RectF unrotated) {
- float dy = rotatedRect[1] - rotatedRect[3];
- float dx = rotatedRect[0] - rotatedRect[2];
- float angle = (float) (Math.atan(dy / dx) * 180 / Math.PI);
- Matrix m = new Matrix();
- m.setRotate(-angle, center[0], center[1]);
- float[] unrotatedRect = new float[rotatedRect.length];
- m.mapPoints(unrotatedRect, rotatedRect);
- unrotated.set(trapToRect(unrotatedRect));
- return angle;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/crop/CropObject.java b/src/com/android/gallery3d/filtershow/crop/CropObject.java
deleted file mode 100644
index b98ed1bfd..000000000
--- a/src/com/android/gallery3d/filtershow/crop/CropObject.java
+++ /dev/null
@@ -1,330 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.crop;
-
-import android.graphics.Rect;
-import android.graphics.RectF;
-
-import com.android.gallery3d.filtershow.imageshow.GeometryMathUtils;
-
-public class CropObject {
- private BoundedRect mBoundedRect;
- private float mAspectWidth = 1;
- private float mAspectHeight = 1;
- private boolean mFixAspectRatio = false;
- private float mRotation = 0;
- private float mTouchTolerance = 45;
- private float mMinSideSize = 20;
-
- public static final int MOVE_NONE = 0;
- // Sides
- public static final int MOVE_LEFT = 1;
- public static final int MOVE_TOP = 2;
- public static final int MOVE_RIGHT = 4;
- public static final int MOVE_BOTTOM = 8;
- public static final int MOVE_BLOCK = 16;
-
- // Corners
- public static final int TOP_LEFT = MOVE_TOP | MOVE_LEFT;
- public static final int TOP_RIGHT = MOVE_TOP | MOVE_RIGHT;
- public static final int BOTTOM_RIGHT = MOVE_BOTTOM | MOVE_RIGHT;
- public static final int BOTTOM_LEFT = MOVE_BOTTOM | MOVE_LEFT;
-
- private int mMovingEdges = MOVE_NONE;
-
- public CropObject(Rect outerBound, Rect innerBound, int outerAngle) {
- mBoundedRect = new BoundedRect(outerAngle % 360, outerBound, innerBound);
- }
-
- public CropObject(RectF outerBound, RectF innerBound, int outerAngle) {
- mBoundedRect = new BoundedRect(outerAngle % 360, outerBound, innerBound);
- }
-
- public void resetBoundsTo(RectF inner, RectF outer) {
- mBoundedRect.resetTo(0, outer, inner);
- }
-
- public void getInnerBounds(RectF r) {
- mBoundedRect.setToInner(r);
- }
-
- public void getOuterBounds(RectF r) {
- mBoundedRect.setToOuter(r);
- }
-
- public RectF getInnerBounds() {
- return mBoundedRect.getInner();
- }
-
- public RectF getOuterBounds() {
- return mBoundedRect.getOuter();
- }
-
- public int getSelectState() {
- return mMovingEdges;
- }
-
- public boolean isFixedAspect() {
- return mFixAspectRatio;
- }
-
- public void rotateOuter(int angle) {
- mRotation = angle % 360;
- mBoundedRect.setRotation(mRotation);
- clearSelectState();
- }
-
- public boolean setInnerAspectRatio(float width, float height) {
- if (width <= 0 || height <= 0) {
- throw new IllegalArgumentException("Width and Height must be greater than zero");
- }
- RectF inner = mBoundedRect.getInner();
- CropMath.fixAspectRatioContained(inner, width, height);
- if (inner.width() < mMinSideSize || inner.height() < mMinSideSize) {
- return false;
- }
- mAspectWidth = width;
- mAspectHeight = height;
- mFixAspectRatio = true;
- mBoundedRect.setInner(inner);
- clearSelectState();
- return true;
- }
-
- public void setTouchTolerance(float tolerance) {
- if (tolerance <= 0) {
- throw new IllegalArgumentException("Tolerance must be greater than zero");
- }
- mTouchTolerance = tolerance;
- }
-
- public void setMinInnerSideSize(float minSide) {
- if (minSide <= 0) {
- throw new IllegalArgumentException("Min dide must be greater than zero");
- }
- mMinSideSize = minSide;
- }
-
- public void unsetAspectRatio() {
- mFixAspectRatio = false;
- clearSelectState();
- }
-
- public boolean hasSelectedEdge() {
- return mMovingEdges != MOVE_NONE;
- }
-
- public static boolean checkCorner(int selected) {
- return selected == TOP_LEFT || selected == TOP_RIGHT || selected == BOTTOM_RIGHT
- || selected == BOTTOM_LEFT;
- }
-
- public static boolean checkEdge(int selected) {
- return selected == MOVE_LEFT || selected == MOVE_TOP || selected == MOVE_RIGHT
- || selected == MOVE_BOTTOM;
- }
-
- public static boolean checkBlock(int selected) {
- return selected == MOVE_BLOCK;
- }
-
- public static boolean checkValid(int selected) {
- return selected == MOVE_NONE || checkBlock(selected) || checkEdge(selected)
- || checkCorner(selected);
- }
-
- public void clearSelectState() {
- mMovingEdges = MOVE_NONE;
- }
-
- public int wouldSelectEdge(float x, float y) {
- int edgeSelected = calculateSelectedEdge(x, y);
- if (edgeSelected != MOVE_NONE && edgeSelected != MOVE_BLOCK) {
- return edgeSelected;
- }
- return MOVE_NONE;
- }
-
- public boolean selectEdge(int edge) {
- if (!checkValid(edge)) {
- // temporary
- throw new IllegalArgumentException("bad edge selected");
- // return false;
- }
- if ((mFixAspectRatio && !checkCorner(edge)) && !checkBlock(edge) && edge != MOVE_NONE) {
- // temporary
- throw new IllegalArgumentException("bad corner selected");
- // return false;
- }
- mMovingEdges = edge;
- return true;
- }
-
- public boolean selectEdge(float x, float y) {
- int edgeSelected = calculateSelectedEdge(x, y);
- if (mFixAspectRatio) {
- edgeSelected = fixEdgeToCorner(edgeSelected);
- }
- if (edgeSelected == MOVE_NONE) {
- return false;
- }
- return selectEdge(edgeSelected);
- }
-
- public boolean moveCurrentSelection(float dX, float dY) {
- if (mMovingEdges == MOVE_NONE) {
- return false;
- }
- RectF crop = mBoundedRect.getInner();
-
- float minWidthHeight = mMinSideSize;
-
- int movingEdges = mMovingEdges;
- if (movingEdges == MOVE_BLOCK) {
- mBoundedRect.moveInner(dX, dY);
- return true;
- } else {
- float dx = 0;
- float dy = 0;
-
- if ((movingEdges & MOVE_LEFT) != 0) {
- dx = Math.min(crop.left + dX, crop.right - minWidthHeight) - crop.left;
- }
- if ((movingEdges & MOVE_TOP) != 0) {
- dy = Math.min(crop.top + dY, crop.bottom - minWidthHeight) - crop.top;
- }
- if ((movingEdges & MOVE_RIGHT) != 0) {
- dx = Math.max(crop.right + dX, crop.left + minWidthHeight)
- - crop.right;
- }
- if ((movingEdges & MOVE_BOTTOM) != 0) {
- dy = Math.max(crop.bottom + dY, crop.top + minWidthHeight)
- - crop.bottom;
- }
-
- if (mFixAspectRatio) {
- float[] l1 = {
- crop.left, crop.bottom
- };
- float[] l2 = {
- crop.right, crop.top
- };
- if (movingEdges == TOP_LEFT || movingEdges == BOTTOM_RIGHT) {
- l1[1] = crop.top;
- l2[1] = crop.bottom;
- }
- float[] b = {
- l1[0] - l2[0], l1[1] - l2[1]
- };
- float[] disp = {
- dx, dy
- };
- float[] bUnit = GeometryMathUtils.normalize(b);
- float sp = GeometryMathUtils.scalarProjection(disp, bUnit);
- dx = sp * bUnit[0];
- dy = sp * bUnit[1];
- RectF newCrop = fixedCornerResize(crop, movingEdges, dx, dy);
-
- mBoundedRect.fixedAspectResizeInner(newCrop);
- } else {
- if ((movingEdges & MOVE_LEFT) != 0) {
- crop.left += dx;
- }
- if ((movingEdges & MOVE_TOP) != 0) {
- crop.top += dy;
- }
- if ((movingEdges & MOVE_RIGHT) != 0) {
- crop.right += dx;
- }
- if ((movingEdges & MOVE_BOTTOM) != 0) {
- crop.bottom += dy;
- }
- mBoundedRect.resizeInner(crop);
- }
- }
- return true;
- }
-
- // Helper methods
-
- private int calculateSelectedEdge(float x, float y) {
- RectF cropped = mBoundedRect.getInner();
-
- float left = Math.abs(x - cropped.left);
- float right = Math.abs(x - cropped.right);
- float top = Math.abs(y - cropped.top);
- float bottom = Math.abs(y - cropped.bottom);
-
- int edgeSelected = MOVE_NONE;
- // Check left or right.
- if ((left <= mTouchTolerance) && ((y + mTouchTolerance) >= cropped.top)
- && ((y - mTouchTolerance) <= cropped.bottom) && (left < right)) {
- edgeSelected |= MOVE_LEFT;
- }
- else if ((right <= mTouchTolerance) && ((y + mTouchTolerance) >= cropped.top)
- && ((y - mTouchTolerance) <= cropped.bottom)) {
- edgeSelected |= MOVE_RIGHT;
- }
-
- // Check top or bottom.
- if ((top <= mTouchTolerance) && ((x + mTouchTolerance) >= cropped.left)
- && ((x - mTouchTolerance) <= cropped.right) && (top < bottom)) {
- edgeSelected |= MOVE_TOP;
- }
- else if ((bottom <= mTouchTolerance) && ((x + mTouchTolerance) >= cropped.left)
- && ((x - mTouchTolerance) <= cropped.right)) {
- edgeSelected |= MOVE_BOTTOM;
- }
- return edgeSelected;
- }
-
- private static RectF fixedCornerResize(RectF r, int moving_corner, float dx, float dy) {
- RectF newCrop = null;
- // Fix opposite corner in place and move sides
- if (moving_corner == BOTTOM_RIGHT) {
- newCrop = new RectF(r.left, r.top, r.left + r.width() + dx, r.top + r.height()
- + dy);
- } else if (moving_corner == BOTTOM_LEFT) {
- newCrop = new RectF(r.right - r.width() + dx, r.top, r.right, r.top + r.height()
- + dy);
- } else if (moving_corner == TOP_LEFT) {
- newCrop = new RectF(r.right - r.width() + dx, r.bottom - r.height() + dy,
- r.right, r.bottom);
- } else if (moving_corner == TOP_RIGHT) {
- newCrop = new RectF(r.left, r.bottom - r.height() + dy, r.left
- + r.width() + dx, r.bottom);
- }
- return newCrop;
- }
-
- private static int fixEdgeToCorner(int moving_edges) {
- if (moving_edges == MOVE_LEFT) {
- moving_edges |= MOVE_TOP;
- }
- if (moving_edges == MOVE_TOP) {
- moving_edges |= MOVE_LEFT;
- }
- if (moving_edges == MOVE_RIGHT) {
- moving_edges |= MOVE_BOTTOM;
- }
- if (moving_edges == MOVE_BOTTOM) {
- moving_edges |= MOVE_RIGHT;
- }
- return moving_edges;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/crop/CropView.java b/src/com/android/gallery3d/filtershow/crop/CropView.java
deleted file mode 100644
index bbb7cfd4c..000000000
--- a/src/com/android/gallery3d/filtershow/crop/CropView.java
+++ /dev/null
@@ -1,378 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.crop;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.DashPathEffect;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.graphics.drawable.Drawable;
-import android.graphics.drawable.NinePatchDrawable;
-import android.util.AttributeSet;
-import android.util.Log;
-import android.view.MotionEvent;
-import android.view.View;
-
-import com.android.gallery3d.R;
-
-
-public class CropView extends View {
- private static final String LOGTAG = "CropView";
-
- private RectF mImageBounds = new RectF();
- private RectF mScreenBounds = new RectF();
- private RectF mScreenImageBounds = new RectF();
- private RectF mScreenCropBounds = new RectF();
- private Rect mShadowBounds = new Rect();
-
- private Bitmap mBitmap;
- private Paint mPaint = new Paint();
-
- private NinePatchDrawable mShadow;
- private CropObject mCropObj = null;
- private Drawable mCropIndicator;
- private int mIndicatorSize;
- private int mRotation = 0;
- private boolean mMovingBlock = false;
- private Matrix mDisplayMatrix = null;
- private Matrix mDisplayMatrixInverse = null;
- private boolean mDirty = false;
-
- private float mPrevX = 0;
- private float mPrevY = 0;
- private float mSpotX = 0;
- private float mSpotY = 0;
- private boolean mDoSpot = false;
-
- private int mShadowMargin = 15;
- private int mMargin = 32;
- private int mOverlayShadowColor = 0xCF000000;
- private int mOverlayWPShadowColor = 0x5F000000;
- private int mWPMarkerColor = 0x7FFFFFFF;
- private int mMinSideSize = 90;
- private int mTouchTolerance = 40;
- private float mDashOnLength = 20;
- private float mDashOffLength = 10;
-
- private enum Mode {
- NONE, MOVE
- }
-
- private Mode mState = Mode.NONE;
-
- public CropView(Context context) {
- super(context);
- setup(context);
- }
-
- public CropView(Context context, AttributeSet attrs) {
- super(context, attrs);
- setup(context);
- }
-
- public CropView(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- setup(context);
- }
-
- private void setup(Context context) {
- Resources rsc = context.getResources();
- mShadow = (NinePatchDrawable) rsc.getDrawable(R.drawable.geometry_shadow);
- mCropIndicator = rsc.getDrawable(R.drawable.camera_crop);
- mIndicatorSize = (int) rsc.getDimension(R.dimen.crop_indicator_size);
- mShadowMargin = (int) rsc.getDimension(R.dimen.shadow_margin);
- mMargin = (int) rsc.getDimension(R.dimen.preview_margin);
- mMinSideSize = (int) rsc.getDimension(R.dimen.crop_min_side);
- mTouchTolerance = (int) rsc.getDimension(R.dimen.crop_touch_tolerance);
- mOverlayShadowColor = (int) rsc.getColor(R.color.crop_shadow_color);
- mOverlayWPShadowColor = (int) rsc.getColor(R.color.crop_shadow_wp_color);
- mWPMarkerColor = (int) rsc.getColor(R.color.crop_wp_markers);
- mDashOnLength = rsc.getDimension(R.dimen.wp_selector_dash_length);
- mDashOffLength = rsc.getDimension(R.dimen.wp_selector_off_length);
- }
-
- public void initialize(Bitmap image, RectF newCropBounds, RectF newPhotoBounds, int rotation) {
- mBitmap = image;
- if (mCropObj != null) {
- RectF crop = mCropObj.getInnerBounds();
- RectF containing = mCropObj.getOuterBounds();
- if (crop != newCropBounds || containing != newPhotoBounds
- || mRotation != rotation) {
- mRotation = rotation;
- mCropObj.resetBoundsTo(newCropBounds, newPhotoBounds);
- clearDisplay();
- }
- } else {
- mRotation = rotation;
- mCropObj = new CropObject(newPhotoBounds, newCropBounds, 0);
- clearDisplay();
- }
- }
-
- public RectF getCrop() {
- return mCropObj.getInnerBounds();
- }
-
- public RectF getPhoto() {
- return mCropObj.getOuterBounds();
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- float x = event.getX();
- float y = event.getY();
- if (mDisplayMatrix == null || mDisplayMatrixInverse == null) {
- return true;
- }
- float[] touchPoint = {
- x, y
- };
- mDisplayMatrixInverse.mapPoints(touchPoint);
- x = touchPoint[0];
- y = touchPoint[1];
- switch (event.getActionMasked()) {
- case (MotionEvent.ACTION_DOWN):
- if (mState == Mode.NONE) {
- if (!mCropObj.selectEdge(x, y)) {
- mMovingBlock = mCropObj.selectEdge(CropObject.MOVE_BLOCK);
- }
- mPrevX = x;
- mPrevY = y;
- mState = Mode.MOVE;
- }
- break;
- case (MotionEvent.ACTION_UP):
- if (mState == Mode.MOVE) {
- mCropObj.selectEdge(CropObject.MOVE_NONE);
- mMovingBlock = false;
- mPrevX = x;
- mPrevY = y;
- mState = Mode.NONE;
- }
- break;
- case (MotionEvent.ACTION_MOVE):
- if (mState == Mode.MOVE) {
- float dx = x - mPrevX;
- float dy = y - mPrevY;
- mCropObj.moveCurrentSelection(dx, dy);
- mPrevX = x;
- mPrevY = y;
- }
- break;
- default:
- break;
- }
- invalidate();
- return true;
- }
-
- private void reset() {
- Log.w(LOGTAG, "crop reset called");
- mState = Mode.NONE;
- mCropObj = null;
- mRotation = 0;
- mMovingBlock = false;
- clearDisplay();
- }
-
- private void clearDisplay() {
- mDisplayMatrix = null;
- mDisplayMatrixInverse = null;
- invalidate();
- }
-
- protected void configChanged() {
- mDirty = true;
- }
-
- public void applyFreeAspect() {
- mCropObj.unsetAspectRatio();
- invalidate();
- }
-
- public void applyOriginalAspect() {
- RectF outer = mCropObj.getOuterBounds();
- float w = outer.width();
- float h = outer.height();
- if (w > 0 && h > 0) {
- applyAspect(w, h);
- mCropObj.resetBoundsTo(outer, outer);
- } else {
- Log.w(LOGTAG, "failed to set aspect ratio original");
- }
- }
-
- public void applySquareAspect() {
- applyAspect(1, 1);
- }
-
- public void applyAspect(float x, float y) {
- if (x <= 0 || y <= 0) {
- throw new IllegalArgumentException("Bad arguments to applyAspect");
- }
- // If we are rotated by 90 degrees from horizontal, swap x and y
- if (((mRotation < 0) ? -mRotation : mRotation) % 180 == 90) {
- float tmp = x;
- x = y;
- y = tmp;
- }
- if (!mCropObj.setInnerAspectRatio(x, y)) {
- Log.w(LOGTAG, "failed to set aspect ratio");
- }
- invalidate();
- }
-
- public void setWallpaperSpotlight(float spotlightX, float spotlightY) {
- mSpotX = spotlightX;
- mSpotY = spotlightY;
- if (mSpotX > 0 && mSpotY > 0) {
- mDoSpot = true;
- }
- }
-
- public void unsetWallpaperSpotlight() {
- mDoSpot = false;
- }
-
- /**
- * Rotates first d bits in integer x to the left some number of times.
- */
- private int bitCycleLeft(int x, int times, int d) {
- int mask = (1 << d) - 1;
- int mout = x & mask;
- times %= d;
- int hi = mout >> (d - times);
- int low = (mout << times) & mask;
- int ret = x & ~mask;
- ret |= low;
- ret |= hi;
- return ret;
- }
-
- /**
- * Find the selected edge or corner in screen coordinates.
- */
- private int decode(int movingEdges, float rotation) {
- int rot = CropMath.constrainedRotation(rotation);
- switch (rot) {
- case 90:
- return bitCycleLeft(movingEdges, 1, 4);
- case 180:
- return bitCycleLeft(movingEdges, 2, 4);
- case 270:
- return bitCycleLeft(movingEdges, 3, 4);
- default:
- return movingEdges;
- }
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- if (mBitmap == null) {
- return;
- }
- if (mDirty) {
- mDirty = false;
- clearDisplay();
- }
-
- mImageBounds = new RectF(0, 0, mBitmap.getWidth(), mBitmap.getHeight());
- mScreenBounds = new RectF(0, 0, canvas.getWidth(), canvas.getHeight());
- mScreenBounds.inset(mMargin, mMargin);
-
- // If crop object doesn't exist, create it and update it from master
- // state
- if (mCropObj == null) {
- reset();
- mCropObj = new CropObject(mImageBounds, mImageBounds, 0);
- }
-
- // If display matrix doesn't exist, create it and its dependencies
- if (mDisplayMatrix == null || mDisplayMatrixInverse == null) {
- mDisplayMatrix = new Matrix();
- mDisplayMatrix.reset();
- if (!CropDrawingUtils.setImageToScreenMatrix(mDisplayMatrix, mImageBounds, mScreenBounds,
- mRotation)) {
- Log.w(LOGTAG, "failed to get screen matrix");
- mDisplayMatrix = null;
- return;
- }
- mDisplayMatrixInverse = new Matrix();
- mDisplayMatrixInverse.reset();
- if (!mDisplayMatrix.invert(mDisplayMatrixInverse)) {
- Log.w(LOGTAG, "could not invert display matrix");
- mDisplayMatrixInverse = null;
- return;
- }
- // Scale min side and tolerance by display matrix scale factor
- mCropObj.setMinInnerSideSize(mDisplayMatrixInverse.mapRadius(mMinSideSize));
- mCropObj.setTouchTolerance(mDisplayMatrixInverse.mapRadius(mTouchTolerance));
- }
-
- mScreenImageBounds.set(mImageBounds);
-
- // Draw background shadow
- if (mDisplayMatrix.mapRect(mScreenImageBounds)) {
- int margin = (int) mDisplayMatrix.mapRadius(mShadowMargin);
- mScreenImageBounds.roundOut(mShadowBounds);
- mShadowBounds.set(mShadowBounds.left - margin, mShadowBounds.top -
- margin, mShadowBounds.right + margin, mShadowBounds.bottom + margin);
- mShadow.setBounds(mShadowBounds);
- mShadow.draw(canvas);
- }
-
- mPaint.setAntiAlias(true);
- mPaint.setFilterBitmap(true);
- // Draw actual bitmap
- canvas.drawBitmap(mBitmap, mDisplayMatrix, mPaint);
-
- mCropObj.getInnerBounds(mScreenCropBounds);
-
- if (mDisplayMatrix.mapRect(mScreenCropBounds)) {
-
- // Draw overlay shadows
- Paint p = new Paint();
- p.setColor(mOverlayShadowColor);
- p.setStyle(Paint.Style.FILL);
- CropDrawingUtils.drawShadows(canvas, p, mScreenCropBounds, mScreenImageBounds);
-
- // Draw crop rect and markers
- CropDrawingUtils.drawCropRect(canvas, mScreenCropBounds);
- if (!mDoSpot) {
- CropDrawingUtils.drawRuleOfThird(canvas, mScreenCropBounds);
- } else {
- Paint wpPaint = new Paint();
- wpPaint.setColor(mWPMarkerColor);
- wpPaint.setStrokeWidth(3);
- wpPaint.setStyle(Paint.Style.STROKE);
- wpPaint.setPathEffect(new DashPathEffect(new float[]
- {mDashOnLength, mDashOnLength + mDashOffLength}, 0));
- p.setColor(mOverlayWPShadowColor);
- CropDrawingUtils.drawWallpaperSelectionFrame(canvas, mScreenCropBounds,
- mSpotX, mSpotY, wpPaint, p);
- }
- CropDrawingUtils.drawIndicators(canvas, mCropIndicator, mIndicatorSize,
- mScreenCropBounds, mCropObj.isFixedAspect(), decode(mCropObj.getSelectState(), mRotation));
- }
-
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/data/FilterStackDBHelper.java b/src/com/android/gallery3d/filtershow/data/FilterStackDBHelper.java
deleted file mode 100644
index e18d3104f..000000000
--- a/src/com/android/gallery3d/filtershow/data/FilterStackDBHelper.java
+++ /dev/null
@@ -1,101 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.data;
-
-import android.content.Context;
-import android.database.sqlite.SQLiteDatabase;
-import android.database.sqlite.SQLiteOpenHelper;
-
-public class FilterStackDBHelper extends SQLiteOpenHelper {
-
- public static final int DATABASE_VERSION = 1;
- public static final String DATABASE_NAME = "filterstacks.db";
- private static final String SQL_CREATE_TABLE = "CREATE TABLE ";
-
- public static interface FilterStack {
- /** The row uid */
- public static final String _ID = "_id";
- /** The table name */
- public static final String TABLE = "filterstack";
- /** The stack name */
- public static final String STACK_ID = "stack_id";
- /** A serialized stack of filters. */
- public static final String FILTER_STACK= "stack";
- }
-
- private static final String[][] CREATE_FILTER_STACK = {
- { FilterStack._ID, "INTEGER PRIMARY KEY AUTOINCREMENT" },
- { FilterStack.STACK_ID, "TEXT" },
- { FilterStack.FILTER_STACK, "BLOB" },
- };
-
- public FilterStackDBHelper(Context context, String name, int version) {
- super(context, name, null, version);
- }
-
- public FilterStackDBHelper(Context context, String name) {
- this(context, name, DATABASE_VERSION);
- }
-
- public FilterStackDBHelper(Context context) {
- this(context, DATABASE_NAME);
- }
-
- @Override
- public void onCreate(SQLiteDatabase db) {
- createTable(db, FilterStack.TABLE, CREATE_FILTER_STACK);
- }
-
- @Override
- public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
- dropTable(db, FilterStack.TABLE);
- onCreate(db);
- }
-
- protected static void createTable(SQLiteDatabase db, String table, String[][] columns) {
- StringBuilder create = new StringBuilder(SQL_CREATE_TABLE);
- create.append(table).append('(');
- boolean first = true;
- for (String[] column : columns) {
- if (!first) {
- create.append(',');
- }
- first = false;
- for (String val : column) {
- create.append(val).append(' ');
- }
- }
- create.append(')');
- db.beginTransaction();
- try {
- db.execSQL(create.toString());
- db.setTransactionSuccessful();
- } finally {
- db.endTransaction();
- }
- }
-
- protected static void dropTable(SQLiteDatabase db, String table) {
- db.beginTransaction();
- try {
- db.execSQL("drop table if exists " + table);
- db.setTransactionSuccessful();
- } finally {
- db.endTransaction();
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/data/FilterStackSource.java b/src/com/android/gallery3d/filtershow/data/FilterStackSource.java
deleted file mode 100644
index d283771b4..000000000
--- a/src/com/android/gallery3d/filtershow/data/FilterStackSource.java
+++ /dev/null
@@ -1,197 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.filtershow.data;
-
-import android.content.ContentValues;
-import android.content.Context;
-import android.database.Cursor;
-import android.database.sqlite.SQLiteDatabase;
-import android.database.sqlite.SQLiteException;
-import android.util.Log;
-import android.util.Pair;
-
-import com.android.gallery3d.filtershow.data.FilterStackDBHelper.FilterStack;
-import com.android.gallery3d.filtershow.filters.FilterUserPresetRepresentation;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-
-import java.util.ArrayList;
-import java.util.List;
-
-public class FilterStackSource {
- private static final String LOGTAG = "FilterStackSource";
-
- private SQLiteDatabase database = null;
- private final FilterStackDBHelper dbHelper;
-
- public FilterStackSource(Context context) {
- dbHelper = new FilterStackDBHelper(context);
- }
-
- public void open() {
- try {
- database = dbHelper.getWritableDatabase();
- } catch (SQLiteException e) {
- Log.w(LOGTAG, "could not open database", e);
- }
- }
-
- public void close() {
- database = null;
- dbHelper.close();
- }
-
- public boolean insertStack(String stackName, byte[] stackBlob) {
- boolean ret = true;
- ContentValues val = new ContentValues();
- val.put(FilterStack.STACK_ID, stackName);
- val.put(FilterStack.FILTER_STACK, stackBlob);
- database.beginTransaction();
- try {
- ret = (-1 != database.insert(FilterStack.TABLE, null, val));
- database.setTransactionSuccessful();
- } finally {
- database.endTransaction();
- }
- return ret;
- }
-
- public void updateStackName(int id, String stackName) {
- ContentValues val = new ContentValues();
- val.put(FilterStack.STACK_ID, stackName);
- database.beginTransaction();
- try {
- database.update(FilterStack.TABLE, val, FilterStack._ID + " = ?",
- new String[] { "" + id});
- database.setTransactionSuccessful();
- } finally {
- database.endTransaction();
- }
- }
-
- public boolean removeStack(int id) {
- boolean ret = true;
- database.beginTransaction();
- try {
- ret = (0 != database.delete(FilterStack.TABLE, FilterStack._ID + " = ?",
- new String[] { "" + id }));
- database.setTransactionSuccessful();
- } finally {
- database.endTransaction();
- }
- return ret;
- }
-
- public void removeAllStacks() {
- database.beginTransaction();
- try {
- database.delete(FilterStack.TABLE, null, null);
- database.setTransactionSuccessful();
- } finally {
- database.endTransaction();
- }
- }
-
- public byte[] getStack(String stackName) {
- byte[] ret = null;
- Cursor c = null;
- database.beginTransaction();
- try {
- c = database.query(FilterStack.TABLE,
- new String[] { FilterStack.FILTER_STACK },
- FilterStack.STACK_ID + " = ?",
- new String[] { stackName }, null, null, null, null);
- if (c != null && c.moveToFirst() && !c.isNull(0)) {
- ret = c.getBlob(0);
- }
- database.setTransactionSuccessful();
- } finally {
- if (c != null) {
- c.close();
- }
- database.endTransaction();
- }
- return ret;
- }
-
- public ArrayList<FilterUserPresetRepresentation> getAllUserPresets() {
- ArrayList<FilterUserPresetRepresentation> ret =
- new ArrayList<FilterUserPresetRepresentation>();
-
- Cursor c = null;
- database.beginTransaction();
- try {
- c = database.query(FilterStack.TABLE,
- new String[] { FilterStack._ID,
- FilterStack.STACK_ID,
- FilterStack.FILTER_STACK },
- null, null, null, null, null, null);
- if (c != null) {
- boolean loopCheck = c.moveToFirst();
- while (loopCheck) {
- int id = c.getInt(0);
- String name = (c.isNull(1)) ? null : c.getString(1);
- byte[] b = (c.isNull(2)) ? null : c.getBlob(2);
- String json = new String(b);
-
- ImagePreset preset = new ImagePreset();
- preset.readJsonFromString(json);
- FilterUserPresetRepresentation representation =
- new FilterUserPresetRepresentation(name, preset, id);
- ret.add(representation);
- loopCheck = c.moveToNext();
- }
- }
- database.setTransactionSuccessful();
- } finally {
- if (c != null) {
- c.close();
- }
- database.endTransaction();
- }
-
- return ret;
- }
-
- public List<Pair<String, byte[]>> getAllStacks() {
- List<Pair<String, byte[]>> ret = new ArrayList<Pair<String, byte[]>>();
- Cursor c = null;
- database.beginTransaction();
- try {
- c = database.query(FilterStack.TABLE,
- new String[] { FilterStack.STACK_ID, FilterStack.FILTER_STACK },
- null, null, null, null, null, null);
- if (c != null) {
- boolean loopCheck = c.moveToFirst();
- while (loopCheck) {
- String name = (c.isNull(0)) ? null : c.getString(0);
- byte[] b = (c.isNull(1)) ? null : c.getBlob(1);
- ret.add(new Pair<String, byte[]>(name, b));
- loopCheck = c.moveToNext();
- }
- }
- database.setTransactionSuccessful();
- } finally {
- if (c != null) {
- c.close();
- }
- database.endTransaction();
- }
- if (ret.size() <= 0) {
- return null;
- }
- return ret;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/data/UserPresetsManager.java b/src/com/android/gallery3d/filtershow/data/UserPresetsManager.java
deleted file mode 100644
index 114cd3ebc..000000000
--- a/src/com/android/gallery3d/filtershow/data/UserPresetsManager.java
+++ /dev/null
@@ -1,149 +0,0 @@
-package com.android.gallery3d.filtershow.data;
-
-import android.os.Handler;
-import android.os.HandlerThread;
-import android.os.Message;
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.filters.FilterUserPresetRepresentation;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-
-import java.util.ArrayList;
-
-public class UserPresetsManager implements Handler.Callback {
-
- private static final String LOGTAG = "UserPresetsManager";
-
- private FilterShowActivity mActivity;
- private HandlerThread mHandlerThread = null;
- private Handler mProcessingHandler = null;
- private FilterStackSource mUserPresets;
-
- private static final int LOAD = 1;
- private static final int LOAD_RESULT = 2;
- private static final int SAVE = 3;
- private static final int DELETE = 4;
- private static final int UPDATE = 5;
-
- private ArrayList<FilterUserPresetRepresentation> mRepresentations;
-
- private final Handler mResultHandler = new Handler() {
- @Override
- public void handleMessage(Message msg) {
- switch (msg.what) {
- case LOAD_RESULT:
- resultLoad(msg);
- break;
- }
- }
- };
-
- @Override
- public boolean handleMessage(Message msg) {
- switch (msg.what) {
- case LOAD:
- processLoad();
- return true;
- case SAVE:
- processSave(msg);
- return true;
- case DELETE:
- processDelete(msg);
- return true;
- case UPDATE:
- processUpdate(msg);
- return true;
- }
- return false;
- }
-
- public UserPresetsManager(FilterShowActivity context) {
- mActivity = context;
- mHandlerThread = new HandlerThread(LOGTAG,
- android.os.Process.THREAD_PRIORITY_BACKGROUND);
- mHandlerThread.start();
- mProcessingHandler = new Handler(mHandlerThread.getLooper(), this);
- mUserPresets = new FilterStackSource(mActivity);
- mUserPresets.open();
- }
-
- public ArrayList<FilterUserPresetRepresentation> getRepresentations() {
- return mRepresentations;
- }
-
- public void load() {
- Message msg = mProcessingHandler.obtainMessage(LOAD);
- mProcessingHandler.sendMessage(msg);
- }
-
- public void close() {
- mUserPresets.close();
- mHandlerThread.quit();
- }
-
- static class SaveOperation {
- String json;
- String name;
- }
-
- public void save(ImagePreset preset) {
- Message msg = mProcessingHandler.obtainMessage(SAVE);
- SaveOperation op = new SaveOperation();
- op.json = preset.getJsonString(mActivity.getString(R.string.saved));
- op.name= mActivity.getString(R.string.filtershow_new_preset);
- msg.obj = op;
- mProcessingHandler.sendMessage(msg);
- }
-
- public void delete(int id) {
- Message msg = mProcessingHandler.obtainMessage(DELETE);
- msg.arg1 = id;
- mProcessingHandler.sendMessage(msg);
- }
-
- static class UpdateOperation {
- int id;
- String name;
- }
-
- public void update(FilterUserPresetRepresentation representation) {
- Message msg = mProcessingHandler.obtainMessage(UPDATE);
- UpdateOperation op = new UpdateOperation();
- op.id = representation.getId();
- op.name = representation.getName();
- msg.obj = op;
- mProcessingHandler.sendMessage(msg);
- }
-
- private void processLoad() {
- ArrayList<FilterUserPresetRepresentation> list = mUserPresets.getAllUserPresets();
- Message msg = mResultHandler.obtainMessage(LOAD_RESULT);
- msg.obj = list;
- mResultHandler.sendMessage(msg);
- }
-
- private void resultLoad(Message msg) {
- mRepresentations =
- (ArrayList<FilterUserPresetRepresentation>) msg.obj;
- mActivity.updateUserPresetsFromManager();
- }
-
- private void processSave(Message msg) {
- SaveOperation op = (SaveOperation) msg.obj;
- mUserPresets.insertStack(op.name, op.json.getBytes());
- processLoad();
- }
-
- private void processDelete(Message msg) {
- int id = msg.arg1;
- mUserPresets.removeStack(id);
- processLoad();
- }
-
- private void processUpdate(Message msg) {
- UpdateOperation op = (UpdateOperation) msg.obj;
- mUserPresets.updateStackName(op.id, op.name);
- processLoad();
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/BasicEditor.java b/src/com/android/gallery3d/filtershow/editors/BasicEditor.java
deleted file mode 100644
index af694d811..000000000
--- a/src/com/android/gallery3d/filtershow/editors/BasicEditor.java
+++ /dev/null
@@ -1,138 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.controller.Control;
-import com.android.gallery3d.filtershow.controller.FilterView;
-import com.android.gallery3d.filtershow.controller.Parameter;
-import com.android.gallery3d.filtershow.controller.ParameterInteger;
-import com.android.gallery3d.filtershow.filters.FilterBasicRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-
-
-/**
- * The basic editor that all the one parameter filters
- */
-public class BasicEditor extends ParametricEditor implements ParameterInteger {
- public static int ID = R.id.basicEditor;
- private final String LOGTAG = "BasicEditor";
-
- public BasicEditor() {
- super(ID, R.layout.filtershow_default_editor, R.id.basicEditor);
- }
-
- protected BasicEditor(int id) {
- super(id, R.layout.filtershow_default_editor, R.id.basicEditor);
- }
-
- protected BasicEditor(int id, int layoutID, int viewID) {
- super(id, layoutID, viewID);
- }
-
- @Override
- public void reflectCurrentFilter() {
- super.reflectCurrentFilter();
- if (getLocalRepresentation() != null && getLocalRepresentation() instanceof FilterBasicRepresentation) {
- FilterBasicRepresentation interval = (FilterBasicRepresentation) getLocalRepresentation();
- updateText();
- }
- }
-
- private FilterBasicRepresentation getBasicRepresentation() {
- FilterRepresentation tmpRep = getLocalRepresentation();
- if (tmpRep != null && tmpRep instanceof FilterBasicRepresentation) {
- return (FilterBasicRepresentation) tmpRep;
-
- }
- return null;
- }
-
- @Override
- public int getMaximum() {
- FilterBasicRepresentation rep = getBasicRepresentation();
- if (rep == null) {
- return 0;
- }
- return rep.getMaximum();
- }
-
- @Override
- public int getMinimum() {
- FilterBasicRepresentation rep = getBasicRepresentation();
- if (rep == null) {
- return 0;
- }
- return rep.getMinimum();
- }
-
- @Override
- public int getDefaultValue() {
- return 0;
- }
-
- @Override
- public int getValue() {
- FilterBasicRepresentation rep = getBasicRepresentation();
- if (rep == null) {
- return 0;
- }
- return rep.getValue();
- }
-
- @Override
- public String getValueString() {
- return null;
- }
-
- @Override
- public void setValue(int value) {
- FilterBasicRepresentation rep = getBasicRepresentation();
- if (rep == null) {
- return;
- }
- rep.setValue(value);
- commitLocalRepresentation();
- }
-
- @Override
- public String getParameterName() {
- FilterBasicRepresentation rep = getBasicRepresentation();
- return mContext.getString(rep.getTextId());
- }
-
- @Override
- public String getParameterType() {
- return sParameterType;
- }
-
- @Override
- public void setController(Control c) {
- }
-
- @Override
- public void setFilterView(FilterView editor) {
-
- }
-
- @Override
- public void copyFrom(Parameter src) {
-
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/Editor.java b/src/com/android/gallery3d/filtershow/editors/Editor.java
deleted file mode 100644
index a9e56e0c1..000000000
--- a/src/com/android/gallery3d/filtershow/editors/Editor.java
+++ /dev/null
@@ -1,330 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.util.AttributeSet;
-import android.view.LayoutInflater;
-import android.view.Menu;
-import android.view.MenuItem;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.Button;
-import android.widget.FrameLayout;
-import android.widget.LinearLayout;
-import android.widget.PopupMenu;
-import android.widget.SeekBar;
-import android.widget.SeekBar.OnSeekBarChangeListener;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.controller.Control;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.imageshow.ImageShow;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-
-import java.util.ArrayList;
-import java.util.Collection;
-
-/**
- * Base class for Editors Must contain a mImageShow and a top level view
- */
-public class Editor implements OnSeekBarChangeListener, SwapButton.SwapButtonListener {
- protected Context mContext;
- protected View mView;
- protected ImageShow mImageShow;
- protected FrameLayout mFrameLayout;
- protected SeekBar mSeekBar;
- Button mEditTitle;
- protected Button mFilterTitle;
- protected int mID;
- private final String LOGTAG = "Editor";
- protected boolean mChangesGeometry = false;
- protected FilterRepresentation mLocalRepresentation = null;
- protected byte mShowParameter = SHOW_VALUE_UNDEFINED;
- private Button mButton;
- public static byte SHOW_VALUE_UNDEFINED = -1;
- public static byte SHOW_VALUE_OFF = 0;
- public static byte SHOW_VALUE_INT = 1;
-
- public static void hackFixStrings(Menu menu) {
- int count = menu.size();
- for (int i = 0; i < count; i++) {
- MenuItem item = menu.getItem(i);
- item.setTitle(item.getTitle().toString().toUpperCase());
- }
- }
-
- public String calculateUserMessage(Context context, String effectName, Object parameterValue) {
- return effectName.toUpperCase() + " " + parameterValue;
- }
-
- protected Editor(int id) {
- mID = id;
- }
-
- public int getID() {
- return mID;
- }
-
- public byte showParameterValue() {
- return mShowParameter;
- }
-
- public boolean showsSeekBar() {
- return true;
- }
-
- public void setUpEditorUI(View actionButton, View editControl,
- Button editTitle, Button stateButton) {
- mEditTitle = editTitle;
- mFilterTitle = stateButton;
- mButton = editTitle;
- setMenuIcon(true);
- setUtilityPanelUI(actionButton, editControl);
- }
-
- public boolean showsPopupIndicator() {
- return true;
- }
-
- /**
- * @param actionButton the would be the area for menu etc
- * @param editControl this is the black area for sliders etc
- */
- public void setUtilityPanelUI(View actionButton, View editControl) {
-
- AttributeSet aset;
- Context context = editControl.getContext();
- LayoutInflater inflater =
- (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
- LinearLayout lp = (LinearLayout) inflater.inflate(
- R.layout.filtershow_seekbar, (ViewGroup) editControl, true);
- mSeekBar = (SeekBar) lp.findViewById(R.id.primarySeekBar);
- mSeekBar.setOnSeekBarChangeListener(this);
-
- if (showsSeekBar()) {
- mSeekBar.setOnSeekBarChangeListener(this);
- mSeekBar.setVisibility(View.VISIBLE);
- } else {
- mSeekBar.setVisibility(View.INVISIBLE);
- }
-
- if (mButton != null) {
- if (showsPopupIndicator()) {
- mButton.setCompoundDrawablesRelativeWithIntrinsicBounds(0, 0,
- R.drawable.filtershow_menu_marker, 0);
- } else {
- mButton.setCompoundDrawablesRelativeWithIntrinsicBounds(0, 0, 0, 0);
- }
- }
- }
-
- @Override
- public void onProgressChanged(SeekBar sbar, int progress, boolean arg2) {
-
- }
-
- public void setPanel() {
-
- }
-
- public void createEditor(Context context,FrameLayout frameLayout) {
- mContext = context;
- mFrameLayout = frameLayout;
- mLocalRepresentation = null;
- }
-
- protected void unpack(int viewid, int layoutid) {
-
- if (mView == null) {
- mView = mFrameLayout.findViewById(viewid);
- if (mView == null) {
- LayoutInflater inflater = (LayoutInflater) mContext.getSystemService
- (Context.LAYOUT_INFLATER_SERVICE);
- mView = inflater.inflate(layoutid, mFrameLayout, false);
- mFrameLayout.addView(mView, mView.getLayoutParams());
- }
- }
- mImageShow = findImageShow(mView);
- }
-
- private ImageShow findImageShow(View view) {
- if (view instanceof ImageShow) {
- return (ImageShow) view;
- }
- if (!(view instanceof ViewGroup)) {
- return null;
- }
- ViewGroup vg = (ViewGroup) view;
- int n = vg.getChildCount();
- for (int i = 0; i < n; i++) {
- View v = vg.getChildAt(i);
- if (v instanceof ImageShow) {
- return (ImageShow) v;
- } else if (v instanceof ViewGroup) {
- return findImageShow(v);
- }
- }
- return null;
- }
-
- public View getTopLevelView() {
- return mView;
- }
-
- public ImageShow getImageShow() {
- return mImageShow;
- }
-
- public void setVisibility(int visible) {
- mView.setVisibility(visible);
- }
-
- public FilterRepresentation getLocalRepresentation() {
- if (mLocalRepresentation == null) {
- ImagePreset preset = MasterImage.getImage().getPreset();
- FilterRepresentation filterRepresentation = MasterImage.getImage().getCurrentFilterRepresentation();
- mLocalRepresentation = preset.getFilterRepresentationCopyFrom(filterRepresentation);
- if (mShowParameter == SHOW_VALUE_UNDEFINED && filterRepresentation != null) {
- boolean show = filterRepresentation.showParameterValue();
- mShowParameter = show ? SHOW_VALUE_INT : SHOW_VALUE_OFF;
- }
-
- }
- return mLocalRepresentation;
- }
-
- /**
- * Call this to update the preset in MasterImage with the current representation
- * returned by getLocalRepresentation. This causes the preview bitmap to be
- * regenerated.
- */
- public void commitLocalRepresentation() {
- commitLocalRepresentation(getLocalRepresentation());
- }
-
- /**
- * Call this to update the preset in MasterImage with a given representation.
- * This causes the preview bitmap to be regenerated.
- */
- public void commitLocalRepresentation(FilterRepresentation rep) {
- ArrayList<FilterRepresentation> filter = new ArrayList<FilterRepresentation>(1);
- filter.add(rep);
- commitLocalRepresentation(filter);
- }
-
- /**
- * Call this to update the preset in MasterImage with a collection of FilterRepresnations.
- * This causes the preview bitmap to be regenerated.
- */
- public void commitLocalRepresentation(Collection<FilterRepresentation> reps) {
- ImagePreset preset = MasterImage.getImage().getPreset();
- preset.updateFilterRepresentations(reps);
- if (mButton != null) {
- updateText();
- }
- if (mChangesGeometry) {
- // Regenerate both the filtered and the geometry-only bitmaps
- MasterImage.getImage().updatePresets(true);
- } else {
- // Regenerate only the filtered bitmap.
- MasterImage.getImage().invalidateFiltersOnly();
- }
- preset.fillImageStateAdapter(MasterImage.getImage().getState());
- }
-
- /**
- * This is called in response to a click to apply and leave the editor.
- */
- public void finalApplyCalled() {
- commitLocalRepresentation();
- }
-
- protected void updateText() {
- String s = "";
- if (mLocalRepresentation != null) {
- s = mContext.getString(mLocalRepresentation.getTextId());
- }
- mButton.setText(calculateUserMessage(mContext, s, ""));
- }
-
- /**
- * called after the filter is set and the select is called
- */
- public void reflectCurrentFilter() {
- mLocalRepresentation = null;
- FilterRepresentation representation = getLocalRepresentation();
- if (representation != null && mFilterTitle != null && representation.getTextId() != 0) {
- String text = mContext.getString(representation.getTextId()).toUpperCase();
- mFilterTitle.setText(text);
- updateText();
- }
- }
-
- public boolean useUtilityPanel() {
- return true;
- }
-
- public void openUtilityPanel(LinearLayout mAccessoryViewList) {
- setMenuIcon(false);
- if (mImageShow != null) {
- mImageShow.openUtilityPanel(mAccessoryViewList);
- }
- }
-
- protected void setMenuIcon(boolean on) {
- mEditTitle.setCompoundDrawablesRelativeWithIntrinsicBounds(
- 0, 0, on ? R.drawable.filtershow_menu_marker : 0, 0);
- }
-
- protected void createMenu(int[] strId, View button) {
- PopupMenu pmenu = new PopupMenu(mContext, button);
- Menu menu = pmenu.getMenu();
- for (int i = 0; i < strId.length; i++) {
- menu.add(Menu.NONE, Menu.FIRST + i, 0, mContext.getString(strId[i]));
- }
- setMenuIcon(true);
-
- }
-
- public Control[] getControls() {
- return null;
- }
- @Override
- public void onStartTrackingTouch(SeekBar arg0) {
-
- }
-
- @Override
- public void onStopTrackingTouch(SeekBar arg0) {
-
- }
-
- @Override
- public void swapLeft(MenuItem item) {
-
- }
-
- @Override
- public void swapRight(MenuItem item) {
-
- }
-
- public void detach() {
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorChanSat.java b/src/com/android/gallery3d/filtershow/editors/EditorChanSat.java
deleted file mode 100644
index 7e31f09ae..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorChanSat.java
+++ /dev/null
@@ -1,227 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.os.Handler;
-import android.view.MenuItem;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.widget.LinearLayout;
-import android.widget.PopupMenu;
-import android.widget.SeekBar.OnSeekBarChangeListener;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.controller.BasicParameterStyle;
-import com.android.gallery3d.filtershow.controller.FilterView;
-import com.android.gallery3d.filtershow.controller.Parameter;
-import com.android.gallery3d.filtershow.filters.FilterChanSatRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-import com.android.gallery3d.filtershow.pipeline.RenderingRequest;
-import com.android.gallery3d.filtershow.pipeline.RenderingRequestCaller;
-
-public class EditorChanSat extends ParametricEditor implements OnSeekBarChangeListener, FilterView {
- public static final int ID = R.id.editorChanSat;
- private final String LOGTAG = "EditorGrunge";
- private SwapButton mButton;
- private final Handler mHandler = new Handler();
-
- int[] mMenuStrings = {
- R.string.editor_chan_sat_main,
- R.string.editor_chan_sat_red,
- R.string.editor_chan_sat_yellow,
- R.string.editor_chan_sat_green,
- R.string.editor_chan_sat_cyan,
- R.string.editor_chan_sat_blue,
- R.string.editor_chan_sat_magenta
- };
-
- String mCurrentlyEditing = null;
-
- public EditorChanSat() {
- super(ID, R.layout.filtershow_default_editor, R.id.basicEditor);
- }
-
- @Override
- public String calculateUserMessage(Context context, String effectName, Object parameterValue) {
- FilterRepresentation rep = getLocalRepresentation();
- if (rep == null || !(rep instanceof FilterChanSatRepresentation)) {
- return "";
- }
- FilterChanSatRepresentation csrep = (FilterChanSatRepresentation) rep;
- int mode = csrep.getParameterMode();
- String paramString;
-
- paramString = mContext.getString(mMenuStrings[mode]);
-
- int val = csrep.getCurrentParameter();
- return paramString + ((val > 0) ? " +" : " ") + val;
- }
-
- @Override
- public void openUtilityPanel(final LinearLayout accessoryViewList) {
- mButton = (SwapButton) accessoryViewList.findViewById(R.id.applyEffect);
- mButton.setText(mContext.getString(R.string.editor_chan_sat_main));
-
- final PopupMenu popupMenu = new PopupMenu(mImageShow.getActivity(), mButton);
-
- popupMenu.getMenuInflater().inflate(R.menu.filtershow_menu_chan_sat, popupMenu.getMenu());
-
- popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {
- @Override
- public boolean onMenuItemClick(MenuItem item) {
- selectMenuItem(item);
- return true;
- }
- });
- mButton.setOnClickListener(new OnClickListener() {
- @Override
- public void onClick(View arg0) {
- popupMenu.show();
- }
- });
- mButton.setListener(this);
-
- FilterChanSatRepresentation csrep = getChanSatRep();
- String menuString = mContext.getString(mMenuStrings[0]);
- switchToMode(csrep, FilterChanSatRepresentation.MODE_MASTER, menuString);
-
- }
-
- public int getParameterIndex(int id) {
- switch (id) {
- case R.id.editor_chan_sat_main:
- return FilterChanSatRepresentation.MODE_MASTER;
- case R.id.editor_chan_sat_red:
- return FilterChanSatRepresentation.MODE_RED;
- case R.id.editor_chan_sat_yellow:
- return FilterChanSatRepresentation.MODE_YELLOW;
- case R.id.editor_chan_sat_green:
- return FilterChanSatRepresentation.MODE_GREEN;
- case R.id.editor_chan_sat_cyan:
- return FilterChanSatRepresentation.MODE_CYAN;
- case R.id.editor_chan_sat_blue:
- return FilterChanSatRepresentation.MODE_BLUE;
- case R.id.editor_chan_sat_magenta:
- return FilterChanSatRepresentation.MODE_MAGENTA;
- }
- return -1;
- }
-
- @Override
- public void detach() {
- mButton.setListener(null);
- mButton.setOnClickListener(null);
- }
-
- private void updateSeekBar(FilterChanSatRepresentation rep) {
- mControl.updateUI();
- }
-
- @Override
- protected Parameter getParameterToEdit(FilterRepresentation rep) {
- if (rep instanceof FilterChanSatRepresentation) {
- FilterChanSatRepresentation csrep = (FilterChanSatRepresentation) rep;
- Parameter param = csrep.getFilterParameter(csrep.getParameterMode());
- if (param instanceof BasicParameterStyle) {
- param.setFilterView(EditorChanSat.this);
- }
- return param;
- }
- return null;
- }
-
- private FilterChanSatRepresentation getChanSatRep() {
- FilterRepresentation rep = getLocalRepresentation();
- if (rep != null
- && rep instanceof FilterChanSatRepresentation) {
- FilterChanSatRepresentation csrep = (FilterChanSatRepresentation) rep;
- return csrep;
- }
- return null;
- }
-
- @Override
- public void computeIcon(int n, RenderingRequestCaller caller) {
- FilterChanSatRepresentation rep = getChanSatRep();
- if (rep == null) return;
- rep = (FilterChanSatRepresentation) rep.copy();
- ImagePreset preset = new ImagePreset();
- preset.addFilter(rep);
- Bitmap src = MasterImage.getImage().getThumbnailBitmap();
- RenderingRequest.post(null, src, preset, RenderingRequest.STYLE_ICON_RENDERING,
- caller);
- }
-
- protected void selectMenuItem(MenuItem item) {
- if (getLocalRepresentation() != null
- && getLocalRepresentation() instanceof FilterChanSatRepresentation) {
- FilterChanSatRepresentation csrep =
- (FilterChanSatRepresentation) getLocalRepresentation();
-
- switchToMode(csrep, getParameterIndex(item.getItemId()), item.getTitle().toString());
-
- }
- }
-
- protected void switchToMode(FilterChanSatRepresentation csrep, int mode, String title) {
- csrep.setParameterMode(mode);
- mCurrentlyEditing = title;
- mButton.setText(mCurrentlyEditing);
- {
- Parameter param = getParameterToEdit(csrep);
-
- control(param, mEditControl);
- }
- updateSeekBar(csrep);
- mView.invalidate();
- }
-
- @Override
- public void swapLeft(MenuItem item) {
- super.swapLeft(item);
- mButton.setTranslationX(0);
- mButton.animate().translationX(mButton.getWidth()).setDuration(SwapButton.ANIM_DURATION);
- Runnable updateButton = new Runnable() {
- @Override
- public void run() {
- mButton.animate().cancel();
- mButton.setTranslationX(0);
- }
- };
- mHandler.postDelayed(updateButton, SwapButton.ANIM_DURATION);
- selectMenuItem(item);
- }
-
- @Override
- public void swapRight(MenuItem item) {
- super.swapRight(item);
- mButton.setTranslationX(0);
- mButton.animate().translationX(-mButton.getWidth()).setDuration(SwapButton.ANIM_DURATION);
- Runnable updateButton = new Runnable() {
- @Override
- public void run() {
- mButton.animate().cancel();
- mButton.setTranslationX(0);
- }
- };
- mHandler.postDelayed(updateButton, SwapButton.ANIM_DURATION);
- selectMenuItem(item);
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorCrop.java b/src/com/android/gallery3d/filtershow/editors/EditorCrop.java
deleted file mode 100644
index 511d4ff87..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorCrop.java
+++ /dev/null
@@ -1,168 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.util.Log;
-import android.util.SparseArray;
-import android.view.MenuItem;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.widget.Button;
-import android.widget.FrameLayout;
-import android.widget.LinearLayout;
-import android.widget.PopupMenu;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.filters.FilterCropRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.imageshow.ImageCrop;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-
-public class EditorCrop extends Editor implements EditorInfo {
- public static final String TAG = EditorCrop.class.getSimpleName();
- public static final int ID = R.id.editorCrop;
-
- // Holder for an aspect ratio it's string id
- protected static final class AspectInfo {
- int mAspectX;
- int mAspectY;
- int mStringId;
- AspectInfo(int stringID, int x, int y) {
- mStringId = stringID;
- mAspectX = x;
- mAspectY = y;
- }
- };
-
- // Mapping from menu id to aspect ratio
- protected static final SparseArray<AspectInfo> sAspects;
- static {
- sAspects = new SparseArray<AspectInfo>();
- sAspects.put(R.id.crop_menu_1to1, new AspectInfo(R.string.aspect1to1_effect, 1, 1));
- sAspects.put(R.id.crop_menu_4to3, new AspectInfo(R.string.aspect4to3_effect, 4, 3));
- sAspects.put(R.id.crop_menu_3to4, new AspectInfo(R.string.aspect3to4_effect, 3, 4));
- sAspects.put(R.id.crop_menu_5to7, new AspectInfo(R.string.aspect5to7_effect, 5, 7));
- sAspects.put(R.id.crop_menu_7to5, new AspectInfo(R.string.aspect7to5_effect, 7, 5));
- sAspects.put(R.id.crop_menu_none, new AspectInfo(R.string.aspectNone_effect, 0, 0));
- sAspects.put(R.id.crop_menu_original, new AspectInfo(R.string.aspectOriginal_effect, 0, 0));
- }
-
- protected ImageCrop mImageCrop;
- private String mAspectString = "";
-
- public EditorCrop() {
- super(ID);
- mChangesGeometry = true;
- }
-
- @Override
- public void createEditor(Context context, FrameLayout frameLayout) {
- super.createEditor(context, frameLayout);
- if (mImageCrop == null) {
- mImageCrop = new ImageCrop(context);
- }
- mView = mImageShow = mImageCrop;
- mImageCrop.setEditor(this);
- }
-
- @Override
- public void reflectCurrentFilter() {
- MasterImage master = MasterImage.getImage();
- master.setCurrentFilterRepresentation(master.getPreset()
- .getFilterWithSerializationName(FilterCropRepresentation.SERIALIZATION_NAME));
- super.reflectCurrentFilter();
- FilterRepresentation rep = getLocalRepresentation();
- if (rep == null || rep instanceof FilterCropRepresentation) {
- mImageCrop.setFilterCropRepresentation((FilterCropRepresentation) rep);
- } else {
- Log.w(TAG, "Could not reflect current filter, not of type: "
- + FilterCropRepresentation.class.getSimpleName());
- }
- mImageCrop.invalidate();
- }
-
- @Override
- public void finalApplyCalled() {
- commitLocalRepresentation(mImageCrop.getFinalRepresentation());
- }
-
- @Override
- public void openUtilityPanel(final LinearLayout accessoryViewList) {
- Button view = (Button) accessoryViewList.findViewById(R.id.applyEffect);
- view.setText(mContext.getString(R.string.crop));
- view.setOnClickListener(new OnClickListener() {
- @Override
- public void onClick(View arg0) {
- showPopupMenu(accessoryViewList);
- }
- });
- }
-
- private void changeCropAspect(int itemId) {
- AspectInfo info = sAspects.get(itemId);
- if (info == null) {
- throw new IllegalArgumentException("Invalid resource ID: " + itemId);
- }
- if (itemId == R.id.crop_menu_original) {
- mImageCrop.applyOriginalAspect();
- } else if (itemId == R.id.crop_menu_none) {
- mImageCrop.applyFreeAspect();
- } else {
- mImageCrop.applyAspect(info.mAspectX, info.mAspectY);
- }
- setAspectString(mContext.getString(info.mStringId));
- }
-
- private void showPopupMenu(LinearLayout accessoryViewList) {
- final Button button = (Button) accessoryViewList.findViewById(R.id.applyEffect);
- final PopupMenu popupMenu = new PopupMenu(mImageShow.getActivity(), button);
- popupMenu.getMenuInflater().inflate(R.menu.filtershow_menu_crop, popupMenu.getMenu());
- popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {
- @Override
- public boolean onMenuItemClick(MenuItem item) {
- changeCropAspect(item.getItemId());
- return true;
- }
- });
- popupMenu.show();
- }
-
- @Override
- public boolean showsSeekBar() {
- return false;
- }
-
- @Override
- public int getTextId() {
- return R.string.crop;
- }
-
- @Override
- public int getOverlayId() {
- return R.drawable.filtershow_button_geometry_crop;
- }
-
- @Override
- public boolean getOverlayOnly() {
- return true;
- }
-
- private void setAspectString(String s) {
- mAspectString = s;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorCurves.java b/src/com/android/gallery3d/filtershow/editors/EditorCurves.java
deleted file mode 100644
index 83fbced79..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorCurves.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.widget.FrameLayout;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.filters.FilterCurvesRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.imageshow.ImageCurves;
-
-public class EditorCurves extends Editor {
- public static final int ID = R.id.imageCurves;
- ImageCurves mImageCurves;
-
- public EditorCurves() {
- super(ID);
- }
-
- @Override
- public void createEditor(Context context, FrameLayout frameLayout) {
- super.createEditor(context, frameLayout);
- mView = mImageShow = mImageCurves = new ImageCurves(context);
- mImageCurves.setEditor(this);
- }
-
- @Override
- public void reflectCurrentFilter() {
- super.reflectCurrentFilter();
- FilterRepresentation rep = getLocalRepresentation();
- if (rep != null && getLocalRepresentation() instanceof FilterCurvesRepresentation) {
- FilterCurvesRepresentation drawRep = (FilterCurvesRepresentation) rep;
- mImageCurves.setFilterDrawRepresentation(drawRep);
- }
- }
-
- @Override
- public boolean showsSeekBar() {
- return false;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorDraw.java b/src/com/android/gallery3d/filtershow/editors/EditorDraw.java
deleted file mode 100644
index 4b09051e2..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorDraw.java
+++ /dev/null
@@ -1,158 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.app.Dialog;
-import android.content.Context;
-import android.view.MenuItem;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.view.WindowManager.LayoutParams;
-import android.widget.Button;
-import android.widget.FrameLayout;
-import android.widget.LinearLayout;
-import android.widget.PopupMenu;
-import android.widget.SeekBar;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.colorpicker.ColorGridDialog;
-import com.android.gallery3d.filtershow.colorpicker.RGBListener;
-import com.android.gallery3d.filtershow.filters.FilterDrawRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.ImageFilterDraw;
-import com.android.gallery3d.filtershow.imageshow.ImageDraw;
-
-public class EditorDraw extends Editor {
- private static final String LOGTAG = "EditorDraw";
- public static final int ID = R.id.editorDraw;
- public ImageDraw mImageDraw;
-
- public EditorDraw() {
- super(ID);
- }
-
- @Override
- public void createEditor(Context context, FrameLayout frameLayout) {
- super.createEditor(context, frameLayout);
- mView = mImageShow = mImageDraw = new ImageDraw(context);
- mImageDraw.setEditor(this);
-
- }
-
- @Override
- public void reflectCurrentFilter() {
- super.reflectCurrentFilter();
- FilterRepresentation rep = getLocalRepresentation();
-
- if (rep != null && getLocalRepresentation() instanceof FilterDrawRepresentation) {
- FilterDrawRepresentation drawRep = (FilterDrawRepresentation) getLocalRepresentation();
- mImageDraw.setFilterDrawRepresentation(drawRep);
- }
- }
-
- @Override
- public void openUtilityPanel(final LinearLayout accessoryViewList) {
- Button view = (Button) accessoryViewList.findViewById(R.id.applyEffect);
- view.setText(mContext.getString(R.string.draw_style));
- view.setOnClickListener(new OnClickListener() {
-
- @Override
- public void onClick(View arg0) {
- showPopupMenu(accessoryViewList);
- }
- });
- }
-
- @Override
- public boolean showsSeekBar() {
- return false;
- }
-
- private void showPopupMenu(LinearLayout accessoryViewList) {
- final Button button = (Button) accessoryViewList.findViewById(
- R.id.applyEffect);
- if (button == null) {
- return;
- }
- final PopupMenu popupMenu = new PopupMenu(mImageShow.getActivity(), button);
- popupMenu.getMenuInflater().inflate(R.menu.filtershow_menu_draw, popupMenu.getMenu());
- popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {
-
- @Override
- public boolean onMenuItemClick(MenuItem item) {
- ImageFilterDraw filter = (ImageFilterDraw) mImageShow.getCurrentFilter();
- if (item.getItemId() == R.id.draw_menu_color) {
- showColorGrid(item);
- } else if (item.getItemId() == R.id.draw_menu_size) {
- showSizeDialog(item);
- } else if (item.getItemId() == R.id.draw_menu_style_brush_marker) {
- ImageDraw idraw = (ImageDraw) mImageShow;
- idraw.setStyle(ImageFilterDraw.BRUSH_STYLE_MARKER);
- } else if (item.getItemId() == R.id.draw_menu_style_brush_spatter) {
- ImageDraw idraw = (ImageDraw) mImageShow;
- idraw.setStyle(ImageFilterDraw.BRUSH_STYLE_SPATTER);
- } else if (item.getItemId() == R.id.draw_menu_style_line) {
- ImageDraw idraw = (ImageDraw) mImageShow;
- idraw.setStyle(ImageFilterDraw.SIMPLE_STYLE);
- } else if (item.getItemId() == R.id.draw_menu_clear) {
- ImageDraw idraw = (ImageDraw) mImageShow;
- idraw.resetParameter();
- commitLocalRepresentation();
- }
- mView.invalidate();
- return true;
- }
- });
- popupMenu.show();
- }
-
- public void showSizeDialog(final MenuItem item) {
- FilterShowActivity ctx = mImageShow.getActivity();
- final Dialog dialog = new Dialog(ctx);
- dialog.setTitle(R.string.draw_size_title);
- dialog.setContentView(R.layout.filtershow_draw_size);
- final SeekBar bar = (SeekBar) dialog.findViewById(R.id.sizeSeekBar);
- ImageDraw idraw = (ImageDraw) mImageShow;
- bar.setProgress(idraw.getSize());
- Button button = (Button) dialog.findViewById(R.id.sizeAcceptButton);
- button.setOnClickListener(new OnClickListener() {
-
- @Override
- public void onClick(View arg0) {
- int p = bar.getProgress();
- ImageDraw idraw = (ImageDraw) mImageShow;
- idraw.setSize(p + 1);
- dialog.dismiss();
- }
- });
- dialog.show();
- }
-
- public void showColorGrid(final MenuItem item) {
- RGBListener cl = new RGBListener() {
- @Override
- public void setColor(int rgb) {
- ImageDraw idraw = (ImageDraw) mImageShow;
- idraw.setColor(rgb);
- }
- };
- ColorGridDialog cpd = new ColorGridDialog(mImageShow.getActivity(), cl);
- cpd.show();
- LayoutParams params = cpd.getWindow().getAttributes();
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorGrad.java b/src/com/android/gallery3d/filtershow/editors/EditorGrad.java
deleted file mode 100644
index f427ccbd8..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorGrad.java
+++ /dev/null
@@ -1,315 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.view.MenuItem;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.widget.Button;
-import android.widget.FrameLayout;
-import android.widget.LinearLayout;
-import android.widget.PopupMenu;
-import android.widget.SeekBar;
-import android.widget.SeekBar.OnSeekBarChangeListener;
-import android.widget.ToggleButton;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.controller.Control;
-import com.android.gallery3d.filtershow.controller.FilterView;
-import com.android.gallery3d.filtershow.controller.Parameter;
-import com.android.gallery3d.filtershow.controller.ParameterActionAndInt;
-import com.android.gallery3d.filtershow.filters.FilterGradRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.imageshow.ImageGrad;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-
-public class EditorGrad extends ParametricEditor
- implements OnSeekBarChangeListener, ParameterActionAndInt {
- private static final String LOGTAG = "EditorGrad";
- public static final int ID = R.id.editorGrad;
- PopupMenu mPopupMenu;
- ToggleButton mAddModeButton;
- String mEffectName = "";
- private static final int MODE_BRIGHTNESS = FilterGradRepresentation.PARAM_BRIGHTNESS;
- private static final int MODE_SATURATION = FilterGradRepresentation.PARAM_SATURATION;
- private static final int MODE_CONTRAST = FilterGradRepresentation.PARAM_CONTRAST;
- private static final int ADD_ICON = R.drawable.ic_grad_add;
- private static final int DEL_ICON = R.drawable.ic_grad_del;
- private int mSliderMode = MODE_BRIGHTNESS;
- ImageGrad mImageGrad;
-
- public EditorGrad() {
- super(ID, R.layout.filtershow_grad_editor, R.id.gradEditor);
- }
-
- @Override
- public void createEditor(Context context, FrameLayout frameLayout) {
- super.createEditor(context, frameLayout);
- mImageGrad = (ImageGrad) mImageShow;
- mImageGrad.setEditor(this);
-
- }
-
- public void clearAddMode() {
- mAddModeButton.setChecked(false);
- FilterRepresentation tmpRep = getLocalRepresentation();
- if (tmpRep instanceof FilterGradRepresentation) {
- updateMenuItems((FilterGradRepresentation) tmpRep);
- }
- }
-
- @Override
- public void reflectCurrentFilter() {
- super.reflectCurrentFilter();
- FilterRepresentation tmpRep = getLocalRepresentation();
- if (tmpRep instanceof FilterGradRepresentation) {
- FilterGradRepresentation rep = (FilterGradRepresentation) tmpRep;
- boolean f = rep.showParameterValue();
-
- mImageGrad.setRepresentation(rep);
- }
- }
-
- public void updateSeekBar(FilterGradRepresentation rep) {
- mControl.updateUI();
- }
-
- @Override
- public void onProgressChanged(SeekBar sbar, int progress, boolean arg2) {
- FilterRepresentation tmpRep = getLocalRepresentation();
- if (tmpRep instanceof FilterGradRepresentation) {
- FilterGradRepresentation rep = (FilterGradRepresentation) tmpRep;
- int min = rep.getParameterMin(mSliderMode);
- int value = progress + min;
- rep.setParameter(mSliderMode, value);
- mView.invalidate();
- commitLocalRepresentation();
- }
- }
-
- @Override
- public void openUtilityPanel(final LinearLayout accessoryViewList) {
- Button view = (Button) accessoryViewList.findViewById(R.id.applyEffect);
- view.setText(mContext.getString(R.string.editor_grad_brightness));
- view.setOnClickListener(new OnClickListener() {
- @Override
- public void onClick(View arg0) {
- showPopupMenu(accessoryViewList);
- }
- });
-
- setUpPopupMenu(view);
- setEffectName();
- }
-
- private void updateMenuItems(FilterGradRepresentation rep) {
- int n = rep.getNumberOfBands();
- }
-
- public void setEffectName() {
- if (mPopupMenu != null) {
- MenuItem item = mPopupMenu.getMenu().findItem(R.id.editor_grad_brightness);
- mEffectName = item.getTitle().toString();
- }
- }
-
- private void showPopupMenu(LinearLayout accessoryViewList) {
- Button button = (Button) accessoryViewList.findViewById(R.id.applyEffect);
- if (button == null) {
- return;
- }
-
- if (mPopupMenu == null) {
- setUpPopupMenu(button);
- }
- mPopupMenu.show();
- }
-
- private void setUpPopupMenu(Button button) {
- mPopupMenu = new PopupMenu(mImageShow.getActivity(), button);
- mPopupMenu.getMenuInflater()
- .inflate(R.menu.filtershow_menu_grad, mPopupMenu.getMenu());
- FilterGradRepresentation rep = (FilterGradRepresentation) getLocalRepresentation();
- if (rep == null) {
- return;
- }
- updateMenuItems(rep);
- hackFixStrings(mPopupMenu.getMenu());
- setEffectName();
- updateText();
-
- mPopupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {
- @Override
- public boolean onMenuItemClick(MenuItem item) {
- FilterRepresentation tmpRep = getLocalRepresentation();
-
- if (tmpRep instanceof FilterGradRepresentation) {
- FilterGradRepresentation rep = (FilterGradRepresentation) tmpRep;
- int cmdID = item.getItemId();
- switch (cmdID) {
- case R.id.editor_grad_brightness:
- mSliderMode = MODE_BRIGHTNESS;
- mEffectName = item.getTitle().toString();
- break;
- case R.id.editor_grad_contrast:
- mSliderMode = MODE_CONTRAST;
- mEffectName = item.getTitle().toString();
- break;
- case R.id.editor_grad_saturation:
- mSliderMode = MODE_SATURATION;
- mEffectName = item.getTitle().toString();
- break;
- }
- updateMenuItems(rep);
- updateSeekBar(rep);
-
- commitLocalRepresentation();
- mView.invalidate();
- }
- return true;
- }
- });
- }
-
- @Override
- public String calculateUserMessage(Context context, String effectName, Object parameterValue) {
- FilterGradRepresentation rep = getGradRepresentation();
- if (rep == null) {
- return mEffectName;
- }
- int val = rep.getParameter(mSliderMode);
- return mEffectName.toUpperCase() + ((val > 0) ? " +" : " ") + val;
- }
-
- private FilterGradRepresentation getGradRepresentation() {
- FilterRepresentation tmpRep = getLocalRepresentation();
- if (tmpRep instanceof FilterGradRepresentation) {
- return (FilterGradRepresentation) tmpRep;
- }
- return null;
- }
-
- @Override
- public int getMaximum() {
- FilterGradRepresentation rep = getGradRepresentation();
- if (rep == null) {
- return 0;
- }
- return rep.getParameterMax(mSliderMode);
- }
-
- @Override
- public int getMinimum() {
- FilterGradRepresentation rep = getGradRepresentation();
- if (rep == null) {
- return 0;
- }
- return rep.getParameterMin(mSliderMode);
- }
-
- @Override
- public int getDefaultValue() {
- return 0;
- }
-
- @Override
- public int getValue() {
- FilterGradRepresentation rep = getGradRepresentation();
- if (rep == null) {
- return 0;
- }
- return rep.getParameter(mSliderMode);
- }
-
- @Override
- public String getValueString() {
- return null;
- }
-
- @Override
- public void setValue(int value) {
- FilterGradRepresentation rep = getGradRepresentation();
- if (rep == null) {
- return;
- }
- rep.setParameter(mSliderMode, value);
- }
-
- @Override
- public String getParameterName() {
- return mEffectName;
- }
-
- @Override
- public String getParameterType() {
- return sParameterType;
- }
-
- @Override
- public void setController(Control c) {
-
- }
-
- @Override
- public void fireLeftAction() {
- FilterGradRepresentation rep = getGradRepresentation();
- if (rep == null) {
- return;
- }
- rep.addBand(MasterImage.getImage().getOriginalBounds());
- updateMenuItems(rep);
- updateSeekBar(rep);
-
- commitLocalRepresentation();
- mView.invalidate();
- }
-
- @Override
- public int getLeftIcon() {
- return ADD_ICON;
- }
-
- @Override
- public void fireRightAction() {
- FilterGradRepresentation rep = getGradRepresentation();
- if (rep == null) {
- return;
- }
- rep.deleteCurrentBand();
-
- updateMenuItems(rep);
- updateSeekBar(rep);
- commitLocalRepresentation();
- mView.invalidate();
- }
-
- @Override
- public int getRightIcon() {
- return DEL_ICON;
- }
-
- @Override
- public void setFilterView(FilterView editor) {
-
- }
-
- @Override
- public void copyFrom(Parameter src) {
-
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorInfo.java b/src/com/android/gallery3d/filtershow/editors/EditorInfo.java
deleted file mode 100644
index 75afe49c2..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorInfo.java
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-public interface EditorInfo {
- public int getTextId();
- public int getOverlayId();
- public boolean getOverlayOnly();
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorMirror.java b/src/com/android/gallery3d/filtershow/editors/EditorMirror.java
deleted file mode 100644
index d6d9ee75d..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorMirror.java
+++ /dev/null
@@ -1,109 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.util.Log;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.widget.Button;
-import android.widget.FrameLayout;
-import android.widget.LinearLayout;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.filters.FilterMirrorRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.imageshow.ImageMirror;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-
-public class EditorMirror extends Editor implements EditorInfo {
- public static final String TAG = EditorMirror.class.getSimpleName();
- public static final int ID = R.id.editorFlip;
- ImageMirror mImageMirror;
-
- public EditorMirror() {
- super(ID);
- mChangesGeometry = true;
- }
-
- @Override
- public void createEditor(Context context, FrameLayout frameLayout) {
- super.createEditor(context, frameLayout);
- if (mImageMirror == null) {
- mImageMirror = new ImageMirror(context);
- }
- mView = mImageShow = mImageMirror;
- mImageMirror.setEditor(this);
- }
-
- @Override
- public void reflectCurrentFilter() {
- MasterImage master = MasterImage.getImage();
- master.setCurrentFilterRepresentation(master.getPreset()
- .getFilterWithSerializationName(FilterMirrorRepresentation.SERIALIZATION_NAME));
- super.reflectCurrentFilter();
- FilterRepresentation rep = getLocalRepresentation();
- if (rep == null || rep instanceof FilterMirrorRepresentation) {
- mImageMirror.setFilterMirrorRepresentation((FilterMirrorRepresentation) rep);
- } else {
- Log.w(TAG, "Could not reflect current filter, not of type: "
- + FilterMirrorRepresentation.class.getSimpleName());
- }
- mImageMirror.invalidate();
- }
-
- @Override
- public void openUtilityPanel(final LinearLayout accessoryViewList) {
- final Button button = (Button) accessoryViewList.findViewById(R.id.applyEffect);
- button.setOnClickListener(new OnClickListener() {
- @Override
- public void onClick(View arg0) {
- mImageMirror.flip();
- }
- });
- }
-
- @Override
- public void finalApplyCalled() {
- commitLocalRepresentation(mImageMirror.getFinalRepresentation());
- }
-
- @Override
- public int getTextId() {
- return R.string.mirror;
- }
-
- @Override
- public int getOverlayId() {
- return R.drawable.filtershow_button_geometry_flip;
- }
-
- @Override
- public boolean getOverlayOnly() {
- return true;
- }
-
- @Override
- public boolean showsSeekBar() {
- return false;
- }
-
- @Override
- public boolean showsPopupIndicator() {
- return false;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorPanel.java b/src/com/android/gallery3d/filtershow/editors/EditorPanel.java
deleted file mode 100644
index bc4ca6ab6..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorPanel.java
+++ /dev/null
@@ -1,143 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.app.Activity;
-import android.os.Bundle;
-import android.support.v4.app.Fragment;
-import android.support.v4.app.FragmentTransaction;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.Button;
-import android.widget.ImageButton;
-import android.widget.LinearLayout;
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.history.HistoryManager;
-import com.android.gallery3d.filtershow.category.MainPanel;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.state.StatePanel;
-
-public class EditorPanel extends Fragment {
-
- private static final String LOGTAG = "EditorPanel";
-
- private LinearLayout mMainView;
- private Editor mEditor;
- private int mEditorID;
-
- public void setEditor(int editor) {
- mEditorID = editor;
- }
-
- @Override
- public void onAttach(Activity activity) {
- super.onAttach(activity);
- FilterShowActivity filterShowActivity = (FilterShowActivity) activity;
- mEditor = filterShowActivity.getEditor(mEditorID);
- }
-
- public void cancelCurrentFilter() {
- MasterImage masterImage = MasterImage.getImage();
- HistoryManager adapter = masterImage.getHistory();
-
- int position = adapter.undo();
- masterImage.onHistoryItemClick(position);
- ((FilterShowActivity)getActivity()).invalidateViews();
- }
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
- FilterShowActivity activity = (FilterShowActivity) getActivity();
- if (mMainView != null) {
- if (mMainView.getParent() != null) {
- ViewGroup parent = (ViewGroup) mMainView.getParent();
- parent.removeView(mMainView);
- }
- showImageStatePanel(activity.isShowingImageStatePanel());
- return mMainView;
- }
- mMainView = (LinearLayout) inflater.inflate(R.layout.filtershow_editor_panel, null);
-
- View actionControl = mMainView.findViewById(R.id.panelAccessoryViewList);
- View editControl = mMainView.findViewById(R.id.controlArea);
- ImageButton cancelButton = (ImageButton) mMainView.findViewById(R.id.cancelFilter);
- ImageButton applyButton = (ImageButton) mMainView.findViewById(R.id.applyFilter);
- Button editTitle = (Button) mMainView.findViewById(R.id.applyEffect);
- cancelButton.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- cancelCurrentFilter();
- FilterShowActivity activity = (FilterShowActivity) getActivity();
- activity.backToMain();
- }
- });
-
- Button toggleState = (Button) mMainView.findViewById(R.id.toggle_state);
- mEditor = activity.getEditor(mEditorID);
- if (mEditor != null) {
- mEditor.setUpEditorUI(actionControl, editControl, editTitle, toggleState);
- mEditor.reflectCurrentFilter();
- if (mEditor.useUtilityPanel()) {
- mEditor.openUtilityPanel((LinearLayout) actionControl);
- }
- }
- applyButton.setOnClickListener(new View.OnClickListener() {
- @Override
- public void onClick(View v) {
- FilterShowActivity activity = (FilterShowActivity) getActivity();
- mEditor.finalApplyCalled();
- activity.backToMain();
- }
- });
-
- showImageStatePanel(activity.isShowingImageStatePanel());
- return mMainView;
- }
-
- @Override
- public void onDetach() {
- if (mEditor != null) {
- mEditor.detach();
- }
- super.onDetach();
- }
-
- public void showImageStatePanel(boolean show) {
- if (mMainView.findViewById(R.id.state_panel_container) == null) {
- return;
- }
- FragmentTransaction transaction = getChildFragmentManager().beginTransaction();
- Fragment panel = getActivity().getSupportFragmentManager().findFragmentByTag(
- MainPanel.FRAGMENT_TAG);
- if (panel == null || panel instanceof MainPanel) {
- transaction.setCustomAnimations(android.R.anim.fade_in, android.R.anim.fade_out);
- }
- if (show) {
- StatePanel statePanel = new StatePanel();
- transaction.replace(R.id.state_panel_container, statePanel, StatePanel.FRAGMENT_TAG);
- } else {
- Fragment statePanel = getChildFragmentManager().findFragmentByTag(StatePanel.FRAGMENT_TAG);
- if (statePanel != null) {
- transaction.remove(statePanel);
- }
- }
- transaction.commit();
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorRedEye.java b/src/com/android/gallery3d/filtershow/editors/EditorRedEye.java
deleted file mode 100644
index b0e88dd44..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorRedEye.java
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.widget.FrameLayout;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.filters.FilterRedEyeRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.imageshow.ImageRedEye;
-
-/**
- * The editor with no slider for filters without UI
- */
-public class EditorRedEye extends Editor {
- public static int ID = R.id.editorRedEye;
- private final String LOGTAG = "EditorRedEye";
- ImageRedEye mImageRedEyes;
-
- public EditorRedEye() {
- super(ID);
- }
-
- protected EditorRedEye(int id) {
- super(id);
- }
-
- @Override
- public void createEditor(Context context, FrameLayout frameLayout) {
- super.createEditor(context, frameLayout);
- mView = mImageShow = mImageRedEyes= new ImageRedEye(context);
- mImageRedEyes.setEditor(this);
- }
-
- @Override
- public void reflectCurrentFilter() {
- super.reflectCurrentFilter();
- FilterRepresentation rep = getLocalRepresentation();
- if (rep != null && getLocalRepresentation() instanceof FilterRedEyeRepresentation) {
- FilterRedEyeRepresentation redEyeRep = (FilterRedEyeRepresentation) rep;
-
- mImageRedEyes.setRepresentation(redEyeRep);
- }
- }
-
- @Override
- public boolean showsSeekBar() {
- return false;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorRotate.java b/src/com/android/gallery3d/filtershow/editors/EditorRotate.java
deleted file mode 100644
index 9452bf0c0..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorRotate.java
+++ /dev/null
@@ -1,112 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.util.Log;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.widget.Button;
-import android.widget.FrameLayout;
-import android.widget.LinearLayout;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRotateRepresentation;
-import com.android.gallery3d.filtershow.imageshow.ImageRotate;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-
-public class EditorRotate extends Editor implements EditorInfo {
- public static final String TAG = EditorRotate.class.getSimpleName();
- public static final int ID = R.id.editorRotate;
- ImageRotate mImageRotate;
-
- public EditorRotate() {
- super(ID);
- mChangesGeometry = true;
- }
-
- @Override
- public void createEditor(Context context, FrameLayout frameLayout) {
- super.createEditor(context, frameLayout);
- if (mImageRotate == null) {
- mImageRotate = new ImageRotate(context);
- }
- mView = mImageShow = mImageRotate;
- mImageRotate.setEditor(this);
- }
-
- @Override
- public void reflectCurrentFilter() {
- MasterImage master = MasterImage.getImage();
- master.setCurrentFilterRepresentation(master.getPreset()
- .getFilterWithSerializationName(FilterRotateRepresentation.SERIALIZATION_NAME));
- super.reflectCurrentFilter();
- FilterRepresentation rep = getLocalRepresentation();
- if (rep == null || rep instanceof FilterRotateRepresentation) {
- mImageRotate.setFilterRotateRepresentation((FilterRotateRepresentation) rep);
- } else {
- Log.w(TAG, "Could not reflect current filter, not of type: "
- + FilterRotateRepresentation.class.getSimpleName());
- }
- mImageRotate.invalidate();
- }
-
- @Override
- public void openUtilityPanel(final LinearLayout accessoryViewList) {
- final Button button = (Button) accessoryViewList.findViewById(R.id.applyEffect);
- button.setOnClickListener(new OnClickListener() {
- @Override
- public void onClick(View arg0) {
- mImageRotate.rotate();
- String displayVal = mContext.getString(getTextId()) + " "
- + mImageRotate.getLocalValue();
- button.setText(displayVal);
- }
- });
- }
-
- @Override
- public void finalApplyCalled() {
- commitLocalRepresentation(mImageRotate.getFinalRepresentation());
- }
-
- @Override
- public int getTextId() {
- return R.string.rotate;
- }
-
- @Override
- public int getOverlayId() {
- return R.drawable.filtershow_button_geometry_rotate;
- }
-
- @Override
- public boolean getOverlayOnly() {
- return true;
- }
-
- @Override
- public boolean showsSeekBar() {
- return false;
- }
-
- @Override
- public boolean showsPopupIndicator() {
- return false;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorStraighten.java b/src/com/android/gallery3d/filtershow/editors/EditorStraighten.java
deleted file mode 100644
index ff84ba8f9..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorStraighten.java
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.util.Log;
-import android.widget.FrameLayout;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterStraightenRepresentation;
-import com.android.gallery3d.filtershow.imageshow.ImageStraighten;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-
-public class EditorStraighten extends Editor implements EditorInfo {
- public static final String TAG = EditorStraighten.class.getSimpleName();
- public static final int ID = R.id.editorStraighten;
- ImageStraighten mImageStraighten;
-
- public EditorStraighten() {
- super(ID);
- mShowParameter = SHOW_VALUE_INT;
- mChangesGeometry = true;
- }
-
- @Override
- public String calculateUserMessage(Context context, String effectName, Object parameterValue) {
- String apply = context.getString(R.string.apply_effect);
- apply += " " + effectName;
- return apply.toUpperCase();
- }
-
- @Override
- public void createEditor(Context context, FrameLayout frameLayout) {
- super.createEditor(context, frameLayout);
- if (mImageStraighten == null) {
- mImageStraighten = new ImageStraighten(context);
- }
- mView = mImageShow = mImageStraighten;
- mImageStraighten.setEditor(this);
- }
-
- @Override
- public void reflectCurrentFilter() {
- MasterImage master = MasterImage.getImage();
- master.setCurrentFilterRepresentation(master.getPreset().getFilterWithSerializationName(
- FilterStraightenRepresentation.SERIALIZATION_NAME));
- super.reflectCurrentFilter();
- FilterRepresentation rep = getLocalRepresentation();
- if (rep == null || rep instanceof FilterStraightenRepresentation) {
- mImageStraighten
- .setFilterStraightenRepresentation((FilterStraightenRepresentation) rep);
- } else {
- Log.w(TAG, "Could not reflect current filter, not of type: "
- + FilterStraightenRepresentation.class.getSimpleName());
- }
- mImageStraighten.invalidate();
- }
-
- @Override
- public void finalApplyCalled() {
- commitLocalRepresentation(mImageStraighten.getFinalRepresentation());
- }
-
- @Override
- public int getTextId() {
- return R.string.straighten;
- }
-
- @Override
- public int getOverlayId() {
- return R.drawable.filtershow_button_geometry_straighten;
- }
-
- @Override
- public boolean getOverlayOnly() {
- return true;
- }
-
- @Override
- public boolean showsSeekBar() {
- return false;
- }
-
- @Override
- public boolean showsPopupIndicator() {
- return false;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorTinyPlanet.java b/src/com/android/gallery3d/filtershow/editors/EditorTinyPlanet.java
deleted file mode 100644
index 9376fbef0..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorTinyPlanet.java
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.widget.FrameLayout;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterTinyPlanetRepresentation;
-import com.android.gallery3d.filtershow.imageshow.ImageTinyPlanet;
-
-public class EditorTinyPlanet extends BasicEditor {
- public static final int ID = R.id.tinyPlanetEditor;
- private static final String LOGTAG = "EditorTinyPlanet";
- ImageTinyPlanet mImageTinyPlanet;
-
- public EditorTinyPlanet() {
- super(ID, R.layout.filtershow_tiny_planet_editor, R.id.imageTinyPlanet);
- }
-
- @Override
- public void createEditor(Context context, FrameLayout frameLayout) {
- super.createEditor(context, frameLayout);
- mImageTinyPlanet = (ImageTinyPlanet) mImageShow;
- mImageTinyPlanet.setEditor(this);
- }
-
- @Override
- public void reflectCurrentFilter() {
- super.reflectCurrentFilter();
- FilterRepresentation rep = getLocalRepresentation();
- if (rep != null && rep instanceof FilterTinyPlanetRepresentation) {
- FilterTinyPlanetRepresentation drawRep = (FilterTinyPlanetRepresentation) rep;
- mImageTinyPlanet.setRepresentation(drawRep);
- }
- }
-
- public void updateUI() {
- if (mControl != null) {
- mControl.updateUI();
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorVignette.java b/src/com/android/gallery3d/filtershow/editors/EditorVignette.java
deleted file mode 100644
index 7127b2188..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorVignette.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.widget.FrameLayout;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterVignetteRepresentation;
-import com.android.gallery3d.filtershow.imageshow.ImageVignette;
-
-public class EditorVignette extends ParametricEditor {
- public static final int ID = R.id.vignetteEditor;
- private static final String LOGTAG = "EditorVignettePlanet";
- ImageVignette mImageVignette;
-
- public EditorVignette() {
- super(ID, R.layout.filtershow_vignette_editor, R.id.imageVignette);
- }
-
- @Override
- public void createEditor(Context context, FrameLayout frameLayout) {
- super.createEditor(context, frameLayout);
- mImageVignette = (ImageVignette) mImageShow;
- mImageVignette.setEditor(this);
- }
-
- @Override
- public void reflectCurrentFilter() {
- super.reflectCurrentFilter();
-
- FilterRepresentation rep = getLocalRepresentation();
- if (rep != null && getLocalRepresentation() instanceof FilterVignetteRepresentation) {
- FilterVignetteRepresentation drawRep = (FilterVignetteRepresentation) rep;
- mImageVignette.setRepresentation(drawRep);
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/EditorZoom.java b/src/com/android/gallery3d/filtershow/editors/EditorZoom.java
deleted file mode 100644
index ea8e3d140..000000000
--- a/src/com/android/gallery3d/filtershow/editors/EditorZoom.java
+++ /dev/null
@@ -1,27 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import com.android.gallery3d.R;
-
-public class EditorZoom extends BasicEditor {
- public static final int ID = R.id.imageZoom;
-
- public EditorZoom() {
- super(ID, R.layout.filtershow_zoom_editor,R.id.imageZoom);
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/ImageOnlyEditor.java b/src/com/android/gallery3d/filtershow/editors/ImageOnlyEditor.java
deleted file mode 100644
index d4e66edf8..000000000
--- a/src/com/android/gallery3d/filtershow/editors/ImageOnlyEditor.java
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.widget.FrameLayout;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.imageshow.ImageShow;
-
-/**
- * The editor with no slider for filters without UI
- */
-public class ImageOnlyEditor extends Editor {
- public final static int ID = R.id.imageOnlyEditor;
- private final String LOGTAG = "ImageOnlyEditor";
-
- public ImageOnlyEditor() {
- super(ID);
- }
-
- protected ImageOnlyEditor(int id) {
- super(id);
- }
-
- public boolean useUtilityPanel() {
- return false;
- }
-
- @Override
- public void createEditor(Context context, FrameLayout frameLayout) {
- super.createEditor(context, frameLayout);
- mView = mImageShow = new ImageShow(context);
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/ParametricEditor.java b/src/com/android/gallery3d/filtershow/editors/ParametricEditor.java
deleted file mode 100644
index 9ec858ca5..000000000
--- a/src/com/android/gallery3d/filtershow/editors/ParametricEditor.java
+++ /dev/null
@@ -1,206 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.graphics.Point;
-import android.util.Log;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.ViewGroup.LayoutParams;
-import android.view.WindowManager;
-import android.widget.FrameLayout;
-import android.widget.LinearLayout;
-import android.widget.SeekBar;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.controller.ActionSlider;
-import com.android.gallery3d.filtershow.controller.BasicSlider;
-import com.android.gallery3d.filtershow.controller.Control;
-import com.android.gallery3d.filtershow.controller.Parameter;
-import com.android.gallery3d.filtershow.controller.ParameterActionAndInt;
-import com.android.gallery3d.filtershow.controller.ParameterInteger;
-import com.android.gallery3d.filtershow.controller.ParameterStyles;
-import com.android.gallery3d.filtershow.controller.StyleChooser;
-import com.android.gallery3d.filtershow.controller.TitledSlider;
-import com.android.gallery3d.filtershow.filters.FilterBasicRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-
-import java.lang.reflect.Constructor;
-import java.util.HashMap;
-
-public class ParametricEditor extends Editor {
- private int mLayoutID;
- private int mViewID;
- public static int ID = R.id.editorParametric;
- private final String LOGTAG = "ParametricEditor";
- protected Control mControl;
- public static final int MINIMUM_WIDTH = 600;
- public static final int MINIMUM_HEIGHT = 800;
- View mActionButton;
- View mEditControl;
- static HashMap<String, Class> portraitMap = new HashMap<String, Class>();
- static HashMap<String, Class> landscapeMap = new HashMap<String, Class>();
- static {
- portraitMap.put(ParameterInteger.sParameterType, BasicSlider.class);
- landscapeMap.put(ParameterInteger.sParameterType, TitledSlider.class);
- portraitMap.put(ParameterActionAndInt.sParameterType, ActionSlider.class);
- landscapeMap.put(ParameterActionAndInt.sParameterType, ActionSlider.class);
- portraitMap.put(ParameterStyles.sParameterType, StyleChooser.class);
- landscapeMap.put(ParameterStyles.sParameterType, StyleChooser.class);
- }
-
- static Constructor getConstructor(Class cl) {
- try {
- return cl.getConstructor(Context.class, ViewGroup.class);
- } catch (Exception e) {
- return null;
- }
- }
-
- public ParametricEditor() {
- super(ID);
- }
-
- protected ParametricEditor(int id) {
- super(id);
- }
-
- protected ParametricEditor(int id, int layoutID, int viewID) {
- super(id);
- mLayoutID = layoutID;
- mViewID = viewID;
- }
-
- @Override
- public String calculateUserMessage(Context context, String effectName, Object parameterValue) {
- String apply = "";
-
- if (mShowParameter == SHOW_VALUE_INT & useCompact(context)) {
- if (getLocalRepresentation() instanceof FilterBasicRepresentation) {
- FilterBasicRepresentation interval = (FilterBasicRepresentation) getLocalRepresentation();
- apply += " " + effectName.toUpperCase() + " " + interval.getStateRepresentation();
- } else {
- apply += " " + effectName.toUpperCase() + " " + parameterValue;
- }
- } else {
- apply += " " + effectName.toUpperCase();
- }
- return apply;
- }
-
- @Override
- public void createEditor(Context context, FrameLayout frameLayout) {
- super.createEditor(context, frameLayout);
- unpack(mViewID, mLayoutID);
- }
-
- @Override
- public void reflectCurrentFilter() {
- super.reflectCurrentFilter();
- if (getLocalRepresentation() != null
- && getLocalRepresentation() instanceof FilterBasicRepresentation) {
- FilterBasicRepresentation interval = (FilterBasicRepresentation) getLocalRepresentation();
- mControl.setPrameter(interval);
- }
- }
-
- @Override
- public Control[] getControls() {
- BasicSlider slider = new BasicSlider();
- return new Control[] {
- slider
- };
- }
-
- // TODO: need a better way to decide which representation
- static boolean useCompact(Context context) {
- WindowManager w = ((WindowManager) context.getSystemService(Context.WINDOW_SERVICE));
- Point size = new Point();
- w.getDefaultDisplay().getSize(size);
- if (size.x < size.y) { // if tall than wider
- return true;
- }
- if (size.x < MINIMUM_WIDTH) {
- return true;
- }
- if (size.y < MINIMUM_HEIGHT) {
- return true;
- }
- return false;
- }
-
- protected Parameter getParameterToEdit(FilterRepresentation rep) {
- if (this instanceof Parameter) {
- return (Parameter) this;
- } else if (rep instanceof Parameter) {
- return ((Parameter) rep);
- }
- return null;
- }
-
- @Override
- public void setUtilityPanelUI(View actionButton, View editControl) {
- mActionButton = actionButton;
- mEditControl = editControl;
- FilterRepresentation rep = getLocalRepresentation();
- Parameter param = getParameterToEdit(rep);
- if (param != null) {
- control(param, editControl);
- } else {
- mSeekBar = new SeekBar(editControl.getContext());
- LayoutParams lp = new LinearLayout.LayoutParams(
- LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT);
- mSeekBar.setLayoutParams(lp);
- ((LinearLayout) editControl).addView(mSeekBar);
- mSeekBar.setOnSeekBarChangeListener(this);
- }
- }
-
- protected void control(Parameter p, View editControl) {
- String pType = p.getParameterType();
- Context context = editControl.getContext();
- Class c = ((useCompact(context)) ? portraitMap : landscapeMap).get(pType);
-
- if (c != null) {
- try {
- mControl = (Control) c.newInstance();
- p.setController(mControl);
- mControl.setUp((ViewGroup) editControl, p, this);
- } catch (Exception e) {
- Log.e(LOGTAG, "Error in loading Control ", e);
- }
- } else {
- Log.e(LOGTAG, "Unable to find class for " + pType);
- for (String string : portraitMap.keySet()) {
- Log.e(LOGTAG, "for " + string + " use " + portraitMap.get(string));
- }
- }
- }
-
- @Override
- public void onProgressChanged(SeekBar sbar, int progress, boolean arg2) {
- }
-
- @Override
- public void onStartTrackingTouch(SeekBar arg0) {
- }
-
- @Override
- public void onStopTrackingTouch(SeekBar arg0) {
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/editors/SwapButton.java b/src/com/android/gallery3d/filtershow/editors/SwapButton.java
deleted file mode 100644
index bb4432e28..000000000
--- a/src/com/android/gallery3d/filtershow/editors/SwapButton.java
+++ /dev/null
@@ -1,111 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.editors;
-
-import android.content.Context;
-import android.util.AttributeSet;
-import android.view.GestureDetector;
-import android.view.Menu;
-import android.view.MenuItem;
-import android.view.MotionEvent;
-import android.widget.Button;
-
-public class SwapButton extends Button implements GestureDetector.OnGestureListener {
-
- public static int ANIM_DURATION = 200;
-
- public interface SwapButtonListener {
- public void swapLeft(MenuItem item);
- public void swapRight(MenuItem item);
- }
-
- private GestureDetector mDetector;
- private SwapButtonListener mListener;
- private Menu mMenu;
- private int mCurrentMenuIndex;
-
- public SwapButton(Context context, AttributeSet attrs) {
- super(context, attrs);
- mDetector = new GestureDetector(context, this);
- }
-
- public SwapButtonListener getListener() {
- return mListener;
- }
-
- public void setListener(SwapButtonListener listener) {
- mListener = listener;
- }
-
- public boolean onTouchEvent(MotionEvent me) {
- if (!mDetector.onTouchEvent(me)) {
- return super.onTouchEvent(me);
- }
- return true;
- }
-
- @Override
- public boolean onDown(MotionEvent e) {
- return true;
- }
-
- @Override
- public void onShowPress(MotionEvent e) {
- }
-
- @Override
- public boolean onSingleTapUp(MotionEvent e) {
- callOnClick();
- return true;
- }
-
- @Override
- public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) {
- return false;
- }
-
- @Override
- public void onLongPress(MotionEvent e) {
- }
-
- @Override
- public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
- if (mMenu == null) {
- return false;
- }
- if (e1.getX() - e2.getX() > 0) {
- // right to left
- mCurrentMenuIndex++;
- if (mCurrentMenuIndex == mMenu.size()) {
- mCurrentMenuIndex = 0;
- }
- if (mListener != null) {
- mListener.swapRight(mMenu.getItem(mCurrentMenuIndex));
- }
- } else {
- // left to right
- mCurrentMenuIndex--;
- if (mCurrentMenuIndex < 0) {
- mCurrentMenuIndex = mMenu.size() - 1;
- }
- if (mListener != null) {
- mListener.swapLeft(mMenu.getItem(mCurrentMenuIndex));
- }
- }
- return true;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/BaseFiltersManager.java b/src/com/android/gallery3d/filtershow/filters/BaseFiltersManager.java
deleted file mode 100644
index 3fa91916d..000000000
--- a/src/com/android/gallery3d/filtershow/filters/BaseFiltersManager.java
+++ /dev/null
@@ -1,296 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.filtershow.filters;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.util.Log;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.EditorCrop;
-import com.android.gallery3d.filtershow.editors.EditorMirror;
-import com.android.gallery3d.filtershow.editors.EditorRotate;
-import com.android.gallery3d.filtershow.editors.EditorStraighten;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.Vector;
-
-public abstract class BaseFiltersManager implements FiltersManagerInterface {
- protected HashMap<Class, ImageFilter> mFilters = null;
- protected HashMap<String, FilterRepresentation> mRepresentationLookup = null;
- private static final String LOGTAG = "BaseFiltersManager";
-
- protected ArrayList<FilterRepresentation> mLooks = new ArrayList<FilterRepresentation>();
- protected ArrayList<FilterRepresentation> mBorders = new ArrayList<FilterRepresentation>();
- protected ArrayList<FilterRepresentation> mTools = new ArrayList<FilterRepresentation>();
- protected ArrayList<FilterRepresentation> mEffects = new ArrayList<FilterRepresentation>();
-
- protected void init() {
- mFilters = new HashMap<Class, ImageFilter>();
- mRepresentationLookup = new HashMap<String, FilterRepresentation>();
- Vector<Class> filters = new Vector<Class>();
- addFilterClasses(filters);
- for (Class filterClass : filters) {
- try {
- Object filterInstance = filterClass.newInstance();
- if (filterInstance instanceof ImageFilter) {
- mFilters.put(filterClass, (ImageFilter) filterInstance);
-
- FilterRepresentation rep =
- ((ImageFilter) filterInstance).getDefaultRepresentation();
- if (rep != null) {
- addRepresentation(rep);
- }
- }
- } catch (InstantiationException e) {
- e.printStackTrace();
- } catch (IllegalAccessException e) {
- e.printStackTrace();
- }
- }
- }
-
- public void addRepresentation(FilterRepresentation rep) {
- mRepresentationLookup.put(rep.getSerializationName(), rep);
- }
-
- public FilterRepresentation createFilterFromName(String name) {
- try {
- return mRepresentationLookup.get(name).copy();
- } catch (Exception e) {
- Log.v(LOGTAG, "unable to generate a filter representation for \"" + name + "\"");
- e.printStackTrace();
- }
- return null;
- }
-
- public ImageFilter getFilter(Class c) {
- return mFilters.get(c);
- }
-
- @Override
- public ImageFilter getFilterForRepresentation(FilterRepresentation representation) {
- return mFilters.get(representation.getFilterClass());
- }
-
- public FilterRepresentation getRepresentation(Class c) {
- ImageFilter filter = mFilters.get(c);
- if (filter != null) {
- return filter.getDefaultRepresentation();
- }
- return null;
- }
-
- public void freeFilterResources(ImagePreset preset) {
- if (preset == null) {
- return;
- }
- Vector<ImageFilter> usedFilters = preset.getUsedFilters(this);
- for (Class c : mFilters.keySet()) {
- ImageFilter filter = mFilters.get(c);
- if (!usedFilters.contains(filter)) {
- filter.freeResources();
- }
- }
- }
-
- public void freeRSFilterScripts() {
- for (Class c : mFilters.keySet()) {
- ImageFilter filter = mFilters.get(c);
- if (filter != null && filter instanceof ImageFilterRS) {
- ((ImageFilterRS) filter).resetScripts();
- }
- }
- }
-
- protected void addFilterClasses(Vector<Class> filters) {
- filters.add(ImageFilterTinyPlanet.class);
- filters.add(ImageFilterRedEye.class);
- filters.add(ImageFilterWBalance.class);
- filters.add(ImageFilterExposure.class);
- filters.add(ImageFilterVignette.class);
- filters.add(ImageFilterGrad.class);
- filters.add(ImageFilterContrast.class);
- filters.add(ImageFilterShadows.class);
- filters.add(ImageFilterHighlights.class);
- filters.add(ImageFilterVibrance.class);
- filters.add(ImageFilterSharpen.class);
- filters.add(ImageFilterCurves.class);
- filters.add(ImageFilterDraw.class);
- filters.add(ImageFilterHue.class);
- filters.add(ImageFilterChanSat.class);
- filters.add(ImageFilterSaturated.class);
- filters.add(ImageFilterBwFilter.class);
- filters.add(ImageFilterNegative.class);
- filters.add(ImageFilterEdge.class);
- filters.add(ImageFilterKMeans.class);
- filters.add(ImageFilterFx.class);
- filters.add(ImageFilterBorder.class);
- filters.add(ImageFilterParametricBorder.class);
- }
-
- public ArrayList<FilterRepresentation> getLooks() {
- return mLooks;
- }
-
- public ArrayList<FilterRepresentation> getBorders() {
- return mBorders;
- }
-
- public ArrayList<FilterRepresentation> getTools() {
- return mTools;
- }
-
- public ArrayList<FilterRepresentation> getEffects() {
- return mEffects;
- }
-
- public void addBorders(Context context) {
-
- }
-
- public void addLooks(Context context) {
- int[] drawid = {
- R.drawable.filtershow_fx_0005_punch,
- R.drawable.filtershow_fx_0000_vintage,
- R.drawable.filtershow_fx_0004_bw_contrast,
- R.drawable.filtershow_fx_0002_bleach,
- R.drawable.filtershow_fx_0001_instant,
- R.drawable.filtershow_fx_0007_washout,
- R.drawable.filtershow_fx_0003_blue_crush,
- R.drawable.filtershow_fx_0008_washout_color,
- R.drawable.filtershow_fx_0006_x_process
- };
-
- int[] fxNameid = {
- R.string.ffx_punch,
- R.string.ffx_vintage,
- R.string.ffx_bw_contrast,
- R.string.ffx_bleach,
- R.string.ffx_instant,
- R.string.ffx_washout,
- R.string.ffx_blue_crush,
- R.string.ffx_washout_color,
- R.string.ffx_x_process
- };
-
- // Do not localize.
- String[] serializationNames = {
- "LUT3D_PUNCH",
- "LUT3D_VINTAGE",
- "LUT3D_BW",
- "LUT3D_BLEACH",
- "LUT3D_INSTANT",
- "LUT3D_WASHOUT",
- "LUT3D_BLUECRUSH",
- "LUT3D_WASHOUT",
- "LUT3D_XPROCESS"
- };
-
- FilterFxRepresentation nullFx =
- new FilterFxRepresentation(context.getString(R.string.none),
- 0, R.string.none);
- mLooks.add(nullFx);
-
- for (int i = 0; i < drawid.length; i++) {
- FilterFxRepresentation fx = new FilterFxRepresentation(
- context.getString(fxNameid[i]), drawid[i], fxNameid[i]);
- fx.setSerializationName(serializationNames[i]);
- ImagePreset preset = new ImagePreset();
- preset.addFilter(fx);
- FilterUserPresetRepresentation rep = new FilterUserPresetRepresentation(
- context.getString(fxNameid[i]), preset, -1);
- mLooks.add(rep);
- addRepresentation(fx);
- }
- }
-
- public void addEffects() {
- mEffects.add(getRepresentation(ImageFilterTinyPlanet.class));
- mEffects.add(getRepresentation(ImageFilterWBalance.class));
- mEffects.add(getRepresentation(ImageFilterExposure.class));
- mEffects.add(getRepresentation(ImageFilterVignette.class));
- mEffects.add(getRepresentation(ImageFilterGrad.class));
- mEffects.add(getRepresentation(ImageFilterContrast.class));
- mEffects.add(getRepresentation(ImageFilterShadows.class));
- mEffects.add(getRepresentation(ImageFilterHighlights.class));
- mEffects.add(getRepresentation(ImageFilterVibrance.class));
- mEffects.add(getRepresentation(ImageFilterSharpen.class));
- mEffects.add(getRepresentation(ImageFilterCurves.class));
- mEffects.add(getRepresentation(ImageFilterHue.class));
- mEffects.add(getRepresentation(ImageFilterChanSat.class));
- mEffects.add(getRepresentation(ImageFilterBwFilter.class));
- mEffects.add(getRepresentation(ImageFilterNegative.class));
- mEffects.add(getRepresentation(ImageFilterEdge.class));
- mEffects.add(getRepresentation(ImageFilterKMeans.class));
- }
-
- public void addTools(Context context) {
-
- int[] editorsId = {
- EditorCrop.ID,
- EditorStraighten.ID,
- EditorRotate.ID,
- EditorMirror.ID
- };
-
- int[] textId = {
- R.string.crop,
- R.string.straighten,
- R.string.rotate,
- R.string.mirror
- };
-
- int[] overlayId = {
- R.drawable.filtershow_button_geometry_crop,
- R.drawable.filtershow_button_geometry_straighten,
- R.drawable.filtershow_button_geometry_rotate,
- R.drawable.filtershow_button_geometry_flip
- };
-
- FilterRepresentation[] geometryFilters = {
- new FilterCropRepresentation(),
- new FilterStraightenRepresentation(),
- new FilterRotateRepresentation(),
- new FilterMirrorRepresentation()
- };
-
- for (int i = 0; i < editorsId.length; i++) {
- int editorId = editorsId[i];
- FilterRepresentation geometry = geometryFilters[i];
- geometry.setEditorId(editorId);
- geometry.setTextId(textId[i]);
- geometry.setOverlayId(overlayId[i]);
- geometry.setOverlayOnly(true);
- if (geometry.getTextId() != 0) {
- geometry.setName(context.getString(geometry.getTextId()));
- }
- mTools.add(geometry);
- }
-
- mTools.add(getRepresentation(ImageFilterRedEye.class));
- mTools.add(getRepresentation(ImageFilterDraw.class));
- }
-
- public void setFilterResources(Resources resources) {
- ImageFilterBorder filterBorder = (ImageFilterBorder) getFilter(ImageFilterBorder.class);
- filterBorder.setResources(resources);
- ImageFilterFx filterFx = (ImageFilterFx) getFilter(ImageFilterFx.class);
- filterFx.setResources(resources);
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ColorSpaceMatrix.java b/src/com/android/gallery3d/filtershow/filters/ColorSpaceMatrix.java
deleted file mode 100644
index 7c307a9e7..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ColorSpaceMatrix.java
+++ /dev/null
@@ -1,225 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import java.util.Arrays;
-
-public class ColorSpaceMatrix {
- private final float[] mMatrix = new float[16];
- private static final float RLUM = 0.3086f;
- private static final float GLUM = 0.6094f;
- private static final float BLUM = 0.0820f;
-
- public ColorSpaceMatrix() {
- identity();
- }
-
- /**
- * Copy constructor
- *
- * @param matrix
- */
- public ColorSpaceMatrix(ColorSpaceMatrix matrix) {
- System.arraycopy(matrix.mMatrix, 0, mMatrix, 0, matrix.mMatrix.length);
- }
-
- /**
- * get the matrix
- *
- * @return the internal matrix
- */
- public float[] getMatrix() {
- return mMatrix;
- }
-
- /**
- * set matrix to identity
- */
- public void identity() {
- Arrays.fill(mMatrix, 0);
- mMatrix[0] = mMatrix[5] = mMatrix[10] = mMatrix[15] = 1;
- }
-
- public void convertToLuminance() {
- mMatrix[0] = mMatrix[1] = mMatrix[2] = 0.3086f;
- mMatrix[4] = mMatrix[5] = mMatrix[6] = 0.6094f;
- mMatrix[8] = mMatrix[9] = mMatrix[10] = 0.0820f;
- }
-
- private void multiply(float[] a)
- {
- int x, y;
- float[] temp = new float[16];
-
- for (y = 0; y < 4; y++) {
- int y4 = y * 4;
- for (x = 0; x < 4; x++) {
- temp[y4 + x] = mMatrix[y4 + 0] * a[x]
- + mMatrix[y4 + 1] * a[4 + x]
- + mMatrix[y4 + 2] * a[8 + x]
- + mMatrix[y4 + 3] * a[12 + x];
- }
- }
- for (int i = 0; i < 16; i++)
- mMatrix[i] = temp[i];
- }
-
- private void xRotateMatrix(float rs, float rc)
- {
- ColorSpaceMatrix c = new ColorSpaceMatrix();
- float[] tmp = c.mMatrix;
-
- tmp[5] = rc;
- tmp[6] = rs;
- tmp[9] = -rs;
- tmp[10] = rc;
-
- multiply(tmp);
- }
-
- private void yRotateMatrix(float rs, float rc)
- {
- ColorSpaceMatrix c = new ColorSpaceMatrix();
- float[] tmp = c.mMatrix;
-
- tmp[0] = rc;
- tmp[2] = -rs;
- tmp[8] = rs;
- tmp[10] = rc;
-
- multiply(tmp);
- }
-
- private void zRotateMatrix(float rs, float rc)
- {
- ColorSpaceMatrix c = new ColorSpaceMatrix();
- float[] tmp = c.mMatrix;
-
- tmp[0] = rc;
- tmp[1] = rs;
- tmp[4] = -rs;
- tmp[5] = rc;
- multiply(tmp);
- }
-
- private void zShearMatrix(float dx, float dy)
- {
- ColorSpaceMatrix c = new ColorSpaceMatrix();
- float[] tmp = c.mMatrix;
-
- tmp[2] = dx;
- tmp[6] = dy;
- multiply(tmp);
- }
-
- /**
- * sets the transform to a shift in Hue
- *
- * @param rot rotation in degrees
- */
- public void setHue(float rot)
- {
- float mag = (float) Math.sqrt(2.0);
- float xrs = 1 / mag;
- float xrc = 1 / mag;
- xRotateMatrix(xrs, xrc);
- mag = (float) Math.sqrt(3.0);
- float yrs = -1 / mag;
- float yrc = (float) Math.sqrt(2.0) / mag;
- yRotateMatrix(yrs, yrc);
-
- float lx = getRedf(RLUM, GLUM, BLUM);
- float ly = getGreenf(RLUM, GLUM, BLUM);
- float lz = getBluef(RLUM, GLUM, BLUM);
- float zsx = lx / lz;
- float zsy = ly / lz;
- zShearMatrix(zsx, zsy);
-
- float zrs = (float) Math.sin(rot * Math.PI / 180.0);
- float zrc = (float) Math.cos(rot * Math.PI / 180.0);
- zRotateMatrix(zrs, zrc);
- zShearMatrix(-zsx, -zsy);
- yRotateMatrix(-yrs, yrc);
- xRotateMatrix(-xrs, xrc);
- }
-
- /**
- * set it to a saturation matrix
- *
- * @param s
- */
- public void changeSaturation(float s) {
- mMatrix[0] = (1 - s) * RLUM + s;
- mMatrix[1] = (1 - s) * RLUM;
- mMatrix[2] = (1 - s) * RLUM;
- mMatrix[4] = (1 - s) * GLUM;
- mMatrix[5] = (1 - s) * GLUM + s;
- mMatrix[6] = (1 - s) * GLUM;
- mMatrix[8] = (1 - s) * BLUM;
- mMatrix[9] = (1 - s) * BLUM;
- mMatrix[10] = (1 - s) * BLUM + s;
- }
-
- /**
- * Transform RGB value
- *
- * @param r red pixel value
- * @param g green pixel value
- * @param b blue pixel value
- * @return computed red pixel value
- */
- public float getRed(int r, int g, int b) {
- return r * mMatrix[0] + g * mMatrix[4] + b * mMatrix[8] + mMatrix[12];
- }
-
- /**
- * Transform RGB value
- *
- * @param r red pixel value
- * @param g green pixel value
- * @param b blue pixel value
- * @return computed green pixel value
- */
- public float getGreen(int r, int g, int b) {
- return r * mMatrix[1] + g * mMatrix[5] + b * mMatrix[9] + mMatrix[13];
- }
-
- /**
- * Transform RGB value
- *
- * @param r red pixel value
- * @param g green pixel value
- * @param b blue pixel value
- * @return computed blue pixel value
- */
- public float getBlue(int r, int g, int b) {
- return r * mMatrix[2] + g * mMatrix[6] + b * mMatrix[10] + mMatrix[14];
- }
-
- private float getRedf(float r, float g, float b) {
- return r * mMatrix[0] + g * mMatrix[4] + b * mMatrix[8] + mMatrix[12];
- }
-
- private float getGreenf(float r, float g, float b) {
- return r * mMatrix[1] + g * mMatrix[5] + b * mMatrix[9] + mMatrix[13];
- }
-
- private float getBluef(float r, float g, float b) {
- return r * mMatrix[2] + g * mMatrix[6] + b * mMatrix[10] + mMatrix[14];
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterBasicRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterBasicRepresentation.java
deleted file mode 100644
index 1eebdb571..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterBasicRepresentation.java
+++ /dev/null
@@ -1,196 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-
-import android.util.Log;
-
-import com.android.gallery3d.filtershow.controller.Control;
-import com.android.gallery3d.filtershow.controller.FilterView;
-import com.android.gallery3d.filtershow.controller.Parameter;
-import com.android.gallery3d.filtershow.controller.ParameterInteger;
-
-public class FilterBasicRepresentation extends FilterRepresentation implements ParameterInteger {
- private static final String LOGTAG = "FilterBasicRep";
- private int mMinimum;
- private int mValue;
- private int mMaximum;
- private int mDefaultValue;
- private int mPreviewValue;
- public static final String SERIAL_NAME = "Name";
- public static final String SERIAL_VALUE = "Value";
- private boolean mLogVerbose = Log.isLoggable(LOGTAG, Log.VERBOSE);
-
- public FilterBasicRepresentation(String name, int minimum, int value, int maximum) {
- super(name);
- mMinimum = minimum;
- mMaximum = maximum;
- setValue(value);
- }
-
- @Override
- public String toString() {
- return getName() + " : " + mMinimum + " < " + mValue + " < " + mMaximum;
- }
-
- @Override
- public FilterRepresentation copy() {
- FilterBasicRepresentation representation = new FilterBasicRepresentation(getName(),0,0,0);
- copyAllParameters(representation);
- return representation;
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- @Override
- public void useParametersFrom(FilterRepresentation a) {
- if (a instanceof FilterBasicRepresentation) {
- FilterBasicRepresentation representation = (FilterBasicRepresentation) a;
- setMinimum(representation.getMinimum());
- setMaximum(representation.getMaximum());
- setValue(representation.getValue());
- setDefaultValue(representation.getDefaultValue());
- setPreviewValue(representation.getPreviewValue());
- }
- }
-
- @Override
- public boolean equals(FilterRepresentation representation) {
- if (!super.equals(representation)) {
- return false;
- }
- if (representation instanceof FilterBasicRepresentation) {
- FilterBasicRepresentation basic = (FilterBasicRepresentation) representation;
- if (basic.mMinimum == mMinimum
- && basic.mMaximum == mMaximum
- && basic.mValue == mValue
- && basic.mDefaultValue == mDefaultValue
- && basic.mPreviewValue == mPreviewValue) {
- return true;
- }
- }
- return false;
- }
-
- @Override
- public int getMinimum() {
- return mMinimum;
- }
-
- public void setMinimum(int minimum) {
- mMinimum = minimum;
- }
-
- @Override
- public int getValue() {
- return mValue;
- }
-
- @Override
- public void setValue(int value) {
- mValue = value;
- if (mValue < mMinimum) {
- mValue = mMinimum;
- }
- if (mValue > mMaximum) {
- mValue = mMaximum;
- }
- }
-
- @Override
- public int getMaximum() {
- return mMaximum;
- }
-
- public void setMaximum(int maximum) {
- mMaximum = maximum;
- }
-
- public void setDefaultValue(int defaultValue) {
- mDefaultValue = defaultValue;
- }
-
- @Override
- public int getDefaultValue() {
- return mDefaultValue;
- }
-
- public int getPreviewValue() {
- return mPreviewValue;
- }
-
- public void setPreviewValue(int previewValue) {
- mPreviewValue = previewValue;
- }
-
- @Override
- public String getStateRepresentation() {
- int val = getValue();
- return ((val > 0) ? "+" : "") + val;
- }
-
- @Override
- public String getParameterType(){
- return sParameterType;
- }
-
- @Override
- public void setController(Control control) {
- }
-
- @Override
- public String getValueString() {
- return getStateRepresentation();
- }
-
- @Override
- public String getParameterName() {
- return getName();
- }
-
- @Override
- public void setFilterView(FilterView editor) {
- }
-
- @Override
- public void copyFrom(Parameter src) {
- useParametersFrom((FilterBasicRepresentation) src);
- }
-
- @Override
- public String[][] serializeRepresentation() {
- String[][] ret = {
- {SERIAL_NAME , getName() },
- {SERIAL_VALUE , Integer.toString(mValue)}};
- return ret;
- }
-
- @Override
- public void deSerializeRepresentation(String[][] rep) {
- super.deSerializeRepresentation(rep);
- for (int i = 0; i < rep.length; i++) {
- if (SERIAL_VALUE.equals(rep[i][0])) {
- mValue = Integer.parseInt(rep[i][1]);
- break;
- }
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterChanSatRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterChanSatRepresentation.java
deleted file mode 100644
index 7ce67dd96..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterChanSatRepresentation.java
+++ /dev/null
@@ -1,211 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.util.JsonReader;
-import android.util.JsonWriter;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.controller.BasicParameterInt;
-import com.android.gallery3d.filtershow.controller.Parameter;
-import com.android.gallery3d.filtershow.controller.ParameterSet;
-import com.android.gallery3d.filtershow.editors.EditorChanSat;
-import com.android.gallery3d.filtershow.imageshow.ControlPoint;
-import com.android.gallery3d.filtershow.imageshow.Spline;
-
-import java.io.IOException;
-import java.util.Vector;
-
-/**
- * Representation for a filter that has per channel & Master saturation
- */
-public class FilterChanSatRepresentation extends FilterRepresentation implements ParameterSet {
- private static final String LOGTAG = "FilterChanSatRepresentation";
- private static final String ARGS = "ARGS";
- private static final String SERIALIZATION_NAME = "channelsaturation";
-
- public static final int MODE_MASTER = 0;
- public static final int MODE_RED = 1;
- public static final int MODE_YELLOW = 2;
- public static final int MODE_GREEN = 3;
- public static final int MODE_CYAN = 4;
- public static final int MODE_BLUE = 5;
- public static final int MODE_MAGENTA = 6;
- private int mParameterMode = MODE_MASTER;
-
- private static int MINSAT = -100;
- private static int MAXSAT = 100;
- private BasicParameterInt mParamMaster = new BasicParameterInt(MODE_MASTER, 0, MINSAT, MAXSAT);
- private BasicParameterInt mParamRed = new BasicParameterInt(MODE_RED, 0, MINSAT, MAXSAT);
- private BasicParameterInt mParamYellow = new BasicParameterInt(MODE_YELLOW, 0, MINSAT, MAXSAT);
- private BasicParameterInt mParamGreen = new BasicParameterInt(MODE_GREEN, 0, MINSAT, MAXSAT);
- private BasicParameterInt mParamCyan = new BasicParameterInt(MODE_CYAN, 0, MINSAT, MAXSAT);
- private BasicParameterInt mParamBlue = new BasicParameterInt(MODE_BLUE, 0, MINSAT, MAXSAT);
- private BasicParameterInt mParamMagenta = new BasicParameterInt(MODE_MAGENTA, 0, MINSAT, MAXSAT);
-
- private BasicParameterInt[] mAllParam = {
- mParamMaster,
- mParamRed,
- mParamYellow,
- mParamGreen,
- mParamCyan,
- mParamBlue,
- mParamMagenta};
-
- public FilterChanSatRepresentation() {
- super("ChannelSaturation");
- setTextId(R.string.saturation);
- setFilterType(FilterRepresentation.TYPE_NORMAL);
- setSerializationName(SERIALIZATION_NAME);
- setFilterClass(ImageFilterChanSat.class);
- setEditorId(EditorChanSat.ID);
- }
-
- public String toString() {
- return getName() + " : " + mParamRed + ", " + mParamCyan + ", " + mParamRed
- + ", " + mParamGreen + ", " + mParamMaster + ", " + mParamYellow;
- }
-
- @Override
- public FilterRepresentation copy() {
- FilterChanSatRepresentation representation = new FilterChanSatRepresentation();
- copyAllParameters(representation);
- return representation;
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- public void useParametersFrom(FilterRepresentation a) {
- if (a instanceof FilterChanSatRepresentation) {
- FilterChanSatRepresentation representation = (FilterChanSatRepresentation) a;
-
- for (int i = 0; i < mAllParam.length; i++) {
- mAllParam[i].copyFrom(representation.mAllParam[i]);
- }
- }
- }
-
- @Override
- public boolean equals(FilterRepresentation representation) {
- if (!super.equals(representation)) {
- return false;
- }
- if (representation instanceof FilterChanSatRepresentation) {
- FilterChanSatRepresentation rep = (FilterChanSatRepresentation) representation;
- for (int i = 0; i < mAllParam.length; i++) {
- if (rep.getValue(i) != getValue(i))
- return false;
- }
- return true;
- }
- return false;
- }
-
- public int getValue(int mode) {
- return mAllParam[mode].getValue();
- }
-
- public void setValue(int mode, int value) {
- mAllParam[mode].setValue(value);
- }
-
- public int getMinimum() {
- return mParamMaster.getMinimum();
- }
-
- public int getMaximum() {
- return mParamMaster.getMaximum();
- }
-
- public int getParameterMode() {
- return mParameterMode;
- }
-
- public void setParameterMode(int parameterMode) {
- mParameterMode = parameterMode;
- }
-
- public int getCurrentParameter() {
- return getValue(mParameterMode);
- }
-
- public void setCurrentParameter(int value) {
- setValue(mParameterMode, value);
- }
-
- @Override
- public int getNumberOfParameters() {
- return 6;
- }
-
- @Override
- public Parameter getFilterParameter(int index) {
- return mAllParam[index];
- }
-
- @Override
- public void serializeRepresentation(JsonWriter writer) throws IOException {
- writer.beginObject();
-
- writer.name(ARGS);
- writer.beginArray();
- writer.value(getValue(MODE_MASTER));
- writer.value(getValue(MODE_RED));
- writer.value(getValue(MODE_YELLOW));
- writer.value(getValue(MODE_GREEN));
- writer.value(getValue(MODE_CYAN));
- writer.value(getValue(MODE_BLUE));
- writer.value(getValue(MODE_MAGENTA));
- writer.endArray();
- writer.endObject();
- }
-
- @Override
- public void deSerializeRepresentation(JsonReader sreader) throws IOException {
- sreader.beginObject();
-
- while (sreader.hasNext()) {
- String name = sreader.nextName();
- if (name.startsWith(ARGS)) {
- sreader.beginArray();
- sreader.hasNext();
- setValue(MODE_MASTER, sreader.nextInt());
- sreader.hasNext();
- setValue(MODE_RED, sreader.nextInt());
- sreader.hasNext();
- setValue(MODE_YELLOW, sreader.nextInt());
- sreader.hasNext();
- setValue(MODE_GREEN, sreader.nextInt());
- sreader.hasNext();
- setValue(MODE_CYAN, sreader.nextInt());
- sreader.hasNext();
- setValue(MODE_BLUE, sreader.nextInt());
- sreader.hasNext();
- setValue(MODE_MAGENTA, sreader.nextInt());
- sreader.hasNext();
- sreader.endArray();
- } else {
- sreader.skipValue();
- }
- }
- sreader.endObject();
- }
-} \ No newline at end of file
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterColorBorderRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterColorBorderRepresentation.java
deleted file mode 100644
index 94eb20631..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterColorBorderRepresentation.java
+++ /dev/null
@@ -1,113 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.ImageOnlyEditor;
-
-public class FilterColorBorderRepresentation extends FilterRepresentation {
- private int mColor;
- private int mBorderSize;
- private int mBorderRadius;
-
- public FilterColorBorderRepresentation(int color, int size, int radius) {
- super("ColorBorder");
- mColor = color;
- mBorderSize = size;
- mBorderRadius = radius;
- setFilterType(FilterRepresentation.TYPE_BORDER);
- setTextId(R.string.borders);
- setEditorId(ImageOnlyEditor.ID);
- setShowParameterValue(false);
- }
-
- public String toString() {
- return "FilterBorder: " + getName();
- }
-
- @Override
- public FilterRepresentation copy() {
- FilterColorBorderRepresentation representation = new FilterColorBorderRepresentation(0,0,0);
- copyAllParameters(representation);
- return representation;
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- public void useParametersFrom(FilterRepresentation a) {
- if (a instanceof FilterColorBorderRepresentation) {
- FilterColorBorderRepresentation representation = (FilterColorBorderRepresentation) a;
- setName(representation.getName());
- setColor(representation.getColor());
- setBorderSize(representation.getBorderSize());
- setBorderRadius(representation.getBorderRadius());
- }
- }
-
- @Override
- public boolean equals(FilterRepresentation representation) {
- if (!super.equals(representation)) {
- return false;
- }
- if (representation instanceof FilterColorBorderRepresentation) {
- FilterColorBorderRepresentation border = (FilterColorBorderRepresentation) representation;
- if (border.mColor == mColor
- && border.mBorderSize == mBorderSize
- && border.mBorderRadius == mBorderRadius) {
- return true;
- }
- }
- return false;
- }
-
- public boolean allowsSingleInstanceOnly() {
- return true;
- }
-
- @Override
- public int getTextId() {
- return R.string.borders;
- }
-
- public int getColor() {
- return mColor;
- }
-
- public void setColor(int color) {
- mColor = color;
- }
-
- public int getBorderSize() {
- return mBorderSize;
- }
-
- public void setBorderSize(int borderSize) {
- mBorderSize = borderSize;
- }
-
- public int getBorderRadius() {
- return mBorderRadius;
- }
-
- public void setBorderRadius(int borderRadius) {
- mBorderRadius = borderRadius;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterCropRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterCropRepresentation.java
deleted file mode 100644
index c1bd7b3bb..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterCropRepresentation.java
+++ /dev/null
@@ -1,179 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.RectF;
-import android.util.JsonReader;
-import android.util.JsonWriter;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.EditorCrop;
-
-import java.io.IOException;
-
-public class FilterCropRepresentation extends FilterRepresentation {
- public static final String SERIALIZATION_NAME = "CROP";
- public static final String[] BOUNDS = {
- "C0", "C1", "C2", "C3"
- };
- private static final String TAG = FilterCropRepresentation.class.getSimpleName();
-
- RectF mCrop = getNil();
-
- public FilterCropRepresentation(RectF crop) {
- super(FilterCropRepresentation.class.getSimpleName());
- setSerializationName(SERIALIZATION_NAME);
- setShowParameterValue(true);
- setFilterClass(FilterCropRepresentation.class);
- setFilterType(FilterRepresentation.TYPE_GEOMETRY);
- setTextId(R.string.crop);
- setEditorId(EditorCrop.ID);
- setCrop(crop);
- }
-
- public FilterCropRepresentation(FilterCropRepresentation m) {
- this(m.mCrop);
- }
-
- public FilterCropRepresentation() {
- this(sNilRect);
- }
-
- public void set(FilterCropRepresentation r) {
- mCrop.set(r.mCrop);
- }
-
- @Override
- public boolean equals(FilterRepresentation rep) {
- if (!(rep instanceof FilterCropRepresentation)) {
- return false;
- }
- FilterCropRepresentation crop = (FilterCropRepresentation) rep;
- if (mCrop.bottom != crop.mCrop.bottom
- || mCrop.left != crop.mCrop.left
- || mCrop.right != crop.mCrop.right
- || mCrop.top != crop.mCrop.top) {
- return false;
- }
- return true;
- }
-
- public RectF getCrop() {
- return new RectF(mCrop);
- }
-
- public void getCrop(RectF r) {
- r.set(mCrop);
- }
-
- public void setCrop(RectF crop) {
- if (crop == null) {
- throw new IllegalArgumentException("Argument to setCrop is null");
- }
- mCrop.set(crop);
- }
-
- /**
- * Takes a crop rect contained by [0, 0, 1, 1] and scales it by the height
- * and width of the image rect.
- */
- public static void findScaledCrop(RectF crop, int bitmapWidth, int bitmapHeight) {
- crop.left *= bitmapWidth;
- crop.top *= bitmapHeight;
- crop.right *= bitmapWidth;
- crop.bottom *= bitmapHeight;
- }
-
- /**
- * Takes crop rect and normalizes it by scaling down by the height and width
- * of the image rect.
- */
- public static void findNormalizedCrop(RectF crop, int bitmapWidth, int bitmapHeight) {
- crop.left /= bitmapWidth;
- crop.top /= bitmapHeight;
- crop.right /= bitmapWidth;
- crop.bottom /= bitmapHeight;
- }
-
- @Override
- public boolean allowsSingleInstanceOnly() {
- return true;
- }
-
- @Override
- public FilterRepresentation copy() {
- return new FilterCropRepresentation(this);
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- if (!(representation instanceof FilterCropRepresentation)) {
- throw new IllegalArgumentException("calling copyAllParameters with incompatible types!");
- }
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- @Override
- public void useParametersFrom(FilterRepresentation a) {
- if (!(a instanceof FilterCropRepresentation)) {
- throw new IllegalArgumentException("calling useParametersFrom with incompatible types!");
- }
- setCrop(((FilterCropRepresentation) a).mCrop);
- }
-
- private static final RectF sNilRect = new RectF(0, 0, 1, 1);
-
- @Override
- public boolean isNil() {
- return mCrop.equals(sNilRect);
- }
-
- public static RectF getNil() {
- return new RectF(sNilRect);
- }
-
- @Override
- public void serializeRepresentation(JsonWriter writer) throws IOException {
- writer.beginObject();
- writer.name(BOUNDS[0]).value(mCrop.left);
- writer.name(BOUNDS[1]).value(mCrop.top);
- writer.name(BOUNDS[2]).value(mCrop.right);
- writer.name(BOUNDS[3]).value(mCrop.bottom);
- writer.endObject();
- }
-
- @Override
- public void deSerializeRepresentation(JsonReader reader) throws IOException {
- reader.beginObject();
- while (reader.hasNext()) {
- String name = reader.nextName();
- if (BOUNDS[0].equals(name)) {
- mCrop.left = (float) reader.nextDouble();
- } else if (BOUNDS[1].equals(name)) {
- mCrop.top = (float) reader.nextDouble();
- } else if (BOUNDS[2].equals(name)) {
- mCrop.right = (float) reader.nextDouble();
- } else if (BOUNDS[3].equals(name)) {
- mCrop.bottom = (float) reader.nextDouble();
- } else {
- reader.skipValue();
- }
- }
- reader.endObject();
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterCurvesRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterCurvesRepresentation.java
deleted file mode 100644
index edab2a08d..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterCurvesRepresentation.java
+++ /dev/null
@@ -1,170 +0,0 @@
-package com.android.gallery3d.filtershow.filters;
-
-import android.util.JsonReader;
-import android.util.JsonWriter;
-import android.util.Log;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.imageshow.ControlPoint;
-import com.android.gallery3d.filtershow.imageshow.Spline;
-
-import java.io.IOException;
-
-/**
- * TODO: Insert description here. (generated by hoford)
- */
-public class FilterCurvesRepresentation extends FilterRepresentation {
- private static final String LOGTAG = "FilterCurvesRepresentation";
- public static final String SERIALIZATION_NAME = "Curve";
- private static final int MAX_SPLINE_NUMBER = 4;
-
- private Spline[] mSplines = new Spline[MAX_SPLINE_NUMBER];
-
- public FilterCurvesRepresentation() {
- super("Curves");
- setSerializationName("CURVES");
- setFilterClass(ImageFilterCurves.class);
- setTextId(R.string.curvesRGB);
- setOverlayId(R.drawable.filtershow_button_colors_curve);
- setEditorId(R.id.imageCurves);
- setShowParameterValue(false);
- setSupportsPartialRendering(true);
- reset();
- }
-
- @Override
- public FilterRepresentation copy() {
- FilterCurvesRepresentation representation = new FilterCurvesRepresentation();
- copyAllParameters(representation);
- return representation;
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- @Override
- public void useParametersFrom(FilterRepresentation a) {
- if (!(a instanceof FilterCurvesRepresentation)) {
- Log.v(LOGTAG, "cannot use parameters from " + a);
- return;
- }
- FilterCurvesRepresentation representation = (FilterCurvesRepresentation) a;
- Spline[] spline = new Spline[MAX_SPLINE_NUMBER];
- for (int i = 0; i < spline.length; i++) {
- Spline sp = representation.mSplines[i];
- if (sp != null) {
- spline[i] = new Spline(sp);
- } else {
- spline[i] = new Spline();
- }
- }
- mSplines = spline;
- }
-
- @Override
- public boolean isNil() {
- for (int i = 0; i < MAX_SPLINE_NUMBER; i++) {
- if (getSpline(i) != null && !getSpline(i).isOriginal()) {
- return false;
- }
- }
- return true;
- }
-
- @Override
- public boolean equals(FilterRepresentation representation) {
- if (!super.equals(representation)) {
- return false;
- }
-
- if (!(representation instanceof FilterCurvesRepresentation)) {
- return false;
- } else {
- FilterCurvesRepresentation curve =
- (FilterCurvesRepresentation) representation;
- for (int i = 0; i < MAX_SPLINE_NUMBER; i++) {
- if (!getSpline(i).sameValues(curve.getSpline(i))) {
- return false;
- }
- }
- }
- // Every spline matches, therefore they are the same.
- return true;
- }
-
- public void reset() {
- Spline spline = new Spline();
-
- spline.addPoint(0.0f, 1.0f);
- spline.addPoint(1.0f, 0.0f);
-
- for (int i = 0; i < MAX_SPLINE_NUMBER; i++) {
- mSplines[i] = new Spline(spline);
- }
- }
-
- public void setSpline(int splineIndex, Spline s) {
- mSplines[splineIndex] = s;
- }
-
- public Spline getSpline(int splineIndex) {
- return mSplines[splineIndex];
- }
-
- @Override
- public void serializeRepresentation(JsonWriter writer) throws IOException {
- writer.beginObject();
- {
- writer.name(NAME_TAG);
- writer.value(getName());
- for (int i = 0; i < mSplines.length; i++) {
- writer.name(SERIALIZATION_NAME + i);
- writer.beginArray();
- int nop = mSplines[i].getNbPoints();
- for (int j = 0; j < nop; j++) {
- ControlPoint p = mSplines[i].getPoint(j);
- writer.beginArray();
- writer.value(p.x);
- writer.value(p.y);
- writer.endArray();
- }
- writer.endArray();
- }
-
- }
- writer.endObject();
- }
-
- @Override
- public void deSerializeRepresentation(JsonReader sreader) throws IOException {
- sreader.beginObject();
- Spline[] spline = new Spline[MAX_SPLINE_NUMBER];
- while (sreader.hasNext()) {
- String name = sreader.nextName();
- if (NAME_TAG.equals(name)) {
- setName(sreader.nextString());
- } else if (name.startsWith(SERIALIZATION_NAME)) {
- int curveNo = Integer.parseInt(name.substring(SERIALIZATION_NAME.length()));
- spline[curveNo] = new Spline();
- sreader.beginArray();
- while (sreader.hasNext()) {
- sreader.beginArray();
- sreader.hasNext();
- float x = (float) sreader.nextDouble();
- sreader.hasNext();
- float y = (float) sreader.nextDouble();
- sreader.endArray();
- spline[curveNo].addPoint(x, y);
- }
- sreader.endArray();
-
- }
- }
- mSplines = spline;
- sreader.endObject();
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterDirectRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterDirectRepresentation.java
deleted file mode 100644
index ac0cb7492..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterDirectRepresentation.java
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-public class FilterDirectRepresentation extends FilterRepresentation {
-
- @Override
- public FilterRepresentation copy() {
- FilterDirectRepresentation representation = new FilterDirectRepresentation(getName());
- copyAllParameters(representation);
- return representation;
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- public FilterDirectRepresentation(String name) {
- super(name);
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterDrawRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterDrawRepresentation.java
deleted file mode 100644
index 977dbeac5..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterDrawRepresentation.java
+++ /dev/null
@@ -1,171 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Path;
-import android.util.Log;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.EditorDraw;
-
-import java.util.Vector;
-
-public class FilterDrawRepresentation extends FilterRepresentation {
- private static final String LOGTAG = "FilterDrawRepresentation";
-
- public static class StrokeData implements Cloneable {
- public byte mType;
- public Path mPath;
- public float mRadius;
- public int mColor;
- public int noPoints = 0;
- @Override
- public String toString() {
- return "stroke(" + mType + ", path(" + (mPath) + "), " + mRadius + " , "
- + Integer.toHexString(mColor) + ")";
- }
- @Override
- public StrokeData clone() throws CloneNotSupportedException {
- return (StrokeData) super.clone();
- }
- }
-
- private Vector<StrokeData> mDrawing = new Vector<StrokeData>();
- private StrokeData mCurrent; // used in the currently drawing style
-
- public FilterDrawRepresentation() {
- super("Draw");
- setFilterClass(ImageFilterDraw.class);
- setSerializationName("DRAW");
- setFilterType(FilterRepresentation.TYPE_VIGNETTE);
- setTextId(R.string.imageDraw);
- setEditorId(EditorDraw.ID);
- setOverlayId(R.drawable.filtershow_drawing);
- setOverlayOnly(true);
- }
-
- @Override
- public String toString() {
- return getName() + " : strokes=" + mDrawing.size()
- + ((mCurrent == null) ? " no current "
- : ("draw=" + mCurrent.mType + " " + mCurrent.noPoints));
- }
-
- public Vector<StrokeData> getDrawing() {
- return mDrawing;
- }
-
- public StrokeData getCurrentDrawing() {
- return mCurrent;
- }
-
- @Override
- public FilterRepresentation copy() {
- FilterDrawRepresentation representation = new FilterDrawRepresentation();
- copyAllParameters(representation);
- return representation;
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- @Override
- public boolean isNil() {
- return getDrawing().isEmpty();
- }
-
- @Override
- public void useParametersFrom(FilterRepresentation a) {
- if (a instanceof FilterDrawRepresentation) {
- FilterDrawRepresentation representation = (FilterDrawRepresentation) a;
- try {
- if (representation.mCurrent != null) {
- mCurrent = (StrokeData) representation.mCurrent.clone();
- } else {
- mCurrent = null;
- }
- if (representation.mDrawing != null) {
- mDrawing = (Vector<StrokeData>) representation.mDrawing.clone();
- } else {
- mDrawing = null;
- }
-
- } catch (CloneNotSupportedException e) {
- e.printStackTrace();
- }
- } else {
- Log.v(LOGTAG, "cannot use parameters from " + a);
- }
- }
-
- @Override
- public boolean equals(FilterRepresentation representation) {
- if (!super.equals(representation)) {
- return false;
- }
- if (representation instanceof FilterDrawRepresentation) {
- FilterDrawRepresentation fdRep = (FilterDrawRepresentation) representation;
- if (fdRep.mDrawing.size() != mDrawing.size())
- return false;
- if (fdRep.mCurrent == null && mCurrent.mPath == null) {
- return true;
- }
- if (fdRep.mCurrent != null && mCurrent.mPath != null) {
- if (fdRep.mCurrent.noPoints == mCurrent.noPoints) {
- return true;
- }
- return false;
- }
- }
- return false;
- }
-
- public void startNewSection(byte type, int color, float size, float x, float y) {
- mCurrent = new StrokeData();
- mCurrent.mColor = color;
- mCurrent.mRadius = size;
- mCurrent.mType = type;
- mCurrent.mPath = new Path();
- mCurrent.mPath.moveTo(x, y);
- mCurrent.noPoints = 0;
- }
-
- public void addPoint(float x, float y) {
- mCurrent.noPoints++;
- mCurrent.mPath.lineTo(x, y);
- }
-
- public void endSection(float x, float y) {
- mCurrent.mPath.lineTo(x, y);
- mCurrent.noPoints++;
- mDrawing.add(mCurrent);
- mCurrent = null;
- }
-
- public void clearCurrentSection() {
- mCurrent = null;
- }
-
- public void clear() {
- mCurrent = null;
- mDrawing.clear();
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterFxRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterFxRepresentation.java
deleted file mode 100644
index e5a6fdd23..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterFxRepresentation.java
+++ /dev/null
@@ -1,112 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.filtershow.editors.ImageOnlyEditor;
-
-public class FilterFxRepresentation extends FilterRepresentation {
- private static final String LOGTAG = "FilterFxRepresentation";
- // TODO: When implementing serialization, we should find a unique way of
- // specifying bitmaps / names (the resource IDs being random)
- private int mBitmapResource = 0;
- private int mNameResource = 0;
-
- public FilterFxRepresentation(String name, int bitmapResource, int nameResource) {
- super(name);
- setFilterClass(ImageFilterFx.class);
- mBitmapResource = bitmapResource;
- mNameResource = nameResource;
- setFilterType(FilterRepresentation.TYPE_FX);
- setTextId(nameResource);
- setEditorId(ImageOnlyEditor.ID);
- setShowParameterValue(false);
- setSupportsPartialRendering(true);
- }
-
- @Override
- public String toString() {
- return "FilterFx: " + hashCode() + " : " + getName() + " bitmap rsc: " + mBitmapResource;
- }
-
- @Override
- public FilterRepresentation copy() {
- FilterFxRepresentation representation = new FilterFxRepresentation(getName(),0,0);
- copyAllParameters(representation);
- return representation;
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- @Override
- public synchronized void useParametersFrom(FilterRepresentation a) {
- if (a instanceof FilterFxRepresentation) {
- FilterFxRepresentation representation = (FilterFxRepresentation) a;
- setName(representation.getName());
- setSerializationName(representation.getSerializationName());
- setBitmapResource(representation.getBitmapResource());
- setNameResource(representation.getNameResource());
- }
- }
-
- @Override
- public boolean equals(FilterRepresentation representation) {
- if (!super.equals(representation)) {
- return false;
- }
- if (representation instanceof FilterFxRepresentation) {
- FilterFxRepresentation fx = (FilterFxRepresentation) representation;
- if (fx.mNameResource == mNameResource
- && fx.mBitmapResource == mBitmapResource) {
- return true;
- }
- }
- return false;
- }
-
- @Override
- public boolean same(FilterRepresentation representation) {
- if (!super.same(representation)) {
- return false;
- }
- return equals(representation);
- }
-
- @Override
- public boolean allowsSingleInstanceOnly() {
- return true;
- }
-
- public int getNameResource() {
- return mNameResource;
- }
-
- public void setNameResource(int nameResource) {
- mNameResource = nameResource;
- }
-
- public int getBitmapResource() {
- return mBitmapResource;
- }
-
- public void setBitmapResource(int bitmapResource) {
- mBitmapResource = bitmapResource;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterGradRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterGradRepresentation.java
deleted file mode 100644
index 0c272d48a..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterGradRepresentation.java
+++ /dev/null
@@ -1,497 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Rect;
-import android.util.JsonReader;
-import android.util.JsonWriter;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.EditorGrad;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.imageshow.Line;
-
-import java.io.IOException;
-import java.util.Vector;
-
-public class FilterGradRepresentation extends FilterRepresentation
- implements Line {
- private static final String LOGTAG = "FilterGradRepresentation";
- public static final int MAX_POINTS = 16;
- public static final int PARAM_BRIGHTNESS = 0;
- public static final int PARAM_SATURATION = 1;
- public static final int PARAM_CONTRAST = 2;
- private static final double ADD_MIN_DIST = .05;
- private static String LINE_NAME = "Point";
- private static final String SERIALIZATION_NAME = "grad";
-
- public FilterGradRepresentation() {
- super("Grad");
- setSerializationName(SERIALIZATION_NAME);
- creatExample();
- setOverlayId(R.drawable.filtershow_button_grad);
- setFilterClass(ImageFilterGrad.class);
- setTextId(R.string.grad);
- setEditorId(EditorGrad.ID);
- }
-
- public void trimVector(){
- int n = mBands.size();
- for (int i = n; i < MAX_POINTS; i++) {
- mBands.add(new Band());
- }
- for (int i = MAX_POINTS; i < n; i++) {
- mBands.remove(i);
- }
- }
-
- Vector<Band> mBands = new Vector<Band>();
- Band mCurrentBand;
-
- static class Band {
- private boolean mask = true;
-
- private int xPos1 = -1;
- private int yPos1 = 100;
- private int xPos2 = -1;
- private int yPos2 = 100;
- private int brightness = 40;
- private int contrast = 0;
- private int saturation = 0;
-
-
- public Band() {
- }
-
- public Band(int x, int y) {
- xPos1 = x;
- yPos1 = y+30;
- xPos2 = x;
- yPos2 = y-30;
- }
-
- public Band(Band copy) {
- mask = copy.mask;
- xPos1 = copy.xPos1;
- yPos1 = copy.yPos1;
- xPos2 = copy.xPos2;
- yPos2 = copy.yPos2;
- brightness = copy.brightness;
- contrast = copy.contrast;
- saturation = copy.saturation;
- }
-
- }
-
- @Override
- public String toString() {
- int count = 0;
- for (Band point : mBands) {
- if (!point.mask) {
- count++;
- }
- }
- return "c=" + mBands.indexOf(mBands) + "[" + mBands.size() + "]" + count;
- }
-
- private void creatExample() {
- Band p = new Band();
- p.mask = false;
- p.xPos1 = -1;
- p.yPos1 = 100;
- p.xPos2 = -1;
- p.yPos2 = 100;
- p.brightness = 40;
- p.contrast = 0;
- p.saturation = 0;
- mBands.add(0, p);
- mCurrentBand = p;
- trimVector();
- }
-
- @Override
- public void useParametersFrom(FilterRepresentation a) {
- FilterGradRepresentation rep = (FilterGradRepresentation) a;
- Vector<Band> tmpBands = new Vector<Band>();
- int n = (rep.mCurrentBand == null) ? 0 : rep.mBands.indexOf(rep.mCurrentBand);
- for (Band band : rep.mBands) {
- tmpBands.add(new Band(band));
- }
- mCurrentBand = null;
- mBands = tmpBands;
- mCurrentBand = mBands.elementAt(n);
- }
-
- @Override
- public FilterRepresentation copy() {
- FilterGradRepresentation representation = new FilterGradRepresentation();
- copyAllParameters(representation);
- return representation;
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- @Override
- public boolean equals(FilterRepresentation representation) {
- if (representation instanceof FilterGradRepresentation) {
- FilterGradRepresentation rep = (FilterGradRepresentation) representation;
- int n = getNumberOfBands();
- if (rep.getNumberOfBands() != n) {
- return false;
- }
- for (int i = 0; i < mBands.size(); i++) {
- Band b1 = mBands.get(i);
- Band b2 = rep.mBands.get(i);
- if (b1.mask != b2.mask
- || b1.brightness != b2.brightness
- || b1.contrast != b2.contrast
- || b1.saturation != b2.saturation
- || b1.xPos1 != b2.xPos1
- || b1.xPos2 != b2.xPos2
- || b1.yPos1 != b2.yPos1
- || b1.yPos2 != b2.yPos2) {
- return false;
- }
- }
- return true;
- }
- return false;
- }
-
- public int getNumberOfBands() {
- int count = 0;
- for (Band point : mBands) {
- if (!point.mask) {
- count++;
- }
- }
- return count;
- }
-
- public int addBand(Rect rect) {
- mBands.add(0, mCurrentBand = new Band(rect.centerX(), rect.centerY()));
- mCurrentBand.mask = false;
- int x = (mCurrentBand.xPos1 + mCurrentBand.xPos2)/2;
- int y = (mCurrentBand.yPos1 + mCurrentBand.yPos2)/2;
- double addDelta = ADD_MIN_DIST * Math.max(rect.width(), rect.height());
- boolean moved = true;
- int count = 0;
- int toMove = mBands.indexOf(mCurrentBand);
-
- while (moved) {
- moved = false;
- count++;
- if (count > 14) {
- break;
- }
-
- for (Band point : mBands) {
- if (point.mask) {
- break;
- }
- }
-
- for (Band point : mBands) {
- if (point.mask) {
- break;
- }
- int index = mBands.indexOf(point);
-
- if (toMove != index) {
- double dist = Math.hypot(point.xPos1 - x, point.yPos1 - y);
- if (dist < addDelta) {
- moved = true;
- mCurrentBand.xPos1 += addDelta;
- mCurrentBand.yPos1 += addDelta;
- mCurrentBand.xPos2 += addDelta;
- mCurrentBand.yPos2 += addDelta;
- x = (mCurrentBand.xPos1 + mCurrentBand.xPos2)/2;
- y = (mCurrentBand.yPos1 + mCurrentBand.yPos2)/2;
-
- if (mCurrentBand.yPos1 > rect.bottom) {
- mCurrentBand.yPos1 = (int) (rect.top + addDelta);
- }
- if (mCurrentBand.xPos1 > rect.right) {
- mCurrentBand.xPos1 = (int) (rect.left + addDelta);
- }
- }
- }
- }
- }
- trimVector();
- return 0;
- }
-
- public void deleteCurrentBand() {
- int index = mBands.indexOf(mCurrentBand);
- mBands.remove(mCurrentBand);
- trimVector();
- if (getNumberOfBands() == 0) {
- addBand(MasterImage.getImage().getOriginalBounds());
- }
- mCurrentBand = mBands.get(0);
- }
-
- public void nextPoint(){
- int index = mBands.indexOf(mCurrentBand);
- int tmp = index;
- Band point;
- int k = 0;
- do {
- index = (index+1)% mBands.size();
- point = mBands.get(index);
- if (k++ >= mBands.size()) {
- break;
- }
- }
- while (point.mask == true);
- mCurrentBand = mBands.get(index);
- }
-
- public void setSelectedPoint(int pos) {
- mCurrentBand = mBands.get(pos);
- }
-
- public int getSelectedPoint() {
- return mBands.indexOf(mCurrentBand);
- }
-
- public boolean[] getMask() {
- boolean[] ret = new boolean[mBands.size()];
- int i = 0;
- for (Band point : mBands) {
- ret[i++] = !point.mask;
- }
- return ret;
- }
-
- public int[] getXPos1() {
- int[] ret = new int[mBands.size()];
- int i = 0;
- for (Band point : mBands) {
- ret[i++] = point.xPos1;
- }
- return ret;
- }
-
- public int[] getYPos1() {
- int[] ret = new int[mBands.size()];
- int i = 0;
- for (Band point : mBands) {
- ret[i++] = point.yPos1;
- }
- return ret;
- }
-
- public int[] getXPos2() {
- int[] ret = new int[mBands.size()];
- int i = 0;
- for (Band point : mBands) {
- ret[i++] = point.xPos2;
- }
- return ret;
- }
-
- public int[] getYPos2() {
- int[] ret = new int[mBands.size()];
- int i = 0;
- for (Band point : mBands) {
- ret[i++] = point.yPos2;
- }
- return ret;
- }
-
- public int[] getBrightness() {
- int[] ret = new int[mBands.size()];
- int i = 0;
- for (Band point : mBands) {
- ret[i++] = point.brightness;
- }
- return ret;
- }
-
- public int[] getContrast() {
- int[] ret = new int[mBands.size()];
- int i = 0;
- for (Band point : mBands) {
- ret[i++] = point.contrast;
- }
- return ret;
- }
-
- public int[] getSaturation() {
- int[] ret = new int[mBands.size()];
- int i = 0;
- for (Band point : mBands) {
- ret[i++] = point.saturation;
- }
- return ret;
- }
-
- public int getParameter(int type) {
- switch (type){
- case PARAM_BRIGHTNESS:
- return mCurrentBand.brightness;
- case PARAM_SATURATION:
- return mCurrentBand.saturation;
- case PARAM_CONTRAST:
- return mCurrentBand.contrast;
- }
- throw new IllegalArgumentException("no such type " + type);
- }
-
- public int getParameterMax(int type) {
- switch (type) {
- case PARAM_BRIGHTNESS:
- return 100;
- case PARAM_SATURATION:
- return 100;
- case PARAM_CONTRAST:
- return 100;
- }
- throw new IllegalArgumentException("no such type " + type);
- }
-
- public int getParameterMin(int type) {
- switch (type) {
- case PARAM_BRIGHTNESS:
- return -100;
- case PARAM_SATURATION:
- return -100;
- case PARAM_CONTRAST:
- return -100;
- }
- throw new IllegalArgumentException("no such type " + type);
- }
-
- public void setParameter(int type, int value) {
- mCurrentBand.mask = false;
- switch (type) {
- case PARAM_BRIGHTNESS:
- mCurrentBand.brightness = value;
- break;
- case PARAM_SATURATION:
- mCurrentBand.saturation = value;
- break;
- case PARAM_CONTRAST:
- mCurrentBand.contrast = value;
- break;
- default:
- throw new IllegalArgumentException("no such type " + type);
- }
- }
-
- @Override
- public void setPoint1(float x, float y) {
- mCurrentBand.xPos1 = (int)x;
- mCurrentBand.yPos1 = (int)y;
- }
-
- @Override
- public void setPoint2(float x, float y) {
- mCurrentBand.xPos2 = (int)x;
- mCurrentBand.yPos2 = (int)y;
- }
-
- @Override
- public float getPoint1X() {
- return mCurrentBand.xPos1;
- }
-
- @Override
- public float getPoint1Y() {
- return mCurrentBand.yPos1;
- }
- @Override
- public float getPoint2X() {
- return mCurrentBand.xPos2;
- }
-
- @Override
- public float getPoint2Y() {
- return mCurrentBand.yPos2;
- }
-
- @Override
- public void serializeRepresentation(JsonWriter writer) throws IOException {
- writer.beginObject();
- int len = mBands.size();
- int count = 0;
-
- for (int i = 0; i < len; i++) {
- Band point = mBands.get(i);
- if (point.mask) {
- continue;
- }
- writer.name(LINE_NAME + count);
- count++;
- writer.beginArray();
- writer.value(point.xPos1);
- writer.value(point.yPos1);
- writer.value(point.xPos2);
- writer.value(point.yPos2);
- writer.value(point.brightness);
- writer.value(point.contrast);
- writer.value(point.saturation);
- writer.endArray();
- }
- writer.endObject();
- }
-
- @Override
- public void deSerializeRepresentation(JsonReader sreader) throws IOException {
- sreader.beginObject();
- Vector<Band> points = new Vector<Band>();
-
- while (sreader.hasNext()) {
- String name = sreader.nextName();
- if (name.startsWith(LINE_NAME)) {
- int pointNo = Integer.parseInt(name.substring(LINE_NAME.length()));
- sreader.beginArray();
- Band p = new Band();
- p.mask = false;
- sreader.hasNext();
- p.xPos1 = sreader.nextInt();
- sreader.hasNext();
- p.yPos1 = sreader.nextInt();
- sreader.hasNext();
- p.xPos2 = sreader.nextInt();
- sreader.hasNext();
- p.yPos2 = sreader.nextInt();
- sreader.hasNext();
- p.brightness = sreader.nextInt();
- sreader.hasNext();
- p.contrast = sreader.nextInt();
- sreader.hasNext();
- p.saturation = sreader.nextInt();
- sreader.hasNext();
- sreader.endArray();
- points.add(p);
-
- } else {
- sreader.skipValue();
- }
- }
- mBands = points;
- trimVector();
- mCurrentBand = mBands.get(0);
- sreader.endObject();
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterImageBorderRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterImageBorderRepresentation.java
deleted file mode 100644
index f310a2be1..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterImageBorderRepresentation.java
+++ /dev/null
@@ -1,91 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.ImageOnlyEditor;
-
-public class FilterImageBorderRepresentation extends FilterRepresentation {
- private int mDrawableResource = 0;
-
- public FilterImageBorderRepresentation(int drawableResource) {
- super("ImageBorder");
- setFilterClass(ImageFilterBorder.class);
- mDrawableResource = drawableResource;
- setFilterType(FilterRepresentation.TYPE_BORDER);
- setTextId(R.string.borders);
- setEditorId(ImageOnlyEditor.ID);
- setShowParameterValue(false);
- }
-
- public String toString() {
- return "FilterBorder: " + getName();
- }
-
- @Override
- public FilterRepresentation copy() {
- FilterImageBorderRepresentation representation =
- new FilterImageBorderRepresentation(mDrawableResource);
- copyAllParameters(representation);
- return representation;
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- public void useParametersFrom(FilterRepresentation a) {
- if (a instanceof FilterImageBorderRepresentation) {
- FilterImageBorderRepresentation representation = (FilterImageBorderRepresentation) a;
- setName(representation.getName());
- setDrawableResource(representation.getDrawableResource());
- }
- }
-
- @Override
- public boolean equals(FilterRepresentation representation) {
- if (!super.equals(representation)) {
- return false;
- }
- if (representation instanceof FilterImageBorderRepresentation) {
- FilterImageBorderRepresentation border = (FilterImageBorderRepresentation) representation;
- if (border.mDrawableResource == mDrawableResource) {
- return true;
- }
- }
- return false;
- }
-
- @Override
- public int getTextId() {
- return R.string.none;
- }
-
- public boolean allowsSingleInstanceOnly() {
- return true;
- }
-
- public int getDrawableResource() {
- return mDrawableResource;
- }
-
- public void setDrawableResource(int drawableResource) {
- mDrawableResource = drawableResource;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterMirrorRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterMirrorRepresentation.java
deleted file mode 100644
index 8dcff0d16..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterMirrorRepresentation.java
+++ /dev/null
@@ -1,190 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.util.JsonReader;
-import android.util.JsonWriter;
-import android.util.Log;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.EditorMirror;
-
-import java.io.IOException;
-
-public class FilterMirrorRepresentation extends FilterRepresentation {
- public static final String SERIALIZATION_NAME = "MIRROR";
- private static final String SERIALIZATION_MIRROR_VALUE = "value";
- private static final String TAG = FilterMirrorRepresentation.class.getSimpleName();
-
- Mirror mMirror;
-
- public enum Mirror {
- NONE('N'), VERTICAL('V'), HORIZONTAL('H'), BOTH('B');
- char mValue;
-
- private Mirror(char value) {
- mValue = value;
- }
-
- public char value() {
- return mValue;
- }
-
- public static Mirror fromValue(char value) {
- switch (value) {
- case 'N':
- return NONE;
- case 'V':
- return VERTICAL;
- case 'H':
- return HORIZONTAL;
- case 'B':
- return BOTH;
- default:
- return null;
- }
- }
- }
-
- public FilterMirrorRepresentation(Mirror mirror) {
- super(FilterMirrorRepresentation.class.getSimpleName());
- setSerializationName(SERIALIZATION_NAME);
- setShowParameterValue(true);
- setFilterClass(FilterMirrorRepresentation.class);
- setFilterType(FilterRepresentation.TYPE_GEOMETRY);
- setTextId(R.string.mirror);
- setEditorId(EditorMirror.ID);
- setMirror(mirror);
- }
-
- public FilterMirrorRepresentation(FilterMirrorRepresentation m) {
- this(m.getMirror());
- }
-
- public FilterMirrorRepresentation() {
- this(getNil());
- }
-
- @Override
- public boolean equals(FilterRepresentation rep) {
- if (!(rep instanceof FilterMirrorRepresentation)) {
- return false;
- }
- FilterMirrorRepresentation mirror = (FilterMirrorRepresentation) rep;
- if (mMirror != mirror.mMirror) {
- return false;
- }
- return true;
- }
-
- public Mirror getMirror() {
- return mMirror;
- }
-
- public void set(FilterMirrorRepresentation r) {
- mMirror = r.mMirror;
- }
-
- public void setMirror(Mirror mirror) {
- if (mirror == null) {
- throw new IllegalArgumentException("Argument to setMirror is null");
- }
- mMirror = mirror;
- }
-
- public void cycle() {
- switch (mMirror) {
- case NONE:
- mMirror = Mirror.HORIZONTAL;
- break;
- case HORIZONTAL:
- mMirror = Mirror.VERTICAL;
- break;
- case VERTICAL:
- mMirror = Mirror.BOTH;
- break;
- case BOTH:
- mMirror = Mirror.NONE;
- break;
- }
- }
-
- @Override
- public boolean allowsSingleInstanceOnly() {
- return true;
- }
-
- @Override
- public FilterRepresentation copy() {
- return new FilterMirrorRepresentation(this);
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- if (!(representation instanceof FilterMirrorRepresentation)) {
- throw new IllegalArgumentException("calling copyAllParameters with incompatible types!");
- }
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- @Override
- public void useParametersFrom(FilterRepresentation a) {
- if (!(a instanceof FilterMirrorRepresentation)) {
- throw new IllegalArgumentException("calling useParametersFrom with incompatible types!");
- }
- setMirror(((FilterMirrorRepresentation) a).getMirror());
- }
-
- @Override
- public boolean isNil() {
- return mMirror == getNil();
- }
-
- public static Mirror getNil() {
- return Mirror.NONE;
- }
-
- @Override
- public void serializeRepresentation(JsonWriter writer) throws IOException {
- writer.beginObject();
- writer.name(SERIALIZATION_MIRROR_VALUE).value(mMirror.value());
- writer.endObject();
- }
-
- @Override
- public void deSerializeRepresentation(JsonReader reader) throws IOException {
- boolean unset = true;
- reader.beginObject();
- while (reader.hasNext()) {
- String name = reader.nextName();
- if (SERIALIZATION_MIRROR_VALUE.equals(name)) {
- Mirror r = Mirror.fromValue((char) reader.nextInt());
- if (r != null) {
- setMirror(r);
- unset = false;
- }
- } else {
- reader.skipValue();
- }
- }
- if (unset) {
- Log.w(TAG, "WARNING: bad value when deserializing " + SERIALIZATION_NAME);
- }
- reader.endObject();
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterPoint.java b/src/com/android/gallery3d/filtershow/filters/FilterPoint.java
deleted file mode 100644
index 4520717a1..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterPoint.java
+++ /dev/null
@@ -1,21 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-public interface FilterPoint {
-
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterPointRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterPointRepresentation.java
deleted file mode 100644
index 9bd1699d9..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterPointRepresentation.java
+++ /dev/null
@@ -1,88 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import java.util.Vector;
-
-public abstract class FilterPointRepresentation extends FilterRepresentation {
- private static final String LOGTAG = "FilterPointRepresentation";
- private Vector<FilterPoint> mCandidates = new Vector<FilterPoint>();
-
- public FilterPointRepresentation(String type, int textid, int editorID) {
- super(type);
- setFilterClass(ImageFilterRedEye.class);
- setFilterType(FilterRepresentation.TYPE_NORMAL);
- setTextId(textid);
- setEditorId(editorID);
- }
-
- @Override
- public abstract FilterRepresentation copy();
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- public boolean hasCandidates() {
- return mCandidates != null;
- }
-
- public Vector<FilterPoint> getCandidates() {
- return mCandidates;
- }
-
- @Override
- public boolean isNil() {
- if (getCandidates() != null && getCandidates().size() > 0) {
- return false;
- }
- return true;
- }
-
- public Object getCandidate(int index) {
- return this.mCandidates.get(index);
- }
-
- public void addCandidate(FilterPoint c) {
- this.mCandidates.add(c);
- }
-
- @Override
- public void useParametersFrom(FilterRepresentation a) {
- if (a instanceof FilterPointRepresentation) {
- FilterPointRepresentation representation = (FilterPointRepresentation) a;
- mCandidates.clear();
- for (FilterPoint redEyeCandidate : representation.mCandidates) {
- mCandidates.add(redEyeCandidate);
- }
- }
- }
-
- public void removeCandidate(RedEyeCandidate c) {
- this.mCandidates.remove(c);
- }
-
- public void clearCandidates() {
- this.mCandidates.clear();
- }
-
- public int getNumberOfCandidates() {
- return mCandidates.size();
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterRedEyeRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterRedEyeRepresentation.java
deleted file mode 100644
index dd06a9760..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterRedEyeRepresentation.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.RectF;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.EditorRedEye;
-
-import java.util.Vector;
-
-public class FilterRedEyeRepresentation extends FilterPointRepresentation {
- private static final String LOGTAG = "FilterRedEyeRepresentation";
-
- public FilterRedEyeRepresentation() {
- super("RedEye",R.string.redeye,EditorRedEye.ID);
- setSerializationName("REDEYE");
- setFilterClass(ImageFilterRedEye.class);
- setOverlayId(R.drawable.photoeditor_effect_redeye);
- setOverlayOnly(true);
- }
-
- @Override
- public FilterRepresentation copy() {
- FilterRedEyeRepresentation representation = new FilterRedEyeRepresentation();
- copyAllParameters(representation);
- return representation;
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- public void addRect(RectF rect, RectF bounds) {
- Vector<RedEyeCandidate> intersects = new Vector<RedEyeCandidate>();
- for (int i = 0; i < getCandidates().size(); i++) {
- RedEyeCandidate r = (RedEyeCandidate) getCandidate(i);
- if (r.intersect(rect)) {
- intersects.add(r);
- }
- }
- for (int i = 0; i < intersects.size(); i++) {
- RedEyeCandidate r = intersects.elementAt(i);
- rect.union(r.mRect);
- bounds.union(r.mBounds);
- removeCandidate(r);
- }
- addCandidate(new RedEyeCandidate(rect, bounds));
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterRepresentation.java
deleted file mode 100644
index 5b33ffba5..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterRepresentation.java
+++ /dev/null
@@ -1,262 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.util.JsonReader;
-import android.util.JsonWriter;
-import android.util.Log;
-
-import com.android.gallery3d.filtershow.editors.BasicEditor;
-
-import java.io.IOException;
-import java.util.ArrayList;
-
-public class FilterRepresentation {
- private static final String LOGTAG = "FilterRepresentation";
- private static final boolean DEBUG = false;
- private String mName;
- private int mPriority = TYPE_NORMAL;
- private Class<?> mFilterClass;
- private boolean mSupportsPartialRendering = false;
- private int mTextId = 0;
- private int mEditorId = BasicEditor.ID;
- private int mButtonId = 0;
- private int mOverlayId = 0;
- private boolean mOverlayOnly = false;
- private boolean mShowParameterValue = true;
- private String mSerializationName;
- public static final byte TYPE_BORDER = 1;
- public static final byte TYPE_FX = 2;
- public static final byte TYPE_WBALANCE = 3;
- public static final byte TYPE_VIGNETTE = 4;
- public static final byte TYPE_NORMAL = 5;
- public static final byte TYPE_TINYPLANET = 6;
- public static final byte TYPE_GEOMETRY = 7;
- protected static final String NAME_TAG = "Name";
-
- public FilterRepresentation(String name) {
- mName = name;
- }
-
- public FilterRepresentation copy(){
- FilterRepresentation representation = new FilterRepresentation(mName);
- representation.useParametersFrom(this);
- return representation;
- }
-
- protected void copyAllParameters(FilterRepresentation representation) {
- representation.setName(getName());
- representation.setFilterClass(getFilterClass());
- representation.setFilterType(getFilterType());
- representation.setSupportsPartialRendering(supportsPartialRendering());
- representation.setTextId(getTextId());
- representation.setEditorId(getEditorId());
- representation.setOverlayId(getOverlayId());
- representation.setOverlayOnly(getOverlayOnly());
- representation.setShowParameterValue(showParameterValue());
- representation.mSerializationName = mSerializationName;
-
- }
-
- public boolean equals(FilterRepresentation representation) {
- if (representation == null) {
- return false;
- }
- if (representation.mFilterClass == mFilterClass
- && representation.mName.equalsIgnoreCase(mName)
- && representation.mPriority == mPriority
- // TODO: After we enable partial rendering, we can switch back
- // to use member variable here.
- && representation.supportsPartialRendering() == supportsPartialRendering()
- && representation.mTextId == mTextId
- && representation.mEditorId == mEditorId
- && representation.mButtonId == mButtonId
- && representation.mOverlayId == mOverlayId
- && representation.mOverlayOnly == mOverlayOnly
- && representation.mShowParameterValue == mShowParameterValue) {
- return true;
- }
- return false;
- }
-
- @Override
- public String toString() {
- return mName;
- }
-
- public void setName(String name) {
- mName = name;
- }
-
- public String getName() {
- return mName;
- }
-
- public void setSerializationName(String sname) {
- mSerializationName = sname;
- }
-
- public String getSerializationName() {
- return mSerializationName;
- }
-
- public void setFilterType(int priority) {
- mPriority = priority;
- }
-
- public int getFilterType() {
- return mPriority;
- }
-
- public boolean isNil() {
- return false;
- }
-
- public boolean supportsPartialRendering() {
- return false && mSupportsPartialRendering; // disable for now
- }
-
- public void setSupportsPartialRendering(boolean value) {
- mSupportsPartialRendering = value;
- }
-
- public void useParametersFrom(FilterRepresentation a) {
- }
-
- public boolean allowsSingleInstanceOnly() {
- return false;
- }
-
- public Class<?> getFilterClass() {
- return mFilterClass;
- }
-
- public void setFilterClass(Class<?> filterClass) {
- mFilterClass = filterClass;
- }
-
- // This same() function is different from equals(), basically it checks
- // whether 2 FilterRepresentations are the same type. It doesn't care about
- // the values.
- public boolean same(FilterRepresentation b) {
- if (b == null) {
- return false;
- }
- return getFilterClass() == b.getFilterClass();
- }
-
- public int getTextId() {
- return mTextId;
- }
-
- public void setTextId(int textId) {
- mTextId = textId;
- }
-
- public int getOverlayId() {
- return mOverlayId;
- }
-
- public void setOverlayId(int overlayId) {
- mOverlayId = overlayId;
- }
-
- public boolean getOverlayOnly() {
- return mOverlayOnly;
- }
-
- public void setOverlayOnly(boolean value) {
- mOverlayOnly = value;
- }
-
- final public int getEditorId() {
- return mEditorId;
- }
-
- public int[] getEditorIds() {
- return new int[] {
- mEditorId };
- }
-
- public void setEditorId(int editorId) {
- mEditorId = editorId;
- }
-
- public boolean showParameterValue() {
- return mShowParameterValue;
- }
-
- public void setShowParameterValue(boolean showParameterValue) {
- mShowParameterValue = showParameterValue;
- }
-
- public String getStateRepresentation() {
- return "";
- }
-
- /**
- * Method must "beginObject()" add its info and "endObject()"
- * @param writer
- * @throws IOException
- */
- public void serializeRepresentation(JsonWriter writer) throws IOException {
- writer.beginObject();
- {
- String[][] rep = serializeRepresentation();
- for (int k = 0; k < rep.length; k++) {
- writer.name(rep[k][0]);
- writer.value(rep[k][1]);
- }
- }
- writer.endObject();
- }
-
- // this is the old way of doing this and will be removed soon
- public String[][] serializeRepresentation() {
- String[][] ret = {{NAME_TAG, getName()}};
- return ret;
- }
-
- public void deSerializeRepresentation(JsonReader reader) throws IOException {
- ArrayList<String[]> al = new ArrayList<String[]>();
- reader.beginObject();
- while (reader.hasNext()) {
- String[] kv = {reader.nextName(), reader.nextString()};
- al.add(kv);
-
- }
- reader.endObject();
- String[][] oldFormat = al.toArray(new String[al.size()][]);
-
- deSerializeRepresentation(oldFormat);
- }
-
- // this is the old way of doing this and will be removed soon
- public void deSerializeRepresentation(String[][] rep) {
- for (int i = 0; i < rep.length; i++) {
- if (NAME_TAG.equals(rep[i][0])) {
- mName = rep[i][1];
- break;
- }
- }
- }
-
- // Override this in subclasses
- public int getStyle() {
- return -1;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterRotateRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterRotateRepresentation.java
deleted file mode 100644
index eb89de036..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterRotateRepresentation.java
+++ /dev/null
@@ -1,190 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.util.JsonReader;
-import android.util.JsonWriter;
-import android.util.Log;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.EditorRotate;
-
-import java.io.IOException;
-
-public class FilterRotateRepresentation extends FilterRepresentation {
- public static final String SERIALIZATION_NAME = "ROTATION";
- public static final String SERIALIZATION_ROTATE_VALUE = "value";
- private static final String TAG = FilterRotateRepresentation.class.getSimpleName();
-
- Rotation mRotation;
-
- public enum Rotation {
- ZERO(0), NINETY(90), ONE_EIGHTY(180), TWO_SEVENTY(270);
- private final int mValue;
-
- private Rotation(int value) {
- mValue = value;
- }
-
- public int value() {
- return mValue;
- }
-
- public static Rotation fromValue(int value) {
- switch (value) {
- case 0:
- return ZERO;
- case 90:
- return NINETY;
- case 180:
- return ONE_EIGHTY;
- case 270:
- return TWO_SEVENTY;
- default:
- return null;
- }
- }
- }
-
- public FilterRotateRepresentation(Rotation rotation) {
- super(FilterRotateRepresentation.class.getSimpleName());
- setSerializationName(SERIALIZATION_NAME);
- setShowParameterValue(true);
- setFilterClass(FilterRotateRepresentation.class);
- setFilterType(FilterRepresentation.TYPE_GEOMETRY);
- setTextId(R.string.rotate);
- setEditorId(EditorRotate.ID);
- setRotation(rotation);
- }
-
- public FilterRotateRepresentation(FilterRotateRepresentation r) {
- this(r.getRotation());
- }
-
- public FilterRotateRepresentation() {
- this(getNil());
- }
-
- public Rotation getRotation() {
- return mRotation;
- }
-
- public void rotateCW() {
- switch(mRotation) {
- case ZERO:
- mRotation = Rotation.NINETY;
- break;
- case NINETY:
- mRotation = Rotation.ONE_EIGHTY;
- break;
- case ONE_EIGHTY:
- mRotation = Rotation.TWO_SEVENTY;
- break;
- case TWO_SEVENTY:
- mRotation = Rotation.ZERO;
- break;
- }
- }
-
- public void set(FilterRotateRepresentation r) {
- mRotation = r.mRotation;
- }
-
- public void setRotation(Rotation rotation) {
- if (rotation == null) {
- throw new IllegalArgumentException("Argument to setRotation is null");
- }
- mRotation = rotation;
- }
-
- @Override
- public boolean allowsSingleInstanceOnly() {
- return true;
- }
-
- @Override
- public FilterRepresentation copy() {
- return new FilterRotateRepresentation(this);
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- if (!(representation instanceof FilterRotateRepresentation)) {
- throw new IllegalArgumentException("calling copyAllParameters with incompatible types!");
- }
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- @Override
- public void useParametersFrom(FilterRepresentation a) {
- if (!(a instanceof FilterRotateRepresentation)) {
- throw new IllegalArgumentException("calling useParametersFrom with incompatible types!");
- }
- setRotation(((FilterRotateRepresentation) a).getRotation());
- }
-
- @Override
- public boolean isNil() {
- return mRotation == getNil();
- }
-
- public static Rotation getNil() {
- return Rotation.ZERO;
- }
-
- @Override
- public void serializeRepresentation(JsonWriter writer) throws IOException {
- writer.beginObject();
- writer.name(SERIALIZATION_ROTATE_VALUE).value(mRotation.value());
- writer.endObject();
- }
-
- @Override
- public boolean equals(FilterRepresentation rep) {
- if (!(rep instanceof FilterRotateRepresentation)) {
- return false;
- }
- FilterRotateRepresentation rotate = (FilterRotateRepresentation) rep;
- if (rotate.mRotation.value() != mRotation.value()) {
- return false;
- }
- return true;
- }
-
- @Override
- public void deSerializeRepresentation(JsonReader reader) throws IOException {
- boolean unset = true;
- reader.beginObject();
- while (reader.hasNext()) {
- String name = reader.nextName();
- if (SERIALIZATION_ROTATE_VALUE.equals(name)) {
- Rotation r = Rotation.fromValue(reader.nextInt());
- if (r != null) {
- setRotation(r);
- unset = false;
- }
- } else {
- reader.skipValue();
- }
- }
- if (unset) {
- Log.w(TAG, "WARNING: bad value when deserializing " + SERIALIZATION_NAME);
- }
- reader.endObject();
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterStraightenRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterStraightenRepresentation.java
deleted file mode 100644
index 94c9497fc..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterStraightenRepresentation.java
+++ /dev/null
@@ -1,154 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.util.JsonReader;
-import android.util.JsonWriter;
-import android.util.Log;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.EditorStraighten;
-
-import java.io.IOException;
-
-public class FilterStraightenRepresentation extends FilterRepresentation {
- public static final String SERIALIZATION_NAME = "STRAIGHTEN";
- public static final String SERIALIZATION_STRAIGHTEN_VALUE = "value";
- private static final String TAG = FilterStraightenRepresentation.class.getSimpleName();
- public static final int MAX_STRAIGHTEN_ANGLE = 45;
- public static final int MIN_STRAIGHTEN_ANGLE = -45;
-
- float mStraighten;
-
- public FilterStraightenRepresentation(float straighten) {
- super(FilterStraightenRepresentation.class.getSimpleName());
- setSerializationName(SERIALIZATION_NAME);
- setShowParameterValue(true);
- setFilterClass(FilterStraightenRepresentation.class);
- setFilterType(FilterRepresentation.TYPE_GEOMETRY);
- setTextId(R.string.straighten);
- setEditorId(EditorStraighten.ID);
- setStraighten(straighten);
- }
-
- public FilterStraightenRepresentation(FilterStraightenRepresentation s) {
- this(s.getStraighten());
- }
-
- public FilterStraightenRepresentation() {
- this(getNil());
- }
-
- public void set(FilterStraightenRepresentation r) {
- mStraighten = r.mStraighten;
- }
-
- @Override
- public boolean equals(FilterRepresentation rep) {
- if (!(rep instanceof FilterStraightenRepresentation)) {
- return false;
- }
- FilterStraightenRepresentation straighten = (FilterStraightenRepresentation) rep;
- if (straighten.mStraighten != mStraighten) {
- return false;
- }
- return true;
- }
-
- public float getStraighten() {
- return mStraighten;
- }
-
- public void setStraighten(float straighten) {
- if (!rangeCheck(straighten)) {
- straighten = Math.min(Math.max(straighten, MIN_STRAIGHTEN_ANGLE), MAX_STRAIGHTEN_ANGLE);
- }
- mStraighten = straighten;
- }
-
- @Override
- public boolean allowsSingleInstanceOnly() {
- return true;
- }
-
- @Override
- public FilterRepresentation copy() {
- return new FilterStraightenRepresentation(this);
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- if (!(representation instanceof FilterStraightenRepresentation)) {
- throw new IllegalArgumentException("calling copyAllParameters with incompatible types!");
- }
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- @Override
- public void useParametersFrom(FilterRepresentation a) {
- if (!(a instanceof FilterStraightenRepresentation)) {
- throw new IllegalArgumentException("calling useParametersFrom with incompatible types!");
- }
- setStraighten(((FilterStraightenRepresentation) a).getStraighten());
- }
-
- @Override
- public boolean isNil() {
- return mStraighten == getNil();
- }
-
- public static float getNil() {
- return 0;
- }
-
- @Override
- public void serializeRepresentation(JsonWriter writer) throws IOException {
- writer.beginObject();
- writer.name(SERIALIZATION_STRAIGHTEN_VALUE).value(mStraighten);
- writer.endObject();
- }
-
- @Override
- public void deSerializeRepresentation(JsonReader reader) throws IOException {
- boolean unset = true;
- reader.beginObject();
- while (reader.hasNext()) {
- String name = reader.nextName();
- if (SERIALIZATION_STRAIGHTEN_VALUE.equals(name)) {
- float s = (float) reader.nextDouble();
- if (rangeCheck(s)) {
- setStraighten(s);
- unset = false;
- }
- } else {
- reader.skipValue();
- }
- }
- if (unset) {
- Log.w(TAG, "WARNING: bad value when deserializing " + SERIALIZATION_NAME);
- }
- reader.endObject();
- }
-
- private boolean rangeCheck(double s) {
- if (s < -45 || s > 45) {
- return false;
- }
- return true;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterTinyPlanetRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterTinyPlanetRepresentation.java
deleted file mode 100644
index be1812957..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterTinyPlanetRepresentation.java
+++ /dev/null
@@ -1,101 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.EditorTinyPlanet;
-
-public class FilterTinyPlanetRepresentation extends FilterBasicRepresentation {
- private static final String SERIALIZATION_NAME = "TINYPLANET";
- private static final String LOGTAG = "FilterTinyPlanetRepresentation";
- private static final String SERIAL_ANGLE = "Angle";
- private float mAngle = 0;
-
- public FilterTinyPlanetRepresentation() {
- super("TinyPlanet", 0, 50, 100);
- setSerializationName(SERIALIZATION_NAME);
- setShowParameterValue(true);
- setFilterClass(ImageFilterTinyPlanet.class);
- setFilterType(FilterRepresentation.TYPE_TINYPLANET);
- setTextId(R.string.tinyplanet);
- setEditorId(EditorTinyPlanet.ID);
- setMinimum(1);
- }
-
- @Override
- public FilterRepresentation copy() {
- FilterTinyPlanetRepresentation representation = new FilterTinyPlanetRepresentation();
- copyAllParameters(representation);
- return representation;
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- @Override
- public void useParametersFrom(FilterRepresentation a) {
- FilterTinyPlanetRepresentation representation = (FilterTinyPlanetRepresentation) a;
- super.useParametersFrom(a);
- mAngle = representation.mAngle;
- setZoom(representation.getZoom());
- }
-
- public void setAngle(float angle) {
- mAngle = angle;
- }
-
- public float getAngle() {
- return mAngle;
- }
-
- public int getZoom() {
- return getValue();
- }
-
- public void setZoom(int zoom) {
- setValue(zoom);
- }
-
- public boolean isNil() {
- // TinyPlanet always has an effect
- return false;
- }
-
- @Override
- public String[][] serializeRepresentation() {
- String[][] ret = {
- {SERIAL_NAME , getName() },
- {SERIAL_VALUE , Integer.toString(getValue())},
- {SERIAL_ANGLE , Float.toString(mAngle)}};
- return ret;
- }
-
- @Override
- public void deSerializeRepresentation(String[][] rep) {
- super.deSerializeRepresentation(rep);
- for (int i = 0; i < rep.length; i++) {
- if (SERIAL_VALUE.equals(rep[i][0])) {
- setValue(Integer.parseInt(rep[i][1]));
- } else if (SERIAL_ANGLE.equals(rep[i][0])) {
- setAngle(Float.parseFloat(rep[i][1]));
- }
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterUserPresetRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterUserPresetRepresentation.java
deleted file mode 100644
index dfdb6fcf0..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterUserPresetRepresentation.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.filtershow.editors.ImageOnlyEditor;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-
-public class FilterUserPresetRepresentation extends FilterRepresentation {
-
- private ImagePreset mPreset;
- private int mId;
-
- public FilterUserPresetRepresentation(String name, ImagePreset preset, int id) {
- super(name);
- setEditorId(ImageOnlyEditor.ID);
- setFilterType(FilterRepresentation.TYPE_FX);
- mPreset = preset;
- mId = id;
- }
-
- public ImagePreset getImagePreset() {
- return mPreset;
- }
-
- public int getId() {
- return mId;
- }
-
- public FilterRepresentation copy(){
- FilterRepresentation representation = new FilterUserPresetRepresentation(getName(),
- new ImagePreset(mPreset), mId);
- return representation;
- }
-
- @Override
- public boolean allowsSingleInstanceOnly() {
- return true;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FilterVignetteRepresentation.java b/src/com/android/gallery3d/filtershow/filters/FilterVignetteRepresentation.java
deleted file mode 100644
index 42a7406bc..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FilterVignetteRepresentation.java
+++ /dev/null
@@ -1,173 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.EditorVignette;
-import com.android.gallery3d.filtershow.imageshow.Oval;
-
-public class FilterVignetteRepresentation extends FilterBasicRepresentation implements Oval {
- private static final String LOGTAG = "FilterVignetteRepresentation";
- private float mCenterX = Float.NaN;
- private float mCenterY;
- private float mRadiusX = Float.NaN;
- private float mRadiusY;
-
- public FilterVignetteRepresentation() {
- super("Vignette", -100, 50, 100);
- setSerializationName("VIGNETTE");
- setShowParameterValue(true);
- setFilterType(FilterRepresentation.TYPE_VIGNETTE);
- setTextId(R.string.vignette);
- setEditorId(EditorVignette.ID);
- setName("Vignette");
- setFilterClass(ImageFilterVignette.class);
- setMinimum(-100);
- setMaximum(100);
- setDefaultValue(0);
- }
-
- @Override
- public void useParametersFrom(FilterRepresentation a) {
- super.useParametersFrom(a);
- mCenterX = ((FilterVignetteRepresentation) a).mCenterX;
- mCenterY = ((FilterVignetteRepresentation) a).mCenterY;
- mRadiusX = ((FilterVignetteRepresentation) a).mRadiusX;
- mRadiusY = ((FilterVignetteRepresentation) a).mRadiusY;
- }
-
- @Override
- public FilterRepresentation copy() {
- FilterVignetteRepresentation representation = new FilterVignetteRepresentation();
- copyAllParameters(representation);
- return representation;
- }
-
- @Override
- protected void copyAllParameters(FilterRepresentation representation) {
- super.copyAllParameters(representation);
- representation.useParametersFrom(this);
- }
-
- @Override
- public void setCenter(float centerX, float centerY) {
- mCenterX = centerX;
- mCenterY = centerY;
- }
-
- @Override
- public float getCenterX() {
- return mCenterX;
- }
-
- @Override
- public float getCenterY() {
- return mCenterY;
- }
-
- @Override
- public void setRadius(float radiusX, float radiusY) {
- mRadiusX = radiusX;
- mRadiusY = radiusY;
- }
-
- @Override
- public void setRadiusX(float radiusX) {
- mRadiusX = radiusX;
- }
-
- @Override
- public void setRadiusY(float radiusY) {
- mRadiusY = radiusY;
- }
-
- @Override
- public float getRadiusX() {
- return mRadiusX;
- }
-
- @Override
- public float getRadiusY() {
- return mRadiusY;
- }
-
- public boolean isCenterSet() {
- return mCenterX != Float.NaN;
- }
-
- @Override
- public boolean isNil() {
- return getValue() == 0;
- }
-
- @Override
- public boolean equals(FilterRepresentation representation) {
- if (!super.equals(representation)) {
- return false;
- }
- if (representation instanceof FilterVignetteRepresentation) {
- FilterVignetteRepresentation rep = (FilterVignetteRepresentation) representation;
- if (rep.getCenterX() == getCenterX()
- && rep.getCenterY() == getCenterY()
- && rep.getRadiusX() == getRadiusX()
- && rep.getRadiusY() == getRadiusY()) {
- return true;
- }
- }
- return false;
- }
-
- private static final String[] sParams = {
- "Name", "value", "mCenterX", "mCenterY", "mRadiusX",
- "mRadiusY"
- };
-
- @Override
- public String[][] serializeRepresentation() {
- String[][] ret = {
- { sParams[0], getName() },
- { sParams[1], Integer.toString(getValue()) },
- { sParams[2], Float.toString(mCenterX) },
- { sParams[3], Float.toString(mCenterY) },
- { sParams[4], Float.toString(mRadiusX) },
- { sParams[5], Float.toString(mRadiusY) }
- };
- return ret;
- }
-
- @Override
- public void deSerializeRepresentation(String[][] rep) {
- super.deSerializeRepresentation(rep);
- for (int i = 0; i < rep.length; i++) {
- String key = rep[i][0];
- String value = rep[i][1];
- if (sParams[0].equals(key)) {
- setName(value);
- } else if (sParams[1].equals(key)) {
- setValue(Integer.parseInt(value));
- } else if (sParams[2].equals(key)) {
- mCenterX = Float.parseFloat(value);
- } else if (sParams[3].equals(key)) {
- mCenterY = Float.parseFloat(value);
- } else if (sParams[4].equals(key)) {
- mRadiusX = Float.parseFloat(value);
- } else if (sParams[5].equals(key)) {
- mRadiusY = Float.parseFloat(value);
- }
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/FiltersManagerInterface.java b/src/com/android/gallery3d/filtershow/filters/FiltersManagerInterface.java
deleted file mode 100644
index 710128f99..000000000
--- a/src/com/android/gallery3d/filtershow/filters/FiltersManagerInterface.java
+++ /dev/null
@@ -1,21 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-public interface FiltersManagerInterface {
- ImageFilter getFilterForRepresentation(FilterRepresentation representation);
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/IconUtilities.java b/src/com/android/gallery3d/filtershow/filters/IconUtilities.java
deleted file mode 100644
index e2a01472d..000000000
--- a/src/com/android/gallery3d/filtershow/filters/IconUtilities.java
+++ /dev/null
@@ -1,75 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-
-import com.android.gallery3d.R;
-
-public class IconUtilities {
- public static final int PUNCH = R.drawable.filtershow_fx_0005_punch;
- public static final int VINTAGE = R.drawable.filtershow_fx_0000_vintage;
- public static final int BW_CONTRAST = R.drawable.filtershow_fx_0004_bw_contrast;
- public static final int BLEACH = R.drawable.filtershow_fx_0002_bleach;
- public static final int INSTANT = R.drawable.filtershow_fx_0001_instant;
- public static final int WASHOUT = R.drawable.filtershow_fx_0007_washout;
- public static final int BLUECRUSH = R.drawable.filtershow_fx_0003_blue_crush;
- public static final int WASHOUT_COLOR = R.drawable.filtershow_fx_0008_washout_color;
- public static final int X_PROCESS = R.drawable.filtershow_fx_0006_x_process;
-
- public static Bitmap getFXBitmap(Resources res, int id) {
- Bitmap ret;
- BitmapFactory.Options o = new BitmapFactory.Options();
- o.inScaled = false;
-
- if (id != 0) {
- return BitmapFactory.decodeResource(res, id, o);
- }
- return null;
- }
-
- public static Bitmap loadBitmap(Resources res, int resource) {
-
- final BitmapFactory.Options options = new BitmapFactory.Options();
- options.inPreferredConfig = Bitmap.Config.ARGB_8888;
- Bitmap bitmap = BitmapFactory.decodeResource(
- res,
- resource, options);
-
- return bitmap;
- }
-
- public static Bitmap applyFX(Bitmap bitmap, final Bitmap fxBitmap) {
- ImageFilterFx fx = new ImageFilterFx() {
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
-
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- int fxw = fxBitmap.getWidth();
- int fxh = fxBitmap.getHeight();
- int start = 0;
- int end = w * h * 4;
- nativeApplyFilter(bitmap, w, h, fxBitmap, fxw, fxh, start, end);
- return bitmap;
- }
- };
- return fx.apply(bitmap, 0, 0);
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilter.java b/src/com/android/gallery3d/filtershow/filters/ImageFilter.java
deleted file mode 100644
index 437137416..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilter.java
+++ /dev/null
@@ -1,109 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.app.Activity;
-import android.graphics.Bitmap;
-import android.graphics.Matrix;
-import android.support.v8.renderscript.Allocation;
-import android.widget.Toast;
-
-import com.android.gallery3d.filtershow.imageshow.GeometryMathUtils;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.pipeline.FilterEnvironment;
-
-public abstract class ImageFilter implements Cloneable {
- private FilterEnvironment mEnvironment = null;
-
- protected String mName = "Original";
- private final String LOGTAG = "ImageFilter";
- protected static final boolean SIMPLE_ICONS = true;
- // TODO: Temporary, for dogfood note memory issues with toasts for better
- // feedback. Remove this when filters actually work in low memory
- // situations.
- private static Activity sActivity = null;
-
- public static void setActivityForMemoryToasts(Activity activity) {
- sActivity = activity;
- }
-
- public static void resetStatics() {
- sActivity = null;
- }
-
- public void freeResources() {}
-
- public void displayLowMemoryToast() {
- if (sActivity != null) {
- sActivity.runOnUiThread(new Runnable() {
- public void run() {
- Toast.makeText(sActivity, "Memory too low for filter " + getName() +
- ", please file a bug report", Toast.LENGTH_SHORT).show();
- }
- });
- }
- }
-
- public void setName(String name) {
- mName = name;
- }
-
- public String getName() {
- return mName;
- }
-
- public boolean supportsAllocationInput() { return false; }
-
- public void apply(Allocation in, Allocation out) {
- setGeneralParameters();
- }
-
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- // do nothing here, subclasses will implement filtering here
- setGeneralParameters();
- return bitmap;
- }
-
- public abstract void useRepresentation(FilterRepresentation representation);
-
- native protected void nativeApplyGradientFilter(Bitmap bitmap, int w, int h,
- int[] redGradient, int[] greenGradient, int[] blueGradient);
-
- public FilterRepresentation getDefaultRepresentation() {
- return null;
- }
-
- protected Matrix getOriginalToScreenMatrix(int w, int h) {
- return GeometryMathUtils.getImageToScreenMatrix(getEnvironment().getImagePreset()
- .getGeometryFilters(), true, MasterImage.getImage().getOriginalBounds(), w, h);
- }
-
- public void setEnvironment(FilterEnvironment environment) {
- mEnvironment = environment;
- }
-
- public FilterEnvironment getEnvironment() {
- return mEnvironment;
- }
-
- public void setGeneralParameters() {
- // should implement in subclass which like to transport
- // some information to other filters. (like the style setting from RetroLux
- // and Film to FixedFrame)
- mEnvironment.clearGeneralParameters();
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterBorder.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterBorder.java
deleted file mode 100644
index a7286f0fa..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterBorder.java
+++ /dev/null
@@ -1,92 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.Canvas;
-import android.graphics.Rect;
-import android.graphics.drawable.BitmapDrawable;
-import android.graphics.drawable.Drawable;
-
-import java.util.HashMap;
-
-public class ImageFilterBorder extends ImageFilter {
- private static final float NINEPATCH_ICON_SCALING = 10;
- private static final float BITMAP_ICON_SCALING = 1 / 3.0f;
- private FilterImageBorderRepresentation mParameters = null;
- private Resources mResources = null;
-
- private HashMap<Integer, Drawable> mDrawables = new HashMap<Integer, Drawable>();
-
- public ImageFilterBorder() {
- mName = "Border";
- }
-
- public void useRepresentation(FilterRepresentation representation) {
- FilterImageBorderRepresentation parameters = (FilterImageBorderRepresentation) representation;
- mParameters = parameters;
- }
-
- public FilterImageBorderRepresentation getParameters() {
- return mParameters;
- }
-
- public void freeResources() {
- mDrawables.clear();
- }
-
- public Bitmap applyHelper(Bitmap bitmap, float scale1, float scale2 ) {
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- Rect bounds = new Rect(0, 0, (int) (w * scale1), (int) (h * scale1));
- Canvas canvas = new Canvas(bitmap);
- canvas.scale(scale2, scale2);
- Drawable drawable = getDrawable(getParameters().getDrawableResource());
- drawable.setBounds(bounds);
- drawable.draw(canvas);
- return bitmap;
- }
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (getParameters() == null || getParameters().getDrawableResource() == 0) {
- return bitmap;
- }
- float scale2 = scaleFactor * 2.0f;
- float scale1 = 1 / scale2;
- return applyHelper(bitmap, scale1, scale2);
- }
-
- public void setResources(Resources resources) {
- if (mResources != resources) {
- mResources = resources;
- mDrawables.clear();
- }
- }
-
- public Drawable getDrawable(int rsc) {
- Drawable drawable = mDrawables.get(rsc);
- if (drawable == null && mResources != null && rsc != 0) {
- drawable = new BitmapDrawable(mResources, BitmapFactory.decodeResource(mResources, rsc));
- mDrawables.put(rsc, drawable);
- }
- return drawable;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterBwFilter.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterBwFilter.java
deleted file mode 100644
index 50837ca2f..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterBwFilter.java
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.R;
-
-import android.graphics.Bitmap;
-import android.graphics.Color;
-
-
-public class ImageFilterBwFilter extends SimpleImageFilter {
- private static final String SERIALIZATION_NAME = "BWFILTER";
-
- public ImageFilterBwFilter() {
- mName = "BW Filter";
- }
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterBasicRepresentation representation = (FilterBasicRepresentation) super.getDefaultRepresentation();
- representation.setName("BW Filter");
- representation.setSerializationName(SERIALIZATION_NAME);
-
- representation.setFilterClass(ImageFilterBwFilter.class);
- representation.setMaximum(180);
- representation.setMinimum(-180);
- representation.setTextId(R.string.bwfilter);
- representation.setSupportsPartialRendering(true);
- return representation;
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int w, int h, int r, int g, int b);
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (getParameters() == null) {
- return bitmap;
- }
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- float[] hsv = new float[] {
- 180 + getParameters().getValue(), 1, 1
- };
- int rgb = Color.HSVToColor(hsv);
- int r = 0xFF & (rgb >> 16);
- int g = 0xFF & (rgb >> 8);
- int b = 0xFF & (rgb >> 0);
- nativeApplyFilter(bitmap, w, h, r, g, b);
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterChanSat.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterChanSat.java
deleted file mode 100644
index 1ea8edfb8..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterChanSat.java
+++ /dev/null
@@ -1,161 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Bitmap;
-import android.graphics.Matrix;
-import android.support.v8.renderscript.Allocation;
-import android.support.v8.renderscript.Element;
-import android.support.v8.renderscript.RenderScript;
-import android.support.v8.renderscript.Script.LaunchOptions;
-import android.support.v8.renderscript.Type;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.pipeline.FilterEnvironment;
-
-public class ImageFilterChanSat extends ImageFilterRS {
- private static final String LOGTAG = "ImageFilterChanSat";
- private ScriptC_saturation mScript;
- private Bitmap mSourceBitmap;
-
- private static final int STRIP_SIZE = 64;
-
- FilterChanSatRepresentation mParameters = new FilterChanSatRepresentation();
- private Bitmap mOverlayBitmap;
-
- public ImageFilterChanSat() {
- mName = "ChannelSat";
- }
-
- @Override
- public FilterRepresentation getDefaultRepresentation() {
- return new FilterChanSatRepresentation();
- }
-
- @Override
- public void useRepresentation(FilterRepresentation representation) {
- mParameters = (FilterChanSatRepresentation) representation;
- }
-
- @Override
- protected void resetAllocations() {
-
- }
-
- @Override
- public void resetScripts() {
- if (mScript != null) {
- mScript.destroy();
- mScript = null;
- }
- }
- @Override
- protected void createFilter(android.content.res.Resources res, float scaleFactor,
- int quality) {
- createFilter(res, scaleFactor, quality, getInPixelsAllocation());
- }
-
- @Override
- protected void createFilter(android.content.res.Resources res, float scaleFactor,
- int quality, Allocation in) {
- RenderScript rsCtx = getRenderScriptContext();
-
- Type.Builder tb_float = new Type.Builder(rsCtx, Element.F32_4(rsCtx));
- tb_float.setX(in.getType().getX());
- tb_float.setY(in.getType().getY());
- mScript = new ScriptC_saturation(rsCtx, res, R.raw.saturation);
- }
-
-
- private Bitmap getSourceBitmap() {
- assert (mSourceBitmap != null);
- return mSourceBitmap;
- }
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (SIMPLE_ICONS && FilterEnvironment.QUALITY_ICON == quality) {
- return bitmap;
- }
-
- mSourceBitmap = bitmap;
- Bitmap ret = super.apply(bitmap, scaleFactor, quality);
- mSourceBitmap = null;
-
- return ret;
- }
-
- @Override
- protected void bindScriptValues() {
- int width = getInPixelsAllocation().getType().getX();
- int height = getInPixelsAllocation().getType().getY();
- }
-
-
-
- @Override
- protected void runFilter() {
- int []sat = new int[7];
- for(int i = 0;i<sat.length ;i ++){
- sat[i] = mParameters.getValue(i);
- }
-
-
- int width = getInPixelsAllocation().getType().getX();
- int height = getInPixelsAllocation().getType().getY();
- Matrix m = getOriginalToScreenMatrix(width, height);
-
-
- mScript.set_saturation(sat);
-
- mScript.invoke_setupGradParams();
- runSelectiveAdjust(
- getInPixelsAllocation(), getOutPixelsAllocation());
-
- }
-
- private void runSelectiveAdjust(Allocation in, Allocation out) {
- int width = in.getType().getX();
- int height = in.getType().getY();
-
- LaunchOptions options = new LaunchOptions();
- int ty;
- options.setX(0, width);
-
- for (ty = 0; ty < height; ty += STRIP_SIZE) {
- int endy = ty + STRIP_SIZE;
- if (endy > height) {
- endy = height;
- }
- options.setY(ty, endy);
- mScript.forEach_selectiveAdjust(in, out, options);
- if (checkStop()) {
- return;
- }
- }
- }
-
- private boolean checkStop() {
- RenderScript rsCtx = getRenderScriptContext();
- rsCtx.finish();
- if (getEnvironment().needsStop()) {
- return true;
- }
- return false;
- }
-}
-
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterContrast.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterContrast.java
deleted file mode 100644
index 27c0e0877..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterContrast.java
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.R;
-
-import android.graphics.Bitmap;
-
-public class ImageFilterContrast extends SimpleImageFilter {
- private static final String SERIALIZATION_NAME = "CONTRAST";
-
- public ImageFilterContrast() {
- mName = "Contrast";
- }
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterBasicRepresentation representation =
- (FilterBasicRepresentation) super.getDefaultRepresentation();
- representation.setName("Contrast");
- representation.setSerializationName(SERIALIZATION_NAME);
-
- representation.setFilterClass(ImageFilterContrast.class);
- representation.setTextId(R.string.contrast);
- representation.setMinimum(-100);
- representation.setMaximum(100);
- representation.setDefaultValue(0);
- representation.setSupportsPartialRendering(true);
- return representation;
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int w, int h, float strength);
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (getParameters() == null) {
- return bitmap;
- }
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- float value = getParameters().getValue();
- nativeApplyFilter(bitmap, w, h, value);
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterCurves.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterCurves.java
deleted file mode 100644
index 61b60d2e3..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterCurves.java
+++ /dev/null
@@ -1,112 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Bitmap;
-
-import com.android.gallery3d.filtershow.imageshow.Spline;
-
-public class ImageFilterCurves extends ImageFilter {
-
- private static final String LOGTAG = "ImageFilterCurves";
- FilterCurvesRepresentation mParameters = new FilterCurvesRepresentation();
-
- @Override
- public FilterRepresentation getDefaultRepresentation() {
- return new FilterCurvesRepresentation();
- }
-
- @Override
- public void useRepresentation(FilterRepresentation representation) {
- FilterCurvesRepresentation parameters = (FilterCurvesRepresentation) representation;
- mParameters = parameters;
- }
-
- public ImageFilterCurves() {
- mName = "Curves";
- reset();
- }
-
- public void populateArray(int[] array, int curveIndex) {
- Spline spline = mParameters.getSpline(curveIndex);
- if (spline == null) {
- return;
- }
- float[] curve = spline.getAppliedCurve();
- for (int i = 0; i < 256; i++) {
- array[i] = (int) (curve[i] * 255);
- }
- }
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (!mParameters.getSpline(Spline.RGB).isOriginal()) {
- int[] rgbGradient = new int[256];
- populateArray(rgbGradient, Spline.RGB);
- nativeApplyGradientFilter(bitmap, bitmap.getWidth(), bitmap.getHeight(),
- rgbGradient, rgbGradient, rgbGradient);
- }
-
- int[] redGradient = null;
- if (!mParameters.getSpline(Spline.RED).isOriginal()) {
- redGradient = new int[256];
- populateArray(redGradient, Spline.RED);
- }
- int[] greenGradient = null;
- if (!mParameters.getSpline(Spline.GREEN).isOriginal()) {
- greenGradient = new int[256];
- populateArray(greenGradient, Spline.GREEN);
- }
- int[] blueGradient = null;
- if (!mParameters.getSpline(Spline.BLUE).isOriginal()) {
- blueGradient = new int[256];
- populateArray(blueGradient, Spline.BLUE);
- }
-
- nativeApplyGradientFilter(bitmap, bitmap.getWidth(), bitmap.getHeight(),
- redGradient, greenGradient, blueGradient);
- return bitmap;
- }
-
- public void setSpline(Spline spline, int splineIndex) {
- mParameters.setSpline(splineIndex, new Spline(spline));
- }
-
- public Spline getSpline(int splineIndex) {
- return mParameters.getSpline(splineIndex);
- }
-
- public void reset() {
- Spline spline = new Spline();
-
- spline.addPoint(0.0f, 1.0f);
- spline.addPoint(1.0f, 0.0f);
-
- for (int i = 0; i < 4; i++) {
- mParameters.setSpline(i, new Spline(spline));
- }
- }
-
- public void useFilter(ImageFilter a) {
- ImageFilterCurves c = (ImageFilterCurves) a;
- for (int i = 0; i < 4; i++) {
- if (c.mParameters.getSpline(i) != null) {
- setSpline(c.mParameters.getSpline(i), i);
- }
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterDownsample.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterDownsample.java
deleted file mode 100644
index efb9cde71..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterDownsample.java
+++ /dev/null
@@ -1,83 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Rect;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.cache.ImageLoader;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-
-public class ImageFilterDownsample extends SimpleImageFilter {
- private static final String SERIALIZATION_NAME = "DOWNSAMPLE";
- private static final int ICON_DOWNSAMPLE_FRACTION = 8;
- private ImageLoader mImageLoader;
-
- public ImageFilterDownsample(ImageLoader loader) {
- mName = "Downsample";
- mImageLoader = loader;
- }
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterBasicRepresentation representation = (FilterBasicRepresentation) super.getDefaultRepresentation();
- representation.setName("Downsample");
- representation.setSerializationName(SERIALIZATION_NAME);
-
- representation.setFilterClass(ImageFilterDownsample.class);
- representation.setMaximum(100);
- representation.setMinimum(1);
- representation.setValue(50);
- representation.setDefaultValue(50);
- representation.setPreviewValue(3);
- representation.setTextId(R.string.downsample);
- return representation;
- }
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (getParameters() == null) {
- return bitmap;
- }
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- int p = getParameters().getValue();
-
- // size of original precached image
- Rect size = MasterImage.getImage().getOriginalBounds();
- int orig_w = size.width();
- int orig_h = size.height();
-
- if (p > 0 && p < 100) {
- // scale preview to same size as the resulting bitmap from a "save"
- int newWidth = orig_w * p / 100;
- int newHeight = orig_h * p / 100;
-
- // only scale preview if preview isn't already scaled enough
- if (newWidth <= 0 || newHeight <= 0 || newWidth >= w || newHeight >= h) {
- return bitmap;
- }
- Bitmap ret = Bitmap.createScaledBitmap(bitmap, newWidth, newHeight, true);
- if (ret != bitmap) {
- bitmap.recycle();
- }
- return ret;
- }
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterDraw.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterDraw.java
deleted file mode 100644
index 7df5ffb64..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterDraw.java
+++ /dev/null
@@ -1,278 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.Paint.Style;
-import android.graphics.Path;
-import android.graphics.PathMeasure;
-import android.graphics.PorterDuff;
-import android.graphics.PorterDuffColorFilter;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.cache.ImageLoader;
-import com.android.gallery3d.filtershow.filters.FilterDrawRepresentation.StrokeData;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.pipeline.FilterEnvironment;
-
-import java.util.Vector;
-
-public class ImageFilterDraw extends ImageFilter {
- private static final String LOGTAG = "ImageFilterDraw";
- public final static byte SIMPLE_STYLE = 0;
- public final static byte BRUSH_STYLE_SPATTER = 1;
- public final static byte BRUSH_STYLE_MARKER = 2;
- public final static int NUMBER_OF_STYLES = 3;
- Bitmap mOverlayBitmap; // this accelerates interaction
- int mCachedStrokes = -1;
- int mCurrentStyle = 0;
-
- FilterDrawRepresentation mParameters = new FilterDrawRepresentation();
-
- public ImageFilterDraw() {
- mName = "Image Draw";
- }
-
- DrawStyle[] mDrawingsTypes = new DrawStyle[] {
- new SimpleDraw(),
- new Brush(R.drawable.brush_marker),
- new Brush(R.drawable.brush_spatter)
- };
- {
- for (int i = 0; i < mDrawingsTypes.length; i++) {
- mDrawingsTypes[i].setType((byte) i);
- }
-
- }
-
- @Override
- public FilterRepresentation getDefaultRepresentation() {
- return new FilterDrawRepresentation();
- }
-
- @Override
- public void useRepresentation(FilterRepresentation representation) {
- FilterDrawRepresentation parameters = (FilterDrawRepresentation) representation;
- mParameters = parameters;
- }
-
- public void setStyle(byte style) {
- mCurrentStyle = style % mDrawingsTypes.length;
- }
-
- public int getStyle() {
- return mCurrentStyle;
- }
-
- public static interface DrawStyle {
- public void setType(byte type);
- public void paint(FilterDrawRepresentation.StrokeData sd, Canvas canvas, Matrix toScrMatrix,
- int quality);
- }
-
- class SimpleDraw implements DrawStyle {
- byte mType;
-
- @Override
- public void setType(byte type) {
- mType = type;
- }
-
- @Override
- public void paint(FilterDrawRepresentation.StrokeData sd, Canvas canvas, Matrix toScrMatrix,
- int quality) {
- if (sd == null) {
- return;
- }
- if (sd.mPath == null) {
- return;
- }
- Paint paint = new Paint();
-
- paint.setStyle(Style.STROKE);
- paint.setColor(sd.mColor);
- paint.setStrokeWidth(toScrMatrix.mapRadius(sd.mRadius));
-
- // done this way because of a bug in path.transform(matrix)
- Path mCacheTransPath = new Path();
- mCacheTransPath.addPath(sd.mPath, toScrMatrix);
-
- canvas.drawPath(mCacheTransPath, paint);
- }
- }
-
- class Brush implements DrawStyle {
- int mBrushID;
- Bitmap mBrush;
- byte mType;
-
- public Brush(int brushID) {
- mBrushID = brushID;
- }
-
- public Bitmap getBrush() {
- if (mBrush == null) {
- BitmapFactory.Options opt = new BitmapFactory.Options();
- opt.inPreferredConfig = Bitmap.Config.ALPHA_8;
- mBrush = BitmapFactory.decodeResource(MasterImage.getImage().getActivity()
- .getResources(), mBrushID, opt);
- mBrush = mBrush.extractAlpha();
- }
- return mBrush;
- }
-
- @Override
- public void paint(FilterDrawRepresentation.StrokeData sd, Canvas canvas,
- Matrix toScrMatrix,
- int quality) {
- if (sd == null || sd.mPath == null) {
- return;
- }
- Paint paint = new Paint();
- paint.setStyle(Style.STROKE);
- paint.setAntiAlias(true);
- Path mCacheTransPath = new Path();
- mCacheTransPath.addPath(sd.mPath, toScrMatrix);
- draw(canvas, paint, sd.mColor, toScrMatrix.mapRadius(sd.mRadius) * 2,
- mCacheTransPath);
- }
-
- public Bitmap createScaledBitmap(Bitmap src, int dstWidth, int dstHeight, boolean filter)
- {
- Matrix m = new Matrix();
- m.setScale(dstWidth / (float) src.getWidth(), dstHeight / (float) src.getHeight());
- Bitmap result = Bitmap.createBitmap(dstWidth, dstHeight, src.getConfig());
- Canvas canvas = new Canvas(result);
-
- Paint paint = new Paint();
- paint.setFilterBitmap(filter);
- canvas.drawBitmap(src, m, paint);
-
- return result;
-
- }
- void draw(Canvas canvas, Paint paint, int color, float size, Path path) {
- PathMeasure mPathMeasure = new PathMeasure();
- float[] mPosition = new float[2];
- float[] mTan = new float[2];
-
- mPathMeasure.setPath(path, false);
-
- paint.setAntiAlias(true);
- paint.setColor(color);
-
- paint.setColorFilter(new PorterDuffColorFilter(color, PorterDuff.Mode.MULTIPLY));
- Bitmap brush;
- // done this way because of a bug in
- // Bitmap.createScaledBitmap(getBrush(),(int) size,(int) size,true);
- brush = createScaledBitmap(getBrush(), (int) size, (int) size, true);
- float len = mPathMeasure.getLength();
- float s2 = size / 2;
- float step = s2 / 8;
- for (float i = 0; i < len; i += step) {
- mPathMeasure.getPosTan(i, mPosition, mTan);
- // canvas.drawCircle(pos[0], pos[1], size, paint);
- canvas.drawBitmap(brush, mPosition[0] - s2, mPosition[1] - s2, paint);
- }
- }
-
- @Override
- public void setType(byte type) {
- mType = type;
- }
- }
-
- void paint(FilterDrawRepresentation.StrokeData sd, Canvas canvas, Matrix toScrMatrix,
- int quality) {
- mDrawingsTypes[sd.mType].paint(sd, canvas, toScrMatrix, quality);
- }
-
- public void drawData(Canvas canvas, Matrix originalRotateToScreen, int quality) {
- Paint paint = new Paint();
- if (quality == FilterEnvironment.QUALITY_FINAL) {
- paint.setAntiAlias(true);
- }
- paint.setStyle(Style.STROKE);
- paint.setColor(Color.RED);
- paint.setStrokeWidth(40);
-
- if (mParameters.getDrawing().isEmpty() && mParameters.getCurrentDrawing() == null) {
- return;
- }
- if (quality == FilterEnvironment.QUALITY_FINAL) {
- for (FilterDrawRepresentation.StrokeData strokeData : mParameters.getDrawing()) {
- paint(strokeData, canvas, originalRotateToScreen, quality);
- }
- return;
- }
-
- if (mOverlayBitmap == null ||
- mOverlayBitmap.getWidth() != canvas.getWidth() ||
- mOverlayBitmap.getHeight() != canvas.getHeight() ||
- mParameters.getDrawing().size() < mCachedStrokes) {
-
- mOverlayBitmap = Bitmap.createBitmap(
- canvas.getWidth(), canvas.getHeight(), Bitmap.Config.ARGB_8888);
- mCachedStrokes = 0;
- }
-
- if (mCachedStrokes < mParameters.getDrawing().size()) {
- fillBuffer(originalRotateToScreen);
- }
- canvas.drawBitmap(mOverlayBitmap, 0, 0, paint);
-
- StrokeData stroke = mParameters.getCurrentDrawing();
- if (stroke != null) {
- paint(stroke, canvas, originalRotateToScreen, quality);
- }
- }
-
- public void fillBuffer(Matrix originalRotateToScreen) {
- Canvas drawCache = new Canvas(mOverlayBitmap);
- Vector<FilterDrawRepresentation.StrokeData> v = mParameters.getDrawing();
- int n = v.size();
-
- for (int i = mCachedStrokes; i < n; i++) {
- paint(v.get(i), drawCache, originalRotateToScreen, FilterEnvironment.QUALITY_PREVIEW);
- }
- mCachedStrokes = n;
- }
-
- public void draw(Canvas canvas, Matrix originalRotateToScreen) {
- for (FilterDrawRepresentation.StrokeData strokeData : mParameters.getDrawing()) {
- paint(strokeData, canvas, originalRotateToScreen, FilterEnvironment.QUALITY_PREVIEW);
- }
- mDrawingsTypes[mCurrentStyle].paint(
- null, canvas, originalRotateToScreen, FilterEnvironment.QUALITY_PREVIEW);
- }
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
-
- Matrix m = getOriginalToScreenMatrix(w, h);
- drawData(new Canvas(bitmap), m, quality);
- return bitmap;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterEdge.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterEdge.java
deleted file mode 100644
index 2d0d7653d..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterEdge.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Bitmap;
-
-import com.android.gallery3d.R;
-
-public class ImageFilterEdge extends SimpleImageFilter {
- private static final String SERIALIZATION_NAME = "EDGE";
- public ImageFilterEdge() {
- mName = "Edge";
- }
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterRepresentation representation = super.getDefaultRepresentation();
- representation.setName("Edge");
- representation.setSerializationName(SERIALIZATION_NAME);
- representation.setFilterClass(ImageFilterEdge.class);
- representation.setTextId(R.string.edge);
- representation.setSupportsPartialRendering(true);
- return representation;
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int w, int h, float p);
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (getParameters() == null) {
- return bitmap;
- }
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- float p = getParameters().getValue() + 101;
- p = (float) p / 100;
- nativeApplyFilter(bitmap, w, h, p);
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterExposure.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterExposure.java
deleted file mode 100644
index 69eab7330..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterExposure.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.R;
-
-import android.graphics.Bitmap;
-
-public class ImageFilterExposure extends SimpleImageFilter {
- private static final String SERIALIZATION_NAME = "EXPOSURE";
- public ImageFilterExposure() {
- mName = "Exposure";
- }
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterBasicRepresentation representation =
- (FilterBasicRepresentation) super.getDefaultRepresentation();
- representation.setName("Exposure");
- representation.setSerializationName(SERIALIZATION_NAME);
- representation.setFilterClass(ImageFilterExposure.class);
- representation.setTextId(R.string.exposure);
- representation.setMinimum(-100);
- representation.setMaximum(100);
- representation.setDefaultValue(0);
- representation.setSupportsPartialRendering(true);
- return representation;
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int w, int h, float bright);
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (getParameters() == null) {
- return bitmap;
- }
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- float value = getParameters().getValue();
- nativeApplyFilter(bitmap, w, h, value);
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterFx.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterFx.java
deleted file mode 100644
index 19bea593b..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterFx.java
+++ /dev/null
@@ -1,111 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import com.android.gallery3d.app.Log;
-
-public class ImageFilterFx extends ImageFilter {
- private static final String LOGTAG = "ImageFilterFx";
- private FilterFxRepresentation mParameters = null;
- private Bitmap mFxBitmap = null;
- private Resources mResources = null;
- private int mFxBitmapId = 0;
-
- public ImageFilterFx() {
- }
-
- @Override
- public void freeResources() {
- if (mFxBitmap != null) mFxBitmap.recycle();
- mFxBitmap = null;
- }
-
- @Override
- public FilterRepresentation getDefaultRepresentation() {
- return null;
- }
-
- public void useRepresentation(FilterRepresentation representation) {
- FilterFxRepresentation parameters = (FilterFxRepresentation) representation;
- mParameters = parameters;
- }
-
- public FilterFxRepresentation getParameters() {
- return mParameters;
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int w, int h,
- Bitmap fxBitmap, int fxw, int fxh,
- int start, int end);
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (getParameters() == null || mResources == null) {
- return bitmap;
- }
-
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
-
- int bitmapResourceId = getParameters().getBitmapResource();
- if (bitmapResourceId == 0) { // null filter fx
- return bitmap;
- }
-
- if (mFxBitmap == null || mFxBitmapId != bitmapResourceId) {
- BitmapFactory.Options o = new BitmapFactory.Options();
- o.inScaled = false;
- mFxBitmapId = bitmapResourceId;
- if (mFxBitmapId != 0) {
- mFxBitmap = BitmapFactory.decodeResource(mResources, mFxBitmapId, o);
- } else {
- Log.w(LOGTAG, "bad resource for filter: " + mName);
- }
- }
-
- if (mFxBitmap == null) {
- return bitmap;
- }
-
- int fxw = mFxBitmap.getWidth();
- int fxh = mFxBitmap.getHeight();
-
- int stride = w * 4;
- int max = stride * h;
- int increment = stride * 256; // 256 lines
- for (int i = 0; i < max; i += increment) {
- int start = i;
- int end = i + increment;
- if (end > max) {
- end = max;
- }
- if (!getEnvironment().needsStop()) {
- nativeApplyFilter(bitmap, w, h, mFxBitmap, fxw, fxh, start, end);
- }
- }
-
- return bitmap;
- }
-
- public void setResources(Resources resources) {
- mResources = resources;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterGrad.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterGrad.java
deleted file mode 100644
index cbdfaa623..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterGrad.java
+++ /dev/null
@@ -1,190 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Bitmap;
-import android.graphics.Color;
-import android.graphics.Matrix;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.pipeline.FilterEnvironment;
-
-import android.graphics.Bitmap;
-import android.graphics.Color;
-import android.graphics.Matrix;
-import android.support.v8.renderscript.Allocation;
-import android.support.v8.renderscript.Element;
-import android.support.v8.renderscript.RenderScript;
-import android.support.v8.renderscript.Script.LaunchOptions;
-import android.support.v8.renderscript.Type;
-import android.util.Log;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.pipeline.FilterEnvironment;
-
-public class ImageFilterGrad extends ImageFilterRS {
- private static final String LOGTAG = "ImageFilterGrad";
- private ScriptC_grad mScript;
- private Bitmap mSourceBitmap;
- private static final int RADIUS_SCALE_FACTOR = 160;
-
- private static final int STRIP_SIZE = 64;
-
- FilterGradRepresentation mParameters = new FilterGradRepresentation();
- private Bitmap mOverlayBitmap;
-
- public ImageFilterGrad() {
- mName = "grad";
- }
-
- @Override
- public FilterRepresentation getDefaultRepresentation() {
- return new FilterGradRepresentation();
- }
-
- @Override
- public void useRepresentation(FilterRepresentation representation) {
- mParameters = (FilterGradRepresentation) representation;
- }
-
- @Override
- protected void resetAllocations() {
-
- }
-
- @Override
- public void resetScripts() {
- if (mScript != null) {
- mScript.destroy();
- mScript = null;
- }
- }
- @Override
- protected void createFilter(android.content.res.Resources res, float scaleFactor,
- int quality) {
- createFilter(res, scaleFactor, quality, getInPixelsAllocation());
- }
-
- @Override
- protected void createFilter(android.content.res.Resources res, float scaleFactor,
- int quality, Allocation in) {
- RenderScript rsCtx = getRenderScriptContext();
-
- Type.Builder tb_float = new Type.Builder(rsCtx, Element.F32_4(rsCtx));
- tb_float.setX(in.getType().getX());
- tb_float.setY(in.getType().getY());
- mScript = new ScriptC_grad(rsCtx, res, R.raw.grad);
- }
-
-
- private Bitmap getSourceBitmap() {
- assert (mSourceBitmap != null);
- return mSourceBitmap;
- }
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (SIMPLE_ICONS && FilterEnvironment.QUALITY_ICON == quality) {
- return bitmap;
- }
-
- mSourceBitmap = bitmap;
- Bitmap ret = super.apply(bitmap, scaleFactor, quality);
- mSourceBitmap = null;
-
- return ret;
- }
-
- @Override
- protected void bindScriptValues() {
- int width = getInPixelsAllocation().getType().getX();
- int height = getInPixelsAllocation().getType().getY();
- mScript.set_inputWidth(width);
- mScript.set_inputHeight(height);
- }
-
- @Override
- protected void runFilter() {
- int[] x1 = mParameters.getXPos1();
- int[] y1 = mParameters.getYPos1();
- int[] x2 = mParameters.getXPos2();
- int[] y2 = mParameters.getYPos2();
-
- int width = getInPixelsAllocation().getType().getX();
- int height = getInPixelsAllocation().getType().getY();
- Matrix m = getOriginalToScreenMatrix(width, height);
- float[] coord = new float[2];
- for (int i = 0; i < x1.length; i++) {
- coord[0] = x1[i];
- coord[1] = y1[i];
- m.mapPoints(coord);
- x1[i] = (int) coord[0];
- y1[i] = (int) coord[1];
- coord[0] = x2[i];
- coord[1] = y2[i];
- m.mapPoints(coord);
- x2[i] = (int) coord[0];
- y2[i] = (int) coord[1];
- }
-
- mScript.set_mask(mParameters.getMask());
- mScript.set_xPos1(x1);
- mScript.set_yPos1(y1);
- mScript.set_xPos2(x2);
- mScript.set_yPos2(y2);
-
- mScript.set_brightness(mParameters.getBrightness());
- mScript.set_contrast(mParameters.getContrast());
- mScript.set_saturation(mParameters.getSaturation());
-
- mScript.invoke_setupGradParams();
- runSelectiveAdjust(
- getInPixelsAllocation(), getOutPixelsAllocation());
-
- }
-
- private void runSelectiveAdjust(Allocation in, Allocation out) {
- int width = in.getType().getX();
- int height = in.getType().getY();
-
- LaunchOptions options = new LaunchOptions();
- int ty;
- options.setX(0, width);
-
- for (ty = 0; ty < height; ty += STRIP_SIZE) {
- int endy = ty + STRIP_SIZE;
- if (endy > height) {
- endy = height;
- }
- options.setY(ty, endy);
- mScript.forEach_selectiveAdjust(in, out, options);
- if (checkStop()) {
- return;
- }
- }
- }
-
- private boolean checkStop() {
- RenderScript rsCtx = getRenderScriptContext();
- rsCtx.finish();
- if (getEnvironment().needsStop()) {
- return true;
- }
- return false;
- }
-}
-
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterHighlights.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterHighlights.java
deleted file mode 100644
index 4c837e0bf..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterHighlights.java
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Bitmap;
-
-import com.android.gallery3d.R;
-
-public class ImageFilterHighlights extends SimpleImageFilter {
- private static final String SERIALIZATION_NAME = "HIGHLIGHTS";
- private static final String LOGTAG = "ImageFilterVignette";
-
- public ImageFilterHighlights() {
- mName = "Highlights";
- }
-
- SplineMath mSpline = new SplineMath(5);
- double[] mHighlightCurve = { 0.0, 0.32, 0.418, 0.476, 0.642 };
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterBasicRepresentation representation =
- (FilterBasicRepresentation) super.getDefaultRepresentation();
- representation.setName("Highlights");
- representation.setSerializationName(SERIALIZATION_NAME);
- representation.setFilterClass(ImageFilterHighlights.class);
- representation.setTextId(R.string.highlight_recovery);
- representation.setMinimum(-100);
- representation.setMaximum(100);
- representation.setDefaultValue(0);
- representation.setSupportsPartialRendering(true);
- return representation;
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int w, int h, float[] luminanceMap);
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (getParameters() == null) {
- return bitmap;
- }
- float p = getParameters().getValue();
- double t = p/100.;
- for (int i = 0; i < 5; i++) {
- double x = i / 4.;
- double y = mHighlightCurve[i] *t+x*(1-t);
- mSpline.setPoint(i, x, y);
- }
-
- float[][] curve = mSpline.calculatetCurve(256);
- float[] luminanceMap = new float[curve.length];
- for (int i = 0; i < luminanceMap.length; i++) {
- luminanceMap[i] = curve[i][1];
- }
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
-
- nativeApplyFilter(bitmap, w, h, luminanceMap);
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterHue.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterHue.java
deleted file mode 100644
index b87c25490..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterHue.java
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.BasicEditor;
-
-import android.graphics.Bitmap;
-
-public class ImageFilterHue extends SimpleImageFilter {
- private static final String SERIALIZATION_NAME = "HUE";
- private ColorSpaceMatrix cmatrix = null;
-
- public ImageFilterHue() {
- mName = "Hue";
- cmatrix = new ColorSpaceMatrix();
- }
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterBasicRepresentation representation =
- (FilterBasicRepresentation) super.getDefaultRepresentation();
- representation.setName("Hue");
- representation.setSerializationName(SERIALIZATION_NAME);
- representation.setFilterClass(ImageFilterHue.class);
- representation.setMinimum(-180);
- representation.setMaximum(180);
- representation.setTextId(R.string.hue);
- representation.setEditorId(BasicEditor.ID);
- representation.setSupportsPartialRendering(true);
- return representation;
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int w, int h, float []matrix);
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (getParameters() == null) {
- return bitmap;
- }
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- float value = getParameters().getValue();
- cmatrix.identity();
- cmatrix.setHue(value);
-
- nativeApplyFilter(bitmap, w, h, cmatrix.getMatrix());
-
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterKMeans.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterKMeans.java
deleted file mode 100644
index 77cdf47b3..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterKMeans.java
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Bitmap;
-import android.text.format.Time;
-
-import com.android.gallery3d.R;
-
-public class ImageFilterKMeans extends SimpleImageFilter {
- private static final String SERIALIZATION_NAME = "KMEANS";
- private int mSeed = 0;
-
- public ImageFilterKMeans() {
- mName = "KMeans";
-
- // set random seed for session
- Time t = new Time();
- t.setToNow();
- mSeed = (int) t.toMillis(false);
- }
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterBasicRepresentation representation = (FilterBasicRepresentation) super.getDefaultRepresentation();
- representation.setName("KMeans");
- representation.setSerializationName(SERIALIZATION_NAME);
- representation.setFilterClass(ImageFilterKMeans.class);
- representation.setMaximum(20);
- representation.setMinimum(2);
- representation.setValue(4);
- representation.setDefaultValue(4);
- representation.setPreviewValue(4);
- representation.setTextId(R.string.kmeans);
- representation.setSupportsPartialRendering(true);
- return representation;
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int width, int height,
- Bitmap large_ds_bm, int lwidth, int lheight, Bitmap small_ds_bm,
- int swidth, int sheight, int p, int seed);
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (getParameters() == null) {
- return bitmap;
- }
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
-
- Bitmap large_bm_ds = bitmap;
- Bitmap small_bm_ds = bitmap;
-
- // find width/height for larger downsampled bitmap
- int lw = w;
- int lh = h;
- while (lw > 256 && lh > 256) {
- lw /= 2;
- lh /= 2;
- }
- if (lw != w) {
- large_bm_ds = Bitmap.createScaledBitmap(bitmap, lw, lh, true);
- }
-
- // find width/height for smaller downsampled bitmap
- int sw = lw;
- int sh = lh;
- while (sw > 64 && sh > 64) {
- sw /= 2;
- sh /= 2;
- }
- if (sw != lw) {
- small_bm_ds = Bitmap.createScaledBitmap(large_bm_ds, sw, sh, true);
- }
-
- if (getParameters() != null) {
- int p = Math.max(getParameters().getValue(), getParameters().getMinimum()) % (getParameters().getMaximum() + 1);
- nativeApplyFilter(bitmap, w, h, large_bm_ds, lw, lh, small_bm_ds, sw, sh, p, mSeed);
- }
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterNegative.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterNegative.java
deleted file mode 100644
index 98497596b..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterNegative.java
+++ /dev/null
@@ -1,39 +0,0 @@
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Bitmap;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.ImageOnlyEditor;
-
-public class ImageFilterNegative extends ImageFilter {
- private static final String SERIALIZATION_NAME = "NEGATIVE";
- public ImageFilterNegative() {
- mName = "Negative";
- }
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterRepresentation representation = new FilterDirectRepresentation("Negative");
- representation.setSerializationName(SERIALIZATION_NAME);
- representation.setFilterClass(ImageFilterNegative.class);
- representation.setTextId(R.string.negative);
- representation.setShowParameterValue(false);
- representation.setEditorId(ImageOnlyEditor.ID);
- representation.setSupportsPartialRendering(true);
- return representation;
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int w, int h);
-
- @Override
- public void useRepresentation(FilterRepresentation representation) {
-
- }
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- nativeApplyFilter(bitmap, w, h);
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterParametricBorder.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterParametricBorder.java
deleted file mode 100644
index 25e5d1476..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterParametricBorder.java
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.graphics.Path;
-import android.graphics.RectF;
-
-public class ImageFilterParametricBorder extends ImageFilter {
- private FilterColorBorderRepresentation mParameters = null;
-
- public ImageFilterParametricBorder() {
- mName = "Border";
- }
-
- public void useRepresentation(FilterRepresentation representation) {
- FilterColorBorderRepresentation parameters = (FilterColorBorderRepresentation) representation;
- mParameters = parameters;
- }
-
- public FilterColorBorderRepresentation getParameters() {
- return mParameters;
- }
-
- private void applyHelper(Canvas canvas, int w, int h) {
- if (getParameters() == null) {
- return;
- }
- Path border = new Path();
- border.moveTo(0, 0);
- float bs = getParameters().getBorderSize() / 100.0f * w;
- float r = getParameters().getBorderRadius() / 100.0f * w;
- border.lineTo(0, h);
- border.lineTo(w, h);
- border.lineTo(w, 0);
- border.lineTo(0, 0);
- border.addRoundRect(new RectF(bs, bs, w - bs, h - bs),
- r, r, Path.Direction.CW);
-
- Paint paint = new Paint();
- paint.setAntiAlias(true);
- paint.setColor(getParameters().getColor());
- canvas.drawPath(border, paint);
- }
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- Canvas canvas = new Canvas(bitmap);
- applyHelper(canvas, bitmap.getWidth(), bitmap.getHeight());
- return bitmap;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterRS.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterRS.java
deleted file mode 100644
index 5695ef53e..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterRS.java
+++ /dev/null
@@ -1,260 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.support.v8.renderscript.*;
-import android.util.Log;
-import android.content.res.Resources;
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.pipeline.PipelineInterface;
-
-public abstract class ImageFilterRS extends ImageFilter {
- private static final String LOGTAG = "ImageFilterRS";
- private boolean DEBUG = false;
- private int mLastInputWidth = 0;
- private int mLastInputHeight = 0;
- private long mLastTimeCalled;
-
- public static boolean PERF_LOGGING = false;
-
- private static ScriptC_grey mGreyConvert = null;
- private static RenderScript mRScache = null;
-
- private volatile boolean mResourcesLoaded = false;
-
- protected abstract void createFilter(android.content.res.Resources res,
- float scaleFactor, int quality);
-
- protected void createFilter(android.content.res.Resources res,
- float scaleFactor, int quality, Allocation in) {}
- protected void bindScriptValues(Allocation in) {}
-
- protected abstract void runFilter();
-
- protected void update(Bitmap bitmap) {
- getOutPixelsAllocation().copyTo(bitmap);
- }
-
- protected RenderScript getRenderScriptContext() {
- PipelineInterface pipeline = getEnvironment().getPipeline();
- return pipeline.getRSContext();
- }
-
- protected Allocation getInPixelsAllocation() {
- PipelineInterface pipeline = getEnvironment().getPipeline();
- return pipeline.getInPixelsAllocation();
- }
-
- protected Allocation getOutPixelsAllocation() {
- PipelineInterface pipeline = getEnvironment().getPipeline();
- return pipeline.getOutPixelsAllocation();
- }
-
- @Override
- public void apply(Allocation in, Allocation out) {
- long startOverAll = System.nanoTime();
- if (PERF_LOGGING) {
- long delay = (startOverAll - mLastTimeCalled) / 1000;
- String msg = String.format("%s; image size %dx%d; ", getName(),
- in.getType().getX(), in.getType().getY());
- msg += String.format("called after %.2f ms (%.2f FPS); ",
- delay / 1000.f, 1000000.f / delay);
- Log.i(LOGTAG, msg);
- }
- mLastTimeCalled = startOverAll;
- long startFilter = 0;
- long endFilter = 0;
- if (!mResourcesLoaded) {
- PipelineInterface pipeline = getEnvironment().getPipeline();
- createFilter(pipeline.getResources(), getEnvironment().getScaleFactor(),
- getEnvironment().getQuality(), in);
- mResourcesLoaded = true;
- }
- startFilter = System.nanoTime();
- bindScriptValues(in);
- run(in, out);
- if (PERF_LOGGING) {
- getRenderScriptContext().finish();
- endFilter = System.nanoTime();
- long endOverAll = System.nanoTime();
- String msg = String.format("%s; image size %dx%d; ", getName(),
- in.getType().getX(), in.getType().getY());
- long timeOverAll = (endOverAll - startOverAll) / 1000;
- long timeFilter = (endFilter - startFilter) / 1000;
- msg += String.format("over all %.2f ms (%.2f FPS); ",
- timeOverAll / 1000.f, 1000000.f / timeOverAll);
- msg += String.format("run filter %.2f ms (%.2f FPS)",
- timeFilter / 1000.f, 1000000.f / timeFilter);
- Log.i(LOGTAG, msg);
- }
- }
-
- protected void run(Allocation in, Allocation out) {}
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (bitmap == null || bitmap.getWidth() == 0 || bitmap.getHeight() == 0) {
- return bitmap;
- }
- try {
- PipelineInterface pipeline = getEnvironment().getPipeline();
- if (DEBUG) {
- Log.v(LOGTAG, "apply filter " + getName() + " in pipeline " + pipeline.getName());
- }
- Resources rsc = pipeline.getResources();
- boolean sizeChanged = false;
- if (getInPixelsAllocation() != null
- && ((getInPixelsAllocation().getType().getX() != mLastInputWidth)
- || (getInPixelsAllocation().getType().getY() != mLastInputHeight))) {
- sizeChanged = true;
- }
- if (pipeline.prepareRenderscriptAllocations(bitmap)
- || !isResourcesLoaded() || sizeChanged) {
- freeResources();
- createFilter(rsc, scaleFactor, quality);
- setResourcesLoaded(true);
- mLastInputWidth = getInPixelsAllocation().getType().getX();
- mLastInputHeight = getInPixelsAllocation().getType().getY();
- }
- bindScriptValues();
- runFilter();
- update(bitmap);
- if (DEBUG) {
- Log.v(LOGTAG, "DONE apply filter " + getName() + " in pipeline " + pipeline.getName());
- }
- } catch (android.renderscript.RSIllegalArgumentException e) {
- Log.e(LOGTAG, "Illegal argument? " + e);
- } catch (android.renderscript.RSRuntimeException e) {
- Log.e(LOGTAG, "RS runtime exception ? " + e);
- } catch (java.lang.OutOfMemoryError e) {
- // Many of the renderscript filters allocated large (>16Mb resources) in order to apply.
- System.gc();
- displayLowMemoryToast();
- Log.e(LOGTAG, "not enough memory for filter " + getName(), e);
- }
- return bitmap;
- }
-
- protected static Allocation convertBitmap(RenderScript RS, Bitmap bitmap) {
- return Allocation.createFromBitmap(RS, bitmap,
- Allocation.MipmapControl.MIPMAP_NONE,
- Allocation.USAGE_SCRIPT | Allocation.USAGE_GRAPHICS_TEXTURE);
- }
-
- private static Allocation convertRGBAtoA(RenderScript RS, Bitmap bitmap) {
- if (RS != mRScache || mGreyConvert == null) {
- mGreyConvert = new ScriptC_grey(RS, RS.getApplicationContext().getResources(),
- R.raw.grey);
- mRScache = RS;
- }
-
- Type.Builder tb_a8 = new Type.Builder(RS, Element.A_8(RS));
-
- Allocation bitmapTemp = convertBitmap(RS, bitmap);
- if (bitmapTemp.getType().getElement().isCompatible(Element.A_8(RS))) {
- return bitmapTemp;
- }
-
- tb_a8.setX(bitmapTemp.getType().getX());
- tb_a8.setY(bitmapTemp.getType().getY());
- Allocation bitmapAlloc = Allocation.createTyped(RS, tb_a8.create(),
- Allocation.MipmapControl.MIPMAP_NONE,
- Allocation.USAGE_SCRIPT | Allocation.USAGE_GRAPHICS_TEXTURE);
- mGreyConvert.forEach_RGBAtoA(bitmapTemp, bitmapAlloc);
- bitmapTemp.destroy();
- return bitmapAlloc;
- }
-
- public Allocation loadScaledResourceAlpha(int resource, int inSampleSize) {
- Resources res = getEnvironment().getPipeline().getResources();
- final BitmapFactory.Options options = new BitmapFactory.Options();
- options.inPreferredConfig = Bitmap.Config.ALPHA_8;
- options.inSampleSize = inSampleSize;
- Bitmap bitmap = BitmapFactory.decodeResource(
- res,
- resource, options);
- Allocation ret = convertRGBAtoA(getRenderScriptContext(), bitmap);
- bitmap.recycle();
- return ret;
- }
-
- public Allocation loadScaledResourceAlpha(int resource, int w, int h, int inSampleSize) {
- Resources res = getEnvironment().getPipeline().getResources();
- final BitmapFactory.Options options = new BitmapFactory.Options();
- options.inPreferredConfig = Bitmap.Config.ALPHA_8;
- options.inSampleSize = inSampleSize;
- Bitmap bitmap = BitmapFactory.decodeResource(
- res,
- resource, options);
- Bitmap resizeBitmap = Bitmap.createScaledBitmap(bitmap, w, h, true);
- Allocation ret = convertRGBAtoA(getRenderScriptContext(), resizeBitmap);
- resizeBitmap.recycle();
- bitmap.recycle();
- return ret;
- }
-
- public Allocation loadResourceAlpha(int resource) {
- return loadScaledResourceAlpha(resource, 1);
- }
-
- public Allocation loadResource(int resource) {
- Resources res = getEnvironment().getPipeline().getResources();
- final BitmapFactory.Options options = new BitmapFactory.Options();
- options.inPreferredConfig = Bitmap.Config.ARGB_8888;
- Bitmap bitmap = BitmapFactory.decodeResource(
- res,
- resource, options);
- Allocation ret = convertBitmap(getRenderScriptContext(), bitmap);
- bitmap.recycle();
- return ret;
- }
-
- private boolean isResourcesLoaded() {
- return mResourcesLoaded;
- }
-
- private void setResourcesLoaded(boolean resourcesLoaded) {
- mResourcesLoaded = resourcesLoaded;
- }
-
- /**
- * Bitmaps and RS Allocations should be cleared here
- */
- abstract protected void resetAllocations();
-
- /**
- * RS Script objects (and all other RS objects) should be cleared here
- */
- public abstract void resetScripts();
-
- /**
- * Scripts values should be bound here
- */
- abstract protected void bindScriptValues();
-
- public void freeResources() {
- if (!isResourcesLoaded()) {
- return;
- }
- resetAllocations();
- mLastInputWidth = 0;
- mLastInputHeight = 0;
- setResourcesLoaded(false);
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterRedEye.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterRedEye.java
deleted file mode 100644
index 511f9e90f..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterRedEye.java
+++ /dev/null
@@ -1,79 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Bitmap;
-import android.graphics.Matrix;
-import android.graphics.RectF;
-
-import java.util.Vector;
-
-public class ImageFilterRedEye extends ImageFilter {
- private static final String LOGTAG = "ImageFilterRedEye";
- FilterRedEyeRepresentation mParameters = new FilterRedEyeRepresentation();
-
- public ImageFilterRedEye() {
- mName = "Red Eye";
- }
-
- @Override
- public FilterRepresentation getDefaultRepresentation() {
- return new FilterRedEyeRepresentation();
- }
-
- public boolean isNil() {
- return mParameters.isNil();
- }
-
- public Vector<FilterPoint> getCandidates() {
- return mParameters.getCandidates();
- }
-
- public void clear() {
- mParameters.clearCandidates();
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int w, int h, short[] matrix);
-
- @Override
- public void useRepresentation(FilterRepresentation representation) {
- FilterRedEyeRepresentation parameters = (FilterRedEyeRepresentation) representation;
- mParameters = parameters;
- }
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- short[] rect = new short[4];
-
- int size = mParameters.getNumberOfCandidates();
- Matrix originalToScreen = getOriginalToScreenMatrix(w, h);
- for (int i = 0; i < size; i++) {
- RectF r = new RectF(((RedEyeCandidate) (mParameters.getCandidate(i))).mRect);
- originalToScreen.mapRect(r);
- if (r.intersect(0, 0, w, h)) {
- rect[0] = (short) r.left;
- rect[1] = (short) r.top;
- rect[2] = (short) r.width();
- rect[3] = (short) r.height();
- nativeApplyFilter(bitmap, w, h, rect);
- }
- }
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterSaturated.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterSaturated.java
deleted file mode 100644
index c3124ff77..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterSaturated.java
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.R;
-
-import android.graphics.Bitmap;
-
-public class ImageFilterSaturated extends SimpleImageFilter {
- private static final String SERIALIZATION_NAME = "SATURATED";
- public ImageFilterSaturated() {
- mName = "Saturated";
- }
-
- @Override
- public FilterRepresentation getDefaultRepresentation() {
- FilterBasicRepresentation representation =
- (FilterBasicRepresentation) super.getDefaultRepresentation();
- representation.setName("Saturated");
- representation.setSerializationName(SERIALIZATION_NAME);
- representation.setFilterClass(ImageFilterSaturated.class);
- representation.setTextId(R.string.saturation);
- representation.setMinimum(-100);
- representation.setMaximum(100);
- representation.setDefaultValue(0);
- representation.setSupportsPartialRendering(true);
- return representation;
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int w, int h, float saturation);
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (getParameters() == null) {
- return bitmap;
- }
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- int p = getParameters().getValue();
- float value = 1 + p / 100.0f;
- nativeApplyFilter(bitmap, w, h, value);
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterShadows.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterShadows.java
deleted file mode 100644
index bd119bbc9..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterShadows.java
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.R;
-
-import android.graphics.Bitmap;
-
-public class ImageFilterShadows extends SimpleImageFilter {
- private static final String SERIALIZATION_NAME = "SHADOWS";
- public ImageFilterShadows() {
- mName = "Shadows";
-
- }
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterBasicRepresentation representation =
- (FilterBasicRepresentation) super.getDefaultRepresentation();
- representation.setName("Shadows");
- representation.setSerializationName(SERIALIZATION_NAME);
- representation.setFilterClass(ImageFilterShadows.class);
- representation.setTextId(R.string.shadow_recovery);
- representation.setMinimum(-100);
- representation.setMaximum(100);
- representation.setDefaultValue(0);
- representation.setSupportsPartialRendering(true);
- return representation;
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int w, int h, float factor);
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (getParameters() == null) {
- return bitmap;
- }
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- float p = getParameters().getValue();
-
- nativeApplyFilter(bitmap, w, h, p);
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterSharpen.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterSharpen.java
deleted file mode 100644
index 3bd794464..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterSharpen.java
+++ /dev/null
@@ -1,107 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.R;
-
-public class ImageFilterSharpen extends ImageFilterRS {
- private static final String SERIALIZATION_NAME = "SHARPEN";
- private static final String LOGTAG = "ImageFilterSharpen";
- private ScriptC_convolve3x3 mScript;
-
- private FilterBasicRepresentation mParameters;
-
- public ImageFilterSharpen() {
- mName = "Sharpen";
- }
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterRepresentation representation = new FilterBasicRepresentation("Sharpen", 0, 0, 100);
- representation.setSerializationName(SERIALIZATION_NAME);
- representation.setShowParameterValue(true);
- representation.setFilterClass(ImageFilterSharpen.class);
- representation.setTextId(R.string.sharpness);
- representation.setOverlayId(R.drawable.filtershow_button_colors_sharpen);
- representation.setEditorId(R.id.imageShow);
- representation.setSupportsPartialRendering(true);
- return representation;
- }
-
- public void useRepresentation(FilterRepresentation representation) {
- FilterBasicRepresentation parameters = (FilterBasicRepresentation) representation;
- mParameters = parameters;
- }
-
- @Override
- protected void resetAllocations() {
- // nothing to do
- }
-
- @Override
- public void resetScripts() {
- if (mScript != null) {
- mScript.destroy();
- mScript = null;
- }
- }
-
- @Override
- protected void createFilter(android.content.res.Resources res, float scaleFactor,
- int quality) {
- if (mScript == null) {
- mScript = new ScriptC_convolve3x3(getRenderScriptContext(), res, R.raw.convolve3x3);
- }
- }
-
- private void computeKernel() {
- float scaleFactor = getEnvironment().getScaleFactor();
- float p1 = mParameters.getValue() * scaleFactor;
- float value = p1 / 100.0f;
- float f[] = new float[9];
- float p = value;
- f[0] = -p;
- f[1] = -p;
- f[2] = -p;
- f[3] = -p;
- f[4] = 8 * p + 1;
- f[5] = -p;
- f[6] = -p;
- f[7] = -p;
- f[8] = -p;
- mScript.set_gCoeffs(f);
- }
-
- @Override
- protected void bindScriptValues() {
- int w = getInPixelsAllocation().getType().getX();
- int h = getInPixelsAllocation().getType().getY();
- mScript.set_gWidth(w);
- mScript.set_gHeight(h);
- }
-
- @Override
- protected void runFilter() {
- if (mParameters == null) {
- return;
- }
- computeKernel();
- mScript.set_gIn(getInPixelsAllocation());
- mScript.bind_gPixels(getInPixelsAllocation());
- mScript.forEach_root(getInPixelsAllocation(), getOutPixelsAllocation());
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterTinyPlanet.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterTinyPlanet.java
deleted file mode 100644
index 77250bd7a..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterTinyPlanet.java
+++ /dev/null
@@ -1,158 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.RectF;
-
-import com.adobe.xmp.XMPException;
-import com.adobe.xmp.XMPMeta;
-import com.android.gallery3d.app.Log;
-import com.android.gallery3d.filtershow.cache.ImageLoader;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-
-/**
- * An image filter which creates a tiny planet projection.
- */
-public class ImageFilterTinyPlanet extends SimpleImageFilter {
-
-
- private static final String LOGTAG = ImageFilterTinyPlanet.class.getSimpleName();
- public static final String GOOGLE_PANO_NAMESPACE = "http://ns.google.com/photos/1.0/panorama/";
- FilterTinyPlanetRepresentation mParameters = new FilterTinyPlanetRepresentation();
-
- public static final String CROPPED_AREA_IMAGE_WIDTH_PIXELS =
- "CroppedAreaImageWidthPixels";
- public static final String CROPPED_AREA_IMAGE_HEIGHT_PIXELS =
- "CroppedAreaImageHeightPixels";
- public static final String CROPPED_AREA_FULL_PANO_WIDTH_PIXELS =
- "FullPanoWidthPixels";
- public static final String CROPPED_AREA_FULL_PANO_HEIGHT_PIXELS =
- "FullPanoHeightPixels";
- public static final String CROPPED_AREA_LEFT =
- "CroppedAreaLeftPixels";
- public static final String CROPPED_AREA_TOP =
- "CroppedAreaTopPixels";
-
- public ImageFilterTinyPlanet() {
- mName = "TinyPlanet";
- }
-
- @Override
- public void useRepresentation(FilterRepresentation representation) {
- FilterTinyPlanetRepresentation parameters = (FilterTinyPlanetRepresentation) representation;
- mParameters = parameters;
- }
-
- @Override
- public FilterRepresentation getDefaultRepresentation() {
- return new FilterTinyPlanetRepresentation();
- }
-
-
- native protected void nativeApplyFilter(
- Bitmap bitmapIn, int width, int height, Bitmap bitmapOut, int outSize, float scale,
- float angle);
-
-
- @Override
- public Bitmap apply(Bitmap bitmapIn, float scaleFactor, int quality) {
- int w = bitmapIn.getWidth();
- int h = bitmapIn.getHeight();
- int outputSize = (int) (w / 2f);
- ImagePreset preset = getEnvironment().getImagePreset();
- Bitmap mBitmapOut = null;
- if (preset != null) {
- XMPMeta xmp = ImageLoader.getXmpObject(MasterImage.getImage().getActivity());
- // Do nothing, just use bitmapIn as is if we don't have XMP.
- if(xmp != null) {
- bitmapIn = applyXmp(bitmapIn, xmp, w);
- }
- }
- if (mBitmapOut != null) {
- if (outputSize != mBitmapOut.getHeight()) {
- mBitmapOut = null;
- }
- }
- while (mBitmapOut == null) {
- try {
- mBitmapOut = getEnvironment().getBitmap(outputSize, outputSize);
- } catch (java.lang.OutOfMemoryError e) {
- System.gc();
- outputSize /= 2;
- Log.v(LOGTAG, "No memory to create Full Tiny Planet create half");
- }
- }
- nativeApplyFilter(bitmapIn, bitmapIn.getWidth(), bitmapIn.getHeight(), mBitmapOut,
- outputSize, mParameters.getZoom() / 100f, mParameters.getAngle());
-
- return mBitmapOut;
- }
-
- private Bitmap applyXmp(Bitmap bitmapIn, XMPMeta xmp, int intermediateWidth) {
- try {
- int croppedAreaWidth =
- getInt(xmp, CROPPED_AREA_IMAGE_WIDTH_PIXELS);
- int croppedAreaHeight =
- getInt(xmp, CROPPED_AREA_IMAGE_HEIGHT_PIXELS);
- int fullPanoWidth =
- getInt(xmp, CROPPED_AREA_FULL_PANO_WIDTH_PIXELS);
- int fullPanoHeight =
- getInt(xmp, CROPPED_AREA_FULL_PANO_HEIGHT_PIXELS);
- int left = getInt(xmp, CROPPED_AREA_LEFT);
- int top = getInt(xmp, CROPPED_AREA_TOP);
-
- if (fullPanoWidth == 0 || fullPanoHeight == 0) {
- return bitmapIn;
- }
- // Make sure the intermediate image has the similar size to the
- // input.
- Bitmap paddedBitmap = null;
- float scale = intermediateWidth / (float) fullPanoWidth;
- while (paddedBitmap == null) {
- try {
- paddedBitmap = Bitmap.createBitmap(
- (int) (fullPanoWidth * scale), (int) (fullPanoHeight * scale),
- Bitmap.Config.ARGB_8888);
- } catch (java.lang.OutOfMemoryError e) {
- System.gc();
- scale /= 2;
- }
- }
- Canvas paddedCanvas = new Canvas(paddedBitmap);
-
- int right = left + croppedAreaWidth;
- int bottom = top + croppedAreaHeight;
- RectF destRect = new RectF(left * scale, top * scale, right * scale, bottom * scale);
- paddedCanvas.drawBitmap(bitmapIn, null, destRect, null);
- bitmapIn = paddedBitmap;
- } catch (XMPException ex) {
- // Do nothing, just use bitmapIn as is.
- }
- return bitmapIn;
- }
-
- private static int getInt(XMPMeta xmp, String key) throws XMPException {
- if (xmp.doesPropertyExist(GOOGLE_PANO_NAMESPACE, key)) {
- return xmp.getPropertyInteger(GOOGLE_PANO_NAMESPACE, key);
- } else {
- return 0;
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterVibrance.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterVibrance.java
deleted file mode 100644
index 86be9a155..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterVibrance.java
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.R;
-
-import android.graphics.Bitmap;
-
-public class ImageFilterVibrance extends SimpleImageFilter {
- private static final String SERIALIZATION_NAME = "VIBRANCE";
- public ImageFilterVibrance() {
- mName = "Vibrance";
- }
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterBasicRepresentation representation =
- (FilterBasicRepresentation) super.getDefaultRepresentation();
- representation.setName("Vibrance");
- representation.setSerializationName(SERIALIZATION_NAME);
- representation.setFilterClass(ImageFilterVibrance.class);
- representation.setTextId(R.string.vibrance);
- representation.setMinimum(-100);
- representation.setMaximum(100);
- representation.setDefaultValue(0);
- representation.setSupportsPartialRendering(true);
- return representation;
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int w, int h, float bright);
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (getParameters() == null) {
- return bitmap;
- }
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- float value = getParameters().getValue();
- nativeApplyFilter(bitmap, w, h, value);
-
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterVignette.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterVignette.java
deleted file mode 100644
index 7e0a452bf..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterVignette.java
+++ /dev/null
@@ -1,98 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Matrix;
-import android.graphics.Rect;
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.pipeline.FilterEnvironment;
-
-public class ImageFilterVignette extends SimpleImageFilter {
- private static final String LOGTAG = "ImageFilterVignette";
- private Bitmap mOverlayBitmap;
-
- public ImageFilterVignette() {
- mName = "Vignette";
- }
-
- @Override
- public FilterRepresentation getDefaultRepresentation() {
- FilterVignetteRepresentation representation = new FilterVignetteRepresentation();
- return representation;
- }
-
- native protected void nativeApplyFilter(
- Bitmap bitmap, int w, int h, int cx, int cy, float radx, float rady, float strength);
-
- private float calcRadius(float cx, float cy, int w, int h) {
- float d = cx;
- if (d < (w - cx)) {
- d = w - cx;
- }
- if (d < cy) {
- d = cy;
- }
- if (d < (h - cy)) {
- d = h - cy;
- }
- return d * d * 2.0f;
- }
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- if (SIMPLE_ICONS && FilterEnvironment.QUALITY_ICON == quality) {
- if (mOverlayBitmap == null) {
- Resources res = getEnvironment().getPipeline().getResources();
- mOverlayBitmap = IconUtilities.getFXBitmap(res,
- R.drawable.filtershow_icon_vignette);
- }
- Canvas c = new Canvas(bitmap);
- int dim = Math.max(bitmap.getWidth(), bitmap.getHeight());
- Rect r = new Rect(0, 0, dim, dim);
- c.drawBitmap(mOverlayBitmap, null, r, null);
- return bitmap;
- }
- FilterVignetteRepresentation rep = (FilterVignetteRepresentation) getParameters();
- if (rep == null) {
- return bitmap;
- }
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- float value = rep.getValue() / 100.0f;
- float cx = w / 2;
- float cy = h / 2;
- float r = calcRadius(cx, cy, w, h);
- float rx = r;
- float ry = r;
- if (rep.isCenterSet()) {
- Matrix m = getOriginalToScreenMatrix(w, h);
- cx = rep.getCenterX();
- cy = rep.getCenterY();
- float[] center = new float[] { cx, cy };
- m.mapPoints(center);
- cx = center[0];
- cy = center[1];
- rx = m.mapRadius(rep.getRadiusX());
- ry = m.mapRadius(rep.getRadiusY());
- }
- nativeApplyFilter(bitmap, w, h, (int) cx, (int) cy, rx, ry, value);
- return bitmap;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/ImageFilterWBalance.java b/src/com/android/gallery3d/filtershow/filters/ImageFilterWBalance.java
deleted file mode 100644
index 6bb88ec21..000000000
--- a/src/com/android/gallery3d/filtershow/filters/ImageFilterWBalance.java
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.ImageOnlyEditor;
-
-import android.graphics.Bitmap;
-
-public class ImageFilterWBalance extends ImageFilter {
- private static final String SERIALIZATION_NAME = "WBALANCE";
- private static final String TAG = "ImageFilterWBalance";
-
- public ImageFilterWBalance() {
- mName = "WBalance";
- }
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterRepresentation representation = new FilterDirectRepresentation("WBalance");
- representation.setSerializationName(SERIALIZATION_NAME);
- representation.setFilterClass(ImageFilterWBalance.class);
- representation.setFilterType(FilterRepresentation.TYPE_WBALANCE);
- representation.setTextId(R.string.wbalance);
- representation.setShowParameterValue(false);
- representation.setEditorId(ImageOnlyEditor.ID);
- representation.setSupportsPartialRendering(true);
- return representation;
- }
-
- @Override
- public void useRepresentation(FilterRepresentation representation) {
-
- }
-
- native protected void nativeApplyFilter(Bitmap bitmap, int w, int h, int locX, int locY);
-
- @Override
- public Bitmap apply(Bitmap bitmap, float scaleFactor, int quality) {
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- nativeApplyFilter(bitmap, w, h, -1, -1);
- return bitmap;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/RedEyeCandidate.java b/src/com/android/gallery3d/filtershow/filters/RedEyeCandidate.java
deleted file mode 100644
index a40d4fa3b..000000000
--- a/src/com/android/gallery3d/filtershow/filters/RedEyeCandidate.java
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-import android.graphics.RectF;
-
-public class RedEyeCandidate implements FilterPoint {
- RectF mRect = new RectF();
- RectF mBounds = new RectF();
-
- public RedEyeCandidate(RedEyeCandidate candidate) {
- mRect.set(candidate.mRect);
- mBounds.set(candidate.mBounds);
- }
-
- public RedEyeCandidate(RectF rect, RectF bounds) {
- mRect.set(rect);
- mBounds.set(bounds);
- }
-
- public boolean equals(RedEyeCandidate candidate) {
- if (candidate.mRect.equals(mRect)
- && candidate.mBounds.equals(mBounds)) {
- return true;
- }
- return false;
- }
-
- public boolean intersect(RectF rect) {
- return mRect.intersect(rect);
- }
-
- public RectF getRect() {
- return mRect;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/SimpleImageFilter.java b/src/com/android/gallery3d/filtershow/filters/SimpleImageFilter.java
deleted file mode 100644
index c891d20f3..000000000
--- a/src/com/android/gallery3d/filtershow/filters/SimpleImageFilter.java
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.filters;
-
-public class SimpleImageFilter extends ImageFilter {
-
- private FilterBasicRepresentation mParameters;
-
- public FilterRepresentation getDefaultRepresentation() {
- FilterRepresentation representation = new FilterBasicRepresentation("Default", 0, 50, 100);
- representation.setShowParameterValue(true);
- return representation;
- }
-
- public void useRepresentation(FilterRepresentation representation) {
- FilterBasicRepresentation parameters = (FilterBasicRepresentation) representation;
- mParameters = parameters;
- }
-
- public FilterBasicRepresentation getParameters() {
- return mParameters;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/SplineMath.java b/src/com/android/gallery3d/filtershow/filters/SplineMath.java
deleted file mode 100644
index 5b12d0a61..000000000
--- a/src/com/android/gallery3d/filtershow/filters/SplineMath.java
+++ /dev/null
@@ -1,166 +0,0 @@
-package com.android.gallery3d.filtershow.filters;
-
-
-public class SplineMath {
- double[][] mPoints = new double[6][2];
- double[] mDerivatives;
- SplineMath(int n) {
- mPoints = new double[n][2];
- }
-
- public void setPoint(int index, double x, double y) {
- mPoints[index][0] = x;
- mPoints[index][1] = y;
- mDerivatives = null;
- }
-
- public float[][] calculatetCurve(int n) {
- float[][] curve = new float[n][2];
- double[][] points = new double[mPoints.length][2];
- for (int i = 0; i < mPoints.length; i++) {
-
- points[i][0] = mPoints[i][0];
- points[i][1] = mPoints[i][1];
-
- }
- double[] derivatives = solveSystem(points);
- float start = (float) points[0][0];
- float end = (float) (points[points.length - 1][0]);
-
- curve[0][0] = (float) (points[0][0]);
- curve[0][1] = (float) (points[0][1]);
- int last = curve.length - 1;
- curve[last][0] = (float) (points[points.length - 1][0]);
- curve[last][1] = (float) (points[points.length - 1][1]);
-
- for (int i = 0; i < curve.length; i++) {
-
- double[] cur = null;
- double[] next = null;
- double x = start + i * (end - start) / (curve.length - 1);
- int pivot = 0;
- for (int j = 0; j < points.length - 1; j++) {
- if (x >= points[j][0] && x <= points[j + 1][0]) {
- pivot = j;
- }
- }
- cur = points[pivot];
- next = points[pivot + 1];
- if (x <= next[0]) {
- double x1 = cur[0];
- double x2 = next[0];
- double y1 = cur[1];
- double y2 = next[1];
-
- // Use the second derivatives to apply the cubic spline
- // equation:
- double delta = (x2 - x1);
- double delta2 = delta * delta;
- double b = (x - x1) / delta;
- double a = 1 - b;
- double ta = a * y1;
- double tb = b * y2;
- double tc = (a * a * a - a) * derivatives[pivot];
- double td = (b * b * b - b) * derivatives[pivot + 1];
- double y = ta + tb + (delta2 / 6) * (tc + td);
-
- curve[i][0] = (float) (x);
- curve[i][1] = (float) (y);
- } else {
- curve[i][0] = (float) (next[0]);
- curve[i][1] = (float) (next[1]);
- }
- }
- return curve;
- }
-
- public double getValue(double x) {
- double[] cur = null;
- double[] next = null;
- if (mDerivatives == null)
- mDerivatives = solveSystem(mPoints);
- int pivot = 0;
- for (int j = 0; j < mPoints.length - 1; j++) {
- pivot = j;
- if (x <= mPoints[j][0]) {
- break;
- }
- }
- cur = mPoints[pivot];
- next = mPoints[pivot + 1];
- double x1 = cur[0];
- double x2 = next[0];
- double y1 = cur[1];
- double y2 = next[1];
-
- // Use the second derivatives to apply the cubic spline
- // equation:
- double delta = (x2 - x1);
- double delta2 = delta * delta;
- double b = (x - x1) / delta;
- double a = 1 - b;
- double ta = a * y1;
- double tb = b * y2;
- double tc = (a * a * a - a) * mDerivatives[pivot];
- double td = (b * b * b - b) * mDerivatives[pivot + 1];
- double y = ta + tb + (delta2 / 6) * (tc + td);
-
- return y;
-
- }
-
- double[] solveSystem(double[][] points) {
- int n = points.length;
- double[][] system = new double[n][3];
- double[] result = new double[n]; // d
- double[] solution = new double[n]; // returned coefficients
- system[0][1] = 1;
- system[n - 1][1] = 1;
- double d6 = 1.0 / 6.0;
- double d3 = 1.0 / 3.0;
-
- // let's create a tridiagonal matrix representing the
- // system, and apply the TDMA algorithm to solve it
- // (see http://en.wikipedia.org/wiki/Tridiagonal_matrix_algorithm)
- for (int i = 1; i < n - 1; i++) {
- double deltaPrevX = points[i][0] - points[i - 1][0];
- double deltaX = points[i + 1][0] - points[i - 1][0];
- double deltaNextX = points[i + 1][0] - points[i][0];
- double deltaNextY = points[i + 1][1] - points[i][1];
- double deltaPrevY = points[i][1] - points[i - 1][1];
- system[i][0] = d6 * deltaPrevX; // a_i
- system[i][1] = d3 * deltaX; // b_i
- system[i][2] = d6 * deltaNextX; // c_i
- result[i] = (deltaNextY / deltaNextX) - (deltaPrevY / deltaPrevX); // d_i
- }
-
- // Forward sweep
- for (int i = 1; i < n; i++) {
- // m = a_i/b_i-1
- double m = system[i][0] / system[i - 1][1];
- // b_i = b_i - m(c_i-1)
- system[i][1] = system[i][1] - m * system[i - 1][2];
- // d_i = d_i - m(d_i-1)
- result[i] = result[i] - m * result[i - 1];
- }
-
- // Back substitution
- solution[n - 1] = result[n - 1] / system[n - 1][1];
- for (int i = n - 2; i >= 0; --i) {
- solution[i] = (result[i] - system[i][2] * solution[i + 1]) / system[i][1];
- }
- return solution;
- }
-
- public static void main(String[] args) {
- SplineMath s = new SplineMath(10);
- for (int i = 0; i < 10; i++) {
- s.setPoint(i, i, i);
- }
- float[][] curve = s.calculatetCurve(40);
-
- for (int j = 0; j < curve.length; j++) {
- System.out.println(curve[j][0] + "," + curve[j][1]);
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/convolve3x3.rs b/src/com/android/gallery3d/filtershow/filters/convolve3x3.rs
deleted file mode 100644
index 2acffab06..000000000
--- a/src/com/android/gallery3d/filtershow/filters/convolve3x3.rs
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma version(1)
-#pragma rs java_package_name(com.android.gallery3d.filtershow.filters)
-#pragma rs_fp_relaxed
-
-int32_t gWidth;
-int32_t gHeight;
-const uchar4 *gPixels;
-rs_allocation gIn;
-
-float gCoeffs[9];
-
-void root(const uchar4 *in, uchar4 *out, const void *usrData, uint32_t x, uint32_t y) {
- uint32_t x1 = min((int32_t)x+1, gWidth-1);
- uint32_t x2 = max((int32_t)x-1, 0);
- uint32_t y1 = min((int32_t)y+1, gHeight-1);
- uint32_t y2 = max((int32_t)y-1, 0);
-
- float4 p00 = rsUnpackColor8888(gPixels[x1 + gWidth * y1]);
- float4 p01 = rsUnpackColor8888(gPixels[x + gWidth * y1]);
- float4 p02 = rsUnpackColor8888(gPixels[x2 + gWidth * y1]);
- float4 p10 = rsUnpackColor8888(gPixels[x1 + gWidth * y]);
- float4 p11 = rsUnpackColor8888(gPixels[x + gWidth * y]);
- float4 p12 = rsUnpackColor8888(gPixels[x2 + gWidth * y]);
- float4 p20 = rsUnpackColor8888(gPixels[x1 + gWidth * y2]);
- float4 p21 = rsUnpackColor8888(gPixels[x + gWidth * y2]);
- float4 p22 = rsUnpackColor8888(gPixels[x2 + gWidth * y2]);
-
- p00 *= gCoeffs[0];
- p01 *= gCoeffs[1];
- p02 *= gCoeffs[2];
- p10 *= gCoeffs[3];
- p11 *= gCoeffs[4];
- p12 *= gCoeffs[5];
- p20 *= gCoeffs[6];
- p21 *= gCoeffs[7];
- p22 *= gCoeffs[8];
-
- p00 += p01;
- p02 += p10;
- p11 += p12;
- p20 += p21;
-
- p22 += p00;
- p02 += p11;
-
- p20 += p22;
- p20 += p02;
-
- p20 = clamp(p20, 0.f, 1.f);
- *out = rsPackColorTo8888(p20.r, p20.g, p20.b);
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/grad.rs b/src/com/android/gallery3d/filtershow/filters/grad.rs
deleted file mode 100644
index ddbafd349..000000000
--- a/src/com/android/gallery3d/filtershow/filters/grad.rs
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * Copyright (C) 2012 Unknown
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma version(1)
-#pragma rs java_package_name(com.android.gallery3d.filtershow.filters)
-
-#define MAX_POINTS 16
-
-uint32_t inputWidth;
-uint32_t inputHeight;
-static const float Rf = 0.2999f;
-static const float Gf = 0.587f;
-static const float Bf = 0.114f;
-//static const float size_scale = 0.01f;
-
-typedef struct {
- rs_matrix3x3 colorMatrix;
- float rgbOff;
- float dx;
- float dy;
- float off;
-} UPointData;
-int mNumberOfLines;
-// input data
-bool mask[MAX_POINTS];
-int xPos1[MAX_POINTS];
-int yPos1[MAX_POINTS];
-int xPos2[MAX_POINTS];
-int yPos2[MAX_POINTS];
-int size[MAX_POINTS];
-int brightness[MAX_POINTS];
-int contrast[MAX_POINTS];
-int saturation[MAX_POINTS];
-
-// generated data
-static UPointData grads[MAX_POINTS];
-
-void setupGradParams() {
- int k = 0;
- for (int i = 0; i < MAX_POINTS; i++) {
- if (!mask[i]) {
- continue;
- }
- float x1 = xPos1[i];
- float y1 = yPos1[i];
- float x2 = xPos2[i];
- float y2 = yPos2[i];
-
- float denom = (y2 * y2 - 2 * y1 * y2 + x2 * x2 - 2 * x1 * x2 + y1 * y1 + x1 * x1);
- if (denom == 0) {
- continue;
- }
- grads[k].dy = (y1 - y2) / denom;
- grads[k].dx = (x1 - x2) / denom;
- grads[k].off = (y2 * y2 + x2 * x2 - x1 * x2 - y1 * y2) / denom;
-
- float S = 1+saturation[i]/100.f;
- float MS = 1-S;
- float Rt = Rf * MS;
- float Gt = Gf * MS;
- float Bt = Bf * MS;
-
- float b = 1+brightness[i]/100.f;
- float c = 1+contrast[i]/100.f;
- b *= c;
- grads[k].rgbOff = .5f - c/2.f;
- rsMatrixSet(&grads[i].colorMatrix, 0, 0, b * (Rt + S));
- rsMatrixSet(&grads[i].colorMatrix, 1, 0, b * Gt);
- rsMatrixSet(&grads[i].colorMatrix, 2, 0, b * Bt);
- rsMatrixSet(&grads[i].colorMatrix, 0, 1, b * Rt);
- rsMatrixSet(&grads[i].colorMatrix, 1, 1, b * (Gt + S));
- rsMatrixSet(&grads[i].colorMatrix, 2, 1, b * Bt);
- rsMatrixSet(&grads[i].colorMatrix, 0, 2, b * Rt);
- rsMatrixSet(&grads[i].colorMatrix, 1, 2, b * Gt);
- rsMatrixSet(&grads[i].colorMatrix, 2, 2, b * (Bt + S));
-
- k++;
- }
- mNumberOfLines = k;
-}
-
-void init() {
-
-}
-
-uchar4 __attribute__((kernel)) selectiveAdjust(const uchar4 in, uint32_t x,
- uint32_t y) {
- float4 pixel = rsUnpackColor8888(in);
-
- float4 wsum = pixel;
- wsum.a = 0.f;
- for (int i = 0; i < mNumberOfLines; i++) {
- UPointData* grad = &grads[i];
- float t = clamp(x*grad->dx+y*grad->dy+grad->off,0.f,1.0f);
- wsum.xyz = wsum.xyz*(1-t)+
- t*(rsMatrixMultiply(&grad->colorMatrix ,wsum.xyz)+grad->rgbOff);
-
- }
-
- pixel.rgb = wsum.rgb;
- pixel.a = 1.0f;
-
- uchar4 out = rsPackColorTo8888(clamp(pixel, 0.f, 1.0f));
- return out;
-}
-
-
-
diff --git a/src/com/android/gallery3d/filtershow/filters/grey.rs b/src/com/android/gallery3d/filtershow/filters/grey.rs
deleted file mode 100644
index e01880360..000000000
--- a/src/com/android/gallery3d/filtershow/filters/grey.rs
+++ /dev/null
@@ -1,22 +0,0 @@
- /*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma version(1)
-#pragma rs java_package_name(com.android.gallery3d.filtershow.filters)
-
-uchar __attribute__((kernel)) RGBAtoA(uchar4 in) {
- return in.r;
-}
diff --git a/src/com/android/gallery3d/filtershow/filters/saturation.rs b/src/com/android/gallery3d/filtershow/filters/saturation.rs
deleted file mode 100644
index 5210e34a3..000000000
--- a/src/com/android/gallery3d/filtershow/filters/saturation.rs
+++ /dev/null
@@ -1,161 +0,0 @@
-/*
- * Copyright (C) 2012 Unknown
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma version(1)
-#pragma rs java_package_name(com.android.gallery3d.filtershow.filters)
-
-#define MAX_CHANELS 7
-#define MAX_HUE 4096
-static const int ABITS = 4;
-static const int HSCALE = 256;
-static const int k1=255 << ABITS;
-static const int k2=HSCALE << ABITS;
-
-static const float Rf = 0.2999f;
-static const float Gf = 0.587f;
-static const float Bf = 0.114f;
-
-rs_matrix3x3 colorMatrix_min;
-rs_matrix3x3 colorMatrix_max;
-
-int mNumberOfLines;
-// input data
-int saturation[MAX_CHANELS];
-float sat[MAX_CHANELS];
-
-float satLut[MAX_HUE];
-// generated data
-
-
-void setupGradParams() {
-
- int master = saturation[0];
- int max = master+saturation[1];
- int min = max;
-
- // calculate the minimum and maximum saturation
- for (int i = 1; i < MAX_CHANELS; i++) {
- int v = master+saturation[i];
- if (max < v) {
- max = v;
- }
- else if (min > v) {
- min = v;
- }
- }
- // generate a lookup table for all hue 0 to 4K which goes from 0 to 1 0=min sat 1 = max sat
- min = min - 1;
- for(int i = 0; i < MAX_HUE ; i++) {
- float p = i * 6 / (float)MAX_HUE;
- int ip = ((int)(p + .5f)) % 6;
- int v = master + saturation[ip + 1];
- satLut[i] = (v - min)/(float)(max - min);
- }
-
- float S = 1 + max / 100.f;
- float MS = 1 - S;
- float Rt = Rf * MS;
- float Gt = Gf * MS;
- float Bt = Bf * MS;
- float b = 1.f;
-
- // Generate 2 color matrix one at min sat and one at max
- rsMatrixSet(&colorMatrix_max, 0, 0, b * (Rt + S));
- rsMatrixSet(&colorMatrix_max, 1, 0, b * Gt);
- rsMatrixSet(&colorMatrix_max, 2, 0, b * Bt);
- rsMatrixSet(&colorMatrix_max, 0, 1, b * Rt);
- rsMatrixSet(&colorMatrix_max, 1, 1, b * (Gt + S));
- rsMatrixSet(&colorMatrix_max, 2, 1, b * Bt);
- rsMatrixSet(&colorMatrix_max, 0, 2, b * Rt);
- rsMatrixSet(&colorMatrix_max, 1, 2, b * Gt);
- rsMatrixSet(&colorMatrix_max, 2, 2, b * (Bt + S));
-
- S = 1 + min / 100.f;
- MS = 1-S;
- Rt = Rf * MS;
- Gt = Gf * MS;
- Bt = Bf * MS;
- b = 1;
-
- rsMatrixSet(&colorMatrix_min, 0, 0, b * (Rt + S));
- rsMatrixSet(&colorMatrix_min, 1, 0, b * Gt);
- rsMatrixSet(&colorMatrix_min, 2, 0, b * Bt);
- rsMatrixSet(&colorMatrix_min, 0, 1, b * Rt);
- rsMatrixSet(&colorMatrix_min, 1, 1, b * (Gt + S));
- rsMatrixSet(&colorMatrix_min, 2, 1, b * Bt);
- rsMatrixSet(&colorMatrix_min, 0, 2, b * Rt);
- rsMatrixSet(&colorMatrix_min, 1, 2, b * Gt);
- rsMatrixSet(&colorMatrix_min, 2, 2, b * (Bt + S));
-}
-
-static ushort rgb2hue( uchar4 rgb)
-{
- int iMin,iMax,chroma;
-
- int ri = rgb.r;
- int gi = rgb.g;
- int bi = rgb.b;
- short rv,rs,rh;
-
- if (ri > gi) {
- iMax = max (ri, bi);
- iMin = min (gi, bi);
- } else {
- iMax = max (gi, bi);
- iMin = min (ri, bi);
- }
-
- rv = (short) (iMax << ABITS);
-
- if (rv == 0) {
- return 0;
- }
-
- chroma = iMax - iMin;
- rs = (short) ((k1 * chroma) / iMax);
- if (rs == 0) {
- return 0;
- }
-
- if ( ri == iMax ) {
- rh = (short) ((k2 * (6 * chroma + gi - bi))/(6 * chroma));
- if (rh >= k2) {
- rh -= k2;
- }
- return rh;
- }
-
- if (gi == iMax) {
- return(short) ((k2 * (2 * chroma + bi - ri)) / (6 * chroma));
- }
-
- return (short) ((k2 * (4 * chroma + ri - gi)) / (6 * chroma));
-}
-
-uchar4 __attribute__((kernel)) selectiveAdjust(const uchar4 in, uint32_t x,
- uint32_t y) {
- float4 pixel = rsUnpackColor8888(in);
-
- float4 wsum = pixel;
- int hue = rgb2hue(in);
-
- float t = satLut[hue];
- pixel.xyz = rsMatrixMultiply(&colorMatrix_min ,pixel.xyz) * (1 - t) +
- t * (rsMatrixMultiply(&colorMatrix_max ,pixel.xyz));
-
- pixel.a = 1.0f;
- return rsPackColorTo8888(clamp(pixel, 0.f, 1.0f));
-} \ No newline at end of file
diff --git a/src/com/android/gallery3d/filtershow/history/HistoryItem.java b/src/com/android/gallery3d/filtershow/history/HistoryItem.java
deleted file mode 100644
index 2baaac327..000000000
--- a/src/com/android/gallery3d/filtershow/history/HistoryItem.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.history;
-
-import android.graphics.Bitmap;
-import android.util.Log;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-
-public class HistoryItem {
- private static final String LOGTAG = "HistoryItem";
- private ImagePreset mImagePreset;
- private FilterRepresentation mFilterRepresentation;
- private Bitmap mPreviewImage;
-
- public HistoryItem(ImagePreset preset, FilterRepresentation representation) {
- mImagePreset = new ImagePreset(preset);
- if (representation != null) {
- mFilterRepresentation = representation.copy();
- }
- }
-
- public ImagePreset getImagePreset() {
- return mImagePreset;
- }
-
- public FilterRepresentation getFilterRepresentation() {
- return mFilterRepresentation;
- }
-
- public Bitmap getPreviewImage() {
- return mPreviewImage;
- }
-
- public void setPreviewImage(Bitmap previewImage) {
- mPreviewImage = previewImage;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/history/HistoryManager.java b/src/com/android/gallery3d/filtershow/history/HistoryManager.java
deleted file mode 100644
index 755e2ea58..000000000
--- a/src/com/android/gallery3d/filtershow/history/HistoryManager.java
+++ /dev/null
@@ -1,172 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.history;
-
-import android.graphics.drawable.Drawable;
-import android.view.MenuItem;
-
-import java.util.Vector;
-
-public class HistoryManager {
- private static final String LOGTAG = "HistoryManager";
-
- private Vector<HistoryItem> mHistoryItems = new Vector<HistoryItem>();
- private int mCurrentPresetPosition = 0;
- private MenuItem mUndoMenuItem = null;
- private MenuItem mRedoMenuItem = null;
- private MenuItem mResetMenuItem = null;
-
- public void setMenuItems(MenuItem undoItem, MenuItem redoItem, MenuItem resetItem) {
- mUndoMenuItem = undoItem;
- mRedoMenuItem = redoItem;
- mResetMenuItem = resetItem;
- updateMenuItems();
- }
-
- private int getCount() {
- return mHistoryItems.size();
- }
-
- public HistoryItem getItem(int position) {
- return mHistoryItems.elementAt(position);
- }
-
- private void clear() {
- mHistoryItems.clear();
- }
-
- private void add(HistoryItem item) {
- mHistoryItems.add(item);
- }
-
- private void notifyDataSetChanged() {
- // TODO
- }
-
- public boolean canReset() {
- if (getCount() <= 1) {
- return false;
- }
- return true;
- }
-
- public boolean canUndo() {
- if (mCurrentPresetPosition == getCount() - 1) {
- return false;
- }
- return true;
- }
-
- public boolean canRedo() {
- if (mCurrentPresetPosition == 0) {
- return false;
- }
- return true;
- }
-
- public void updateMenuItems() {
- if (mUndoMenuItem != null) {
- setEnabled(mUndoMenuItem, canUndo());
- }
- if (mRedoMenuItem != null) {
- setEnabled(mRedoMenuItem, canRedo());
- }
- if (mResetMenuItem != null) {
- setEnabled(mResetMenuItem, canReset());
- }
- }
-
- private void setEnabled(MenuItem item, boolean enabled) {
- item.setEnabled(enabled);
- Drawable drawable = item.getIcon();
- if (drawable != null) {
- drawable.setAlpha(enabled ? 255 : 80);
- }
- }
-
- public void setCurrentPreset(int n) {
- mCurrentPresetPosition = n;
- updateMenuItems();
- notifyDataSetChanged();
- }
-
- public void reset() {
- if (getCount() == 0) {
- return;
- }
- HistoryItem first = getItem(getCount() - 1);
- clear();
- addHistoryItem(first);
- updateMenuItems();
- }
-
- public HistoryItem getLast() {
- if (getCount() == 0) {
- return null;
- }
- return getItem(0);
- }
-
- public HistoryItem getCurrent() {
- return getItem(mCurrentPresetPosition);
- }
-
- public void addHistoryItem(HistoryItem preset) {
- insert(preset, 0);
- updateMenuItems();
- }
-
- private void insert(HistoryItem preset, int position) {
- if (mCurrentPresetPosition != 0) {
- // in this case, let's discount the presets before the current one
- Vector<HistoryItem> oldItems = new Vector<HistoryItem>();
- for (int i = mCurrentPresetPosition; i < getCount(); i++) {
- oldItems.add(getItem(i));
- }
- clear();
- for (int i = 0; i < oldItems.size(); i++) {
- add(oldItems.elementAt(i));
- }
- mCurrentPresetPosition = position;
- notifyDataSetChanged();
- }
- mHistoryItems.insertElementAt(preset, position);
- mCurrentPresetPosition = position;
- notifyDataSetChanged();
- }
-
- public int redo() {
- mCurrentPresetPosition--;
- if (mCurrentPresetPosition < 0) {
- mCurrentPresetPosition = 0;
- }
- notifyDataSetChanged();
- updateMenuItems();
- return mCurrentPresetPosition;
- }
-
- public int undo() {
- mCurrentPresetPosition++;
- if (mCurrentPresetPosition >= getCount()) {
- mCurrentPresetPosition = getCount() - 1;
- }
- notifyDataSetChanged();
- updateMenuItems();
- return mCurrentPresetPosition;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ControlPoint.java b/src/com/android/gallery3d/filtershow/imageshow/ControlPoint.java
deleted file mode 100644
index aaec728a6..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/ControlPoint.java
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-public class ControlPoint implements Comparable {
- public float x;
- public float y;
-
- public ControlPoint(float px, float py) {
- x = px;
- y = py;
- }
-
- public ControlPoint(ControlPoint point) {
- x = point.x;
- y = point.y;
- }
-
- public boolean sameValues(ControlPoint other) {
- if (this == other) {
- return true;
- }
- if (other == null) {
- return false;
- }
-
- if (Float.floatToIntBits(x) != Float.floatToIntBits(other.x)) {
- return false;
- }
- if (Float.floatToIntBits(y) != Float.floatToIntBits(other.y)) {
- return false;
- }
- return true;
- }
-
- public ControlPoint copy() {
- return new ControlPoint(x, y);
- }
-
- @Override
- public int compareTo(Object another) {
- ControlPoint p = (ControlPoint) another;
- if (p.x < x) {
- return 1;
- } else if (p.x > x) {
- return -1;
- }
- return 0;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/EclipseControl.java b/src/com/android/gallery3d/filtershow/imageshow/EclipseControl.java
deleted file mode 100644
index 8ceb37599..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/EclipseControl.java
+++ /dev/null
@@ -1,302 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.RadialGradient;
-import android.graphics.RectF;
-import android.graphics.Shader;
-
-import com.android.gallery3d.R;
-
-public class EclipseControl {
- private float mCenterX = Float.NaN;
- private float mCenterY = 0;
- private float mRadiusX = 200;
- private float mRadiusY = 300;
- private static int MIN_TOUCH_DIST = 80;// should be a resource & in dips
-
- private float[] handlex = new float[9];
- private float[] handley = new float[9];
- private int mSliderColor;
- private int mCenterDotSize = 40;
- private float mDownX;
- private float mDownY;
- private float mDownCenterX;
- private float mDownCenterY;
- private float mDownRadiusX;
- private float mDownRadiusY;
- private Matrix mScrToImg;
-
- private boolean mShowReshapeHandles = true;
- public final static int HAN_CENTER = 0;
- public final static int HAN_NORTH = 7;
- public final static int HAN_NE = 8;
- public final static int HAN_EAST = 1;
- public final static int HAN_SE = 2;
- public final static int HAN_SOUTH = 3;
- public final static int HAN_SW = 4;
- public final static int HAN_WEST = 5;
- public final static int HAN_NW = 6;
-
- public EclipseControl(Context context) {
- mSliderColor = Color.WHITE;
- }
-
- public void setRadius(float x, float y) {
- mRadiusX = x;
- mRadiusY = y;
- }
-
- public void setCenter(float x, float y) {
- mCenterX = x;
- mCenterY = y;
- }
-
- public int getCloseHandle(float x, float y) {
- float min = Float.MAX_VALUE;
- int handle = -1;
- for (int i = 0; i < handlex.length; i++) {
- float dx = handlex[i] - x;
- float dy = handley[i] - y;
- float dist = dx * dx + dy * dy;
- if (dist < min) {
- min = dist;
- handle = i;
- }
- }
-
- if (min < MIN_TOUCH_DIST * MIN_TOUCH_DIST) {
- return handle;
- }
- for (int i = 0; i < handlex.length; i++) {
- float dx = handlex[i] - x;
- float dy = handley[i] - y;
- float dist = (float) Math.sqrt(dx * dx + dy * dy);
- }
-
- return -1;
- }
-
- public void setScrToImageMatrix(Matrix scrToImg) {
- mScrToImg = scrToImg;
- }
-
- public void actionDown(float x, float y, Oval oval) {
- float[] point = new float[] {
- x, y };
- mScrToImg.mapPoints(point);
- mDownX = point[0];
- mDownY = point[1];
- mDownCenterX = oval.getCenterX();
- mDownCenterY = oval.getCenterY();
- mDownRadiusX = oval.getRadiusX();
- mDownRadiusY = oval.getRadiusY();
- }
-
- public void actionMove(int handle, float x, float y, Oval oval) {
- float[] point = new float[] {
- x, y };
- mScrToImg.mapPoints(point);
- x = point[0];
- y = point[1];
-
- // Test if the matrix is swapping x and y
- point[0] = 0;
- point[1] = 1;
- mScrToImg.mapVectors(point);
- boolean swapxy = (point[0] > 0.0f);
-
- int sign = 1;
- switch (handle) {
- case HAN_CENTER:
- float ctrdx = mDownX - mDownCenterX;
- float ctrdy = mDownY - mDownCenterY;
- oval.setCenter(x - ctrdx, y - ctrdy);
- // setRepresentation(mVignetteRep);
- break;
- case HAN_NORTH:
- sign = -1;
- case HAN_SOUTH:
- if (swapxy) {
- float raddx = mDownRadiusY - Math.abs(mDownX - mDownCenterY);
- oval.setRadiusY(Math.abs(x - oval.getCenterY() + sign * raddx));
- } else {
- float raddy = mDownRadiusY - Math.abs(mDownY - mDownCenterY);
- oval.setRadiusY(Math.abs(y - oval.getCenterY() + sign * raddy));
- }
- break;
- case HAN_EAST:
- sign = -1;
- case HAN_WEST:
- if (swapxy) {
- float raddy = mDownRadiusX - Math.abs(mDownY - mDownCenterX);
- oval.setRadiusX(Math.abs(y - oval.getCenterX() + sign * raddy));
- } else {
- float raddx = mDownRadiusX - Math.abs(mDownX - mDownCenterX);
- oval.setRadiusX(Math.abs(x - oval.getCenterX() - sign * raddx));
- }
- break;
- case HAN_SE:
- case HAN_NE:
- case HAN_SW:
- case HAN_NW:
- float sin45 = (float) Math.sin(45);
- float dr = (mDownRadiusX + mDownRadiusY) * sin45;
- float ctr_dx = mDownX - mDownCenterX;
- float ctr_dy = mDownY - mDownCenterY;
- float downRad = Math.abs(ctr_dx) + Math.abs(ctr_dy) - dr;
- float rx = oval.getRadiusX();
- float ry = oval.getRadiusY();
- float r = (Math.abs(rx) + Math.abs(ry)) * sin45;
- float dx = x - oval.getCenterX();
- float dy = y - oval.getCenterY();
- float nr = Math.abs(Math.abs(dx) + Math.abs(dy) - downRad);
- oval.setRadius(rx * nr / r, ry * nr / r);
-
- break;
- }
- }
-
- public void paintGrayPoint(Canvas canvas, float x, float y) {
- if (x == Float.NaN) {
- return;
- }
-
- Paint paint = new Paint();
-
- paint.setStyle(Paint.Style.FILL);
- paint.setColor(Color.BLUE);
- int[] colors3 = new int[] {
- Color.GRAY, Color.LTGRAY, 0x66000000, 0 };
- RadialGradient g = new RadialGradient(x, y, mCenterDotSize, colors3, new float[] {
- 0, .3f, .31f, 1 }, Shader.TileMode.CLAMP);
- paint.setShader(g);
- canvas.drawCircle(x, y, mCenterDotSize, paint);
- }
-
- public void paintPoint(Canvas canvas, float x, float y) {
- if (x == Float.NaN) {
- return;
- }
-
- Paint paint = new Paint();
-
- paint.setStyle(Paint.Style.FILL);
- paint.setColor(Color.BLUE);
- int[] colors3 = new int[] {
- mSliderColor, mSliderColor, 0x66000000, 0 };
- RadialGradient g = new RadialGradient(x, y, mCenterDotSize, colors3, new float[] {
- 0, .3f, .31f, 1 }, Shader.TileMode.CLAMP);
- paint.setShader(g);
- canvas.drawCircle(x, y, mCenterDotSize, paint);
- }
-
- void paintRadius(Canvas canvas, float cx, float cy, float rx, float ry) {
- if (cx == Float.NaN) {
- return;
- }
- int mSliderColor = 0xFF33B5E5;
- Paint paint = new Paint();
- RectF rect = new RectF(cx - rx, cy - ry, cx + rx, cy + ry);
- paint.setAntiAlias(true);
- paint.setStyle(Paint.Style.STROKE);
- paint.setStrokeWidth(6);
- paint.setColor(Color.BLACK);
- paintOvallines(canvas, rect, paint, cx, cy, rx, ry);
-
- paint.setStrokeWidth(3);
- paint.setColor(Color.WHITE);
- paintOvallines(canvas, rect, paint, cx, cy, rx, ry);
- }
-
- public void paintOvallines(
- Canvas canvas, RectF rect, Paint paint, float cx, float cy, float rx, float ry) {
- canvas.drawOval(rect, paint);
- float da = 4;
- float arclen = da + da;
- if (mShowReshapeHandles) {
- paint.setStyle(Paint.Style.STROKE);
-
- for (int i = 0; i < 361; i += 90) {
- float dx = rx + 10;
- float dy = ry + 10;
- rect.left = cx - dx;
- rect.top = cy - dy;
- rect.right = cx + dx;
- rect.bottom = cy + dy;
- canvas.drawArc(rect, i - da, arclen, false, paint);
- dx = rx - 10;
- dy = ry - 10;
- rect.left = cx - dx;
- rect.top = cy - dy;
- rect.right = cx + dx;
- rect.bottom = cy + dy;
- canvas.drawArc(rect, i - da, arclen, false, paint);
- }
- }
- da *= 2;
- paint.setStyle(Paint.Style.FILL);
-
- for (int i = 45; i < 361; i += 90) {
- double angle = Math.PI * i / 180.;
- float x = cx + (float) (rx * Math.cos(angle));
- float y = cy + (float) (ry * Math.sin(angle));
- canvas.drawRect(x - da, y - da, x + da, y + da, paint);
- }
- paint.setStyle(Paint.Style.STROKE);
- rect.left = cx - rx;
- rect.top = cy - ry;
- rect.right = cx + rx;
- rect.bottom = cy + ry;
- }
-
- public void fillHandles(Canvas canvas, float cx, float cy, float rx, float ry) {
- handlex[0] = cx;
- handley[0] = cy;
- int k = 1;
-
- for (int i = 0; i < 360; i += 45) {
- double angle = Math.PI * i / 180.;
-
- float x = cx + (float) (rx * Math.cos(angle));
- float y = cy + (float) (ry * Math.sin(angle));
- handlex[k] = x;
- handley[k] = y;
-
- k++;
- }
- }
-
- public void draw(Canvas canvas) {
- paintRadius(canvas, mCenterX, mCenterY, mRadiusX, mRadiusY);
- fillHandles(canvas, mCenterX, mCenterY, mRadiusX, mRadiusY);
- paintPoint(canvas, mCenterX, mCenterY);
- }
-
- public boolean isUndefined() {
- return Float.isNaN(mCenterX);
- }
-
- public void setShowReshapeHandles(boolean showReshapeHandles) {
- this.mShowReshapeHandles = showReshapeHandles;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/GeometryMathUtils.java b/src/com/android/gallery3d/filtershow/imageshow/GeometryMathUtils.java
deleted file mode 100644
index 81394f142..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/GeometryMathUtils.java
+++ /dev/null
@@ -1,416 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.Rect;
-import android.graphics.RectF;
-
-import com.android.gallery3d.filtershow.cache.ImageLoader;
-import com.android.gallery3d.filtershow.filters.FilterCropRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterMirrorRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterMirrorRepresentation.Mirror;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRotateRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRotateRepresentation.Rotation;
-import com.android.gallery3d.filtershow.filters.FilterStraightenRepresentation;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-
-import java.util.Collection;
-import java.util.Iterator;
-
-public final class GeometryMathUtils {
- private GeometryMathUtils() {};
-
- // Holder class for Geometry data.
- public static final class GeometryHolder {
- public Rotation rotation = FilterRotateRepresentation.getNil();
- public float straighten = FilterStraightenRepresentation.getNil();
- public RectF crop = FilterCropRepresentation.getNil();
- public Mirror mirror = FilterMirrorRepresentation.getNil();
-
- public void set(GeometryHolder h) {
- rotation = h.rotation;
- straighten = h.straighten;
- crop.set(h.crop);
- mirror = h.mirror;
- }
-
- public void wipe() {
- rotation = FilterRotateRepresentation.getNil();
- straighten = FilterStraightenRepresentation.getNil();
- crop = FilterCropRepresentation.getNil();
- mirror = FilterMirrorRepresentation.getNil();
- }
-
- public boolean isNil() {
- return rotation == FilterRotateRepresentation.getNil() &&
- straighten == FilterStraightenRepresentation.getNil() &&
- crop.equals(FilterCropRepresentation.getNil()) &&
- mirror == FilterMirrorRepresentation.getNil();
- }
-
- @Override
- public boolean equals(Object o) {
- if (this == o) {
- return true;
- }
- if (!(o instanceof GeometryHolder)) {
- return false;
- }
- GeometryHolder h = (GeometryHolder) o;
- return rotation == h.rotation && straighten == h.straighten &&
- ((crop == null && h.crop == null) || (crop != null && crop.equals(h.crop))) &&
- mirror == h.mirror;
- }
-
- @Override
- public String toString() {
- return getClass().getSimpleName() + "[" + "rotation:" + rotation.value()
- + ",straighten:" + straighten + ",crop:" + crop.toString()
- + ",mirror:" + mirror.value() + "]";
- }
- }
-
- // Math operations for 2d vectors
- public static float clamp(float i, float low, float high) {
- return Math.max(Math.min(i, high), low);
- }
-
- public static float[] lineIntersect(float[] line1, float[] line2) {
- float a0 = line1[0];
- float a1 = line1[1];
- float b0 = line1[2];
- float b1 = line1[3];
- float c0 = line2[0];
- float c1 = line2[1];
- float d0 = line2[2];
- float d1 = line2[3];
- float t0 = a0 - b0;
- float t1 = a1 - b1;
- float t2 = b0 - d0;
- float t3 = d1 - b1;
- float t4 = c0 - d0;
- float t5 = c1 - d1;
-
- float denom = t1 * t4 - t0 * t5;
- if (denom == 0)
- return null;
- float u = (t3 * t4 + t5 * t2) / denom;
- float[] intersect = {
- b0 + u * t0, b1 + u * t1
- };
- return intersect;
- }
-
- public static float[] shortestVectorFromPointToLine(float[] point, float[] line) {
- float x1 = line[0];
- float x2 = line[2];
- float y1 = line[1];
- float y2 = line[3];
- float xdelt = x2 - x1;
- float ydelt = y2 - y1;
- if (xdelt == 0 && ydelt == 0)
- return null;
- float u = ((point[0] - x1) * xdelt + (point[1] - y1) * ydelt)
- / (xdelt * xdelt + ydelt * ydelt);
- float[] ret = {
- (x1 + u * (x2 - x1)), (y1 + u * (y2 - y1))
- };
- float[] vec = {
- ret[0] - point[0], ret[1] - point[1]
- };
- return vec;
- }
-
- // A . B
- public static float dotProduct(float[] a, float[] b) {
- return a[0] * b[0] + a[1] * b[1];
- }
-
- public static float[] normalize(float[] a) {
- float length = (float) Math.sqrt(a[0] * a[0] + a[1] * a[1]);
- float[] b = {
- a[0] / length, a[1] / length
- };
- return b;
- }
-
- // A onto B
- public static float scalarProjection(float[] a, float[] b) {
- float length = (float) Math.sqrt(b[0] * b[0] + b[1] * b[1]);
- return dotProduct(a, b) / length;
- }
-
- public static float[] getVectorFromPoints(float[] point1, float[] point2) {
- float[] p = {
- point2[0] - point1[0], point2[1] - point1[1]
- };
- return p;
- }
-
- public static float[] getUnitVectorFromPoints(float[] point1, float[] point2) {
- float[] p = {
- point2[0] - point1[0], point2[1] - point1[1]
- };
- float length = (float) Math.sqrt(p[0] * p[0] + p[1] * p[1]);
- p[0] = p[0] / length;
- p[1] = p[1] / length;
- return p;
- }
-
- public static void scaleRect(RectF r, float scale) {
- r.set(r.left * scale, r.top * scale, r.right * scale, r.bottom * scale);
- }
-
- // A - B
- public static float[] vectorSubtract(float[] a, float[] b) {
- int len = a.length;
- if (len != b.length)
- return null;
- float[] ret = new float[len];
- for (int i = 0; i < len; i++) {
- ret[i] = a[i] - b[i];
- }
- return ret;
- }
-
- public static float vectorLength(float[] a) {
- return (float) Math.sqrt(a[0] * a[0] + a[1] * a[1]);
- }
-
- public static float scale(float oldWidth, float oldHeight, float newWidth, float newHeight) {
- if (oldHeight == 0 || oldWidth == 0 || (oldWidth == newWidth && oldHeight == newHeight)) {
- return 1;
- }
- return Math.min(newWidth / oldWidth, newHeight / oldHeight);
- }
-
- public static Rect roundNearest(RectF r) {
- Rect q = new Rect(Math.round(r.left), Math.round(r.top), Math.round(r.right),
- Math.round(r.bottom));
- return q;
- }
-
- private static void concatMirrorMatrix(Matrix m, Mirror type) {
- if (type == Mirror.HORIZONTAL) {
- m.postScale(-1, 1);
- } else if (type == Mirror.VERTICAL) {
- m.postScale(1, -1);
- } else if (type == Mirror.BOTH) {
- m.postScale(1, -1);
- m.postScale(-1, 1);
- }
- }
-
- private static int getRotationForOrientation(int orientation) {
- switch (orientation) {
- case ImageLoader.ORI_ROTATE_90:
- return 90;
- case ImageLoader.ORI_ROTATE_180:
- return 180;
- case ImageLoader.ORI_ROTATE_270:
- return 270;
- default:
- return 0;
- }
- }
-
- public static GeometryHolder unpackGeometry(Collection<FilterRepresentation> geometry) {
- GeometryHolder holder = new GeometryHolder();
- unpackGeometry(holder, geometry);
- return holder;
- }
-
- public static void unpackGeometry(GeometryHolder out,
- Collection<FilterRepresentation> geometry) {
- out.wipe();
- // Get geometry data from filters
- for (FilterRepresentation r : geometry) {
- if (r.isNil()) {
- continue;
- }
- if (r.getSerializationName() == FilterRotateRepresentation.SERIALIZATION_NAME) {
- out.rotation = ((FilterRotateRepresentation) r).getRotation();
- } else if (r.getSerializationName() ==
- FilterStraightenRepresentation.SERIALIZATION_NAME) {
- out.straighten = ((FilterStraightenRepresentation) r).getStraighten();
- } else if (r.getSerializationName() == FilterCropRepresentation.SERIALIZATION_NAME) {
- ((FilterCropRepresentation) r).getCrop(out.crop);
- } else if (r.getSerializationName() == FilterMirrorRepresentation.SERIALIZATION_NAME) {
- out.mirror = ((FilterMirrorRepresentation) r).getMirror();
- }
- }
- }
-
- public static void replaceInstances(Collection<FilterRepresentation> geometry,
- FilterRepresentation rep) {
- Iterator<FilterRepresentation> iter = geometry.iterator();
- while (iter.hasNext()) {
- FilterRepresentation r = iter.next();
- if (ImagePreset.sameSerializationName(rep, r)) {
- iter.remove();
- }
- }
- if (!rep.isNil()) {
- geometry.add(rep);
- }
- }
-
- public static void initializeHolder(GeometryHolder outHolder,
- FilterRepresentation currentLocal) {
- Collection<FilterRepresentation> geometry = MasterImage.getImage().getPreset()
- .getGeometryFilters();
- replaceInstances(geometry, currentLocal);
- unpackGeometry(outHolder, geometry);
- }
-
- private static Bitmap applyFullGeometryMatrix(Bitmap image, GeometryHolder holder) {
- int width = image.getWidth();
- int height = image.getHeight();
- RectF crop = getTrueCropRect(holder, width, height);
- Rect frame = new Rect();
- crop.roundOut(frame);
- Matrix m = getCropSelectionToScreenMatrix(null, holder, width, height, frame.width(),
- frame.height());
- Bitmap temp = Bitmap.createBitmap(frame.width(), frame.height(), Bitmap.Config.ARGB_8888);
- Canvas canvas = new Canvas(temp);
- Paint paint = new Paint();
- paint.setAntiAlias(true);
- paint.setFilterBitmap(true);
- paint.setDither(true);
- canvas.drawBitmap(image, m, paint);
- return temp;
- }
-
- public static Matrix getImageToScreenMatrix(Collection<FilterRepresentation> geometry,
- boolean reflectRotation, Rect bmapDimens, float viewWidth, float viewHeight) {
- GeometryHolder h = unpackGeometry(geometry);
- return GeometryMathUtils.getOriginalToScreen(h, reflectRotation, bmapDimens.width(),
- bmapDimens.height(), viewWidth, viewHeight);
- }
-
- public static Matrix getOriginalToScreen(GeometryHolder holder, boolean rotate,
- float originalWidth,
- float originalHeight, float viewWidth, float viewHeight) {
- int orientation = MasterImage.getImage().getZoomOrientation();
- int rotation = getRotationForOrientation(orientation);
- Rotation prev = holder.rotation;
- rotation = (rotation + prev.value()) % 360;
- holder.rotation = Rotation.fromValue(rotation);
- Matrix m = getCropSelectionToScreenMatrix(null, holder, (int) originalWidth,
- (int) originalHeight, (int) viewWidth, (int) viewHeight);
- holder.rotation = prev;
- return m;
- }
-
- public static Bitmap applyGeometryRepresentations(Collection<FilterRepresentation> res,
- Bitmap image) {
- GeometryHolder holder = unpackGeometry(res);
- Bitmap bmap = image;
- // If there are geometry changes, apply them to the image
- if (!holder.isNil()) {
- bmap = applyFullGeometryMatrix(bmap, holder);
- }
- return bmap;
- }
-
- public static RectF drawTransformedCropped(GeometryHolder holder, Canvas canvas,
- Bitmap photo, int viewWidth, int viewHeight) {
- if (photo == null) {
- return null;
- }
- RectF crop = new RectF();
- Matrix m = getCropSelectionToScreenMatrix(crop, holder, photo.getWidth(), photo.getHeight(),
- viewWidth, viewHeight);
- canvas.save();
- canvas.clipRect(crop);
- Paint p = new Paint();
- p.setAntiAlias(true);
- canvas.drawBitmap(photo, m, p);
- canvas.restore();
- return crop;
- }
-
- public static boolean needsDimensionSwap(Rotation rotation) {
- switch (rotation) {
- case NINETY:
- case TWO_SEVENTY:
- return true;
- default:
- return false;
- }
- }
-
- // Gives matrix for rotated, straightened, mirrored bitmap centered at 0,0.
- private static Matrix getFullGeometryMatrix(GeometryHolder holder, int bitmapWidth,
- int bitmapHeight) {
- float centerX = bitmapWidth / 2f;
- float centerY = bitmapHeight / 2f;
- Matrix m = new Matrix();
- m.setTranslate(-centerX, -centerY);
- m.postRotate(holder.straighten + holder.rotation.value());
- concatMirrorMatrix(m, holder.mirror);
- return m;
- }
-
- public static Matrix getFullGeometryToScreenMatrix(GeometryHolder holder, int bitmapWidth,
- int bitmapHeight, int viewWidth, int viewHeight) {
- float scale = GeometryMathUtils.scale(bitmapWidth, bitmapHeight, viewWidth, viewHeight);
- Matrix m = getFullGeometryMatrix(holder, bitmapWidth, bitmapHeight);
- m.postScale(scale, scale);
- m.postTranslate(viewWidth / 2f, viewHeight / 2f);
- return m;
- }
-
- public static RectF getTrueCropRect(GeometryHolder holder, int bitmapWidth, int bitmapHeight) {
- RectF r = new RectF(holder.crop);
- FilterCropRepresentation.findScaledCrop(r, bitmapWidth, bitmapHeight);
- float s = holder.straighten;
- holder.straighten = 0;
- Matrix m1 = getFullGeometryMatrix(holder, bitmapWidth, bitmapHeight);
- holder.straighten = s;
- m1.mapRect(r);
- return r;
- }
-
- public static Matrix getCropSelectionToScreenMatrix(RectF outCrop, GeometryHolder holder,
- int bitmapWidth, int bitmapHeight, int viewWidth, int viewHeight) {
- Matrix m = getFullGeometryMatrix(holder, bitmapWidth, bitmapHeight);
- RectF crop = getTrueCropRect(holder, bitmapWidth, bitmapHeight);
- float scale = GeometryMathUtils.scale(crop.width(), crop.height(), viewWidth, viewHeight);
- m.postScale(scale, scale);
- GeometryMathUtils.scaleRect(crop, scale);
- m.postTranslate(viewWidth / 2f - crop.centerX(), viewHeight / 2f - crop.centerY());
- if (outCrop != null) {
- crop.offset(viewWidth / 2f - crop.centerX(), viewHeight / 2f - crop.centerY());
- outCrop.set(crop);
- }
- return m;
- }
-
- public static Matrix getCropSelectionToScreenMatrix(RectF outCrop,
- Collection<FilterRepresentation> res, int bitmapWidth, int bitmapHeight, int viewWidth,
- int viewHeight) {
- GeometryHolder holder = unpackGeometry(res);
- return getCropSelectionToScreenMatrix(outCrop, holder, bitmapWidth, bitmapHeight,
- viewWidth, viewHeight);
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/GradControl.java b/src/com/android/gallery3d/filtershow/imageshow/GradControl.java
deleted file mode 100644
index 964da99e9..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/GradControl.java
+++ /dev/null
@@ -1,274 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.DashPathEffect;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.RadialGradient;
-import android.graphics.Rect;
-import android.graphics.Shader;
-
-import com.android.gallery3d.R;
-
-public class GradControl {
- private float mPoint1X = Float.NaN; // used to flag parameters have not been set
- private float mPoint1Y = 0;
- private float mPoint2X = 200;
- private float mPoint2Y = 300;
- private int mMinTouchDist = 80;// should be a resource & in dips
-
- private float[] handlex = new float[3];
- private float[] handley = new float[3];
- private int mSliderColor;
- private int mCenterDotSize;
- private float mDownX;
- private float mDownY;
- private float mDownPoint1X;
- private float mDownPoint1Y;
- private float mDownPoint2X;
- private float mDownPoint2Y;
- Rect mImageBounds;
- int mImageHeight;
- private Matrix mScrToImg;
- Paint mPaint = new Paint();
- DashPathEffect mDash = new DashPathEffect(new float[]{30, 30}, 0);
- private boolean mShowReshapeHandles = true;
- public final static int HAN_CENTER = 0;
- public final static int HAN_NORTH = 2;
- public final static int HAN_SOUTH = 1;
- private int[] mPointColorPatern;
- private int[] mGrayPointColorPatern;
- private float[] mPointRadialPos = new float[]{0, .3f, .31f, 1};
- private int mLineColor;
- private int mlineShadowColor;
-
- public GradControl(Context context) {
-
- Resources res = context.getResources();
- mCenterDotSize = (int) res.getDimension(R.dimen.gradcontrol_dot_size);
- mMinTouchDist = (int) res.getDimension(R.dimen.gradcontrol_min_touch_dist);
- int grayPointCenterColor = res.getColor(R.color.gradcontrol_graypoint_center);
- int grayPointEdgeColor = res.getColor(R.color.gradcontrol_graypoint_edge);
- int pointCenterColor = res.getColor(R.color.gradcontrol_point_center);
- int pointEdgeColor = res.getColor(R.color.gradcontrol_point_edge);
- int pointShadowStartColor = res.getColor(R.color.gradcontrol_point_shadow_start);
- int pointShadowEndColor = res.getColor(R.color.gradcontrol_point_shadow_end);
- mPointColorPatern = new int[]{
- pointCenterColor, pointEdgeColor, pointShadowStartColor, pointShadowEndColor};
- mGrayPointColorPatern = new int[]{
- grayPointCenterColor, grayPointEdgeColor, pointShadowStartColor, pointShadowEndColor};
- mSliderColor = Color.WHITE;
- mLineColor = res.getColor(R.color.gradcontrol_line_color);
- mlineShadowColor = res.getColor(R.color.gradcontrol_line_shadow);
- }
-
- public void setPoint2(float x, float y) {
- mPoint2X = x;
- mPoint2Y = y;
- }
-
- public void setPoint1(float x, float y) {
- mPoint1X = x;
- mPoint1Y = y;
- }
-
- public int getCloseHandle(float x, float y) {
- float min = Float.MAX_VALUE;
- int handle = -1;
- for (int i = 0; i < handlex.length; i++) {
- float dx = handlex[i] - x;
- float dy = handley[i] - y;
- float dist = dx * dx + dy * dy;
- if (dist < min) {
- min = dist;
- handle = i;
- }
- }
-
- if (min < mMinTouchDist * mMinTouchDist) {
- return handle;
- }
- for (int i = 0; i < handlex.length; i++) {
- float dx = handlex[i] - x;
- float dy = handley[i] - y;
- float dist = (float) Math.sqrt(dx * dx + dy * dy);
- }
-
- return -1;
- }
-
- public void setScrImageInfo(Matrix scrToImg, Rect imageBounds) {
- mScrToImg = scrToImg;
- mImageBounds = new Rect(imageBounds);
- }
-
- private boolean centerIsOutside(float x1, float y1, float x2, float y2) {
- return (!mImageBounds.contains((int) ((x1 + x2) / 2), (int) ((y1 + y2) / 2)));
- }
-
- public void actionDown(float x, float y, Line line) {
- float[] point = new float[]{
- x, y};
- mScrToImg.mapPoints(point);
- mDownX = point[0];
- mDownY = point[1];
- mDownPoint1X = line.getPoint1X();
- mDownPoint1Y = line.getPoint1Y();
- mDownPoint2X = line.getPoint2X();
- mDownPoint2Y = line.getPoint2Y();
- }
-
- public void actionMove(int handle, float x, float y, Line line) {
- float[] point = new float[]{
- x, y};
- mScrToImg.mapPoints(point);
- x = point[0];
- y = point[1];
-
- // Test if the matrix is swapping x and y
- point[0] = 0;
- point[1] = 1;
- mScrToImg.mapVectors(point);
- boolean swapxy = (point[0] > 0.0f);
-
- int sign = 1;
-
- float dx = x - mDownX;
- float dy = y - mDownY;
- switch (handle) {
- case HAN_CENTER:
- if (centerIsOutside(mDownPoint1X + dx, mDownPoint1Y + dy,
- mDownPoint2X + dx, mDownPoint2Y + dy)) {
- break;
- }
- line.setPoint1(mDownPoint1X + dx, mDownPoint1Y + dy);
- line.setPoint2(mDownPoint2X + dx, mDownPoint2Y + dy);
- break;
- case HAN_SOUTH:
- if (centerIsOutside(mDownPoint1X + dx, mDownPoint1Y + dy,
- mDownPoint2X, mDownPoint2Y)) {
- break;
- }
- line.setPoint1(mDownPoint1X + dx, mDownPoint1Y + dy);
- break;
- case HAN_NORTH:
- if (centerIsOutside(mDownPoint1X, mDownPoint1Y,
- mDownPoint2X + dx, mDownPoint2Y + dy)) {
- break;
- }
- line.setPoint2(mDownPoint2X + dx, mDownPoint2Y + dy);
- break;
- }
- }
-
- public void paintGrayPoint(Canvas canvas, float x, float y) {
- if (isUndefined()) {
- return;
- }
-
- Paint paint = new Paint();
- paint.setStyle(Paint.Style.FILL);
- RadialGradient g = new RadialGradient(x, y, mCenterDotSize, mGrayPointColorPatern,
- mPointRadialPos, Shader.TileMode.CLAMP);
- paint.setShader(g);
- canvas.drawCircle(x, y, mCenterDotSize, paint);
- }
-
- public void paintPoint(Canvas canvas, float x, float y) {
- if (isUndefined()) {
- return;
- }
-
- Paint paint = new Paint();
- paint.setStyle(Paint.Style.FILL);
- RadialGradient g = new RadialGradient(x, y, mCenterDotSize, mPointColorPatern,
- mPointRadialPos, Shader.TileMode.CLAMP);
- paint.setShader(g);
- canvas.drawCircle(x, y, mCenterDotSize, paint);
- }
-
- void paintLines(Canvas canvas, float p1x, float p1y, float p2x, float p2y) {
- if (isUndefined()) {
- return;
- }
-
- mPaint.setAntiAlias(true);
- mPaint.setStyle(Paint.Style.STROKE);
-
- mPaint.setStrokeWidth(6);
- mPaint.setColor(mlineShadowColor);
- mPaint.setPathEffect(mDash);
- paintOvallines(canvas, mPaint, p1x, p1y, p2x, p2y);
-
- mPaint.setStrokeWidth(3);
- mPaint.setColor(mLineColor);
- mPaint.setPathEffect(mDash);
- paintOvallines(canvas, mPaint, p1x, p1y, p2x, p2y);
- }
-
- public void paintOvallines(
- Canvas canvas, Paint paint, float p1x, float p1y, float p2x, float p2y) {
-
-
-
- canvas.drawLine(p1x, p1y, p2x, p2y, paint);
-
- float cx = (p1x + p2x) / 2;
- float cy = (p1y + p2y) / 2;
- float dx = p1x - p2x;
- float dy = p1y - p2y;
- float len = (float) Math.sqrt(dx * dx + dy * dy);
- dx *= 2048 / len;
- dy *= 2048 / len;
-
- canvas.drawLine(p1x + dy, p1y - dx, p1x - dy, p1y + dx, paint);
- canvas.drawLine(p2x + dy, p2y - dx, p2x - dy, p2y + dx, paint);
- }
-
- public void fillHandles(Canvas canvas, float p1x, float p1y, float p2x, float p2y) {
- float cx = (p1x + p2x) / 2;
- float cy = (p1y + p2y) / 2;
- handlex[0] = cx;
- handley[0] = cy;
- handlex[1] = p1x;
- handley[1] = p1y;
- handlex[2] = p2x;
- handley[2] = p2y;
-
- }
-
- public void draw(Canvas canvas) {
- paintLines(canvas, mPoint1X, mPoint1Y, mPoint2X, mPoint2Y);
- fillHandles(canvas, mPoint1X, mPoint1Y, mPoint2X, mPoint2Y);
- paintPoint(canvas, mPoint2X, mPoint2Y);
- paintPoint(canvas, mPoint1X, mPoint1Y);
- paintPoint(canvas, (mPoint1X + mPoint2X) / 2, (mPoint1Y + mPoint2Y) / 2);
- }
-
- public boolean isUndefined() {
- return Float.isNaN(mPoint1X);
- }
-
- public void setShowReshapeHandles(boolean showReshapeHandles) {
- this.mShowReshapeHandles = showReshapeHandles;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageCrop.java b/src/com/android/gallery3d/filtershow/imageshow/ImageCrop.java
deleted file mode 100644
index 7fee03188..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/ImageCrop.java
+++ /dev/null
@@ -1,307 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.RectF;
-import android.graphics.drawable.Drawable;
-import android.util.AttributeSet;
-import android.util.Log;
-import android.view.MotionEvent;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.crop.CropDrawingUtils;
-import com.android.gallery3d.filtershow.crop.CropMath;
-import com.android.gallery3d.filtershow.crop.CropObject;
-import com.android.gallery3d.filtershow.editors.EditorCrop;
-import com.android.gallery3d.filtershow.filters.FilterCropRepresentation;
-import com.android.gallery3d.filtershow.imageshow.GeometryMathUtils.GeometryHolder;
-
-public class ImageCrop extends ImageShow {
- private static final String TAG = ImageCrop.class.getSimpleName();
- private RectF mImageBounds = new RectF();
- private RectF mScreenCropBounds = new RectF();
- private Paint mPaint = new Paint();
- private CropObject mCropObj = null;
- private GeometryHolder mGeometry = new GeometryHolder();
- private GeometryHolder mUpdateHolder = new GeometryHolder();
- private Drawable mCropIndicator;
- private int mIndicatorSize;
- private boolean mMovingBlock = false;
- private Matrix mDisplayMatrix = null;
- private Matrix mDisplayCropMatrix = null;
- private Matrix mDisplayMatrixInverse = null;
- private float mPrevX = 0;
- private float mPrevY = 0;
- private int mMinSideSize = 90;
- private int mTouchTolerance = 40;
- private enum Mode {
- NONE, MOVE
- }
- private Mode mState = Mode.NONE;
- private boolean mValidDraw = false;
- FilterCropRepresentation mLocalRep = new FilterCropRepresentation();
- EditorCrop mEditorCrop;
-
- public ImageCrop(Context context) {
- super(context);
- setup(context);
- }
-
- public ImageCrop(Context context, AttributeSet attrs) {
- super(context, attrs);
- setup(context);
- }
-
- public ImageCrop(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- setup(context);
- }
-
- private void setup(Context context) {
- Resources rsc = context.getResources();
- mCropIndicator = rsc.getDrawable(R.drawable.camera_crop);
- mIndicatorSize = (int) rsc.getDimension(R.dimen.crop_indicator_size);
- mMinSideSize = (int) rsc.getDimension(R.dimen.crop_min_side);
- mTouchTolerance = (int) rsc.getDimension(R.dimen.crop_touch_tolerance);
- }
-
- public void setFilterCropRepresentation(FilterCropRepresentation crop) {
- mLocalRep = (crop == null) ? new FilterCropRepresentation() : crop;
- GeometryMathUtils.initializeHolder(mUpdateHolder, mLocalRep);
- mValidDraw = true;
- }
-
- public FilterCropRepresentation getFinalRepresentation() {
- return mLocalRep;
- }
-
- private void internallyUpdateLocalRep(RectF crop, RectF image) {
- FilterCropRepresentation
- .findNormalizedCrop(crop, (int) image.width(), (int) image.height());
- mGeometry.crop.set(crop);
- mUpdateHolder.set(mGeometry);
- mLocalRep.setCrop(crop);
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- float x = event.getX();
- float y = event.getY();
- if (mDisplayMatrix == null || mDisplayMatrixInverse == null) {
- return true;
- }
- float[] touchPoint = {
- x, y
- };
- mDisplayMatrixInverse.mapPoints(touchPoint);
- x = touchPoint[0];
- y = touchPoint[1];
- switch (event.getActionMasked()) {
- case (MotionEvent.ACTION_DOWN):
- if (mState == Mode.NONE) {
- if (!mCropObj.selectEdge(x, y)) {
- mMovingBlock = mCropObj.selectEdge(CropObject.MOVE_BLOCK);
- }
- mPrevX = x;
- mPrevY = y;
- mState = Mode.MOVE;
- }
- break;
- case (MotionEvent.ACTION_UP):
- if (mState == Mode.MOVE) {
- mCropObj.selectEdge(CropObject.MOVE_NONE);
- mMovingBlock = false;
- mPrevX = x;
- mPrevY = y;
- mState = Mode.NONE;
- internallyUpdateLocalRep(mCropObj.getInnerBounds(), mCropObj.getOuterBounds());
- }
- break;
- case (MotionEvent.ACTION_MOVE):
- if (mState == Mode.MOVE) {
- float dx = x - mPrevX;
- float dy = y - mPrevY;
- mCropObj.moveCurrentSelection(dx, dy);
- mPrevX = x;
- mPrevY = y;
- }
- break;
- default:
- break;
- }
- invalidate();
- return true;
- }
-
- private void clearDisplay() {
- mDisplayMatrix = null;
- mDisplayMatrixInverse = null;
- invalidate();
- }
-
- public void applyFreeAspect() {
- mCropObj.unsetAspectRatio();
- invalidate();
- }
-
- public void applyOriginalAspect() {
- RectF outer = mCropObj.getOuterBounds();
- float w = outer.width();
- float h = outer.height();
- if (w > 0 && h > 0) {
- applyAspect(w, h);
- mCropObj.resetBoundsTo(outer, outer);
- internallyUpdateLocalRep(mCropObj.getInnerBounds(), mCropObj.getOuterBounds());
- } else {
- Log.w(TAG, "failed to set aspect ratio original");
- }
- invalidate();
- }
-
- public void applyAspect(float x, float y) {
- if (x <= 0 || y <= 0) {
- throw new IllegalArgumentException("Bad arguments to applyAspect");
- }
- // If we are rotated by 90 degrees from horizontal, swap x and y
- if (GeometryMathUtils.needsDimensionSwap(mGeometry.rotation)) {
- float tmp = x;
- x = y;
- y = tmp;
- }
- if (!mCropObj.setInnerAspectRatio(x, y)) {
- Log.w(TAG, "failed to set aspect ratio");
- }
- internallyUpdateLocalRep(mCropObj.getInnerBounds(), mCropObj.getOuterBounds());
- invalidate();
- }
-
- /**
- * Rotates first d bits in integer x to the left some number of times.
- */
- private int bitCycleLeft(int x, int times, int d) {
- int mask = (1 << d) - 1;
- int mout = x & mask;
- times %= d;
- int hi = mout >> (d - times);
- int low = (mout << times) & mask;
- int ret = x & ~mask;
- ret |= low;
- ret |= hi;
- return ret;
- }
-
- /**
- * Find the selected edge or corner in screen coordinates.
- */
- private int decode(int movingEdges, float rotation) {
- int rot = CropMath.constrainedRotation(rotation);
- switch (rot) {
- case 90:
- return bitCycleLeft(movingEdges, 1, 4);
- case 180:
- return bitCycleLeft(movingEdges, 2, 4);
- case 270:
- return bitCycleLeft(movingEdges, 3, 4);
- default:
- return movingEdges;
- }
- }
-
- private void forceStateConsistency() {
- MasterImage master = MasterImage.getImage();
- Bitmap image = master.getFiltersOnlyImage();
- int width = image.getWidth();
- int height = image.getHeight();
- if (mCropObj == null || !mUpdateHolder.equals(mGeometry)
- || mImageBounds.width() != width || mImageBounds.height() != height
- || !mLocalRep.getCrop().equals(mUpdateHolder.crop)) {
- mImageBounds.set(0, 0, width, height);
- mGeometry.set(mUpdateHolder);
- mLocalRep.setCrop(mUpdateHolder.crop);
- RectF scaledCrop = new RectF(mUpdateHolder.crop);
- FilterCropRepresentation.findScaledCrop(scaledCrop, width, height);
- mCropObj = new CropObject(mImageBounds, scaledCrop, (int) mUpdateHolder.straighten);
- mState = Mode.NONE;
- clearDisplay();
- }
- }
-
- @Override
- protected void onSizeChanged(int w, int h, int oldw, int oldh) {
- super.onSizeChanged(w, h, oldw, oldh);
- clearDisplay();
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- Bitmap bitmap = MasterImage.getImage().getFiltersOnlyImage();
- if (!mValidDraw || bitmap == null) {
- return;
- }
- forceStateConsistency();
- mImageBounds.set(0, 0, bitmap.getWidth(), bitmap.getHeight());
- // If display matrix doesn't exist, create it and its dependencies
- if (mDisplayCropMatrix == null || mDisplayMatrix == null || mDisplayMatrixInverse == null) {
- mDisplayMatrix = GeometryMathUtils.getFullGeometryToScreenMatrix(mGeometry,
- bitmap.getWidth(), bitmap.getHeight(), canvas.getWidth(), canvas.getHeight());
- float straighten = mGeometry.straighten;
- mGeometry.straighten = 0;
- mDisplayCropMatrix = GeometryMathUtils.getFullGeometryToScreenMatrix(mGeometry,
- bitmap.getWidth(), bitmap.getHeight(), canvas.getWidth(), canvas.getHeight());
- mGeometry.straighten = straighten;
- mDisplayMatrixInverse = new Matrix();
- mDisplayMatrixInverse.reset();
- if (!mDisplayCropMatrix.invert(mDisplayMatrixInverse)) {
- Log.w(TAG, "could not invert display matrix");
- mDisplayMatrixInverse = null;
- return;
- }
- // Scale min side and tolerance by display matrix scale factor
- mCropObj.setMinInnerSideSize(mDisplayMatrixInverse.mapRadius(mMinSideSize));
- mCropObj.setTouchTolerance(mDisplayMatrixInverse.mapRadius(mTouchTolerance));
- }
- // Draw actual bitmap
- mPaint.reset();
- mPaint.setAntiAlias(true);
- mPaint.setFilterBitmap(true);
- canvas.drawBitmap(bitmap, mDisplayMatrix, mPaint);
- mCropObj.getInnerBounds(mScreenCropBounds);
- RectF outer = mCropObj.getOuterBounds();
- FilterCropRepresentation.findNormalizedCrop(mScreenCropBounds, (int) outer.width(),
- (int) outer.height());
- FilterCropRepresentation.findScaledCrop(mScreenCropBounds, bitmap.getWidth(),
- bitmap.getHeight());
- if (mDisplayCropMatrix.mapRect(mScreenCropBounds)) {
- // Draw crop rect and markers
- CropDrawingUtils.drawCropRect(canvas, mScreenCropBounds);
- CropDrawingUtils.drawRuleOfThird(canvas, mScreenCropBounds);
- CropDrawingUtils.drawIndicators(canvas, mCropIndicator, mIndicatorSize,
- mScreenCropBounds, mCropObj.isFixedAspect(),
- decode(mCropObj.getSelectState(), mGeometry.rotation.value()));
- }
- }
-
- public void setEditor(EditorCrop editorCrop) {
- mEditorCrop = editorCrop;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageCurves.java b/src/com/android/gallery3d/filtershow/imageshow/ImageCurves.java
deleted file mode 100644
index 82c4b2fc7..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/ImageCurves.java
+++ /dev/null
@@ -1,445 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.Path;
-import android.graphics.PorterDuff;
-import android.graphics.PorterDuffXfermode;
-import android.os.AsyncTask;
-import android.util.AttributeSet;
-import android.view.MenuItem;
-import android.view.MotionEvent;
-import android.view.View;
-import android.widget.Button;
-import android.widget.LinearLayout;
-import android.widget.PopupMenu;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.Editor;
-import com.android.gallery3d.filtershow.editors.EditorCurves;
-import com.android.gallery3d.filtershow.filters.FilterCurvesRepresentation;
-import com.android.gallery3d.filtershow.filters.FiltersManager;
-import com.android.gallery3d.filtershow.filters.ImageFilterCurves;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-
-import java.util.HashMap;
-
-public class ImageCurves extends ImageShow {
-
- private static final String LOGTAG = "ImageCurves";
- Paint gPaint = new Paint();
- Path gPathSpline = new Path();
- HashMap<Integer, String> mIdStrLut;
-
- private int mCurrentCurveIndex = Spline.RGB;
- private boolean mDidAddPoint = false;
- private boolean mDidDelete = false;
- private ControlPoint mCurrentControlPoint = null;
- private int mCurrentPick = -1;
- private ImagePreset mLastPreset = null;
- int[] redHistogram = new int[256];
- int[] greenHistogram = new int[256];
- int[] blueHistogram = new int[256];
- Path gHistoPath = new Path();
-
- boolean mDoingTouchMove = false;
- private EditorCurves mEditorCurves;
- private FilterCurvesRepresentation mFilterCurvesRepresentation;
-
- public ImageCurves(Context context) {
- super(context);
- setLayerType(LAYER_TYPE_SOFTWARE, gPaint);
- resetCurve();
- }
-
- public ImageCurves(Context context, AttributeSet attrs) {
- super(context, attrs);
- setLayerType(LAYER_TYPE_SOFTWARE, gPaint);
- resetCurve();
- }
-
- @Override
- protected boolean enableComparison() {
- return false;
- }
-
- @Override
- public boolean useUtilityPanel() {
- return true;
- }
-
- private void showPopupMenu(LinearLayout accessoryViewList) {
- final Button button = (Button) accessoryViewList.findViewById(
- R.id.applyEffect);
- if (button == null) {
- return;
- }
- if (mIdStrLut == null){
- mIdStrLut = new HashMap<Integer, String>();
- mIdStrLut.put(R.id.curve_menu_rgb,
- getContext().getString(R.string.curves_channel_rgb));
- mIdStrLut.put(R.id.curve_menu_red,
- getContext().getString(R.string.curves_channel_red));
- mIdStrLut.put(R.id.curve_menu_green,
- getContext().getString(R.string.curves_channel_green));
- mIdStrLut.put(R.id.curve_menu_blue,
- getContext().getString(R.string.curves_channel_blue));
- }
- PopupMenu popupMenu = new PopupMenu(getActivity(), button);
- popupMenu.getMenuInflater().inflate(R.menu.filtershow_menu_curves, popupMenu.getMenu());
- popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() {
- @Override
- public boolean onMenuItemClick(MenuItem item) {
- setChannel(item.getItemId());
- button.setText(mIdStrLut.get(item.getItemId()));
- return true;
- }
- });
- Editor.hackFixStrings(popupMenu.getMenu());
- popupMenu.show();
- }
-
- @Override
- public void openUtilityPanel(final LinearLayout accessoryViewList) {
- Context context = accessoryViewList.getContext();
- Button view = (Button) accessoryViewList.findViewById(R.id.applyEffect);
- view.setText(context.getString(R.string.curves_channel_rgb));
- view.setVisibility(View.VISIBLE);
-
- view.setOnClickListener(new OnClickListener() {
- @Override
- public void onClick(View arg0) {
- showPopupMenu(accessoryViewList);
- }
- });
-
- if (view != null) {
- view.setVisibility(View.VISIBLE);
- }
- }
-
- public void nextChannel() {
- mCurrentCurveIndex = ((mCurrentCurveIndex + 1) % 4);
- invalidate();
- }
-
- private ImageFilterCurves curves() {
- String filterName = getFilterName();
- ImagePreset p = getImagePreset();
- if (p != null) {
- return (ImageFilterCurves) FiltersManager.getManager().getFilter(ImageFilterCurves.class);
- }
- return null;
- }
-
- private Spline getSpline(int index) {
- return mFilterCurvesRepresentation.getSpline(index);
- }
-
- @Override
- public void resetParameter() {
- super.resetParameter();
- resetCurve();
- mLastPreset = null;
- invalidate();
- }
-
- public void resetCurve() {
- if (mFilterCurvesRepresentation != null) {
- mFilterCurvesRepresentation.reset();
- updateCachedImage();
- }
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- super.onDraw(canvas);
- if (mFilterCurvesRepresentation == null) {
- return;
- }
-
- gPaint.setAntiAlias(true);
-
- if (getImagePreset() != mLastPreset && getFilteredImage() != null) {
- new ComputeHistogramTask().execute(getFilteredImage());
- mLastPreset = getImagePreset();
- }
-
- if (curves() == null) {
- return;
- }
-
- if (mCurrentCurveIndex == Spline.RGB || mCurrentCurveIndex == Spline.RED) {
- drawHistogram(canvas, redHistogram, Color.RED, PorterDuff.Mode.SCREEN);
- }
- if (mCurrentCurveIndex == Spline.RGB || mCurrentCurveIndex == Spline.GREEN) {
- drawHistogram(canvas, greenHistogram, Color.GREEN, PorterDuff.Mode.SCREEN);
- }
- if (mCurrentCurveIndex == Spline.RGB || mCurrentCurveIndex == Spline.BLUE) {
- drawHistogram(canvas, blueHistogram, Color.BLUE, PorterDuff.Mode.SCREEN);
- }
- // We only display the other channels curves when showing the RGB curve
- if (mCurrentCurveIndex == Spline.RGB) {
- for (int i = 0; i < 4; i++) {
- Spline spline = getSpline(i);
- if (i != mCurrentCurveIndex && !spline.isOriginal()) {
- // And we only display a curve if it has more than two
- // points
- spline.draw(canvas, Spline.colorForCurve(i), getWidth(),
- getHeight(), false, mDoingTouchMove);
- }
- }
- }
- // ...but we always display the current curve.
- getSpline(mCurrentCurveIndex)
- .draw(canvas, Spline.colorForCurve(mCurrentCurveIndex), getWidth(), getHeight(),
- true, mDoingTouchMove);
-
- }
-
- private int pickControlPoint(float x, float y) {
- int pick = 0;
- Spline spline = getSpline(mCurrentCurveIndex);
- float px = spline.getPoint(0).x;
- float py = spline.getPoint(0).y;
- double delta = Math.sqrt((px - x) * (px - x) + (py - y) * (py - y));
- for (int i = 1; i < spline.getNbPoints(); i++) {
- px = spline.getPoint(i).x;
- py = spline.getPoint(i).y;
- double currentDelta = Math.sqrt((px - x) * (px - x) + (py - y)
- * (py - y));
- if (currentDelta < delta) {
- delta = currentDelta;
- pick = i;
- }
- }
-
- if (!mDidAddPoint && (delta * getWidth() > 100)
- && (spline.getNbPoints() < 10)) {
- return -1;
- }
-
- return pick;
- }
-
- private String getFilterName() {
- return "Curves";
- }
-
- @Override
- public synchronized boolean onTouchEvent(MotionEvent e) {
- if (e.getPointerCount() != 1) {
- return true;
- }
-
- if (didFinishScalingOperation()) {
- return true;
- }
-
- float margin = Spline.curveHandleSize() / 2;
- float posX = e.getX();
- if (posX < margin) {
- posX = margin;
- }
- float posY = e.getY();
- if (posY < margin) {
- posY = margin;
- }
- if (posX > getWidth() - margin) {
- posX = getWidth() - margin;
- }
- if (posY > getHeight() - margin) {
- posY = getHeight() - margin;
- }
- posX = (posX - margin) / (getWidth() - 2 * margin);
- posY = (posY - margin) / (getHeight() - 2 * margin);
-
- if (e.getActionMasked() == MotionEvent.ACTION_UP) {
- mCurrentControlPoint = null;
- mCurrentPick = -1;
- updateCachedImage();
- mDidAddPoint = false;
- if (mDidDelete) {
- mDidDelete = false;
- }
- mDoingTouchMove = false;
- return true;
- }
-
- if (mDidDelete) {
- return true;
- }
-
- if (curves() == null) {
- return true;
- }
-
- if (e.getActionMasked() == MotionEvent.ACTION_MOVE) {
- mDoingTouchMove = true;
- Spline spline = getSpline(mCurrentCurveIndex);
- int pick = mCurrentPick;
- if (mCurrentControlPoint == null) {
- pick = pickControlPoint(posX, posY);
- if (pick == -1) {
- mCurrentControlPoint = new ControlPoint(posX, posY);
- pick = spline.addPoint(mCurrentControlPoint);
- mDidAddPoint = true;
- } else {
- mCurrentControlPoint = spline.getPoint(pick);
- }
- mCurrentPick = pick;
- }
-
- if (spline.isPointContained(posX, pick)) {
- spline.movePoint(pick, posX, posY);
- } else if (pick != -1 && spline.getNbPoints() > 2) {
- spline.deletePoint(pick);
- mDidDelete = true;
- }
- updateCachedImage();
- invalidate();
- }
- return true;
- }
-
- public synchronized void updateCachedImage() {
- if (getImagePreset() != null) {
- resetImageCaches(this);
- if (mEditorCurves != null) {
- mEditorCurves.commitLocalRepresentation();
- }
- invalidate();
- }
- }
-
- class ComputeHistogramTask extends AsyncTask<Bitmap, Void, int[]> {
- @Override
- protected int[] doInBackground(Bitmap... params) {
- int[] histo = new int[256 * 3];
- Bitmap bitmap = params[0];
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
- int[] pixels = new int[w * h];
- bitmap.getPixels(pixels, 0, w, 0, 0, w, h);
- for (int i = 0; i < w; i++) {
- for (int j = 0; j < h; j++) {
- int index = j * w + i;
- int r = Color.red(pixels[index]);
- int g = Color.green(pixels[index]);
- int b = Color.blue(pixels[index]);
- histo[r]++;
- histo[256 + g]++;
- histo[512 + b]++;
- }
- }
- return histo;
- }
-
- @Override
- protected void onPostExecute(int[] result) {
- System.arraycopy(result, 0, redHistogram, 0, 256);
- System.arraycopy(result, 256, greenHistogram, 0, 256);
- System.arraycopy(result, 512, blueHistogram, 0, 256);
- invalidate();
- }
- }
-
- private void drawHistogram(Canvas canvas, int[] histogram, int color, PorterDuff.Mode mode) {
- int max = 0;
- for (int i = 0; i < histogram.length; i++) {
- if (histogram[i] > max) {
- max = histogram[i];
- }
- }
- float w = getWidth() - Spline.curveHandleSize();
- float h = getHeight() - Spline.curveHandleSize() / 2.0f;
- float dx = Spline.curveHandleSize() / 2.0f;
- float wl = w / histogram.length;
- float wh = (0.3f * h) / max;
- Paint paint = new Paint();
- paint.setARGB(100, 255, 255, 255);
- paint.setStrokeWidth((int) Math.ceil(wl));
-
- Paint paint2 = new Paint();
- paint2.setColor(color);
- paint2.setStrokeWidth(6);
- paint2.setXfermode(new PorterDuffXfermode(mode));
- gHistoPath.reset();
- gHistoPath.moveTo(dx, h);
- boolean firstPointEncountered = false;
- float prev = 0;
- float last = 0;
- for (int i = 0; i < histogram.length; i++) {
- float x = i * wl + dx;
- float l = histogram[i] * wh;
- if (l != 0) {
- float v = h - (l + prev) / 2.0f;
- if (!firstPointEncountered) {
- gHistoPath.lineTo(x, h);
- firstPointEncountered = true;
- }
- gHistoPath.lineTo(x, v);
- prev = l;
- last = x;
- }
- }
- gHistoPath.lineTo(last, h);
- gHistoPath.lineTo(w, h);
- gHistoPath.close();
- canvas.drawPath(gHistoPath, paint2);
- paint2.setStrokeWidth(2);
- paint2.setStyle(Paint.Style.STROKE);
- paint2.setARGB(255, 200, 200, 200);
- canvas.drawPath(gHistoPath, paint2);
- }
-
- public void setChannel(int itemId) {
- switch (itemId) {
- case R.id.curve_menu_rgb: {
- mCurrentCurveIndex = Spline.RGB;
- break;
- }
- case R.id.curve_menu_red: {
- mCurrentCurveIndex = Spline.RED;
- break;
- }
- case R.id.curve_menu_green: {
- mCurrentCurveIndex = Spline.GREEN;
- break;
- }
- case R.id.curve_menu_blue: {
- mCurrentCurveIndex = Spline.BLUE;
- break;
- }
- }
- mEditorCurves.commitLocalRepresentation();
- invalidate();
- }
-
- public void setEditor(EditorCurves editorCurves) {
- mEditorCurves = editorCurves;
- }
-
- public void setFilterDrawRepresentation(FilterCurvesRepresentation drawRep) {
- mFilterCurvesRepresentation = drawRep;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageDraw.java b/src/com/android/gallery3d/filtershow/imageshow/ImageDraw.java
deleted file mode 100644
index 9722034e0..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/ImageDraw.java
+++ /dev/null
@@ -1,139 +0,0 @@
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Matrix;
-import android.graphics.drawable.Drawable;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-
-import com.android.gallery3d.filtershow.editors.EditorDraw;
-import com.android.gallery3d.filtershow.filters.FilterDrawRepresentation;
-import com.android.gallery3d.filtershow.filters.ImageFilterDraw;
-
-public class ImageDraw extends ImageShow {
-
- private static final String LOGTAG = "ImageDraw";
- private int mCurrentColor = Color.RED;
- final static float INITAL_STROKE_RADIUS = 40;
- private float mCurrentSize = INITAL_STROKE_RADIUS;
- private byte mType = 0;
- private FilterDrawRepresentation mFRep;
- private EditorDraw mEditorDraw;
-
- public ImageDraw(Context context, AttributeSet attrs) {
- super(context, attrs);
- resetParameter();
- }
-
- public ImageDraw(Context context) {
- super(context);
- resetParameter();
- }
-
- public void setEditor(EditorDraw editorDraw) {
- mEditorDraw = editorDraw;
- }
- public void setFilterDrawRepresentation(FilterDrawRepresentation fr) {
- mFRep = fr;
- }
-
- public Drawable getIcon(Context context) {
-
- return null;
- }
-
- @Override
- public void resetParameter() {
- if (mFRep != null) {
- mFRep.clear();
- }
- }
-
- public void setColor(int color) {
- mCurrentColor = color;
- }
-
- public void setSize(int size) {
- mCurrentSize = size;
- }
-
- public void setStyle(byte style) {
- mType = (byte) (style % ImageFilterDraw.NUMBER_OF_STYLES);
- }
-
- public int getStyle() {
- return mType;
- }
-
- public int getSize() {
- return (int) mCurrentSize;
- }
-
- float[] mTmpPoint = new float[2]; // so we do not malloc
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- if (event.getPointerCount() > 1) {
- boolean ret = super.onTouchEvent(event);
- if (mFRep.getCurrentDrawing() != null) {
- mFRep.clearCurrentSection();
- mEditorDraw.commitLocalRepresentation();
- }
- return ret;
- }
- if (event.getAction() != MotionEvent.ACTION_DOWN) {
- if (mFRep.getCurrentDrawing() == null) {
- return super.onTouchEvent(event);
- }
- }
-
- if (event.getAction() == MotionEvent.ACTION_DOWN) {
- calcScreenMapping();
- mTmpPoint[0] = event.getX();
- mTmpPoint[1] = event.getY();
- mToOrig.mapPoints(mTmpPoint);
- mFRep.startNewSection(mType, mCurrentColor, mCurrentSize, mTmpPoint[0], mTmpPoint[1]);
- }
-
- if (event.getAction() == MotionEvent.ACTION_MOVE) {
-
- int historySize = event.getHistorySize();
- for (int h = 0; h < historySize; h++) {
- int p = 0;
- {
- mTmpPoint[0] = event.getHistoricalX(p, h);
- mTmpPoint[1] = event.getHistoricalY(p, h);
- mToOrig.mapPoints(mTmpPoint);
- mFRep.addPoint(mTmpPoint[0], mTmpPoint[1]);
- }
- }
- }
-
- if (event.getAction() == MotionEvent.ACTION_UP) {
- mTmpPoint[0] = event.getX();
- mTmpPoint[1] = event.getY();
- mToOrig.mapPoints(mTmpPoint);
- mFRep.endSection(mTmpPoint[0], mTmpPoint[1]);
- }
- mEditorDraw.commitLocalRepresentation();
- invalidate();
- return true;
- }
-
- Matrix mRotateToScreen = new Matrix();
- Matrix mToOrig;
- private void calcScreenMapping() {
- mToOrig = getScreenToImageMatrix(true);
- mToOrig.invert(mRotateToScreen);
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- super.onDraw(canvas);
- calcScreenMapping();
-
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageGrad.java b/src/com/android/gallery3d/filtershow/imageshow/ImageGrad.java
deleted file mode 100644
index b55cc2bc4..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/ImageGrad.java
+++ /dev/null
@@ -1,215 +0,0 @@
-package com.android.gallery3d.filtershow.imageshow;
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.Canvas;
-import android.graphics.Matrix;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.editors.EditorGrad;
-import com.android.gallery3d.filtershow.filters.FilterGradRepresentation;
-
-public class ImageGrad extends ImageShow {
- private static final String LOGTAG = "ImageGrad";
- private FilterGradRepresentation mGradRep;
- private EditorGrad mEditorGrad;
- private float mMinTouchDist;
- private int mActiveHandle = -1;
- private GradControl mEllipse;
-
- Matrix mToScr = new Matrix();
- float[] mPointsX = new float[FilterGradRepresentation.MAX_POINTS];
- float[] mPointsY = new float[FilterGradRepresentation.MAX_POINTS];
-
- public ImageGrad(Context context) {
- super(context);
- Resources res = context.getResources();
- mMinTouchDist = res.getDimensionPixelSize(R.dimen.gradcontrol_min_touch_dist);
- mEllipse = new GradControl(context);
- mEllipse.setShowReshapeHandles(false);
- }
-
- public ImageGrad(Context context, AttributeSet attrs) {
- super(context, attrs);
- Resources res = context.getResources();
- mMinTouchDist = res.getDimensionPixelSize(R.dimen.gradcontrol_min_touch_dist);
- mEllipse = new GradControl(context);
- mEllipse.setShowReshapeHandles(false);
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- int mask = event.getActionMasked();
-
- if (mActiveHandle == -1) {
- if (MotionEvent.ACTION_DOWN != mask) {
- return super.onTouchEvent(event);
- }
- if (event.getPointerCount() == 1) {
- mActiveHandle = mEllipse.getCloseHandle(event.getX(), event.getY());
- if (mActiveHandle == -1) {
- float x = event.getX();
- float y = event.getY();
- float min_d = Float.MAX_VALUE;
- int pos = -1;
- for (int i = 0; i < mPointsX.length; i++) {
- if (mPointsX[i] == -1) {
- continue;
- }
- float d = (float) Math.hypot(x - mPointsX[i], y - mPointsY[i]);
- if ( min_d > d) {
- min_d = d;
- pos = i;
- }
- }
- if (min_d > mMinTouchDist){
- pos = -1;
- }
-
- if (pos != -1) {
- mGradRep.setSelectedPoint(pos);
- resetImageCaches(this);
- mEditorGrad.updateSeekBar(mGradRep);
- mEditorGrad.commitLocalRepresentation();
- invalidate();
- }
- }
- }
- if (mActiveHandle == -1) {
- return super.onTouchEvent(event);
- }
- } else {
- switch (mask) {
- case MotionEvent.ACTION_UP: {
-
- mActiveHandle = -1;
- break;
- }
- case MotionEvent.ACTION_DOWN: {
- break;
- }
- }
- }
- float x = event.getX();
- float y = event.getY();
-
- mEllipse.setScrImageInfo(getScreenToImageMatrix(true),
- MasterImage.getImage().getOriginalBounds());
-
- switch (mask) {
- case (MotionEvent.ACTION_DOWN): {
- mEllipse.actionDown(x, y, mGradRep);
- break;
- }
- case (MotionEvent.ACTION_UP):
- case (MotionEvent.ACTION_MOVE): {
- mEllipse.actionMove(mActiveHandle, x, y, mGradRep);
- setRepresentation(mGradRep);
- break;
- }
- }
- invalidate();
- mEditorGrad.commitLocalRepresentation();
- return true;
- }
-
- public void setRepresentation(FilterGradRepresentation pointRep) {
- mGradRep = pointRep;
- Matrix toImg = getScreenToImageMatrix(false);
-
- toImg.invert(mToScr);
-
- float[] c1 = new float[] { mGradRep.getPoint1X(), mGradRep.getPoint1Y() };
- float[] c2 = new float[] { mGradRep.getPoint2X(), mGradRep.getPoint2Y() };
-
- if (c1[0] == -1) {
- float cx = MasterImage.getImage().getOriginalBounds().width() / 2;
- float cy = MasterImage.getImage().getOriginalBounds().height() / 2;
- float rx = Math.min(cx, cy) * .4f;
-
- mGradRep.setPoint1(cx, cy-rx);
- mGradRep.setPoint2(cx, cy+rx);
- c1[0] = cx;
- c1[1] = cy-rx;
- mToScr.mapPoints(c1);
- if (getWidth() != 0) {
- mEllipse.setPoint1(c1[0], c1[1]);
- c2[0] = cx;
- c2[1] = cy+rx;
- mToScr.mapPoints(c2);
- mEllipse.setPoint2(c2[0], c2[1]);
- }
- mEditorGrad.commitLocalRepresentation();
- } else {
- mToScr.mapPoints(c1);
- mToScr.mapPoints(c2);
- mEllipse.setPoint1(c1[0], c1[1]);
- mEllipse.setPoint2(c2[0], c2[1]);
- }
- }
-
- public void drawOtherPoints(Canvas canvas) {
- computCenterLocations();
- for (int i = 0; i < mPointsX.length; i++) {
- if (mPointsX[i] != -1) {
- mEllipse.paintGrayPoint(canvas, mPointsX[i], mPointsY[i]);
- }
- }
- }
-
- public void computCenterLocations() {
- int x1[] = mGradRep.getXPos1();
- int y1[] = mGradRep.getYPos1();
- int x2[] = mGradRep.getXPos2();
- int y2[] = mGradRep.getYPos2();
- int selected = mGradRep.getSelectedPoint();
- boolean m[] = mGradRep.getMask();
- float[] c = new float[2];
- for (int i = 0; i < m.length; i++) {
- if (selected == i || !m[i]) {
- mPointsX[i] = -1;
- continue;
- }
-
- c[0] = (x1[i]+x2[i])/2;
- c[1] = (y1[i]+y2[i])/2;
- mToScr.mapPoints(c);
-
- mPointsX[i] = c[0];
- mPointsY[i] = c[1];
- }
- }
-
- public void setEditor(EditorGrad editorGrad) {
- mEditorGrad = editorGrad;
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- super.onDraw(canvas);
- if (mGradRep == null) {
- return;
- }
- setRepresentation(mGradRep);
- mEllipse.draw(canvas);
- drawOtherPoints(canvas);
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageMirror.java b/src/com/android/gallery3d/filtershow/imageshow/ImageMirror.java
deleted file mode 100644
index 26c49b1a8..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/ImageMirror.java
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-
-import com.android.gallery3d.filtershow.editors.EditorMirror;
-import com.android.gallery3d.filtershow.filters.FilterMirrorRepresentation;
-import com.android.gallery3d.filtershow.imageshow.GeometryMathUtils.GeometryHolder;
-
-public class ImageMirror extends ImageShow {
- private static final String TAG = ImageMirror.class.getSimpleName();
- private EditorMirror mEditorMirror;
- private FilterMirrorRepresentation mLocalRep = new FilterMirrorRepresentation();
- private GeometryHolder mDrawHolder = new GeometryHolder();
-
- public ImageMirror(Context context, AttributeSet attrs) {
- super(context, attrs);
- }
-
- public ImageMirror(Context context) {
- super(context);
- }
-
- public void setFilterMirrorRepresentation(FilterMirrorRepresentation rep) {
- mLocalRep = (rep == null) ? new FilterMirrorRepresentation() : rep;
- }
-
- public void flip() {
- mLocalRep.cycle();
- invalidate();
- }
-
- public FilterMirrorRepresentation getFinalRepresentation() {
- return mLocalRep;
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- // Treat event as handled.
- return true;
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- MasterImage master = MasterImage.getImage();
- Bitmap image = master.getFiltersOnlyImage();
- if (image == null) {
- return;
- }
- GeometryMathUtils.initializeHolder(mDrawHolder, mLocalRep);
- GeometryMathUtils.drawTransformedCropped(mDrawHolder, canvas, image, getWidth(),
- getHeight());
- }
-
- public void setEditor(EditorMirror editorFlip) {
- mEditorMirror = editorFlip;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImagePoint.java b/src/com/android/gallery3d/filtershow/imageshow/ImagePoint.java
deleted file mode 100644
index fd5714139..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/ImagePoint.java
+++ /dev/null
@@ -1,89 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.Paint.Style;
-import android.util.AttributeSet;
-
-import com.android.gallery3d.filtershow.editors.EditorRedEye;
-import com.android.gallery3d.filtershow.filters.FilterPoint;
-import com.android.gallery3d.filtershow.filters.FilterRedEyeRepresentation;
-import com.android.gallery3d.filtershow.filters.ImageFilterRedEye;
-
-public abstract class ImagePoint extends ImageShow {
-
- private static final String LOGTAG = "ImageRedEyes";
- protected EditorRedEye mEditorRedEye;
- protected FilterRedEyeRepresentation mRedEyeRep;
- protected static float mTouchPadding = 80;
-
- public static void setTouchPadding(float padding) {
- mTouchPadding = padding;
- }
-
- public ImagePoint(Context context, AttributeSet attrs) {
- super(context, attrs);
- }
-
- public ImagePoint(Context context) {
- super(context);
- }
-
- @Override
- public void resetParameter() {
- ImageFilterRedEye filter = (ImageFilterRedEye) getCurrentFilter();
- if (filter != null) {
- filter.clear();
- }
- invalidate();
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- super.onDraw(canvas);
- Paint paint = new Paint();
- paint.setStyle(Style.STROKE);
- paint.setColor(Color.RED);
- paint.setStrokeWidth(2);
-
- Matrix originalToScreen = getImageToScreenMatrix(false);
- Matrix originalRotateToScreen = getImageToScreenMatrix(true);
-
- if (mRedEyeRep != null) {
- for (FilterPoint candidate : mRedEyeRep.getCandidates()) {
- drawPoint(candidate, canvas, originalToScreen, originalRotateToScreen, paint);
- }
- }
- }
-
- protected abstract void drawPoint(
- FilterPoint candidate, Canvas canvas, Matrix originalToScreen,
- Matrix originalRotateToScreen, Paint paint);
-
- public void setEditor(EditorRedEye editorRedEye) {
- mEditorRedEye = editorRedEye;
- }
-
- public void setRepresentation(FilterRedEyeRepresentation redEyeRep) {
- mRedEyeRep = redEyeRep;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageRedEye.java b/src/com/android/gallery3d/filtershow/imageshow/ImageRedEye.java
deleted file mode 100644
index 40433a02e..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/ImageRedEye.java
+++ /dev/null
@@ -1,137 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.Paint.Style;
-import android.graphics.RectF;
-import android.view.MotionEvent;
-
-import com.android.gallery3d.filtershow.filters.FilterPoint;
-import com.android.gallery3d.filtershow.filters.RedEyeCandidate;
-
-public class ImageRedEye extends ImagePoint {
- private static final String LOGTAG = "ImageRedEyes";
- private RectF mCurrentRect = null;
-
- public ImageRedEye(Context context) {
- super(context);
- }
-
- @Override
- public void resetParameter() {
- super.resetParameter();
- invalidate();
- }
-
- @Override
-
- public boolean onTouchEvent(MotionEvent event) {
- super.onTouchEvent(event);
-
- if (event.getPointerCount() > 1) {
- return true;
- }
-
- if (didFinishScalingOperation()) {
- return true;
- }
-
- float ex = event.getX();
- float ey = event.getY();
-
- // let's transform (ex, ey) to displayed image coordinates
- if (event.getAction() == MotionEvent.ACTION_DOWN) {
- mCurrentRect = new RectF();
- mCurrentRect.left = ex - mTouchPadding;
- mCurrentRect.top = ey - mTouchPadding;
- }
- if (event.getAction() == MotionEvent.ACTION_MOVE) {
- mCurrentRect.right = ex + mTouchPadding;
- mCurrentRect.bottom = ey + mTouchPadding;
- }
- if (event.getAction() == MotionEvent.ACTION_UP) {
- if (mCurrentRect != null) {
- // transform to original coordinates
- Matrix originalNoRotateToScreen = getImageToScreenMatrix(false);
- Matrix originalToScreen = getImageToScreenMatrix(true);
- Matrix invert = new Matrix();
- originalToScreen.invert(invert);
- RectF r = new RectF(mCurrentRect);
- invert.mapRect(r);
- RectF r2 = new RectF(mCurrentRect);
- invert.reset();
- originalNoRotateToScreen.invert(invert);
- invert.mapRect(r2);
- mRedEyeRep.addRect(r, r2);
- this.resetImageCaches(this);
- }
- mCurrentRect = null;
- }
- mEditorRedEye.commitLocalRepresentation();
- invalidate();
- return true;
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- super.onDraw(canvas);
- Paint paint = new Paint();
- paint.setStyle(Style.STROKE);
- paint.setColor(Color.RED);
- paint.setStrokeWidth(2);
- if (mCurrentRect != null) {
- paint.setColor(Color.RED);
- RectF drawRect = new RectF(mCurrentRect);
- canvas.drawRect(drawRect, paint);
- }
- }
-
- @Override
- protected void drawPoint(FilterPoint point, Canvas canvas, Matrix originalToScreen,
- Matrix originalRotateToScreen, Paint paint) {
- RedEyeCandidate candidate = (RedEyeCandidate) point;
- RectF rect = candidate.getRect();
- RectF drawRect = new RectF();
- originalToScreen.mapRect(drawRect, rect);
- RectF fullRect = new RectF();
- originalRotateToScreen.mapRect(fullRect, rect);
- paint.setColor(Color.BLUE);
- canvas.drawRect(fullRect, paint);
- canvas.drawLine(fullRect.centerX(), fullRect.top,
- fullRect.centerX(), fullRect.bottom, paint);
- canvas.drawLine(fullRect.left, fullRect.centerY(),
- fullRect.right, fullRect.centerY(), paint);
- paint.setColor(Color.GREEN);
- float dw = drawRect.width();
- float dh = drawRect.height();
- float dx = fullRect.centerX() - dw / 2;
- float dy = fullRect.centerY() - dh / 2;
- drawRect.set(dx, dy, dx + dw, dy + dh);
- canvas.drawRect(drawRect, paint);
- canvas.drawLine(drawRect.centerX(), drawRect.top,
- drawRect.centerX(), drawRect.bottom, paint);
- canvas.drawLine(drawRect.left, drawRect.centerY(),
- drawRect.right, drawRect.centerY(), paint);
- canvas.drawCircle(drawRect.centerX(), drawRect.centerY(),
- mTouchPadding, paint);
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageRotate.java b/src/com/android/gallery3d/filtershow/imageshow/ImageRotate.java
deleted file mode 100644
index 5186c09d7..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/ImageRotate.java
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-
-import com.android.gallery3d.filtershow.editors.EditorRotate;
-import com.android.gallery3d.filtershow.filters.FilterRotateRepresentation;
-import com.android.gallery3d.filtershow.imageshow.GeometryMathUtils.GeometryHolder;
-
-public class ImageRotate extends ImageShow {
- private EditorRotate mEditorRotate;
- private static final String TAG = ImageRotate.class.getSimpleName();
- private FilterRotateRepresentation mLocalRep = new FilterRotateRepresentation();
- private GeometryHolder mDrawHolder = new GeometryHolder();
-
- public ImageRotate(Context context, AttributeSet attrs) {
- super(context, attrs);
- }
-
- public ImageRotate(Context context) {
- super(context);
- }
-
- public void setFilterRotateRepresentation(FilterRotateRepresentation rep) {
- mLocalRep = (rep == null) ? new FilterRotateRepresentation() : rep;
- }
-
- public void rotate() {
- mLocalRep.rotateCW();
- invalidate();
- }
-
- public FilterRotateRepresentation getFinalRepresentation() {
- return mLocalRep;
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- // Treat event as handled.
- return true;
- }
-
- public int getLocalValue() {
- return mLocalRep.getRotation().value();
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- MasterImage master = MasterImage.getImage();
- Bitmap image = master.getFiltersOnlyImage();
- if (image == null) {
- return;
- }
- GeometryMathUtils.initializeHolder(mDrawHolder, mLocalRep);
- GeometryMathUtils.drawTransformedCropped(mDrawHolder, canvas, image, canvas.getWidth(),
- canvas.getHeight());
- }
-
- public void setEditor(EditorRotate editorRotate) {
- mEditorRotate = editorRotate;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageShow.java b/src/com/android/gallery3d/filtershow/imageshow/ImageShow.java
deleted file mode 100644
index 6278b2ad4..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/ImageShow.java
+++ /dev/null
@@ -1,578 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.Point;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.util.AttributeSet;
-import android.view.GestureDetector;
-import android.view.GestureDetector.OnDoubleTapListener;
-import android.view.GestureDetector.OnGestureListener;
-import android.view.MotionEvent;
-import android.view.ScaleGestureDetector;
-import android.view.View;
-import android.widget.LinearLayout;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.filters.ImageFilter;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-import com.android.gallery3d.filtershow.tools.SaveImage;
-
-import java.io.File;
-
-public class ImageShow extends View implements OnGestureListener,
- ScaleGestureDetector.OnScaleGestureListener,
- OnDoubleTapListener {
-
- private static final String LOGTAG = "ImageShow";
- private static final boolean ENABLE_ZOOMED_COMPARISON = false;
-
- protected Paint mPaint = new Paint();
- protected int mTextSize;
- protected int mTextPadding;
-
- protected int mBackgroundColor;
-
- private GestureDetector mGestureDetector = null;
- private ScaleGestureDetector mScaleGestureDetector = null;
-
- protected Rect mImageBounds = new Rect();
- private boolean mOriginalDisabled = false;
- private boolean mTouchShowOriginal = false;
- private long mTouchShowOriginalDate = 0;
- private final long mTouchShowOriginalDelayMin = 200; // 200ms
- private int mShowOriginalDirection = 0;
- private static int UNVEIL_HORIZONTAL = 1;
- private static int UNVEIL_VERTICAL = 2;
-
- private Point mTouchDown = new Point();
- private Point mTouch = new Point();
- private boolean mFinishedScalingOperation = false;
-
- private int mOriginalTextMargin;
- private int mOriginalTextSize;
- private String mOriginalText;
- private boolean mZoomIn = false;
- Point mOriginalTranslation = new Point();
- float mOriginalScale;
- float mStartFocusX, mStartFocusY;
- private enum InteractionMode {
- NONE,
- SCALE,
- MOVE
- }
- InteractionMode mInteractionMode = InteractionMode.NONE;
-
- private FilterShowActivity mActivity = null;
-
- public FilterShowActivity getActivity() {
- return mActivity;
- }
-
- public boolean hasModifications() {
- return MasterImage.getImage().hasModifications();
- }
-
- public void resetParameter() {
- // TODO: implement reset
- }
-
- public void onNewValue(int parameter) {
- invalidate();
- }
-
- public ImageShow(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- setupImageShow(context);
- }
-
- public ImageShow(Context context, AttributeSet attrs) {
- super(context, attrs);
- setupImageShow(context);
-
- }
-
- public ImageShow(Context context) {
- super(context);
- setupImageShow(context);
- }
-
- private void setupImageShow(Context context) {
- Resources res = context.getResources();
- mTextSize = res.getDimensionPixelSize(R.dimen.photoeditor_text_size);
- mTextPadding = res.getDimensionPixelSize(R.dimen.photoeditor_text_padding);
- mOriginalTextMargin = res.getDimensionPixelSize(R.dimen.photoeditor_original_text_margin);
- mOriginalTextSize = res.getDimensionPixelSize(R.dimen.photoeditor_original_text_size);
- mBackgroundColor = res.getColor(R.color.background_screen);
- mOriginalText = res.getString(R.string.original_picture_text);
- setupGestureDetector(context);
- mActivity = (FilterShowActivity) context;
- MasterImage.getImage().addObserver(this);
- }
-
- public void setupGestureDetector(Context context) {
- mGestureDetector = new GestureDetector(context, this);
- mScaleGestureDetector = new ScaleGestureDetector(context, this);
- }
-
- @Override
- protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
- int parentWidth = MeasureSpec.getSize(widthMeasureSpec);
- int parentHeight = MeasureSpec.getSize(heightMeasureSpec);
- setMeasuredDimension(parentWidth, parentHeight);
- }
-
- public ImageFilter getCurrentFilter() {
- return MasterImage.getImage().getCurrentFilter();
- }
-
- /* consider moving the following 2 methods into a subclass */
- /**
- * This function calculates a Image to Screen Transformation matrix
- *
- * @param reflectRotation set true if you want the rotation encoded
- * @return Image to Screen transformation matrix
- */
- protected Matrix getImageToScreenMatrix(boolean reflectRotation) {
- MasterImage master = MasterImage.getImage();
- if (master.getOriginalBounds() == null) {
- return new Matrix();
- }
- Matrix m = GeometryMathUtils.getImageToScreenMatrix(master.getPreset().getGeometryFilters(),
- reflectRotation, master.getOriginalBounds(), getWidth(), getHeight());
- Point translate = master.getTranslation();
- float scaleFactor = master.getScaleFactor();
- m.postTranslate(translate.x, translate.y);
- m.postScale(scaleFactor, scaleFactor, getWidth() / 2.0f, getHeight() / 2.0f);
- return m;
- }
-
- /**
- * This function calculates a to Screen Image Transformation matrix
- *
- * @param reflectRotation set true if you want the rotation encoded
- * @return Screen to Image transformation matrix
- */
- protected Matrix getScreenToImageMatrix(boolean reflectRotation) {
- Matrix m = getImageToScreenMatrix(reflectRotation);
- Matrix invert = new Matrix();
- m.invert(invert);
- return invert;
- }
-
- public ImagePreset getImagePreset() {
- return MasterImage.getImage().getPreset();
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- MasterImage.getImage().setImageShowSize(getWidth(), getHeight());
-
- float cx = canvas.getWidth()/2.0f;
- float cy = canvas.getHeight()/2.0f;
- float scaleFactor = MasterImage.getImage().getScaleFactor();
- Point translation = MasterImage.getImage().getTranslation();
-
- Matrix scalingMatrix = new Matrix();
- scalingMatrix.postScale(scaleFactor, scaleFactor, cx, cy);
- scalingMatrix.preTranslate(translation.x, translation.y);
-
- RectF unscaledClipRect = new RectF(mImageBounds);
- scalingMatrix.mapRect(unscaledClipRect, unscaledClipRect);
-
- canvas.save();
-
- boolean enablePartialRendering = false;
-
- // For now, partial rendering is disabled for all filters,
- // so no need to clip.
- if (enablePartialRendering && !unscaledClipRect.isEmpty()) {
- canvas.clipRect(unscaledClipRect);
- }
-
- canvas.save();
- // TODO: center scale on gesture
- canvas.scale(scaleFactor, scaleFactor, cx, cy);
- canvas.translate(translation.x, translation.y);
- drawImage(canvas, getFilteredImage(), true);
- Bitmap highresPreview = MasterImage.getImage().getHighresImage();
- if (highresPreview != null) {
- drawImage(canvas, highresPreview, true);
- }
- canvas.restore();
-
- Bitmap partialPreview = MasterImage.getImage().getPartialImage();
- if (partialPreview != null) {
- Rect src = new Rect(0, 0, partialPreview.getWidth(), partialPreview.getHeight());
- Rect dest = new Rect(0, 0, getWidth(), getHeight());
- canvas.drawBitmap(partialPreview, src, dest, mPaint);
- }
-
- canvas.save();
- canvas.scale(scaleFactor, scaleFactor, cx, cy);
- canvas.translate(translation.x, translation.y);
- drawPartialImage(canvas, getGeometryOnlyImage());
- canvas.restore();
-
- canvas.restore();
- }
-
- public void resetImageCaches(ImageShow caller) {
- MasterImage.getImage().updatePresets(true);
- }
-
- public Bitmap getFiltersOnlyImage() {
- return MasterImage.getImage().getFiltersOnlyImage();
- }
-
- public Bitmap getGeometryOnlyImage() {
- return MasterImage.getImage().getGeometryOnlyImage();
- }
-
- public Bitmap getFilteredImage() {
- return MasterImage.getImage().getFilteredImage();
- }
-
- public void drawImage(Canvas canvas, Bitmap image, boolean updateBounds) {
- if (image != null) {
- Rect s = new Rect(0, 0, image.getWidth(),
- image.getHeight());
-
- float scale = GeometryMathUtils.scale(image.getWidth(), image.getHeight(), getWidth(),
- getHeight());
-
- float w = image.getWidth() * scale;
- float h = image.getHeight() * scale;
- float ty = (getHeight() - h) / 2.0f;
- float tx = (getWidth() - w) / 2.0f;
-
- Rect d = new Rect((int) tx, (int) ty, (int) (w + tx),
- (int) (h + ty));
- if (updateBounds) {
- mImageBounds = d;
- }
- canvas.drawBitmap(image, s, d, mPaint);
- }
- }
-
- public void drawPartialImage(Canvas canvas, Bitmap image) {
- boolean showsOriginal = MasterImage.getImage().showsOriginal();
- if (!showsOriginal && !mTouchShowOriginal)
- return;
- canvas.save();
- if (image != null) {
- if (mShowOriginalDirection == 0) {
- if (Math.abs(mTouch.y - mTouchDown.y) > Math.abs(mTouch.x - mTouchDown.x)) {
- mShowOriginalDirection = UNVEIL_VERTICAL;
- } else {
- mShowOriginalDirection = UNVEIL_HORIZONTAL;
- }
- }
-
- int px = 0;
- int py = 0;
- if (mShowOriginalDirection == UNVEIL_VERTICAL) {
- px = mImageBounds.width();
- py = mTouch.y - mImageBounds.top;
- } else {
- px = mTouch.x - mImageBounds.left;
- py = mImageBounds.height();
- if (showsOriginal) {
- px = mImageBounds.width();
- }
- }
-
- Rect d = new Rect(mImageBounds.left, mImageBounds.top,
- mImageBounds.left + px, mImageBounds.top + py);
- canvas.clipRect(d);
- drawImage(canvas, image, false);
- Paint paint = new Paint();
- paint.setColor(Color.BLACK);
- paint.setStrokeWidth(3);
-
- if (mShowOriginalDirection == UNVEIL_VERTICAL) {
- canvas.drawLine(mImageBounds.left, mTouch.y,
- mImageBounds.right, mTouch.y, paint);
- } else {
- canvas.drawLine(mTouch.x, mImageBounds.top,
- mTouch.x, mImageBounds.bottom, paint);
- }
-
- Rect bounds = new Rect();
- paint.setAntiAlias(true);
- paint.setTextSize(mOriginalTextSize);
- paint.getTextBounds(mOriginalText, 0, mOriginalText.length(), bounds);
- paint.setColor(Color.BLACK);
- paint.setStyle(Paint.Style.STROKE);
- paint.setStrokeWidth(3);
- canvas.drawText(mOriginalText, mImageBounds.left + mOriginalTextMargin,
- mImageBounds.top + bounds.height() + mOriginalTextMargin, paint);
- paint.setStyle(Paint.Style.FILL);
- paint.setStrokeWidth(1);
- paint.setColor(Color.WHITE);
- canvas.drawText(mOriginalText, mImageBounds.left + mOriginalTextMargin,
- mImageBounds.top + bounds.height() + mOriginalTextMargin, paint);
- }
- canvas.restore();
- }
-
- public void bindAsImageLoadListener() {
- MasterImage.getImage().addListener(this);
- }
-
- public void updateImage() {
- invalidate();
- }
-
- public void imageLoaded() {
- updateImage();
- }
-
- public void saveImage(FilterShowActivity filterShowActivity, File file) {
- SaveImage.saveImage(getImagePreset(), filterShowActivity, file);
- }
-
-
- public boolean scaleInProgress() {
- return mScaleGestureDetector.isInProgress();
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- super.onTouchEvent(event);
- int action = event.getAction();
- action = action & MotionEvent.ACTION_MASK;
-
- mGestureDetector.onTouchEvent(event);
- boolean scaleInProgress = scaleInProgress();
- mScaleGestureDetector.onTouchEvent(event);
- if (mInteractionMode == InteractionMode.SCALE) {
- return true;
- }
- if (!scaleInProgress() && scaleInProgress) {
- // If we were scaling, the scale will stop but we will
- // still issue an ACTION_UP. Let the subclasses know.
- mFinishedScalingOperation = true;
- }
-
- int ex = (int) event.getX();
- int ey = (int) event.getY();
- if (action == MotionEvent.ACTION_DOWN) {
- mInteractionMode = InteractionMode.MOVE;
- mTouchDown.x = ex;
- mTouchDown.y = ey;
- mTouchShowOriginalDate = System.currentTimeMillis();
- mShowOriginalDirection = 0;
- MasterImage.getImage().setOriginalTranslation(MasterImage.getImage().getTranslation());
- }
-
- if (action == MotionEvent.ACTION_MOVE && mInteractionMode == InteractionMode.MOVE) {
- mTouch.x = ex;
- mTouch.y = ey;
-
- float scaleFactor = MasterImage.getImage().getScaleFactor();
- if (scaleFactor > 1 && (!ENABLE_ZOOMED_COMPARISON || event.getPointerCount() == 2)) {
- float translateX = (mTouch.x - mTouchDown.x) / scaleFactor;
- float translateY = (mTouch.y - mTouchDown.y) / scaleFactor;
- Point originalTranslation = MasterImage.getImage().getOriginalTranslation();
- Point translation = MasterImage.getImage().getTranslation();
- translation.x = (int) (originalTranslation.x + translateX);
- translation.y = (int) (originalTranslation.y + translateY);
- constrainTranslation(translation, scaleFactor);
- MasterImage.getImage().setTranslation(translation);
- mTouchShowOriginal = false;
- } else if (enableComparison() && !mOriginalDisabled
- && (System.currentTimeMillis() - mTouchShowOriginalDate
- > mTouchShowOriginalDelayMin)
- && event.getPointerCount() == 1) {
- mTouchShowOriginal = true;
- }
- }
-
- if (action == MotionEvent.ACTION_UP) {
- mInteractionMode = InteractionMode.NONE;
- mTouchShowOriginal = false;
- mTouchDown.x = 0;
- mTouchDown.y = 0;
- mTouch.x = 0;
- mTouch.y = 0;
- if (MasterImage.getImage().getScaleFactor() <= 1) {
- MasterImage.getImage().setScaleFactor(1);
- MasterImage.getImage().resetTranslation();
- }
- }
- invalidate();
- return true;
- }
-
- protected boolean enableComparison() {
- return true;
- }
-
- @Override
- public boolean onDoubleTap(MotionEvent arg0) {
- mZoomIn = !mZoomIn;
- float scale = 1.0f;
- if (mZoomIn) {
- scale = MasterImage.getImage().getMaxScaleFactor();
- }
- if (scale != MasterImage.getImage().getScaleFactor()) {
- MasterImage.getImage().setScaleFactor(scale);
- float translateX = (getWidth() / 2 - arg0.getX());
- float translateY = (getHeight() / 2 - arg0.getY());
- Point translation = MasterImage.getImage().getTranslation();
- translation.x = (int) (mOriginalTranslation.x + translateX);
- translation.y = (int) (mOriginalTranslation.y + translateY);
- constrainTranslation(translation, scale);
- MasterImage.getImage().setTranslation(translation);
- invalidate();
- }
- return true;
- }
-
- private void constrainTranslation(Point translation, float scale) {
- float maxTranslationX = getWidth() / scale;
- float maxTranslationY = getHeight() / scale;
- if (Math.abs(translation.x) > maxTranslationX) {
- translation.x = (int) (Math.signum(translation.x) *
- maxTranslationX);
- if (Math.abs(translation.y) > maxTranslationY) {
- translation.y = (int) (Math.signum(translation.y) *
- maxTranslationY);
- }
-
- }
- }
-
- @Override
- public boolean onDoubleTapEvent(MotionEvent arg0) {
- return false;
- }
-
- @Override
- public boolean onSingleTapConfirmed(MotionEvent arg0) {
- return false;
- }
-
- @Override
- public boolean onDown(MotionEvent arg0) {
- return false;
- }
-
- @Override
- public boolean onFling(MotionEvent startEvent, MotionEvent endEvent, float arg2, float arg3) {
- if (mActivity == null) {
- return false;
- }
- if (endEvent.getPointerCount() == 2) {
- return false;
- }
- return true;
- }
-
- @Override
- public void onLongPress(MotionEvent arg0) {
- }
-
- @Override
- public boolean onScroll(MotionEvent arg0, MotionEvent arg1, float arg2, float arg3) {
- return false;
- }
-
- @Override
- public void onShowPress(MotionEvent arg0) {
- }
-
- @Override
- public boolean onSingleTapUp(MotionEvent arg0) {
- return false;
- }
-
- public boolean useUtilityPanel() {
- return false;
- }
-
- public void openUtilityPanel(final LinearLayout accessoryViewList) {
- }
-
- @Override
- public boolean onScale(ScaleGestureDetector detector) {
- MasterImage img = MasterImage.getImage();
- float scaleFactor = img.getScaleFactor();
-
- scaleFactor = scaleFactor * detector.getScaleFactor();
- if (scaleFactor > MasterImage.getImage().getMaxScaleFactor()) {
- scaleFactor = MasterImage.getImage().getMaxScaleFactor();
- }
- if (scaleFactor < 0.5) {
- scaleFactor = 0.5f;
- }
- MasterImage.getImage().setScaleFactor(scaleFactor);
- scaleFactor = img.getScaleFactor();
- float focusx = detector.getFocusX();
- float focusy = detector.getFocusY();
- float translateX = (focusx - mStartFocusX) / scaleFactor;
- float translateY = (focusy - mStartFocusY) / scaleFactor;
- Point translation = MasterImage.getImage().getTranslation();
- translation.x = (int) (mOriginalTranslation.x + translateX);
- translation.y = (int) (mOriginalTranslation.y + translateY);
- constrainTranslation(translation, scaleFactor);
- MasterImage.getImage().setTranslation(translation);
-
- invalidate();
- return true;
- }
-
- @Override
- public boolean onScaleBegin(ScaleGestureDetector detector) {
- Point pos = MasterImage.getImage().getTranslation();
- mOriginalTranslation.x = pos.x;
- mOriginalTranslation.y = pos.y;
- mOriginalScale = MasterImage.getImage().getScaleFactor();
- mStartFocusX = detector.getFocusX();
- mStartFocusY = detector.getFocusY();
- mInteractionMode = InteractionMode.SCALE;
- return true;
- }
-
- @Override
- public void onScaleEnd(ScaleGestureDetector detector) {
- mInteractionMode = InteractionMode.NONE;
- if (MasterImage.getImage().getScaleFactor() < 1) {
- MasterImage.getImage().setScaleFactor(1);
- invalidate();
- }
- }
-
- public boolean didFinishScalingOperation() {
- if (mFinishedScalingOperation) {
- mFinishedScalingOperation = false;
- return true;
- }
- return false;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageStraighten.java b/src/com/android/gallery3d/filtershow/imageshow/ImageStraighten.java
deleted file mode 100644
index ff75dcc09..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/ImageStraighten.java
+++ /dev/null
@@ -1,260 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.graphics.Paint.Style;
-import android.graphics.Path;
-import android.graphics.RectF;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-
-import com.android.gallery3d.filtershow.editors.EditorStraighten;
-import com.android.gallery3d.filtershow.filters.FilterCropRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterStraightenRepresentation;
-import com.android.gallery3d.filtershow.imageshow.GeometryMathUtils.GeometryHolder;
-
-import java.util.ArrayList;
-import java.util.Collection;
-
-
-public class ImageStraighten extends ImageShow {
- private static final String TAG = ImageStraighten.class.getSimpleName();
- private float mBaseAngle = 0;
- private float mAngle = 0;
- private float mInitialAngle = 0;
- private boolean mFirstDrawSinceUp = false;
- private EditorStraighten mEditorStraighten;
- private FilterStraightenRepresentation mLocalRep = new FilterStraightenRepresentation();
- private RectF mPriorCropAtUp = new RectF();
- private RectF mDrawRect = new RectF();
- private Path mDrawPath = new Path();
- private GeometryHolder mDrawHolder = new GeometryHolder();
- private enum MODES {
- NONE, MOVE
- }
- private MODES mState = MODES.NONE;
- private static final float MAX_STRAIGHTEN_ANGLE
- = FilterStraightenRepresentation.MAX_STRAIGHTEN_ANGLE;
- private static final float MIN_STRAIGHTEN_ANGLE
- = FilterStraightenRepresentation.MIN_STRAIGHTEN_ANGLE;
- private float mCurrentX;
- private float mCurrentY;
- private float mTouchCenterX;
- private float mTouchCenterY;
- private RectF mCrop = new RectF();
- private final Paint mPaint = new Paint();
-
- public ImageStraighten(Context context) {
- super(context);
- }
-
- public ImageStraighten(Context context, AttributeSet attrs) {
- super(context, attrs);
- }
-
- public void setFilterStraightenRepresentation(FilterStraightenRepresentation rep) {
- mLocalRep = (rep == null) ? new FilterStraightenRepresentation() : rep;
- mInitialAngle = mBaseAngle = mAngle = mLocalRep.getStraighten();
- }
-
- public Collection<FilterRepresentation> getFinalRepresentation() {
- ArrayList<FilterRepresentation> reps = new ArrayList<FilterRepresentation>(2);
- reps.add(mLocalRep);
- if (mInitialAngle != mLocalRep.getStraighten()) {
- reps.add(new FilterCropRepresentation(mCrop));
- }
- return reps;
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- float x = event.getX();
- float y = event.getY();
-
- switch (event.getActionMasked()) {
- case (MotionEvent.ACTION_DOWN):
- if (mState == MODES.NONE) {
- mTouchCenterX = x;
- mTouchCenterY = y;
- mCurrentX = x;
- mCurrentY = y;
- mState = MODES.MOVE;
- mBaseAngle = mAngle;
- }
- break;
- case (MotionEvent.ACTION_UP):
- if (mState == MODES.MOVE) {
- mState = MODES.NONE;
- mCurrentX = x;
- mCurrentY = y;
- computeValue();
- mFirstDrawSinceUp = true;
- }
- break;
- case (MotionEvent.ACTION_MOVE):
- if (mState == MODES.MOVE) {
- mCurrentX = x;
- mCurrentY = y;
- computeValue();
- }
- break;
- default:
- break;
- }
- invalidate();
- return true;
- }
-
- private static float angleFor(float dx, float dy) {
- return (float) (Math.atan2(dx, dy) * 180 / Math.PI);
- }
-
- private float getCurrentTouchAngle() {
- float centerX = getWidth() / 2f;
- float centerY = getHeight() / 2f;
- if (mCurrentX == mTouchCenterX && mCurrentY == mTouchCenterY) {
- return 0;
- }
- float dX1 = mTouchCenterX - centerX;
- float dY1 = mTouchCenterY - centerY;
- float dX2 = mCurrentX - centerX;
- float dY2 = mCurrentY - centerY;
- float angleA = angleFor(dX1, dY1);
- float angleB = angleFor(dX2, dY2);
- return (angleB - angleA) % 360;
- }
-
- private void computeValue() {
- float angle = getCurrentTouchAngle();
- mAngle = (mBaseAngle - angle) % 360;
- mAngle = Math.max(MIN_STRAIGHTEN_ANGLE, mAngle);
- mAngle = Math.min(MAX_STRAIGHTEN_ANGLE, mAngle);
- }
-
- private static void getUntranslatedStraightenCropBounds(RectF outRect, float straightenAngle) {
- float deg = straightenAngle;
- if (deg < 0) {
- deg = -deg;
- }
- double a = Math.toRadians(deg);
- double sina = Math.sin(a);
- double cosa = Math.cos(a);
- double rw = outRect.width();
- double rh = outRect.height();
- double h1 = rh * rh / (rw * sina + rh * cosa);
- double h2 = rh * rw / (rw * cosa + rh * sina);
- double hh = Math.min(h1, h2);
- double ww = hh * rw / rh;
- float left = (float) ((rw - ww) * 0.5f);
- float top = (float) ((rh - hh) * 0.5f);
- float right = (float) (left + ww);
- float bottom = (float) (top + hh);
- outRect.set(left, top, right, bottom);
- }
-
- private void updateCurrentCrop(Matrix m, GeometryHolder h, RectF tmp, int imageWidth,
- int imageHeight, int viewWidth, int viewHeight) {
- if (GeometryMathUtils.needsDimensionSwap(h.rotation)) {
- tmp.set(0, 0, imageHeight, imageWidth);
- } else {
- tmp.set(0, 0, imageWidth, imageHeight);
- }
- float scale = GeometryMathUtils.scale(imageWidth, imageHeight, viewWidth, viewHeight);
- GeometryMathUtils.scaleRect(tmp, scale);
- getUntranslatedStraightenCropBounds(tmp, mAngle);
- tmp.offset(viewWidth / 2f - tmp.centerX(), viewHeight / 2f - tmp.centerY());
- h.straighten = 0;
- Matrix m1 = GeometryMathUtils.getFullGeometryToScreenMatrix(h, imageWidth,
- imageHeight, viewWidth, viewHeight);
- m.reset();
- m1.invert(m);
- mCrop.set(tmp);
- m.mapRect(mCrop);
- FilterCropRepresentation.findNormalizedCrop(mCrop, imageWidth, imageHeight);
- }
-
-
- @Override
- public void onDraw(Canvas canvas) {
- MasterImage master = MasterImage.getImage();
- Bitmap image = master.getFiltersOnlyImage();
- if (image == null) {
- return;
- }
- GeometryMathUtils.initializeHolder(mDrawHolder, mLocalRep);
- mDrawHolder.straighten = mAngle;
- int imageWidth = image.getWidth();
- int imageHeight = image.getHeight();
- int viewWidth = canvas.getWidth();
- int viewHeight = canvas.getHeight();
-
- // Get matrix for drawing bitmap
- Matrix m = GeometryMathUtils.getFullGeometryToScreenMatrix(mDrawHolder, imageWidth,
- imageHeight, viewWidth, viewHeight);
- mPaint.reset();
- mPaint.setAntiAlias(true);
- mPaint.setFilterBitmap(true);
- canvas.drawBitmap(image, m, mPaint);
-
- mPaint.setFilterBitmap(false);
- mPaint.setColor(Color.WHITE);
- mPaint.setStrokeWidth(2);
- mPaint.setStyle(Paint.Style.FILL_AND_STROKE);
- updateCurrentCrop(m, mDrawHolder, mDrawRect, imageWidth,
- imageHeight, viewWidth, viewHeight);
- if (mFirstDrawSinceUp) {
- mPriorCropAtUp.set(mCrop);
- mLocalRep.setStraighten(mAngle);
- mFirstDrawSinceUp = false;
- }
-
- // Draw the grid
- if (mState == MODES.MOVE) {
- canvas.save();
- canvas.clipRect(mDrawRect);
- int n = 16;
- float step = viewWidth / n;
- float p = 0;
- for (int i = 1; i < n; i++) {
- p = i * step;
- mPaint.setAlpha(60);
- canvas.drawLine(p, 0, p, viewHeight, mPaint);
- canvas.drawLine(0, p, viewHeight, p, mPaint);
- }
- canvas.restore();
- }
- mPaint.reset();
- mPaint.setColor(Color.WHITE);
- mPaint.setStyle(Style.STROKE);
- mPaint.setStrokeWidth(3);
- mDrawPath.reset();
- mDrawPath.addRect(mDrawRect, Path.Direction.CW);
- canvas.drawPath(mDrawPath, mPaint);
- }
-
- public void setEditor(EditorStraighten editorStraighten) {
- mEditorStraighten = editorStraighten;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageTinyPlanet.java b/src/com/android/gallery3d/filtershow/imageshow/ImageTinyPlanet.java
deleted file mode 100644
index 25a0a9073..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/ImageTinyPlanet.java
+++ /dev/null
@@ -1,174 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.RectF;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-import android.view.ScaleGestureDetector;
-import android.view.ScaleGestureDetector.OnScaleGestureListener;
-
-import com.android.gallery3d.filtershow.editors.BasicEditor;
-import com.android.gallery3d.filtershow.editors.EditorTinyPlanet;
-import com.android.gallery3d.filtershow.filters.FilterTinyPlanetRepresentation;
-
-public class ImageTinyPlanet extends ImageShow {
- private static final String LOGTAG = "ImageTinyPlanet";
-
- private float mTouchCenterX = 0;
- private float mTouchCenterY = 0;
- private float mCurrentX = 0;
- private float mCurrentY = 0;
- private float mCenterX = 0;
- private float mCenterY = 0;
- private float mStartAngle = 0;
- private FilterTinyPlanetRepresentation mTinyPlanetRep;
- private EditorTinyPlanet mEditorTinyPlanet;
- private ScaleGestureDetector mScaleGestureDetector = null;
- boolean mInScale = false;
- RectF mDestRect = new RectF();
-
- OnScaleGestureListener mScaleGestureListener = new OnScaleGestureListener() {
- private float mScale = 100;
- @Override
- public void onScaleEnd(ScaleGestureDetector detector) {
- mInScale = false;
- }
-
- @Override
- public boolean onScaleBegin(ScaleGestureDetector detector) {
- mInScale = true;
- mScale = mTinyPlanetRep.getValue();
- return true;
- }
-
- @Override
- public boolean onScale(ScaleGestureDetector detector) {
- int value = mTinyPlanetRep.getValue();
- mScale *= detector.getScaleFactor();
- value = (int) (mScale);
- value = Math.min(mTinyPlanetRep.getMaximum(), value);
- value = Math.max(mTinyPlanetRep.getMinimum(), value);
- mTinyPlanetRep.setValue(value);
- invalidate();
- mEditorTinyPlanet.commitLocalRepresentation();
- mEditorTinyPlanet.updateUI();
- return true;
- }
- };
-
- public ImageTinyPlanet(Context context) {
- super(context);
- mScaleGestureDetector = new ScaleGestureDetector(context, mScaleGestureListener);
- }
-
- public ImageTinyPlanet(Context context, AttributeSet attrs) {
- super(context, attrs);
- mScaleGestureDetector = new ScaleGestureDetector(context,mScaleGestureListener );
- }
-
- protected static float angleFor(float dx, float dy) {
- return (float) (Math.atan2(dx, dy) * 180 / Math.PI);
- }
-
- protected float getCurrentTouchAngle() {
- if (mCurrentX == mTouchCenterX && mCurrentY == mTouchCenterY) {
- return 0;
- }
- float dX1 = mTouchCenterX - mCenterX;
- float dY1 = mTouchCenterY - mCenterY;
- float dX2 = mCurrentX - mCenterX;
- float dY2 = mCurrentY - mCenterY;
-
- float angleA = angleFor(dX1, dY1);
- float angleB = angleFor(dX2, dY2);
- return (float) (((angleB - angleA) % 360) * Math.PI / 180);
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- float x = event.getX();
- float y = event.getY();
- mCurrentX = x;
- mCurrentY = y;
- mCenterX = getWidth() / 2;
- mCenterY = getHeight() / 2;
- mScaleGestureDetector.onTouchEvent(event);
- if (mInScale) {
- return true;
- }
- switch (event.getActionMasked()) {
- case (MotionEvent.ACTION_DOWN):
- mTouchCenterX = x;
- mTouchCenterY = y;
- mStartAngle = mTinyPlanetRep.getAngle();
- break;
-
- case (MotionEvent.ACTION_MOVE):
- mTinyPlanetRep.setAngle(mStartAngle + getCurrentTouchAngle());
- break;
- }
- invalidate();
- mEditorTinyPlanet.commitLocalRepresentation();
- return true;
- }
-
- public void setRepresentation(FilterTinyPlanetRepresentation tinyPlanetRep) {
- mTinyPlanetRep = tinyPlanetRep;
- }
-
- public void setEditor(BasicEditor editorTinyPlanet) {
- mEditorTinyPlanet = (EditorTinyPlanet) editorTinyPlanet;
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- Bitmap bitmap = MasterImage.getImage().getHighresImage();
- if (bitmap == null) {
- bitmap = MasterImage.getImage().getFilteredImage();
- }
-
- if (bitmap != null) {
- display(canvas, bitmap);
- }
- }
-
- private void display(Canvas canvas, Bitmap bitmap) {
- float sw = canvas.getWidth();
- float sh = canvas.getHeight();
- float iw = bitmap.getWidth();
- float ih = bitmap.getHeight();
- float nsw = sw;
- float nsh = sh;
-
- if (sw * ih > sh * iw) {
- nsw = sh * iw / ih;
- } else {
- nsh = sw * ih / iw;
- }
-
- mDestRect.left = (sw - nsw) / 2;
- mDestRect.top = (sh - nsh) / 2;
- mDestRect.right = sw - mDestRect.left;
- mDestRect.bottom = sh - mDestRect.top;
-
- canvas.drawBitmap(bitmap, null, mDestRect, mPaint);
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/ImageVignette.java b/src/com/android/gallery3d/filtershow/imageshow/ImageVignette.java
deleted file mode 100644
index 518969ee1..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/ImageVignette.java
+++ /dev/null
@@ -1,165 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Matrix;
-import android.util.AttributeSet;
-import android.util.Log;
-import android.view.MotionEvent;
-
-import com.android.gallery3d.filtershow.editors.EditorVignette;
-import com.android.gallery3d.filtershow.filters.FilterVignetteRepresentation;
-
-public class ImageVignette extends ImageShow {
- private static final String LOGTAG = "ImageVignette";
-
- private FilterVignetteRepresentation mVignetteRep;
- private EditorVignette mEditorVignette;
-
- private int mActiveHandle = -1;
-
- EclipseControl mElipse;
-
- public ImageVignette(Context context) {
- super(context);
- mElipse = new EclipseControl(context);
- }
-
- public ImageVignette(Context context, AttributeSet attrs) {
- super(context, attrs);
- mElipse = new EclipseControl(context);
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- int mask = event.getActionMasked();
- if (mActiveHandle == -1) {
- if (MotionEvent.ACTION_DOWN != mask) {
- return super.onTouchEvent(event);
- }
- if (event.getPointerCount() == 1) {
- mActiveHandle = mElipse.getCloseHandle(event.getX(), event.getY());
- }
- if (mActiveHandle == -1) {
- return super.onTouchEvent(event);
- }
- } else {
- switch (mask) {
- case MotionEvent.ACTION_UP:
- mActiveHandle = -1;
- break;
- case MotionEvent.ACTION_DOWN:
- break;
- }
- }
- float x = event.getX();
- float y = event.getY();
-
- mElipse.setScrToImageMatrix(getScreenToImageMatrix(true));
-
- boolean didComputeEllipses = false;
- switch (mask) {
- case (MotionEvent.ACTION_DOWN):
- mElipse.actionDown(x, y, mVignetteRep);
- break;
- case (MotionEvent.ACTION_UP):
- case (MotionEvent.ACTION_MOVE):
- mElipse.actionMove(mActiveHandle, x, y, mVignetteRep);
- setRepresentation(mVignetteRep);
- didComputeEllipses = true;
- break;
- }
- if (!didComputeEllipses) {
- computeEllipses();
- }
- invalidate();
- return true;
- }
-
- public void setRepresentation(FilterVignetteRepresentation vignetteRep) {
- mVignetteRep = vignetteRep;
- computeEllipses();
- }
-
- public void computeEllipses() {
- if (mVignetteRep == null) {
- return;
- }
- Matrix toImg = getScreenToImageMatrix(false);
- Matrix toScr = new Matrix();
- toImg.invert(toScr);
-
- float[] c = new float[] {
- mVignetteRep.getCenterX(), mVignetteRep.getCenterY() };
- if (Float.isNaN(c[0])) {
- float cx = MasterImage.getImage().getOriginalBounds().width() / 2;
- float cy = MasterImage.getImage().getOriginalBounds().height() / 2;
- float rx = Math.min(cx, cy) * .8f;
- float ry = rx;
- mVignetteRep.setCenter(cx, cy);
- mVignetteRep.setRadius(rx, ry);
-
- c[0] = cx;
- c[1] = cy;
- toScr.mapPoints(c);
- if (getWidth() != 0) {
- mElipse.setCenter(c[0], c[1]);
- mElipse.setRadius(c[0] * 0.8f, c[1] * 0.8f);
- }
- } else {
-
- toScr.mapPoints(c);
-
- mElipse.setCenter(c[0], c[1]);
- mElipse.setRadius(toScr.mapRadius(mVignetteRep.getRadiusX()),
- toScr.mapRadius(mVignetteRep.getRadiusY()));
- }
- mEditorVignette.commitLocalRepresentation();
- }
-
- public void setEditor(EditorVignette editorVignette) {
- mEditorVignette = editorVignette;
- }
-
- @Override
- public void onSizeChanged(int w, int h, int oldw, int oldh) {
- super.onSizeChanged(w, h, oldw, oldh);
- computeEllipses();
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- super.onDraw(canvas);
- if (mVignetteRep == null) {
- return;
- }
- Matrix toImg = getScreenToImageMatrix(false);
- Matrix toScr = new Matrix();
- toImg.invert(toScr);
- float[] c = new float[] {
- mVignetteRep.getCenterX(), mVignetteRep.getCenterY() };
- toScr.mapPoints(c);
- mElipse.setCenter(c[0], c[1]);
- mElipse.setRadius(toScr.mapRadius(mVignetteRep.getRadiusX()),
- toScr.mapRadius(mVignetteRep.getRadiusY()));
-
- mElipse.draw(canvas);
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/Line.java b/src/com/android/gallery3d/filtershow/imageshow/Line.java
deleted file mode 100644
index a767bd809..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/Line.java
+++ /dev/null
@@ -1,26 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-public interface Line {
- void setPoint1(float x, float y);
- void setPoint2(float x, float y);
- float getPoint1X();
- float getPoint1Y();
- float getPoint2X();
- float getPoint2Y();
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/MasterImage.java b/src/com/android/gallery3d/filtershow/imageshow/MasterImage.java
deleted file mode 100644
index 92e57bfc1..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/MasterImage.java
+++ /dev/null
@@ -1,581 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.graphics.Bitmap;
-import android.graphics.Matrix;
-import android.graphics.Point;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.net.Uri;
-import android.os.Handler;
-import android.os.Message;
-
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.cache.ImageLoader;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.ImageFilter;
-import com.android.gallery3d.filtershow.history.HistoryItem;
-import com.android.gallery3d.filtershow.history.HistoryManager;
-import com.android.gallery3d.filtershow.pipeline.Buffer;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-import com.android.gallery3d.filtershow.pipeline.RenderingRequest;
-import com.android.gallery3d.filtershow.pipeline.RenderingRequestCaller;
-import com.android.gallery3d.filtershow.pipeline.SharedBuffer;
-import com.android.gallery3d.filtershow.pipeline.SharedPreset;
-import com.android.gallery3d.filtershow.state.StateAdapter;
-
-import java.util.Vector;
-
-public class MasterImage implements RenderingRequestCaller {
-
- private static final String LOGTAG = "MasterImage";
- private boolean DEBUG = false;
- private static final boolean DISABLEZOOM = false;
- public static final int SMALL_BITMAP_DIM = 160;
- public static final int MAX_BITMAP_DIM = 900;
- private static MasterImage sMasterImage = null;
-
- private boolean mSupportsHighRes = false;
-
- private ImageFilter mCurrentFilter = null;
- private ImagePreset mPreset = null;
- private ImagePreset mLoadedPreset = null;
- private ImagePreset mGeometryOnlyPreset = null;
- private ImagePreset mFiltersOnlyPreset = null;
-
- private SharedBuffer mPreviewBuffer = new SharedBuffer();
- private SharedPreset mPreviewPreset = new SharedPreset();
-
- private Bitmap mOriginalBitmapSmall = null;
- private Bitmap mOriginalBitmapLarge = null;
- private Bitmap mOriginalBitmapHighres = null;
- private int mOrientation;
- private Rect mOriginalBounds;
- private final Vector<ImageShow> mLoadListeners = new Vector<ImageShow>();
- private Uri mUri = null;
- private int mZoomOrientation = ImageLoader.ORI_NORMAL;
-
- private Bitmap mGeometryOnlyBitmap = null;
- private Bitmap mFiltersOnlyBitmap = null;
- private Bitmap mPartialBitmap = null;
- private Bitmap mHighresBitmap = null;
-
- private HistoryManager mHistory = null;
- private StateAdapter mState = null;
-
- private FilterShowActivity mActivity = null;
-
- private Vector<ImageShow> mObservers = new Vector<ImageShow>();
- private FilterRepresentation mCurrentFilterRepresentation;
-
- private float mScaleFactor = 1.0f;
- private float mMaxScaleFactor = 3.0f; // TODO: base this on the current view / image
- private Point mTranslation = new Point();
- private Point mOriginalTranslation = new Point();
-
- private Point mImageShowSize = new Point();
-
- private boolean mShowsOriginal;
-
- private MasterImage() {
- }
-
- // TODO: remove singleton
- public static void setMaster(MasterImage master) {
- sMasterImage = master;
- }
-
- public static MasterImage getImage() {
- if (sMasterImage == null) {
- sMasterImage = new MasterImage();
- }
- return sMasterImage;
- }
-
- public Bitmap getOriginalBitmapSmall() {
- return mOriginalBitmapSmall;
- }
-
- public Bitmap getOriginalBitmapLarge() {
- return mOriginalBitmapLarge;
- }
-
- public Bitmap getOriginalBitmapHighres() {
- return mOriginalBitmapHighres;
- }
-
- public void setOriginalBitmapHighres(Bitmap mOriginalBitmapHighres) {
- this.mOriginalBitmapHighres = mOriginalBitmapHighres;
- }
-
- public int getOrientation() {
- return mOrientation;
- }
-
- public Rect getOriginalBounds() {
- return mOriginalBounds;
- }
-
- public void setOriginalBounds(Rect r) {
- mOriginalBounds = r;
- }
-
- public Uri getUri() {
- return mUri;
- }
-
- public void setUri(Uri uri) {
- mUri = uri;
- }
-
- public int getZoomOrientation() {
- return mZoomOrientation;
- }
-
- public void addListener(ImageShow imageShow) {
- if (!mLoadListeners.contains(imageShow)) {
- mLoadListeners.add(imageShow);
- }
- }
-
- public void warnListeners() {
- mActivity.runOnUiThread(mWarnListenersRunnable);
- }
-
- private Runnable mWarnListenersRunnable = new Runnable() {
- @Override
- public void run() {
- for (int i = 0; i < mLoadListeners.size(); i++) {
- ImageShow imageShow = mLoadListeners.elementAt(i);
- imageShow.imageLoaded();
- }
- invalidatePreview();
- }
- };
-
- public boolean loadBitmap(Uri uri, int size) {
- setUri(uri);
- mOrientation = ImageLoader.getMetadataOrientation(mActivity, uri);
- Rect originalBounds = new Rect();
- mOriginalBitmapLarge = ImageLoader.loadOrientedConstrainedBitmap(uri, mActivity,
- Math.min(MAX_BITMAP_DIM, size),
- mOrientation, originalBounds);
- setOriginalBounds(originalBounds);
- if (mOriginalBitmapLarge == null) {
- return false;
- }
- int sw = SMALL_BITMAP_DIM;
- int sh = (int) (sw * (float) mOriginalBitmapLarge.getHeight() / mOriginalBitmapLarge
- .getWidth());
- mOriginalBitmapSmall = Bitmap.createScaledBitmap(mOriginalBitmapLarge, sw, sh, true);
- mZoomOrientation = mOrientation;
- warnListeners();
- return true;
- }
-
- public void setSupportsHighRes(boolean value) {
- mSupportsHighRes = value;
- }
-
- public void addObserver(ImageShow observer) {
- if (mObservers.contains(observer)) {
- return;
- }
- mObservers.add(observer);
- }
-
- public void setActivity(FilterShowActivity activity) {
- mActivity = activity;
- }
-
- public FilterShowActivity getActivity() {
- return mActivity;
- }
-
- public synchronized ImagePreset getPreset() {
- return mPreset;
- }
-
- public synchronized ImagePreset getGeometryPreset() {
- return mGeometryOnlyPreset;
- }
-
- public synchronized ImagePreset getFiltersOnlyPreset() {
- return mFiltersOnlyPreset;
- }
-
- public synchronized void setPreset(ImagePreset preset,
- FilterRepresentation change,
- boolean addToHistory) {
- if (DEBUG) {
- preset.showFilters();
- }
- mPreset = preset;
- mPreset.fillImageStateAdapter(mState);
- if (addToHistory) {
- HistoryItem historyItem = new HistoryItem(mPreset, change);
- mHistory.addHistoryItem(historyItem);
- }
- updatePresets(true);
- mActivity.updateCategories();
- }
-
- public void onHistoryItemClick(int position) {
- HistoryItem historyItem = mHistory.getItem(position);
- // We need a copy from the history
- ImagePreset newPreset = new ImagePreset(historyItem.getImagePreset());
- // don't need to add it to the history
- setPreset(newPreset, historyItem.getFilterRepresentation(), false);
- mHistory.setCurrentPreset(position);
- }
-
- public HistoryManager getHistory() {
- return mHistory;
- }
-
- public StateAdapter getState() {
- return mState;
- }
-
- public void setHistoryManager(HistoryManager adapter) {
- mHistory = adapter;
- }
-
- public void setStateAdapter(StateAdapter adapter) {
- mState = adapter;
- }
-
- public void setCurrentFilter(ImageFilter filter) {
- mCurrentFilter = filter;
- }
-
- public ImageFilter getCurrentFilter() {
- return mCurrentFilter;
- }
-
- public synchronized boolean hasModifications() {
- // TODO: We need to have a better same effects check to see if two
- // presets are functionally the same. Right now, we are relying on a
- // stricter check as equals().
- ImagePreset loadedPreset = getLoadedPreset();
- if (mPreset == null) {
- if (loadedPreset == null) {
- return false;
- } else {
- return loadedPreset.hasModifications();
- }
- } else {
- if (loadedPreset == null) {
- return mPreset.hasModifications();
- } else {
- return !mPreset.equals(loadedPreset);
- }
- }
- }
-
- public SharedBuffer getPreviewBuffer() {
- return mPreviewBuffer;
- }
-
- public SharedPreset getPreviewPreset() {
- return mPreviewPreset;
- }
-
- public Bitmap getFilteredImage() {
- mPreviewBuffer.swapConsumerIfNeeded(); // get latest bitmap
- Buffer consumer = mPreviewBuffer.getConsumer();
- if (consumer != null) {
- return consumer.getBitmap();
- }
- return null;
- }
-
- public Bitmap getFiltersOnlyImage() {
- return mFiltersOnlyBitmap;
- }
-
- public Bitmap getGeometryOnlyImage() {
- return mGeometryOnlyBitmap;
- }
-
- public Bitmap getPartialImage() {
- return mPartialBitmap;
- }
-
- public Bitmap getHighresImage() {
- return mHighresBitmap;
- }
-
- public void notifyObservers() {
- for (ImageShow observer : mObservers) {
- observer.invalidate();
- }
- }
-
- public void updatePresets(boolean force) {
- if (force || mGeometryOnlyPreset == null) {
- ImagePreset newPreset = new ImagePreset(mPreset);
- newPreset.setDoApplyFilters(false);
- newPreset.setDoApplyGeometry(true);
- if (force || mGeometryOnlyPreset == null
- || !newPreset.same(mGeometryOnlyPreset)) {
- mGeometryOnlyPreset = newPreset;
- RenderingRequest.post(mActivity, getOriginalBitmapLarge(),
- mGeometryOnlyPreset, RenderingRequest.GEOMETRY_RENDERING, this);
- }
- }
- if (force || mFiltersOnlyPreset == null) {
- ImagePreset newPreset = new ImagePreset(mPreset);
- newPreset.setDoApplyFilters(true);
- newPreset.setDoApplyGeometry(false);
- if (force || mFiltersOnlyPreset == null
- || !newPreset.same(mFiltersOnlyPreset)) {
- mFiltersOnlyPreset = newPreset;
- RenderingRequest.post(mActivity, MasterImage.getImage().getOriginalBitmapLarge(),
- mFiltersOnlyPreset, RenderingRequest.FILTERS_RENDERING, this);
- }
- }
- invalidatePreview();
- }
-
- public FilterRepresentation getCurrentFilterRepresentation() {
- return mCurrentFilterRepresentation;
- }
-
- public void setCurrentFilterRepresentation(FilterRepresentation currentFilterRepresentation) {
- mCurrentFilterRepresentation = currentFilterRepresentation;
- }
-
- public void invalidateFiltersOnly() {
- mFiltersOnlyPreset = null;
- updatePresets(false);
- }
-
- public void invalidatePartialPreview() {
- if (mPartialBitmap != null) {
- mPartialBitmap = null;
- notifyObservers();
- }
- }
-
- public void invalidateHighresPreview() {
- if (mHighresBitmap != null) {
- mHighresBitmap = null;
- notifyObservers();
- }
- }
-
- public void invalidatePreview() {
- mPreviewPreset.enqueuePreset(mPreset);
- mPreviewBuffer.invalidate();
- invalidatePartialPreview();
- invalidateHighresPreview();
- needsUpdatePartialPreview();
- needsUpdateHighResPreview();
- mActivity.getProcessingService().updatePreviewBuffer();
- }
-
- public void setImageShowSize(int w, int h) {
- if (mImageShowSize.x != w || mImageShowSize.y != h) {
- mImageShowSize.set(w, h);
- needsUpdatePartialPreview();
- needsUpdateHighResPreview();
- }
- }
-
- private Matrix getImageToScreenMatrix(boolean reflectRotation) {
- if (getOriginalBounds() == null || mImageShowSize.x == 0 || mImageShowSize.y == 0) {
- return new Matrix();
- }
- Matrix m = GeometryMathUtils.getImageToScreenMatrix(mPreset.getGeometryFilters(),
- reflectRotation, getOriginalBounds(), mImageShowSize.x, mImageShowSize.y);
- if (m == null) {
- m = new Matrix();
- m.reset();
- return m;
- }
- Point translate = getTranslation();
- float scaleFactor = getScaleFactor();
- m.postTranslate(translate.x, translate.y);
- m.postScale(scaleFactor, scaleFactor, mImageShowSize.x / 2.0f, mImageShowSize.y / 2.0f);
- return m;
- }
-
- private Matrix getScreenToImageMatrix(boolean reflectRotation) {
- Matrix m = getImageToScreenMatrix(reflectRotation);
- Matrix invert = new Matrix();
- m.invert(invert);
- return invert;
- }
-
- public void needsUpdateHighResPreview() {
- if (!mSupportsHighRes) {
- return;
- }
- if (mActivity.getProcessingService() == null) {
- return;
- }
- mActivity.getProcessingService().postHighresRenderingRequest(mPreset,
- getScaleFactor(), this);
- invalidateHighresPreview();
- }
-
- public void needsUpdatePartialPreview() {
- if (mPreset == null) {
- return;
- }
- if (!mPreset.canDoPartialRendering()) {
- invalidatePartialPreview();
- return;
- }
- Matrix m = getScreenToImageMatrix(true);
- RectF r = new RectF(0, 0, mImageShowSize.x, mImageShowSize.y);
- RectF dest = new RectF();
- m.mapRect(dest, r);
- Rect bounds = new Rect();
- dest.roundOut(bounds);
- RenderingRequest.post(mActivity, null, mPreset, RenderingRequest.PARTIAL_RENDERING,
- this, bounds, new Rect(0, 0, mImageShowSize.x, mImageShowSize.y));
- invalidatePartialPreview();
- }
-
- @Override
- public void available(RenderingRequest request) {
- if (request.getBitmap() == null) {
- return;
- }
-
- boolean needsCheckModification = false;
- if (request.getType() == RenderingRequest.GEOMETRY_RENDERING) {
- mGeometryOnlyBitmap = request.getBitmap();
- needsCheckModification = true;
- }
- if (request.getType() == RenderingRequest.FILTERS_RENDERING) {
- mFiltersOnlyBitmap = request.getBitmap();
- notifyObservers();
- needsCheckModification = true;
- }
- if (request.getType() == RenderingRequest.PARTIAL_RENDERING
- && request.getScaleFactor() == getScaleFactor()) {
- mPartialBitmap = request.getBitmap();
- notifyObservers();
- needsCheckModification = true;
- }
- if (request.getType() == RenderingRequest.HIGHRES_RENDERING) {
- mHighresBitmap = request.getBitmap();
- notifyObservers();
- needsCheckModification = true;
- }
- if (needsCheckModification) {
- mActivity.enableSave(hasModifications());
- }
- }
-
- public static void reset() {
- sMasterImage = null;
- }
-
- public float getScaleFactor() {
- return mScaleFactor;
- }
-
- public void setScaleFactor(float scaleFactor) {
- if (DISABLEZOOM) {
- return;
- }
- if (scaleFactor == mScaleFactor) {
- return;
- }
- mScaleFactor = scaleFactor;
- invalidatePartialPreview();
- }
-
- public Point getTranslation() {
- return mTranslation;
- }
-
- public void setTranslation(Point translation) {
- if (DISABLEZOOM) {
- mTranslation.x = 0;
- mTranslation.y = 0;
- return;
- }
- mTranslation.x = translation.x;
- mTranslation.y = translation.y;
- needsUpdatePartialPreview();
- }
-
- public Point getOriginalTranslation() {
- return mOriginalTranslation;
- }
-
- public void setOriginalTranslation(Point originalTranslation) {
- if (DISABLEZOOM) {
- return;
- }
- mOriginalTranslation.x = originalTranslation.x;
- mOriginalTranslation.y = originalTranslation.y;
- }
-
- public void resetTranslation() {
- mTranslation.x = 0;
- mTranslation.y = 0;
- needsUpdatePartialPreview();
- }
-
- public Bitmap getThumbnailBitmap() {
- return getOriginalBitmapSmall();
- }
-
- public Bitmap getLargeThumbnailBitmap() {
- return getOriginalBitmapLarge();
- }
-
- public float getMaxScaleFactor() {
- if (DISABLEZOOM) {
- return 1;
- }
- return mMaxScaleFactor;
- }
-
- public void setMaxScaleFactor(float maxScaleFactor) {
- mMaxScaleFactor = maxScaleFactor;
- }
-
- public boolean supportsHighRes() {
- return mSupportsHighRes;
- }
-
- public void setShowsOriginal(boolean value) {
- mShowsOriginal = value;
- notifyObservers();
- }
-
- public boolean showsOriginal() {
- return mShowsOriginal;
- }
-
- public void setLoadedPreset(ImagePreset preset) {
- mLoadedPreset = preset;
- }
-
- public ImagePreset getLoadedPreset() {
- return mLoadedPreset;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/Oval.java b/src/com/android/gallery3d/filtershow/imageshow/Oval.java
deleted file mode 100644
index 28f278f1c..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/Oval.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-public interface Oval {
- void setCenter(float x, float y);
- void setRadius(float w, float h);
- float getCenterX();
- float getCenterY();
- float getRadiusX();
- float getRadiusY();
- void setRadiusY(float y);
- void setRadiusX(float x);
-
-}
diff --git a/src/com/android/gallery3d/filtershow/imageshow/Spline.java b/src/com/android/gallery3d/filtershow/imageshow/Spline.java
deleted file mode 100644
index 3c27a4d0f..000000000
--- a/src/com/android/gallery3d/filtershow/imageshow/Spline.java
+++ /dev/null
@@ -1,450 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.imageshow;
-
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.Path;
-import android.graphics.drawable.Drawable;
-import android.util.Log;
-
-import java.util.Collections;
-import java.util.Vector;
-
-public class Spline {
- private final Vector<ControlPoint> mPoints;
- private static Drawable mCurveHandle;
- private static int mCurveHandleSize;
- private static int mCurveWidth;
-
- public static final int RGB = 0;
- public static final int RED = 1;
- public static final int GREEN = 2;
- public static final int BLUE = 3;
- private static final String LOGTAG = "Spline";
-
- private final Paint gPaint = new Paint();
- private ControlPoint mCurrentControlPoint = null;
-
- public Spline() {
- mPoints = new Vector<ControlPoint>();
- }
-
- public Spline(Spline spline) {
- mPoints = new Vector<ControlPoint>();
- for (int i = 0; i < spline.mPoints.size(); i++) {
- ControlPoint p = spline.mPoints.elementAt(i);
- ControlPoint newPoint = new ControlPoint(p);
- mPoints.add(newPoint);
- if (spline.mCurrentControlPoint == p) {
- mCurrentControlPoint = newPoint;
- }
- }
- Collections.sort(mPoints);
- }
-
- public static void setCurveHandle(Drawable drawable, int size) {
- mCurveHandle = drawable;
- mCurveHandleSize = size;
- }
-
- public static void setCurveWidth(int width) {
- mCurveWidth = width;
- }
-
- public static int curveHandleSize() {
- return mCurveHandleSize;
- }
-
- public static int colorForCurve(int curveIndex) {
- switch (curveIndex) {
- case Spline.RED:
- return Color.RED;
- case GREEN:
- return Color.GREEN;
- case BLUE:
- return Color.BLUE;
- }
- return Color.WHITE;
- }
-
- public boolean sameValues(Spline other) {
- if (this == other) {
- return true;
- }
- if (other == null) {
- return false;
- }
-
- if (getNbPoints() != other.getNbPoints()) {
- return false;
- }
-
- for (int i = 0; i < getNbPoints(); i++) {
- ControlPoint p = mPoints.elementAt(i);
- ControlPoint otherPoint = other.mPoints.elementAt(i);
- if (!p.sameValues(otherPoint)) {
- return false;
- }
- }
- return true;
- }
-
- private void didMovePoint(ControlPoint point) {
- mCurrentControlPoint = point;
- }
-
- public void movePoint(int pick, float x, float y) {
- if (pick < 0 || pick > mPoints.size() - 1) {
- return;
- }
- ControlPoint point = mPoints.elementAt(pick);
- point.x = x;
- point.y = y;
- didMovePoint(point);
- }
-
- public boolean isOriginal() {
- if (this.getNbPoints() != 2) {
- return false;
- }
- if (mPoints.elementAt(0).x != 0 || mPoints.elementAt(0).y != 1) {
- return false;
- }
- if (mPoints.elementAt(1).x != 1 || mPoints.elementAt(1).y != 0) {
- return false;
- }
- return true;
- }
-
- public void reset() {
- mPoints.clear();
- addPoint(0.0f, 1.0f);
- addPoint(1.0f, 0.0f);
- }
-
- private void drawHandles(Canvas canvas, Drawable indicator, float centerX, float centerY) {
- int left = (int) centerX - mCurveHandleSize / 2;
- int top = (int) centerY - mCurveHandleSize / 2;
- indicator.setBounds(left, top, left + mCurveHandleSize, top + mCurveHandleSize);
- indicator.draw(canvas);
- }
-
- public float[] getAppliedCurve() {
- float[] curve = new float[256];
- ControlPoint[] points = new ControlPoint[mPoints.size()];
- for (int i = 0; i < mPoints.size(); i++) {
- ControlPoint p = mPoints.get(i);
- points[i] = new ControlPoint(p.x, p.y);
- }
- double[] derivatives = solveSystem(points);
- int start = 0;
- int end = 256;
- if (points[0].x != 0) {
- start = (int) (points[0].x * 256);
- }
- if (points[points.length - 1].x != 1) {
- end = (int) (points[points.length - 1].x * 256);
- }
- for (int i = 0; i < start; i++) {
- curve[i] = 1.0f - points[0].y;
- }
- for (int i = end; i < 256; i++) {
- curve[i] = 1.0f - points[points.length - 1].y;
- }
- for (int i = start; i < end; i++) {
- ControlPoint cur = null;
- ControlPoint next = null;
- double x = i / 256.0;
- int pivot = 0;
- for (int j = 0; j < points.length - 1; j++) {
- if (x >= points[j].x && x <= points[j + 1].x) {
- pivot = j;
- }
- }
- cur = points[pivot];
- next = points[pivot + 1];
- if (x <= next.x) {
- double x1 = cur.x;
- double x2 = next.x;
- double y1 = cur.y;
- double y2 = next.y;
-
- // Use the second derivatives to apply the cubic spline
- // equation:
- double delta = (x2 - x1);
- double delta2 = delta * delta;
- double b = (x - x1) / delta;
- double a = 1 - b;
- double ta = a * y1;
- double tb = b * y2;
- double tc = (a * a * a - a) * derivatives[pivot];
- double td = (b * b * b - b) * derivatives[pivot + 1];
- double y = ta + tb + (delta2 / 6) * (tc + td);
- if (y > 1.0f) {
- y = 1.0f;
- }
- if (y < 0) {
- y = 0;
- }
- curve[i] = (float) (1.0f - y);
- } else {
- curve[i] = 1.0f - next.y;
- }
- }
- return curve;
- }
-
- private void drawGrid(Canvas canvas, float w, float h) {
- // Grid
- gPaint.setARGB(128, 150, 150, 150);
- gPaint.setStrokeWidth(1);
-
- float stepH = h / 9;
- float stepW = w / 9;
-
- // central diagonal
- gPaint.setARGB(255, 100, 100, 100);
- gPaint.setStrokeWidth(2);
- canvas.drawLine(0, h, w, 0, gPaint);
-
- gPaint.setARGB(128, 200, 200, 200);
- gPaint.setStrokeWidth(4);
- stepH = h / 3;
- stepW = w / 3;
- for (int j = 1; j < 3; j++) {
- canvas.drawLine(0, j * stepH, w, j * stepH, gPaint);
- canvas.drawLine(j * stepW, 0, j * stepW, h, gPaint);
- }
- canvas.drawLine(0, 0, 0, h, gPaint);
- canvas.drawLine(w, 0, w, h, gPaint);
- canvas.drawLine(0, 0, w, 0, gPaint);
- canvas.drawLine(0, h, w, h, gPaint);
- }
-
- public void draw(Canvas canvas, int color, int canvasWidth, int canvasHeight,
- boolean showHandles, boolean moving) {
- float w = canvasWidth - mCurveHandleSize;
- float h = canvasHeight - mCurveHandleSize;
- float dx = mCurveHandleSize / 2;
- float dy = mCurveHandleSize / 2;
-
- // The cubic spline equation is (from numerical recipes in C):
- // y = a(y_i) + b(y_i+1) + c(y"_i) + d(y"_i+1)
- //
- // with c(y"_i) and d(y"_i+1):
- // c(y"_i) = 1/6 (a^3 - a) delta^2 (y"_i)
- // d(y"_i_+1) = 1/6 (b^3 - b) delta^2 (y"_i+1)
- //
- // and delta:
- // delta = x_i+1 - x_i
- //
- // To find the second derivatives y", we can rearrange the equation as:
- // A(y"_i-1) + B(y"_i) + C(y"_i+1) = D
- //
- // With the coefficients A, B, C, D:
- // A = 1/6 (x_i - x_i-1)
- // B = 1/3 (x_i+1 - x_i-1)
- // C = 1/6 (x_i+1 - x_i)
- // D = (y_i+1 - y_i)/(x_i+1 - x_i) - (y_i - y_i-1)/(x_i - x_i-1)
- //
- // We can now easily solve the equation to find the second derivatives:
- ControlPoint[] points = new ControlPoint[mPoints.size()];
- for (int i = 0; i < mPoints.size(); i++) {
- ControlPoint p = mPoints.get(i);
- points[i] = new ControlPoint(p.x * w, p.y * h);
- }
- double[] derivatives = solveSystem(points);
-
- Path path = new Path();
- path.moveTo(0, points[0].y);
- for (int i = 0; i < points.length - 1; i++) {
- double x1 = points[i].x;
- double x2 = points[i + 1].x;
- double y1 = points[i].y;
- double y2 = points[i + 1].y;
-
- for (double x = x1; x < x2; x += 20) {
- // Use the second derivatives to apply the cubic spline
- // equation:
- double delta = (x2 - x1);
- double delta2 = delta * delta;
- double b = (x - x1) / delta;
- double a = 1 - b;
- double ta = a * y1;
- double tb = b * y2;
- double tc = (a * a * a - a) * derivatives[i];
- double td = (b * b * b - b) * derivatives[i + 1];
- double y = ta + tb + (delta2 / 6) * (tc + td);
- if (y > h) {
- y = h;
- }
- if (y < 0) {
- y = 0;
- }
- path.lineTo((float) x, (float) y);
- }
- }
- canvas.save();
- canvas.translate(dx, dy);
- drawGrid(canvas, w, h);
- ControlPoint lastPoint = points[points.length - 1];
- path.lineTo(lastPoint.x, lastPoint.y);
- path.lineTo(w, lastPoint.y);
- Paint paint = new Paint();
- paint.setAntiAlias(true);
- paint.setFilterBitmap(true);
- paint.setDither(true);
- paint.setStyle(Paint.Style.STROKE);
- int curveWidth = mCurveWidth;
- if (showHandles) {
- curveWidth *= 1.5;
- }
- paint.setStrokeWidth(curveWidth + 2);
- paint.setColor(Color.BLACK);
- canvas.drawPath(path, paint);
-
- if (moving && mCurrentControlPoint != null) {
- float px = mCurrentControlPoint.x * w;
- float py = mCurrentControlPoint.y * h;
- paint.setStrokeWidth(3);
- paint.setColor(Color.BLACK);
- canvas.drawLine(px, py, px, h, paint);
- canvas.drawLine(0, py, px, py, paint);
- paint.setStrokeWidth(1);
- paint.setColor(color);
- canvas.drawLine(px, py, px, h, paint);
- canvas.drawLine(0, py, px, py, paint);
- }
-
- paint.setStrokeWidth(curveWidth);
- paint.setColor(color);
- canvas.drawPath(path, paint);
- if (showHandles) {
- for (int i = 0; i < points.length; i++) {
- float x = points[i].x;
- float y = points[i].y;
- drawHandles(canvas, mCurveHandle, x, y);
- }
- }
- canvas.restore();
- }
-
- double[] solveSystem(ControlPoint[] points) {
- int n = points.length;
- double[][] system = new double[n][3];
- double[] result = new double[n]; // d
- double[] solution = new double[n]; // returned coefficients
- system[0][1] = 1;
- system[n - 1][1] = 1;
- double d6 = 1.0 / 6.0;
- double d3 = 1.0 / 3.0;
-
- // let's create a tridiagonal matrix representing the
- // system, and apply the TDMA algorithm to solve it
- // (see http://en.wikipedia.org/wiki/Tridiagonal_matrix_algorithm)
- for (int i = 1; i < n - 1; i++) {
- double deltaPrevX = points[i].x - points[i - 1].x;
- double deltaX = points[i + 1].x - points[i - 1].x;
- double deltaNextX = points[i + 1].x - points[i].x;
- double deltaNextY = points[i + 1].y - points[i].y;
- double deltaPrevY = points[i].y - points[i - 1].y;
- system[i][0] = d6 * deltaPrevX; // a_i
- system[i][1] = d3 * deltaX; // b_i
- system[i][2] = d6 * deltaNextX; // c_i
- result[i] = (deltaNextY / deltaNextX) - (deltaPrevY / deltaPrevX); // d_i
- }
-
- // Forward sweep
- for (int i = 1; i < n; i++) {
- // m = a_i/b_i-1
- double m = system[i][0] / system[i - 1][1];
- // b_i = b_i - m(c_i-1)
- system[i][1] = system[i][1] - m * system[i - 1][2];
- // d_i = d_i - m(d_i-1)
- result[i] = result[i] - m * result[i - 1];
- }
-
- // Back substitution
- solution[n - 1] = result[n - 1] / system[n - 1][1];
- for (int i = n - 2; i >= 0; --i) {
- solution[i] = (result[i] - system[i][2] * solution[i + 1]) / system[i][1];
- }
- return solution;
- }
-
- public int addPoint(float x, float y) {
- return addPoint(new ControlPoint(x, y));
- }
-
- public int addPoint(ControlPoint v) {
- mPoints.add(v);
- Collections.sort(mPoints);
- return mPoints.indexOf(v);
- }
-
- public void deletePoint(int n) {
- mPoints.remove(n);
- if (mPoints.size() < 2) {
- reset();
- }
- Collections.sort(mPoints);
- }
-
- public int getNbPoints() {
- return mPoints.size();
- }
-
- public ControlPoint getPoint(int n) {
- return mPoints.elementAt(n);
- }
-
- public boolean isPointContained(float x, int n) {
- for (int i = 0; i < n; i++) {
- ControlPoint point = mPoints.elementAt(i);
- if (point.x > x) {
- return false;
- }
- }
- for (int i = n + 1; i < mPoints.size(); i++) {
- ControlPoint point = mPoints.elementAt(i);
- if (point.x < x) {
- return false;
- }
- }
- return true;
- }
-
- public Spline copy() {
- Spline spline = new Spline();
- for (int i = 0; i < mPoints.size(); i++) {
- ControlPoint point = mPoints.elementAt(i);
- spline.addPoint(point.copy());
- }
- return spline;
- }
-
- public void show() {
- Log.v(LOGTAG, "show curve " + this);
- for (int i = 0; i < mPoints.size(); i++) {
- ControlPoint point = mPoints.elementAt(i);
- Log.v(LOGTAG, "point " + i + " is (" + point.x + ", " + point.y + ")");
- }
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/Buffer.java b/src/com/android/gallery3d/filtershow/pipeline/Buffer.java
deleted file mode 100644
index 744451229..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/Buffer.java
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.graphics.Bitmap;
-import android.support.v8.renderscript.Allocation;
-import android.support.v8.renderscript.RenderScript;
-
-public class Buffer {
- private static final String LOGTAG = "Buffer";
- private Bitmap mBitmap;
- private Allocation mAllocation;
- private boolean mUseAllocation = false;
- private static final Bitmap.Config BITMAP_CONFIG = Bitmap.Config.ARGB_8888;
- private ImagePreset mPreset;
-
- public Buffer(Bitmap bitmap) {
- RenderScript rs = CachingPipeline.getRenderScriptContext();
- if (bitmap != null) {
- mBitmap = bitmap.copy(BITMAP_CONFIG, true);
- }
- if (mUseAllocation) {
- // TODO: recreate the allocation when the RS context changes
- mAllocation = Allocation.createFromBitmap(rs, mBitmap,
- Allocation.MipmapControl.MIPMAP_NONE,
- Allocation.USAGE_SHARED | Allocation.USAGE_SCRIPT);
- }
- }
-
- public void setBitmap(Bitmap bitmap) {
- mBitmap = bitmap.copy(BITMAP_CONFIG, true);
- }
-
- public Bitmap getBitmap() {
- return mBitmap;
- }
-
- public Allocation getAllocation() {
- return mAllocation;
- }
-
- public void sync() {
- if (mUseAllocation) {
- mAllocation.copyTo(mBitmap);
- }
- }
-
- public ImagePreset getPreset() {
- return mPreset;
- }
-
- public void setPreset(ImagePreset preset) {
- if ((mPreset == null) || (!mPreset.same(preset))) {
- mPreset = new ImagePreset(preset);
- } else {
- mPreset.updateWith(preset);
- }
- }
-}
-
diff --git a/src/com/android/gallery3d/filtershow/pipeline/CacheProcessing.java b/src/com/android/gallery3d/filtershow/pipeline/CacheProcessing.java
deleted file mode 100644
index e0269e9bb..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/CacheProcessing.java
+++ /dev/null
@@ -1,193 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.graphics.Bitmap;
-import android.util.Log;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-
-import java.util.Vector;
-
-public class CacheProcessing {
- private static final String LOGTAG = "CacheProcessing";
- private static final boolean DEBUG = false;
- private Vector<CacheStep> mSteps = new Vector<CacheStep>();
-
- static class CacheStep {
- FilterRepresentation representation;
- Bitmap cache;
- }
-
- public Bitmap process(Bitmap originalBitmap,
- Vector<FilterRepresentation> filters,
- FilterEnvironment environment) {
-
- if (filters.size() == 0) {
- return originalBitmap;
- }
-
- // New set of filters, let's clear the cache and rebuild it.
- if (filters.size() != mSteps.size()) {
- mSteps.clear();
- for (int i = 0; i < filters.size(); i++) {
- FilterRepresentation representation = filters.elementAt(i);
- CacheStep step = new CacheStep();
- step.representation = representation.copy();
- mSteps.add(step);
- }
- }
-
- if (DEBUG) {
- displayFilters(filters);
- }
-
- // First, let's find how similar we are in our cache
- // compared to the current list of filters
- int similarUpToIndex = -1;
- for (int i = 0; i < filters.size(); i++) {
- FilterRepresentation representation = filters.elementAt(i);
- CacheStep step = mSteps.elementAt(i);
- boolean similar = step.representation.equals(representation);
- if (similar) {
- similarUpToIndex = i;
- } else {
- break;
- }
- }
- if (DEBUG) {
- Log.v(LOGTAG, "similar up to index " + similarUpToIndex);
- }
-
- // Now, let's get the earliest cached result in our pipeline
- Bitmap cacheBitmap = null;
- int findBaseImageIndex = similarUpToIndex;
- if (findBaseImageIndex > -1) {
- while (findBaseImageIndex > 0
- && mSteps.elementAt(findBaseImageIndex).cache == null) {
- findBaseImageIndex--;
- }
- cacheBitmap = mSteps.elementAt(findBaseImageIndex).cache;
- }
- boolean emptyStack = false;
- if (cacheBitmap == null) {
- emptyStack = true;
- // Damn, it's an empty stack, we have to start from scratch
- // TODO: use a bitmap cache + RS allocation instead of Bitmap.copy()
- cacheBitmap = originalBitmap.copy(Bitmap.Config.ARGB_8888, true);
- if (findBaseImageIndex > -1) {
- FilterRepresentation representation = filters.elementAt(findBaseImageIndex);
- if (representation.getFilterType() != FilterRepresentation.TYPE_GEOMETRY) {
- cacheBitmap = environment.applyRepresentation(representation, cacheBitmap);
- }
- mSteps.elementAt(findBaseImageIndex).representation = representation.copy();
- mSteps.elementAt(findBaseImageIndex).cache = cacheBitmap;
- }
- if (DEBUG) {
- Log.v(LOGTAG, "empty stack");
- }
- }
-
- // Ok, so sadly the earliest cached result is before the index we want.
- // We have to rebuild a new result for this position, and then cache it.
- if (findBaseImageIndex != similarUpToIndex) {
- if (DEBUG) {
- Log.v(LOGTAG, "rebuild cacheBitmap from " + findBaseImageIndex
- + " to " + similarUpToIndex);
- }
- // rebuild the cache image for this step
- if (!emptyStack) {
- cacheBitmap = cacheBitmap.copy(Bitmap.Config.ARGB_8888, true);
- } else {
- // if it was an empty stack, we already applied it
- findBaseImageIndex ++;
- }
- for (int i = findBaseImageIndex; i <= similarUpToIndex; i++) {
- FilterRepresentation representation = filters.elementAt(i);
- if (representation.getFilterType() != FilterRepresentation.TYPE_GEOMETRY) {
- cacheBitmap = environment.applyRepresentation(representation, cacheBitmap);
- }
- if (DEBUG) {
- Log.v(LOGTAG, " - " + i + " => apply " + representation.getName());
- }
- }
- // Let's cache it!
- mSteps.elementAt(similarUpToIndex).cache = cacheBitmap;
- }
-
- if (DEBUG) {
- Log.v(LOGTAG, "process pipeline from " + similarUpToIndex
- + " to " + (filters.size() - 1));
- }
-
- // Now we are good to go, let's use the cacheBitmap as a starting point
- for (int i = similarUpToIndex + 1; i < filters.size(); i++) {
- FilterRepresentation representation = filters.elementAt(i);
- CacheStep currentStep = mSteps.elementAt(i);
- cacheBitmap = cacheBitmap.copy(Bitmap.Config.ARGB_8888, true);
- if (representation.getFilterType() != FilterRepresentation.TYPE_GEOMETRY) {
- cacheBitmap = environment.applyRepresentation(representation, cacheBitmap);
- }
- currentStep.representation = representation.copy();
- currentStep.cache = cacheBitmap;
- if (DEBUG) {
- Log.v(LOGTAG, " - " + i + " => apply " + representation.getName());
- }
- }
-
- if (DEBUG) {
- Log.v(LOGTAG, "now let's cleanup the cache...");
- displayNbBitmapsInCache();
- }
-
- // Let's see if we can cleanup the cache for unused bitmaps
- for (int i = 0; i < similarUpToIndex; i++) {
- CacheStep currentStep = mSteps.elementAt(i);
- currentStep.cache = null;
- }
-
- if (DEBUG) {
- Log.v(LOGTAG, "cleanup done...");
- displayNbBitmapsInCache();
- }
- return cacheBitmap;
- }
-
- private void displayFilters(Vector<FilterRepresentation> filters) {
- Log.v(LOGTAG, "------>>>");
- for (int i = 0; i < filters.size(); i++) {
- FilterRepresentation representation = filters.elementAt(i);
- CacheStep step = mSteps.elementAt(i);
- boolean similar = step.representation.equals(representation);
- Log.v(LOGTAG, "[" + i + "] - " + representation.getName()
- + " similar rep ? " + (similar ? "YES" : "NO")
- + " -- bitmap: " + step.cache);
- }
- Log.v(LOGTAG, "<<<------");
- }
-
- private void displayNbBitmapsInCache() {
- int nbBitmapsCached = 0;
- for (int i = 0; i < mSteps.size(); i++) {
- CacheStep step = mSteps.elementAt(i);
- if (step.cache != null) {
- nbBitmapsCached++;
- }
- }
- Log.v(LOGTAG, "nb bitmaps in cache: " + nbBitmapsCached + " / " + mSteps.size());
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/CachingPipeline.java b/src/com/android/gallery3d/filtershow/pipeline/CachingPipeline.java
deleted file mode 100644
index fc0d6ce49..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/CachingPipeline.java
+++ /dev/null
@@ -1,469 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.support.v8.renderscript.Allocation;
-import android.support.v8.renderscript.RenderScript;
-import android.util.Log;
-
-import com.android.gallery3d.filtershow.cache.ImageLoader;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.FiltersManager;
-import com.android.gallery3d.filtershow.imageshow.GeometryMathUtils;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-
-import java.util.Vector;
-
-public class CachingPipeline implements PipelineInterface {
- private static final String LOGTAG = "CachingPipeline";
- private boolean DEBUG = false;
-
- private static final Bitmap.Config BITMAP_CONFIG = Bitmap.Config.ARGB_8888;
-
- private static volatile RenderScript sRS = null;
-
- private FiltersManager mFiltersManager = null;
- private volatile Bitmap mOriginalBitmap = null;
- private volatile Bitmap mResizedOriginalBitmap = null;
-
- private FilterEnvironment mEnvironment = new FilterEnvironment();
- private CacheProcessing mCachedProcessing = new CacheProcessing();
-
-
- private volatile Allocation mOriginalAllocation = null;
- private volatile Allocation mFiltersOnlyOriginalAllocation = null;
-
- protected volatile Allocation mInPixelsAllocation;
- protected volatile Allocation mOutPixelsAllocation;
- private volatile int mWidth = 0;
- private volatile int mHeight = 0;
-
- private volatile float mPreviewScaleFactor = 1.0f;
- private volatile float mHighResPreviewScaleFactor = 1.0f;
- private volatile String mName = "";
-
- public CachingPipeline(FiltersManager filtersManager, String name) {
- mFiltersManager = filtersManager;
- mName = name;
- }
-
- public static synchronized RenderScript getRenderScriptContext() {
- return sRS;
- }
-
- public static synchronized void createRenderscriptContext(Context context) {
- if (sRS != null) {
- Log.w(LOGTAG, "A prior RS context exists when calling setRenderScriptContext");
- destroyRenderScriptContext();
- }
- sRS = RenderScript.create(context);
- }
-
- public static synchronized void destroyRenderScriptContext() {
- if (sRS != null) {
- sRS.destroy();
- }
- sRS = null;
- }
-
- public void stop() {
- mEnvironment.setStop(true);
- }
-
- public synchronized void reset() {
- synchronized (CachingPipeline.class) {
- if (getRenderScriptContext() == null) {
- return;
- }
- mOriginalBitmap = null; // just a reference to the bitmap in ImageLoader
- if (mResizedOriginalBitmap != null) {
- mResizedOriginalBitmap.recycle();
- mResizedOriginalBitmap = null;
- }
- if (mOriginalAllocation != null) {
- mOriginalAllocation.destroy();
- mOriginalAllocation = null;
- }
- if (mFiltersOnlyOriginalAllocation != null) {
- mFiltersOnlyOriginalAllocation.destroy();
- mFiltersOnlyOriginalAllocation = null;
- }
- mPreviewScaleFactor = 1.0f;
- mHighResPreviewScaleFactor = 1.0f;
-
- destroyPixelAllocations();
- }
- }
-
- public Resources getResources() {
- return sRS.getApplicationContext().getResources();
- }
-
- private synchronized void destroyPixelAllocations() {
- if (DEBUG) {
- Log.v(LOGTAG, "destroyPixelAllocations in " + getName());
- }
- if (mInPixelsAllocation != null) {
- mInPixelsAllocation.destroy();
- mInPixelsAllocation = null;
- }
- if (mOutPixelsAllocation != null) {
- mOutPixelsAllocation.destroy();
- mOutPixelsAllocation = null;
- }
- mWidth = 0;
- mHeight = 0;
- }
-
- private String getType(RenderingRequest request) {
- if (request.getType() == RenderingRequest.ICON_RENDERING) {
- return "ICON_RENDERING";
- }
- if (request.getType() == RenderingRequest.FILTERS_RENDERING) {
- return "FILTERS_RENDERING";
- }
- if (request.getType() == RenderingRequest.FULL_RENDERING) {
- return "FULL_RENDERING";
- }
- if (request.getType() == RenderingRequest.GEOMETRY_RENDERING) {
- return "GEOMETRY_RENDERING";
- }
- if (request.getType() == RenderingRequest.PARTIAL_RENDERING) {
- return "PARTIAL_RENDERING";
- }
- if (request.getType() == RenderingRequest.HIGHRES_RENDERING) {
- return "HIGHRES_RENDERING";
- }
- return "UNKNOWN TYPE!";
- }
-
- private void setupEnvironment(ImagePreset preset, boolean highResPreview) {
- mEnvironment.setPipeline(this);
- mEnvironment.setFiltersManager(mFiltersManager);
- if (highResPreview) {
- mEnvironment.setScaleFactor(mHighResPreviewScaleFactor);
- } else {
- mEnvironment.setScaleFactor(mPreviewScaleFactor);
- }
- mEnvironment.setQuality(FilterEnvironment.QUALITY_PREVIEW);
- mEnvironment.setImagePreset(preset);
- mEnvironment.setStop(false);
- }
-
- public void setOriginal(Bitmap bitmap) {
- mOriginalBitmap = bitmap;
- Log.v(LOGTAG,"setOriginal, size " + bitmap.getWidth() + " x " + bitmap.getHeight());
- ImagePreset preset = MasterImage.getImage().getPreset();
- setupEnvironment(preset, false);
- updateOriginalAllocation(preset);
- }
-
- private synchronized boolean updateOriginalAllocation(ImagePreset preset) {
- Bitmap originalBitmap = mOriginalBitmap;
-
- if (originalBitmap == null) {
- return false;
- }
-
- RenderScript RS = getRenderScriptContext();
-
- Allocation filtersOnlyOriginalAllocation = mFiltersOnlyOriginalAllocation;
- mFiltersOnlyOriginalAllocation = Allocation.createFromBitmap(RS, originalBitmap,
- Allocation.MipmapControl.MIPMAP_NONE, Allocation.USAGE_SCRIPT);
- if (filtersOnlyOriginalAllocation != null) {
- filtersOnlyOriginalAllocation.destroy();
- }
-
- Allocation originalAllocation = mOriginalAllocation;
- mResizedOriginalBitmap = preset.applyGeometry(originalBitmap, mEnvironment);
- mOriginalAllocation = Allocation.createFromBitmap(RS, mResizedOriginalBitmap,
- Allocation.MipmapControl.MIPMAP_NONE, Allocation.USAGE_SCRIPT);
- if (originalAllocation != null) {
- originalAllocation.destroy();
- }
-
- return true;
- }
-
- public void renderHighres(RenderingRequest request) {
- synchronized (CachingPipeline.class) {
- if (getRenderScriptContext() == null) {
- return;
- }
- ImagePreset preset = request.getImagePreset();
- setupEnvironment(preset, false);
- Bitmap bitmap = MasterImage.getImage().getOriginalBitmapHighres();
- if (bitmap == null) {
- return;
- }
- // TODO: use a cache of bitmaps
- bitmap = bitmap.copy(Bitmap.Config.ARGB_8888, true);
- bitmap = preset.applyGeometry(bitmap, mEnvironment);
-
- mEnvironment.setQuality(FilterEnvironment.QUALITY_PREVIEW);
- Bitmap bmp = preset.apply(bitmap, mEnvironment);
- if (!mEnvironment.needsStop()) {
- request.setBitmap(bmp);
- }
- mFiltersManager.freeFilterResources(preset);
- }
- }
-
- public synchronized void render(RenderingRequest request) {
- synchronized (CachingPipeline.class) {
- if (getRenderScriptContext() == null) {
- return;
- }
- if (((request.getType() != RenderingRequest.PARTIAL_RENDERING
- && request.getType() != RenderingRequest.HIGHRES_RENDERING)
- && request.getBitmap() == null)
- || request.getImagePreset() == null) {
- return;
- }
-
- if (DEBUG) {
- Log.v(LOGTAG, "render image of type " + getType(request));
- }
-
- Bitmap bitmap = request.getBitmap();
- ImagePreset preset = request.getImagePreset();
- setupEnvironment(preset,
- request.getType() != RenderingRequest.HIGHRES_RENDERING);
- mFiltersManager.freeFilterResources(preset);
-
- if (request.getType() == RenderingRequest.PARTIAL_RENDERING) {
- MasterImage master = MasterImage.getImage();
- bitmap = ImageLoader.getScaleOneImageForPreset(master.getActivity(),
- master.getUri(), request.getBounds(),
- request.getDestination());
- if (bitmap == null) {
- Log.w(LOGTAG, "could not get bitmap for: " + getType(request));
- return;
- }
- }
-
- if (request.getType() == RenderingRequest.HIGHRES_RENDERING) {
- bitmap = MasterImage.getImage().getOriginalBitmapHighres();
- if (bitmap != null) {
- bitmap = preset.applyGeometry(bitmap, mEnvironment);
- }
- }
-
- if (request.getType() == RenderingRequest.FULL_RENDERING
- || request.getType() == RenderingRequest.GEOMETRY_RENDERING
- || request.getType() == RenderingRequest.FILTERS_RENDERING) {
- updateOriginalAllocation(preset);
- }
-
- if (DEBUG) {
- Log.v(LOGTAG, "after update, req bitmap (" + bitmap.getWidth() + "x" + bitmap.getHeight()
- + " ? resizeOriginal (" + mResizedOriginalBitmap.getWidth() + "x"
- + mResizedOriginalBitmap.getHeight());
- }
-
- if (request.getType() == RenderingRequest.FULL_RENDERING
- || request.getType() == RenderingRequest.GEOMETRY_RENDERING) {
- mOriginalAllocation.copyTo(bitmap);
- } else if (request.getType() == RenderingRequest.FILTERS_RENDERING) {
- mFiltersOnlyOriginalAllocation.copyTo(bitmap);
- }
-
- if (request.getType() == RenderingRequest.FULL_RENDERING
- || request.getType() == RenderingRequest.FILTERS_RENDERING
- || request.getType() == RenderingRequest.ICON_RENDERING
- || request.getType() == RenderingRequest.PARTIAL_RENDERING
- || request.getType() == RenderingRequest.HIGHRES_RENDERING
- || request.getType() == RenderingRequest.STYLE_ICON_RENDERING) {
-
- if (request.getType() == RenderingRequest.ICON_RENDERING) {
- mEnvironment.setQuality(FilterEnvironment.QUALITY_ICON);
- } else {
- mEnvironment.setQuality(FilterEnvironment.QUALITY_PREVIEW);
- }
-
- Bitmap bmp = preset.apply(bitmap, mEnvironment);
- if (!mEnvironment.needsStop()) {
- request.setBitmap(bmp);
- }
- mFiltersManager.freeFilterResources(preset);
- }
- }
- }
-
- public synchronized void renderImage(ImagePreset preset, Allocation in, Allocation out) {
- synchronized (CachingPipeline.class) {
- if (getRenderScriptContext() == null) {
- return;
- }
- setupEnvironment(preset, false);
- mFiltersManager.freeFilterResources(preset);
- preset.applyFilters(-1, -1, in, out, mEnvironment);
- boolean copyOut = false;
- if (preset.nbFilters() > 0) {
- copyOut = true;
- }
- preset.applyBorder(in, out, copyOut, mEnvironment);
- }
- }
-
- public synchronized Bitmap renderFinalImage(Bitmap bitmap, ImagePreset preset) {
- synchronized (CachingPipeline.class) {
- if (getRenderScriptContext() == null) {
- return bitmap;
- }
- setupEnvironment(preset, false);
- mEnvironment.setQuality(FilterEnvironment.QUALITY_FINAL);
- mEnvironment.setScaleFactor(1.0f);
- mFiltersManager.freeFilterResources(preset);
- bitmap = preset.applyGeometry(bitmap, mEnvironment);
- bitmap = preset.apply(bitmap, mEnvironment);
- return bitmap;
- }
- }
-
- public Bitmap renderGeometryIcon(Bitmap bitmap, ImagePreset preset) {
- return GeometryMathUtils.applyGeometryRepresentations(preset.getGeometryFilters(), bitmap);
- }
-
- public void compute(SharedBuffer buffer, ImagePreset preset, int type) {
- if (getRenderScriptContext() == null) {
- return;
- }
- setupEnvironment(preset, false);
- Vector<FilterRepresentation> filters = preset.getFilters();
- Bitmap result = mCachedProcessing.process(mOriginalBitmap, filters, mEnvironment);
- buffer.setProducer(result);
- }
-
- public synchronized void computeOld(SharedBuffer buffer, ImagePreset preset, int type) {
- synchronized (CachingPipeline.class) {
- if (getRenderScriptContext() == null) {
- return;
- }
- if (DEBUG) {
- Log.v(LOGTAG, "compute preset " + preset);
- preset.showFilters();
- }
-
- String thread = Thread.currentThread().getName();
- long time = System.currentTimeMillis();
- setupEnvironment(preset, false);
- mFiltersManager.freeFilterResources(preset);
-
- Bitmap resizedOriginalBitmap = mResizedOriginalBitmap;
- if (updateOriginalAllocation(preset) || buffer.getProducer() == null) {
- resizedOriginalBitmap = mResizedOriginalBitmap;
- buffer.setProducer(resizedOriginalBitmap);
- mEnvironment.cache(buffer.getProducer());
- }
-
- Bitmap bitmap = buffer.getProducer().getBitmap();
- long time2 = System.currentTimeMillis();
-
- if (bitmap == null || (bitmap.getWidth() != resizedOriginalBitmap.getWidth())
- || (bitmap.getHeight() != resizedOriginalBitmap.getHeight())) {
- mEnvironment.cache(buffer.getProducer());
- buffer.setProducer(resizedOriginalBitmap);
- bitmap = buffer.getProducer().getBitmap();
- }
- mOriginalAllocation.copyTo(bitmap);
-
- Bitmap tmpbitmap = preset.apply(bitmap, mEnvironment);
- if (tmpbitmap != bitmap) {
- mEnvironment.cache(buffer.getProducer());
- buffer.setProducer(tmpbitmap);
- }
-
- mFiltersManager.freeFilterResources(preset);
-
- time = System.currentTimeMillis() - time;
- time2 = System.currentTimeMillis() - time2;
- if (DEBUG) {
- Log.v(LOGTAG, "Applying type " + type + " filters to bitmap "
- + bitmap + " (" + bitmap.getWidth() + " x " + bitmap.getHeight()
- + ") took " + time + " ms, " + time2 + " ms for the filter, on thread " + thread);
- }
- }
- }
-
- public boolean needsRepaint() {
- SharedBuffer buffer = MasterImage.getImage().getPreviewBuffer();
- return buffer.checkRepaintNeeded();
- }
-
- public void setPreviewScaleFactor(float previewScaleFactor) {
- mPreviewScaleFactor = previewScaleFactor;
- }
-
- public void setHighResPreviewScaleFactor(float highResPreviewScaleFactor) {
- mHighResPreviewScaleFactor = highResPreviewScaleFactor;
- }
-
- public synchronized boolean isInitialized() {
- return getRenderScriptContext() != null && mOriginalBitmap != null;
- }
-
- public boolean prepareRenderscriptAllocations(Bitmap bitmap) {
- RenderScript RS = getRenderScriptContext();
- boolean needsUpdate = false;
- if (mOutPixelsAllocation == null || mInPixelsAllocation == null ||
- bitmap.getWidth() != mWidth || bitmap.getHeight() != mHeight) {
- destroyPixelAllocations();
- Bitmap bitmapBuffer = bitmap;
- if (bitmap.getConfig() == null || bitmap.getConfig() != BITMAP_CONFIG) {
- bitmapBuffer = bitmap.copy(BITMAP_CONFIG, true);
- }
- mOutPixelsAllocation = Allocation.createFromBitmap(RS, bitmapBuffer,
- Allocation.MipmapControl.MIPMAP_NONE, Allocation.USAGE_SCRIPT);
- mInPixelsAllocation = Allocation.createTyped(RS,
- mOutPixelsAllocation.getType());
- needsUpdate = true;
- }
- if (RS != null) {
- mInPixelsAllocation.copyFrom(bitmap);
- }
- if (bitmap.getWidth() != mWidth
- || bitmap.getHeight() != mHeight) {
- mWidth = bitmap.getWidth();
- mHeight = bitmap.getHeight();
- needsUpdate = true;
- }
- if (DEBUG) {
- Log.v(LOGTAG, "prepareRenderscriptAllocations: " + needsUpdate + " in " + getName());
- }
- return needsUpdate;
- }
-
- public synchronized Allocation getInPixelsAllocation() {
- return mInPixelsAllocation;
- }
-
- public synchronized Allocation getOutPixelsAllocation() {
- return mOutPixelsAllocation;
- }
-
- public String getName() {
- return mName;
- }
-
- public RenderScript getRSContext() {
- return CachingPipeline.getRenderScriptContext();
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/FilterEnvironment.java b/src/com/android/gallery3d/filtershow/pipeline/FilterEnvironment.java
deleted file mode 100644
index 4fac956be..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/FilterEnvironment.java
+++ /dev/null
@@ -1,178 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Matrix;
-import android.graphics.Paint;
-import android.support.v8.renderscript.Allocation;
-
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterUserPresetRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRotateRepresentation.Rotation;
-import com.android.gallery3d.filtershow.filters.FiltersManagerInterface;
-import com.android.gallery3d.filtershow.filters.ImageFilter;
-
-import java.lang.ref.WeakReference;
-import java.util.HashMap;
-
-public class FilterEnvironment {
- private static final String LOGTAG = "FilterEnvironment";
- private ImagePreset mImagePreset;
- private float mScaleFactor;
- private int mQuality;
- private FiltersManagerInterface mFiltersManager;
- private PipelineInterface mPipeline;
- private volatile boolean mStop = false;
-
- public static final int QUALITY_ICON = 0;
- public static final int QUALITY_PREVIEW = 1;
- public static final int QUALITY_FINAL = 2;
-
- public synchronized boolean needsStop() {
- return mStop;
- }
-
- public synchronized void setStop(boolean stop) {
- this.mStop = stop;
- }
-
- private HashMap<Long, WeakReference<Bitmap>>
- bitmapCach = new HashMap<Long, WeakReference<Bitmap>>();
-
- private HashMap<Integer, Integer>
- generalParameters = new HashMap<Integer, Integer>();
-
- public void cache(Buffer buffer) {
- if (buffer == null) {
- return;
- }
- Bitmap bitmap = buffer.getBitmap();
- if (bitmap == null) {
- return;
- }
- Long key = calcKey(bitmap.getWidth(), bitmap.getHeight());
- bitmapCach.put(key, new WeakReference<Bitmap>(bitmap));
- }
-
- public Bitmap getBitmap(int w, int h) {
- Long key = calcKey(w, h);
- WeakReference<Bitmap> ref = bitmapCach.remove(key);
- Bitmap bitmap = null;
- if (ref != null) {
- bitmap = ref.get();
- }
- if (bitmap == null) {
- bitmap = Bitmap.createBitmap(
- w, h, Bitmap.Config.ARGB_8888);
- }
- return bitmap;
- }
-
- private Long calcKey(long w, long h) {
- return (w << 32) | (h << 32);
- }
-
- public void setImagePreset(ImagePreset imagePreset) {
- mImagePreset = imagePreset;
- }
-
- public ImagePreset getImagePreset() {
- return mImagePreset;
- }
-
- public void setScaleFactor(float scaleFactor) {
- mScaleFactor = scaleFactor;
- }
-
- public float getScaleFactor() {
- return mScaleFactor;
- }
-
- public void setQuality(int quality) {
- mQuality = quality;
- }
-
- public int getQuality() {
- return mQuality;
- }
-
- public void setFiltersManager(FiltersManagerInterface filtersManager) {
- mFiltersManager = filtersManager;
- }
-
- public FiltersManagerInterface getFiltersManager() {
- return mFiltersManager;
- }
-
- public void applyRepresentation(FilterRepresentation representation,
- Allocation in, Allocation out) {
- ImageFilter filter = mFiltersManager.getFilterForRepresentation(representation);
- filter.useRepresentation(representation);
- filter.setEnvironment(this);
- if (filter.supportsAllocationInput()) {
- filter.apply(in, out);
- }
- filter.setGeneralParameters();
- filter.setEnvironment(null);
- }
-
- public Bitmap applyRepresentation(FilterRepresentation representation, Bitmap bitmap) {
- if (representation instanceof FilterUserPresetRepresentation) {
- // we allow instances of FilterUserPresetRepresentation in a preset only to know if one
- // has been applied (so we can show this in the UI). But as all the filters in them are
- // applied directly they do not themselves need to do any kind of filtering.
- return bitmap;
- }
- ImageFilter filter = mFiltersManager.getFilterForRepresentation(representation);
- filter.useRepresentation(representation);
- filter.setEnvironment(this);
- Bitmap ret = filter.apply(bitmap, mScaleFactor, mQuality);
- filter.setGeneralParameters();
- filter.setEnvironment(null);
- return ret;
- }
-
- public PipelineInterface getPipeline() {
- return mPipeline;
- }
-
- public void setPipeline(PipelineInterface cachingPipeline) {
- mPipeline = cachingPipeline;
- }
-
- public synchronized void clearGeneralParameters() {
- generalParameters = null;
- }
-
- public synchronized Integer getGeneralParameter(int id) {
- if (generalParameters == null || !generalParameters.containsKey(id)) {
- return null;
- }
- return generalParameters.get(id);
- }
-
- public synchronized void setGeneralParameter(int id, int value) {
- if (generalParameters == null) {
- generalParameters = new HashMap<Integer, Integer>();
- }
-
- generalParameters.put(id, value);
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/HighresRenderingRequestTask.java b/src/com/android/gallery3d/filtershow/pipeline/HighresRenderingRequestTask.java
deleted file mode 100644
index 5a0eb4d45..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/HighresRenderingRequestTask.java
+++ /dev/null
@@ -1,90 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.graphics.Bitmap;
-import com.android.gallery3d.filtershow.filters.FiltersManager;
-
-public class HighresRenderingRequestTask extends ProcessingTask {
-
- private CachingPipeline mHighresPreviewPipeline = null;
- private boolean mPipelineIsOn = false;
-
- public void setHighresPreviewScaleFactor(float highResPreviewScale) {
- mHighresPreviewPipeline.setHighResPreviewScaleFactor(highResPreviewScale);
- }
-
- public void setPreviewScaleFactor(float previewScale) {
- mHighresPreviewPipeline.setPreviewScaleFactor(previewScale);
- }
-
- static class Render implements Request {
- RenderingRequest request;
- }
-
- static class RenderResult implements Result {
- RenderingRequest request;
- }
-
- public HighresRenderingRequestTask() {
- mHighresPreviewPipeline = new CachingPipeline(
- FiltersManager.getHighresManager(), "Highres");
- }
-
- public void setOriginal(Bitmap bitmap) {
- mHighresPreviewPipeline.setOriginal(bitmap);
- }
-
- public void setOriginalBitmapHighres(Bitmap originalHires) {
- mPipelineIsOn = true;
- }
-
- public void stop() {
- mHighresPreviewPipeline.stop();
- }
-
- public void postRenderingRequest(RenderingRequest request) {
- if (!mPipelineIsOn) {
- return;
- }
- Render render = new Render();
- render.request = request;
- postRequest(render);
- }
-
- @Override
- public Result doInBackground(Request message) {
- RenderingRequest request = ((Render) message).request;
- RenderResult result = null;
- mHighresPreviewPipeline.renderHighres(request);
- result = new RenderResult();
- result.request = request;
- return result;
- }
-
- @Override
- public void onResult(Result message) {
- if (message == null) {
- return;
- }
- RenderingRequest request = ((RenderResult) message).request;
- request.markAvailable();
- }
-
- @Override
- public boolean isDelayedTask() { return true; }
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/ImagePreset.java b/src/com/android/gallery3d/filtershow/pipeline/ImagePreset.java
deleted file mode 100644
index d34216ad6..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/ImagePreset.java
+++ /dev/null
@@ -1,694 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.graphics.Bitmap;
-import android.graphics.Rect;
-import android.support.v8.renderscript.Allocation;
-import android.util.JsonReader;
-import android.util.JsonWriter;
-import android.util.Log;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.cache.ImageLoader;
-import com.android.gallery3d.filtershow.filters.BaseFiltersManager;
-import com.android.gallery3d.filtershow.filters.FilterCropRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterFxRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterImageBorderRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterMirrorRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRotateRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterStraightenRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterUserPresetRepresentation;
-import com.android.gallery3d.filtershow.filters.FiltersManager;
-import com.android.gallery3d.filtershow.filters.ImageFilter;
-import com.android.gallery3d.filtershow.imageshow.GeometryMathUtils;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.state.State;
-import com.android.gallery3d.filtershow.state.StateAdapter;
-import com.android.gallery3d.util.UsageStatistics;
-
-import java.io.IOException;
-import java.io.StringReader;
-import java.io.StringWriter;
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Vector;
-
-public class ImagePreset {
-
- private static final String LOGTAG = "ImagePreset";
-
- private Vector<FilterRepresentation> mFilters = new Vector<FilterRepresentation>();
-
- private boolean mDoApplyGeometry = true;
- private boolean mDoApplyFilters = true;
-
- private boolean mPartialRendering = false;
- private Rect mPartialRenderingBounds;
- private static final boolean DEBUG = false;
-
- public ImagePreset() {
- }
-
- public ImagePreset(ImagePreset source) {
- for (int i = 0; i < source.mFilters.size(); i++) {
- FilterRepresentation sourceRepresentation = source.mFilters.elementAt(i);
- mFilters.add(sourceRepresentation.copy());
- }
- }
-
- public Vector<FilterRepresentation> getFilters() {
- return mFilters;
- }
-
- public FilterRepresentation getFilterRepresentation(int position) {
- FilterRepresentation representation = null;
-
- representation = mFilters.elementAt(position).copy();
-
- return representation;
- }
-
- private static boolean sameSerializationName(String a, String b) {
- if (a != null && b != null) {
- return a.equals(b);
- } else {
- return a == null && b == null;
- }
- }
-
- public static boolean sameSerializationName(FilterRepresentation a, FilterRepresentation b) {
- if (a == null || b == null) {
- return false;
- }
- return sameSerializationName(a.getSerializationName(), b.getSerializationName());
- }
-
- public int getPositionForRepresentation(FilterRepresentation representation) {
- for (int i = 0; i < mFilters.size(); i++) {
- if (sameSerializationName(mFilters.elementAt(i), representation)) {
- return i;
- }
- }
- return -1;
- }
-
- private FilterRepresentation getFilterRepresentationForType(int type) {
- for (int i = 0; i < mFilters.size(); i++) {
- if (mFilters.elementAt(i).getFilterType() == type) {
- return mFilters.elementAt(i);
- }
- }
- return null;
- }
-
- public int getPositionForType(int type) {
- for (int i = 0; i < mFilters.size(); i++) {
- if (mFilters.elementAt(i).getFilterType() == type) {
- return i;
- }
- }
- return -1;
- }
-
- public FilterRepresentation getFilterRepresentationCopyFrom(
- FilterRepresentation filterRepresentation) {
- // TODO: add concept of position in the filters (to allow multiple instances)
- if (filterRepresentation == null) {
- return null;
- }
- int position = getPositionForRepresentation(filterRepresentation);
- if (position == -1) {
- return null;
- }
- FilterRepresentation representation = mFilters.elementAt(position);
- if (representation != null) {
- representation = representation.copy();
- }
- return representation;
- }
-
- public void updateFilterRepresentations(Collection<FilterRepresentation> reps) {
- for (FilterRepresentation r : reps) {
- updateOrAddFilterRepresentation(r);
- }
- }
-
- public void updateOrAddFilterRepresentation(FilterRepresentation rep) {
- int pos = getPositionForRepresentation(rep);
- if (pos != -1) {
- mFilters.elementAt(pos).useParametersFrom(rep);
- } else {
- addFilter(rep.copy());
- }
- }
-
- public void setDoApplyGeometry(boolean value) {
- mDoApplyGeometry = value;
- }
-
- public void setDoApplyFilters(boolean value) {
- mDoApplyFilters = value;
- }
-
- public boolean getDoApplyFilters() {
- return mDoApplyFilters;
- }
-
- public boolean hasModifications() {
- for (int i = 0; i < mFilters.size(); i++) {
- FilterRepresentation filter = mFilters.elementAt(i);
- if (!filter.isNil()) {
- return true;
- }
- }
- return false;
- }
-
- public boolean isPanoramaSafe() {
- for (FilterRepresentation representation : mFilters) {
- if (representation.getFilterType() == FilterRepresentation.TYPE_GEOMETRY
- && !representation.isNil()) {
- return false;
- }
- if (representation.getFilterType() == FilterRepresentation.TYPE_BORDER
- && !representation.isNil()) {
- return false;
- }
- if (representation.getFilterType() == FilterRepresentation.TYPE_VIGNETTE
- && !representation.isNil()) {
- return false;
- }
- if (representation.getFilterType() == FilterRepresentation.TYPE_TINYPLANET
- && !representation.isNil()) {
- return false;
- }
- }
- return true;
- }
-
- public boolean same(ImagePreset preset) {
- if (preset == null) {
- return false;
- }
-
- if (preset.mFilters.size() != mFilters.size()) {
- return false;
- }
-
- if (mDoApplyGeometry != preset.mDoApplyGeometry) {
- return false;
- }
-
- if (mDoApplyFilters != preset.mDoApplyFilters) {
- if (mFilters.size() > 0 || preset.mFilters.size() > 0) {
- return false;
- }
- }
-
- if (mDoApplyFilters && preset.mDoApplyFilters) {
- for (int i = 0; i < preset.mFilters.size(); i++) {
- FilterRepresentation a = preset.mFilters.elementAt(i);
- FilterRepresentation b = mFilters.elementAt(i);
-
- if (!a.same(b)) {
- return false;
- }
- }
- }
-
- return true;
- }
-
- public int similarUpTo(ImagePreset preset) {
- for (int i = 0; i < preset.mFilters.size(); i++) {
- FilterRepresentation a = preset.mFilters.elementAt(i);
- if (i < mFilters.size()) {
- FilterRepresentation b = mFilters.elementAt(i);
- if (!a.same(b)) {
- return i;
- }
- if (!a.equals(b)) {
- return i;
- }
- } else {
- return i;
- }
- }
- return preset.mFilters.size();
- }
-
- public void showFilters() {
- Log.v(LOGTAG, "\\\\\\ showFilters -- " + mFilters.size() + " filters");
- int n = 0;
- for (FilterRepresentation representation : mFilters) {
- Log.v(LOGTAG, " filter " + n + " : " + representation.toString());
- n++;
- }
- Log.v(LOGTAG, "/// showFilters -- " + mFilters.size() + " filters");
- }
-
- public FilterRepresentation getLastRepresentation() {
- if (mFilters.size() > 0) {
- return mFilters.lastElement();
- }
- return null;
- }
-
- public void removeFilter(FilterRepresentation filterRepresentation) {
- if (filterRepresentation.getFilterType() == FilterRepresentation.TYPE_BORDER) {
- for (int i = 0; i < mFilters.size(); i++) {
- if (mFilters.elementAt(i).getFilterType()
- == filterRepresentation.getFilterType()) {
- mFilters.remove(i);
- break;
- }
- }
- } else {
- for (int i = 0; i < mFilters.size(); i++) {
- if (sameSerializationName(mFilters.elementAt(i), filterRepresentation)) {
- mFilters.remove(i);
- break;
- }
- }
- }
- }
-
- // If the filter is an "None" effect or border, then just don't add this filter.
- public void addFilter(FilterRepresentation representation) {
- if (representation instanceof FilterUserPresetRepresentation) {
- ImagePreset preset = ((FilterUserPresetRepresentation) representation).getImagePreset();
- // user preset replace everything but geometry
- mFilters.clear();
- for (int i = 0; i < preset.nbFilters(); i++) {
- addFilter(preset.getFilterRepresentation(i));
- }
- mFilters.add(representation);
- } else if (representation.getFilterType() == FilterRepresentation.TYPE_GEOMETRY) {
- // Add geometry filter, removing duplicates and do-nothing operations.
- for (int i = 0; i < mFilters.size(); i++) {
- if (sameSerializationName(representation, mFilters.elementAt(i))) {
- mFilters.remove(i);
- }
- }
- if (!representation.isNil()) {
- mFilters.add(representation);
- }
- } else if (representation.getFilterType() == FilterRepresentation.TYPE_BORDER) {
- removeFilter(representation);
- if (!isNoneBorderFilter(representation)) {
- mFilters.add(representation);
- }
- } else if (representation.getFilterType() == FilterRepresentation.TYPE_FX) {
- boolean found = false;
- for (int i = 0; i < mFilters.size(); i++) {
- FilterRepresentation current = mFilters.elementAt(i);
- int type = current.getFilterType();
- if (found) {
- if (type != FilterRepresentation.TYPE_VIGNETTE) {
- mFilters.remove(i);
- continue;
- }
- }
- if (type == FilterRepresentation.TYPE_FX) {
- if (current instanceof FilterUserPresetRepresentation) {
- ImagePreset preset = ((FilterUserPresetRepresentation) current)
- .getImagePreset();
- // If we had an existing user preset, let's remove all the presets that
- // were added by it
- for (int j = 0; j < preset.nbFilters(); j++) {
- FilterRepresentation rep = preset.getFilterRepresentation(j);
- int pos = getPositionForRepresentation(rep);
- if (pos != -1) {
- mFilters.remove(pos);
- }
- }
- int pos = getPositionForRepresentation(current);
- if (pos != -1) {
- mFilters.remove(pos);
- } else {
- pos = 0;
- }
- if (!isNoneFxFilter(representation)) {
- mFilters.add(pos, representation);
- }
-
- } else {
- mFilters.remove(i);
- if (!isNoneFxFilter(representation)) {
- mFilters.add(i, representation);
- }
- }
- found = true;
- }
- }
- if (!found) {
- if (!isNoneFxFilter(representation)) {
- mFilters.add(representation);
- }
- }
- } else {
- mFilters.add(representation);
- }
- }
-
- private boolean isNoneBorderFilter(FilterRepresentation representation) {
- return representation instanceof FilterImageBorderRepresentation &&
- ((FilterImageBorderRepresentation) representation).getDrawableResource() == 0;
- }
-
- private boolean isNoneFxFilter(FilterRepresentation representation) {
- return representation instanceof FilterFxRepresentation &&
- ((FilterFxRepresentation) representation).getNameResource() == R.string.none;
- }
-
- public FilterRepresentation getRepresentation(FilterRepresentation filterRepresentation) {
- for (int i = 0; i < mFilters.size(); i++) {
- FilterRepresentation representation = mFilters.elementAt(i);
- if (sameSerializationName(representation, filterRepresentation)) {
- return representation;
- }
- }
- return null;
- }
-
- public Bitmap apply(Bitmap original, FilterEnvironment environment) {
- Bitmap bitmap = original;
- bitmap = applyFilters(bitmap, -1, -1, environment);
- return applyBorder(bitmap, environment);
- }
-
- public Collection<FilterRepresentation> getGeometryFilters() {
- ArrayList<FilterRepresentation> geometry = new ArrayList<FilterRepresentation>();
- for (FilterRepresentation r : mFilters) {
- if (r.getFilterType() == FilterRepresentation.TYPE_GEOMETRY) {
- geometry.add(r);
- }
- }
- return geometry;
- }
-
- public FilterRepresentation getFilterWithSerializationName(String serializationName) {
- for (FilterRepresentation r : mFilters) {
- if (r != null) {
- if (sameSerializationName(r.getSerializationName(), serializationName)) {
- return r.copy();
- }
- }
- }
- return null;
- }
-
- public Bitmap applyGeometry(Bitmap bitmap, FilterEnvironment environment) {
- // Apply any transform -- 90 rotate, flip, straighten, crop
- // Returns a new bitmap.
- if (mDoApplyGeometry) {
- bitmap = GeometryMathUtils.applyGeometryRepresentations(getGeometryFilters(), bitmap);
- }
- return bitmap;
- }
-
- public Bitmap applyBorder(Bitmap bitmap, FilterEnvironment environment) {
- // get the border from the list of filters.
- FilterRepresentation border = getFilterRepresentationForType(
- FilterRepresentation.TYPE_BORDER);
- if (border != null && mDoApplyGeometry) {
- bitmap = environment.applyRepresentation(border, bitmap);
- if (environment.getQuality() == FilterEnvironment.QUALITY_FINAL) {
- UsageStatistics.onEvent(UsageStatistics.COMPONENT_EDITOR,
- "SaveBorder", border.getSerializationName(), 1);
- }
- }
- return bitmap;
- }
-
- public int nbFilters() {
- return mFilters.size();
- }
-
- public Bitmap applyFilters(Bitmap bitmap, int from, int to, FilterEnvironment environment) {
- if (mDoApplyFilters) {
- if (from < 0) {
- from = 0;
- }
- if (to == -1) {
- to = mFilters.size();
- }
- if (environment.getQuality() == FilterEnvironment.QUALITY_FINAL) {
- UsageStatistics.onEvent(UsageStatistics.COMPONENT_EDITOR,
- "SaveFilters", "Total", to - from + 1);
- }
- for (int i = from; i < to; i++) {
- FilterRepresentation representation = mFilters.elementAt(i);
- if (representation.getFilterType() == FilterRepresentation.TYPE_GEOMETRY) {
- // skip the geometry as it's already applied.
- continue;
- }
- if (representation.getFilterType() == FilterRepresentation.TYPE_BORDER) {
- // for now, let's skip the border as it will be applied in
- // applyBorder()
- // TODO: might be worth getting rid of applyBorder.
- continue;
- }
- bitmap = environment.applyRepresentation(representation, bitmap);
- if (environment.getQuality() == FilterEnvironment.QUALITY_FINAL) {
- UsageStatistics.onEvent(UsageStatistics.COMPONENT_EDITOR,
- "SaveFilter", representation.getSerializationName(), 1);
- }
- if (environment.needsStop()) {
- return bitmap;
- }
- }
- }
-
- return bitmap;
- }
-
- public void applyBorder(Allocation in, Allocation out,
- boolean copyOut, FilterEnvironment environment) {
- FilterRepresentation border = getFilterRepresentationForType(
- FilterRepresentation.TYPE_BORDER);
- if (border != null && mDoApplyGeometry) {
- // TODO: should keep the bitmap around
- Allocation bitmapIn = in;
- if (copyOut) {
- bitmapIn = Allocation.createTyped(
- CachingPipeline.getRenderScriptContext(), in.getType());
- bitmapIn.copyFrom(out);
- }
- environment.applyRepresentation(border, bitmapIn, out);
- }
- }
-
- public void applyFilters(int from, int to, Allocation in, Allocation out,
- FilterEnvironment environment) {
- if (mDoApplyFilters) {
- if (from < 0) {
- from = 0;
- }
- if (to == -1) {
- to = mFilters.size();
- }
- for (int i = from; i < to; i++) {
- FilterRepresentation representation = mFilters.elementAt(i);
- if (representation.getFilterType() == FilterRepresentation.TYPE_GEOMETRY
- || representation.getFilterType() == FilterRepresentation.TYPE_BORDER) {
- continue;
- }
- if (i > from) {
- in.copyFrom(out);
- }
- environment.applyRepresentation(representation, in, out);
- }
- }
- }
-
- public boolean canDoPartialRendering() {
- if (MasterImage.getImage().getZoomOrientation() != ImageLoader.ORI_NORMAL) {
- return false;
- }
- for (int i = 0; i < mFilters.size(); i++) {
- FilterRepresentation representation = mFilters.elementAt(i);
- if (representation.getFilterType() == FilterRepresentation.TYPE_GEOMETRY
- && !representation.isNil()) {
- return false;
- }
- if (!representation.supportsPartialRendering()) {
- return false;
- }
- }
- return true;
- }
-
- public void fillImageStateAdapter(StateAdapter imageStateAdapter) {
- if (imageStateAdapter == null) {
- return;
- }
- Vector<State> states = new Vector<State>();
- for (FilterRepresentation filter : mFilters) {
- if (filter.getFilterType() == FilterRepresentation.TYPE_GEOMETRY) {
- // TODO: supports Geometry representations in the state panel.
- continue;
- }
- if (filter instanceof FilterUserPresetRepresentation) {
- // do not show the user preset itself in the state panel
- continue;
- }
- State state = new State(filter.getName());
- state.setFilterRepresentation(filter);
- states.add(state);
- }
- imageStateAdapter.fill(states);
- }
-
- public void setPartialRendering(boolean partialRendering, Rect bounds) {
- mPartialRendering = partialRendering;
- mPartialRenderingBounds = bounds;
- }
-
- public boolean isPartialRendering() {
- return mPartialRendering;
- }
-
- public Rect getPartialRenderingBounds() {
- return mPartialRenderingBounds;
- }
-
- public Vector<ImageFilter> getUsedFilters(BaseFiltersManager filtersManager) {
- Vector<ImageFilter> usedFilters = new Vector<ImageFilter>();
- for (int i = 0; i < mFilters.size(); i++) {
- FilterRepresentation representation = mFilters.elementAt(i);
- ImageFilter filter = filtersManager.getFilterForRepresentation(representation);
- usedFilters.add(filter);
- }
- return usedFilters;
- }
-
- public String getJsonString(String name) {
- StringWriter swriter = new StringWriter();
- try {
- JsonWriter writer = new JsonWriter(swriter);
- writeJson(writer, name);
- writer.close();
- } catch (IOException e) {
- return null;
- }
- return swriter.toString();
- }
-
- public void writeJson(JsonWriter writer, String name) {
- int numFilters = mFilters.size();
- try {
- writer.beginObject();
- for (int i = 0; i < numFilters; i++) {
- FilterRepresentation filter = mFilters.get(i);
- if (filter instanceof FilterUserPresetRepresentation) {
- continue;
- }
- String sname = filter.getSerializationName();
- if (DEBUG) {
- Log.v(LOGTAG, "Serialization: " + sname);
- if (sname == null) {
- Log.v(LOGTAG, "Serialization name null for filter: " + filter);
- }
- }
- writer.name(sname);
- filter.serializeRepresentation(writer);
- }
- writer.endObject();
-
- } catch (IOException e) {
- Log.e(LOGTAG,"Error encoding JASON",e);
- }
- }
-
- /**
- * populates preset from JSON string
- *
- * @param filterString a JSON string
- * @return true on success if false ImagePreset is undefined
- */
- public boolean readJsonFromString(String filterString) {
- if (DEBUG) {
- Log.v(LOGTAG, "reading preset: \"" + filterString + "\"");
- }
- StringReader sreader = new StringReader(filterString);
- try {
- JsonReader reader = new JsonReader(sreader);
- boolean ok = readJson(reader);
- if (!ok) {
- reader.close();
- return false;
- }
- reader.close();
- } catch (Exception e) {
- Log.e(LOGTAG, "parsing the filter parameters:", e);
- return false;
- }
- return true;
- }
-
- /**
- * populates preset from JSON stream
- *
- * @param sreader a JSON string
- * @return true on success if false ImagePreset is undefined
- */
- public boolean readJson(JsonReader sreader) throws IOException {
- sreader.beginObject();
-
- while (sreader.hasNext()) {
- String name = sreader.nextName();
- FilterRepresentation filter = creatFilterFromName(name);
- if (filter == null) {
- Log.w(LOGTAG, "UNKNOWN FILTER! " + name);
- return false;
- }
- filter.deSerializeRepresentation(sreader);
- addFilter(filter);
- }
- sreader.endObject();
- return true;
- }
-
- FilterRepresentation creatFilterFromName(String name) {
- if (FilterRotateRepresentation.SERIALIZATION_NAME.equals(name)) {
- return new FilterRotateRepresentation();
- } else if (FilterMirrorRepresentation.SERIALIZATION_NAME.equals(name)) {
- return new FilterMirrorRepresentation();
- } else if (FilterStraightenRepresentation.SERIALIZATION_NAME.equals(name)) {
- return new FilterStraightenRepresentation();
- } else if (FilterCropRepresentation.SERIALIZATION_NAME.equals(name)) {
- return new FilterCropRepresentation();
- }
- FiltersManager filtersManager = FiltersManager.getManager();
- return filtersManager.createFilterFromName(name);
- }
-
- public void updateWith(ImagePreset preset) {
- if (preset.mFilters.size() != mFilters.size()) {
- Log.e(LOGTAG, "Updating a preset with an incompatible one");
- return;
- }
- for (int i = 0; i < mFilters.size(); i++) {
- FilterRepresentation destRepresentation = mFilters.elementAt(i);
- FilterRepresentation sourceRepresentation = preset.mFilters.elementAt(i);
- destRepresentation.useParametersFrom(sourceRepresentation);
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/ImageSavingTask.java b/src/com/android/gallery3d/filtershow/pipeline/ImageSavingTask.java
deleted file mode 100644
index b760edd5a..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/ImageSavingTask.java
+++ /dev/null
@@ -1,125 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.net.Uri;
-import com.android.gallery3d.filtershow.cache.ImageLoader;
-import com.android.gallery3d.filtershow.filters.FiltersManager;
-import com.android.gallery3d.filtershow.tools.SaveImage;
-
-import java.io.File;
-
-public class ImageSavingTask extends ProcessingTask {
- private ProcessingService mProcessingService;
-
- static class SaveRequest implements Request {
- Uri sourceUri;
- Uri selectedUri;
- File destinationFile;
- ImagePreset preset;
- boolean flatten;
- int quality;
- }
-
- static class UpdateBitmap implements Update {
- Bitmap bitmap;
- }
-
- static class UpdateProgress implements Update {
- int max;
- int current;
- }
-
- static class URIResult implements Result {
- Uri uri;
- }
-
- public ImageSavingTask(ProcessingService service) {
- mProcessingService = service;
- }
-
- public void saveImage(Uri sourceUri, Uri selectedUri,
- File destinationFile, ImagePreset preset, boolean flatten, int quality) {
- SaveRequest request = new SaveRequest();
- request.sourceUri = sourceUri;
- request.selectedUri = selectedUri;
- request.destinationFile = destinationFile;
- request.preset = preset;
- request.flatten = flatten;
- request.quality = quality;
- postRequest(request);
- }
-
- public Result doInBackground(Request message) {
- SaveRequest request = (SaveRequest) message;
- Uri sourceUri = request.sourceUri;
- Uri selectedUri = request.selectedUri;
- File destinationFile = request.destinationFile;
- ImagePreset preset = request.preset;
- boolean flatten = request.flatten;
- // We create a small bitmap showing the result that we can
- // give to the notification
- UpdateBitmap updateBitmap = new UpdateBitmap();
- updateBitmap.bitmap = createNotificationBitmap(sourceUri, preset);
- postUpdate(updateBitmap);
- SaveImage saveImage = new SaveImage(mProcessingService, sourceUri,
- selectedUri, destinationFile,
- new SaveImage.Callback() {
- @Override
- public void onProgress(int max, int current) {
- UpdateProgress updateProgress = new UpdateProgress();
- updateProgress.max = max;
- updateProgress.current = current;
- postUpdate(updateProgress);
- }
- });
- Uri uri = saveImage.processAndSaveImage(preset, !flatten, request.quality);
- URIResult result = new URIResult();
- result.uri = uri;
- return result;
- }
-
- @Override
- public void onResult(Result message) {
- URIResult result = (URIResult) message;
- mProcessingService.completeSaveImage(result.uri);
- }
-
- @Override
- public void onUpdate(Update message) {
- if (message instanceof UpdateBitmap) {
- Bitmap bitmap = ((UpdateBitmap) message).bitmap;
- mProcessingService.updateNotificationWithBitmap(bitmap);
- }
- if (message instanceof UpdateProgress) {
- UpdateProgress progress = (UpdateProgress) message;
- mProcessingService.updateProgress(progress.max, progress.current);
- }
- }
-
- private Bitmap createNotificationBitmap(Uri sourceUri, ImagePreset preset) {
- int notificationBitmapSize = Resources.getSystem().getDimensionPixelSize(
- android.R.dimen.notification_large_icon_width);
- Bitmap bitmap = ImageLoader.loadConstrainedBitmap(sourceUri, getContext(),
- notificationBitmapSize, null, true);
- CachingPipeline pipeline = new CachingPipeline(FiltersManager.getManager(), "Thumb");
- return pipeline.renderFinalImage(bitmap, preset);
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/PipelineInterface.java b/src/com/android/gallery3d/filtershow/pipeline/PipelineInterface.java
deleted file mode 100644
index d53768c95..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/PipelineInterface.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.support.v8.renderscript.Allocation;
-import android.support.v8.renderscript.RenderScript;
-
-public interface PipelineInterface {
- public String getName();
- public Resources getResources();
- public Allocation getInPixelsAllocation();
- public Allocation getOutPixelsAllocation();
- public boolean prepareRenderscriptAllocations(Bitmap bitmap);
- public RenderScript getRSContext();
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/ProcessingService.java b/src/com/android/gallery3d/filtershow/pipeline/ProcessingService.java
deleted file mode 100644
index d0504d11f..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/ProcessingService.java
+++ /dev/null
@@ -1,283 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.app.Notification;
-import android.app.NotificationManager;
-import android.app.Service;
-import android.content.Context;
-import android.content.Intent;
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.net.Uri;
-import android.os.Binder;
-import android.os.IBinder;
-import android.util.Log;
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.filters.FiltersManager;
-import com.android.gallery3d.filtershow.filters.ImageFilter;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.tools.SaveImage;
-
-import java.io.File;
-
-public class ProcessingService extends Service {
- private static final String LOGTAG = "ProcessingService";
- private static final boolean SHOW_IMAGE = false;
- private int mNotificationId;
- private NotificationManager mNotifyMgr = null;
- private Notification.Builder mBuilder = null;
-
- private static final String PRESET = "preset";
- private static final String QUALITY = "quality";
- private static final String SOURCE_URI = "sourceUri";
- private static final String SELECTED_URI = "selectedUri";
- private static final String DESTINATION_FILE = "destinationFile";
- private static final String SAVING = "saving";
- private static final String FLATTEN = "flatten";
-
- private ProcessingTaskController mProcessingTaskController;
- private ImageSavingTask mImageSavingTask;
- private UpdatePreviewTask mUpdatePreviewTask;
- private HighresRenderingRequestTask mHighresRenderingRequestTask;
- private RenderingRequestTask mRenderingRequestTask;
-
- private final IBinder mBinder = new LocalBinder();
- private FilterShowActivity mFiltershowActivity;
-
- private boolean mSaving = false;
- private boolean mNeedsAlive = false;
-
- public void setFiltershowActivity(FilterShowActivity filtershowActivity) {
- mFiltershowActivity = filtershowActivity;
- }
-
- public void setOriginalBitmap(Bitmap originalBitmap) {
- if (mUpdatePreviewTask == null) {
- return;
- }
- mUpdatePreviewTask.setOriginal(originalBitmap);
- mHighresRenderingRequestTask.setOriginal(originalBitmap);
- mRenderingRequestTask.setOriginal(originalBitmap);
- }
-
- public void updatePreviewBuffer() {
- mHighresRenderingRequestTask.stop();
- mUpdatePreviewTask.updatePreview();
- }
-
- public void postRenderingRequest(RenderingRequest request) {
- mRenderingRequestTask.postRenderingRequest(request);
- }
-
- public void postHighresRenderingRequest(ImagePreset preset, float scaleFactor,
- RenderingRequestCaller caller) {
- RenderingRequest request = new RenderingRequest();
- // TODO: use the triple buffer preset as UpdatePreviewTask does instead of creating a copy
- ImagePreset passedPreset = new ImagePreset(preset);
- request.setOriginalImagePreset(preset);
- request.setScaleFactor(scaleFactor);
- request.setImagePreset(passedPreset);
- request.setType(RenderingRequest.HIGHRES_RENDERING);
- request.setCaller(caller);
- mHighresRenderingRequestTask.postRenderingRequest(request);
- }
-
- public void setHighresPreviewScaleFactor(float highResPreviewScale) {
- mHighresRenderingRequestTask.setHighresPreviewScaleFactor(highResPreviewScale);
- }
-
- public void setPreviewScaleFactor(float previewScale) {
- mHighresRenderingRequestTask.setPreviewScaleFactor(previewScale);
- mRenderingRequestTask.setPreviewScaleFactor(previewScale);
- }
-
- public void setOriginalBitmapHighres(Bitmap originalHires) {
- mHighresRenderingRequestTask.setOriginalBitmapHighres(originalHires);
- }
-
- public class LocalBinder extends Binder {
- public ProcessingService getService() {
- return ProcessingService.this;
- }
- }
-
- public static Intent getSaveIntent(Context context, ImagePreset preset, File destination,
- Uri selectedImageUri, Uri sourceImageUri, boolean doFlatten, int quality) {
- Intent processIntent = new Intent(context, ProcessingService.class);
- processIntent.putExtra(ProcessingService.SOURCE_URI,
- sourceImageUri.toString());
- processIntent.putExtra(ProcessingService.SELECTED_URI,
- selectedImageUri.toString());
- processIntent.putExtra(ProcessingService.QUALITY, quality);
- if (destination != null) {
- processIntent.putExtra(ProcessingService.DESTINATION_FILE, destination.toString());
- }
- processIntent.putExtra(ProcessingService.PRESET,
- preset.getJsonString(context.getString(R.string.saved)));
- processIntent.putExtra(ProcessingService.SAVING, true);
- if (doFlatten) {
- processIntent.putExtra(ProcessingService.FLATTEN, true);
- }
- return processIntent;
- }
-
-
- @Override
- public void onCreate() {
- mProcessingTaskController = new ProcessingTaskController(this);
- mImageSavingTask = new ImageSavingTask(this);
- mUpdatePreviewTask = new UpdatePreviewTask();
- mHighresRenderingRequestTask = new HighresRenderingRequestTask();
- mRenderingRequestTask = new RenderingRequestTask();
- mProcessingTaskController.add(mImageSavingTask);
- mProcessingTaskController.add(mUpdatePreviewTask);
- mProcessingTaskController.add(mHighresRenderingRequestTask);
- mProcessingTaskController.add(mRenderingRequestTask);
- setupPipeline();
- }
-
- @Override
- public void onDestroy() {
- tearDownPipeline();
- mProcessingTaskController.quit();
- }
-
- @Override
- public int onStartCommand(Intent intent, int flags, int startId) {
- mNeedsAlive = true;
- if (intent != null && intent.getBooleanExtra(SAVING, false)) {
- // we save using an intent to keep the service around after the
- // activity has been destroyed.
- String presetJson = intent.getStringExtra(PRESET);
- String source = intent.getStringExtra(SOURCE_URI);
- String selected = intent.getStringExtra(SELECTED_URI);
- String destination = intent.getStringExtra(DESTINATION_FILE);
- int quality = intent.getIntExtra(QUALITY, 100);
- boolean flatten = intent.getBooleanExtra(FLATTEN, false);
- Uri sourceUri = Uri.parse(source);
- Uri selectedUri = null;
- if (selected != null) {
- selectedUri = Uri.parse(selected);
- }
- File destinationFile = null;
- if (destination != null) {
- destinationFile = new File(destination);
- }
- ImagePreset preset = new ImagePreset();
- preset.readJsonFromString(presetJson);
- mNeedsAlive = false;
- mSaving = true;
- handleSaveRequest(sourceUri, selectedUri, destinationFile, preset, flatten, quality);
- }
- return START_REDELIVER_INTENT;
- }
-
- @Override
- public IBinder onBind(Intent intent) {
- return mBinder;
- }
-
- public void onStart() {
- mNeedsAlive = true;
- if (!mSaving && mFiltershowActivity != null) {
- mFiltershowActivity.updateUIAfterServiceStarted();
- }
- }
-
- public void handleSaveRequest(Uri sourceUri, Uri selectedUri,
- File destinationFile, ImagePreset preset, boolean flatten, int quality) {
- mNotifyMgr = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
-
- mNotificationId++;
-
- mBuilder =
- new Notification.Builder(this)
- .setSmallIcon(R.drawable.filtershow_button_fx)
- .setContentTitle(getString(R.string.filtershow_notification_label))
- .setContentText(getString(R.string.filtershow_notification_message));
-
- startForeground(mNotificationId, mBuilder.build());
-
- updateProgress(SaveImage.MAX_PROCESSING_STEPS, 0);
-
- // Process the image
-
- mImageSavingTask.saveImage(sourceUri, selectedUri, destinationFile,
- preset, flatten, quality);
- }
-
- public void updateNotificationWithBitmap(Bitmap bitmap) {
- mBuilder.setLargeIcon(bitmap);
- mNotifyMgr.notify(mNotificationId, mBuilder.build());
- }
-
- public void updateProgress(int max, int current) {
- mBuilder.setProgress(max, current, false);
- mNotifyMgr.notify(mNotificationId, mBuilder.build());
- }
-
- public void completeSaveImage(Uri result) {
- if (SHOW_IMAGE) {
- // TODO: we should update the existing image in Gallery instead
- Intent viewImage = new Intent(Intent.ACTION_VIEW, result);
- viewImage.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
- startActivity(viewImage);
- }
- stopForeground(true);
- stopSelf();
- if (mNeedsAlive) {
- // If the app has been restarted while we were saving...
- mFiltershowActivity.updateUIAfterServiceStarted();
- } else if (mFiltershowActivity.isSimpleEditAction()) {
- // terminate now
- mFiltershowActivity.completeSaveImage(result);
- }
- }
-
- private void setupPipeline() {
- Resources res = getResources();
- FiltersManager.setResources(res);
- CachingPipeline.createRenderscriptContext(this);
-
- FiltersManager filtersManager = FiltersManager.getManager();
- filtersManager.addLooks(this);
- filtersManager.addBorders(this);
- filtersManager.addTools(this);
- filtersManager.addEffects();
-
- FiltersManager highresFiltersManager = FiltersManager.getHighresManager();
- highresFiltersManager.addLooks(this);
- highresFiltersManager.addBorders(this);
- highresFiltersManager.addTools(this);
- highresFiltersManager.addEffects();
- }
-
- private void tearDownPipeline() {
- ImageFilter.resetStatics();
- FiltersManager.getPreviewManager().freeRSFilterScripts();
- FiltersManager.getManager().freeRSFilterScripts();
- FiltersManager.getHighresManager().freeRSFilterScripts();
- FiltersManager.reset();
- CachingPipeline.destroyRenderScriptContext();
- }
-
- static {
- System.loadLibrary("jni_filtershow_filters");
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/ProcessingTask.java b/src/com/android/gallery3d/filtershow/pipeline/ProcessingTask.java
deleted file mode 100644
index 8d3e8110f..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/ProcessingTask.java
+++ /dev/null
@@ -1,88 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.content.Context;
-import android.os.Handler;
-import android.os.Message;
-
-public abstract class ProcessingTask {
- private ProcessingTaskController mTaskController;
- private Handler mProcessingHandler;
- private Handler mResultHandler;
- private int mType;
- private static final int DELAY = 300;
-
- static interface Request {}
- static interface Update {}
- static interface Result {}
-
- public boolean postRequest(Request message) {
- Message msg = mProcessingHandler.obtainMessage(mType);
- msg.obj = message;
- if (isPriorityTask()) {
- if (mProcessingHandler.hasMessages(getType())) {
- return false;
- }
- mProcessingHandler.sendMessageAtFrontOfQueue(msg);
- } else if (isDelayedTask()) {
- if (mProcessingHandler.hasMessages(getType())) {
- mProcessingHandler.removeMessages(getType());
- }
- mProcessingHandler.sendMessageDelayed(msg, DELAY);
- } else {
- mProcessingHandler.sendMessage(msg);
- }
- return true;
- }
-
- public void postUpdate(Update message) {
- Message msg = mResultHandler.obtainMessage(mType);
- msg.obj = message;
- msg.arg1 = ProcessingTaskController.UPDATE;
- mResultHandler.sendMessage(msg);
- }
-
- public void processRequest(Request message) {
- Object result = doInBackground(message);
- Message msg = mResultHandler.obtainMessage(mType);
- msg.obj = result;
- msg.arg1 = ProcessingTaskController.RESULT;
- mResultHandler.sendMessage(msg);
- }
-
- public void added(ProcessingTaskController taskController) {
- mTaskController = taskController;
- mResultHandler = taskController.getResultHandler();
- mProcessingHandler = taskController.getProcessingHandler();
- mType = taskController.getReservedType();
- }
-
- public int getType() {
- return mType;
- }
-
- public Context getContext() {
- return mTaskController.getContext();
- }
-
- public abstract Result doInBackground(Request message);
- public abstract void onResult(Result message);
- public void onUpdate(Update message) {}
- public boolean isPriorityTask() { return false; }
- public boolean isDelayedTask() { return false; }
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/ProcessingTaskController.java b/src/com/android/gallery3d/filtershow/pipeline/ProcessingTaskController.java
deleted file mode 100644
index b54bbb044..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/ProcessingTaskController.java
+++ /dev/null
@@ -1,97 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.content.Context;
-import android.os.Handler;
-import android.os.HandlerThread;
-import android.os.Message;
-import android.util.Log;
-
-import java.util.HashMap;
-
-public class ProcessingTaskController implements Handler.Callback {
- private static final String LOGTAG = "ProcessingTaskController";
-
- private Context mContext;
- private HandlerThread mHandlerThread = null;
- private Handler mProcessingHandler = null;
- private int mCurrentType;
- private HashMap<Integer, ProcessingTask> mTasks = new HashMap<Integer, ProcessingTask>();
-
- public final static int RESULT = 1;
- public final static int UPDATE = 2;
-
- private final Handler mResultHandler = new Handler() {
- @Override
- public void handleMessage(Message msg) {
- ProcessingTask task = mTasks.get(msg.what);
- if (task != null) {
- if (msg.arg1 == RESULT) {
- task.onResult((ProcessingTask.Result) msg.obj);
- } else if (msg.arg1 == UPDATE) {
- task.onUpdate((ProcessingTask.Update) msg.obj);
- } else {
- Log.w(LOGTAG, "received unknown message! " + msg.arg1);
- }
- }
- }
- };
-
- @Override
- public boolean handleMessage(Message msg) {
- ProcessingTask task = mTasks.get(msg.what);
- if (task != null) {
- task.processRequest((ProcessingTask.Request) msg.obj);
- return true;
- }
- return false;
- }
-
- public ProcessingTaskController(Context context) {
- mContext = context;
- mHandlerThread = new HandlerThread("ProcessingTaskController",
- android.os.Process.THREAD_PRIORITY_FOREGROUND);
- mHandlerThread.start();
- mProcessingHandler = new Handler(mHandlerThread.getLooper(), this);
- }
-
- public Handler getProcessingHandler() {
- return mProcessingHandler;
- }
-
- public Handler getResultHandler() {
- return mResultHandler;
- }
-
- public int getReservedType() {
- return mCurrentType++;
- }
-
- public Context getContext() {
- return mContext;
- }
-
- public void add(ProcessingTask task) {
- task.added(this);
- mTasks.put(task.getType(), task);
- }
-
- public void quit() {
- mHandlerThread.quit();
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/RenderingRequest.java b/src/com/android/gallery3d/filtershow/pipeline/RenderingRequest.java
deleted file mode 100644
index ef4bb9bc0..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/RenderingRequest.java
+++ /dev/null
@@ -1,174 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Rect;
-import com.android.gallery3d.app.Log;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.filters.FiltersManager;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-
-public class RenderingRequest {
- private static final String LOGTAG = "RenderingRequest";
- private boolean mIsDirect = false;
- private Bitmap mBitmap = null;
- private ImagePreset mImagePreset = null;
- private ImagePreset mOriginalImagePreset = null;
- private RenderingRequestCaller mCaller = null;
- private float mScaleFactor = 1.0f;
- private Rect mBounds = null;
- private Rect mDestination = null;
- private int mType = FULL_RENDERING;
- public static final int FULL_RENDERING = 0;
- public static final int FILTERS_RENDERING = 1;
- public static final int GEOMETRY_RENDERING = 2;
- public static final int ICON_RENDERING = 3;
- public static final int PARTIAL_RENDERING = 4;
- public static final int HIGHRES_RENDERING = 5;
- public static final int STYLE_ICON_RENDERING = 6;
-
- private static final Bitmap.Config mConfig = Bitmap.Config.ARGB_8888;
-
- public static void post(Context context, Bitmap source, ImagePreset preset,
- int type, RenderingRequestCaller caller) {
- RenderingRequest.post(context, source, preset, type, caller, null, null);
- }
-
- public static void post(Context context, Bitmap source, ImagePreset preset, int type,
- RenderingRequestCaller caller, Rect bounds, Rect destination) {
- if (((type != PARTIAL_RENDERING && type != HIGHRES_RENDERING) && source == null)
- || preset == null || caller == null) {
- Log.v(LOGTAG, "something null: source: " + source
- + " or preset: " + preset + " or caller: " + caller);
- return;
- }
- RenderingRequest request = new RenderingRequest();
- Bitmap bitmap = null;
- if (type == FULL_RENDERING
- || type == GEOMETRY_RENDERING
- || type == ICON_RENDERING
- || type == STYLE_ICON_RENDERING) {
- CachingPipeline pipeline = new CachingPipeline(
- FiltersManager.getManager(), "Icon");
- bitmap = pipeline.renderGeometryIcon(source, preset);
- } else if (type != PARTIAL_RENDERING && type != HIGHRES_RENDERING) {
- bitmap = Bitmap.createBitmap(source.getWidth(), source.getHeight(), mConfig);
- }
-
- request.setBitmap(bitmap);
- ImagePreset passedPreset = new ImagePreset(preset);
- request.setOriginalImagePreset(preset);
- request.setScaleFactor(MasterImage.getImage().getScaleFactor());
-
- if (type == PARTIAL_RENDERING) {
- request.setBounds(bounds);
- request.setDestination(destination);
- passedPreset.setPartialRendering(true, bounds);
- }
-
- request.setImagePreset(passedPreset);
- request.setType(type);
- request.setCaller(caller);
- request.post(context);
- }
-
- public void post(Context context) {
- if (context instanceof FilterShowActivity) {
- FilterShowActivity activity = (FilterShowActivity) context;
- ProcessingService service = activity.getProcessingService();
- service.postRenderingRequest(this);
- }
- }
-
- public void markAvailable() {
- if (mBitmap == null || mImagePreset == null
- || mCaller == null) {
- return;
- }
- mCaller.available(this);
- }
-
- public boolean isDirect() {
- return mIsDirect;
- }
-
- public void setDirect(boolean isDirect) {
- mIsDirect = isDirect;
- }
-
- public Bitmap getBitmap() {
- return mBitmap;
- }
-
- public void setBitmap(Bitmap bitmap) {
- mBitmap = bitmap;
- }
-
- public ImagePreset getImagePreset() {
- return mImagePreset;
- }
-
- public void setImagePreset(ImagePreset imagePreset) {
- mImagePreset = imagePreset;
- }
-
- public int getType() {
- return mType;
- }
-
- public void setType(int type) {
- mType = type;
- }
-
- public void setCaller(RenderingRequestCaller caller) {
- mCaller = caller;
- }
-
- public Rect getBounds() {
- return mBounds;
- }
-
- public void setBounds(Rect bounds) {
- mBounds = bounds;
- }
-
- public void setScaleFactor(float scaleFactor) {
- mScaleFactor = scaleFactor;
- }
-
- public float getScaleFactor() {
- return mScaleFactor;
- }
-
- public Rect getDestination() {
- return mDestination;
- }
-
- public void setDestination(Rect destination) {
- mDestination = destination;
- }
-
- public ImagePreset getOriginalImagePreset() {
- return mOriginalImagePreset;
- }
-
- public void setOriginalImagePreset(ImagePreset originalImagePreset) {
- mOriginalImagePreset = originalImagePreset;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/RenderingRequestCaller.java b/src/com/android/gallery3d/filtershow/pipeline/RenderingRequestCaller.java
deleted file mode 100644
index b978e7040..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/RenderingRequestCaller.java
+++ /dev/null
@@ -1,21 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-public interface RenderingRequestCaller {
- public void available(RenderingRequest request);
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/RenderingRequestTask.java b/src/com/android/gallery3d/filtershow/pipeline/RenderingRequestTask.java
deleted file mode 100644
index 7a83f7072..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/RenderingRequestTask.java
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.graphics.Bitmap;
-import com.android.gallery3d.filtershow.filters.FiltersManager;
-
-public class RenderingRequestTask extends ProcessingTask {
-
- private CachingPipeline mPreviewPipeline = null;
- private boolean mPipelineIsOn = false;
-
- public void setPreviewScaleFactor(float previewScale) {
- mPreviewPipeline.setPreviewScaleFactor(previewScale);
- }
-
- static class Render implements Request {
- RenderingRequest request;
- }
-
- static class RenderResult implements Result {
- RenderingRequest request;
- }
-
- public RenderingRequestTask() {
- mPreviewPipeline = new CachingPipeline(
- FiltersManager.getManager(), "Normal");
- }
-
- public void setOriginal(Bitmap bitmap) {
- mPreviewPipeline.setOriginal(bitmap);
- mPipelineIsOn = true;
- }
-
- public void stop() {
- mPreviewPipeline.stop();
- }
-
- public void postRenderingRequest(RenderingRequest request) {
- if (!mPipelineIsOn) {
- return;
- }
- Render render = new Render();
- render.request = request;
- postRequest(render);
- }
-
- @Override
- public Result doInBackground(Request message) {
- RenderingRequest request = ((Render) message).request;
- RenderResult result = null;
- mPreviewPipeline.render(request);
- result = new RenderResult();
- result.request = request;
- return result;
- }
-
- @Override
- public void onResult(Result message) {
- if (message == null) {
- return;
- }
- RenderingRequest request = ((RenderResult) message).request;
- request.markAvailable();
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/SharedBuffer.java b/src/com/android/gallery3d/filtershow/pipeline/SharedBuffer.java
deleted file mode 100644
index 98e69f60e..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/SharedBuffer.java
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.graphics.Bitmap;
-
-public class SharedBuffer {
-
- private static final String LOGTAG = "SharedBuffer";
-
- private volatile Buffer mProducer = null;
- private volatile Buffer mConsumer = null;
- private volatile Buffer mIntermediate = null;
-
- private volatile boolean mNeedsSwap = false;
- private volatile boolean mNeedsRepaint = true;
-
- public void setProducer(Bitmap producer) {
- Buffer buffer = new Buffer(producer);
- synchronized (this) {
- mProducer = buffer;
- }
- }
-
- public synchronized Buffer getProducer() {
- return mProducer;
- }
-
- public synchronized Buffer getConsumer() {
- return mConsumer;
- }
-
- public synchronized void swapProducer() {
- Buffer intermediate = mIntermediate;
- mIntermediate = mProducer;
- mProducer = intermediate;
- mNeedsSwap = true;
- }
-
- public synchronized void swapConsumerIfNeeded() {
- if (!mNeedsSwap) {
- return;
- }
- Buffer intermediate = mIntermediate;
- mIntermediate = mConsumer;
- mConsumer = intermediate;
- mNeedsSwap = false;
- }
-
- public synchronized void invalidate() {
- mNeedsRepaint = true;
- }
-
- public synchronized boolean checkRepaintNeeded() {
- if (mNeedsRepaint) {
- mNeedsRepaint = false;
- return true;
- }
- return false;
- }
-
-}
-
diff --git a/src/com/android/gallery3d/filtershow/pipeline/SharedPreset.java b/src/com/android/gallery3d/filtershow/pipeline/SharedPreset.java
deleted file mode 100644
index 3f850fed2..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/SharedPreset.java
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-public class SharedPreset {
-
- private volatile ImagePreset mProducerPreset = null;
- private volatile ImagePreset mConsumerPreset = null;
- private volatile ImagePreset mIntermediatePreset = null;
-
- public synchronized void enqueuePreset(ImagePreset preset) {
- if (mProducerPreset == null || (!mProducerPreset.same(preset))) {
- mProducerPreset = new ImagePreset(preset);
- } else {
- mProducerPreset.updateWith(preset);
- }
- ImagePreset temp = mIntermediatePreset;
- mIntermediatePreset = mProducerPreset;
- mProducerPreset = temp;
- }
-
- public synchronized ImagePreset dequeuePreset() {
- ImagePreset temp = mConsumerPreset;
- mConsumerPreset = mIntermediatePreset;
- mIntermediatePreset = temp;
- return mConsumerPreset;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/pipeline/UpdatePreviewTask.java b/src/com/android/gallery3d/filtershow/pipeline/UpdatePreviewTask.java
deleted file mode 100644
index 406cc9bf5..000000000
--- a/src/com/android/gallery3d/filtershow/pipeline/UpdatePreviewTask.java
+++ /dev/null
@@ -1,79 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.pipeline;
-
-import android.graphics.Bitmap;
-import com.android.gallery3d.filtershow.filters.FiltersManager;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-
-public class UpdatePreviewTask extends ProcessingTask {
- private CachingPipeline mPreviewPipeline = null;
- private boolean mHasUnhandledPreviewRequest = false;
- private boolean mPipelineIsOn = false;
-
- public UpdatePreviewTask() {
- mPreviewPipeline = new CachingPipeline(
- FiltersManager.getPreviewManager(), "Preview");
- }
-
- public void setOriginal(Bitmap bitmap) {
- mPreviewPipeline.setOriginal(bitmap);
- mPipelineIsOn = true;
- }
-
- public void updatePreview() {
- if (!mPipelineIsOn) {
- return;
- }
- mHasUnhandledPreviewRequest = true;
- if (postRequest(null)) {
- mHasUnhandledPreviewRequest = false;
- }
- }
-
- @Override
- public boolean isPriorityTask() {
- return true;
- }
-
- @Override
- public Result doInBackground(Request message) {
- SharedBuffer buffer = MasterImage.getImage().getPreviewBuffer();
- SharedPreset preset = MasterImage.getImage().getPreviewPreset();
- ImagePreset renderingPreset = preset.dequeuePreset();
- if (renderingPreset != null) {
- mPreviewPipeline.compute(buffer, renderingPreset, 0);
- // set the preset we used in the buffer for later inspection UI-side
- buffer.getProducer().setPreset(renderingPreset);
- buffer.getProducer().sync();
- buffer.swapProducer(); // push back the result
- }
- return null;
- }
-
- @Override
- public void onResult(Result message) {
- MasterImage.getImage().notifyObservers();
- if (mHasUnhandledPreviewRequest) {
- updatePreview();
- }
- }
-
- public void setPipelineIsOn(boolean pipelineIsOn) {
- mPipelineIsOn = pipelineIsOn;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/presets/PresetManagementDialog.java b/src/com/android/gallery3d/filtershow/presets/PresetManagementDialog.java
deleted file mode 100644
index 7ab61fcc9..000000000
--- a/src/com/android/gallery3d/filtershow/presets/PresetManagementDialog.java
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.presets;
-
-import android.os.Bundle;
-import android.support.v4.app.DialogFragment;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.ListView;
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-
-public class PresetManagementDialog extends DialogFragment implements View.OnClickListener {
- private UserPresetsAdapter mAdapter;
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
- View view = inflater.inflate(R.layout.filtershow_presets_management_dialog, container);
-
- FilterShowActivity activity = (FilterShowActivity) getActivity();
- mAdapter = activity.getUserPresetsAdapter();
- ListView panel = (ListView) view.findViewById(R.id.listItems);
- panel.setAdapter(mAdapter);
-
- view.findViewById(R.id.cancel).setOnClickListener(this);
- view.findViewById(R.id.addpreset).setOnClickListener(this);
- view.findViewById(R.id.ok).setOnClickListener(this);
- getDialog().setTitle(getString(R.string.filtershow_manage_preset));
- return view;
- }
-
- @Override
- public void onClick(View v) {
- FilterShowActivity activity = (FilterShowActivity) getActivity();
- switch (v.getId()) {
- case R.id.cancel:
- mAdapter.clearChangedRepresentations();
- mAdapter.clearDeletedRepresentations();
- activity.updateUserPresetsFromAdapter(mAdapter);
- dismiss();
- break;
- case R.id.addpreset:
- activity.saveCurrentImagePreset();
- dismiss();
- break;
- case R.id.ok:
- mAdapter.updateCurrent();
- activity.updateUserPresetsFromAdapter(mAdapter);
- dismiss();
- break;
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/presets/UserPresetsAdapter.java b/src/com/android/gallery3d/filtershow/presets/UserPresetsAdapter.java
deleted file mode 100644
index dab9ea454..000000000
--- a/src/com/android/gallery3d/filtershow/presets/UserPresetsAdapter.java
+++ /dev/null
@@ -1,171 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.presets;
-
-import android.content.Context;
-import android.graphics.Rect;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.ArrayAdapter;
-import android.widget.EditText;
-import android.widget.ImageButton;
-import android.widget.ImageView;
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.category.Action;
-import com.android.gallery3d.filtershow.category.CategoryView;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterUserPresetRepresentation;
-
-import java.util.ArrayList;
-
-public class UserPresetsAdapter extends ArrayAdapter<Action>
- implements View.OnClickListener, View.OnFocusChangeListener {
- private static final String LOGTAG = "UserPresetsAdapter";
- private LayoutInflater mInflater;
- private int mIconSize = 160;
- private ArrayList<FilterUserPresetRepresentation> mDeletedRepresentations =
- new ArrayList<FilterUserPresetRepresentation>();
- private ArrayList<FilterUserPresetRepresentation> mChangedRepresentations =
- new ArrayList<FilterUserPresetRepresentation>();
- private EditText mCurrentEditText;
-
- public UserPresetsAdapter(Context context, int textViewResourceId) {
- super(context, textViewResourceId);
- mInflater = LayoutInflater.from(context);
- mIconSize = context.getResources().getDimensionPixelSize(R.dimen.category_panel_icon_size);
- }
-
- public UserPresetsAdapter(Context context) {
- this(context, 0);
- }
-
- @Override
- public void add(Action action) {
- super.add(action);
- action.setAdapter(this);
- }
-
- private void deletePreset(Action action) {
- FilterRepresentation rep = action.getRepresentation();
- if (rep instanceof FilterUserPresetRepresentation) {
- mDeletedRepresentations.add((FilterUserPresetRepresentation) rep);
- }
- remove(action);
- notifyDataSetChanged();
- }
-
- private void changePreset(Action action) {
- FilterRepresentation rep = action.getRepresentation();
- rep.setName(action.getName());
- if (rep instanceof FilterUserPresetRepresentation) {
- mChangedRepresentations.add((FilterUserPresetRepresentation) rep);
- }
- }
-
- public void updateCurrent() {
- if (mCurrentEditText != null) {
- updateActionFromEditText(mCurrentEditText);
- }
- }
-
- static class UserPresetViewHolder {
- ImageView imageView;
- EditText editText;
- ImageButton deleteButton;
- }
-
- @Override
- public View getView(int position, View convertView, ViewGroup parent) {
- UserPresetViewHolder viewHolder;
- if (convertView == null) {
- convertView = mInflater.inflate(R.layout.filtershow_presets_management_row, null);
- viewHolder = new UserPresetViewHolder();
- viewHolder.imageView = (ImageView) convertView.findViewById(R.id.imageView);
- viewHolder.editText = (EditText) convertView.findViewById(R.id.editView);
- viewHolder.deleteButton = (ImageButton) convertView.findViewById(R.id.deleteUserPreset);
- viewHolder.editText.setOnClickListener(this);
- viewHolder.editText.setOnFocusChangeListener(this);
- viewHolder.deleteButton.setOnClickListener(this);
- convertView.setTag(viewHolder);
- } else {
- viewHolder = (UserPresetViewHolder) convertView.getTag();
- }
- Action action = getItem(position);
- viewHolder.imageView.setImageBitmap(action.getImage());
- if (action.getImage() == null) {
- // queue image rendering for this action
- action.setImageFrame(new Rect(0, 0, mIconSize, mIconSize), CategoryView.VERTICAL);
- }
- viewHolder.deleteButton.setTag(action);
- viewHolder.editText.setTag(action);
- viewHolder.editText.setHint(action.getName());
-
- return convertView;
- }
-
- public ArrayList<FilterUserPresetRepresentation> getDeletedRepresentations() {
- return mDeletedRepresentations;
- }
-
- public void clearDeletedRepresentations() {
- mDeletedRepresentations.clear();
- }
-
- public ArrayList<FilterUserPresetRepresentation> getChangedRepresentations() {
- return mChangedRepresentations;
- }
-
- public void clearChangedRepresentations() {
- mChangedRepresentations.clear();
- }
-
- @Override
- public void onClick(View v) {
- switch (v.getId()) {
- case R.id.editView:
- v.requestFocus();
- break;
- case R.id.deleteUserPreset:
- Action action = (Action) v.getTag();
- deletePreset(action);
- break;
- }
- }
-
- @Override
- public void onFocusChange(View v, boolean hasFocus) {
- if (v.getId() != R.id.editView) {
- return;
- }
- EditText editText = (EditText) v;
- if (!hasFocus) {
- updateActionFromEditText(editText);
- } else {
- mCurrentEditText = editText;
- }
- }
-
- private void updateActionFromEditText(EditText editText) {
- Action action = (Action) editText.getTag();
- String newName = editText.getText().toString();
- if (newName.length() > 0) {
- action.setName(editText.getText().toString());
- changePreset(action);
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/provider/SharedImageProvider.java b/src/com/android/gallery3d/filtershow/provider/SharedImageProvider.java
deleted file mode 100644
index bc17a6e03..000000000
--- a/src/com/android/gallery3d/filtershow/provider/SharedImageProvider.java
+++ /dev/null
@@ -1,137 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.provider;
-
-import android.content.ContentProvider;
-import android.content.ContentValues;
-import android.database.Cursor;
-import android.database.MatrixCursor;
-import android.net.Uri;
-import android.os.ConditionVariable;
-import android.os.ParcelFileDescriptor;
-import android.provider.BaseColumns;
-import android.provider.MediaStore;
-import android.provider.OpenableColumns;
-
-import java.io.File;
-import java.io.FileNotFoundException;
-
-public class SharedImageProvider extends ContentProvider {
-
- private static final String LOGTAG = "SharedImageProvider";
-
- public static final String MIME_TYPE = "image/jpeg";
- public static final String AUTHORITY = "com.android.gallery3d.filtershow.provider.SharedImageProvider";
- public static final Uri CONTENT_URI = Uri.parse("content://" + AUTHORITY + "/image");
- public static final String PREPARE = "prepare";
-
- private final String[] mMimeStreamType = {
- MIME_TYPE
- };
-
- private static ConditionVariable mImageReadyCond = new ConditionVariable(false);
-
- @Override
- public int delete(Uri arg0, String arg1, String[] arg2) {
- return 0;
- }
-
- @Override
- public String getType(Uri arg0) {
- return MIME_TYPE;
- }
-
- @Override
- public String[] getStreamTypes(Uri arg0, String mimeTypeFilter) {
- return mMimeStreamType;
- }
-
- @Override
- public Uri insert(Uri uri, ContentValues values) {
- if (values.containsKey(PREPARE)) {
- if (values.getAsBoolean(PREPARE)) {
- mImageReadyCond.close();
- } else {
- mImageReadyCond.open();
- }
- }
- return null;
- }
-
- @Override
- public int update(Uri arg0, ContentValues arg1, String arg2, String[] arg3) {
- return 0;
- }
-
- @Override
- public boolean onCreate() {
- return true;
- }
-
- @Override
- public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs, String sortOrder) {
- String uriPath = uri.getLastPathSegment();
- if (uriPath == null) {
- return null;
- }
- if (projection == null) {
- projection = new String[] {
- BaseColumns._ID,
- MediaStore.MediaColumns.DATA,
- OpenableColumns.DISPLAY_NAME,
- OpenableColumns.SIZE
- };
- }
- // If we receive a query on display name or size,
- // we should block until the image is ready
- mImageReadyCond.block();
-
- File path = new File(uriPath);
-
- MatrixCursor cursor = new MatrixCursor(projection);
- Object[] columns = new Object[projection.length];
- for (int i = 0; i < projection.length; i++) {
- if (projection[i].equalsIgnoreCase(BaseColumns._ID)) {
- columns[i] = 0;
- } else if (projection[i].equalsIgnoreCase(MediaStore.MediaColumns.DATA)) {
- columns[i] = uri;
- } else if (projection[i].equalsIgnoreCase(OpenableColumns.DISPLAY_NAME)) {
- columns[i] = path.getName();
- } else if (projection[i].equalsIgnoreCase(OpenableColumns.SIZE)) {
- columns[i] = path.length();
- }
- }
- cursor.addRow(columns);
-
- return cursor;
- }
-
- @Override
- public ParcelFileDescriptor openFile(Uri uri, String mode)
- throws FileNotFoundException {
- String uriPath = uri.getLastPathSegment();
- if (uriPath == null) {
- return null;
- }
- // Here we need to block until the image is ready
- mImageReadyCond.block();
- File path = new File(uriPath);
- int imode = 0;
- imode |= ParcelFileDescriptor.MODE_READ_ONLY;
- return ParcelFileDescriptor.open(path, imode);
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/state/DragListener.java b/src/com/android/gallery3d/filtershow/state/DragListener.java
deleted file mode 100644
index 1aa81ed69..000000000
--- a/src/com/android/gallery3d/filtershow/state/DragListener.java
+++ /dev/null
@@ -1,110 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.state;
-
-import android.view.DragEvent;
-import android.view.View;
-import android.widget.ArrayAdapter;
-import android.widget.LinearLayout;
-
-class DragListener implements View.OnDragListener {
-
- private static final String LOGTAG = "DragListener";
- private PanelTrack mStatePanelTrack;
- private static float sSlope = 0.2f;
-
- public DragListener(PanelTrack statePanelTrack) {
- mStatePanelTrack = statePanelTrack;
- }
-
- private void setState(DragEvent event) {
- float translation = event.getY() - mStatePanelTrack.getTouchPoint().y;
- float alpha = 1.0f - (Math.abs(translation)
- / mStatePanelTrack.getCurrentView().getHeight());
- if (mStatePanelTrack.getOrientation() == LinearLayout.VERTICAL) {
- translation = event.getX() - mStatePanelTrack.getTouchPoint().x;
- alpha = 1.0f - (Math.abs(translation)
- / mStatePanelTrack.getCurrentView().getWidth());
- mStatePanelTrack.getCurrentView().setTranslationX(translation);
- } else {
- mStatePanelTrack.getCurrentView().setTranslationY(translation);
- }
- mStatePanelTrack.getCurrentView().setBackgroundAlpha(alpha);
- }
-
- @Override
- public boolean onDrag(View v, DragEvent event) {
- switch (event.getAction()) {
- case DragEvent.ACTION_DRAG_STARTED: {
- break;
- }
- case DragEvent.ACTION_DRAG_LOCATION: {
- if (mStatePanelTrack.getCurrentView() != null) {
- setState(event);
- View over = mStatePanelTrack.findChildAt((int) event.getX(),
- (int) event.getY());
- if (over != null && over != mStatePanelTrack.getCurrentView()) {
- StateView stateView = (StateView) over;
- if (stateView != mStatePanelTrack.getCurrentView()) {
- int pos = mStatePanelTrack.findChild(over);
- int origin = mStatePanelTrack.findChild(
- mStatePanelTrack.getCurrentView());
- ArrayAdapter array = (ArrayAdapter) mStatePanelTrack.getAdapter();
- if (origin != -1 && pos != -1) {
- State current = (State) array.getItem(origin);
- array.remove(current);
- array.insert(current, pos);
- mStatePanelTrack.fillContent(false);
- mStatePanelTrack.setCurrentView(mStatePanelTrack.getChildAt(pos));
- }
- }
- }
- }
- break;
- }
- case DragEvent.ACTION_DRAG_ENTERED: {
- mStatePanelTrack.setExited(false);
- if (mStatePanelTrack.getCurrentView() != null) {
- mStatePanelTrack.getCurrentView().setVisibility(View.VISIBLE);
- }
- return true;
- }
- case DragEvent.ACTION_DRAG_EXITED: {
- if (mStatePanelTrack.getCurrentView() != null) {
- setState(event);
- mStatePanelTrack.getCurrentView().setVisibility(View.INVISIBLE);
- }
- mStatePanelTrack.setExited(true);
- break;
- }
- case DragEvent.ACTION_DROP: {
- break;
- }
- case DragEvent.ACTION_DRAG_ENDED: {
- if (mStatePanelTrack.getCurrentView() != null
- && mStatePanelTrack.getCurrentView().getAlpha() > sSlope) {
- setState(event);
- }
- mStatePanelTrack.checkEndState();
- break;
- }
- default:
- break;
- }
- return true;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/state/PanelTrack.java b/src/com/android/gallery3d/filtershow/state/PanelTrack.java
deleted file mode 100644
index d02207d9b..000000000
--- a/src/com/android/gallery3d/filtershow/state/PanelTrack.java
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.state;
-
-import android.graphics.Point;
-import android.view.MotionEvent;
-import android.view.View;
-import android.widget.Adapter;
-
-public interface PanelTrack {
- public int getOrientation();
- public void onTouch(MotionEvent event, StateView view);
- public StateView getCurrentView();
- public void setCurrentView(View view);
- public Point getTouchPoint();
- public View findChildAt(int x, int y);
- public int findChild(View view);
- public Adapter getAdapter();
- public void fillContent(boolean value);
- public View getChildAt(int pos);
- public void setExited(boolean value);
- public void checkEndState();
-}
diff --git a/src/com/android/gallery3d/filtershow/state/State.java b/src/com/android/gallery3d/filtershow/state/State.java
deleted file mode 100644
index e7dedd6a2..000000000
--- a/src/com/android/gallery3d/filtershow/state/State.java
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.state;
-
-import com.android.gallery3d.filtershow.filters.FilterFxRepresentation;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-
-public class State {
- private String mText;
- private int mType;
- private FilterRepresentation mFilterRepresentation;
-
- public State(State state) {
- this(state.getText(), state.getType());
- }
-
- public State(String text) {
- this(text, StateView.DEFAULT);
- }
-
- public State(String text, int type) {
- mText = text;
- mType = type;
- }
-
- public boolean equals(State state) {
- if (mFilterRepresentation.getFilterClass()
- != state.mFilterRepresentation.getFilterClass()) {
- return false;
- }
- if (mFilterRepresentation instanceof FilterFxRepresentation) {
- return mFilterRepresentation.equals(state.getFilterRepresentation());
- }
- return true;
- }
-
- public boolean isDraggable() {
- return mFilterRepresentation != null;
- }
-
- String getText() {
- return mText;
- }
-
- void setText(String text) {
- mText = text;
- }
-
- int getType() {
- return mType;
- }
-
- void setType(int type) {
- mType = type;
- }
-
- public FilterRepresentation getFilterRepresentation() {
- return mFilterRepresentation;
- }
-
- public void setFilterRepresentation(FilterRepresentation filterRepresentation) {
- mFilterRepresentation = filterRepresentation;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/state/StateAdapter.java b/src/com/android/gallery3d/filtershow/state/StateAdapter.java
deleted file mode 100644
index 522585280..000000000
--- a/src/com/android/gallery3d/filtershow/state/StateAdapter.java
+++ /dev/null
@@ -1,115 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.state;
-
-import android.content.Context;
-import android.util.Log;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.ArrayAdapter;
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.editors.ImageOnlyEditor;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-
-import java.util.Vector;
-
-public class StateAdapter extends ArrayAdapter<State> {
-
- private static final String LOGTAG = "StateAdapter";
- private int mOrientation;
- private String mOriginalText;
- private String mResultText;
-
- public StateAdapter(Context context, int textViewResourceId) {
- super(context, textViewResourceId);
- mOriginalText = context.getString(R.string.state_panel_original);
- mResultText = context.getString(R.string.state_panel_result);
- }
-
- @Override
- public View getView(int position, View convertView, ViewGroup parent) {
- StateView view = null;
- if (convertView == null) {
- convertView = new StateView(getContext());
- }
- view = (StateView) convertView;
- State state = getItem(position);
- view.setState(state);
- view.setOrientation(mOrientation);
- FilterRepresentation currentRep = MasterImage.getImage().getCurrentFilterRepresentation();
- FilterRepresentation stateRep = state.getFilterRepresentation();
- if (currentRep != null && stateRep != null
- && currentRep.getFilterClass() == stateRep.getFilterClass()
- && currentRep.getEditorId() != ImageOnlyEditor.ID) {
- view.setSelected(true);
- } else {
- view.setSelected(false);
- }
- return view;
- }
-
- public boolean contains(State state) {
- for (int i = 0; i < getCount(); i++) {
- if (state == getItem(i)) {
- return true;
- }
- }
- return false;
- }
-
- public void setOrientation(int orientation) {
- mOrientation = orientation;
- }
-
- public void addOriginal() {
- add(new State(mOriginalText));
- }
-
- public boolean same(Vector<State> states) {
- // we have the original state in addition
- if (states.size() + 1 != getCount()) {
- return false;
- }
- for (int i = 1; i < getCount(); i++) {
- State state = getItem(i);
- if (!state.equals(states.elementAt(i-1))) {
- return false;
- }
- }
- return true;
- }
-
- public void fill(Vector<State> states) {
- if (same(states)) {
- return;
- }
- clear();
- addOriginal();
- addAll(states);
- notifyDataSetChanged();
- }
-
- @Override
- public void remove(State state) {
- super.remove(state);
- FilterRepresentation filterRepresentation = state.getFilterRepresentation();
- FilterShowActivity activity = (FilterShowActivity) getContext();
- activity.removeFilterRepresentation(filterRepresentation);
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/state/StatePanel.java b/src/com/android/gallery3d/filtershow/state/StatePanel.java
deleted file mode 100644
index df470f23e..000000000
--- a/src/com/android/gallery3d/filtershow/state/StatePanel.java
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.state;
-
-import android.os.Bundle;
-import android.support.v4.app.Fragment;
-import android.util.Log;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.LinearLayout;
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-
-public class StatePanel extends Fragment {
- private static final String LOGTAG = "StatePanel";
- private StatePanelTrack track;
- private LinearLayout mMainView;
- public static final String FRAGMENT_TAG = "StatePanel";
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
- mMainView = (LinearLayout) inflater.inflate(R.layout.filtershow_state_panel_new, null);
- View panel = mMainView.findViewById(R.id.listStates);
- track = (StatePanelTrack) panel;
- track.setAdapter(MasterImage.getImage().getState());
- return mMainView;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/state/StatePanelTrack.java b/src/com/android/gallery3d/filtershow/state/StatePanelTrack.java
deleted file mode 100644
index fff7e7f5f..000000000
--- a/src/com/android/gallery3d/filtershow/state/StatePanelTrack.java
+++ /dev/null
@@ -1,351 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.state;
-
-import android.animation.LayoutTransition;
-import android.content.Context;
-import android.content.res.TypedArray;
-import android.database.DataSetObserver;
-import android.graphics.Canvas;
-import android.graphics.Point;
-import android.graphics.Rect;
-import android.util.AttributeSet;
-import android.util.Log;
-import android.view.GestureDetector;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.Adapter;
-import android.widget.LinearLayout;
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.editors.ImageOnlyEditor;
-import com.android.gallery3d.filtershow.filters.FilterRepresentation;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-
-public class StatePanelTrack extends LinearLayout implements PanelTrack {
-
- private static final String LOGTAG = "StatePanelTrack";
- private Point mTouchPoint;
- private StateView mCurrentView;
- private StateView mCurrentSelectedView;
- private boolean mExited = false;
- private boolean mStartedDrag = false;
- private StateAdapter mAdapter;
- private DragListener mDragListener = new DragListener(this);
- private float mDeleteSlope = 0.2f;
- private GestureDetector mGestureDetector;
- private int mElemWidth;
- private int mElemHeight;
- private int mElemSize;
- private int mElemEndSize;
- private int mEndElemWidth;
- private int mEndElemHeight;
- private long mTouchTime;
- private int mMaxTouchDelay = 300; // 300ms delay for touch
- private static final boolean ALLOWS_DRAG = false;
- private DataSetObserver mObserver = new DataSetObserver() {
- @Override
- public void onChanged() {
- super.onChanged();
- fillContent(false);
- }
-
- @Override
- public void onInvalidated() {
- super.onInvalidated();
- fillContent(false);
- }
- };
-
- public StatePanelTrack(Context context, AttributeSet attrs) {
- super(context, attrs);
- TypedArray a = getContext().obtainStyledAttributes(attrs, R.styleable.StatePanelTrack);
- mElemSize = a.getDimensionPixelSize(R.styleable.StatePanelTrack_elemSize, 0);
- mElemEndSize = a.getDimensionPixelSize(R.styleable.StatePanelTrack_elemEndSize, 0);
- if (getOrientation() == LinearLayout.HORIZONTAL) {
- mElemWidth = mElemSize;
- mElemHeight = LayoutParams.MATCH_PARENT;
- mEndElemWidth = mElemEndSize;
- mEndElemHeight = LayoutParams.MATCH_PARENT;
- } else {
- mElemWidth = LayoutParams.MATCH_PARENT;
- mElemHeight = mElemSize;
- mEndElemWidth = LayoutParams.MATCH_PARENT;
- mEndElemHeight = mElemEndSize;
- }
- GestureDetector.SimpleOnGestureListener simpleOnGestureListener
- = new GestureDetector.SimpleOnGestureListener(){
- @Override
- public void onLongPress(MotionEvent e) {
- longPress(e);
- }
- @Override
- public boolean onDoubleTap(MotionEvent e) {
- addDuplicate(e);
- return true;
- }
- };
- mGestureDetector = new GestureDetector(context, simpleOnGestureListener);
- }
-
- private void addDuplicate(MotionEvent e) {
- if (mCurrentSelectedView == null) {
- return;
- }
- int pos = findChild(mCurrentSelectedView);
- if (pos != -1) {
- mAdapter.insert(new State(mCurrentSelectedView.getState()), pos);
- fillContent(true);
- }
- }
-
- private void longPress(MotionEvent e) {
- View view = findChildAt((int) e.getX(), (int) e.getY());
- if (view == null) {
- return;
- }
- if (view instanceof StateView) {
- StateView stateView = (StateView) view;
- stateView.setDuplicateButton(true);
- }
- }
-
- public void setAdapter(StateAdapter adapter) {
- mAdapter = adapter;
- mAdapter.registerDataSetObserver(mObserver);
- mAdapter.setOrientation(getOrientation());
- fillContent(false);
- requestLayout();
- }
-
- public StateView findChildWithState(State state) {
- for (int i = 0; i < getChildCount(); i++) {
- StateView view = (StateView) getChildAt(i);
- if (view.getState() == state) {
- return view;
- }
- }
- return null;
- }
-
- public void fillContent(boolean animate) {
- if (!animate) {
- this.setLayoutTransition(null);
- }
- int n = mAdapter.getCount();
- for (int i = 0; i < getChildCount(); i++) {
- StateView child = (StateView) getChildAt(i);
- child.resetPosition();
- if (!mAdapter.contains(child.getState())) {
- removeView(child);
- }
- }
- LayoutParams params = new LayoutParams(mElemWidth, mElemHeight);
- for (int i = 0; i < n; i++) {
- State s = mAdapter.getItem(i);
- if (findChildWithState(s) == null) {
- View view = mAdapter.getView(i, null, this);
- addView(view, i, params);
- }
- }
-
- for (int i = 0; i < n; i++) {
- State state = mAdapter.getItem(i);
- StateView view = (StateView) getChildAt(i);
- view.setState(state);
- if (i == 0) {
- view.setType(StateView.BEGIN);
- } else if (i == n - 1) {
- view.setType(StateView.END);
- } else {
- view.setType(StateView.DEFAULT);
- }
- view.resetPosition();
- }
-
- if (!animate) {
- this.setLayoutTransition(new LayoutTransition());
- }
- }
-
- public void onTouch(MotionEvent event, StateView view) {
- if (!view.isDraggable()) {
- return;
- }
- mCurrentView = view;
- if (mCurrentSelectedView == mCurrentView) {
- return;
- }
- if (mCurrentSelectedView != null) {
- mCurrentSelectedView.setSelected(false);
- }
- // We changed the current view -- let's reset the
- // gesture detector.
- MotionEvent cancelEvent = MotionEvent.obtain(event);
- cancelEvent.setAction(MotionEvent.ACTION_CANCEL);
- mGestureDetector.onTouchEvent(cancelEvent);
- mCurrentSelectedView = mCurrentView;
- // We have to send the event to the gesture detector
- mGestureDetector.onTouchEvent(event);
- mTouchTime = System.currentTimeMillis();
- }
-
- @Override
- public boolean onInterceptTouchEvent(MotionEvent event) {
- if (mCurrentView != null) {
- return true;
- }
- return false;
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- if (mCurrentView == null) {
- return false;
- }
- if (mTouchTime == 0) {
- mTouchTime = System.currentTimeMillis();
- }
- mGestureDetector.onTouchEvent(event);
- if (mTouchPoint == null) {
- mTouchPoint = new Point();
- mTouchPoint.x = (int) event.getX();
- mTouchPoint.y = (int) event.getY();
- }
-
- if (event.getActionMasked() == MotionEvent.ACTION_MOVE) {
- float translation = event.getY() - mTouchPoint.y;
- float alpha = 1.0f - (Math.abs(translation) / mCurrentView.getHeight());
- if (getOrientation() == LinearLayout.VERTICAL) {
- translation = event.getX() - mTouchPoint.x;
- alpha = 1.0f - (Math.abs(translation) / mCurrentView.getWidth());
- mCurrentView.setTranslationX(translation);
- } else {
- mCurrentView.setTranslationY(translation);
- }
- mCurrentView.setBackgroundAlpha(alpha);
- if (ALLOWS_DRAG && alpha < 0.7) {
- setOnDragListener(mDragListener);
- DragShadowBuilder shadowBuilder = new DragShadowBuilder(mCurrentView);
- mCurrentView.startDrag(null, shadowBuilder, mCurrentView, 0);
- mStartedDrag = true;
- }
- }
- if (!mExited && mCurrentView != null
- && mCurrentView.getBackgroundAlpha() > mDeleteSlope
- && event.getActionMasked() == MotionEvent.ACTION_UP
- && System.currentTimeMillis() - mTouchTime < mMaxTouchDelay) {
- FilterRepresentation representation = mCurrentView.getState().getFilterRepresentation();
- mCurrentView.setSelected(true);
- if (representation != MasterImage.getImage().getCurrentFilterRepresentation()) {
- FilterShowActivity activity = (FilterShowActivity) getContext();
- activity.showRepresentation(representation);
- mCurrentView.setSelected(false);
- }
- }
- if (event.getActionMasked() == MotionEvent.ACTION_UP
- || (!mStartedDrag && event.getActionMasked() == MotionEvent.ACTION_CANCEL)) {
- checkEndState();
- if (mCurrentView != null) {
- FilterRepresentation representation = mCurrentView.getState().getFilterRepresentation();
- if (representation.getEditorId() == ImageOnlyEditor.ID) {
- mCurrentView.setSelected(false);
- }
- }
- }
- return true;
- }
-
- public void checkEndState() {
- mTouchPoint = null;
- mTouchTime = 0;
- if (mExited || mCurrentView.getBackgroundAlpha() < mDeleteSlope) {
- int origin = findChild(mCurrentView);
- if (origin != -1) {
- State current = mAdapter.getItem(origin);
- FilterRepresentation currentRep = MasterImage.getImage().getCurrentFilterRepresentation();
- FilterRepresentation removedRep = current.getFilterRepresentation();
- mAdapter.remove(current);
- fillContent(true);
- if (currentRep != null && removedRep != null
- && currentRep.getFilterClass() == removedRep.getFilterClass()) {
- FilterShowActivity activity = (FilterShowActivity) getContext();
- activity.backToMain();
- return;
- }
- }
- } else {
- mCurrentView.setBackgroundAlpha(1.0f);
- mCurrentView.setTranslationX(0);
- mCurrentView.setTranslationY(0);
- }
- if (mCurrentSelectedView != null) {
- mCurrentSelectedView.invalidate();
- }
- if (mCurrentView != null) {
- mCurrentView.invalidate();
- }
- mCurrentView = null;
- mExited = false;
- mStartedDrag = false;
- }
-
- public View findChildAt(int x, int y) {
- Rect frame = new Rect();
- int scrolledXInt = getScrollX() + x;
- int scrolledYInt = getScrollY() + y;
- for (int i = 0; i < getChildCount(); i++) {
- View child = getChildAt(i);
- child.getHitRect(frame);
- if (frame.contains(scrolledXInt, scrolledYInt)) {
- return child;
- }
- }
- return null;
- }
-
- public int findChild(View view) {
- for (int i = 0; i < getChildCount(); i++) {
- View child = getChildAt(i);
- if (child == view) {
- return i;
- }
- }
- return -1;
- }
-
- public StateView getCurrentView() {
- return mCurrentView;
- }
-
- public void setCurrentView(View currentView) {
- mCurrentView = (StateView) currentView;
- }
-
- public void setExited(boolean value) {
- mExited = value;
- }
-
- public Point getTouchPoint() {
- return mTouchPoint;
- }
-
- public Adapter getAdapter() {
- return mAdapter;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/state/StateView.java b/src/com/android/gallery3d/filtershow/state/StateView.java
deleted file mode 100644
index 73d57846a..000000000
--- a/src/com/android/gallery3d/filtershow/state/StateView.java
+++ /dev/null
@@ -1,291 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.state;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.*;
-import android.util.AttributeSet;
-import android.util.Log;
-import android.view.MotionEvent;
-import android.view.View;
-import android.view.ViewParent;
-import android.widget.LinearLayout;
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-
-public class StateView extends View {
-
- private static final String LOGTAG = "StateView";
- private Path mPath = new Path();
- private Paint mPaint = new Paint();
-
- public static int DEFAULT = 0;
- public static int BEGIN = 1;
- public static int END = 2;
-
- public static int UP = 1;
- public static int DOWN = 2;
- public static int LEFT = 3;
- public static int RIGHT = 4;
-
- private int mType = DEFAULT;
- private float mAlpha = 1.0f;
- private String mText = "Default";
- private float mTextSize = 32;
- private static int sMargin = 16;
- private static int sArrowHeight = 16;
- private static int sArrowWidth = 8;
- private int mOrientation = LinearLayout.VERTICAL;
- private int mDirection = DOWN;
- private boolean mDuplicateButton;
- private State mState;
-
- private int mEndsBackgroundColor;
- private int mEndsTextColor;
- private int mBackgroundColor;
- private int mTextColor;
- private int mSelectedBackgroundColor;
- private int mSelectedTextColor;
- private Rect mTextBounds = new Rect();
-
- public StateView(Context context) {
- this(context, DEFAULT);
- }
-
- public StateView(Context context, int type) {
- super(context);
- mType = type;
- Resources res = getResources();
- mEndsBackgroundColor = res.getColor(R.color.filtershow_stateview_end_background);
- mEndsTextColor = res.getColor(R.color.filtershow_stateview_end_text);
- mBackgroundColor = res.getColor(R.color.filtershow_stateview_background);
- mTextColor = res.getColor(R.color.filtershow_stateview_text);
- mSelectedBackgroundColor = res.getColor(R.color.filtershow_stateview_selected_background);
- mSelectedTextColor = res.getColor(R.color.filtershow_stateview_selected_text);
- mTextSize = res.getDimensionPixelSize(R.dimen.state_panel_text_size);
- }
-
- public String getText() {
- return mText;
- }
-
- public void setText(String text) {
- mText = text;
- invalidate();
- }
-
- public void setType(int type) {
- mType = type;
- invalidate();
- }
-
- @Override
- public void setSelected(boolean value) {
- super.setSelected(value);
- if (!value) {
- mDuplicateButton = false;
- }
- invalidate();
- }
-
- @Override
- public boolean onTouchEvent(MotionEvent event) {
- if (event.getActionMasked() == MotionEvent.ACTION_DOWN) {
- ViewParent parent = getParent();
- if (parent instanceof PanelTrack) {
- ((PanelTrack) getParent()).onTouch(event, this);
- }
- if (mType == BEGIN) {
- MasterImage.getImage().setShowsOriginal(true);
- }
- }
- if (event.getActionMasked() == MotionEvent.ACTION_UP
- || event.getActionMasked() == MotionEvent.ACTION_CANCEL) {
- MasterImage.getImage().setShowsOriginal(false);
- }
- return true;
- }
-
- public void drawText(Canvas canvas) {
- if (mText == null) {
- return;
- }
- mPaint.reset();
- if (isSelected()) {
- mPaint.setColor(mSelectedTextColor);
- } else {
- mPaint.setColor(mTextColor);
- }
- if (mType == BEGIN) {
- mPaint.setColor(mEndsTextColor);
- }
- mPaint.setTypeface(Typeface.DEFAULT_BOLD);
- mPaint.setAntiAlias(true);
- mPaint.setTextSize(mTextSize);
- mPaint.getTextBounds(mText, 0, mText.length(), mTextBounds);
- int x = (canvas.getWidth() - mTextBounds.width()) / 2;
- int y = mTextBounds.height() + (canvas.getHeight() - mTextBounds.height()) / 2;
- canvas.drawText(mText, x, y, mPaint);
- }
-
- public void onDraw(Canvas canvas) {
- canvas.drawARGB(0, 0, 0, 0);
- mPaint.reset();
- mPath.reset();
-
- float w = canvas.getWidth();
- float h = canvas.getHeight();
- float r = sArrowHeight;
- float d = sArrowWidth;
-
- if (mOrientation == LinearLayout.HORIZONTAL) {
- drawHorizontalPath(w, h, r, d);
- } else {
- if (mDirection == DOWN) {
- drawVerticalDownPath(w, h, r, d);
- } else {
- drawVerticalPath(w, h, r, d);
- }
- }
-
- if (mType == DEFAULT || mType == END) {
- if (mDuplicateButton) {
- mPaint.setARGB(255, 200, 0, 0);
- } else if (isSelected()) {
- mPaint.setColor(mSelectedBackgroundColor);
- } else {
- mPaint.setColor(mBackgroundColor);
- }
- } else {
- mPaint.setColor(mEndsBackgroundColor);
- }
- canvas.drawPath(mPath, mPaint);
- drawText(canvas);
- }
-
- private void drawHorizontalPath(float w, float h, float r, float d) {
- mPath.moveTo(0, 0);
- if (mType == END) {
- mPath.lineTo(w, 0);
- mPath.lineTo(w, h);
- } else {
- mPath.lineTo(w - d, 0);
- mPath.lineTo(w - d, r);
- mPath.lineTo(w, r + d);
- mPath.lineTo(w - d, r + d + r);
- mPath.lineTo(w - d, h);
- }
- mPath.lineTo(0, h);
- if (mType != BEGIN) {
- mPath.lineTo(0, r + d + r);
- mPath.lineTo(d, r + d);
- mPath.lineTo(0, r);
- }
- mPath.close();
- }
-
- private void drawVerticalPath(float w, float h, float r, float d) {
- if (mType == BEGIN) {
- mPath.moveTo(0, 0);
- mPath.lineTo(w, 0);
- } else {
- mPath.moveTo(0, d);
- mPath.lineTo(r, d);
- mPath.lineTo(r + d, 0);
- mPath.lineTo(r + d + r, d);
- mPath.lineTo(w, d);
- }
- mPath.lineTo(w, h);
- if (mType != END) {
- mPath.lineTo(r + d + r, h);
- mPath.lineTo(r + d, h - d);
- mPath.lineTo(r, h);
- }
- mPath.lineTo(0, h);
- mPath.close();
- }
-
- private void drawVerticalDownPath(float w, float h, float r, float d) {
- mPath.moveTo(0, 0);
- if (mType != BEGIN) {
- mPath.lineTo(r, 0);
- mPath.lineTo(r + d, d);
- mPath.lineTo(r + d + r, 0);
- }
- mPath.lineTo(w, 0);
-
- if (mType != END) {
- mPath.lineTo(w, h - d);
-
- mPath.lineTo(r + d + r, h - d);
- mPath.lineTo(r + d, h);
- mPath.lineTo(r, h - d);
-
- mPath.lineTo(0, h - d);
- } else {
- mPath.lineTo(w, h);
- mPath.lineTo(0, h);
- }
-
- mPath.close();
- }
-
- public void setBackgroundAlpha(float alpha) {
- if (mType == BEGIN) {
- return;
- }
- mAlpha = alpha;
- setAlpha(alpha);
- invalidate();
- }
-
- public float getBackgroundAlpha() {
- return mAlpha;
- }
-
- public void setOrientation(int orientation) {
- mOrientation = orientation;
- }
-
- public void setDuplicateButton(boolean b) {
- mDuplicateButton = b;
- invalidate();
- }
-
- public State getState() {
- return mState;
- }
-
- public void setState(State state) {
- mState = state;
- mText = mState.getText().toUpperCase();
- mType = mState.getType();
- invalidate();
- }
-
- public void resetPosition() {
- setTranslationX(0);
- setTranslationY(0);
- setBackgroundAlpha(1.0f);
- }
-
- public boolean isDraggable() {
- return mState.isDraggable();
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/tools/IconFactory.java b/src/com/android/gallery3d/filtershow/tools/IconFactory.java
deleted file mode 100644
index 9e39f27fc..000000000
--- a/src/com/android/gallery3d/filtershow/tools/IconFactory.java
+++ /dev/null
@@ -1,108 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.tools;
-
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.graphics.Rect;
-import android.graphics.RectF;
-
-/**
- * A factory class for producing bitmaps to use as UI icons.
- */
-public class IconFactory {
-
- /**
- * Builds an icon with the dimensions iconWidth:iconHeight. If scale is set
- * the source image is stretched to fit within the given dimensions;
- * otherwise, the source image is cropped to the proper aspect ratio.
- *
- * @param sourceImage image to create an icon from.
- * @param iconWidth width of the icon bitmap.
- * @param iconHeight height of the icon bitmap.
- * @param scale if true, stretch sourceImage to fit the icon dimensions.
- * @return an icon bitmap with the dimensions iconWidth:iconHeight.
- */
- public static Bitmap createIcon(Bitmap sourceImage, int iconWidth, int iconHeight,
- boolean scale) {
- if (sourceImage == null) {
- throw new IllegalArgumentException("Null argument to buildIcon");
- }
-
- int sourceWidth = sourceImage.getWidth();
- int sourceHeight = sourceImage.getHeight();
-
- if (sourceWidth == 0 || sourceHeight == 0 || iconWidth == 0 || iconHeight == 0) {
- throw new IllegalArgumentException("Bitmap with dimension 0 used as input");
- }
-
- Bitmap icon = Bitmap.createBitmap(iconWidth, iconHeight,
- Bitmap.Config.ARGB_8888);
- drawIcon(icon, sourceImage, scale);
- return icon;
- }
-
- /**
- * Draws an icon in the destination bitmap. If scale is set the source image
- * is stretched to fit within the destination dimensions; otherwise, the
- * source image is cropped to the proper aspect ratio.
- *
- * @param dest bitmap into which to draw the icon.
- * @param sourceImage image to create an icon from.
- * @param scale if true, stretch sourceImage to fit the destination.
- */
- public static void drawIcon(Bitmap dest, Bitmap sourceImage, boolean scale) {
- if (dest == null || sourceImage == null) {
- throw new IllegalArgumentException("Null argument to buildIcon");
- }
-
- int sourceWidth = sourceImage.getWidth();
- int sourceHeight = sourceImage.getHeight();
- int iconWidth = dest.getWidth();
- int iconHeight = dest.getHeight();
-
- if (sourceWidth == 0 || sourceHeight == 0 || iconWidth == 0 || iconHeight == 0) {
- throw new IllegalArgumentException("Bitmap with dimension 0 used as input");
- }
-
- Rect destRect = new Rect(0, 0, iconWidth, iconHeight);
- Canvas canvas = new Canvas(dest);
-
- Rect srcRect = null;
- if (scale) {
- // scale image to fit in icon (stretches if aspect isn't the same)
- srcRect = new Rect(0, 0, sourceWidth, sourceHeight);
- } else {
- // crop image to aspect ratio iconWidth:iconHeight
- float wScale = sourceWidth / (float) iconWidth;
- float hScale = sourceHeight / (float) iconHeight;
- float s = Math.min(hScale, wScale);
-
- float iw = iconWidth * s;
- float ih = iconHeight * s;
-
- float borderW = (sourceWidth - iw) / 2.0f;
- float borderH = (sourceHeight - ih) / 2.0f;
- RectF rec = new RectF(borderW, borderH, borderW + iw, borderH + ih);
- srcRect = new Rect();
- rec.roundOut(srcRect);
- }
-
- canvas.drawBitmap(sourceImage, srcRect, destRect, new Paint(Paint.FILTER_BITMAP_FLAG));
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/tools/MatrixFit.java b/src/com/android/gallery3d/filtershow/tools/MatrixFit.java
deleted file mode 100644
index 3b815673c..000000000
--- a/src/com/android/gallery3d/filtershow/tools/MatrixFit.java
+++ /dev/null
@@ -1,200 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.tools;
-
-import android.util.Log;
-
-public class MatrixFit {
- // Simple implementation of a matrix fit in N dimensions.
-
- private static final String LOGTAG = "MatrixFit";
-
- private double[][] mMatrix;
- private int mDimension;
- private boolean mValid = false;
- private static double sEPS = 1.0f/10000000000.0f;
-
- public MatrixFit(double[][] from, double[][] to) {
- mValid = fit(from, to);
- }
-
- public int getDimension() {
- return mDimension;
- }
-
- public boolean isValid() {
- return mValid;
- }
-
- public double[][] getMatrix() {
- return mMatrix;
- }
-
- public boolean fit(double[][] from, double[][] to) {
- if ((from.length != to.length) || (from.length < 1)) {
- Log.e(LOGTAG, "from and to must be of same size");
- return false;
- }
-
- mDimension = from[0].length;
- mMatrix = new double[mDimension +1][mDimension + mDimension +1];
-
- if (from.length < mDimension) {
- Log.e(LOGTAG, "Too few points => under-determined system");
- return false;
- }
-
- double[][] q = new double[from.length][mDimension];
- for (int i = 0; i < from.length; i++) {
- for (int j = 0; j < mDimension; j++) {
- q[i][j] = from[i][j];
- }
- }
-
- double[][] p = new double[to.length][mDimension];
- for (int i = 0; i < to.length; i++) {
- for (int j = 0; j < mDimension; j++) {
- p[i][j] = to[i][j];
- }
- }
-
- // Make an empty (dim) x (dim + 1) matrix and fill it
- double[][] c = new double[mDimension+1][mDimension];
- for (int j = 0; j < mDimension; j++) {
- for (int k = 0; k < mDimension + 1; k++) {
- for (int i = 0; i < q.length; i++) {
- double qt = 1;
- if (k < mDimension) {
- qt = q[i][k];
- }
- c[k][j] += qt * p[i][j];
- }
- }
- }
-
- // Make an empty (dim+1) x (dim+1) matrix and fill it
- double[][] Q = new double[mDimension+1][mDimension+1];
- for (int qi = 0; qi < q.length; qi++) {
- double[] qt = new double[mDimension + 1];
- for (int i = 0; i < mDimension; i++) {
- qt[i] = q[qi][i];
- }
- qt[mDimension] = 1;
- for (int i = 0; i < mDimension + 1; i++) {
- for (int j = 0; j < mDimension + 1; j++) {
- Q[i][j] += qt[i] * qt[j];
- }
- }
- }
-
- // Use a gaussian elimination to solve the linear system
- for (int i = 0; i < mDimension + 1; i++) {
- for (int j = 0; j < mDimension + 1; j++) {
- mMatrix[i][j] = Q[i][j];
- }
- for (int j = 0; j < mDimension; j++) {
- mMatrix[i][mDimension + 1 + j] = c[i][j];
- }
- }
- if (!gaussianElimination(mMatrix)) {
- return false;
- }
- return true;
- }
-
- public double[] apply(double[] point) {
- if (mDimension != point.length) {
- return null;
- }
- double[] res = new double[mDimension];
- for (int j = 0; j < mDimension; j++) {
- for (int i = 0; i < mDimension; i++) {
- res[j] += point[i] * mMatrix[i][j+ mDimension +1];
- }
- res[j] += mMatrix[mDimension][j+ mDimension +1];
- }
- return res;
- }
-
- public void printEquation() {
- for (int j = 0; j < mDimension; j++) {
- String str = "x" + j + "' = ";
- for (int i = 0; i < mDimension; i++) {
- str += "x" + i + " * " + mMatrix[i][j+mDimension+1] + " + ";
- }
- str += mMatrix[mDimension][j+mDimension+1];
- Log.v(LOGTAG, str);
- }
- }
-
- private void printMatrix(String name, double[][] matrix) {
- Log.v(LOGTAG, "name: " + name);
- for (int i = 0; i < matrix.length; i++) {
- String str = "";
- for (int j = 0; j < matrix[0].length; j++) {
- str += "" + matrix[i][j] + " ";
- }
- Log.v(LOGTAG, str);
- }
- }
-
- /*
- * Transforms the given matrix into a row echelon matrix
- */
- private boolean gaussianElimination(double[][] m) {
- int h = m.length;
- int w = m[0].length;
-
- for (int y = 0; y < h; y++) {
- int maxrow = y;
- for (int y2 = y + 1; y2 < h; y2++) { // Find max pivot
- if (Math.abs(m[y2][y]) > Math.abs(m[maxrow][y])) {
- maxrow = y2;
- }
- }
- // swap
- for (int i = 0; i < mDimension; i++) {
- double t = m[y][i];
- m[y][i] = m[maxrow][i];
- m[maxrow][i] = t;
- }
-
- if (Math.abs(m[y][y]) <= sEPS) { // Singular Matrix
- return false;
- }
- for (int y2 = y + 1; y2 < h; y2++) { // Eliminate column y
- double c = m[y2][y] / m[y][y];
- for (int x = y; x < w; x++) {
- m[y2][x] -= m[y][x] * c;
- }
- }
- }
- for (int y = h -1; y > -1; y--) { // Back substitution
- double c = m[y][y];
- for (int y2 = 0; y2 < y; y2++) {
- for (int x = w - 1; x > y - 1; x--) {
- m[y2][x] -= m[y][x] * m[y2][y] / c;
- }
- }
- m[y][y] /= c;
- for (int x = h; x < w; x++) { // Normalize row y
- m[y][x] /= c;
- }
- }
- return true;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/tools/SaveImage.java b/src/com/android/gallery3d/filtershow/tools/SaveImage.java
deleted file mode 100644
index 83cbd0136..000000000
--- a/src/com/android/gallery3d/filtershow/tools/SaveImage.java
+++ /dev/null
@@ -1,632 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.tools;
-
-import android.content.ContentResolver;
-import android.content.ContentValues;
-import android.content.Context;
-import android.content.Intent;
-import android.database.Cursor;
-import android.graphics.Bitmap;
-import android.net.Uri;
-import android.os.Environment;
-import android.provider.MediaStore;
-import android.provider.MediaStore.Images;
-import android.provider.MediaStore.Images.ImageColumns;
-import android.util.Log;
-
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.exif.ExifInterface;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.cache.ImageLoader;
-import com.android.gallery3d.filtershow.filters.FiltersManager;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.pipeline.CachingPipeline;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-import com.android.gallery3d.filtershow.pipeline.ProcessingService;
-import com.android.gallery3d.util.UsageStatistics;
-import com.android.gallery3d.util.XmpUtilHelper;
-
-import java.io.File;
-import java.io.FileNotFoundException;
-import java.io.FilenameFilter;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.OutputStream;
-import java.sql.Date;
-import java.text.SimpleDateFormat;
-import java.util.TimeZone;
-
-/**
- * Handles saving edited photo
- */
-public class SaveImage {
- private static final String LOGTAG = "SaveImage";
-
- /**
- * Callback for updates
- */
- public interface Callback {
- void onProgress(int max, int current);
- }
-
- public interface ContentResolverQueryCallback {
- void onCursorResult(Cursor cursor);
- }
-
- private static final String TIME_STAMP_NAME = "_yyyyMMdd_HHmmss";
- private static final String PREFIX_PANO = "PANO";
- private static final String PREFIX_IMG = "IMG";
- private static final String POSTFIX_JPG = ".jpg";
- private static final String AUX_DIR_NAME = ".aux";
-
- private final Context mContext;
- private final Uri mSourceUri;
- private final Callback mCallback;
- private final File mDestinationFile;
- private final Uri mSelectedImageUri;
-
- private int mCurrentProcessingStep = 1;
-
- public static final int MAX_PROCESSING_STEPS = 6;
- public static final String DEFAULT_SAVE_DIRECTORY = "EditedOnlinePhotos";
-
- // In order to support the new edit-save behavior such that user won't see
- // the edited image together with the original image, we are adding a new
- // auxiliary directory for the edited image. Basically, the original image
- // will be hidden in that directory after edit and user will see the edited
- // image only.
- // Note that deletion on the edited image will also cause the deletion of
- // the original image under auxiliary directory.
- //
- // There are several situations we need to consider:
- // 1. User edit local image local01.jpg. A local02.jpg will be created in the
- // same directory, and original image will be moved to auxiliary directory as
- // ./.aux/local02.jpg.
- // If user edit the local02.jpg, local03.jpg will be created in the local
- // directory and ./.aux/local02.jpg will be renamed to ./.aux/local03.jpg
- //
- // 2. User edit remote image remote01.jpg from picassa or other server.
- // remoteSavedLocal01.jpg will be saved under proper local directory.
- // In remoteSavedLocal01.jpg, there will be a reference pointing to the
- // remote01.jpg. There will be no local copy of remote01.jpg.
- // If user edit remoteSavedLocal01.jpg, then a new remoteSavedLocal02.jpg
- // will be generated and still pointing to the remote01.jpg
- //
- // 3. User delete any local image local.jpg.
- // Since the filenames are kept consistent in auxiliary directory, every
- // time a local.jpg get deleted, the files in auxiliary directory whose
- // names starting with "local." will be deleted.
- // This pattern will facilitate the multiple images deletion in the auxiliary
- // directory.
-
- /**
- * @param context
- * @param sourceUri The Uri for the original image, which can be the hidden
- * image under the auxiliary directory or the same as selectedImageUri.
- * @param selectedImageUri The Uri for the image selected by the user.
- * In most cases, it is a content Uri for local image or remote image.
- * @param destination Destinaton File, if this is null, a new file will be
- * created under the same directory as selectedImageUri.
- * @param callback Let the caller know the saving has completed.
- * @return the newSourceUri
- */
- public SaveImage(Context context, Uri sourceUri, Uri selectedImageUri,
- File destination, Callback callback) {
- mContext = context;
- mSourceUri = sourceUri;
- mCallback = callback;
- if (destination == null) {
- mDestinationFile = getNewFile(context, selectedImageUri);
- } else {
- mDestinationFile = destination;
- }
-
- mSelectedImageUri = selectedImageUri;
- }
-
- public static File getFinalSaveDirectory(Context context, Uri sourceUri) {
- File saveDirectory = SaveImage.getSaveDirectory(context, sourceUri);
- if ((saveDirectory == null) || !saveDirectory.canWrite()) {
- saveDirectory = new File(Environment.getExternalStorageDirectory(),
- SaveImage.DEFAULT_SAVE_DIRECTORY);
- }
- // Create the directory if it doesn't exist
- if (!saveDirectory.exists())
- saveDirectory.mkdirs();
- return saveDirectory;
- }
-
- public static File getNewFile(Context context, Uri sourceUri) {
- File saveDirectory = getFinalSaveDirectory(context, sourceUri);
- String filename = new SimpleDateFormat(TIME_STAMP_NAME).format(new Date(
- System.currentTimeMillis()));
- if (hasPanoPrefix(context, sourceUri)) {
- return new File(saveDirectory, PREFIX_PANO + filename + POSTFIX_JPG);
- }
- return new File(saveDirectory, PREFIX_IMG + filename + POSTFIX_JPG);
- }
-
- /**
- * Remove the files in the auxiliary directory whose names are the same as
- * the source image.
- * @param contentResolver The application's contentResolver
- * @param srcContentUri The content Uri for the source image.
- */
- public static void deleteAuxFiles(ContentResolver contentResolver,
- Uri srcContentUri) {
- final String[] fullPath = new String[1];
- String[] queryProjection = new String[] { ImageColumns.DATA };
- querySourceFromContentResolver(contentResolver,
- srcContentUri, queryProjection,
- new ContentResolverQueryCallback() {
- @Override
- public void onCursorResult(Cursor cursor) {
- fullPath[0] = cursor.getString(0);
- }
- }
- );
- if (fullPath[0] != null) {
- // Construct the auxiliary directory given the source file's path.
- // Then select and delete all the files starting with the same name
- // under the auxiliary directory.
- File currentFile = new File(fullPath[0]);
-
- String filename = currentFile.getName();
- int firstDotPos = filename.indexOf(".");
- final String filenameNoExt = (firstDotPos == -1) ? filename :
- filename.substring(0, firstDotPos);
- File auxDir = getLocalAuxDirectory(currentFile);
- if (auxDir.exists()) {
- FilenameFilter filter = new FilenameFilter() {
- @Override
- public boolean accept(File dir, String name) {
- if (name.startsWith(filenameNoExt + ".")) {
- return true;
- } else {
- return false;
- }
- }
- };
-
- // Delete all auxiliary files whose name is matching the
- // current local image.
- File[] auxFiles = auxDir.listFiles(filter);
- for (File file : auxFiles) {
- file.delete();
- }
- }
- }
- }
-
- public Object getPanoramaXMPData(Uri source, ImagePreset preset) {
- Object xmp = null;
- if (preset.isPanoramaSafe()) {
- InputStream is = null;
- try {
- is = mContext.getContentResolver().openInputStream(source);
- xmp = XmpUtilHelper.extractXMPMeta(is);
- } catch (FileNotFoundException e) {
- Log.w(LOGTAG, "Failed to get XMP data from image: ", e);
- } finally {
- Utils.closeSilently(is);
- }
- }
- return xmp;
- }
-
- public boolean putPanoramaXMPData(File file, Object xmp) {
- if (xmp != null) {
- return XmpUtilHelper.writeXMPMeta(file.getAbsolutePath(), xmp);
- }
- return false;
- }
-
- public ExifInterface getExifData(Uri source) {
- ExifInterface exif = new ExifInterface();
- String mimeType = mContext.getContentResolver().getType(mSelectedImageUri);
- if (mimeType == null) {
- mimeType = ImageLoader.getMimeType(mSelectedImageUri);
- }
- if (mimeType.equals(ImageLoader.JPEG_MIME_TYPE)) {
- InputStream inStream = null;
- try {
- inStream = mContext.getContentResolver().openInputStream(source);
- exif.readExif(inStream);
- } catch (FileNotFoundException e) {
- Log.w(LOGTAG, "Cannot find file: " + source, e);
- } catch (IOException e) {
- Log.w(LOGTAG, "Cannot read exif for: " + source, e);
- } finally {
- Utils.closeSilently(inStream);
- }
- }
- return exif;
- }
-
- public boolean putExifData(File file, ExifInterface exif, Bitmap image,
- int jpegCompressQuality) {
- boolean ret = false;
- OutputStream s = null;
- try {
- s = exif.getExifWriterStream(file.getAbsolutePath());
- image.compress(Bitmap.CompressFormat.JPEG,
- (jpegCompressQuality > 0) ? jpegCompressQuality : 1, s);
- s.flush();
- s.close();
- s = null;
- ret = true;
- } catch (FileNotFoundException e) {
- Log.w(LOGTAG, "File not found: " + file.getAbsolutePath(), e);
- } catch (IOException e) {
- Log.w(LOGTAG, "Could not write exif: ", e);
- } finally {
- Utils.closeSilently(s);
- }
- return ret;
- }
-
- private Uri resetToOriginalImageIfNeeded(ImagePreset preset, boolean doAuxBackup) {
- Uri uri = null;
- if (!preset.hasModifications()) {
- // This can happen only when preset has no modification but save
- // button is enabled, it means the file is loaded with filters in
- // the XMP, then all the filters are removed or restore to default.
- // In this case, when mSourceUri exists, rename it to the
- // destination file.
- File srcFile = getLocalFileFromUri(mContext, mSourceUri);
- // If the source is not a local file, then skip this renaming and
- // create a local copy as usual.
- if (srcFile != null) {
- srcFile.renameTo(mDestinationFile);
- uri = SaveImage.linkNewFileToUri(mContext, mSelectedImageUri,
- mDestinationFile, System.currentTimeMillis(), doAuxBackup);
- }
- }
- return uri;
- }
-
- private void resetProgress() {
- mCurrentProcessingStep = 0;
- }
-
- private void updateProgress() {
- if (mCallback != null) {
- mCallback.onProgress(MAX_PROCESSING_STEPS, ++mCurrentProcessingStep);
- }
- }
-
- public Uri processAndSaveImage(ImagePreset preset, boolean doAuxBackup, int quality) {
-
- Uri uri = resetToOriginalImageIfNeeded(preset, doAuxBackup);
- if (uri != null) {
- return null;
- }
-
- resetProgress();
-
- boolean noBitmap = true;
- int num_tries = 0;
- int sampleSize = 1;
-
- // If necessary, move the source file into the auxiliary directory,
- // newSourceUri is then pointing to the new location.
- // If no file is moved, newSourceUri will be the same as mSourceUri.
- Uri newSourceUri = mSourceUri;
- if (doAuxBackup) {
- newSourceUri = moveSrcToAuxIfNeeded(mSourceUri, mDestinationFile);
- }
-
- // Stopgap fix for low-memory devices.
- while (noBitmap) {
- try {
- updateProgress();
- // Try to do bitmap operations, downsample if low-memory
- Bitmap bitmap = ImageLoader.loadOrientedBitmapWithBackouts(mContext, newSourceUri,
- sampleSize);
- if (bitmap == null) {
- return null;
- }
- updateProgress();
- CachingPipeline pipeline = new CachingPipeline(FiltersManager.getManager(),
- "Saving");
-
- bitmap = pipeline.renderFinalImage(bitmap, preset);
- updateProgress();
-
- Object xmp = getPanoramaXMPData(newSourceUri, preset);
- ExifInterface exif = getExifData(newSourceUri);
-
- updateProgress();
- // Set tags
- long time = System.currentTimeMillis();
- exif.addDateTimeStampTag(ExifInterface.TAG_DATE_TIME, time,
- TimeZone.getDefault());
- exif.setTag(exif.buildTag(ExifInterface.TAG_ORIENTATION,
- ExifInterface.Orientation.TOP_LEFT));
- // Remove old thumbnail
- exif.removeCompressedThumbnail();
-
- updateProgress();
-
- // If we succeed in writing the bitmap as a jpeg, return a uri.
- if (putExifData(mDestinationFile, exif, bitmap, quality)) {
- putPanoramaXMPData(mDestinationFile, xmp);
- // mDestinationFile will save the newSourceUri info in the XMP.
- XmpPresets.writeFilterXMP(mContext, newSourceUri,
- mDestinationFile, preset);
-
- // After this call, mSelectedImageUri will be actually
- // pointing at the new file mDestinationFile.
- uri = SaveImage.linkNewFileToUri(mContext, mSelectedImageUri,
- mDestinationFile, time, doAuxBackup);
- }
- updateProgress();
-
- noBitmap = false;
- UsageStatistics.onEvent(UsageStatistics.COMPONENT_EDITOR,
- "SaveComplete", null);
- } catch (OutOfMemoryError e) {
- // Try 5 times before failing for good.
- if (++num_tries >= 5) {
- throw e;
- }
- System.gc();
- sampleSize *= 2;
- resetProgress();
- }
- }
- return uri;
- }
-
- /**
- * Move the source file to auxiliary directory if needed and return the Uri
- * pointing to this new source file.
- * @param srcUri Uri to the source image.
- * @param dstFile Providing the destination file info to help to build the
- * auxiliary directory and new source file's name.
- * @return the newSourceUri pointing to the new source image.
- */
- private Uri moveSrcToAuxIfNeeded(Uri srcUri, File dstFile) {
- File srcFile = getLocalFileFromUri(mContext, srcUri);
- if (srcFile == null) {
- Log.d(LOGTAG, "Source file is not a local file, no update.");
- return srcUri;
- }
-
- // Get the destination directory and create the auxilliary directory
- // if necessary.
- File auxDiretory = getLocalAuxDirectory(dstFile);
- if (!auxDiretory.exists()) {
- auxDiretory.mkdirs();
- }
-
- // Make sure there is a .nomedia file in the auxiliary directory, such
- // that MediaScanner will not report those files under this directory.
- File noMedia = new File(auxDiretory, ".nomedia");
- if (!noMedia.exists()) {
- try {
- noMedia.createNewFile();
- } catch (IOException e) {
- Log.e(LOGTAG, "Can't create the nomedia");
- return srcUri;
- }
- }
- // We are using the destination file name such that photos sitting in
- // the auxiliary directory are matching the parent directory.
- File newSrcFile = new File(auxDiretory, dstFile.getName());
-
- if (!newSrcFile.exists()) {
- srcFile.renameTo(newSrcFile);
- }
-
- return Uri.fromFile(newSrcFile);
-
- }
-
- private static File getLocalAuxDirectory(File dstFile) {
- File dstDirectory = dstFile.getParentFile();
- File auxDiretory = new File(dstDirectory + "/" + AUX_DIR_NAME);
- return auxDiretory;
- }
-
- public static Uri makeAndInsertUri(Context context, Uri sourceUri) {
- long time = System.currentTimeMillis();
- String filename = new SimpleDateFormat(TIME_STAMP_NAME).format(new Date(time));
- File saveDirectory = getFinalSaveDirectory(context, sourceUri);
- File file = new File(saveDirectory, filename + ".JPG");
- return linkNewFileToUri(context, sourceUri, file, time, false);
- }
-
- public static void saveImage(ImagePreset preset, final FilterShowActivity filterShowActivity,
- File destination) {
- Uri selectedImageUri = filterShowActivity.getSelectedImageUri();
- Uri sourceImageUri = MasterImage.getImage().getUri();
-
- Intent processIntent = ProcessingService.getSaveIntent(filterShowActivity, preset,
- destination, selectedImageUri, sourceImageUri, false, 90);
-
- filterShowActivity.startService(processIntent);
-
- if (!filterShowActivity.isSimpleEditAction()) {
- // terminate for now
- filterShowActivity.completeSaveImage(selectedImageUri);
- }
- }
-
- public static void querySource(Context context, Uri sourceUri, String[] projection,
- ContentResolverQueryCallback callback) {
- ContentResolver contentResolver = context.getContentResolver();
- querySourceFromContentResolver(contentResolver, sourceUri, projection, callback);
- }
-
- private static void querySourceFromContentResolver(
- ContentResolver contentResolver, Uri sourceUri, String[] projection,
- ContentResolverQueryCallback callback) {
- Cursor cursor = null;
- try {
- cursor = contentResolver.query(sourceUri, projection, null, null,
- null);
- if ((cursor != null) && cursor.moveToNext()) {
- callback.onCursorResult(cursor);
- }
- } catch (Exception e) {
- // Ignore error for lacking the data column from the source.
- } finally {
- if (cursor != null) {
- cursor.close();
- }
- }
- }
-
- private static File getSaveDirectory(Context context, Uri sourceUri) {
- File file = getLocalFileFromUri(context, sourceUri);
- if (file != null) {
- return file.getParentFile();
- } else {
- return null;
- }
- }
-
- /**
- * Construct a File object based on the srcUri.
- * @return The file object. Return null if srcUri is invalid or not a local
- * file.
- */
- private static File getLocalFileFromUri(Context context, Uri srcUri) {
- if (srcUri == null) {
- Log.e(LOGTAG, "srcUri is null.");
- return null;
- }
-
- String scheme = srcUri.getScheme();
- if (scheme == null) {
- Log.e(LOGTAG, "scheme is null.");
- return null;
- }
-
- final File[] file = new File[1];
- // sourceUri can be a file path or a content Uri, it need to be handled
- // differently.
- if (scheme.equals(ContentResolver.SCHEME_CONTENT)) {
- if (srcUri.getAuthority().equals(MediaStore.AUTHORITY)) {
- querySource(context, srcUri, new String[] {
- ImageColumns.DATA
- },
- new ContentResolverQueryCallback() {
-
- @Override
- public void onCursorResult(Cursor cursor) {
- file[0] = new File(cursor.getString(0));
- }
- });
- }
- } else if (scheme.equals(ContentResolver.SCHEME_FILE)) {
- file[0] = new File(srcUri.getPath());
- }
- return file[0];
- }
-
- /**
- * Gets the actual filename for a Uri from Gallery's ContentProvider.
- */
- private static String getTrueFilename(Context context, Uri src) {
- if (context == null || src == null) {
- return null;
- }
- final String[] trueName = new String[1];
- querySource(context, src, new String[] {
- ImageColumns.DATA
- }, new ContentResolverQueryCallback() {
- @Override
- public void onCursorResult(Cursor cursor) {
- trueName[0] = new File(cursor.getString(0)).getName();
- }
- });
- return trueName[0];
- }
-
- /**
- * Checks whether the true filename has the panorama image prefix.
- */
- private static boolean hasPanoPrefix(Context context, Uri src) {
- String name = getTrueFilename(context, src);
- return name != null && name.startsWith(PREFIX_PANO);
- }
-
- /**
- * If the <code>sourceUri</code> is a local content Uri, update the
- * <code>sourceUri</code> to point to the <code>file</code>.
- * At the same time, the old file <code>sourceUri</code> used to point to
- * will be removed if it is local.
- * If the <code>sourceUri</code> is not a local content Uri, then the
- * <code>file</code> will be inserted as a new content Uri.
- * @return the final Uri referring to the <code>file</code>.
- */
- public static Uri linkNewFileToUri(Context context, Uri sourceUri,
- File file, long time, boolean deleteOriginal) {
- File oldSelectedFile = getLocalFileFromUri(context, sourceUri);
- final ContentValues values = new ContentValues();
-
- time /= 1000;
- values.put(Images.Media.TITLE, file.getName());
- values.put(Images.Media.DISPLAY_NAME, file.getName());
- values.put(Images.Media.MIME_TYPE, "image/jpeg");
- values.put(Images.Media.DATE_TAKEN, time);
- values.put(Images.Media.DATE_MODIFIED, time);
- values.put(Images.Media.DATE_ADDED, time);
- values.put(Images.Media.ORIENTATION, 0);
- values.put(Images.Media.DATA, file.getAbsolutePath());
- values.put(Images.Media.SIZE, file.length());
-
- final String[] projection = new String[] {
- ImageColumns.DATE_TAKEN,
- ImageColumns.LATITUDE, ImageColumns.LONGITUDE,
- };
- SaveImage.querySource(context, sourceUri, projection,
- new SaveImage.ContentResolverQueryCallback() {
-
- @Override
- public void onCursorResult(Cursor cursor) {
- values.put(Images.Media.DATE_TAKEN, cursor.getLong(0));
-
- double latitude = cursor.getDouble(1);
- double longitude = cursor.getDouble(2);
- // TODO: Change || to && after the default location
- // issue is fixed.
- if ((latitude != 0f) || (longitude != 0f)) {
- values.put(Images.Media.LATITUDE, latitude);
- values.put(Images.Media.LONGITUDE, longitude);
- }
- }
- });
-
- Uri result = sourceUri;
- if (oldSelectedFile == null || !deleteOriginal) {
- result = context.getContentResolver().insert(
- Images.Media.EXTERNAL_CONTENT_URI, values);
- } else {
- context.getContentResolver().update(sourceUri, values, null, null);
- if (oldSelectedFile.exists()) {
- oldSelectedFile.delete();
- }
- }
-
- return result;
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/tools/XmpPresets.java b/src/com/android/gallery3d/filtershow/tools/XmpPresets.java
deleted file mode 100644
index 3995eeb85..000000000
--- a/src/com/android/gallery3d/filtershow/tools/XmpPresets.java
+++ /dev/null
@@ -1,133 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.tools;
-
-import android.content.Context;
-import android.net.Uri;
-import android.util.Log;
-
-import com.adobe.xmp.XMPException;
-import com.adobe.xmp.XMPMeta;
-import com.adobe.xmp.XMPMetaFactory;
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.pipeline.ImagePreset;
-import com.android.gallery3d.util.XmpUtilHelper;
-
-import java.io.File;
-import java.io.FileNotFoundException;
-import java.io.InputStream;
-
-public class XmpPresets {
- public static final String
- XMP_GOOGLE_FILTER_NAMESPACE = "http://ns.google.com/photos/1.0/filter/";
- public static final String XMP_GOOGLE_FILTER_PREFIX = "AFltr";
- public static final String XMP_SRC_FILE_URI = "SourceFileUri";
- public static final String XMP_FILTERSTACK = "filterstack";
- private static final String LOGTAG = "XmpPresets";
-
- public static class XMresults {
- public String presetString;
- public ImagePreset preset;
- public Uri originalimage;
- }
-
- static {
- try {
- XMPMetaFactory.getSchemaRegistry().registerNamespace(
- XMP_GOOGLE_FILTER_NAMESPACE, XMP_GOOGLE_FILTER_PREFIX);
- } catch (XMPException e) {
- Log.e(LOGTAG, "Register XMP name space failed", e);
- }
- }
-
- public static void writeFilterXMP(
- Context context, Uri srcUri, File dstFile, ImagePreset preset) {
- InputStream is = null;
- XMPMeta xmpMeta = null;
- try {
- is = context.getContentResolver().openInputStream(srcUri);
- xmpMeta = XmpUtilHelper.extractXMPMeta(is);
- } catch (FileNotFoundException e) {
-
- } finally {
- Utils.closeSilently(is);
- }
-
- if (xmpMeta == null) {
- xmpMeta = XMPMetaFactory.create();
- }
- try {
- xmpMeta.setProperty(XMP_GOOGLE_FILTER_NAMESPACE,
- XMP_SRC_FILE_URI, srcUri.toString());
- xmpMeta.setProperty(XMP_GOOGLE_FILTER_NAMESPACE,
- XMP_FILTERSTACK, preset.getJsonString(context.getString(R.string.saved)));
- } catch (XMPException e) {
- Log.v(LOGTAG, "Write XMP meta to file failed:" + dstFile.getAbsolutePath());
- return;
- }
-
- if (!XmpUtilHelper.writeXMPMeta(dstFile.getAbsolutePath(), xmpMeta)) {
- Log.v(LOGTAG, "Write XMP meta to file failed:" + dstFile.getAbsolutePath());
- }
- }
-
- public static XMresults extractXMPData(
- Context context, MasterImage mMasterImage, Uri uriToEdit) {
- XMresults ret = new XMresults();
-
- InputStream is = null;
- XMPMeta xmpMeta = null;
- try {
- is = context.getContentResolver().openInputStream(uriToEdit);
- xmpMeta = XmpUtilHelper.extractXMPMeta(is);
- } catch (FileNotFoundException e) {
- } finally {
- Utils.closeSilently(is);
- }
-
- if (xmpMeta == null) {
- return null;
- }
-
- try {
- String strSrcUri = xmpMeta.getPropertyString(XMP_GOOGLE_FILTER_NAMESPACE,
- XMP_SRC_FILE_URI);
-
- if (strSrcUri != null) {
- String filterString = xmpMeta.getPropertyString(XMP_GOOGLE_FILTER_NAMESPACE,
- XMP_FILTERSTACK);
-
- Uri srcUri = Uri.parse(strSrcUri);
- ret.originalimage = srcUri;
-
- ret.preset = new ImagePreset(mMasterImage.getPreset());
- ret.presetString = filterString;
- boolean ok = ret.preset.readJsonFromString(filterString);
- if (!ok) {
- return null;
- }
- return ret;
- }
- } catch (XMPException e) {
- e.printStackTrace();
- }
-
- return null;
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/ui/ExportDialog.java b/src/com/android/gallery3d/filtershow/ui/ExportDialog.java
deleted file mode 100644
index 4b30e7b18..000000000
--- a/src/com/android/gallery3d/filtershow/ui/ExportDialog.java
+++ /dev/null
@@ -1,90 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.ui;
-
-import android.content.Intent;
-import android.net.Uri;
-import android.os.Bundle;
-import android.support.v4.app.DialogFragment;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.SeekBar;
-import android.widget.TextView;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.filtershow.FilterShowActivity;
-import com.android.gallery3d.filtershow.imageshow.MasterImage;
-import com.android.gallery3d.filtershow.pipeline.ProcessingService;
-import com.android.gallery3d.filtershow.tools.SaveImage;
-
-import java.io.File;
-
-public class ExportDialog extends DialogFragment implements View.OnClickListener, SeekBar.OnSeekBarChangeListener{
- SeekBar mSeekBar;
- TextView mSeekVal;
- String mSliderLabel;
-
- @Override
- public View onCreateView(LayoutInflater inflater, ViewGroup container,
- Bundle savedInstanceState) {
- View view = inflater.inflate(R.layout.filtershow_export_dialog, container);
- mSeekBar = (SeekBar) view.findViewById(R.id.qualitySeekBar);
- mSeekVal = (TextView) view.findViewById(R.id.qualityTextView);
- mSliderLabel = getString(R.string.quality) + ": ";
- mSeekVal.setText(mSliderLabel + mSeekBar.getProgress());
- mSeekBar.setOnSeekBarChangeListener(this);
- view.findViewById(R.id.cancel).setOnClickListener(this);
- view.findViewById(R.id.done).setOnClickListener(this);
- getDialog().setTitle(R.string.export_flattened);
- return view;
- }
-
- @Override
- public void onStopTrackingTouch(SeekBar arg0) {
- // Do nothing
- }
-
- @Override
- public void onStartTrackingTouch(SeekBar arg0) {
- // Do nothing
- }
-
- @Override
- public void onProgressChanged(SeekBar arg0, int arg1, boolean arg2) {
- mSeekVal.setText(mSliderLabel + arg1);
- }
-
- @Override
- public void onClick(View v) {
- switch (v.getId()) {
- case R.id.cancel:
- dismiss();
- break;
- case R.id.done:
- FilterShowActivity activity = (FilterShowActivity) getActivity();
- Uri sourceUri = MasterImage.getImage().getUri();
- File dest = SaveImage.getNewFile(activity, sourceUri);
- Intent processIntent = ProcessingService.getSaveIntent(activity, MasterImage
- .getImage().getPreset(), dest, activity.getSelectedImageUri(), sourceUri,
- true, mSeekBar.getProgress());
- activity.startService(processIntent);
- dismiss();
- break;
- }
- }
-}
diff --git a/src/com/android/gallery3d/filtershow/ui/FramedTextButton.java b/src/com/android/gallery3d/filtershow/ui/FramedTextButton.java
deleted file mode 100644
index c1e4109d2..000000000
--- a/src/com/android/gallery3d/filtershow/ui/FramedTextButton.java
+++ /dev/null
@@ -1,137 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.ui;
-
-import android.content.Context;
-import android.content.res.TypedArray;
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.graphics.Path;
-import android.graphics.Rect;
-import android.util.AttributeSet;
-import android.widget.ImageButton;
-
-import com.android.gallery3d.R;
-
-public class FramedTextButton extends ImageButton {
- private static final String LOGTAG = "FramedTextButton";
- private String mText = null;
- private static int mTextSize = 24;
- private static int mTextPadding = 20;
- private static Paint gPaint = new Paint();
- private static Path gPath = new Path();
- private static int mTrianglePadding = 2;
- private static int mTriangleSize = 30;
-
- public static void setTextSize(int value) {
- mTextSize = value;
- }
-
- public static void setTextPadding(int value) {
- mTextPadding = value;
- }
-
- public static void setTrianglePadding(int value) {
- mTrianglePadding = value;
- }
-
- public static void setTriangleSize(int value) {
- mTriangleSize = value;
- }
-
- public void setText(String text) {
- mText = text;
- invalidate();
- }
-
- public void setTextFrom(int itemId) {
- switch (itemId) {
- case R.id.curve_menu_rgb: {
- setText(getContext().getString(R.string.curves_channel_rgb));
- break;
- }
- case R.id.curve_menu_red: {
- setText(getContext().getString(R.string.curves_channel_red));
- break;
- }
- case R.id.curve_menu_green: {
- setText(getContext().getString(R.string.curves_channel_green));
- break;
- }
- case R.id.curve_menu_blue: {
- setText(getContext().getString(R.string.curves_channel_blue));
- break;
- }
- }
- invalidate();
- }
-
- public FramedTextButton(Context context) {
- this(context, null);
- }
-
- public FramedTextButton(Context context, AttributeSet attrs) {
- super(context, attrs);
- if (attrs == null) {
- return;
- }
- TypedArray a = getContext().obtainStyledAttributes(
- attrs, R.styleable.ImageButtonTitle);
-
- mText = a.getString(R.styleable.ImageButtonTitle_android_text);
- }
-
- public String getText(){
- return mText;
- }
-
- @Override
- public void onDraw(Canvas canvas) {
- gPaint.setARGB(96, 255, 255, 255);
- gPaint.setStrokeWidth(2);
- gPaint.setStyle(Paint.Style.STROKE);
- int w = getWidth();
- int h = getHeight();
- canvas.drawRect(mTextPadding, mTextPadding, w - mTextPadding,
- h - mTextPadding, gPaint);
- gPath.reset();
- gPath.moveTo(w - mTextPadding - mTrianglePadding - mTriangleSize,
- h - mTextPadding - mTrianglePadding);
- gPath.lineTo(w - mTextPadding - mTrianglePadding,
- h - mTextPadding - mTrianglePadding - mTriangleSize);
- gPath.lineTo(w - mTextPadding - mTrianglePadding,
- h - mTextPadding - mTrianglePadding);
- gPath.close();
- gPaint.setARGB(128, 255, 255, 255);
- gPaint.setStrokeWidth(1);
- gPaint.setStyle(Paint.Style.FILL_AND_STROKE);
- canvas.drawPath(gPath, gPaint);
- if (mText != null) {
- gPaint.reset();
- gPaint.setARGB(255, 255, 255, 255);
- gPaint.setTextSize(mTextSize);
- float textWidth = gPaint.measureText(mText);
- Rect bounds = new Rect();
- gPaint.getTextBounds(mText, 0, mText.length(), bounds);
- int x = (int) ((w - textWidth) / 2);
- int y = (h + bounds.height()) / 2;
-
- canvas.drawText(mText, x, y, gPaint);
- }
- }
-
-}
diff --git a/src/com/android/gallery3d/filtershow/ui/SelectionRenderer.java b/src/com/android/gallery3d/filtershow/ui/SelectionRenderer.java
deleted file mode 100644
index ef40c5e44..000000000
--- a/src/com/android/gallery3d/filtershow/ui/SelectionRenderer.java
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.filtershow.ui;
-
-import android.graphics.Canvas;
-import android.graphics.Paint;
-
-public class SelectionRenderer {
-
- public static void drawSelection(Canvas canvas, int left, int top, int right, int bottom,
- int stroke, Paint paint) {
- canvas.drawRect(left, top, right, top + stroke, paint);
- canvas.drawRect(left, bottom - stroke, right, bottom, paint);
- canvas.drawRect(left, top, left + stroke, bottom, paint);
- canvas.drawRect(right - stroke, top, right, bottom, paint);
- }
-
- public static void drawSelection(Canvas canvas, int left, int top, int right, int bottom,
- int stroke, Paint selectPaint, int border, Paint borderPaint) {
- canvas.drawRect(left, top, right, top + stroke, selectPaint);
- canvas.drawRect(left, bottom - stroke, right, bottom, selectPaint);
- canvas.drawRect(left, top, left + stroke, bottom, selectPaint);
- canvas.drawRect(right - stroke, top, right, bottom, selectPaint);
- canvas.drawRect(left + stroke, top + stroke, right - stroke,
- top + stroke + border, borderPaint);
- canvas.drawRect(left + stroke, bottom - stroke - border, right - stroke,
- bottom - stroke, borderPaint);
- canvas.drawRect(left + stroke, top + stroke, left + stroke + border,
- bottom - stroke, borderPaint);
- canvas.drawRect(right - stroke - border, top + stroke, right - stroke,
- bottom - stroke, borderPaint);
- }
-
-}
diff --git a/src/com/android/gallery3d/gadget/LocalPhotoSource.java b/src/com/android/gallery3d/gadget/LocalPhotoSource.java
deleted file mode 100644
index 4e94e8d75..000000000
--- a/src/com/android/gallery3d/gadget/LocalPhotoSource.java
+++ /dev/null
@@ -1,205 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.gadget;
-
-import android.content.ContentResolver;
-import android.content.Context;
-import android.database.ContentObserver;
-import android.database.Cursor;
-import android.graphics.Bitmap;
-import android.net.Uri;
-import android.os.Environment;
-import android.os.Handler;
-import android.provider.MediaStore.Images.Media;
-
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.ContentListener;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.util.GalleryUtils;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.HashSet;
-import java.util.Random;
-
-public class LocalPhotoSource implements WidgetSource {
-
- @SuppressWarnings("unused")
- private static final String TAG = "LocalPhotoSource";
-
- private static final int MAX_PHOTO_COUNT = 128;
-
- /* Static fields used to query for the correct set of images */
- private static final Uri CONTENT_URI = Media.EXTERNAL_CONTENT_URI;
- private static final String DATE_TAKEN = Media.DATE_TAKEN;
- private static final String[] PROJECTION = {Media._ID};
- private static final String[] COUNT_PROJECTION = {"count(*)"};
- /* We don't want to include the download directory */
- private static final String SELECTION =
- String.format("%s != %s", Media.BUCKET_ID, getDownloadBucketId());
- private static final String ORDER = String.format("%s DESC", DATE_TAKEN);
-
- private Context mContext;
- private ArrayList<Long> mPhotos = new ArrayList<Long>();
- private ContentListener mContentListener;
- private ContentObserver mContentObserver;
- private boolean mContentDirty = true;
- private DataManager mDataManager;
- private static final Path LOCAL_IMAGE_ROOT = Path.fromString("/local/image/item");
-
- public LocalPhotoSource(Context context) {
- mContext = context;
- mDataManager = ((GalleryApp) context.getApplicationContext()).getDataManager();
- mContentObserver = new ContentObserver(new Handler()) {
- @Override
- public void onChange(boolean selfChange) {
- mContentDirty = true;
- if (mContentListener != null) mContentListener.onContentDirty();
- }
- };
- mContext.getContentResolver()
- .registerContentObserver(CONTENT_URI, true, mContentObserver);
- }
-
- @Override
- public void close() {
- mContext.getContentResolver().unregisterContentObserver(mContentObserver);
- }
-
- @Override
- public Uri getContentUri(int index) {
- if (index < mPhotos.size()) {
- return CONTENT_URI.buildUpon()
- .appendPath(String.valueOf(mPhotos.get(index)))
- .build();
- }
- return null;
- }
-
- @Override
- public Bitmap getImage(int index) {
- if (index >= mPhotos.size()) return null;
- long id = mPhotos.get(index);
- MediaItem image = (MediaItem)
- mDataManager.getMediaObject(LOCAL_IMAGE_ROOT.getChild(id));
- if (image == null) return null;
-
- return WidgetUtils.createWidgetBitmap(image);
- }
-
- private int[] getExponentialIndice(int total, int count) {
- Random random = new Random();
- if (count > total) count = total;
- HashSet<Integer> selected = new HashSet<Integer>(count);
- while (selected.size() < count) {
- int row = (int)(-Math.log(random.nextDouble()) * total / 2);
- if (row < total) selected.add(row);
- }
- int values[] = new int[count];
- int index = 0;
- for (int value : selected) {
- values[index++] = value;
- }
- return values;
- }
-
- private int getPhotoCount(ContentResolver resolver) {
- Cursor cursor = resolver.query(
- CONTENT_URI, COUNT_PROJECTION, SELECTION, null, null);
- if (cursor == null) return 0;
- try {
- Utils.assertTrue(cursor.moveToNext());
- return cursor.getInt(0);
- } finally {
- cursor.close();
- }
- }
-
- private boolean isContentSound(int totalCount) {
- if (mPhotos.size() < Math.min(totalCount, MAX_PHOTO_COUNT)) return false;
- if (mPhotos.size() == 0) return true; // totalCount is also 0
-
- StringBuilder builder = new StringBuilder();
- for (Long imageId : mPhotos) {
- if (builder.length() > 0) builder.append(",");
- builder.append(imageId);
- }
- Cursor cursor = mContext.getContentResolver().query(
- CONTENT_URI, COUNT_PROJECTION,
- String.format("%s in (%s)", Media._ID, builder.toString()),
- null, null);
- if (cursor == null) return false;
- try {
- Utils.assertTrue(cursor.moveToNext());
- return cursor.getInt(0) == mPhotos.size();
- } finally {
- cursor.close();
- }
- }
-
- @Override
- public void reload() {
- if (!mContentDirty) return;
- mContentDirty = false;
-
- ContentResolver resolver = mContext.getContentResolver();
- int photoCount = getPhotoCount(resolver);
- if (isContentSound(photoCount)) return;
-
- int choosedIds[] = getExponentialIndice(photoCount, MAX_PHOTO_COUNT);
- Arrays.sort(choosedIds);
-
- mPhotos.clear();
- Cursor cursor = mContext.getContentResolver().query(
- CONTENT_URI, PROJECTION, SELECTION, null, ORDER);
- if (cursor == null) return;
- try {
- for (int index : choosedIds) {
- if (cursor.moveToPosition(index)) {
- mPhotos.add(cursor.getLong(0));
- }
- }
- } finally {
- cursor.close();
- }
- }
-
- @Override
- public int size() {
- reload();
- return mPhotos.size();
- }
-
- /**
- * Builds the bucket ID for the public external storage Downloads directory
- * @return the bucket ID
- */
- private static int getDownloadBucketId() {
- String downloadsPath = Environment
- .getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS)
- .getAbsolutePath();
- return GalleryUtils.getBucketId(downloadsPath);
- }
-
- @Override
- public void setContentListener(ContentListener listener) {
- mContentListener = listener;
- }
-}
diff --git a/src/com/android/gallery3d/gadget/MediaSetSource.java b/src/com/android/gallery3d/gadget/MediaSetSource.java
deleted file mode 100644
index 458651c98..000000000
--- a/src/com/android/gallery3d/gadget/MediaSetSource.java
+++ /dev/null
@@ -1,233 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.gadget;
-
-import android.graphics.Bitmap;
-import android.net.Uri;
-import android.os.Binder;
-
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.ContentListener;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-
-public class MediaSetSource implements WidgetSource, ContentListener {
- private static final String TAG = "MediaSetSource";
-
- private DataManager mDataManager;
- private Path mAlbumPath;
-
- private WidgetSource mSource;
-
- private MediaSet mRootSet;
- private ContentListener mListener;
-
- public MediaSetSource(DataManager manager, String albumPath) {
- MediaSet mediaSet = (MediaSet) manager.getMediaObject(albumPath);
- if (mediaSet != null) {
- mSource = new CheckedMediaSetSource(mediaSet);
- return;
- }
-
- // Initialize source to an empty source until the album path can be resolved
- mDataManager = Utils.checkNotNull(manager);
- mAlbumPath = Path.fromString(albumPath);
- mSource = new EmptySource();
- monitorRootPath();
- }
-
- @Override
- public int size() {
- return mSource.size();
- }
-
- @Override
- public Bitmap getImage(int index) {
- return mSource.getImage(index);
- }
-
- @Override
- public Uri getContentUri(int index) {
- return mSource.getContentUri(index);
- }
-
- @Override
- public synchronized void setContentListener(ContentListener listener) {
- if (mRootSet != null) {
- mListener = listener;
- } else {
- mSource.setContentListener(listener);
- }
- }
-
- @Override
- public void reload() {
- mSource.reload();
- }
-
- @Override
- public void close() {
- mSource.close();
- }
-
- @Override
- public void onContentDirty() {
- resolveAlbumPath();
- }
-
- private void monitorRootPath() {
- String rootPath = mDataManager.getTopSetPath(DataManager.INCLUDE_ALL);
- mRootSet = (MediaSet) mDataManager.getMediaObject(rootPath);
- mRootSet.addContentListener(this);
- }
-
- private synchronized void resolveAlbumPath() {
- if (mDataManager == null) return;
- MediaSet mediaSet = (MediaSet) mDataManager.getMediaObject(mAlbumPath);
- if (mediaSet != null) {
- // Clear the reference instead of removing the listener
- // to get around a concurrent modification exception.
- mRootSet = null;
-
- mSource = new CheckedMediaSetSource(mediaSet);
- if (mListener != null) {
- mListener.onContentDirty();
- mSource.setContentListener(mListener);
- mListener = null;
- }
- mDataManager = null;
- mAlbumPath = null;
- }
- }
-
- private static class CheckedMediaSetSource implements WidgetSource, ContentListener {
- private static final int CACHE_SIZE = 32;
-
- @SuppressWarnings("unused")
- private static final String TAG = "CheckedMediaSetSource";
-
- private MediaSet mSource;
- private MediaItem mCache[] = new MediaItem[CACHE_SIZE];
- private int mCacheStart;
- private int mCacheEnd;
- private long mSourceVersion = MediaObject.INVALID_DATA_VERSION;
-
- private ContentListener mContentListener;
-
- public CheckedMediaSetSource(MediaSet source) {
- mSource = Utils.checkNotNull(source);
- mSource.addContentListener(this);
- }
-
- @Override
- public void close() {
- mSource.removeContentListener(this);
- }
-
- private void ensureCacheRange(int index) {
- if (index >= mCacheStart && index < mCacheEnd) return;
-
- long token = Binder.clearCallingIdentity();
- try {
- mCacheStart = index;
- ArrayList<MediaItem> items = mSource.getMediaItem(mCacheStart, CACHE_SIZE);
- mCacheEnd = mCacheStart + items.size();
- items.toArray(mCache);
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public synchronized Uri getContentUri(int index) {
- ensureCacheRange(index);
- if (index < mCacheStart || index >= mCacheEnd) return null;
- return mCache[index - mCacheStart].getContentUri();
- }
-
- @Override
- public synchronized Bitmap getImage(int index) {
- ensureCacheRange(index);
- if (index < mCacheStart || index >= mCacheEnd) return null;
- return WidgetUtils.createWidgetBitmap(mCache[index - mCacheStart]);
- }
-
- @Override
- public void reload() {
- long version = mSource.reload();
- if (mSourceVersion != version) {
- mSourceVersion = version;
- mCacheStart = 0;
- mCacheEnd = 0;
- Arrays.fill(mCache, null);
- }
- }
-
- @Override
- public void setContentListener(ContentListener listener) {
- mContentListener = listener;
- }
-
- @Override
- public int size() {
- long token = Binder.clearCallingIdentity();
- try {
- return mSource.getMediaItemCount();
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public void onContentDirty() {
- if (mContentListener != null) mContentListener.onContentDirty();
- }
- }
-
- private static class EmptySource implements WidgetSource {
-
- @Override
- public int size() {
- return 0;
- }
-
- @Override
- public Bitmap getImage(int index) {
- throw new UnsupportedOperationException();
- }
-
- @Override
- public Uri getContentUri(int index) {
- throw new UnsupportedOperationException();
- }
-
- @Override
- public void setContentListener(ContentListener listener) {}
-
- @Override
- public void reload() {}
-
- @Override
- public void close() {}
- }
-}
diff --git a/src/com/android/gallery3d/gadget/PhotoAppWidgetProvider.java b/src/com/android/gallery3d/gadget/PhotoAppWidgetProvider.java
deleted file mode 100644
index 58466bf01..000000000
--- a/src/com/android/gallery3d/gadget/PhotoAppWidgetProvider.java
+++ /dev/null
@@ -1,139 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.gadget;
-
-import android.annotation.TargetApi;
-import android.app.PendingIntent;
-import android.appwidget.AppWidgetManager;
-import android.appwidget.AppWidgetProvider;
-import android.content.Context;
-import android.content.Intent;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.net.Uri;
-import android.util.Log;
-import android.widget.RemoteViews;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.gadget.WidgetDatabaseHelper.Entry;
-import com.android.gallery3d.onetimeinitializer.GalleryWidgetMigrator;
-
-public class PhotoAppWidgetProvider extends AppWidgetProvider {
-
- private static final String TAG = "WidgetProvider";
-
- static RemoteViews buildWidget(Context context, int id, Entry entry) {
-
- switch (entry.type) {
- case WidgetDatabaseHelper.TYPE_ALBUM:
- case WidgetDatabaseHelper.TYPE_SHUFFLE:
- return buildStackWidget(context, id, entry);
- case WidgetDatabaseHelper.TYPE_SINGLE_PHOTO:
- return buildFrameWidget(context, id, entry);
- }
- throw new RuntimeException("invalid type - " + entry.type);
- }
-
- @Override
- public void onUpdate(Context context,
- AppWidgetManager appWidgetManager, int[] appWidgetIds) {
-
- if (ApiHelper.HAS_REMOTE_VIEWS_SERVICE) {
- // migrate gallery widgets from pre-JB releases to JB due to bucket ID change
- GalleryWidgetMigrator.migrateGalleryWidgets(context);
- }
-
- WidgetDatabaseHelper helper = new WidgetDatabaseHelper(context);
- try {
- for (int id : appWidgetIds) {
- Entry entry = helper.getEntry(id);
- if (entry != null) {
- RemoteViews views = buildWidget(context, id, entry);
- appWidgetManager.updateAppWidget(id, views);
- } else {
- Log.e(TAG, "cannot load widget: " + id);
- }
- }
- } finally {
- helper.close();
- }
- super.onUpdate(context, appWidgetManager, appWidgetIds);
- }
-
- @SuppressWarnings("deprecation")
- @TargetApi(ApiHelper.VERSION_CODES.HONEYCOMB)
- private static RemoteViews buildStackWidget(Context context, int widgetId, Entry entry) {
- RemoteViews views = new RemoteViews(
- context.getPackageName(), R.layout.appwidget_main);
-
- Intent intent = new Intent(context, WidgetService.class);
- intent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, widgetId);
- intent.putExtra(WidgetService.EXTRA_WIDGET_TYPE, entry.type);
- intent.putExtra(WidgetService.EXTRA_ALBUM_PATH, entry.albumPath);
- intent.setData(Uri.parse("widget://gallery/" + widgetId));
-
- // We use the deprecated API for backward compatibility
- // The new API is available in ICE_CREAM_SANDWICH (15)
- views.setRemoteAdapter(widgetId, R.id.appwidget_stack_view, intent);
-
- views.setEmptyView(R.id.appwidget_stack_view, R.id.appwidget_empty_view);
-
- Intent clickIntent = new Intent(context, WidgetClickHandler.class);
- PendingIntent pendingIntent = PendingIntent.getActivity(
- context, 0, clickIntent, PendingIntent.FLAG_UPDATE_CURRENT);
- views.setPendingIntentTemplate(R.id.appwidget_stack_view, pendingIntent);
-
- return views;
- }
-
- static RemoteViews buildFrameWidget(Context context, int appWidgetId, Entry entry) {
- RemoteViews views = new RemoteViews(
- context.getPackageName(), R.layout.photo_frame);
- try {
- byte[] data = entry.imageData;
- Bitmap bitmap = BitmapFactory.decodeByteArray(data, 0, data.length);
- views.setImageViewBitmap(R.id.photo, bitmap);
- } catch (Throwable t) {
- Log.w(TAG, "cannot load widget image: " + appWidgetId, t);
- }
-
- if (entry.imageUri != null) {
- try {
- Uri uri = Uri.parse(entry.imageUri);
- Intent clickIntent = new Intent(context, WidgetClickHandler.class)
- .setData(uri);
- PendingIntent pendingClickIntent = PendingIntent.getActivity(context, 0,
- clickIntent, PendingIntent.FLAG_CANCEL_CURRENT);
- views.setOnClickPendingIntent(R.id.photo, pendingClickIntent);
- } catch (Throwable t) {
- Log.w(TAG, "cannot load widget uri: " + appWidgetId, t);
- }
- }
- return views;
- }
-
- @Override
- public void onDeleted(Context context, int[] appWidgetIds) {
- // Clean deleted photos out of our database
- WidgetDatabaseHelper helper = new WidgetDatabaseHelper(context);
- for (int appWidgetId : appWidgetIds) {
- helper.deleteEntry(appWidgetId);
- }
- helper.close();
- }
-}
diff --git a/src/com/android/gallery3d/gadget/WidgetClickHandler.java b/src/com/android/gallery3d/gadget/WidgetClickHandler.java
deleted file mode 100644
index 37ee1a651..000000000
--- a/src/com/android/gallery3d/gadget/WidgetClickHandler.java
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * Copyright (C) 2009 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.gadget;
-
-import android.annotation.TargetApi;
-import android.app.Activity;
-import android.content.Intent;
-import android.content.res.AssetFileDescriptor;
-import android.net.Uri;
-import android.os.Build;
-import android.os.Bundle;
-import android.util.Log;
-import android.widget.Toast;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.Gallery;
-import com.android.gallery3d.app.PhotoPage;
-import com.android.gallery3d.common.ApiHelper;
-
-public class WidgetClickHandler extends Activity {
- private static final String TAG = "PhotoAppWidgetClickHandler";
-
- private boolean isValidDataUri(Uri dataUri) {
- if (dataUri == null) return false;
- try {
- AssetFileDescriptor f = getContentResolver()
- .openAssetFileDescriptor(dataUri, "r");
- f.close();
- return true;
- } catch (Throwable e) {
- Log.w(TAG, "cannot open uri: " + dataUri, e);
- return false;
- }
- }
-
- @Override
- @TargetApi(ApiHelper.VERSION_CODES.HONEYCOMB)
- protected void onCreate(Bundle savedState) {
- super.onCreate(savedState);
- // The behavior is changed in JB, refer to b/6384492 for more details
- boolean tediousBack = Build.VERSION.SDK_INT >= ApiHelper.VERSION_CODES.JELLY_BEAN;
- Uri uri = getIntent().getData();
- Intent intent;
- if (isValidDataUri(uri)) {
- intent = new Intent(Intent.ACTION_VIEW, uri);
- if (tediousBack) {
- intent.putExtra(PhotoPage.KEY_TREAT_BACK_AS_UP, true);
- }
- } else {
- Toast.makeText(this,
- R.string.no_such_item, Toast.LENGTH_LONG).show();
- intent = new Intent(this, Gallery.class);
- }
- if (tediousBack) {
- intent.setFlags(
- Intent.FLAG_ACTIVITY_NEW_TASK |
- Intent.FLAG_ACTIVITY_CLEAR_TASK |
- Intent.FLAG_ACTIVITY_TASK_ON_HOME);
- }
- startActivity(intent);
- finish();
- }
-}
diff --git a/src/com/android/gallery3d/gadget/WidgetConfigure.java b/src/com/android/gallery3d/gadget/WidgetConfigure.java
deleted file mode 100644
index 2a4c6cfe4..000000000
--- a/src/com/android/gallery3d/gadget/WidgetConfigure.java
+++ /dev/null
@@ -1,209 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.gadget;
-
-import android.app.Activity;
-import android.appwidget.AppWidgetManager;
-import android.content.Intent;
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.net.Uri;
-import android.os.Bundle;
-import android.util.Log;
-import android.widget.RemoteViews;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.AlbumPicker;
-import com.android.gallery3d.app.DialogPicker;
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.LocalAlbum;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.filtershow.crop.CropActivity;
-import com.android.gallery3d.filtershow.crop.CropExtras;
-
-public class WidgetConfigure extends Activity {
- @SuppressWarnings("unused")
- private static final String TAG = "WidgetConfigure";
-
- public static final String KEY_WIDGET_TYPE = "widget-type";
- private static final String KEY_PICKED_ITEM = "picked-item";
-
- private static final int REQUEST_WIDGET_TYPE = 1;
- private static final int REQUEST_CHOOSE_ALBUM = 2;
- private static final int REQUEST_CROP_IMAGE = 3;
- private static final int REQUEST_GET_PHOTO = 4;
-
- public static final int RESULT_ERROR = RESULT_FIRST_USER;
-
- // Scale up the widget size since we only specified the minimized
- // size of the gadget. The real size could be larger.
- // Note: There is also a limit on the size of data that can be
- // passed in Binder's transaction.
- private static float WIDGET_SCALE_FACTOR = 1.5f;
- private static int MAX_WIDGET_SIDE = 360;
-
- private int mAppWidgetId = -1;
- private Uri mPickedItem;
-
- @Override
- protected void onCreate(Bundle savedState) {
- super.onCreate(savedState);
- mAppWidgetId = getIntent().getIntExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, -1);
-
- if (mAppWidgetId == -1) {
- setResult(Activity.RESULT_CANCELED);
- finish();
- return;
- }
-
- if (savedState == null) {
- if (ApiHelper.HAS_REMOTE_VIEWS_SERVICE) {
- Intent intent = new Intent(this, WidgetTypeChooser.class);
- startActivityForResult(intent, REQUEST_WIDGET_TYPE);
- } else { // Choose the photo type widget
- setWidgetType(new Intent()
- .putExtra(KEY_WIDGET_TYPE, R.id.widget_type_photo));
- }
- } else {
- mPickedItem = savedState.getParcelable(KEY_PICKED_ITEM);
- }
- }
-
- protected void onSaveInstanceStates(Bundle outState) {
- super.onSaveInstanceState(outState);
- outState.putParcelable(KEY_PICKED_ITEM, mPickedItem);
- }
-
- private void updateWidgetAndFinish(WidgetDatabaseHelper.Entry entry) {
- AppWidgetManager manager = AppWidgetManager.getInstance(this);
- RemoteViews views = PhotoAppWidgetProvider.buildWidget(this, mAppWidgetId, entry);
- manager.updateAppWidget(mAppWidgetId, views);
- setResult(RESULT_OK, new Intent().putExtra(
- AppWidgetManager.EXTRA_APPWIDGET_ID, mAppWidgetId));
- finish();
- }
-
- @Override
- protected void onActivityResult(int requestCode, int resultCode, Intent data) {
- if (resultCode != RESULT_OK) {
- setResult(resultCode, new Intent().putExtra(
- AppWidgetManager.EXTRA_APPWIDGET_ID, mAppWidgetId));
- finish();
- return;
- }
-
- if (requestCode == REQUEST_WIDGET_TYPE) {
- setWidgetType(data);
- } else if (requestCode == REQUEST_CHOOSE_ALBUM) {
- setChoosenAlbum(data);
- } else if (requestCode == REQUEST_GET_PHOTO) {
- setChoosenPhoto(data);
- } else if (requestCode == REQUEST_CROP_IMAGE) {
- setPhotoWidget(data);
- } else {
- throw new AssertionError("unknown request: " + requestCode);
- }
- }
-
- private void setPhotoWidget(Intent data) {
- // Store the cropped photo in our database
- Bitmap bitmap = (Bitmap) data.getParcelableExtra("data");
- WidgetDatabaseHelper helper = new WidgetDatabaseHelper(this);
- try {
- helper.setPhoto(mAppWidgetId, mPickedItem, bitmap);
- updateWidgetAndFinish(helper.getEntry(mAppWidgetId));
- } finally {
- helper.close();
- }
- }
-
- private void setChoosenPhoto(Intent data) {
- Resources res = getResources();
-
- float width = res.getDimension(R.dimen.appwidget_width);
- float height = res.getDimension(R.dimen.appwidget_height);
-
- // We try to crop a larger image (by scale factor), but there is still
- // a bound on the binder limit.
- float scale = Math.min(WIDGET_SCALE_FACTOR,
- MAX_WIDGET_SIDE / Math.max(width, height));
-
- int widgetWidth = Math.round(width * scale);
- int widgetHeight = Math.round(height * scale);
-
- mPickedItem = data.getData();
- Intent request = new Intent(CropActivity.CROP_ACTION, mPickedItem)
- .putExtra(CropExtras.KEY_OUTPUT_X, widgetWidth)
- .putExtra(CropExtras.KEY_OUTPUT_Y, widgetHeight)
- .putExtra(CropExtras.KEY_ASPECT_X, widgetWidth)
- .putExtra(CropExtras.KEY_ASPECT_Y, widgetHeight)
- .putExtra(CropExtras.KEY_SCALE_UP_IF_NEEDED, true)
- .putExtra(CropExtras.KEY_SCALE, true)
- .putExtra(CropExtras.KEY_RETURN_DATA, true);
- startActivityForResult(request, REQUEST_CROP_IMAGE);
- }
-
- private void setChoosenAlbum(Intent data) {
- String albumPath = data.getStringExtra(AlbumPicker.KEY_ALBUM_PATH);
- WidgetDatabaseHelper helper = new WidgetDatabaseHelper(this);
- try {
- String relativePath = null;
- GalleryApp galleryApp = (GalleryApp) getApplicationContext();
- DataManager manager = galleryApp.getDataManager();
- Path path = Path.fromString(albumPath);
- MediaSet mediaSet = (MediaSet) manager.getMediaObject(path);
- if (mediaSet instanceof LocalAlbum) {
- int bucketId = Integer.parseInt(path.getSuffix());
- // If the chosen album is a local album, find relative path
- // Otherwise, leave the relative path field empty
- relativePath = LocalAlbum.getRelativePath(bucketId);
- Log.i(TAG, "Setting widget, album path: " + albumPath
- + ", relative path: " + relativePath);
- }
- helper.setWidget(mAppWidgetId,
- WidgetDatabaseHelper.TYPE_ALBUM, albumPath, relativePath);
- updateWidgetAndFinish(helper.getEntry(mAppWidgetId));
- } finally {
- helper.close();
- }
- }
-
- private void setWidgetType(Intent data) {
- int widgetType = data.getIntExtra(KEY_WIDGET_TYPE, R.id.widget_type_shuffle);
- if (widgetType == R.id.widget_type_album) {
- Intent intent = new Intent(this, AlbumPicker.class);
- startActivityForResult(intent, REQUEST_CHOOSE_ALBUM);
- } else if (widgetType == R.id.widget_type_shuffle) {
- WidgetDatabaseHelper helper = new WidgetDatabaseHelper(this);
- try {
- helper.setWidget(mAppWidgetId, WidgetDatabaseHelper.TYPE_SHUFFLE, null, null);
- updateWidgetAndFinish(helper.getEntry(mAppWidgetId));
- } finally {
- helper.close();
- }
- } else {
- // Explicitly send the intent to the DialogPhotoPicker
- Intent request = new Intent(this, DialogPicker.class)
- .setAction(Intent.ACTION_GET_CONTENT)
- .setType("image/*");
- startActivityForResult(request, REQUEST_GET_PHOTO);
- }
- }
-}
diff --git a/src/com/android/gallery3d/gadget/WidgetDatabaseHelper.java b/src/com/android/gallery3d/gadget/WidgetDatabaseHelper.java
deleted file mode 100644
index c0145843b..000000000
--- a/src/com/android/gallery3d/gadget/WidgetDatabaseHelper.java
+++ /dev/null
@@ -1,309 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.gadget;
-
-import android.content.ContentValues;
-import android.content.Context;
-import android.database.Cursor;
-import android.database.sqlite.SQLiteDatabase;
-import android.database.sqlite.SQLiteException;
-import android.database.sqlite.SQLiteOpenHelper;
-import android.graphics.Bitmap;
-import android.net.Uri;
-import android.util.Log;
-
-import com.android.gallery3d.common.Utils;
-
-import java.io.ByteArrayOutputStream;
-import java.util.ArrayList;
-import java.util.List;
-
-public class WidgetDatabaseHelper extends SQLiteOpenHelper {
- private static final String TAG = "PhotoDatabaseHelper";
- private static final String DATABASE_NAME = "launcher.db";
-
- // Increment the database version to 5. In version 5, we
- // add a column in widgets table to record relative paths.
- private static final int DATABASE_VERSION = 5;
-
- private static final String TABLE_WIDGETS = "widgets";
-
- private static final String FIELD_APPWIDGET_ID = "appWidgetId";
- private static final String FIELD_IMAGE_URI = "imageUri";
- private static final String FIELD_PHOTO_BLOB = "photoBlob";
- private static final String FIELD_WIDGET_TYPE = "widgetType";
- private static final String FIELD_ALBUM_PATH = "albumPath";
- private static final String FIELD_RELATIVE_PATH = "relativePath";
-
- public static final int TYPE_SINGLE_PHOTO = 0;
- public static final int TYPE_SHUFFLE = 1;
- public static final int TYPE_ALBUM = 2;
-
- private static final String[] PROJECTION = {
- FIELD_WIDGET_TYPE, FIELD_IMAGE_URI, FIELD_PHOTO_BLOB, FIELD_ALBUM_PATH,
- FIELD_APPWIDGET_ID, FIELD_RELATIVE_PATH};
- private static final int INDEX_WIDGET_TYPE = 0;
- private static final int INDEX_IMAGE_URI = 1;
- private static final int INDEX_PHOTO_BLOB = 2;
- private static final int INDEX_ALBUM_PATH = 3;
- private static final int INDEX_APPWIDGET_ID = 4;
- private static final int INDEX_RELATIVE_PATH = 5;
- private static final String WHERE_APPWIDGET_ID = FIELD_APPWIDGET_ID + " = ?";
- private static final String WHERE_WIDGET_TYPE = FIELD_WIDGET_TYPE + " = ?";
-
- public static class Entry {
- public int widgetId;
- public int type;
- public String imageUri;
- public byte imageData[];
- public String albumPath;
- public String relativePath;
-
- private Entry() {}
-
- private Entry(int id, Cursor cursor) {
- widgetId = id;
- type = cursor.getInt(INDEX_WIDGET_TYPE);
- if (type == TYPE_SINGLE_PHOTO) {
- imageUri = cursor.getString(INDEX_IMAGE_URI);
- imageData = cursor.getBlob(INDEX_PHOTO_BLOB);
- } else if (type == TYPE_ALBUM) {
- albumPath = cursor.getString(INDEX_ALBUM_PATH);
- relativePath = cursor.getString(INDEX_RELATIVE_PATH);
- }
- }
-
- private Entry(Cursor cursor) {
- this(cursor.getInt(INDEX_APPWIDGET_ID), cursor);
- }
- }
-
- public WidgetDatabaseHelper(Context context) {
- super(context, DATABASE_NAME, null, DATABASE_VERSION);
- }
-
- @Override
- public void onCreate(SQLiteDatabase db) {
- db.execSQL("CREATE TABLE " + TABLE_WIDGETS + " ("
- + FIELD_APPWIDGET_ID + " INTEGER PRIMARY KEY, "
- + FIELD_WIDGET_TYPE + " INTEGER DEFAULT 0, "
- + FIELD_IMAGE_URI + " TEXT, "
- + FIELD_ALBUM_PATH + " TEXT, "
- + FIELD_PHOTO_BLOB + " BLOB, "
- + FIELD_RELATIVE_PATH + " TEXT)");
- }
-
- private void saveData(SQLiteDatabase db, int oldVersion, ArrayList<Entry> data) {
- if (oldVersion <= 2) {
- Cursor cursor = db.query("photos",
- new String[] {FIELD_APPWIDGET_ID, FIELD_PHOTO_BLOB},
- null, null, null, null, null);
- if (cursor == null) return;
- try {
- while (cursor.moveToNext()) {
- Entry entry = new Entry();
- entry.type = TYPE_SINGLE_PHOTO;
- entry.widgetId = cursor.getInt(0);
- entry.imageData = cursor.getBlob(1);
- data.add(entry);
- }
- } finally {
- cursor.close();
- }
- } else if (oldVersion == 3) {
- Cursor cursor = db.query("photos",
- new String[] {FIELD_APPWIDGET_ID, FIELD_PHOTO_BLOB, FIELD_IMAGE_URI},
- null, null, null, null, null);
- if (cursor == null) return;
- try {
- while (cursor.moveToNext()) {
- Entry entry = new Entry();
- entry.type = TYPE_SINGLE_PHOTO;
- entry.widgetId = cursor.getInt(0);
- entry.imageData = cursor.getBlob(1);
- entry.imageUri = cursor.getString(2);
- data.add(entry);
- }
- } finally {
- cursor.close();
- }
- }
- }
-
- private void restoreData(SQLiteDatabase db, ArrayList<Entry> data) {
- db.beginTransaction();
- try {
- for (Entry entry : data) {
- ContentValues values = new ContentValues();
- values.put(FIELD_APPWIDGET_ID, entry.widgetId);
- values.put(FIELD_WIDGET_TYPE, entry.type);
- values.put(FIELD_IMAGE_URI, entry.imageUri);
- values.put(FIELD_PHOTO_BLOB, entry.imageData);
- values.put(FIELD_ALBUM_PATH, entry.albumPath);
- db.insert(TABLE_WIDGETS, null, values);
- }
- db.setTransactionSuccessful();
- } finally {
- db.endTransaction();
- }
- }
-
- @Override
- public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
- if (oldVersion < 4) {
- // Table "photos" is renamed to "widget" in version 4
- ArrayList<Entry> data = new ArrayList<Entry>();
- saveData(db, oldVersion, data);
-
- Log.w(TAG, "destroying all old data.");
- db.execSQL("DROP TABLE IF EXISTS photos");
- db.execSQL("DROP TABLE IF EXISTS " + TABLE_WIDGETS);
- onCreate(db);
-
- restoreData(db, data);
- }
- // Add a column for relative path
- if (oldVersion < DATABASE_VERSION) {
- try {
- db.execSQL("ALTER TABLE widgets ADD COLUMN relativePath TEXT");
- } catch (Throwable t) {
- Log.e(TAG, "Failed to add the column for relative path.");
- return;
- }
- }
- }
-
- /**
- * Store the given bitmap in this database for the given appWidgetId.
- */
- public boolean setPhoto(int appWidgetId, Uri imageUri, Bitmap bitmap) {
- try {
- // Try go guesstimate how much space the icon will take when
- // serialized to avoid unnecessary allocations/copies during
- // the write.
- int size = bitmap.getWidth() * bitmap.getHeight() * 4;
- ByteArrayOutputStream out = new ByteArrayOutputStream(size);
- bitmap.compress(Bitmap.CompressFormat.PNG, 100, out);
- out.close();
-
- ContentValues values = new ContentValues();
- values.put(FIELD_APPWIDGET_ID, appWidgetId);
- values.put(FIELD_WIDGET_TYPE, TYPE_SINGLE_PHOTO);
- values.put(FIELD_IMAGE_URI, imageUri.toString());
- values.put(FIELD_PHOTO_BLOB, out.toByteArray());
-
- SQLiteDatabase db = getWritableDatabase();
- db.replaceOrThrow(TABLE_WIDGETS, null, values);
- return true;
- } catch (Throwable e) {
- Log.e(TAG, "set widget photo fail", e);
- return false;
- }
- }
-
- public boolean setWidget(int id, int type, String albumPath, String relativePath) {
- try {
- ContentValues values = new ContentValues();
- values.put(FIELD_APPWIDGET_ID, id);
- values.put(FIELD_WIDGET_TYPE, type);
- values.put(FIELD_ALBUM_PATH, Utils.ensureNotNull(albumPath));
- values.put(FIELD_RELATIVE_PATH, relativePath);
- getWritableDatabase().replaceOrThrow(TABLE_WIDGETS, null, values);
- return true;
- } catch (Throwable e) {
- Log.e(TAG, "set widget fail", e);
- return false;
- }
- }
-
- public Entry getEntry(int appWidgetId) {
- Cursor cursor = null;
- try {
- SQLiteDatabase db = getReadableDatabase();
- cursor = db.query(TABLE_WIDGETS, PROJECTION,
- WHERE_APPWIDGET_ID, new String[] {String.valueOf(appWidgetId)},
- null, null, null);
- if (cursor == null || !cursor.moveToNext()) {
- Log.e(TAG, "query fail: empty cursor: " + cursor + " appWidgetId: "
- + appWidgetId);
- return null;
- }
- return new Entry(appWidgetId, cursor);
- } catch (Throwable e) {
- Log.e(TAG, "Could not load photo from database", e);
- return null;
- } finally {
- Utils.closeSilently(cursor);
- }
- }
-
- public List<Entry> getEntries(int type) {
- Cursor cursor = null;
- try {
- SQLiteDatabase db = getReadableDatabase();
- cursor = db.query(TABLE_WIDGETS, PROJECTION,
- WHERE_WIDGET_TYPE, new String[] {String.valueOf(type)},
- null, null, null);
- if (cursor == null) {
- Log.e(TAG, "query fail: null cursor: " + cursor);
- return null;
- }
- ArrayList<Entry> result = new ArrayList<Entry>(cursor.getCount());
- while (cursor.moveToNext()) {
- result.add(new Entry(cursor));
- }
- return result;
- } catch (Throwable e) {
- Log.e(TAG, "Could not load widget from database", e);
- return null;
- } finally {
- Utils.closeSilently(cursor);
- }
- }
-
- /**
- * Updates the entry in the widget database.
- */
- public void updateEntry(Entry entry) {
- deleteEntry(entry.widgetId);
- try {
- ContentValues values = new ContentValues();
- values.put(FIELD_APPWIDGET_ID, entry.widgetId);
- values.put(FIELD_WIDGET_TYPE, entry.type);
- values.put(FIELD_ALBUM_PATH, entry.albumPath);
- values.put(FIELD_IMAGE_URI, entry.imageUri);
- values.put(FIELD_PHOTO_BLOB, entry.imageData);
- values.put(FIELD_RELATIVE_PATH, entry.relativePath);
- getWritableDatabase().insert(TABLE_WIDGETS, null, values);
- } catch (Throwable e) {
- Log.e(TAG, "set widget fail", e);
- }
- }
-
- /**
- * Remove any bitmap associated with the given appWidgetId.
- */
- public void deleteEntry(int appWidgetId) {
- try {
- SQLiteDatabase db = getWritableDatabase();
- db.delete(TABLE_WIDGETS, WHERE_APPWIDGET_ID,
- new String[] {String.valueOf(appWidgetId)});
- } catch (SQLiteException e) {
- Log.e(TAG, "Could not delete photo from database", e);
- }
- }
-}
diff --git a/src/com/android/gallery3d/gadget/WidgetService.java b/src/com/android/gallery3d/gadget/WidgetService.java
deleted file mode 100644
index 94dd16439..000000000
--- a/src/com/android/gallery3d/gadget/WidgetService.java
+++ /dev/null
@@ -1,143 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.gadget;
-
-import android.annotation.TargetApi;
-import android.appwidget.AppWidgetManager;
-import android.content.Intent;
-import android.graphics.Bitmap;
-import android.net.Uri;
-import android.widget.RemoteViews;
-import android.widget.RemoteViewsService;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.data.ContentListener;
-
-@TargetApi(ApiHelper.VERSION_CODES.HONEYCOMB)
-public class WidgetService extends RemoteViewsService {
-
- @SuppressWarnings("unused")
- private static final String TAG = "GalleryAppWidgetService";
-
- public static final String EXTRA_WIDGET_TYPE = "widget-type";
- public static final String EXTRA_ALBUM_PATH = "album-path";
-
- @Override
- public RemoteViewsFactory onGetViewFactory(Intent intent) {
- int id = intent.getIntExtra(AppWidgetManager.EXTRA_APPWIDGET_ID,
- AppWidgetManager.INVALID_APPWIDGET_ID);
- int type = intent.getIntExtra(EXTRA_WIDGET_TYPE, 0);
- String albumPath = intent.getStringExtra(EXTRA_ALBUM_PATH);
-
- return new PhotoRVFactory((GalleryApp) getApplicationContext(),
- id, type, albumPath);
- }
-
- private static class PhotoRVFactory implements
- RemoteViewsService.RemoteViewsFactory, ContentListener {
-
- private final int mAppWidgetId;
- private final int mType;
- private final String mAlbumPath;
- private final GalleryApp mApp;
-
- private WidgetSource mSource;
-
- public PhotoRVFactory(GalleryApp app, int id, int type, String albumPath) {
- mApp = app;
- mAppWidgetId = id;
- mType = type;
- mAlbumPath = albumPath;
- }
-
- @Override
- public void onCreate() {
- if (mType == WidgetDatabaseHelper.TYPE_ALBUM) {
- mSource = new MediaSetSource(mApp.getDataManager(), mAlbumPath);
- } else {
- mSource = new LocalPhotoSource(mApp.getAndroidContext());
- }
- mSource.setContentListener(this);
- AppWidgetManager.getInstance(mApp.getAndroidContext())
- .notifyAppWidgetViewDataChanged(
- mAppWidgetId, R.id.appwidget_stack_view);
- }
-
- @Override
- public void onDestroy() {
- mSource.close();
- mSource = null;
- }
-
- @Override
- public int getCount() {
- return mSource.size();
- }
-
- @Override
- public long getItemId(int position) {
- return position;
- }
-
- @Override
- public int getViewTypeCount() {
- return 1;
- }
-
- @Override
- public boolean hasStableIds() {
- return true;
- }
-
- @Override
- public RemoteViews getLoadingView() {
- RemoteViews rv = new RemoteViews(
- mApp.getAndroidContext().getPackageName(),
- R.layout.appwidget_loading_item);
- rv.setProgressBar(R.id.appwidget_loading_item, 0, 0, true);
- return rv;
- }
-
- @Override
- public RemoteViews getViewAt(int position) {
- Bitmap bitmap = mSource.getImage(position);
- if (bitmap == null) return getLoadingView();
- RemoteViews views = new RemoteViews(
- mApp.getAndroidContext().getPackageName(),
- R.layout.appwidget_photo_item);
- views.setImageViewBitmap(R.id.appwidget_photo_item, bitmap);
- views.setOnClickFillInIntent(R.id.appwidget_photo_item, new Intent()
- .setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP)
- .setData(mSource.getContentUri(position)));
- return views;
- }
-
- @Override
- public void onDataSetChanged() {
- mSource.reload();
- }
-
- @Override
- public void onContentDirty() {
- AppWidgetManager.getInstance(mApp.getAndroidContext())
- .notifyAppWidgetViewDataChanged(
- mAppWidgetId, R.id.appwidget_stack_view);
- }
- }
-}
diff --git a/src/com/android/gallery3d/gadget/WidgetSource.java b/src/com/android/gallery3d/gadget/WidgetSource.java
deleted file mode 100644
index 92874c740..000000000
--- a/src/com/android/gallery3d/gadget/WidgetSource.java
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.gadget;
-
-import android.graphics.Bitmap;
-import android.net.Uri;
-
-import com.android.gallery3d.data.ContentListener;
-
-public interface WidgetSource {
- public int size();
- public Bitmap getImage(int index);
- public Uri getContentUri(int index);
- public void setContentListener(ContentListener listener);
- public void reload();
- public void close();
-}
diff --git a/src/com/android/gallery3d/gadget/WidgetTypeChooser.java b/src/com/android/gallery3d/gadget/WidgetTypeChooser.java
deleted file mode 100644
index 1694f1c04..000000000
--- a/src/com/android/gallery3d/gadget/WidgetTypeChooser.java
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.gadget;
-
-import android.app.Activity;
-import android.content.Intent;
-import android.os.Bundle;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.widget.Button;
-import android.widget.RadioGroup;
-import android.widget.RadioGroup.OnCheckedChangeListener;
-
-import com.android.gallery3d.R;
-
-public class WidgetTypeChooser extends Activity {
-
- private OnCheckedChangeListener mListener = new OnCheckedChangeListener() {
- @Override
- public void onCheckedChanged(RadioGroup group, int checkedId) {
- Intent data = new Intent()
- .putExtra(WidgetConfigure.KEY_WIDGET_TYPE, checkedId);
- setResult(RESULT_OK, data);
- finish();
- }
- };
-
- @Override
- public void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- setTitle(R.string.widget_type);
- setContentView(R.layout.choose_widget_type);
- RadioGroup rg = (RadioGroup) findViewById(R.id.widget_type);
- rg.setOnCheckedChangeListener(mListener);
-
- Button cancel = (Button) findViewById(R.id.cancel);
- cancel.setOnClickListener(new OnClickListener() {
- @Override
- public void onClick(View v) {
- setResult(RESULT_CANCELED);
- finish();
- }
- });
- }
-}
diff --git a/src/com/android/gallery3d/gadget/WidgetUtils.java b/src/com/android/gallery3d/gadget/WidgetUtils.java
deleted file mode 100644
index c20c186df..000000000
--- a/src/com/android/gallery3d/gadget/WidgetUtils.java
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.gadget;
-
-import android.content.Context;
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.Bitmap.Config;
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.util.Log;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.util.ThreadPool;
-
-public class WidgetUtils {
-
- private static final String TAG = "WidgetUtils";
-
- private static int sStackPhotoWidth = 220;
- private static int sStackPhotoHeight = 170;
-
- private WidgetUtils() {
- }
-
- public static void initialize(Context context) {
- Resources r = context.getResources();
- sStackPhotoWidth = r.getDimensionPixelSize(R.dimen.stack_photo_width);
- sStackPhotoHeight = r.getDimensionPixelSize(R.dimen.stack_photo_height);
- }
-
- public static Bitmap createWidgetBitmap(MediaItem image) {
- Bitmap bitmap = image.requestImage(MediaItem.TYPE_THUMBNAIL)
- .run(ThreadPool.JOB_CONTEXT_STUB);
- if (bitmap == null) {
- Log.w(TAG, "fail to get image of " + image.toString());
- return null;
- }
- return createWidgetBitmap(bitmap, image.getRotation());
- }
-
- public static Bitmap createWidgetBitmap(Bitmap bitmap, int rotation) {
- int w = bitmap.getWidth();
- int h = bitmap.getHeight();
-
- float scale;
- if (((rotation / 90) & 1) == 0) {
- scale = Math.max((float) sStackPhotoWidth / w,
- (float) sStackPhotoHeight / h);
- } else {
- scale = Math.max((float) sStackPhotoWidth / h,
- (float) sStackPhotoHeight / w);
- }
-
- Bitmap target = Bitmap.createBitmap(
- sStackPhotoWidth, sStackPhotoHeight, Config.ARGB_8888);
- Canvas canvas = new Canvas(target);
- canvas.translate(sStackPhotoWidth / 2, sStackPhotoHeight / 2);
- canvas.rotate(rotation);
- canvas.scale(scale, scale);
- Paint paint = new Paint(Paint.FILTER_BITMAP_FLAG | Paint.DITHER_FLAG);
- canvas.drawBitmap(bitmap, -w / 2, -h / 2, paint);
- return target;
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/BasicTexture.java b/src/com/android/gallery3d/glrenderer/BasicTexture.java
deleted file mode 100644
index 2e77b903f..000000000
--- a/src/com/android/gallery3d/glrenderer/BasicTexture.java
+++ /dev/null
@@ -1,212 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import android.util.Log;
-
-import com.android.gallery3d.common.Utils;
-
-import java.util.WeakHashMap;
-
-// BasicTexture is a Texture corresponds to a real GL texture.
-// The state of a BasicTexture indicates whether its data is loaded to GL memory.
-// If a BasicTexture is loaded into GL memory, it has a GL texture id.
-public abstract class BasicTexture implements Texture {
-
- @SuppressWarnings("unused")
- private static final String TAG = "BasicTexture";
- protected static final int UNSPECIFIED = -1;
-
- protected static final int STATE_UNLOADED = 0;
- protected static final int STATE_LOADED = 1;
- protected static final int STATE_ERROR = -1;
-
- // Log a warning if a texture is larger along a dimension
- private static final int MAX_TEXTURE_SIZE = 4096;
-
- protected int mId = -1;
- protected int mState;
-
- protected int mWidth = UNSPECIFIED;
- protected int mHeight = UNSPECIFIED;
-
- protected int mTextureWidth;
- protected int mTextureHeight;
-
- private boolean mHasBorder;
-
- protected GLCanvas mCanvasRef = null;
- private static WeakHashMap<BasicTexture, Object> sAllTextures
- = new WeakHashMap<BasicTexture, Object>();
- private static ThreadLocal sInFinalizer = new ThreadLocal();
-
- protected BasicTexture(GLCanvas canvas, int id, int state) {
- setAssociatedCanvas(canvas);
- mId = id;
- mState = state;
- synchronized (sAllTextures) {
- sAllTextures.put(this, null);
- }
- }
-
- protected BasicTexture() {
- this(null, 0, STATE_UNLOADED);
- }
-
- protected void setAssociatedCanvas(GLCanvas canvas) {
- mCanvasRef = canvas;
- }
-
- /**
- * Sets the content size of this texture. In OpenGL, the actual texture
- * size must be of power of 2, the size of the content may be smaller.
- */
- public void setSize(int width, int height) {
- mWidth = width;
- mHeight = height;
- mTextureWidth = width > 0 ? Utils.nextPowerOf2(width) : 0;
- mTextureHeight = height > 0 ? Utils.nextPowerOf2(height) : 0;
- if (mTextureWidth > MAX_TEXTURE_SIZE || mTextureHeight > MAX_TEXTURE_SIZE) {
- Log.w(TAG, String.format("texture is too large: %d x %d",
- mTextureWidth, mTextureHeight), new Exception());
- }
- }
-
- public boolean isFlippedVertically() {
- return false;
- }
-
- public int getId() {
- return mId;
- }
-
- @Override
- public int getWidth() {
- return mWidth;
- }
-
- @Override
- public int getHeight() {
- return mHeight;
- }
-
- // Returns the width rounded to the next power of 2.
- public int getTextureWidth() {
- return mTextureWidth;
- }
-
- // Returns the height rounded to the next power of 2.
- public int getTextureHeight() {
- return mTextureHeight;
- }
-
- // Returns true if the texture has one pixel transparent border around the
- // actual content. This is used to avoid jigged edges.
- //
- // The jigged edges appear because we use GL_CLAMP_TO_EDGE for texture wrap
- // mode (GL_CLAMP is not available in OpenGL ES), so a pixel partially
- // covered by the texture will use the color of the edge texel. If we add
- // the transparent border, the color of the edge texel will be mixed with
- // appropriate amount of transparent.
- //
- // Currently our background is black, so we can draw the thumbnails without
- // enabling blending.
- public boolean hasBorder() {
- return mHasBorder;
- }
-
- protected void setBorder(boolean hasBorder) {
- mHasBorder = hasBorder;
- }
-
- @Override
- public void draw(GLCanvas canvas, int x, int y) {
- canvas.drawTexture(this, x, y, getWidth(), getHeight());
- }
-
- @Override
- public void draw(GLCanvas canvas, int x, int y, int w, int h) {
- canvas.drawTexture(this, x, y, w, h);
- }
-
- // onBind is called before GLCanvas binds this texture.
- // It should make sure the data is uploaded to GL memory.
- abstract protected boolean onBind(GLCanvas canvas);
-
- // Returns the GL texture target for this texture (e.g. GL_TEXTURE_2D).
- abstract protected int getTarget();
-
- public boolean isLoaded() {
- return mState == STATE_LOADED;
- }
-
- // recycle() is called when the texture will never be used again,
- // so it can free all resources.
- public void recycle() {
- freeResource();
- }
-
- // yield() is called when the texture will not be used temporarily,
- // so it can free some resources.
- // The default implementation unloads the texture from GL memory, so
- // the subclass should make sure it can reload the texture to GL memory
- // later, or it will have to override this method.
- public void yield() {
- freeResource();
- }
-
- private void freeResource() {
- GLCanvas canvas = mCanvasRef;
- if (canvas != null && mId != -1) {
- canvas.unloadTexture(this);
- mId = -1; // Don't free it again.
- }
- mState = STATE_UNLOADED;
- setAssociatedCanvas(null);
- }
-
- @Override
- protected void finalize() {
- sInFinalizer.set(BasicTexture.class);
- recycle();
- sInFinalizer.set(null);
- }
-
- // This is for deciding if we can call Bitmap's recycle().
- // We cannot call Bitmap's recycle() in finalizer because at that point
- // the finalizer of Bitmap may already be called so recycle() will crash.
- public static boolean inFinalizer() {
- return sInFinalizer.get() != null;
- }
-
- public static void yieldAllTextures() {
- synchronized (sAllTextures) {
- for (BasicTexture t : sAllTextures.keySet()) {
- t.yield();
- }
- }
- }
-
- public static void invalidateAllTextures() {
- synchronized (sAllTextures) {
- for (BasicTexture t : sAllTextures.keySet()) {
- t.mState = STATE_UNLOADED;
- t.setAssociatedCanvas(null);
- }
- }
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/BitmapTexture.java b/src/com/android/gallery3d/glrenderer/BitmapTexture.java
deleted file mode 100644
index 100b0b3b9..000000000
--- a/src/com/android/gallery3d/glrenderer/BitmapTexture.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import android.graphics.Bitmap;
-
-import junit.framework.Assert;
-
-// BitmapTexture is a texture whose content is specified by a fixed Bitmap.
-//
-// The texture does not own the Bitmap. The user should make sure the Bitmap
-// is valid during the texture's lifetime. When the texture is recycled, it
-// does not free the Bitmap.
-public class BitmapTexture extends UploadedTexture {
- protected Bitmap mContentBitmap;
-
- public BitmapTexture(Bitmap bitmap) {
- this(bitmap, false);
- }
-
- public BitmapTexture(Bitmap bitmap, boolean hasBorder) {
- super(hasBorder);
- Assert.assertTrue(bitmap != null && !bitmap.isRecycled());
- mContentBitmap = bitmap;
- }
-
- @Override
- protected void onFreeBitmap(Bitmap bitmap) {
- // Do nothing.
- }
-
- @Override
- protected Bitmap onGetBitmap() {
- return mContentBitmap;
- }
-
- public Bitmap getBitmap() {
- return mContentBitmap;
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/CanvasTexture.java b/src/com/android/gallery3d/glrenderer/CanvasTexture.java
deleted file mode 100644
index bff9d4baa..000000000
--- a/src/com/android/gallery3d/glrenderer/CanvasTexture.java
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import android.graphics.Bitmap;
-import android.graphics.Bitmap.Config;
-import android.graphics.Canvas;
-
-// CanvasTexture is a texture whose content is the drawing on a Canvas.
-// The subclasses should override onDraw() to draw on the bitmap.
-// By default CanvasTexture is not opaque.
-abstract class CanvasTexture extends UploadedTexture {
- protected Canvas mCanvas;
- private final Config mConfig;
-
- public CanvasTexture(int width, int height) {
- mConfig = Config.ARGB_8888;
- setSize(width, height);
- setOpaque(false);
- }
-
- @Override
- protected Bitmap onGetBitmap() {
- Bitmap bitmap = Bitmap.createBitmap(mWidth, mHeight, mConfig);
- mCanvas = new Canvas(bitmap);
- onDraw(mCanvas, bitmap);
- return bitmap;
- }
-
- @Override
- protected void onFreeBitmap(Bitmap bitmap) {
- if (!inFinalizer()) {
- bitmap.recycle();
- }
- }
-
- abstract protected void onDraw(Canvas canvas, Bitmap backing);
-}
diff --git a/src/com/android/gallery3d/glrenderer/ColorTexture.java b/src/com/android/gallery3d/glrenderer/ColorTexture.java
deleted file mode 100644
index 904c78e1b..000000000
--- a/src/com/android/gallery3d/glrenderer/ColorTexture.java
+++ /dev/null
@@ -1,63 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import com.android.gallery3d.common.Utils;
-
-// ColorTexture is a texture which fills the rectangle with the specified color.
-public class ColorTexture implements Texture {
-
- private final int mColor;
- private int mWidth;
- private int mHeight;
-
- public ColorTexture(int color) {
- mColor = color;
- mWidth = 1;
- mHeight = 1;
- }
-
- @Override
- public void draw(GLCanvas canvas, int x, int y) {
- draw(canvas, x, y, mWidth, mHeight);
- }
-
- @Override
- public void draw(GLCanvas canvas, int x, int y, int w, int h) {
- canvas.fillRect(x, y, w, h, mColor);
- }
-
- @Override
- public boolean isOpaque() {
- return Utils.isOpaque(mColor);
- }
-
- public void setSize(int width, int height) {
- mWidth = width;
- mHeight = height;
- }
-
- @Override
- public int getWidth() {
- return mWidth;
- }
-
- @Override
- public int getHeight() {
- return mHeight;
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/ExtTexture.java b/src/com/android/gallery3d/glrenderer/ExtTexture.java
deleted file mode 100644
index af76300b1..000000000
--- a/src/com/android/gallery3d/glrenderer/ExtTexture.java
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-// ExtTexture is a texture whose content comes from a external texture.
-// Before drawing, setSize() should be called.
-public class ExtTexture extends BasicTexture {
-
- private int mTarget;
-
- public ExtTexture(GLCanvas canvas, int target) {
- GLId glId = canvas.getGLId();
- mId = glId.generateTexture();
- mTarget = target;
- }
-
- private void uploadToCanvas(GLCanvas canvas) {
- canvas.setTextureParameters(this);
- setAssociatedCanvas(canvas);
- mState = STATE_LOADED;
- }
-
- @Override
- protected boolean onBind(GLCanvas canvas) {
- if (!isLoaded()) {
- uploadToCanvas(canvas);
- }
-
- return true;
- }
-
- @Override
- public int getTarget() {
- return mTarget;
- }
-
- @Override
- public boolean isOpaque() {
- return true;
- }
-
- @Override
- public void yield() {
- // we cannot free the texture because we have no backup.
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/FadeInTexture.java b/src/com/android/gallery3d/glrenderer/FadeInTexture.java
deleted file mode 100644
index 838d465f5..000000000
--- a/src/com/android/gallery3d/glrenderer/FadeInTexture.java
+++ /dev/null
@@ -1,43 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-
-// FadeInTexture is a texture which begins with a color, then gradually animates
-// into a given texture.
-public class FadeInTexture extends FadeTexture implements Texture {
- @SuppressWarnings("unused")
- private static final String TAG = "FadeInTexture";
-
- private final int mColor;
- private final TiledTexture mTexture;
-
- public FadeInTexture(int color, TiledTexture texture) {
- super(texture.getWidth(), texture.getHeight(), texture.isOpaque());
- mColor = color;
- mTexture = texture;
- }
-
- @Override
- public void draw(GLCanvas canvas, int x, int y, int w, int h) {
- if (isAnimating()) {
- mTexture.drawMixed(canvas, mColor, getRatio(), x, y, w, h);
- } else {
- mTexture.draw(canvas, x, y, w, h);
- }
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/FadeOutTexture.java b/src/com/android/gallery3d/glrenderer/FadeOutTexture.java
deleted file mode 100644
index b05f3b631..000000000
--- a/src/com/android/gallery3d/glrenderer/FadeOutTexture.java
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-
-// FadeOutTexture is a texture which begins with a given texture, then gradually animates
-// into fading out totally.
-public class FadeOutTexture extends FadeTexture {
- @SuppressWarnings("unused")
- private static final String TAG = "FadeOutTexture";
-
- private final BasicTexture mTexture;
-
- public FadeOutTexture(BasicTexture texture) {
- super(texture.getWidth(), texture.getHeight(), texture.isOpaque());
- mTexture = texture;
- }
-
- @Override
- public void draw(GLCanvas canvas, int x, int y, int w, int h) {
- if (isAnimating()) {
- canvas.save(GLCanvas.SAVE_FLAG_ALPHA);
- canvas.setAlpha(getRatio());
- mTexture.draw(canvas, x, y, w, h);
- canvas.restore();
- }
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/FadeTexture.java b/src/com/android/gallery3d/glrenderer/FadeTexture.java
deleted file mode 100644
index 002c90f5c..000000000
--- a/src/com/android/gallery3d/glrenderer/FadeTexture.java
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.ui.AnimationTime;
-
-// FadeTexture is a texture which fades the given texture along the time.
-public abstract class FadeTexture implements Texture {
- @SuppressWarnings("unused")
- private static final String TAG = "FadeTexture";
-
- // The duration of the fading animation in milliseconds
- public static final int DURATION = 180;
-
- private final long mStartTime;
- private final int mWidth;
- private final int mHeight;
- private final boolean mIsOpaque;
- private boolean mIsAnimating;
-
- public FadeTexture(int width, int height, boolean opaque) {
- mWidth = width;
- mHeight = height;
- mIsOpaque = opaque;
- mStartTime = now();
- mIsAnimating = true;
- }
-
- @Override
- public void draw(GLCanvas canvas, int x, int y) {
- draw(canvas, x, y, mWidth, mHeight);
- }
-
- @Override
- public boolean isOpaque() {
- return mIsOpaque;
- }
-
- @Override
- public int getWidth() {
- return mWidth;
- }
-
- @Override
- public int getHeight() {
- return mHeight;
- }
-
- public boolean isAnimating() {
- if (mIsAnimating) {
- if (now() - mStartTime >= DURATION) {
- mIsAnimating = false;
- }
- }
- return mIsAnimating;
- }
-
- protected float getRatio() {
- float r = (float)(now() - mStartTime) / DURATION;
- return Utils.clamp(1.0f - r, 0.0f, 1.0f);
- }
-
- private long now() {
- return AnimationTime.get();
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/GLCanvas.java b/src/com/android/gallery3d/glrenderer/GLCanvas.java
deleted file mode 100644
index 305e90521..000000000
--- a/src/com/android/gallery3d/glrenderer/GLCanvas.java
+++ /dev/null
@@ -1,217 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import android.graphics.Bitmap;
-import android.graphics.Rect;
-import android.graphics.RectF;
-
-import javax.microedition.khronos.opengles.GL11;
-
-//
-// GLCanvas gives a convenient interface to draw using OpenGL.
-//
-// When a rectangle is specified in this interface, it means the region
-// [x, x+width) * [y, y+height)
-//
-public interface GLCanvas {
-
- public GLId getGLId();
-
- // Tells GLCanvas the size of the underlying GL surface. This should be
- // called before first drawing and when the size of GL surface is changed.
- // This is called by GLRoot and should not be called by the clients
- // who only want to draw on the GLCanvas. Both width and height must be
- // nonnegative.
- public abstract void setSize(int width, int height);
-
- // Clear the drawing buffers. This should only be used by GLRoot.
- public abstract void clearBuffer();
-
- public abstract void clearBuffer(float[] argb);
-
- // Sets and gets the current alpha, alpha must be in [0, 1].
- public abstract void setAlpha(float alpha);
-
- public abstract float getAlpha();
-
- // (current alpha) = (current alpha) * alpha
- public abstract void multiplyAlpha(float alpha);
-
- // Change the current transform matrix.
- public abstract void translate(float x, float y, float z);
-
- public abstract void translate(float x, float y);
-
- public abstract void scale(float sx, float sy, float sz);
-
- public abstract void rotate(float angle, float x, float y, float z);
-
- public abstract void multiplyMatrix(float[] mMatrix, int offset);
-
- // Pushes the configuration state (matrix, and alpha) onto
- // a private stack.
- public abstract void save();
-
- // Same as save(), but only save those specified in saveFlags.
- public abstract void save(int saveFlags);
-
- public static final int SAVE_FLAG_ALL = 0xFFFFFFFF;
- public static final int SAVE_FLAG_ALPHA = 0x01;
- public static final int SAVE_FLAG_MATRIX = 0x02;
-
- // Pops from the top of the stack as current configuration state (matrix,
- // alpha, and clip). This call balances a previous call to save(), and is
- // used to remove all modifications to the configuration state since the
- // last save call.
- public abstract void restore();
-
- // Draws a line using the specified paint from (x1, y1) to (x2, y2).
- // (Both end points are included).
- public abstract void drawLine(float x1, float y1, float x2, float y2, GLPaint paint);
-
- // Draws a rectangle using the specified paint from (x1, y1) to (x2, y2).
- // (Both end points are included).
- public abstract void drawRect(float x1, float y1, float x2, float y2, GLPaint paint);
-
- // Fills the specified rectangle with the specified color.
- public abstract void fillRect(float x, float y, float width, float height, int color);
-
- // Draws a texture to the specified rectangle.
- public abstract void drawTexture(
- BasicTexture texture, int x, int y, int width, int height);
-
- public abstract void drawMesh(BasicTexture tex, int x, int y, int xyBuffer,
- int uvBuffer, int indexBuffer, int indexCount);
-
- // Draws the source rectangle part of the texture to the target rectangle.
- public abstract void drawTexture(BasicTexture texture, RectF source, RectF target);
-
- // Draw a texture with a specified texture transform.
- public abstract void drawTexture(BasicTexture texture, float[] mTextureTransform,
- int x, int y, int w, int h);
-
- // Draw two textures to the specified rectangle. The actual texture used is
- // from * (1 - ratio) + to * ratio
- // The two textures must have the same size.
- public abstract void drawMixed(BasicTexture from, int toColor,
- float ratio, int x, int y, int w, int h);
-
- // Draw a region of a texture and a specified color to the specified
- // rectangle. The actual color used is from * (1 - ratio) + to * ratio.
- // The region of the texture is defined by parameter "src". The target
- // rectangle is specified by parameter "target".
- public abstract void drawMixed(BasicTexture from, int toColor,
- float ratio, RectF src, RectF target);
-
- // Unloads the specified texture from the canvas. The resource allocated
- // to draw the texture will be released. The specified texture will return
- // to the unloaded state. This function should be called only from
- // BasicTexture or its descendant
- public abstract boolean unloadTexture(BasicTexture texture);
-
- // Delete the specified buffer object, similar to unloadTexture.
- public abstract void deleteBuffer(int bufferId);
-
- // Delete the textures and buffers in GL side. This function should only be
- // called in the GL thread.
- public abstract void deleteRecycledResources();
-
- // Dump statistics information and clear the counters. For debug only.
- public abstract void dumpStatisticsAndClear();
-
- public abstract void beginRenderTarget(RawTexture texture);
-
- public abstract void endRenderTarget();
-
- /**
- * Sets texture parameters to use GL_CLAMP_TO_EDGE for both
- * GL_TEXTURE_WRAP_S and GL_TEXTURE_WRAP_T. Sets texture parameters to be
- * GL_LINEAR for GL_TEXTURE_MIN_FILTER and GL_TEXTURE_MAG_FILTER.
- * bindTexture() must be called prior to this.
- *
- * @param texture The texture to set parameters on.
- */
- public abstract void setTextureParameters(BasicTexture texture);
-
- /**
- * Initializes the texture to a size by calling texImage2D on it.
- *
- * @param texture The texture to initialize the size.
- * @param format The texture format (e.g. GL_RGBA)
- * @param type The texture type (e.g. GL_UNSIGNED_BYTE)
- */
- public abstract void initializeTextureSize(BasicTexture texture, int format, int type);
-
- /**
- * Initializes the texture to a size by calling texImage2D on it.
- *
- * @param texture The texture to initialize the size.
- * @param bitmap The bitmap to initialize the bitmap with.
- */
- public abstract void initializeTexture(BasicTexture texture, Bitmap bitmap);
-
- /**
- * Calls glTexSubImage2D to upload a bitmap to the texture.
- *
- * @param texture The target texture to write to.
- * @param xOffset Specifies a texel offset in the x direction within the
- * texture array.
- * @param yOffset Specifies a texel offset in the y direction within the
- * texture array.
- * @param format The texture format (e.g. GL_RGBA)
- * @param type The texture type (e.g. GL_UNSIGNED_BYTE)
- */
- public abstract void texSubImage2D(BasicTexture texture, int xOffset, int yOffset,
- Bitmap bitmap,
- int format, int type);
-
- /**
- * Generates buffers and uploads the buffer data.
- *
- * @param buffer The buffer to upload
- * @return The buffer ID that was generated.
- */
- public abstract int uploadBuffer(java.nio.FloatBuffer buffer);
-
- /**
- * Generates buffers and uploads the element array buffer data.
- *
- * @param buffer The buffer to upload
- * @return The buffer ID that was generated.
- */
- public abstract int uploadBuffer(java.nio.ByteBuffer buffer);
-
- /**
- * After LightCycle makes GL calls, this method is called to restore the GL
- * configuration to the one expected by GLCanvas.
- */
- public abstract void recoverFromLightCycle();
-
- /**
- * Gets the bounds given by x, y, width, and height as well as the internal
- * matrix state. There is no special handling for non-90-degree rotations.
- * It only considers the lower-left and upper-right corners as the bounds.
- *
- * @param bounds The output bounds to write to.
- * @param x The left side of the input rectangle.
- * @param y The bottom of the input rectangle.
- * @param width The width of the input rectangle.
- * @param height The height of the input rectangle.
- */
- public abstract void getBounds(Rect bounds, int x, int y, int width, int height);
-}
diff --git a/src/com/android/gallery3d/glrenderer/GLES11Canvas.java b/src/com/android/gallery3d/glrenderer/GLES11Canvas.java
deleted file mode 100644
index 7013c3d1f..000000000
--- a/src/com/android/gallery3d/glrenderer/GLES11Canvas.java
+++ /dev/null
@@ -1,997 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import android.graphics.Bitmap;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.opengl.GLU;
-import android.opengl.GLUtils;
-import android.opengl.Matrix;
-import android.util.Log;
-
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.util.IntArray;
-
-import junit.framework.Assert;
-
-import java.nio.Buffer;
-import java.nio.ByteBuffer;
-import java.nio.ByteOrder;
-import java.nio.FloatBuffer;
-import java.util.ArrayList;
-
-import javax.microedition.khronos.opengles.GL10;
-import javax.microedition.khronos.opengles.GL11;
-import javax.microedition.khronos.opengles.GL11Ext;
-import javax.microedition.khronos.opengles.GL11ExtensionPack;
-
-public class GLES11Canvas implements GLCanvas {
- @SuppressWarnings("unused")
- private static final String TAG = "GLCanvasImp";
-
- private static final float OPAQUE_ALPHA = 0.95f;
-
- private static final int OFFSET_FILL_RECT = 0;
- private static final int OFFSET_DRAW_LINE = 4;
- private static final int OFFSET_DRAW_RECT = 6;
- private static final float[] BOX_COORDINATES = {
- 0, 0, 1, 0, 0, 1, 1, 1, // used for filling a rectangle
- 0, 0, 1, 1, // used for drawing a line
- 0, 0, 0, 1, 1, 1, 1, 0}; // used for drawing the outline of a rectangle
-
- private GL11 mGL;
-
- private final float mMatrixValues[] = new float[16];
- private final float mTextureMatrixValues[] = new float[16];
-
- // The results of mapPoints are stored in this buffer, and the order is
- // x1, y1, x2, y2.
- private final float mMapPointsBuffer[] = new float[4];
-
- private final float mTextureColor[] = new float[4];
-
- private int mBoxCoords;
-
- private GLState mGLState;
- private final ArrayList<RawTexture> mTargetStack = new ArrayList<RawTexture>();
-
- private float mAlpha;
- private final ArrayList<ConfigState> mRestoreStack = new ArrayList<ConfigState>();
- private ConfigState mRecycledRestoreAction;
-
- private final RectF mDrawTextureSourceRect = new RectF();
- private final RectF mDrawTextureTargetRect = new RectF();
- private final float[] mTempMatrix = new float[32];
- private final IntArray mUnboundTextures = new IntArray();
- private final IntArray mDeleteBuffers = new IntArray();
- private int mScreenWidth;
- private int mScreenHeight;
- private boolean mBlendEnabled = true;
- private int mFrameBuffer[] = new int[1];
- private static float[] sCropRect = new float[4];
-
- private RawTexture mTargetTexture;
-
- // Drawing statistics
- int mCountDrawLine;
- int mCountFillRect;
- int mCountDrawMesh;
- int mCountTextureRect;
- int mCountTextureOES;
-
- private static GLId mGLId = new GLES11IdImpl();
-
- public GLES11Canvas(GL11 gl) {
- mGL = gl;
- mGLState = new GLState(gl);
- // First create an nio buffer, then create a VBO from it.
- int size = BOX_COORDINATES.length * Float.SIZE / Byte.SIZE;
- FloatBuffer xyBuffer = allocateDirectNativeOrderBuffer(size).asFloatBuffer();
- xyBuffer.put(BOX_COORDINATES, 0, BOX_COORDINATES.length).position(0);
-
- int[] name = new int[1];
- mGLId.glGenBuffers(1, name, 0);
- mBoxCoords = name[0];
-
- gl.glBindBuffer(GL11.GL_ARRAY_BUFFER, mBoxCoords);
- gl.glBufferData(GL11.GL_ARRAY_BUFFER, xyBuffer.capacity() * (Float.SIZE / Byte.SIZE),
- xyBuffer, GL11.GL_STATIC_DRAW);
-
- gl.glVertexPointer(2, GL11.GL_FLOAT, 0, 0);
- gl.glTexCoordPointer(2, GL11.GL_FLOAT, 0, 0);
-
- // Enable the texture coordinate array for Texture 1
- gl.glClientActiveTexture(GL11.GL_TEXTURE1);
- gl.glTexCoordPointer(2, GL11.GL_FLOAT, 0, 0);
- gl.glClientActiveTexture(GL11.GL_TEXTURE0);
- gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
-
- // mMatrixValues and mAlpha will be initialized in setSize()
- }
-
- @Override
- public void setSize(int width, int height) {
- Assert.assertTrue(width >= 0 && height >= 0);
-
- if (mTargetTexture == null) {
- mScreenWidth = width;
- mScreenHeight = height;
- }
- mAlpha = 1.0f;
-
- GL11 gl = mGL;
- gl.glViewport(0, 0, width, height);
- gl.glMatrixMode(GL11.GL_PROJECTION);
- gl.glLoadIdentity();
- GLU.gluOrtho2D(gl, 0, width, 0, height);
-
- gl.glMatrixMode(GL11.GL_MODELVIEW);
- gl.glLoadIdentity();
-
- float matrix[] = mMatrixValues;
- Matrix.setIdentityM(matrix, 0);
- // to match the graphic coordinate system in android, we flip it vertically.
- if (mTargetTexture == null) {
- Matrix.translateM(matrix, 0, 0, height, 0);
- Matrix.scaleM(matrix, 0, 1, -1, 1);
- }
- }
-
- @Override
- public void setAlpha(float alpha) {
- Assert.assertTrue(alpha >= 0 && alpha <= 1);
- mAlpha = alpha;
- }
-
- @Override
- public float getAlpha() {
- return mAlpha;
- }
-
- @Override
- public void multiplyAlpha(float alpha) {
- Assert.assertTrue(alpha >= 0 && alpha <= 1);
- mAlpha *= alpha;
- }
-
- private static ByteBuffer allocateDirectNativeOrderBuffer(int size) {
- return ByteBuffer.allocateDirect(size).order(ByteOrder.nativeOrder());
- }
-
- @Override
- public void drawRect(float x, float y, float width, float height, GLPaint paint) {
- GL11 gl = mGL;
-
- mGLState.setColorMode(paint.getColor(), mAlpha);
- mGLState.setLineWidth(paint.getLineWidth());
-
- saveTransform();
- translate(x, y);
- scale(width, height, 1);
-
- gl.glLoadMatrixf(mMatrixValues, 0);
- gl.glDrawArrays(GL11.GL_LINE_LOOP, OFFSET_DRAW_RECT, 4);
-
- restoreTransform();
- mCountDrawLine++;
- }
-
- @Override
- public void drawLine(float x1, float y1, float x2, float y2, GLPaint paint) {
- GL11 gl = mGL;
-
- mGLState.setColorMode(paint.getColor(), mAlpha);
- mGLState.setLineWidth(paint.getLineWidth());
-
- saveTransform();
- translate(x1, y1);
- scale(x2 - x1, y2 - y1, 1);
-
- gl.glLoadMatrixf(mMatrixValues, 0);
- gl.glDrawArrays(GL11.GL_LINE_STRIP, OFFSET_DRAW_LINE, 2);
-
- restoreTransform();
- mCountDrawLine++;
- }
-
- @Override
- public void fillRect(float x, float y, float width, float height, int color) {
- mGLState.setColorMode(color, mAlpha);
- GL11 gl = mGL;
-
- saveTransform();
- translate(x, y);
- scale(width, height, 1);
-
- gl.glLoadMatrixf(mMatrixValues, 0);
- gl.glDrawArrays(GL11.GL_TRIANGLE_STRIP, OFFSET_FILL_RECT, 4);
-
- restoreTransform();
- mCountFillRect++;
- }
-
- @Override
- public void translate(float x, float y, float z) {
- Matrix.translateM(mMatrixValues, 0, x, y, z);
- }
-
- // This is a faster version of translate(x, y, z) because
- // (1) we knows z = 0, (2) we inline the Matrix.translateM call,
- // (3) we unroll the loop
- @Override
- public void translate(float x, float y) {
- float[] m = mMatrixValues;
- m[12] += m[0] * x + m[4] * y;
- m[13] += m[1] * x + m[5] * y;
- m[14] += m[2] * x + m[6] * y;
- m[15] += m[3] * x + m[7] * y;
- }
-
- @Override
- public void scale(float sx, float sy, float sz) {
- Matrix.scaleM(mMatrixValues, 0, sx, sy, sz);
- }
-
- @Override
- public void rotate(float angle, float x, float y, float z) {
- if (angle == 0) return;
- float[] temp = mTempMatrix;
- Matrix.setRotateM(temp, 0, angle, x, y, z);
- Matrix.multiplyMM(temp, 16, mMatrixValues, 0, temp, 0);
- System.arraycopy(temp, 16, mMatrixValues, 0, 16);
- }
-
- @Override
- public void multiplyMatrix(float matrix[], int offset) {
- float[] temp = mTempMatrix;
- Matrix.multiplyMM(temp, 0, mMatrixValues, 0, matrix, offset);
- System.arraycopy(temp, 0, mMatrixValues, 0, 16);
- }
-
- private void textureRect(float x, float y, float width, float height) {
- GL11 gl = mGL;
-
- saveTransform();
- translate(x, y);
- scale(width, height, 1);
-
- gl.glLoadMatrixf(mMatrixValues, 0);
- gl.glDrawArrays(GL11.GL_TRIANGLE_STRIP, OFFSET_FILL_RECT, 4);
-
- restoreTransform();
- mCountTextureRect++;
- }
-
- @Override
- public void drawMesh(BasicTexture tex, int x, int y, int xyBuffer,
- int uvBuffer, int indexBuffer, int indexCount) {
- float alpha = mAlpha;
- if (!bindTexture(tex)) return;
-
- mGLState.setBlendEnabled(mBlendEnabled
- && (!tex.isOpaque() || alpha < OPAQUE_ALPHA));
- mGLState.setTextureAlpha(alpha);
-
- // Reset the texture matrix. We will set our own texture coordinates
- // below.
- setTextureCoords(0, 0, 1, 1);
-
- saveTransform();
- translate(x, y);
-
- mGL.glLoadMatrixf(mMatrixValues, 0);
-
- mGL.glBindBuffer(GL11.GL_ARRAY_BUFFER, xyBuffer);
- mGL.glVertexPointer(2, GL11.GL_FLOAT, 0, 0);
-
- mGL.glBindBuffer(GL11.GL_ARRAY_BUFFER, uvBuffer);
- mGL.glTexCoordPointer(2, GL11.GL_FLOAT, 0, 0);
-
- mGL.glBindBuffer(GL11.GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
- mGL.glDrawElements(GL11.GL_TRIANGLE_STRIP,
- indexCount, GL11.GL_UNSIGNED_BYTE, 0);
-
- mGL.glBindBuffer(GL11.GL_ARRAY_BUFFER, mBoxCoords);
- mGL.glVertexPointer(2, GL11.GL_FLOAT, 0, 0);
- mGL.glTexCoordPointer(2, GL11.GL_FLOAT, 0, 0);
-
- restoreTransform();
- mCountDrawMesh++;
- }
-
- // Transforms two points by the given matrix m. The result
- // {x1', y1', x2', y2'} are stored in mMapPointsBuffer and also returned.
- private float[] mapPoints(float m[], int x1, int y1, int x2, int y2) {
- float[] r = mMapPointsBuffer;
-
- // Multiply m and (x1 y1 0 1) to produce (x3 y3 z3 w3). z3 is unused.
- float x3 = m[0] * x1 + m[4] * y1 + m[12];
- float y3 = m[1] * x1 + m[5] * y1 + m[13];
- float w3 = m[3] * x1 + m[7] * y1 + m[15];
- r[0] = x3 / w3;
- r[1] = y3 / w3;
-
- // Same for x2 y2.
- float x4 = m[0] * x2 + m[4] * y2 + m[12];
- float y4 = m[1] * x2 + m[5] * y2 + m[13];
- float w4 = m[3] * x2 + m[7] * y2 + m[15];
- r[2] = x4 / w4;
- r[3] = y4 / w4;
-
- return r;
- }
-
- private void drawBoundTexture(
- BasicTexture texture, int x, int y, int width, int height) {
- // Test whether it has been rotated or flipped, if so, glDrawTexiOES
- // won't work
- if (isMatrixRotatedOrFlipped(mMatrixValues)) {
- if (texture.hasBorder()) {
- setTextureCoords(
- 1.0f / texture.getTextureWidth(),
- 1.0f / texture.getTextureHeight(),
- (texture.getWidth() - 1.0f) / texture.getTextureWidth(),
- (texture.getHeight() - 1.0f) / texture.getTextureHeight());
- } else {
- setTextureCoords(0, 0,
- (float) texture.getWidth() / texture.getTextureWidth(),
- (float) texture.getHeight() / texture.getTextureHeight());
- }
- textureRect(x, y, width, height);
- } else {
- // draw the rect from bottom-left to top-right
- float points[] = mapPoints(
- mMatrixValues, x, y + height, x + width, y);
- x = (int) (points[0] + 0.5f);
- y = (int) (points[1] + 0.5f);
- width = (int) (points[2] + 0.5f) - x;
- height = (int) (points[3] + 0.5f) - y;
- if (width > 0 && height > 0) {
- ((GL11Ext) mGL).glDrawTexiOES(x, y, 0, width, height);
- mCountTextureOES++;
- }
- }
- }
-
- @Override
- public void drawTexture(
- BasicTexture texture, int x, int y, int width, int height) {
- drawTexture(texture, x, y, width, height, mAlpha);
- }
-
- private void drawTexture(BasicTexture texture,
- int x, int y, int width, int height, float alpha) {
- if (width <= 0 || height <= 0) return;
-
- mGLState.setBlendEnabled(mBlendEnabled
- && (!texture.isOpaque() || alpha < OPAQUE_ALPHA));
- if (!bindTexture(texture)) return;
- mGLState.setTextureAlpha(alpha);
- drawBoundTexture(texture, x, y, width, height);
- }
-
- @Override
- public void drawTexture(BasicTexture texture, RectF source, RectF target) {
- if (target.width() <= 0 || target.height() <= 0) return;
-
- // Copy the input to avoid changing it.
- mDrawTextureSourceRect.set(source);
- mDrawTextureTargetRect.set(target);
- source = mDrawTextureSourceRect;
- target = mDrawTextureTargetRect;
-
- mGLState.setBlendEnabled(mBlendEnabled
- && (!texture.isOpaque() || mAlpha < OPAQUE_ALPHA));
- if (!bindTexture(texture)) return;
- convertCoordinate(source, target, texture);
- setTextureCoords(source);
- mGLState.setTextureAlpha(mAlpha);
- textureRect(target.left, target.top, target.width(), target.height());
- }
-
- @Override
- public void drawTexture(BasicTexture texture, float[] mTextureTransform,
- int x, int y, int w, int h) {
- mGLState.setBlendEnabled(mBlendEnabled
- && (!texture.isOpaque() || mAlpha < OPAQUE_ALPHA));
- if (!bindTexture(texture)) return;
- setTextureCoords(mTextureTransform);
- mGLState.setTextureAlpha(mAlpha);
- textureRect(x, y, w, h);
- }
-
- // This function changes the source coordinate to the texture coordinates.
- // It also clips the source and target coordinates if it is beyond the
- // bound of the texture.
- private static void convertCoordinate(RectF source, RectF target,
- BasicTexture texture) {
-
- int width = texture.getWidth();
- int height = texture.getHeight();
- int texWidth = texture.getTextureWidth();
- int texHeight = texture.getTextureHeight();
- // Convert to texture coordinates
- source.left /= texWidth;
- source.right /= texWidth;
- source.top /= texHeight;
- source.bottom /= texHeight;
-
- // Clip if the rendering range is beyond the bound of the texture.
- float xBound = (float) width / texWidth;
- if (source.right > xBound) {
- target.right = target.left + target.width() *
- (xBound - source.left) / source.width();
- source.right = xBound;
- }
- float yBound = (float) height / texHeight;
- if (source.bottom > yBound) {
- target.bottom = target.top + target.height() *
- (yBound - source.top) / source.height();
- source.bottom = yBound;
- }
- }
-
- @Override
- public void drawMixed(BasicTexture from,
- int toColor, float ratio, int x, int y, int w, int h) {
- drawMixed(from, toColor, ratio, x, y, w, h, mAlpha);
- }
-
- private boolean bindTexture(BasicTexture texture) {
- if (!texture.onBind(this)) return false;
- int target = texture.getTarget();
- mGLState.setTextureTarget(target);
- mGL.glBindTexture(target, texture.getId());
- return true;
- }
-
- private void setTextureColor(float r, float g, float b, float alpha) {
- float[] color = mTextureColor;
- color[0] = r;
- color[1] = g;
- color[2] = b;
- color[3] = alpha;
- }
-
- private void setMixedColor(int toColor, float ratio, float alpha) {
- //
- // The formula we want:
- // alpha * ((1 - ratio) * from + ratio * to)
- //
- // The formula that GL supports is in the form of:
- // combo * from + (1 - combo) * to * scale
- //
- // So, we have combo = alpha * (1 - ratio)
- // and scale = alpha * ratio / (1 - combo)
- //
- float combo = alpha * (1 - ratio);
- float scale = alpha * ratio / (1 - combo);
-
- // Specify the interpolation factor via the alpha component of
- // GL_TEXTURE_ENV_COLORs.
- // RGB component are get from toColor and will used as SRC1
- float colorScale = scale * (toColor >>> 24) / (0xff * 0xff);
- setTextureColor(((toColor >>> 16) & 0xff) * colorScale,
- ((toColor >>> 8) & 0xff) * colorScale,
- (toColor & 0xff) * colorScale, combo);
- GL11 gl = mGL;
- gl.glTexEnvfv(GL11.GL_TEXTURE_ENV, GL11.GL_TEXTURE_ENV_COLOR, mTextureColor, 0);
-
- gl.glTexEnvf(GL11.GL_TEXTURE_ENV, GL11.GL_COMBINE_RGB, GL11.GL_INTERPOLATE);
- gl.glTexEnvf(GL11.GL_TEXTURE_ENV, GL11.GL_COMBINE_ALPHA, GL11.GL_INTERPOLATE);
- gl.glTexEnvf(GL11.GL_TEXTURE_ENV, GL11.GL_SRC1_RGB, GL11.GL_CONSTANT);
- gl.glTexEnvf(GL11.GL_TEXTURE_ENV, GL11.GL_OPERAND1_RGB, GL11.GL_SRC_COLOR);
- gl.glTexEnvf(GL11.GL_TEXTURE_ENV, GL11.GL_SRC1_ALPHA, GL11.GL_CONSTANT);
- gl.glTexEnvf(GL11.GL_TEXTURE_ENV, GL11.GL_OPERAND1_ALPHA, GL11.GL_SRC_ALPHA);
-
- // Wire up the interpolation factor for RGB.
- gl.glTexEnvf(GL11.GL_TEXTURE_ENV, GL11.GL_SRC2_RGB, GL11.GL_CONSTANT);
- gl.glTexEnvf(GL11.GL_TEXTURE_ENV, GL11.GL_OPERAND2_RGB, GL11.GL_SRC_ALPHA);
-
- // Wire up the interpolation factor for alpha.
- gl.glTexEnvf(GL11.GL_TEXTURE_ENV, GL11.GL_SRC2_ALPHA, GL11.GL_CONSTANT);
- gl.glTexEnvf(GL11.GL_TEXTURE_ENV, GL11.GL_OPERAND2_ALPHA, GL11.GL_SRC_ALPHA);
-
- }
-
- @Override
- public void drawMixed(BasicTexture from, int toColor, float ratio,
- RectF source, RectF target) {
- if (target.width() <= 0 || target.height() <= 0) return;
-
- if (ratio <= 0.01f) {
- drawTexture(from, source, target);
- return;
- } else if (ratio >= 1) {
- fillRect(target.left, target.top, target.width(), target.height(), toColor);
- return;
- }
-
- float alpha = mAlpha;
-
- // Copy the input to avoid changing it.
- mDrawTextureSourceRect.set(source);
- mDrawTextureTargetRect.set(target);
- source = mDrawTextureSourceRect;
- target = mDrawTextureTargetRect;
-
- mGLState.setBlendEnabled(mBlendEnabled && (!from.isOpaque()
- || !Utils.isOpaque(toColor) || alpha < OPAQUE_ALPHA));
-
- if (!bindTexture(from)) return;
-
- // Interpolate the RGB and alpha values between both textures.
- mGLState.setTexEnvMode(GL11.GL_COMBINE);
- setMixedColor(toColor, ratio, alpha);
- convertCoordinate(source, target, from);
- setTextureCoords(source);
- textureRect(target.left, target.top, target.width(), target.height());
- mGLState.setTexEnvMode(GL11.GL_REPLACE);
- }
-
- private void drawMixed(BasicTexture from, int toColor,
- float ratio, int x, int y, int width, int height, float alpha) {
- // change from 0 to 0.01f to prevent getting divided by zero below
- if (ratio <= 0.01f) {
- drawTexture(from, x, y, width, height, alpha);
- return;
- } else if (ratio >= 1) {
- fillRect(x, y, width, height, toColor);
- return;
- }
-
- mGLState.setBlendEnabled(mBlendEnabled && (!from.isOpaque()
- || !Utils.isOpaque(toColor) || alpha < OPAQUE_ALPHA));
-
- final GL11 gl = mGL;
- if (!bindTexture(from)) return;
-
- // Interpolate the RGB and alpha values between both textures.
- mGLState.setTexEnvMode(GL11.GL_COMBINE);
- setMixedColor(toColor, ratio, alpha);
-
- drawBoundTexture(from, x, y, width, height);
- mGLState.setTexEnvMode(GL11.GL_REPLACE);
- }
-
- // TODO: the code only work for 2D should get fixed for 3D or removed
- private static final int MSKEW_X = 4;
- private static final int MSKEW_Y = 1;
- private static final int MSCALE_X = 0;
- private static final int MSCALE_Y = 5;
-
- private static boolean isMatrixRotatedOrFlipped(float matrix[]) {
- final float eps = 1e-5f;
- return Math.abs(matrix[MSKEW_X]) > eps
- || Math.abs(matrix[MSKEW_Y]) > eps
- || matrix[MSCALE_X] < -eps
- || matrix[MSCALE_Y] > eps;
- }
-
- private static class GLState {
-
- private final GL11 mGL;
-
- private int mTexEnvMode = GL11.GL_REPLACE;
- private float mTextureAlpha = 1.0f;
- private int mTextureTarget = GL11.GL_TEXTURE_2D;
- private boolean mBlendEnabled = true;
- private float mLineWidth = 1.0f;
- private boolean mLineSmooth = false;
-
- public GLState(GL11 gl) {
- mGL = gl;
-
- // Disable unused state
- gl.glDisable(GL11.GL_LIGHTING);
-
- // Enable used features
- gl.glEnable(GL11.GL_DITHER);
-
- gl.glEnableClientState(GL10.GL_VERTEX_ARRAY);
- gl.glEnableClientState(GL10.GL_TEXTURE_COORD_ARRAY);
- gl.glEnable(GL11.GL_TEXTURE_2D);
-
- gl.glTexEnvf(GL11.GL_TEXTURE_ENV,
- GL11.GL_TEXTURE_ENV_MODE, GL11.GL_REPLACE);
-
- // Set the background color
- gl.glClearColor(0f, 0f, 0f, 0f);
-
- gl.glEnable(GL11.GL_BLEND);
- gl.glBlendFunc(GL11.GL_ONE, GL11.GL_ONE_MINUS_SRC_ALPHA);
-
- // We use 565 or 8888 format, so set the alignment to 2 bytes/pixel.
- gl.glPixelStorei(GL11.GL_UNPACK_ALIGNMENT, 2);
- }
-
- public void setTexEnvMode(int mode) {
- if (mTexEnvMode == mode) return;
- mTexEnvMode = mode;
- mGL.glTexEnvf(GL11.GL_TEXTURE_ENV, GL11.GL_TEXTURE_ENV_MODE, mode);
- }
-
- public void setLineWidth(float width) {
- if (mLineWidth == width) return;
- mLineWidth = width;
- mGL.glLineWidth(width);
- }
-
- public void setTextureAlpha(float alpha) {
- if (mTextureAlpha == alpha) return;
- mTextureAlpha = alpha;
- if (alpha >= OPAQUE_ALPHA) {
- // The alpha is need for those texture without alpha channel
- mGL.glColor4f(1, 1, 1, 1);
- setTexEnvMode(GL11.GL_REPLACE);
- } else {
- mGL.glColor4f(alpha, alpha, alpha, alpha);
- setTexEnvMode(GL11.GL_MODULATE);
- }
- }
-
- public void setColorMode(int color, float alpha) {
- setBlendEnabled(!Utils.isOpaque(color) || alpha < OPAQUE_ALPHA);
-
- // Set mTextureAlpha to an invalid value, so that it will reset
- // again in setTextureAlpha(float) later.
- mTextureAlpha = -1.0f;
-
- setTextureTarget(0);
-
- float prealpha = (color >>> 24) * alpha * 65535f / 255f / 255f;
- mGL.glColor4x(
- Math.round(((color >> 16) & 0xFF) * prealpha),
- Math.round(((color >> 8) & 0xFF) * prealpha),
- Math.round((color & 0xFF) * prealpha),
- Math.round(255 * prealpha));
- }
-
- // target is a value like GL_TEXTURE_2D. If target = 0, texturing is disabled.
- public void setTextureTarget(int target) {
- if (mTextureTarget == target) return;
- if (mTextureTarget != 0) {
- mGL.glDisable(mTextureTarget);
- }
- mTextureTarget = target;
- if (mTextureTarget != 0) {
- mGL.glEnable(mTextureTarget);
- }
- }
-
- public void setBlendEnabled(boolean enabled) {
- if (mBlendEnabled == enabled) return;
- mBlendEnabled = enabled;
- if (enabled) {
- mGL.glEnable(GL11.GL_BLEND);
- } else {
- mGL.glDisable(GL11.GL_BLEND);
- }
- }
- }
-
- @Override
- public void clearBuffer(float[] argb) {
- if(argb != null && argb.length == 4) {
- mGL.glClearColor(argb[1], argb[2], argb[3], argb[0]);
- } else {
- mGL.glClearColor(0, 0, 0, 1);
- }
- mGL.glClear(GL10.GL_COLOR_BUFFER_BIT);
- }
-
- @Override
- public void clearBuffer() {
- clearBuffer(null);
- }
-
- private void setTextureCoords(RectF source) {
- setTextureCoords(source.left, source.top, source.right, source.bottom);
- }
-
- private void setTextureCoords(float left, float top,
- float right, float bottom) {
- mGL.glMatrixMode(GL11.GL_TEXTURE);
- mTextureMatrixValues[0] = right - left;
- mTextureMatrixValues[5] = bottom - top;
- mTextureMatrixValues[10] = 1;
- mTextureMatrixValues[12] = left;
- mTextureMatrixValues[13] = top;
- mTextureMatrixValues[15] = 1;
- mGL.glLoadMatrixf(mTextureMatrixValues, 0);
- mGL.glMatrixMode(GL11.GL_MODELVIEW);
- }
-
- private void setTextureCoords(float[] mTextureTransform) {
- mGL.glMatrixMode(GL11.GL_TEXTURE);
- mGL.glLoadMatrixf(mTextureTransform, 0);
- mGL.glMatrixMode(GL11.GL_MODELVIEW);
- }
-
- // unloadTexture and deleteBuffer can be called from the finalizer thread,
- // so we synchronized on the mUnboundTextures object.
- @Override
- public boolean unloadTexture(BasicTexture t) {
- synchronized (mUnboundTextures) {
- if (!t.isLoaded()) return false;
- mUnboundTextures.add(t.mId);
- return true;
- }
- }
-
- @Override
- public void deleteBuffer(int bufferId) {
- synchronized (mUnboundTextures) {
- mDeleteBuffers.add(bufferId);
- }
- }
-
- @Override
- public void deleteRecycledResources() {
- synchronized (mUnboundTextures) {
- IntArray ids = mUnboundTextures;
- if (ids.size() > 0) {
- mGLId.glDeleteTextures(mGL, ids.size(), ids.getInternalArray(), 0);
- ids.clear();
- }
-
- ids = mDeleteBuffers;
- if (ids.size() > 0) {
- mGLId.glDeleteBuffers(mGL, ids.size(), ids.getInternalArray(), 0);
- ids.clear();
- }
- }
- }
-
- @Override
- public void save() {
- save(SAVE_FLAG_ALL);
- }
-
- @Override
- public void save(int saveFlags) {
- ConfigState config = obtainRestoreConfig();
-
- if ((saveFlags & SAVE_FLAG_ALPHA) != 0) {
- config.mAlpha = mAlpha;
- } else {
- config.mAlpha = -1;
- }
-
- if ((saveFlags & SAVE_FLAG_MATRIX) != 0) {
- System.arraycopy(mMatrixValues, 0, config.mMatrix, 0, 16);
- } else {
- config.mMatrix[0] = Float.NEGATIVE_INFINITY;
- }
-
- mRestoreStack.add(config);
- }
-
- @Override
- public void restore() {
- if (mRestoreStack.isEmpty()) throw new IllegalStateException();
- ConfigState config = mRestoreStack.remove(mRestoreStack.size() - 1);
- config.restore(this);
- freeRestoreConfig(config);
- }
-
- private void freeRestoreConfig(ConfigState action) {
- action.mNextFree = mRecycledRestoreAction;
- mRecycledRestoreAction = action;
- }
-
- private ConfigState obtainRestoreConfig() {
- if (mRecycledRestoreAction != null) {
- ConfigState result = mRecycledRestoreAction;
- mRecycledRestoreAction = result.mNextFree;
- return result;
- }
- return new ConfigState();
- }
-
- private static class ConfigState {
- float mAlpha;
- float mMatrix[] = new float[16];
- ConfigState mNextFree;
-
- public void restore(GLES11Canvas canvas) {
- if (mAlpha >= 0) canvas.setAlpha(mAlpha);
- if (mMatrix[0] != Float.NEGATIVE_INFINITY) {
- System.arraycopy(mMatrix, 0, canvas.mMatrixValues, 0, 16);
- }
- }
- }
-
- @Override
- public void dumpStatisticsAndClear() {
- String line = String.format(
- "MESH:%d, TEX_OES:%d, TEX_RECT:%d, FILL_RECT:%d, LINE:%d",
- mCountDrawMesh, mCountTextureRect, mCountTextureOES,
- mCountFillRect, mCountDrawLine);
- mCountDrawMesh = 0;
- mCountTextureRect = 0;
- mCountTextureOES = 0;
- mCountFillRect = 0;
- mCountDrawLine = 0;
- Log.d(TAG, line);
- }
-
- private void saveTransform() {
- System.arraycopy(mMatrixValues, 0, mTempMatrix, 0, 16);
- }
-
- private void restoreTransform() {
- System.arraycopy(mTempMatrix, 0, mMatrixValues, 0, 16);
- }
-
- private void setRenderTarget(RawTexture texture) {
- GL11ExtensionPack gl11ep = (GL11ExtensionPack) mGL;
-
- if (mTargetTexture == null && texture != null) {
- mGLId.glGenBuffers(1, mFrameBuffer, 0);
- gl11ep.glBindFramebufferOES(
- GL11ExtensionPack.GL_FRAMEBUFFER_OES, mFrameBuffer[0]);
- }
- if (mTargetTexture != null && texture == null) {
- gl11ep.glBindFramebufferOES(GL11ExtensionPack.GL_FRAMEBUFFER_OES, 0);
- gl11ep.glDeleteFramebuffersOES(1, mFrameBuffer, 0);
- }
-
- mTargetTexture = texture;
- if (texture == null) {
- setSize(mScreenWidth, mScreenHeight);
- } else {
- setSize(texture.getWidth(), texture.getHeight());
-
- if (!texture.isLoaded()) texture.prepare(this);
-
- gl11ep.glFramebufferTexture2DOES(
- GL11ExtensionPack.GL_FRAMEBUFFER_OES,
- GL11ExtensionPack.GL_COLOR_ATTACHMENT0_OES,
- GL11.GL_TEXTURE_2D, texture.getId(), 0);
-
- checkFramebufferStatus(gl11ep);
- }
- }
-
- @Override
- public void endRenderTarget() {
- RawTexture texture = mTargetStack.remove(mTargetStack.size() - 1);
- setRenderTarget(texture);
- restore(); // restore matrix and alpha
- }
-
- @Override
- public void beginRenderTarget(RawTexture texture) {
- save(); // save matrix and alpha
- mTargetStack.add(mTargetTexture);
- setRenderTarget(texture);
- }
-
- private static void checkFramebufferStatus(GL11ExtensionPack gl11ep) {
- int status = gl11ep.glCheckFramebufferStatusOES(GL11ExtensionPack.GL_FRAMEBUFFER_OES);
- if (status != GL11ExtensionPack.GL_FRAMEBUFFER_COMPLETE_OES) {
- String msg = "";
- switch (status) {
- case GL11ExtensionPack.GL_FRAMEBUFFER_INCOMPLETE_FORMATS_OES:
- msg = "FRAMEBUFFER_FORMATS";
- break;
- case GL11ExtensionPack.GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT_OES:
- msg = "FRAMEBUFFER_ATTACHMENT";
- break;
- case GL11ExtensionPack.GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT_OES:
- msg = "FRAMEBUFFER_MISSING_ATTACHMENT";
- break;
- case GL11ExtensionPack.GL_FRAMEBUFFER_INCOMPLETE_DRAW_BUFFER_OES:
- msg = "FRAMEBUFFER_DRAW_BUFFER";
- break;
- case GL11ExtensionPack.GL_FRAMEBUFFER_INCOMPLETE_READ_BUFFER_OES:
- msg = "FRAMEBUFFER_READ_BUFFER";
- break;
- case GL11ExtensionPack.GL_FRAMEBUFFER_UNSUPPORTED_OES:
- msg = "FRAMEBUFFER_UNSUPPORTED";
- break;
- case GL11ExtensionPack.GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS_OES:
- msg = "FRAMEBUFFER_INCOMPLETE_DIMENSIONS";
- break;
- }
- throw new RuntimeException(msg + ":" + Integer.toHexString(status));
- }
- }
-
- @Override
- public void setTextureParameters(BasicTexture texture) {
- int width = texture.getWidth();
- int height = texture.getHeight();
- // Define a vertically flipped crop rectangle for OES_draw_texture.
- // The four values in sCropRect are: left, bottom, width, and
- // height. Negative value of width or height means flip.
- sCropRect[0] = 0;
- sCropRect[1] = height;
- sCropRect[2] = width;
- sCropRect[3] = -height;
-
- // Set texture parameters.
- int target = texture.getTarget();
- mGL.glBindTexture(target, texture.getId());
- mGL.glTexParameterfv(target, GL11Ext.GL_TEXTURE_CROP_RECT_OES, sCropRect, 0);
- mGL.glTexParameteri(target, GL11.GL_TEXTURE_WRAP_S, GL11.GL_CLAMP_TO_EDGE);
- mGL.glTexParameteri(target, GL11.GL_TEXTURE_WRAP_T, GL11.GL_CLAMP_TO_EDGE);
- mGL.glTexParameterf(target, GL11.GL_TEXTURE_MIN_FILTER, GL11.GL_LINEAR);
- mGL.glTexParameterf(target, GL11.GL_TEXTURE_MAG_FILTER, GL11.GL_LINEAR);
- }
-
- @Override
- public void initializeTextureSize(BasicTexture texture, int format, int type) {
- int target = texture.getTarget();
- mGL.glBindTexture(target, texture.getId());
- int width = texture.getTextureWidth();
- int height = texture.getTextureHeight();
- mGL.glTexImage2D(target, 0, format, width, height, 0, format, type, null);
- }
-
- @Override
- public void initializeTexture(BasicTexture texture, Bitmap bitmap) {
- int target = texture.getTarget();
- mGL.glBindTexture(target, texture.getId());
- GLUtils.texImage2D(target, 0, bitmap, 0);
- }
-
- @Override
- public void texSubImage2D(BasicTexture texture, int xOffset, int yOffset, Bitmap bitmap,
- int format, int type) {
- int target = texture.getTarget();
- mGL.glBindTexture(target, texture.getId());
- GLUtils.texSubImage2D(target, 0, xOffset, yOffset, bitmap, format, type);
- }
-
- @Override
- public int uploadBuffer(FloatBuffer buf) {
- return uploadBuffer(buf, Float.SIZE / Byte.SIZE);
- }
-
- @Override
- public int uploadBuffer(ByteBuffer buf) {
- return uploadBuffer(buf, 1);
- }
-
- private int uploadBuffer(Buffer buf, int elementSize) {
- int[] bufferIds = new int[1];
- mGLId.glGenBuffers(bufferIds.length, bufferIds, 0);
- int bufferId = bufferIds[0];
- mGL.glBindBuffer(GL11.GL_ARRAY_BUFFER, bufferId);
- mGL.glBufferData(GL11.GL_ARRAY_BUFFER, buf.capacity() * elementSize, buf,
- GL11.GL_STATIC_DRAW);
- return bufferId;
- }
-
- @Override
- public void recoverFromLightCycle() {
- // This is only required for GLES20
- }
-
- @Override
- public void getBounds(Rect bounds, int x, int y, int width, int height) {
- // This is only required for GLES20
- }
-
- @Override
- public GLId getGLId() {
- return mGLId;
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/GLES11IdImpl.java b/src/com/android/gallery3d/glrenderer/GLES11IdImpl.java
deleted file mode 100644
index e4793730f..000000000
--- a/src/com/android/gallery3d/glrenderer/GLES11IdImpl.java
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.glrenderer;
-
-import javax.microedition.khronos.opengles.GL11;
-import javax.microedition.khronos.opengles.GL11ExtensionPack;
-
-/**
- * Open GL ES 1.1 implementation for generating and destroying texture IDs and
- * buffer IDs
- */
-public class GLES11IdImpl implements GLId {
- private static int sNextId = 1;
- // Mutex for sNextId
- private static Object sLock = new Object();
-
- @Override
- public int generateTexture() {
- synchronized (sLock) {
- return sNextId++;
- }
- }
-
- @Override
- public void glGenBuffers(int n, int[] buffers, int offset) {
- synchronized (sLock) {
- while (n-- > 0) {
- buffers[offset + n] = sNextId++;
- }
- }
- }
-
- @Override
- public void glDeleteTextures(GL11 gl, int n, int[] textures, int offset) {
- synchronized (sLock) {
- gl.glDeleteTextures(n, textures, offset);
- }
- }
-
- @Override
- public void glDeleteBuffers(GL11 gl, int n, int[] buffers, int offset) {
- synchronized (sLock) {
- gl.glDeleteBuffers(n, buffers, offset);
- }
- }
-
- @Override
- public void glDeleteFramebuffers(GL11ExtensionPack gl11ep, int n, int[] buffers, int offset) {
- synchronized (sLock) {
- gl11ep.glDeleteFramebuffersOES(n, buffers, offset);
- }
- }
-
-
-}
diff --git a/src/com/android/gallery3d/glrenderer/GLES20Canvas.java b/src/com/android/gallery3d/glrenderer/GLES20Canvas.java
deleted file mode 100644
index 4ead1315e..000000000
--- a/src/com/android/gallery3d/glrenderer/GLES20Canvas.java
+++ /dev/null
@@ -1,1009 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.glrenderer;
-
-import android.graphics.Bitmap;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.opengl.GLES20;
-import android.opengl.GLUtils;
-import android.opengl.Matrix;
-import android.util.Log;
-
-import com.android.gallery3d.util.IntArray;
-
-import java.nio.Buffer;
-import java.nio.ByteBuffer;
-import java.nio.ByteOrder;
-import java.nio.FloatBuffer;
-import java.util.ArrayList;
-import java.util.Arrays;
-
-public class GLES20Canvas implements GLCanvas {
- // ************** Constants **********************
- private static final String TAG = GLES20Canvas.class.getSimpleName();
- private static final int FLOAT_SIZE = Float.SIZE / Byte.SIZE;
- private static final float OPAQUE_ALPHA = 0.95f;
-
- private static final int COORDS_PER_VERTEX = 2;
- private static final int VERTEX_STRIDE = COORDS_PER_VERTEX * FLOAT_SIZE;
-
- private static final int COUNT_FILL_VERTEX = 4;
- private static final int COUNT_LINE_VERTEX = 2;
- private static final int COUNT_RECT_VERTEX = 4;
- private static final int OFFSET_FILL_RECT = 0;
- private static final int OFFSET_DRAW_LINE = OFFSET_FILL_RECT + COUNT_FILL_VERTEX;
- private static final int OFFSET_DRAW_RECT = OFFSET_DRAW_LINE + COUNT_LINE_VERTEX;
-
- private static final float[] BOX_COORDINATES = {
- 0, 0, // Fill rectangle
- 1, 0,
- 0, 1,
- 1, 1,
- 0, 0, // Draw line
- 1, 1,
- 0, 0, // Draw rectangle outline
- 0, 1,
- 1, 1,
- 1, 0,
- };
-
- private static final float[] BOUNDS_COORDINATES = {
- 0, 0, 0, 1,
- 1, 1, 0, 1,
- };
-
- private static final String POSITION_ATTRIBUTE = "aPosition";
- private static final String COLOR_UNIFORM = "uColor";
- private static final String MATRIX_UNIFORM = "uMatrix";
- private static final String TEXTURE_MATRIX_UNIFORM = "uTextureMatrix";
- private static final String TEXTURE_SAMPLER_UNIFORM = "uTextureSampler";
- private static final String ALPHA_UNIFORM = "uAlpha";
- private static final String TEXTURE_COORD_ATTRIBUTE = "aTextureCoordinate";
-
- private static final String DRAW_VERTEX_SHADER = ""
- + "uniform mat4 " + MATRIX_UNIFORM + ";\n"
- + "attribute vec2 " + POSITION_ATTRIBUTE + ";\n"
- + "void main() {\n"
- + " vec4 pos = vec4(" + POSITION_ATTRIBUTE + ", 0.0, 1.0);\n"
- + " gl_Position = " + MATRIX_UNIFORM + " * pos;\n"
- + "}\n";
-
- private static final String DRAW_FRAGMENT_SHADER = ""
- + "precision mediump float;\n"
- + "uniform vec4 " + COLOR_UNIFORM + ";\n"
- + "void main() {\n"
- + " gl_FragColor = " + COLOR_UNIFORM + ";\n"
- + "}\n";
-
- private static final String TEXTURE_VERTEX_SHADER = ""
- + "uniform mat4 " + MATRIX_UNIFORM + ";\n"
- + "uniform mat4 " + TEXTURE_MATRIX_UNIFORM + ";\n"
- + "attribute vec2 " + POSITION_ATTRIBUTE + ";\n"
- + "varying vec2 vTextureCoord;\n"
- + "void main() {\n"
- + " vec4 pos = vec4(" + POSITION_ATTRIBUTE + ", 0.0, 1.0);\n"
- + " gl_Position = " + MATRIX_UNIFORM + " * pos;\n"
- + " vTextureCoord = (" + TEXTURE_MATRIX_UNIFORM + " * pos).xy;\n"
- + "}\n";
-
- private static final String MESH_VERTEX_SHADER = ""
- + "uniform mat4 " + MATRIX_UNIFORM + ";\n"
- + "attribute vec2 " + POSITION_ATTRIBUTE + ";\n"
- + "attribute vec2 " + TEXTURE_COORD_ATTRIBUTE + ";\n"
- + "varying vec2 vTextureCoord;\n"
- + "void main() {\n"
- + " vec4 pos = vec4(" + POSITION_ATTRIBUTE + ", 0.0, 1.0);\n"
- + " gl_Position = " + MATRIX_UNIFORM + " * pos;\n"
- + " vTextureCoord = " + TEXTURE_COORD_ATTRIBUTE + ";\n"
- + "}\n";
-
- private static final String TEXTURE_FRAGMENT_SHADER = ""
- + "precision mediump float;\n"
- + "varying vec2 vTextureCoord;\n"
- + "uniform float " + ALPHA_UNIFORM + ";\n"
- + "uniform sampler2D " + TEXTURE_SAMPLER_UNIFORM + ";\n"
- + "void main() {\n"
- + " gl_FragColor = texture2D(" + TEXTURE_SAMPLER_UNIFORM + ", vTextureCoord);\n"
- + " gl_FragColor *= " + ALPHA_UNIFORM + ";\n"
- + "}\n";
-
- private static final String OES_TEXTURE_FRAGMENT_SHADER = ""
- + "#extension GL_OES_EGL_image_external : require\n"
- + "precision mediump float;\n"
- + "varying vec2 vTextureCoord;\n"
- + "uniform float " + ALPHA_UNIFORM + ";\n"
- + "uniform samplerExternalOES " + TEXTURE_SAMPLER_UNIFORM + ";\n"
- + "void main() {\n"
- + " gl_FragColor = texture2D(" + TEXTURE_SAMPLER_UNIFORM + ", vTextureCoord);\n"
- + " gl_FragColor *= " + ALPHA_UNIFORM + ";\n"
- + "}\n";
-
- private static final int INITIAL_RESTORE_STATE_SIZE = 8;
- private static final int MATRIX_SIZE = 16;
-
- // Keep track of restore state
- private float[] mMatrices = new float[INITIAL_RESTORE_STATE_SIZE * MATRIX_SIZE];
- private float[] mAlphas = new float[INITIAL_RESTORE_STATE_SIZE];
- private IntArray mSaveFlags = new IntArray();
-
- private int mCurrentAlphaIndex = 0;
- private int mCurrentMatrixIndex = 0;
-
- // Viewport size
- private int mWidth;
- private int mHeight;
-
- // Projection matrix
- private float[] mProjectionMatrix = new float[MATRIX_SIZE];
-
- // Screen size for when we aren't bound to a texture
- private int mScreenWidth;
- private int mScreenHeight;
-
- // GL programs
- private int mDrawProgram;
- private int mTextureProgram;
- private int mOesTextureProgram;
- private int mMeshProgram;
-
- // GL buffer containing BOX_COORDINATES
- private int mBoxCoordinates;
-
- // Handle indices -- common
- private static final int INDEX_POSITION = 0;
- private static final int INDEX_MATRIX = 1;
-
- // Handle indices -- draw
- private static final int INDEX_COLOR = 2;
-
- // Handle indices -- texture
- private static final int INDEX_TEXTURE_MATRIX = 2;
- private static final int INDEX_TEXTURE_SAMPLER = 3;
- private static final int INDEX_ALPHA = 4;
-
- // Handle indices -- mesh
- private static final int INDEX_TEXTURE_COORD = 2;
-
- private abstract static class ShaderParameter {
- public int handle;
- protected final String mName;
-
- public ShaderParameter(String name) {
- mName = name;
- }
-
- public abstract void loadHandle(int program);
- }
-
- private static class UniformShaderParameter extends ShaderParameter {
- public UniformShaderParameter(String name) {
- super(name);
- }
-
- @Override
- public void loadHandle(int program) {
- handle = GLES20.glGetUniformLocation(program, mName);
- checkError();
- }
- }
-
- private static class AttributeShaderParameter extends ShaderParameter {
- public AttributeShaderParameter(String name) {
- super(name);
- }
-
- @Override
- public void loadHandle(int program) {
- handle = GLES20.glGetAttribLocation(program, mName);
- checkError();
- }
- }
-
- ShaderParameter[] mDrawParameters = {
- new AttributeShaderParameter(POSITION_ATTRIBUTE), // INDEX_POSITION
- new UniformShaderParameter(MATRIX_UNIFORM), // INDEX_MATRIX
- new UniformShaderParameter(COLOR_UNIFORM), // INDEX_COLOR
- };
- ShaderParameter[] mTextureParameters = {
- new AttributeShaderParameter(POSITION_ATTRIBUTE), // INDEX_POSITION
- new UniformShaderParameter(MATRIX_UNIFORM), // INDEX_MATRIX
- new UniformShaderParameter(TEXTURE_MATRIX_UNIFORM), // INDEX_TEXTURE_MATRIX
- new UniformShaderParameter(TEXTURE_SAMPLER_UNIFORM), // INDEX_TEXTURE_SAMPLER
- new UniformShaderParameter(ALPHA_UNIFORM), // INDEX_ALPHA
- };
- ShaderParameter[] mOesTextureParameters = {
- new AttributeShaderParameter(POSITION_ATTRIBUTE), // INDEX_POSITION
- new UniformShaderParameter(MATRIX_UNIFORM), // INDEX_MATRIX
- new UniformShaderParameter(TEXTURE_MATRIX_UNIFORM), // INDEX_TEXTURE_MATRIX
- new UniformShaderParameter(TEXTURE_SAMPLER_UNIFORM), // INDEX_TEXTURE_SAMPLER
- new UniformShaderParameter(ALPHA_UNIFORM), // INDEX_ALPHA
- };
- ShaderParameter[] mMeshParameters = {
- new AttributeShaderParameter(POSITION_ATTRIBUTE), // INDEX_POSITION
- new UniformShaderParameter(MATRIX_UNIFORM), // INDEX_MATRIX
- new AttributeShaderParameter(TEXTURE_COORD_ATTRIBUTE), // INDEX_TEXTURE_COORD
- new UniformShaderParameter(TEXTURE_SAMPLER_UNIFORM), // INDEX_TEXTURE_SAMPLER
- new UniformShaderParameter(ALPHA_UNIFORM), // INDEX_ALPHA
- };
-
- private final IntArray mUnboundTextures = new IntArray();
- private final IntArray mDeleteBuffers = new IntArray();
-
- // Keep track of statistics for debugging
- private int mCountDrawMesh = 0;
- private int mCountTextureRect = 0;
- private int mCountFillRect = 0;
- private int mCountDrawLine = 0;
-
- // Buffer for framebuffer IDs -- we keep track so we can switch the attached
- // texture.
- private int[] mFrameBuffer = new int[1];
-
- // Bound textures.
- private ArrayList<RawTexture> mTargetTextures = new ArrayList<RawTexture>();
-
- // Temporary variables used within calculations
- private final float[] mTempMatrix = new float[32];
- private final float[] mTempColor = new float[4];
- private final RectF mTempSourceRect = new RectF();
- private final RectF mTempTargetRect = new RectF();
- private final float[] mTempTextureMatrix = new float[MATRIX_SIZE];
- private final int[] mTempIntArray = new int[1];
-
- private static final GLId mGLId = new GLES20IdImpl();
-
- public GLES20Canvas() {
- Matrix.setIdentityM(mTempTextureMatrix, 0);
- Matrix.setIdentityM(mMatrices, mCurrentMatrixIndex);
- mAlphas[mCurrentAlphaIndex] = 1f;
- mTargetTextures.add(null);
-
- FloatBuffer boxBuffer = createBuffer(BOX_COORDINATES);
- mBoxCoordinates = uploadBuffer(boxBuffer);
-
- int drawVertexShader = loadShader(GLES20.GL_VERTEX_SHADER, DRAW_VERTEX_SHADER);
- int textureVertexShader = loadShader(GLES20.GL_VERTEX_SHADER, TEXTURE_VERTEX_SHADER);
- int meshVertexShader = loadShader(GLES20.GL_VERTEX_SHADER, MESH_VERTEX_SHADER);
- int drawFragmentShader = loadShader(GLES20.GL_FRAGMENT_SHADER, DRAW_FRAGMENT_SHADER);
- int textureFragmentShader = loadShader(GLES20.GL_FRAGMENT_SHADER, TEXTURE_FRAGMENT_SHADER);
- int oesTextureFragmentShader = loadShader(GLES20.GL_FRAGMENT_SHADER,
- OES_TEXTURE_FRAGMENT_SHADER);
-
- mDrawProgram = assembleProgram(drawVertexShader, drawFragmentShader, mDrawParameters);
- mTextureProgram = assembleProgram(textureVertexShader, textureFragmentShader,
- mTextureParameters);
- mOesTextureProgram = assembleProgram(textureVertexShader, oesTextureFragmentShader,
- mOesTextureParameters);
- mMeshProgram = assembleProgram(meshVertexShader, textureFragmentShader, mMeshParameters);
- GLES20.glBlendFunc(GLES20.GL_ONE, GLES20.GL_ONE_MINUS_SRC_ALPHA);
- checkError();
- }
-
- private static FloatBuffer createBuffer(float[] values) {
- // First create an nio buffer, then create a VBO from it.
- int size = values.length * FLOAT_SIZE;
- FloatBuffer buffer = ByteBuffer.allocateDirect(size).order(ByteOrder.nativeOrder())
- .asFloatBuffer();
- buffer.put(values, 0, values.length).position(0);
- return buffer;
- }
-
- private int assembleProgram(int vertexShader, int fragmentShader, ShaderParameter[] params) {
- int program = GLES20.glCreateProgram();
- checkError();
- if (program == 0) {
- throw new RuntimeException("Cannot create GL program: " + GLES20.glGetError());
- }
- GLES20.glAttachShader(program, vertexShader);
- checkError();
- GLES20.glAttachShader(program, fragmentShader);
- checkError();
- GLES20.glLinkProgram(program);
- checkError();
- int[] mLinkStatus = mTempIntArray;
- GLES20.glGetProgramiv(program, GLES20.GL_LINK_STATUS, mLinkStatus, 0);
- if (mLinkStatus[0] != GLES20.GL_TRUE) {
- Log.e(TAG, "Could not link program: ");
- Log.e(TAG, GLES20.glGetProgramInfoLog(program));
- GLES20.glDeleteProgram(program);
- program = 0;
- }
- for (int i = 0; i < params.length; i++) {
- params[i].loadHandle(program);
- }
- return program;
- }
-
- private static int loadShader(int type, String shaderCode) {
- // create a vertex shader type (GLES20.GL_VERTEX_SHADER)
- // or a fragment shader type (GLES20.GL_FRAGMENT_SHADER)
- int shader = GLES20.glCreateShader(type);
-
- // add the source code to the shader and compile it
- GLES20.glShaderSource(shader, shaderCode);
- checkError();
- GLES20.glCompileShader(shader);
- checkError();
-
- return shader;
- }
-
- @Override
- public void setSize(int width, int height) {
- mWidth = width;
- mHeight = height;
- GLES20.glViewport(0, 0, mWidth, mHeight);
- checkError();
- Matrix.setIdentityM(mMatrices, mCurrentMatrixIndex);
- Matrix.orthoM(mProjectionMatrix, 0, 0, width, 0, height, -1, 1);
- if (getTargetTexture() == null) {
- mScreenWidth = width;
- mScreenHeight = height;
- Matrix.translateM(mMatrices, mCurrentMatrixIndex, 0, height, 0);
- Matrix.scaleM(mMatrices, mCurrentMatrixIndex, 1, -1, 1);
- }
- }
-
- @Override
- public void clearBuffer() {
- GLES20.glClearColor(0f, 0f, 0f, 1f);
- checkError();
- GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT);
- checkError();
- }
-
- @Override
- public void clearBuffer(float[] argb) {
- GLES20.glClearColor(argb[1], argb[2], argb[3], argb[0]);
- checkError();
- GLES20.glClear(GLES20.GL_COLOR_BUFFER_BIT);
- checkError();
- }
-
- @Override
- public float getAlpha() {
- return mAlphas[mCurrentAlphaIndex];
- }
-
- @Override
- public void setAlpha(float alpha) {
- mAlphas[mCurrentAlphaIndex] = alpha;
- }
-
- @Override
- public void multiplyAlpha(float alpha) {
- setAlpha(getAlpha() * alpha);
- }
-
- @Override
- public void translate(float x, float y, float z) {
- Matrix.translateM(mMatrices, mCurrentMatrixIndex, x, y, z);
- }
-
- // This is a faster version of translate(x, y, z) because
- // (1) we knows z = 0, (2) we inline the Matrix.translateM call,
- // (3) we unroll the loop
- @Override
- public void translate(float x, float y) {
- int index = mCurrentMatrixIndex;
- float[] m = mMatrices;
- m[index + 12] += m[index + 0] * x + m[index + 4] * y;
- m[index + 13] += m[index + 1] * x + m[index + 5] * y;
- m[index + 14] += m[index + 2] * x + m[index + 6] * y;
- m[index + 15] += m[index + 3] * x + m[index + 7] * y;
- }
-
- @Override
- public void scale(float sx, float sy, float sz) {
- Matrix.scaleM(mMatrices, mCurrentMatrixIndex, sx, sy, sz);
- }
-
- @Override
- public void rotate(float angle, float x, float y, float z) {
- if (angle == 0f) {
- return;
- }
- float[] temp = mTempMatrix;
- Matrix.setRotateM(temp, 0, angle, x, y, z);
- float[] matrix = mMatrices;
- int index = mCurrentMatrixIndex;
- Matrix.multiplyMM(temp, MATRIX_SIZE, matrix, index, temp, 0);
- System.arraycopy(temp, MATRIX_SIZE, matrix, index, MATRIX_SIZE);
- }
-
- @Override
- public void multiplyMatrix(float[] matrix, int offset) {
- float[] temp = mTempMatrix;
- float[] currentMatrix = mMatrices;
- int index = mCurrentMatrixIndex;
- Matrix.multiplyMM(temp, 0, currentMatrix, index, matrix, offset);
- System.arraycopy(temp, 0, currentMatrix, index, 16);
- }
-
- @Override
- public void save() {
- save(SAVE_FLAG_ALL);
- }
-
- @Override
- public void save(int saveFlags) {
- boolean saveAlpha = (saveFlags & SAVE_FLAG_ALPHA) == SAVE_FLAG_ALPHA;
- if (saveAlpha) {
- float currentAlpha = getAlpha();
- mCurrentAlphaIndex++;
- if (mAlphas.length <= mCurrentAlphaIndex) {
- mAlphas = Arrays.copyOf(mAlphas, mAlphas.length * 2);
- }
- mAlphas[mCurrentAlphaIndex] = currentAlpha;
- }
- boolean saveMatrix = (saveFlags & SAVE_FLAG_MATRIX) == SAVE_FLAG_MATRIX;
- if (saveMatrix) {
- int currentIndex = mCurrentMatrixIndex;
- mCurrentMatrixIndex += MATRIX_SIZE;
- if (mMatrices.length <= mCurrentMatrixIndex) {
- mMatrices = Arrays.copyOf(mMatrices, mMatrices.length * 2);
- }
- System.arraycopy(mMatrices, currentIndex, mMatrices, mCurrentMatrixIndex, MATRIX_SIZE);
- }
- mSaveFlags.add(saveFlags);
- }
-
- @Override
- public void restore() {
- int restoreFlags = mSaveFlags.removeLast();
- boolean restoreAlpha = (restoreFlags & SAVE_FLAG_ALPHA) == SAVE_FLAG_ALPHA;
- if (restoreAlpha) {
- mCurrentAlphaIndex--;
- }
- boolean restoreMatrix = (restoreFlags & SAVE_FLAG_MATRIX) == SAVE_FLAG_MATRIX;
- if (restoreMatrix) {
- mCurrentMatrixIndex -= MATRIX_SIZE;
- }
- }
-
- @Override
- public void drawLine(float x1, float y1, float x2, float y2, GLPaint paint) {
- draw(GLES20.GL_LINE_STRIP, OFFSET_DRAW_LINE, COUNT_LINE_VERTEX, x1, y1, x2 - x1, y2 - y1,
- paint);
- mCountDrawLine++;
- }
-
- @Override
- public void drawRect(float x, float y, float width, float height, GLPaint paint) {
- draw(GLES20.GL_LINE_LOOP, OFFSET_DRAW_RECT, COUNT_RECT_VERTEX, x, y, width, height, paint);
- mCountDrawLine++;
- }
-
- private void draw(int type, int offset, int count, float x, float y, float width, float height,
- GLPaint paint) {
- draw(type, offset, count, x, y, width, height, paint.getColor(), paint.getLineWidth());
- }
-
- private void draw(int type, int offset, int count, float x, float y, float width, float height,
- int color, float lineWidth) {
- prepareDraw(offset, color, lineWidth);
- draw(mDrawParameters, type, count, x, y, width, height);
- }
-
- private void prepareDraw(int offset, int color, float lineWidth) {
- GLES20.glUseProgram(mDrawProgram);
- checkError();
- if (lineWidth > 0) {
- GLES20.glLineWidth(lineWidth);
- checkError();
- }
- float[] colorArray = getColor(color);
- boolean blendingEnabled = (colorArray[3] < 1f);
- enableBlending(blendingEnabled);
- if (blendingEnabled) {
- GLES20.glBlendColor(colorArray[0], colorArray[1], colorArray[2], colorArray[3]);
- checkError();
- }
-
- GLES20.glUniform4fv(mDrawParameters[INDEX_COLOR].handle, 1, colorArray, 0);
- setPosition(mDrawParameters, offset);
- checkError();
- }
-
- private float[] getColor(int color) {
- float alpha = ((color >>> 24) & 0xFF) / 255f * getAlpha();
- float red = ((color >>> 16) & 0xFF) / 255f * alpha;
- float green = ((color >>> 8) & 0xFF) / 255f * alpha;
- float blue = (color & 0xFF) / 255f * alpha;
- mTempColor[0] = red;
- mTempColor[1] = green;
- mTempColor[2] = blue;
- mTempColor[3] = alpha;
- return mTempColor;
- }
-
- private void enableBlending(boolean enableBlending) {
- if (enableBlending) {
- GLES20.glEnable(GLES20.GL_BLEND);
- checkError();
- } else {
- GLES20.glDisable(GLES20.GL_BLEND);
- checkError();
- }
- }
-
- private void setPosition(ShaderParameter[] params, int offset) {
- GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, mBoxCoordinates);
- checkError();
- GLES20.glVertexAttribPointer(params[INDEX_POSITION].handle, COORDS_PER_VERTEX,
- GLES20.GL_FLOAT, false, VERTEX_STRIDE, offset * VERTEX_STRIDE);
- checkError();
- GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, 0);
- checkError();
- }
-
- private void draw(ShaderParameter[] params, int type, int count, float x, float y, float width,
- float height) {
- setMatrix(params, x, y, width, height);
- int positionHandle = params[INDEX_POSITION].handle;
- GLES20.glEnableVertexAttribArray(positionHandle);
- checkError();
- GLES20.glDrawArrays(type, 0, count);
- checkError();
- GLES20.glDisableVertexAttribArray(positionHandle);
- checkError();
- }
-
- private void setMatrix(ShaderParameter[] params, float x, float y, float width, float height) {
- Matrix.translateM(mTempMatrix, 0, mMatrices, mCurrentMatrixIndex, x, y, 0f);
- Matrix.scaleM(mTempMatrix, 0, width, height, 1f);
- Matrix.multiplyMM(mTempMatrix, MATRIX_SIZE, mProjectionMatrix, 0, mTempMatrix, 0);
- GLES20.glUniformMatrix4fv(params[INDEX_MATRIX].handle, 1, false, mTempMatrix, MATRIX_SIZE);
- checkError();
- }
-
- @Override
- public void fillRect(float x, float y, float width, float height, int color) {
- draw(GLES20.GL_TRIANGLE_STRIP, OFFSET_FILL_RECT, COUNT_FILL_VERTEX, x, y, width, height,
- color, 0f);
- mCountFillRect++;
- }
-
- @Override
- public void drawTexture(BasicTexture texture, int x, int y, int width, int height) {
- if (width <= 0 || height <= 0) {
- return;
- }
- copyTextureCoordinates(texture, mTempSourceRect);
- mTempTargetRect.set(x, y, x + width, y + height);
- convertCoordinate(mTempSourceRect, mTempTargetRect, texture);
- drawTextureRect(texture, mTempSourceRect, mTempTargetRect);
- }
-
- private static void copyTextureCoordinates(BasicTexture texture, RectF outRect) {
- int left = 0;
- int top = 0;
- int right = texture.getWidth();
- int bottom = texture.getHeight();
- if (texture.hasBorder()) {
- left = 1;
- top = 1;
- right -= 1;
- bottom -= 1;
- }
- outRect.set(left, top, right, bottom);
- }
-
- @Override
- public void drawTexture(BasicTexture texture, RectF source, RectF target) {
- if (target.width() <= 0 || target.height() <= 0) {
- return;
- }
- mTempSourceRect.set(source);
- mTempTargetRect.set(target);
-
- convertCoordinate(mTempSourceRect, mTempTargetRect, texture);
- drawTextureRect(texture, mTempSourceRect, mTempTargetRect);
- }
-
- @Override
- public void drawTexture(BasicTexture texture, float[] textureTransform, int x, int y, int w,
- int h) {
- if (w <= 0 || h <= 0) {
- return;
- }
- mTempTargetRect.set(x, y, x + w, y + h);
- drawTextureRect(texture, textureTransform, mTempTargetRect);
- }
-
- private void drawTextureRect(BasicTexture texture, RectF source, RectF target) {
- setTextureMatrix(source);
- drawTextureRect(texture, mTempTextureMatrix, target);
- }
-
- private void setTextureMatrix(RectF source) {
- mTempTextureMatrix[0] = source.width();
- mTempTextureMatrix[5] = source.height();
- mTempTextureMatrix[12] = source.left;
- mTempTextureMatrix[13] = source.top;
- }
-
- // This function changes the source coordinate to the texture coordinates.
- // It also clips the source and target coordinates if it is beyond the
- // bound of the texture.
- private static void convertCoordinate(RectF source, RectF target, BasicTexture texture) {
- int width = texture.getWidth();
- int height = texture.getHeight();
- int texWidth = texture.getTextureWidth();
- int texHeight = texture.getTextureHeight();
- // Convert to texture coordinates
- source.left /= texWidth;
- source.right /= texWidth;
- source.top /= texHeight;
- source.bottom /= texHeight;
-
- // Clip if the rendering range is beyond the bound of the texture.
- float xBound = (float) width / texWidth;
- if (source.right > xBound) {
- target.right = target.left + target.width() * (xBound - source.left) / source.width();
- source.right = xBound;
- }
- float yBound = (float) height / texHeight;
- if (source.bottom > yBound) {
- target.bottom = target.top + target.height() * (yBound - source.top) / source.height();
- source.bottom = yBound;
- }
- }
-
- private void drawTextureRect(BasicTexture texture, float[] textureMatrix, RectF target) {
- ShaderParameter[] params = prepareTexture(texture);
- setPosition(params, OFFSET_FILL_RECT);
- GLES20.glUniformMatrix4fv(params[INDEX_TEXTURE_MATRIX].handle, 1, false, textureMatrix, 0);
- checkError();
- if (texture.isFlippedVertically()) {
- save(SAVE_FLAG_MATRIX);
- translate(0, target.centerY());
- scale(1, -1, 1);
- translate(0, -target.centerY());
- }
- draw(params, GLES20.GL_TRIANGLE_STRIP, COUNT_FILL_VERTEX, target.left, target.top,
- target.width(), target.height());
- if (texture.isFlippedVertically()) {
- restore();
- }
- mCountTextureRect++;
- }
-
- private ShaderParameter[] prepareTexture(BasicTexture texture) {
- ShaderParameter[] params;
- int program;
- if (texture.getTarget() == GLES20.GL_TEXTURE_2D) {
- params = mTextureParameters;
- program = mTextureProgram;
- } else {
- params = mOesTextureParameters;
- program = mOesTextureProgram;
- }
- prepareTexture(texture, program, params);
- return params;
- }
-
- private void prepareTexture(BasicTexture texture, int program, ShaderParameter[] params) {
- GLES20.glUseProgram(program);
- checkError();
- enableBlending(!texture.isOpaque() || getAlpha() < OPAQUE_ALPHA);
- GLES20.glActiveTexture(GLES20.GL_TEXTURE0);
- checkError();
- texture.onBind(this);
- GLES20.glBindTexture(texture.getTarget(), texture.getId());
- checkError();
- GLES20.glUniform1i(params[INDEX_TEXTURE_SAMPLER].handle, 0);
- checkError();
- GLES20.glUniform1f(params[INDEX_ALPHA].handle, getAlpha());
- checkError();
- }
-
- @Override
- public void drawMesh(BasicTexture texture, int x, int y, int xyBuffer, int uvBuffer,
- int indexBuffer, int indexCount) {
- prepareTexture(texture, mMeshProgram, mMeshParameters);
-
- GLES20.glBindBuffer(GLES20.GL_ELEMENT_ARRAY_BUFFER, indexBuffer);
- checkError();
-
- GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, xyBuffer);
- checkError();
- int positionHandle = mMeshParameters[INDEX_POSITION].handle;
- GLES20.glVertexAttribPointer(positionHandle, COORDS_PER_VERTEX, GLES20.GL_FLOAT, false,
- VERTEX_STRIDE, 0);
- checkError();
-
- GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, uvBuffer);
- checkError();
- int texCoordHandle = mMeshParameters[INDEX_TEXTURE_COORD].handle;
- GLES20.glVertexAttribPointer(texCoordHandle, COORDS_PER_VERTEX, GLES20.GL_FLOAT,
- false, VERTEX_STRIDE, 0);
- checkError();
- GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, 0);
- checkError();
-
- GLES20.glEnableVertexAttribArray(positionHandle);
- checkError();
- GLES20.glEnableVertexAttribArray(texCoordHandle);
- checkError();
-
- setMatrix(mMeshParameters, x, y, 1, 1);
- GLES20.glDrawElements(GLES20.GL_TRIANGLE_STRIP, indexCount, GLES20.GL_UNSIGNED_BYTE, 0);
- checkError();
-
- GLES20.glDisableVertexAttribArray(positionHandle);
- checkError();
- GLES20.glDisableVertexAttribArray(texCoordHandle);
- checkError();
- GLES20.glBindBuffer(GLES20.GL_ELEMENT_ARRAY_BUFFER, 0);
- checkError();
- mCountDrawMesh++;
- }
-
- @Override
- public void drawMixed(BasicTexture texture, int toColor, float ratio, int x, int y, int w, int h) {
- copyTextureCoordinates(texture, mTempSourceRect);
- mTempTargetRect.set(x, y, x + w, y + h);
- drawMixed(texture, toColor, ratio, mTempSourceRect, mTempTargetRect);
- }
-
- @Override
- public void drawMixed(BasicTexture texture, int toColor, float ratio, RectF source, RectF target) {
- if (target.width() <= 0 || target.height() <= 0) {
- return;
- }
- save(SAVE_FLAG_ALPHA);
-
- float currentAlpha = getAlpha();
- float cappedRatio = Math.min(1f, Math.max(0f, ratio));
-
- float textureAlpha = (1f - cappedRatio) * currentAlpha;
- setAlpha(textureAlpha);
- drawTexture(texture, source, target);
-
- float colorAlpha = cappedRatio * currentAlpha;
- setAlpha(colorAlpha);
- fillRect(target.left, target.top, target.width(), target.height(), toColor);
-
- restore();
- }
-
- @Override
- public boolean unloadTexture(BasicTexture texture) {
- boolean unload = texture.isLoaded();
- if (unload) {
- synchronized (mUnboundTextures) {
- mUnboundTextures.add(texture.getId());
- }
- }
- return unload;
- }
-
- @Override
- public void deleteBuffer(int bufferId) {
- synchronized (mUnboundTextures) {
- mDeleteBuffers.add(bufferId);
- }
- }
-
- @Override
- public void deleteRecycledResources() {
- synchronized (mUnboundTextures) {
- IntArray ids = mUnboundTextures;
- if (mUnboundTextures.size() > 0) {
- mGLId.glDeleteTextures(null, ids.size(), ids.getInternalArray(), 0);
- ids.clear();
- }
-
- ids = mDeleteBuffers;
- if (ids.size() > 0) {
- mGLId.glDeleteBuffers(null, ids.size(), ids.getInternalArray(), 0);
- ids.clear();
- }
- }
- }
-
- @Override
- public void dumpStatisticsAndClear() {
- String line = String.format("MESH:%d, TEX_RECT:%d, FILL_RECT:%d, LINE:%d", mCountDrawMesh,
- mCountTextureRect, mCountFillRect, mCountDrawLine);
- mCountDrawMesh = 0;
- mCountTextureRect = 0;
- mCountFillRect = 0;
- mCountDrawLine = 0;
- Log.d(TAG, line);
- }
-
- @Override
- public void endRenderTarget() {
- RawTexture oldTexture = mTargetTextures.remove(mTargetTextures.size() - 1);
- RawTexture texture = getTargetTexture();
- setRenderTarget(oldTexture, texture);
- restore(); // restore matrix and alpha
- }
-
- @Override
- public void beginRenderTarget(RawTexture texture) {
- save(); // save matrix and alpha and blending
- RawTexture oldTexture = getTargetTexture();
- mTargetTextures.add(texture);
- setRenderTarget(oldTexture, texture);
- }
-
- private RawTexture getTargetTexture() {
- return mTargetTextures.get(mTargetTextures.size() - 1);
- }
-
- private void setRenderTarget(BasicTexture oldTexture, RawTexture texture) {
- if (oldTexture == null && texture != null) {
- GLES20.glGenFramebuffers(1, mFrameBuffer, 0);
- checkError();
- GLES20.glBindFramebuffer(GLES20.GL_FRAMEBUFFER, mFrameBuffer[0]);
- checkError();
- } else if (oldTexture != null && texture == null) {
- GLES20.glBindFramebuffer(GLES20.GL_FRAMEBUFFER, 0);
- checkError();
- GLES20.glDeleteFramebuffers(1, mFrameBuffer, 0);
- checkError();
- }
-
- if (texture == null) {
- setSize(mScreenWidth, mScreenHeight);
- } else {
- setSize(texture.getWidth(), texture.getHeight());
-
- if (!texture.isLoaded()) {
- texture.prepare(this);
- }
-
- GLES20.glFramebufferTexture2D(GLES20.GL_FRAMEBUFFER, GLES20.GL_COLOR_ATTACHMENT0,
- texture.getTarget(), texture.getId(), 0);
- checkError();
-
- checkFramebufferStatus();
- }
- }
-
- private static void checkFramebufferStatus() {
- int status = GLES20.glCheckFramebufferStatus(GLES20.GL_FRAMEBUFFER);
- if (status != GLES20.GL_FRAMEBUFFER_COMPLETE) {
- String msg = "";
- switch (status) {
- case GLES20.GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT:
- msg = "GL_FRAMEBUFFER_INCOMPLETE_ATTACHMENT";
- break;
- case GLES20.GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS:
- msg = "GL_FRAMEBUFFER_INCOMPLETE_DIMENSIONS";
- break;
- case GLES20.GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT:
- msg = "GL_FRAMEBUFFER_INCOMPLETE_MISSING_ATTACHMENT";
- break;
- case GLES20.GL_FRAMEBUFFER_UNSUPPORTED:
- msg = "GL_FRAMEBUFFER_UNSUPPORTED";
- break;
- }
- throw new RuntimeException(msg + ":" + Integer.toHexString(status));
- }
- }
-
- @Override
- public void setTextureParameters(BasicTexture texture) {
- int target = texture.getTarget();
- GLES20.glBindTexture(target, texture.getId());
- checkError();
- GLES20.glTexParameteri(target, GLES20.GL_TEXTURE_WRAP_S, GLES20.GL_CLAMP_TO_EDGE);
- GLES20.glTexParameteri(target, GLES20.GL_TEXTURE_WRAP_T, GLES20.GL_CLAMP_TO_EDGE);
- GLES20.glTexParameterf(target, GLES20.GL_TEXTURE_MIN_FILTER, GLES20.GL_LINEAR);
- GLES20.glTexParameterf(target, GLES20.GL_TEXTURE_MAG_FILTER, GLES20.GL_LINEAR);
- }
-
- @Override
- public void initializeTextureSize(BasicTexture texture, int format, int type) {
- int target = texture.getTarget();
- GLES20.glBindTexture(target, texture.getId());
- checkError();
- int width = texture.getTextureWidth();
- int height = texture.getTextureHeight();
- GLES20.glTexImage2D(target, 0, format, width, height, 0, format, type, null);
- }
-
- @Override
- public void initializeTexture(BasicTexture texture, Bitmap bitmap) {
- int target = texture.getTarget();
- GLES20.glBindTexture(target, texture.getId());
- checkError();
- GLUtils.texImage2D(target, 0, bitmap, 0);
- }
-
- @Override
- public void texSubImage2D(BasicTexture texture, int xOffset, int yOffset, Bitmap bitmap,
- int format, int type) {
- int target = texture.getTarget();
- GLES20.glBindTexture(target, texture.getId());
- checkError();
- GLUtils.texSubImage2D(target, 0, xOffset, yOffset, bitmap, format, type);
- }
-
- @Override
- public int uploadBuffer(FloatBuffer buf) {
- return uploadBuffer(buf, FLOAT_SIZE);
- }
-
- @Override
- public int uploadBuffer(ByteBuffer buf) {
- return uploadBuffer(buf, 1);
- }
-
- private int uploadBuffer(Buffer buffer, int elementSize) {
- mGLId.glGenBuffers(1, mTempIntArray, 0);
- checkError();
- int bufferId = mTempIntArray[0];
- GLES20.glBindBuffer(GLES20.GL_ARRAY_BUFFER, bufferId);
- checkError();
- GLES20.glBufferData(GLES20.GL_ARRAY_BUFFER, buffer.capacity() * elementSize, buffer,
- GLES20.GL_STATIC_DRAW);
- checkError();
- return bufferId;
- }
-
- public static void checkError() {
- int error = GLES20.glGetError();
- if (error != 0) {
- Throwable t = new Throwable();
- Log.e(TAG, "GL error: " + error, t);
- }
- }
-
- @SuppressWarnings("unused")
- private static void printMatrix(String message, float[] m, int offset) {
- StringBuilder b = new StringBuilder(message);
- for (int i = 0; i < MATRIX_SIZE; i++) {
- b.append(' ');
- if (i % 4 == 0) {
- b.append('\n');
- }
- b.append(m[offset + i]);
- }
- Log.v(TAG, b.toString());
- }
-
- @Override
- public void recoverFromLightCycle() {
- GLES20.glViewport(0, 0, mWidth, mHeight);
- GLES20.glDisable(GLES20.GL_DEPTH_TEST);
- GLES20.glBlendFunc(GLES20.GL_ONE, GLES20.GL_ONE_MINUS_SRC_ALPHA);
- checkError();
- }
-
- @Override
- public void getBounds(Rect bounds, int x, int y, int width, int height) {
- Matrix.translateM(mTempMatrix, 0, mMatrices, mCurrentMatrixIndex, x, y, 0f);
- Matrix.scaleM(mTempMatrix, 0, width, height, 1f);
- Matrix.multiplyMV(mTempMatrix, MATRIX_SIZE, mTempMatrix, 0, BOUNDS_COORDINATES, 0);
- Matrix.multiplyMV(mTempMatrix, MATRIX_SIZE + 4, mTempMatrix, 0, BOUNDS_COORDINATES, 4);
- bounds.left = Math.round(mTempMatrix[MATRIX_SIZE]);
- bounds.right = Math.round(mTempMatrix[MATRIX_SIZE + 4]);
- bounds.top = Math.round(mTempMatrix[MATRIX_SIZE + 1]);
- bounds.bottom = Math.round(mTempMatrix[MATRIX_SIZE + 5]);
- bounds.sort();
- }
-
- @Override
- public GLId getGLId() {
- return mGLId;
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/GLES20IdImpl.java b/src/com/android/gallery3d/glrenderer/GLES20IdImpl.java
deleted file mode 100644
index 6cd7149cb..000000000
--- a/src/com/android/gallery3d/glrenderer/GLES20IdImpl.java
+++ /dev/null
@@ -1,42 +0,0 @@
-package com.android.gallery3d.glrenderer;
-
-import android.opengl.GLES20;
-
-import javax.microedition.khronos.opengles.GL11;
-import javax.microedition.khronos.opengles.GL11ExtensionPack;
-
-public class GLES20IdImpl implements GLId {
- private final int[] mTempIntArray = new int[1];
-
- @Override
- public int generateTexture() {
- GLES20.glGenTextures(1, mTempIntArray, 0);
- GLES20Canvas.checkError();
- return mTempIntArray[0];
- }
-
- @Override
- public void glGenBuffers(int n, int[] buffers, int offset) {
- GLES20.glGenBuffers(n, buffers, offset);
- GLES20Canvas.checkError();
- }
-
- @Override
- public void glDeleteTextures(GL11 gl, int n, int[] textures, int offset) {
- GLES20.glDeleteTextures(n, textures, offset);
- GLES20Canvas.checkError();
- }
-
-
- @Override
- public void glDeleteBuffers(GL11 gl, int n, int[] buffers, int offset) {
- GLES20.glDeleteBuffers(n, buffers, offset);
- GLES20Canvas.checkError();
- }
-
- @Override
- public void glDeleteFramebuffers(GL11ExtensionPack gl11ep, int n, int[] buffers, int offset) {
- GLES20.glDeleteFramebuffers(n, buffers, offset);
- GLES20Canvas.checkError();
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/GLId.java b/src/com/android/gallery3d/glrenderer/GLId.java
deleted file mode 100644
index 3cec558f6..000000000
--- a/src/com/android/gallery3d/glrenderer/GLId.java
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import javax.microedition.khronos.opengles.GL11;
-import javax.microedition.khronos.opengles.GL11ExtensionPack;
-
-// This mimics corresponding GL functions.
-public interface GLId {
- public int generateTexture();
-
- public void glGenBuffers(int n, int[] buffers, int offset);
-
- public void glDeleteTextures(GL11 gl, int n, int[] textures, int offset);
-
- public void glDeleteBuffers(GL11 gl, int n, int[] buffers, int offset);
-
- public void glDeleteFramebuffers(GL11ExtensionPack gl11ep, int n, int[] buffers, int offset);
-}
diff --git a/src/com/android/gallery3d/glrenderer/GLPaint.java b/src/com/android/gallery3d/glrenderer/GLPaint.java
deleted file mode 100644
index 16b220690..000000000
--- a/src/com/android/gallery3d/glrenderer/GLPaint.java
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import junit.framework.Assert;
-
-public class GLPaint {
- private float mLineWidth = 1f;
- private int mColor = 0;
-
- public void setColor(int color) {
- mColor = color;
- }
-
- public int getColor() {
- return mColor;
- }
-
- public void setLineWidth(float width) {
- Assert.assertTrue(width >= 0);
- mLineWidth = width;
- }
-
- public float getLineWidth() {
- return mLineWidth;
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/MultiLineTexture.java b/src/com/android/gallery3d/glrenderer/MultiLineTexture.java
deleted file mode 100644
index 82839f107..000000000
--- a/src/com/android/gallery3d/glrenderer/MultiLineTexture.java
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.text.Layout;
-import android.text.StaticLayout;
-import android.text.TextPaint;
-
-
-// MultiLineTexture is a texture shows the content of a specified String.
-//
-// To create a MultiLineTexture, use the newInstance() method and specify
-// the String, the font size, and the color.
-class MultiLineTexture extends CanvasTexture {
- private final Layout mLayout;
-
- private MultiLineTexture(Layout layout) {
- super(layout.getWidth(), layout.getHeight());
- mLayout = layout;
- }
-
- public static MultiLineTexture newInstance(
- String text, int maxWidth, float textSize, int color,
- Layout.Alignment alignment) {
- TextPaint paint = StringTexture.getDefaultPaint(textSize, color);
- Layout layout = new StaticLayout(text, 0, text.length(), paint,
- maxWidth, alignment, 1, 0, true, null, 0);
-
- return new MultiLineTexture(layout);
- }
-
- @Override
- protected void onDraw(Canvas canvas, Bitmap backing) {
- mLayout.draw(canvas);
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/NinePatchChunk.java b/src/com/android/gallery3d/glrenderer/NinePatchChunk.java
deleted file mode 100644
index 9dc326622..000000000
--- a/src/com/android/gallery3d/glrenderer/NinePatchChunk.java
+++ /dev/null
@@ -1,82 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import android.graphics.Rect;
-
-import java.nio.ByteBuffer;
-import java.nio.ByteOrder;
-
-// See "frameworks/base/include/utils/ResourceTypes.h" for the format of
-// NinePatch chunk.
-class NinePatchChunk {
-
- public static final int NO_COLOR = 0x00000001;
- public static final int TRANSPARENT_COLOR = 0x00000000;
-
- public Rect mPaddings = new Rect();
-
- public int mDivX[];
- public int mDivY[];
- public int mColor[];
-
- private static void readIntArray(int[] data, ByteBuffer buffer) {
- for (int i = 0, n = data.length; i < n; ++i) {
- data[i] = buffer.getInt();
- }
- }
-
- private static void checkDivCount(int length) {
- if (length == 0 || (length & 0x01) != 0) {
- throw new RuntimeException("invalid nine-patch: " + length);
- }
- }
-
- public static NinePatchChunk deserialize(byte[] data) {
- ByteBuffer byteBuffer =
- ByteBuffer.wrap(data).order(ByteOrder.nativeOrder());
-
- byte wasSerialized = byteBuffer.get();
- if (wasSerialized == 0) return null;
-
- NinePatchChunk chunk = new NinePatchChunk();
- chunk.mDivX = new int[byteBuffer.get()];
- chunk.mDivY = new int[byteBuffer.get()];
- chunk.mColor = new int[byteBuffer.get()];
-
- checkDivCount(chunk.mDivX.length);
- checkDivCount(chunk.mDivY.length);
-
- // skip 8 bytes
- byteBuffer.getInt();
- byteBuffer.getInt();
-
- chunk.mPaddings.left = byteBuffer.getInt();
- chunk.mPaddings.right = byteBuffer.getInt();
- chunk.mPaddings.top = byteBuffer.getInt();
- chunk.mPaddings.bottom = byteBuffer.getInt();
-
- // skip 4 bytes
- byteBuffer.getInt();
-
- readIntArray(chunk.mDivX, byteBuffer);
- readIntArray(chunk.mDivY, byteBuffer);
- readIntArray(chunk.mColor, byteBuffer);
-
- return chunk;
- }
-} \ No newline at end of file
diff --git a/src/com/android/gallery3d/glrenderer/NinePatchTexture.java b/src/com/android/gallery3d/glrenderer/NinePatchTexture.java
deleted file mode 100644
index d0ddc46c3..000000000
--- a/src/com/android/gallery3d/glrenderer/NinePatchTexture.java
+++ /dev/null
@@ -1,424 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.Rect;
-
-import com.android.gallery3d.common.Utils;
-
-import java.nio.ByteBuffer;
-import java.nio.ByteOrder;
-import java.nio.FloatBuffer;
-
-// NinePatchTexture is a texture backed by a NinePatch resource.
-//
-// getPaddings() returns paddings specified in the NinePatch.
-// getNinePatchChunk() returns the layout data specified in the NinePatch.
-//
-public class NinePatchTexture extends ResourceTexture {
- @SuppressWarnings("unused")
- private static final String TAG = "NinePatchTexture";
- private NinePatchChunk mChunk;
- private SmallCache<NinePatchInstance> mInstanceCache
- = new SmallCache<NinePatchInstance>();
-
- public NinePatchTexture(Context context, int resId) {
- super(context, resId);
- }
-
- @Override
- protected Bitmap onGetBitmap() {
- if (mBitmap != null) return mBitmap;
-
- BitmapFactory.Options options = new BitmapFactory.Options();
- options.inPreferredConfig = Bitmap.Config.ARGB_8888;
- Bitmap bitmap = BitmapFactory.decodeResource(
- mContext.getResources(), mResId, options);
- mBitmap = bitmap;
- setSize(bitmap.getWidth(), bitmap.getHeight());
- byte[] chunkData = bitmap.getNinePatchChunk();
- mChunk = chunkData == null
- ? null
- : NinePatchChunk.deserialize(bitmap.getNinePatchChunk());
- if (mChunk == null) {
- throw new RuntimeException("invalid nine-patch image: " + mResId);
- }
- return bitmap;
- }
-
- public Rect getPaddings() {
- // get the paddings from nine patch
- if (mChunk == null) onGetBitmap();
- return mChunk.mPaddings;
- }
-
- public NinePatchChunk getNinePatchChunk() {
- if (mChunk == null) onGetBitmap();
- return mChunk;
- }
-
- // This is a simple cache for a small number of things. Linear search
- // is used because the cache is small. It also tries to remove less used
- // item when the cache is full by moving the often-used items to the front.
- private static class SmallCache<V> {
- private static final int CACHE_SIZE = 16;
- private static final int CACHE_SIZE_START_MOVE = CACHE_SIZE / 2;
- private int[] mKey = new int[CACHE_SIZE];
- private V[] mValue = (V[]) new Object[CACHE_SIZE];
- private int mCount; // number of items in this cache
-
- // Puts a value into the cache. If the cache is full, also returns
- // a less used item, otherwise returns null.
- public V put(int key, V value) {
- if (mCount == CACHE_SIZE) {
- V old = mValue[CACHE_SIZE - 1]; // remove the last item
- mKey[CACHE_SIZE - 1] = key;
- mValue[CACHE_SIZE - 1] = value;
- return old;
- } else {
- mKey[mCount] = key;
- mValue[mCount] = value;
- mCount++;
- return null;
- }
- }
-
- public V get(int key) {
- for (int i = 0; i < mCount; i++) {
- if (mKey[i] == key) {
- // Move the accessed item one position to the front, so it
- // will less likely to be removed when cache is full. Only
- // do this if the cache is starting to get full.
- if (mCount > CACHE_SIZE_START_MOVE && i > 0) {
- int tmpKey = mKey[i];
- mKey[i] = mKey[i - 1];
- mKey[i - 1] = tmpKey;
-
- V tmpValue = mValue[i];
- mValue[i] = mValue[i - 1];
- mValue[i - 1] = tmpValue;
- }
- return mValue[i];
- }
- }
- return null;
- }
-
- public void clear() {
- for (int i = 0; i < mCount; i++) {
- mValue[i] = null; // make sure it's can be garbage-collected.
- }
- mCount = 0;
- }
-
- public int size() {
- return mCount;
- }
-
- public V valueAt(int i) {
- return mValue[i];
- }
- }
-
- private NinePatchInstance findInstance(GLCanvas canvas, int w, int h) {
- int key = w;
- key = (key << 16) | h;
- NinePatchInstance instance = mInstanceCache.get(key);
-
- if (instance == null) {
- instance = new NinePatchInstance(this, w, h);
- NinePatchInstance removed = mInstanceCache.put(key, instance);
- if (removed != null) {
- removed.recycle(canvas);
- }
- }
-
- return instance;
- }
-
- @Override
- public void draw(GLCanvas canvas, int x, int y, int w, int h) {
- if (!isLoaded()) {
- mInstanceCache.clear();
- }
-
- if (w != 0 && h != 0) {
- findInstance(canvas, w, h).draw(canvas, this, x, y);
- }
- }
-
- @Override
- public void recycle() {
- super.recycle();
- GLCanvas canvas = mCanvasRef;
- if (canvas == null) return;
- int n = mInstanceCache.size();
- for (int i = 0; i < n; i++) {
- NinePatchInstance instance = mInstanceCache.valueAt(i);
- instance.recycle(canvas);
- }
- mInstanceCache.clear();
- }
-}
-
-// This keeps data for a specialization of NinePatchTexture with the size
-// (width, height). We pre-compute the coordinates for efficiency.
-class NinePatchInstance {
-
- @SuppressWarnings("unused")
- private static final String TAG = "NinePatchInstance";
-
- // We need 16 vertices for a normal nine-patch image (the 4x4 vertices)
- private static final int VERTEX_BUFFER_SIZE = 16 * 2;
-
- // We need 22 indices for a normal nine-patch image, plus 2 for each
- // transparent region. Current there are at most 1 transparent region.
- private static final int INDEX_BUFFER_SIZE = 22 + 2;
-
- private FloatBuffer mXyBuffer;
- private FloatBuffer mUvBuffer;
- private ByteBuffer mIndexBuffer;
-
- // Names for buffer names: xy, uv, index.
- private int mXyBufferName = -1;
- private int mUvBufferName;
- private int mIndexBufferName;
-
- private int mIdxCount;
-
- public NinePatchInstance(NinePatchTexture tex, int width, int height) {
- NinePatchChunk chunk = tex.getNinePatchChunk();
-
- if (width <= 0 || height <= 0) {
- throw new RuntimeException("invalid dimension");
- }
-
- // The code should be easily extended to handle the general cases by
- // allocating more space for buffers. But let's just handle the only
- // use case.
- if (chunk.mDivX.length != 2 || chunk.mDivY.length != 2) {
- throw new RuntimeException("unsupported nine patch");
- }
-
- float divX[] = new float[4];
- float divY[] = new float[4];
- float divU[] = new float[4];
- float divV[] = new float[4];
-
- int nx = stretch(divX, divU, chunk.mDivX, tex.getWidth(), width);
- int ny = stretch(divY, divV, chunk.mDivY, tex.getHeight(), height);
-
- prepareVertexData(divX, divY, divU, divV, nx, ny, chunk.mColor);
- }
-
- /**
- * Stretches the texture according to the nine-patch rules. It will
- * linearly distribute the strechy parts defined in the nine-patch chunk to
- * the target area.
- *
- * <pre>
- * source
- * /--------------^---------------\
- * u0 u1 u2 u3 u4 u5
- * div ---> |fffff|ssssssss|fff|ssssss|ffff| ---> u
- * | div0 div1 div2 div3 |
- * | | / / / /
- * | | / / / /
- * | | / / / /
- * |fffff|ssss|fff|sss|ffff| ---> x
- * x0 x1 x2 x3 x4 x5
- * \----------v------------/
- * target
- *
- * f: fixed segment
- * s: stretchy segment
- * </pre>
- *
- * @param div the stretch parts defined in nine-patch chunk
- * @param source the length of the texture
- * @param target the length on the drawing plan
- * @param u output, the positions of these dividers in the texture
- * coordinate
- * @param x output, the corresponding position of these dividers on the
- * drawing plan
- * @return the number of these dividers.
- */
- private static int stretch(
- float x[], float u[], int div[], int source, int target) {
- int textureSize = Utils.nextPowerOf2(source);
- float textureBound = (float) source / textureSize;
-
- float stretch = 0;
- for (int i = 0, n = div.length; i < n; i += 2) {
- stretch += div[i + 1] - div[i];
- }
-
- float remaining = target - source + stretch;
-
- float lastX = 0;
- float lastU = 0;
-
- x[0] = 0;
- u[0] = 0;
- for (int i = 0, n = div.length; i < n; i += 2) {
- // Make the stretchy segment a little smaller to prevent sampling
- // on neighboring fixed segments.
- // fixed segment
- x[i + 1] = lastX + (div[i] - lastU) + 0.5f;
- u[i + 1] = Math.min((div[i] + 0.5f) / textureSize, textureBound);
-
- // stretchy segment
- float partU = div[i + 1] - div[i];
- float partX = remaining * partU / stretch;
- remaining -= partX;
- stretch -= partU;
-
- lastX = x[i + 1] + partX;
- lastU = div[i + 1];
- x[i + 2] = lastX - 0.5f;
- u[i + 2] = Math.min((lastU - 0.5f)/ textureSize, textureBound);
- }
- // the last fixed segment
- x[div.length + 1] = target;
- u[div.length + 1] = textureBound;
-
- // remove segments with length 0.
- int last = 0;
- for (int i = 1, n = div.length + 2; i < n; ++i) {
- if ((x[i] - x[last]) < 1f) continue;
- x[++last] = x[i];
- u[last] = u[i];
- }
- return last + 1;
- }
-
- private void prepareVertexData(float x[], float y[], float u[], float v[],
- int nx, int ny, int[] color) {
- /*
- * Given a 3x3 nine-patch image, the vertex order is defined as the
- * following graph:
- *
- * (0) (1) (2) (3)
- * | /| /| /|
- * | / | / | / |
- * (4) (5) (6) (7)
- * | \ | \ | \ |
- * | \| \| \|
- * (8) (9) (A) (B)
- * | /| /| /|
- * | / | / | / |
- * (C) (D) (E) (F)
- *
- * And we draw the triangle strip in the following index order:
- *
- * index: 04152637B6A5948C9DAEBF
- */
- int pntCount = 0;
- float xy[] = new float[VERTEX_BUFFER_SIZE];
- float uv[] = new float[VERTEX_BUFFER_SIZE];
- for (int j = 0; j < ny; ++j) {
- for (int i = 0; i < nx; ++i) {
- int xIndex = (pntCount++) << 1;
- int yIndex = xIndex + 1;
- xy[xIndex] = x[i];
- xy[yIndex] = y[j];
- uv[xIndex] = u[i];
- uv[yIndex] = v[j];
- }
- }
-
- int idxCount = 1;
- boolean isForward = false;
- byte index[] = new byte[INDEX_BUFFER_SIZE];
- for (int row = 0; row < ny - 1; row++) {
- --idxCount;
- isForward = !isForward;
-
- int start, end, inc;
- if (isForward) {
- start = 0;
- end = nx;
- inc = 1;
- } else {
- start = nx - 1;
- end = -1;
- inc = -1;
- }
-
- for (int col = start; col != end; col += inc) {
- int k = row * nx + col;
- if (col != start) {
- int colorIdx = row * (nx - 1) + col;
- if (isForward) colorIdx--;
- if (color[colorIdx] == NinePatchChunk.TRANSPARENT_COLOR) {
- index[idxCount] = index[idxCount - 1];
- ++idxCount;
- index[idxCount++] = (byte) k;
- }
- }
-
- index[idxCount++] = (byte) k;
- index[idxCount++] = (byte) (k + nx);
- }
- }
-
- mIdxCount = idxCount;
-
- int size = (pntCount * 2) * (Float.SIZE / Byte.SIZE);
- mXyBuffer = allocateDirectNativeOrderBuffer(size).asFloatBuffer();
- mUvBuffer = allocateDirectNativeOrderBuffer(size).asFloatBuffer();
- mIndexBuffer = allocateDirectNativeOrderBuffer(mIdxCount);
-
- mXyBuffer.put(xy, 0, pntCount * 2).position(0);
- mUvBuffer.put(uv, 0, pntCount * 2).position(0);
- mIndexBuffer.put(index, 0, idxCount).position(0);
- }
-
- private static ByteBuffer allocateDirectNativeOrderBuffer(int size) {
- return ByteBuffer.allocateDirect(size).order(ByteOrder.nativeOrder());
- }
-
- private void prepareBuffers(GLCanvas canvas) {
- mXyBufferName = canvas.uploadBuffer(mXyBuffer);
- mUvBufferName = canvas.uploadBuffer(mUvBuffer);
- mIndexBufferName = canvas.uploadBuffer(mIndexBuffer);
-
- // These buffers are never used again.
- mXyBuffer = null;
- mUvBuffer = null;
- mIndexBuffer = null;
- }
-
- public void draw(GLCanvas canvas, NinePatchTexture tex, int x, int y) {
- if (mXyBufferName == -1) {
- prepareBuffers(canvas);
- }
- canvas.drawMesh(tex, x, y, mXyBufferName, mUvBufferName, mIndexBufferName, mIdxCount);
- }
-
- public void recycle(GLCanvas canvas) {
- if (mXyBuffer == null) {
- canvas.deleteBuffer(mXyBufferName);
- canvas.deleteBuffer(mUvBufferName);
- canvas.deleteBuffer(mIndexBufferName);
- mXyBufferName = -1;
- }
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/RawTexture.java b/src/com/android/gallery3d/glrenderer/RawTexture.java
deleted file mode 100644
index 93f0fdff9..000000000
--- a/src/com/android/gallery3d/glrenderer/RawTexture.java
+++ /dev/null
@@ -1,73 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import android.util.Log;
-
-import javax.microedition.khronos.opengles.GL11;
-
-public class RawTexture extends BasicTexture {
- private static final String TAG = "RawTexture";
-
- private final boolean mOpaque;
- private boolean mIsFlipped;
-
- public RawTexture(int width, int height, boolean opaque) {
- mOpaque = opaque;
- setSize(width, height);
- }
-
- @Override
- public boolean isOpaque() {
- return mOpaque;
- }
-
- @Override
- public boolean isFlippedVertically() {
- return mIsFlipped;
- }
-
- public void setIsFlippedVertically(boolean isFlipped) {
- mIsFlipped = isFlipped;
- }
-
- protected void prepare(GLCanvas canvas) {
- GLId glId = canvas.getGLId();
- mId = glId.generateTexture();
- canvas.initializeTextureSize(this, GL11.GL_RGBA, GL11.GL_UNSIGNED_BYTE);
- canvas.setTextureParameters(this);
- mState = STATE_LOADED;
- setAssociatedCanvas(canvas);
- }
-
- @Override
- protected boolean onBind(GLCanvas canvas) {
- if (isLoaded()) return true;
- Log.w(TAG, "lost the content due to context change");
- return false;
- }
-
- @Override
- public void yield() {
- // we cannot free the texture because we have no backup.
- }
-
- @Override
- protected int getTarget() {
- return GL11.GL_TEXTURE_2D;
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/ResourceTexture.java b/src/com/android/gallery3d/glrenderer/ResourceTexture.java
deleted file mode 100644
index eb8e8a517..000000000
--- a/src/com/android/gallery3d/glrenderer/ResourceTexture.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-
-import junit.framework.Assert;
-
-// ResourceTexture is a texture whose Bitmap is decoded from a resource.
-// By default ResourceTexture is not opaque.
-public class ResourceTexture extends UploadedTexture {
-
- protected final Context mContext;
- protected final int mResId;
-
- public ResourceTexture(Context context, int resId) {
- Assert.assertNotNull(context);
- mContext = context;
- mResId = resId;
- setOpaque(false);
- }
-
- @Override
- protected Bitmap onGetBitmap() {
- BitmapFactory.Options options = new BitmapFactory.Options();
- options.inPreferredConfig = Bitmap.Config.ARGB_8888;
- return BitmapFactory.decodeResource(
- mContext.getResources(), mResId, options);
- }
-
- @Override
- protected void onFreeBitmap(Bitmap bitmap) {
- if (!inFinalizer()) {
- bitmap.recycle();
- }
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/StringTexture.java b/src/com/android/gallery3d/glrenderer/StringTexture.java
deleted file mode 100644
index 56ca29753..000000000
--- a/src/com/android/gallery3d/glrenderer/StringTexture.java
+++ /dev/null
@@ -1,88 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint.FontMetricsInt;
-import android.graphics.Typeface;
-import android.text.TextPaint;
-import android.text.TextUtils;
-import android.util.FloatMath;
-
-// StringTexture is a texture shows the content of a specified String.
-//
-// To create a StringTexture, use the newInstance() method and specify
-// the String, the font size, and the color.
-public class StringTexture extends CanvasTexture {
- private final String mText;
- private final TextPaint mPaint;
- private final FontMetricsInt mMetrics;
-
- private StringTexture(String text, TextPaint paint,
- FontMetricsInt metrics, int width, int height) {
- super(width, height);
- mText = text;
- mPaint = paint;
- mMetrics = metrics;
- }
-
- public static TextPaint getDefaultPaint(float textSize, int color) {
- TextPaint paint = new TextPaint();
- paint.setTextSize(textSize);
- paint.setAntiAlias(true);
- paint.setColor(color);
- paint.setShadowLayer(2f, 0f, 0f, Color.BLACK);
- return paint;
- }
-
- public static StringTexture newInstance(
- String text, float textSize, int color) {
- return newInstance(text, getDefaultPaint(textSize, color));
- }
-
- public static StringTexture newInstance(
- String text, float textSize, int color,
- float lengthLimit, boolean isBold) {
- TextPaint paint = getDefaultPaint(textSize, color);
- if (isBold) {
- paint.setTypeface(Typeface.defaultFromStyle(Typeface.BOLD));
- }
- if (lengthLimit > 0) {
- text = TextUtils.ellipsize(
- text, paint, lengthLimit, TextUtils.TruncateAt.END).toString();
- }
- return newInstance(text, paint);
- }
-
- private static StringTexture newInstance(String text, TextPaint paint) {
- FontMetricsInt metrics = paint.getFontMetricsInt();
- int width = (int) FloatMath.ceil(paint.measureText(text));
- int height = metrics.bottom - metrics.top;
- // The texture size needs to be at least 1x1.
- if (width <= 0) width = 1;
- if (height <= 0) height = 1;
- return new StringTexture(text, paint, metrics, width, height);
- }
-
- @Override
- protected void onDraw(Canvas canvas, Bitmap backing) {
- canvas.translate(0, -mMetrics.ascent);
- canvas.drawText(mText, 0, 0, mPaint);
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/Texture.java b/src/com/android/gallery3d/glrenderer/Texture.java
deleted file mode 100644
index 3dcae4aec..000000000
--- a/src/com/android/gallery3d/glrenderer/Texture.java
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-
-// Texture is a rectangular image which can be drawn on GLCanvas.
-// The isOpaque() function gives a hint about whether the texture is opaque,
-// so the drawing can be done faster.
-//
-// This is the current texture hierarchy:
-//
-// Texture
-// -- ColorTexture
-// -- FadeInTexture
-// -- BasicTexture
-// -- UploadedTexture
-// -- BitmapTexture
-// -- Tile
-// -- ResourceTexture
-// -- NinePatchTexture
-// -- CanvasTexture
-// -- StringTexture
-//
-public interface Texture {
- public int getWidth();
- public int getHeight();
- public void draw(GLCanvas canvas, int x, int y);
- public void draw(GLCanvas canvas, int x, int y, int w, int h);
- public boolean isOpaque();
-}
diff --git a/src/com/android/gallery3d/glrenderer/TextureUploader.java b/src/com/android/gallery3d/glrenderer/TextureUploader.java
deleted file mode 100644
index f17ab845c..000000000
--- a/src/com/android/gallery3d/glrenderer/TextureUploader.java
+++ /dev/null
@@ -1,105 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import com.android.gallery3d.ui.GLRoot;
-import com.android.gallery3d.ui.GLRoot.OnGLIdleListener;
-
-import java.util.ArrayDeque;
-
-public class TextureUploader implements OnGLIdleListener {
- private static final int INIT_CAPACITY = 64;
- private static final int QUOTA_PER_FRAME = 1;
-
- private final ArrayDeque<UploadedTexture> mFgTextures =
- new ArrayDeque<UploadedTexture>(INIT_CAPACITY);
- private final ArrayDeque<UploadedTexture> mBgTextures =
- new ArrayDeque<UploadedTexture>(INIT_CAPACITY);
- private final GLRoot mGLRoot;
- private volatile boolean mIsQueued = false;
-
- public TextureUploader(GLRoot root) {
- mGLRoot = root;
- }
-
- public synchronized void clear() {
- while (!mFgTextures.isEmpty()) {
- mFgTextures.pop().setIsUploading(false);
- }
- while (!mBgTextures.isEmpty()) {
- mBgTextures.pop().setIsUploading(false);
- }
- }
-
- // caller should hold synchronized on "this"
- private void queueSelfIfNeed() {
- if (mIsQueued) return;
- mIsQueued = true;
- mGLRoot.addOnGLIdleListener(this);
- }
-
- public synchronized void addBgTexture(UploadedTexture t) {
- if (t.isContentValid()) return;
- mBgTextures.addLast(t);
- t.setIsUploading(true);
- queueSelfIfNeed();
- }
-
- public synchronized void addFgTexture(UploadedTexture t) {
- if (t.isContentValid()) return;
- mFgTextures.addLast(t);
- t.setIsUploading(true);
- queueSelfIfNeed();
- }
-
- private int upload(GLCanvas canvas, ArrayDeque<UploadedTexture> deque,
- int uploadQuota, boolean isBackground) {
- while (uploadQuota > 0) {
- UploadedTexture t;
- synchronized (this) {
- if (deque.isEmpty()) break;
- t = deque.removeFirst();
- t.setIsUploading(false);
- if (t.isContentValid()) continue;
-
- // this has to be protected by the synchronized block
- // to prevent the inner bitmap get recycled
- t.updateContent(canvas);
- }
-
- // It will took some more time for a texture to be drawn for
- // the first time.
- // Thus, when scrolling, if a new column appears on screen,
- // it may cause a UI jank even these textures are uploaded.
- if (isBackground) t.draw(canvas, 0, 0);
- --uploadQuota;
- }
- return uploadQuota;
- }
-
- @Override
- public boolean onGLIdle(GLCanvas canvas, boolean renderRequested) {
- int uploadQuota = QUOTA_PER_FRAME;
- uploadQuota = upload(canvas, mFgTextures, uploadQuota, false);
- if (uploadQuota < QUOTA_PER_FRAME) mGLRoot.requestRender();
- upload(canvas, mBgTextures, uploadQuota, true);
- synchronized (this) {
- mIsQueued = !mFgTextures.isEmpty() || !mBgTextures.isEmpty();
- return mIsQueued;
- }
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/TiledTexture.java b/src/com/android/gallery3d/glrenderer/TiledTexture.java
deleted file mode 100644
index 6ca1de088..000000000
--- a/src/com/android/gallery3d/glrenderer/TiledTexture.java
+++ /dev/null
@@ -1,349 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import android.graphics.Bitmap;
-import android.graphics.Bitmap.Config;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.PorterDuff.Mode;
-import android.graphics.PorterDuffXfermode;
-import android.graphics.RectF;
-import android.os.SystemClock;
-
-import com.android.gallery3d.ui.GLRoot;
-import com.android.gallery3d.ui.GLRoot.OnGLIdleListener;
-
-import java.util.ArrayDeque;
-import java.util.ArrayList;
-
-// This class is similar to BitmapTexture, except the bitmap is
-// split into tiles. By doing so, we may increase the time required to
-// upload the whole bitmap but we reduce the time of uploading each tile
-// so it make the animation more smooth and prevents jank.
-public class TiledTexture implements Texture {
- private static final int CONTENT_SIZE = 254;
- private static final int BORDER_SIZE = 1;
- private static final int TILE_SIZE = CONTENT_SIZE + 2 * BORDER_SIZE;
- private static final int INIT_CAPACITY = 8;
-
- // We are targeting at 60fps, so we have 16ms for each frame.
- // In this 16ms, we use about 4~8 ms to upload tiles.
- private static final long UPLOAD_TILE_LIMIT = 4; // ms
-
- private static Tile sFreeTileHead = null;
- private static final Object sFreeTileLock = new Object();
-
- private static Bitmap sUploadBitmap;
- private static Canvas sCanvas;
- private static Paint sBitmapPaint;
- private static Paint sPaint;
-
- private int mUploadIndex = 0;
-
- private final Tile[] mTiles; // Can be modified in different threads.
- // Should be protected by "synchronized."
- private final int mWidth;
- private final int mHeight;
- private final RectF mSrcRect = new RectF();
- private final RectF mDestRect = new RectF();
-
- public static class Uploader implements OnGLIdleListener {
- private final ArrayDeque<TiledTexture> mTextures =
- new ArrayDeque<TiledTexture>(INIT_CAPACITY);
-
- private final GLRoot mGlRoot;
- private boolean mIsQueued = false;
-
- public Uploader(GLRoot glRoot) {
- mGlRoot = glRoot;
- }
-
- public synchronized void clear() {
- mTextures.clear();
- }
-
- public synchronized void addTexture(TiledTexture t) {
- if (t.isReady()) return;
- mTextures.addLast(t);
-
- if (mIsQueued) return;
- mIsQueued = true;
- mGlRoot.addOnGLIdleListener(this);
- }
-
- @Override
- public boolean onGLIdle(GLCanvas canvas, boolean renderRequested) {
- ArrayDeque<TiledTexture> deque = mTextures;
- synchronized (this) {
- long now = SystemClock.uptimeMillis();
- long dueTime = now + UPLOAD_TILE_LIMIT;
- while (now < dueTime && !deque.isEmpty()) {
- TiledTexture t = deque.peekFirst();
- if (t.uploadNextTile(canvas)) {
- deque.removeFirst();
- mGlRoot.requestRender();
- }
- now = SystemClock.uptimeMillis();
- }
- mIsQueued = !mTextures.isEmpty();
-
- // return true to keep this listener in the queue
- return mIsQueued;
- }
- }
- }
-
- private static class Tile extends UploadedTexture {
- public int offsetX;
- public int offsetY;
- public Bitmap bitmap;
- public Tile nextFreeTile;
- public int contentWidth;
- public int contentHeight;
-
- @Override
- public void setSize(int width, int height) {
- contentWidth = width;
- contentHeight = height;
- mWidth = width + 2 * BORDER_SIZE;
- mHeight = height + 2 * BORDER_SIZE;
- mTextureWidth = TILE_SIZE;
- mTextureHeight = TILE_SIZE;
- }
-
- @Override
- protected Bitmap onGetBitmap() {
- int x = BORDER_SIZE - offsetX;
- int y = BORDER_SIZE - offsetY;
- int r = bitmap.getWidth() + x;
- int b = bitmap.getHeight() + y;
- sCanvas.drawBitmap(bitmap, x, y, sBitmapPaint);
- bitmap = null;
-
- // draw borders if need
- if (x > 0) sCanvas.drawLine(x - 1, 0, x - 1, TILE_SIZE, sPaint);
- if (y > 0) sCanvas.drawLine(0, y - 1, TILE_SIZE, y - 1, sPaint);
- if (r < CONTENT_SIZE) sCanvas.drawLine(r, 0, r, TILE_SIZE, sPaint);
- if (b < CONTENT_SIZE) sCanvas.drawLine(0, b, TILE_SIZE, b, sPaint);
-
- return sUploadBitmap;
- }
-
- @Override
- protected void onFreeBitmap(Bitmap bitmap) {
- // do nothing
- }
- }
-
- private static void freeTile(Tile tile) {
- tile.invalidateContent();
- tile.bitmap = null;
- synchronized (sFreeTileLock) {
- tile.nextFreeTile = sFreeTileHead;
- sFreeTileHead = tile;
- }
- }
-
- private static Tile obtainTile() {
- synchronized (sFreeTileLock) {
- Tile result = sFreeTileHead;
- if (result == null) return new Tile();
- sFreeTileHead = result.nextFreeTile;
- result.nextFreeTile = null;
- return result;
- }
- }
-
- private boolean uploadNextTile(GLCanvas canvas) {
- if (mUploadIndex == mTiles.length) return true;
-
- synchronized (mTiles) {
- Tile next = mTiles[mUploadIndex++];
-
- // Make sure tile has not already been recycled by the time
- // this is called (race condition in onGLIdle)
- if (next.bitmap != null) {
- boolean hasBeenLoad = next.isLoaded();
- next.updateContent(canvas);
-
- // It will take some time for a texture to be drawn for the first
- // time. When scrolling, we need to draw several tiles on the screen
- // at the same time. It may cause a UI jank even these textures has
- // been uploaded.
- if (!hasBeenLoad) next.draw(canvas, 0, 0);
- }
- }
- return mUploadIndex == mTiles.length;
- }
-
- public TiledTexture(Bitmap bitmap) {
- mWidth = bitmap.getWidth();
- mHeight = bitmap.getHeight();
- ArrayList<Tile> list = new ArrayList<Tile>();
-
- for (int x = 0, w = mWidth; x < w; x += CONTENT_SIZE) {
- for (int y = 0, h = mHeight; y < h; y += CONTENT_SIZE) {
- Tile tile = obtainTile();
- tile.offsetX = x;
- tile.offsetY = y;
- tile.bitmap = bitmap;
- tile.setSize(
- Math.min(CONTENT_SIZE, mWidth - x),
- Math.min(CONTENT_SIZE, mHeight - y));
- list.add(tile);
- }
- }
- mTiles = list.toArray(new Tile[list.size()]);
- }
-
- public boolean isReady() {
- return mUploadIndex == mTiles.length;
- }
-
- // Can be called in UI thread.
- public void recycle() {
- synchronized (mTiles) {
- for (int i = 0, n = mTiles.length; i < n; ++i) {
- freeTile(mTiles[i]);
- }
- }
- }
-
- public static void freeResources() {
- sUploadBitmap = null;
- sCanvas = null;
- sBitmapPaint = null;
- sPaint = null;
- }
-
- public static void prepareResources() {
- sUploadBitmap = Bitmap.createBitmap(TILE_SIZE, TILE_SIZE, Config.ARGB_8888);
- sCanvas = new Canvas(sUploadBitmap);
- sBitmapPaint = new Paint(Paint.FILTER_BITMAP_FLAG);
- sBitmapPaint.setXfermode(new PorterDuffXfermode(Mode.SRC));
- sPaint = new Paint();
- sPaint.setXfermode(new PorterDuffXfermode(Mode.SRC));
- sPaint.setColor(Color.TRANSPARENT);
- }
-
- // We want to draw the "source" on the "target".
- // This method is to find the "output" rectangle which is
- // the corresponding area of the "src".
- // (x,y) target
- // (x0,y0) source +---------------+
- // +----------+ | |
- // | src | | output |
- // | +--+ | linear map | +----+ |
- // | +--+ | ----------> | | | |
- // | | by (scaleX, scaleY) | +----+ |
- // +----------+ | |
- // Texture +---------------+
- // Canvas
- private static void mapRect(RectF output,
- RectF src, float x0, float y0, float x, float y, float scaleX,
- float scaleY) {
- output.set(x + (src.left - x0) * scaleX,
- y + (src.top - y0) * scaleY,
- x + (src.right - x0) * scaleX,
- y + (src.bottom - y0) * scaleY);
- }
-
- // Draws a mixed color of this texture and a specified color onto the
- // a rectangle. The used color is: from * (1 - ratio) + to * ratio.
- public void drawMixed(GLCanvas canvas, int color, float ratio,
- int x, int y, int width, int height) {
- RectF src = mSrcRect;
- RectF dest = mDestRect;
- float scaleX = (float) width / mWidth;
- float scaleY = (float) height / mHeight;
- synchronized (mTiles) {
- for (int i = 0, n = mTiles.length; i < n; ++i) {
- Tile t = mTiles[i];
- src.set(0, 0, t.contentWidth, t.contentHeight);
- src.offset(t.offsetX, t.offsetY);
- mapRect(dest, src, 0, 0, x, y, scaleX, scaleY);
- src.offset(BORDER_SIZE - t.offsetX, BORDER_SIZE - t.offsetY);
- canvas.drawMixed(t, color, ratio, mSrcRect, mDestRect);
- }
- }
- }
-
- // Draws the texture on to the specified rectangle.
- @Override
- public void draw(GLCanvas canvas, int x, int y, int width, int height) {
- RectF src = mSrcRect;
- RectF dest = mDestRect;
- float scaleX = (float) width / mWidth;
- float scaleY = (float) height / mHeight;
- synchronized (mTiles) {
- for (int i = 0, n = mTiles.length; i < n; ++i) {
- Tile t = mTiles[i];
- src.set(0, 0, t.contentWidth, t.contentHeight);
- src.offset(t.offsetX, t.offsetY);
- mapRect(dest, src, 0, 0, x, y, scaleX, scaleY);
- src.offset(BORDER_SIZE - t.offsetX, BORDER_SIZE - t.offsetY);
- canvas.drawTexture(t, mSrcRect, mDestRect);
- }
- }
- }
-
- // Draws a sub region of this texture on to the specified rectangle.
- public void draw(GLCanvas canvas, RectF source, RectF target) {
- RectF src = mSrcRect;
- RectF dest = mDestRect;
- float x0 = source.left;
- float y0 = source.top;
- float x = target.left;
- float y = target.top;
- float scaleX = target.width() / source.width();
- float scaleY = target.height() / source.height();
-
- synchronized (mTiles) {
- for (int i = 0, n = mTiles.length; i < n; ++i) {
- Tile t = mTiles[i];
- src.set(0, 0, t.contentWidth, t.contentHeight);
- src.offset(t.offsetX, t.offsetY);
- if (!src.intersect(source)) continue;
- mapRect(dest, src, x0, y0, x, y, scaleX, scaleY);
- src.offset(BORDER_SIZE - t.offsetX, BORDER_SIZE - t.offsetY);
- canvas.drawTexture(t, src, dest);
- }
- }
- }
-
- @Override
- public int getWidth() {
- return mWidth;
- }
-
- @Override
- public int getHeight() {
- return mHeight;
- }
-
- @Override
- public void draw(GLCanvas canvas, int x, int y) {
- draw(canvas, x, y, mWidth, mHeight);
- }
-
- @Override
- public boolean isOpaque() {
- return false;
- }
-}
diff --git a/src/com/android/gallery3d/glrenderer/UploadedTexture.java b/src/com/android/gallery3d/glrenderer/UploadedTexture.java
deleted file mode 100644
index f41a979b7..000000000
--- a/src/com/android/gallery3d/glrenderer/UploadedTexture.java
+++ /dev/null
@@ -1,298 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.glrenderer;
-
-import android.graphics.Bitmap;
-import android.graphics.Bitmap.Config;
-import android.opengl.GLUtils;
-
-import junit.framework.Assert;
-
-import java.util.HashMap;
-
-import javax.microedition.khronos.opengles.GL11;
-
-// UploadedTextures use a Bitmap for the content of the texture.
-//
-// Subclasses should implement onGetBitmap() to provide the Bitmap and
-// implement onFreeBitmap(mBitmap) which will be called when the Bitmap
-// is not needed anymore.
-//
-// isContentValid() is meaningful only when the isLoaded() returns true.
-// It means whether the content needs to be updated.
-//
-// The user of this class should call recycle() when the texture is not
-// needed anymore.
-//
-// By default an UploadedTexture is opaque (so it can be drawn faster without
-// blending). The user or subclass can override it using setOpaque().
-public abstract class UploadedTexture extends BasicTexture {
-
- // To prevent keeping allocation the borders, we store those used borders here.
- // Since the length will be power of two, it won't use too much memory.
- private static HashMap<BorderKey, Bitmap> sBorderLines =
- new HashMap<BorderKey, Bitmap>();
- private static BorderKey sBorderKey = new BorderKey();
-
- @SuppressWarnings("unused")
- private static final String TAG = "Texture";
- private boolean mContentValid = true;
-
- // indicate this textures is being uploaded in background
- private boolean mIsUploading = false;
- private boolean mOpaque = true;
- private boolean mThrottled = false;
- private static int sUploadedCount;
- private static final int UPLOAD_LIMIT = 100;
-
- protected Bitmap mBitmap;
- private int mBorder;
-
- protected UploadedTexture() {
- this(false);
- }
-
- protected UploadedTexture(boolean hasBorder) {
- super(null, 0, STATE_UNLOADED);
- if (hasBorder) {
- setBorder(true);
- mBorder = 1;
- }
- }
-
- protected void setIsUploading(boolean uploading) {
- mIsUploading = uploading;
- }
-
- public boolean isUploading() {
- return mIsUploading;
- }
-
- private static class BorderKey implements Cloneable {
- public boolean vertical;
- public Config config;
- public int length;
-
- @Override
- public int hashCode() {
- int x = config.hashCode() ^ length;
- return vertical ? x : -x;
- }
-
- @Override
- public boolean equals(Object object) {
- if (!(object instanceof BorderKey)) return false;
- BorderKey o = (BorderKey) object;
- return vertical == o.vertical
- && config == o.config && length == o.length;
- }
-
- @Override
- public BorderKey clone() {
- try {
- return (BorderKey) super.clone();
- } catch (CloneNotSupportedException e) {
- throw new AssertionError(e);
- }
- }
- }
-
- protected void setThrottled(boolean throttled) {
- mThrottled = throttled;
- }
-
- private static Bitmap getBorderLine(
- boolean vertical, Config config, int length) {
- BorderKey key = sBorderKey;
- key.vertical = vertical;
- key.config = config;
- key.length = length;
- Bitmap bitmap = sBorderLines.get(key);
- if (bitmap == null) {
- bitmap = vertical
- ? Bitmap.createBitmap(1, length, config)
- : Bitmap.createBitmap(length, 1, config);
- sBorderLines.put(key.clone(), bitmap);
- }
- return bitmap;
- }
-
- private Bitmap getBitmap() {
- if (mBitmap == null) {
- mBitmap = onGetBitmap();
- int w = mBitmap.getWidth() + mBorder * 2;
- int h = mBitmap.getHeight() + mBorder * 2;
- if (mWidth == UNSPECIFIED) {
- setSize(w, h);
- }
- }
- return mBitmap;
- }
-
- private void freeBitmap() {
- Assert.assertTrue(mBitmap != null);
- onFreeBitmap(mBitmap);
- mBitmap = null;
- }
-
- @Override
- public int getWidth() {
- if (mWidth == UNSPECIFIED) getBitmap();
- return mWidth;
- }
-
- @Override
- public int getHeight() {
- if (mWidth == UNSPECIFIED) getBitmap();
- return mHeight;
- }
-
- protected abstract Bitmap onGetBitmap();
-
- protected abstract void onFreeBitmap(Bitmap bitmap);
-
- protected void invalidateContent() {
- if (mBitmap != null) freeBitmap();
- mContentValid = false;
- mWidth = UNSPECIFIED;
- mHeight = UNSPECIFIED;
- }
-
- /**
- * Whether the content on GPU is valid.
- */
- public boolean isContentValid() {
- return isLoaded() && mContentValid;
- }
-
- /**
- * Updates the content on GPU's memory.
- * @param canvas
- */
- public void updateContent(GLCanvas canvas) {
- if (!isLoaded()) {
- if (mThrottled && ++sUploadedCount > UPLOAD_LIMIT) {
- return;
- }
- uploadToCanvas(canvas);
- } else if (!mContentValid) {
- Bitmap bitmap = getBitmap();
- int format = GLUtils.getInternalFormat(bitmap);
- int type = GLUtils.getType(bitmap);
- canvas.texSubImage2D(this, mBorder, mBorder, bitmap, format, type);
- freeBitmap();
- mContentValid = true;
- }
- }
-
- public static void resetUploadLimit() {
- sUploadedCount = 0;
- }
-
- public static boolean uploadLimitReached() {
- return sUploadedCount > UPLOAD_LIMIT;
- }
-
- private void uploadToCanvas(GLCanvas canvas) {
-
- Bitmap bitmap = getBitmap();
- if (bitmap != null) {
- try {
- int bWidth = bitmap.getWidth();
- int bHeight = bitmap.getHeight();
- int width = bWidth + mBorder * 2;
- int height = bHeight + mBorder * 2;
- int texWidth = getTextureWidth();
- int texHeight = getTextureHeight();
-
- Assert.assertTrue(bWidth <= texWidth && bHeight <= texHeight);
-
- // Upload the bitmap to a new texture.
- mId = canvas.getGLId().generateTexture();
- canvas.setTextureParameters(this);
-
- if (bWidth == texWidth && bHeight == texHeight) {
- canvas.initializeTexture(this, bitmap);
- } else {
- int format = GLUtils.getInternalFormat(bitmap);
- int type = GLUtils.getType(bitmap);
- Config config = bitmap.getConfig();
-
- canvas.initializeTextureSize(this, format, type);
- canvas.texSubImage2D(this, mBorder, mBorder, bitmap, format, type);
-
- if (mBorder > 0) {
- // Left border
- Bitmap line = getBorderLine(true, config, texHeight);
- canvas.texSubImage2D(this, 0, 0, line, format, type);
-
- // Top border
- line = getBorderLine(false, config, texWidth);
- canvas.texSubImage2D(this, 0, 0, line, format, type);
- }
-
- // Right border
- if (mBorder + bWidth < texWidth) {
- Bitmap line = getBorderLine(true, config, texHeight);
- canvas.texSubImage2D(this, mBorder + bWidth, 0, line, format, type);
- }
-
- // Bottom border
- if (mBorder + bHeight < texHeight) {
- Bitmap line = getBorderLine(false, config, texWidth);
- canvas.texSubImage2D(this, 0, mBorder + bHeight, line, format, type);
- }
- }
- } finally {
- freeBitmap();
- }
- // Update texture state.
- setAssociatedCanvas(canvas);
- mState = STATE_LOADED;
- mContentValid = true;
- } else {
- mState = STATE_ERROR;
- throw new RuntimeException("Texture load fail, no bitmap");
- }
- }
-
- @Override
- protected boolean onBind(GLCanvas canvas) {
- updateContent(canvas);
- return isContentValid();
- }
-
- @Override
- protected int getTarget() {
- return GL11.GL_TEXTURE_2D;
- }
-
- public void setOpaque(boolean isOpaque) {
- mOpaque = isOpaque;
- }
-
- @Override
- public boolean isOpaque() {
- return mOpaque;
- }
-
- @Override
- public void recycle() {
- super.recycle();
- if (mBitmap != null) freeBitmap();
- }
-}
diff --git a/src/com/android/gallery3d/ingest/ImportTask.java b/src/com/android/gallery3d/ingest/ImportTask.java
deleted file mode 100644
index 7d2d641a5..000000000
--- a/src/com/android/gallery3d/ingest/ImportTask.java
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest;
-
-import android.content.Context;
-import android.mtp.MtpDevice;
-import android.mtp.MtpObjectInfo;
-import android.os.Environment;
-import android.os.PowerManager;
-
-import com.android.gallery3d.util.GalleryUtils;
-
-import java.io.File;
-import java.util.Collection;
-import java.util.LinkedList;
-import java.util.List;
-
-public class ImportTask implements Runnable {
-
- public interface Listener {
- void onImportProgress(int visitedCount, int totalCount, String pathIfSuccessful);
-
- void onImportFinish(Collection<MtpObjectInfo> objectsNotImported, int visitedCount);
- }
-
- static private final String WAKELOCK_LABEL = "MTP Import Task";
-
- private Listener mListener;
- private String mDestAlbumName;
- private Collection<MtpObjectInfo> mObjectsToImport;
- private MtpDevice mDevice;
- private PowerManager.WakeLock mWakeLock;
-
- public ImportTask(MtpDevice device, Collection<MtpObjectInfo> objectsToImport,
- String destAlbumName, Context context) {
- mDestAlbumName = destAlbumName;
- mObjectsToImport = objectsToImport;
- mDevice = device;
- PowerManager pm = (PowerManager) context.getSystemService(Context.POWER_SERVICE);
- mWakeLock = pm.newWakeLock(PowerManager.SCREEN_DIM_WAKE_LOCK, WAKELOCK_LABEL);
- }
-
- public void setListener(Listener listener) {
- mListener = listener;
- }
-
- @Override
- public void run() {
- mWakeLock.acquire();
- try {
- List<MtpObjectInfo> objectsNotImported = new LinkedList<MtpObjectInfo>();
- int visited = 0;
- int total = mObjectsToImport.size();
- mListener.onImportProgress(visited, total, null);
- File dest = new File(Environment.getExternalStorageDirectory(), mDestAlbumName);
- dest.mkdirs();
- for (MtpObjectInfo object : mObjectsToImport) {
- visited++;
- String importedPath = null;
- if (GalleryUtils.hasSpaceForSize(object.getCompressedSize())) {
- importedPath = new File(dest, object.getName()).getAbsolutePath();
- if (!mDevice.importFile(object.getObjectHandle(), importedPath)) {
- importedPath = null;
- }
- }
- if (importedPath == null) {
- objectsNotImported.add(object);
- }
- if (mListener != null) {
- mListener.onImportProgress(visited, total, importedPath);
- }
- }
- if (mListener != null) {
- mListener.onImportFinish(objectsNotImported, visited);
- }
- } finally {
- mListener = null;
- mWakeLock.release();
- }
- }
-}
diff --git a/src/com/android/gallery3d/ingest/IngestActivity.java b/src/com/android/gallery3d/ingest/IngestActivity.java
deleted file mode 100644
index 687e9fd44..000000000
--- a/src/com/android/gallery3d/ingest/IngestActivity.java
+++ /dev/null
@@ -1,570 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest;
-
-import android.app.Activity;
-import android.app.ProgressDialog;
-import android.content.ComponentName;
-import android.content.Context;
-import android.content.Intent;
-import android.content.ServiceConnection;
-import android.content.res.Configuration;
-import android.database.DataSetObserver;
-import android.mtp.MtpObjectInfo;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.IBinder;
-import android.os.Message;
-import android.support.v4.view.ViewPager;
-import android.util.SparseBooleanArray;
-import android.view.ActionMode;
-import android.view.Menu;
-import android.view.MenuInflater;
-import android.view.MenuItem;
-import android.view.View;
-import android.widget.AbsListView.MultiChoiceModeListener;
-import android.widget.AdapterView;
-import android.widget.AdapterView.OnItemClickListener;
-import android.widget.TextView;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.ingest.adapter.CheckBroker;
-import com.android.gallery3d.ingest.adapter.MtpAdapter;
-import com.android.gallery3d.ingest.adapter.MtpPagerAdapter;
-import com.android.gallery3d.ingest.data.MtpBitmapFetch;
-import com.android.gallery3d.ingest.ui.DateTileView;
-import com.android.gallery3d.ingest.ui.IngestGridView;
-import com.android.gallery3d.ingest.ui.IngestGridView.OnClearChoicesListener;
-
-import java.lang.ref.WeakReference;
-import java.util.Collection;
-
-public class IngestActivity extends Activity implements
- MtpDeviceIndex.ProgressListener, ImportTask.Listener {
-
- private IngestService mHelperService;
- private boolean mActive = false;
- private IngestGridView mGridView;
- private MtpAdapter mAdapter;
- private Handler mHandler;
- private ProgressDialog mProgressDialog;
- private ActionMode mActiveActionMode;
-
- private View mWarningView;
- private TextView mWarningText;
- private int mLastCheckedPosition = 0;
-
- private ViewPager mFullscreenPager;
- private MtpPagerAdapter mPagerAdapter;
- private boolean mFullscreenPagerVisible = false;
-
- private MenuItem mMenuSwitcherItem;
- private MenuItem mActionMenuSwitcherItem;
-
- // The MTP framework components don't give us fine-grained file copy
- // progress updates, so for large photos and videos, we will be stuck
- // with a dialog not updating for a long time. To give the user feedback,
- // we switch to the animated indeterminate progress bar after the timeout
- // specified by INDETERMINATE_SWITCH_TIMEOUT_MS. On the next update from
- // the framework, we switch back to the normal progress bar.
- private static final int INDETERMINATE_SWITCH_TIMEOUT_MS = 3000;
-
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- doBindHelperService();
-
- setContentView(R.layout.ingest_activity_item_list);
- mGridView = (IngestGridView) findViewById(R.id.ingest_gridview);
- mAdapter = new MtpAdapter(this);
- mAdapter.registerDataSetObserver(mMasterObserver);
- mGridView.setAdapter(mAdapter);
- mGridView.setMultiChoiceModeListener(mMultiChoiceModeListener);
- mGridView.setOnItemClickListener(mOnItemClickListener);
- mGridView.setOnClearChoicesListener(mPositionMappingCheckBroker);
-
- mFullscreenPager = (ViewPager) findViewById(R.id.ingest_view_pager);
-
- mHandler = new ItemListHandler(this);
-
- MtpBitmapFetch.configureForContext(this);
- }
-
- private OnItemClickListener mOnItemClickListener = new OnItemClickListener() {
- @Override
- public void onItemClick(AdapterView<?> adapterView, View itemView, int position, long arg3) {
- mLastCheckedPosition = position;
- mGridView.setItemChecked(position, !mGridView.getCheckedItemPositions().get(position));
- }
- };
-
- private MultiChoiceModeListener mMultiChoiceModeListener = new MultiChoiceModeListener() {
- private boolean mIgnoreItemCheckedStateChanges = false;
-
- private void updateSelectedTitle(ActionMode mode) {
- int count = mGridView.getCheckedItemCount();
- mode.setTitle(getResources().getQuantityString(
- R.plurals.number_of_items_selected, count, count));
- }
-
- @Override
- public void onItemCheckedStateChanged(ActionMode mode, int position, long id,
- boolean checked) {
- if (mIgnoreItemCheckedStateChanges) return;
- if (mAdapter.itemAtPositionIsBucket(position)) {
- SparseBooleanArray checkedItems = mGridView.getCheckedItemPositions();
- mIgnoreItemCheckedStateChanges = true;
- mGridView.setItemChecked(position, false);
-
- // Takes advantage of the fact that SectionIndexer imposes the
- // need to clamp to the valid range
- int nextSectionStart = mAdapter.getPositionForSection(
- mAdapter.getSectionForPosition(position) + 1);
- if (nextSectionStart == position)
- nextSectionStart = mAdapter.getCount();
-
- boolean rangeValue = false; // Value we want to set all of the bucket items to
-
- // Determine if all the items in the bucket are currently checked, so that we
- // can uncheck them, otherwise we will check all items in the bucket.
- for (int i = position + 1; i < nextSectionStart; i++) {
- if (checkedItems.get(i) == false) {
- rangeValue = true;
- break;
- }
- }
-
- // Set all items in the bucket to the desired state
- for (int i = position + 1; i < nextSectionStart; i++) {
- if (checkedItems.get(i) != rangeValue)
- mGridView.setItemChecked(i, rangeValue);
- }
-
- mPositionMappingCheckBroker.onBulkCheckedChange();
- mIgnoreItemCheckedStateChanges = false;
- } else {
- mPositionMappingCheckBroker.onCheckedChange(position, checked);
- }
- mLastCheckedPosition = position;
- updateSelectedTitle(mode);
- }
-
- @Override
- public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
- return onOptionsItemSelected(item);
- }
-
- @Override
- public boolean onCreateActionMode(ActionMode mode, Menu menu) {
- MenuInflater inflater = mode.getMenuInflater();
- inflater.inflate(R.menu.ingest_menu_item_list_selection, menu);
- updateSelectedTitle(mode);
- mActiveActionMode = mode;
- mActionMenuSwitcherItem = menu.findItem(R.id.ingest_switch_view);
- setSwitcherMenuState(mActionMenuSwitcherItem, mFullscreenPagerVisible);
- return true;
- }
-
- @Override
- public void onDestroyActionMode(ActionMode mode) {
- mActiveActionMode = null;
- mActionMenuSwitcherItem = null;
- mHandler.sendEmptyMessage(ItemListHandler.MSG_BULK_CHECKED_CHANGE);
- }
-
- @Override
- public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
- updateSelectedTitle(mode);
- return false;
- }
- };
-
- public boolean onOptionsItemSelected(MenuItem item) {
- switch (item.getItemId()) {
- case R.id.import_items:
- if (mActiveActionMode != null) {
- mHelperService.importSelectedItems(
- mGridView.getCheckedItemPositions(),
- mAdapter);
- mActiveActionMode.finish();
- }
- return true;
- case R.id.ingest_switch_view:
- setFullscreenPagerVisibility(!mFullscreenPagerVisible);
- return true;
- default:
- return false;
- }
- }
-
- @Override
- public boolean onCreateOptionsMenu(Menu menu) {
- MenuInflater inflater = getMenuInflater();
- inflater.inflate(R.menu.ingest_menu_item_list_selection, menu);
- mMenuSwitcherItem = menu.findItem(R.id.ingest_switch_view);
- menu.findItem(R.id.import_items).setVisible(false);
- setSwitcherMenuState(mMenuSwitcherItem, mFullscreenPagerVisible);
- return true;
- }
-
- @Override
- protected void onDestroy() {
- super.onDestroy();
- doUnbindHelperService();
- }
-
- @Override
- protected void onResume() {
- DateTileView.refreshLocale();
- mActive = true;
- if (mHelperService != null) mHelperService.setClientActivity(this);
- updateWarningView();
- super.onResume();
- }
-
- @Override
- protected void onPause() {
- if (mHelperService != null) mHelperService.setClientActivity(null);
- mActive = false;
- cleanupProgressDialog();
- super.onPause();
- }
-
- @Override
- public void onConfigurationChanged(Configuration newConfig) {
- super.onConfigurationChanged(newConfig);
- MtpBitmapFetch.configureForContext(this);
- }
-
- private void showWarningView(int textResId) {
- if (mWarningView == null) {
- mWarningView = findViewById(R.id.ingest_warning_view);
- mWarningText =
- (TextView)mWarningView.findViewById(R.id.ingest_warning_view_text);
- }
- mWarningText.setText(textResId);
- mWarningView.setVisibility(View.VISIBLE);
- setFullscreenPagerVisibility(false);
- mGridView.setVisibility(View.GONE);
- }
-
- private void hideWarningView() {
- if (mWarningView != null) {
- mWarningView.setVisibility(View.GONE);
- setFullscreenPagerVisibility(false);
- }
- }
-
- private PositionMappingCheckBroker mPositionMappingCheckBroker = new PositionMappingCheckBroker();
-
- private class PositionMappingCheckBroker extends CheckBroker
- implements OnClearChoicesListener {
- private int mLastMappingPager = -1;
- private int mLastMappingGrid = -1;
-
- private int mapPagerToGridPosition(int position) {
- if (position != mLastMappingPager) {
- mLastMappingPager = position;
- mLastMappingGrid = mAdapter.translatePositionWithoutLabels(position);
- }
- return mLastMappingGrid;
- }
-
- private int mapGridToPagerPosition(int position) {
- if (position != mLastMappingGrid) {
- mLastMappingGrid = position;
- mLastMappingPager = mPagerAdapter.translatePositionWithLabels(position);
- }
- return mLastMappingPager;
- }
-
- @Override
- public void setItemChecked(int position, boolean checked) {
- mGridView.setItemChecked(mapPagerToGridPosition(position), checked);
- }
-
- @Override
- public void onCheckedChange(int position, boolean checked) {
- if (mPagerAdapter != null) {
- super.onCheckedChange(mapGridToPagerPosition(position), checked);
- }
- }
-
- @Override
- public boolean isItemChecked(int position) {
- return mGridView.getCheckedItemPositions().get(mapPagerToGridPosition(position));
- }
-
- @Override
- public void onClearChoices() {
- onBulkCheckedChange();
- }
- };
-
- private DataSetObserver mMasterObserver = new DataSetObserver() {
- @Override
- public void onChanged() {
- if (mPagerAdapter != null) mPagerAdapter.notifyDataSetChanged();
- }
-
- @Override
- public void onInvalidated() {
- if (mPagerAdapter != null) mPagerAdapter.notifyDataSetChanged();
- }
- };
-
- private int pickFullscreenStartingPosition() {
- int firstVisiblePosition = mGridView.getFirstVisiblePosition();
- if (mLastCheckedPosition <= firstVisiblePosition
- || mLastCheckedPosition > mGridView.getLastVisiblePosition()) {
- return firstVisiblePosition;
- } else {
- return mLastCheckedPosition;
- }
- }
-
- private void setSwitcherMenuState(MenuItem menuItem, boolean inFullscreenMode) {
- if (menuItem == null) return;
- if (!inFullscreenMode) {
- menuItem.setIcon(android.R.drawable.ic_menu_zoom);
- menuItem.setTitle(R.string.switch_photo_fullscreen);
- } else {
- menuItem.setIcon(android.R.drawable.ic_dialog_dialer);
- menuItem.setTitle(R.string.switch_photo_grid);
- }
- }
-
- private void setFullscreenPagerVisibility(boolean visible) {
- mFullscreenPagerVisible = visible;
- if (visible) {
- if (mPagerAdapter == null) {
- mPagerAdapter = new MtpPagerAdapter(this, mPositionMappingCheckBroker);
- mPagerAdapter.setMtpDeviceIndex(mAdapter.getMtpDeviceIndex());
- }
- mFullscreenPager.setAdapter(mPagerAdapter);
- mFullscreenPager.setCurrentItem(mPagerAdapter.translatePositionWithLabels(
- pickFullscreenStartingPosition()), false);
- } else if (mPagerAdapter != null) {
- mGridView.setSelection(mAdapter.translatePositionWithoutLabels(
- mFullscreenPager.getCurrentItem()));
- mFullscreenPager.setAdapter(null);
- }
- mGridView.setVisibility(visible ? View.INVISIBLE : View.VISIBLE);
- mFullscreenPager.setVisibility(visible ? View.VISIBLE : View.INVISIBLE);
- if (mActionMenuSwitcherItem != null) {
- setSwitcherMenuState(mActionMenuSwitcherItem, visible);
- }
- setSwitcherMenuState(mMenuSwitcherItem, visible);
- }
-
- private void updateWarningView() {
- if (!mAdapter.deviceConnected()) {
- showWarningView(R.string.ingest_no_device);
- } else if (mAdapter.indexReady() && mAdapter.getCount() == 0) {
- showWarningView(R.string.ingest_empty_device);
- } else {
- hideWarningView();
- }
- }
-
- private void UiThreadNotifyIndexChanged() {
- mAdapter.notifyDataSetChanged();
- if (mActiveActionMode != null) {
- mActiveActionMode.finish();
- mActiveActionMode = null;
- }
- updateWarningView();
- }
-
- protected void notifyIndexChanged() {
- mHandler.sendEmptyMessage(ItemListHandler.MSG_NOTIFY_CHANGED);
- }
-
- private static class ProgressState {
- String message;
- String title;
- int current;
- int max;
-
- public void reset() {
- title = null;
- message = null;
- current = 0;
- max = 0;
- }
- }
-
- private ProgressState mProgressState = new ProgressState();
-
- @Override
- public void onObjectIndexed(MtpObjectInfo object, int numVisited) {
- // Not guaranteed to be called on the UI thread
- mProgressState.reset();
- mProgressState.max = 0;
- mProgressState.message = getResources().getQuantityString(
- R.plurals.ingest_number_of_items_scanned, numVisited, numVisited);
- mHandler.sendEmptyMessage(ItemListHandler.MSG_PROGRESS_UPDATE);
- }
-
- @Override
- public void onSorting() {
- // Not guaranteed to be called on the UI thread
- mProgressState.reset();
- mProgressState.max = 0;
- mProgressState.message = getResources().getString(R.string.ingest_sorting);
- mHandler.sendEmptyMessage(ItemListHandler.MSG_PROGRESS_UPDATE);
- }
-
- @Override
- public void onIndexFinish() {
- // Not guaranteed to be called on the UI thread
- mHandler.sendEmptyMessage(ItemListHandler.MSG_PROGRESS_HIDE);
- mHandler.sendEmptyMessage(ItemListHandler.MSG_NOTIFY_CHANGED);
- }
-
- @Override
- public void onImportProgress(final int visitedCount, final int totalCount,
- String pathIfSuccessful) {
- // Not guaranteed to be called on the UI thread
- mProgressState.reset();
- mProgressState.max = totalCount;
- mProgressState.current = visitedCount;
- mProgressState.title = getResources().getString(R.string.ingest_importing);
- mHandler.sendEmptyMessage(ItemListHandler.MSG_PROGRESS_UPDATE);
- mHandler.removeMessages(ItemListHandler.MSG_PROGRESS_INDETERMINATE);
- mHandler.sendEmptyMessageDelayed(ItemListHandler.MSG_PROGRESS_INDETERMINATE,
- INDETERMINATE_SWITCH_TIMEOUT_MS);
- }
-
- @Override
- public void onImportFinish(Collection<MtpObjectInfo> objectsNotImported,
- int numVisited) {
- // Not guaranteed to be called on the UI thread
- mHandler.sendEmptyMessage(ItemListHandler.MSG_PROGRESS_HIDE);
- mHandler.removeMessages(ItemListHandler.MSG_PROGRESS_INDETERMINATE);
- // TODO: maybe show an extra dialog listing the ones that failed
- // importing, if any?
- }
-
- private ProgressDialog getProgressDialog() {
- if (mProgressDialog == null || !mProgressDialog.isShowing()) {
- mProgressDialog = new ProgressDialog(this);
- mProgressDialog.setCancelable(false);
- }
- return mProgressDialog;
- }
-
- private void updateProgressDialog() {
- ProgressDialog dialog = getProgressDialog();
- boolean indeterminate = (mProgressState.max == 0);
- dialog.setIndeterminate(indeterminate);
- dialog.setProgressStyle(indeterminate ? ProgressDialog.STYLE_SPINNER
- : ProgressDialog.STYLE_HORIZONTAL);
- if (mProgressState.title != null) {
- dialog.setTitle(mProgressState.title);
- }
- if (mProgressState.message != null) {
- dialog.setMessage(mProgressState.message);
- }
- if (!indeterminate) {
- dialog.setProgress(mProgressState.current);
- dialog.setMax(mProgressState.max);
- }
- if (!dialog.isShowing()) {
- dialog.show();
- }
- }
-
- private void makeProgressDialogIndeterminate() {
- ProgressDialog dialog = getProgressDialog();
- dialog.setIndeterminate(true);
- }
-
- private void cleanupProgressDialog() {
- if (mProgressDialog != null) {
- mProgressDialog.hide();
- mProgressDialog = null;
- }
- }
-
- // This is static and uses a WeakReference in order to avoid leaking the Activity
- private static class ItemListHandler extends Handler {
- public static final int MSG_PROGRESS_UPDATE = 0;
- public static final int MSG_PROGRESS_HIDE = 1;
- public static final int MSG_NOTIFY_CHANGED = 2;
- public static final int MSG_BULK_CHECKED_CHANGE = 3;
- public static final int MSG_PROGRESS_INDETERMINATE = 4;
-
- WeakReference<IngestActivity> mParentReference;
-
- public ItemListHandler(IngestActivity parent) {
- super();
- mParentReference = new WeakReference<IngestActivity>(parent);
- }
-
- public void handleMessage(Message message) {
- IngestActivity parent = mParentReference.get();
- if (parent == null || !parent.mActive)
- return;
- switch (message.what) {
- case MSG_PROGRESS_HIDE:
- parent.cleanupProgressDialog();
- break;
- case MSG_PROGRESS_UPDATE:
- parent.updateProgressDialog();
- break;
- case MSG_NOTIFY_CHANGED:
- parent.UiThreadNotifyIndexChanged();
- break;
- case MSG_BULK_CHECKED_CHANGE:
- parent.mPositionMappingCheckBroker.onBulkCheckedChange();
- break;
- case MSG_PROGRESS_INDETERMINATE:
- parent.makeProgressDialogIndeterminate();
- break;
- default:
- break;
- }
- }
- }
-
- private ServiceConnection mHelperServiceConnection = new ServiceConnection() {
- public void onServiceConnected(ComponentName className, IBinder service) {
- mHelperService = ((IngestService.LocalBinder) service).getService();
- mHelperService.setClientActivity(IngestActivity.this);
- MtpDeviceIndex index = mHelperService.getIndex();
- mAdapter.setMtpDeviceIndex(index);
- if (mPagerAdapter != null) mPagerAdapter.setMtpDeviceIndex(index);
- }
-
- public void onServiceDisconnected(ComponentName className) {
- mHelperService = null;
- }
- };
-
- private void doBindHelperService() {
- bindService(new Intent(getApplicationContext(), IngestService.class),
- mHelperServiceConnection, Context.BIND_AUTO_CREATE);
- }
-
- private void doUnbindHelperService() {
- if (mHelperService != null) {
- mHelperService.setClientActivity(null);
- unbindService(mHelperServiceConnection);
- }
- }
-}
diff --git a/src/com/android/gallery3d/ingest/IngestService.java b/src/com/android/gallery3d/ingest/IngestService.java
deleted file mode 100644
index 0ce3ab6a9..000000000
--- a/src/com/android/gallery3d/ingest/IngestService.java
+++ /dev/null
@@ -1,320 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest;
-
-import android.app.NotificationManager;
-import android.app.PendingIntent;
-import android.app.Service;
-import android.content.Context;
-import android.content.Intent;
-import android.media.MediaScannerConnection;
-import android.media.MediaScannerConnection.MediaScannerConnectionClient;
-import android.mtp.MtpDevice;
-import android.mtp.MtpDeviceInfo;
-import android.mtp.MtpObjectInfo;
-import android.net.Uri;
-import android.os.Binder;
-import android.os.IBinder;
-import android.os.SystemClock;
-import android.support.v4.app.NotificationCompat;
-import android.util.SparseBooleanArray;
-import android.widget.Adapter;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.NotificationIds;
-import com.android.gallery3d.data.MtpClient;
-import com.android.gallery3d.util.BucketNames;
-import com.android.gallery3d.util.UsageStatistics;
-
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.List;
-
-public class IngestService extends Service implements ImportTask.Listener,
- MtpDeviceIndex.ProgressListener, MtpClient.Listener {
-
- public class LocalBinder extends Binder {
- IngestService getService() {
- return IngestService.this;
- }
- }
-
- private static final int PROGRESS_UPDATE_INTERVAL_MS = 180;
-
- private static MtpClient sClient;
-
- private final IBinder mBinder = new LocalBinder();
- private ScannerClient mScannerClient;
- private MtpDevice mDevice;
- private String mDevicePrettyName;
- private MtpDeviceIndex mIndex;
- private IngestActivity mClientActivity;
- private boolean mRedeliverImportFinish = false;
- private int mRedeliverImportFinishCount = 0;
- private Collection<MtpObjectInfo> mRedeliverObjectsNotImported;
- private boolean mRedeliverNotifyIndexChanged = false;
- private boolean mRedeliverIndexFinish = false;
- private NotificationManager mNotificationManager;
- private NotificationCompat.Builder mNotificationBuilder;
- private long mLastProgressIndexTime = 0;
- private boolean mNeedRelaunchNotification = false;
-
- @Override
- public void onCreate() {
- super.onCreate();
- mScannerClient = new ScannerClient(this);
- mNotificationManager = (NotificationManager) getSystemService(NOTIFICATION_SERVICE);
- mNotificationBuilder = new NotificationCompat.Builder(this);
- mNotificationBuilder.setSmallIcon(android.R.drawable.stat_notify_sync) // TODO drawable
- .setContentIntent(PendingIntent.getActivity(this, 0, new Intent(this, IngestActivity.class), 0));
- mIndex = MtpDeviceIndex.getInstance();
- mIndex.setProgressListener(this);
-
- if (sClient == null) {
- sClient = new MtpClient(getApplicationContext());
- }
- List<MtpDevice> devices = sClient.getDeviceList();
- if (devices.size() > 0) {
- setDevice(devices.get(0));
- }
- sClient.addListener(this);
- }
-
- @Override
- public void onDestroy() {
- sClient.removeListener(this);
- mIndex.unsetProgressListener(this);
- super.onDestroy();
- }
-
- @Override
- public IBinder onBind(Intent intent) {
- return mBinder;
- }
-
- private void setDevice(MtpDevice device) {
- if (mDevice == device) return;
- mRedeliverImportFinish = false;
- mRedeliverObjectsNotImported = null;
- mRedeliverNotifyIndexChanged = false;
- mRedeliverIndexFinish = false;
- mDevice = device;
- mIndex.setDevice(mDevice);
- if (mDevice != null) {
- MtpDeviceInfo deviceInfo = mDevice.getDeviceInfo();
- if (deviceInfo == null) {
- setDevice(null);
- return;
- } else {
- mDevicePrettyName = deviceInfo.getModel();
- mNotificationBuilder.setContentTitle(mDevicePrettyName);
- new Thread(mIndex.getIndexRunnable()).start();
- }
- } else {
- mDevicePrettyName = null;
- }
- if (mClientActivity != null) {
- mClientActivity.notifyIndexChanged();
- } else {
- mRedeliverNotifyIndexChanged = true;
- }
- }
-
- protected MtpDeviceIndex getIndex() {
- return mIndex;
- }
-
- protected void setClientActivity(IngestActivity activity) {
- if (mClientActivity == activity) return;
- mClientActivity = activity;
- if (mClientActivity == null) {
- if (mNeedRelaunchNotification) {
- mNotificationBuilder.setProgress(0, 0, false)
- .setContentText(getResources().getText(R.string.ingest_scanning_done));
- mNotificationManager.notify(NotificationIds.INGEST_NOTIFICATION_SCANNING,
- mNotificationBuilder.build());
- }
- return;
- }
- mNotificationManager.cancel(NotificationIds.INGEST_NOTIFICATION_IMPORTING);
- mNotificationManager.cancel(NotificationIds.INGEST_NOTIFICATION_SCANNING);
- if (mRedeliverImportFinish) {
- mClientActivity.onImportFinish(mRedeliverObjectsNotImported,
- mRedeliverImportFinishCount);
- mRedeliverImportFinish = false;
- mRedeliverObjectsNotImported = null;
- }
- if (mRedeliverNotifyIndexChanged) {
- mClientActivity.notifyIndexChanged();
- mRedeliverNotifyIndexChanged = false;
- }
- if (mRedeliverIndexFinish) {
- mClientActivity.onIndexFinish();
- mRedeliverIndexFinish = false;
- }
- }
-
- protected void importSelectedItems(SparseBooleanArray selected, Adapter adapter) {
- List<MtpObjectInfo> importHandles = new ArrayList<MtpObjectInfo>();
- for (int i = 0; i < selected.size(); i++) {
- if (selected.valueAt(i)) {
- Object item = adapter.getItem(selected.keyAt(i));
- if (item instanceof MtpObjectInfo) {
- importHandles.add(((MtpObjectInfo) item));
- }
- }
- }
- ImportTask task = new ImportTask(mDevice, importHandles, BucketNames.IMPORTED, this);
- task.setListener(this);
- mNotificationBuilder.setProgress(0, 0, true)
- .setContentText(getResources().getText(R.string.ingest_importing));
- startForeground(NotificationIds.INGEST_NOTIFICATION_IMPORTING,
- mNotificationBuilder.build());
- new Thread(task).start();
- }
-
- @Override
- public void deviceAdded(MtpDevice device) {
- if (mDevice == null) {
- setDevice(device);
- UsageStatistics.onEvent(UsageStatistics.COMPONENT_IMPORTER,
- "DeviceConnected", null);
- }
- }
-
- @Override
- public void deviceRemoved(MtpDevice device) {
- if (device == mDevice) {
- setDevice(null);
- mNeedRelaunchNotification = false;
- mNotificationManager.cancel(NotificationIds.INGEST_NOTIFICATION_SCANNING);
- }
- }
-
- @Override
- public void onImportProgress(int visitedCount, int totalCount,
- String pathIfSuccessful) {
- if (pathIfSuccessful != null) {
- mScannerClient.scanPath(pathIfSuccessful);
- }
- mNeedRelaunchNotification = false;
- if (mClientActivity != null) {
- mClientActivity.onImportProgress(visitedCount, totalCount, pathIfSuccessful);
- }
- mNotificationBuilder.setProgress(totalCount, visitedCount, false)
- .setContentText(getResources().getText(R.string.ingest_importing));
- mNotificationManager.notify(NotificationIds.INGEST_NOTIFICATION_IMPORTING,
- mNotificationBuilder.build());
- }
-
- @Override
- public void onImportFinish(Collection<MtpObjectInfo> objectsNotImported,
- int visitedCount) {
- stopForeground(true);
- mNeedRelaunchNotification = true;
- if (mClientActivity != null) {
- mClientActivity.onImportFinish(objectsNotImported, visitedCount);
- } else {
- mRedeliverImportFinish = true;
- mRedeliverObjectsNotImported = objectsNotImported;
- mRedeliverImportFinishCount = visitedCount;
- mNotificationBuilder.setProgress(0, 0, false)
- .setContentText(getResources().getText(R.string.import_complete));
- mNotificationManager.notify(NotificationIds.INGEST_NOTIFICATION_IMPORTING,
- mNotificationBuilder.build());
- }
- UsageStatistics.onEvent(UsageStatistics.COMPONENT_IMPORTER,
- "ImportFinished", null, visitedCount);
- }
-
- @Override
- public void onObjectIndexed(MtpObjectInfo object, int numVisited) {
- mNeedRelaunchNotification = false;
- if (mClientActivity != null) {
- mClientActivity.onObjectIndexed(object, numVisited);
- } else {
- // Throttle the updates to one every PROGRESS_UPDATE_INTERVAL_MS milliseconds
- long currentTime = SystemClock.uptimeMillis();
- if (currentTime > mLastProgressIndexTime + PROGRESS_UPDATE_INTERVAL_MS) {
- mLastProgressIndexTime = currentTime;
- mNotificationBuilder.setProgress(0, numVisited, true)
- .setContentText(getResources().getText(R.string.ingest_scanning));
- mNotificationManager.notify(NotificationIds.INGEST_NOTIFICATION_SCANNING,
- mNotificationBuilder.build());
- }
- }
- }
-
- @Override
- public void onSorting() {
- if (mClientActivity != null) mClientActivity.onSorting();
- }
-
- @Override
- public void onIndexFinish() {
- mNeedRelaunchNotification = true;
- if (mClientActivity != null) {
- mClientActivity.onIndexFinish();
- } else {
- mNotificationBuilder.setProgress(0, 0, false)
- .setContentText(getResources().getText(R.string.ingest_scanning_done));
- mNotificationManager.notify(NotificationIds.INGEST_NOTIFICATION_SCANNING,
- mNotificationBuilder.build());
- mRedeliverIndexFinish = true;
- }
- }
-
- // Copied from old Gallery3d code
- private static final class ScannerClient implements MediaScannerConnectionClient {
- ArrayList<String> mPaths = new ArrayList<String>();
- MediaScannerConnection mScannerConnection;
- boolean mConnected;
- Object mLock = new Object();
-
- public ScannerClient(Context context) {
- mScannerConnection = new MediaScannerConnection(context, this);
- }
-
- public void scanPath(String path) {
- synchronized (mLock) {
- if (mConnected) {
- mScannerConnection.scanFile(path, null);
- } else {
- mPaths.add(path);
- mScannerConnection.connect();
- }
- }
- }
-
- @Override
- public void onMediaScannerConnected() {
- synchronized (mLock) {
- mConnected = true;
- if (!mPaths.isEmpty()) {
- for (String path : mPaths) {
- mScannerConnection.scanFile(path, null);
- }
- mPaths.clear();
- }
- }
- }
-
- @Override
- public void onScanCompleted(String path, Uri uri) {
- }
- }
-}
diff --git a/src/com/android/gallery3d/ingest/MtpDeviceIndex.java b/src/com/android/gallery3d/ingest/MtpDeviceIndex.java
deleted file mode 100644
index d30f94a87..000000000
--- a/src/com/android/gallery3d/ingest/MtpDeviceIndex.java
+++ /dev/null
@@ -1,596 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest;
-
-import android.mtp.MtpConstants;
-import android.mtp.MtpDevice;
-import android.mtp.MtpObjectInfo;
-
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Collection;
-import java.util.Collections;
-import java.util.Comparator;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-import java.util.Stack;
-
-/**
- * MTP objects in the index are organized into "buckets," or groupings.
- * At present, these buckets are based on the date an item was created.
- *
- * When the index is created, the buckets are sorted in their natural
- * order, and the items within the buckets sorted by the date they are taken.
- *
- * The index enables the access of items and bucket labels as one unified list.
- * For example, let's say we have the following data in the index:
- * [Bucket A]: [photo 1], [photo 2]
- * [Bucket B]: [photo 3]
- *
- * Then the items can be thought of as being organized as a 5 element list:
- * [Bucket A], [photo 1], [photo 2], [Bucket B], [photo 3]
- *
- * The data can also be accessed in descending order, in which case the list
- * would be a bit different from simply reversing the ascending list, since the
- * bucket labels need to always be at the beginning:
- * [Bucket B], [photo 3], [Bucket A], [photo 2], [photo 1]
- *
- * The index enables all the following operations in constant time, both for
- * ascending and descending views of the data:
- * - get/getAscending/getDescending: get an item at a specified list position
- * - size: get the total number of items (bucket labels and MTP objects)
- * - getFirstPositionForBucketNumber
- * - getBucketNumberForPosition
- * - isFirstInBucket
- *
- * See the comments in buildLookupIndex for implementation notes.
- */
-public class MtpDeviceIndex {
-
- public static final int FORMAT_MOV = 0x300D; // For some reason this is not in MtpConstants
-
- public static final Set<Integer> SUPPORTED_IMAGE_FORMATS;
- public static final Set<Integer> SUPPORTED_VIDEO_FORMATS;
-
- static {
- SUPPORTED_IMAGE_FORMATS = new HashSet<Integer>();
- SUPPORTED_IMAGE_FORMATS.add(MtpConstants.FORMAT_JFIF);
- SUPPORTED_IMAGE_FORMATS.add(MtpConstants.FORMAT_EXIF_JPEG);
- SUPPORTED_IMAGE_FORMATS.add(MtpConstants.FORMAT_PNG);
- SUPPORTED_IMAGE_FORMATS.add(MtpConstants.FORMAT_GIF);
- SUPPORTED_IMAGE_FORMATS.add(MtpConstants.FORMAT_BMP);
-
- SUPPORTED_VIDEO_FORMATS = new HashSet<Integer>();
- SUPPORTED_VIDEO_FORMATS.add(MtpConstants.FORMAT_3GP_CONTAINER);
- SUPPORTED_VIDEO_FORMATS.add(MtpConstants.FORMAT_AVI);
- SUPPORTED_VIDEO_FORMATS.add(MtpConstants.FORMAT_MP4_CONTAINER);
- SUPPORTED_VIDEO_FORMATS.add(MtpConstants.FORMAT_MPEG);
- // TODO: add FORMAT_MOV once Media Scanner supports .mov files
- }
-
- @Override
- public int hashCode() {
- final int prime = 31;
- int result = 1;
- result = prime * result + ((mDevice == null) ? 0 : mDevice.getDeviceId());
- result = prime * result + mGeneration;
- return result;
- }
-
- public interface ProgressListener {
- public void onObjectIndexed(MtpObjectInfo object, int numVisited);
-
- public void onSorting();
-
- public void onIndexFinish();
- }
-
- public enum SortOrder {
- Ascending, Descending
- }
-
- private MtpDevice mDevice;
- private int[] mUnifiedLookupIndex;
- private MtpObjectInfo[] mMtpObjects;
- private DateBucket[] mBuckets;
- private int mGeneration = 0;
-
- public enum Progress {
- Uninitialized, Initialized, Pending, Started, Sorting, Finished
- }
-
- private Progress mProgress = Progress.Uninitialized;
- private ProgressListener mProgressListener;
-
- private static final MtpDeviceIndex sInstance = new MtpDeviceIndex();
- private static final MtpObjectTimestampComparator sMtpObjectComparator =
- new MtpObjectTimestampComparator();
-
- public static MtpDeviceIndex getInstance() {
- return sInstance;
- }
-
- private MtpDeviceIndex() {
- }
-
- synchronized public MtpDevice getDevice() {
- return mDevice;
- }
-
- /**
- * Sets the MtpDevice that should be indexed and initializes state, but does
- * not kick off the actual indexing task, which is instead done by using
- * {@link #getIndexRunnable()}
- *
- * @param device The MtpDevice that should be indexed
- */
- synchronized public void setDevice(MtpDevice device) {
- if (device == mDevice) return;
- mDevice = device;
- resetState();
- }
-
- /**
- * Provides a Runnable for the indexing task assuming the state has already
- * been correctly initialized (by calling {@link #setDevice(MtpDevice)}) and
- * has not already been run.
- *
- * @return Runnable for the main indexing task
- */
- synchronized public Runnable getIndexRunnable() {
- if (mProgress != Progress.Initialized) return null;
- mProgress = Progress.Pending;
- return new IndexRunnable(mDevice);
- }
-
- synchronized public boolean indexReady() {
- return mProgress == Progress.Finished;
- }
-
- synchronized public Progress getProgress() {
- return mProgress;
- }
-
- /**
- * @param listener Listener to change to
- * @return Progress at the time the listener was added (useful for
- * configuring initial UI state)
- */
- synchronized public Progress setProgressListener(ProgressListener listener) {
- mProgressListener = listener;
- return mProgress;
- }
-
- /**
- * Make the listener null if it matches the argument
- *
- * @param listener Listener to unset, if currently registered
- */
- synchronized public void unsetProgressListener(ProgressListener listener) {
- if (mProgressListener == listener)
- mProgressListener = null;
- }
-
- /**
- * @return The total number of elements in the index (labels and items)
- */
- public int size() {
- return mProgress == Progress.Finished ? mUnifiedLookupIndex.length : 0;
- }
-
- /**
- * @param position Index of item to fetch, where 0 is the first item in the
- * specified order
- * @param order
- * @return the bucket label or MtpObjectInfo at the specified position and
- * order
- */
- public Object get(int position, SortOrder order) {
- if (mProgress != Progress.Finished) return null;
- if(order == SortOrder.Ascending) {
- DateBucket bucket = mBuckets[mUnifiedLookupIndex[position]];
- if (bucket.unifiedStartIndex == position) {
- return bucket.bucket;
- } else {
- return mMtpObjects[bucket.itemsStartIndex + position - 1
- - bucket.unifiedStartIndex];
- }
- } else {
- int zeroIndex = mUnifiedLookupIndex.length - 1 - position;
- DateBucket bucket = mBuckets[mUnifiedLookupIndex[zeroIndex]];
- if (bucket.unifiedEndIndex == zeroIndex) {
- return bucket.bucket;
- } else {
- return mMtpObjects[bucket.itemsStartIndex + zeroIndex
- - bucket.unifiedStartIndex];
- }
- }
- }
-
- /**
- * @param position Index of item to fetch from a view of the data that doesn't
- * include labels and is in the specified order
- * @return position-th item in specified order, when not including labels
- */
- public MtpObjectInfo getWithoutLabels(int position, SortOrder order) {
- if (mProgress != Progress.Finished) return null;
- if (order == SortOrder.Ascending) {
- return mMtpObjects[position];
- } else {
- return mMtpObjects[mMtpObjects.length - 1 - position];
- }
- }
-
- /**
- * Although this is O(log(number of buckets)), and thus should not be used
- * in hotspots, even if the attached device has items for every day for
- * a five-year timeframe, it would still only take 11 iterations at most,
- * so shouldn't be a huge issue.
- * @param position Index of item to map from a view of the data that doesn't
- * include labels and is in the specified order
- * @param order
- * @return position in a view of the data that does include labels
- */
- public int getPositionFromPositionWithoutLabels(int position, SortOrder order) {
- if (mProgress != Progress.Finished) return -1;
- if (order == SortOrder.Descending) {
- position = mMtpObjects.length - 1 - position;
- }
- int bucketNumber = 0;
- int iMin = 0;
- int iMax = mBuckets.length - 1;
- while (iMax >= iMin) {
- int iMid = (iMax + iMin) / 2;
- if (mBuckets[iMid].itemsStartIndex + mBuckets[iMid].numItems <= position) {
- iMin = iMid + 1;
- } else if (mBuckets[iMid].itemsStartIndex > position) {
- iMax = iMid - 1;
- } else {
- bucketNumber = iMid;
- break;
- }
- }
- int mappedPos = mBuckets[bucketNumber].unifiedStartIndex
- + position - mBuckets[bucketNumber].itemsStartIndex;
- if (order == SortOrder.Descending) {
- mappedPos = mUnifiedLookupIndex.length - 1 - mappedPos;
- }
- return mappedPos;
- }
-
- public int getPositionWithoutLabelsFromPosition(int position, SortOrder order) {
- if (mProgress != Progress.Finished) return -1;
- if(order == SortOrder.Ascending) {
- DateBucket bucket = mBuckets[mUnifiedLookupIndex[position]];
- if (bucket.unifiedStartIndex == position) position++;
- return bucket.itemsStartIndex + position - 1 - bucket.unifiedStartIndex;
- } else {
- int zeroIndex = mUnifiedLookupIndex.length - 1 - position;
- DateBucket bucket = mBuckets[mUnifiedLookupIndex[zeroIndex]];
- if (bucket.unifiedEndIndex == zeroIndex) zeroIndex--;
- return mMtpObjects.length - 1 - bucket.itemsStartIndex
- - zeroIndex + bucket.unifiedStartIndex;
- }
- }
-
- /**
- * @return The number of MTP items in the index (without labels)
- */
- public int sizeWithoutLabels() {
- return mProgress == Progress.Finished ? mMtpObjects.length : 0;
- }
-
- public int getFirstPositionForBucketNumber(int bucketNumber, SortOrder order) {
- if (order == SortOrder.Ascending) {
- return mBuckets[bucketNumber].unifiedStartIndex;
- } else {
- return mUnifiedLookupIndex.length - mBuckets[mBuckets.length - 1 - bucketNumber].unifiedEndIndex - 1;
- }
- }
-
- public int getBucketNumberForPosition(int position, SortOrder order) {
- if (order == SortOrder.Ascending) {
- return mUnifiedLookupIndex[position];
- } else {
- return mBuckets.length - 1 - mUnifiedLookupIndex[mUnifiedLookupIndex.length - 1 - position];
- }
- }
-
- public boolean isFirstInBucket(int position, SortOrder order) {
- if (order == SortOrder.Ascending) {
- return mBuckets[mUnifiedLookupIndex[position]].unifiedStartIndex == position;
- } else {
- position = mUnifiedLookupIndex.length - 1 - position;
- return mBuckets[mUnifiedLookupIndex[position]].unifiedEndIndex == position;
- }
- }
-
- private Object[] mCachedReverseBuckets;
-
- public Object[] getBuckets(SortOrder order) {
- if (mBuckets == null) return null;
- if (order == SortOrder.Ascending) {
- return mBuckets;
- } else {
- if (mCachedReverseBuckets == null) {
- computeReversedBuckets();
- }
- return mCachedReverseBuckets;
- }
- }
-
- /*
- * See the comments for buildLookupIndex for notes on the specific fields of
- * this class.
- */
- private class DateBucket implements Comparable<DateBucket> {
- SimpleDate bucket;
- List<MtpObjectInfo> tempElementsList = new ArrayList<MtpObjectInfo>();
- int unifiedStartIndex;
- int unifiedEndIndex;
- int itemsStartIndex;
- int numItems;
-
- public DateBucket(SimpleDate bucket) {
- this.bucket = bucket;
- }
-
- public DateBucket(SimpleDate bucket, MtpObjectInfo firstElement) {
- this(bucket);
- tempElementsList.add(firstElement);
- }
-
- void sortElements(Comparator<MtpObjectInfo> comparator) {
- Collections.sort(tempElementsList, comparator);
- }
-
- @Override
- public String toString() {
- return bucket.toString();
- }
-
- @Override
- public int hashCode() {
- return bucket.hashCode();
- }
-
- @Override
- public boolean equals(Object obj) {
- if (this == obj) return true;
- if (obj == null) return false;
- if (!(obj instanceof DateBucket)) return false;
- DateBucket other = (DateBucket) obj;
- if (bucket == null) {
- if (other.bucket != null) return false;
- } else if (!bucket.equals(other.bucket)) {
- return false;
- }
- return true;
- }
-
- @Override
- public int compareTo(DateBucket another) {
- return this.bucket.compareTo(another.bucket);
- }
- }
-
- /**
- * Comparator to sort MtpObjectInfo objects by date created.
- */
- private static class MtpObjectTimestampComparator implements Comparator<MtpObjectInfo> {
- @Override
- public int compare(MtpObjectInfo o1, MtpObjectInfo o2) {
- long diff = o1.getDateCreated() - o2.getDateCreated();
- if (diff < 0) {
- return -1;
- } else if (diff == 0) {
- return 0;
- } else {
- return 1;
- }
- }
- }
-
- private void resetState() {
- mGeneration++;
- mUnifiedLookupIndex = null;
- mMtpObjects = null;
- mBuckets = null;
- mCachedReverseBuckets = null;
- mProgress = (mDevice == null) ? Progress.Uninitialized : Progress.Initialized;
- }
-
-
- private class IndexRunnable implements Runnable {
- private int[] mUnifiedLookupIndex;
- private MtpObjectInfo[] mMtpObjects;
- private DateBucket[] mBuckets;
- private Map<SimpleDate, DateBucket> mBucketsTemp;
- private MtpDevice mDevice;
- private int mNumObjects = 0;
-
- private class IndexingException extends Exception {};
-
- public IndexRunnable(MtpDevice device) {
- mDevice = device;
- }
-
- /*
- * Implementation note: this is the way the index supports a lot of its operations in
- * constant time and respecting the need to have bucket names always come before items
- * in that bucket when accessing the list sequentially, both in ascending and descending
- * orders.
- *
- * Let's say the data we have in the index is the following:
- * [Bucket A]: [photo 1], [photo 2]
- * [Bucket B]: [photo 3]
- *
- * In this case, the lookup index array would be
- * [0, 0, 0, 1, 1]
- *
- * Now, whether we access the list in ascending or descending order, we know which bucket
- * to look in (0 corresponds to A and 1 to B), and can return the bucket label as the first
- * item in a bucket as needed. The individual IndexBUckets have a startIndex and endIndex
- * that correspond to indices in this lookup index array, allowing us to calculate the
- * offset of the specific item we want from within a specific bucket.
- */
- private void buildLookupIndex() {
- int numBuckets = mBuckets.length;
- mUnifiedLookupIndex = new int[mNumObjects + numBuckets];
- int currentUnifiedIndexEntry = 0;
- int nextUnifiedEntry;
-
- mMtpObjects = new MtpObjectInfo[mNumObjects];
- int currentItemsEntry = 0;
- for (int i = 0; i < numBuckets; i++) {
- DateBucket bucket = mBuckets[i];
- nextUnifiedEntry = currentUnifiedIndexEntry + bucket.tempElementsList.size() + 1;
- Arrays.fill(mUnifiedLookupIndex, currentUnifiedIndexEntry, nextUnifiedEntry, i);
- bucket.unifiedStartIndex = currentUnifiedIndexEntry;
- bucket.unifiedEndIndex = nextUnifiedEntry - 1;
- currentUnifiedIndexEntry = nextUnifiedEntry;
-
- bucket.itemsStartIndex = currentItemsEntry;
- bucket.numItems = bucket.tempElementsList.size();
- for (int j = 0; j < bucket.numItems; j++) {
- mMtpObjects[currentItemsEntry] = bucket.tempElementsList.get(j);
- currentItemsEntry++;
- }
- bucket.tempElementsList = null;
- }
- }
-
- private void copyResults() {
- MtpDeviceIndex.this.mUnifiedLookupIndex = mUnifiedLookupIndex;
- MtpDeviceIndex.this.mMtpObjects = mMtpObjects;
- MtpDeviceIndex.this.mBuckets = mBuckets;
- mUnifiedLookupIndex = null;
- mMtpObjects = null;
- mBuckets = null;
- }
-
- @Override
- public void run() {
- try {
- indexDevice();
- } catch (IndexingException e) {
- synchronized (MtpDeviceIndex.this) {
- resetState();
- if (mProgressListener != null) {
- mProgressListener.onIndexFinish();
- }
- }
- }
- }
-
- private void indexDevice() throws IndexingException {
- synchronized (MtpDeviceIndex.this) {
- mProgress = Progress.Started;
- }
- mBucketsTemp = new HashMap<SimpleDate, DateBucket>();
- for (int storageId : mDevice.getStorageIds()) {
- if (mDevice != getDevice()) throw new IndexingException();
- Stack<Integer> pendingDirectories = new Stack<Integer>();
- pendingDirectories.add(0xFFFFFFFF); // start at the root of the device
- while (!pendingDirectories.isEmpty()) {
- if (mDevice != getDevice()) throw new IndexingException();
- int dirHandle = pendingDirectories.pop();
- for (int objectHandle : mDevice.getObjectHandles(storageId, 0, dirHandle)) {
- MtpObjectInfo objectInfo = mDevice.getObjectInfo(objectHandle);
- if (objectInfo == null) throw new IndexingException();
- int format = objectInfo.getFormat();
- if (format == MtpConstants.FORMAT_ASSOCIATION) {
- pendingDirectories.add(objectHandle);
- } else if (SUPPORTED_IMAGE_FORMATS.contains(format)
- || SUPPORTED_VIDEO_FORMATS.contains(format)) {
- addObject(objectInfo);
- }
- }
- }
- }
- Collection<DateBucket> values = mBucketsTemp.values();
- mBucketsTemp = null;
- mBuckets = values.toArray(new DateBucket[values.size()]);
- values = null;
- synchronized (MtpDeviceIndex.this) {
- mProgress = Progress.Sorting;
- if (mProgressListener != null) {
- mProgressListener.onSorting();
- }
- }
- sortAll();
- buildLookupIndex();
- synchronized (MtpDeviceIndex.this) {
- if (mDevice != getDevice()) throw new IndexingException();
- copyResults();
-
- /*
- * In order for getBuckets to operate in constant time for descending
- * order, we must precompute a reversed array of the buckets, mainly
- * because the android.widget.SectionIndexer interface which adapters
- * that call getBuckets implement depends on section numbers to be
- * ascending relative to the scroll position, so we must have this for
- * descending order or the scrollbar goes crazy.
- */
- computeReversedBuckets();
-
- mProgress = Progress.Finished;
- if (mProgressListener != null) {
- mProgressListener.onIndexFinish();
- }
- }
- }
-
- private SimpleDate mDateInstance = new SimpleDate();
-
- private void addObject(MtpObjectInfo objectInfo) {
- mNumObjects++;
- mDateInstance.setTimestamp(objectInfo.getDateCreated());
- DateBucket bucket = mBucketsTemp.get(mDateInstance);
- if (bucket == null) {
- bucket = new DateBucket(mDateInstance, objectInfo);
- mBucketsTemp.put(mDateInstance, bucket);
- mDateInstance = new SimpleDate(); // only create new date
- // objects when they are used
- return;
- } else {
- bucket.tempElementsList.add(objectInfo);
- }
- if (mProgressListener != null) {
- mProgressListener.onObjectIndexed(objectInfo, mNumObjects);
- }
- }
-
- private void sortAll() {
- Arrays.sort(mBuckets);
- for (DateBucket bucket : mBuckets) {
- bucket.sortElements(sMtpObjectComparator);
- }
- }
-
- }
-
- private void computeReversedBuckets() {
- mCachedReverseBuckets = new Object[mBuckets.length];
- for (int i = 0; i < mCachedReverseBuckets.length; i++) {
- mCachedReverseBuckets[i] = mBuckets[mBuckets.length - 1 - i];
- }
- }
-}
diff --git a/src/com/android/gallery3d/ingest/SimpleDate.java b/src/com/android/gallery3d/ingest/SimpleDate.java
deleted file mode 100644
index 05db2cde2..000000000
--- a/src/com/android/gallery3d/ingest/SimpleDate.java
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest;
-
-import java.text.DateFormat;
-import java.util.Calendar;
-
-/**
- * Represents a date (year, month, day)
- */
-public class SimpleDate implements Comparable<SimpleDate> {
- public int month; // MM
- public int day; // DD
- public int year; // YYYY
- private long timestamp;
- private String mCachedStringRepresentation;
-
- public SimpleDate() {
- }
-
- public SimpleDate(long timestamp) {
- setTimestamp(timestamp);
- }
-
- private static Calendar sCalendarInstance = Calendar.getInstance();
-
- public void setTimestamp(long timestamp) {
- synchronized (sCalendarInstance) {
- // TODO find a more efficient way to convert a timestamp to a date?
- sCalendarInstance.setTimeInMillis(timestamp);
- this.day = sCalendarInstance.get(Calendar.DATE);
- this.month = sCalendarInstance.get(Calendar.MONTH);
- this.year = sCalendarInstance.get(Calendar.YEAR);
- this.timestamp = timestamp;
- mCachedStringRepresentation = DateFormat.getDateInstance(DateFormat.SHORT).format(timestamp);
- }
- }
-
- @Override
- public int hashCode() {
- final int prime = 31;
- int result = 1;
- result = prime * result + day;
- result = prime * result + month;
- result = prime * result + year;
- return result;
- }
-
- @Override
- public boolean equals(Object obj) {
- if (this == obj)
- return true;
- if (obj == null)
- return false;
- if (!(obj instanceof SimpleDate))
- return false;
- SimpleDate other = (SimpleDate) obj;
- if (year != other.year)
- return false;
- if (month != other.month)
- return false;
- if (day != other.day)
- return false;
- return true;
- }
-
- @Override
- public int compareTo(SimpleDate other) {
- int yearDiff = this.year - other.getYear();
- if (yearDiff != 0)
- return yearDiff;
- else {
- int monthDiff = this.month - other.getMonth();
- if (monthDiff != 0)
- return monthDiff;
- else
- return this.day - other.getDay();
- }
- }
-
- public int getDay() {
- return day;
- }
-
- public int getMonth() {
- return month;
- }
-
- public int getYear() {
- return year;
- }
-
- @Override
- public String toString() {
- if (mCachedStringRepresentation == null) {
- mCachedStringRepresentation = DateFormat.getDateInstance(DateFormat.SHORT).format(timestamp);
- }
- return mCachedStringRepresentation;
- }
-}
diff --git a/src/com/android/gallery3d/ingest/adapter/CheckBroker.java b/src/com/android/gallery3d/ingest/adapter/CheckBroker.java
deleted file mode 100644
index 6783f23c5..000000000
--- a/src/com/android/gallery3d/ingest/adapter/CheckBroker.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest.adapter;
-
-import java.util.ArrayList;
-import java.util.Collection;
-
-public abstract class CheckBroker {
- private Collection<OnCheckedChangedListener> mListeners =
- new ArrayList<OnCheckedChangedListener>();
-
- public interface OnCheckedChangedListener {
- public void onCheckedChanged(int position, boolean isChecked);
- public void onBulkCheckedChanged();
- }
-
- public abstract void setItemChecked(int position, boolean checked);
-
- public void onCheckedChange(int position, boolean checked) {
- if (isItemChecked(position) != checked) {
- for (OnCheckedChangedListener l : mListeners) {
- l.onCheckedChanged(position, checked);
- }
- }
- }
-
- public void onBulkCheckedChange() {
- for (OnCheckedChangedListener l : mListeners) {
- l.onBulkCheckedChanged();
- }
- }
-
- public abstract boolean isItemChecked(int position);
-
- public void registerOnCheckedChangeListener(OnCheckedChangedListener l) {
- mListeners.add(l);
- }
-
- public void unregisterOnCheckedChangeListener(OnCheckedChangedListener l) {
- mListeners.remove(l);
- }
-}
diff --git a/src/com/android/gallery3d/ingest/adapter/MtpAdapter.java b/src/com/android/gallery3d/ingest/adapter/MtpAdapter.java
deleted file mode 100644
index e8dd69f8c..000000000
--- a/src/com/android/gallery3d/ingest/adapter/MtpAdapter.java
+++ /dev/null
@@ -1,192 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest.adapter;
-
-import android.app.Activity;
-import android.content.Context;
-import android.mtp.MtpObjectInfo;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.BaseAdapter;
-import android.widget.SectionIndexer;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.ingest.MtpDeviceIndex;
-import com.android.gallery3d.ingest.MtpDeviceIndex.SortOrder;
-import com.android.gallery3d.ingest.SimpleDate;
-import com.android.gallery3d.ingest.ui.DateTileView;
-import com.android.gallery3d.ingest.ui.MtpThumbnailTileView;
-
-public class MtpAdapter extends BaseAdapter implements SectionIndexer {
- public static final int ITEM_TYPE_MEDIA = 0;
- public static final int ITEM_TYPE_BUCKET = 1;
-
- private Context mContext;
- private MtpDeviceIndex mModel;
- private SortOrder mSortOrder = SortOrder.Descending;
- private LayoutInflater mInflater;
- private int mGeneration = 0;
-
- public MtpAdapter(Activity context) {
- super();
- mContext = context;
- mInflater = LayoutInflater.from(context);
- }
-
- public void setMtpDeviceIndex(MtpDeviceIndex index) {
- mModel = index;
- notifyDataSetChanged();
- }
-
- public MtpDeviceIndex getMtpDeviceIndex() {
- return mModel;
- }
-
- @Override
- public void notifyDataSetChanged() {
- mGeneration++;
- super.notifyDataSetChanged();
- }
-
- @Override
- public void notifyDataSetInvalidated() {
- mGeneration++;
- super.notifyDataSetInvalidated();
- }
-
- public boolean deviceConnected() {
- return (mModel != null) && (mModel.getDevice() != null);
- }
-
- public boolean indexReady() {
- return (mModel != null) && mModel.indexReady();
- }
-
- @Override
- public int getCount() {
- return mModel != null ? mModel.size() : 0;
- }
-
- @Override
- public Object getItem(int position) {
- return mModel.get(position, mSortOrder);
- }
-
- @Override
- public boolean areAllItemsEnabled() {
- return true;
- }
-
- @Override
- public boolean isEnabled(int position) {
- return true;
- }
-
- @Override
- public long getItemId(int position) {
- return position;
- }
-
- @Override
- public int getViewTypeCount() {
- return 2;
- }
-
- @Override
- public int getItemViewType(int position) {
- // If the position is the first in its section, then it corresponds to
- // a title tile, if not it's a media tile
- if (position == getPositionForSection(getSectionForPosition(position))) {
- return ITEM_TYPE_BUCKET;
- } else {
- return ITEM_TYPE_MEDIA;
- }
- }
-
- public boolean itemAtPositionIsBucket(int position) {
- return getItemViewType(position) == ITEM_TYPE_BUCKET;
- }
-
- public boolean itemAtPositionIsMedia(int position) {
- return getItemViewType(position) == ITEM_TYPE_MEDIA;
- }
-
- @Override
- public View getView(int position, View convertView, ViewGroup parent) {
- int type = getItemViewType(position);
- if (type == ITEM_TYPE_MEDIA) {
- MtpThumbnailTileView imageView;
- if (convertView == null) {
- imageView = (MtpThumbnailTileView) mInflater.inflate(
- R.layout.ingest_thumbnail, parent, false);
- } else {
- imageView = (MtpThumbnailTileView) convertView;
- }
- imageView.setMtpDeviceAndObjectInfo(mModel.getDevice(), (MtpObjectInfo)getItem(position), mGeneration);
- return imageView;
- } else {
- DateTileView dateTile;
- if (convertView == null) {
- dateTile = (DateTileView) mInflater.inflate(
- R.layout.ingest_date_tile, parent, false);
- } else {
- dateTile = (DateTileView) convertView;
- }
- dateTile.setDate((SimpleDate)getItem(position));
- return dateTile;
- }
- }
-
- @Override
- public int getPositionForSection(int section) {
- if (getCount() == 0) {
- return 0;
- }
- int numSections = getSections().length;
- if (section >= numSections) {
- section = numSections - 1;
- }
- return mModel.getFirstPositionForBucketNumber(section, mSortOrder);
- }
-
- @Override
- public int getSectionForPosition(int position) {
- int count = getCount();
- if (count == 0) {
- return 0;
- }
- if (position >= count) {
- position = count - 1;
- }
- return mModel.getBucketNumberForPosition(position, mSortOrder);
- }
-
- @Override
- public Object[] getSections() {
- return getCount() > 0 ? mModel.getBuckets(mSortOrder) : null;
- }
-
- public SortOrder getSortOrder() {
- return mSortOrder;
- }
-
- public int translatePositionWithoutLabels(int position) {
- if (mModel == null) return -1;
- return mModel.getPositionFromPositionWithoutLabels(position, mSortOrder);
- }
-}
diff --git a/src/com/android/gallery3d/ingest/adapter/MtpPagerAdapter.java b/src/com/android/gallery3d/ingest/adapter/MtpPagerAdapter.java
deleted file mode 100644
index 9e7abc01d..000000000
--- a/src/com/android/gallery3d/ingest/adapter/MtpPagerAdapter.java
+++ /dev/null
@@ -1,102 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest.adapter;
-
-import android.content.Context;
-import android.mtp.MtpObjectInfo;
-import android.support.v4.view.PagerAdapter;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.ingest.MtpDeviceIndex;
-import com.android.gallery3d.ingest.MtpDeviceIndex.SortOrder;
-import com.android.gallery3d.ingest.ui.MtpFullscreenView;
-
-public class MtpPagerAdapter extends PagerAdapter {
-
- private LayoutInflater mInflater;
- private int mGeneration = 0;
- private CheckBroker mBroker;
- private MtpDeviceIndex mModel;
- private SortOrder mSortOrder = SortOrder.Descending;
-
- private MtpFullscreenView mReusableView = null;
-
- public MtpPagerAdapter(Context context, CheckBroker broker) {
- super();
- mInflater = LayoutInflater.from(context);
- mBroker = broker;
- }
-
- public void setMtpDeviceIndex(MtpDeviceIndex index) {
- mModel = index;
- notifyDataSetChanged();
- }
-
- @Override
- public int getCount() {
- return mModel != null ? mModel.sizeWithoutLabels() : 0;
- }
-
- @Override
- public void notifyDataSetChanged() {
- mGeneration++;
- super.notifyDataSetChanged();
- }
-
- public int translatePositionWithLabels(int position) {
- if (mModel == null) return -1;
- return mModel.getPositionWithoutLabelsFromPosition(position, mSortOrder);
- }
-
- @Override
- public void finishUpdate(ViewGroup container) {
- mReusableView = null;
- super.finishUpdate(container);
- }
-
- @Override
- public boolean isViewFromObject(View view, Object object) {
- return view == object;
- }
-
- @Override
- public void destroyItem(ViewGroup container, int position, Object object) {
- MtpFullscreenView v = (MtpFullscreenView)object;
- container.removeView(v);
- mBroker.unregisterOnCheckedChangeListener(v);
- mReusableView = v;
- }
-
- @Override
- public Object instantiateItem(ViewGroup container, int position) {
- MtpFullscreenView v;
- if (mReusableView != null) {
- v = mReusableView;
- mReusableView = null;
- } else {
- v = (MtpFullscreenView) mInflater.inflate(R.layout.ingest_fullsize, container, false);
- }
- MtpObjectInfo i = mModel.getWithoutLabels(position, mSortOrder);
- v.getImageView().setMtpDeviceAndObjectInfo(mModel.getDevice(), i, mGeneration);
- v.setPositionAndBroker(position, mBroker);
- container.addView(v);
- return v;
- }
-}
diff --git a/src/com/android/gallery3d/ingest/data/BitmapWithMetadata.java b/src/com/android/gallery3d/ingest/data/BitmapWithMetadata.java
deleted file mode 100644
index bbc90f670..000000000
--- a/src/com/android/gallery3d/ingest/data/BitmapWithMetadata.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest.data;
-
-import android.graphics.Bitmap;
-
-public class BitmapWithMetadata {
- public Bitmap bitmap;
- public int rotationDegrees;
-
- public BitmapWithMetadata(Bitmap bitmap, int rotationDegrees) {
- this.bitmap = bitmap;
- this.rotationDegrees = rotationDegrees;
- }
-}
diff --git a/src/com/android/gallery3d/ingest/data/MtpBitmapFetch.java b/src/com/android/gallery3d/ingest/data/MtpBitmapFetch.java
deleted file mode 100644
index 30868c22b..000000000
--- a/src/com/android/gallery3d/ingest/data/MtpBitmapFetch.java
+++ /dev/null
@@ -1,106 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest.data;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.mtp.MtpDevice;
-import android.mtp.MtpObjectInfo;
-import android.util.DisplayMetrics;
-import android.view.WindowManager;
-
-import com.android.camera.Exif;
-import com.android.photos.data.GalleryBitmapPool;
-
-public class MtpBitmapFetch {
- private static int sMaxSize = 0;
-
- public static void recycleThumbnail(Bitmap b) {
- if (b != null) {
- GalleryBitmapPool.getInstance().put(b);
- }
- }
-
- public static Bitmap getThumbnail(MtpDevice device, MtpObjectInfo info) {
- byte[] imageBytes = device.getThumbnail(info.getObjectHandle());
- if (imageBytes == null) {
- return null;
- }
- BitmapFactory.Options o = new BitmapFactory.Options();
- o.inJustDecodeBounds = true;
- BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.length, o);
- if (o.outWidth == 0 || o.outHeight == 0) {
- return null;
- }
- o.inBitmap = GalleryBitmapPool.getInstance().get(o.outWidth, o.outHeight);
- o.inMutable = true;
- o.inJustDecodeBounds = false;
- o.inSampleSize = 1;
- try {
- return BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.length, o);
- } catch (IllegalArgumentException e) {
- // BitmapFactory throws an exception rather than returning null
- // when image decoding fails and an existing bitmap was supplied
- // for recycling, even if the failure was not caused by the use
- // of that bitmap.
- return BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.length);
- }
- }
-
- public static BitmapWithMetadata getFullsize(MtpDevice device, MtpObjectInfo info) {
- return getFullsize(device, info, sMaxSize);
- }
-
- public static BitmapWithMetadata getFullsize(MtpDevice device, MtpObjectInfo info, int maxSide) {
- byte[] imageBytes = device.getObject(info.getObjectHandle(), info.getCompressedSize());
- if (imageBytes == null) {
- return null;
- }
- Bitmap created;
- if (maxSide > 0) {
- BitmapFactory.Options o = new BitmapFactory.Options();
- o.inJustDecodeBounds = true;
- BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.length, o);
- int w = o.outWidth;
- int h = o.outHeight;
- int comp = Math.max(h, w);
- int sampleSize = 1;
- while ((comp >> 1) >= maxSide) {
- comp = comp >> 1;
- sampleSize++;
- }
- o.inSampleSize = sampleSize;
- o.inJustDecodeBounds = false;
- created = BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.length, o);
- } else {
- created = BitmapFactory.decodeByteArray(imageBytes, 0, imageBytes.length);
- }
- if (created == null) {
- return null;
- }
-
- return new BitmapWithMetadata(created, Exif.getOrientation(imageBytes));
- }
-
- public static void configureForContext(Context context) {
- DisplayMetrics metrics = new DisplayMetrics();
- WindowManager wm = (WindowManager)context.getSystemService(Context.WINDOW_SERVICE);
- wm.getDefaultDisplay().getMetrics(metrics);
- sMaxSize = Math.max(metrics.heightPixels, metrics.widthPixels);
- }
-}
diff --git a/src/com/android/gallery3d/ingest/ui/DateTileView.java b/src/com/android/gallery3d/ingest/ui/DateTileView.java
deleted file mode 100644
index 52fe9b85b..000000000
--- a/src/com/android/gallery3d/ingest/ui/DateTileView.java
+++ /dev/null
@@ -1,107 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest.ui;
-
-import android.content.Context;
-import android.util.AttributeSet;
-import android.widget.FrameLayout;
-import android.widget.TextView;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.ingest.SimpleDate;
-
-import java.text.DateFormatSymbols;
-import java.util.Locale;
-
-public class DateTileView extends FrameLayout {
- private static String[] sMonthNames = DateFormatSymbols.getInstance().getShortMonths();
- private static Locale sLocale;
-
- static {
- refreshLocale();
- }
-
- public static boolean refreshLocale() {
- Locale currentLocale = Locale.getDefault();
- if (!currentLocale.equals(sLocale)) {
- sLocale = currentLocale;
- sMonthNames = DateFormatSymbols.getInstance(sLocale).getShortMonths();
- return true;
- } else {
- return false;
- }
- }
-
- private TextView mDateTextView;
- private TextView mMonthTextView;
- private TextView mYearTextView;
- private int mMonth = -1;
- private int mYear = -1;
- private int mDate = -1;
- private String[] mMonthNames = sMonthNames;
-
- public DateTileView(Context context) {
- super(context);
- }
-
- public DateTileView(Context context, AttributeSet attrs) {
- super(context, attrs);
- }
-
- public DateTileView(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- }
-
- @Override
- public void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
- // Force this to be square
- super.onMeasure(widthMeasureSpec, widthMeasureSpec);
- }
-
- @Override
- protected void onFinishInflate() {
- super.onFinishInflate();
- mDateTextView = (TextView) findViewById(R.id.date_tile_day);
- mMonthTextView = (TextView) findViewById(R.id.date_tile_month);
- mYearTextView = (TextView) findViewById(R.id.date_tile_year);
- }
-
- public void setDate(SimpleDate date) {
- setDate(date.getDay(), date.getMonth(), date.getYear());
- }
-
- public void setDate(int date, int month, int year) {
- if (date != mDate) {
- mDate = date;
- mDateTextView.setText(mDate > 9 ? Integer.toString(mDate) : "0" + mDate);
- }
- if (mMonthNames != sMonthNames) {
- mMonthNames = sMonthNames;
- if (month == mMonth) {
- mMonthTextView.setText(mMonthNames[mMonth]);
- }
- }
- if (month != mMonth) {
- mMonth = month;
- mMonthTextView.setText(mMonthNames[mMonth]);
- }
- if (year != mYear) {
- mYear = year;
- mYearTextView.setText(Integer.toString(mYear));
- }
- }
-}
diff --git a/src/com/android/gallery3d/ingest/ui/IngestGridView.java b/src/com/android/gallery3d/ingest/ui/IngestGridView.java
deleted file mode 100644
index c821259fe..000000000
--- a/src/com/android/gallery3d/ingest/ui/IngestGridView.java
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest.ui;
-
-import android.content.Context;
-import android.util.AttributeSet;
-import android.widget.GridView;
-
-/**
- * This just extends GridView with the ability to listen for calls
- * to clearChoices()
- */
-public class IngestGridView extends GridView {
-
- public interface OnClearChoicesListener {
- public void onClearChoices();
- }
-
- private OnClearChoicesListener mOnClearChoicesListener = null;
-
- public IngestGridView(Context context) {
- super(context);
- }
-
- public IngestGridView(Context context, AttributeSet attrs) {
- super(context, attrs);
- }
-
- public IngestGridView(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- }
-
- public void setOnClearChoicesListener(OnClearChoicesListener l) {
- mOnClearChoicesListener = l;
- }
-
- @Override
- public void clearChoices() {
- super.clearChoices();
- if (mOnClearChoicesListener != null) {
- mOnClearChoicesListener.onClearChoices();
- }
- }
-}
diff --git a/src/com/android/gallery3d/ingest/ui/MtpFullscreenView.java b/src/com/android/gallery3d/ingest/ui/MtpFullscreenView.java
deleted file mode 100644
index 8d3884dc6..000000000
--- a/src/com/android/gallery3d/ingest/ui/MtpFullscreenView.java
+++ /dev/null
@@ -1,115 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest.ui;
-
-import android.content.Context;
-import android.util.AttributeSet;
-import android.widget.CheckBox;
-import android.widget.Checkable;
-import android.widget.CompoundButton;
-import android.widget.CompoundButton.OnCheckedChangeListener;
-import android.widget.RelativeLayout;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.ingest.adapter.CheckBroker;
-
-public class MtpFullscreenView extends RelativeLayout implements Checkable,
- CompoundButton.OnCheckedChangeListener, CheckBroker.OnCheckedChangedListener {
-
- private MtpImageView mImageView;
- private CheckBox mCheckbox;
- private int mPosition = -1;
- private CheckBroker mBroker;
-
- public MtpFullscreenView(Context context) {
- super(context);
- }
-
- public MtpFullscreenView(Context context, AttributeSet attrs) {
- super(context, attrs);
- }
-
- public MtpFullscreenView(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- }
-
- @Override
- protected void onFinishInflate() {
- super.onFinishInflate();
- mImageView = (MtpImageView) findViewById(R.id.ingest_fullsize_image);
- mCheckbox = (CheckBox) findViewById(R.id.ingest_fullsize_image_checkbox);
- mCheckbox.setOnCheckedChangeListener(this);
- }
-
- @Override
- public boolean isChecked() {
- return mCheckbox.isChecked();
- }
-
- @Override
- public void setChecked(boolean checked) {
- mCheckbox.setChecked(checked);
- }
-
- @Override
- public void toggle() {
- mCheckbox.toggle();
- }
-
- @Override
- public void onDetachedFromWindow() {
- setPositionAndBroker(-1, null);
- super.onDetachedFromWindow();
- }
-
- public MtpImageView getImageView() {
- return mImageView;
- }
-
- public int getPosition() {
- return mPosition;
- }
-
- public void setPositionAndBroker(int position, CheckBroker b) {
- if (mBroker != null) {
- mBroker.unregisterOnCheckedChangeListener(this);
- }
- mPosition = position;
- mBroker = b;
- if (mBroker != null) {
- setChecked(mBroker.isItemChecked(position));
- mBroker.registerOnCheckedChangeListener(this);
- }
- }
-
- @Override
- public void onCheckedChanged(CompoundButton arg0, boolean isChecked) {
- if (mBroker != null) mBroker.setItemChecked(mPosition, isChecked);
- }
-
- @Override
- public void onCheckedChanged(int position, boolean isChecked) {
- if (position == mPosition) {
- setChecked(isChecked);
- }
- }
-
- @Override
- public void onBulkCheckedChanged() {
- if(mBroker != null) setChecked(mBroker.isItemChecked(mPosition));
- }
-}
diff --git a/src/com/android/gallery3d/ingest/ui/MtpImageView.java b/src/com/android/gallery3d/ingest/ui/MtpImageView.java
deleted file mode 100644
index 80c105126..000000000
--- a/src/com/android/gallery3d/ingest/ui/MtpImageView.java
+++ /dev/null
@@ -1,280 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest.ui;
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Matrix;
-import android.graphics.drawable.Drawable;
-import android.mtp.MtpDevice;
-import android.mtp.MtpObjectInfo;
-import android.os.Handler;
-import android.os.HandlerThread;
-import android.os.Looper;
-import android.os.Message;
-import android.util.AttributeSet;
-import android.widget.ImageView;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.ingest.MtpDeviceIndex;
-import com.android.gallery3d.ingest.data.BitmapWithMetadata;
-import com.android.gallery3d.ingest.data.MtpBitmapFetch;
-
-import java.lang.ref.WeakReference;
-
-public class MtpImageView extends ImageView {
- // We will use the thumbnail for images larger than this threshold
- private static final int MAX_FULLSIZE_PREVIEW_SIZE = 8388608; // 8 megabytes
-
- private int mObjectHandle;
- private int mGeneration;
-
- private WeakReference<MtpImageView> mWeakReference = new WeakReference<MtpImageView>(this);
- private Object mFetchLock = new Object();
- private boolean mFetchPending = false;
- private MtpObjectInfo mFetchObjectInfo;
- private MtpDevice mFetchDevice;
- private Object mFetchResult;
- private Drawable mOverlayIcon;
- private boolean mShowOverlayIcon;
-
- private static final FetchImageHandler sFetchHandler = FetchImageHandler.createOnNewThread();
- private static final ShowImageHandler sFetchCompleteHandler = new ShowImageHandler();
-
- private void init() {
- showPlaceholder();
- }
-
- public MtpImageView(Context context) {
- super(context);
- init();
- }
-
- public MtpImageView(Context context, AttributeSet attrs) {
- super(context, attrs);
- init();
- }
-
- public MtpImageView(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- init();
- }
-
- private void showPlaceholder() {
- setImageResource(android.R.color.transparent);
- }
-
- public void setMtpDeviceAndObjectInfo(MtpDevice device, MtpObjectInfo object, int gen) {
- int handle = object.getObjectHandle();
- if (handle == mObjectHandle && gen == mGeneration) {
- return;
- }
- cancelLoadingAndClear();
- showPlaceholder();
- mGeneration = gen;
- mObjectHandle = handle;
- mShowOverlayIcon = MtpDeviceIndex.SUPPORTED_VIDEO_FORMATS.contains(object.getFormat());
- if (mShowOverlayIcon && mOverlayIcon == null) {
- mOverlayIcon = getResources().getDrawable(R.drawable.ic_control_play);
- updateOverlayIconBounds();
- }
- synchronized (mFetchLock) {
- mFetchObjectInfo = object;
- mFetchDevice = device;
- if (mFetchPending) return;
- mFetchPending = true;
- sFetchHandler.sendMessage(
- sFetchHandler.obtainMessage(0, mWeakReference));
- }
- }
-
- protected Object fetchMtpImageDataFromDevice(MtpDevice device, MtpObjectInfo info) {
- if (info.getCompressedSize() <= MAX_FULLSIZE_PREVIEW_SIZE
- && MtpDeviceIndex.SUPPORTED_IMAGE_FORMATS.contains(info.getFormat())) {
- return MtpBitmapFetch.getFullsize(device, info);
- } else {
- return new BitmapWithMetadata(MtpBitmapFetch.getThumbnail(device, info), 0);
- }
- }
-
- private float mLastBitmapWidth;
- private float mLastBitmapHeight;
- private int mLastRotationDegrees;
- private Matrix mDrawMatrix = new Matrix();
-
- private void updateDrawMatrix() {
- mDrawMatrix.reset();
- float dwidth;
- float dheight;
- float vheight = getHeight();
- float vwidth = getWidth();
- float scale;
- boolean rotated90 = (mLastRotationDegrees % 180 != 0);
- if (rotated90) {
- dwidth = mLastBitmapHeight;
- dheight = mLastBitmapWidth;
- } else {
- dwidth = mLastBitmapWidth;
- dheight = mLastBitmapHeight;
- }
- if (dwidth <= vwidth && dheight <= vheight) {
- scale = 1.0f;
- } else {
- scale = Math.min(vwidth / dwidth, vheight / dheight);
- }
- mDrawMatrix.setScale(scale, scale);
- if (rotated90) {
- mDrawMatrix.postTranslate(-dheight * scale * 0.5f,
- -dwidth * scale * 0.5f);
- mDrawMatrix.postRotate(mLastRotationDegrees);
- mDrawMatrix.postTranslate(dwidth * scale * 0.5f,
- dheight * scale * 0.5f);
- }
- mDrawMatrix.postTranslate((vwidth - dwidth * scale) * 0.5f,
- (vheight - dheight * scale) * 0.5f);
- if (!rotated90 && mLastRotationDegrees > 0) {
- // rotated by a multiple of 180
- mDrawMatrix.postRotate(mLastRotationDegrees, vwidth / 2, vheight / 2);
- }
- setImageMatrix(mDrawMatrix);
- }
-
- private static final int OVERLAY_ICON_SIZE_DENOMINATOR = 4;
-
- private void updateOverlayIconBounds() {
- int iheight = mOverlayIcon.getIntrinsicHeight();
- int iwidth = mOverlayIcon.getIntrinsicWidth();
- int vheight = getHeight();
- int vwidth = getWidth();
- float scale_height = ((float) vheight) / (iheight * OVERLAY_ICON_SIZE_DENOMINATOR);
- float scale_width = ((float) vwidth) / (iwidth * OVERLAY_ICON_SIZE_DENOMINATOR);
- if (scale_height >= 1f && scale_width >= 1f) {
- mOverlayIcon.setBounds((vwidth - iwidth) / 2,
- (vheight - iheight) / 2,
- (vwidth + iwidth) / 2,
- (vheight + iheight) / 2);
- } else {
- float scale = Math.min(scale_height, scale_width);
- mOverlayIcon.setBounds((int) (vwidth - scale * iwidth) / 2,
- (int) (vheight - scale * iheight) / 2,
- (int) (vwidth + scale * iwidth) / 2,
- (int) (vheight + scale * iheight) / 2);
- }
- }
-
- @Override
- protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
- super.onLayout(changed, left, top, right, bottom);
- if (changed && getScaleType() == ScaleType.MATRIX) {
- updateDrawMatrix();
- }
- if (mShowOverlayIcon && changed && mOverlayIcon != null) {
- updateOverlayIconBounds();
- }
- }
-
- @Override
- protected void onDraw(Canvas canvas) {
- super.onDraw(canvas);
- if (mShowOverlayIcon && mOverlayIcon != null) {
- mOverlayIcon.draw(canvas);
- }
- }
-
- protected void onMtpImageDataFetchedFromDevice(Object result) {
- BitmapWithMetadata bitmapWithMetadata = (BitmapWithMetadata)result;
- if (getScaleType() == ScaleType.MATRIX) {
- mLastBitmapHeight = bitmapWithMetadata.bitmap.getHeight();
- mLastBitmapWidth = bitmapWithMetadata.bitmap.getWidth();
- mLastRotationDegrees = bitmapWithMetadata.rotationDegrees;
- updateDrawMatrix();
- } else {
- setRotation(bitmapWithMetadata.rotationDegrees);
- }
- setAlpha(0f);
- setImageBitmap(bitmapWithMetadata.bitmap);
- animate().alpha(1f);
- }
-
- protected void cancelLoadingAndClear() {
- synchronized (mFetchLock) {
- mFetchDevice = null;
- mFetchObjectInfo = null;
- mFetchResult = null;
- }
- animate().cancel();
- setImageResource(android.R.color.transparent);
- }
-
- @Override
- public void onDetachedFromWindow() {
- cancelLoadingAndClear();
- super.onDetachedFromWindow();
- }
-
- private static class FetchImageHandler extends Handler {
- public FetchImageHandler(Looper l) {
- super(l);
- }
-
- public static FetchImageHandler createOnNewThread() {
- HandlerThread t = new HandlerThread("MtpImageView Fetch");
- t.start();
- return new FetchImageHandler(t.getLooper());
- }
-
- @Override
- public void handleMessage(Message msg) {
- @SuppressWarnings("unchecked")
- MtpImageView parent = ((WeakReference<MtpImageView>) msg.obj).get();
- if (parent == null) return;
- MtpObjectInfo objectInfo;
- MtpDevice device;
- synchronized (parent.mFetchLock) {
- parent.mFetchPending = false;
- device = parent.mFetchDevice;
- objectInfo = parent.mFetchObjectInfo;
- }
- if (device == null) return;
- Object result = parent.fetchMtpImageDataFromDevice(device, objectInfo);
- if (result == null) return;
- synchronized (parent.mFetchLock) {
- if (parent.mFetchObjectInfo != objectInfo) return;
- parent.mFetchResult = result;
- parent.mFetchDevice = null;
- parent.mFetchObjectInfo = null;
- sFetchCompleteHandler.sendMessage(
- sFetchCompleteHandler.obtainMessage(0, parent.mWeakReference));
- }
- }
- }
-
- private static class ShowImageHandler extends Handler {
- @Override
- public void handleMessage(Message msg) {
- @SuppressWarnings("unchecked")
- MtpImageView parent = ((WeakReference<MtpImageView>) msg.obj).get();
- if (parent == null) return;
- Object result;
- synchronized (parent.mFetchLock) {
- result = parent.mFetchResult;
- }
- if (result == null) return;
- parent.onMtpImageDataFetchedFromDevice(result);
- }
- }
-}
diff --git a/src/com/android/gallery3d/ingest/ui/MtpThumbnailTileView.java b/src/com/android/gallery3d/ingest/ui/MtpThumbnailTileView.java
deleted file mode 100644
index 3307e78aa..000000000
--- a/src/com/android/gallery3d/ingest/ui/MtpThumbnailTileView.java
+++ /dev/null
@@ -1,106 +0,0 @@
-/*
- * Copyright (C) 2013 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ingest.ui;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.mtp.MtpDevice;
-import android.mtp.MtpObjectInfo;
-import android.util.AttributeSet;
-import android.widget.Checkable;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.ingest.data.MtpBitmapFetch;
-
-
-public class MtpThumbnailTileView extends MtpImageView implements Checkable {
-
- private Paint mForegroundPaint;
- private boolean mIsChecked;
- private Bitmap mBitmap;
-
- private void init() {
- mForegroundPaint = new Paint();
- mForegroundPaint.setColor(getResources().getColor(R.color.ingest_highlight_semitransparent));
- }
-
- public MtpThumbnailTileView(Context context) {
- super(context);
- init();
- }
-
- public MtpThumbnailTileView(Context context, AttributeSet attrs) {
- super(context, attrs);
- init();
- }
-
- public MtpThumbnailTileView(Context context, AttributeSet attrs, int defStyle) {
- super(context, attrs, defStyle);
- init();
- }
-
- @Override
- public void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
- // Force this to be square
- super.onMeasure(widthMeasureSpec, widthMeasureSpec);
- }
-
- @Override
- protected Object fetchMtpImageDataFromDevice(MtpDevice device, MtpObjectInfo info) {
- return MtpBitmapFetch.getThumbnail(device, info);
- }
-
- @Override
- protected void onMtpImageDataFetchedFromDevice(Object result) {
- mBitmap = (Bitmap)result;
- setImageBitmap(mBitmap);
- }
-
- @Override
- public void draw(Canvas canvas) {
- super.draw(canvas);
- if (isChecked()) {
- canvas.drawRect(canvas.getClipBounds(), mForegroundPaint);
- }
- }
-
- @Override
- public boolean isChecked() {
- return mIsChecked;
- }
-
- @Override
- public void setChecked(boolean checked) {
- mIsChecked = checked;
- }
-
- @Override
- public void toggle() {
- setChecked(!mIsChecked);
- }
-
- @Override
- protected void cancelLoadingAndClear() {
- super.cancelLoadingAndClear();
- if (mBitmap != null) {
- MtpBitmapFetch.recycleThumbnail(mBitmap);
- mBitmap = null;
- }
- }
-}
diff --git a/src/com/android/gallery3d/onetimeinitializer/GalleryWidgetMigrator.java b/src/com/android/gallery3d/onetimeinitializer/GalleryWidgetMigrator.java
deleted file mode 100644
index ef26b1b97..000000000
--- a/src/com/android/gallery3d/onetimeinitializer/GalleryWidgetMigrator.java
+++ /dev/null
@@ -1,169 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.onetimeinitializer;
-
-import android.content.Context;
-import android.content.SharedPreferences;
-import android.os.Build;
-import android.os.Environment;
-import android.preference.PreferenceManager;
-import android.util.Log;
-
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.LocalAlbum;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.gadget.WidgetDatabaseHelper;
-import com.android.gallery3d.gadget.WidgetDatabaseHelper.Entry;
-import com.android.gallery3d.util.GalleryUtils;
-
-import java.io.File;
-import java.util.HashMap;
-import java.util.List;
-
-/**
- * This one-timer migrates local-album gallery app widgets from old paths from prior releases
- * to updated paths in the current build version. This migration is needed because of
- * bucket ID (i.e., directory hash) change in JB and JB MR1 (The external storage path has changed
- * from /mnt/sdcard in pre-JB releases, to /storage/sdcard0 in JB, then again
- * to /external/storage/sdcard/0 in JB MR1).
- */
-public class GalleryWidgetMigrator {
- private static final String TAG = "GalleryWidgetMigrator";
- private static final String PRE_JB_EXT_PATH = "/mnt/sdcard";
- private static final String JB_EXT_PATH = "/storage/sdcard0";
- private static final String NEW_EXT_PATH =
- Environment.getExternalStorageDirectory().getAbsolutePath();
- private static final int RELATIVE_PATH_START = NEW_EXT_PATH.length();
- private static final String KEY_EXT_PATH = "external_storage_path";
-
- /**
- * Migrates local-album gallery widgets from prior releases to current release
- * due to bucket ID (i.e., directory hash) change.
- */
- public static void migrateGalleryWidgets(Context context) {
- SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
- // Migration is only needed when external storage path has changed
- String extPath = prefs.getString(KEY_EXT_PATH, null);
- boolean isDone = NEW_EXT_PATH.equals(extPath);
- if (isDone) return;
-
- try {
- migrateGalleryWidgetsInternal(context);
- prefs.edit().putString(KEY_EXT_PATH, NEW_EXT_PATH).commit();
- } catch (Throwable t) {
- // exception may be thrown if external storage is not available(?)
- Log.w(TAG, "migrateGalleryWidgets", t);
- }
- }
-
- private static void migrateGalleryWidgetsInternal(Context context) {
- GalleryApp galleryApp = (GalleryApp) context.getApplicationContext();
- DataManager manager = galleryApp.getDataManager();
- WidgetDatabaseHelper dbHelper = new WidgetDatabaseHelper(context);
-
- // only need to migrate local-album entries of type TYPE_ALBUM
- List<Entry> entries = dbHelper.getEntries(WidgetDatabaseHelper.TYPE_ALBUM);
- if (entries == null) return;
-
- // Check each entry's relativePath. If exists, update bucket id using relative
- // path combined with external storage path. Otherwise, iterate through old external
- // storage paths to find the relative path that matches the old bucket id, and then update
- // bucket id and relative path
- HashMap<Integer, Entry> localEntries = new HashMap<Integer, Entry>(entries.size());
- for (Entry entry : entries) {
- Path path = Path.fromString(entry.albumPath);
- MediaSet mediaSet = (MediaSet) manager.getMediaObject(path);
- if (mediaSet instanceof LocalAlbum) {
- if (entry.relativePath != null && entry.relativePath.length() > 0) {
- // update entry using relative path + external storage path
- updateEntryUsingRelativePath(entry, dbHelper);
- } else {
- int bucketId = Integer.parseInt(path.getSuffix());
- localEntries.put(bucketId, entry);
- }
- }
- }
- if (!localEntries.isEmpty()) migrateLocalEntries(context, localEntries, dbHelper);
- }
-
- private static void migrateLocalEntries(Context context,
- HashMap<Integer, Entry> entries, WidgetDatabaseHelper dbHelper) {
- SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
- String oldExtPath = prefs.getString(KEY_EXT_PATH, null);
- if (oldExtPath != null) {
- migrateLocalEntries(entries, dbHelper, oldExtPath);
- return;
- }
- // If old external storage path is unknown, it could be either Pre-JB or JB version
- // we need to try both.
- migrateLocalEntries(entries, dbHelper, PRE_JB_EXT_PATH);
- if (!entries.isEmpty() &&
- Build.VERSION.SDK_INT > ApiHelper.VERSION_CODES.JELLY_BEAN) {
- migrateLocalEntries(entries, dbHelper, JB_EXT_PATH);
- }
- }
-
- private static void migrateLocalEntries(HashMap<Integer, Entry> entries,
- WidgetDatabaseHelper dbHelper, String oldExtPath) {
- File root = Environment.getExternalStorageDirectory();
- // check the DCIM directory first; this should take care of 99% use cases
- updatePath(new File(root, "DCIM"), entries, dbHelper, oldExtPath);
- // check other directories if DCIM doesn't cut it
- if (!entries.isEmpty()) updatePath(root, entries, dbHelper, oldExtPath);
- }
- private static void updatePath(File root, HashMap<Integer, Entry> entries,
- WidgetDatabaseHelper dbHelper, String oldExtStorage) {
- File[] files = root.listFiles();
- if (files != null) {
- for (File file : files) {
- if (file.isDirectory() && !entries.isEmpty()) {
- String path = file.getAbsolutePath();
- String oldPath = oldExtStorage + path.substring(RELATIVE_PATH_START);
- int oldBucketId = GalleryUtils.getBucketId(oldPath);
- Entry entry = entries.remove(oldBucketId);
- if (entry != null) {
- int newBucketId = GalleryUtils.getBucketId(path);
- String newAlbumPath = Path.fromString(entry.albumPath)
- .getParent()
- .getChild(newBucketId)
- .toString();
- Log.d(TAG, "migrate from " + entry.albumPath + " to " + newAlbumPath);
- entry.albumPath = newAlbumPath;
- // update entry's relative path
- entry.relativePath = path.substring(RELATIVE_PATH_START);
- dbHelper.updateEntry(entry);
- }
- updatePath(file, entries, dbHelper, oldExtStorage); // recursion
- }
- }
- }
- }
-
- private static void updateEntryUsingRelativePath(Entry entry, WidgetDatabaseHelper dbHelper) {
- String newPath = NEW_EXT_PATH + entry.relativePath;
- int newBucketId = GalleryUtils.getBucketId(newPath);
- String newAlbumPath = Path.fromString(entry.albumPath)
- .getParent()
- .getChild(newBucketId)
- .toString();
- entry.albumPath = newAlbumPath;
- dbHelper.updateEntry(entry);
- }
-}
diff --git a/src/com/android/gallery3d/provider/GalleryProvider.java b/src/com/android/gallery3d/provider/GalleryProvider.java
deleted file mode 100644
index d6c7ccd4d..000000000
--- a/src/com/android/gallery3d/provider/GalleryProvider.java
+++ /dev/null
@@ -1,228 +0,0 @@
-/*
- * Copyright (C) 2009 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.provider;
-
-import android.content.ContentProvider;
-import android.content.ContentValues;
-import android.content.Context;
-import android.database.Cursor;
-import android.database.MatrixCursor;
-import android.net.Uri;
-import android.os.AsyncTask;
-import android.os.Binder;
-import android.os.ParcelFileDescriptor;
-import android.provider.MediaStore.Images.ImageColumns;
-import android.util.Log;
-
-import com.android.gallery3d.app.GalleryApp;
-import com.android.gallery3d.common.AsyncTaskUtil;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.picasasource.PicasaSource;
-import com.android.gallery3d.util.GalleryUtils;
-
-import java.io.FileNotFoundException;
-import java.io.IOException;
-
-public class GalleryProvider extends ContentProvider {
- private static final String TAG = "GalleryProvider";
-
- public static final String AUTHORITY = "com.android.gallery3d.provider";
- public static final Uri BASE_URI = Uri.parse("content://" + AUTHORITY);
-
- public static interface PicasaColumns {
- public static final String USER_ACCOUNT = "user_account";
- public static final String PICASA_ID = "picasa_id";
- }
-
- private static final String[] SUPPORTED_PICASA_COLUMNS = {
- PicasaColumns.USER_ACCOUNT,
- PicasaColumns.PICASA_ID,
- ImageColumns.DISPLAY_NAME,
- ImageColumns.SIZE,
- ImageColumns.MIME_TYPE,
- ImageColumns.DATE_TAKEN,
- ImageColumns.LATITUDE,
- ImageColumns.LONGITUDE,
- ImageColumns.ORIENTATION};
-
- private DataManager mDataManager;
- private static Uri sBaseUri;
-
- public static String getAuthority(Context context) {
- return context.getPackageName() + ".provider";
- }
-
- public static Uri getUriFor(Context context, Path path) {
- if (sBaseUri == null) {
- sBaseUri = Uri.parse("content://" + context.getPackageName() + ".provider");
- }
- return sBaseUri.buildUpon()
- .appendEncodedPath(path.toString().substring(1)) // ignore the leading '/'
- .build();
- }
-
- @Override
- public int delete(Uri uri, String selection, String[] selectionArgs) {
- throw new UnsupportedOperationException();
- }
-
- // TODO: consider concurrent access
- @Override
- public String getType(Uri uri) {
- long token = Binder.clearCallingIdentity();
- try {
- Path path = Path.fromString(uri.getPath());
- MediaItem item = (MediaItem) mDataManager.getMediaObject(path);
- return item != null ? item.getMimeType() : null;
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public Uri insert(Uri uri, ContentValues values) {
- throw new UnsupportedOperationException();
- }
-
- @Override
- public boolean onCreate() {
- GalleryApp app = (GalleryApp) getContext().getApplicationContext();
- mDataManager = app.getDataManager();
- return true;
- }
-
- // TODO: consider concurrent access
- @Override
- public Cursor query(Uri uri, String[] projection,
- String selection, String[] selectionArgs, String sortOrder) {
- long token = Binder.clearCallingIdentity();
- try {
- Path path = Path.fromString(uri.getPath());
- MediaObject object = mDataManager.getMediaObject(path);
- if (object == null) {
- Log.w(TAG, "cannot find: " + uri);
- return null;
- }
- if (PicasaSource.isPicasaImage(object)) {
- return queryPicasaItem(object,
- projection, selection, selectionArgs, sortOrder);
- } else {
- return null;
- }
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- private Cursor queryPicasaItem(MediaObject image, String[] projection,
- String selection, String[] selectionArgs, String sortOrder) {
- if (projection == null) projection = SUPPORTED_PICASA_COLUMNS;
- Object[] columnValues = new Object[projection.length];
- double latitude = PicasaSource.getLatitude(image);
- double longitude = PicasaSource.getLongitude(image);
- boolean isValidLatlong = GalleryUtils.isValidLocation(latitude, longitude);
-
- for (int i = 0, n = projection.length; i < n; ++i) {
- String column = projection[i];
- if (PicasaColumns.USER_ACCOUNT.equals(column)) {
- columnValues[i] = PicasaSource.getUserAccount(getContext(), image);
- } else if (PicasaColumns.PICASA_ID.equals(column)) {
- columnValues[i] = PicasaSource.getPicasaId(image);
- } else if (ImageColumns.DISPLAY_NAME.equals(column)) {
- columnValues[i] = PicasaSource.getImageTitle(image);
- } else if (ImageColumns.SIZE.equals(column)){
- columnValues[i] = PicasaSource.getImageSize(image);
- } else if (ImageColumns.MIME_TYPE.equals(column)) {
- columnValues[i] = PicasaSource.getContentType(image);
- } else if (ImageColumns.DATE_TAKEN.equals(column)) {
- columnValues[i] = PicasaSource.getDateTaken(image);
- } else if (ImageColumns.LATITUDE.equals(column)) {
- columnValues[i] = isValidLatlong ? latitude : null;
- } else if (ImageColumns.LONGITUDE.equals(column)) {
- columnValues[i] = isValidLatlong ? longitude : null;
- } else if (ImageColumns.ORIENTATION.equals(column)) {
- columnValues[i] = PicasaSource.getRotation(image);
- } else {
- Log.w(TAG, "unsupported column: " + column);
- }
- }
- MatrixCursor cursor = new MatrixCursor(projection);
- cursor.addRow(columnValues);
- return cursor;
- }
-
- @Override
- public ParcelFileDescriptor openFile(Uri uri, String mode)
- throws FileNotFoundException {
- long token = Binder.clearCallingIdentity();
- try {
- if (mode.contains("w")) {
- throw new FileNotFoundException("cannot open file for write");
- }
- Path path = Path.fromString(uri.getPath());
- MediaObject object = mDataManager.getMediaObject(path);
- if (object == null) {
- throw new FileNotFoundException(uri.toString());
- }
- if (PicasaSource.isPicasaImage(object)) {
- return PicasaSource.openFile(getContext(), object, mode);
- } else {
- throw new FileNotFoundException("unspported type: " + object);
- }
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs) {
- throw new UnsupportedOperationException();
- }
-
- private static interface PipeDataWriter<T> {
- void writeDataToPipe(ParcelFileDescriptor output, T args);
- }
-
- // Modified from ContentProvider.openPipeHelper. We are target at API LEVEL 10.
- // But openPipeHelper is available in API LEVEL 11.
- private static <T> ParcelFileDescriptor openPipeHelper(
- final T args, final PipeDataWriter<T> func) throws FileNotFoundException {
- try {
- final ParcelFileDescriptor[] pipe = ParcelFileDescriptor.createPipe();
- AsyncTask<Object, Object, Object> task = new AsyncTask<Object, Object, Object>() {
- @Override
- protected Object doInBackground(Object... params) {
- try {
- func.writeDataToPipe(pipe[1], args);
- return null;
- } finally {
- Utils.closeSilently(pipe[1]);
- }
- }
- };
- AsyncTaskUtil.executeInParallel(task, (Object[]) null);
- return pipe[0];
- } catch (IOException e) {
- throw new FileNotFoundException("failure making pipe");
- }
- }
-
-}
diff --git a/src/com/android/gallery3d/ui/AbstractSlotRenderer.java b/src/com/android/gallery3d/ui/AbstractSlotRenderer.java
deleted file mode 100644
index 729439dc3..000000000
--- a/src/com/android/gallery3d/ui/AbstractSlotRenderer.java
+++ /dev/null
@@ -1,119 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.graphics.Rect;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.glrenderer.FadeOutTexture;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.NinePatchTexture;
-import com.android.gallery3d.glrenderer.ResourceTexture;
-import com.android.gallery3d.glrenderer.Texture;
-
-public abstract class AbstractSlotRenderer implements SlotView.SlotRenderer {
-
- private final ResourceTexture mVideoOverlay;
- private final ResourceTexture mVideoPlayIcon;
- private final ResourceTexture mPanoramaIcon;
- private final NinePatchTexture mFramePressed;
- private final NinePatchTexture mFrameSelected;
- private FadeOutTexture mFramePressedUp;
-
- protected AbstractSlotRenderer(Context context) {
- mVideoOverlay = new ResourceTexture(context, R.drawable.ic_video_thumb);
- mVideoPlayIcon = new ResourceTexture(context, R.drawable.ic_gallery_play);
- mPanoramaIcon = new ResourceTexture(context, R.drawable.ic_360pano_holo_light);
- mFramePressed = new NinePatchTexture(context, R.drawable.grid_pressed);
- mFrameSelected = new NinePatchTexture(context, R.drawable.grid_selected);
- }
-
- protected void drawContent(GLCanvas canvas,
- Texture content, int width, int height, int rotation) {
- canvas.save(GLCanvas.SAVE_FLAG_MATRIX);
-
- // The content is always rendered in to the largest square that fits
- // inside the slot, aligned to the top of the slot.
- width = height = Math.min(width, height);
- if (rotation != 0) {
- canvas.translate(width / 2, height / 2);
- canvas.rotate(rotation, 0, 0, 1);
- canvas.translate(-width / 2, -height / 2);
- }
-
- // Fit the content into the box
- float scale = Math.min(
- (float) width / content.getWidth(),
- (float) height / content.getHeight());
- canvas.scale(scale, scale, 1);
- content.draw(canvas, 0, 0);
-
- canvas.restore();
- }
-
- protected void drawVideoOverlay(GLCanvas canvas, int width, int height) {
- // Scale the video overlay to the height of the thumbnail and put it
- // on the left side.
- ResourceTexture v = mVideoOverlay;
- float scale = (float) height / v.getHeight();
- int w = Math.round(scale * v.getWidth());
- int h = Math.round(scale * v.getHeight());
- v.draw(canvas, 0, 0, w, h);
-
- int s = Math.min(width, height) / 6;
- mVideoPlayIcon.draw(canvas, (width - s) / 2, (height - s) / 2, s, s);
- }
-
- protected void drawPanoramaIcon(GLCanvas canvas, int width, int height) {
- int iconSize = Math.min(width, height) / 6;
- mPanoramaIcon.draw(canvas, (width - iconSize) / 2, (height - iconSize) / 2,
- iconSize, iconSize);
- }
-
- protected boolean isPressedUpFrameFinished() {
- if (mFramePressedUp != null) {
- if (mFramePressedUp.isAnimating()) {
- return false;
- } else {
- mFramePressedUp = null;
- }
- }
- return true;
- }
-
- protected void drawPressedUpFrame(GLCanvas canvas, int width, int height) {
- if (mFramePressedUp == null) {
- mFramePressedUp = new FadeOutTexture(mFramePressed);
- }
- drawFrame(canvas, mFramePressed.getPaddings(), mFramePressedUp, 0, 0, width, height);
- }
-
- protected void drawPressedFrame(GLCanvas canvas, int width, int height) {
- drawFrame(canvas, mFramePressed.getPaddings(), mFramePressed, 0, 0, width, height);
- }
-
- protected void drawSelectedFrame(GLCanvas canvas, int width, int height) {
- drawFrame(canvas, mFrameSelected.getPaddings(), mFrameSelected, 0, 0, width, height);
- }
-
- protected static void drawFrame(GLCanvas canvas, Rect padding, Texture frame,
- int x, int y, int width, int height) {
- frame.draw(canvas, x - padding.left, y - padding.top, width + padding.left + padding.right,
- height + padding.top + padding.bottom);
- }
-}
diff --git a/src/com/android/gallery3d/ui/ActionModeHandler.java b/src/com/android/gallery3d/ui/ActionModeHandler.java
deleted file mode 100644
index 6b4f10312..000000000
--- a/src/com/android/gallery3d/ui/ActionModeHandler.java
+++ /dev/null
@@ -1,501 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.annotation.TargetApi;
-import android.app.Activity;
-import android.content.Intent;
-import android.net.Uri;
-import android.nfc.NfcAdapter;
-import android.os.Handler;
-import android.view.ActionMode;
-import android.view.ActionMode.Callback;
-import android.view.LayoutInflater;
-import android.view.Menu;
-import android.view.MenuItem;
-import android.view.View;
-import android.widget.Button;
-import android.widget.ShareActionProvider;
-import android.widget.ShareActionProvider.OnShareTargetSelectedListener;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.MediaObject.PanoramaSupportCallback;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.ui.MenuExecutor.ProgressListener;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.util.ArrayList;
-
-public class ActionModeHandler implements Callback, PopupList.OnPopupItemClickListener {
-
- @SuppressWarnings("unused")
- private static final String TAG = "ActionModeHandler";
-
- private static final int MAX_SELECTED_ITEMS_FOR_SHARE_INTENT = 300;
- private static final int MAX_SELECTED_ITEMS_FOR_PANORAMA_SHARE_INTENT = 10;
-
- private static final int SUPPORT_MULTIPLE_MASK = MediaObject.SUPPORT_DELETE
- | MediaObject.SUPPORT_ROTATE | MediaObject.SUPPORT_SHARE
- | MediaObject.SUPPORT_CACHE;
-
- public interface ActionModeListener {
- public boolean onActionItemClicked(MenuItem item);
- }
-
- private final AbstractGalleryActivity mActivity;
- private final MenuExecutor mMenuExecutor;
- private final SelectionManager mSelectionManager;
- private final NfcAdapter mNfcAdapter;
- private Menu mMenu;
- private MenuItem mSharePanoramaMenuItem;
- private MenuItem mShareMenuItem;
- private ShareActionProvider mSharePanoramaActionProvider;
- private ShareActionProvider mShareActionProvider;
- private SelectionMenu mSelectionMenu;
- private ActionModeListener mListener;
- private Future<?> mMenuTask;
- private final Handler mMainHandler;
- private ActionMode mActionMode;
-
- private static class GetAllPanoramaSupports implements PanoramaSupportCallback {
- private int mNumInfoRequired;
- private JobContext mJobContext;
- public boolean mAllPanoramas = true;
- public boolean mAllPanorama360 = true;
- public boolean mHasPanorama360 = false;
- private Object mLock = new Object();
-
- public GetAllPanoramaSupports(ArrayList<MediaObject> mediaObjects, JobContext jc) {
- mJobContext = jc;
- mNumInfoRequired = mediaObjects.size();
- for (MediaObject mediaObject : mediaObjects) {
- mediaObject.getPanoramaSupport(this);
- }
- }
-
- @Override
- public void panoramaInfoAvailable(MediaObject mediaObject, boolean isPanorama,
- boolean isPanorama360) {
- synchronized (mLock) {
- mNumInfoRequired--;
- mAllPanoramas = isPanorama && mAllPanoramas;
- mAllPanorama360 = isPanorama360 && mAllPanorama360;
- mHasPanorama360 = mHasPanorama360 || isPanorama360;
- if (mNumInfoRequired == 0 || mJobContext.isCancelled()) {
- mLock.notifyAll();
- }
- }
- }
-
- public void waitForPanoramaSupport() {
- synchronized (mLock) {
- while (mNumInfoRequired != 0 && !mJobContext.isCancelled()) {
- try {
- mLock.wait();
- } catch (InterruptedException e) {
- // May be a cancelled job context
- }
- }
- }
- }
- }
-
- public ActionModeHandler(
- AbstractGalleryActivity activity, SelectionManager selectionManager) {
- mActivity = Utils.checkNotNull(activity);
- mSelectionManager = Utils.checkNotNull(selectionManager);
- mMenuExecutor = new MenuExecutor(activity, selectionManager);
- mMainHandler = new Handler(activity.getMainLooper());
- mNfcAdapter = NfcAdapter.getDefaultAdapter(mActivity.getAndroidContext());
- }
-
- public void startActionMode() {
- Activity a = mActivity;
- mActionMode = a.startActionMode(this);
- View customView = LayoutInflater.from(a).inflate(
- R.layout.action_mode, null);
- mActionMode.setCustomView(customView);
- mSelectionMenu = new SelectionMenu(a,
- (Button) customView.findViewById(R.id.selection_menu), this);
- updateSelectionMenu();
- }
-
- public void finishActionMode() {
- mActionMode.finish();
- }
-
- public void setTitle(String title) {
- mSelectionMenu.setTitle(title);
- }
-
- public void setActionModeListener(ActionModeListener listener) {
- mListener = listener;
- }
-
- private WakeLockHoldingProgressListener mDeleteProgressListener;
-
- @Override
- public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
- GLRoot root = mActivity.getGLRoot();
- root.lockRenderThread();
- try {
- boolean result;
- // Give listener a chance to process this command before it's routed to
- // ActionModeHandler, which handles command only based on the action id.
- // Sometimes the listener may have more background information to handle
- // an action command.
- if (mListener != null) {
- result = mListener.onActionItemClicked(item);
- if (result) {
- mSelectionManager.leaveSelectionMode();
- return result;
- }
- }
- ProgressListener listener = null;
- String confirmMsg = null;
- int action = item.getItemId();
- if (action == R.id.action_delete) {
- confirmMsg = mActivity.getResources().getQuantityString(
- R.plurals.delete_selection, mSelectionManager.getSelectedCount());
- if (mDeleteProgressListener == null) {
- mDeleteProgressListener = new WakeLockHoldingProgressListener(mActivity,
- "Gallery Delete Progress Listener");
- }
- listener = mDeleteProgressListener;
- }
- mMenuExecutor.onMenuClicked(item, confirmMsg, listener);
- } finally {
- root.unlockRenderThread();
- }
- return true;
- }
-
- @Override
- public boolean onPopupItemClick(int itemId) {
- GLRoot root = mActivity.getGLRoot();
- root.lockRenderThread();
- try {
- if (itemId == R.id.action_select_all) {
- updateSupportedOperation();
- mMenuExecutor.onMenuClicked(itemId, null, false, true);
- }
- return true;
- } finally {
- root.unlockRenderThread();
- }
- }
-
- private void updateSelectionMenu() {
- // update title
- int count = mSelectionManager.getSelectedCount();
- String format = mActivity.getResources().getQuantityString(
- R.plurals.number_of_items_selected, count);
- setTitle(String.format(format, count));
-
- // For clients who call SelectionManager.selectAll() directly, we need to ensure the
- // menu status is consistent with selection manager.
- mSelectionMenu.updateSelectAllMode(mSelectionManager.inSelectAllMode());
- }
-
- private final OnShareTargetSelectedListener mShareTargetSelectedListener =
- new OnShareTargetSelectedListener() {
- @Override
- public boolean onShareTargetSelected(ShareActionProvider source, Intent intent) {
- mSelectionManager.leaveSelectionMode();
- return false;
- }
- };
-
- @Override
- public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
- return false;
- }
-
- @Override
- public boolean onCreateActionMode(ActionMode mode, Menu menu) {
- mode.getMenuInflater().inflate(R.menu.operation, menu);
-
- mMenu = menu;
- mSharePanoramaMenuItem = menu.findItem(R.id.action_share_panorama);
- if (mSharePanoramaMenuItem != null) {
- mSharePanoramaActionProvider = (ShareActionProvider) mSharePanoramaMenuItem
- .getActionProvider();
- mSharePanoramaActionProvider.setOnShareTargetSelectedListener(
- mShareTargetSelectedListener);
- mSharePanoramaActionProvider.setShareHistoryFileName("panorama_share_history.xml");
- }
- mShareMenuItem = menu.findItem(R.id.action_share);
- if (mShareMenuItem != null) {
- mShareActionProvider = (ShareActionProvider) mShareMenuItem
- .getActionProvider();
- mShareActionProvider.setOnShareTargetSelectedListener(
- mShareTargetSelectedListener);
- mShareActionProvider.setShareHistoryFileName("share_history.xml");
- }
- return true;
- }
-
- @Override
- public void onDestroyActionMode(ActionMode mode) {
- mSelectionManager.leaveSelectionMode();
- }
-
- private ArrayList<MediaObject> getSelectedMediaObjects(JobContext jc) {
- ArrayList<Path> unexpandedPaths = mSelectionManager.getSelected(false);
- if (unexpandedPaths.isEmpty()) {
- // This happens when starting selection mode from overflow menu
- // (instead of long press a media object)
- return null;
- }
- ArrayList<MediaObject> selected = new ArrayList<MediaObject>();
- DataManager manager = mActivity.getDataManager();
- for (Path path : unexpandedPaths) {
- if (jc.isCancelled()) {
- return null;
- }
- selected.add(manager.getMediaObject(path));
- }
-
- return selected;
- }
- // Menu options are determined by selection set itself.
- // We cannot expand it because MenuExecuter executes it based on
- // the selection set instead of the expanded result.
- // e.g. LocalImage can be rotated but collections of them (LocalAlbum) can't.
- private int computeMenuOptions(ArrayList<MediaObject> selected) {
- int operation = MediaObject.SUPPORT_ALL;
- int type = 0;
- for (MediaObject mediaObject: selected) {
- int support = mediaObject.getSupportedOperations();
- type |= mediaObject.getMediaType();
- operation &= support;
- }
-
- switch (selected.size()) {
- case 1:
- final String mimeType = MenuExecutor.getMimeType(type);
- if (!GalleryUtils.isEditorAvailable(mActivity, mimeType)) {
- operation &= ~MediaObject.SUPPORT_EDIT;
- }
- break;
- default:
- operation &= SUPPORT_MULTIPLE_MASK;
- }
-
- return operation;
- }
-
- @TargetApi(ApiHelper.VERSION_CODES.JELLY_BEAN)
- private void setNfcBeamPushUris(Uri[] uris) {
- if (mNfcAdapter != null && ApiHelper.HAS_SET_BEAM_PUSH_URIS) {
- mNfcAdapter.setBeamPushUrisCallback(null, mActivity);
- mNfcAdapter.setBeamPushUris(uris, mActivity);
- }
- }
-
- // Share intent needs to expand the selection set so we can get URI of
- // each media item
- private Intent computePanoramaSharingIntent(JobContext jc, int maxItems) {
- ArrayList<Path> expandedPaths = mSelectionManager.getSelected(true, maxItems);
- if (expandedPaths == null || expandedPaths.size() == 0) {
- return new Intent();
- }
- final ArrayList<Uri> uris = new ArrayList<Uri>();
- DataManager manager = mActivity.getDataManager();
- final Intent intent = new Intent();
- for (Path path : expandedPaths) {
- if (jc.isCancelled()) return null;
- uris.add(manager.getContentUri(path));
- }
-
- final int size = uris.size();
- if (size > 0) {
- if (size > 1) {
- intent.setAction(Intent.ACTION_SEND_MULTIPLE);
- intent.setType(GalleryUtils.MIME_TYPE_PANORAMA360);
- intent.putParcelableArrayListExtra(Intent.EXTRA_STREAM, uris);
- } else {
- intent.setAction(Intent.ACTION_SEND);
- intent.setType(GalleryUtils.MIME_TYPE_PANORAMA360);
- intent.putExtra(Intent.EXTRA_STREAM, uris.get(0));
- }
- intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
- }
-
- return intent;
- }
-
- private Intent computeSharingIntent(JobContext jc, int maxItems) {
- ArrayList<Path> expandedPaths = mSelectionManager.getSelected(true, maxItems);
- if (expandedPaths == null || expandedPaths.size() == 0) {
- setNfcBeamPushUris(null);
- return new Intent();
- }
- final ArrayList<Uri> uris = new ArrayList<Uri>();
- DataManager manager = mActivity.getDataManager();
- int type = 0;
- final Intent intent = new Intent();
- for (Path path : expandedPaths) {
- if (jc.isCancelled()) return null;
- int support = manager.getSupportedOperations(path);
- type |= manager.getMediaType(path);
-
- if ((support & MediaObject.SUPPORT_SHARE) != 0) {
- uris.add(manager.getContentUri(path));
- }
- }
-
- final int size = uris.size();
- if (size > 0) {
- final String mimeType = MenuExecutor.getMimeType(type);
- if (size > 1) {
- intent.setAction(Intent.ACTION_SEND_MULTIPLE).setType(mimeType);
- intent.putParcelableArrayListExtra(Intent.EXTRA_STREAM, uris);
- } else {
- intent.setAction(Intent.ACTION_SEND).setType(mimeType);
- intent.putExtra(Intent.EXTRA_STREAM, uris.get(0));
- }
- intent.addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
- setNfcBeamPushUris(uris.toArray(new Uri[uris.size()]));
- } else {
- setNfcBeamPushUris(null);
- }
-
- return intent;
- }
-
- public void updateSupportedOperation(Path path, boolean selected) {
- // TODO: We need to improve the performance
- updateSupportedOperation();
- }
-
- public void updateSupportedOperation() {
- // Interrupt previous unfinished task, mMenuTask is only accessed in main thread
- if (mMenuTask != null) mMenuTask.cancel();
-
- updateSelectionMenu();
-
- // Disable share actions until share intent is in good shape
- if (mSharePanoramaMenuItem != null) mSharePanoramaMenuItem.setEnabled(false);
- if (mShareMenuItem != null) mShareMenuItem.setEnabled(false);
-
- // Generate sharing intent and update supported operations in the background
- // The task can take a long time and be canceled in the mean time.
- mMenuTask = mActivity.getThreadPool().submit(new Job<Void>() {
- @Override
- public Void run(final JobContext jc) {
- // Pass1: Deal with unexpanded media object list for menu operation.
- ArrayList<MediaObject> selected = getSelectedMediaObjects(jc);
- if (selected == null) {
- mMainHandler.post(new Runnable() {
- @Override
- public void run() {
- mMenuTask = null;
- if (jc.isCancelled()) return;
- // Disable all the operations when no item is selected
- MenuExecutor.updateMenuOperation(mMenu, 0);
- }
- });
- return null;
- }
- final int operation = computeMenuOptions(selected);
- if (jc.isCancelled()) {
- return null;
- }
- int numSelected = selected.size();
- final boolean canSharePanoramas =
- numSelected < MAX_SELECTED_ITEMS_FOR_PANORAMA_SHARE_INTENT;
- final boolean canShare =
- numSelected < MAX_SELECTED_ITEMS_FOR_SHARE_INTENT;
-
- final GetAllPanoramaSupports supportCallback = canSharePanoramas ?
- new GetAllPanoramaSupports(selected, jc)
- : null;
-
- // Pass2: Deal with expanded media object list for sharing operation.
- final Intent share_panorama_intent = canSharePanoramas ?
- computePanoramaSharingIntent(jc, MAX_SELECTED_ITEMS_FOR_PANORAMA_SHARE_INTENT)
- : new Intent();
- final Intent share_intent = canShare ?
- computeSharingIntent(jc, MAX_SELECTED_ITEMS_FOR_SHARE_INTENT)
- : new Intent();
-
- if (canSharePanoramas) {
- supportCallback.waitForPanoramaSupport();
- }
- if (jc.isCancelled()) {
- return null;
- }
- mMainHandler.post(new Runnable() {
- @Override
- public void run() {
- mMenuTask = null;
- if (jc.isCancelled()) return;
- MenuExecutor.updateMenuOperation(mMenu, operation);
- MenuExecutor.updateMenuForPanorama(mMenu,
- canSharePanoramas && supportCallback.mAllPanorama360,
- canSharePanoramas && supportCallback.mHasPanorama360);
- if (mSharePanoramaMenuItem != null) {
- mSharePanoramaMenuItem.setEnabled(true);
- if (canSharePanoramas && supportCallback.mAllPanorama360) {
- mShareMenuItem.setShowAsAction(MenuItem.SHOW_AS_ACTION_NEVER);
- mShareMenuItem.setTitle(
- mActivity.getResources().getString(R.string.share_as_photo));
- } else {
- mSharePanoramaMenuItem.setVisible(false);
- mShareMenuItem.setShowAsAction(MenuItem.SHOW_AS_ACTION_IF_ROOM);
- mShareMenuItem.setTitle(
- mActivity.getResources().getString(R.string.share));
- }
- mSharePanoramaActionProvider.setShareIntent(share_panorama_intent);
- }
- if (mShareMenuItem != null) {
- mShareMenuItem.setEnabled(canShare);
- mShareActionProvider.setShareIntent(share_intent);
- }
- }
- });
- return null;
- }
- });
- }
-
- public void pause() {
- if (mMenuTask != null) {
- mMenuTask.cancel();
- mMenuTask = null;
- }
- mMenuExecutor.pause();
- }
-
- public void destroy() {
- mMenuExecutor.destroy();
- }
-
- public void resume() {
- if (mSelectionManager.inSelectionMode()) updateSupportedOperation();
- mMenuExecutor.resume();
- }
-}
diff --git a/src/com/android/gallery3d/ui/AlbumLabelMaker.java b/src/com/android/gallery3d/ui/AlbumLabelMaker.java
deleted file mode 100644
index da1cac0bd..000000000
--- a/src/com/android/gallery3d/ui/AlbumLabelMaker.java
+++ /dev/null
@@ -1,206 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Bitmap.Config;
-import android.graphics.BitmapFactory;
-import android.graphics.Canvas;
-import android.graphics.PorterDuff;
-import android.graphics.Typeface;
-import android.text.TextPaint;
-import android.text.TextUtils;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.data.DataSourceType;
-import com.android.photos.data.GalleryBitmapPool;
-import com.android.gallery3d.util.ThreadPool;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-public class AlbumLabelMaker {
- private static final int BORDER_SIZE = 0;
-
- private final AlbumSetSlotRenderer.LabelSpec mSpec;
- private final TextPaint mTitlePaint;
- private final TextPaint mCountPaint;
- private final Context mContext;
-
- private int mLabelWidth;
- private int mBitmapWidth;
- private int mBitmapHeight;
-
- private final LazyLoadedBitmap mLocalSetIcon;
- private final LazyLoadedBitmap mPicasaIcon;
- private final LazyLoadedBitmap mCameraIcon;
-
- public AlbumLabelMaker(Context context, AlbumSetSlotRenderer.LabelSpec spec) {
- mContext = context;
- mSpec = spec;
- mTitlePaint = getTextPaint(spec.titleFontSize, spec.titleColor, false);
- mCountPaint = getTextPaint(spec.countFontSize, spec.countColor, false);
-
- mLocalSetIcon = new LazyLoadedBitmap(R.drawable.frame_overlay_gallery_folder);
- mPicasaIcon = new LazyLoadedBitmap(R.drawable.frame_overlay_gallery_picasa);
- mCameraIcon = new LazyLoadedBitmap(R.drawable.frame_overlay_gallery_camera);
- }
-
- public static int getBorderSize() {
- return BORDER_SIZE;
- }
-
- private Bitmap getOverlayAlbumIcon(int sourceType) {
- switch (sourceType) {
- case DataSourceType.TYPE_CAMERA:
- return mCameraIcon.get();
- case DataSourceType.TYPE_LOCAL:
- return mLocalSetIcon.get();
- case DataSourceType.TYPE_PICASA:
- return mPicasaIcon.get();
- }
- return null;
- }
-
- private static TextPaint getTextPaint(int textSize, int color, boolean isBold) {
- TextPaint paint = new TextPaint();
- paint.setTextSize(textSize);
- paint.setAntiAlias(true);
- paint.setColor(color);
- //paint.setShadowLayer(2f, 0f, 0f, Color.LTGRAY);
- if (isBold) {
- paint.setTypeface(Typeface.defaultFromStyle(Typeface.BOLD));
- }
- return paint;
- }
-
- private class LazyLoadedBitmap {
- private Bitmap mBitmap;
- private int mResId;
-
- public LazyLoadedBitmap(int resId) {
- mResId = resId;
- }
-
- public synchronized Bitmap get() {
- if (mBitmap == null) {
- BitmapFactory.Options options = new BitmapFactory.Options();
- options.inPreferredConfig = Bitmap.Config.ARGB_8888;
- mBitmap = BitmapFactory.decodeResource(
- mContext.getResources(), mResId, options);
- }
- return mBitmap;
- }
- }
-
- public synchronized void setLabelWidth(int width) {
- if (mLabelWidth == width) return;
- mLabelWidth = width;
- int borders = 2 * BORDER_SIZE;
- mBitmapWidth = width + borders;
- mBitmapHeight = mSpec.labelBackgroundHeight + borders;
- }
-
- public ThreadPool.Job<Bitmap> requestLabel(
- String title, String count, int sourceType) {
- return new AlbumLabelJob(title, count, sourceType);
- }
-
- static void drawText(Canvas canvas,
- int x, int y, String text, int lengthLimit, TextPaint p) {
- // The TextPaint cannot be used concurrently
- synchronized (p) {
- text = TextUtils.ellipsize(
- text, p, lengthLimit, TextUtils.TruncateAt.END).toString();
- canvas.drawText(text, x, y - p.getFontMetricsInt().ascent, p);
- }
- }
-
- private class AlbumLabelJob implements ThreadPool.Job<Bitmap> {
- private final String mTitle;
- private final String mCount;
- private final int mSourceType;
-
- public AlbumLabelJob(String title, String count, int sourceType) {
- mTitle = title;
- mCount = count;
- mSourceType = sourceType;
- }
-
- @Override
- public Bitmap run(JobContext jc) {
- AlbumSetSlotRenderer.LabelSpec s = mSpec;
-
- String title = mTitle;
- String count = mCount;
- Bitmap icon = getOverlayAlbumIcon(mSourceType);
-
- Bitmap bitmap;
- int labelWidth;
-
- synchronized (this) {
- labelWidth = mLabelWidth;
- bitmap = GalleryBitmapPool.getInstance().get(mBitmapWidth, mBitmapHeight);
- }
-
- if (bitmap == null) {
- int borders = 2 * BORDER_SIZE;
- bitmap = Bitmap.createBitmap(labelWidth + borders,
- s.labelBackgroundHeight + borders, Config.ARGB_8888);
- }
-
- Canvas canvas = new Canvas(bitmap);
- canvas.clipRect(BORDER_SIZE, BORDER_SIZE,
- bitmap.getWidth() - BORDER_SIZE,
- bitmap.getHeight() - BORDER_SIZE);
- canvas.drawColor(mSpec.backgroundColor, PorterDuff.Mode.SRC);
-
- canvas.translate(BORDER_SIZE, BORDER_SIZE);
-
- // draw title
- if (jc.isCancelled()) return null;
- int x = s.leftMargin + s.iconSize;
- // TODO: is the offset relevant in new reskin?
- // int y = s.titleOffset;
- int y = (s.labelBackgroundHeight - s.titleFontSize) / 2;
- drawText(canvas, x, y, title, labelWidth - s.leftMargin - x -
- s.titleRightMargin, mTitlePaint);
-
- // draw count
- if (jc.isCancelled()) return null;
- x = labelWidth - s.titleRightMargin;
- y = (s.labelBackgroundHeight - s.countFontSize) / 2;
- drawText(canvas, x, y, count,
- labelWidth - x , mCountPaint);
-
- // draw the icon
- if (icon != null) {
- if (jc.isCancelled()) return null;
- float scale = (float) s.iconSize / icon.getWidth();
- canvas.translate(s.leftMargin, (s.labelBackgroundHeight -
- Math.round(scale * icon.getHeight()))/2f);
- canvas.scale(scale, scale);
- canvas.drawBitmap(icon, 0, 0, null);
- }
-
- return bitmap;
- }
- }
-
- public void recycleLabel(Bitmap label) {
- GalleryBitmapPool.getInstance().put(label);
- }
-}
diff --git a/src/com/android/gallery3d/ui/AlbumSetSlidingWindow.java b/src/com/android/gallery3d/ui/AlbumSetSlidingWindow.java
deleted file mode 100644
index 8149df4b3..000000000
--- a/src/com/android/gallery3d/ui/AlbumSetSlidingWindow.java
+++ /dev/null
@@ -1,549 +0,0 @@
-/*T
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.graphics.Bitmap;
-import android.os.Message;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.app.AlbumSetDataLoader;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.DataSourceType;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.glrenderer.BitmapTexture;
-import com.android.gallery3d.glrenderer.Texture;
-import com.android.gallery3d.glrenderer.TextureUploader;
-import com.android.gallery3d.glrenderer.TiledTexture;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.FutureListener;
-import com.android.gallery3d.util.ThreadPool;
-
-public class AlbumSetSlidingWindow implements AlbumSetDataLoader.DataListener {
- private static final String TAG = "AlbumSetSlidingWindow";
- private static final int MSG_UPDATE_ALBUM_ENTRY = 1;
-
- public static interface Listener {
- public void onSizeChanged(int size);
- public void onContentChanged();
- }
-
- private final AlbumSetDataLoader mSource;
- private int mSize;
-
- private int mContentStart = 0;
- private int mContentEnd = 0;
-
- private int mActiveStart = 0;
- private int mActiveEnd = 0;
-
- private Listener mListener;
-
- private final AlbumSetEntry mData[];
- private final SynchronizedHandler mHandler;
- private final ThreadPool mThreadPool;
- private final AlbumLabelMaker mLabelMaker;
- private final String mLoadingText;
-
- private final TiledTexture.Uploader mContentUploader;
- private final TextureUploader mLabelUploader;
-
- private int mActiveRequestCount = 0;
- private boolean mIsActive = false;
- private BitmapTexture mLoadingLabel;
-
- private int mSlotWidth;
-
- public static class AlbumSetEntry {
- public MediaSet album;
- public MediaItem coverItem;
- public Texture content;
- public BitmapTexture labelTexture;
- public TiledTexture bitmapTexture;
- public Path setPath;
- public String title;
- public int totalCount;
- public int sourceType;
- public int cacheFlag;
- public int cacheStatus;
- public int rotation;
- public boolean isWaitLoadingDisplayed;
- public long setDataVersion;
- public long coverDataVersion;
- private BitmapLoader labelLoader;
- private BitmapLoader coverLoader;
- }
-
- public AlbumSetSlidingWindow(AbstractGalleryActivity activity,
- AlbumSetDataLoader source, AlbumSetSlotRenderer.LabelSpec labelSpec, int cacheSize) {
- source.setModelListener(this);
- mSource = source;
- mData = new AlbumSetEntry[cacheSize];
- mSize = source.size();
- mThreadPool = activity.getThreadPool();
-
- mLabelMaker = new AlbumLabelMaker(activity.getAndroidContext(), labelSpec);
- mLoadingText = activity.getAndroidContext().getString(R.string.loading);
- mContentUploader = new TiledTexture.Uploader(activity.getGLRoot());
- mLabelUploader = new TextureUploader(activity.getGLRoot());
-
- mHandler = new SynchronizedHandler(activity.getGLRoot()) {
- @Override
- public void handleMessage(Message message) {
- Utils.assertTrue(message.what == MSG_UPDATE_ALBUM_ENTRY);
- ((EntryUpdater) message.obj).updateEntry();
- }
- };
- }
-
- public void setListener(Listener listener) {
- mListener = listener;
- }
-
- public AlbumSetEntry get(int slotIndex) {
- if (!isActiveSlot(slotIndex)) {
- Utils.fail("invalid slot: %s outsides (%s, %s)",
- slotIndex, mActiveStart, mActiveEnd);
- }
- return mData[slotIndex % mData.length];
- }
-
- public int size() {
- return mSize;
- }
-
- public boolean isActiveSlot(int slotIndex) {
- return slotIndex >= mActiveStart && slotIndex < mActiveEnd;
- }
-
- private void setContentWindow(int contentStart, int contentEnd) {
- if (contentStart == mContentStart && contentEnd == mContentEnd) return;
-
- if (contentStart >= mContentEnd || mContentStart >= contentEnd) {
- for (int i = mContentStart, n = mContentEnd; i < n; ++i) {
- freeSlotContent(i);
- }
- mSource.setActiveWindow(contentStart, contentEnd);
- for (int i = contentStart; i < contentEnd; ++i) {
- prepareSlotContent(i);
- }
- } else {
- for (int i = mContentStart; i < contentStart; ++i) {
- freeSlotContent(i);
- }
- for (int i = contentEnd, n = mContentEnd; i < n; ++i) {
- freeSlotContent(i);
- }
- mSource.setActiveWindow(contentStart, contentEnd);
- for (int i = contentStart, n = mContentStart; i < n; ++i) {
- prepareSlotContent(i);
- }
- for (int i = mContentEnd; i < contentEnd; ++i) {
- prepareSlotContent(i);
- }
- }
-
- mContentStart = contentStart;
- mContentEnd = contentEnd;
- }
-
- public void setActiveWindow(int start, int end) {
- if (!(start <= end && end - start <= mData.length && end <= mSize)) {
- Utils.fail("start = %s, end = %s, length = %s, size = %s",
- start, end, mData.length, mSize);
- }
-
- AlbumSetEntry data[] = mData;
- mActiveStart = start;
- mActiveEnd = end;
- int contentStart = Utils.clamp((start + end) / 2 - data.length / 2,
- 0, Math.max(0, mSize - data.length));
- int contentEnd = Math.min(contentStart + data.length, mSize);
- setContentWindow(contentStart, contentEnd);
-
- if (mIsActive) {
- updateTextureUploadQueue();
- updateAllImageRequests();
- }
- }
-
- // We would like to request non active slots in the following order:
- // Order: 8 6 4 2 1 3 5 7
- // |---------|---------------|---------|
- // |<- active ->|
- // |<-------- cached range ----------->|
- private void requestNonactiveImages() {
- int range = Math.max(
- mContentEnd - mActiveEnd, mActiveStart - mContentStart);
- for (int i = 0 ;i < range; ++i) {
- requestImagesInSlot(mActiveEnd + i);
- requestImagesInSlot(mActiveStart - 1 - i);
- }
- }
-
- private void cancelNonactiveImages() {
- int range = Math.max(
- mContentEnd - mActiveEnd, mActiveStart - mContentStart);
- for (int i = 0 ;i < range; ++i) {
- cancelImagesInSlot(mActiveEnd + i);
- cancelImagesInSlot(mActiveStart - 1 - i);
- }
- }
-
- private void requestImagesInSlot(int slotIndex) {
- if (slotIndex < mContentStart || slotIndex >= mContentEnd) return;
- AlbumSetEntry entry = mData[slotIndex % mData.length];
- if (entry.coverLoader != null) entry.coverLoader.startLoad();
- if (entry.labelLoader != null) entry.labelLoader.startLoad();
- }
-
- private void cancelImagesInSlot(int slotIndex) {
- if (slotIndex < mContentStart || slotIndex >= mContentEnd) return;
- AlbumSetEntry entry = mData[slotIndex % mData.length];
- if (entry.coverLoader != null) entry.coverLoader.cancelLoad();
- if (entry.labelLoader != null) entry.labelLoader.cancelLoad();
- }
-
- private static long getDataVersion(MediaObject object) {
- return object == null
- ? MediaSet.INVALID_DATA_VERSION
- : object.getDataVersion();
- }
-
- private void freeSlotContent(int slotIndex) {
- AlbumSetEntry entry = mData[slotIndex % mData.length];
- if (entry.coverLoader != null) entry.coverLoader.recycle();
- if (entry.labelLoader != null) entry.labelLoader.recycle();
- if (entry.labelTexture != null) entry.labelTexture.recycle();
- if (entry.bitmapTexture != null) entry.bitmapTexture.recycle();
- mData[slotIndex % mData.length] = null;
- }
-
- private boolean isLabelChanged(
- AlbumSetEntry entry, String title, int totalCount, int sourceType) {
- return !Utils.equals(entry.title, title)
- || entry.totalCount != totalCount
- || entry.sourceType != sourceType;
- }
-
- private void updateAlbumSetEntry(AlbumSetEntry entry, int slotIndex) {
- MediaSet album = mSource.getMediaSet(slotIndex);
- MediaItem cover = mSource.getCoverItem(slotIndex);
- int totalCount = mSource.getTotalCount(slotIndex);
-
- entry.album = album;
- entry.setDataVersion = getDataVersion(album);
- entry.cacheFlag = identifyCacheFlag(album);
- entry.cacheStatus = identifyCacheStatus(album);
- entry.setPath = (album == null) ? null : album.getPath();
-
- String title = (album == null) ? "" : Utils.ensureNotNull(album.getName());
- int sourceType = DataSourceType.identifySourceType(album);
- if (isLabelChanged(entry, title, totalCount, sourceType)) {
- entry.title = title;
- entry.totalCount = totalCount;
- entry.sourceType = sourceType;
- if (entry.labelLoader != null) {
- entry.labelLoader.recycle();
- entry.labelLoader = null;
- entry.labelTexture = null;
- }
- if (album != null) {
- entry.labelLoader = new AlbumLabelLoader(
- slotIndex, title, totalCount, sourceType);
- }
- }
-
- entry.coverItem = cover;
- if (getDataVersion(cover) != entry.coverDataVersion) {
- entry.coverDataVersion = getDataVersion(cover);
- entry.rotation = (cover == null) ? 0 : cover.getRotation();
- if (entry.coverLoader != null) {
- entry.coverLoader.recycle();
- entry.coverLoader = null;
- entry.bitmapTexture = null;
- entry.content = null;
- }
- if (cover != null) {
- entry.coverLoader = new AlbumCoverLoader(slotIndex, cover);
- }
- }
- }
-
- private void prepareSlotContent(int slotIndex) {
- AlbumSetEntry entry = new AlbumSetEntry();
- updateAlbumSetEntry(entry, slotIndex);
- mData[slotIndex % mData.length] = entry;
- }
-
- private static boolean startLoadBitmap(BitmapLoader loader) {
- if (loader == null) return false;
- loader.startLoad();
- return loader.isRequestInProgress();
- }
-
- private void uploadBackgroundTextureInSlot(int index) {
- if (index < mContentStart || index >= mContentEnd) return;
- AlbumSetEntry entry = mData[index % mData.length];
- if (entry.bitmapTexture != null) {
- mContentUploader.addTexture(entry.bitmapTexture);
- }
- if (entry.labelTexture != null) {
- mLabelUploader.addBgTexture(entry.labelTexture);
- }
- }
-
- private void updateTextureUploadQueue() {
- if (!mIsActive) return;
- mContentUploader.clear();
- mLabelUploader.clear();
-
- // Upload foreground texture
- for (int i = mActiveStart, n = mActiveEnd; i < n; ++i) {
- AlbumSetEntry entry = mData[i % mData.length];
- if (entry.bitmapTexture != null) {
- mContentUploader.addTexture(entry.bitmapTexture);
- }
- if (entry.labelTexture != null) {
- mLabelUploader.addFgTexture(entry.labelTexture);
- }
- }
-
- // add background textures
- int range = Math.max(
- (mContentEnd - mActiveEnd), (mActiveStart - mContentStart));
- for (int i = 0; i < range; ++i) {
- uploadBackgroundTextureInSlot(mActiveEnd + i);
- uploadBackgroundTextureInSlot(mActiveStart - i - 1);
- }
- }
-
- private void updateAllImageRequests() {
- mActiveRequestCount = 0;
- for (int i = mActiveStart, n = mActiveEnd; i < n; ++i) {
- AlbumSetEntry entry = mData[i % mData.length];
- if (startLoadBitmap(entry.coverLoader)) ++mActiveRequestCount;
- if (startLoadBitmap(entry.labelLoader)) ++mActiveRequestCount;
- }
- if (mActiveRequestCount == 0) {
- requestNonactiveImages();
- } else {
- cancelNonactiveImages();
- }
- }
-
- @Override
- public void onSizeChanged(int size) {
- if (mIsActive && mSize != size) {
- mSize = size;
- if (mListener != null) mListener.onSizeChanged(mSize);
- if (mContentEnd > mSize) mContentEnd = mSize;
- if (mActiveEnd > mSize) mActiveEnd = mSize;
- }
- }
-
- @Override
- public void onContentChanged(int index) {
- if (!mIsActive) {
- // paused, ignore slot changed event
- return;
- }
-
- // If the updated content is not cached, ignore it
- if (index < mContentStart || index >= mContentEnd) {
- Log.w(TAG, String.format(
- "invalid update: %s is outside (%s, %s)",
- index, mContentStart, mContentEnd) );
- return;
- }
-
- AlbumSetEntry entry = mData[index % mData.length];
- updateAlbumSetEntry(entry, index);
- updateAllImageRequests();
- updateTextureUploadQueue();
- if (mListener != null && isActiveSlot(index)) {
- mListener.onContentChanged();
- }
- }
-
- public BitmapTexture getLoadingTexture() {
- if (mLoadingLabel == null) {
- Bitmap bitmap = mLabelMaker.requestLabel(
- mLoadingText, "", DataSourceType.TYPE_NOT_CATEGORIZED)
- .run(ThreadPool.JOB_CONTEXT_STUB);
- mLoadingLabel = new BitmapTexture(bitmap);
- mLoadingLabel.setOpaque(false);
- }
- return mLoadingLabel;
- }
-
- public void pause() {
- mIsActive = false;
- mLabelUploader.clear();
- mContentUploader.clear();
- TiledTexture.freeResources();
- for (int i = mContentStart, n = mContentEnd; i < n; ++i) {
- freeSlotContent(i);
- }
- }
-
- public void resume() {
- mIsActive = true;
- TiledTexture.prepareResources();
- for (int i = mContentStart, n = mContentEnd; i < n; ++i) {
- prepareSlotContent(i);
- }
- updateAllImageRequests();
- }
-
- private static interface EntryUpdater {
- public void updateEntry();
- }
-
- private class AlbumCoverLoader extends BitmapLoader implements EntryUpdater {
- private MediaItem mMediaItem;
- private final int mSlotIndex;
-
- public AlbumCoverLoader(int slotIndex, MediaItem item) {
- mSlotIndex = slotIndex;
- mMediaItem = item;
- }
-
- @Override
- protected Future<Bitmap> submitBitmapTask(FutureListener<Bitmap> l) {
- return mThreadPool.submit(mMediaItem.requestImage(
- MediaItem.TYPE_MICROTHUMBNAIL), l);
- }
-
- @Override
- protected void onLoadComplete(Bitmap bitmap) {
- mHandler.obtainMessage(MSG_UPDATE_ALBUM_ENTRY, this).sendToTarget();
- }
-
- @Override
- public void updateEntry() {
- Bitmap bitmap = getBitmap();
- if (bitmap == null) return; // error or recycled
-
- AlbumSetEntry entry = mData[mSlotIndex % mData.length];
- TiledTexture texture = new TiledTexture(bitmap);
- entry.bitmapTexture = texture;
- entry.content = texture;
-
- if (isActiveSlot(mSlotIndex)) {
- mContentUploader.addTexture(texture);
- --mActiveRequestCount;
- if (mActiveRequestCount == 0) requestNonactiveImages();
- if (mListener != null) mListener.onContentChanged();
- } else {
- mContentUploader.addTexture(texture);
- }
- }
- }
-
- private static int identifyCacheFlag(MediaSet set) {
- if (set == null || (set.getSupportedOperations()
- & MediaSet.SUPPORT_CACHE) == 0) {
- return MediaSet.CACHE_FLAG_NO;
- }
-
- return set.getCacheFlag();
- }
-
- private static int identifyCacheStatus(MediaSet set) {
- if (set == null || (set.getSupportedOperations()
- & MediaSet.SUPPORT_CACHE) == 0) {
- return MediaSet.CACHE_STATUS_NOT_CACHED;
- }
-
- return set.getCacheStatus();
- }
-
- private class AlbumLabelLoader extends BitmapLoader implements EntryUpdater {
- private final int mSlotIndex;
- private final String mTitle;
- private final int mTotalCount;
- private final int mSourceType;
-
- public AlbumLabelLoader(
- int slotIndex, String title, int totalCount, int sourceType) {
- mSlotIndex = slotIndex;
- mTitle = title;
- mTotalCount = totalCount;
- mSourceType = sourceType;
- }
-
- @Override
- protected Future<Bitmap> submitBitmapTask(FutureListener<Bitmap> l) {
- return mThreadPool.submit(mLabelMaker.requestLabel(
- mTitle, String.valueOf(mTotalCount), mSourceType), l);
- }
-
- @Override
- protected void onLoadComplete(Bitmap bitmap) {
- mHandler.obtainMessage(MSG_UPDATE_ALBUM_ENTRY, this).sendToTarget();
- }
-
- @Override
- public void updateEntry() {
- Bitmap bitmap = getBitmap();
- if (bitmap == null) return; // Error or recycled
-
- AlbumSetEntry entry = mData[mSlotIndex % mData.length];
- BitmapTexture texture = new BitmapTexture(bitmap);
- texture.setOpaque(false);
- entry.labelTexture = texture;
-
- if (isActiveSlot(mSlotIndex)) {
- mLabelUploader.addFgTexture(texture);
- --mActiveRequestCount;
- if (mActiveRequestCount == 0) requestNonactiveImages();
- if (mListener != null) mListener.onContentChanged();
- } else {
- mLabelUploader.addBgTexture(texture);
- }
- }
- }
-
- public void onSlotSizeChanged(int width, int height) {
- if (mSlotWidth == width) return;
-
- mSlotWidth = width;
- mLoadingLabel = null;
- mLabelMaker.setLabelWidth(mSlotWidth);
-
- if (!mIsActive) return;
-
- for (int i = mContentStart, n = mContentEnd; i < n; ++i) {
- AlbumSetEntry entry = mData[i % mData.length];
- if (entry.labelLoader != null) {
- entry.labelLoader.recycle();
- entry.labelLoader = null;
- entry.labelTexture = null;
- }
- if (entry.album != null) {
- entry.labelLoader = new AlbumLabelLoader(i,
- entry.title, entry.totalCount, entry.sourceType);
- }
- }
- updateAllImageRequests();
- updateTextureUploadQueue();
- }
-}
diff --git a/src/com/android/gallery3d/ui/AlbumSetSlotRenderer.java b/src/com/android/gallery3d/ui/AlbumSetSlotRenderer.java
deleted file mode 100644
index 5332ef89a..000000000
--- a/src/com/android/gallery3d/ui/AlbumSetSlotRenderer.java
+++ /dev/null
@@ -1,242 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.app.AlbumSetDataLoader;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.glrenderer.ColorTexture;
-import com.android.gallery3d.glrenderer.FadeInTexture;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.ResourceTexture;
-import com.android.gallery3d.glrenderer.Texture;
-import com.android.gallery3d.glrenderer.TiledTexture;
-import com.android.gallery3d.glrenderer.UploadedTexture;
-import com.android.gallery3d.ui.AlbumSetSlidingWindow.AlbumSetEntry;
-
-public class AlbumSetSlotRenderer extends AbstractSlotRenderer {
- @SuppressWarnings("unused")
- private static final String TAG = "AlbumSetView";
- private static final int CACHE_SIZE = 96;
- private final int mPlaceholderColor;
-
- private final ColorTexture mWaitLoadingTexture;
- private final ResourceTexture mCameraOverlay;
- private final AbstractGalleryActivity mActivity;
- private final SelectionManager mSelectionManager;
- protected final LabelSpec mLabelSpec;
-
- protected AlbumSetSlidingWindow mDataWindow;
- private SlotView mSlotView;
-
- private int mPressedIndex = -1;
- private boolean mAnimatePressedUp;
- private Path mHighlightItemPath = null;
- private boolean mInSelectionMode;
-
- public static class LabelSpec {
- public int labelBackgroundHeight;
- public int titleOffset;
- public int countOffset;
- public int titleFontSize;
- public int countFontSize;
- public int leftMargin;
- public int iconSize;
- public int titleRightMargin;
- public int backgroundColor;
- public int titleColor;
- public int countColor;
- public int borderSize;
- }
-
- public AlbumSetSlotRenderer(AbstractGalleryActivity activity,
- SelectionManager selectionManager,
- SlotView slotView, LabelSpec labelSpec, int placeholderColor) {
- super (activity);
- mActivity = activity;
- mSelectionManager = selectionManager;
- mSlotView = slotView;
- mLabelSpec = labelSpec;
- mPlaceholderColor = placeholderColor;
-
- mWaitLoadingTexture = new ColorTexture(mPlaceholderColor);
- mWaitLoadingTexture.setSize(1, 1);
- mCameraOverlay = new ResourceTexture(activity,
- R.drawable.ic_cameraalbum_overlay);
- }
-
- public void setPressedIndex(int index) {
- if (mPressedIndex == index) return;
- mPressedIndex = index;
- mSlotView.invalidate();
- }
-
- public void setPressedUp() {
- if (mPressedIndex == -1) return;
- mAnimatePressedUp = true;
- mSlotView.invalidate();
- }
-
- public void setHighlightItemPath(Path path) {
- if (mHighlightItemPath == path) return;
- mHighlightItemPath = path;
- mSlotView.invalidate();
- }
-
- public void setModel(AlbumSetDataLoader model) {
- if (mDataWindow != null) {
- mDataWindow.setListener(null);
- mDataWindow = null;
- mSlotView.setSlotCount(0);
- }
- if (model != null) {
- mDataWindow = new AlbumSetSlidingWindow(
- mActivity, model, mLabelSpec, CACHE_SIZE);
- mDataWindow.setListener(new MyCacheListener());
- mSlotView.setSlotCount(mDataWindow.size());
- }
- }
-
- private static Texture checkLabelTexture(Texture texture) {
- return ((texture instanceof UploadedTexture)
- && ((UploadedTexture) texture).isUploading())
- ? null
- : texture;
- }
-
- private static Texture checkContentTexture(Texture texture) {
- return ((texture instanceof TiledTexture)
- && !((TiledTexture) texture).isReady())
- ? null
- : texture;
- }
-
- @Override
- public int renderSlot(GLCanvas canvas, int index, int pass, int width, int height) {
- AlbumSetEntry entry = mDataWindow.get(index);
- int renderRequestFlags = 0;
- renderRequestFlags |= renderContent(canvas, entry, width, height);
- renderRequestFlags |= renderLabel(canvas, entry, width, height);
- renderRequestFlags |= renderOverlay(canvas, index, entry, width, height);
- return renderRequestFlags;
- }
-
- protected int renderOverlay(
- GLCanvas canvas, int index, AlbumSetEntry entry, int width, int height) {
- int renderRequestFlags = 0;
- if (entry.album != null && entry.album.isCameraRoll()) {
- int uncoveredHeight = height - mLabelSpec.labelBackgroundHeight;
- int dim = uncoveredHeight / 2;
- mCameraOverlay.draw(canvas, (width - dim) / 2,
- (uncoveredHeight - dim) / 2, dim, dim);
- }
- if (mPressedIndex == index) {
- if (mAnimatePressedUp) {
- drawPressedUpFrame(canvas, width, height);
- renderRequestFlags |= SlotView.RENDER_MORE_FRAME;
- if (isPressedUpFrameFinished()) {
- mAnimatePressedUp = false;
- mPressedIndex = -1;
- }
- } else {
- drawPressedFrame(canvas, width, height);
- }
- } else if ((mHighlightItemPath != null) && (mHighlightItemPath == entry.setPath)) {
- drawSelectedFrame(canvas, width, height);
- } else if (mInSelectionMode && mSelectionManager.isItemSelected(entry.setPath)) {
- drawSelectedFrame(canvas, width, height);
- }
- return renderRequestFlags;
- }
-
- protected int renderContent(
- GLCanvas canvas, AlbumSetEntry entry, int width, int height) {
- int renderRequestFlags = 0;
-
- Texture content = checkContentTexture(entry.content);
- if (content == null) {
- content = mWaitLoadingTexture;
- entry.isWaitLoadingDisplayed = true;
- } else if (entry.isWaitLoadingDisplayed) {
- entry.isWaitLoadingDisplayed = false;
- content = new FadeInTexture(mPlaceholderColor, entry.bitmapTexture);
- entry.content = content;
- }
- drawContent(canvas, content, width, height, entry.rotation);
- if ((content instanceof FadeInTexture) &&
- ((FadeInTexture) content).isAnimating()) {
- renderRequestFlags |= SlotView.RENDER_MORE_FRAME;
- }
-
- return renderRequestFlags;
- }
-
- protected int renderLabel(
- GLCanvas canvas, AlbumSetEntry entry, int width, int height) {
- Texture content = checkLabelTexture(entry.labelTexture);
- if (content == null) {
- content = mWaitLoadingTexture;
- }
- int b = AlbumLabelMaker.getBorderSize();
- int h = mLabelSpec.labelBackgroundHeight;
- content.draw(canvas, -b, height - h + b, width + b + b, h);
-
- return 0;
- }
-
- @Override
- public void prepareDrawing() {
- mInSelectionMode = mSelectionManager.inSelectionMode();
- }
-
- private class MyCacheListener implements AlbumSetSlidingWindow.Listener {
-
- @Override
- public void onSizeChanged(int size) {
- mSlotView.setSlotCount(size);
- }
-
- @Override
- public void onContentChanged() {
- mSlotView.invalidate();
- }
- }
-
- public void pause() {
- mDataWindow.pause();
- }
-
- public void resume() {
- mDataWindow.resume();
- }
-
- @Override
- public void onVisibleRangeChanged(int visibleStart, int visibleEnd) {
- if (mDataWindow != null) {
- mDataWindow.setActiveWindow(visibleStart, visibleEnd);
- }
- }
-
- @Override
- public void onSlotSizeChanged(int width, int height) {
- if (mDataWindow != null) {
- mDataWindow.onSlotSizeChanged(width, height);
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/AlbumSlidingWindow.java b/src/com/android/gallery3d/ui/AlbumSlidingWindow.java
deleted file mode 100644
index fec7d1e92..000000000
--- a/src/com/android/gallery3d/ui/AlbumSlidingWindow.java
+++ /dev/null
@@ -1,365 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.graphics.Bitmap;
-import android.os.Message;
-
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.app.AlbumDataLoader;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.MediaObject.PanoramaSupportCallback;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.glrenderer.Texture;
-import com.android.gallery3d.glrenderer.TiledTexture;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.FutureListener;
-import com.android.gallery3d.util.JobLimiter;
-
-public class AlbumSlidingWindow implements AlbumDataLoader.DataListener {
- @SuppressWarnings("unused")
- private static final String TAG = "AlbumSlidingWindow";
-
- private static final int MSG_UPDATE_ENTRY = 0;
- private static final int JOB_LIMIT = 2;
-
- public static interface Listener {
- public void onSizeChanged(int size);
- public void onContentChanged();
- }
-
- public static class AlbumEntry {
- public MediaItem item;
- public Path path;
- public boolean isPanorama;
- public int rotation;
- public int mediaType;
- public boolean isWaitDisplayed;
- public TiledTexture bitmapTexture;
- public Texture content;
- private BitmapLoader contentLoader;
- private PanoSupportListener mPanoSupportListener;
- }
-
- private final AlbumDataLoader mSource;
- private final AlbumEntry mData[];
- private final SynchronizedHandler mHandler;
- private final JobLimiter mThreadPool;
- private final TiledTexture.Uploader mTileUploader;
-
- private int mSize;
-
- private int mContentStart = 0;
- private int mContentEnd = 0;
-
- private int mActiveStart = 0;
- private int mActiveEnd = 0;
-
- private Listener mListener;
-
- private int mActiveRequestCount = 0;
- private boolean mIsActive = false;
-
- private class PanoSupportListener implements PanoramaSupportCallback {
- public final AlbumEntry mEntry;
- public PanoSupportListener (AlbumEntry entry) {
- mEntry = entry;
- }
- @Override
- public void panoramaInfoAvailable(MediaObject mediaObject, boolean isPanorama,
- boolean isPanorama360) {
- if (mEntry != null) mEntry.isPanorama = isPanorama;
- }
- }
-
- public AlbumSlidingWindow(AbstractGalleryActivity activity,
- AlbumDataLoader source, int cacheSize) {
- source.setDataListener(this);
- mSource = source;
- mData = new AlbumEntry[cacheSize];
- mSize = source.size();
-
- mHandler = new SynchronizedHandler(activity.getGLRoot()) {
- @Override
- public void handleMessage(Message message) {
- Utils.assertTrue(message.what == MSG_UPDATE_ENTRY);
- ((ThumbnailLoader) message.obj).updateEntry();
- }
- };
-
- mThreadPool = new JobLimiter(activity.getThreadPool(), JOB_LIMIT);
- mTileUploader = new TiledTexture.Uploader(activity.getGLRoot());
- }
-
- public void setListener(Listener listener) {
- mListener = listener;
- }
-
- public AlbumEntry get(int slotIndex) {
- if (!isActiveSlot(slotIndex)) {
- Utils.fail("invalid slot: %s outsides (%s, %s)",
- slotIndex, mActiveStart, mActiveEnd);
- }
- return mData[slotIndex % mData.length];
- }
-
- public boolean isActiveSlot(int slotIndex) {
- return slotIndex >= mActiveStart && slotIndex < mActiveEnd;
- }
-
- private void setContentWindow(int contentStart, int contentEnd) {
- if (contentStart == mContentStart && contentEnd == mContentEnd) return;
-
- if (!mIsActive) {
- mContentStart = contentStart;
- mContentEnd = contentEnd;
- mSource.setActiveWindow(contentStart, contentEnd);
- return;
- }
-
- if (contentStart >= mContentEnd || mContentStart >= contentEnd) {
- for (int i = mContentStart, n = mContentEnd; i < n; ++i) {
- freeSlotContent(i);
- }
- mSource.setActiveWindow(contentStart, contentEnd);
- for (int i = contentStart; i < contentEnd; ++i) {
- prepareSlotContent(i);
- }
- } else {
- for (int i = mContentStart; i < contentStart; ++i) {
- freeSlotContent(i);
- }
- for (int i = contentEnd, n = mContentEnd; i < n; ++i) {
- freeSlotContent(i);
- }
- mSource.setActiveWindow(contentStart, contentEnd);
- for (int i = contentStart, n = mContentStart; i < n; ++i) {
- prepareSlotContent(i);
- }
- for (int i = mContentEnd; i < contentEnd; ++i) {
- prepareSlotContent(i);
- }
- }
-
- mContentStart = contentStart;
- mContentEnd = contentEnd;
- }
-
- public void setActiveWindow(int start, int end) {
- if (!(start <= end && end - start <= mData.length && end <= mSize)) {
- Utils.fail("%s, %s, %s, %s", start, end, mData.length, mSize);
- }
- AlbumEntry data[] = mData;
-
- mActiveStart = start;
- mActiveEnd = end;
-
- int contentStart = Utils.clamp((start + end) / 2 - data.length / 2,
- 0, Math.max(0, mSize - data.length));
- int contentEnd = Math.min(contentStart + data.length, mSize);
- setContentWindow(contentStart, contentEnd);
- updateTextureUploadQueue();
- if (mIsActive) updateAllImageRequests();
- }
-
- private void uploadBgTextureInSlot(int index) {
- if (index < mContentEnd && index >= mContentStart) {
- AlbumEntry entry = mData[index % mData.length];
- if (entry.bitmapTexture != null) {
- mTileUploader.addTexture(entry.bitmapTexture);
- }
- }
- }
-
- private void updateTextureUploadQueue() {
- if (!mIsActive) return;
- mTileUploader.clear();
-
- // add foreground textures
- for (int i = mActiveStart, n = mActiveEnd; i < n; ++i) {
- AlbumEntry entry = mData[i % mData.length];
- if (entry.bitmapTexture != null) {
- mTileUploader.addTexture(entry.bitmapTexture);
- }
- }
-
- // add background textures
- int range = Math.max(
- (mContentEnd - mActiveEnd), (mActiveStart - mContentStart));
- for (int i = 0; i < range; ++i) {
- uploadBgTextureInSlot(mActiveEnd + i);
- uploadBgTextureInSlot(mActiveStart - i - 1);
- }
- }
-
- // We would like to request non active slots in the following order:
- // Order: 8 6 4 2 1 3 5 7
- // |---------|---------------|---------|
- // |<- active ->|
- // |<-------- cached range ----------->|
- private void requestNonactiveImages() {
- int range = Math.max(
- (mContentEnd - mActiveEnd), (mActiveStart - mContentStart));
- for (int i = 0 ;i < range; ++i) {
- requestSlotImage(mActiveEnd + i);
- requestSlotImage(mActiveStart - 1 - i);
- }
- }
-
- // return whether the request is in progress or not
- private boolean requestSlotImage(int slotIndex) {
- if (slotIndex < mContentStart || slotIndex >= mContentEnd) return false;
- AlbumEntry entry = mData[slotIndex % mData.length];
- if (entry.content != null || entry.item == null) return false;
-
- // Set up the panorama callback
- entry.mPanoSupportListener = new PanoSupportListener(entry);
- entry.item.getPanoramaSupport(entry.mPanoSupportListener);
-
- entry.contentLoader.startLoad();
- return entry.contentLoader.isRequestInProgress();
- }
-
- private void cancelNonactiveImages() {
- int range = Math.max(
- (mContentEnd - mActiveEnd), (mActiveStart - mContentStart));
- for (int i = 0 ;i < range; ++i) {
- cancelSlotImage(mActiveEnd + i);
- cancelSlotImage(mActiveStart - 1 - i);
- }
- }
-
- private void cancelSlotImage(int slotIndex) {
- if (slotIndex < mContentStart || slotIndex >= mContentEnd) return;
- AlbumEntry item = mData[slotIndex % mData.length];
- if (item.contentLoader != null) item.contentLoader.cancelLoad();
- }
-
- private void freeSlotContent(int slotIndex) {
- AlbumEntry data[] = mData;
- int index = slotIndex % data.length;
- AlbumEntry entry = data[index];
- if (entry.contentLoader != null) entry.contentLoader.recycle();
- if (entry.bitmapTexture != null) entry.bitmapTexture.recycle();
- data[index] = null;
- }
-
- private void prepareSlotContent(int slotIndex) {
- AlbumEntry entry = new AlbumEntry();
- MediaItem item = mSource.get(slotIndex); // item could be null;
- entry.item = item;
- entry.mediaType = (item == null)
- ? MediaItem.MEDIA_TYPE_UNKNOWN
- : entry.item.getMediaType();
- entry.path = (item == null) ? null : item.getPath();
- entry.rotation = (item == null) ? 0 : item.getRotation();
- entry.contentLoader = new ThumbnailLoader(slotIndex, entry.item);
- mData[slotIndex % mData.length] = entry;
- }
-
- private void updateAllImageRequests() {
- mActiveRequestCount = 0;
- for (int i = mActiveStart, n = mActiveEnd; i < n; ++i) {
- if (requestSlotImage(i)) ++mActiveRequestCount;
- }
- if (mActiveRequestCount == 0) {
- requestNonactiveImages();
- } else {
- cancelNonactiveImages();
- }
- }
-
- private class ThumbnailLoader extends BitmapLoader {
- private final int mSlotIndex;
- private final MediaItem mItem;
-
- public ThumbnailLoader(int slotIndex, MediaItem item) {
- mSlotIndex = slotIndex;
- mItem = item;
- }
-
- @Override
- protected Future<Bitmap> submitBitmapTask(FutureListener<Bitmap> l) {
- return mThreadPool.submit(
- mItem.requestImage(MediaItem.TYPE_MICROTHUMBNAIL), this);
- }
-
- @Override
- protected void onLoadComplete(Bitmap bitmap) {
- mHandler.obtainMessage(MSG_UPDATE_ENTRY, this).sendToTarget();
- }
-
- public void updateEntry() {
- Bitmap bitmap = getBitmap();
- if (bitmap == null) return; // error or recycled
- AlbumEntry entry = mData[mSlotIndex % mData.length];
- entry.bitmapTexture = new TiledTexture(bitmap);
- entry.content = entry.bitmapTexture;
-
- if (isActiveSlot(mSlotIndex)) {
- mTileUploader.addTexture(entry.bitmapTexture);
- --mActiveRequestCount;
- if (mActiveRequestCount == 0) requestNonactiveImages();
- if (mListener != null) mListener.onContentChanged();
- } else {
- mTileUploader.addTexture(entry.bitmapTexture);
- }
- }
- }
-
- @Override
- public void onSizeChanged(int size) {
- if (mSize != size) {
- mSize = size;
- if (mListener != null) mListener.onSizeChanged(mSize);
- if (mContentEnd > mSize) mContentEnd = mSize;
- if (mActiveEnd > mSize) mActiveEnd = mSize;
- }
- }
-
- @Override
- public void onContentChanged(int index) {
- if (index >= mContentStart && index < mContentEnd && mIsActive) {
- freeSlotContent(index);
- prepareSlotContent(index);
- updateAllImageRequests();
- if (mListener != null && isActiveSlot(index)) {
- mListener.onContentChanged();
- }
- }
- }
-
- public void resume() {
- mIsActive = true;
- TiledTexture.prepareResources();
- for (int i = mContentStart, n = mContentEnd; i < n; ++i) {
- prepareSlotContent(i);
- }
- updateAllImageRequests();
- }
-
- public void pause() {
- mIsActive = false;
- mTileUploader.clear();
- TiledTexture.freeResources();
- for (int i = mContentStart, n = mContentEnd; i < n; ++i) {
- freeSlotContent(i);
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/AlbumSlotRenderer.java b/src/com/android/gallery3d/ui/AlbumSlotRenderer.java
deleted file mode 100644
index dc6c89b0e..000000000
--- a/src/com/android/gallery3d/ui/AlbumSlotRenderer.java
+++ /dev/null
@@ -1,201 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.app.AlbumDataLoader;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.glrenderer.ColorTexture;
-import com.android.gallery3d.glrenderer.FadeInTexture;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.Texture;
-import com.android.gallery3d.glrenderer.TiledTexture;
-
-public class AlbumSlotRenderer extends AbstractSlotRenderer {
- @SuppressWarnings("unused")
- private static final String TAG = "AlbumView";
-
- public interface SlotFilter {
- public boolean acceptSlot(int index);
- }
-
- private final int mPlaceholderColor;
- private static final int CACHE_SIZE = 96;
-
- private AlbumSlidingWindow mDataWindow;
- private final AbstractGalleryActivity mActivity;
- private final ColorTexture mWaitLoadingTexture;
- private final SlotView mSlotView;
- private final SelectionManager mSelectionManager;
-
- private int mPressedIndex = -1;
- private boolean mAnimatePressedUp;
- private Path mHighlightItemPath = null;
- private boolean mInSelectionMode;
-
- private SlotFilter mSlotFilter;
-
- public AlbumSlotRenderer(AbstractGalleryActivity activity, SlotView slotView,
- SelectionManager selectionManager, int placeholderColor) {
- super(activity);
- mActivity = activity;
- mSlotView = slotView;
- mSelectionManager = selectionManager;
- mPlaceholderColor = placeholderColor;
-
- mWaitLoadingTexture = new ColorTexture(mPlaceholderColor);
- mWaitLoadingTexture.setSize(1, 1);
- }
-
- public void setPressedIndex(int index) {
- if (mPressedIndex == index) return;
- mPressedIndex = index;
- mSlotView.invalidate();
- }
-
- public void setPressedUp() {
- if (mPressedIndex == -1) return;
- mAnimatePressedUp = true;
- mSlotView.invalidate();
- }
-
- public void setHighlightItemPath(Path path) {
- if (mHighlightItemPath == path) return;
- mHighlightItemPath = path;
- mSlotView.invalidate();
- }
-
- public void setModel(AlbumDataLoader model) {
- if (mDataWindow != null) {
- mDataWindow.setListener(null);
- mSlotView.setSlotCount(0);
- mDataWindow = null;
- }
- if (model != null) {
- mDataWindow = new AlbumSlidingWindow(mActivity, model, CACHE_SIZE);
- mDataWindow.setListener(new MyDataModelListener());
- mSlotView.setSlotCount(model.size());
- }
- }
-
- private static Texture checkTexture(Texture texture) {
- return (texture instanceof TiledTexture)
- && !((TiledTexture) texture).isReady()
- ? null
- : texture;
- }
-
- @Override
- public int renderSlot(GLCanvas canvas, int index, int pass, int width, int height) {
- if (mSlotFilter != null && !mSlotFilter.acceptSlot(index)) return 0;
-
- AlbumSlidingWindow.AlbumEntry entry = mDataWindow.get(index);
-
- int renderRequestFlags = 0;
-
- Texture content = checkTexture(entry.content);
- if (content == null) {
- content = mWaitLoadingTexture;
- entry.isWaitDisplayed = true;
- } else if (entry.isWaitDisplayed) {
- entry.isWaitDisplayed = false;
- content = new FadeInTexture(mPlaceholderColor, entry.bitmapTexture);
- entry.content = content;
- }
- drawContent(canvas, content, width, height, entry.rotation);
- if ((content instanceof FadeInTexture) &&
- ((FadeInTexture) content).isAnimating()) {
- renderRequestFlags |= SlotView.RENDER_MORE_FRAME;
- }
-
- if (entry.mediaType == MediaObject.MEDIA_TYPE_VIDEO) {
- drawVideoOverlay(canvas, width, height);
- }
-
- if (entry.isPanorama) {
- drawPanoramaIcon(canvas, width, height);
- }
-
- renderRequestFlags |= renderOverlay(canvas, index, entry, width, height);
-
- return renderRequestFlags;
- }
-
- private int renderOverlay(GLCanvas canvas, int index,
- AlbumSlidingWindow.AlbumEntry entry, int width, int height) {
- int renderRequestFlags = 0;
- if (mPressedIndex == index) {
- if (mAnimatePressedUp) {
- drawPressedUpFrame(canvas, width, height);
- renderRequestFlags |= SlotView.RENDER_MORE_FRAME;
- if (isPressedUpFrameFinished()) {
- mAnimatePressedUp = false;
- mPressedIndex = -1;
- }
- } else {
- drawPressedFrame(canvas, width, height);
- }
- } else if ((entry.path != null) && (mHighlightItemPath == entry.path)) {
- drawSelectedFrame(canvas, width, height);
- } else if (mInSelectionMode && mSelectionManager.isItemSelected(entry.path)) {
- drawSelectedFrame(canvas, width, height);
- }
- return renderRequestFlags;
- }
-
- private class MyDataModelListener implements AlbumSlidingWindow.Listener {
- @Override
- public void onContentChanged() {
- mSlotView.invalidate();
- }
-
- @Override
- public void onSizeChanged(int size) {
- mSlotView.setSlotCount(size);
- }
- }
-
- public void resume() {
- mDataWindow.resume();
- }
-
- public void pause() {
- mDataWindow.pause();
- }
-
- @Override
- public void prepareDrawing() {
- mInSelectionMode = mSelectionManager.inSelectionMode();
- }
-
- @Override
- public void onVisibleRangeChanged(int visibleStart, int visibleEnd) {
- if (mDataWindow != null) {
- mDataWindow.setActiveWindow(visibleStart, visibleEnd);
- }
- }
-
- @Override
- public void onSlotSizeChanged(int width, int height) {
- // Do nothing
- }
-
- public void setSlotFilter(SlotFilter slotFilter) {
- mSlotFilter = slotFilter;
- }
-}
diff --git a/src/com/android/gallery3d/ui/AnimationTime.java b/src/com/android/gallery3d/ui/AnimationTime.java
deleted file mode 100644
index 063677423..000000000
--- a/src/com/android/gallery3d/ui/AnimationTime.java
+++ /dev/null
@@ -1,45 +0,0 @@
-
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.os.SystemClock;
-
-//
-// The animation time should ideally be the vsync time the frame will be
-// displayed, but that is an unknown time in the future. So we use the system
-// time just after eglSwapBuffers (when GLSurfaceView.onDrawFrame is called)
-// as a approximation.
-//
-public class AnimationTime {
- private static volatile long sTime;
-
- // Sets current time as the animation time.
- public static void update() {
- sTime = SystemClock.uptimeMillis();
- }
-
- // Returns the animation time.
- public static long get() {
- return sTime;
- }
-
- public static long startTime() {
- sTime = SystemClock.uptimeMillis();
- return sTime;
- }
-}
diff --git a/src/com/android/gallery3d/ui/BitmapLoader.java b/src/com/android/gallery3d/ui/BitmapLoader.java
deleted file mode 100644
index a708a90f3..000000000
--- a/src/com/android/gallery3d/ui/BitmapLoader.java
+++ /dev/null
@@ -1,108 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.graphics.Bitmap;
-
-import com.android.photos.data.GalleryBitmapPool;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.FutureListener;
-
-// We use this class to
-// 1.) load bitmaps in background.
-// 2.) as a place holder for the loaded bitmap
-public abstract class BitmapLoader implements FutureListener<Bitmap> {
- @SuppressWarnings("unused")
- private static final String TAG = "BitmapLoader";
-
- /* Transition Map:
- * INIT -> REQUESTED, RECYCLED
- * REQUESTED -> INIT (cancel), LOADED, ERROR, RECYCLED
- * LOADED, ERROR -> RECYCLED
- */
- private static final int STATE_INIT = 0;
- private static final int STATE_REQUESTED = 1;
- private static final int STATE_LOADED = 2;
- private static final int STATE_ERROR = 3;
- private static final int STATE_RECYCLED = 4;
-
- private int mState = STATE_INIT;
- // mTask is not null only when a task is on the way
- private Future<Bitmap> mTask;
- private Bitmap mBitmap;
-
- @Override
- public void onFutureDone(Future<Bitmap> future) {
- synchronized (this) {
- mTask = null;
- mBitmap = future.get();
- if (mState == STATE_RECYCLED) {
- if (mBitmap != null) {
- GalleryBitmapPool.getInstance().put(mBitmap);
- mBitmap = null;
- }
- return; // don't call callback
- }
- if (future.isCancelled() && mBitmap == null) {
- if (mState == STATE_REQUESTED) mTask = submitBitmapTask(this);
- return; // don't call callback
- } else {
- mState = mBitmap == null ? STATE_ERROR : STATE_LOADED;
- }
- }
- onLoadComplete(mBitmap);
- }
-
- public synchronized void startLoad() {
- if (mState == STATE_INIT) {
- mState = STATE_REQUESTED;
- if (mTask == null) mTask = submitBitmapTask(this);
- }
- }
-
- public synchronized void cancelLoad() {
- if (mState == STATE_REQUESTED) {
- mState = STATE_INIT;
- if (mTask != null) mTask.cancel();
- }
- }
-
- // Recycle the loader and the bitmap
- public synchronized void recycle() {
- mState = STATE_RECYCLED;
- if (mBitmap != null) {
- GalleryBitmapPool.getInstance().put(mBitmap);
- mBitmap = null;
- }
- if (mTask != null) mTask.cancel();
- }
-
- public synchronized boolean isRequestInProgress() {
- return mState == STATE_REQUESTED;
- }
-
- public synchronized boolean isRecycled() {
- return mState == STATE_RECYCLED;
- }
-
- public synchronized Bitmap getBitmap() {
- return mBitmap;
- }
-
- abstract protected Future<Bitmap> submitBitmapTask(FutureListener<Bitmap> l);
- abstract protected void onLoadComplete(Bitmap bitmap);
-}
diff --git a/src/com/android/gallery3d/ui/BitmapScreenNail.java b/src/com/android/gallery3d/ui/BitmapScreenNail.java
deleted file mode 100644
index a3d403946..000000000
--- a/src/com/android/gallery3d/ui/BitmapScreenNail.java
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.graphics.Bitmap;
-import android.graphics.RectF;
-
-import com.android.gallery3d.glrenderer.BitmapTexture;
-import com.android.gallery3d.glrenderer.GLCanvas;
-
-public class BitmapScreenNail implements ScreenNail {
- private final BitmapTexture mBitmapTexture;
-
- public BitmapScreenNail(Bitmap bitmap) {
- mBitmapTexture = new BitmapTexture(bitmap);
- }
-
- @Override
- public int getWidth() {
- return mBitmapTexture.getWidth();
- }
-
- @Override
- public int getHeight() {
- return mBitmapTexture.getHeight();
- }
-
- @Override
- public void draw(GLCanvas canvas, int x, int y, int width, int height) {
- mBitmapTexture.draw(canvas, x, y, width, height);
- }
-
- @Override
- public void noDraw() {
- // do nothing
- }
-
- @Override
- public void recycle() {
- mBitmapTexture.recycle();
- }
-
- @Override
- public void draw(GLCanvas canvas, RectF source, RectF dest) {
- canvas.drawTexture(mBitmapTexture, source, dest);
- }
-}
diff --git a/src/com/android/gallery3d/ui/BitmapTileProvider.java b/src/com/android/gallery3d/ui/BitmapTileProvider.java
deleted file mode 100644
index e1a8b7644..000000000
--- a/src/com/android/gallery3d/ui/BitmapTileProvider.java
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.graphics.Bitmap;
-import android.graphics.Bitmap.Config;
-import android.graphics.Canvas;
-
-import com.android.gallery3d.common.BitmapUtils;
-import com.android.photos.data.GalleryBitmapPool;
-
-import java.util.ArrayList;
-
-public class BitmapTileProvider implements TileImageView.TileSource {
- private final ScreenNail mScreenNail;
- private final Bitmap[] mMipmaps;
- private final Config mConfig;
- private final int mImageWidth;
- private final int mImageHeight;
-
- private boolean mRecycled = false;
-
- public BitmapTileProvider(Bitmap bitmap, int maxBackupSize) {
- mImageWidth = bitmap.getWidth();
- mImageHeight = bitmap.getHeight();
- ArrayList<Bitmap> list = new ArrayList<Bitmap>();
- list.add(bitmap);
- while (bitmap.getWidth() > maxBackupSize
- || bitmap.getHeight() > maxBackupSize) {
- bitmap = BitmapUtils.resizeBitmapByScale(bitmap, 0.5f, false);
- list.add(bitmap);
- }
-
- mScreenNail = new BitmapScreenNail(list.remove(list.size() - 1));
- mMipmaps = list.toArray(new Bitmap[list.size()]);
- mConfig = Config.ARGB_8888;
- }
-
- @Override
- public ScreenNail getScreenNail() {
- return mScreenNail;
- }
-
- @Override
- public int getImageHeight() {
- return mImageHeight;
- }
-
- @Override
- public int getImageWidth() {
- return mImageWidth;
- }
-
- @Override
- public int getLevelCount() {
- return mMipmaps.length;
- }
-
- @Override
- public Bitmap getTile(int level, int x, int y, int tileSize) {
- x >>= level;
- y >>= level;
-
- Bitmap result = GalleryBitmapPool.getInstance().get(tileSize, tileSize);
- if (result == null) {
- result = Bitmap.createBitmap(tileSize, tileSize, mConfig);
- } else {
- result.eraseColor(0);
- }
-
- Bitmap mipmap = mMipmaps[level];
- Canvas canvas = new Canvas(result);
- int offsetX = -x;
- int offsetY = -y;
- canvas.drawBitmap(mipmap, offsetX, offsetY, null);
- return result;
- }
-
- public void recycle() {
- if (mRecycled) return;
- mRecycled = true;
- for (Bitmap bitmap : mMipmaps) {
- BitmapUtils.recycleSilently(bitmap);
- }
- if (mScreenNail != null) {
- mScreenNail.recycle();
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/CacheStorageUsageInfo.java b/src/com/android/gallery3d/ui/CacheStorageUsageInfo.java
deleted file mode 100644
index 46f7a2433..000000000
--- a/src/com/android/gallery3d/ui/CacheStorageUsageInfo.java
+++ /dev/null
@@ -1,90 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.os.StatFs;
-
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.io.File;
-
-public class CacheStorageUsageInfo {
- @SuppressWarnings("unused")
- private static final String TAG = "CacheStorageUsageInfo";
-
- // number of bytes the storage has.
- private long mTotalBytes;
-
- // number of bytes already used.
- private long mUsedBytes;
-
- // number of bytes used for the cache (should be less then usedBytes).
- private long mUsedCacheBytes;
-
- // number of bytes used for the cache if all pending downloads (and removals) are completed.
- private long mTargetCacheBytes;
-
- private AbstractGalleryActivity mActivity;
- private Context mContext;
- private long mUserChangeDelta;
-
- public CacheStorageUsageInfo(AbstractGalleryActivity activity) {
- mActivity = activity;
- mContext = activity.getAndroidContext();
- }
-
- public void increaseTargetCacheSize(long delta) {
- mUserChangeDelta += delta;
- }
-
- public void loadStorageInfo(JobContext jc) {
- File cacheDir = mContext.getExternalCacheDir();
- if (cacheDir == null) {
- cacheDir = mContext.getCacheDir();
- }
-
- String path = cacheDir.getAbsolutePath();
- StatFs stat = new StatFs(path);
- long blockSize = stat.getBlockSize();
- long availableBlocks = stat.getAvailableBlocks();
- long totalBlocks = stat.getBlockCount();
-
- mTotalBytes = blockSize * totalBlocks;
- mUsedBytes = blockSize * (totalBlocks - availableBlocks);
- mUsedCacheBytes = mActivity.getDataManager().getTotalUsedCacheSize();
- mTargetCacheBytes = mActivity.getDataManager().getTotalTargetCacheSize();
- }
-
- public long getTotalBytes() {
- return mTotalBytes;
- }
-
- public long getExpectedUsedBytes() {
- return mUsedBytes - mUsedCacheBytes + mTargetCacheBytes + mUserChangeDelta;
- }
-
- public long getUsedBytes() {
- // Should it be usedBytes - usedCacheBytes + targetCacheBytes ?
- return mUsedBytes;
- }
-
- public long getFreeBytes() {
- return mTotalBytes - mUsedBytes;
- }
-}
diff --git a/src/com/android/gallery3d/ui/CaptureAnimation.java b/src/com/android/gallery3d/ui/CaptureAnimation.java
deleted file mode 100644
index 87c054ab3..000000000
--- a/src/com/android/gallery3d/ui/CaptureAnimation.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.view.animation.AccelerateDecelerateInterpolator;
-import android.view.animation.AccelerateInterpolator;
-import android.view.animation.DecelerateInterpolator;
-import android.view.animation.Interpolator;
-
-public class CaptureAnimation {
- // The amount of change for zooming out.
- private static final float ZOOM_DELTA = 0.2f;
- // Pre-calculated value for convenience.
- private static final float ZOOM_IN_BEGIN = 1f - ZOOM_DELTA;
-
- private static final Interpolator sZoomOutInterpolator =
- new DecelerateInterpolator();
- private static final Interpolator sZoomInInterpolator =
- new AccelerateInterpolator();
- private static final Interpolator sSlideInterpolator =
- new AccelerateDecelerateInterpolator();
-
- // Calculate the slide factor based on the give time fraction.
- public static float calculateSlide(float fraction) {
- return sSlideInterpolator.getInterpolation(fraction);
- }
-
- // Calculate the scale factor based on the given time fraction.
- public static float calculateScale(float fraction) {
- float value;
- if (fraction <= 0.5f) {
- // Zoom in for the beginning.
- value = 1f - ZOOM_DELTA *
- sZoomOutInterpolator.getInterpolation(fraction * 2);
- } else {
- // Zoom out for the ending.
- value = ZOOM_IN_BEGIN + ZOOM_DELTA *
- sZoomInInterpolator.getInterpolation((fraction - 0.5f) * 2f);
- }
- return value;
- }
-}
diff --git a/src/com/android/gallery3d/ui/DetailsAddressResolver.java b/src/com/android/gallery3d/ui/DetailsAddressResolver.java
deleted file mode 100644
index 8de667745..000000000
--- a/src/com/android/gallery3d/ui/DetailsAddressResolver.java
+++ /dev/null
@@ -1,118 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.location.Address;
-import android.os.Handler;
-import android.os.Looper;
-
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.data.MediaDetails;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.FutureListener;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.ReverseGeocoder;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-public class DetailsAddressResolver {
- private AddressResolvingListener mListener;
- private final AbstractGalleryActivity mContext;
- private Future<Address> mAddressLookupJob;
- private final Handler mHandler;
-
- private class AddressLookupJob implements Job<Address> {
- private double[] mLatlng;
-
- protected AddressLookupJob(double[] latlng) {
- mLatlng = latlng;
- }
-
- @Override
- public Address run(JobContext jc) {
- ReverseGeocoder geocoder = new ReverseGeocoder(mContext.getAndroidContext());
- return geocoder.lookupAddress(mLatlng[0], mLatlng[1], true);
- }
- }
-
- public interface AddressResolvingListener {
- public void onAddressAvailable(String address);
- }
-
- public DetailsAddressResolver(AbstractGalleryActivity context) {
- mContext = context;
- mHandler = new Handler(Looper.getMainLooper());
- }
-
- public String resolveAddress(double[] latlng, AddressResolvingListener listener) {
- mListener = listener;
- mAddressLookupJob = mContext.getThreadPool().submit(
- new AddressLookupJob(latlng),
- new FutureListener<Address>() {
- @Override
- public void onFutureDone(final Future<Address> future) {
- mAddressLookupJob = null;
- if (!future.isCancelled()) {
- mHandler.post(new Runnable() {
- @Override
- public void run() {
- updateLocation(future.get());
- }
- });
- }
- }
- });
- return GalleryUtils.formatLatitudeLongitude("(%f,%f)", latlng[0], latlng[1]);
- }
-
- private void updateLocation(Address address) {
- if (address != null) {
- Context context = mContext.getAndroidContext();
- String parts[] = {
- address.getAdminArea(),
- address.getSubAdminArea(),
- address.getLocality(),
- address.getSubLocality(),
- address.getThoroughfare(),
- address.getSubThoroughfare(),
- address.getPremises(),
- address.getPostalCode(),
- address.getCountryName()
- };
-
- String addressText = "";
- for (int i = 0; i < parts.length; i++) {
- if (parts[i] == null || parts[i].isEmpty()) continue;
- if (!addressText.isEmpty()) {
- addressText += ", ";
- }
- addressText += parts[i];
- }
- String text = String.format("%s : %s", DetailsHelper.getDetailsName(
- context, MediaDetails.INDEX_LOCATION), addressText);
- mListener.onAddressAvailable(text);
- }
- }
-
- public void cancel() {
- if (mAddressLookupJob != null) {
- mAddressLookupJob.cancel();
- mAddressLookupJob = null;
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/DetailsHelper.java b/src/com/android/gallery3d/ui/DetailsHelper.java
deleted file mode 100644
index 47296f655..000000000
--- a/src/com/android/gallery3d/ui/DetailsHelper.java
+++ /dev/null
@@ -1,148 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.view.View.MeasureSpec;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.data.MediaDetails;
-import com.android.gallery3d.ui.DetailsAddressResolver.AddressResolvingListener;
-
-public class DetailsHelper {
- private static DetailsAddressResolver sAddressResolver;
- private DetailsViewContainer mContainer;
-
- public interface DetailsSource {
- public int size();
- public int setIndex();
- public MediaDetails getDetails();
- }
-
- public interface CloseListener {
- public void onClose();
- }
-
- public interface DetailsViewContainer {
- public void reloadDetails();
- public void setCloseListener(CloseListener listener);
- public void show();
- public void hide();
- }
-
- public interface ResolutionResolvingListener {
- public void onResolutionAvailable(int width, int height);
- }
-
- public DetailsHelper(AbstractGalleryActivity activity, GLView rootPane, DetailsSource source) {
- mContainer = new DialogDetailsView(activity, source);
- }
-
- public void layout(int left, int top, int right, int bottom) {
- if (mContainer instanceof GLView) {
- GLView view = (GLView) mContainer;
- view.measure(MeasureSpec.UNSPECIFIED,
- MeasureSpec.makeMeasureSpec(bottom - top, MeasureSpec.AT_MOST));
- view.layout(0, top, view.getMeasuredWidth(), top + view.getMeasuredHeight());
- }
- }
-
- public void reloadDetails() {
- mContainer.reloadDetails();
- }
-
- public void setCloseListener(CloseListener listener) {
- mContainer.setCloseListener(listener);
- }
-
- public static String resolveAddress(AbstractGalleryActivity activity, double[] latlng,
- AddressResolvingListener listener) {
- if (sAddressResolver == null) {
- sAddressResolver = new DetailsAddressResolver(activity);
- } else {
- sAddressResolver.cancel();
- }
- return sAddressResolver.resolveAddress(latlng, listener);
- }
-
- public static void resolveResolution(String path, ResolutionResolvingListener listener) {
- Bitmap bitmap = BitmapFactory.decodeFile(path);
- if (bitmap == null) return;
- listener.onResolutionAvailable(bitmap.getWidth(), bitmap.getHeight());
- }
-
- public static void pause() {
- if (sAddressResolver != null) sAddressResolver.cancel();
- }
-
- public void show() {
- mContainer.show();
- }
-
- public void hide() {
- mContainer.hide();
- }
-
- public static String getDetailsName(Context context, int key) {
- switch (key) {
- case MediaDetails.INDEX_TITLE:
- return context.getString(R.string.title);
- case MediaDetails.INDEX_DESCRIPTION:
- return context.getString(R.string.description);
- case MediaDetails.INDEX_DATETIME:
- return context.getString(R.string.time);
- case MediaDetails.INDEX_LOCATION:
- return context.getString(R.string.location);
- case MediaDetails.INDEX_PATH:
- return context.getString(R.string.path);
- case MediaDetails.INDEX_WIDTH:
- return context.getString(R.string.width);
- case MediaDetails.INDEX_HEIGHT:
- return context.getString(R.string.height);
- case MediaDetails.INDEX_ORIENTATION:
- return context.getString(R.string.orientation);
- case MediaDetails.INDEX_DURATION:
- return context.getString(R.string.duration);
- case MediaDetails.INDEX_MIMETYPE:
- return context.getString(R.string.mimetype);
- case MediaDetails.INDEX_SIZE:
- return context.getString(R.string.file_size);
- case MediaDetails.INDEX_MAKE:
- return context.getString(R.string.maker);
- case MediaDetails.INDEX_MODEL:
- return context.getString(R.string.model);
- case MediaDetails.INDEX_FLASH:
- return context.getString(R.string.flash);
- case MediaDetails.INDEX_APERTURE:
- return context.getString(R.string.aperture);
- case MediaDetails.INDEX_FOCAL_LENGTH:
- return context.getString(R.string.focal_length);
- case MediaDetails.INDEX_WHITE_BALANCE:
- return context.getString(R.string.white_balance);
- case MediaDetails.INDEX_EXPOSURE_TIME:
- return context.getString(R.string.exposure_time);
- case MediaDetails.INDEX_ISO:
- return context.getString(R.string.iso);
- default:
- return "Unknown key" + key;
- }
- }
-}
-
-
diff --git a/src/com/android/gallery3d/ui/DialogDetailsView.java b/src/com/android/gallery3d/ui/DialogDetailsView.java
deleted file mode 100644
index 058c03654..000000000
--- a/src/com/android/gallery3d/ui/DialogDetailsView.java
+++ /dev/null
@@ -1,288 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.app.AlertDialog;
-import android.app.Dialog;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.content.DialogInterface.OnDismissListener;
-import android.text.format.Formatter;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.widget.BaseAdapter;
-import android.widget.ListView;
-import android.widget.TextView;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.MediaDetails;
-import com.android.gallery3d.ui.DetailsAddressResolver.AddressResolvingListener;
-import com.android.gallery3d.ui.DetailsHelper.CloseListener;
-import com.android.gallery3d.ui.DetailsHelper.DetailsSource;
-import com.android.gallery3d.ui.DetailsHelper.DetailsViewContainer;
-import com.android.gallery3d.ui.DetailsHelper.ResolutionResolvingListener;
-
-import java.util.ArrayList;
-import java.util.Map.Entry;
-
-public class DialogDetailsView implements DetailsViewContainer {
- @SuppressWarnings("unused")
- private static final String TAG = "DialogDetailsView";
-
- private final AbstractGalleryActivity mActivity;
- private DetailsAdapter mAdapter;
- private MediaDetails mDetails;
- private final DetailsSource mSource;
- private int mIndex;
- private Dialog mDialog;
- private CloseListener mListener;
-
- public DialogDetailsView(AbstractGalleryActivity activity, DetailsSource source) {
- mActivity = activity;
- mSource = source;
- }
-
- @Override
- public void show() {
- reloadDetails();
- mDialog.show();
- }
-
- @Override
- public void hide() {
- mDialog.hide();
- }
-
- @Override
- public void reloadDetails() {
- int index = mSource.setIndex();
- if (index == -1) return;
- MediaDetails details = mSource.getDetails();
- if (details != null) {
- if (mIndex == index && mDetails == details) return;
- mIndex = index;
- mDetails = details;
- setDetails(details);
- }
- }
-
- private void setDetails(MediaDetails details) {
- mAdapter = new DetailsAdapter(details);
- String title = String.format(
- mActivity.getAndroidContext().getString(R.string.details_title),
- mIndex + 1, mSource.size());
- ListView detailsList = (ListView) LayoutInflater.from(mActivity.getAndroidContext()).inflate(
- R.layout.details_list, null, false);
- detailsList.setAdapter(mAdapter);
- mDialog = new AlertDialog.Builder(mActivity)
- .setView(detailsList)
- .setTitle(title)
- .setPositiveButton(R.string.close, new DialogInterface.OnClickListener() {
- @Override
- public void onClick(DialogInterface dialog, int whichButton) {
- mDialog.dismiss();
- }
- })
- .create();
-
- mDialog.setOnDismissListener(new OnDismissListener() {
- @Override
- public void onDismiss(DialogInterface dialog) {
- if (mListener != null) {
- mListener.onClose();
- }
- }
- });
- }
-
-
- private class DetailsAdapter extends BaseAdapter
- implements AddressResolvingListener, ResolutionResolvingListener {
- private final ArrayList<String> mItems;
- private int mLocationIndex;
- private int mWidthIndex = -1;
- private int mHeightIndex = -1;
-
- public DetailsAdapter(MediaDetails details) {
- Context context = mActivity.getAndroidContext();
- mItems = new ArrayList<String>(details.size());
- mLocationIndex = -1;
- setDetails(context, details);
- }
-
- private void setDetails(Context context, MediaDetails details) {
- boolean resolutionIsValid = true;
- String path = null;
- for (Entry<Integer, Object> detail : details) {
- String value;
- switch (detail.getKey()) {
- case MediaDetails.INDEX_LOCATION: {
- double[] latlng = (double[]) detail.getValue();
- mLocationIndex = mItems.size();
- value = DetailsHelper.resolveAddress(mActivity, latlng, this);
- break;
- }
- case MediaDetails.INDEX_SIZE: {
- value = Formatter.formatFileSize(
- context, (Long) detail.getValue());
- break;
- }
- case MediaDetails.INDEX_WHITE_BALANCE: {
- value = "1".equals(detail.getValue())
- ? context.getString(R.string.manual)
- : context.getString(R.string.auto);
- break;
- }
- case MediaDetails.INDEX_FLASH: {
- MediaDetails.FlashState flash =
- (MediaDetails.FlashState) detail.getValue();
- // TODO: camera doesn't fill in the complete values, show more information
- // when it is fixed.
- if (flash.isFlashFired()) {
- value = context.getString(R.string.flash_on);
- } else {
- value = context.getString(R.string.flash_off);
- }
- break;
- }
- case MediaDetails.INDEX_EXPOSURE_TIME: {
- value = (String) detail.getValue();
- double time = Double.valueOf(value);
- if (time < 1.0f) {
- value = String.format("1/%d", (int) (0.5f + 1 / time));
- } else {
- int integer = (int) time;
- time -= integer;
- value = String.valueOf(integer) + "''";
- if (time > 0.0001) {
- value += String.format(" 1/%d", (int) (0.5f + 1 / time));
- }
- }
- break;
- }
- case MediaDetails.INDEX_WIDTH:
- mWidthIndex = mItems.size();
- value = detail.getValue().toString();
- if (value.equalsIgnoreCase("0")) {
- value = context.getString(R.string.unknown);
- resolutionIsValid = false;
- }
- break;
- case MediaDetails.INDEX_HEIGHT: {
- mHeightIndex = mItems.size();
- value = detail.getValue().toString();
- if (value.equalsIgnoreCase("0")) {
- value = context.getString(R.string.unknown);
- resolutionIsValid = false;
- }
- break;
- }
- case MediaDetails.INDEX_PATH:
- // Get the path and then fall through to the default case
- path = detail.getValue().toString();
- default: {
- Object valueObj = detail.getValue();
- // This shouldn't happen, log its key to help us diagnose the problem.
- if (valueObj == null) {
- Utils.fail("%s's value is Null",
- DetailsHelper.getDetailsName(context, detail.getKey()));
- }
- value = valueObj.toString();
- }
- }
- int key = detail.getKey();
- if (details.hasUnit(key)) {
- value = String.format("%s: %s %s", DetailsHelper.getDetailsName(
- context, key), value, context.getString(details.getUnit(key)));
- } else {
- value = String.format("%s: %s", DetailsHelper.getDetailsName(
- context, key), value);
- }
- mItems.add(value);
- if (!resolutionIsValid) {
- DetailsHelper.resolveResolution(path, this);
- }
- }
- }
-
- @Override
- public boolean areAllItemsEnabled() {
- return false;
- }
-
- @Override
- public boolean isEnabled(int position) {
- return false;
- }
-
- @Override
- public int getCount() {
- return mItems.size();
- }
-
- @Override
- public Object getItem(int position) {
- return mDetails.getDetail(position);
- }
-
- @Override
- public long getItemId(int position) {
- return position;
- }
-
- @Override
- public View getView(int position, View convertView, ViewGroup parent) {
- TextView tv;
- if (convertView == null) {
- tv = (TextView) LayoutInflater.from(mActivity.getAndroidContext()).inflate(
- R.layout.details, parent, false);
- } else {
- tv = (TextView) convertView;
- }
- tv.setText(mItems.get(position));
- return tv;
- }
-
- @Override
- public void onAddressAvailable(String address) {
- mItems.set(mLocationIndex, address);
- notifyDataSetChanged();
- }
-
- @Override
- public void onResolutionAvailable(int width, int height) {
- if (width == 0 || height == 0) return;
- // Update the resolution with the new width and height
- Context context = mActivity.getAndroidContext();
- String widthString = String.format("%s: %d", DetailsHelper.getDetailsName(
- context, MediaDetails.INDEX_WIDTH), width);
- String heightString = String.format("%s: %d", DetailsHelper.getDetailsName(
- context, MediaDetails.INDEX_HEIGHT), height);
- mItems.set(mWidthIndex, String.valueOf(widthString));
- mItems.set(mHeightIndex, String.valueOf(heightString));
- notifyDataSetChanged();
- }
- }
-
- @Override
- public void setCloseListener(CloseListener listener) {
- mListener = listener;
- }
-}
diff --git a/src/com/android/gallery3d/ui/DownUpDetector.java b/src/com/android/gallery3d/ui/DownUpDetector.java
deleted file mode 100644
index 19db77262..000000000
--- a/src/com/android/gallery3d/ui/DownUpDetector.java
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.view.MotionEvent;
-
-public class DownUpDetector {
- public interface DownUpListener {
- void onDown(MotionEvent e);
- void onUp(MotionEvent e);
- }
-
- private boolean mStillDown;
- private DownUpListener mListener;
-
- public DownUpDetector(DownUpListener listener) {
- mListener = listener;
- }
-
- private void setState(boolean down, MotionEvent e) {
- if (down == mStillDown) return;
- mStillDown = down;
- if (down) {
- mListener.onDown(e);
- } else {
- mListener.onUp(e);
- }
- }
-
- public void onTouchEvent(MotionEvent ev) {
- switch (ev.getAction() & MotionEvent.ACTION_MASK) {
- case MotionEvent.ACTION_DOWN:
- setState(true, ev);
- break;
-
- case MotionEvent.ACTION_UP:
- case MotionEvent.ACTION_CANCEL:
- case MotionEvent.ACTION_POINTER_DOWN: // Multitouch event - abort.
- setState(false, ev);
- break;
- }
- }
-
- public boolean isDown() {
- return mStillDown;
- }
-}
diff --git a/src/com/android/gallery3d/ui/EdgeEffect.java b/src/com/android/gallery3d/ui/EdgeEffect.java
deleted file mode 100644
index 87ff0c5d3..000000000
--- a/src/com/android/gallery3d/ui/EdgeEffect.java
+++ /dev/null
@@ -1,443 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.graphics.Canvas;
-import android.graphics.Rect;
-import android.view.animation.DecelerateInterpolator;
-import android.view.animation.Interpolator;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.ResourceTexture;
-
-// This is copied from android.widget.EdgeEffect with some small modifications:
-// (1) Copy the images (overscroll_{edge|glow}.png) to local resources.
-// (2) Use "GLCanvas" instead of "Canvas" for draw()'s parameter.
-// (3) Use a private Drawable class (which inherits from ResourceTexture)
-// instead of android.graphics.drawable.Drawable to hold the images.
-// The private Drawable class is used to translate original Canvas calls to
-// corresponding GLCanvas calls.
-
-/**
- * This class performs the graphical effect used at the edges of scrollable widgets
- * when the user scrolls beyond the content bounds in 2D space.
- *
- * <p>EdgeEffect is stateful. Custom widgets using EdgeEffect should create an
- * instance for each edge that should show the effect, feed it input data using
- * the methods {@link #onAbsorb(int)}, {@link #onPull(float)}, and {@link #onRelease()},
- * and draw the effect using {@link #draw(Canvas)} in the widget's overridden
- * {@link android.view.View#draw(Canvas)} method. If {@link #isFinished()} returns
- * false after drawing, the edge effect's animation is not yet complete and the widget
- * should schedule another drawing pass to continue the animation.</p>
- *
- * <p>When drawing, widgets should draw their main content and child views first,
- * usually by invoking <code>super.draw(canvas)</code> from an overridden <code>draw</code>
- * method. (This will invoke onDraw and dispatch drawing to child views as needed.)
- * The edge effect may then be drawn on top of the view's content using the
- * {@link #draw(Canvas)} method.</p>
- */
-public class EdgeEffect {
- @SuppressWarnings("unused")
- private static final String TAG = "EdgeEffect";
-
- // Time it will take the effect to fully recede in ms
- private static final int RECEDE_TIME = 1000;
-
- // Time it will take before a pulled glow begins receding in ms
- private static final int PULL_TIME = 167;
-
- // Time it will take in ms for a pulled glow to decay to partial strength before release
- private static final int PULL_DECAY_TIME = 1000;
-
- private static final float MAX_ALPHA = 0.8f;
- private static final float HELD_EDGE_ALPHA = 0.7f;
- private static final float HELD_EDGE_SCALE_Y = 0.5f;
- private static final float HELD_GLOW_ALPHA = 0.5f;
- private static final float HELD_GLOW_SCALE_Y = 0.5f;
-
- private static final float MAX_GLOW_HEIGHT = 4.f;
-
- private static final float PULL_GLOW_BEGIN = 1.f;
- private static final float PULL_EDGE_BEGIN = 0.6f;
-
- // Minimum velocity that will be absorbed
- private static final int MIN_VELOCITY = 100;
-
- private static final float EPSILON = 0.001f;
-
- private final Drawable mEdge;
- private final Drawable mGlow;
- private int mWidth;
- private int mHeight;
- private final int MIN_WIDTH = 300;
- private final int mMinWidth;
-
- private float mEdgeAlpha;
- private float mEdgeScaleY;
- private float mGlowAlpha;
- private float mGlowScaleY;
-
- private float mEdgeAlphaStart;
- private float mEdgeAlphaFinish;
- private float mEdgeScaleYStart;
- private float mEdgeScaleYFinish;
- private float mGlowAlphaStart;
- private float mGlowAlphaFinish;
- private float mGlowScaleYStart;
- private float mGlowScaleYFinish;
-
- private long mStartTime;
- private float mDuration;
-
- private final Interpolator mInterpolator;
-
- private static final int STATE_IDLE = 0;
- private static final int STATE_PULL = 1;
- private static final int STATE_ABSORB = 2;
- private static final int STATE_RECEDE = 3;
- private static final int STATE_PULL_DECAY = 4;
-
- // How much dragging should effect the height of the edge image.
- // Number determined by user testing.
- private static final int PULL_DISTANCE_EDGE_FACTOR = 7;
-
- // How much dragging should effect the height of the glow image.
- // Number determined by user testing.
- private static final int PULL_DISTANCE_GLOW_FACTOR = 7;
- private static final float PULL_DISTANCE_ALPHA_GLOW_FACTOR = 1.1f;
-
- private static final int VELOCITY_EDGE_FACTOR = 8;
- private static final int VELOCITY_GLOW_FACTOR = 16;
-
- private int mState = STATE_IDLE;
-
- private float mPullDistance;
-
- /**
- * Construct a new EdgeEffect with a theme appropriate for the provided context.
- * @param context Context used to provide theming and resource information for the EdgeEffect
- */
- public EdgeEffect(Context context) {
- mEdge = new Drawable(context, R.drawable.overscroll_edge);
- mGlow = new Drawable(context, R.drawable.overscroll_glow);
-
- mMinWidth = (int) (context.getResources().getDisplayMetrics().density * MIN_WIDTH + 0.5f);
- mInterpolator = new DecelerateInterpolator();
- }
-
- /**
- * Set the size of this edge effect in pixels.
- *
- * @param width Effect width in pixels
- * @param height Effect height in pixels
- */
- public void setSize(int width, int height) {
- mWidth = width;
- mHeight = height;
- }
-
- /**
- * Reports if this EdgeEffect's animation is finished. If this method returns false
- * after a call to {@link #draw(Canvas)} the host widget should schedule another
- * drawing pass to continue the animation.
- *
- * @return true if animation is finished, false if drawing should continue on the next frame.
- */
- public boolean isFinished() {
- return mState == STATE_IDLE;
- }
-
- /**
- * Immediately finish the current animation.
- * After this call {@link #isFinished()} will return true.
- */
- public void finish() {
- mState = STATE_IDLE;
- }
-
- /**
- * A view should call this when content is pulled away from an edge by the user.
- * This will update the state of the current visual effect and its associated animation.
- * The host view should always {@link android.view.View#invalidate()} after this
- * and draw the results accordingly.
- *
- * @param deltaDistance Change in distance since the last call. Values may be 0 (no change) to
- * 1.f (full length of the view) or negative values to express change
- * back toward the edge reached to initiate the effect.
- */
- public void onPull(float deltaDistance) {
- final long now = AnimationTime.get();
- if (mState == STATE_PULL_DECAY && now - mStartTime < mDuration) {
- return;
- }
- if (mState != STATE_PULL) {
- mGlowScaleY = PULL_GLOW_BEGIN;
- }
- mState = STATE_PULL;
-
- mStartTime = now;
- mDuration = PULL_TIME;
-
- mPullDistance += deltaDistance;
- float distance = Math.abs(mPullDistance);
-
- mEdgeAlpha = mEdgeAlphaStart = Math.max(PULL_EDGE_BEGIN, Math.min(distance, MAX_ALPHA));
- mEdgeScaleY = mEdgeScaleYStart = Math.max(
- HELD_EDGE_SCALE_Y, Math.min(distance * PULL_DISTANCE_EDGE_FACTOR, 1.f));
-
- mGlowAlpha = mGlowAlphaStart = Math.min(MAX_ALPHA,
- mGlowAlpha +
- (Math.abs(deltaDistance) * PULL_DISTANCE_ALPHA_GLOW_FACTOR));
-
- float glowChange = Math.abs(deltaDistance);
- if (deltaDistance > 0 && mPullDistance < 0) {
- glowChange = -glowChange;
- }
- if (mPullDistance == 0) {
- mGlowScaleY = 0;
- }
-
- // Do not allow glow to get larger than MAX_GLOW_HEIGHT.
- mGlowScaleY = mGlowScaleYStart = Math.min(MAX_GLOW_HEIGHT, Math.max(
- 0, mGlowScaleY + glowChange * PULL_DISTANCE_GLOW_FACTOR));
-
- mEdgeAlphaFinish = mEdgeAlpha;
- mEdgeScaleYFinish = mEdgeScaleY;
- mGlowAlphaFinish = mGlowAlpha;
- mGlowScaleYFinish = mGlowScaleY;
- }
-
- /**
- * Call when the object is released after being pulled.
- * This will begin the "decay" phase of the effect. After calling this method
- * the host view should {@link android.view.View#invalidate()} and thereby
- * draw the results accordingly.
- */
- public void onRelease() {
- mPullDistance = 0;
-
- if (mState != STATE_PULL && mState != STATE_PULL_DECAY) {
- return;
- }
-
- mState = STATE_RECEDE;
- mEdgeAlphaStart = mEdgeAlpha;
- mEdgeScaleYStart = mEdgeScaleY;
- mGlowAlphaStart = mGlowAlpha;
- mGlowScaleYStart = mGlowScaleY;
-
- mEdgeAlphaFinish = 0.f;
- mEdgeScaleYFinish = 0.f;
- mGlowAlphaFinish = 0.f;
- mGlowScaleYFinish = 0.f;
-
- mStartTime = AnimationTime.get();
- mDuration = RECEDE_TIME;
- }
-
- /**
- * Call when the effect absorbs an impact at the given velocity.
- * Used when a fling reaches the scroll boundary.
- *
- * <p>When using a {@link android.widget.Scroller} or {@link android.widget.OverScroller},
- * the method <code>getCurrVelocity</code> will provide a reasonable approximation
- * to use here.</p>
- *
- * @param velocity Velocity at impact in pixels per second.
- */
- public void onAbsorb(int velocity) {
- mState = STATE_ABSORB;
- velocity = Math.max(MIN_VELOCITY, Math.abs(velocity));
-
- mStartTime = AnimationTime.get();
- mDuration = 0.1f + (velocity * 0.03f);
-
- // The edge should always be at least partially visible, regardless
- // of velocity.
- mEdgeAlphaStart = 0.f;
- mEdgeScaleY = mEdgeScaleYStart = 0.f;
- // The glow depends more on the velocity, and therefore starts out
- // nearly invisible.
- mGlowAlphaStart = 0.5f;
- mGlowScaleYStart = 0.f;
-
- // Factor the velocity by 8. Testing on device shows this works best to
- // reflect the strength of the user's scrolling.
- mEdgeAlphaFinish = Math.max(0, Math.min(velocity * VELOCITY_EDGE_FACTOR, 1));
- // Edge should never get larger than the size of its asset.
- mEdgeScaleYFinish = Math.max(
- HELD_EDGE_SCALE_Y, Math.min(velocity * VELOCITY_EDGE_FACTOR, 1.f));
-
- // Growth for the size of the glow should be quadratic to properly
- // respond
- // to a user's scrolling speed. The faster the scrolling speed, the more
- // intense the effect should be for both the size and the saturation.
- mGlowScaleYFinish = Math.min(0.025f + (velocity * (velocity / 100) * 0.00015f), 1.75f);
- // Alpha should change for the glow as well as size.
- mGlowAlphaFinish = Math.max(
- mGlowAlphaStart, Math.min(velocity * VELOCITY_GLOW_FACTOR * .00001f, MAX_ALPHA));
- }
-
-
- /**
- * Draw into the provided canvas. Assumes that the canvas has been rotated
- * accordingly and the size has been set. The effect will be drawn the full
- * width of X=0 to X=width, beginning from Y=0 and extending to some factor <
- * 1.f of height.
- *
- * @param canvas Canvas to draw into
- * @return true if drawing should continue beyond this frame to continue the
- * animation
- */
- public boolean draw(GLCanvas canvas) {
- update();
-
- final int edgeHeight = mEdge.getIntrinsicHeight();
- final int edgeWidth = mEdge.getIntrinsicWidth();
- final int glowHeight = mGlow.getIntrinsicHeight();
- final int glowWidth = mGlow.getIntrinsicWidth();
-
- mGlow.setAlpha((int) (Math.max(0, Math.min(mGlowAlpha, 1)) * 255));
-
- int glowBottom = (int) Math.min(
- glowHeight * mGlowScaleY * glowHeight/ glowWidth * 0.6f,
- glowHeight * MAX_GLOW_HEIGHT);
- if (mWidth < mMinWidth) {
- // Center the glow and clip it.
- int glowLeft = (mWidth - mMinWidth)/2;
- mGlow.setBounds(glowLeft, 0, mWidth - glowLeft, glowBottom);
- } else {
- // Stretch the glow to fit.
- mGlow.setBounds(0, 0, mWidth, glowBottom);
- }
-
- mGlow.draw(canvas);
-
- mEdge.setAlpha((int) (Math.max(0, Math.min(mEdgeAlpha, 1)) * 255));
-
- int edgeBottom = (int) (edgeHeight * mEdgeScaleY);
- if (mWidth < mMinWidth) {
- // Center the edge and clip it.
- int edgeLeft = (mWidth - mMinWidth)/2;
- mEdge.setBounds(edgeLeft, 0, mWidth - edgeLeft, edgeBottom);
- } else {
- // Stretch the edge to fit.
- mEdge.setBounds(0, 0, mWidth, edgeBottom);
- }
- mEdge.draw(canvas);
-
- return mState != STATE_IDLE;
- }
-
- private void update() {
- final long time = AnimationTime.get();
- final float t = Math.min((time - mStartTime) / mDuration, 1.f);
-
- final float interp = mInterpolator.getInterpolation(t);
-
- mEdgeAlpha = mEdgeAlphaStart + (mEdgeAlphaFinish - mEdgeAlphaStart) * interp;
- mEdgeScaleY = mEdgeScaleYStart + (mEdgeScaleYFinish - mEdgeScaleYStart) * interp;
- mGlowAlpha = mGlowAlphaStart + (mGlowAlphaFinish - mGlowAlphaStart) * interp;
- mGlowScaleY = mGlowScaleYStart + (mGlowScaleYFinish - mGlowScaleYStart) * interp;
-
- if (t >= 1.f - EPSILON) {
- switch (mState) {
- case STATE_ABSORB:
- mState = STATE_RECEDE;
- mStartTime = AnimationTime.get();
- mDuration = RECEDE_TIME;
-
- mEdgeAlphaStart = mEdgeAlpha;
- mEdgeScaleYStart = mEdgeScaleY;
- mGlowAlphaStart = mGlowAlpha;
- mGlowScaleYStart = mGlowScaleY;
-
- // After absorb, the glow and edge should fade to nothing.
- mEdgeAlphaFinish = 0.f;
- mEdgeScaleYFinish = 0.f;
- mGlowAlphaFinish = 0.f;
- mGlowScaleYFinish = 0.f;
- break;
- case STATE_PULL:
- mState = STATE_PULL_DECAY;
- mStartTime = AnimationTime.get();
- mDuration = PULL_DECAY_TIME;
-
- mEdgeAlphaStart = mEdgeAlpha;
- mEdgeScaleYStart = mEdgeScaleY;
- mGlowAlphaStart = mGlowAlpha;
- mGlowScaleYStart = mGlowScaleY;
-
- // After pull, the glow and edge should fade to nothing.
- mEdgeAlphaFinish = 0.f;
- mEdgeScaleYFinish = 0.f;
- mGlowAlphaFinish = 0.f;
- mGlowScaleYFinish = 0.f;
- break;
- case STATE_PULL_DECAY:
- // When receding, we want edge to decrease more slowly
- // than the glow.
- float factor = mGlowScaleYFinish != 0 ? 1
- / (mGlowScaleYFinish * mGlowScaleYFinish)
- : Float.MAX_VALUE;
- mEdgeScaleY = mEdgeScaleYStart +
- (mEdgeScaleYFinish - mEdgeScaleYStart) *
- interp * factor;
- mState = STATE_RECEDE;
- break;
- case STATE_RECEDE:
- mState = STATE_IDLE;
- break;
- }
- }
- }
-
- private static class Drawable extends ResourceTexture {
- private Rect mBounds = new Rect();
- private int mAlpha = 255;
-
- public Drawable(Context context, int resId) {
- super(context, resId);
- }
-
- public int getIntrinsicWidth() {
- return getWidth();
- }
-
- public int getIntrinsicHeight() {
- return getHeight();
- }
-
- public void setBounds(int left, int top, int right, int bottom) {
- mBounds.set(left, top, right, bottom);
- }
-
- public void setAlpha(int alpha) {
- mAlpha = alpha;
- }
-
- public void draw(GLCanvas canvas) {
- canvas.save(GLCanvas.SAVE_FLAG_ALPHA);
- canvas.multiplyAlpha(mAlpha / 255.0f);
- Rect b = mBounds;
- draw(canvas, b.left, b.top, b.width(), b.height());
- canvas.restore();
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/EdgeView.java b/src/com/android/gallery3d/ui/EdgeView.java
deleted file mode 100644
index 051de18fa..000000000
--- a/src/com/android/gallery3d/ui/EdgeView.java
+++ /dev/null
@@ -1,132 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.opengl.Matrix;
-
-import com.android.gallery3d.glrenderer.GLCanvas;
-
-// EdgeView draws EdgeEffect (blue glow) at four sides of the view.
-public class EdgeView extends GLView {
- @SuppressWarnings("unused")
- private static final String TAG = "EdgeView";
-
- public static final int INVALID_DIRECTION = -1;
- public static final int TOP = 0;
- public static final int LEFT = 1;
- public static final int BOTTOM = 2;
- public static final int RIGHT = 3;
-
- // Each edge effect has a transform matrix, and each matrix has 16 elements.
- // We put all the elements in one array. These constants specify the
- // starting index of each matrix.
- private static final int TOP_M = TOP * 16;
- private static final int LEFT_M = LEFT * 16;
- private static final int BOTTOM_M = BOTTOM * 16;
- private static final int RIGHT_M = RIGHT * 16;
-
- private EdgeEffect[] mEffect = new EdgeEffect[4];
- private float[] mMatrix = new float[4 * 16];
-
- public EdgeView(Context context) {
- for (int i = 0; i < 4; i++) {
- mEffect[i] = new EdgeEffect(context);
- }
- }
-
- @Override
- protected void onLayout(
- boolean changeSize, int left, int top, int right, int bottom) {
- if (!changeSize) return;
-
- int w = right - left;
- int h = bottom - top;
- for (int i = 0; i < 4; i++) {
- if ((i & 1) == 0) { // top or bottom
- mEffect[i].setSize(w, h);
- } else { // left or right
- mEffect[i].setSize(h, w);
- }
- }
-
- // Set up transforms for the four edges. Without transforms an
- // EdgeEffect draws the TOP edge from (0, 0) to (w, Y * h) where Y
- // is some factor < 1. For other edges we need to move, rotate, and
- // flip the effects into proper places.
- Matrix.setIdentityM(mMatrix, TOP_M);
- Matrix.setIdentityM(mMatrix, LEFT_M);
- Matrix.setIdentityM(mMatrix, BOTTOM_M);
- Matrix.setIdentityM(mMatrix, RIGHT_M);
-
- Matrix.rotateM(mMatrix, LEFT_M, 90, 0, 0, 1);
- Matrix.scaleM(mMatrix, LEFT_M, 1, -1, 1);
-
- Matrix.translateM(mMatrix, BOTTOM_M, 0, h, 0);
- Matrix.scaleM(mMatrix, BOTTOM_M, 1, -1, 1);
-
- Matrix.translateM(mMatrix, RIGHT_M, w, 0, 0);
- Matrix.rotateM(mMatrix, RIGHT_M, 90, 0, 0, 1);
- }
-
- @Override
- protected void render(GLCanvas canvas) {
- super.render(canvas);
- boolean more = false;
- for (int i = 0; i < 4; i++) {
- canvas.save(GLCanvas.SAVE_FLAG_MATRIX);
- canvas.multiplyMatrix(mMatrix, i * 16);
- more |= mEffect[i].draw(canvas);
- canvas.restore();
- }
- if (more) {
- invalidate();
- }
- }
-
- // Called when the content is pulled away from the edge.
- // offset is in pixels. direction is one of {TOP, LEFT, BOTTOM, RIGHT}.
- public void onPull(int offset, int direction) {
- int fullLength = ((direction & 1) == 0) ? getWidth() : getHeight();
- mEffect[direction].onPull((float)offset / fullLength);
- if (!mEffect[direction].isFinished()) {
- invalidate();
- }
- }
-
- // Call when the object is released after being pulled.
- public void onRelease() {
- boolean more = false;
- for (int i = 0; i < 4; i++) {
- mEffect[i].onRelease();
- more |= !mEffect[i].isFinished();
- }
- if (more) {
- invalidate();
- }
- }
-
- // Call when the effect absorbs an impact at the given velocity.
- // Used when a fling reaches the scroll boundary. velocity is in pixels
- // per second. direction is one of {TOP, LEFT, BOTTOM, RIGHT}.
- public void onAbsorb(int velocity, int direction) {
- mEffect[direction].onAbsorb(velocity);
- if (!mEffect[direction].isFinished()) {
- invalidate();
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/FlingScroller.java b/src/com/android/gallery3d/ui/FlingScroller.java
deleted file mode 100644
index 6f98c64f9..000000000
--- a/src/com/android/gallery3d/ui/FlingScroller.java
+++ /dev/null
@@ -1,141 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-
-// This is a customized version of Scroller, with a interface similar to
-// android.widget.Scroller. It does fling only, not scroll.
-//
-// The differences between the this Scroller and the system one are:
-//
-// (1) The velocity does not change because of min/max limit.
-// (2) The duration is different.
-// (3) The deceleration curve is different.
-class FlingScroller {
- @SuppressWarnings("unused")
- private static final String TAG = "FlingController";
-
- // The fling duration (in milliseconds) when velocity is 1 pixel/second
- private static final float FLING_DURATION_PARAM = 50f;
- private static final int DECELERATED_FACTOR = 4;
-
- private int mStartX, mStartY;
- private int mMinX, mMinY, mMaxX, mMaxY;
- private double mSinAngle;
- private double mCosAngle;
- private int mDuration;
- private int mDistance;
- private int mFinalX, mFinalY;
-
- private int mCurrX, mCurrY;
- private double mCurrV;
-
- public int getFinalX() {
- return mFinalX;
- }
-
- public int getFinalY() {
- return mFinalY;
- }
-
- public int getDuration() {
- return mDuration;
- }
-
- public int getCurrX() {
- return mCurrX;
-
- }
-
- public int getCurrY() {
- return mCurrY;
- }
-
- public int getCurrVelocityX() {
- return (int)Math.round(mCurrV * mCosAngle);
- }
-
- public int getCurrVelocityY() {
- return (int)Math.round(mCurrV * mSinAngle);
- }
-
- public void fling(int startX, int startY, int velocityX, int velocityY,
- int minX, int maxX, int minY, int maxY) {
- mStartX = startX;
- mStartY = startY;
- mMinX = minX;
- mMinY = minY;
- mMaxX = maxX;
- mMaxY = maxY;
-
- double velocity = Math.hypot(velocityX, velocityY);
- mSinAngle = velocityY / velocity;
- mCosAngle = velocityX / velocity;
- //
- // The position formula: x(t) = s + (e - s) * (1 - (1 - t / T) ^ d)
- // velocity formula: v(t) = d * (e - s) * (1 - t / T) ^ (d - 1) / T
- // Thus,
- // v0 = d * (e - s) / T => (e - s) = v0 * T / d
- //
-
- // Ta = T_ref * (Va / V_ref) ^ (1 / (d - 1)); V_ref = 1 pixel/second;
- mDuration = (int)Math.round(FLING_DURATION_PARAM
- * Math.pow(Math.abs(velocity), 1.0 / (DECELERATED_FACTOR - 1)));
-
- // (e - s) = v0 * T / d
- mDistance = (int)Math.round(
- velocity * mDuration / DECELERATED_FACTOR / 1000);
-
- mFinalX = getX(1.0f);
- mFinalY = getY(1.0f);
- }
-
- public void computeScrollOffset(float progress) {
- progress = Math.min(progress, 1);
- float f = 1 - progress;
- f = 1 - (float) Math.pow(f, DECELERATED_FACTOR);
- mCurrX = getX(f);
- mCurrY = getY(f);
- mCurrV = getV(progress);
- }
-
- private int getX(float f) {
- int r = (int) Math.round(mStartX + f * mDistance * mCosAngle);
- if (mCosAngle > 0 && mStartX <= mMaxX) {
- r = Math.min(r, mMaxX);
- } else if (mCosAngle < 0 && mStartX >= mMinX) {
- r = Math.max(r, mMinX);
- }
- return r;
- }
-
- private int getY(float f) {
- int r = (int) Math.round(mStartY + f * mDistance * mSinAngle);
- if (mSinAngle > 0 && mStartY <= mMaxY) {
- r = Math.min(r, mMaxY);
- } else if (mSinAngle < 0 && mStartY >= mMinY) {
- r = Math.max(r, mMinY);
- }
- return r;
- }
-
- private double getV(float progress) {
- // velocity formula: v(t) = d * (e - s) * (1 - t / T) ^ (d - 1) / T
- return DECELERATED_FACTOR * mDistance * 1000 *
- Math.pow(1 - progress, DECELERATED_FACTOR - 1) / mDuration;
- }
-}
diff --git a/src/com/android/gallery3d/ui/GLRoot.java b/src/com/android/gallery3d/ui/GLRoot.java
deleted file mode 100644
index 33a82eaf7..000000000
--- a/src/com/android/gallery3d/ui/GLRoot.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.graphics.Matrix;
-
-import com.android.gallery3d.anim.CanvasAnimation;
-import com.android.gallery3d.glrenderer.GLCanvas;
-
-public interface GLRoot {
-
- // Listener will be called when GL is idle AND before each frame.
- // Mainly used for uploading textures.
- public static interface OnGLIdleListener {
- public boolean onGLIdle(
- GLCanvas canvas, boolean renderRequested);
- }
-
- public void addOnGLIdleListener(OnGLIdleListener listener);
- public void registerLaunchedAnimation(CanvasAnimation animation);
- public void requestRenderForced();
- public void requestRender();
- public void requestLayoutContentPane();
-
- public void lockRenderThread();
- public void unlockRenderThread();
-
- public void setContentPane(GLView content);
- public void setOrientationSource(OrientationSource source);
- public int getDisplayRotation();
- public int getCompensation();
- public Matrix getCompensationMatrix();
- public void freeze();
- public void unfreeze();
- public void setLightsOutMode(boolean enabled);
-
- public Context getContext();
-}
diff --git a/src/com/android/gallery3d/ui/GLRootView.java b/src/com/android/gallery3d/ui/GLRootView.java
deleted file mode 100644
index dc898d83d..000000000
--- a/src/com/android/gallery3d/ui/GLRootView.java
+++ /dev/null
@@ -1,630 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.annotation.TargetApi;
-import android.content.Context;
-import android.graphics.Matrix;
-import android.graphics.PixelFormat;
-import android.opengl.GLSurfaceView;
-import android.os.Build;
-import android.os.Process;
-import android.os.SystemClock;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-import android.view.SurfaceHolder;
-import android.view.View;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.anim.CanvasAnimation;
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.glrenderer.BasicTexture;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.GLES11Canvas;
-import com.android.gallery3d.glrenderer.GLES20Canvas;
-import com.android.gallery3d.glrenderer.UploadedTexture;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.MotionEventHelper;
-import com.android.gallery3d.util.Profile;
-
-import java.util.ArrayDeque;
-import java.util.ArrayList;
-import java.util.concurrent.locks.Condition;
-import java.util.concurrent.locks.ReentrantLock;
-
-import javax.microedition.khronos.egl.EGLConfig;
-import javax.microedition.khronos.opengles.GL10;
-import javax.microedition.khronos.opengles.GL11;
-
-// The root component of all <code>GLView</code>s. The rendering is done in GL
-// thread while the event handling is done in the main thread. To synchronize
-// the two threads, the entry points of this package need to synchronize on the
-// <code>GLRootView</code> instance unless it can be proved that the rendering
-// thread won't access the same thing as the method. The entry points include:
-// (1) The public methods of HeadUpDisplay
-// (2) The public methods of CameraHeadUpDisplay
-// (3) The overridden methods in GLRootView.
-public class GLRootView extends GLSurfaceView
- implements GLSurfaceView.Renderer, GLRoot {
- private static final String TAG = "GLRootView";
-
- private static final boolean DEBUG_FPS = false;
- private int mFrameCount = 0;
- private long mFrameCountingStart = 0;
-
- private static final boolean DEBUG_INVALIDATE = false;
- private int mInvalidateColor = 0;
-
- private static final boolean DEBUG_DRAWING_STAT = false;
-
- private static final boolean DEBUG_PROFILE = false;
- private static final boolean DEBUG_PROFILE_SLOW_ONLY = false;
-
- private static final int FLAG_INITIALIZED = 1;
- private static final int FLAG_NEED_LAYOUT = 2;
-
- private GL11 mGL;
- private GLCanvas mCanvas;
- private GLView mContentView;
-
- private OrientationSource mOrientationSource;
- // mCompensation is the difference between the UI orientation on GLCanvas
- // and the framework orientation. See OrientationManager for details.
- private int mCompensation;
- // mCompensationMatrix maps the coordinates of touch events. It is kept sync
- // with mCompensation.
- private Matrix mCompensationMatrix = new Matrix();
- private int mDisplayRotation;
-
- private int mFlags = FLAG_NEED_LAYOUT;
- private volatile boolean mRenderRequested = false;
-
- private final ArrayList<CanvasAnimation> mAnimations =
- new ArrayList<CanvasAnimation>();
-
- private final ArrayDeque<OnGLIdleListener> mIdleListeners =
- new ArrayDeque<OnGLIdleListener>();
-
- private final IdleRunner mIdleRunner = new IdleRunner();
-
- private final ReentrantLock mRenderLock = new ReentrantLock();
- private final Condition mFreezeCondition =
- mRenderLock.newCondition();
- private boolean mFreeze;
-
- private long mLastDrawFinishTime;
- private boolean mInDownState = false;
- private boolean mFirstDraw = true;
-
- public GLRootView(Context context) {
- this(context, null);
- }
-
- public GLRootView(Context context, AttributeSet attrs) {
- super(context, attrs);
- mFlags |= FLAG_INITIALIZED;
- setBackgroundDrawable(null);
- setEGLContextClientVersion(ApiHelper.HAS_GLES20_REQUIRED ? 2 : 1);
- if (ApiHelper.USE_888_PIXEL_FORMAT) {
- setEGLConfigChooser(8, 8, 8, 0, 0, 0);
- } else {
- setEGLConfigChooser(5, 6, 5, 0, 0, 0);
- }
- setRenderer(this);
- if (ApiHelper.USE_888_PIXEL_FORMAT) {
- getHolder().setFormat(PixelFormat.RGB_888);
- } else {
- getHolder().setFormat(PixelFormat.RGB_565);
- }
-
- // Uncomment this to enable gl error check.
- // setDebugFlags(DEBUG_CHECK_GL_ERROR);
- }
-
- @Override
- public void registerLaunchedAnimation(CanvasAnimation animation) {
- // Register the newly launched animation so that we can set the start
- // time more precisely. (Usually, it takes much longer for first
- // rendering, so we set the animation start time as the time we
- // complete rendering)
- mAnimations.add(animation);
- }
-
- @Override
- public void addOnGLIdleListener(OnGLIdleListener listener) {
- synchronized (mIdleListeners) {
- mIdleListeners.addLast(listener);
- mIdleRunner.enable();
- }
- }
-
- @Override
- public void setContentPane(GLView content) {
- if (mContentView == content) return;
- if (mContentView != null) {
- if (mInDownState) {
- long now = SystemClock.uptimeMillis();
- MotionEvent cancelEvent = MotionEvent.obtain(
- now, now, MotionEvent.ACTION_CANCEL, 0, 0, 0);
- mContentView.dispatchTouchEvent(cancelEvent);
- cancelEvent.recycle();
- mInDownState = false;
- }
- mContentView.detachFromRoot();
- BasicTexture.yieldAllTextures();
- }
- mContentView = content;
- if (content != null) {
- content.attachToRoot(this);
- requestLayoutContentPane();
- }
- }
-
- @Override
- public void requestRenderForced() {
- superRequestRender();
- }
-
- @Override
- public void requestRender() {
- if (DEBUG_INVALIDATE) {
- StackTraceElement e = Thread.currentThread().getStackTrace()[4];
- String caller = e.getFileName() + ":" + e.getLineNumber() + " ";
- Log.d(TAG, "invalidate: " + caller);
- }
- if (mRenderRequested) return;
- mRenderRequested = true;
- if (ApiHelper.HAS_POST_ON_ANIMATION) {
- postOnAnimation(mRequestRenderOnAnimationFrame);
- } else {
- super.requestRender();
- }
- }
-
- private Runnable mRequestRenderOnAnimationFrame = new Runnable() {
- @Override
- public void run() {
- superRequestRender();
- }
- };
-
- private void superRequestRender() {
- super.requestRender();
- }
-
- @Override
- public void requestLayoutContentPane() {
- mRenderLock.lock();
- try {
- if (mContentView == null || (mFlags & FLAG_NEED_LAYOUT) != 0) return;
-
- // "View" system will invoke onLayout() for initialization(bug ?), we
- // have to ignore it since the GLThread is not ready yet.
- if ((mFlags & FLAG_INITIALIZED) == 0) return;
-
- mFlags |= FLAG_NEED_LAYOUT;
- requestRender();
- } finally {
- mRenderLock.unlock();
- }
- }
-
- private void layoutContentPane() {
- mFlags &= ~FLAG_NEED_LAYOUT;
-
- int w = getWidth();
- int h = getHeight();
- int displayRotation = 0;
- int compensation = 0;
-
- // Get the new orientation values
- if (mOrientationSource != null) {
- displayRotation = mOrientationSource.getDisplayRotation();
- compensation = mOrientationSource.getCompensation();
- } else {
- displayRotation = 0;
- compensation = 0;
- }
-
- if (mCompensation != compensation) {
- mCompensation = compensation;
- if (mCompensation % 180 != 0) {
- mCompensationMatrix.setRotate(mCompensation);
- // move center to origin before rotation
- mCompensationMatrix.preTranslate(-w / 2, -h / 2);
- // align with the new origin after rotation
- mCompensationMatrix.postTranslate(h / 2, w / 2);
- } else {
- mCompensationMatrix.setRotate(mCompensation, w / 2, h / 2);
- }
- }
- mDisplayRotation = displayRotation;
-
- // Do the actual layout.
- if (mCompensation % 180 != 0) {
- int tmp = w;
- w = h;
- h = tmp;
- }
- Log.i(TAG, "layout content pane " + w + "x" + h
- + " (compensation " + mCompensation + ")");
- if (mContentView != null && w != 0 && h != 0) {
- mContentView.layout(0, 0, w, h);
- }
- // Uncomment this to dump the view hierarchy.
- //mContentView.dumpTree("");
- }
-
- @Override
- protected void onLayout(
- boolean changed, int left, int top, int right, int bottom) {
- if (changed) requestLayoutContentPane();
- }
-
- /**
- * Called when the context is created, possibly after automatic destruction.
- */
- // This is a GLSurfaceView.Renderer callback
- @Override
- public void onSurfaceCreated(GL10 gl1, EGLConfig config) {
- GL11 gl = (GL11) gl1;
- if (mGL != null) {
- // The GL Object has changed
- Log.i(TAG, "GLObject has changed from " + mGL + " to " + gl);
- }
- mRenderLock.lock();
- try {
- mGL = gl;
- mCanvas = ApiHelper.HAS_GLES20_REQUIRED ? new GLES20Canvas() : new GLES11Canvas(gl);
- BasicTexture.invalidateAllTextures();
- } finally {
- mRenderLock.unlock();
- }
-
- if (DEBUG_FPS || DEBUG_PROFILE) {
- setRenderMode(GLSurfaceView.RENDERMODE_CONTINUOUSLY);
- } else {
- setRenderMode(GLSurfaceView.RENDERMODE_WHEN_DIRTY);
- }
- }
-
- /**
- * Called when the OpenGL surface is recreated without destroying the
- * context.
- */
- // This is a GLSurfaceView.Renderer callback
- @Override
- public void onSurfaceChanged(GL10 gl1, int width, int height) {
- Log.i(TAG, "onSurfaceChanged: " + width + "x" + height
- + ", gl10: " + gl1.toString());
- Process.setThreadPriority(Process.THREAD_PRIORITY_DISPLAY);
- GalleryUtils.setRenderThread();
- if (DEBUG_PROFILE) {
- Log.d(TAG, "Start profiling");
- Profile.enable(20); // take a sample every 20ms
- }
- GL11 gl = (GL11) gl1;
- Utils.assertTrue(mGL == gl);
-
- mCanvas.setSize(width, height);
- }
-
- private void outputFps() {
- long now = System.nanoTime();
- if (mFrameCountingStart == 0) {
- mFrameCountingStart = now;
- } else if ((now - mFrameCountingStart) > 1000000000) {
- Log.d(TAG, "fps: " + (double) mFrameCount
- * 1000000000 / (now - mFrameCountingStart));
- mFrameCountingStart = now;
- mFrameCount = 0;
- }
- ++mFrameCount;
- }
-
- @Override
- public void onDrawFrame(GL10 gl) {
- AnimationTime.update();
- long t0;
- if (DEBUG_PROFILE_SLOW_ONLY) {
- Profile.hold();
- t0 = System.nanoTime();
- }
- mRenderLock.lock();
-
- while (mFreeze) {
- mFreezeCondition.awaitUninterruptibly();
- }
-
- try {
- onDrawFrameLocked(gl);
- } finally {
- mRenderLock.unlock();
- }
-
- // We put a black cover View in front of the SurfaceView and hide it
- // after the first draw. This prevents the SurfaceView being transparent
- // before the first draw.
- if (mFirstDraw) {
- mFirstDraw = false;
- post(new Runnable() {
- @Override
- public void run() {
- View root = getRootView();
- View cover = root.findViewById(R.id.gl_root_cover);
- cover.setVisibility(GONE);
- }
- });
- }
-
- if (DEBUG_PROFILE_SLOW_ONLY) {
- long t = System.nanoTime();
- long durationInMs = (t - mLastDrawFinishTime) / 1000000;
- long durationDrawInMs = (t - t0) / 1000000;
- mLastDrawFinishTime = t;
-
- if (durationInMs > 34) { // 34ms -> we skipped at least 2 frames
- Log.v(TAG, "----- SLOW (" + durationDrawInMs + "/" +
- durationInMs + ") -----");
- Profile.commit();
- } else {
- Profile.drop();
- }
- }
- }
-
- private void onDrawFrameLocked(GL10 gl) {
- if (DEBUG_FPS) outputFps();
-
- // release the unbound textures and deleted buffers.
- mCanvas.deleteRecycledResources();
-
- // reset texture upload limit
- UploadedTexture.resetUploadLimit();
-
- mRenderRequested = false;
-
- if ((mOrientationSource != null
- && mDisplayRotation != mOrientationSource.getDisplayRotation())
- || (mFlags & FLAG_NEED_LAYOUT) != 0) {
- layoutContentPane();
- }
-
- mCanvas.save(GLCanvas.SAVE_FLAG_ALL);
- rotateCanvas(-mCompensation);
- if (mContentView != null) {
- mContentView.render(mCanvas);
- } else {
- // Make sure we always draw something to prevent displaying garbage
- mCanvas.clearBuffer();
- }
- mCanvas.restore();
-
- if (!mAnimations.isEmpty()) {
- long now = AnimationTime.get();
- for (int i = 0, n = mAnimations.size(); i < n; i++) {
- mAnimations.get(i).setStartTime(now);
- }
- mAnimations.clear();
- }
-
- if (UploadedTexture.uploadLimitReached()) {
- requestRender();
- }
-
- synchronized (mIdleListeners) {
- if (!mIdleListeners.isEmpty()) mIdleRunner.enable();
- }
-
- if (DEBUG_INVALIDATE) {
- mCanvas.fillRect(10, 10, 5, 5, mInvalidateColor);
- mInvalidateColor = ~mInvalidateColor;
- }
-
- if (DEBUG_DRAWING_STAT) {
- mCanvas.dumpStatisticsAndClear();
- }
- }
-
- private void rotateCanvas(int degrees) {
- if (degrees == 0) return;
- int w = getWidth();
- int h = getHeight();
- int cx = w / 2;
- int cy = h / 2;
- mCanvas.translate(cx, cy);
- mCanvas.rotate(degrees, 0, 0, 1);
- if (degrees % 180 != 0) {
- mCanvas.translate(-cy, -cx);
- } else {
- mCanvas.translate(-cx, -cy);
- }
- }
-
- @Override
- public boolean dispatchTouchEvent(MotionEvent event) {
- if (!isEnabled()) return false;
-
- int action = event.getAction();
- if (action == MotionEvent.ACTION_CANCEL
- || action == MotionEvent.ACTION_UP) {
- mInDownState = false;
- } else if (!mInDownState && action != MotionEvent.ACTION_DOWN) {
- return false;
- }
-
- if (mCompensation != 0) {
- event = MotionEventHelper.transformEvent(event, mCompensationMatrix);
- }
-
- mRenderLock.lock();
- try {
- // If this has been detached from root, we don't need to handle event
- boolean handled = mContentView != null
- && mContentView.dispatchTouchEvent(event);
- if (action == MotionEvent.ACTION_DOWN && handled) {
- mInDownState = true;
- }
- return handled;
- } finally {
- mRenderLock.unlock();
- }
- }
-
- private class IdleRunner implements Runnable {
- // true if the idle runner is in the queue
- private boolean mActive = false;
-
- @Override
- public void run() {
- OnGLIdleListener listener;
- synchronized (mIdleListeners) {
- mActive = false;
- if (mIdleListeners.isEmpty()) return;
- listener = mIdleListeners.removeFirst();
- }
- mRenderLock.lock();
- boolean keepInQueue;
- try {
- keepInQueue = listener.onGLIdle(mCanvas, mRenderRequested);
- } finally {
- mRenderLock.unlock();
- }
- synchronized (mIdleListeners) {
- if (keepInQueue) mIdleListeners.addLast(listener);
- if (!mRenderRequested && !mIdleListeners.isEmpty()) enable();
- }
- }
-
- public void enable() {
- // Who gets the flag can add it to the queue
- if (mActive) return;
- mActive = true;
- queueEvent(this);
- }
- }
-
- @Override
- public void lockRenderThread() {
- mRenderLock.lock();
- }
-
- @Override
- public void unlockRenderThread() {
- mRenderLock.unlock();
- }
-
- @Override
- public void onPause() {
- unfreeze();
- super.onPause();
- if (DEBUG_PROFILE) {
- Log.d(TAG, "Stop profiling");
- Profile.disableAll();
- Profile.dumpToFile("/sdcard/gallery.prof");
- Profile.reset();
- }
- }
-
- @Override
- public void setOrientationSource(OrientationSource source) {
- mOrientationSource = source;
- }
-
- @Override
- public int getDisplayRotation() {
- return mDisplayRotation;
- }
-
- @Override
- public int getCompensation() {
- return mCompensation;
- }
-
- @Override
- public Matrix getCompensationMatrix() {
- return mCompensationMatrix;
- }
-
- @Override
- public void freeze() {
- mRenderLock.lock();
- mFreeze = true;
- mRenderLock.unlock();
- }
-
- @Override
- public void unfreeze() {
- mRenderLock.lock();
- mFreeze = false;
- mFreezeCondition.signalAll();
- mRenderLock.unlock();
- }
-
- @Override
- @TargetApi(Build.VERSION_CODES.JELLY_BEAN)
- public void setLightsOutMode(boolean enabled) {
- if (!ApiHelper.HAS_SET_SYSTEM_UI_VISIBILITY) return;
-
- int flags = 0;
- if (enabled) {
- flags = STATUS_BAR_HIDDEN;
- if (ApiHelper.HAS_VIEW_SYSTEM_UI_FLAG_LAYOUT_STABLE) {
- flags |= (SYSTEM_UI_FLAG_FULLSCREEN | SYSTEM_UI_FLAG_LAYOUT_STABLE);
- }
- }
- setSystemUiVisibility(flags);
- }
-
- // We need to unfreeze in the following methods and in onPause().
- // These methods will wait on GLThread. If we have freezed the GLRootView,
- // the GLThread will wait on main thread to call unfreeze and cause dead
- // lock.
- @Override
- public void surfaceChanged(SurfaceHolder holder, int format, int w, int h) {
- unfreeze();
- super.surfaceChanged(holder, format, w, h);
- }
-
- @Override
- public void surfaceCreated(SurfaceHolder holder) {
- unfreeze();
- super.surfaceCreated(holder);
- }
-
- @Override
- public void surfaceDestroyed(SurfaceHolder holder) {
- unfreeze();
- super.surfaceDestroyed(holder);
- }
-
- @Override
- protected void onDetachedFromWindow() {
- unfreeze();
- super.onDetachedFromWindow();
- }
-
- @Override
- protected void finalize() throws Throwable {
- try {
- unfreeze();
- } finally {
- super.finalize();
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/GLView.java b/src/com/android/gallery3d/ui/GLView.java
deleted file mode 100644
index 83de19fe4..000000000
--- a/src/com/android/gallery3d/ui/GLView.java
+++ /dev/null
@@ -1,465 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.graphics.Rect;
-import android.os.SystemClock;
-import android.view.MotionEvent;
-
-import com.android.gallery3d.anim.CanvasAnimation;
-import com.android.gallery3d.anim.StateTransitionAnimation;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.glrenderer.GLCanvas;
-
-import java.util.ArrayList;
-
-// GLView is a UI component. It can render to a GLCanvas and accept touch
-// events. A GLView may have zero or more child GLView and they form a tree
-// structure. The rendering and event handling will pass through the tree
-// structure.
-//
-// A GLView tree should be attached to a GLRoot before event dispatching and
-// rendering happens. GLView asks GLRoot to re-render or re-layout the
-// GLView hierarchy using requestRender() and requestLayoutContentPane().
-//
-// The render() method is called in a separate thread. Before calling
-// dispatchTouchEvent() and layout(), GLRoot acquires a lock to avoid the
-// rendering thread running at the same time. If there are other entry points
-// from main thread (like a Handler) in your GLView, you need to call
-// lockRendering() if the rendering thread should not run at the same time.
-//
-public class GLView {
- private static final String TAG = "GLView";
-
- public static final int VISIBLE = 0;
- public static final int INVISIBLE = 1;
-
- private static final int FLAG_INVISIBLE = 1;
- private static final int FLAG_SET_MEASURED_SIZE = 2;
- private static final int FLAG_LAYOUT_REQUESTED = 4;
-
- public interface OnClickListener {
- void onClick(GLView v);
- }
-
- protected final Rect mBounds = new Rect();
- protected final Rect mPaddings = new Rect();
-
- private GLRoot mRoot;
- protected GLView mParent;
- private ArrayList<GLView> mComponents;
- private GLView mMotionTarget;
-
- private CanvasAnimation mAnimation;
-
- private int mViewFlags = 0;
-
- protected int mMeasuredWidth = 0;
- protected int mMeasuredHeight = 0;
-
- private int mLastWidthSpec = -1;
- private int mLastHeightSpec = -1;
-
- protected int mScrollY = 0;
- protected int mScrollX = 0;
- protected int mScrollHeight = 0;
- protected int mScrollWidth = 0;
-
- private float [] mBackgroundColor;
- private StateTransitionAnimation mTransition;
-
- public void startAnimation(CanvasAnimation animation) {
- GLRoot root = getGLRoot();
- if (root == null) throw new IllegalStateException();
- mAnimation = animation;
- if (mAnimation != null) {
- mAnimation.start();
- root.registerLaunchedAnimation(mAnimation);
- }
- invalidate();
- }
-
- // Sets the visiblity of this GLView (either GLView.VISIBLE or
- // GLView.INVISIBLE).
- public void setVisibility(int visibility) {
- if (visibility == getVisibility()) return;
- if (visibility == VISIBLE) {
- mViewFlags &= ~FLAG_INVISIBLE;
- } else {
- mViewFlags |= FLAG_INVISIBLE;
- }
- onVisibilityChanged(visibility);
- invalidate();
- }
-
- // Returns GLView.VISIBLE or GLView.INVISIBLE
- public int getVisibility() {
- return (mViewFlags & FLAG_INVISIBLE) == 0 ? VISIBLE : INVISIBLE;
- }
-
- // This should only be called on the content pane (the topmost GLView).
- public void attachToRoot(GLRoot root) {
- Utils.assertTrue(mParent == null && mRoot == null);
- onAttachToRoot(root);
- }
-
- // This should only be called on the content pane (the topmost GLView).
- public void detachFromRoot() {
- Utils.assertTrue(mParent == null && mRoot != null);
- onDetachFromRoot();
- }
-
- // Returns the number of children of the GLView.
- public int getComponentCount() {
- return mComponents == null ? 0 : mComponents.size();
- }
-
- // Returns the children for the given index.
- public GLView getComponent(int index) {
- if (mComponents == null) {
- throw new ArrayIndexOutOfBoundsException(index);
- }
- return mComponents.get(index);
- }
-
- // Adds a child to this GLView.
- public void addComponent(GLView component) {
- // Make sure the component doesn't have a parent currently.
- if (component.mParent != null) throw new IllegalStateException();
-
- // Build parent-child links
- if (mComponents == null) {
- mComponents = new ArrayList<GLView>();
- }
- mComponents.add(component);
- component.mParent = this;
-
- // If this is added after we have a root, tell the component.
- if (mRoot != null) {
- component.onAttachToRoot(mRoot);
- }
- }
-
- // Removes a child from this GLView.
- public boolean removeComponent(GLView component) {
- if (mComponents == null) return false;
- if (mComponents.remove(component)) {
- removeOneComponent(component);
- return true;
- }
- return false;
- }
-
- // Removes all children of this GLView.
- public void removeAllComponents() {
- for (int i = 0, n = mComponents.size(); i < n; ++i) {
- removeOneComponent(mComponents.get(i));
- }
- mComponents.clear();
- }
-
- private void removeOneComponent(GLView component) {
- if (mMotionTarget == component) {
- long now = SystemClock.uptimeMillis();
- MotionEvent cancelEvent = MotionEvent.obtain(
- now, now, MotionEvent.ACTION_CANCEL, 0, 0, 0);
- dispatchTouchEvent(cancelEvent);
- cancelEvent.recycle();
- }
- component.onDetachFromRoot();
- component.mParent = null;
- }
-
- public Rect bounds() {
- return mBounds;
- }
-
- public int getWidth() {
- return mBounds.right - mBounds.left;
- }
-
- public int getHeight() {
- return mBounds.bottom - mBounds.top;
- }
-
- public GLRoot getGLRoot() {
- return mRoot;
- }
-
- // Request re-rendering of the view hierarchy.
- // This is used for animation or when the contents changed.
- public void invalidate() {
- GLRoot root = getGLRoot();
- if (root != null) root.requestRender();
- }
-
- // Request re-layout of the view hierarchy.
- public void requestLayout() {
- mViewFlags |= FLAG_LAYOUT_REQUESTED;
- mLastHeightSpec = -1;
- mLastWidthSpec = -1;
- if (mParent != null) {
- mParent.requestLayout();
- } else {
- // Is this a content pane ?
- GLRoot root = getGLRoot();
- if (root != null) root.requestLayoutContentPane();
- }
- }
-
- protected void render(GLCanvas canvas) {
- boolean transitionActive = false;
- if (mTransition != null && mTransition.calculate(AnimationTime.get())) {
- invalidate();
- transitionActive = mTransition.isActive();
- }
- renderBackground(canvas);
- canvas.save();
- if (transitionActive) {
- mTransition.applyContentTransform(this, canvas);
- }
- for (int i = 0, n = getComponentCount(); i < n; ++i) {
- renderChild(canvas, getComponent(i));
- }
- canvas.restore();
- if (transitionActive) {
- mTransition.applyOverlay(this, canvas);
- }
- }
-
- public void setIntroAnimation(StateTransitionAnimation intro) {
- mTransition = intro;
- if (mTransition != null) mTransition.start();
- }
-
- public float [] getBackgroundColor() {
- return mBackgroundColor;
- }
-
- public void setBackgroundColor(float [] color) {
- mBackgroundColor = color;
- }
-
- protected void renderBackground(GLCanvas view) {
- if (mBackgroundColor != null) {
- view.clearBuffer(mBackgroundColor);
- }
- if (mTransition != null && mTransition.isActive()) {
- mTransition.applyBackground(this, view);
- return;
- }
- }
-
- protected void renderChild(GLCanvas canvas, GLView component) {
- if (component.getVisibility() != GLView.VISIBLE
- && component.mAnimation == null) return;
-
- int xoffset = component.mBounds.left - mScrollX;
- int yoffset = component.mBounds.top - mScrollY;
-
- canvas.translate(xoffset, yoffset);
-
- CanvasAnimation anim = component.mAnimation;
- if (anim != null) {
- canvas.save(anim.getCanvasSaveFlags());
- if (anim.calculate(AnimationTime.get())) {
- invalidate();
- } else {
- component.mAnimation = null;
- }
- anim.apply(canvas);
- }
- component.render(canvas);
- if (anim != null) canvas.restore();
- canvas.translate(-xoffset, -yoffset);
- }
-
- protected boolean onTouch(MotionEvent event) {
- return false;
- }
-
- protected boolean dispatchTouchEvent(MotionEvent event,
- int x, int y, GLView component, boolean checkBounds) {
- Rect rect = component.mBounds;
- int left = rect.left;
- int top = rect.top;
- if (!checkBounds || rect.contains(x, y)) {
- event.offsetLocation(-left, -top);
- if (component.dispatchTouchEvent(event)) {
- event.offsetLocation(left, top);
- return true;
- }
- event.offsetLocation(left, top);
- }
- return false;
- }
-
- protected boolean dispatchTouchEvent(MotionEvent event) {
- int x = (int) event.getX();
- int y = (int) event.getY();
- int action = event.getAction();
- if (mMotionTarget != null) {
- if (action == MotionEvent.ACTION_DOWN) {
- MotionEvent cancel = MotionEvent.obtain(event);
- cancel.setAction(MotionEvent.ACTION_CANCEL);
- dispatchTouchEvent(cancel, x, y, mMotionTarget, false);
- mMotionTarget = null;
- } else {
- dispatchTouchEvent(event, x, y, mMotionTarget, false);
- if (action == MotionEvent.ACTION_CANCEL
- || action == MotionEvent.ACTION_UP) {
- mMotionTarget = null;
- }
- return true;
- }
- }
- if (action == MotionEvent.ACTION_DOWN) {
- // in the reverse rendering order
- for (int i = getComponentCount() - 1; i >= 0; --i) {
- GLView component = getComponent(i);
- if (component.getVisibility() != GLView.VISIBLE) continue;
- if (dispatchTouchEvent(event, x, y, component, true)) {
- mMotionTarget = component;
- return true;
- }
- }
- }
- return onTouch(event);
- }
-
- public Rect getPaddings() {
- return mPaddings;
- }
-
- public void layout(int left, int top, int right, int bottom) {
- boolean sizeChanged = setBounds(left, top, right, bottom);
- mViewFlags &= ~FLAG_LAYOUT_REQUESTED;
- // We call onLayout no matter sizeChanged is true or not because the
- // orientation may change without changing the size of the View (for
- // example, rotate the device by 180 degrees), and we want to handle
- // orientation change in onLayout.
- onLayout(sizeChanged, left, top, right, bottom);
- }
-
- private boolean setBounds(int left, int top, int right, int bottom) {
- boolean sizeChanged = (right - left) != (mBounds.right - mBounds.left)
- || (bottom - top) != (mBounds.bottom - mBounds.top);
- mBounds.set(left, top, right, bottom);
- return sizeChanged;
- }
-
- public void measure(int widthSpec, int heightSpec) {
- if (widthSpec == mLastWidthSpec && heightSpec == mLastHeightSpec
- && (mViewFlags & FLAG_LAYOUT_REQUESTED) == 0) {
- return;
- }
-
- mLastWidthSpec = widthSpec;
- mLastHeightSpec = heightSpec;
-
- mViewFlags &= ~FLAG_SET_MEASURED_SIZE;
- onMeasure(widthSpec, heightSpec);
- if ((mViewFlags & FLAG_SET_MEASURED_SIZE) == 0) {
- throw new IllegalStateException(getClass().getName()
- + " should call setMeasuredSize() in onMeasure()");
- }
- }
-
- protected void onMeasure(int widthSpec, int heightSpec) {
- }
-
- protected void setMeasuredSize(int width, int height) {
- mViewFlags |= FLAG_SET_MEASURED_SIZE;
- mMeasuredWidth = width;
- mMeasuredHeight = height;
- }
-
- public int getMeasuredWidth() {
- return mMeasuredWidth;
- }
-
- public int getMeasuredHeight() {
- return mMeasuredHeight;
- }
-
- protected void onLayout(
- boolean changeSize, int left, int top, int right, int bottom) {
- }
-
- /**
- * Gets the bounds of the given descendant that relative to this view.
- */
- public boolean getBoundsOf(GLView descendant, Rect out) {
- int xoffset = 0;
- int yoffset = 0;
- GLView view = descendant;
- while (view != this) {
- if (view == null) return false;
- Rect bounds = view.mBounds;
- xoffset += bounds.left;
- yoffset += bounds.top;
- view = view.mParent;
- }
- out.set(xoffset, yoffset, xoffset + descendant.getWidth(),
- yoffset + descendant.getHeight());
- return true;
- }
-
- protected void onVisibilityChanged(int visibility) {
- for (int i = 0, n = getComponentCount(); i < n; ++i) {
- GLView child = getComponent(i);
- if (child.getVisibility() == GLView.VISIBLE) {
- child.onVisibilityChanged(visibility);
- }
- }
- }
-
- protected void onAttachToRoot(GLRoot root) {
- mRoot = root;
- for (int i = 0, n = getComponentCount(); i < n; ++i) {
- getComponent(i).onAttachToRoot(root);
- }
- }
-
- protected void onDetachFromRoot() {
- for (int i = 0, n = getComponentCount(); i < n; ++i) {
- getComponent(i).onDetachFromRoot();
- }
- mRoot = null;
- }
-
- public void lockRendering() {
- if (mRoot != null) {
- mRoot.lockRenderThread();
- }
- }
-
- public void unlockRendering() {
- if (mRoot != null) {
- mRoot.unlockRenderThread();
- }
- }
-
- // This is for debugging only.
- // Dump the view hierarchy into log.
- void dumpTree(String prefix) {
- Log.d(TAG, prefix + getClass().getSimpleName());
- for (int i = 0, n = getComponentCount(); i < n; ++i) {
- getComponent(i).dumpTree(prefix + "....");
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/GestureRecognizer.java b/src/com/android/gallery3d/ui/GestureRecognizer.java
deleted file mode 100644
index 1e5250b9b..000000000
--- a/src/com/android/gallery3d/ui/GestureRecognizer.java
+++ /dev/null
@@ -1,132 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.os.SystemClock;
-import android.view.GestureDetector;
-import android.view.MotionEvent;
-import android.view.ScaleGestureDetector;
-
-// This class aggregates three gesture detectors: GestureDetector,
-// ScaleGestureDetector, and DownUpDetector.
-public class GestureRecognizer {
- @SuppressWarnings("unused")
- private static final String TAG = "GestureRecognizer";
-
- public interface Listener {
- boolean onSingleTapUp(float x, float y);
- boolean onDoubleTap(float x, float y);
- boolean onScroll(float dx, float dy, float totalX, float totalY);
- boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY);
- boolean onScaleBegin(float focusX, float focusY);
- boolean onScale(float focusX, float focusY, float scale);
- void onScaleEnd();
- void onDown(float x, float y);
- void onUp();
- }
-
- private final GestureDetector mGestureDetector;
- private final ScaleGestureDetector mScaleDetector;
- private final DownUpDetector mDownUpDetector;
- private final Listener mListener;
-
- public GestureRecognizer(Context context, Listener listener) {
- mListener = listener;
- mGestureDetector = new GestureDetector(context, new MyGestureListener(),
- null, true /* ignoreMultitouch */);
- mScaleDetector = new ScaleGestureDetector(
- context, new MyScaleListener());
- mDownUpDetector = new DownUpDetector(new MyDownUpListener());
- }
-
- public void onTouchEvent(MotionEvent event) {
- mGestureDetector.onTouchEvent(event);
- mScaleDetector.onTouchEvent(event);
- mDownUpDetector.onTouchEvent(event);
- }
-
- public boolean isDown() {
- return mDownUpDetector.isDown();
- }
-
- public void cancelScale() {
- long now = SystemClock.uptimeMillis();
- MotionEvent cancelEvent = MotionEvent.obtain(
- now, now, MotionEvent.ACTION_CANCEL, 0, 0, 0);
- mScaleDetector.onTouchEvent(cancelEvent);
- cancelEvent.recycle();
- }
-
- private class MyGestureListener
- extends GestureDetector.SimpleOnGestureListener {
- @Override
- public boolean onSingleTapUp(MotionEvent e) {
- return mListener.onSingleTapUp(e.getX(), e.getY());
- }
-
- @Override
- public boolean onDoubleTap(MotionEvent e) {
- return mListener.onDoubleTap(e.getX(), e.getY());
- }
-
- @Override
- public boolean onScroll(
- MotionEvent e1, MotionEvent e2, float dx, float dy) {
- return mListener.onScroll(
- dx, dy, e2.getX() - e1.getX(), e2.getY() - e1.getY());
- }
-
- @Override
- public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX,
- float velocityY) {
- return mListener.onFling(e1, e2, velocityX, velocityY);
- }
- }
-
- private class MyScaleListener
- extends ScaleGestureDetector.SimpleOnScaleGestureListener {
- @Override
- public boolean onScaleBegin(ScaleGestureDetector detector) {
- return mListener.onScaleBegin(
- detector.getFocusX(), detector.getFocusY());
- }
-
- @Override
- public boolean onScale(ScaleGestureDetector detector) {
- return mListener.onScale(detector.getFocusX(),
- detector.getFocusY(), detector.getScaleFactor());
- }
-
- @Override
- public void onScaleEnd(ScaleGestureDetector detector) {
- mListener.onScaleEnd();
- }
- }
-
- private class MyDownUpListener implements DownUpDetector.DownUpListener {
- @Override
- public void onDown(MotionEvent e) {
- mListener.onDown(e.getX(), e.getY());
- }
-
- @Override
- public void onUp(MotionEvent e) {
- mListener.onUp();
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/Log.java b/src/com/android/gallery3d/ui/Log.java
deleted file mode 100644
index 5570763bb..000000000
--- a/src/com/android/gallery3d/ui/Log.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-// TODO: Delete this
-public class Log {
- public static int v(String tag, String msg) {
- return android.util.Log.v(tag, msg);
- }
- public static int v(String tag, String msg, Throwable tr) {
- return android.util.Log.v(tag, msg, tr);
- }
- public static int d(String tag, String msg) {
- return android.util.Log.d(tag, msg);
- }
- public static int d(String tag, String msg, Throwable tr) {
- return android.util.Log.d(tag, msg, tr);
- }
- public static int i(String tag, String msg) {
- return android.util.Log.i(tag, msg);
- }
- public static int i(String tag, String msg, Throwable tr) {
- return android.util.Log.i(tag, msg, tr);
- }
- public static int w(String tag, String msg) {
- return android.util.Log.w(tag, msg);
- }
- public static int w(String tag, String msg, Throwable tr) {
- return android.util.Log.w(tag, msg, tr);
- }
- public static int w(String tag, Throwable tr) {
- return android.util.Log.w(tag, tr);
- }
- public static int e(String tag, String msg) {
- return android.util.Log.e(tag, msg);
- }
- public static int e(String tag, String msg, Throwable tr) {
- return android.util.Log.e(tag, msg, tr);
- }
-}
diff --git a/src/com/android/gallery3d/ui/ManageCacheDrawer.java b/src/com/android/gallery3d/ui/ManageCacheDrawer.java
deleted file mode 100644
index d210bd1f1..000000000
--- a/src/com/android/gallery3d/ui/ManageCacheDrawer.java
+++ /dev/null
@@ -1,116 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.data.DataSourceType;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.ResourceTexture;
-import com.android.gallery3d.glrenderer.StringTexture;
-import com.android.gallery3d.ui.AlbumSetSlidingWindow.AlbumSetEntry;
-
-public class ManageCacheDrawer extends AlbumSetSlotRenderer {
- private final ResourceTexture mCheckedItem;
- private final ResourceTexture mUnCheckedItem;
- private final SelectionManager mSelectionManager;
-
- private final ResourceTexture mLocalAlbumIcon;
- private final StringTexture mCachingText;
-
- private final int mCachePinSize;
- private final int mCachePinMargin;
-
- public ManageCacheDrawer(AbstractGalleryActivity activity, SelectionManager selectionManager,
- SlotView slotView, LabelSpec labelSpec, int cachePinSize, int cachePinMargin) {
- super(activity, selectionManager, slotView, labelSpec,
- activity.getResources().getColor(R.color.cache_placeholder));
- Context context = activity;
- mCheckedItem = new ResourceTexture(
- context, R.drawable.btn_make_offline_normal_on_holo_dark);
- mUnCheckedItem = new ResourceTexture(
- context, R.drawable.btn_make_offline_normal_off_holo_dark);
- mLocalAlbumIcon = new ResourceTexture(
- context, R.drawable.btn_make_offline_disabled_on_holo_dark);
- String cachingLabel = context.getString(R.string.caching_label);
- mCachingText = StringTexture.newInstance(cachingLabel, 12, 0xffffffff);
- mSelectionManager = selectionManager;
- mCachePinSize = cachePinSize;
- mCachePinMargin = cachePinMargin;
- }
-
- private static boolean isLocal(int dataSourceType) {
- return dataSourceType != DataSourceType.TYPE_PICASA;
- }
-
- @Override
- public int renderSlot(GLCanvas canvas, int index, int pass, int width, int height) {
- AlbumSetEntry entry = mDataWindow.get(index);
-
- boolean wantCache = entry.cacheFlag == MediaSet.CACHE_FLAG_FULL;
- boolean isCaching = wantCache && (
- entry.cacheStatus != MediaSet.CACHE_STATUS_CACHED_FULL);
- boolean selected = mSelectionManager.isItemSelected(entry.setPath);
- boolean chooseToCache = wantCache ^ selected;
- boolean available = isLocal(entry.sourceType) || chooseToCache;
-
- int renderRequestFlags = 0;
-
- if (!available) {
- canvas.save(GLCanvas.SAVE_FLAG_ALPHA);
- canvas.multiplyAlpha(0.6f);
- }
- renderRequestFlags |= renderContent(canvas, entry, width, height);
- if (!available) canvas.restore();
-
- renderRequestFlags |= renderLabel(canvas, entry, width, height);
-
- drawCachingPin(canvas, entry.setPath,
- entry.sourceType, isCaching, chooseToCache, width, height);
-
- renderRequestFlags |= renderOverlay(canvas, index, entry, width, height);
- return renderRequestFlags;
- }
-
- private void drawCachingPin(GLCanvas canvas, Path path, int dataSourceType,
- boolean isCaching, boolean chooseToCache, int width, int height) {
- ResourceTexture icon;
- if (isLocal(dataSourceType)) {
- icon = mLocalAlbumIcon;
- } else if (chooseToCache) {
- icon = mCheckedItem;
- } else {
- icon = mUnCheckedItem;
- }
-
- // show the icon in right bottom
- int s = mCachePinSize;
- int m = mCachePinMargin;
- icon.draw(canvas, width - m - s, height - s, s, s);
-
- if (isCaching) {
- int w = mCachingText.getWidth();
- int h = mCachingText.getHeight();
- // Show the caching text in bottom center
- mCachingText.draw(canvas, (width - w) / 2, height - h);
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/MeasureHelper.java b/src/com/android/gallery3d/ui/MeasureHelper.java
deleted file mode 100644
index f65dc10b3..000000000
--- a/src/com/android/gallery3d/ui/MeasureHelper.java
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.graphics.Rect;
-import android.view.View.MeasureSpec;
-
-class MeasureHelper {
-
- private static MeasureHelper sInstance = new MeasureHelper(null);
-
- private GLView mComponent;
- private int mPreferredWidth;
- private int mPreferredHeight;
-
- private MeasureHelper(GLView component) {
- mComponent = component;
- }
-
- public static MeasureHelper getInstance(GLView component) {
- sInstance.mComponent = component;
- return sInstance;
- }
-
- public MeasureHelper setPreferredContentSize(int width, int height) {
- mPreferredWidth = width;
- mPreferredHeight = height;
- return this;
- }
-
- public void measure(int widthSpec, int heightSpec) {
- Rect p = mComponent.getPaddings();
- setMeasuredSize(
- getLength(widthSpec, mPreferredWidth + p.left + p.right),
- getLength(heightSpec, mPreferredHeight + p.top + p.bottom));
- }
-
- private static int getLength(int measureSpec, int prefered) {
- int specLength = MeasureSpec.getSize(measureSpec);
- switch(MeasureSpec.getMode(measureSpec)) {
- case MeasureSpec.EXACTLY: return specLength;
- case MeasureSpec.AT_MOST: return Math.min(prefered, specLength);
- default: return prefered;
- }
- }
-
- protected void setMeasuredSize(int width, int height) {
- mComponent.setMeasuredSize(width, height);
- }
-
-}
diff --git a/src/com/android/gallery3d/ui/MenuExecutor.java b/src/com/android/gallery3d/ui/MenuExecutor.java
deleted file mode 100644
index 29def0527..000000000
--- a/src/com/android/gallery3d/ui/MenuExecutor.java
+++ /dev/null
@@ -1,448 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.app.Activity;
-import android.app.AlertDialog;
-import android.app.ProgressDialog;
-import android.content.Context;
-import android.content.DialogInterface;
-import android.content.DialogInterface.OnCancelListener;
-import android.content.DialogInterface.OnClickListener;
-import android.content.Intent;
-import android.os.Handler;
-import android.os.Message;
-import android.view.Menu;
-import android.view.MenuItem;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.filtershow.crop.CropActivity;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.util.ArrayList;
-
-public class MenuExecutor {
- @SuppressWarnings("unused")
- private static final String TAG = "MenuExecutor";
-
- private static final int MSG_TASK_COMPLETE = 1;
- private static final int MSG_TASK_UPDATE = 2;
- private static final int MSG_TASK_START = 3;
- private static final int MSG_DO_SHARE = 4;
-
- public static final int EXECUTION_RESULT_SUCCESS = 1;
- public static final int EXECUTION_RESULT_FAIL = 2;
- public static final int EXECUTION_RESULT_CANCEL = 3;
-
- private ProgressDialog mDialog;
- private Future<?> mTask;
- // wait the operation to finish when we want to stop it.
- private boolean mWaitOnStop;
- private boolean mPaused;
-
- private final AbstractGalleryActivity mActivity;
- private final SelectionManager mSelectionManager;
- private final Handler mHandler;
-
- private static ProgressDialog createProgressDialog(
- Context context, int titleId, int progressMax) {
- ProgressDialog dialog = new ProgressDialog(context);
- dialog.setTitle(titleId);
- dialog.setMax(progressMax);
- dialog.setCancelable(false);
- dialog.setIndeterminate(false);
- if (progressMax > 1) {
- dialog.setProgressStyle(ProgressDialog.STYLE_HORIZONTAL);
- }
- return dialog;
- }
-
- public interface ProgressListener {
- public void onConfirmDialogShown();
- public void onConfirmDialogDismissed(boolean confirmed);
- public void onProgressStart();
- public void onProgressUpdate(int index);
- public void onProgressComplete(int result);
- }
-
- public MenuExecutor(
- AbstractGalleryActivity activity, SelectionManager selectionManager) {
- mActivity = Utils.checkNotNull(activity);
- mSelectionManager = Utils.checkNotNull(selectionManager);
- mHandler = new SynchronizedHandler(mActivity.getGLRoot()) {
- @Override
- public void handleMessage(Message message) {
- switch (message.what) {
- case MSG_TASK_START: {
- if (message.obj != null) {
- ProgressListener listener = (ProgressListener) message.obj;
- listener.onProgressStart();
- }
- break;
- }
- case MSG_TASK_COMPLETE: {
- stopTaskAndDismissDialog();
- if (message.obj != null) {
- ProgressListener listener = (ProgressListener) message.obj;
- listener.onProgressComplete(message.arg1);
- }
- mSelectionManager.leaveSelectionMode();
- break;
- }
- case MSG_TASK_UPDATE: {
- if (mDialog != null && !mPaused) mDialog.setProgress(message.arg1);
- if (message.obj != null) {
- ProgressListener listener = (ProgressListener) message.obj;
- listener.onProgressUpdate(message.arg1);
- }
- break;
- }
- case MSG_DO_SHARE: {
- ((Activity) mActivity).startActivity((Intent) message.obj);
- break;
- }
- }
- }
- };
- }
-
- private void stopTaskAndDismissDialog() {
- if (mTask != null) {
- if (!mWaitOnStop) mTask.cancel();
- if (mDialog != null && mDialog.isShowing()) mDialog.dismiss();
- mDialog = null;
- mTask = null;
- }
- }
-
- public void resume() {
- mPaused = false;
- if (mDialog != null) mDialog.show();
- }
-
- public void pause() {
- mPaused = true;
- if (mDialog != null && mDialog.isShowing()) mDialog.hide();
- }
-
- public void destroy() {
- stopTaskAndDismissDialog();
- }
-
- private void onProgressUpdate(int index, ProgressListener listener) {
- mHandler.sendMessage(
- mHandler.obtainMessage(MSG_TASK_UPDATE, index, 0, listener));
- }
-
- private void onProgressStart(ProgressListener listener) {
- mHandler.sendMessage(mHandler.obtainMessage(MSG_TASK_START, listener));
- }
-
- private void onProgressComplete(int result, ProgressListener listener) {
- mHandler.sendMessage(mHandler.obtainMessage(MSG_TASK_COMPLETE, result, 0, listener));
- }
-
- public static void updateMenuOperation(Menu menu, int supported) {
- boolean supportDelete = (supported & MediaObject.SUPPORT_DELETE) != 0;
- boolean supportRotate = (supported & MediaObject.SUPPORT_ROTATE) != 0;
- boolean supportCrop = (supported & MediaObject.SUPPORT_CROP) != 0;
- boolean supportTrim = (supported & MediaObject.SUPPORT_TRIM) != 0;
- boolean supportMute = (supported & MediaObject.SUPPORT_MUTE) != 0;
- boolean supportShare = (supported & MediaObject.SUPPORT_SHARE) != 0;
- boolean supportSetAs = (supported & MediaObject.SUPPORT_SETAS) != 0;
- boolean supportShowOnMap = (supported & MediaObject.SUPPORT_SHOW_ON_MAP) != 0;
- boolean supportCache = (supported & MediaObject.SUPPORT_CACHE) != 0;
- boolean supportEdit = (supported & MediaObject.SUPPORT_EDIT) != 0;
- boolean supportInfo = (supported & MediaObject.SUPPORT_INFO) != 0;
-
- setMenuItemVisible(menu, R.id.action_delete, supportDelete);
- setMenuItemVisible(menu, R.id.action_rotate_ccw, supportRotate);
- setMenuItemVisible(menu, R.id.action_rotate_cw, supportRotate);
- setMenuItemVisible(menu, R.id.action_crop, supportCrop);
- setMenuItemVisible(menu, R.id.action_trim, supportTrim);
- setMenuItemVisible(menu, R.id.action_mute, supportMute);
- // Hide panorama until call to updateMenuForPanorama corrects it
- setMenuItemVisible(menu, R.id.action_share_panorama, false);
- setMenuItemVisible(menu, R.id.action_share, supportShare);
- setMenuItemVisible(menu, R.id.action_setas, supportSetAs);
- setMenuItemVisible(menu, R.id.action_show_on_map, supportShowOnMap);
- setMenuItemVisible(menu, R.id.action_edit, supportEdit);
- setMenuItemVisible(menu, R.id.action_simple_edit, supportEdit);
- setMenuItemVisible(menu, R.id.action_details, supportInfo);
- }
-
- public static void updateMenuForPanorama(Menu menu, boolean shareAsPanorama360,
- boolean disablePanorama360Options) {
- setMenuItemVisible(menu, R.id.action_share_panorama, shareAsPanorama360);
- if (disablePanorama360Options) {
- setMenuItemVisible(menu, R.id.action_rotate_ccw, false);
- setMenuItemVisible(menu, R.id.action_rotate_cw, false);
- }
- }
-
- private static void setMenuItemVisible(Menu menu, int itemId, boolean visible) {
- MenuItem item = menu.findItem(itemId);
- if (item != null) item.setVisible(visible);
- }
-
- private Path getSingleSelectedPath() {
- ArrayList<Path> ids = mSelectionManager.getSelected(true);
- Utils.assertTrue(ids.size() == 1);
- return ids.get(0);
- }
-
- private Intent getIntentBySingleSelectedPath(String action) {
- DataManager manager = mActivity.getDataManager();
- Path path = getSingleSelectedPath();
- String mimeType = getMimeType(manager.getMediaType(path));
- return new Intent(action).setDataAndType(manager.getContentUri(path), mimeType);
- }
-
- private void onMenuClicked(int action, ProgressListener listener) {
- onMenuClicked(action, listener, false, true);
- }
-
- public void onMenuClicked(int action, ProgressListener listener,
- boolean waitOnStop, boolean showDialog) {
- int title;
- switch (action) {
- case R.id.action_select_all:
- if (mSelectionManager.inSelectAllMode()) {
- mSelectionManager.deSelectAll();
- } else {
- mSelectionManager.selectAll();
- }
- return;
- case R.id.action_crop: {
- Intent intent = getIntentBySingleSelectedPath(CropActivity.CROP_ACTION);
- ((Activity) mActivity).startActivity(intent);
- return;
- }
- case R.id.action_edit: {
- Intent intent = getIntentBySingleSelectedPath(Intent.ACTION_EDIT)
- .setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
- ((Activity) mActivity).startActivity(Intent.createChooser(intent, null));
- return;
- }
- case R.id.action_setas: {
- Intent intent = getIntentBySingleSelectedPath(Intent.ACTION_ATTACH_DATA)
- .addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
- intent.putExtra("mimeType", intent.getType());
- Activity activity = mActivity;
- activity.startActivity(Intent.createChooser(
- intent, activity.getString(R.string.set_as)));
- return;
- }
- case R.id.action_delete:
- title = R.string.delete;
- break;
- case R.id.action_rotate_cw:
- title = R.string.rotate_right;
- break;
- case R.id.action_rotate_ccw:
- title = R.string.rotate_left;
- break;
- case R.id.action_show_on_map:
- title = R.string.show_on_map;
- break;
- default:
- return;
- }
- startAction(action, title, listener, waitOnStop, showDialog);
- }
-
- private class ConfirmDialogListener implements OnClickListener, OnCancelListener {
- private final int mActionId;
- private final ProgressListener mListener;
-
- public ConfirmDialogListener(int actionId, ProgressListener listener) {
- mActionId = actionId;
- mListener = listener;
- }
-
- @Override
- public void onClick(DialogInterface dialog, int which) {
- if (which == DialogInterface.BUTTON_POSITIVE) {
- if (mListener != null) {
- mListener.onConfirmDialogDismissed(true);
- }
- onMenuClicked(mActionId, mListener);
- } else {
- if (mListener != null) {
- mListener.onConfirmDialogDismissed(false);
- }
- }
- }
-
- @Override
- public void onCancel(DialogInterface dialog) {
- if (mListener != null) {
- mListener.onConfirmDialogDismissed(false);
- }
- }
- }
-
- public void onMenuClicked(MenuItem menuItem, String confirmMsg,
- final ProgressListener listener) {
- final int action = menuItem.getItemId();
-
- if (confirmMsg != null) {
- if (listener != null) listener.onConfirmDialogShown();
- ConfirmDialogListener cdl = new ConfirmDialogListener(action, listener);
- new AlertDialog.Builder(mActivity.getAndroidContext())
- .setMessage(confirmMsg)
- .setOnCancelListener(cdl)
- .setPositiveButton(R.string.ok, cdl)
- .setNegativeButton(R.string.cancel, cdl)
- .create().show();
- } else {
- onMenuClicked(action, listener);
- }
- }
-
- public void startAction(int action, int title, ProgressListener listener) {
- startAction(action, title, listener, false, true);
- }
-
- public void startAction(int action, int title, ProgressListener listener,
- boolean waitOnStop, boolean showDialog) {
- ArrayList<Path> ids = mSelectionManager.getSelected(false);
- stopTaskAndDismissDialog();
-
- Activity activity = mActivity;
- if (showDialog) {
- mDialog = createProgressDialog(activity, title, ids.size());
- mDialog.show();
- } else {
- mDialog = null;
- }
- MediaOperation operation = new MediaOperation(action, ids, listener);
- mTask = mActivity.getBatchServiceThreadPoolIfAvailable().submit(operation, null);
- mWaitOnStop = waitOnStop;
- }
-
- public void startSingleItemAction(int action, Path targetPath) {
- ArrayList<Path> ids = new ArrayList<Path>(1);
- ids.add(targetPath);
- mDialog = null;
- MediaOperation operation = new MediaOperation(action, ids, null);
- mTask = mActivity.getBatchServiceThreadPoolIfAvailable().submit(operation, null);
- mWaitOnStop = false;
- }
-
- public static String getMimeType(int type) {
- switch (type) {
- case MediaObject.MEDIA_TYPE_IMAGE :
- return GalleryUtils.MIME_TYPE_IMAGE;
- case MediaObject.MEDIA_TYPE_VIDEO :
- return GalleryUtils.MIME_TYPE_VIDEO;
- default: return GalleryUtils.MIME_TYPE_ALL;
- }
- }
-
- private boolean execute(
- DataManager manager, JobContext jc, int cmd, Path path) {
- boolean result = true;
- Log.v(TAG, "Execute cmd: " + cmd + " for " + path);
- long startTime = System.currentTimeMillis();
-
- switch (cmd) {
- case R.id.action_delete:
- manager.delete(path);
- break;
- case R.id.action_rotate_cw:
- manager.rotate(path, 90);
- break;
- case R.id.action_rotate_ccw:
- manager.rotate(path, -90);
- break;
- case R.id.action_toggle_full_caching: {
- MediaObject obj = manager.getMediaObject(path);
- int cacheFlag = obj.getCacheFlag();
- if (cacheFlag == MediaObject.CACHE_FLAG_FULL) {
- cacheFlag = MediaObject.CACHE_FLAG_SCREENNAIL;
- } else {
- cacheFlag = MediaObject.CACHE_FLAG_FULL;
- }
- obj.cache(cacheFlag);
- break;
- }
- case R.id.action_show_on_map: {
- MediaItem item = (MediaItem) manager.getMediaObject(path);
- double latlng[] = new double[2];
- item.getLatLong(latlng);
- if (GalleryUtils.isValidLocation(latlng[0], latlng[1])) {
- GalleryUtils.showOnMap(mActivity, latlng[0], latlng[1]);
- }
- break;
- }
- default:
- throw new AssertionError();
- }
- Log.v(TAG, "It takes " + (System.currentTimeMillis() - startTime) +
- " ms to execute cmd for " + path);
- return result;
- }
-
- private class MediaOperation implements Job<Void> {
- private final ArrayList<Path> mItems;
- private final int mOperation;
- private final ProgressListener mListener;
-
- public MediaOperation(int operation, ArrayList<Path> items,
- ProgressListener listener) {
- mOperation = operation;
- mItems = items;
- mListener = listener;
- }
-
- @Override
- public Void run(JobContext jc) {
- int index = 0;
- DataManager manager = mActivity.getDataManager();
- int result = EXECUTION_RESULT_SUCCESS;
- try {
- onProgressStart(mListener);
- for (Path id : mItems) {
- if (jc.isCancelled()) {
- result = EXECUTION_RESULT_CANCEL;
- break;
- }
- if (!execute(manager, jc, mOperation, id)) {
- result = EXECUTION_RESULT_FAIL;
- }
- onProgressUpdate(index++, mListener);
- }
- } catch (Throwable th) {
- Log.e(TAG, "failed to execute operation " + mOperation
- + " : " + th);
- } finally {
- onProgressComplete(result, mListener);
- }
- return null;
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/OrientationSource.java b/src/com/android/gallery3d/ui/OrientationSource.java
deleted file mode 100644
index e13ce1cec..000000000
--- a/src/com/android/gallery3d/ui/OrientationSource.java
+++ /dev/null
@@ -1,22 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-public interface OrientationSource {
- public int getDisplayRotation();
- public int getCompensation();
-}
diff --git a/src/com/android/gallery3d/ui/Paper.java b/src/com/android/gallery3d/ui/Paper.java
deleted file mode 100644
index b36f5c3a2..000000000
--- a/src/com/android/gallery3d/ui/Paper.java
+++ /dev/null
@@ -1,183 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.graphics.Rect;
-import android.opengl.Matrix;
-import android.view.animation.DecelerateInterpolator;
-import android.view.animation.Interpolator;
-
-import com.android.gallery3d.common.Utils;
-
-// This class does the overscroll effect.
-class Paper {
- @SuppressWarnings("unused")
- private static final String TAG = "Paper";
- private static final int ROTATE_FACTOR = 4;
- private EdgeAnimation mAnimationLeft = new EdgeAnimation();
- private EdgeAnimation mAnimationRight = new EdgeAnimation();
- private int mWidth;
- private float[] mMatrix = new float[16];
-
- public void overScroll(float distance) {
- distance /= mWidth; // make it relative to width
- if (distance < 0) {
- mAnimationLeft.onPull(-distance);
- } else {
- mAnimationRight.onPull(distance);
- }
- }
-
- public void edgeReached(float velocity) {
- velocity /= mWidth; // make it relative to width
- if (velocity < 0) {
- mAnimationRight.onAbsorb(-velocity);
- } else {
- mAnimationLeft.onAbsorb(velocity);
- }
- }
-
- public void onRelease() {
- mAnimationLeft.onRelease();
- mAnimationRight.onRelease();
- }
-
- public boolean advanceAnimation() {
- // Note that we use "|" because we want both animations get updated.
- return mAnimationLeft.update() | mAnimationRight.update();
- }
-
- public void setSize(int width, int height) {
- mWidth = width;
- }
-
- public float[] getTransform(Rect rect, float scrollX) {
- float left = mAnimationLeft.getValue();
- float right = mAnimationRight.getValue();
- float screenX = rect.centerX() - scrollX;
- // We linearly interpolate the value [left, right] for the screenX
- // range int [-1/4, 5/4]*mWidth. So if part of the thumbnail is outside
- // the screen, we still get some transform.
- float x = screenX + mWidth / 4;
- int range = 3 * mWidth / 2;
- float t = ((range - x) * left - x * right) / range;
- // compress t to the range (-1, 1) by the function
- // f(t) = (1 / (1 + e^-t) - 0.5) * 2
- // then multiply by 90 to make the range (-45, 45)
- float degrees =
- (1 / (1 + (float) Math.exp(-t * ROTATE_FACTOR)) - 0.5f) * 2 * -45;
- Matrix.setIdentityM(mMatrix, 0);
- Matrix.translateM(mMatrix, 0, mMatrix, 0, rect.centerX(), rect.centerY(), 0);
- Matrix.rotateM(mMatrix, 0, degrees, 0, 1, 0);
- Matrix.translateM(mMatrix, 0, mMatrix, 0, -rect.width() / 2, -rect.height() / 2, 0);
- return mMatrix;
- }
-}
-
-// This class follows the structure of frameworks's EdgeEffect class.
-class EdgeAnimation {
- @SuppressWarnings("unused")
- private static final String TAG = "EdgeAnimation";
-
- private static final int STATE_IDLE = 0;
- private static final int STATE_PULL = 1;
- private static final int STATE_ABSORB = 2;
- private static final int STATE_RELEASE = 3;
-
- // Time it will take the effect to fully done in ms
- private static final int ABSORB_TIME = 200;
- private static final int RELEASE_TIME = 500;
-
- private static final float VELOCITY_FACTOR = 0.1f;
-
- private final Interpolator mInterpolator;
-
- private int mState;
- private float mValue;
-
- private float mValueStart;
- private float mValueFinish;
- private long mStartTime;
- private long mDuration;
-
- public EdgeAnimation() {
- mInterpolator = new DecelerateInterpolator();
- mState = STATE_IDLE;
- }
-
- private void startAnimation(float start, float finish, long duration,
- int newState) {
- mValueStart = start;
- mValueFinish = finish;
- mDuration = duration;
- mStartTime = now();
- mState = newState;
- }
-
- // The deltaDistance's magnitude is in the range of -1 (no change) to 1.
- // The value 1 is the full length of the view. Negative values means the
- // movement is in the opposite direction.
- public void onPull(float deltaDistance) {
- if (mState == STATE_ABSORB) return;
- mValue = Utils.clamp(mValue + deltaDistance, -1.0f, 1.0f);
- mState = STATE_PULL;
- }
-
- public void onRelease() {
- if (mState == STATE_IDLE || mState == STATE_ABSORB) return;
- startAnimation(mValue, 0, RELEASE_TIME, STATE_RELEASE);
- }
-
- public void onAbsorb(float velocity) {
- float finish = Utils.clamp(mValue + velocity * VELOCITY_FACTOR,
- -1.0f, 1.0f);
- startAnimation(mValue, finish, ABSORB_TIME, STATE_ABSORB);
- }
-
- public boolean update() {
- if (mState == STATE_IDLE) return false;
- if (mState == STATE_PULL) return true;
-
- float t = Utils.clamp((float)(now() - mStartTime) / mDuration, 0.0f, 1.0f);
- /* Use linear interpolation for absorb, quadratic for others */
- float interp = (mState == STATE_ABSORB)
- ? t : mInterpolator.getInterpolation(t);
-
- mValue = mValueStart + (mValueFinish - mValueStart) * interp;
-
- if (t >= 1.0f) {
- switch (mState) {
- case STATE_ABSORB:
- startAnimation(mValue, 0, RELEASE_TIME, STATE_RELEASE);
- break;
- case STATE_RELEASE:
- mState = STATE_IDLE;
- break;
- }
- }
-
- return true;
- }
-
- public float getValue() {
- return mValue;
- }
-
- private long now() {
- return AnimationTime.get();
- }
-}
diff --git a/src/com/android/gallery3d/ui/PhotoFallbackEffect.java b/src/com/android/gallery3d/ui/PhotoFallbackEffect.java
deleted file mode 100644
index 4603285a4..000000000
--- a/src/com/android/gallery3d/ui/PhotoFallbackEffect.java
+++ /dev/null
@@ -1,179 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.view.animation.DecelerateInterpolator;
-import android.view.animation.Interpolator;
-
-import com.android.gallery3d.anim.Animation;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.RawTexture;
-import com.android.gallery3d.ui.AlbumSlotRenderer.SlotFilter;
-
-import java.util.ArrayList;
-
-public class PhotoFallbackEffect extends Animation implements SlotFilter {
-
- private static final int ANIM_DURATION = 300;
- private static final Interpolator ANIM_INTERPOLATE = new DecelerateInterpolator(1.5f);
-
- public static class Entry {
- public int index;
- public Path path;
- public Rect source;
- public Rect dest;
- public RawTexture texture;
-
- public Entry(Path path, Rect source, RawTexture texture) {
- this.path = path;
- this.source = source;
- this.texture = texture;
- }
- }
-
- public interface PositionProvider {
- public Rect getPosition(int index);
- public int getItemIndex(Path path);
- }
-
- private RectF mSource = new RectF();
- private RectF mTarget = new RectF();
- private float mProgress;
- private PositionProvider mPositionProvider;
-
- private ArrayList<Entry> mList = new ArrayList<Entry>();
-
- public PhotoFallbackEffect() {
- setDuration(ANIM_DURATION);
- setInterpolator(ANIM_INTERPOLATE);
- }
-
- public void addEntry(Path path, Rect rect, RawTexture texture) {
- mList.add(new Entry(path, rect, texture));
- }
-
- public Entry getEntry(Path path) {
- for (int i = 0, n = mList.size(); i < n; ++i) {
- Entry entry = mList.get(i);
- if (entry.path == path) return entry;
- }
- return null;
- }
-
- public boolean draw(GLCanvas canvas) {
- boolean more = calculate(AnimationTime.get());
- for (int i = 0, n = mList.size(); i < n; ++i) {
- Entry entry = mList.get(i);
- if (entry.index < 0) continue;
- entry.dest = mPositionProvider.getPosition(entry.index);
- drawEntry(canvas, entry);
- }
- return more;
- }
-
- private void drawEntry(GLCanvas canvas, Entry entry) {
- if (!entry.texture.isLoaded()) return;
-
- int w = entry.texture.getWidth();
- int h = entry.texture.getHeight();
-
- Rect s = entry.source;
- Rect d = entry.dest;
-
- // the following calculation is based on d.width() == d.height()
-
- float p = mProgress;
-
- float fullScale = (float) d.height() / Math.min(s.width(), s.height());
- float scale = fullScale * p + 1 * (1 - p);
-
- float cx = d.centerX() * p + s.centerX() * (1 - p);
- float cy = d.centerY() * p + s.centerY() * (1 - p);
-
- float ch = s.height() * scale;
- float cw = s.width() * scale;
-
- if (w > h) {
- // draw the center part
- mTarget.set(cx - ch / 2, cy - ch / 2, cx + ch / 2, cy + ch / 2);
- mSource.set((w - h) / 2, 0, (w + h) / 2, h);
- canvas.drawTexture(entry.texture, mSource, mTarget);
-
- canvas.save(GLCanvas.SAVE_FLAG_ALPHA);
- canvas.multiplyAlpha(1 - p);
-
- // draw the left part
- mTarget.set(cx - cw / 2, cy - ch / 2, cx - ch / 2, cy + ch / 2);
- mSource.set(0, 0, (w - h) / 2, h);
- canvas.drawTexture(entry.texture, mSource, mTarget);
-
- // draw the right part
- mTarget.set(cx + ch / 2, cy - ch / 2, cx + cw / 2, cy + ch / 2);
- mSource.set((w + h) / 2, 0, w, h);
- canvas.drawTexture(entry.texture, mSource, mTarget);
-
- canvas.restore();
- } else {
- // draw the center part
- mTarget.set(cx - cw / 2, cy - cw / 2, cx + cw / 2, cy + cw / 2);
- mSource.set(0, (h - w) / 2, w, (h + w) / 2);
- canvas.drawTexture(entry.texture, mSource, mTarget);
-
- canvas.save(GLCanvas.SAVE_FLAG_ALPHA);
- canvas.multiplyAlpha(1 - p);
-
- // draw the upper part
- mTarget.set(cx - cw / 2, cy - ch / 2, cx + cw / 2, cy - cw / 2);
- mSource.set(0, 0, w, (h - w) / 2);
- canvas.drawTexture(entry.texture, mSource, mTarget);
-
- // draw the bottom part
- mTarget.set(cx - cw / 2, cy + cw / 2, cx + cw / 2, cy + ch / 2);
- mSource.set(0, (w + h) / 2, w, h);
- canvas.drawTexture(entry.texture, mSource, mTarget);
-
- canvas.restore();
- }
- }
-
- @Override
- protected void onCalculate(float progress) {
- mProgress = progress;
- }
-
- public void setPositionProvider(PositionProvider provider) {
- mPositionProvider = provider;
- if (mPositionProvider != null) {
- for (int i = 0, n = mList.size(); i < n; ++i) {
- Entry entry = mList.get(i);
- entry.index = mPositionProvider.getItemIndex(entry.path);
- }
- }
- }
-
- @Override
- public boolean acceptSlot(int index) {
- for (int i = 0, n = mList.size(); i < n; ++i) {
- Entry entry = mList.get(i);
- if (entry.index == index) return false;
- }
- return true;
- }
-}
diff --git a/src/com/android/gallery3d/ui/PhotoView.java b/src/com/android/gallery3d/ui/PhotoView.java
deleted file mode 100644
index 7afa20348..000000000
--- a/src/com/android/gallery3d/ui/PhotoView.java
+++ /dev/null
@@ -1,1858 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.content.res.Configuration;
-import android.graphics.Color;
-import android.graphics.Matrix;
-import android.graphics.Rect;
-import android.os.Build;
-import android.os.Message;
-import android.util.FloatMath;
-import android.view.MotionEvent;
-import android.view.View.MeasureSpec;
-import android.view.animation.AccelerateInterpolator;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaObject;
-import com.android.gallery3d.data.Path;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.RawTexture;
-import com.android.gallery3d.glrenderer.ResourceTexture;
-import com.android.gallery3d.glrenderer.StringTexture;
-import com.android.gallery3d.glrenderer.Texture;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.RangeArray;
-import com.android.gallery3d.util.UsageStatistics;
-
-public class PhotoView extends GLView {
- @SuppressWarnings("unused")
- private static final String TAG = "PhotoView";
- private final int mPlaceholderColor;
-
- public static final int INVALID_SIZE = -1;
- public static final long INVALID_DATA_VERSION =
- MediaObject.INVALID_DATA_VERSION;
-
- public static class Size {
- public int width;
- public int height;
- }
-
- public interface Model extends TileImageView.TileSource {
- public int getCurrentIndex();
- public void moveTo(int index);
-
- // Returns the size for the specified picture. If the size information is
- // not avaiable, width = height = 0.
- public void getImageSize(int offset, Size size);
-
- // Returns the media item for the specified picture.
- public MediaItem getMediaItem(int offset);
-
- // Returns the rotation for the specified picture.
- public int getImageRotation(int offset);
-
- // This amends the getScreenNail() method of TileImageView.Model to get
- // ScreenNail at previous (negative offset) or next (positive offset)
- // positions. Returns null if the specified ScreenNail is unavailable.
- public ScreenNail getScreenNail(int offset);
-
- // Set this to true if we need the model to provide full images.
- public void setNeedFullImage(boolean enabled);
-
- // Returns true if the item is the Camera preview.
- public boolean isCamera(int offset);
-
- // Returns true if the item is the Panorama.
- public boolean isPanorama(int offset);
-
- // Returns true if the item is a static image that represents camera
- // preview.
- public boolean isStaticCamera(int offset);
-
- // Returns true if the item is a Video.
- public boolean isVideo(int offset);
-
- // Returns true if the item can be deleted.
- public boolean isDeletable(int offset);
-
- public static final int LOADING_INIT = 0;
- public static final int LOADING_COMPLETE = 1;
- public static final int LOADING_FAIL = 2;
-
- public int getLoadingState(int offset);
-
- // When data change happens, we need to decide which MediaItem to focus
- // on.
- //
- // 1. If focus hint path != null, we try to focus on it if we can find
- // it. This is used for undo a deletion, so we can focus on the
- // undeleted item.
- //
- // 2. Otherwise try to focus on the MediaItem that is currently focused,
- // if we can find it.
- //
- // 3. Otherwise try to focus on the previous MediaItem or the next
- // MediaItem, depending on the value of focus hint direction.
- public static final int FOCUS_HINT_NEXT = 0;
- public static final int FOCUS_HINT_PREVIOUS = 1;
- public void setFocusHintDirection(int direction);
- public void setFocusHintPath(Path path);
- }
-
- public interface Listener {
- public void onSingleTapUp(int x, int y);
- public void onFullScreenChanged(boolean full);
- public void onActionBarAllowed(boolean allowed);
- public void onActionBarWanted();
- public void onCurrentImageUpdated();
- public void onDeleteImage(Path path, int offset);
- public void onUndoDeleteImage();
- public void onCommitDeleteImage();
- public void onFilmModeChanged(boolean enabled);
- public void onPictureCenter(boolean isCamera);
- public void onUndoBarVisibilityChanged(boolean visible);
- }
-
- // The rules about orientation locking:
- //
- // (1) We need to lock the orientation if we are in page mode camera
- // preview, so there is no (unwanted) rotation animation when the user
- // rotates the device.
- //
- // (2) We need to unlock the orientation if we want to show the action bar
- // because the action bar follows the system orientation.
- //
- // The rules about action bar:
- //
- // (1) If we are in film mode, we don't show action bar.
- //
- // (2) If we go from camera to gallery with capture animation, we show
- // action bar.
- private static final int MSG_CANCEL_EXTRA_SCALING = 2;
- private static final int MSG_SWITCH_FOCUS = 3;
- private static final int MSG_CAPTURE_ANIMATION_DONE = 4;
- private static final int MSG_DELETE_ANIMATION_DONE = 5;
- private static final int MSG_DELETE_DONE = 6;
- private static final int MSG_UNDO_BAR_TIMEOUT = 7;
- private static final int MSG_UNDO_BAR_FULL_CAMERA = 8;
-
- private static final float SWIPE_THRESHOLD = 300f;
-
- private static final float DEFAULT_TEXT_SIZE = 20;
- private static float TRANSITION_SCALE_FACTOR = 0.74f;
- private static final int ICON_RATIO = 6;
-
- // whether we want to apply card deck effect in page mode.
- private static final boolean CARD_EFFECT = true;
-
- // whether we want to apply offset effect in film mode.
- private static final boolean OFFSET_EFFECT = true;
-
- // Used to calculate the scaling factor for the card deck effect.
- private ZInterpolator mScaleInterpolator = new ZInterpolator(0.5f);
-
- // Used to calculate the alpha factor for the fading animation.
- private AccelerateInterpolator mAlphaInterpolator =
- new AccelerateInterpolator(0.9f);
-
- // We keep this many previous ScreenNails. (also this many next ScreenNails)
- public static final int SCREEN_NAIL_MAX = 3;
-
- // These are constants for the delete gesture.
- private static final int SWIPE_ESCAPE_VELOCITY = 500; // dp/sec
- private static final int MAX_DISMISS_VELOCITY = 2500; // dp/sec
- private static final int SWIPE_ESCAPE_DISTANCE = 150; // dp
-
- // The picture entries, the valid index is from -SCREEN_NAIL_MAX to
- // SCREEN_NAIL_MAX.
- private final RangeArray<Picture> mPictures =
- new RangeArray<Picture>(-SCREEN_NAIL_MAX, SCREEN_NAIL_MAX);
- private Size[] mSizes = new Size[2 * SCREEN_NAIL_MAX + 1];
-
- private final MyGestureListener mGestureListener;
- private final GestureRecognizer mGestureRecognizer;
- private final PositionController mPositionController;
-
- private Listener mListener;
- private Model mModel;
- private StringTexture mNoThumbnailText;
- private TileImageView mTileView;
- private EdgeView mEdgeView;
- private UndoBarView mUndoBar;
- private Texture mVideoPlayIcon;
-
- private SynchronizedHandler mHandler;
-
- private boolean mCancelExtraScalingPending;
- private boolean mFilmMode = false;
- private boolean mWantPictureCenterCallbacks = false;
- private int mDisplayRotation = 0;
- private int mCompensation = 0;
- private boolean mFullScreenCamera;
- private Rect mCameraRelativeFrame = new Rect();
- private Rect mCameraRect = new Rect();
- private boolean mFirst = true;
-
- // [mPrevBound, mNextBound] is the range of index for all pictures in the
- // model, if we assume the index of current focused picture is 0. So if
- // there are some previous pictures, mPrevBound < 0, and if there are some
- // next pictures, mNextBound > 0.
- private int mPrevBound;
- private int mNextBound;
-
- // This variable prevents us doing snapback until its values goes to 0. This
- // happens if the user gesture is still in progress or we are in a capture
- // animation.
- private int mHolding;
- private static final int HOLD_TOUCH_DOWN = 1;
- private static final int HOLD_CAPTURE_ANIMATION = 2;
- private static final int HOLD_DELETE = 4;
-
- // mTouchBoxIndex is the index of the box that is touched by the down
- // gesture in film mode. The value Integer.MAX_VALUE means no box was
- // touched.
- private int mTouchBoxIndex = Integer.MAX_VALUE;
- // Whether the box indicated by mTouchBoxIndex is deletable. Only meaningful
- // if mTouchBoxIndex is not Integer.MAX_VALUE.
- private boolean mTouchBoxDeletable;
- // This is the index of the last deleted item. This is only used as a hint
- // to hide the undo button when we are too far away from the deleted
- // item. The value Integer.MAX_VALUE means there is no such hint.
- private int mUndoIndexHint = Integer.MAX_VALUE;
-
- private Context mContext;
-
- public PhotoView(AbstractGalleryActivity activity) {
- mTileView = new TileImageView(activity);
- addComponent(mTileView);
- mContext = activity.getAndroidContext();
- mPlaceholderColor = mContext.getResources().getColor(
- R.color.photo_placeholder);
- mEdgeView = new EdgeView(mContext);
- addComponent(mEdgeView);
- mUndoBar = new UndoBarView(mContext);
- addComponent(mUndoBar);
- mUndoBar.setVisibility(GLView.INVISIBLE);
- mUndoBar.setOnClickListener(new OnClickListener() {
- @Override
- public void onClick(GLView v) {
- mListener.onUndoDeleteImage();
- hideUndoBar();
- }
- });
- mNoThumbnailText = StringTexture.newInstance(
- mContext.getString(R.string.no_thumbnail),
- DEFAULT_TEXT_SIZE, Color.WHITE);
-
- mHandler = new MyHandler(activity.getGLRoot());
-
- mGestureListener = new MyGestureListener();
- mGestureRecognizer = new GestureRecognizer(mContext, mGestureListener);
-
- mPositionController = new PositionController(mContext,
- new PositionController.Listener() {
-
- @Override
- public void invalidate() {
- PhotoView.this.invalidate();
- }
-
- @Override
- public boolean isHoldingDown() {
- return (mHolding & HOLD_TOUCH_DOWN) != 0;
- }
-
- @Override
- public boolean isHoldingDelete() {
- return (mHolding & HOLD_DELETE) != 0;
- }
-
- @Override
- public void onPull(int offset, int direction) {
- mEdgeView.onPull(offset, direction);
- }
-
- @Override
- public void onRelease() {
- mEdgeView.onRelease();
- }
-
- @Override
- public void onAbsorb(int velocity, int direction) {
- mEdgeView.onAbsorb(velocity, direction);
- }
- });
- mVideoPlayIcon = new ResourceTexture(mContext, R.drawable.ic_control_play);
- for (int i = -SCREEN_NAIL_MAX; i <= SCREEN_NAIL_MAX; i++) {
- if (i == 0) {
- mPictures.put(i, new FullPicture());
- } else {
- mPictures.put(i, new ScreenNailPicture(i));
- }
- }
- }
-
- public void stopScrolling() {
- mPositionController.stopScrolling();
- }
-
- public void setModel(Model model) {
- mModel = model;
- mTileView.setModel(mModel);
- }
-
- class MyHandler extends SynchronizedHandler {
- public MyHandler(GLRoot root) {
- super(root);
- }
-
- @Override
- public void handleMessage(Message message) {
- switch (message.what) {
- case MSG_CANCEL_EXTRA_SCALING: {
- mGestureRecognizer.cancelScale();
- mPositionController.setExtraScalingRange(false);
- mCancelExtraScalingPending = false;
- break;
- }
- case MSG_SWITCH_FOCUS: {
- switchFocus();
- break;
- }
- case MSG_CAPTURE_ANIMATION_DONE: {
- // message.arg1 is the offset parameter passed to
- // switchWithCaptureAnimation().
- captureAnimationDone(message.arg1);
- break;
- }
- case MSG_DELETE_ANIMATION_DONE: {
- // message.obj is the Path of the MediaItem which should be
- // deleted. message.arg1 is the offset of the image.
- mListener.onDeleteImage((Path) message.obj, message.arg1);
- // Normally a box which finishes delete animation will hold
- // position until the underlying MediaItem is actually
- // deleted, and HOLD_DELETE will be cancelled that time. In
- // case the MediaItem didn't actually get deleted in 2
- // seconds, we will cancel HOLD_DELETE and make it bounce
- // back.
-
- // We make sure there is at most one MSG_DELETE_DONE
- // in the handler.
- mHandler.removeMessages(MSG_DELETE_DONE);
- Message m = mHandler.obtainMessage(MSG_DELETE_DONE);
- mHandler.sendMessageDelayed(m, 2000);
-
- int numberOfPictures = mNextBound - mPrevBound + 1;
- if (numberOfPictures == 2) {
- if (mModel.isCamera(mNextBound)
- || mModel.isCamera(mPrevBound)) {
- numberOfPictures--;
- }
- }
- showUndoBar(numberOfPictures <= 1);
- break;
- }
- case MSG_DELETE_DONE: {
- if (!mHandler.hasMessages(MSG_DELETE_ANIMATION_DONE)) {
- mHolding &= ~HOLD_DELETE;
- snapback();
- }
- break;
- }
- case MSG_UNDO_BAR_TIMEOUT: {
- checkHideUndoBar(UNDO_BAR_TIMEOUT);
- break;
- }
- case MSG_UNDO_BAR_FULL_CAMERA: {
- checkHideUndoBar(UNDO_BAR_FULL_CAMERA);
- break;
- }
- default: throw new AssertionError(message.what);
- }
- }
- }
-
- public void setWantPictureCenterCallbacks(boolean wanted) {
- mWantPictureCenterCallbacks = wanted;
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Data/Image change notifications
- ////////////////////////////////////////////////////////////////////////////
-
- public void notifyDataChange(int[] fromIndex, int prevBound, int nextBound) {
- mPrevBound = prevBound;
- mNextBound = nextBound;
-
- // Update mTouchBoxIndex
- if (mTouchBoxIndex != Integer.MAX_VALUE) {
- int k = mTouchBoxIndex;
- mTouchBoxIndex = Integer.MAX_VALUE;
- for (int i = 0; i < 2 * SCREEN_NAIL_MAX + 1; i++) {
- if (fromIndex[i] == k) {
- mTouchBoxIndex = i - SCREEN_NAIL_MAX;
- break;
- }
- }
- }
-
- // Hide undo button if we are too far away
- if (mUndoIndexHint != Integer.MAX_VALUE) {
- if (Math.abs(mUndoIndexHint - mModel.getCurrentIndex()) >= 3) {
- hideUndoBar();
- }
- }
-
- // Update the ScreenNails.
- for (int i = -SCREEN_NAIL_MAX; i <= SCREEN_NAIL_MAX; i++) {
- Picture p = mPictures.get(i);
- p.reload();
- mSizes[i + SCREEN_NAIL_MAX] = p.getSize();
- }
-
- boolean wasDeleting = mPositionController.hasDeletingBox();
-
- // Move the boxes
- mPositionController.moveBox(fromIndex, mPrevBound < 0, mNextBound > 0,
- mModel.isCamera(0), mSizes);
-
- for (int i = -SCREEN_NAIL_MAX; i <= SCREEN_NAIL_MAX; i++) {
- setPictureSize(i);
- }
-
- boolean isDeleting = mPositionController.hasDeletingBox();
-
- // If the deletion is done, make HOLD_DELETE persist for only the time
- // needed for a snapback animation.
- if (wasDeleting && !isDeleting) {
- mHandler.removeMessages(MSG_DELETE_DONE);
- Message m = mHandler.obtainMessage(MSG_DELETE_DONE);
- mHandler.sendMessageDelayed(
- m, PositionController.SNAPBACK_ANIMATION_TIME);
- }
-
- invalidate();
- }
-
- public boolean isDeleting() {
- return (mHolding & HOLD_DELETE) != 0
- && mPositionController.hasDeletingBox();
- }
-
- public void notifyImageChange(int index) {
- if (index == 0) {
- mListener.onCurrentImageUpdated();
- }
- mPictures.get(index).reload();
- setPictureSize(index);
- invalidate();
- }
-
- private void setPictureSize(int index) {
- Picture p = mPictures.get(index);
- mPositionController.setImageSize(index, p.getSize(),
- index == 0 && p.isCamera() ? mCameraRect : null);
- }
-
- @Override
- protected void onLayout(
- boolean changeSize, int left, int top, int right, int bottom) {
- int w = right - left;
- int h = bottom - top;
- mTileView.layout(0, 0, w, h);
- mEdgeView.layout(0, 0, w, h);
- mUndoBar.measure(MeasureSpec.UNSPECIFIED, MeasureSpec.UNSPECIFIED);
- mUndoBar.layout(0, h - mUndoBar.getMeasuredHeight(), w, h);
-
- GLRoot root = getGLRoot();
- int displayRotation = root.getDisplayRotation();
- int compensation = root.getCompensation();
- if (mDisplayRotation != displayRotation
- || mCompensation != compensation) {
- mDisplayRotation = displayRotation;
- mCompensation = compensation;
-
- // We need to change the size and rotation of the Camera ScreenNail,
- // but we don't want it to animate because the size doen't actually
- // change in the eye of the user.
- for (int i = -SCREEN_NAIL_MAX; i <= SCREEN_NAIL_MAX; i++) {
- Picture p = mPictures.get(i);
- if (p.isCamera()) {
- p.forceSize();
- }
- }
- }
-
- updateCameraRect();
- mPositionController.setConstrainedFrame(mCameraRect);
- if (changeSize) {
- mPositionController.setViewSize(getWidth(), getHeight());
- }
- }
-
- // Update the camera rectangle due to layout change or camera relative frame
- // change.
- private void updateCameraRect() {
- // Get the width and height in framework orientation because the given
- // mCameraRelativeFrame is in that coordinates.
- int w = getWidth();
- int h = getHeight();
- if (mCompensation % 180 != 0) {
- int tmp = w;
- w = h;
- h = tmp;
- }
- int l = mCameraRelativeFrame.left;
- int t = mCameraRelativeFrame.top;
- int r = mCameraRelativeFrame.right;
- int b = mCameraRelativeFrame.bottom;
-
- // Now convert it to the coordinates we are using.
- switch (mCompensation) {
- case 0: mCameraRect.set(l, t, r, b); break;
- case 90: mCameraRect.set(h - b, l, h - t, r); break;
- case 180: mCameraRect.set(w - r, h - b, w - l, h - t); break;
- case 270: mCameraRect.set(t, w - r, b, w - l); break;
- }
-
- Log.d(TAG, "compensation = " + mCompensation
- + ", CameraRelativeFrame = " + mCameraRelativeFrame
- + ", mCameraRect = " + mCameraRect);
- }
-
- public void setCameraRelativeFrame(Rect frame) {
- mCameraRelativeFrame.set(frame);
- updateCameraRect();
- // Originally we do
- // mPositionController.setConstrainedFrame(mCameraRect);
- // here, but it is moved to a parameter of the setImageSize() call, so
- // it can be updated atomically with the CameraScreenNail's size change.
- }
-
- // Returns the rotation we need to do to the camera texture before drawing
- // it to the canvas, assuming the camera texture is correct when the device
- // is in its natural orientation.
- private int getCameraRotation() {
- return (mCompensation - mDisplayRotation + 360) % 360;
- }
-
- private int getPanoramaRotation() {
- // This function is magic
- // The issue here is that Pano makes bad assumptions about rotation and
- // orientation. The first is it assumes only two rotations are possible,
- // 0 and 90. Thus, if display rotation is >= 180, we invert the output.
- // The second is that it assumes landscape is a 90 rotation from portrait,
- // however on landscape devices this is not true. Thus, if we are in portrait
- // on a landscape device, we need to invert the output
- int orientation = mContext.getResources().getConfiguration().orientation;
- boolean invertPortrait = (orientation == Configuration.ORIENTATION_PORTRAIT
- && (mDisplayRotation == 90 || mDisplayRotation == 270));
- boolean invert = (mDisplayRotation >= 180);
- if (invert != invertPortrait) {
- return (mCompensation + 180) % 360;
- }
- return mCompensation;
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Pictures
- ////////////////////////////////////////////////////////////////////////////
-
- private interface Picture {
- void reload();
- void draw(GLCanvas canvas, Rect r);
- void setScreenNail(ScreenNail s);
- boolean isCamera(); // whether the picture is a camera preview
- boolean isDeletable(); // whether the picture can be deleted
- void forceSize(); // called when mCompensation changes
- Size getSize();
- }
-
- class FullPicture implements Picture {
- private int mRotation;
- private boolean mIsCamera;
- private boolean mIsPanorama;
- private boolean mIsStaticCamera;
- private boolean mIsVideo;
- private boolean mIsDeletable;
- private int mLoadingState = Model.LOADING_INIT;
- private Size mSize = new Size();
-
- @Override
- public void reload() {
- // mImageWidth and mImageHeight will get updated
- mTileView.notifyModelInvalidated();
-
- mIsCamera = mModel.isCamera(0);
- mIsPanorama = mModel.isPanorama(0);
- mIsStaticCamera = mModel.isStaticCamera(0);
- mIsVideo = mModel.isVideo(0);
- mIsDeletable = mModel.isDeletable(0);
- mLoadingState = mModel.getLoadingState(0);
- setScreenNail(mModel.getScreenNail(0));
- updateSize();
- }
-
- @Override
- public Size getSize() {
- return mSize;
- }
-
- @Override
- public void forceSize() {
- updateSize();
- mPositionController.forceImageSize(0, mSize);
- }
-
- private void updateSize() {
- if (mIsPanorama) {
- mRotation = getPanoramaRotation();
- } else if (mIsCamera && !mIsStaticCamera) {
- mRotation = getCameraRotation();
- } else {
- mRotation = mModel.getImageRotation(0);
- }
-
- int w = mTileView.mImageWidth;
- int h = mTileView.mImageHeight;
- mSize.width = getRotated(mRotation, w, h);
- mSize.height = getRotated(mRotation, h, w);
- }
-
- @Override
- public void draw(GLCanvas canvas, Rect r) {
- drawTileView(canvas, r);
-
- // We want to have the following transitions:
- // (1) Move camera preview out of its place: switch to film mode
- // (2) Move camera preview into its place: switch to page mode
- // The extra mWasCenter check makes sure (1) does not apply if in
- // page mode, we move _to_ the camera preview from another picture.
-
- // Holdings except touch-down prevent the transitions.
- if ((mHolding & ~HOLD_TOUCH_DOWN) != 0) return;
-
- if (mWantPictureCenterCallbacks && mPositionController.isCenter()) {
- mListener.onPictureCenter(mIsCamera);
- }
- }
-
- @Override
- public void setScreenNail(ScreenNail s) {
- mTileView.setScreenNail(s);
- }
-
- @Override
- public boolean isCamera() {
- return mIsCamera;
- }
-
- @Override
- public boolean isDeletable() {
- return mIsDeletable;
- }
-
- private void drawTileView(GLCanvas canvas, Rect r) {
- float imageScale = mPositionController.getImageScale();
- int viewW = getWidth();
- int viewH = getHeight();
- float cx = r.exactCenterX();
- float cy = r.exactCenterY();
- float scale = 1f; // the scaling factor due to card effect
-
- canvas.save(GLCanvas.SAVE_FLAG_MATRIX | GLCanvas.SAVE_FLAG_ALPHA);
- float filmRatio = mPositionController.getFilmRatio();
- boolean wantsCardEffect = CARD_EFFECT && !mIsCamera
- && filmRatio != 1f && !mPictures.get(-1).isCamera()
- && !mPositionController.inOpeningAnimation();
- boolean wantsOffsetEffect = OFFSET_EFFECT && mIsDeletable
- && filmRatio == 1f && r.centerY() != viewH / 2;
- if (wantsCardEffect) {
- // Calculate the move-out progress value.
- int left = r.left;
- int right = r.right;
- float progress = calculateMoveOutProgress(left, right, viewW);
- progress = Utils.clamp(progress, -1f, 1f);
-
- // We only want to apply the fading animation if the scrolling
- // movement is to the right.
- if (progress < 0) {
- scale = getScrollScale(progress);
- float alpha = getScrollAlpha(progress);
- scale = interpolate(filmRatio, scale, 1f);
- alpha = interpolate(filmRatio, alpha, 1f);
-
- imageScale *= scale;
- canvas.multiplyAlpha(alpha);
-
- float cxPage; // the cx value in page mode
- if (right - left <= viewW) {
- // If the picture is narrower than the view, keep it at
- // the center of the view.
- cxPage = viewW / 2f;
- } else {
- // If the picture is wider than the view (it's
- // zoomed-in), keep the left edge of the object align
- // the the left edge of the view.
- cxPage = (right - left) * scale / 2f;
- }
- cx = interpolate(filmRatio, cxPage, cx);
- }
- } else if (wantsOffsetEffect) {
- float offset = (float) (r.centerY() - viewH / 2) / viewH;
- float alpha = getOffsetAlpha(offset);
- canvas.multiplyAlpha(alpha);
- }
-
- // Draw the tile view.
- setTileViewPosition(cx, cy, viewW, viewH, imageScale);
- renderChild(canvas, mTileView);
-
- // Draw the play video icon and the message.
- canvas.translate((int) (cx + 0.5f), (int) (cy + 0.5f));
- int s = (int) (scale * Math.min(r.width(), r.height()) + 0.5f);
- if (mIsVideo) drawVideoPlayIcon(canvas, s);
- if (mLoadingState == Model.LOADING_FAIL) {
- drawLoadingFailMessage(canvas);
- }
-
- // Draw a debug indicator showing which picture has focus (index ==
- // 0).
- //canvas.fillRect(-10, -10, 20, 20, 0x80FF00FF);
-
- canvas.restore();
- }
-
- // Set the position of the tile view
- private void setTileViewPosition(float cx, float cy,
- int viewW, int viewH, float scale) {
- // Find out the bitmap coordinates of the center of the view
- int imageW = mPositionController.getImageWidth();
- int imageH = mPositionController.getImageHeight();
- int centerX = (int) (imageW / 2f + (viewW / 2f - cx) / scale + 0.5f);
- int centerY = (int) (imageH / 2f + (viewH / 2f - cy) / scale + 0.5f);
-
- int inverseX = imageW - centerX;
- int inverseY = imageH - centerY;
- int x, y;
- switch (mRotation) {
- case 0: x = centerX; y = centerY; break;
- case 90: x = centerY; y = inverseX; break;
- case 180: x = inverseX; y = inverseY; break;
- case 270: x = inverseY; y = centerX; break;
- default:
- throw new RuntimeException(String.valueOf(mRotation));
- }
- mTileView.setPosition(x, y, scale, mRotation);
- }
- }
-
- private class ScreenNailPicture implements Picture {
- private int mIndex;
- private int mRotation;
- private ScreenNail mScreenNail;
- private boolean mIsCamera;
- private boolean mIsPanorama;
- private boolean mIsStaticCamera;
- private boolean mIsVideo;
- private boolean mIsDeletable;
- private int mLoadingState = Model.LOADING_INIT;
- private Size mSize = new Size();
-
- public ScreenNailPicture(int index) {
- mIndex = index;
- }
-
- @Override
- public void reload() {
- mIsCamera = mModel.isCamera(mIndex);
- mIsPanorama = mModel.isPanorama(mIndex);
- mIsStaticCamera = mModel.isStaticCamera(mIndex);
- mIsVideo = mModel.isVideo(mIndex);
- mIsDeletable = mModel.isDeletable(mIndex);
- mLoadingState = mModel.getLoadingState(mIndex);
- setScreenNail(mModel.getScreenNail(mIndex));
- updateSize();
- }
-
- @Override
- public Size getSize() {
- return mSize;
- }
-
- @Override
- public void draw(GLCanvas canvas, Rect r) {
- if (mScreenNail == null) {
- // Draw a placeholder rectange if there should be a picture in
- // this position (but somehow there isn't).
- if (mIndex >= mPrevBound && mIndex <= mNextBound) {
- drawPlaceHolder(canvas, r);
- }
- return;
- }
- int w = getWidth();
- int h = getHeight();
- if (r.left >= w || r.right <= 0 || r.top >= h || r.bottom <= 0) {
- mScreenNail.noDraw();
- return;
- }
-
- float filmRatio = mPositionController.getFilmRatio();
- boolean wantsCardEffect = CARD_EFFECT && mIndex > 0
- && filmRatio != 1f && !mPictures.get(0).isCamera();
- boolean wantsOffsetEffect = OFFSET_EFFECT && mIsDeletable
- && filmRatio == 1f && r.centerY() != h / 2;
- int cx = wantsCardEffect
- ? (int) (interpolate(filmRatio, w / 2, r.centerX()) + 0.5f)
- : r.centerX();
- int cy = r.centerY();
- canvas.save(GLCanvas.SAVE_FLAG_MATRIX | GLCanvas.SAVE_FLAG_ALPHA);
- canvas.translate(cx, cy);
- if (wantsCardEffect) {
- float progress = (float) (w / 2 - r.centerX()) / w;
- progress = Utils.clamp(progress, -1, 1);
- float alpha = getScrollAlpha(progress);
- float scale = getScrollScale(progress);
- alpha = interpolate(filmRatio, alpha, 1f);
- scale = interpolate(filmRatio, scale, 1f);
- canvas.multiplyAlpha(alpha);
- canvas.scale(scale, scale, 1);
- } else if (wantsOffsetEffect) {
- float offset = (float) (r.centerY() - h / 2) / h;
- float alpha = getOffsetAlpha(offset);
- canvas.multiplyAlpha(alpha);
- }
- if (mRotation != 0) {
- canvas.rotate(mRotation, 0, 0, 1);
- }
- int drawW = getRotated(mRotation, r.width(), r.height());
- int drawH = getRotated(mRotation, r.height(), r.width());
- mScreenNail.draw(canvas, -drawW / 2, -drawH / 2, drawW, drawH);
- if (isScreenNailAnimating()) {
- invalidate();
- }
- int s = Math.min(drawW, drawH);
- if (mIsVideo) drawVideoPlayIcon(canvas, s);
- if (mLoadingState == Model.LOADING_FAIL) {
- drawLoadingFailMessage(canvas);
- }
- canvas.restore();
- }
-
- private boolean isScreenNailAnimating() {
- return (mScreenNail instanceof TiledScreenNail)
- && ((TiledScreenNail) mScreenNail).isAnimating();
- }
-
- @Override
- public void setScreenNail(ScreenNail s) {
- mScreenNail = s;
- }
-
- @Override
- public void forceSize() {
- updateSize();
- mPositionController.forceImageSize(mIndex, mSize);
- }
-
- private void updateSize() {
- if (mIsPanorama) {
- mRotation = getPanoramaRotation();
- } else if (mIsCamera && !mIsStaticCamera) {
- mRotation = getCameraRotation();
- } else {
- mRotation = mModel.getImageRotation(mIndex);
- }
-
- if (mScreenNail != null) {
- mSize.width = mScreenNail.getWidth();
- mSize.height = mScreenNail.getHeight();
- } else {
- // If we don't have ScreenNail available, we can still try to
- // get the size information of it.
- mModel.getImageSize(mIndex, mSize);
- }
-
- int w = mSize.width;
- int h = mSize.height;
- mSize.width = getRotated(mRotation, w, h);
- mSize.height = getRotated(mRotation, h, w);
- }
-
- @Override
- public boolean isCamera() {
- return mIsCamera;
- }
-
- @Override
- public boolean isDeletable() {
- return mIsDeletable;
- }
- }
-
- // Draw a gray placeholder in the specified rectangle.
- private void drawPlaceHolder(GLCanvas canvas, Rect r) {
- canvas.fillRect(r.left, r.top, r.width(), r.height(), mPlaceholderColor);
- }
-
- // Draw the video play icon (in the place where the spinner was)
- private void drawVideoPlayIcon(GLCanvas canvas, int side) {
- int s = side / ICON_RATIO;
- // Draw the video play icon at the center
- mVideoPlayIcon.draw(canvas, -s / 2, -s / 2, s, s);
- }
-
- // Draw the "no thumbnail" message
- private void drawLoadingFailMessage(GLCanvas canvas) {
- StringTexture m = mNoThumbnailText;
- m.draw(canvas, -m.getWidth() / 2, -m.getHeight() / 2);
- }
-
- private static int getRotated(int degree, int original, int theother) {
- return (degree % 180 == 0) ? original : theother;
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Gestures Handling
- ////////////////////////////////////////////////////////////////////////////
-
- @Override
- protected boolean onTouch(MotionEvent event) {
- mGestureRecognizer.onTouchEvent(event);
- return true;
- }
-
- private class MyGestureListener implements GestureRecognizer.Listener {
- private boolean mIgnoreUpEvent = false;
- // If we can change mode for this scale gesture.
- private boolean mCanChangeMode;
- // If we have changed the film mode in this scaling gesture.
- private boolean mModeChanged;
- // If this scaling gesture should be ignored.
- private boolean mIgnoreScalingGesture;
- // whether the down action happened while the view is scrolling.
- private boolean mDownInScrolling;
- // If we should ignore all gestures other than onSingleTapUp.
- private boolean mIgnoreSwipingGesture;
- // If a scrolling has happened after a down gesture.
- private boolean mScrolledAfterDown;
- // If the first scrolling move is in X direction. In the film mode, X
- // direction scrolling is normal scrolling. but Y direction scrolling is
- // a delete gesture.
- private boolean mFirstScrollX;
- // The accumulated Y delta that has been sent to mPositionController.
- private int mDeltaY;
- // The accumulated scaling change from a scaling gesture.
- private float mAccScale;
- // If an onFling happened after the last onDown
- private boolean mHadFling;
-
- @Override
- public boolean onSingleTapUp(float x, float y) {
- // On crespo running Android 2.3.6 (gingerbread), a pinch out gesture results in the
- // following call sequence: onDown(), onUp() and then onSingleTapUp(). The correct
- // sequence for a single-tap-up gesture should be: onDown(), onSingleTapUp() and onUp().
- // The call sequence for a pinch out gesture in JB is: onDown(), then onUp() and there's
- // no onSingleTapUp(). Base on these observations, the following condition is added to
- // filter out the false alarm where onSingleTapUp() is called within a pinch out
- // gesture. The framework fix went into ICS. Refer to b/4588114.
- if (Build.VERSION.SDK_INT < ApiHelper.VERSION_CODES.ICE_CREAM_SANDWICH) {
- if ((mHolding & HOLD_TOUCH_DOWN) == 0) {
- return true;
- }
- }
-
- // We do this in addition to onUp() because we want the snapback of
- // setFilmMode to happen.
- mHolding &= ~HOLD_TOUCH_DOWN;
-
- if (mFilmMode && !mDownInScrolling) {
- switchToHitPicture((int) (x + 0.5f), (int) (y + 0.5f));
-
- // If this is a lock screen photo, let the listener handle the
- // event. Tapping on lock screen photo should take the user
- // directly to the lock screen.
- MediaItem item = mModel.getMediaItem(0);
- int supported = 0;
- if (item != null) supported = item.getSupportedOperations();
- if ((supported & MediaItem.SUPPORT_ACTION) == 0) {
- setFilmMode(false);
- mIgnoreUpEvent = true;
- return true;
- }
- }
-
- if (mListener != null) {
- // Do the inverse transform of the touch coordinates.
- Matrix m = getGLRoot().getCompensationMatrix();
- Matrix inv = new Matrix();
- m.invert(inv);
- float[] pts = new float[] {x, y};
- inv.mapPoints(pts);
- mListener.onSingleTapUp((int) (pts[0] + 0.5f), (int) (pts[1] + 0.5f));
- }
- return true;
- }
-
- @Override
- public boolean onDoubleTap(float x, float y) {
- if (mIgnoreSwipingGesture) return true;
- if (mPictures.get(0).isCamera()) return false;
- PositionController controller = mPositionController;
- float scale = controller.getImageScale();
- // onDoubleTap happened on the second ACTION_DOWN.
- // We need to ignore the next UP event.
- mIgnoreUpEvent = true;
- if (scale <= .75f || controller.isAtMinimalScale()) {
- controller.zoomIn(x, y, Math.max(1.0f, scale * 1.5f));
- } else {
- controller.resetToFullView();
- }
- return true;
- }
-
- @Override
- public boolean onScroll(float dx, float dy, float totalX, float totalY) {
- if (mIgnoreSwipingGesture) return true;
- if (!mScrolledAfterDown) {
- mScrolledAfterDown = true;
- mFirstScrollX = (Math.abs(dx) > Math.abs(dy));
- }
-
- int dxi = (int) (-dx + 0.5f);
- int dyi = (int) (-dy + 0.5f);
- if (mFilmMode) {
- if (mFirstScrollX) {
- mPositionController.scrollFilmX(dxi);
- } else {
- if (mTouchBoxIndex == Integer.MAX_VALUE) return true;
- int newDeltaY = calculateDeltaY(totalY);
- int d = newDeltaY - mDeltaY;
- if (d != 0) {
- mPositionController.scrollFilmY(mTouchBoxIndex, d);
- mDeltaY = newDeltaY;
- }
- }
- } else {
- mPositionController.scrollPage(dxi, dyi);
- }
- return true;
- }
-
- private int calculateDeltaY(float delta) {
- if (mTouchBoxDeletable) return (int) (delta + 0.5f);
-
- // don't let items that can't be deleted be dragged more than
- // maxScrollDistance, and make it harder and harder to drag.
- int size = getHeight();
- float maxScrollDistance = 0.15f * size;
- if (Math.abs(delta) >= size) {
- delta = delta > 0 ? maxScrollDistance : -maxScrollDistance;
- } else {
- delta = maxScrollDistance *
- FloatMath.sin((delta / size) * (float) (Math.PI / 2));
- }
- return (int) (delta + 0.5f);
- }
-
- @Override
- public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) {
- if (mIgnoreSwipingGesture) return true;
- if (mModeChanged) return true;
- if (swipeImages(velocityX, velocityY)) {
- mIgnoreUpEvent = true;
- } else {
- flingImages(velocityX, velocityY, Math.abs(e2.getY() - e1.getY()));
- }
- mHadFling = true;
- return true;
- }
-
- private boolean flingImages(float velocityX, float velocityY, float dY) {
- int vx = (int) (velocityX + 0.5f);
- int vy = (int) (velocityY + 0.5f);
- if (!mFilmMode) {
- return mPositionController.flingPage(vx, vy);
- }
- if (Math.abs(velocityX) > Math.abs(velocityY)) {
- return mPositionController.flingFilmX(vx);
- }
- // If we scrolled in Y direction fast enough, treat it as a delete
- // gesture.
- if (!mFilmMode || mTouchBoxIndex == Integer.MAX_VALUE
- || !mTouchBoxDeletable) {
- return false;
- }
- int maxVelocity = GalleryUtils.dpToPixel(MAX_DISMISS_VELOCITY);
- int escapeVelocity = GalleryUtils.dpToPixel(SWIPE_ESCAPE_VELOCITY);
- int escapeDistance = GalleryUtils.dpToPixel(SWIPE_ESCAPE_DISTANCE);
- int centerY = mPositionController.getPosition(mTouchBoxIndex)
- .centerY();
- boolean fastEnough = (Math.abs(vy) > escapeVelocity)
- && (Math.abs(vy) > Math.abs(vx))
- && ((vy > 0) == (centerY > getHeight() / 2))
- && dY >= escapeDistance;
- if (fastEnough) {
- vy = Math.min(vy, maxVelocity);
- int duration = mPositionController.flingFilmY(mTouchBoxIndex, vy);
- if (duration >= 0) {
- mPositionController.setPopFromTop(vy < 0);
- deleteAfterAnimation(duration);
- // We reset mTouchBoxIndex, so up() won't check if Y
- // scrolled far enough to be a delete gesture.
- mTouchBoxIndex = Integer.MAX_VALUE;
- return true;
- }
- }
- return false;
- }
-
- private void deleteAfterAnimation(int duration) {
- MediaItem item = mModel.getMediaItem(mTouchBoxIndex);
- if (item == null) return;
- mListener.onCommitDeleteImage();
- mUndoIndexHint = mModel.getCurrentIndex() + mTouchBoxIndex;
- mHolding |= HOLD_DELETE;
- Message m = mHandler.obtainMessage(MSG_DELETE_ANIMATION_DONE);
- m.obj = item.getPath();
- m.arg1 = mTouchBoxIndex;
- mHandler.sendMessageDelayed(m, duration);
- }
-
- @Override
- public boolean onScaleBegin(float focusX, float focusY) {
- if (mIgnoreSwipingGesture) return true;
- // We ignore the scaling gesture if it is a camera preview.
- mIgnoreScalingGesture = mPictures.get(0).isCamera();
- if (mIgnoreScalingGesture) {
- return true;
- }
- mPositionController.beginScale(focusX, focusY);
- // We can change mode if we are in film mode, or we are in page
- // mode and at minimal scale.
- mCanChangeMode = mFilmMode
- || mPositionController.isAtMinimalScale();
- mAccScale = 1f;
- return true;
- }
-
- @Override
- public boolean onScale(float focusX, float focusY, float scale) {
- if (mIgnoreSwipingGesture) return true;
- if (mIgnoreScalingGesture) return true;
- if (mModeChanged) return true;
- if (Float.isNaN(scale) || Float.isInfinite(scale)) return false;
-
- int outOfRange = mPositionController.scaleBy(scale, focusX, focusY);
-
- // We wait for a large enough scale change before changing mode.
- // Otherwise we may mistakenly treat a zoom-in gesture as zoom-out
- // or vice versa.
- mAccScale *= scale;
- boolean largeEnough = (mAccScale < 0.97f || mAccScale > 1.03f);
-
- // If mode changes, we treat this scaling gesture has ended.
- if (mCanChangeMode && largeEnough) {
- if ((outOfRange < 0 && !mFilmMode) ||
- (outOfRange > 0 && mFilmMode)) {
- stopExtraScalingIfNeeded();
-
- // Removing the touch down flag allows snapback to happen
- // for film mode change.
- mHolding &= ~HOLD_TOUCH_DOWN;
- if (mFilmMode) {
- UsageStatistics.setPendingTransitionCause(
- UsageStatistics.TRANSITION_PINCH_OUT);
- } else {
- UsageStatistics.setPendingTransitionCause(
- UsageStatistics.TRANSITION_PINCH_IN);
- }
- setFilmMode(!mFilmMode);
-
-
- // We need to call onScaleEnd() before setting mModeChanged
- // to true.
- onScaleEnd();
- mModeChanged = true;
- return true;
- }
- }
-
- if (outOfRange != 0) {
- startExtraScalingIfNeeded();
- } else {
- stopExtraScalingIfNeeded();
- }
- return true;
- }
-
- @Override
- public void onScaleEnd() {
- if (mIgnoreSwipingGesture) return;
- if (mIgnoreScalingGesture) return;
- if (mModeChanged) return;
- mPositionController.endScale();
- }
-
- private void startExtraScalingIfNeeded() {
- if (!mCancelExtraScalingPending) {
- mHandler.sendEmptyMessageDelayed(
- MSG_CANCEL_EXTRA_SCALING, 700);
- mPositionController.setExtraScalingRange(true);
- mCancelExtraScalingPending = true;
- }
- }
-
- private void stopExtraScalingIfNeeded() {
- if (mCancelExtraScalingPending) {
- mHandler.removeMessages(MSG_CANCEL_EXTRA_SCALING);
- mPositionController.setExtraScalingRange(false);
- mCancelExtraScalingPending = false;
- }
- }
-
- @Override
- public void onDown(float x, float y) {
- checkHideUndoBar(UNDO_BAR_TOUCHED);
-
- mDeltaY = 0;
- mModeChanged = false;
-
- if (mIgnoreSwipingGesture) return;
-
- mHolding |= HOLD_TOUCH_DOWN;
-
- if (mFilmMode && mPositionController.isScrolling()) {
- mDownInScrolling = true;
- mPositionController.stopScrolling();
- } else {
- mDownInScrolling = false;
- }
- mHadFling = false;
- mScrolledAfterDown = false;
- if (mFilmMode) {
- int xi = (int) (x + 0.5f);
- int yi = (int) (y + 0.5f);
- // We only care about being within the x bounds, necessary for
- // handling very wide images which are otherwise very hard to fling
- mTouchBoxIndex = mPositionController.hitTest(xi, getHeight() / 2);
-
- if (mTouchBoxIndex < mPrevBound || mTouchBoxIndex > mNextBound) {
- mTouchBoxIndex = Integer.MAX_VALUE;
- } else {
- mTouchBoxDeletable =
- mPictures.get(mTouchBoxIndex).isDeletable();
- }
- } else {
- mTouchBoxIndex = Integer.MAX_VALUE;
- }
- }
-
- @Override
- public void onUp() {
- if (mIgnoreSwipingGesture) return;
-
- mHolding &= ~HOLD_TOUCH_DOWN;
- mEdgeView.onRelease();
-
- // If we scrolled in Y direction far enough, treat it as a delete
- // gesture.
- if (mFilmMode && mScrolledAfterDown && !mFirstScrollX
- && mTouchBoxIndex != Integer.MAX_VALUE) {
- Rect r = mPositionController.getPosition(mTouchBoxIndex);
- int h = getHeight();
- if (Math.abs(r.centerY() - h * 0.5f) > 0.4f * h) {
- int duration = mPositionController
- .flingFilmY(mTouchBoxIndex, 0);
- if (duration >= 0) {
- mPositionController.setPopFromTop(r.centerY() < h * 0.5f);
- deleteAfterAnimation(duration);
- }
- }
- }
-
- if (mIgnoreUpEvent) {
- mIgnoreUpEvent = false;
- return;
- }
-
- if (!(mFilmMode && !mHadFling && mFirstScrollX
- && snapToNeighborImage())) {
- snapback();
- }
- }
-
- public void setSwipingEnabled(boolean enabled) {
- mIgnoreSwipingGesture = !enabled;
- }
- }
-
- public void setSwipingEnabled(boolean enabled) {
- mGestureListener.setSwipingEnabled(enabled);
- }
-
- private void updateActionBar() {
- boolean isCamera = mPictures.get(0).isCamera();
- if (isCamera && !mFilmMode) {
- // Move into camera in page mode, lock
- mListener.onActionBarAllowed(false);
- } else {
- mListener.onActionBarAllowed(true);
- if (mFilmMode) mListener.onActionBarWanted();
- }
- }
-
- public void setFilmMode(boolean enabled) {
- if (mFilmMode == enabled) return;
- mFilmMode = enabled;
- mPositionController.setFilmMode(mFilmMode);
- mModel.setNeedFullImage(!enabled);
- mModel.setFocusHintDirection(
- mFilmMode ? Model.FOCUS_HINT_PREVIOUS : Model.FOCUS_HINT_NEXT);
- updateActionBar();
- mListener.onFilmModeChanged(enabled);
- }
-
- public boolean getFilmMode() {
- return mFilmMode;
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Framework events
- ////////////////////////////////////////////////////////////////////////////
-
- public void pause() {
- mPositionController.skipAnimation();
- mTileView.freeTextures();
- for (int i = -SCREEN_NAIL_MAX; i <= SCREEN_NAIL_MAX; i++) {
- mPictures.get(i).setScreenNail(null);
- }
- hideUndoBar();
- }
-
- public void resume() {
- mTileView.prepareTextures();
- mPositionController.skipToFinalPosition();
- }
-
- // move to the camera preview and show controls after resume
- public void resetToFirstPicture() {
- mModel.moveTo(0);
- setFilmMode(false);
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Undo Bar
- ////////////////////////////////////////////////////////////////////////////
-
- private int mUndoBarState;
- private static final int UNDO_BAR_SHOW = 1;
- private static final int UNDO_BAR_TIMEOUT = 2;
- private static final int UNDO_BAR_TOUCHED = 4;
- private static final int UNDO_BAR_FULL_CAMERA = 8;
- private static final int UNDO_BAR_DELETE_LAST = 16;
-
- // "deleteLast" means if the deletion is on the last remaining picture in
- // the album.
- private void showUndoBar(boolean deleteLast) {
- mHandler.removeMessages(MSG_UNDO_BAR_TIMEOUT);
- mUndoBarState = UNDO_BAR_SHOW;
- if(deleteLast) mUndoBarState |= UNDO_BAR_DELETE_LAST;
- mUndoBar.animateVisibility(GLView.VISIBLE);
- mHandler.sendEmptyMessageDelayed(MSG_UNDO_BAR_TIMEOUT, 3000);
- if (mListener != null) mListener.onUndoBarVisibilityChanged(true);
- }
-
- private void hideUndoBar() {
- mHandler.removeMessages(MSG_UNDO_BAR_TIMEOUT);
- mListener.onCommitDeleteImage();
- mUndoBar.animateVisibility(GLView.INVISIBLE);
- mUndoBarState = 0;
- mUndoIndexHint = Integer.MAX_VALUE;
- mListener.onUndoBarVisibilityChanged(false);
- }
-
- // Check if the one of the conditions for hiding the undo bar has been
- // met. The conditions are:
- //
- // 1. It has been three seconds since last showing, and (a) the user has
- // touched, or (b) the deleted picture is the last remaining picture in the
- // album.
- //
- // 2. The camera is shown in full screen.
- private void checkHideUndoBar(int addition) {
- mUndoBarState |= addition;
- if ((mUndoBarState & UNDO_BAR_SHOW) == 0) return;
- boolean timeout = (mUndoBarState & UNDO_BAR_TIMEOUT) != 0;
- boolean touched = (mUndoBarState & UNDO_BAR_TOUCHED) != 0;
- boolean fullCamera = (mUndoBarState & UNDO_BAR_FULL_CAMERA) != 0;
- boolean deleteLast = (mUndoBarState & UNDO_BAR_DELETE_LAST) != 0;
- if ((timeout && deleteLast) || fullCamera || touched) {
- hideUndoBar();
- }
- }
-
- public boolean canUndo() {
- return (mUndoBarState & UNDO_BAR_SHOW) != 0;
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Rendering
- ////////////////////////////////////////////////////////////////////////////
-
- @Override
- protected void render(GLCanvas canvas) {
- if (mFirst) {
- // Make sure the fields are properly initialized before checking
- // whether isCamera()
- mPictures.get(0).reload();
- }
- // Check if the camera preview occupies the full screen.
- boolean full = !mFilmMode && mPictures.get(0).isCamera()
- && mPositionController.isCenter()
- && mPositionController.isAtMinimalScale();
- if (mFirst || full != mFullScreenCamera) {
- mFullScreenCamera = full;
- mFirst = false;
- mListener.onFullScreenChanged(full);
- if (full) mHandler.sendEmptyMessage(MSG_UNDO_BAR_FULL_CAMERA);
- }
-
- // Determine how many photos we need to draw in addition to the center
- // one.
- int neighbors;
- if (mFullScreenCamera) {
- neighbors = 0;
- } else {
- // In page mode, we draw only one previous/next photo. But if we are
- // doing capture animation, we want to draw all photos.
- boolean inPageMode = (mPositionController.getFilmRatio() == 0f);
- boolean inCaptureAnimation =
- ((mHolding & HOLD_CAPTURE_ANIMATION) != 0);
- if (inPageMode && !inCaptureAnimation) {
- neighbors = 1;
- } else {
- neighbors = SCREEN_NAIL_MAX;
- }
- }
-
- // Draw photos from back to front
- for (int i = neighbors; i >= -neighbors; i--) {
- Rect r = mPositionController.getPosition(i);
- mPictures.get(i).draw(canvas, r);
- }
-
- renderChild(canvas, mEdgeView);
- renderChild(canvas, mUndoBar);
-
- mPositionController.advanceAnimation();
- checkFocusSwitching();
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Film mode focus switching
- ////////////////////////////////////////////////////////////////////////////
-
- // Runs in GL thread.
- private void checkFocusSwitching() {
- if (!mFilmMode) return;
- if (mHandler.hasMessages(MSG_SWITCH_FOCUS)) return;
- if (switchPosition() != 0) {
- mHandler.sendEmptyMessage(MSG_SWITCH_FOCUS);
- }
- }
-
- // Runs in main thread.
- private void switchFocus() {
- if (mHolding != 0) return;
- switch (switchPosition()) {
- case -1:
- switchToPrevImage();
- break;
- case 1:
- switchToNextImage();
- break;
- }
- }
-
- // Returns -1 if we should switch focus to the previous picture, +1 if we
- // should switch to the next, 0 otherwise.
- private int switchPosition() {
- Rect curr = mPositionController.getPosition(0);
- int center = getWidth() / 2;
-
- if (curr.left > center && mPrevBound < 0) {
- Rect prev = mPositionController.getPosition(-1);
- int currDist = curr.left - center;
- int prevDist = center - prev.right;
- if (prevDist < currDist) {
- return -1;
- }
- } else if (curr.right < center && mNextBound > 0) {
- Rect next = mPositionController.getPosition(1);
- int currDist = center - curr.right;
- int nextDist = next.left - center;
- if (nextDist < currDist) {
- return 1;
- }
- }
-
- return 0;
- }
-
- // Switch to the previous or next picture if the hit position is inside
- // one of their boxes. This runs in main thread.
- private void switchToHitPicture(int x, int y) {
- if (mPrevBound < 0) {
- Rect r = mPositionController.getPosition(-1);
- if (r.right >= x) {
- slideToPrevPicture();
- return;
- }
- }
-
- if (mNextBound > 0) {
- Rect r = mPositionController.getPosition(1);
- if (r.left <= x) {
- slideToNextPicture();
- return;
- }
- }
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Page mode focus switching
- //
- // We slide image to the next one or the previous one in two cases: 1: If
- // the user did a fling gesture with enough velocity. 2 If the user has
- // moved the picture a lot.
- ////////////////////////////////////////////////////////////////////////////
-
- private boolean swipeImages(float velocityX, float velocityY) {
- if (mFilmMode) return false;
-
- // Avoid swiping images if we're possibly flinging to view the
- // zoomed in picture vertically.
- PositionController controller = mPositionController;
- boolean isMinimal = controller.isAtMinimalScale();
- int edges = controller.getImageAtEdges();
- if (!isMinimal && Math.abs(velocityY) > Math.abs(velocityX))
- if ((edges & PositionController.IMAGE_AT_TOP_EDGE) == 0
- || (edges & PositionController.IMAGE_AT_BOTTOM_EDGE) == 0)
- return false;
-
- // If we are at the edge of the current photo and the sweeping velocity
- // exceeds the threshold, slide to the next / previous image.
- if (velocityX < -SWIPE_THRESHOLD && (isMinimal
- || (edges & PositionController.IMAGE_AT_RIGHT_EDGE) != 0)) {
- return slideToNextPicture();
- } else if (velocityX > SWIPE_THRESHOLD && (isMinimal
- || (edges & PositionController.IMAGE_AT_LEFT_EDGE) != 0)) {
- return slideToPrevPicture();
- }
-
- return false;
- }
-
- private void snapback() {
- if ((mHolding & ~HOLD_DELETE) != 0) return;
- if (mFilmMode || !snapToNeighborImage()) {
- mPositionController.snapback();
- }
- }
-
- private boolean snapToNeighborImage() {
- Rect r = mPositionController.getPosition(0);
- int viewW = getWidth();
- // Setting the move threshold proportional to the width of the view
- int moveThreshold = viewW / 5 ;
- int threshold = moveThreshold + gapToSide(r.width(), viewW);
-
- // If we have moved the picture a lot, switching.
- if (viewW - r.right > threshold) {
- return slideToNextPicture();
- } else if (r.left > threshold) {
- return slideToPrevPicture();
- }
-
- return false;
- }
-
- private boolean slideToNextPicture() {
- if (mNextBound <= 0) return false;
- switchToNextImage();
- mPositionController.startHorizontalSlide();
- return true;
- }
-
- private boolean slideToPrevPicture() {
- if (mPrevBound >= 0) return false;
- switchToPrevImage();
- mPositionController.startHorizontalSlide();
- return true;
- }
-
- private static int gapToSide(int imageWidth, int viewWidth) {
- return Math.max(0, (viewWidth - imageWidth) / 2);
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Focus switching
- ////////////////////////////////////////////////////////////////////////////
-
- public void switchToImage(int index) {
- mModel.moveTo(index);
- }
-
- private void switchToNextImage() {
- mModel.moveTo(mModel.getCurrentIndex() + 1);
- }
-
- private void switchToPrevImage() {
- mModel.moveTo(mModel.getCurrentIndex() - 1);
- }
-
- private void switchToFirstImage() {
- mModel.moveTo(0);
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Opening Animation
- ////////////////////////////////////////////////////////////////////////////
-
- public void setOpenAnimationRect(Rect rect) {
- mPositionController.setOpenAnimationRect(rect);
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Capture Animation
- ////////////////////////////////////////////////////////////////////////////
-
- public boolean switchWithCaptureAnimation(int offset) {
- GLRoot root = getGLRoot();
- if(root == null) return false;
- root.lockRenderThread();
- try {
- return switchWithCaptureAnimationLocked(offset);
- } finally {
- root.unlockRenderThread();
- }
- }
-
- private boolean switchWithCaptureAnimationLocked(int offset) {
- if (mHolding != 0) return true;
- if (offset == 1) {
- if (mNextBound <= 0) return false;
- // Temporary disable action bar until the capture animation is done.
- if (!mFilmMode) mListener.onActionBarAllowed(false);
- switchToNextImage();
- mPositionController.startCaptureAnimationSlide(-1);
- } else if (offset == -1) {
- if (mPrevBound >= 0) return false;
- if (mFilmMode) setFilmMode(false);
-
- // If we are too far away from the first image (so that we don't
- // have all the ScreenNails in-between), we go directly without
- // animation.
- if (mModel.getCurrentIndex() > SCREEN_NAIL_MAX) {
- switchToFirstImage();
- mPositionController.skipToFinalPosition();
- return true;
- }
-
- switchToFirstImage();
- mPositionController.startCaptureAnimationSlide(1);
- } else {
- return false;
- }
- mHolding |= HOLD_CAPTURE_ANIMATION;
- Message m = mHandler.obtainMessage(MSG_CAPTURE_ANIMATION_DONE, offset, 0);
- mHandler.sendMessageDelayed(m, PositionController.CAPTURE_ANIMATION_TIME);
- return true;
- }
-
- private void captureAnimationDone(int offset) {
- mHolding &= ~HOLD_CAPTURE_ANIMATION;
- if (offset == 1 && !mFilmMode) {
- // Now the capture animation is done, enable the action bar.
- mListener.onActionBarAllowed(true);
- mListener.onActionBarWanted();
- }
- snapback();
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Card deck effect calculation
- ////////////////////////////////////////////////////////////////////////////
-
- // Returns the scrolling progress value for an object moving out of a
- // view. The progress value measures how much the object has moving out of
- // the view. The object currently displays in [left, right), and the view is
- // at [0, viewWidth].
- //
- // The returned value is negative when the object is moving right, and
- // positive when the object is moving left. The value goes to -1 or 1 when
- // the object just moves out of the view completely. The value is 0 if the
- // object currently fills the view.
- private static float calculateMoveOutProgress(int left, int right,
- int viewWidth) {
- // w = object width
- // viewWidth = view width
- int w = right - left;
-
- // If the object width is smaller than the view width,
- // |....view....|
- // |<-->| progress = -1 when left = viewWidth
- // |<-->| progress = 0 when left = viewWidth / 2 - w / 2
- // |<-->| progress = 1 when left = -w
- if (w < viewWidth) {
- int zx = viewWidth / 2 - w / 2;
- if (left > zx) {
- return -(left - zx) / (float) (viewWidth - zx); // progress = (0, -1]
- } else {
- return (left - zx) / (float) (-w - zx); // progress = [0, 1]
- }
- }
-
- // If the object width is larger than the view width,
- // |..view..|
- // |<--------->| progress = -1 when left = viewWidth
- // |<--------->| progress = 0 between left = 0
- // |<--------->| and right = viewWidth
- // |<--------->| progress = 1 when right = 0
- if (left > 0) {
- return -left / (float) viewWidth;
- }
-
- if (right < viewWidth) {
- return (viewWidth - right) / (float) viewWidth;
- }
-
- return 0;
- }
-
- // Maps a scrolling progress value to the alpha factor in the fading
- // animation.
- private float getScrollAlpha(float scrollProgress) {
- return scrollProgress < 0 ? mAlphaInterpolator.getInterpolation(
- 1 - Math.abs(scrollProgress)) : 1.0f;
- }
-
- // Maps a scrolling progress value to the scaling factor in the fading
- // animation.
- private float getScrollScale(float scrollProgress) {
- float interpolatedProgress = mScaleInterpolator.getInterpolation(
- Math.abs(scrollProgress));
- float scale = (1 - interpolatedProgress) +
- interpolatedProgress * TRANSITION_SCALE_FACTOR;
- return scale;
- }
-
-
- // This interpolator emulates the rate at which the perceived scale of an
- // object changes as its distance from a camera increases. When this
- // interpolator is applied to a scale animation on a view, it evokes the
- // sense that the object is shrinking due to moving away from the camera.
- private static class ZInterpolator {
- private float focalLength;
-
- public ZInterpolator(float foc) {
- focalLength = foc;
- }
-
- public float getInterpolation(float input) {
- return (1.0f - focalLength / (focalLength + input)) /
- (1.0f - focalLength / (focalLength + 1.0f));
- }
- }
-
- // Returns an interpolated value for the page/film transition.
- // When ratio = 0, the result is from.
- // When ratio = 1, the result is to.
- private static float interpolate(float ratio, float from, float to) {
- return from + (to - from) * ratio * ratio;
- }
-
- // Returns the alpha factor in film mode if a picture is not in the center.
- // The 0.03 lower bound is to make the item always visible a bit.
- private float getOffsetAlpha(float offset) {
- offset /= 0.5f;
- float alpha = (offset > 0) ? (1 - offset) : (1 + offset);
- return Utils.clamp(alpha, 0.03f, 1f);
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Simple public utilities
- ////////////////////////////////////////////////////////////////////////////
-
- public void setListener(Listener listener) {
- mListener = listener;
- }
-
- public Rect getPhotoRect(int index) {
- return mPositionController.getPosition(index);
- }
-
- public PhotoFallbackEffect buildFallbackEffect(GLView root, GLCanvas canvas) {
- Rect location = new Rect();
- Utils.assertTrue(root.getBoundsOf(this, location));
-
- Rect fullRect = bounds();
- PhotoFallbackEffect effect = new PhotoFallbackEffect();
- for (int i = -SCREEN_NAIL_MAX; i <= SCREEN_NAIL_MAX; ++i) {
- MediaItem item = mModel.getMediaItem(i);
- if (item == null) continue;
- ScreenNail sc = mModel.getScreenNail(i);
- if (!(sc instanceof TiledScreenNail)
- || ((TiledScreenNail) sc).isShowingPlaceholder()) continue;
-
- // Now, sc is BitmapScreenNail and is not showing placeholder
- Rect rect = new Rect(getPhotoRect(i));
- if (!Rect.intersects(fullRect, rect)) continue;
- rect.offset(location.left, location.top);
-
- int width = sc.getWidth();
- int height = sc.getHeight();
-
- int rotation = mModel.getImageRotation(i);
- RawTexture texture;
- if ((rotation % 180) == 0) {
- texture = new RawTexture(width, height, true);
- canvas.beginRenderTarget(texture);
- canvas.translate(width / 2f, height / 2f);
- } else {
- texture = new RawTexture(height, width, true);
- canvas.beginRenderTarget(texture);
- canvas.translate(height / 2f, width / 2f);
- }
-
- canvas.rotate(rotation, 0, 0, 1);
- canvas.translate(-width / 2f, -height / 2f);
- sc.draw(canvas, 0, 0, width, height);
- canvas.endRenderTarget();
- effect.addEntry(item.getPath(), rect, texture);
- }
- return effect;
- }
-}
diff --git a/src/com/android/gallery3d/ui/PopupList.java b/src/com/android/gallery3d/ui/PopupList.java
deleted file mode 100644
index 248f50b25..000000000
--- a/src/com/android/gallery3d/ui/PopupList.java
+++ /dev/null
@@ -1,206 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.graphics.Rect;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.View.MeasureSpec;
-import android.view.ViewGroup;
-import android.view.ViewTreeObserver;
-import android.view.ViewTreeObserver.OnGlobalLayoutListener;
-import android.widget.AdapterView;
-import android.widget.AdapterView.OnItemClickListener;
-import android.widget.BaseAdapter;
-import android.widget.ListView;
-import android.widget.PopupWindow;
-import android.widget.TextView;
-
-import com.android.gallery3d.R;
-
-import java.util.ArrayList;
-
-public class PopupList {
-
- public static interface OnPopupItemClickListener {
- public boolean onPopupItemClick(int itemId);
- }
-
- public static class Item {
- public final int id;
- public String title;
-
- public Item(int id, String title) {
- this.id = id;
- this.title = title;
- }
-
- public void setTitle(String title) {
- this.title = title;
- }
- }
-
- private final Context mContext;
- private final View mAnchorView;
- private final ArrayList<Item> mItems = new ArrayList<Item>();
- private PopupWindow mPopupWindow;
- private ListView mContentList;
- private OnPopupItemClickListener mOnPopupItemClickListener;
- private int mPopupOffsetX;
- private int mPopupOffsetY;
- private int mPopupWidth;
- private int mPopupHeight;
-
- public PopupList(Context context, View anchorView) {
- mContext = context;
- mAnchorView = anchorView;
- }
-
- public void setOnPopupItemClickListener(OnPopupItemClickListener listener) {
- mOnPopupItemClickListener = listener;
- }
-
- public void addItem(int id, String title) {
- mItems.add(new Item(id, title));
- }
-
- public void clearItems() {
- mItems.clear();
- }
-
- private final PopupWindow.OnDismissListener mOnDismissListener =
- new PopupWindow.OnDismissListener() {
- @SuppressWarnings("deprecation")
- @Override
- public void onDismiss() {
- if (mPopupWindow == null) return;
- mPopupWindow = null;
- ViewTreeObserver observer = mAnchorView.getViewTreeObserver();
- if (observer.isAlive()) {
- // We used the deprecated function for backward compatibility
- // The new "removeOnGlobalLayoutListener" is introduced in API level 16
- observer.removeGlobalOnLayoutListener(mOnGLobalLayoutListener);
- }
- }
- };
-
- private final OnItemClickListener mOnItemClickListener =
- new OnItemClickListener() {
- @Override
- public void onItemClick(AdapterView<?> parent, View view, int position, long id) {
- if (mPopupWindow == null) return;
- mPopupWindow.dismiss();
- if (mOnPopupItemClickListener != null) {
- mOnPopupItemClickListener.onPopupItemClick((int) id);
- }
- }
- };
-
- private final OnGlobalLayoutListener mOnGLobalLayoutListener =
- new OnGlobalLayoutListener() {
- @Override
- public void onGlobalLayout() {
- if (mPopupWindow == null) return;
- updatePopupLayoutParams();
- // Need to update the position of the popup window
- mPopupWindow.update(mAnchorView,
- mPopupOffsetX, mPopupOffsetY, mPopupWidth, mPopupHeight);
- }
- };
-
- public void show() {
- if (mPopupWindow != null) return;
- mAnchorView.getViewTreeObserver()
- .addOnGlobalLayoutListener(mOnGLobalLayoutListener);
- mPopupWindow = createPopupWindow();
- updatePopupLayoutParams();
- mPopupWindow.setWidth(mPopupWidth);
- mPopupWindow.setHeight(mPopupHeight);
- mPopupWindow.showAsDropDown(mAnchorView, mPopupOffsetX, mPopupOffsetY);
- }
-
- private void updatePopupLayoutParams() {
- ListView content = mContentList;
- PopupWindow popup = mPopupWindow;
-
- Rect p = new Rect();
- popup.getBackground().getPadding(p);
-
- int maxHeight = mPopupWindow.getMaxAvailableHeight(mAnchorView) - p.top - p.bottom;
- mContentList.measure(
- MeasureSpec.makeMeasureSpec(0, MeasureSpec.UNSPECIFIED),
- MeasureSpec.makeMeasureSpec(maxHeight, MeasureSpec.AT_MOST));
- mPopupWidth = content.getMeasuredWidth() + p.top + p.bottom;
- mPopupHeight = Math.min(maxHeight, content.getMeasuredHeight() + p.left + p.right);
- mPopupOffsetX = -p.left;
- mPopupOffsetY = -p.top;
- }
-
- private PopupWindow createPopupWindow() {
- PopupWindow popup = new PopupWindow(mContext);
- popup.setOnDismissListener(mOnDismissListener);
-
- popup.setBackgroundDrawable(mContext.getResources().getDrawable(
- R.drawable.menu_dropdown_panel_holo_dark));
-
- mContentList = new ListView(mContext, null,
- android.R.attr.dropDownListViewStyle);
- mContentList.setAdapter(new ItemDataAdapter());
- mContentList.setOnItemClickListener(mOnItemClickListener);
- popup.setContentView(mContentList);
- popup.setFocusable(true);
- popup.setOutsideTouchable(true);
-
- return popup;
- }
-
- public Item findItem(int id) {
- for (Item item : mItems) {
- if (item.id == id) return item;
- }
- return null;
- }
-
- private class ItemDataAdapter extends BaseAdapter {
- @Override
- public int getCount() {
- return mItems.size();
- }
-
- @Override
- public Object getItem(int position) {
- return mItems.get(position);
- }
-
- @Override
- public long getItemId(int position) {
- return mItems.get(position).id;
- }
-
- @Override
- public View getView(int position, View convertView, ViewGroup parent) {
- if (convertView == null) {
- convertView = LayoutInflater.from(mContext)
- .inflate(R.layout.popup_list_item, null);
- }
- TextView text = (TextView) convertView.findViewById(android.R.id.text1);
- text.setText(mItems.get(position).title);
- return convertView;
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/PositionController.java b/src/com/android/gallery3d/ui/PositionController.java
deleted file mode 100644
index 6a4bcea87..000000000
--- a/src/com/android/gallery3d/ui/PositionController.java
+++ /dev/null
@@ -1,1821 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.graphics.Rect;
-import android.util.Log;
-import android.widget.Scroller;
-
-import com.android.gallery3d.app.PhotoPage;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.ui.PhotoView.Size;
-import com.android.gallery3d.util.GalleryUtils;
-import com.android.gallery3d.util.RangeArray;
-import com.android.gallery3d.util.RangeIntArray;
-
-class PositionController {
- private static final String TAG = "PositionController";
-
- public static final int IMAGE_AT_LEFT_EDGE = 1;
- public static final int IMAGE_AT_RIGHT_EDGE = 2;
- public static final int IMAGE_AT_TOP_EDGE = 4;
- public static final int IMAGE_AT_BOTTOM_EDGE = 8;
-
- public static final int CAPTURE_ANIMATION_TIME = 700;
- public static final int SNAPBACK_ANIMATION_TIME = 600;
-
- // Special values for animation time.
- private static final long NO_ANIMATION = -1;
- private static final long LAST_ANIMATION = -2;
-
- private static final int ANIM_KIND_NONE = -1;
- private static final int ANIM_KIND_SCROLL = 0;
- private static final int ANIM_KIND_SCALE = 1;
- private static final int ANIM_KIND_SNAPBACK = 2;
- private static final int ANIM_KIND_SLIDE = 3;
- private static final int ANIM_KIND_ZOOM = 4;
- private static final int ANIM_KIND_OPENING = 5;
- private static final int ANIM_KIND_FLING = 6;
- private static final int ANIM_KIND_FLING_X = 7;
- private static final int ANIM_KIND_DELETE = 8;
- private static final int ANIM_KIND_CAPTURE = 9;
-
- // Animation time in milliseconds. The order must match ANIM_KIND_* above.
- //
- // The values for ANIM_KIND_FLING_X does't matter because we use
- // mFilmScroller.isFinished() to decide when to stop. We set it to 0 so it's
- // faster for Animatable.advanceAnimation() to calculate the progress
- // (always 1).
- private static final int ANIM_TIME[] = {
- 0, // ANIM_KIND_SCROLL
- 0, // ANIM_KIND_SCALE
- SNAPBACK_ANIMATION_TIME, // ANIM_KIND_SNAPBACK
- 400, // ANIM_KIND_SLIDE
- 300, // ANIM_KIND_ZOOM
- 300, // ANIM_KIND_OPENING
- 0, // ANIM_KIND_FLING (the duration is calculated dynamically)
- 0, // ANIM_KIND_FLING_X (see the comment above)
- 0, // ANIM_KIND_DELETE (the duration is calculated dynamically)
- CAPTURE_ANIMATION_TIME, // ANIM_KIND_CAPTURE
- };
-
- // We try to scale up the image to fill the screen. But in order not to
- // scale too much for small icons, we limit the max up-scaling factor here.
- private static final float SCALE_LIMIT = 4;
-
- // For user's gestures, we give a temporary extra scaling range which goes
- // above or below the usual scaling limits.
- private static final float SCALE_MIN_EXTRA = 0.7f;
- private static final float SCALE_MAX_EXTRA = 1.4f;
-
- // Setting this true makes the extra scaling range permanent (until this is
- // set to false again).
- private boolean mExtraScalingRange = false;
-
- // Film Mode v.s. Page Mode: in film mode we show smaller pictures.
- private boolean mFilmMode = false;
-
- // These are the limits for width / height of the picture in film mode.
- private static final float FILM_MODE_PORTRAIT_HEIGHT = 0.48f;
- private static final float FILM_MODE_PORTRAIT_WIDTH = 0.7f;
- private static final float FILM_MODE_LANDSCAPE_HEIGHT = 0.7f;
- private static final float FILM_MODE_LANDSCAPE_WIDTH = 0.7f;
-
- // In addition to the focused box (index == 0). We also keep information
- // about this many boxes on each side.
- private static final int BOX_MAX = PhotoView.SCREEN_NAIL_MAX;
- private static final int[] CENTER_OUT_INDEX = new int[2 * BOX_MAX + 1];
-
- private static final int IMAGE_GAP = GalleryUtils.dpToPixel(16);
- private static final int HORIZONTAL_SLACK = GalleryUtils.dpToPixel(12);
-
- // These are constants for the delete gesture.
- private static final int DEFAULT_DELETE_ANIMATION_DURATION = 200; // ms
- private static final int MAX_DELETE_ANIMATION_DURATION = 400; // ms
-
- private Listener mListener;
- private volatile Rect mOpenAnimationRect;
-
- // Use a large enough value, so we won't see the gray shadow in the beginning.
- private int mViewW = 1200;
- private int mViewH = 1200;
-
- // A scaling gesture is in progress.
- private boolean mInScale;
- // The focus point of the scaling gesture, relative to the center of the
- // picture in bitmap pixels.
- private float mFocusX, mFocusY;
-
- // whether there is a previous/next picture.
- private boolean mHasPrev, mHasNext;
-
- // This is used by the fling animation (page mode).
- private FlingScroller mPageScroller;
-
- // This is used by the fling animation (film mode).
- private Scroller mFilmScroller;
-
- // The bound of the stable region that the focused box can stay, see the
- // comments above calculateStableBound() for details.
- private int mBoundLeft, mBoundRight, mBoundTop, mBoundBottom;
-
- // Constrained frame is a rectangle that the focused box should fit into if
- // it is constrained. It has two effects:
- //
- // (1) In page mode, if the focused box is constrained, scaling for the
- // focused box is adjusted to fit into the constrained frame, instead of the
- // whole view.
- //
- // (2) In page mode, if the focused box is constrained, the mPlatform's
- // default center (mDefaultX/Y) is moved to the center of the constrained
- // frame, instead of the view center.
- //
- private Rect mConstrainedFrame = new Rect();
-
- // Whether the focused box is constrained.
- //
- // Our current program's first call to moveBox() sets constrained = true, so
- // we set the initial value of this variable to true, and we will not see
- // see unwanted transition animation.
- private boolean mConstrained = true;
-
- //
- // ___________________________________________________________
- // | _____ _____ _____ _____ _____ |
- // | | | | | | | | | | | |
- // | | Box | | Box | | Box*| | Box | | Box | |
- // | |_____|.....|_____|.....|_____|.....|_____|.....|_____| |
- // | Gap Gap Gap Gap |
- // |___________________________________________________________|
- //
- // <-- Platform -->
- //
- // The focused box (Box*) centers at mPlatform's (mCurrentX, mCurrentY)
-
- private Platform mPlatform = new Platform();
- private RangeArray<Box> mBoxes = new RangeArray<Box>(-BOX_MAX, BOX_MAX);
- // The gap at the right of a Box i is at index i. The gap at the left of a
- // Box i is at index i - 1.
- private RangeArray<Gap> mGaps = new RangeArray<Gap>(-BOX_MAX, BOX_MAX - 1);
- private FilmRatio mFilmRatio = new FilmRatio();
-
- // These are only used during moveBox().
- private RangeArray<Box> mTempBoxes = new RangeArray<Box>(-BOX_MAX, BOX_MAX);
- private RangeArray<Gap> mTempGaps =
- new RangeArray<Gap>(-BOX_MAX, BOX_MAX - 1);
-
- // The output of the PositionController. Available through getPosition().
- private RangeArray<Rect> mRects = new RangeArray<Rect>(-BOX_MAX, BOX_MAX);
-
- // The direction of a new picture should appear. New pictures pop from top
- // if this value is true, or from bottom if this value is false.
- boolean mPopFromTop;
-
- public interface Listener {
- void invalidate();
- boolean isHoldingDown();
- boolean isHoldingDelete();
-
- // EdgeView
- void onPull(int offset, int direction);
- void onRelease();
- void onAbsorb(int velocity, int direction);
- }
-
- static {
- // Initialize the CENTER_OUT_INDEX array.
- // The array maps 0, 1, 2, 3, 4, ..., 2 * BOX_MAX
- // to 0, 1, -1, 2, -2, ..., BOX_MAX, -BOX_MAX
- for (int i = 0; i < CENTER_OUT_INDEX.length; i++) {
- int j = (i + 1) / 2;
- if ((i & 1) == 0) j = -j;
- CENTER_OUT_INDEX[i] = j;
- }
- }
-
- public PositionController(Context context, Listener listener) {
- mListener = listener;
- mPageScroller = new FlingScroller();
- mFilmScroller = new Scroller(context, null, false);
-
- // Initialize the areas.
- initPlatform();
- for (int i = -BOX_MAX; i <= BOX_MAX; i++) {
- mBoxes.put(i, new Box());
- initBox(i);
- mRects.put(i, new Rect());
- }
- for (int i = -BOX_MAX; i < BOX_MAX; i++) {
- mGaps.put(i, new Gap());
- initGap(i);
- }
- }
-
- public void setOpenAnimationRect(Rect r) {
- mOpenAnimationRect = r;
- }
-
- public void setViewSize(int viewW, int viewH) {
- if (viewW == mViewW && viewH == mViewH) return;
-
- boolean wasMinimal = isAtMinimalScale();
-
- mViewW = viewW;
- mViewH = viewH;
- initPlatform();
-
- for (int i = -BOX_MAX; i <= BOX_MAX; i++) {
- setBoxSize(i, viewW, viewH, true);
- }
-
- updateScaleAndGapLimit();
-
- // If the focused box was at minimal scale, we try to make it the
- // minimal scale under the new view size.
- if (wasMinimal) {
- Box b = mBoxes.get(0);
- b.mCurrentScale = b.mScaleMin;
- }
-
- // If we have the opening animation, do it. Otherwise go directly to the
- // right position.
- if (!startOpeningAnimationIfNeeded()) {
- skipToFinalPosition();
- }
- }
-
- public void setConstrainedFrame(Rect cFrame) {
- if (mConstrainedFrame.equals(cFrame)) return;
- mConstrainedFrame.set(cFrame);
- mPlatform.updateDefaultXY();
- updateScaleAndGapLimit();
- snapAndRedraw();
- }
-
- public void forceImageSize(int index, Size s) {
- if (s.width == 0 || s.height == 0) return;
- Box b = mBoxes.get(index);
- b.mImageW = s.width;
- b.mImageH = s.height;
- return;
- }
-
- public void setImageSize(int index, Size s, Rect cFrame) {
- if (s.width == 0 || s.height == 0) return;
-
- boolean needUpdate = false;
- if (cFrame != null && !mConstrainedFrame.equals(cFrame)) {
- mConstrainedFrame.set(cFrame);
- mPlatform.updateDefaultXY();
- needUpdate = true;
- }
- needUpdate |= setBoxSize(index, s.width, s.height, false);
-
- if (!needUpdate) return;
- updateScaleAndGapLimit();
- snapAndRedraw();
- }
-
- // Returns false if the box size doesn't change.
- private boolean setBoxSize(int i, int width, int height, boolean isViewSize) {
- Box b = mBoxes.get(i);
- boolean wasViewSize = b.mUseViewSize;
-
- // If we already have an image size, we don't want to use the view size.
- if (!wasViewSize && isViewSize) return false;
-
- b.mUseViewSize = isViewSize;
-
- if (width == b.mImageW && height == b.mImageH) {
- return false;
- }
-
- // The ratio of the old size and the new size.
- //
- // If the aspect ratio changes, we don't know if it is because one side
- // grows or the other side shrinks. Currently we just assume the view
- // angle of the longer side doesn't change (so the aspect ratio change
- // is because the view angle of the shorter side changes). This matches
- // what camera preview does.
- float ratio = (width > height)
- ? (float) b.mImageW / width
- : (float) b.mImageH / height;
-
- b.mImageW = width;
- b.mImageH = height;
-
- // If this is the first time we receive an image size or we are in fullscreen,
- // we change the scale directly. Otherwise adjust the scales by a ratio,
- // and snapback will animate the scale into the min/max bounds if necessary.
- if ((wasViewSize && !isViewSize) || !mFilmMode) {
- b.mCurrentScale = getMinimalScale(b);
- b.mAnimationStartTime = NO_ANIMATION;
- } else {
- b.mCurrentScale *= ratio;
- b.mFromScale *= ratio;
- b.mToScale *= ratio;
- }
-
- if (i == 0) {
- mFocusX /= ratio;
- mFocusY /= ratio;
- }
-
- return true;
- }
-
- private boolean startOpeningAnimationIfNeeded() {
- if (mOpenAnimationRect == null) return false;
- Box b = mBoxes.get(0);
- if (b.mUseViewSize) return false;
-
- // Start animation from the saved rectangle if we have one.
- Rect r = mOpenAnimationRect;
- mOpenAnimationRect = null;
-
- mPlatform.mCurrentX = r.centerX() - mViewW / 2;
- b.mCurrentY = r.centerY() - mViewH / 2;
- b.mCurrentScale = Math.max(r.width() / (float) b.mImageW,
- r.height() / (float) b.mImageH);
- startAnimation(mPlatform.mDefaultX, 0, b.mScaleMin,
- ANIM_KIND_OPENING);
-
- // Animate from large gaps for neighbor boxes to avoid them
- // shown on the screen during opening animation.
- for (int i = -1; i < 1; i++) {
- Gap g = mGaps.get(i);
- g.mCurrentGap = mViewW;
- g.doAnimation(g.mDefaultSize, ANIM_KIND_OPENING);
- }
-
- return true;
- }
-
- public void setFilmMode(boolean enabled) {
- if (enabled == mFilmMode) return;
- mFilmMode = enabled;
-
- mPlatform.updateDefaultXY();
- updateScaleAndGapLimit();
- stopAnimation();
- snapAndRedraw();
- }
-
- public void setExtraScalingRange(boolean enabled) {
- if (mExtraScalingRange == enabled) return;
- mExtraScalingRange = enabled;
- if (!enabled) {
- snapAndRedraw();
- }
- }
-
- // This should be called whenever the scale range of boxes or the default
- // gap size may change. Currently this can happen due to change of view
- // size, image size, mFilmMode, mConstrained, and mConstrainedFrame.
- private void updateScaleAndGapLimit() {
- for (int i = -BOX_MAX; i <= BOX_MAX; i++) {
- Box b = mBoxes.get(i);
- b.mScaleMin = getMinimalScale(b);
- b.mScaleMax = getMaximalScale(b);
- }
-
- for (int i = -BOX_MAX; i < BOX_MAX; i++) {
- Gap g = mGaps.get(i);
- g.mDefaultSize = getDefaultGapSize(i);
- }
- }
-
- // Returns the default gap size according the the size of the boxes around
- // the gap and the current mode.
- private int getDefaultGapSize(int i) {
- if (mFilmMode) return IMAGE_GAP;
- Box a = mBoxes.get(i);
- Box b = mBoxes.get(i + 1);
- return IMAGE_GAP + Math.max(gapToSide(a), gapToSide(b));
- }
-
- // Here is how we layout the boxes in the page mode.
- //
- // previous current next
- // ___________ ________________ __________
- // | _______ | | __________ | | ______ |
- // | | | | | | right->| | | | | |
- // | | |<-------->|<--left | | | | | |
- // | |_______| | | | |__________| | | |______| |
- // |___________| | |________________| |__________|
- // | <--> gapToSide()
- // |
- // IMAGE_GAP + MAX(gapToSide(previous), gapToSide(current))
- private int gapToSide(Box b) {
- return (int) ((mViewW - getMinimalScale(b) * b.mImageW) / 2 + 0.5f);
- }
-
- // Stop all animations at where they are now.
- public void stopAnimation() {
- mPlatform.mAnimationStartTime = NO_ANIMATION;
- for (int i = -BOX_MAX; i <= BOX_MAX; i++) {
- mBoxes.get(i).mAnimationStartTime = NO_ANIMATION;
- }
- for (int i = -BOX_MAX; i < BOX_MAX; i++) {
- mGaps.get(i).mAnimationStartTime = NO_ANIMATION;
- }
- }
-
- public void skipAnimation() {
- if (mPlatform.mAnimationStartTime != NO_ANIMATION) {
- mPlatform.mCurrentX = mPlatform.mToX;
- mPlatform.mCurrentY = mPlatform.mToY;
- mPlatform.mAnimationStartTime = NO_ANIMATION;
- }
- for (int i = -BOX_MAX; i <= BOX_MAX; i++) {
- Box b = mBoxes.get(i);
- if (b.mAnimationStartTime == NO_ANIMATION) continue;
- b.mCurrentY = b.mToY;
- b.mCurrentScale = b.mToScale;
- b.mAnimationStartTime = NO_ANIMATION;
- }
- for (int i = -BOX_MAX; i < BOX_MAX; i++) {
- Gap g = mGaps.get(i);
- if (g.mAnimationStartTime == NO_ANIMATION) continue;
- g.mCurrentGap = g.mToGap;
- g.mAnimationStartTime = NO_ANIMATION;
- }
- redraw();
- }
-
- public void snapback() {
- snapAndRedraw();
- }
-
- public void skipToFinalPosition() {
- stopAnimation();
- snapAndRedraw();
- skipAnimation();
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Start an animations for the focused box
- ////////////////////////////////////////////////////////////////////////////
-
- public void zoomIn(float tapX, float tapY, float targetScale) {
- tapX -= mViewW / 2;
- tapY -= mViewH / 2;
- Box b = mBoxes.get(0);
-
- // Convert the tap position to distance to center in bitmap coordinates
- float tempX = (tapX - mPlatform.mCurrentX) / b.mCurrentScale;
- float tempY = (tapY - b.mCurrentY) / b.mCurrentScale;
-
- int x = (int) (-tempX * targetScale + 0.5f);
- int y = (int) (-tempY * targetScale + 0.5f);
-
- calculateStableBound(targetScale);
- int targetX = Utils.clamp(x, mBoundLeft, mBoundRight);
- int targetY = Utils.clamp(y, mBoundTop, mBoundBottom);
- targetScale = Utils.clamp(targetScale, b.mScaleMin, b.mScaleMax);
-
- startAnimation(targetX, targetY, targetScale, ANIM_KIND_ZOOM);
- }
-
- public void resetToFullView() {
- Box b = mBoxes.get(0);
- startAnimation(mPlatform.mDefaultX, 0, b.mScaleMin, ANIM_KIND_ZOOM);
- }
-
- public void beginScale(float focusX, float focusY) {
- focusX -= mViewW / 2;
- focusY -= mViewH / 2;
- Box b = mBoxes.get(0);
- Platform p = mPlatform;
- mInScale = true;
- mFocusX = (int) ((focusX - p.mCurrentX) / b.mCurrentScale + 0.5f);
- mFocusY = (int) ((focusY - b.mCurrentY) / b.mCurrentScale + 0.5f);
- }
-
- // Scales the image by the given factor.
- // Returns an out-of-range indicator:
- // 1 if the intended scale is too large for the stable range.
- // 0 if the intended scale is in the stable range.
- // -1 if the intended scale is too small for the stable range.
- public int scaleBy(float s, float focusX, float focusY) {
- focusX -= mViewW / 2;
- focusY -= mViewH / 2;
- Box b = mBoxes.get(0);
- Platform p = mPlatform;
-
- // We want to keep the focus point (on the bitmap) the same as when we
- // begin the scale gesture, that is,
- //
- // (focusX' - currentX') / scale' = (focusX - currentX) / scale
- //
- s = b.clampScale(s * getTargetScale(b));
- int x = mFilmMode ? p.mCurrentX : (int) (focusX - s * mFocusX + 0.5f);
- int y = mFilmMode ? b.mCurrentY : (int) (focusY - s * mFocusY + 0.5f);
- startAnimation(x, y, s, ANIM_KIND_SCALE);
- if (s < b.mScaleMin) return -1;
- if (s > b.mScaleMax) return 1;
- return 0;
- }
-
- public void endScale() {
- mInScale = false;
- snapAndRedraw();
- }
-
- // Slide the focused box to the center of the view.
- public void startHorizontalSlide() {
- Box b = mBoxes.get(0);
- startAnimation(mPlatform.mDefaultX, 0, b.mScaleMin, ANIM_KIND_SLIDE);
- }
-
- // Slide the focused box to the center of the view with the capture
- // animation. In addition to the sliding, the animation will also scale the
- // the focused box, the specified neighbor box, and the gap between the
- // two. The specified offset should be 1 or -1.
- public void startCaptureAnimationSlide(int offset) {
- Box b = mBoxes.get(0);
- Box n = mBoxes.get(offset); // the neighbor box
- Gap g = mGaps.get(offset); // the gap between the two boxes
-
- mPlatform.doAnimation(mPlatform.mDefaultX, mPlatform.mDefaultY,
- ANIM_KIND_CAPTURE);
- b.doAnimation(0, b.mScaleMin, ANIM_KIND_CAPTURE);
- n.doAnimation(0, n.mScaleMin, ANIM_KIND_CAPTURE);
- g.doAnimation(g.mDefaultSize, ANIM_KIND_CAPTURE);
- redraw();
- }
-
- // Only allow scrolling when we are not currently in an animation or we
- // are in some animation with can be interrupted.
- private boolean canScroll() {
- Box b = mBoxes.get(0);
- if (b.mAnimationStartTime == NO_ANIMATION) return true;
- switch (b.mAnimationKind) {
- case ANIM_KIND_SCROLL:
- case ANIM_KIND_FLING:
- case ANIM_KIND_FLING_X:
- return true;
- }
- return false;
- }
-
- public void scrollPage(int dx, int dy) {
- if (!canScroll()) return;
-
- Box b = mBoxes.get(0);
- Platform p = mPlatform;
-
- calculateStableBound(b.mCurrentScale);
-
- int x = p.mCurrentX + dx;
- int y = b.mCurrentY + dy;
-
- // Vertical direction: If we have space to move in the vertical
- // direction, we show the edge effect when scrolling reaches the edge.
- if (mBoundTop != mBoundBottom) {
- if (y < mBoundTop) {
- mListener.onPull(mBoundTop - y, EdgeView.BOTTOM);
- } else if (y > mBoundBottom) {
- mListener.onPull(y - mBoundBottom, EdgeView.TOP);
- }
- }
-
- y = Utils.clamp(y, mBoundTop, mBoundBottom);
-
- // Horizontal direction: we show the edge effect when the scrolling
- // tries to go left of the first image or go right of the last image.
- if (!mHasPrev && x > mBoundRight) {
- int pixels = x - mBoundRight;
- mListener.onPull(pixels, EdgeView.LEFT);
- x = mBoundRight;
- } else if (!mHasNext && x < mBoundLeft) {
- int pixels = mBoundLeft - x;
- mListener.onPull(pixels, EdgeView.RIGHT);
- x = mBoundLeft;
- }
-
- startAnimation(x, y, b.mCurrentScale, ANIM_KIND_SCROLL);
- }
-
- public void scrollFilmX(int dx) {
- if (!canScroll()) return;
-
- Box b = mBoxes.get(0);
- Platform p = mPlatform;
-
- // Only allow scrolling when we are not currently in an animation or we
- // are in some animation with can be interrupted.
- if (b.mAnimationStartTime != NO_ANIMATION) {
- switch (b.mAnimationKind) {
- case ANIM_KIND_SCROLL:
- case ANIM_KIND_FLING:
- case ANIM_KIND_FLING_X:
- break;
- default:
- return;
- }
- }
-
- int x = p.mCurrentX + dx;
-
- // Horizontal direction: we show the edge effect when the scrolling
- // tries to go left of the first image or go right of the last image.
- x -= mPlatform.mDefaultX;
- if (!mHasPrev && x > 0) {
- mListener.onPull(x, EdgeView.LEFT);
- x = 0;
- } else if (!mHasNext && x < 0) {
- mListener.onPull(-x, EdgeView.RIGHT);
- x = 0;
- }
- x += mPlatform.mDefaultX;
- startAnimation(x, b.mCurrentY, b.mCurrentScale, ANIM_KIND_SCROLL);
- }
-
- public void scrollFilmY(int boxIndex, int dy) {
- if (!canScroll()) return;
-
- Box b = mBoxes.get(boxIndex);
- int y = b.mCurrentY + dy;
- b.doAnimation(y, b.mCurrentScale, ANIM_KIND_SCROLL);
- redraw();
- }
-
- public boolean flingPage(int velocityX, int velocityY) {
- Box b = mBoxes.get(0);
- Platform p = mPlatform;
-
- // We only want to do fling when the picture is zoomed-in.
- if (viewWiderThanScaledImage(b.mCurrentScale) &&
- viewTallerThanScaledImage(b.mCurrentScale)) {
- return false;
- }
-
- // We only allow flinging in the directions where it won't go over the
- // picture.
- int edges = getImageAtEdges();
- if ((velocityX > 0 && (edges & IMAGE_AT_LEFT_EDGE) != 0) ||
- (velocityX < 0 && (edges & IMAGE_AT_RIGHT_EDGE) != 0)) {
- velocityX = 0;
- }
- if ((velocityY > 0 && (edges & IMAGE_AT_TOP_EDGE) != 0) ||
- (velocityY < 0 && (edges & IMAGE_AT_BOTTOM_EDGE) != 0)) {
- velocityY = 0;
- }
-
- if (velocityX == 0 && velocityY == 0) return false;
-
- mPageScroller.fling(p.mCurrentX, b.mCurrentY, velocityX, velocityY,
- mBoundLeft, mBoundRight, mBoundTop, mBoundBottom);
- int targetX = mPageScroller.getFinalX();
- int targetY = mPageScroller.getFinalY();
- ANIM_TIME[ANIM_KIND_FLING] = mPageScroller.getDuration();
- return startAnimation(targetX, targetY, b.mCurrentScale, ANIM_KIND_FLING);
- }
-
- public boolean flingFilmX(int velocityX) {
- if (velocityX == 0) return false;
-
- Box b = mBoxes.get(0);
- Platform p = mPlatform;
-
- // If we are already at the edge, don't start the fling.
- int defaultX = p.mDefaultX;
- if ((!mHasPrev && p.mCurrentX >= defaultX)
- || (!mHasNext && p.mCurrentX <= defaultX)) {
- return false;
- }
-
- mFilmScroller.fling(p.mCurrentX, 0, velocityX, 0,
- Integer.MIN_VALUE, Integer.MAX_VALUE, 0, 0);
- int targetX = mFilmScroller.getFinalX();
- return startAnimation(
- targetX, b.mCurrentY, b.mCurrentScale, ANIM_KIND_FLING_X);
- }
-
- // Moves the specified box out of screen. If velocityY is 0, a default
- // velocity is used. Returns the time for the duration, or -1 if we cannot
- // not do the animation.
- public int flingFilmY(int boxIndex, int velocityY) {
- Box b = mBoxes.get(boxIndex);
-
- // Calculate targetY
- int h = heightOf(b);
- int targetY;
- int FUZZY = 3; // TODO: figure out why this is needed.
- if (velocityY < 0 || (velocityY == 0 && b.mCurrentY <= 0)) {
- targetY = -mViewH / 2 - (h + 1) / 2 - FUZZY;
- } else {
- targetY = (mViewH + 1) / 2 + h / 2 + FUZZY;
- }
-
- // Calculate duration
- int duration;
- if (velocityY != 0) {
- duration = (int) (Math.abs(targetY - b.mCurrentY) * 1000f
- / Math.abs(velocityY));
- duration = Math.min(MAX_DELETE_ANIMATION_DURATION, duration);
- } else {
- duration = DEFAULT_DELETE_ANIMATION_DURATION;
- }
-
- // Start animation
- ANIM_TIME[ANIM_KIND_DELETE] = duration;
- if (b.doAnimation(targetY, b.mCurrentScale, ANIM_KIND_DELETE)) {
- redraw();
- return duration;
- }
- return -1;
- }
-
- // Returns the index of the box which contains the given point (x, y)
- // Returns Integer.MAX_VALUE if there is no hit. There may be more than
- // one box contains the given point, and we want to give priority to the
- // one closer to the focused index (0).
- public int hitTest(int x, int y) {
- for (int i = 0; i < 2 * BOX_MAX + 1; i++) {
- int j = CENTER_OUT_INDEX[i];
- Rect r = mRects.get(j);
- if (r.contains(x, y)) {
- return j;
- }
- }
-
- return Integer.MAX_VALUE;
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Redraw
- //
- // If a method changes box positions directly, redraw()
- // should be called.
- //
- // If a method may also cause a snapback to happen, snapAndRedraw() should
- // be called.
- //
- // If a method starts an animation to change the position of focused box,
- // startAnimation() should be called.
- //
- // If time advances to change the box position, advanceAnimation() should
- // be called.
- ////////////////////////////////////////////////////////////////////////////
- private void redraw() {
- layoutAndSetPosition();
- mListener.invalidate();
- }
-
- private void snapAndRedraw() {
- mPlatform.startSnapback();
- for (int i = -BOX_MAX; i <= BOX_MAX; i++) {
- mBoxes.get(i).startSnapback();
- }
- for (int i = -BOX_MAX; i < BOX_MAX; i++) {
- mGaps.get(i).startSnapback();
- }
- mFilmRatio.startSnapback();
- redraw();
- }
-
- private boolean startAnimation(int targetX, int targetY, float targetScale,
- int kind) {
- boolean changed = false;
- changed |= mPlatform.doAnimation(targetX, mPlatform.mDefaultY, kind);
- changed |= mBoxes.get(0).doAnimation(targetY, targetScale, kind);
- if (changed) redraw();
- return changed;
- }
-
- public void advanceAnimation() {
- boolean changed = false;
- changed |= mPlatform.advanceAnimation();
- for (int i = -BOX_MAX; i <= BOX_MAX; i++) {
- changed |= mBoxes.get(i).advanceAnimation();
- }
- for (int i = -BOX_MAX; i < BOX_MAX; i++) {
- changed |= mGaps.get(i).advanceAnimation();
- }
- changed |= mFilmRatio.advanceAnimation();
- if (changed) redraw();
- }
-
- public boolean inOpeningAnimation() {
- return (mPlatform.mAnimationKind == ANIM_KIND_OPENING &&
- mPlatform.mAnimationStartTime != NO_ANIMATION) ||
- (mBoxes.get(0).mAnimationKind == ANIM_KIND_OPENING &&
- mBoxes.get(0).mAnimationStartTime != NO_ANIMATION);
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Layout
- ////////////////////////////////////////////////////////////////////////////
-
- // Returns the display width of this box.
- private int widthOf(Box b) {
- return (int) (b.mImageW * b.mCurrentScale + 0.5f);
- }
-
- // Returns the display height of this box.
- private int heightOf(Box b) {
- return (int) (b.mImageH * b.mCurrentScale + 0.5f);
- }
-
- // Returns the display width of this box, using the given scale.
- private int widthOf(Box b, float scale) {
- return (int) (b.mImageW * scale + 0.5f);
- }
-
- // Returns the display height of this box, using the given scale.
- private int heightOf(Box b, float scale) {
- return (int) (b.mImageH * scale + 0.5f);
- }
-
- // Convert the information in mPlatform and mBoxes to mRects, so the user
- // can get the position of each box by getPosition().
- //
- // Note we go from center-out because each box's X coordinate
- // is relative to its anchor box (except the focused box).
- private void layoutAndSetPosition() {
- for (int i = 0; i < 2 * BOX_MAX + 1; i++) {
- convertBoxToRect(CENTER_OUT_INDEX[i]);
- }
- //dumpState();
- }
-
- @SuppressWarnings("unused")
- private void dumpState() {
- for (int i = -BOX_MAX; i < BOX_MAX; i++) {
- Log.d(TAG, "Gap " + i + ": " + mGaps.get(i).mCurrentGap);
- }
-
- for (int i = 0; i < 2 * BOX_MAX + 1; i++) {
- dumpRect(CENTER_OUT_INDEX[i]);
- }
-
- for (int i = -BOX_MAX; i <= BOX_MAX; i++) {
- for (int j = i + 1; j <= BOX_MAX; j++) {
- if (Rect.intersects(mRects.get(i), mRects.get(j))) {
- Log.d(TAG, "rect " + i + " and rect " + j + "intersects!");
- }
- }
- }
- }
-
- private void dumpRect(int i) {
- StringBuilder sb = new StringBuilder();
- Rect r = mRects.get(i);
- sb.append("Rect " + i + ":");
- sb.append("(");
- sb.append(r.centerX());
- sb.append(",");
- sb.append(r.centerY());
- sb.append(") [");
- sb.append(r.width());
- sb.append("x");
- sb.append(r.height());
- sb.append("]");
- Log.d(TAG, sb.toString());
- }
-
- private void convertBoxToRect(int i) {
- Box b = mBoxes.get(i);
- Rect r = mRects.get(i);
- int y = b.mCurrentY + mPlatform.mCurrentY + mViewH / 2;
- int w = widthOf(b);
- int h = heightOf(b);
- if (i == 0) {
- int x = mPlatform.mCurrentX + mViewW / 2;
- r.left = x - w / 2;
- r.right = r.left + w;
- } else if (i > 0) {
- Rect a = mRects.get(i - 1);
- Gap g = mGaps.get(i - 1);
- r.left = a.right + g.mCurrentGap;
- r.right = r.left + w;
- } else { // i < 0
- Rect a = mRects.get(i + 1);
- Gap g = mGaps.get(i);
- r.right = a.left - g.mCurrentGap;
- r.left = r.right - w;
- }
- r.top = y - h / 2;
- r.bottom = r.top + h;
- }
-
- // Returns the position of a box.
- public Rect getPosition(int index) {
- return mRects.get(index);
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Box management
- ////////////////////////////////////////////////////////////////////////////
-
- // Initialize the platform to be at the view center.
- private void initPlatform() {
- mPlatform.updateDefaultXY();
- mPlatform.mCurrentX = mPlatform.mDefaultX;
- mPlatform.mCurrentY = mPlatform.mDefaultY;
- mPlatform.mAnimationStartTime = NO_ANIMATION;
- }
-
- // Initialize a box to have the size of the view.
- private void initBox(int index) {
- Box b = mBoxes.get(index);
- b.mImageW = mViewW;
- b.mImageH = mViewH;
- b.mUseViewSize = true;
- b.mScaleMin = getMinimalScale(b);
- b.mScaleMax = getMaximalScale(b);
- b.mCurrentY = 0;
- b.mCurrentScale = b.mScaleMin;
- b.mAnimationStartTime = NO_ANIMATION;
- b.mAnimationKind = ANIM_KIND_NONE;
- }
-
- // Initialize a box to a given size.
- private void initBox(int index, Size size) {
- if (size.width == 0 || size.height == 0) {
- initBox(index);
- return;
- }
- Box b = mBoxes.get(index);
- b.mImageW = size.width;
- b.mImageH = size.height;
- b.mUseViewSize = false;
- b.mScaleMin = getMinimalScale(b);
- b.mScaleMax = getMaximalScale(b);
- b.mCurrentY = 0;
- b.mCurrentScale = b.mScaleMin;
- b.mAnimationStartTime = NO_ANIMATION;
- b.mAnimationKind = ANIM_KIND_NONE;
- }
-
- // Initialize a gap. This can only be called after the boxes around the gap
- // has been initialized.
- private void initGap(int index) {
- Gap g = mGaps.get(index);
- g.mDefaultSize = getDefaultGapSize(index);
- g.mCurrentGap = g.mDefaultSize;
- g.mAnimationStartTime = NO_ANIMATION;
- }
-
- private void initGap(int index, int size) {
- Gap g = mGaps.get(index);
- g.mDefaultSize = getDefaultGapSize(index);
- g.mCurrentGap = size;
- g.mAnimationStartTime = NO_ANIMATION;
- }
-
- @SuppressWarnings("unused")
- private void debugMoveBox(int fromIndex[]) {
- StringBuilder s = new StringBuilder("moveBox:");
- for (int i = 0; i < fromIndex.length; i++) {
- int j = fromIndex[i];
- if (j == Integer.MAX_VALUE) {
- s.append(" N");
- } else {
- s.append(" ");
- s.append(fromIndex[i]);
- }
- }
- Log.d(TAG, s.toString());
- }
-
- // Move the boxes: it may indicate focus change, box deleted, box appearing,
- // box reordered, etc.
- //
- // Each element in the fromIndex array indicates where each box was in the
- // old array. If the value is Integer.MAX_VALUE (pictured as N below), it
- // means the box is new.
- //
- // For example:
- // N N N N N N N -- all new boxes
- // -3 -2 -1 0 1 2 3 -- nothing changed
- // -2 -1 0 1 2 3 N -- focus goes to the next box
- // N -3 -2 -1 0 1 2 -- focus goes to the previous box
- // -3 -2 -1 1 2 3 N -- the focused box was deleted.
- //
- // hasPrev/hasNext indicates if there are previous/next boxes for the
- // focused box. constrained indicates whether the focused box should be put
- // into the constrained frame.
- public void moveBox(int fromIndex[], boolean hasPrev, boolean hasNext,
- boolean constrained, Size[] sizes) {
- //debugMoveBox(fromIndex);
- mHasPrev = hasPrev;
- mHasNext = hasNext;
-
- RangeIntArray from = new RangeIntArray(fromIndex, -BOX_MAX, BOX_MAX);
-
- // 1. Get the absolute X coordinates for the boxes.
- layoutAndSetPosition();
- for (int i = -BOX_MAX; i <= BOX_MAX; i++) {
- Box b = mBoxes.get(i);
- Rect r = mRects.get(i);
- b.mAbsoluteX = r.centerX() - mViewW / 2;
- }
-
- // 2. copy boxes and gaps to temporary storage.
- for (int i = -BOX_MAX; i <= BOX_MAX; i++) {
- mTempBoxes.put(i, mBoxes.get(i));
- mBoxes.put(i, null);
- }
- for (int i = -BOX_MAX; i < BOX_MAX; i++) {
- mTempGaps.put(i, mGaps.get(i));
- mGaps.put(i, null);
- }
-
- // 3. move back boxes that are used in the new array.
- for (int i = -BOX_MAX; i <= BOX_MAX; i++) {
- int j = from.get(i);
- if (j == Integer.MAX_VALUE) continue;
- mBoxes.put(i, mTempBoxes.get(j));
- mTempBoxes.put(j, null);
- }
-
- // 4. move back gaps if both boxes around it are kept together.
- for (int i = -BOX_MAX; i < BOX_MAX; i++) {
- int j = from.get(i);
- if (j == Integer.MAX_VALUE) continue;
- int k = from.get(i + 1);
- if (k == Integer.MAX_VALUE) continue;
- if (j + 1 == k) {
- mGaps.put(i, mTempGaps.get(j));
- mTempGaps.put(j, null);
- }
- }
-
- // 5. recycle the boxes that are not used in the new array.
- int k = -BOX_MAX;
- for (int i = -BOX_MAX; i <= BOX_MAX; i++) {
- if (mBoxes.get(i) != null) continue;
- while (mTempBoxes.get(k) == null) {
- k++;
- }
- mBoxes.put(i, mTempBoxes.get(k++));
- initBox(i, sizes[i + BOX_MAX]);
- }
-
- // 6. Now give the recycled box a reasonable absolute X position.
- //
- // First try to find the first and the last box which the absolute X
- // position is known.
- int first, last;
- for (first = -BOX_MAX; first <= BOX_MAX; first++) {
- if (from.get(first) != Integer.MAX_VALUE) break;
- }
- for (last = BOX_MAX; last >= -BOX_MAX; last--) {
- if (from.get(last) != Integer.MAX_VALUE) break;
- }
- // If there is no box has known X position at all, make the focused one
- // as known.
- if (first > BOX_MAX) {
- mBoxes.get(0).mAbsoluteX = mPlatform.mCurrentX;
- first = last = 0;
- }
- // Now for those boxes between first and last, assign their position to
- // align to the previous box or the next box with known position. For
- // the boxes before first or after last, we will use a new default gap
- // size below.
-
- // Align to the previous box
- for (int i = Math.max(0, first + 1); i < last; i++) {
- if (from.get(i) != Integer.MAX_VALUE) continue;
- Box a = mBoxes.get(i - 1);
- Box b = mBoxes.get(i);
- int wa = widthOf(a);
- int wb = widthOf(b);
- b.mAbsoluteX = a.mAbsoluteX + (wa - wa / 2) + wb / 2
- + getDefaultGapSize(i);
- if (mPopFromTop) {
- b.mCurrentY = -(mViewH / 2 + heightOf(b) / 2);
- } else {
- b.mCurrentY = (mViewH / 2 + heightOf(b) / 2);
- }
- }
-
- // Align to the next box
- for (int i = Math.min(-1, last - 1); i > first; i--) {
- if (from.get(i) != Integer.MAX_VALUE) continue;
- Box a = mBoxes.get(i + 1);
- Box b = mBoxes.get(i);
- int wa = widthOf(a);
- int wb = widthOf(b);
- b.mAbsoluteX = a.mAbsoluteX - wa / 2 - (wb - wb / 2)
- - getDefaultGapSize(i);
- if (mPopFromTop) {
- b.mCurrentY = -(mViewH / 2 + heightOf(b) / 2);
- } else {
- b.mCurrentY = (mViewH / 2 + heightOf(b) / 2);
- }
- }
-
- // 7. recycle the gaps that are not used in the new array.
- k = -BOX_MAX;
- for (int i = -BOX_MAX; i < BOX_MAX; i++) {
- if (mGaps.get(i) != null) continue;
- while (mTempGaps.get(k) == null) {
- k++;
- }
- mGaps.put(i, mTempGaps.get(k++));
- Box a = mBoxes.get(i);
- Box b = mBoxes.get(i + 1);
- int wa = widthOf(a);
- int wb = widthOf(b);
- if (i >= first && i < last) {
- int g = b.mAbsoluteX - a.mAbsoluteX - wb / 2 - (wa - wa / 2);
- initGap(i, g);
- } else {
- initGap(i);
- }
- }
-
- // 8. calculate the new absolute X coordinates for those box before
- // first or after last.
- for (int i = first - 1; i >= -BOX_MAX; i--) {
- Box a = mBoxes.get(i + 1);
- Box b = mBoxes.get(i);
- int wa = widthOf(a);
- int wb = widthOf(b);
- Gap g = mGaps.get(i);
- b.mAbsoluteX = a.mAbsoluteX - wa / 2 - (wb - wb / 2) - g.mCurrentGap;
- }
-
- for (int i = last + 1; i <= BOX_MAX; i++) {
- Box a = mBoxes.get(i - 1);
- Box b = mBoxes.get(i);
- int wa = widthOf(a);
- int wb = widthOf(b);
- Gap g = mGaps.get(i - 1);
- b.mAbsoluteX = a.mAbsoluteX + (wa - wa / 2) + wb / 2 + g.mCurrentGap;
- }
-
- // 9. offset the Platform position
- int dx = mBoxes.get(0).mAbsoluteX - mPlatform.mCurrentX;
- mPlatform.mCurrentX += dx;
- mPlatform.mFromX += dx;
- mPlatform.mToX += dx;
- mPlatform.mFlingOffset += dx;
-
- if (mConstrained != constrained) {
- mConstrained = constrained;
- mPlatform.updateDefaultXY();
- updateScaleAndGapLimit();
- }
-
- snapAndRedraw();
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Public utilities
- ////////////////////////////////////////////////////////////////////////////
-
- public boolean isAtMinimalScale() {
- Box b = mBoxes.get(0);
- return isAlmostEqual(b.mCurrentScale, b.mScaleMin);
- }
-
- public boolean isCenter() {
- Box b = mBoxes.get(0);
- return mPlatform.mCurrentX == mPlatform.mDefaultX
- && b.mCurrentY == 0;
- }
-
- public int getImageWidth() {
- Box b = mBoxes.get(0);
- return b.mImageW;
- }
-
- public int getImageHeight() {
- Box b = mBoxes.get(0);
- return b.mImageH;
- }
-
- public float getImageScale() {
- Box b = mBoxes.get(0);
- return b.mCurrentScale;
- }
-
- public int getImageAtEdges() {
- Box b = mBoxes.get(0);
- Platform p = mPlatform;
- calculateStableBound(b.mCurrentScale);
- int edges = 0;
- if (p.mCurrentX <= mBoundLeft) {
- edges |= IMAGE_AT_RIGHT_EDGE;
- }
- if (p.mCurrentX >= mBoundRight) {
- edges |= IMAGE_AT_LEFT_EDGE;
- }
- if (b.mCurrentY <= mBoundTop) {
- edges |= IMAGE_AT_BOTTOM_EDGE;
- }
- if (b.mCurrentY >= mBoundBottom) {
- edges |= IMAGE_AT_TOP_EDGE;
- }
- return edges;
- }
-
- public boolean isScrolling() {
- return mPlatform.mAnimationStartTime != NO_ANIMATION
- && mPlatform.mCurrentX != mPlatform.mToX;
- }
-
- public void stopScrolling() {
- if (mPlatform.mAnimationStartTime == NO_ANIMATION) return;
- if (mFilmMode) mFilmScroller.forceFinished(true);
- mPlatform.mFromX = mPlatform.mToX = mPlatform.mCurrentX;
- }
-
- public float getFilmRatio() {
- return mFilmRatio.mCurrentRatio;
- }
-
- public void setPopFromTop(boolean top) {
- mPopFromTop = top;
- }
-
- public boolean hasDeletingBox() {
- for(int i = -BOX_MAX; i <= BOX_MAX; i++) {
- if (mBoxes.get(i).mAnimationKind == ANIM_KIND_DELETE) {
- return true;
- }
- }
- return false;
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Private utilities
- ////////////////////////////////////////////////////////////////////////////
-
- private float getMinimalScale(Box b) {
- float wFactor = 1.0f;
- float hFactor = 1.0f;
- int viewW, viewH;
-
- if (!mFilmMode && mConstrained && !mConstrainedFrame.isEmpty()
- && b == mBoxes.get(0)) {
- viewW = mConstrainedFrame.width();
- viewH = mConstrainedFrame.height();
- } else {
- viewW = mViewW;
- viewH = mViewH;
- }
-
- if (mFilmMode) {
- if (mViewH > mViewW) { // portrait
- wFactor = FILM_MODE_PORTRAIT_WIDTH;
- hFactor = FILM_MODE_PORTRAIT_HEIGHT;
- } else { // landscape
- wFactor = FILM_MODE_LANDSCAPE_WIDTH;
- hFactor = FILM_MODE_LANDSCAPE_HEIGHT;
- }
- }
-
- float s = Math.min(wFactor * viewW / b.mImageW,
- hFactor * viewH / b.mImageH);
- return Math.min(SCALE_LIMIT, s);
- }
-
- private float getMaximalScale(Box b) {
- if (mFilmMode) return getMinimalScale(b);
- if (mConstrained && !mConstrainedFrame.isEmpty()) return getMinimalScale(b);
- return SCALE_LIMIT;
- }
-
- private static boolean isAlmostEqual(float a, float b) {
- float diff = a - b;
- return (diff < 0 ? -diff : diff) < 0.02f;
- }
-
- // Calculates the stable region of mPlatform.mCurrentX and
- // mBoxes.get(0).mCurrentY, where "stable" means
- //
- // (1) If the dimension of scaled image >= view dimension, we will not
- // see black region outside the image (at that dimension).
- // (2) If the dimension of scaled image < view dimension, we will center
- // the scaled image.
- //
- // We might temporarily go out of this stable during user interaction,
- // but will "snap back" after user stops interaction.
- //
- // The results are stored in mBound{Left/Right/Top/Bottom}.
- //
- // An extra parameter "horizontalSlack" (which has the value of 0 usually)
- // is used to extend the stable region by some pixels on each side
- // horizontally.
- private void calculateStableBound(float scale, int horizontalSlack) {
- Box b = mBoxes.get(0);
-
- // The width and height of the box in number of view pixels
- int w = widthOf(b, scale);
- int h = heightOf(b, scale);
-
- // When the edge of the view is aligned with the edge of the box
- mBoundLeft = (mViewW + 1) / 2 - (w + 1) / 2 - horizontalSlack;
- mBoundRight = w / 2 - mViewW / 2 + horizontalSlack;
- mBoundTop = (mViewH + 1) / 2 - (h + 1) / 2;
- mBoundBottom = h / 2 - mViewH / 2;
-
- // If the scaled height is smaller than the view height,
- // force it to be in the center.
- if (viewTallerThanScaledImage(scale)) {
- mBoundTop = mBoundBottom = 0;
- }
-
- // Same for width
- if (viewWiderThanScaledImage(scale)) {
- mBoundLeft = mBoundRight = mPlatform.mDefaultX;
- }
- }
-
- private void calculateStableBound(float scale) {
- calculateStableBound(scale, 0);
- }
-
- private boolean viewTallerThanScaledImage(float scale) {
- return mViewH >= heightOf(mBoxes.get(0), scale);
- }
-
- private boolean viewWiderThanScaledImage(float scale) {
- return mViewW >= widthOf(mBoxes.get(0), scale);
- }
-
- private float getTargetScale(Box b) {
- return b.mAnimationStartTime == NO_ANIMATION
- ? b.mCurrentScale : b.mToScale;
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Animatable: an thing which can do animation.
- ////////////////////////////////////////////////////////////////////////////
- private abstract static class Animatable {
- public long mAnimationStartTime;
- public int mAnimationKind;
- public int mAnimationDuration;
-
- // This should be overridden in subclass to change the animation values
- // give the progress value in [0, 1].
- protected abstract boolean interpolate(float progress);
- public abstract boolean startSnapback();
-
- // Returns true if the animation values changes, so things need to be
- // redrawn.
- public boolean advanceAnimation() {
- if (mAnimationStartTime == NO_ANIMATION) {
- return false;
- }
- if (mAnimationStartTime == LAST_ANIMATION) {
- mAnimationStartTime = NO_ANIMATION;
- return startSnapback();
- }
-
- float progress;
- if (mAnimationDuration == 0) {
- progress = 1;
- } else {
- long now = AnimationTime.get();
- progress =
- (float) (now - mAnimationStartTime) / mAnimationDuration;
- }
-
- if (progress >= 1) {
- progress = 1;
- } else {
- progress = applyInterpolationCurve(mAnimationKind, progress);
- }
-
- boolean done = interpolate(progress);
-
- if (done) {
- mAnimationStartTime = LAST_ANIMATION;
- }
-
- return true;
- }
-
- private static float applyInterpolationCurve(int kind, float progress) {
- float f = 1 - progress;
- switch (kind) {
- case ANIM_KIND_SCROLL:
- case ANIM_KIND_FLING:
- case ANIM_KIND_FLING_X:
- case ANIM_KIND_DELETE:
- case ANIM_KIND_CAPTURE:
- progress = 1 - f; // linear
- break;
- case ANIM_KIND_OPENING:
- case ANIM_KIND_SCALE:
- progress = 1 - f * f; // quadratic
- break;
- case ANIM_KIND_SNAPBACK:
- case ANIM_KIND_ZOOM:
- case ANIM_KIND_SLIDE:
- progress = 1 - f * f * f * f * f; // x^5
- break;
- }
- return progress;
- }
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Platform: captures the global X/Y movement.
- ////////////////////////////////////////////////////////////////////////////
- private class Platform extends Animatable {
- public int mCurrentX, mFromX, mToX, mDefaultX;
- public int mCurrentY, mFromY, mToY, mDefaultY;
- public int mFlingOffset;
-
- @Override
- public boolean startSnapback() {
- if (mAnimationStartTime != NO_ANIMATION) return false;
- if (mAnimationKind == ANIM_KIND_SCROLL
- && mListener.isHoldingDown()) return false;
- if (mInScale) return false;
-
- Box b = mBoxes.get(0);
- float scaleMin = mExtraScalingRange ?
- b.mScaleMin * SCALE_MIN_EXTRA : b.mScaleMin;
- float scaleMax = mExtraScalingRange ?
- b.mScaleMax * SCALE_MAX_EXTRA : b.mScaleMax;
- float scale = Utils.clamp(b.mCurrentScale, scaleMin, scaleMax);
- int x = mCurrentX;
- int y = mDefaultY;
- if (mFilmMode) {
- x = mDefaultX;
- } else {
- calculateStableBound(scale, HORIZONTAL_SLACK);
- // If the picture is zoomed-in, we want to keep the focus point
- // stay in the same position on screen, so we need to adjust
- // target mCurrentX (which is the center of the focused
- // box). The position of the focus point on screen (relative the
- // the center of the view) is:
- //
- // mCurrentX + scale * mFocusX = mCurrentX' + scale' * mFocusX
- // => mCurrentX' = mCurrentX + (scale - scale') * mFocusX
- //
- if (!viewWiderThanScaledImage(scale)) {
- float scaleDiff = b.mCurrentScale - scale;
- x += (int) (mFocusX * scaleDiff + 0.5f);
- }
- x = Utils.clamp(x, mBoundLeft, mBoundRight);
- }
- if (mCurrentX != x || mCurrentY != y) {
- return doAnimation(x, y, ANIM_KIND_SNAPBACK);
- }
- return false;
- }
-
- // The updateDefaultXY() should be called whenever these variables
- // changes: (1) mConstrained (2) mConstrainedFrame (3) mViewW/H (4)
- // mFilmMode
- public void updateDefaultXY() {
- // We don't check mFilmMode and return 0 for mDefaultX. Because
- // otherwise if we decide to leave film mode because we are
- // centered, we will immediately back into film mode because we find
- // we are not centered.
- if (mConstrained && !mConstrainedFrame.isEmpty()) {
- mDefaultX = mConstrainedFrame.centerX() - mViewW / 2;
- mDefaultY = mFilmMode ? 0 :
- mConstrainedFrame.centerY() - mViewH / 2;
- } else {
- mDefaultX = 0;
- mDefaultY = 0;
- }
- }
-
- // Starts an animation for the platform.
- private boolean doAnimation(int targetX, int targetY, int kind) {
- if (mCurrentX == targetX && mCurrentY == targetY) return false;
- mAnimationKind = kind;
- mFromX = mCurrentX;
- mFromY = mCurrentY;
- mToX = targetX;
- mToY = targetY;
- mAnimationStartTime = AnimationTime.startTime();
- mAnimationDuration = ANIM_TIME[kind];
- mFlingOffset = 0;
- advanceAnimation();
- return true;
- }
-
- @Override
- protected boolean interpolate(float progress) {
- if (mAnimationKind == ANIM_KIND_FLING) {
- return interpolateFlingPage(progress);
- } else if (mAnimationKind == ANIM_KIND_FLING_X) {
- return interpolateFlingFilm(progress);
- } else {
- return interpolateLinear(progress);
- }
- }
-
- private boolean interpolateFlingFilm(float progress) {
- mFilmScroller.computeScrollOffset();
- mCurrentX = mFilmScroller.getCurrX() + mFlingOffset;
-
- int dir = EdgeView.INVALID_DIRECTION;
- if (mCurrentX < mDefaultX) {
- if (!mHasNext) {
- dir = EdgeView.RIGHT;
- }
- } else if (mCurrentX > mDefaultX) {
- if (!mHasPrev) {
- dir = EdgeView.LEFT;
- }
- }
- if (dir != EdgeView.INVALID_DIRECTION) {
- // TODO: restore this onAbsorb call
- //int v = (int) (mFilmScroller.getCurrVelocity() + 0.5f);
- //mListener.onAbsorb(v, dir);
- mFilmScroller.forceFinished(true);
- mCurrentX = mDefaultX;
- }
- return mFilmScroller.isFinished();
- }
-
- private boolean interpolateFlingPage(float progress) {
- mPageScroller.computeScrollOffset(progress);
- Box b = mBoxes.get(0);
- calculateStableBound(b.mCurrentScale);
-
- int oldX = mCurrentX;
- mCurrentX = mPageScroller.getCurrX();
-
- // Check if we hit the edges; show edge effects if we do.
- if (oldX > mBoundLeft && mCurrentX == mBoundLeft) {
- int v = (int) (-mPageScroller.getCurrVelocityX() + 0.5f);
- mListener.onAbsorb(v, EdgeView.RIGHT);
- } else if (oldX < mBoundRight && mCurrentX == mBoundRight) {
- int v = (int) (mPageScroller.getCurrVelocityX() + 0.5f);
- mListener.onAbsorb(v, EdgeView.LEFT);
- }
-
- return progress >= 1;
- }
-
- private boolean interpolateLinear(float progress) {
- // Other animations
- if (progress >= 1) {
- mCurrentX = mToX;
- mCurrentY = mToY;
- return true;
- } else {
- if (mAnimationKind == ANIM_KIND_CAPTURE) {
- progress = CaptureAnimation.calculateSlide(progress);
- }
- mCurrentX = (int) (mFromX + progress * (mToX - mFromX));
- mCurrentY = (int) (mFromY + progress * (mToY - mFromY));
- if (mAnimationKind == ANIM_KIND_CAPTURE) {
- return false;
- } else {
- return (mCurrentX == mToX && mCurrentY == mToY);
- }
- }
- }
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Box: represents a rectangular area which shows a picture.
- ////////////////////////////////////////////////////////////////////////////
- private class Box extends Animatable {
- // Size of the bitmap
- public int mImageW, mImageH;
-
- // This is true if we assume the image size is the same as view size
- // until we know the actual size of image. This is also used to
- // determine if there is an image ready to show.
- public boolean mUseViewSize;
-
- // The minimum and maximum scale we allow for this box.
- public float mScaleMin, mScaleMax;
-
- // The X/Y value indicates where the center of the box is on the view
- // coordinate. We always keep the mCurrent{X,Y,Scale} sync with the
- // actual values used currently. Note that the X values are implicitly
- // defined by Platform and Gaps.
- public int mCurrentY, mFromY, mToY;
- public float mCurrentScale, mFromScale, mToScale;
-
- // The absolute X coordinate of the center of the box. This is only used
- // during moveBox().
- public int mAbsoluteX;
-
- @Override
- public boolean startSnapback() {
- if (mAnimationStartTime != NO_ANIMATION) return false;
- if (mAnimationKind == ANIM_KIND_SCROLL
- && mListener.isHoldingDown()) return false;
- if (mAnimationKind == ANIM_KIND_DELETE
- && mListener.isHoldingDelete()) return false;
- if (mInScale && this == mBoxes.get(0)) return false;
-
- int y = mCurrentY;
- float scale;
-
- if (this == mBoxes.get(0)) {
- float scaleMin = mExtraScalingRange ?
- mScaleMin * SCALE_MIN_EXTRA : mScaleMin;
- float scaleMax = mExtraScalingRange ?
- mScaleMax * SCALE_MAX_EXTRA : mScaleMax;
- scale = Utils.clamp(mCurrentScale, scaleMin, scaleMax);
- if (mFilmMode) {
- y = 0;
- } else {
- calculateStableBound(scale, HORIZONTAL_SLACK);
- // If the picture is zoomed-in, we want to keep the focus
- // point stay in the same position on screen. See the
- // comment in Platform.startSnapback for details.
- if (!viewTallerThanScaledImage(scale)) {
- float scaleDiff = mCurrentScale - scale;
- y += (int) (mFocusY * scaleDiff + 0.5f);
- }
- y = Utils.clamp(y, mBoundTop, mBoundBottom);
- }
- } else {
- y = 0;
- scale = mScaleMin;
- }
-
- if (mCurrentY != y || mCurrentScale != scale) {
- return doAnimation(y, scale, ANIM_KIND_SNAPBACK);
- }
- return false;
- }
-
- private boolean doAnimation(int targetY, float targetScale, int kind) {
- targetScale = clampScale(targetScale);
-
- if (mCurrentY == targetY && mCurrentScale == targetScale
- && kind != ANIM_KIND_CAPTURE) {
- return false;
- }
-
- // Now starts an animation for the box.
- mAnimationKind = kind;
- mFromY = mCurrentY;
- mFromScale = mCurrentScale;
- mToY = targetY;
- mToScale = targetScale;
- mAnimationStartTime = AnimationTime.startTime();
- mAnimationDuration = ANIM_TIME[kind];
- advanceAnimation();
- return true;
- }
-
- // Clamps the input scale to the range that doAnimation() can reach.
- public float clampScale(float s) {
- return Utils.clamp(s,
- SCALE_MIN_EXTRA * mScaleMin,
- SCALE_MAX_EXTRA * mScaleMax);
- }
-
- @Override
- protected boolean interpolate(float progress) {
- if (mAnimationKind == ANIM_KIND_FLING) {
- return interpolateFlingPage(progress);
- } else {
- return interpolateLinear(progress);
- }
- }
-
- private boolean interpolateFlingPage(float progress) {
- mPageScroller.computeScrollOffset(progress);
- calculateStableBound(mCurrentScale);
-
- int oldY = mCurrentY;
- mCurrentY = mPageScroller.getCurrY();
-
- // Check if we hit the edges; show edge effects if we do.
- if (oldY > mBoundTop && mCurrentY == mBoundTop) {
- int v = (int) (-mPageScroller.getCurrVelocityY() + 0.5f);
- mListener.onAbsorb(v, EdgeView.BOTTOM);
- } else if (oldY < mBoundBottom && mCurrentY == mBoundBottom) {
- int v = (int) (mPageScroller.getCurrVelocityY() + 0.5f);
- mListener.onAbsorb(v, EdgeView.TOP);
- }
-
- return progress >= 1;
- }
-
- private boolean interpolateLinear(float progress) {
- if (progress >= 1) {
- mCurrentY = mToY;
- mCurrentScale = mToScale;
- return true;
- } else {
- mCurrentY = (int) (mFromY + progress * (mToY - mFromY));
- mCurrentScale = mFromScale + progress * (mToScale - mFromScale);
- if (mAnimationKind == ANIM_KIND_CAPTURE) {
- float f = CaptureAnimation.calculateScale(progress);
- mCurrentScale *= f;
- return false;
- } else {
- return (mCurrentY == mToY && mCurrentScale == mToScale);
- }
- }
- }
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Gap: represents a rectangular area which is between two boxes.
- ////////////////////////////////////////////////////////////////////////////
- private class Gap extends Animatable {
- // The default gap size between two boxes. The value may vary for
- // different image size of the boxes and for different modes (page or
- // film).
- public int mDefaultSize;
-
- // The gap size between the two boxes.
- public int mCurrentGap, mFromGap, mToGap;
-
- @Override
- public boolean startSnapback() {
- if (mAnimationStartTime != NO_ANIMATION) return false;
- return doAnimation(mDefaultSize, ANIM_KIND_SNAPBACK);
- }
-
- // Starts an animation for a gap.
- public boolean doAnimation(int targetSize, int kind) {
- if (mCurrentGap == targetSize && kind != ANIM_KIND_CAPTURE) {
- return false;
- }
- mAnimationKind = kind;
- mFromGap = mCurrentGap;
- mToGap = targetSize;
- mAnimationStartTime = AnimationTime.startTime();
- mAnimationDuration = ANIM_TIME[mAnimationKind];
- advanceAnimation();
- return true;
- }
-
- @Override
- protected boolean interpolate(float progress) {
- if (progress >= 1) {
- mCurrentGap = mToGap;
- return true;
- } else {
- mCurrentGap = (int) (mFromGap + progress * (mToGap - mFromGap));
- if (mAnimationKind == ANIM_KIND_CAPTURE) {
- float f = CaptureAnimation.calculateScale(progress);
- mCurrentGap = (int) (mCurrentGap * f);
- return false;
- } else {
- return (mCurrentGap == mToGap);
- }
- }
- }
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // FilmRatio: represents the progress of film mode change.
- ////////////////////////////////////////////////////////////////////////////
- private class FilmRatio extends Animatable {
- // The film ratio: 1 means switching to film mode is complete, 0 means
- // switching to page mode is complete.
- public float mCurrentRatio, mFromRatio, mToRatio;
-
- @Override
- public boolean startSnapback() {
- float target = mFilmMode ? 1f : 0f;
- if (target == mToRatio) return false;
- return doAnimation(target, ANIM_KIND_SNAPBACK);
- }
-
- // Starts an animation for the film ratio.
- private boolean doAnimation(float targetRatio, int kind) {
- mAnimationKind = kind;
- mFromRatio = mCurrentRatio;
- mToRatio = targetRatio;
- mAnimationStartTime = AnimationTime.startTime();
- mAnimationDuration = ANIM_TIME[mAnimationKind];
- advanceAnimation();
- return true;
- }
-
- @Override
- protected boolean interpolate(float progress) {
- if (progress >= 1) {
- mCurrentRatio = mToRatio;
- return true;
- } else {
- mCurrentRatio = mFromRatio + progress * (mToRatio - mFromRatio);
- return (mCurrentRatio == mToRatio);
- }
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/PreparePageFadeoutTexture.java b/src/com/android/gallery3d/ui/PreparePageFadeoutTexture.java
deleted file mode 100644
index ce672f211..000000000
--- a/src/com/android/gallery3d/ui/PreparePageFadeoutTexture.java
+++ /dev/null
@@ -1,85 +0,0 @@
-package com.android.gallery3d.ui;
-
-import android.os.ConditionVariable;
-
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.RawTexture;
-import com.android.gallery3d.ui.GLRoot.OnGLIdleListener;
-
-public class PreparePageFadeoutTexture implements OnGLIdleListener {
- private static final long TIMEOUT = 200;
- public static final String KEY_FADE_TEXTURE = "fade_texture";
-
- private RawTexture mTexture;
- private ConditionVariable mResultReady = new ConditionVariable(false);
- private boolean mCancelled = false;
- private GLView mRootPane;
-
- public PreparePageFadeoutTexture(GLView rootPane) {
- if (rootPane == null) {
- mCancelled = true;
- return;
- }
- int w = rootPane.getWidth();
- int h = rootPane.getHeight();
- if (w == 0 || h == 0) {
- mCancelled = true;
- return;
- }
- mTexture = new RawTexture(w, h, true);
- mRootPane = rootPane;
- }
-
- public boolean isCancelled() {
- return mCancelled;
- }
-
- public synchronized RawTexture get() {
- if (mCancelled) {
- return null;
- } else if (mResultReady.block(TIMEOUT)) {
- return mTexture;
- } else {
- mCancelled = true;
- return null;
- }
- }
-
- @Override
- public boolean onGLIdle(GLCanvas canvas, boolean renderRequested) {
- if (!mCancelled) {
- try {
- canvas.beginRenderTarget(mTexture);
- mRootPane.render(canvas);
- canvas.endRenderTarget();
- } catch (RuntimeException e) {
- mTexture = null;
- }
- } else {
- mTexture = null;
- }
- mResultReady.open();
- return false;
- }
-
- public static void prepareFadeOutTexture(AbstractGalleryActivity activity,
- GLView rootPane) {
- PreparePageFadeoutTexture task = new PreparePageFadeoutTexture(rootPane);
- if (task.isCancelled()) return;
- GLRoot root = activity.getGLRoot();
- RawTexture texture = null;
- root.unlockRenderThread();
- try {
- root.addOnGLIdleListener(task);
- texture = task.get();
- } finally {
- root.lockRenderThread();
- }
-
- if (texture == null) {
- return;
- }
- activity.getTransitionStore().put(KEY_FADE_TEXTURE, texture);
- }
-}
diff --git a/src/com/android/gallery3d/ui/ProgressSpinner.java b/src/com/android/gallery3d/ui/ProgressSpinner.java
deleted file mode 100644
index 1b31af278..000000000
--- a/src/com/android/gallery3d/ui/ProgressSpinner.java
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.ResourceTexture;
-
-public class ProgressSpinner {
- private static float ROTATE_SPEED_OUTER = 1080f / 3500f;
- private static float ROTATE_SPEED_INNER = -720f / 3500f;
- private final ResourceTexture mOuter;
- private final ResourceTexture mInner;
- private final int mWidth;
- private final int mHeight;
-
- private float mInnerDegree = 0f;
- private float mOuterDegree = 0f;
- private long mAnimationTimestamp = -1;
-
- public ProgressSpinner(Context context) {
- mOuter = new ResourceTexture(context, R.drawable.spinner_76_outer_holo);
- mInner = new ResourceTexture(context, R.drawable.spinner_76_inner_holo);
-
- mWidth = Math.max(mOuter.getWidth(), mInner.getWidth());
- mHeight = Math.max(mOuter.getHeight(), mInner.getHeight());
- }
-
- public int getWidth() {
- return mWidth;
- }
-
- public int getHeight() {
- return mHeight;
- }
-
- public void startAnimation() {
- mAnimationTimestamp = -1;
- mOuterDegree = 0;
- mInnerDegree = 0;
- }
-
- public void draw(GLCanvas canvas, int x, int y) {
- long now = AnimationTime.get();
- if (mAnimationTimestamp == -1) mAnimationTimestamp = now;
- mOuterDegree += (now - mAnimationTimestamp) * ROTATE_SPEED_OUTER;
- mInnerDegree += (now - mAnimationTimestamp) * ROTATE_SPEED_INNER;
-
- mAnimationTimestamp = now;
-
- // just preventing overflow
- if (mOuterDegree > 360) mOuterDegree -= 360f;
- if (mInnerDegree < 0) mInnerDegree += 360f;
-
- canvas.save(GLCanvas.SAVE_FLAG_MATRIX);
-
- canvas.translate(x + mWidth / 2, y + mHeight / 2);
- canvas.rotate(mInnerDegree, 0, 0, 1);
- mOuter.draw(canvas, -mOuter.getWidth() / 2, -mOuter.getHeight() / 2);
- canvas.rotate(mOuterDegree - mInnerDegree, 0, 0, 1);
- mInner.draw(canvas, -mInner.getWidth() / 2, -mInner.getHeight() / 2);
- canvas.restore();
- }
-}
diff --git a/src/com/android/gallery3d/ui/RelativePosition.java b/src/com/android/gallery3d/ui/RelativePosition.java
deleted file mode 100644
index 0f2bfd812..000000000
--- a/src/com/android/gallery3d/ui/RelativePosition.java
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-public class RelativePosition {
- private float mAbsoluteX;
- private float mAbsoluteY;
- private float mReferenceX;
- private float mReferenceY;
-
- public void setAbsolutePosition(int absoluteX, int absoluteY) {
- mAbsoluteX = absoluteX;
- mAbsoluteY = absoluteY;
- }
-
- public void setReferencePosition(int x, int y) {
- mReferenceX = x;
- mReferenceY = y;
- }
-
- public float getX() {
- return mAbsoluteX - mReferenceX;
- }
-
- public float getY() {
- return mAbsoluteY - mReferenceY;
- }
-}
diff --git a/src/com/android/gallery3d/ui/ScreenNail.java b/src/com/android/gallery3d/ui/ScreenNail.java
deleted file mode 100644
index 965bf0b54..000000000
--- a/src/com/android/gallery3d/ui/ScreenNail.java
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.ui;
-
-import android.graphics.RectF;
-
-import com.android.gallery3d.glrenderer.GLCanvas;
-
-public interface ScreenNail {
- public int getWidth();
- public int getHeight();
- public void draw(GLCanvas canvas, int x, int y, int width, int height);
-
- // We do not need to draw this ScreenNail in this frame.
- public void noDraw();
-
- // This ScreenNail will not be used anymore. Release related resources.
- public void recycle();
-
- // This is only used by TileImageView to back up the tiles not yet loaded.
- public void draw(GLCanvas canvas, RectF source, RectF dest);
-}
diff --git a/src/com/android/gallery3d/ui/ScrollBarView.java b/src/com/android/gallery3d/ui/ScrollBarView.java
deleted file mode 100644
index 34fbcef7a..000000000
--- a/src/com/android/gallery3d/ui/ScrollBarView.java
+++ /dev/null
@@ -1,97 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.graphics.Rect;
-import android.util.TypedValue;
-
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.NinePatchTexture;
-
-public class ScrollBarView extends GLView {
- @SuppressWarnings("unused")
- private static final String TAG = "ScrollBarView";
-
- private int mBarHeight;
-
- private int mGripHeight;
- private int mGripPosition; // left side of the grip
- private int mGripWidth; // zero if the grip is disabled
- private int mGivenGripWidth;
-
- private int mContentPosition;
- private int mContentTotal;
-
- private NinePatchTexture mScrollBarTexture;
-
- public ScrollBarView(Context context, int gripHeight, int gripWidth) {
- TypedValue outValue = new TypedValue();
- context.getTheme().resolveAttribute(
- android.R.attr.scrollbarThumbHorizontal, outValue, true);
- mScrollBarTexture = new NinePatchTexture(
- context, outValue.resourceId);
- mGripPosition = 0;
- mGripWidth = 0;
- mGivenGripWidth = gripWidth;
- mGripHeight = gripHeight;
- }
-
- @Override
- protected void onLayout(
- boolean changed, int left, int top, int right, int bottom) {
- if (!changed) return;
- mBarHeight = bottom - top;
- }
-
- // The content position is between 0 to "total". The current position is
- // in "position".
- public void setContentPosition(int position, int total) {
- if (position == mContentPosition && total == mContentTotal) {
- return;
- }
-
- invalidate();
-
- mContentPosition = position;
- mContentTotal = total;
-
- // If the grip cannot move, don't draw it.
- if (mContentTotal <= 0) {
- mGripPosition = 0;
- mGripWidth = 0;
- return;
- }
-
- // Map from the content range to scroll bar range.
- //
- // mContentTotal --> getWidth() - mGripWidth
- // mContentPosition --> mGripPosition
- mGripWidth = mGivenGripWidth;
- float r = (getWidth() - mGripWidth) / (float) mContentTotal;
- mGripPosition = Math.round(r * mContentPosition);
- }
-
- @Override
- protected void render(GLCanvas canvas) {
- super.render(canvas);
- if (mGripWidth == 0) return;
- Rect b = bounds();
- int y = (mBarHeight - mGripHeight) / 2;
- mScrollBarTexture.draw(canvas, mGripPosition, y, mGripWidth, mGripHeight);
- }
-}
diff --git a/src/com/android/gallery3d/ui/ScrollerHelper.java b/src/com/android/gallery3d/ui/ScrollerHelper.java
deleted file mode 100644
index aa68d19d9..000000000
--- a/src/com/android/gallery3d/ui/ScrollerHelper.java
+++ /dev/null
@@ -1,97 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.view.ViewConfiguration;
-
-import com.android.gallery3d.common.OverScroller;
-import com.android.gallery3d.common.Utils;
-
-public class ScrollerHelper {
- private OverScroller mScroller;
- private int mOverflingDistance;
- private boolean mOverflingEnabled;
-
- public ScrollerHelper(Context context) {
- mScroller = new OverScroller(context);
- ViewConfiguration configuration = ViewConfiguration.get(context);
- mOverflingDistance = configuration.getScaledOverflingDistance();
- }
-
- public void setOverfling(boolean enabled) {
- mOverflingEnabled = enabled;
- }
-
- /**
- * Call this when you want to know the new location. The position will be
- * updated and can be obtained by getPosition(). Returns true if the
- * animation is not yet finished.
- */
- public boolean advanceAnimation(long currentTimeMillis) {
- return mScroller.computeScrollOffset();
- }
-
- public boolean isFinished() {
- return mScroller.isFinished();
- }
-
- public void forceFinished() {
- mScroller.forceFinished(true);
- }
-
- public int getPosition() {
- return mScroller.getCurrX();
- }
-
- public float getCurrVelocity() {
- return mScroller.getCurrVelocity();
- }
-
- public void setPosition(int position) {
- mScroller.startScroll(
- position, 0, // startX, startY
- 0, 0, 0); // dx, dy, duration
-
- // This forces the scroller to reach the final position.
- mScroller.abortAnimation();
- }
-
- public void fling(int velocity, int min, int max) {
- int currX = getPosition();
- mScroller.fling(
- currX, 0, // startX, startY
- velocity, 0, // velocityX, velocityY
- min, max, // minX, maxX
- 0, 0, // minY, maxY
- mOverflingEnabled ? mOverflingDistance : 0, 0);
- }
-
- // Returns the distance that over the scroll limit.
- public int startScroll(int distance, int min, int max) {
- int currPosition = mScroller.getCurrX();
- int finalPosition = mScroller.isFinished() ? currPosition :
- mScroller.getFinalX();
- int newPosition = Utils.clamp(finalPosition + distance, min, max);
- if (newPosition != currPosition) {
- mScroller.startScroll(
- currPosition, 0, // startX, startY
- newPosition - currPosition, 0, 0); // dx, dy, duration
- }
- return finalPosition + distance - newPosition;
- }
-}
diff --git a/src/com/android/gallery3d/ui/SelectionManager.java b/src/com/android/gallery3d/ui/SelectionManager.java
deleted file mode 100644
index be6811bc1..000000000
--- a/src/com/android/gallery3d/ui/SelectionManager.java
+++ /dev/null
@@ -1,251 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-
-import java.util.ArrayList;
-import java.util.HashSet;
-import java.util.Set;
-
-public class SelectionManager {
- @SuppressWarnings("unused")
- private static final String TAG = "SelectionManager";
-
- public static final int ENTER_SELECTION_MODE = 1;
- public static final int LEAVE_SELECTION_MODE = 2;
- public static final int SELECT_ALL_MODE = 3;
-
- private Set<Path> mClickedSet;
- private MediaSet mSourceMediaSet;
- private SelectionListener mListener;
- private DataManager mDataManager;
- private boolean mInverseSelection;
- private boolean mIsAlbumSet;
- private boolean mInSelectionMode;
- private boolean mAutoLeave = true;
- private int mTotal;
-
- public interface SelectionListener {
- public void onSelectionModeChange(int mode);
- public void onSelectionChange(Path path, boolean selected);
- }
-
- public SelectionManager(AbstractGalleryActivity activity, boolean isAlbumSet) {
- mDataManager = activity.getDataManager();
- mClickedSet = new HashSet<Path>();
- mIsAlbumSet = isAlbumSet;
- mTotal = -1;
- }
-
- // Whether we will leave selection mode automatically once the number of
- // selected items is down to zero.
- public void setAutoLeaveSelectionMode(boolean enable) {
- mAutoLeave = enable;
- }
-
- public void setSelectionListener(SelectionListener listener) {
- mListener = listener;
- }
-
- public void selectAll() {
- mInverseSelection = true;
- mClickedSet.clear();
- enterSelectionMode();
- if (mListener != null) mListener.onSelectionModeChange(SELECT_ALL_MODE);
- }
-
- public void deSelectAll() {
- leaveSelectionMode();
- mInverseSelection = false;
- mClickedSet.clear();
- }
-
- public boolean inSelectAllMode() {
- return mInverseSelection;
- }
-
- public boolean inSelectionMode() {
- return mInSelectionMode;
- }
-
- public void enterSelectionMode() {
- if (mInSelectionMode) return;
-
- mInSelectionMode = true;
- if (mListener != null) mListener.onSelectionModeChange(ENTER_SELECTION_MODE);
- }
-
- public void leaveSelectionMode() {
- if (!mInSelectionMode) return;
-
- mInSelectionMode = false;
- mInverseSelection = false;
- mClickedSet.clear();
- if (mListener != null) mListener.onSelectionModeChange(LEAVE_SELECTION_MODE);
- }
-
- public boolean isItemSelected(Path itemId) {
- return mInverseSelection ^ mClickedSet.contains(itemId);
- }
-
- private int getTotalCount() {
- if (mSourceMediaSet == null) return -1;
-
- if (mTotal < 0) {
- mTotal = mIsAlbumSet
- ? mSourceMediaSet.getSubMediaSetCount()
- : mSourceMediaSet.getMediaItemCount();
- }
- return mTotal;
- }
-
- public int getSelectedCount() {
- int count = mClickedSet.size();
- if (mInverseSelection) {
- count = getTotalCount() - count;
- }
- return count;
- }
-
- public void toggle(Path path) {
- if (mClickedSet.contains(path)) {
- mClickedSet.remove(path);
- } else {
- enterSelectionMode();
- mClickedSet.add(path);
- }
-
- // Convert to inverse selection mode if everything is selected.
- int count = getSelectedCount();
- if (count == getTotalCount()) {
- selectAll();
- }
-
- if (mListener != null) mListener.onSelectionChange(path, isItemSelected(path));
- if (count == 0 && mAutoLeave) {
- leaveSelectionMode();
- }
- }
-
- private static boolean expandMediaSet(ArrayList<Path> items, MediaSet set, int maxSelection) {
- int subCount = set.getSubMediaSetCount();
- for (int i = 0; i < subCount; i++) {
- if (!expandMediaSet(items, set.getSubMediaSet(i), maxSelection)) {
- return false;
- }
- }
- int total = set.getMediaItemCount();
- int batch = 50;
- int index = 0;
-
- while (index < total) {
- int count = index + batch < total
- ? batch
- : total - index;
- ArrayList<MediaItem> list = set.getMediaItem(index, count);
- if (list != null
- && list.size() > (maxSelection - items.size())) {
- return false;
- }
- for (MediaItem item : list) {
- items.add(item.getPath());
- }
- index += batch;
- }
- return true;
- }
-
- public ArrayList<Path> getSelected(boolean expandSet) {
- return getSelected(expandSet, Integer.MAX_VALUE);
- }
-
- public ArrayList<Path> getSelected(boolean expandSet, int maxSelection) {
- ArrayList<Path> selected = new ArrayList<Path>();
- if (mIsAlbumSet) {
- if (mInverseSelection) {
- int total = getTotalCount();
- for (int i = 0; i < total; i++) {
- MediaSet set = mSourceMediaSet.getSubMediaSet(i);
- Path id = set.getPath();
- if (!mClickedSet.contains(id)) {
- if (expandSet) {
- if (!expandMediaSet(selected, set, maxSelection)) {
- return null;
- }
- } else {
- selected.add(id);
- if (selected.size() > maxSelection) {
- return null;
- }
- }
- }
- }
- } else {
- for (Path id : mClickedSet) {
- if (expandSet) {
- if (!expandMediaSet(selected, mDataManager.getMediaSet(id),
- maxSelection)) {
- return null;
- }
- } else {
- selected.add(id);
- if (selected.size() > maxSelection) {
- return null;
- }
- }
- }
- }
- } else {
- if (mInverseSelection) {
- int total = getTotalCount();
- int index = 0;
- while (index < total) {
- int count = Math.min(total - index, MediaSet.MEDIAITEM_BATCH_FETCH_COUNT);
- ArrayList<MediaItem> list = mSourceMediaSet.getMediaItem(index, count);
- for (MediaItem item : list) {
- Path id = item.getPath();
- if (!mClickedSet.contains(id)) {
- selected.add(id);
- if (selected.size() > maxSelection) {
- return null;
- }
- }
- }
- index += count;
- }
- } else {
- for (Path id : mClickedSet) {
- selected.add(id);
- if (selected.size() > maxSelection) {
- return null;
- }
- }
- }
- }
- return selected;
- }
-
- public void setSourceMediaSet(MediaSet set) {
- mSourceMediaSet = set;
- mTotal = -1;
- }
-}
diff --git a/src/com/android/gallery3d/ui/SelectionMenu.java b/src/com/android/gallery3d/ui/SelectionMenu.java
deleted file mode 100644
index 5b0828328..000000000
--- a/src/com/android/gallery3d/ui/SelectionMenu.java
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.view.View;
-import android.view.View.OnClickListener;
-import android.widget.Button;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.ui.PopupList.OnPopupItemClickListener;
-
-public class SelectionMenu implements OnClickListener {
- @SuppressWarnings("unused")
- private static final String TAG = "SelectionMenu";
-
- private final Context mContext;
- private final Button mButton;
- private final PopupList mPopupList;
-
- public SelectionMenu(Context context, Button button, OnPopupItemClickListener listener) {
- mContext = context;
- mButton = button;
- mPopupList = new PopupList(context, mButton);
- mPopupList.addItem(R.id.action_select_all,
- context.getString(R.string.select_all));
- mPopupList.setOnPopupItemClickListener(listener);
- mButton.setOnClickListener(this);
- }
-
- @Override
- public void onClick(View v) {
- mPopupList.show();
- }
-
- public void updateSelectAllMode(boolean inSelectAllMode) {
- PopupList.Item item = mPopupList.findItem(R.id.action_select_all);
- if (item != null) {
- item.setTitle(mContext.getString(
- inSelectAllMode ? R.string.deselect_all : R.string.select_all));
- }
- }
-
- public void setTitle(CharSequence title) {
- mButton.setText(title);
- }
-}
diff --git a/src/com/android/gallery3d/ui/SlideshowView.java b/src/com/android/gallery3d/ui/SlideshowView.java
deleted file mode 100644
index 43784232d..000000000
--- a/src/com/android/gallery3d/ui/SlideshowView.java
+++ /dev/null
@@ -1,163 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.graphics.Bitmap;
-import android.graphics.PointF;
-
-import com.android.gallery3d.anim.CanvasAnimation;
-import com.android.gallery3d.anim.FloatAnimation;
-import com.android.gallery3d.glrenderer.BitmapTexture;
-import com.android.gallery3d.glrenderer.GLCanvas;
-
-import java.util.Random;
-
-public class SlideshowView extends GLView {
- @SuppressWarnings("unused")
- private static final String TAG = "SlideshowView";
-
- private static final int SLIDESHOW_DURATION = 3500;
- private static final int TRANSITION_DURATION = 1000;
-
- private static final float SCALE_SPEED = 0.20f ;
- private static final float MOVE_SPEED = SCALE_SPEED;
-
- private int mCurrentRotation;
- private BitmapTexture mCurrentTexture;
- private SlideshowAnimation mCurrentAnimation;
-
- private int mPrevRotation;
- private BitmapTexture mPrevTexture;
- private SlideshowAnimation mPrevAnimation;
-
- private final FloatAnimation mTransitionAnimation =
- new FloatAnimation(0, 1, TRANSITION_DURATION);
-
- private Random mRandom = new Random();
-
- public void next(Bitmap bitmap, int rotation) {
-
- mTransitionAnimation.start();
-
- if (mPrevTexture != null) {
- mPrevTexture.getBitmap().recycle();
- mPrevTexture.recycle();
- }
-
- mPrevTexture = mCurrentTexture;
- mPrevAnimation = mCurrentAnimation;
- mPrevRotation = mCurrentRotation;
-
- mCurrentRotation = rotation;
- mCurrentTexture = new BitmapTexture(bitmap);
- if (((rotation / 90) & 0x01) == 0) {
- mCurrentAnimation = new SlideshowAnimation(
- mCurrentTexture.getWidth(), mCurrentTexture.getHeight(),
- mRandom);
- } else {
- mCurrentAnimation = new SlideshowAnimation(
- mCurrentTexture.getHeight(), mCurrentTexture.getWidth(),
- mRandom);
- }
- mCurrentAnimation.start();
-
- invalidate();
- }
-
- public void release() {
- if (mPrevTexture != null) {
- mPrevTexture.recycle();
- mPrevTexture = null;
- }
- if (mCurrentTexture != null) {
- mCurrentTexture.recycle();
- mCurrentTexture = null;
- }
- }
-
- @Override
- protected void render(GLCanvas canvas) {
- long animTime = AnimationTime.get();
- boolean requestRender = mTransitionAnimation.calculate(animTime);
- float alpha = mPrevTexture == null ? 1f : mTransitionAnimation.get();
-
- if (mPrevTexture != null && alpha != 1f) {
- requestRender |= mPrevAnimation.calculate(animTime);
- canvas.save(GLCanvas.SAVE_FLAG_ALPHA | GLCanvas.SAVE_FLAG_MATRIX);
- canvas.setAlpha(1f - alpha);
- mPrevAnimation.apply(canvas);
- canvas.rotate(mPrevRotation, 0, 0, 1);
- mPrevTexture.draw(canvas, -mPrevTexture.getWidth() / 2,
- -mPrevTexture.getHeight() / 2);
- canvas.restore();
- }
- if (mCurrentTexture != null) {
- requestRender |= mCurrentAnimation.calculate(animTime);
- canvas.save(GLCanvas.SAVE_FLAG_ALPHA | GLCanvas.SAVE_FLAG_MATRIX);
- canvas.setAlpha(alpha);
- mCurrentAnimation.apply(canvas);
- canvas.rotate(mCurrentRotation, 0, 0, 1);
- mCurrentTexture.draw(canvas, -mCurrentTexture.getWidth() / 2,
- -mCurrentTexture.getHeight() / 2);
- canvas.restore();
- }
- if (requestRender) invalidate();
- }
-
- private class SlideshowAnimation extends CanvasAnimation {
- private final int mWidth;
- private final int mHeight;
-
- private final PointF mMovingVector;
- private float mProgress;
-
- public SlideshowAnimation(int width, int height, Random random) {
- mWidth = width;
- mHeight = height;
- mMovingVector = new PointF(
- MOVE_SPEED * mWidth * (random.nextFloat() - 0.5f),
- MOVE_SPEED * mHeight * (random.nextFloat() - 0.5f));
- setDuration(SLIDESHOW_DURATION);
- }
-
- @Override
- public void apply(GLCanvas canvas) {
- int viewWidth = getWidth();
- int viewHeight = getHeight();
-
- float initScale = Math.min((float)
- viewWidth / mWidth, (float) viewHeight / mHeight);
- float scale = initScale * (1 + SCALE_SPEED * mProgress);
-
- float centerX = viewWidth / 2 + mMovingVector.x * mProgress;
- float centerY = viewHeight / 2 + mMovingVector.y * mProgress;
-
- canvas.translate(centerX, centerY);
- canvas.scale(scale, scale, 0);
- }
-
- @Override
- public int getCanvasSaveFlags() {
- return GLCanvas.SAVE_FLAG_MATRIX;
- }
-
- @Override
- protected void onCalculate(float progress) {
- mProgress = progress;
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/SlotView.java b/src/com/android/gallery3d/ui/SlotView.java
deleted file mode 100644
index bd0ffdc15..000000000
--- a/src/com/android/gallery3d/ui/SlotView.java
+++ /dev/null
@@ -1,788 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.graphics.Rect;
-import android.os.Handler;
-import android.view.GestureDetector;
-import android.view.MotionEvent;
-import android.view.animation.DecelerateInterpolator;
-
-import com.android.gallery3d.anim.Animation;
-import com.android.gallery3d.app.AbstractGalleryActivity;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.glrenderer.GLCanvas;
-
-public class SlotView extends GLView {
- @SuppressWarnings("unused")
- private static final String TAG = "SlotView";
-
- private static final boolean WIDE = true;
- private static final int INDEX_NONE = -1;
-
- public static final int RENDER_MORE_PASS = 1;
- public static final int RENDER_MORE_FRAME = 2;
-
- public interface Listener {
- public void onDown(int index);
- public void onUp(boolean followedByLongPress);
- public void onSingleTapUp(int index);
- public void onLongTap(int index);
- public void onScrollPositionChanged(int position, int total);
- }
-
- public static class SimpleListener implements Listener {
- @Override public void onDown(int index) {}
- @Override public void onUp(boolean followedByLongPress) {}
- @Override public void onSingleTapUp(int index) {}
- @Override public void onLongTap(int index) {}
- @Override public void onScrollPositionChanged(int position, int total) {}
- }
-
- public static interface SlotRenderer {
- public void prepareDrawing();
- public void onVisibleRangeChanged(int visibleStart, int visibleEnd);
- public void onSlotSizeChanged(int width, int height);
- public int renderSlot(GLCanvas canvas, int index, int pass, int width, int height);
- }
-
- private final GestureDetector mGestureDetector;
- private final ScrollerHelper mScroller;
- private final Paper mPaper = new Paper();
-
- private Listener mListener;
- private UserInteractionListener mUIListener;
-
- private boolean mMoreAnimation = false;
- private SlotAnimation mAnimation = null;
- private final Layout mLayout = new Layout();
- private int mStartIndex = INDEX_NONE;
-
- // whether the down action happened while the view is scrolling.
- private boolean mDownInScrolling;
- private int mOverscrollEffect = OVERSCROLL_3D;
- private final Handler mHandler;
-
- private SlotRenderer mRenderer;
-
- private int[] mRequestRenderSlots = new int[16];
-
- public static final int OVERSCROLL_3D = 0;
- public static final int OVERSCROLL_SYSTEM = 1;
- public static final int OVERSCROLL_NONE = 2;
-
- // to prevent allocating memory
- private final Rect mTempRect = new Rect();
-
- public SlotView(AbstractGalleryActivity activity, Spec spec) {
- mGestureDetector = new GestureDetector(activity, new MyGestureListener());
- mScroller = new ScrollerHelper(activity);
- mHandler = new SynchronizedHandler(activity.getGLRoot());
- setSlotSpec(spec);
- }
-
- public void setSlotRenderer(SlotRenderer slotDrawer) {
- mRenderer = slotDrawer;
- if (mRenderer != null) {
- mRenderer.onSlotSizeChanged(mLayout.mSlotWidth, mLayout.mSlotHeight);
- mRenderer.onVisibleRangeChanged(getVisibleStart(), getVisibleEnd());
- }
- }
-
- public void setCenterIndex(int index) {
- int slotCount = mLayout.mSlotCount;
- if (index < 0 || index >= slotCount) {
- return;
- }
- Rect rect = mLayout.getSlotRect(index, mTempRect);
- int position = WIDE
- ? (rect.left + rect.right - getWidth()) / 2
- : (rect.top + rect.bottom - getHeight()) / 2;
- setScrollPosition(position);
- }
-
- public void makeSlotVisible(int index) {
- Rect rect = mLayout.getSlotRect(index, mTempRect);
- int visibleBegin = WIDE ? mScrollX : mScrollY;
- int visibleLength = WIDE ? getWidth() : getHeight();
- int visibleEnd = visibleBegin + visibleLength;
- int slotBegin = WIDE ? rect.left : rect.top;
- int slotEnd = WIDE ? rect.right : rect.bottom;
-
- int position = visibleBegin;
- if (visibleLength < slotEnd - slotBegin) {
- position = visibleBegin;
- } else if (slotBegin < visibleBegin) {
- position = slotBegin;
- } else if (slotEnd > visibleEnd) {
- position = slotEnd - visibleLength;
- }
-
- setScrollPosition(position);
- }
-
- public void setScrollPosition(int position) {
- position = Utils.clamp(position, 0, mLayout.getScrollLimit());
- mScroller.setPosition(position);
- updateScrollPosition(position, false);
- }
-
- public void setSlotSpec(Spec spec) {
- mLayout.setSlotSpec(spec);
- }
-
- @Override
- public void addComponent(GLView view) {
- throw new UnsupportedOperationException();
- }
-
- @Override
- protected void onLayout(boolean changeSize, int l, int t, int r, int b) {
- if (!changeSize) return;
-
- // Make sure we are still at a resonable scroll position after the size
- // is changed (like orientation change). We choose to keep the center
- // visible slot still visible. This is arbitrary but reasonable.
- int visibleIndex =
- (mLayout.getVisibleStart() + mLayout.getVisibleEnd()) / 2;
- mLayout.setSize(r - l, b - t);
- makeSlotVisible(visibleIndex);
- if (mOverscrollEffect == OVERSCROLL_3D) {
- mPaper.setSize(r - l, b - t);
- }
- }
-
- public void startScatteringAnimation(RelativePosition position) {
- mAnimation = new ScatteringAnimation(position);
- mAnimation.start();
- if (mLayout.mSlotCount != 0) invalidate();
- }
-
- public void startRisingAnimation() {
- mAnimation = new RisingAnimation();
- mAnimation.start();
- if (mLayout.mSlotCount != 0) invalidate();
- }
-
- private void updateScrollPosition(int position, boolean force) {
- if (!force && (WIDE ? position == mScrollX : position == mScrollY)) return;
- if (WIDE) {
- mScrollX = position;
- } else {
- mScrollY = position;
- }
- mLayout.setScrollPosition(position);
- onScrollPositionChanged(position);
- }
-
- protected void onScrollPositionChanged(int newPosition) {
- int limit = mLayout.getScrollLimit();
- mListener.onScrollPositionChanged(newPosition, limit);
- }
-
- public Rect getSlotRect(int slotIndex) {
- return mLayout.getSlotRect(slotIndex, new Rect());
- }
-
- @Override
- protected boolean onTouch(MotionEvent event) {
- if (mUIListener != null) mUIListener.onUserInteraction();
- mGestureDetector.onTouchEvent(event);
- switch (event.getAction()) {
- case MotionEvent.ACTION_DOWN:
- mDownInScrolling = !mScroller.isFinished();
- mScroller.forceFinished();
- break;
- case MotionEvent.ACTION_UP:
- mPaper.onRelease();
- invalidate();
- break;
- }
- return true;
- }
-
- public void setListener(Listener listener) {
- mListener = listener;
- }
-
- public void setUserInteractionListener(UserInteractionListener listener) {
- mUIListener = listener;
- }
-
- public void setOverscrollEffect(int kind) {
- mOverscrollEffect = kind;
- mScroller.setOverfling(kind == OVERSCROLL_SYSTEM);
- }
-
- private static int[] expandIntArray(int array[], int capacity) {
- while (array.length < capacity) {
- array = new int[array.length * 2];
- }
- return array;
- }
-
- @Override
- protected void render(GLCanvas canvas) {
- super.render(canvas);
-
- if (mRenderer == null) return;
- mRenderer.prepareDrawing();
-
- long animTime = AnimationTime.get();
- boolean more = mScroller.advanceAnimation(animTime);
- more |= mLayout.advanceAnimation(animTime);
- int oldX = mScrollX;
- updateScrollPosition(mScroller.getPosition(), false);
-
- boolean paperActive = false;
- if (mOverscrollEffect == OVERSCROLL_3D) {
- // Check if an edge is reached and notify mPaper if so.
- int newX = mScrollX;
- int limit = mLayout.getScrollLimit();
- if (oldX > 0 && newX == 0 || oldX < limit && newX == limit) {
- float v = mScroller.getCurrVelocity();
- if (newX == limit) v = -v;
-
- // I don't know why, but getCurrVelocity() can return NaN.
- if (!Float.isNaN(v)) {
- mPaper.edgeReached(v);
- }
- }
- paperActive = mPaper.advanceAnimation();
- }
-
- more |= paperActive;
-
- if (mAnimation != null) {
- more |= mAnimation.calculate(animTime);
- }
-
- canvas.translate(-mScrollX, -mScrollY);
-
- int requestCount = 0;
- int requestedSlot[] = expandIntArray(mRequestRenderSlots,
- mLayout.mVisibleEnd - mLayout.mVisibleStart);
-
- for (int i = mLayout.mVisibleEnd - 1; i >= mLayout.mVisibleStart; --i) {
- int r = renderItem(canvas, i, 0, paperActive);
- if ((r & RENDER_MORE_FRAME) != 0) more = true;
- if ((r & RENDER_MORE_PASS) != 0) requestedSlot[requestCount++] = i;
- }
-
- for (int pass = 1; requestCount != 0; ++pass) {
- int newCount = 0;
- for (int i = 0; i < requestCount; ++i) {
- int r = renderItem(canvas,
- requestedSlot[i], pass, paperActive);
- if ((r & RENDER_MORE_FRAME) != 0) more = true;
- if ((r & RENDER_MORE_PASS) != 0) requestedSlot[newCount++] = i;
- }
- requestCount = newCount;
- }
-
- canvas.translate(mScrollX, mScrollY);
-
- if (more) invalidate();
-
- final UserInteractionListener listener = mUIListener;
- if (mMoreAnimation && !more && listener != null) {
- mHandler.post(new Runnable() {
- @Override
- public void run() {
- listener.onUserInteractionEnd();
- }
- });
- }
- mMoreAnimation = more;
- }
-
- private int renderItem(
- GLCanvas canvas, int index, int pass, boolean paperActive) {
- canvas.save(GLCanvas.SAVE_FLAG_ALPHA | GLCanvas.SAVE_FLAG_MATRIX);
- Rect rect = mLayout.getSlotRect(index, mTempRect);
- if (paperActive) {
- canvas.multiplyMatrix(mPaper.getTransform(rect, mScrollX), 0);
- } else {
- canvas.translate(rect.left, rect.top, 0);
- }
- if (mAnimation != null && mAnimation.isActive()) {
- mAnimation.apply(canvas, index, rect);
- }
- int result = mRenderer.renderSlot(
- canvas, index, pass, rect.right - rect.left, rect.bottom - rect.top);
- canvas.restore();
- return result;
- }
-
- public static abstract class SlotAnimation extends Animation {
- protected float mProgress = 0;
-
- public SlotAnimation() {
- setInterpolator(new DecelerateInterpolator(4));
- setDuration(1500);
- }
-
- @Override
- protected void onCalculate(float progress) {
- mProgress = progress;
- }
-
- abstract public void apply(GLCanvas canvas, int slotIndex, Rect target);
- }
-
- public static class RisingAnimation extends SlotAnimation {
- private static final int RISING_DISTANCE = 128;
-
- @Override
- public void apply(GLCanvas canvas, int slotIndex, Rect target) {
- canvas.translate(0, 0, RISING_DISTANCE * (1 - mProgress));
- }
- }
-
- public static class ScatteringAnimation extends SlotAnimation {
- private int PHOTO_DISTANCE = 1000;
- private RelativePosition mCenter;
-
- public ScatteringAnimation(RelativePosition center) {
- mCenter = center;
- }
-
- @Override
- public void apply(GLCanvas canvas, int slotIndex, Rect target) {
- canvas.translate(
- (mCenter.getX() - target.centerX()) * (1 - mProgress),
- (mCenter.getY() - target.centerY()) * (1 - mProgress),
- slotIndex * PHOTO_DISTANCE * (1 - mProgress));
- canvas.setAlpha(mProgress);
- }
- }
-
- // This Spec class is used to specify the size of each slot in the SlotView.
- // There are two ways to do it:
- //
- // (1) Specify slotWidth and slotHeight: they specify the width and height
- // of each slot. The number of rows and the gap between slots will be
- // determined automatically.
- // (2) Specify rowsLand, rowsPort, and slotGap: they specify the number
- // of rows in landscape/portrait mode and the gap between slots. The
- // width and height of each slot is determined automatically.
- //
- // The initial value of -1 means they are not specified.
- public static class Spec {
- public int slotWidth = -1;
- public int slotHeight = -1;
- public int slotHeightAdditional = 0;
-
- public int rowsLand = -1;
- public int rowsPort = -1;
- public int slotGap = -1;
- }
-
- public class Layout {
-
- private int mVisibleStart;
- private int mVisibleEnd;
-
- private int mSlotCount;
- private int mSlotWidth;
- private int mSlotHeight;
- private int mSlotGap;
-
- private Spec mSpec;
-
- private int mWidth;
- private int mHeight;
-
- private int mUnitCount;
- private int mContentLength;
- private int mScrollPosition;
-
- private IntegerAnimation mVerticalPadding = new IntegerAnimation();
- private IntegerAnimation mHorizontalPadding = new IntegerAnimation();
-
- public void setSlotSpec(Spec spec) {
- mSpec = spec;
- }
-
- public boolean setSlotCount(int slotCount) {
- if (slotCount == mSlotCount) return false;
- if (mSlotCount != 0) {
- mHorizontalPadding.setEnabled(true);
- mVerticalPadding.setEnabled(true);
- }
- mSlotCount = slotCount;
- int hPadding = mHorizontalPadding.getTarget();
- int vPadding = mVerticalPadding.getTarget();
- initLayoutParameters();
- return vPadding != mVerticalPadding.getTarget()
- || hPadding != mHorizontalPadding.getTarget();
- }
-
- public Rect getSlotRect(int index, Rect rect) {
- int col, row;
- if (WIDE) {
- col = index / mUnitCount;
- row = index - col * mUnitCount;
- } else {
- row = index / mUnitCount;
- col = index - row * mUnitCount;
- }
-
- int x = mHorizontalPadding.get() + col * (mSlotWidth + mSlotGap);
- int y = mVerticalPadding.get() + row * (mSlotHeight + mSlotGap);
- rect.set(x, y, x + mSlotWidth, y + mSlotHeight);
- return rect;
- }
-
- public int getSlotWidth() {
- return mSlotWidth;
- }
-
- public int getSlotHeight() {
- return mSlotHeight;
- }
-
- // Calculate
- // (1) mUnitCount: the number of slots we can fit into one column (or row).
- // (2) mContentLength: the width (or height) we need to display all the
- // columns (rows).
- // (3) padding[]: the vertical and horizontal padding we need in order
- // to put the slots towards to the center of the display.
- //
- // The "major" direction is the direction the user can scroll. The other
- // direction is the "minor" direction.
- //
- // The comments inside this method are the description when the major
- // directon is horizontal (X), and the minor directon is vertical (Y).
- private void initLayoutParameters(
- int majorLength, int minorLength, /* The view width and height */
- int majorUnitSize, int minorUnitSize, /* The slot width and height */
- int[] padding) {
- int unitCount = (minorLength + mSlotGap) / (minorUnitSize + mSlotGap);
- if (unitCount == 0) unitCount = 1;
- mUnitCount = unitCount;
-
- // We put extra padding above and below the column.
- int availableUnits = Math.min(mUnitCount, mSlotCount);
- int usedMinorLength = availableUnits * minorUnitSize +
- (availableUnits - 1) * mSlotGap;
- padding[0] = (minorLength - usedMinorLength) / 2;
-
- // Then calculate how many columns we need for all slots.
- int count = ((mSlotCount + mUnitCount - 1) / mUnitCount);
- mContentLength = count * majorUnitSize + (count - 1) * mSlotGap;
-
- // If the content length is less then the screen width, put
- // extra padding in left and right.
- padding[1] = Math.max(0, (majorLength - mContentLength) / 2);
- }
-
- private void initLayoutParameters() {
- // Initialize mSlotWidth and mSlotHeight from mSpec
- if (mSpec.slotWidth != -1) {
- mSlotGap = 0;
- mSlotWidth = mSpec.slotWidth;
- mSlotHeight = mSpec.slotHeight;
- } else {
- int rows = (mWidth > mHeight) ? mSpec.rowsLand : mSpec.rowsPort;
- mSlotGap = mSpec.slotGap;
- mSlotHeight = Math.max(1, (mHeight - (rows - 1) * mSlotGap) / rows);
- mSlotWidth = mSlotHeight - mSpec.slotHeightAdditional;
- }
-
- if (mRenderer != null) {
- mRenderer.onSlotSizeChanged(mSlotWidth, mSlotHeight);
- }
-
- int[] padding = new int[2];
- if (WIDE) {
- initLayoutParameters(mWidth, mHeight, mSlotWidth, mSlotHeight, padding);
- mVerticalPadding.startAnimateTo(padding[0]);
- mHorizontalPadding.startAnimateTo(padding[1]);
- } else {
- initLayoutParameters(mHeight, mWidth, mSlotHeight, mSlotWidth, padding);
- mVerticalPadding.startAnimateTo(padding[1]);
- mHorizontalPadding.startAnimateTo(padding[0]);
- }
- updateVisibleSlotRange();
- }
-
- public void setSize(int width, int height) {
- mWidth = width;
- mHeight = height;
- initLayoutParameters();
- }
-
- private void updateVisibleSlotRange() {
- int position = mScrollPosition;
-
- if (WIDE) {
- int startCol = position / (mSlotWidth + mSlotGap);
- int start = Math.max(0, mUnitCount * startCol);
- int endCol = (position + mWidth + mSlotWidth + mSlotGap - 1) /
- (mSlotWidth + mSlotGap);
- int end = Math.min(mSlotCount, mUnitCount * endCol);
- setVisibleRange(start, end);
- } else {
- int startRow = position / (mSlotHeight + mSlotGap);
- int start = Math.max(0, mUnitCount * startRow);
- int endRow = (position + mHeight + mSlotHeight + mSlotGap - 1) /
- (mSlotHeight + mSlotGap);
- int end = Math.min(mSlotCount, mUnitCount * endRow);
- setVisibleRange(start, end);
- }
- }
-
- public void setScrollPosition(int position) {
- if (mScrollPosition == position) return;
- mScrollPosition = position;
- updateVisibleSlotRange();
- }
-
- private void setVisibleRange(int start, int end) {
- if (start == mVisibleStart && end == mVisibleEnd) return;
- if (start < end) {
- mVisibleStart = start;
- mVisibleEnd = end;
- } else {
- mVisibleStart = mVisibleEnd = 0;
- }
- if (mRenderer != null) {
- mRenderer.onVisibleRangeChanged(mVisibleStart, mVisibleEnd);
- }
- }
-
- public int getVisibleStart() {
- return mVisibleStart;
- }
-
- public int getVisibleEnd() {
- return mVisibleEnd;
- }
-
- public int getSlotIndexByPosition(float x, float y) {
- int absoluteX = Math.round(x) + (WIDE ? mScrollPosition : 0);
- int absoluteY = Math.round(y) + (WIDE ? 0 : mScrollPosition);
-
- absoluteX -= mHorizontalPadding.get();
- absoluteY -= mVerticalPadding.get();
-
- if (absoluteX < 0 || absoluteY < 0) {
- return INDEX_NONE;
- }
-
- int columnIdx = absoluteX / (mSlotWidth + mSlotGap);
- int rowIdx = absoluteY / (mSlotHeight + mSlotGap);
-
- if (!WIDE && columnIdx >= mUnitCount) {
- return INDEX_NONE;
- }
-
- if (WIDE && rowIdx >= mUnitCount) {
- return INDEX_NONE;
- }
-
- if (absoluteX % (mSlotWidth + mSlotGap) >= mSlotWidth) {
- return INDEX_NONE;
- }
-
- if (absoluteY % (mSlotHeight + mSlotGap) >= mSlotHeight) {
- return INDEX_NONE;
- }
-
- int index = WIDE
- ? (columnIdx * mUnitCount + rowIdx)
- : (rowIdx * mUnitCount + columnIdx);
-
- return index >= mSlotCount ? INDEX_NONE : index;
- }
-
- public int getScrollLimit() {
- int limit = WIDE ? mContentLength - mWidth : mContentLength - mHeight;
- return limit <= 0 ? 0 : limit;
- }
-
- public boolean advanceAnimation(long animTime) {
- // use '|' to make sure both sides will be executed
- return mVerticalPadding.calculate(animTime) | mHorizontalPadding.calculate(animTime);
- }
- }
-
- private class MyGestureListener implements GestureDetector.OnGestureListener {
- private boolean isDown;
-
- // We call the listener's onDown() when our onShowPress() is called and
- // call the listener's onUp() when we receive any further event.
- @Override
- public void onShowPress(MotionEvent e) {
- GLRoot root = getGLRoot();
- root.lockRenderThread();
- try {
- if (isDown) return;
- int index = mLayout.getSlotIndexByPosition(e.getX(), e.getY());
- if (index != INDEX_NONE) {
- isDown = true;
- mListener.onDown(index);
- }
- } finally {
- root.unlockRenderThread();
- }
- }
-
- private void cancelDown(boolean byLongPress) {
- if (!isDown) return;
- isDown = false;
- mListener.onUp(byLongPress);
- }
-
- @Override
- public boolean onDown(MotionEvent e) {
- return false;
- }
-
- @Override
- public boolean onFling(MotionEvent e1,
- MotionEvent e2, float velocityX, float velocityY) {
- cancelDown(false);
- int scrollLimit = mLayout.getScrollLimit();
- if (scrollLimit == 0) return false;
- float velocity = WIDE ? velocityX : velocityY;
- mScroller.fling((int) -velocity, 0, scrollLimit);
- if (mUIListener != null) mUIListener.onUserInteractionBegin();
- invalidate();
- return true;
- }
-
- @Override
- public boolean onScroll(MotionEvent e1,
- MotionEvent e2, float distanceX, float distanceY) {
- cancelDown(false);
- float distance = WIDE ? distanceX : distanceY;
- int overDistance = mScroller.startScroll(
- Math.round(distance), 0, mLayout.getScrollLimit());
- if (mOverscrollEffect == OVERSCROLL_3D && overDistance != 0) {
- mPaper.overScroll(overDistance);
- }
- invalidate();
- return true;
- }
-
- @Override
- public boolean onSingleTapUp(MotionEvent e) {
- cancelDown(false);
- if (mDownInScrolling) return true;
- int index = mLayout.getSlotIndexByPosition(e.getX(), e.getY());
- if (index != INDEX_NONE) mListener.onSingleTapUp(index);
- return true;
- }
-
- @Override
- public void onLongPress(MotionEvent e) {
- cancelDown(true);
- if (mDownInScrolling) return;
- lockRendering();
- try {
- int index = mLayout.getSlotIndexByPosition(e.getX(), e.getY());
- if (index != INDEX_NONE) mListener.onLongTap(index);
- } finally {
- unlockRendering();
- }
- }
- }
-
- public void setStartIndex(int index) {
- mStartIndex = index;
- }
-
- // Return true if the layout parameters have been changed
- public boolean setSlotCount(int slotCount) {
- boolean changed = mLayout.setSlotCount(slotCount);
-
- // mStartIndex is applied the first time setSlotCount is called.
- if (mStartIndex != INDEX_NONE) {
- setCenterIndex(mStartIndex);
- mStartIndex = INDEX_NONE;
- }
- // Reset the scroll position to avoid scrolling over the updated limit.
- setScrollPosition(WIDE ? mScrollX : mScrollY);
- return changed;
- }
-
- public int getVisibleStart() {
- return mLayout.getVisibleStart();
- }
-
- public int getVisibleEnd() {
- return mLayout.getVisibleEnd();
- }
-
- public int getScrollX() {
- return mScrollX;
- }
-
- public int getScrollY() {
- return mScrollY;
- }
-
- public Rect getSlotRect(int slotIndex, GLView rootPane) {
- // Get slot rectangle relative to this root pane.
- Rect offset = new Rect();
- rootPane.getBoundsOf(this, offset);
- Rect r = getSlotRect(slotIndex);
- r.offset(offset.left - getScrollX(),
- offset.top - getScrollY());
- return r;
- }
-
- private static class IntegerAnimation extends Animation {
- private int mTarget;
- private int mCurrent = 0;
- private int mFrom = 0;
- private boolean mEnabled = false;
-
- public void setEnabled(boolean enabled) {
- mEnabled = enabled;
- }
-
- public void startAnimateTo(int target) {
- if (!mEnabled) {
- mTarget = mCurrent = target;
- return;
- }
- if (target == mTarget) return;
-
- mFrom = mCurrent;
- mTarget = target;
- setDuration(180);
- start();
- }
-
- public int get() {
- return mCurrent;
- }
-
- public int getTarget() {
- return mTarget;
- }
-
- @Override
- protected void onCalculate(float progress) {
- mCurrent = Math.round(mFrom + progress * (mTarget - mFrom));
- if (progress == 1f) mEnabled = false;
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/SurfaceTextureScreenNail.java b/src/com/android/gallery3d/ui/SurfaceTextureScreenNail.java
deleted file mode 100644
index 18121e63b..000000000
--- a/src/com/android/gallery3d/ui/SurfaceTextureScreenNail.java
+++ /dev/null
@@ -1,142 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.annotation.TargetApi;
-import android.graphics.RectF;
-import android.graphics.SurfaceTexture;
-
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.glrenderer.ExtTexture;
-import com.android.gallery3d.glrenderer.GLCanvas;
-
-@TargetApi(ApiHelper.VERSION_CODES.HONEYCOMB)
-public abstract class SurfaceTextureScreenNail implements ScreenNail,
- SurfaceTexture.OnFrameAvailableListener {
- @SuppressWarnings("unused")
- private static final String TAG = "SurfaceTextureScreenNail";
- // This constant is not available in API level before 15, but it was just an
- // oversight.
- private static final int GL_TEXTURE_EXTERNAL_OES = 0x8D65;
-
- protected ExtTexture mExtTexture;
- private SurfaceTexture mSurfaceTexture;
- private int mWidth, mHeight;
- private float[] mTransform = new float[16];
- private boolean mHasTexture = false;
-
- public SurfaceTextureScreenNail() {
- }
-
- public void acquireSurfaceTexture(GLCanvas canvas) {
- mExtTexture = new ExtTexture(canvas, GL_TEXTURE_EXTERNAL_OES);
- mExtTexture.setSize(mWidth, mHeight);
- mSurfaceTexture = new SurfaceTexture(mExtTexture.getId());
- setDefaultBufferSize(mSurfaceTexture, mWidth, mHeight);
- mSurfaceTexture.setOnFrameAvailableListener(this);
- synchronized (this) {
- mHasTexture = true;
- }
- }
-
- @TargetApi(ApiHelper.VERSION_CODES.ICE_CREAM_SANDWICH_MR1)
- private static void setDefaultBufferSize(SurfaceTexture st, int width, int height) {
- if (ApiHelper.HAS_SET_DEFALT_BUFFER_SIZE) {
- st.setDefaultBufferSize(width, height);
- }
- }
-
- @TargetApi(ApiHelper.VERSION_CODES.ICE_CREAM_SANDWICH)
- private static void releaseSurfaceTexture(SurfaceTexture st) {
- st.setOnFrameAvailableListener(null);
- if (ApiHelper.HAS_RELEASE_SURFACE_TEXTURE) {
- st.release();
- }
- }
-
- public SurfaceTexture getSurfaceTexture() {
- return mSurfaceTexture;
- }
-
- public void releaseSurfaceTexture() {
- synchronized (this) {
- mHasTexture = false;
- }
- mExtTexture.recycle();
- mExtTexture = null;
- releaseSurfaceTexture(mSurfaceTexture);
- mSurfaceTexture = null;
- }
-
- public void setSize(int width, int height) {
- mWidth = width;
- mHeight = height;
- }
-
- public void resizeTexture() {
- if (mExtTexture != null) {
- mExtTexture.setSize(mWidth, mHeight);
- setDefaultBufferSize(mSurfaceTexture, mWidth, mHeight);
- }
- }
-
- @Override
- public int getWidth() {
- return mWidth;
- }
-
- @Override
- public int getHeight() {
- return mHeight;
- }
-
- @Override
- public void draw(GLCanvas canvas, int x, int y, int width, int height) {
- synchronized (this) {
- if (!mHasTexture) return;
- mSurfaceTexture.updateTexImage();
- mSurfaceTexture.getTransformMatrix(mTransform);
-
- // Flip vertically.
- canvas.save(GLCanvas.SAVE_FLAG_MATRIX);
- int cx = x + width / 2;
- int cy = y + height / 2;
- canvas.translate(cx, cy);
- canvas.scale(1, -1, 1);
- canvas.translate(-cx, -cy);
- updateTransformMatrix(mTransform);
- canvas.drawTexture(mExtTexture, mTransform, x, y, width, height);
- canvas.restore();
- }
- }
-
- @Override
- public void draw(GLCanvas canvas, RectF source, RectF dest) {
- throw new UnsupportedOperationException();
- }
-
- protected void updateTransformMatrix(float[] matrix) {}
-
- @Override
- abstract public void noDraw();
-
- @Override
- abstract public void recycle();
-
- @Override
- abstract public void onFrameAvailable(SurfaceTexture surfaceTexture);
-}
diff --git a/src/com/android/gallery3d/ui/SynchronizedHandler.java b/src/com/android/gallery3d/ui/SynchronizedHandler.java
deleted file mode 100644
index ba1035747..000000000
--- a/src/com/android/gallery3d/ui/SynchronizedHandler.java
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.os.Handler;
-import android.os.Message;
-
-import com.android.gallery3d.common.Utils;
-
-public class SynchronizedHandler extends Handler {
-
- private final GLRoot mRoot;
-
- public SynchronizedHandler(GLRoot root) {
- mRoot = Utils.checkNotNull(root);
- }
-
- @Override
- public void dispatchMessage(Message message) {
- mRoot.lockRenderThread();
- try {
- super.dispatchMessage(message);
- } finally {
- mRoot.unlockRenderThread();
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/TileImageView.java b/src/com/android/gallery3d/ui/TileImageView.java
deleted file mode 100644
index 3185c7598..000000000
--- a/src/com/android/gallery3d/ui/TileImageView.java
+++ /dev/null
@@ -1,786 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.graphics.Bitmap;
-import android.graphics.Point;
-import android.graphics.Rect;
-import android.graphics.RectF;
-import android.support.v4.util.LongSparseArray;
-import android.util.DisplayMetrics;
-import android.util.FloatMath;
-import android.view.WindowManager;
-
-import com.android.gallery3d.app.GalleryContext;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.data.DecodeUtils;
-import com.android.photos.data.GalleryBitmapPool;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.UploadedTexture;
-import com.android.gallery3d.util.Future;
-import com.android.gallery3d.util.ThreadPool;
-import com.android.gallery3d.util.ThreadPool.CancelListener;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.util.concurrent.atomic.AtomicBoolean;
-
-public class TileImageView extends GLView {
- public static final int SIZE_UNKNOWN = -1;
-
- @SuppressWarnings("unused")
- private static final String TAG = "TileImageView";
- private static final int UPLOAD_LIMIT = 1;
-
- // TILE_SIZE must be 2^N
- private static int sTileSize;
-
- /*
- * This is the tile state in the CPU side.
- * Life of a Tile:
- * ACTIVATED (initial state)
- * --> IN_QUEUE - by queueForDecode()
- * --> RECYCLED - by recycleTile()
- * IN_QUEUE --> DECODING - by decodeTile()
- * --> RECYCLED - by recycleTile)
- * DECODING --> RECYCLING - by recycleTile()
- * --> DECODED - by decodeTile()
- * --> DECODE_FAIL - by decodeTile()
- * RECYCLING --> RECYCLED - by decodeTile()
- * DECODED --> ACTIVATED - (after the decoded bitmap is uploaded)
- * DECODED --> RECYCLED - by recycleTile()
- * DECODE_FAIL -> RECYCLED - by recycleTile()
- * RECYCLED --> ACTIVATED - by obtainTile()
- */
- private static final int STATE_ACTIVATED = 0x01;
- private static final int STATE_IN_QUEUE = 0x02;
- private static final int STATE_DECODING = 0x04;
- private static final int STATE_DECODED = 0x08;
- private static final int STATE_DECODE_FAIL = 0x10;
- private static final int STATE_RECYCLING = 0x20;
- private static final int STATE_RECYCLED = 0x40;
-
- private TileSource mModel;
- private ScreenNail mScreenNail;
- protected int mLevelCount; // cache the value of mScaledBitmaps.length
-
- // The mLevel variable indicates which level of bitmap we should use.
- // Level 0 means the original full-sized bitmap, and a larger value means
- // a smaller scaled bitmap (The width and height of each scaled bitmap is
- // half size of the previous one). If the value is in [0, mLevelCount), we
- // use the bitmap in mScaledBitmaps[mLevel] for display, otherwise the value
- // is mLevelCount, and that means we use mScreenNail for display.
- private int mLevel = 0;
-
- // The offsets of the (left, top) of the upper-left tile to the (left, top)
- // of the view.
- private int mOffsetX;
- private int mOffsetY;
-
- private int mUploadQuota;
- private boolean mRenderComplete;
-
- private final RectF mSourceRect = new RectF();
- private final RectF mTargetRect = new RectF();
-
- private final LongSparseArray<Tile> mActiveTiles = new LongSparseArray<Tile>();
-
- // The following three queue is guarded by TileImageView.this
- private final TileQueue mRecycledQueue = new TileQueue();
- private final TileQueue mUploadQueue = new TileQueue();
- private final TileQueue mDecodeQueue = new TileQueue();
-
- // The width and height of the full-sized bitmap
- protected int mImageWidth = SIZE_UNKNOWN;
- protected int mImageHeight = SIZE_UNKNOWN;
-
- protected int mCenterX;
- protected int mCenterY;
- protected float mScale;
- protected int mRotation;
-
- // Temp variables to avoid memory allocation
- private final Rect mTileRange = new Rect();
- private final Rect mActiveRange[] = {new Rect(), new Rect()};
-
- private final TileUploader mTileUploader = new TileUploader();
- private boolean mIsTextureFreed;
- private Future<Void> mTileDecoder;
- private final ThreadPool mThreadPool;
- private boolean mBackgroundTileUploaded;
-
- public static interface TileSource {
- public int getLevelCount();
- public ScreenNail getScreenNail();
- public int getImageWidth();
- public int getImageHeight();
-
- // The tile returned by this method can be specified this way: Assuming
- // the image size is (width, height), first take the intersection of (0,
- // 0) - (width, height) and (x, y) - (x + tileSize, y + tileSize). If
- // in extending the region, we found some part of the region are outside
- // the image, those pixels are filled with black.
- //
- // If level > 0, it does the same operation on a down-scaled version of
- // the original image (down-scaled by a factor of 2^level), but (x, y)
- // still refers to the coordinate on the original image.
- //
- // The method would be called in another thread.
- public Bitmap getTile(int level, int x, int y, int tileSize);
- }
-
- public static boolean isHighResolution(Context context) {
- DisplayMetrics metrics = new DisplayMetrics();
- WindowManager wm = (WindowManager)
- context.getSystemService(Context.WINDOW_SERVICE);
- wm.getDefaultDisplay().getMetrics(metrics);
- return metrics.heightPixels > 2048 || metrics.widthPixels > 2048;
- }
-
- public TileImageView(GalleryContext context) {
- mThreadPool = context.getThreadPool();
- mTileDecoder = mThreadPool.submit(new TileDecoder());
- if (sTileSize == 0) {
- if (isHighResolution(context.getAndroidContext())) {
- sTileSize = 512 ;
- } else {
- sTileSize = 256;
- }
- }
- }
-
- public void setModel(TileSource model) {
- mModel = model;
- if (model != null) notifyModelInvalidated();
- }
-
- public void setScreenNail(ScreenNail s) {
- mScreenNail = s;
- }
-
- public void notifyModelInvalidated() {
- invalidateTiles();
- if (mModel == null) {
- mScreenNail = null;
- mImageWidth = 0;
- mImageHeight = 0;
- mLevelCount = 0;
- } else {
- setScreenNail(mModel.getScreenNail());
- mImageWidth = mModel.getImageWidth();
- mImageHeight = mModel.getImageHeight();
- mLevelCount = mModel.getLevelCount();
- }
- layoutTiles(mCenterX, mCenterY, mScale, mRotation);
- invalidate();
- }
-
- @Override
- protected void onLayout(
- boolean changeSize, int left, int top, int right, int bottom) {
- super.onLayout(changeSize, left, top, right, bottom);
- if (changeSize) layoutTiles(mCenterX, mCenterY, mScale, mRotation);
- }
-
- // Prepare the tiles we want to use for display.
- //
- // 1. Decide the tile level we want to use for display.
- // 2. Decide the tile levels we want to keep as texture (in addition to
- // the one we use for display).
- // 3. Recycle unused tiles.
- // 4. Activate the tiles we want.
- private void layoutTiles(int centerX, int centerY, float scale, int rotation) {
- // The width and height of this view.
- int width = getWidth();
- int height = getHeight();
-
- // The tile levels we want to keep as texture is in the range
- // [fromLevel, endLevel).
- int fromLevel;
- int endLevel;
-
- // We want to use a texture larger than or equal to the display size.
- mLevel = Utils.clamp(Utils.floorLog2(1f / scale), 0, mLevelCount);
-
- // We want to keep one more tile level as texture in addition to what
- // we use for display. So it can be faster when the scale moves to the
- // next level. We choose a level closer to the current scale.
- if (mLevel != mLevelCount) {
- Rect range = mTileRange;
- getRange(range, centerX, centerY, mLevel, scale, rotation);
- mOffsetX = Math.round(width / 2f + (range.left - centerX) * scale);
- mOffsetY = Math.round(height / 2f + (range.top - centerY) * scale);
- fromLevel = scale * (1 << mLevel) > 0.75f ? mLevel - 1 : mLevel;
- } else {
- // Activate the tiles of the smallest two levels.
- fromLevel = mLevel - 2;
- mOffsetX = Math.round(width / 2f - centerX * scale);
- mOffsetY = Math.round(height / 2f - centerY * scale);
- }
-
- fromLevel = Math.max(0, Math.min(fromLevel, mLevelCount - 2));
- endLevel = Math.min(fromLevel + 2, mLevelCount);
-
- Rect range[] = mActiveRange;
- for (int i = fromLevel; i < endLevel; ++i) {
- getRange(range[i - fromLevel], centerX, centerY, i, rotation);
- }
-
- // If rotation is transient, don't update the tile.
- if (rotation % 90 != 0) return;
-
- synchronized (this) {
- mDecodeQueue.clean();
- mUploadQueue.clean();
- mBackgroundTileUploaded = false;
-
- // Recycle unused tiles: if the level of the active tile is outside the
- // range [fromLevel, endLevel) or not in the visible range.
- int n = mActiveTiles.size();
- for (int i = 0; i < n; i++) {
- Tile tile = mActiveTiles.valueAt(i);
- int level = tile.mTileLevel;
- if (level < fromLevel || level >= endLevel
- || !range[level - fromLevel].contains(tile.mX, tile.mY)) {
- mActiveTiles.removeAt(i);
- i--;
- n--;
- recycleTile(tile);
- }
- }
- }
-
- for (int i = fromLevel; i < endLevel; ++i) {
- int size = sTileSize << i;
- Rect r = range[i - fromLevel];
- for (int y = r.top, bottom = r.bottom; y < bottom; y += size) {
- for (int x = r.left, right = r.right; x < right; x += size) {
- activateTile(x, y, i);
- }
- }
- }
- invalidate();
- }
-
- protected synchronized void invalidateTiles() {
- mDecodeQueue.clean();
- mUploadQueue.clean();
-
- // TODO disable decoder
- int n = mActiveTiles.size();
- for (int i = 0; i < n; i++) {
- Tile tile = mActiveTiles.valueAt(i);
- recycleTile(tile);
- }
- mActiveTiles.clear();
- }
-
- private void getRange(Rect out, int cX, int cY, int level, int rotation) {
- getRange(out, cX, cY, level, 1f / (1 << (level + 1)), rotation);
- }
-
- // If the bitmap is scaled by the given factor "scale", return the
- // rectangle containing visible range. The left-top coordinate returned is
- // aligned to the tile boundary.
- //
- // (cX, cY) is the point on the original bitmap which will be put in the
- // center of the ImageViewer.
- private void getRange(Rect out,
- int cX, int cY, int level, float scale, int rotation) {
-
- double radians = Math.toRadians(-rotation);
- double w = getWidth();
- double h = getHeight();
-
- double cos = Math.cos(radians);
- double sin = Math.sin(radians);
- int width = (int) Math.ceil(Math.max(
- Math.abs(cos * w - sin * h), Math.abs(cos * w + sin * h)));
- int height = (int) Math.ceil(Math.max(
- Math.abs(sin * w + cos * h), Math.abs(sin * w - cos * h)));
-
- int left = (int) FloatMath.floor(cX - width / (2f * scale));
- int top = (int) FloatMath.floor(cY - height / (2f * scale));
- int right = (int) FloatMath.ceil(left + width / scale);
- int bottom = (int) FloatMath.ceil(top + height / scale);
-
- // align the rectangle to tile boundary
- int size = sTileSize << level;
- left = Math.max(0, size * (left / size));
- top = Math.max(0, size * (top / size));
- right = Math.min(mImageWidth, right);
- bottom = Math.min(mImageHeight, bottom);
-
- out.set(left, top, right, bottom);
- }
-
- // Calculate where the center of the image is, in the view coordinates.
- public void getImageCenter(Point center) {
- // The width and height of this view.
- int viewW = getWidth();
- int viewH = getHeight();
-
- // The distance between the center of the view to the center of the
- // bitmap, in bitmap units. (mCenterX and mCenterY are the bitmap
- // coordinates correspond to the center of view)
- int distW, distH;
- if (mRotation % 180 == 0) {
- distW = mImageWidth / 2 - mCenterX;
- distH = mImageHeight / 2 - mCenterY;
- } else {
- distW = mImageHeight / 2 - mCenterY;
- distH = mImageWidth / 2 - mCenterX;
- }
-
- // Convert to view coordinates. mScale translates from bitmap units to
- // view units.
- center.x = Math.round(viewW / 2f + distW * mScale);
- center.y = Math.round(viewH / 2f + distH * mScale);
- }
-
- public boolean setPosition(int centerX, int centerY, float scale, int rotation) {
- if (mCenterX == centerX && mCenterY == centerY
- && mScale == scale && mRotation == rotation) return false;
- mCenterX = centerX;
- mCenterY = centerY;
- mScale = scale;
- mRotation = rotation;
- layoutTiles(centerX, centerY, scale, rotation);
- invalidate();
- return true;
- }
-
- public void freeTextures() {
- mIsTextureFreed = true;
-
- if (mTileDecoder != null) {
- mTileDecoder.cancel();
- mTileDecoder.get();
- mTileDecoder = null;
- }
-
- int n = mActiveTiles.size();
- for (int i = 0; i < n; i++) {
- Tile texture = mActiveTiles.valueAt(i);
- texture.recycle();
- }
- mActiveTiles.clear();
- mTileRange.set(0, 0, 0, 0);
-
- synchronized (this) {
- mUploadQueue.clean();
- mDecodeQueue.clean();
- Tile tile = mRecycledQueue.pop();
- while (tile != null) {
- tile.recycle();
- tile = mRecycledQueue.pop();
- }
- }
- setScreenNail(null);
- }
-
- public void prepareTextures() {
- if (mTileDecoder == null) {
- mTileDecoder = mThreadPool.submit(new TileDecoder());
- }
- if (mIsTextureFreed) {
- layoutTiles(mCenterX, mCenterY, mScale, mRotation);
- mIsTextureFreed = false;
- setScreenNail(mModel == null ? null : mModel.getScreenNail());
- }
- }
-
- @Override
- protected void render(GLCanvas canvas) {
- mUploadQuota = UPLOAD_LIMIT;
- mRenderComplete = true;
-
- int level = mLevel;
- int rotation = mRotation;
- int flags = 0;
- if (rotation != 0) flags |= GLCanvas.SAVE_FLAG_MATRIX;
-
- if (flags != 0) {
- canvas.save(flags);
- if (rotation != 0) {
- int centerX = getWidth() / 2, centerY = getHeight() / 2;
- canvas.translate(centerX, centerY);
- canvas.rotate(rotation, 0, 0, 1);
- canvas.translate(-centerX, -centerY);
- }
- }
- try {
- if (level != mLevelCount && !isScreenNailAnimating()) {
- if (mScreenNail != null) {
- mScreenNail.noDraw();
- }
-
- int size = (sTileSize << level);
- float length = size * mScale;
- Rect r = mTileRange;
-
- for (int ty = r.top, i = 0; ty < r.bottom; ty += size, i++) {
- float y = mOffsetY + i * length;
- for (int tx = r.left, j = 0; tx < r.right; tx += size, j++) {
- float x = mOffsetX + j * length;
- drawTile(canvas, tx, ty, level, x, y, length);
- }
- }
- } else if (mScreenNail != null) {
- mScreenNail.draw(canvas, mOffsetX, mOffsetY,
- Math.round(mImageWidth * mScale),
- Math.round(mImageHeight * mScale));
- if (isScreenNailAnimating()) {
- invalidate();
- }
- }
- } finally {
- if (flags != 0) canvas.restore();
- }
-
- if (mRenderComplete) {
- if (!mBackgroundTileUploaded) uploadBackgroundTiles(canvas);
- } else {
- invalidate();
- }
- }
-
- private boolean isScreenNailAnimating() {
- return (mScreenNail instanceof TiledScreenNail)
- && ((TiledScreenNail) mScreenNail).isAnimating();
- }
-
- private void uploadBackgroundTiles(GLCanvas canvas) {
- mBackgroundTileUploaded = true;
- int n = mActiveTiles.size();
- for (int i = 0; i < n; i++) {
- Tile tile = mActiveTiles.valueAt(i);
- if (!tile.isContentValid()) queueForDecode(tile);
- }
- }
-
- void queueForUpload(Tile tile) {
- synchronized (this) {
- mUploadQueue.push(tile);
- }
- if (mTileUploader.mActive.compareAndSet(false, true)) {
- getGLRoot().addOnGLIdleListener(mTileUploader);
- }
- }
-
- synchronized void queueForDecode(Tile tile) {
- if (tile.mTileState == STATE_ACTIVATED) {
- tile.mTileState = STATE_IN_QUEUE;
- if (mDecodeQueue.push(tile)) notifyAll();
- }
- }
-
- boolean decodeTile(Tile tile) {
- synchronized (this) {
- if (tile.mTileState != STATE_IN_QUEUE) return false;
- tile.mTileState = STATE_DECODING;
- }
- boolean decodeComplete = tile.decode();
- synchronized (this) {
- if (tile.mTileState == STATE_RECYCLING) {
- tile.mTileState = STATE_RECYCLED;
- if (tile.mDecodedTile != null) {
- GalleryBitmapPool.getInstance().put(tile.mDecodedTile);
- tile.mDecodedTile = null;
- }
- mRecycledQueue.push(tile);
- return false;
- }
- tile.mTileState = decodeComplete ? STATE_DECODED : STATE_DECODE_FAIL;
- return decodeComplete;
- }
- }
-
- private synchronized Tile obtainTile(int x, int y, int level) {
- Tile tile = mRecycledQueue.pop();
- if (tile != null) {
- tile.mTileState = STATE_ACTIVATED;
- tile.update(x, y, level);
- return tile;
- }
- return new Tile(x, y, level);
- }
-
- synchronized void recycleTile(Tile tile) {
- if (tile.mTileState == STATE_DECODING) {
- tile.mTileState = STATE_RECYCLING;
- return;
- }
- tile.mTileState = STATE_RECYCLED;
- if (tile.mDecodedTile != null) {
- GalleryBitmapPool.getInstance().put(tile.mDecodedTile);
- tile.mDecodedTile = null;
- }
- mRecycledQueue.push(tile);
- }
-
- private void activateTile(int x, int y, int level) {
- long key = makeTileKey(x, y, level);
- Tile tile = mActiveTiles.get(key);
- if (tile != null) {
- if (tile.mTileState == STATE_IN_QUEUE) {
- tile.mTileState = STATE_ACTIVATED;
- }
- return;
- }
- tile = obtainTile(x, y, level);
- mActiveTiles.put(key, tile);
- }
-
- private Tile getTile(int x, int y, int level) {
- return mActiveTiles.get(makeTileKey(x, y, level));
- }
-
- private static long makeTileKey(int x, int y, int level) {
- long result = x;
- result = (result << 16) | y;
- result = (result << 16) | level;
- return result;
- }
-
- private class TileUploader implements GLRoot.OnGLIdleListener {
- AtomicBoolean mActive = new AtomicBoolean(false);
-
- @Override
- public boolean onGLIdle(GLCanvas canvas, boolean renderRequested) {
- // Skips uploading if there is a pending rendering request.
- // Returns true to keep uploading in next rendering loop.
- if (renderRequested) return true;
- int quota = UPLOAD_LIMIT;
- Tile tile = null;
- while (quota > 0) {
- synchronized (TileImageView.this) {
- tile = mUploadQueue.pop();
- }
- if (tile == null) break;
- if (!tile.isContentValid()) {
- boolean hasBeenLoaded = tile.isLoaded();
- Utils.assertTrue(tile.mTileState == STATE_DECODED);
- tile.updateContent(canvas);
- if (!hasBeenLoaded) tile.draw(canvas, 0, 0);
- --quota;
- }
- }
- if (tile == null) mActive.set(false);
- return tile != null;
- }
- }
-
- // Draw the tile to a square at canvas that locates at (x, y) and
- // has a side length of length.
- public void drawTile(GLCanvas canvas,
- int tx, int ty, int level, float x, float y, float length) {
- RectF source = mSourceRect;
- RectF target = mTargetRect;
- target.set(x, y, x + length, y + length);
- source.set(0, 0, sTileSize, sTileSize);
-
- Tile tile = getTile(tx, ty, level);
- if (tile != null) {
- if (!tile.isContentValid()) {
- if (tile.mTileState == STATE_DECODED) {
- if (mUploadQuota > 0) {
- --mUploadQuota;
- tile.updateContent(canvas);
- } else {
- mRenderComplete = false;
- }
- } else if (tile.mTileState != STATE_DECODE_FAIL){
- mRenderComplete = false;
- queueForDecode(tile);
- }
- }
- if (drawTile(tile, canvas, source, target)) return;
- }
- if (mScreenNail != null) {
- int size = sTileSize << level;
- float scaleX = (float) mScreenNail.getWidth() / mImageWidth;
- float scaleY = (float) mScreenNail.getHeight() / mImageHeight;
- source.set(tx * scaleX, ty * scaleY, (tx + size) * scaleX,
- (ty + size) * scaleY);
- mScreenNail.draw(canvas, source, target);
- }
- }
-
- static boolean drawTile(
- Tile tile, GLCanvas canvas, RectF source, RectF target) {
- while (true) {
- if (tile.isContentValid()) {
- canvas.drawTexture(tile, source, target);
- return true;
- }
-
- // Parent can be divided to four quads and tile is one of the four.
- Tile parent = tile.getParentTile();
- if (parent == null) return false;
- if (tile.mX == parent.mX) {
- source.left /= 2f;
- source.right /= 2f;
- } else {
- source.left = (sTileSize + source.left) / 2f;
- source.right = (sTileSize + source.right) / 2f;
- }
- if (tile.mY == parent.mY) {
- source.top /= 2f;
- source.bottom /= 2f;
- } else {
- source.top = (sTileSize + source.top) / 2f;
- source.bottom = (sTileSize + source.bottom) / 2f;
- }
- tile = parent;
- }
- }
-
- private class Tile extends UploadedTexture {
- public int mX;
- public int mY;
- public int mTileLevel;
- public Tile mNext;
- public Bitmap mDecodedTile;
- public volatile int mTileState = STATE_ACTIVATED;
-
- public Tile(int x, int y, int level) {
- mX = x;
- mY = y;
- mTileLevel = level;
- }
-
- @Override
- protected void onFreeBitmap(Bitmap bitmap) {
- GalleryBitmapPool.getInstance().put(bitmap);
- }
-
- boolean decode() {
- // Get a tile from the original image. The tile is down-scaled
- // by (1 << mTilelevel) from a region in the original image.
- try {
- mDecodedTile = DecodeUtils.ensureGLCompatibleBitmap(mModel.getTile(
- mTileLevel, mX, mY, sTileSize));
- } catch (Throwable t) {
- Log.w(TAG, "fail to decode tile", t);
- }
- return mDecodedTile != null;
- }
-
- @Override
- protected Bitmap onGetBitmap() {
- Utils.assertTrue(mTileState == STATE_DECODED);
-
- // We need to override the width and height, so that we won't
- // draw beyond the boundaries.
- int rightEdge = ((mImageWidth - mX) >> mTileLevel);
- int bottomEdge = ((mImageHeight - mY) >> mTileLevel);
- setSize(Math.min(sTileSize, rightEdge), Math.min(sTileSize, bottomEdge));
-
- Bitmap bitmap = mDecodedTile;
- mDecodedTile = null;
- mTileState = STATE_ACTIVATED;
- return bitmap;
- }
-
- // We override getTextureWidth() and getTextureHeight() here, so the
- // texture can be re-used for different tiles regardless of the actual
- // size of the tile (which may be small because it is a tile at the
- // boundary).
- @Override
- public int getTextureWidth() {
- return sTileSize;
- }
-
- @Override
- public int getTextureHeight() {
- return sTileSize;
- }
-
- public void update(int x, int y, int level) {
- mX = x;
- mY = y;
- mTileLevel = level;
- invalidateContent();
- }
-
- public Tile getParentTile() {
- if (mTileLevel + 1 == mLevelCount) return null;
- int size = sTileSize << (mTileLevel + 1);
- int x = size * (mX / size);
- int y = size * (mY / size);
- return getTile(x, y, mTileLevel + 1);
- }
-
- @Override
- public String toString() {
- return String.format("tile(%s, %s, %s / %s)",
- mX / sTileSize, mY / sTileSize, mLevel, mLevelCount);
- }
- }
-
- private static class TileQueue {
- private Tile mHead;
-
- public Tile pop() {
- Tile tile = mHead;
- if (tile != null) mHead = tile.mNext;
- return tile;
- }
-
- public boolean push(Tile tile) {
- boolean wasEmpty = mHead == null;
- tile.mNext = mHead;
- mHead = tile;
- return wasEmpty;
- }
-
- public void clean() {
- mHead = null;
- }
- }
-
- private class TileDecoder implements ThreadPool.Job<Void> {
-
- private CancelListener mNotifier = new CancelListener() {
- @Override
- public void onCancel() {
- synchronized (TileImageView.this) {
- TileImageView.this.notifyAll();
- }
- }
- };
-
- @Override
- public Void run(JobContext jc) {
- jc.setMode(ThreadPool.MODE_NONE);
- jc.setCancelListener(mNotifier);
- while (!jc.isCancelled()) {
- Tile tile = null;
- synchronized(TileImageView.this) {
- tile = mDecodeQueue.pop();
- if (tile == null && !jc.isCancelled()) {
- Utils.waitWithoutInterrupt(TileImageView.this);
- }
- }
- if (tile == null) continue;
- if (decodeTile(tile)) queueForUpload(tile);
- }
- return null;
- }
- }
-}
diff --git a/src/com/android/gallery3d/ui/TileImageViewAdapter.java b/src/com/android/gallery3d/ui/TileImageViewAdapter.java
deleted file mode 100644
index 0c1f66d0c..000000000
--- a/src/com/android/gallery3d/ui/TileImageViewAdapter.java
+++ /dev/null
@@ -1,200 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.annotation.TargetApi;
-import android.graphics.Bitmap;
-import android.graphics.Bitmap.Config;
-import android.graphics.BitmapFactory;
-import android.graphics.BitmapRegionDecoder;
-import android.graphics.Canvas;
-import android.graphics.Rect;
-
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.common.Utils;
-import com.android.photos.data.GalleryBitmapPool;
-
-public class TileImageViewAdapter implements TileImageView.TileSource {
- private static final String TAG = "TileImageViewAdapter";
- protected ScreenNail mScreenNail;
- protected boolean mOwnScreenNail;
- protected BitmapRegionDecoder mRegionDecoder;
- protected int mImageWidth;
- protected int mImageHeight;
- protected int mLevelCount;
-
- public TileImageViewAdapter() {
- }
-
- public synchronized void clear() {
- mScreenNail = null;
- mImageWidth = 0;
- mImageHeight = 0;
- mLevelCount = 0;
- mRegionDecoder = null;
- }
-
- // Caller is responsible to recycle the ScreenNail
- public synchronized void setScreenNail(
- ScreenNail screenNail, int width, int height) {
- Utils.checkNotNull(screenNail);
- mScreenNail = screenNail;
- mImageWidth = width;
- mImageHeight = height;
- mRegionDecoder = null;
- mLevelCount = 0;
- }
-
- public synchronized void setRegionDecoder(BitmapRegionDecoder decoder) {
- mRegionDecoder = Utils.checkNotNull(decoder);
- mImageWidth = decoder.getWidth();
- mImageHeight = decoder.getHeight();
- mLevelCount = calculateLevelCount();
- }
-
- private int calculateLevelCount() {
- return Math.max(0, Utils.ceilLog2(
- (float) mImageWidth / mScreenNail.getWidth()));
- }
-
- // Gets a sub image on a rectangle of the current photo. For example,
- // getTile(1, 50, 50, 100, 3, pool) means to get the region located
- // at (50, 50) with sample level 1 (ie, down sampled by 2^1) and the
- // target tile size (after sampling) 100 with border 3.
- //
- // From this spec, we can infer the actual tile size to be
- // 100 + 3x2 = 106, and the size of the region to be extracted from the
- // photo to be 200 with border 6.
- //
- // As a result, we should decode region (50-6, 50-6, 250+6, 250+6) or
- // (44, 44, 256, 256) from the original photo and down sample it to 106.
- @TargetApi(ApiHelper.VERSION_CODES.HONEYCOMB)
- @Override
- public Bitmap getTile(int level, int x, int y, int tileSize) {
- if (!ApiHelper.HAS_REUSING_BITMAP_IN_BITMAP_REGION_DECODER) {
- return getTileWithoutReusingBitmap(level, x, y, tileSize);
- }
-
- int t = tileSize << level;
-
- Rect wantRegion = new Rect(x, y, x + t, y + t);
-
- boolean needClear;
- BitmapRegionDecoder regionDecoder = null;
-
- synchronized (this) {
- regionDecoder = mRegionDecoder;
- if (regionDecoder == null) return null;
-
- // We need to clear a reused bitmap, if wantRegion is not fully
- // within the image.
- needClear = !new Rect(0, 0, mImageWidth, mImageHeight)
- .contains(wantRegion);
- }
-
- Bitmap bitmap = GalleryBitmapPool.getInstance().get(tileSize, tileSize);
- if (bitmap != null) {
- if (needClear) bitmap.eraseColor(0);
- } else {
- bitmap = Bitmap.createBitmap(tileSize, tileSize, Config.ARGB_8888);
- }
-
- BitmapFactory.Options options = new BitmapFactory.Options();
- options.inPreferredConfig = Config.ARGB_8888;
- options.inPreferQualityOverSpeed = true;
- options.inSampleSize = (1 << level);
- options.inBitmap = bitmap;
-
- try {
- // In CropImage, we may call the decodeRegion() concurrently.
- synchronized (regionDecoder) {
- bitmap = regionDecoder.decodeRegion(wantRegion, options);
- }
- } finally {
- if (options.inBitmap != bitmap && options.inBitmap != null) {
- GalleryBitmapPool.getInstance().put(options.inBitmap);
- options.inBitmap = null;
- }
- }
-
- if (bitmap == null) {
- Log.w(TAG, "fail in decoding region");
- }
- return bitmap;
- }
-
- private Bitmap getTileWithoutReusingBitmap(
- int level, int x, int y, int tileSize) {
- int t = tileSize << level;
- Rect wantRegion = new Rect(x, y, x + t, y + t);
-
- BitmapRegionDecoder regionDecoder;
- Rect overlapRegion;
-
- synchronized (this) {
- regionDecoder = mRegionDecoder;
- if (regionDecoder == null) return null;
- overlapRegion = new Rect(0, 0, mImageWidth, mImageHeight);
- Utils.assertTrue(overlapRegion.intersect(wantRegion));
- }
-
- BitmapFactory.Options options = new BitmapFactory.Options();
- options.inPreferredConfig = Config.ARGB_8888;
- options.inPreferQualityOverSpeed = true;
- options.inSampleSize = (1 << level);
- Bitmap bitmap = null;
-
- // In CropImage, we may call the decodeRegion() concurrently.
- synchronized (regionDecoder) {
- bitmap = regionDecoder.decodeRegion(overlapRegion, options);
- }
-
- if (bitmap == null) {
- Log.w(TAG, "fail in decoding region");
- }
-
- if (wantRegion.equals(overlapRegion)) return bitmap;
-
- Bitmap result = Bitmap.createBitmap(tileSize, tileSize, Config.ARGB_8888);
- Canvas canvas = new Canvas(result);
- canvas.drawBitmap(bitmap,
- (overlapRegion.left - wantRegion.left) >> level,
- (overlapRegion.top - wantRegion.top) >> level, null);
- return result;
- }
-
-
- @Override
- public ScreenNail getScreenNail() {
- return mScreenNail;
- }
-
- @Override
- public int getImageHeight() {
- return mImageHeight;
- }
-
- @Override
- public int getImageWidth() {
- return mImageWidth;
- }
-
- @Override
- public int getLevelCount() {
- return mLevelCount;
- }
-}
diff --git a/src/com/android/gallery3d/ui/TiledScreenNail.java b/src/com/android/gallery3d/ui/TiledScreenNail.java
deleted file mode 100644
index 860e230bb..000000000
--- a/src/com/android/gallery3d/ui/TiledScreenNail.java
+++ /dev/null
@@ -1,218 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.graphics.Bitmap;
-import android.graphics.RectF;
-
-import com.android.gallery3d.common.Utils;
-import com.android.photos.data.GalleryBitmapPool;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.TiledTexture;
-
-// This is a ScreenNail wraps a Bitmap. There are some extra functions:
-//
-// - If we need to draw before the bitmap is available, we draw a rectange of
-// placeholder color (gray).
-//
-// - When the the bitmap is available, and we have drawn the placeholder color
-// before, we will do a fade-in animation.
-public class TiledScreenNail implements ScreenNail {
- @SuppressWarnings("unused")
- private static final String TAG = "TiledScreenNail";
-
- // The duration of the fading animation in milliseconds
- private static final int DURATION = 180;
-
- private static int sMaxSide = 640;
-
- // These are special values for mAnimationStartTime
- private static final long ANIMATION_NOT_NEEDED = -1;
- private static final long ANIMATION_NEEDED = -2;
- private static final long ANIMATION_DONE = -3;
-
- private int mWidth;
- private int mHeight;
- private long mAnimationStartTime = ANIMATION_NOT_NEEDED;
-
- private Bitmap mBitmap;
- private TiledTexture mTexture;
-
- public TiledScreenNail(Bitmap bitmap) {
- mWidth = bitmap.getWidth();
- mHeight = bitmap.getHeight();
- mBitmap = bitmap;
- mTexture = new TiledTexture(bitmap);
- }
-
- public TiledScreenNail(int width, int height) {
- setSize(width, height);
- }
-
- // This gets overridden by bitmap_screennail_placeholder
- // in GalleryUtils.initialize
- private static int mPlaceholderColor = 0xFF222222;
- private static boolean mDrawPlaceholder = true;
-
- public static void setPlaceholderColor(int color) {
- mPlaceholderColor = color;
- }
-
- private void setSize(int width, int height) {
- if (width == 0 || height == 0) {
- width = sMaxSide;
- height = sMaxSide * 3 / 4;
- }
- float scale = Math.min(1, (float) sMaxSide / Math.max(width, height));
- mWidth = Math.round(scale * width);
- mHeight = Math.round(scale * height);
- }
-
- // Combines the two ScreenNails.
- // Returns the used one and recycle the unused one.
- public ScreenNail combine(ScreenNail other) {
- if (other == null) {
- return this;
- }
-
- if (!(other instanceof TiledScreenNail)) {
- recycle();
- return other;
- }
-
- // Now both are TiledScreenNail. Move over the information about width,
- // height, and Bitmap, then recycle the other.
- TiledScreenNail newer = (TiledScreenNail) other;
- mWidth = newer.mWidth;
- mHeight = newer.mHeight;
- if (newer.mTexture != null) {
- if (mBitmap != null) GalleryBitmapPool.getInstance().put(mBitmap);
- if (mTexture != null) mTexture.recycle();
- mBitmap = newer.mBitmap;
- mTexture = newer.mTexture;
- newer.mBitmap = null;
- newer.mTexture = null;
- }
- newer.recycle();
- return this;
- }
-
- public void updatePlaceholderSize(int width, int height) {
- if (mBitmap != null) return;
- if (width == 0 || height == 0) return;
- setSize(width, height);
- }
-
- @Override
- public int getWidth() {
- return mWidth;
- }
-
- @Override
- public int getHeight() {
- return mHeight;
- }
-
- @Override
- public void noDraw() {
- }
-
- @Override
- public void recycle() {
- if (mTexture != null) {
- mTexture.recycle();
- mTexture = null;
- }
- if (mBitmap != null) {
- GalleryBitmapPool.getInstance().put(mBitmap);
- mBitmap = null;
- }
- }
-
- public static void disableDrawPlaceholder() {
- mDrawPlaceholder = false;
- }
-
- public static void enableDrawPlaceholder() {
- mDrawPlaceholder = true;
- }
-
- @Override
- public void draw(GLCanvas canvas, int x, int y, int width, int height) {
- if (mTexture == null || !mTexture.isReady()) {
- if (mAnimationStartTime == ANIMATION_NOT_NEEDED) {
- mAnimationStartTime = ANIMATION_NEEDED;
- }
- if(mDrawPlaceholder) {
- canvas.fillRect(x, y, width, height, mPlaceholderColor);
- }
- return;
- }
-
- if (mAnimationStartTime == ANIMATION_NEEDED) {
- mAnimationStartTime = AnimationTime.get();
- }
-
- if (isAnimating()) {
- mTexture.drawMixed(canvas, mPlaceholderColor, getRatio(), x, y,
- width, height);
- } else {
- mTexture.draw(canvas, x, y, width, height);
- }
- }
-
- @Override
- public void draw(GLCanvas canvas, RectF source, RectF dest) {
- if (mTexture == null || !mTexture.isReady()) {
- canvas.fillRect(dest.left, dest.top, dest.width(), dest.height(),
- mPlaceholderColor);
- return;
- }
-
- mTexture.draw(canvas, source, dest);
- }
-
- public boolean isAnimating() {
- // The TiledTexture may not be uploaded completely yet.
- // In that case, we count it as animating state and we will draw
- // the placeholder in TileImageView.
- if (mTexture == null || !mTexture.isReady()) return true;
- if (mAnimationStartTime < 0) return false;
- if (AnimationTime.get() - mAnimationStartTime >= DURATION) {
- mAnimationStartTime = ANIMATION_DONE;
- return false;
- }
- return true;
- }
-
- private float getRatio() {
- float r = (float) (AnimationTime.get() - mAnimationStartTime) / DURATION;
- return Utils.clamp(1.0f - r, 0.0f, 1.0f);
- }
-
- public boolean isShowingPlaceholder() {
- return (mBitmap == null) || isAnimating();
- }
-
- public TiledTexture getTexture() {
- return mTexture;
- }
-
- public static void setMaxSide(int size) {
- sMaxSide = size;
- }
-}
diff --git a/src/com/android/gallery3d/ui/UndoBarView.java b/src/com/android/gallery3d/ui/UndoBarView.java
deleted file mode 100644
index 42f12ae72..000000000
--- a/src/com/android/gallery3d/ui/UndoBarView.java
+++ /dev/null
@@ -1,211 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.content.Context;
-import android.view.MotionEvent;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.glrenderer.GLCanvas;
-import com.android.gallery3d.glrenderer.NinePatchTexture;
-import com.android.gallery3d.glrenderer.ResourceTexture;
-import com.android.gallery3d.glrenderer.StringTexture;
-import com.android.gallery3d.util.GalleryUtils;
-
-public class UndoBarView extends GLView {
- @SuppressWarnings("unused")
- private static final String TAG = "UndoBarView";
-
- private static final int WHITE = 0xFFFFFFFF;
- private static final int GRAY = 0xFFAAAAAA;
-
- private final NinePatchTexture mPanel;
- private final StringTexture mUndoText;
- private final StringTexture mDeletedText;
- private final ResourceTexture mUndoIcon;
- private final int mBarHeight;
- private final int mBarMargin;
- private final int mUndoTextMargin;
- private final int mIconSize;
- private final int mIconMargin;
- private final int mSeparatorTopMargin;
- private final int mSeparatorBottomMargin;
- private final int mSeparatorRightMargin;
- private final int mSeparatorWidth;
- private final int mDeletedTextMargin;
- private final int mClickRegion;
-
- private OnClickListener mOnClickListener;
- private boolean mDownOnButton;
-
- // This is the layout of UndoBarView. The unit is dp.
- //
- // +-+----+----------------+-+--+----+-+------+--+-+
- // 48 | | | Deleted | | | <- | | UNDO | | |
- // +-+----+----------------+-+--+----+-+------+--+-+
- // 4 16 1 12 32 8 16 4
- public UndoBarView(Context context) {
- mBarHeight = GalleryUtils.dpToPixel(48);
- mBarMargin = GalleryUtils.dpToPixel(4);
- mUndoTextMargin = GalleryUtils.dpToPixel(16);
- mIconMargin = GalleryUtils.dpToPixel(8);
- mIconSize = GalleryUtils.dpToPixel(32);
- mSeparatorRightMargin = GalleryUtils.dpToPixel(12);
- mSeparatorTopMargin = GalleryUtils.dpToPixel(10);
- mSeparatorBottomMargin = GalleryUtils.dpToPixel(10);
- mSeparatorWidth = GalleryUtils.dpToPixel(1);
- mDeletedTextMargin = GalleryUtils.dpToPixel(16);
-
- mPanel = new NinePatchTexture(context, R.drawable.panel_undo_holo);
- mUndoText = StringTexture.newInstance(context.getString(R.string.undo),
- GalleryUtils.dpToPixel(12), GRAY, 0, true);
- mDeletedText = StringTexture.newInstance(
- context.getString(R.string.deleted),
- GalleryUtils.dpToPixel(16), WHITE);
- mUndoIcon = new ResourceTexture(
- context, R.drawable.ic_menu_revert_holo_dark);
- mClickRegion = mBarMargin + mUndoTextMargin + mUndoText.getWidth()
- + mIconMargin + mIconSize + mSeparatorRightMargin;
- }
-
- public void setOnClickListener(OnClickListener listener) {
- mOnClickListener = listener;
- }
-
- @Override
- protected void onMeasure(int widthSpec, int heightSpec) {
- setMeasuredSize(0 /* unused */, mBarHeight);
- }
-
- @Override
- protected void render(GLCanvas canvas) {
- super.render(canvas);
- advanceAnimation();
-
- canvas.save(GLCanvas.SAVE_FLAG_ALPHA);
- canvas.multiplyAlpha(mAlpha);
-
- int w = getWidth();
- int h = getHeight();
- mPanel.draw(canvas, mBarMargin, 0, w - mBarMargin * 2, mBarHeight);
-
- int x = w - mBarMargin;
- int y;
-
- x -= mUndoTextMargin + mUndoText.getWidth();
- y = (mBarHeight - mUndoText.getHeight()) / 2;
- mUndoText.draw(canvas, x, y);
-
- x -= mIconMargin + mIconSize;
- y = (mBarHeight - mIconSize) / 2;
- mUndoIcon.draw(canvas, x, y, mIconSize, mIconSize);
-
- x -= mSeparatorRightMargin + mSeparatorWidth;
- y = mSeparatorTopMargin;
- canvas.fillRect(x, y, mSeparatorWidth,
- mBarHeight - mSeparatorTopMargin - mSeparatorBottomMargin, GRAY);
-
- x = mBarMargin + mDeletedTextMargin;
- y = (mBarHeight - mDeletedText.getHeight()) / 2;
- mDeletedText.draw(canvas, x, y);
-
- canvas.restore();
- }
-
- @Override
- protected boolean onTouch(MotionEvent event) {
- switch (event.getAction()) {
- case MotionEvent.ACTION_DOWN:
- mDownOnButton = inUndoButton(event);
- break;
- case MotionEvent.ACTION_UP:
- if (mDownOnButton) {
- if (mOnClickListener != null && inUndoButton(event)) {
- mOnClickListener.onClick(this);
- }
- mDownOnButton = false;
- }
- break;
- case MotionEvent.ACTION_CANCEL:
- mDownOnButton = false;
- break;
- }
- return true;
- }
-
- // Check if the event is on the right of the separator
- private boolean inUndoButton(MotionEvent event) {
- float x = event.getX();
- float y = event.getY();
- int w = getWidth();
- int h = getHeight();
- return (x >= w - mClickRegion && x < w && y >= 0 && y < h);
- }
-
- ////////////////////////////////////////////////////////////////////////////
- // Alpha Animation
- ////////////////////////////////////////////////////////////////////////////
-
- private static final long NO_ANIMATION = -1;
- private static long ANIM_TIME = 200;
- private long mAnimationStartTime = NO_ANIMATION;
- private float mFromAlpha, mToAlpha;
- private float mAlpha;
-
- private static float getTargetAlpha(int visibility) {
- return (visibility == VISIBLE) ? 1f : 0f;
- }
-
- @Override
- public void setVisibility(int visibility) {
- mAlpha = getTargetAlpha(visibility);
- mAnimationStartTime = NO_ANIMATION;
- super.setVisibility(visibility);
- invalidate();
- }
-
- public void animateVisibility(int visibility) {
- float target = getTargetAlpha(visibility);
- if (mAnimationStartTime == NO_ANIMATION && mAlpha == target) return;
- if (mAnimationStartTime != NO_ANIMATION && mToAlpha == target) return;
-
- mFromAlpha = mAlpha;
- mToAlpha = target;
- mAnimationStartTime = AnimationTime.startTime();
-
- super.setVisibility(VISIBLE);
- invalidate();
- }
-
- private void advanceAnimation() {
- if (mAnimationStartTime == NO_ANIMATION) return;
-
- float delta = (float) (AnimationTime.get() - mAnimationStartTime) /
- ANIM_TIME;
- mAlpha = mFromAlpha + ((mToAlpha > mFromAlpha) ? delta : -delta);
- mAlpha = Utils.clamp(mAlpha, 0f, 1f);
-
- if (mAlpha == mToAlpha) {
- mAnimationStartTime = NO_ANIMATION;
- if (mAlpha == 0) {
- super.setVisibility(INVISIBLE);
- }
- }
- invalidate();
- }
-}
diff --git a/src/com/android/gallery3d/ui/UserInteractionListener.java b/src/com/android/gallery3d/ui/UserInteractionListener.java
deleted file mode 100644
index bc4a71800..000000000
--- a/src/com/android/gallery3d/ui/UserInteractionListener.java
+++ /dev/null
@@ -1,26 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-public interface UserInteractionListener {
- // Called when a user interaction begins (for example, fling).
- public void onUserInteractionBegin();
- // Called when the user interaction ends.
- public void onUserInteractionEnd();
- // Other one-shot user interactions.
- public void onUserInteraction();
-}
diff --git a/src/com/android/gallery3d/ui/WakeLockHoldingProgressListener.java b/src/com/android/gallery3d/ui/WakeLockHoldingProgressListener.java
deleted file mode 100644
index ee61d8edb..000000000
--- a/src/com/android/gallery3d/ui/WakeLockHoldingProgressListener.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.ui;
-
-import android.app.Activity;
-import android.content.Context;
-import android.os.PowerManager;
-
-import com.android.gallery3d.app.AbstractGalleryActivity;
-
-public class WakeLockHoldingProgressListener implements MenuExecutor.ProgressListener {
- static private final String DEFAULT_WAKE_LOCK_LABEL = "Gallery Progress Listener";
- private AbstractGalleryActivity mActivity;
- private PowerManager.WakeLock mWakeLock;
-
- public WakeLockHoldingProgressListener(AbstractGalleryActivity galleryActivity) {
- this(galleryActivity, DEFAULT_WAKE_LOCK_LABEL);
- }
-
- public WakeLockHoldingProgressListener(AbstractGalleryActivity galleryActivity, String label) {
- mActivity = galleryActivity;
- PowerManager pm =
- (PowerManager) ((Activity) mActivity).getSystemService(Context.POWER_SERVICE);
- mWakeLock = pm.newWakeLock(PowerManager.SCREEN_DIM_WAKE_LOCK, label);
- }
-
- @Override
- public void onProgressComplete(int result) {
- mWakeLock.release();
- }
-
- @Override
- public void onProgressStart() {
- mWakeLock.acquire();
- }
-
- protected AbstractGalleryActivity getActivity() {
- return mActivity;
- }
-
- @Override
- public void onProgressUpdate(int index) {
- }
-
- @Override
- public void onConfirmDialogDismissed(boolean confirmed) {
- }
-
- @Override
- public void onConfirmDialogShown() {
- }
-}
diff --git a/src/com/android/gallery3d/util/AccessibilityUtils.java b/src/com/android/gallery3d/util/AccessibilityUtils.java
deleted file mode 100644
index 9df8e4ece..000000000
--- a/src/com/android/gallery3d/util/AccessibilityUtils.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-import android.content.Context;
-import android.support.v4.view.accessibility.AccessibilityRecordCompat;
-import android.view.View;
-import android.view.accessibility.AccessibilityEvent;
-import android.view.accessibility.AccessibilityManager;
-
-import com.android.gallery3d.common.ApiHelper;
-
-/**
- * AccessibilityUtils provides functions needed in accessibility mode. All the functions
- * in this class are made compatible with gingerbread and later API's
-*/
-public class AccessibilityUtils {
- public static void makeAnnouncement(View view, CharSequence announcement) {
- if (view == null)
- return;
- if (ApiHelper.HAS_ANNOUNCE_FOR_ACCESSIBILITY) {
- view.announceForAccessibility(announcement);
- } else {
- // For API 15 and earlier, we need to construct an accessibility event
- Context ctx = view.getContext();
- AccessibilityManager am = (AccessibilityManager) ctx.getSystemService(
- Context.ACCESSIBILITY_SERVICE);
- if (!am.isEnabled()) return;
- AccessibilityEvent event = AccessibilityEvent.obtain(
- AccessibilityEvent.TYPE_NOTIFICATION_STATE_CHANGED);
- AccessibilityRecordCompat arc = new AccessibilityRecordCompat(event);
- arc.setSource(view);
- event.setClassName(view.getClass().getName());
- event.setPackageName(view.getContext().getPackageName());
- event.setEnabled(view.isEnabled());
- event.getText().add(announcement);
- am.sendAccessibilityEvent(event);
- }
- }
-} \ No newline at end of file
diff --git a/src/com/android/gallery3d/util/BucketNames.java b/src/com/android/gallery3d/util/BucketNames.java
deleted file mode 100644
index 990dc8224..000000000
--- a/src/com/android/gallery3d/util/BucketNames.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-/**
- * Bucket names for buckets that are created and used in the Gallery.
- */
-public class BucketNames {
-
- public static final String CAMERA = "DCIM/Camera";
- public static final String IMPORTED = "Imported";
- public static final String DOWNLOAD = "download";
- public static final String EDITED_ONLINE_PHOTOS = "EditedOnlinePhotos";
- public static final String SCREENSHOTS = "Pictures/Screenshots";
-}
diff --git a/src/com/android/gallery3d/util/CacheManager.java b/src/com/android/gallery3d/util/CacheManager.java
deleted file mode 100644
index ba466f79b..000000000
--- a/src/com/android/gallery3d/util/CacheManager.java
+++ /dev/null
@@ -1,82 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-import android.content.Context;
-import android.content.SharedPreferences;
-import android.preference.PreferenceManager;
-
-import com.android.gallery3d.common.BlobCache;
-
-import java.io.File;
-import java.io.IOException;
-import java.util.HashMap;
-
-public class CacheManager {
- private static final String TAG = "CacheManager";
- private static final String KEY_CACHE_UP_TO_DATE = "cache-up-to-date";
- private static HashMap<String, BlobCache> sCacheMap =
- new HashMap<String, BlobCache>();
- private static boolean sOldCheckDone = false;
-
- // Return null when we cannot instantiate a BlobCache, e.g.:
- // there is no SD card found.
- // This can only be called from data thread.
- public static BlobCache getCache(Context context, String filename,
- int maxEntries, int maxBytes, int version) {
- synchronized (sCacheMap) {
- if (!sOldCheckDone) {
- removeOldFilesIfNecessary(context);
- sOldCheckDone = true;
- }
- BlobCache cache = sCacheMap.get(filename);
- if (cache == null) {
- File cacheDir = context.getExternalCacheDir();
- String path = cacheDir.getAbsolutePath() + "/" + filename;
- try {
- cache = new BlobCache(path, maxEntries, maxBytes, false,
- version);
- sCacheMap.put(filename, cache);
- } catch (IOException e) {
- Log.e(TAG, "Cannot instantiate cache!", e);
- }
- }
- return cache;
- }
- }
-
- // Removes the old files if the data is wiped.
- private static void removeOldFilesIfNecessary(Context context) {
- SharedPreferences pref = PreferenceManager
- .getDefaultSharedPreferences(context);
- int n = 0;
- try {
- n = pref.getInt(KEY_CACHE_UP_TO_DATE, 0);
- } catch (Throwable t) {
- // ignore.
- }
- if (n != 0) return;
- pref.edit().putInt(KEY_CACHE_UP_TO_DATE, 1).commit();
-
- File cacheDir = context.getExternalCacheDir();
- String prefix = cacheDir.getAbsolutePath() + "/";
-
- BlobCache.deleteFiles(prefix + "imgcache");
- BlobCache.deleteFiles(prefix + "rev_geocoding");
- BlobCache.deleteFiles(prefix + "bookmark");
- }
-}
diff --git a/src/com/android/gallery3d/util/GalleryUtils.java b/src/com/android/gallery3d/util/GalleryUtils.java
deleted file mode 100644
index 9245e2c5f..000000000
--- a/src/com/android/gallery3d/util/GalleryUtils.java
+++ /dev/null
@@ -1,404 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-import android.annotation.TargetApi;
-import android.content.ActivityNotFoundException;
-import android.content.ComponentName;
-import android.content.Context;
-import android.content.Intent;
-import android.content.SharedPreferences;
-import android.content.pm.PackageManager;
-import android.content.pm.ResolveInfo;
-import android.content.res.Resources;
-import android.graphics.Color;
-import android.net.Uri;
-import android.os.ConditionVariable;
-import android.os.Environment;
-import android.os.StatFs;
-import android.preference.PreferenceManager;
-import android.provider.MediaStore;
-import android.util.DisplayMetrics;
-import android.util.Log;
-import android.view.WindowManager;
-
-import com.android.gallery3d.R;
-import com.android.gallery3d.app.Gallery;
-import com.android.gallery3d.app.PackagesMonitor;
-import com.android.gallery3d.common.ApiHelper;
-import com.android.gallery3d.data.DataManager;
-import com.android.gallery3d.data.MediaItem;
-import com.android.gallery3d.ui.TiledScreenNail;
-import com.android.gallery3d.util.ThreadPool.CancelListener;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.io.File;
-import java.util.Arrays;
-import java.util.List;
-import java.util.Locale;
-
-public class GalleryUtils {
- private static final String TAG = "GalleryUtils";
- private static final String MAPS_PACKAGE_NAME = "com.google.android.apps.maps";
- private static final String MAPS_CLASS_NAME = "com.google.android.maps.MapsActivity";
- private static final String CAMERA_LAUNCHER_NAME = "com.android.camera.CameraLauncher";
-
- public static final String MIME_TYPE_IMAGE = "image/*";
- public static final String MIME_TYPE_VIDEO = "video/*";
- public static final String MIME_TYPE_PANORAMA360 = "application/vnd.google.panorama360+jpg";
- public static final String MIME_TYPE_ALL = "*/*";
-
- private static final String DIR_TYPE_IMAGE = "vnd.android.cursor.dir/image";
- private static final String DIR_TYPE_VIDEO = "vnd.android.cursor.dir/video";
-
- private static final String PREFIX_PHOTO_EDITOR_UPDATE = "editor-update-";
- private static final String PREFIX_HAS_PHOTO_EDITOR = "has-editor-";
-
- private static final String KEY_CAMERA_UPDATE = "camera-update";
- private static final String KEY_HAS_CAMERA = "has-camera";
-
- private static float sPixelDensity = -1f;
- private static boolean sCameraAvailableInitialized = false;
- private static boolean sCameraAvailable;
-
- public static void initialize(Context context) {
- DisplayMetrics metrics = new DisplayMetrics();
- WindowManager wm = (WindowManager)
- context.getSystemService(Context.WINDOW_SERVICE);
- wm.getDefaultDisplay().getMetrics(metrics);
- sPixelDensity = metrics.density;
- Resources r = context.getResources();
- TiledScreenNail.setPlaceholderColor(r.getColor(
- R.color.bitmap_screennail_placeholder));
- initializeThumbnailSizes(metrics, r);
- }
-
- private static void initializeThumbnailSizes(DisplayMetrics metrics, Resources r) {
- int maxPixels = Math.max(metrics.heightPixels, metrics.widthPixels);
-
- // For screen-nails, we never need to completely fill the screen
- MediaItem.setThumbnailSizes(maxPixels / 2, maxPixels / 5);
- TiledScreenNail.setMaxSide(maxPixels / 2);
- }
-
- public static float[] intColorToFloatARGBArray(int from) {
- return new float[] {
- Color.alpha(from) / 255f,
- Color.red(from) / 255f,
- Color.green(from) / 255f,
- Color.blue(from) / 255f
- };
- }
-
- public static float dpToPixel(float dp) {
- return sPixelDensity * dp;
- }
-
- public static int dpToPixel(int dp) {
- return Math.round(dpToPixel((float) dp));
- }
-
- public static int meterToPixel(float meter) {
- // 1 meter = 39.37 inches, 1 inch = 160 dp.
- return Math.round(dpToPixel(meter * 39.37f * 160));
- }
-
- public static byte[] getBytes(String in) {
- byte[] result = new byte[in.length() * 2];
- int output = 0;
- for (char ch : in.toCharArray()) {
- result[output++] = (byte) (ch & 0xFF);
- result[output++] = (byte) (ch >> 8);
- }
- return result;
- }
-
- // Below are used the detect using database in the render thread. It only
- // works most of the time, but that's ok because it's for debugging only.
-
- private static volatile Thread sCurrentThread;
- private static volatile boolean sWarned;
-
- public static void setRenderThread() {
- sCurrentThread = Thread.currentThread();
- }
-
- public static void assertNotInRenderThread() {
- if (!sWarned) {
- if (Thread.currentThread() == sCurrentThread) {
- sWarned = true;
- Log.w(TAG, new Throwable("Should not do this in render thread"));
- }
- }
- }
-
- private static final double RAD_PER_DEG = Math.PI / 180.0;
- private static final double EARTH_RADIUS_METERS = 6367000.0;
-
- public static double fastDistanceMeters(double latRad1, double lngRad1,
- double latRad2, double lngRad2) {
- if ((Math.abs(latRad1 - latRad2) > RAD_PER_DEG)
- || (Math.abs(lngRad1 - lngRad2) > RAD_PER_DEG)) {
- return accurateDistanceMeters(latRad1, lngRad1, latRad2, lngRad2);
- }
- // Approximate sin(x) = x.
- double sineLat = (latRad1 - latRad2);
-
- // Approximate sin(x) = x.
- double sineLng = (lngRad1 - lngRad2);
-
- // Approximate cos(lat1) * cos(lat2) using
- // cos((lat1 + lat2)/2) ^ 2
- double cosTerms = Math.cos((latRad1 + latRad2) / 2.0);
- cosTerms = cosTerms * cosTerms;
- double trigTerm = sineLat * sineLat + cosTerms * sineLng * sineLng;
- trigTerm = Math.sqrt(trigTerm);
-
- // Approximate arcsin(x) = x
- return EARTH_RADIUS_METERS * trigTerm;
- }
-
- public static double accurateDistanceMeters(double lat1, double lng1,
- double lat2, double lng2) {
- double dlat = Math.sin(0.5 * (lat2 - lat1));
- double dlng = Math.sin(0.5 * (lng2 - lng1));
- double x = dlat * dlat + dlng * dlng * Math.cos(lat1) * Math.cos(lat2);
- return (2 * Math.atan2(Math.sqrt(x), Math.sqrt(Math.max(0.0,
- 1.0 - x)))) * EARTH_RADIUS_METERS;
- }
-
-
- public static final double toMile(double meter) {
- return meter / 1609;
- }
-
- // For debugging, it will block the caller for timeout millis.
- public static void fakeBusy(JobContext jc, int timeout) {
- final ConditionVariable cv = new ConditionVariable();
- jc.setCancelListener(new CancelListener() {
- @Override
- public void onCancel() {
- cv.open();
- }
- });
- cv.block(timeout);
- jc.setCancelListener(null);
- }
-
- public static boolean isEditorAvailable(Context context, String mimeType) {
- int version = PackagesMonitor.getPackagesVersion(context);
-
- String updateKey = PREFIX_PHOTO_EDITOR_UPDATE + mimeType;
- String hasKey = PREFIX_HAS_PHOTO_EDITOR + mimeType;
-
- SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
- if (prefs.getInt(updateKey, 0) != version) {
- PackageManager packageManager = context.getPackageManager();
- List<ResolveInfo> infos = packageManager.queryIntentActivities(
- new Intent(Intent.ACTION_EDIT).setType(mimeType), 0);
- prefs.edit().putInt(updateKey, version)
- .putBoolean(hasKey, !infos.isEmpty())
- .commit();
- }
-
- return prefs.getBoolean(hasKey, true);
- }
-
- public static boolean isAnyCameraAvailable(Context context) {
- int version = PackagesMonitor.getPackagesVersion(context);
- SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
- if (prefs.getInt(KEY_CAMERA_UPDATE, 0) != version) {
- PackageManager packageManager = context.getPackageManager();
- List<ResolveInfo> infos = packageManager.queryIntentActivities(
- new Intent(MediaStore.INTENT_ACTION_STILL_IMAGE_CAMERA), 0);
- prefs.edit().putInt(KEY_CAMERA_UPDATE, version)
- .putBoolean(KEY_HAS_CAMERA, !infos.isEmpty())
- .commit();
- }
- return prefs.getBoolean(KEY_HAS_CAMERA, true);
- }
-
- public static boolean isCameraAvailable(Context context) {
- if (sCameraAvailableInitialized) return sCameraAvailable;
- PackageManager pm = context.getPackageManager();
- ComponentName name = new ComponentName(context, CAMERA_LAUNCHER_NAME);
- int state = pm.getComponentEnabledSetting(name);
- sCameraAvailableInitialized = true;
- sCameraAvailable =
- (state == PackageManager.COMPONENT_ENABLED_STATE_DEFAULT)
- || (state == PackageManager.COMPONENT_ENABLED_STATE_ENABLED);
- return sCameraAvailable;
- }
-
- public static void startCameraActivity(Context context) {
- Intent intent = new Intent(MediaStore.INTENT_ACTION_STILL_IMAGE_CAMERA)
- .setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP
- | Intent.FLAG_ACTIVITY_NEW_TASK);
- context.startActivity(intent);
- }
-
- public static void startGalleryActivity(Context context) {
- Intent intent = new Intent(context, Gallery.class)
- .setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP
- | Intent.FLAG_ACTIVITY_NEW_TASK);
- context.startActivity(intent);
- }
-
- public static boolean isValidLocation(double latitude, double longitude) {
- // TODO: change || to && after we fix the default location issue
- return (latitude != MediaItem.INVALID_LATLNG || longitude != MediaItem.INVALID_LATLNG);
- }
-
- public static String formatLatitudeLongitude(String format, double latitude,
- double longitude) {
- // We need to specify the locale otherwise it may go wrong in some language
- // (e.g. Locale.FRENCH)
- return String.format(Locale.ENGLISH, format, latitude, longitude);
- }
-
- public static void showOnMap(Context context, double latitude, double longitude) {
- try {
- // We don't use "geo:latitude,longitude" because it only centers
- // the MapView to the specified location, but we need a marker
- // for further operations (routing to/from).
- // The q=(lat, lng) syntax is suggested by geo-team.
- String uri = formatLatitudeLongitude("http://maps.google.com/maps?f=q&q=(%f,%f)",
- latitude, longitude);
- ComponentName compName = new ComponentName(MAPS_PACKAGE_NAME,
- MAPS_CLASS_NAME);
- Intent mapsIntent = new Intent(Intent.ACTION_VIEW,
- Uri.parse(uri)).setComponent(compName);
- context.startActivity(mapsIntent);
- } catch (ActivityNotFoundException e) {
- // Use the "geo intent" if no GMM is installed
- Log.e(TAG, "GMM activity not found!", e);
- String url = formatLatitudeLongitude("geo:%f,%f", latitude, longitude);
- Intent mapsIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
- context.startActivity(mapsIntent);
- }
- }
-
- public static void setViewPointMatrix(
- float matrix[], float x, float y, float z) {
- // The matrix is
- // -z, 0, x, 0
- // 0, -z, y, 0
- // 0, 0, 1, 0
- // 0, 0, 1, -z
- Arrays.fill(matrix, 0, 16, 0);
- matrix[0] = matrix[5] = matrix[15] = -z;
- matrix[8] = x;
- matrix[9] = y;
- matrix[10] = matrix[11] = 1;
- }
-
- public static int getBucketId(String path) {
- return path.toLowerCase().hashCode();
- }
-
- // Return the local path that matches the given bucketId. If no match is
- // found, return null
- public static String searchDirForPath(File dir, int bucketId) {
- File[] files = dir.listFiles();
- if (files != null) {
- for (File file : files) {
- if (file.isDirectory()) {
- String path = file.getAbsolutePath();
- if (GalleryUtils.getBucketId(path) == bucketId) {
- return path;
- } else {
- path = searchDirForPath(file, bucketId);
- if (path != null) return path;
- }
- }
- }
- }
- return null;
- }
-
- // Returns a (localized) string for the given duration (in seconds).
- public static String formatDuration(final Context context, int duration) {
- int h = duration / 3600;
- int m = (duration - h * 3600) / 60;
- int s = duration - (h * 3600 + m * 60);
- String durationValue;
- if (h == 0) {
- durationValue = String.format(context.getString(R.string.details_ms), m, s);
- } else {
- durationValue = String.format(context.getString(R.string.details_hms), h, m, s);
- }
- return durationValue;
- }
-
- @TargetApi(ApiHelper.VERSION_CODES.HONEYCOMB)
- public static int determineTypeBits(Context context, Intent intent) {
- int typeBits = 0;
- String type = intent.resolveType(context);
-
- if (MIME_TYPE_ALL.equals(type)) {
- typeBits = DataManager.INCLUDE_ALL;
- } else if (MIME_TYPE_IMAGE.equals(type) ||
- DIR_TYPE_IMAGE.equals(type)) {
- typeBits = DataManager.INCLUDE_IMAGE;
- } else if (MIME_TYPE_VIDEO.equals(type) ||
- DIR_TYPE_VIDEO.equals(type)) {
- typeBits = DataManager.INCLUDE_VIDEO;
- } else {
- typeBits = DataManager.INCLUDE_ALL;
- }
-
- if (ApiHelper.HAS_INTENT_EXTRA_LOCAL_ONLY) {
- if (intent.getBooleanExtra(Intent.EXTRA_LOCAL_ONLY, false)) {
- typeBits |= DataManager.INCLUDE_LOCAL_ONLY;
- }
- }
-
- return typeBits;
- }
-
- public static int getSelectionModePrompt(int typeBits) {
- if ((typeBits & DataManager.INCLUDE_VIDEO) != 0) {
- return (typeBits & DataManager.INCLUDE_IMAGE) == 0
- ? R.string.select_video
- : R.string.select_item;
- }
- return R.string.select_image;
- }
-
- public static boolean hasSpaceForSize(long size) {
- String state = Environment.getExternalStorageState();
- if (!Environment.MEDIA_MOUNTED.equals(state)) {
- return false;
- }
-
- String path = Environment.getExternalStorageDirectory().getPath();
- try {
- StatFs stat = new StatFs(path);
- return stat.getAvailableBlocks() * (long) stat.getBlockSize() > size;
- } catch (Exception e) {
- Log.i(TAG, "Fail to access external storage", e);
- }
- return false;
- }
-
- public static boolean isPanorama(MediaItem item) {
- if (item == null) return false;
- int w = item.getWidth();
- int h = item.getHeight();
- return (h > 0 && w / h >= 2);
- }
-}
diff --git a/src/com/android/gallery3d/util/Holder.java b/src/com/android/gallery3d/util/Holder.java
deleted file mode 100644
index 0ce914c1d..000000000
--- a/src/com/android/gallery3d/util/Holder.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-public class Holder<T> {
- private T mObject;
-
- public void set(T object) {
- mObject = object;
- }
-
- public T get() {
- return mObject;
- }
-}
diff --git a/src/com/android/gallery3d/util/IdentityCache.java b/src/com/android/gallery3d/util/IdentityCache.java
deleted file mode 100644
index 3edc424a3..000000000
--- a/src/com/android/gallery3d/util/IdentityCache.java
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-import java.lang.ref.ReferenceQueue;
-import java.lang.ref.WeakReference;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.Set;
-
-public class IdentityCache<K, V> {
-
- private final HashMap<K, Entry<K, V>> mWeakMap =
- new HashMap<K, Entry<K, V>>();
- private ReferenceQueue<V> mQueue = new ReferenceQueue<V>();
-
- public IdentityCache() {
- }
-
- private static class Entry<K, V> extends WeakReference<V> {
- K mKey;
-
- public Entry(K key, V value, ReferenceQueue<V> queue) {
- super(value, queue);
- mKey = key;
- }
- }
-
- private void cleanUpWeakMap() {
- Entry<K, V> entry = (Entry<K, V>) mQueue.poll();
- while (entry != null) {
- mWeakMap.remove(entry.mKey);
- entry = (Entry<K, V>) mQueue.poll();
- }
- }
-
- public synchronized V put(K key, V value) {
- cleanUpWeakMap();
- Entry<K, V> entry = mWeakMap.put(
- key, new Entry<K, V>(key, value, mQueue));
- return entry == null ? null : entry.get();
- }
-
- public synchronized V get(K key) {
- cleanUpWeakMap();
- Entry<K, V> entry = mWeakMap.get(key);
- return entry == null ? null : entry.get();
- }
-
- // This is currently unused.
- /*
- public synchronized void clear() {
- mWeakMap.clear();
- mQueue = new ReferenceQueue<V>();
- }
- */
-
- // This is for debugging only
- public synchronized ArrayList<K> keys() {
- Set<K> set = mWeakMap.keySet();
- ArrayList<K> result = new ArrayList<K>(set);
- return result;
- }
-}
diff --git a/src/com/android/gallery3d/util/IntArray.java b/src/com/android/gallery3d/util/IntArray.java
deleted file mode 100644
index 2c4dc2c83..000000000
--- a/src/com/android/gallery3d/util/IntArray.java
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-public class IntArray {
- private static final int INIT_CAPACITY = 8;
-
- private int mData[] = new int[INIT_CAPACITY];
- private int mSize = 0;
-
- public void add(int value) {
- if (mData.length == mSize) {
- int temp[] = new int[mSize + mSize];
- System.arraycopy(mData, 0, temp, 0, mSize);
- mData = temp;
- }
- mData[mSize++] = value;
- }
-
- public int removeLast() {
- mSize--;
- return mData[mSize];
- }
-
- public int size() {
- return mSize;
- }
-
- // For testing only
- public int[] toArray(int[] result) {
- if (result == null || result.length < mSize) {
- result = new int[mSize];
- }
- System.arraycopy(mData, 0, result, 0, mSize);
- return result;
- }
-
- public int[] getInternalArray() {
- return mData;
- }
-
- public void clear() {
- mSize = 0;
- if (mData.length != INIT_CAPACITY) mData = new int[INIT_CAPACITY];
- }
-}
diff --git a/src/com/android/gallery3d/util/InterruptableOutputStream.java b/src/com/android/gallery3d/util/InterruptableOutputStream.java
deleted file mode 100644
index 1ab62ab98..000000000
--- a/src/com/android/gallery3d/util/InterruptableOutputStream.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-import com.android.gallery3d.common.Utils;
-
-import java.io.IOException;
-import java.io.InterruptedIOException;
-import java.io.OutputStream;
-
-public class InterruptableOutputStream extends OutputStream {
-
- private static final int MAX_WRITE_BYTES = 4096;
-
- private OutputStream mOutputStream;
- private volatile boolean mIsInterrupted = false;
-
- public InterruptableOutputStream(OutputStream outputStream) {
- mOutputStream = Utils.checkNotNull(outputStream);
- }
-
- @Override
- public void write(int oneByte) throws IOException {
- if (mIsInterrupted) throw new InterruptedIOException();
- mOutputStream.write(oneByte);
- }
-
- @Override
- public void write(byte[] buffer, int offset, int count) throws IOException {
- int end = offset + count;
- while (offset < end) {
- if (mIsInterrupted) throw new InterruptedIOException();
- int bytesCount = Math.min(MAX_WRITE_BYTES, end - offset);
- mOutputStream.write(buffer, offset, bytesCount);
- offset += bytesCount;
- }
- }
-
- @Override
- public void close() throws IOException {
- mOutputStream.close();
- }
-
- @Override
- public void flush() throws IOException {
- if (mIsInterrupted) throw new InterruptedIOException();
- mOutputStream.flush();
- }
-
- public void interrupt() {
- mIsInterrupted = true;
- }
-}
diff --git a/src/com/android/gallery3d/util/JobLimiter.java b/src/com/android/gallery3d/util/JobLimiter.java
deleted file mode 100644
index 42b754153..000000000
--- a/src/com/android/gallery3d/util/JobLimiter.java
+++ /dev/null
@@ -1,159 +0,0 @@
-/*
- * Copyright (C) 2011 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-import com.android.gallery3d.common.Utils;
-import com.android.gallery3d.util.ThreadPool.Job;
-import com.android.gallery3d.util.ThreadPool.JobContext;
-
-import java.util.LinkedList;
-
-// Limit the number of concurrent jobs that has been submitted into a ThreadPool
-@SuppressWarnings("rawtypes")
-public class JobLimiter implements FutureListener {
- private static final String TAG = "JobLimiter";
-
- // State Transition:
- // INIT -> DONE, CANCELLED
- // DONE -> CANCELLED
- private static final int STATE_INIT = 0;
- private static final int STATE_DONE = 1;
- private static final int STATE_CANCELLED = 2;
-
- private final LinkedList<JobWrapper<?>> mJobs = new LinkedList<JobWrapper<?>>();
- private final ThreadPool mPool;
- private int mLimit;
-
- private static class JobWrapper<T> implements Future<T>, Job<T> {
- private int mState = STATE_INIT;
- private Job<T> mJob;
- private Future<T> mDelegate;
- private FutureListener<T> mListener;
- private T mResult;
-
- public JobWrapper(Job<T> job, FutureListener<T> listener) {
- mJob = job;
- mListener = listener;
- }
-
- public synchronized void setFuture(Future<T> future) {
- if (mState != STATE_INIT) return;
- mDelegate = future;
- }
-
- @Override
- public void cancel() {
- FutureListener<T> listener = null;
- synchronized (this) {
- if (mState != STATE_DONE) {
- listener = mListener;
- mJob = null;
- mListener = null;
- if (mDelegate != null) {
- mDelegate.cancel();
- mDelegate = null;
- }
- }
- mState = STATE_CANCELLED;
- mResult = null;
- notifyAll();
- }
- if (listener != null) listener.onFutureDone(this);
- }
-
- @Override
- public synchronized boolean isCancelled() {
- return mState == STATE_CANCELLED;
- }
-
- @Override
- public boolean isDone() {
- // Both CANCELLED AND DONE is considered as done
- return mState != STATE_INIT;
- }
-
- @Override
- public synchronized T get() {
- while (mState == STATE_INIT) {
- // handle the interrupted exception of wait()
- Utils.waitWithoutInterrupt(this);
- }
- return mResult;
- }
-
- @Override
- public void waitDone() {
- get();
- }
-
- @Override
- public T run(JobContext jc) {
- Job<T> job = null;
- synchronized (this) {
- if (mState == STATE_CANCELLED) return null;
- job = mJob;
- }
- T result = null;
- try {
- result = job.run(jc);
- } catch (Throwable t) {
- Log.w(TAG, "error executing job: " + job, t);
- }
- FutureListener<T> listener = null;
- synchronized (this) {
- if (mState == STATE_CANCELLED) return null;
- mState = STATE_DONE;
- listener = mListener;
- mListener = null;
- mJob = null;
- mResult = result;
- notifyAll();
- }
- if (listener != null) listener.onFutureDone(this);
- return result;
- }
- }
-
- public JobLimiter(ThreadPool pool, int limit) {
- mPool = Utils.checkNotNull(pool);
- mLimit = limit;
- }
-
- public synchronized <T> Future<T> submit(Job<T> job, FutureListener<T> listener) {
- JobWrapper<T> future = new JobWrapper<T>(Utils.checkNotNull(job), listener);
- mJobs.addLast(future);
- submitTasksIfAllowed();
- return future;
- }
-
- @SuppressWarnings({"rawtypes", "unchecked"})
- private void submitTasksIfAllowed() {
- while (mLimit > 0 && !mJobs.isEmpty()) {
- JobWrapper wrapper = mJobs.removeFirst();
- if (!wrapper.isCancelled()) {
- --mLimit;
- wrapper.setFuture(mPool.submit(wrapper, this));
- }
- }
- }
-
- @Override
- public synchronized void onFutureDone(Future future) {
- ++mLimit;
- submitTasksIfAllowed();
- }
-}
diff --git a/src/com/android/gallery3d/util/LinkedNode.java b/src/com/android/gallery3d/util/LinkedNode.java
deleted file mode 100644
index 4cfc3cded..000000000
--- a/src/com/android/gallery3d/util/LinkedNode.java
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-
-public class LinkedNode {
- private LinkedNode mPrev;
- private LinkedNode mNext;
-
- public LinkedNode() {
- mPrev = mNext = this;
- }
-
- public void insert(LinkedNode node) {
- node.mNext = mNext;
- mNext.mPrev = node;
- node.mPrev = this;
- mNext = node;
- }
-
- public void remove() {
- if (mNext == this) throw new IllegalStateException();
- mPrev.mNext = mNext;
- mNext.mPrev = mPrev;
- mPrev = mNext = null;
- }
-
- @SuppressWarnings("unchecked")
- public static class List<T extends LinkedNode> {
- private LinkedNode mHead = new LinkedNode();
-
- public void insertLast(T node) {
- mHead.mPrev.insert(node);
- }
-
- public T getFirst() {
- return (T) (mHead.mNext == mHead ? null : mHead.mNext);
- }
-
- public T getLast() {
- return (T) (mHead.mPrev == mHead ? null : mHead.mPrev);
- }
-
- public T nextOf(T node) {
- return (T) (node.mNext == mHead ? null : node.mNext);
- }
-
- public T previousOf(T node) {
- return (T) (node.mPrev == mHead ? null : node.mPrev);
- }
-
- }
-
- public static <T extends LinkedNode> List<T> newList() {
- return new List<T>();
- }
-}
diff --git a/src/com/android/gallery3d/util/Log.java b/src/com/android/gallery3d/util/Log.java
deleted file mode 100644
index d7f8e85d0..000000000
--- a/src/com/android/gallery3d/util/Log.java
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-public class Log {
- public static int v(String tag, String msg) {
- return android.util.Log.v(tag, msg);
- }
- public static int v(String tag, String msg, Throwable tr) {
- return android.util.Log.v(tag, msg, tr);
- }
- public static int d(String tag, String msg) {
- return android.util.Log.d(tag, msg);
- }
- public static int d(String tag, String msg, Throwable tr) {
- return android.util.Log.d(tag, msg, tr);
- }
- public static int i(String tag, String msg) {
- return android.util.Log.i(tag, msg);
- }
- public static int i(String tag, String msg, Throwable tr) {
- return android.util.Log.i(tag, msg, tr);
- }
- public static int w(String tag, String msg) {
- return android.util.Log.w(tag, msg);
- }
- public static int w(String tag, String msg, Throwable tr) {
- return android.util.Log.w(tag, msg, tr);
- }
- public static int w(String tag, Throwable tr) {
- return android.util.Log.w(tag, tr);
- }
- public static int e(String tag, String msg) {
- return android.util.Log.e(tag, msg);
- }
- public static int e(String tag, String msg, Throwable tr) {
- return android.util.Log.e(tag, msg, tr);
- }
-}
diff --git a/src/com/android/gallery3d/util/MediaSetUtils.java b/src/com/android/gallery3d/util/MediaSetUtils.java
deleted file mode 100644
index 043800561..000000000
--- a/src/com/android/gallery3d/util/MediaSetUtils.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-import android.os.Environment;
-
-import com.android.gallery3d.data.LocalAlbum;
-import com.android.gallery3d.data.LocalMergeAlbum;
-import com.android.gallery3d.data.MediaSet;
-import com.android.gallery3d.data.Path;
-
-import java.util.Comparator;
-
-public class MediaSetUtils {
- public static final Comparator<MediaSet> NAME_COMPARATOR = new NameComparator();
-
- public static final int CAMERA_BUCKET_ID = GalleryUtils.getBucketId(
- Environment.getExternalStorageDirectory().toString() + "/"
- + BucketNames.CAMERA);
- public static final int DOWNLOAD_BUCKET_ID = GalleryUtils.getBucketId(
- Environment.getExternalStorageDirectory().toString() + "/"
- + BucketNames.DOWNLOAD);
- public static final int EDITED_ONLINE_PHOTOS_BUCKET_ID = GalleryUtils.getBucketId(
- Environment.getExternalStorageDirectory().toString() + "/"
- + BucketNames.EDITED_ONLINE_PHOTOS);
- public static final int IMPORTED_BUCKET_ID = GalleryUtils.getBucketId(
- Environment.getExternalStorageDirectory().toString() + "/"
- + BucketNames.IMPORTED);
- public static final int SNAPSHOT_BUCKET_ID = GalleryUtils.getBucketId(
- Environment.getExternalStorageDirectory().toString() +
- "/" + BucketNames.SCREENSHOTS);
-
- private static final Path[] CAMERA_PATHS = {
- Path.fromString("/local/all/" + CAMERA_BUCKET_ID),
- Path.fromString("/local/image/" + CAMERA_BUCKET_ID),
- Path.fromString("/local/video/" + CAMERA_BUCKET_ID)};
-
- public static boolean isCameraSource(Path path) {
- return CAMERA_PATHS[0] == path || CAMERA_PATHS[1] == path
- || CAMERA_PATHS[2] == path;
- }
-
- // Sort MediaSets by name
- public static class NameComparator implements Comparator<MediaSet> {
- @Override
- public int compare(MediaSet set1, MediaSet set2) {
- int result = set1.getName().compareToIgnoreCase(set2.getName());
- if (result != 0) return result;
- return set1.getPath().toString().compareTo(set2.getPath().toString());
- }
- }
-}
diff --git a/src/com/android/gallery3d/util/MotionEventHelper.java b/src/com/android/gallery3d/util/MotionEventHelper.java
deleted file mode 100644
index 715f7fa69..000000000
--- a/src/com/android/gallery3d/util/MotionEventHelper.java
+++ /dev/null
@@ -1,120 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.util;
-
-import android.annotation.TargetApi;
-import android.graphics.Matrix;
-import android.util.FloatMath;
-import android.view.MotionEvent;
-import android.view.MotionEvent.PointerCoords;
-
-import com.android.gallery3d.common.ApiHelper;
-
-public final class MotionEventHelper {
- private MotionEventHelper() {}
-
- public static MotionEvent transformEvent(MotionEvent e, Matrix m) {
- // We try to use the new transform method if possible because it uses
- // less memory.
- if (ApiHelper.HAS_MOTION_EVENT_TRANSFORM) {
- return transformEventNew(e, m);
- } else {
- return transformEventOld(e, m);
- }
- }
-
- @TargetApi(ApiHelper.VERSION_CODES.HONEYCOMB)
- private static MotionEvent transformEventNew(MotionEvent e, Matrix m) {
- MotionEvent newEvent = MotionEvent.obtain(e);
- newEvent.transform(m);
- return newEvent;
- }
-
- // This is copied from Input.cpp in the android framework.
- private static MotionEvent transformEventOld(MotionEvent e, Matrix m) {
- long downTime = e.getDownTime();
- long eventTime = e.getEventTime();
- int action = e.getAction();
- int pointerCount = e.getPointerCount();
- int[] pointerIds = getPointerIds(e);
- PointerCoords[] pointerCoords = getPointerCoords(e);
- int metaState = e.getMetaState();
- float xPrecision = e.getXPrecision();
- float yPrecision = e.getYPrecision();
- int deviceId = e.getDeviceId();
- int edgeFlags = e.getEdgeFlags();
- int source = e.getSource();
- int flags = e.getFlags();
-
- // Copy the x and y coordinates into an array, map them, and copy back.
- float[] xy = new float[pointerCoords.length * 2];
- for (int i = 0; i < pointerCount;i++) {
- xy[2 * i] = pointerCoords[i].x;
- xy[2 * i + 1] = pointerCoords[i].y;
- }
- m.mapPoints(xy);
- for (int i = 0; i < pointerCount;i++) {
- pointerCoords[i].x = xy[2 * i];
- pointerCoords[i].y = xy[2 * i + 1];
- pointerCoords[i].orientation = transformAngle(
- m, pointerCoords[i].orientation);
- }
-
- MotionEvent n = MotionEvent.obtain(downTime, eventTime, action,
- pointerCount, pointerIds, pointerCoords, metaState, xPrecision,
- yPrecision, deviceId, edgeFlags, source, flags);
-
- return n;
- }
-
- private static int[] getPointerIds(MotionEvent e) {
- int n = e.getPointerCount();
- int[] r = new int[n];
- for (int i = 0; i < n; i++) {
- r[i] = e.getPointerId(i);
- }
- return r;
- }
-
- private static PointerCoords[] getPointerCoords(MotionEvent e) {
- int n = e.getPointerCount();
- PointerCoords[] r = new PointerCoords[n];
- for (int i = 0; i < n; i++) {
- r[i] = new PointerCoords();
- e.getPointerCoords(i, r[i]);
- }
- return r;
- }
-
- private static float transformAngle(Matrix m, float angleRadians) {
- // Construct and transform a vector oriented at the specified clockwise
- // angle from vertical. Coordinate system: down is increasing Y, right is
- // increasing X.
- float[] v = new float[2];
- v[0] = FloatMath.sin(angleRadians);
- v[1] = -FloatMath.cos(angleRadians);
- m.mapVectors(v);
-
- // Derive the transformed vector's clockwise angle from vertical.
- float result = (float) Math.atan2(v[0], -v[1]);
- if (result < -Math.PI / 2) {
- result += Math.PI;
- } else if (result > Math.PI / 2) {
- result -= Math.PI;
- }
- return result;
- }
-}
diff --git a/src/com/android/gallery3d/util/Profile.java b/src/com/android/gallery3d/util/Profile.java
deleted file mode 100644
index 7ed72c90e..000000000
--- a/src/com/android/gallery3d/util/Profile.java
+++ /dev/null
@@ -1,226 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-import android.os.Handler;
-import android.os.HandlerThread;
-import android.os.Process;
-
-import java.util.ArrayList;
-import java.util.Random;
-
-// The Profile class is used to collect profiling information for a thread. It
-// samples stack traces for a thread periodically. enable() and disable() is
-// used to enable and disable profiling for the calling thread. The profiling
-// information can then be dumped to a file using the dumpToFile() method.
-//
-// The disableAll() method can be used to disable profiling for all threads and
-// can be called in onPause() to ensure all profiling is disabled when an
-// activity is paused.
-public class Profile {
- @SuppressWarnings("unused")
- private static final String TAG = "Profile";
- private static final int NS_PER_MS = 1000000;
-
- // This is a watchdog entry for one thread.
- // For every cycleTime period, we dump the stack of the thread.
- private static class WatchEntry {
- Thread thread;
-
- // Both are in milliseconds
- int cycleTime;
- int wakeTime;
-
- boolean isHolding;
- ArrayList<String[]> holdingStacks = new ArrayList<String[]>();
- }
-
- // This is a watchdog thread which dumps stacks of other threads periodically.
- private static Watchdog sWatchdog = new Watchdog();
-
- private static class Watchdog {
- private ArrayList<WatchEntry> mList = new ArrayList<WatchEntry>();
- private HandlerThread mHandlerThread;
- private Handler mHandler;
- private Runnable mProcessRunnable = new Runnable() {
- @Override
- public void run() {
- synchronized (Watchdog.this) {
- processList();
- }
- }
- };
- private Random mRandom = new Random();
- private ProfileData mProfileData = new ProfileData();
-
- public Watchdog() {
- mHandlerThread = new HandlerThread("Watchdog Handler",
- Process.THREAD_PRIORITY_FOREGROUND);
- mHandlerThread.start();
- mHandler = new Handler(mHandlerThread.getLooper());
- }
-
- public synchronized void addWatchEntry(Thread thread, int cycleTime) {
- WatchEntry e = new WatchEntry();
- e.thread = thread;
- e.cycleTime = cycleTime;
- int firstDelay = 1 + mRandom.nextInt(cycleTime);
- e.wakeTime = (int) (System.nanoTime() / NS_PER_MS) + firstDelay;
- mList.add(e);
- processList();
- }
-
- public synchronized void removeWatchEntry(Thread thread) {
- for (int i = 0; i < mList.size(); i++) {
- if (mList.get(i).thread == thread) {
- mList.remove(i);
- break;
- }
- }
- processList();
- }
-
- public synchronized void removeAllWatchEntries() {
- mList.clear();
- processList();
- }
-
- private void processList() {
- mHandler.removeCallbacks(mProcessRunnable);
- if (mList.size() == 0) return;
-
- int currentTime = (int) (System.nanoTime() / NS_PER_MS);
- int nextWakeTime = 0;
-
- for (WatchEntry entry : mList) {
- if (currentTime > entry.wakeTime) {
- entry.wakeTime += entry.cycleTime;
- Thread thread = entry.thread;
- sampleStack(entry);
- }
-
- if (entry.wakeTime > nextWakeTime) {
- nextWakeTime = entry.wakeTime;
- }
- }
-
- long delay = nextWakeTime - currentTime;
- mHandler.postDelayed(mProcessRunnable, delay);
- }
-
- private void sampleStack(WatchEntry entry) {
- Thread thread = entry.thread;
- StackTraceElement[] stack = thread.getStackTrace();
- String[] lines = new String[stack.length];
- for (int i = 0; i < stack.length; i++) {
- lines[i] = stack[i].toString();
- }
- if (entry.isHolding) {
- entry.holdingStacks.add(lines);
- } else {
- mProfileData.addSample(lines);
- }
- }
-
- private WatchEntry findEntry(Thread thread) {
- for (int i = 0; i < mList.size(); i++) {
- WatchEntry entry = mList.get(i);
- if (entry.thread == thread) return entry;
- }
- return null;
- }
-
- public synchronized void dumpToFile(String filename) {
- mProfileData.dumpToFile(filename);
- }
-
- public synchronized void reset() {
- mProfileData.reset();
- }
-
- public synchronized void hold(Thread t) {
- WatchEntry entry = findEntry(t);
-
- // This can happen if the profiling is disabled (probably from
- // another thread). Same check is applied in commit() and drop()
- // below.
- if (entry == null) return;
-
- entry.isHolding = true;
- }
-
- public synchronized void commit(Thread t) {
- WatchEntry entry = findEntry(t);
- if (entry == null) return;
- ArrayList<String[]> stacks = entry.holdingStacks;
- for (int i = 0; i < stacks.size(); i++) {
- mProfileData.addSample(stacks.get(i));
- }
- entry.isHolding = false;
- entry.holdingStacks.clear();
- }
-
- public synchronized void drop(Thread t) {
- WatchEntry entry = findEntry(t);
- if (entry == null) return;
- entry.isHolding = false;
- entry.holdingStacks.clear();
- }
- }
-
- // Enable profiling for the calling thread. Periodically (every cycleTimeInMs
- // milliseconds) sample the stack trace of the calling thread.
- public static void enable(int cycleTimeInMs) {
- Thread t = Thread.currentThread();
- sWatchdog.addWatchEntry(t, cycleTimeInMs);
- }
-
- // Disable profiling for the calling thread.
- public static void disable() {
- sWatchdog.removeWatchEntry(Thread.currentThread());
- }
-
- // Disable profiling for all threads.
- public static void disableAll() {
- sWatchdog.removeAllWatchEntries();
- }
-
- // Dump the profiling data to a file.
- public static void dumpToFile(String filename) {
- sWatchdog.dumpToFile(filename);
- }
-
- // Reset the collected profiling data.
- public static void reset() {
- sWatchdog.reset();
- }
-
- // Hold the future samples coming from current thread until commit() or
- // drop() is called, and those samples are recorded or ignored as a result.
- // This must called after enable() to be effective.
- public static void hold() {
- sWatchdog.hold(Thread.currentThread());
- }
-
- public static void commit() {
- sWatchdog.commit(Thread.currentThread());
- }
-
- public static void drop() {
- sWatchdog.drop(Thread.currentThread());
- }
-}
diff --git a/src/com/android/gallery3d/util/ProfileData.java b/src/com/android/gallery3d/util/ProfileData.java
deleted file mode 100644
index a1bb8e1e4..000000000
--- a/src/com/android/gallery3d/util/ProfileData.java
+++ /dev/null
@@ -1,168 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-import android.util.Log;
-
-import com.android.gallery3d.common.Utils;
-
-import java.io.DataOutputStream;
-import java.io.FileOutputStream;
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.Map.Entry;
-
-// ProfileData keeps profiling samples in a tree structure.
-// The addSample() method adds a sample. The dumpToFile() method saves the data
-// to a file. The reset() method clears all samples.
-public class ProfileData {
- @SuppressWarnings("unused")
- private static final String TAG = "ProfileData";
-
- private static class Node {
- public int id; // this is the name of this node, mapped from mNameToId
- public Node parent;
- public int sampleCount;
- public ArrayList<Node> children;
- public Node(Node parent, int id) {
- this.parent = parent;
- this.id = id;
- }
- }
-
- private Node mRoot;
- private int mNextId;
- private HashMap<String, Integer> mNameToId;
- private DataOutputStream mOut;
- private byte mScratch[] = new byte[4]; // scratch space for writeInt()
-
- public ProfileData() {
- mRoot = new Node(null, -1); // The id of the root node is unused.
- mNameToId = new HashMap<String, Integer>();
- }
-
- public void reset() {
- mRoot = new Node(null, -1);
- mNameToId.clear();
- mNextId = 0;
- }
-
- private int nameToId(String name) {
- Integer id = mNameToId.get(name);
- if (id == null) {
- id = ++mNextId; // The tool doesn't want id=0, so we start from 1.
- mNameToId.put(name, id);
- }
- return id;
- }
-
- public void addSample(String[] stack) {
- int[] ids = new int[stack.length];
- for (int i = 0; i < stack.length; i++) {
- ids[i] = nameToId(stack[i]);
- }
-
- Node node = mRoot;
- for (int i = stack.length - 1; i >= 0; i--) {
- if (node.children == null) {
- node.children = new ArrayList<Node>();
- }
-
- int id = ids[i];
- ArrayList<Node> children = node.children;
- int j;
- for (j = 0; j < children.size(); j++) {
- if (children.get(j).id == id) break;
- }
- if (j == children.size()) {
- children.add(new Node(node, id));
- }
-
- node = children.get(j);
- }
-
- node.sampleCount++;
- }
-
- public void dumpToFile(String filename) {
- try {
- mOut = new DataOutputStream(new FileOutputStream(filename));
- // Start record
- writeInt(0);
- writeInt(3);
- writeInt(1);
- writeInt(20000); // Sampling period: 20ms
- writeInt(0);
-
- // Samples
- writeAllStacks(mRoot, 0);
-
- // End record
- writeInt(0);
- writeInt(1);
- writeInt(0);
- writeAllSymbols();
- } catch (IOException ex) {
- Log.w("Failed to dump to file", ex);
- } finally {
- Utils.closeSilently(mOut);
- }
- }
-
- // Writes out one stack, consisting of N+2 words:
- // first word: sample count
- // second word: depth of the stack (N)
- // N words: each word is the id of one address in the stack
- private void writeOneStack(Node node, int depth) throws IOException {
- writeInt(node.sampleCount);
- writeInt(depth);
- while (depth-- > 0) {
- writeInt(node.id);
- node = node.parent;
- }
- }
-
- private void writeAllStacks(Node node, int depth) throws IOException {
- if (node.sampleCount > 0) {
- writeOneStack(node, depth);
- }
-
- ArrayList<Node> children = node.children;
- if (children != null) {
- for (int i = 0; i < children.size(); i++) {
- writeAllStacks(children.get(i), depth + 1);
- }
- }
- }
-
- // Writes out the symbol table. Each line is like:
- // 0x17e java.util.ArrayList.isEmpty(ArrayList.java:319)
- private void writeAllSymbols() throws IOException {
- for (Entry<String, Integer> entry : mNameToId.entrySet()) {
- mOut.writeBytes(String.format("0x%x %s\n", entry.getValue(), entry.getKey()));
- }
- }
-
- private void writeInt(int v) throws IOException {
- mScratch[0] = (byte) v;
- mScratch[1] = (byte) (v >> 8);
- mScratch[2] = (byte) (v >> 16);
- mScratch[3] = (byte) (v >> 24);
- mOut.write(mScratch);
- }
-}
diff --git a/src/com/android/gallery3d/util/RangeArray.java b/src/com/android/gallery3d/util/RangeArray.java
deleted file mode 100644
index 8e61348a3..000000000
--- a/src/com/android/gallery3d/util/RangeArray.java
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-// This is an array whose index ranges from min to max (inclusive).
-public class RangeArray<T> {
- private T[] mData;
- private int mOffset;
-
- public RangeArray(int min, int max) {
- mData = (T[]) new Object[max - min + 1];
- mOffset = min;
- }
-
- // Wraps around an existing array
- public RangeArray(T[] src, int min, int max) {
- if (max - min + 1 != src.length) {
- throw new AssertionError();
- }
- mData = src;
- mOffset = min;
- }
-
- public void put(int i, T object) {
- mData[i - mOffset] = object;
- }
-
- public T get(int i) {
- return mData[i - mOffset];
- }
-
- public int indexOf(T object) {
- for (int i = 0; i < mData.length; i++) {
- if (mData[i] == object) return i + mOffset;
- }
- return Integer.MAX_VALUE;
- }
-}
diff --git a/src/com/android/gallery3d/util/RangeBoolArray.java b/src/com/android/gallery3d/util/RangeBoolArray.java
deleted file mode 100644
index 035fc40a4..000000000
--- a/src/com/android/gallery3d/util/RangeBoolArray.java
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-// This is an array whose index ranges from min to max (inclusive).
-public class RangeBoolArray {
- private boolean[] mData;
- private int mOffset;
-
- public RangeBoolArray(int min, int max) {
- mData = new boolean[max - min + 1];
- mOffset = min;
- }
-
- // Wraps around an existing array
- public RangeBoolArray(boolean[] src, int min, int max) {
- mData = src;
- mOffset = min;
- }
-
- public void put(int i, boolean object) {
- mData[i - mOffset] = object;
- }
-
- public boolean get(int i) {
- return mData[i - mOffset];
- }
-
- public int indexOf(boolean object) {
- for (int i = 0; i < mData.length; i++) {
- if (mData[i] == object) return i + mOffset;
- }
- return Integer.MAX_VALUE;
- }
-}
diff --git a/src/com/android/gallery3d/util/RangeIntArray.java b/src/com/android/gallery3d/util/RangeIntArray.java
deleted file mode 100644
index 9dbb99fac..000000000
--- a/src/com/android/gallery3d/util/RangeIntArray.java
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-// This is an array whose index ranges from min to max (inclusive).
-public class RangeIntArray {
- private int[] mData;
- private int mOffset;
-
- public RangeIntArray(int min, int max) {
- mData = new int[max - min + 1];
- mOffset = min;
- }
-
- // Wraps around an existing array
- public RangeIntArray(int[] src, int min, int max) {
- mData = src;
- mOffset = min;
- }
-
- public void put(int i, int object) {
- mData[i - mOffset] = object;
- }
-
- public int get(int i) {
- return mData[i - mOffset];
- }
-
- public int indexOf(int object) {
- for (int i = 0; i < mData.length; i++) {
- if (mData[i] == object) return i + mOffset;
- }
- return Integer.MAX_VALUE;
- }
-}
diff --git a/src/com/android/gallery3d/util/ReverseGeocoder.java b/src/com/android/gallery3d/util/ReverseGeocoder.java
deleted file mode 100644
index a8b26d9b5..000000000
--- a/src/com/android/gallery3d/util/ReverseGeocoder.java
+++ /dev/null
@@ -1,418 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-import android.content.Context;
-import android.location.Address;
-import android.location.Geocoder;
-import android.location.Location;
-import android.location.LocationManager;
-import android.net.ConnectivityManager;
-import android.net.NetworkInfo;
-
-import com.android.gallery3d.common.BlobCache;
-
-import java.io.ByteArrayInputStream;
-import java.io.ByteArrayOutputStream;
-import java.io.DataInputStream;
-import java.io.DataOutputStream;
-import java.io.IOException;
-import java.util.List;
-import java.util.Locale;
-
-public class ReverseGeocoder {
- @SuppressWarnings("unused")
- private static final String TAG = "ReverseGeocoder";
- public static final int EARTH_RADIUS_METERS = 6378137;
- public static final int LAT_MIN = -90;
- public static final int LAT_MAX = 90;
- public static final int LON_MIN = -180;
- public static final int LON_MAX = 180;
- private static final int MAX_COUNTRY_NAME_LENGTH = 8;
- // If two points are within 20 miles of each other, use
- // "Around Palo Alto, CA" or "Around Mountain View, CA".
- // instead of directly jumping to the next level and saying
- // "California, US".
- private static final int MAX_LOCALITY_MILE_RANGE = 20;
-
- private static final String GEO_CACHE_FILE = "rev_geocoding";
- private static final int GEO_CACHE_MAX_ENTRIES = 1000;
- private static final int GEO_CACHE_MAX_BYTES = 500 * 1024;
- private static final int GEO_CACHE_VERSION = 0;
-
- public static class SetLatLong {
- // The latitude and longitude of the min latitude point.
- public double mMinLatLatitude = LAT_MAX;
- public double mMinLatLongitude;
- // The latitude and longitude of the max latitude point.
- public double mMaxLatLatitude = LAT_MIN;
- public double mMaxLatLongitude;
- // The latitude and longitude of the min longitude point.
- public double mMinLonLatitude;
- public double mMinLonLongitude = LON_MAX;
- // The latitude and longitude of the max longitude point.
- public double mMaxLonLatitude;
- public double mMaxLonLongitude = LON_MIN;
- }
-
- private Context mContext;
- private Geocoder mGeocoder;
- private BlobCache mGeoCache;
- private ConnectivityManager mConnectivityManager;
- private static Address sCurrentAddress; // last known address
-
- public ReverseGeocoder(Context context) {
- mContext = context;
- mGeocoder = new Geocoder(mContext);
- mGeoCache = CacheManager.getCache(context, GEO_CACHE_FILE,
- GEO_CACHE_MAX_ENTRIES, GEO_CACHE_MAX_BYTES,
- GEO_CACHE_VERSION);
- mConnectivityManager = (ConnectivityManager)
- context.getSystemService(Context.CONNECTIVITY_SERVICE);
- }
-
- public String computeAddress(SetLatLong set) {
- // The overall min and max latitudes and longitudes of the set.
- double setMinLatitude = set.mMinLatLatitude;
- double setMinLongitude = set.mMinLatLongitude;
- double setMaxLatitude = set.mMaxLatLatitude;
- double setMaxLongitude = set.mMaxLatLongitude;
- if (Math.abs(set.mMaxLatLatitude - set.mMinLatLatitude)
- < Math.abs(set.mMaxLonLongitude - set.mMinLonLongitude)) {
- setMinLatitude = set.mMinLonLatitude;
- setMinLongitude = set.mMinLonLongitude;
- setMaxLatitude = set.mMaxLonLatitude;
- setMaxLongitude = set.mMaxLonLongitude;
- }
- Address addr1 = lookupAddress(setMinLatitude, setMinLongitude, true);
- Address addr2 = lookupAddress(setMaxLatitude, setMaxLongitude, true);
- if (addr1 == null)
- addr1 = addr2;
- if (addr2 == null)
- addr2 = addr1;
- if (addr1 == null || addr2 == null) {
- return null;
- }
-
- // Get current location, we decide the granularity of the string based
- // on this.
- LocationManager locationManager =
- (LocationManager) mContext.getSystemService(Context.LOCATION_SERVICE);
- Location location = null;
- List<String> providers = locationManager.getAllProviders();
- for (int i = 0; i < providers.size(); ++i) {
- String provider = providers.get(i);
- location = (provider != null) ? locationManager.getLastKnownLocation(provider) : null;
- if (location != null)
- break;
- }
- String currentCity = "";
- String currentAdminArea = "";
- String currentCountry = Locale.getDefault().getCountry();
- if (location != null) {
- Address currentAddress = lookupAddress(
- location.getLatitude(), location.getLongitude(), true);
- if (currentAddress == null) {
- currentAddress = sCurrentAddress;
- } else {
- sCurrentAddress = currentAddress;
- }
- if (currentAddress != null && currentAddress.getCountryCode() != null) {
- currentCity = checkNull(currentAddress.getLocality());
- currentCountry = checkNull(currentAddress.getCountryCode());
- currentAdminArea = checkNull(currentAddress.getAdminArea());
- }
- }
-
- String closestCommonLocation = null;
- String addr1Locality = checkNull(addr1.getLocality());
- String addr2Locality = checkNull(addr2.getLocality());
- String addr1AdminArea = checkNull(addr1.getAdminArea());
- String addr2AdminArea = checkNull(addr2.getAdminArea());
- String addr1CountryCode = checkNull(addr1.getCountryCode());
- String addr2CountryCode = checkNull(addr2.getCountryCode());
-
- if (currentCity.equals(addr1Locality) || currentCity.equals(addr2Locality)) {
- String otherCity = currentCity;
- if (currentCity.equals(addr1Locality)) {
- otherCity = addr2Locality;
- if (otherCity.length() == 0) {
- otherCity = addr2AdminArea;
- if (!currentCountry.equals(addr2CountryCode)) {
- otherCity += " " + addr2CountryCode;
- }
- }
- addr2Locality = addr1Locality;
- addr2AdminArea = addr1AdminArea;
- addr2CountryCode = addr1CountryCode;
- } else {
- otherCity = addr1Locality;
- if (otherCity.length() == 0) {
- otherCity = addr1AdminArea;
- if (!currentCountry.equals(addr1CountryCode)) {
- otherCity += " " + addr1CountryCode;
- }
- }
- addr1Locality = addr2Locality;
- addr1AdminArea = addr2AdminArea;
- addr1CountryCode = addr2CountryCode;
- }
- closestCommonLocation = valueIfEqual(addr1.getAddressLine(0), addr2.getAddressLine(0));
- if (closestCommonLocation != null && !("null".equals(closestCommonLocation))) {
- if (!currentCity.equals(otherCity)) {
- closestCommonLocation += " - " + otherCity;
- }
- return closestCommonLocation;
- }
-
- // Compare thoroughfare (street address) next.
- closestCommonLocation = valueIfEqual(addr1.getThoroughfare(), addr2.getThoroughfare());
- if (closestCommonLocation != null && !("null".equals(closestCommonLocation))) {
- return closestCommonLocation;
- }
- }
-
- // Compare the locality.
- closestCommonLocation = valueIfEqual(addr1Locality, addr2Locality);
- if (closestCommonLocation != null && !("".equals(closestCommonLocation))) {
- String adminArea = addr1AdminArea;
- String countryCode = addr1CountryCode;
- if (adminArea != null && adminArea.length() > 0) {
- if (!countryCode.equals(currentCountry)) {
- closestCommonLocation += ", " + adminArea + " " + countryCode;
- } else {
- closestCommonLocation += ", " + adminArea;
- }
- }
- return closestCommonLocation;
- }
-
- // If the admin area is the same as the current location, we hide it and
- // instead show the city name.
- if (currentAdminArea.equals(addr1AdminArea) && currentAdminArea.equals(addr2AdminArea)) {
- if ("".equals(addr1Locality)) {
- addr1Locality = addr2Locality;
- }
- if ("".equals(addr2Locality)) {
- addr2Locality = addr1Locality;
- }
- if (!"".equals(addr1Locality)) {
- if (addr1Locality.equals(addr2Locality)) {
- closestCommonLocation = addr1Locality + ", " + currentAdminArea;
- } else {
- closestCommonLocation = addr1Locality + " - " + addr2Locality;
- }
- return closestCommonLocation;
- }
- }
-
- // Just choose one of the localities if within a MAX_LOCALITY_MILE_RANGE
- // mile radius.
- float[] distanceFloat = new float[1];
- Location.distanceBetween(setMinLatitude, setMinLongitude,
- setMaxLatitude, setMaxLongitude, distanceFloat);
- int distance = (int) GalleryUtils.toMile(distanceFloat[0]);
- if (distance < MAX_LOCALITY_MILE_RANGE) {
- // Try each of the points and just return the first one to have a
- // valid address.
- closestCommonLocation = getLocalityAdminForAddress(addr1, true);
- if (closestCommonLocation != null) {
- return closestCommonLocation;
- }
- closestCommonLocation = getLocalityAdminForAddress(addr2, true);
- if (closestCommonLocation != null) {
- return closestCommonLocation;
- }
- }
-
- // Check the administrative area.
- closestCommonLocation = valueIfEqual(addr1AdminArea, addr2AdminArea);
- if (closestCommonLocation != null && !("".equals(closestCommonLocation))) {
- String countryCode = addr1CountryCode;
- if (!countryCode.equals(currentCountry)) {
- if (countryCode != null && countryCode.length() > 0) {
- closestCommonLocation += " " + countryCode;
- }
- }
- return closestCommonLocation;
- }
-
- // Check the country codes.
- closestCommonLocation = valueIfEqual(addr1CountryCode, addr2CountryCode);
- if (closestCommonLocation != null && !("".equals(closestCommonLocation))) {
- return closestCommonLocation;
- }
- // There is no intersection, let's choose a nicer name.
- String addr1Country = addr1.getCountryName();
- String addr2Country = addr2.getCountryName();
- if (addr1Country == null)
- addr1Country = addr1CountryCode;
- if (addr2Country == null)
- addr2Country = addr2CountryCode;
- if (addr1Country == null || addr2Country == null)
- return null;
- if (addr1Country.length() > MAX_COUNTRY_NAME_LENGTH || addr2Country.length() > MAX_COUNTRY_NAME_LENGTH) {
- closestCommonLocation = addr1CountryCode + " - " + addr2CountryCode;
- } else {
- closestCommonLocation = addr1Country + " - " + addr2Country;
- }
- return closestCommonLocation;
- }
-
- private String checkNull(String locality) {
- if (locality == null)
- return "";
- if (locality.equals("null"))
- return "";
- return locality;
- }
-
- private String getLocalityAdminForAddress(final Address addr, final boolean approxLocation) {
- if (addr == null)
- return "";
- String localityAdminStr = addr.getLocality();
- if (localityAdminStr != null && !("null".equals(localityAdminStr))) {
- if (approxLocation) {
- // TODO: Uncomment these lines as soon as we may translations
- // for Res.string.around.
- // localityAdminStr =
- // mContext.getResources().getString(Res.string.around) + " " +
- // localityAdminStr;
- }
- String adminArea = addr.getAdminArea();
- if (adminArea != null && adminArea.length() > 0) {
- localityAdminStr += ", " + adminArea;
- }
- return localityAdminStr;
- }
- return null;
- }
-
- public Address lookupAddress(final double latitude, final double longitude,
- boolean useCache) {
- try {
- long locationKey = (long) (((latitude + LAT_MAX) * 2 * LAT_MAX
- + (longitude + LON_MAX)) * EARTH_RADIUS_METERS);
- byte[] cachedLocation = null;
- if (useCache && mGeoCache != null) {
- cachedLocation = mGeoCache.lookup(locationKey);
- }
- Address address = null;
- NetworkInfo networkInfo = mConnectivityManager.getActiveNetworkInfo();
- if (cachedLocation == null || cachedLocation.length == 0) {
- if (networkInfo == null || !networkInfo.isConnected()) {
- return null;
- }
- List<Address> addresses = mGeocoder.getFromLocation(latitude, longitude, 1);
- if (!addresses.isEmpty()) {
- address = addresses.get(0);
- ByteArrayOutputStream bos = new ByteArrayOutputStream();
- DataOutputStream dos = new DataOutputStream(bos);
- Locale locale = address.getLocale();
- writeUTF(dos, locale.getLanguage());
- writeUTF(dos, locale.getCountry());
- writeUTF(dos, locale.getVariant());
-
- writeUTF(dos, address.getThoroughfare());
- int numAddressLines = address.getMaxAddressLineIndex();
- dos.writeInt(numAddressLines);
- for (int i = 0; i < numAddressLines; ++i) {
- writeUTF(dos, address.getAddressLine(i));
- }
- writeUTF(dos, address.getFeatureName());
- writeUTF(dos, address.getLocality());
- writeUTF(dos, address.getAdminArea());
- writeUTF(dos, address.getSubAdminArea());
-
- writeUTF(dos, address.getCountryName());
- writeUTF(dos, address.getCountryCode());
- writeUTF(dos, address.getPostalCode());
- writeUTF(dos, address.getPhone());
- writeUTF(dos, address.getUrl());
-
- dos.flush();
- if (mGeoCache != null) {
- mGeoCache.insert(locationKey, bos.toByteArray());
- }
- dos.close();
- }
- } else {
- // Parsing the address from the byte stream.
- DataInputStream dis = new DataInputStream(
- new ByteArrayInputStream(cachedLocation));
- String language = readUTF(dis);
- String country = readUTF(dis);
- String variant = readUTF(dis);
- Locale locale = null;
- if (language != null) {
- if (country == null) {
- locale = new Locale(language);
- } else if (variant == null) {
- locale = new Locale(language, country);
- } else {
- locale = new Locale(language, country, variant);
- }
- }
- if (!locale.getLanguage().equals(Locale.getDefault().getLanguage())) {
- dis.close();
- return lookupAddress(latitude, longitude, false);
- }
- address = new Address(locale);
-
- address.setThoroughfare(readUTF(dis));
- int numAddressLines = dis.readInt();
- for (int i = 0; i < numAddressLines; ++i) {
- address.setAddressLine(i, readUTF(dis));
- }
- address.setFeatureName(readUTF(dis));
- address.setLocality(readUTF(dis));
- address.setAdminArea(readUTF(dis));
- address.setSubAdminArea(readUTF(dis));
-
- address.setCountryName(readUTF(dis));
- address.setCountryCode(readUTF(dis));
- address.setPostalCode(readUTF(dis));
- address.setPhone(readUTF(dis));
- address.setUrl(readUTF(dis));
- dis.close();
- }
- return address;
- } catch (Exception e) {
- // Ignore.
- }
- return null;
- }
-
- private String valueIfEqual(String a, String b) {
- return (a != null && b != null && a.equalsIgnoreCase(b)) ? a : null;
- }
-
- public static final void writeUTF(DataOutputStream dos, String string) throws IOException {
- if (string == null) {
- dos.writeUTF("");
- } else {
- dos.writeUTF(string);
- }
- }
-
- public static final String readUTF(DataInputStream dis) throws IOException {
- String retVal = dis.readUTF();
- if (retVal.length() == 0)
- return null;
- return retVal;
- }
-}
diff --git a/src/com/android/gallery3d/util/SaveVideoFileInfo.java b/src/com/android/gallery3d/util/SaveVideoFileInfo.java
deleted file mode 100644
index c7e5e8568..000000000
--- a/src/com/android/gallery3d/util/SaveVideoFileInfo.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-import java.io.File;
-
-public class SaveVideoFileInfo {
- public File mFile = null;
- public String mFileName = null;
- // This the full directory path.
- public File mDirectory = null;
- // This is just the folder's name.
- public String mFolderName = null;
-
-}
diff --git a/src/com/android/gallery3d/util/SaveVideoFileUtils.java b/src/com/android/gallery3d/util/SaveVideoFileUtils.java
deleted file mode 100644
index 10c41de90..000000000
--- a/src/com/android/gallery3d/util/SaveVideoFileUtils.java
+++ /dev/null
@@ -1,154 +0,0 @@
-/*
- * Copyright (C) 2012 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.gallery3d.util;
-
-import android.content.ContentResolver;
-import android.content.ContentValues;
-import android.database.Cursor;
-import android.media.MediaMetadataRetriever;
-import android.net.Uri;
-import android.os.Environment;
-import android.provider.MediaStore.Video;
-import android.provider.MediaStore.Video.VideoColumns;
-
-import com.android.gallery3d.filtershow.tools.SaveImage.ContentResolverQueryCallback;
-
-import java.io.File;
-import java.sql.Date;
-import java.text.SimpleDateFormat;
-
-public class SaveVideoFileUtils {
- // This function can decide which folder to save the video file, and generate
- // the needed information for the video file including filename.
- public static SaveVideoFileInfo getDstMp4FileInfo(String fileNameFormat,
- ContentResolver contentResolver, Uri uri, String defaultFolderName) {
- SaveVideoFileInfo dstFileInfo = new SaveVideoFileInfo();
- // Use the default save directory if the source directory cannot be
- // saved.
- dstFileInfo.mDirectory = getSaveDirectory(contentResolver, uri);
- if ((dstFileInfo.mDirectory == null) || !dstFileInfo.mDirectory.canWrite()) {
- dstFileInfo.mDirectory = new File(Environment.getExternalStorageDirectory(),
- BucketNames.DOWNLOAD);
- dstFileInfo.mFolderName = defaultFolderName;
- } else {
- dstFileInfo.mFolderName = dstFileInfo.mDirectory.getName();
- }
- dstFileInfo.mFileName = new SimpleDateFormat(fileNameFormat).format(
- new Date(System.currentTimeMillis()));
-
- dstFileInfo.mFile = new File(dstFileInfo.mDirectory, dstFileInfo.mFileName + ".mp4");
- return dstFileInfo;
- }
-
- private static void querySource(ContentResolver contentResolver, Uri uri,
- String[] projection, ContentResolverQueryCallback callback) {
- Cursor cursor = null;
- try {
- cursor = contentResolver.query(uri, projection, null, null, null);
- if ((cursor != null) && cursor.moveToNext()) {
- callback.onCursorResult(cursor);
- }
- } catch (Exception e) {
- // Ignore error for lacking the data column from the source.
- } finally {
- if (cursor != null) {
- cursor.close();
- }
- }
- }
-
- private static File getSaveDirectory(ContentResolver contentResolver, Uri uri) {
- final File[] dir = new File[1];
- querySource(contentResolver, uri,
- new String[] { VideoColumns.DATA },
- new ContentResolverQueryCallback() {
- @Override
- public void onCursorResult(Cursor cursor) {
- dir[0] = new File(cursor.getString(0)).getParentFile();
- }
- });
- return dir[0];
- }
-
-
- /**
- * Insert the content (saved file) with proper video properties.
- */
- public static Uri insertContent(SaveVideoFileInfo mDstFileInfo,
- ContentResolver contentResolver, Uri uri ) {
- long nowInMs = System.currentTimeMillis();
- long nowInSec = nowInMs / 1000;
- final ContentValues values = new ContentValues(13);
- values.put(Video.Media.TITLE, mDstFileInfo.mFileName);
- values.put(Video.Media.DISPLAY_NAME, mDstFileInfo.mFile.getName());
- values.put(Video.Media.MIME_TYPE, "video/mp4");
- values.put(Video.Media.DATE_TAKEN, nowInMs);
- values.put(Video.Media.DATE_MODIFIED, nowInSec);
- values.put(Video.Media.DATE_ADDED, nowInSec);
- values.put(Video.Media.DATA, mDstFileInfo.mFile.getAbsolutePath());
- values.put(Video.Media.SIZE, mDstFileInfo.mFile.length());
- int durationMs = retriveVideoDurationMs(mDstFileInfo.mFile.getPath());
- values.put(Video.Media.DURATION, durationMs);
- // Copy the data taken and location info from src.
- String[] projection = new String[] {
- VideoColumns.DATE_TAKEN,
- VideoColumns.LATITUDE,
- VideoColumns.LONGITUDE,
- VideoColumns.RESOLUTION,
- };
-
- // Copy some info from the source file.
- querySource(contentResolver, uri, projection,
- new ContentResolverQueryCallback() {
- @Override
- public void onCursorResult(Cursor cursor) {
- long timeTaken = cursor.getLong(0);
- if (timeTaken > 0) {
- values.put(Video.Media.DATE_TAKEN, timeTaken);
- }
- double latitude = cursor.getDouble(1);
- double longitude = cursor.getDouble(2);
- // TODO: Change || to && after the default location
- // issue is
- // fixed.
- if ((latitude != 0f) || (longitude != 0f)) {
- values.put(Video.Media.LATITUDE, latitude);
- values.put(Video.Media.LONGITUDE, longitude);
- }
- values.put(Video.Media.RESOLUTION, cursor.getString(3));
-
- }
- });
-
- return contentResolver.insert(Video.Media.EXTERNAL_CONTENT_URI, values);
- }
-
- public static int retriveVideoDurationMs(String path) {
- int durationMs = 0;
- // Calculate the duration of the destination file.
- MediaMetadataRetriever retriever = new MediaMetadataRetriever();
- retriever.setDataSource(path);
- String duration = retriever.extractMetadata(
- MediaMetadataRetriever.METADATA_KEY_DURATION);
- if (duration != null) {
- durationMs = Integer.parseInt(duration);
- }
- retriever.release();
- return durationMs;
- }
-
-}
diff --git a/src/com/android/gallery3d/util/UpdateHelper.java b/src/com/android/gallery3d/util/UpdateHelper.java
deleted file mode 100644
index f76705d06..000000000
--- a/src/com/android/gallery3d/util/UpdateHelper.java
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package com.android.gallery3d.util;
-
-import com.android.gallery3d.common.Utils;
-
-public class UpdateHelper {
-
- private boolean mUpdated = false;
-
- public int update(int original, int update) {
- if (original != update) {
- mUpdated = true;
- original = update;
- }
- return original;
- }
-
- public long update(long original, long update) {
- if (original != update) {
- mUpdated = true;
- original = update;
- }
- return original;
- }
-
- public double update(double original, double update) {
- if (original != update) {
- mUpdated = true;
- original = update;
- }
- return original;
- }
-
- public <T> T update(T original, T update) {
- if (!Utils.equals(original, update)) {
- mUpdated = true;
- original = update;
- }
- return original;
- }
-
- public boolean isUpdated() {
- return mUpdated;
- }
-}