diff options
author | The Android Open Source Project <initial-contribution@android.com> | 2009-03-03 18:28:49 -0800 |
---|---|---|
committer | The Android Open Source Project <initial-contribution@android.com> | 2009-03-03 18:28:49 -0800 |
commit | becfb351a5bc43050128f44eb1bcfbcc0c6dcb7a (patch) | |
tree | 4b825dc642cb6eb9a060e54bf8d69288fbee4904 | |
parent | a6aa03f5bd2270bcc52ba1899c22d881955e8e7e (diff) | |
download | LegacyCamera-becfb351a5bc43050128f44eb1bcfbcc0c6dcb7a.zip LegacyCamera-becfb351a5bc43050128f44eb1bcfbcc0c6dcb7a.tar.gz LegacyCamera-becfb351a5bc43050128f44eb1bcfbcc0c6dcb7a.tar.bz2 |
auto import from //depot/cupcake/@135843
176 files changed, 0 insertions, 22210 deletions
diff --git a/Android.mk b/Android.mk deleted file mode 100644 index d35d7cb..0000000 --- a/Android.mk +++ /dev/null @@ -1,16 +0,0 @@ -LOCAL_PATH:= $(call my-dir) -include $(CLEAR_VARS) - -LOCAL_MODULE_TAGS := user development - -LOCAL_SRC_FILES := $(call all-java-files-under, src) - -LOCAL_PACKAGE_NAME := Camera -LOCAL_CERTIFICATE := media - -LOCAL_STATIC_JAVA_LIBRARIES := googlelogin-client - -include $(BUILD_PACKAGE) - -# Use the following include to make our test apk. -include $(call all-makefiles-under,$(LOCAL_PATH)) diff --git a/AndroidManifest.xml b/AndroidManifest.xml deleted file mode 100644 index ee36428..0000000 --- a/AndroidManifest.xml +++ /dev/null @@ -1,215 +0,0 @@ -<manifest xmlns:android="http://schemas.android.com/apk/res/android" - package="com.android.camera" - android:sharedUserId="android.media"> - <uses-permission android:name="android.permission.CAMERA" /> - <uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/> - <uses-permission android:name="android.permission.WAKE_LOCK" /> - <uses-permission android:name="android.permission.SET_WALLPAPER" /> - <!-- Needed by the ZoomRingController to set the bit saying we've already shown the - tutorial toast. --> - <uses-permission android:name="android.permission.WRITE_SETTINGS"/> - <application android:icon="@drawable/ic_launcher_camera" - android:label="@string/camera_label" - android:taskAffinity=""> - <service android:name="UploadService" android:process="android.process.media" /> - <receiver android:name="CameraButtonIntentReceiver"> - <intent-filter> - <action android:name="android.intent.action.CAMERA_BUTTON"/> - </intent-filter> - </receiver> - <activity android:name="Camera" - android:configChanges="orientation|keyboardHidden" - android:theme="@android:style/Theme.Black.NoTitleBar.Fullscreen" - android:screenOrientation="landscape" - android:clearTaskOnLaunch="true" - android:taskAffinity="android.task.camera"> - <intent-filter> - <action android:name="android.intent.action.MAIN" /> - <category android:name="android.intent.category.DEFAULT" /> - <category android:name="android.intent.category.LAUNCHER" /> - </intent-filter> - <intent-filter> - <action android:name="android.media.action.IMAGE_CAPTURE" /> - <category android:name="android.intent.category.DEFAULT" /> - </intent-filter> - <intent-filter> - <action android:name="android.media.action.STILL_IMAGE_CAMERA" /> - <category android:name="android.intent.category.DEFAULT" /> - </intent-filter> - </activity> - <activity android:name="VideoCamera" - android:configChanges="orientation|keyboardHidden" - android:theme="@android:style/Theme.Black.NoTitleBar.Fullscreen" - android:screenOrientation="landscape" - android:clearTaskOnLaunch="true" - android:taskAffinity="android.task.camera"> - <intent-filter> - <action android:name="android.media.action.VIDEO_CAMERA" /> - <category android:name="android.intent.category.DEFAULT" /> - </intent-filter> - <intent-filter> - <action android:name="android.media.action.VIDEO_CAPTURE" /> - <category android:name="android.intent.category.DEFAULT" /> - </intent-filter> - </activity> - <activity android:name="GalleryPicker" android:label="@string/gallery_picker_label" - android:configChanges="orientation|keyboardHidden" - android:icon="@drawable/ic_launcher_gallery" - android:clearTaskOnLaunch="true" - android:taskAffinity="android.task.pictures"> - <intent-filter> - <action android:name="android.intent.action.MAIN" /> - <category android:name="android.intent.category.DEFAULT" /> - <category android:name="android.intent.category.LAUNCHER" /> - </intent-filter> - </activity> - - <activity android:name="ImageGallery2" android:label="@string/gallery_label" - android:configChanges="orientation|keyboardHidden" - android:icon="@drawable/ic_launcher_gallery"> - <intent-filter> - <action android:name="android.intent.action.MAIN" /> - <category android:name="android.intent.category.DEFAULT" /> - </intent-filter> - <intent-filter> - <action android:name="android.intent.action.VIEW" /> - <category android:name="android.intent.category.DEFAULT" /> - <data android:mimeType="vnd.android.cursor.dir/image" /> - </intent-filter> - <intent-filter> - <action android:name="android.intent.action.VIEW" /> - <category android:name="android.intent.category.DEFAULT" /> - <data android:mimeType="vnd.android.cursor.dir/video" /> - </intent-filter> - <intent-filter> - <action android:name="android.intent.action.GET_CONTENT" /> - <category android:name="android.intent.category.OPENABLE" /> - <data android:mimeType="vnd.android.cursor.dir/image" /> - </intent-filter> - <intent-filter> - <action android:name="android.intent.action.GET_CONTENT" /> - <category android:name="android.intent.category.OPENABLE" /> - <category android:name="android.intent.category.DEFAULT" /> - <data android:mimeType="image/*" /> - <data android:mimeType="video/*" /> - </intent-filter> - <intent-filter> - <action android:name="android.intent.action.PICK" /> - <category android:name="android.intent.category.DEFAULT" /> - <data android:mimeType="image/*" /> - <data android:mimeType="video/*" /> - </intent-filter> - <intent-filter> - <action android:name="android.intent.action.PICK" /> - <category android:name="android.intent.category.DEFAULT" /> - <data android:mimeType="vnd.android.cursor.dir/image" /> - </intent-filter> - </activity> - <activity - android:name="CropImage" - android:process=":CropImage" - android:configChanges="orientation|keyboardHidden" - android:label="@string/crop_label"> - <intent-filter android:label="@string/crop_label"> - <action android:name="com.android.camera.action.CROP" /> - <data android:mimeType="image/*" /> - <category android:name="android.intent.category.DEFAULT" /> - <category android:name="android.intent.category.ALTERNATIVE" /> - <category android:name="android.intent.category.SELECTED_ALTERNATIVE" /> - </intent-filter> - </activity> - - <activity android:name="ViewImage" - android:label="@string/view_label" - android:configChanges="orientation|keyboardHidden"> - <intent-filter> - <action android:name="android.intent.action.VIEW" /> - <category android:name="android.intent.category.DEFAULT" /> - <data android:mimeType="image/*" /> - </intent-filter> - </activity> - <activity android:name="MovieView" - android:label="@string/movieviewlabel" - android:screenOrientation="landscape" - android:configChanges="orientation|keyboardHidden" - android:theme="@android:style/Theme.Black.NoTitleBar.Fullscreen"> - <intent-filter> - <action android:name="android.intent.action.VIEW" /> - <category android:name="android.intent.category.DEFAULT" /> - <category android:name="android.intent.category.BROWSABLE" /> - <data android:scheme="rtsp" /> - </intent-filter> - <intent-filter> - <action android:name="android.intent.action.VIEW" /> - <category android:name="android.intent.category.DEFAULT" /> - <data android:mimeType="video/*" /> - </intent-filter> - <intent-filter> - <action android:name="android.intent.action.VIEW" /> - <category android:name="android.intent.category.DEFAULT" /> - <category android:name="android.intent.category.BROWSABLE" /> - <data android:scheme="http" /> - <data android:mimeType="video/mp4" /> - <data android:mimeType="video/3gp" /> - <data android:mimeType="video/3gpp" /> - <data android:mimeType="video/3gpp2" /> - </intent-filter> - </activity> - - <activity android:name="CameraSettings" android:label="@string/preferences_label"> - <intent-filter> - <action android:name="android.intent.action.MAIN" /> - <category android:name="android.intent.category.DEVELOPMENT_PREFERENCE" /> - </intent-filter> - </activity> - - <activity android:name="GallerySettings" android:label="@string/preferences_label"> - <intent-filter> - <action android:name="android.intent.action.MAIN" /> - <category android:name="android.intent.category.DEVELOPMENT_PREFERENCE" /> - </intent-filter> - </activity> - - <activity android:name="SlideShow" android:label="Raw Image Viewer" - android:theme="@android:style/Theme.NoTitleBar.Fullscreen"> - <intent-filter> - <action android:name="android.intent.action.MAIN" /> - <category android:name="android.intent.category.TEST" /> - </intent-filter> - </activity> - - <activity android:name=".Wallpaper" - android:label="@string/camera_setas_wallpaper" - android:icon="@drawable/ic_launcher_gallery"> - <intent-filter> - <action android:name="android.intent.action.ATTACH_DATA" /> - <data android:mimeType="image/*" /> - <category android:name="android.intent.category.DEFAULT" /> - </intent-filter> - </activity> - - <activity android:name=".PickWallpaper" - android:label="@string/camera_pick_wallpaper" - android:icon="@drawable/ic_launcher_gallery"> - <intent-filter> - <action android:name="android.intent.action.SET_WALLPAPER" /> - <category android:name="android.intent.category.DEFAULT" /> - </intent-filter> - </activity> - - <receiver android:name="PhotoGadgetProvider" android:label="@string/gadget_title"> - <intent-filter> - <action android:name="android.gadget.action.GADGET_UPDATE" /> - </intent-filter> - <meta-data android:name="android.gadget.provider" android:resource="@xml/gadget_info" /> - </receiver> - - <!-- We configure a gadget by asking to pick a photo, then crop it, and store the config internally --> - <activity android:name="PhotoGadgetConfigure"> - <intent-filter> - <action android:name="android.gadget.action.GADGET_CONFIGURE" /> - </intent-filter> - </activity> - </application> -</manifest> - diff --git a/MODULE_LICENSE_APACHE2 b/MODULE_LICENSE_APACHE2 deleted file mode 100644 index e69de29..0000000 --- a/MODULE_LICENSE_APACHE2 +++ /dev/null @@ -1,190 +0,0 @@ - - Copyright (c) 2005-2008, The Android Open Source Project - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. - - - Apache License - Version 2.0, January 2004 - http://www.apache.org/licenses/ - - TERMS AND CONDITIONS FOR USE, REPRODUCTION, AND DISTRIBUTION - - 1. Definitions. - - "License" shall mean the terms and conditions for use, reproduction, - and distribution as defined by Sections 1 through 9 of this document. - - "Licensor" shall mean the copyright owner or entity authorized by - the copyright owner that is granting the License. - - "Legal Entity" shall mean the union of the acting entity and all - other entities that control, are controlled by, or are under common - control with that entity. For the purposes of this definition, - "control" means (i) the power, direct or indirect, to cause the - direction or management of such entity, whether by contract or - otherwise, or (ii) ownership of fifty percent (50%) or more of the - outstanding shares, or (iii) beneficial ownership of such entity. - - "You" (or "Your") shall mean an individual or Legal Entity - exercising permissions granted by this License. - - "Source" form shall mean the preferred form for making modifications, - including but not limited to software source code, documentation - source, and configuration files. - - "Object" form shall mean any form resulting from mechanical - transformation or translation of a Source form, including but - not limited to compiled object code, generated documentation, - and conversions to other media types. - - "Work" shall mean the work of authorship, whether in Source or - Object form, made available under the License, as indicated by a - copyright notice that is included in or attached to the work - (an example is provided in the Appendix below). - - "Derivative Works" shall mean any work, whether in Source or Object - form, that is based on (or derived from) the Work and for which the - editorial revisions, annotations, elaborations, or other modifications - represent, as a whole, an original work of authorship. For the purposes - of this License, Derivative Works shall not include works that remain - separable from, or merely link (or bind by name) to the interfaces of, - the Work and Derivative Works thereof. - - "Contribution" shall mean any work of authorship, including - the original version of the Work and any modifications or additions - to that Work or Derivative Works thereof, that is intentionally - submitted to Licensor for inclusion in the Work by the copyright owner - or by an individual or Legal Entity authorized to submit on behalf of - the copyright owner. For the purposes of this definition, "submitted" - means any form of electronic, verbal, or written communication sent - to the Licensor or its representatives, including but not limited to - communication on electronic mailing lists, source code control systems, - and issue tracking systems that are managed by, or on behalf of, the - Licensor for the purpose of discussing and improving the Work, but - excluding communication that is conspicuously marked or otherwise - designated in writing by the copyright owner as "Not a Contribution." - - "Contributor" shall mean Licensor and any individual or Legal Entity - on behalf of whom a Contribution has been received by Licensor and - subsequently incorporated within the Work. - - 2. Grant of Copyright License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - copyright license to reproduce, prepare Derivative Works of, - publicly display, publicly perform, sublicense, and distribute the - Work and such Derivative Works in Source or Object form. - - 3. Grant of Patent License. Subject to the terms and conditions of - this License, each Contributor hereby grants to You a perpetual, - worldwide, non-exclusive, no-charge, royalty-free, irrevocable - (except as stated in this section) patent license to make, have made, - use, offer to sell, sell, import, and otherwise transfer the Work, - where such license applies only to those patent claims licensable - by such Contributor that are necessarily infringed by their - Contribution(s) alone or by combination of their Contribution(s) - with the Work to which such Contribution(s) was submitted. If You - institute patent litigation against any entity (including a - cross-claim or counterclaim in a lawsuit) alleging that the Work - or a Contribution incorporated within the Work constitutes direct - or contributory patent infringement, then any patent licenses - granted to You under this License for that Work shall terminate - as of the date such litigation is filed. - - 4. Redistribution. You may reproduce and distribute copies of the - Work or Derivative Works thereof in any medium, with or without - modifications, and in Source or Object form, provided that You - meet the following conditions: - - (a) You must give any other recipients of the Work or - Derivative Works a copy of this License; and - - (b) You must cause any modified files to carry prominent notices - stating that You changed the files; and - - (c) You must retain, in the Source form of any Derivative Works - that You distribute, all copyright, patent, trademark, and - attribution notices from the Source form of the Work, - excluding those notices that do not pertain to any part of - the Derivative Works; and - - (d) If the Work includes a "NOTICE" text file as part of its - distribution, then any Derivative Works that You distribute must - include a readable copy of the attribution notices contained - within such NOTICE file, excluding those notices that do not - pertain to any part of the Derivative Works, in at least one - of the following places: within a NOTICE text file distributed - as part of the Derivative Works; within the Source form or - documentation, if provided along with the Derivative Works; or, - within a display generated by the Derivative Works, if and - wherever such third-party notices normally appear. The contents - of the NOTICE file are for informational purposes only and - do not modify the License. You may add Your own attribution - notices within Derivative Works that You distribute, alongside - or as an addendum to the NOTICE text from the Work, provided - that such additional attribution notices cannot be construed - as modifying the License. - - You may add Your own copyright statement to Your modifications and - may provide additional or different license terms and conditions - for use, reproduction, or distribution of Your modifications, or - for any such Derivative Works as a whole, provided Your use, - reproduction, and distribution of the Work otherwise complies with - the conditions stated in this License. - - 5. Submission of Contributions. Unless You explicitly state otherwise, - any Contribution intentionally submitted for inclusion in the Work - by You to the Licensor shall be under the terms and conditions of - this License, without any additional terms or conditions. - Notwithstanding the above, nothing herein shall supersede or modify - the terms of any separate license agreement you may have executed - with Licensor regarding such Contributions. - - 6. Trademarks. This License does not grant permission to use the trade - names, trademarks, service marks, or product names of the Licensor, - except as required for reasonable and customary use in describing the - origin of the Work and reproducing the content of the NOTICE file. - - 7. Disclaimer of Warranty. Unless required by applicable law or - agreed to in writing, Licensor provides the Work (and each - Contributor provides its Contributions) on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or - implied, including, without limitation, any warranties or conditions - of TITLE, NON-INFRINGEMENT, MERCHANTABILITY, or FITNESS FOR A - PARTICULAR PURPOSE. You are solely responsible for determining the - appropriateness of using or redistributing the Work and assume any - risks associated with Your exercise of permissions under this License. - - 8. Limitation of Liability. In no event and under no legal theory, - whether in tort (including negligence), contract, or otherwise, - unless required by applicable law (such as deliberate and grossly - negligent acts) or agreed to in writing, shall any Contributor be - liable to You for damages, including any direct, indirect, special, - incidental, or consequential damages of any character arising as a - result of this License or out of the use or inability to use the - Work (including but not limited to damages for loss of goodwill, - work stoppage, computer failure or malfunction, or any and all - other commercial damages or losses), even if such Contributor - has been advised of the possibility of such damages. - - 9. Accepting Warranty or Additional Liability. While redistributing - the Work or Derivative Works thereof, You may choose to offer, - and charge a fee for, acceptance of support, warranty, indemnity, - or other liability obligations and/or rights consistent with this - License. However, in accepting such obligations, You may act only - on Your own behalf and on Your sole responsibility, not on behalf - of any other Contributor, and only if You agree to indemnify, - defend, and hold each Contributor harmless for any liability - incurred by, or claims asserted against, such Contributor by reason - of your accepting any such warranty or additional liability. - - END OF TERMS AND CONDITIONS - diff --git a/res/anim/auto_focus_blink.xml b/res/anim/auto_focus_blink.xml deleted file mode 100644 index dff217d..0000000 --- a/res/anim/auto_focus_blink.xml +++ /dev/null @@ -1,19 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- Copyright (C) 2008 The Android Open Source Project - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. ---> - -<alpha xmlns:android="http://schemas.android.com/apk/res/android" - android:interpolator="@android:anim/accelerate_interpolator" - android:fromAlpha="0.0" android:toAlpha="1.0" android:duration="200" /> diff --git a/res/anim/on_screen_hint_enter.xml b/res/anim/on_screen_hint_enter.xml deleted file mode 100644 index 0f00760..0000000 --- a/res/anim/on_screen_hint_enter.xml +++ /dev/null @@ -1,23 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* -** Copyright 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. -*/ ---> - -<alpha xmlns:android="http://schemas.android.com/apk/res/android" - android:interpolator="@android:anim/decelerate_interpolator" - android:fromAlpha="0.0" android:toAlpha="1.0" android:duration="400" -/> diff --git a/res/anim/on_screen_hint_exit.xml b/res/anim/on_screen_hint_exit.xml deleted file mode 100644 index e9b38f8..0000000 --- a/res/anim/on_screen_hint_exit.xml +++ /dev/null @@ -1,23 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* -** Copyright 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. -*/ ---> - -<alpha xmlns:android="http://schemas.android.com/apk/res/android" - android:interpolator="@android:anim/accelerate_interpolator" - android:fromAlpha="1.0" android:toAlpha="0.0" android:duration="400" -/> diff --git a/res/anim/slide_in.xml b/res/anim/slide_in.xml deleted file mode 100644 index d1b9e5e..0000000 --- a/res/anim/slide_in.xml +++ /dev/null @@ -1,21 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<translate xmlns:android="http://schemas.android.com/apk/res/android" - android:fromXDelta="100%p" - android:toXDelta="0" - android:startOffset="0" - android:duration="400" /> diff --git a/res/anim/slide_in_vertical.xml b/res/anim/slide_in_vertical.xml deleted file mode 100644 index 4727689..0000000 --- a/res/anim/slide_in_vertical.xml +++ /dev/null @@ -1,21 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<translate xmlns:android="http://schemas.android.com/apk/res/android" - android:fromYDelta="100%p" - android:toYDelta="0" - android:startOffset="0" - android:duration="400" /> diff --git a/res/anim/slide_out.xml b/res/anim/slide_out.xml deleted file mode 100644 index 204cf28..0000000 --- a/res/anim/slide_out.xml +++ /dev/null @@ -1,21 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<translate xmlns:android="http://schemas.android.com/apk/res/android" - android:fromXDelta="0" - android:toXDelta="-100%p" - android:startOffset="0" - android:duration="400" /> diff --git a/res/anim/slide_out_vertical.xml b/res/anim/slide_out_vertical.xml deleted file mode 100644 index 3f3f2a0..0000000 --- a/res/anim/slide_out_vertical.xml +++ /dev/null @@ -1,21 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<translate xmlns:android="http://schemas.android.com/apk/res/android" - android:fromYDelta="0" - android:toYDelta="-100%p" - android:startOffset="0" - android:duration="400" /> diff --git a/res/anim/transition_in.xml b/res/anim/transition_in.xml deleted file mode 100644 index 6c2ad61..0000000 --- a/res/anim/transition_in.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* //device/apps/common/res/anim/fade_in.xml -** -** Copyright 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. -*/ ---> - -<alpha xmlns:android="http://schemas.android.com/apk/res/android" - android:fromAlpha="0.0" - android:toAlpha="1.0" - android:duration="1000" /> diff --git a/res/anim/transition_out.xml b/res/anim/transition_out.xml deleted file mode 100644 index 76e67f4..0000000 --- a/res/anim/transition_out.xml +++ /dev/null @@ -1,25 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* //device/apps/common/res/anim/fade_out.xml -** -** Copyright 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. -*/ ---> - -<alpha xmlns:android="http://schemas.android.com/apk/res/android" - android:fromAlpha="1.0" - android:toAlpha="0.0" - android:duration="1000" -/> diff --git a/res/drawable/btn_camera_arrow_left.xml b/res/drawable/btn_camera_arrow_left.xml deleted file mode 100644 index 494899b..0000000 --- a/res/drawable/btn_camera_arrow_left.xml +++ /dev/null @@ -1,28 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- Copyright (C) 2008 The Android Open Source Project - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. ---> - -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - - <item android:state_pressed="true" - android:drawable="@drawable/btn_camera_arrow_left_press" /> - - <item android:state_window_focused="true" android:state_focused="true" - android:drawable="@drawable/btn_camera_arrow_left_selected" /> - - <item - android:drawable="@drawable/btn_camera_arrow_left_default" /> - -</selector> diff --git a/res/drawable/btn_camera_arrow_left_default.png b/res/drawable/btn_camera_arrow_left_default.png Binary files differdeleted file mode 100644 index a9709aa..0000000 --- a/res/drawable/btn_camera_arrow_left_default.png +++ /dev/null diff --git a/res/drawable/btn_camera_arrow_left_press.png b/res/drawable/btn_camera_arrow_left_press.png Binary files differdeleted file mode 100644 index 262c928..0000000 --- a/res/drawable/btn_camera_arrow_left_press.png +++ /dev/null diff --git a/res/drawable/btn_camera_arrow_left_selected.png b/res/drawable/btn_camera_arrow_left_selected.png Binary files differdeleted file mode 100644 index 839704f..0000000 --- a/res/drawable/btn_camera_arrow_left_selected.png +++ /dev/null diff --git a/res/drawable/btn_camera_arrow_right.xml b/res/drawable/btn_camera_arrow_right.xml deleted file mode 100644 index 1d0cc0c..0000000 --- a/res/drawable/btn_camera_arrow_right.xml +++ /dev/null @@ -1,29 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- Copyright (C) 2008 The Android Open Source Project - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. ---> - -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - - - <item android:state_pressed="true" - android:drawable="@drawable/btn_camera_arrow_right_press" /> - - <item android:state_window_focused="true" android:state_focused="true" - android:drawable="@drawable/btn_camera_arrow_right_selected" /> - - <item - android:drawable="@drawable/btn_camera_arrow_right_default" /> - -</selector> diff --git a/res/drawable/btn_camera_arrow_right_default.png b/res/drawable/btn_camera_arrow_right_default.png Binary files differdeleted file mode 100644 index a4f78dc..0000000 --- a/res/drawable/btn_camera_arrow_right_default.png +++ /dev/null diff --git a/res/drawable/btn_camera_arrow_right_press.png b/res/drawable/btn_camera_arrow_right_press.png Binary files differdeleted file mode 100644 index 4b37b0d..0000000 --- a/res/drawable/btn_camera_arrow_right_press.png +++ /dev/null diff --git a/res/drawable/btn_camera_arrow_right_selected.png b/res/drawable/btn_camera_arrow_right_selected.png Binary files differdeleted file mode 100644 index 630a606..0000000 --- a/res/drawable/btn_camera_arrow_right_selected.png +++ /dev/null diff --git a/res/drawable/camera_crop_height.png b/res/drawable/camera_crop_height.png Binary files differdeleted file mode 100644 index b089aec..0000000 --- a/res/drawable/camera_crop_height.png +++ /dev/null diff --git a/res/drawable/camera_crop_width.png b/res/drawable/camera_crop_width.png Binary files differdeleted file mode 100644 index 65216af..0000000 --- a/res/drawable/camera_crop_width.png +++ /dev/null diff --git a/res/drawable/detail_photo_border.9.png b/res/drawable/detail_photo_border.9.png Binary files differdeleted file mode 100644 index 6de37b7..0000000 --- a/res/drawable/detail_photo_border.9.png +++ /dev/null diff --git a/res/drawable/frame_gallery_preview.xml b/res/drawable/frame_gallery_preview.xml deleted file mode 100644 index 5550bff..0000000 --- a/res/drawable/frame_gallery_preview.xml +++ /dev/null @@ -1,31 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- Copyright (C) 2008 The Android Open Source Project - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. ---> - -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - - <item android:state_window_focused="false" - android:drawable="@drawable/frame_gallery_preview_album" /> - - <item android:state_selected="true" android:state_pressed="true" - android:drawable="@drawable/frame_gallery_preview_album_pressed" /> - - <item android:state_selected="false" android:state_pressed="true" - android:drawable="@drawable/frame_gallery_preview_album_pressed" /> - - <item android:state_selected="true" - android:drawable="@drawable/frame_gallery_preview_album_selected" /> - -</selector> diff --git a/res/drawable/frame_gallery_preview_album.png b/res/drawable/frame_gallery_preview_album.png Binary files differdeleted file mode 100644 index 5b92ee2..0000000 --- a/res/drawable/frame_gallery_preview_album.png +++ /dev/null diff --git a/res/drawable/frame_gallery_preview_album_mask.png b/res/drawable/frame_gallery_preview_album_mask.png Binary files differdeleted file mode 100644 index b053f30..0000000 --- a/res/drawable/frame_gallery_preview_album_mask.png +++ /dev/null diff --git a/res/drawable/frame_gallery_preview_album_pressed.png b/res/drawable/frame_gallery_preview_album_pressed.png Binary files differdeleted file mode 100644 index e3575ff..0000000 --- a/res/drawable/frame_gallery_preview_album_pressed.png +++ /dev/null diff --git a/res/drawable/frame_gallery_preview_album_selected.png b/res/drawable/frame_gallery_preview_album_selected.png Binary files differdeleted file mode 100644 index 222a38a..0000000 --- a/res/drawable/frame_gallery_preview_album_selected.png +++ /dev/null diff --git a/res/drawable/frame_overlay_gallery_camera.png b/res/drawable/frame_overlay_gallery_camera.png Binary files differdeleted file mode 100644 index e0c24a6..0000000 --- a/res/drawable/frame_overlay_gallery_camera.png +++ /dev/null diff --git a/res/drawable/frame_overlay_gallery_folder.png b/res/drawable/frame_overlay_gallery_folder.png Binary files differdeleted file mode 100644 index 05f64cc..0000000 --- a/res/drawable/frame_overlay_gallery_folder.png +++ /dev/null diff --git a/res/drawable/frame_overlay_gallery_video.png b/res/drawable/frame_overlay_gallery_video.png Binary files differdeleted file mode 100644 index 4b84854..0000000 --- a/res/drawable/frame_overlay_gallery_video.png +++ /dev/null diff --git a/res/drawable/frame_thumbnail.xml b/res/drawable/frame_thumbnail.xml deleted file mode 100644 index 0cbbacc..0000000 --- a/res/drawable/frame_thumbnail.xml +++ /dev/null @@ -1,21 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- Copyright (C) 2008 The Android Open Source Project - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. ---> - -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - <item android:state_pressed="true" android:drawable="@drawable/frame_thumbnail_pressed" /> - <item android:state_window_focused="true" android:state_focused="true" android:drawable="@drawable/frame_thumbnail_selected" /> - <item android:drawable="@drawable/frame_thumbnail_default" /> -</selector> diff --git a/res/drawable/frame_thumbnail_default.png b/res/drawable/frame_thumbnail_default.png Binary files differdeleted file mode 100644 index 3db932e..0000000 --- a/res/drawable/frame_thumbnail_default.png +++ /dev/null diff --git a/res/drawable/frame_thumbnail_pressed.png b/res/drawable/frame_thumbnail_pressed.png Binary files differdeleted file mode 100644 index b15aea7..0000000 --- a/res/drawable/frame_thumbnail_pressed.png +++ /dev/null diff --git a/res/drawable/frame_thumbnail_selected.png b/res/drawable/frame_thumbnail_selected.png Binary files differdeleted file mode 100644 index 408b14a..0000000 --- a/res/drawable/frame_thumbnail_selected.png +++ /dev/null diff --git a/res/drawable/grid_background.xml b/res/drawable/grid_background.xml deleted file mode 100644 index fad1d2a..0000000 --- a/res/drawable/grid_background.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* grid_background.xml -** -** Copyright 2006, The Android Open Source Project -** -** Licensed under the Apache License, Version 2.0 (the "License"); -** you may not use this file except in compliance with the License. -** You may obtain a copy of the License at -** -** http://www.apache.org/licenses/LICENSE-2.0 -** -** Unless required by applicable law or agreed to in writing, software -** distributed under the License is distributed on an "AS IS" BASIS, -** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -** See the License for the specific language governing permissions and -** limitations under the License. -*/ ---> -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - <item android:state_pressed="true" android:drawable="@drawable/image_border_bg_pressed_blue" /> - <item android:state_window_focused="true" android:state_focused="true" android:drawable="@drawable/image_border_bg_focus_blue" /> - <item android:drawable="@drawable/image_border_bg_normal" /> -</selector> diff --git a/res/drawable/ic_btn_actionmenu_attach_default.png b/res/drawable/ic_btn_actionmenu_attach_default.png Binary files differdeleted file mode 100644 index 78d6e1b..0000000 --- a/res/drawable/ic_btn_actionmenu_attach_default.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_attach_pressed.png b/res/drawable/ic_btn_actionmenu_attach_pressed.png Binary files differdeleted file mode 100644 index 01cbe46..0000000 --- a/res/drawable/ic_btn_actionmenu_attach_pressed.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_attach_selected.png b/res/drawable/ic_btn_actionmenu_attach_selected.png Binary files differdeleted file mode 100644 index ee7af0b..0000000 --- a/res/drawable/ic_btn_actionmenu_attach_selected.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_cancel_default.png b/res/drawable/ic_btn_actionmenu_cancel_default.png Binary files differdeleted file mode 100644 index cb8f7bc..0000000 --- a/res/drawable/ic_btn_actionmenu_cancel_default.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_cancel_pressed.png b/res/drawable/ic_btn_actionmenu_cancel_pressed.png Binary files differdeleted file mode 100644 index 02bdb49..0000000 --- a/res/drawable/ic_btn_actionmenu_cancel_pressed.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_cancel_selected.png b/res/drawable/ic_btn_actionmenu_cancel_selected.png Binary files differdeleted file mode 100644 index a0b6017..0000000 --- a/res/drawable/ic_btn_actionmenu_cancel_selected.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_delete_default.png b/res/drawable/ic_btn_actionmenu_delete_default.png Binary files differdeleted file mode 100644 index 7e25f0d..0000000 --- a/res/drawable/ic_btn_actionmenu_delete_default.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_delete_pressed.png b/res/drawable/ic_btn_actionmenu_delete_pressed.png Binary files differdeleted file mode 100644 index 94087f6..0000000 --- a/res/drawable/ic_btn_actionmenu_delete_pressed.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_delete_selected.png b/res/drawable/ic_btn_actionmenu_delete_selected.png Binary files differdeleted file mode 100644 index 780310b..0000000 --- a/res/drawable/ic_btn_actionmenu_delete_selected.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_gallery_default.png b/res/drawable/ic_btn_actionmenu_gallery_default.png Binary files differdeleted file mode 100644 index a2d38db..0000000 --- a/res/drawable/ic_btn_actionmenu_gallery_default.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_gallery_pressed.png b/res/drawable/ic_btn_actionmenu_gallery_pressed.png Binary files differdeleted file mode 100644 index a01b7f8..0000000 --- a/res/drawable/ic_btn_actionmenu_gallery_pressed.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_gallery_selected.png b/res/drawable/ic_btn_actionmenu_gallery_selected.png Binary files differdeleted file mode 100644 index 400a63b..0000000 --- a/res/drawable/ic_btn_actionmenu_gallery_selected.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_play_default.png b/res/drawable/ic_btn_actionmenu_play_default.png Binary files differdeleted file mode 100644 index 17e0748..0000000 --- a/res/drawable/ic_btn_actionmenu_play_default.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_play_pressed.png b/res/drawable/ic_btn_actionmenu_play_pressed.png Binary files differdeleted file mode 100644 index c671669..0000000 --- a/res/drawable/ic_btn_actionmenu_play_pressed.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_play_selected.png b/res/drawable/ic_btn_actionmenu_play_selected.png Binary files differdeleted file mode 100644 index 35e1425..0000000 --- a/res/drawable/ic_btn_actionmenu_play_selected.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_set_as_default.png b/res/drawable/ic_btn_actionmenu_set_as_default.png Binary files differdeleted file mode 100644 index 0d341c7..0000000 --- a/res/drawable/ic_btn_actionmenu_set_as_default.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_set_as_pressed.png b/res/drawable/ic_btn_actionmenu_set_as_pressed.png Binary files differdeleted file mode 100644 index 58dc85c..0000000 --- a/res/drawable/ic_btn_actionmenu_set_as_pressed.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_set_as_selected.png b/res/drawable/ic_btn_actionmenu_set_as_selected.png Binary files differdeleted file mode 100644 index 6281229..0000000 --- a/res/drawable/ic_btn_actionmenu_set_as_selected.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_share_default.png b/res/drawable/ic_btn_actionmenu_share_default.png Binary files differdeleted file mode 100644 index 19f6ef4..0000000 --- a/res/drawable/ic_btn_actionmenu_share_default.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_share_pressed.png b/res/drawable/ic_btn_actionmenu_share_pressed.png Binary files differdeleted file mode 100644 index 8583114..0000000 --- a/res/drawable/ic_btn_actionmenu_share_pressed.png +++ /dev/null diff --git a/res/drawable/ic_btn_actionmenu_share_selected.png b/res/drawable/ic_btn_actionmenu_share_selected.png Binary files differdeleted file mode 100644 index fc9679b..0000000 --- a/res/drawable/ic_btn_actionmenu_share_selected.png +++ /dev/null diff --git a/res/drawable/ic_btn_camera_background.xml b/res/drawable/ic_btn_camera_background.xml deleted file mode 100644 index 2e28a80..0000000 --- a/res/drawable/ic_btn_camera_background.xml +++ /dev/null @@ -1,23 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* -** Copyright 2006, The Android Open Source Project -** -** Licensed under the Apache License, Version 2.0 (the "License"); -** you may not use this file except in compliance with the License. -** You may obtain a copy of the License at -** -** http://www.apache.org/licenses/LICENSE-2.0 -** -** Unless required by applicable law or agreed to in writing, software -** distributed under the License is distributed on an "AS IS" BASIS, -** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -** See the License for the specific language governing permissions and -** limitations under the License. -*/ ---> -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - <item android:state_pressed="true" android:drawable="@drawable/ic_btn_camera_pressed_background" /> - <item android:state_window_focused="true" android:state_focused="true" android:drawable="@drawable/ic_btn_camera_selected_background" /> - <item android:drawable="@drawable/ic_btn_camera_default_background" /> -</selector> diff --git a/res/drawable/ic_btn_camera_default_background.png b/res/drawable/ic_btn_camera_default_background.png Binary files differdeleted file mode 100644 index c37a86e..0000000 --- a/res/drawable/ic_btn_camera_default_background.png +++ /dev/null diff --git a/res/drawable/ic_btn_camera_pressed_background.png b/res/drawable/ic_btn_camera_pressed_background.png Binary files differdeleted file mode 100644 index 8707b8a..0000000 --- a/res/drawable/ic_btn_camera_pressed_background.png +++ /dev/null diff --git a/res/drawable/ic_btn_camera_selected_background.png b/res/drawable/ic_btn_camera_selected_background.png Binary files differdeleted file mode 100644 index a6bbdb1..0000000 --- a/res/drawable/ic_btn_camera_selected_background.png +++ /dev/null diff --git a/res/drawable/ic_camera_bar_indicator_record.png b/res/drawable/ic_camera_bar_indicator_record.png Binary files differdeleted file mode 100644 index 60f7a01..0000000 --- a/res/drawable/ic_camera_bar_indicator_record.png +++ /dev/null diff --git a/res/drawable/ic_camera_indicator_auto_focus_green.png b/res/drawable/ic_camera_indicator_auto_focus_green.png Binary files differdeleted file mode 100644 index 7bc09db..0000000 --- a/res/drawable/ic_camera_indicator_auto_focus_green.png +++ /dev/null diff --git a/res/drawable/ic_camera_indicator_photo.png b/res/drawable/ic_camera_indicator_photo.png Binary files differdeleted file mode 100644 index 3b0483b..0000000 --- a/res/drawable/ic_camera_indicator_photo.png +++ /dev/null diff --git a/res/drawable/ic_camera_indicator_video.png b/res/drawable/ic_camera_indicator_video.png Binary files differdeleted file mode 100644 index a4cb8d0..0000000 --- a/res/drawable/ic_camera_indicator_video.png +++ /dev/null diff --git a/res/drawable/ic_error_mms_video_overlay.png b/res/drawable/ic_error_mms_video_overlay.png Binary files differdeleted file mode 100644 index 4f50072..0000000 --- a/res/drawable/ic_error_mms_video_overlay.png +++ /dev/null diff --git a/res/drawable/ic_gallery_empty2.png b/res/drawable/ic_gallery_empty2.png Binary files differdeleted file mode 100644 index f950e08..0000000 --- a/res/drawable/ic_gallery_empty2.png +++ /dev/null diff --git a/res/drawable/ic_gallery_video_overlay.png b/res/drawable/ic_gallery_video_overlay.png Binary files differdeleted file mode 100644 index ae263a7..0000000 --- a/res/drawable/ic_gallery_video_overlay.png +++ /dev/null diff --git a/res/drawable/ic_launcher_camera.png b/res/drawable/ic_launcher_camera.png Binary files differdeleted file mode 100644 index 9bb4c61..0000000 --- a/res/drawable/ic_launcher_camera.png +++ /dev/null diff --git a/res/drawable/ic_launcher_gallery.png b/res/drawable/ic_launcher_gallery.png Binary files differdeleted file mode 100644 index 965fb71..0000000 --- a/res/drawable/ic_launcher_gallery.png +++ /dev/null diff --git a/res/drawable/ic_menu_attach.xml b/res/drawable/ic_menu_attach.xml deleted file mode 100644 index 209f6b5..0000000 --- a/res/drawable/ic_menu_attach.xml +++ /dev/null @@ -1,23 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* -** Copyright 2006, The Android Open Source Project -** -** Licensed under the Apache License, Version 2.0 (the "License"); -** you may not use this file except in compliance with the License. -** You may obtain a copy of the License at -** -** http://www.apache.org/licenses/LICENSE-2.0 -** -** Unless required by applicable law or agreed to in writing, software -** distributed under the License is distributed on an "AS IS" BASIS, -** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -** See the License for the specific language governing permissions and -** limitations under the License. -*/ ---> -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - <item android:state_pressed="true" android:drawable="@drawable/ic_btn_actionmenu_attach_pressed" /> - <item android:state_window_focused="true" android:state_focused="true" android:drawable="@drawable/ic_btn_actionmenu_attach_selected" /> - <item android:drawable="@drawable/ic_btn_actionmenu_attach_default" /> -</selector> diff --git a/res/drawable/ic_menu_camera_play.xml b/res/drawable/ic_menu_camera_play.xml deleted file mode 100644 index 3a70e69..0000000 --- a/res/drawable/ic_menu_camera_play.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* grid_background.xml -** -** Copyright 2006, The Android Open Source Project -** -** Licensed under the Apache License, Version 2.0 (the "License"); -** you may not use this file except in compliance with the License. -** You may obtain a copy of the License at -** -** http://www.apache.org/licenses/LICENSE-2.0 -** -** Unless required by applicable law or agreed to in writing, software -** distributed under the License is distributed on an "AS IS" BASIS, -** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -** See the License for the specific language governing permissions and -** limitations under the License. -*/ ---> -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - <item android:state_pressed="true" android:drawable="@drawable/ic_btn_actionmenu_play_pressed" /> - <item android:state_window_focused="true" android:state_focused="true" android:drawable="@drawable/ic_btn_actionmenu_play_selected" /> - <item android:drawable="@drawable/ic_btn_actionmenu_play_default" /> -</selector> diff --git a/res/drawable/ic_menu_camera_video_view.png b/res/drawable/ic_menu_camera_video_view.png Binary files differdeleted file mode 100644 index f7e52c2..0000000 --- a/res/drawable/ic_menu_camera_video_view.png +++ /dev/null diff --git a/res/drawable/ic_menu_cancel.xml b/res/drawable/ic_menu_cancel.xml deleted file mode 100644 index 92960d9..0000000 --- a/res/drawable/ic_menu_cancel.xml +++ /dev/null @@ -1,23 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* -** Copyright 2006, The Android Open Source Project -** -** Licensed under the Apache License, Version 2.0 (the "License"); -** you may not use this file except in compliance with the License. -** You may obtain a copy of the License at -** -** http://www.apache.org/licenses/LICENSE-2.0 -** -** Unless required by applicable law or agreed to in writing, software -** distributed under the License is distributed on an "AS IS" BASIS, -** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -** See the License for the specific language governing permissions and -** limitations under the License. -*/ ---> -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - <item android:state_pressed="true" android:drawable="@drawable/ic_btn_actionmenu_cancel_pressed" /> - <item android:state_window_focused="true" android:state_focused="true" android:drawable="@drawable/ic_btn_actionmenu_cancel_selected" /> - <item android:drawable="@drawable/ic_btn_actionmenu_cancel_default" /> -</selector> diff --git a/res/drawable/ic_menu_delete.xml b/res/drawable/ic_menu_delete.xml deleted file mode 100644 index efea2df..0000000 --- a/res/drawable/ic_menu_delete.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* grid_background.xml -** -** Copyright 2006, The Android Open Source Project -** -** Licensed under the Apache License, Version 2.0 (the "License"); -** you may not use this file except in compliance with the License. -** You may obtain a copy of the License at -** -** http://www.apache.org/licenses/LICENSE-2.0 -** -** Unless required by applicable law or agreed to in writing, software -** distributed under the License is distributed on an "AS IS" BASIS, -** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -** See the License for the specific language governing permissions and -** limitations under the License. -*/ ---> -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - <item android:state_pressed="true" android:drawable="@drawable/ic_btn_actionmenu_delete_pressed" /> - <item android:state_window_focused="true" android:state_focused="true" android:drawable="@drawable/ic_btn_actionmenu_delete_selected" /> - <item android:drawable="@drawable/ic_btn_actionmenu_delete_default" /> -</selector> diff --git a/res/drawable/ic_menu_gallery.xml b/res/drawable/ic_menu_gallery.xml deleted file mode 100644 index 4b0319a..0000000 --- a/res/drawable/ic_menu_gallery.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* grid_background.xml -** -** Copyright 2006, The Android Open Source Project -** -** Licensed under the Apache License, Version 2.0 (the "License"); -** you may not use this file except in compliance with the License. -** You may obtain a copy of the License at -** -** http://www.apache.org/licenses/LICENSE-2.0 -** -** Unless required by applicable law or agreed to in writing, software -** distributed under the License is distributed on an "AS IS" BASIS, -** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -** See the License for the specific language governing permissions and -** limitations under the License. -*/ ---> -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - <item android:state_pressed="true" android:drawable="@drawable/ic_btn_actionmenu_gallery_pressed" /> - <item android:state_window_focused="true" android:state_focused="true" android:drawable="@drawable/ic_btn_actionmenu_gallery_selected" /> - <item android:drawable="@drawable/ic_btn_actionmenu_gallery_default" /> -</selector> diff --git a/res/drawable/ic_menu_set_as.xml b/res/drawable/ic_menu_set_as.xml deleted file mode 100644 index 119e712..0000000 --- a/res/drawable/ic_menu_set_as.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* grid_background.xml -** -** Copyright 2006, The Android Open Source Project -** -** Licensed under the Apache License, Version 2.0 (the "License"); -** you may not use this file except in compliance with the License. -** You may obtain a copy of the License at -** -** http://www.apache.org/licenses/LICENSE-2.0 -** -** Unless required by applicable law or agreed to in writing, software -** distributed under the License is distributed on an "AS IS" BASIS, -** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -** See the License for the specific language governing permissions and -** limitations under the License. -*/ ---> -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - <item android:state_pressed="true" android:drawable="@drawable/ic_btn_actionmenu_set_as_pressed" /> - <item android:state_window_focused="true" android:state_focused="true" android:drawable="@drawable/ic_btn_actionmenu_set_as_selected" /> - <item android:drawable="@drawable/ic_btn_actionmenu_set_as_default" /> -</selector> diff --git a/res/drawable/ic_menu_share.xml b/res/drawable/ic_menu_share.xml deleted file mode 100644 index cf376ac..0000000 --- a/res/drawable/ic_menu_share.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* grid_background.xml -** -** Copyright 2006, The Android Open Source Project -** -** Licensed under the Apache License, Version 2.0 (the "License"); -** you may not use this file except in compliance with the License. -** You may obtain a copy of the License at -** -** http://www.apache.org/licenses/LICENSE-2.0 -** -** Unless required by applicable law or agreed to in writing, software -** distributed under the License is distributed on an "AS IS" BASIS, -** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -** See the License for the specific language governing permissions and -** limitations under the License. -*/ ---> -<selector xmlns:android="http://schemas.android.com/apk/res/android"> - <item android:state_pressed="true" android:drawable="@drawable/ic_btn_actionmenu_share_pressed" /> - <item android:state_window_focused="true" android:state_focused="true" android:drawable="@drawable/ic_btn_actionmenu_share_selected" /> - <item android:drawable="@drawable/ic_btn_actionmenu_share_default" /> -</selector> diff --git a/res/drawable/ic_menu_view_details.png b/res/drawable/ic_menu_view_details.png Binary files differdeleted file mode 100644 index a5a184f..0000000 --- a/res/drawable/ic_menu_view_details.png +++ /dev/null diff --git a/res/drawable/ic_missing_thumbnail_picture.png b/res/drawable/ic_missing_thumbnail_picture.png Binary files differdeleted file mode 100644 index ebab487..0000000 --- a/res/drawable/ic_missing_thumbnail_picture.png +++ /dev/null diff --git a/res/drawable/ic_missing_thumbnail_video.png b/res/drawable/ic_missing_thumbnail_video.png Binary files differdeleted file mode 100644 index b44d821..0000000 --- a/res/drawable/ic_missing_thumbnail_video.png +++ /dev/null diff --git a/res/drawable/image_border_bg_focus_blue.9.png b/res/drawable/image_border_bg_focus_blue.9.png Binary files differdeleted file mode 100644 index 89debd2..0000000 --- a/res/drawable/image_border_bg_focus_blue.9.png +++ /dev/null diff --git a/res/drawable/image_border_bg_normal.9.png b/res/drawable/image_border_bg_normal.9.png Binary files differdeleted file mode 100644 index 18e3607..0000000 --- a/res/drawable/image_border_bg_normal.9.png +++ /dev/null diff --git a/res/drawable/image_border_bg_pressed_blue.9.png b/res/drawable/image_border_bg_pressed_blue.9.png Binary files differdeleted file mode 100644 index 94fa74f..0000000 --- a/res/drawable/image_border_bg_pressed_blue.9.png +++ /dev/null diff --git a/res/drawable/indicator_autocrop.png b/res/drawable/indicator_autocrop.png Binary files differdeleted file mode 100644 index d960b1f..0000000 --- a/res/drawable/indicator_autocrop.png +++ /dev/null diff --git a/res/drawable/on_screen_hint_frame.9.png b/res/drawable/on_screen_hint_frame.9.png Binary files differdeleted file mode 100755 index 08c4f86..0000000 --- a/res/drawable/on_screen_hint_frame.9.png +++ /dev/null diff --git a/res/drawable/photo_frame.9.png b/res/drawable/photo_frame.9.png Binary files differdeleted file mode 100644 index b153260..0000000 --- a/res/drawable/photo_frame.9.png +++ /dev/null diff --git a/res/layout/camera.xml b/res/layout/camera.xml deleted file mode 100644 index d23066e..0000000 --- a/res/layout/camera.xml +++ /dev/null @@ -1,73 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" - android:id="@+id/camera" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:orientation="horizontal"> - - <com.android.camera.VideoPreview - android:id="@+id/camera_preview" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:layout_centerInParent="true" /> - - <View - android:id="@+id/blackout" - android:background="#ff000000" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:visibility="invisible" /> - - <com.android.camera.ShutterButton - android:id="@+id/shutter_button" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:src="@drawable/ic_camera_indicator_photo" - android:background="@drawable/ic_btn_camera_background" - android:clickable="true" - android:focusable="true" - android:layout_alignParentRight="true" - android:layout_alignParentTop="true" - android:layout_marginRight="50dip" - android:layout_marginTop="10dip" - android:scaleType="center" /> - - <ImageView - android:id="@+id/focus_indicator" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:src="@drawable/ic_camera_indicator_auto_focus_green" - android:layout_alignLeft="@id/shutter_button" - android:layout_alignTop="@id/shutter_button" - android:layout_marginLeft="39dip" - android:layout_marginTop="16dip" - android:scaleType="center" - android:visibility="gone" /> - - <ImageView - android:visibility="gone" - android:id="@+id/last_picture_button" - android:layout_width="72dip" - android:layout_height="72dip" - android:clickable="true" - android:focusable="true" - android:layout_alignParentLeft="true" - android:layout_alignParentTop="true" - android:layout_marginLeft="10dip" - android:layout_marginTop="10dip" /> -</RelativeLayout> diff --git a/res/layout/cropimage.xml b/res/layout/cropimage.xml deleted file mode 100644 index 4f3dcb7..0000000 --- a/res/layout/cropimage.xml +++ /dev/null @@ -1,58 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" - android:layout_width="fill_parent" - android:layout_height="fill_parent"> - - <RelativeLayout - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:orientation="horizontal"> - - <view class="com.android.camera.CropImage$CropImageView" android:id="@+id/image" - android:background="#55000000" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:layout_x="0dip" - android:layout_y="0dip" - /> - <RelativeLayout android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:orientation="horizontal" - android:paddingLeft="10dip" - android:paddingRight="10dip" - android:layout_alignParentBottom="true" - android:layout_centerHorizontal="true"> - <Button - android:id="@+id/save" - android:layout_width="100dip" - android:layout_height="wrap_content" - android:layout_alignParentLeft="true" - android:text="@string/crop_save_text" - /> - <Button - android:id="@+id/discard" - android:layout_width="100dip" - android:layout_height="wrap_content" - android:layout_alignParentRight="true" - android:text="@string/crop_discard_text" - /> - </RelativeLayout> - </RelativeLayout> - -</FrameLayout> - diff --git a/res/layout/custom_gallery_title.xml b/res/layout/custom_gallery_title.xml deleted file mode 100644 index 0652678..0000000 --- a/res/layout/custom_gallery_title.xml +++ /dev/null @@ -1,61 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- Copyright (C) 2008 The Android Open Source Project - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. ---> - -<RelativeLayout - xmlns:android="http://schemas.android.com/apk/res/android" - android:id="@+id/screen" android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:orientation="vertical"> - - <TextView android:id="@+id/left_text" - android:gravity="center_vertical" - style="?android:attr/windowTitleStyle" - android:layout_width="wrap_content" - android:layout_height="fill_parent" android:paddingLeft="5dip" - android:layout_alignParentLeft="true" /> - - <TextView android:id="@+id/right_text" - android:gravity="center_vertical" - style="?android:attr/windowTitleStyle" - android:layout_width="wrap_content" - android:layout_height="fill_parent" android:paddingRight="5dip" - android:layout_alignParentRight="true" - android:visibility="gone" /> - - <LinearLayout android:id="@+id/loading_indicator" - android:orientation="horizontal" - android:gravity="center_vertical" - android:paddingTop="2dip" - android:layout_alignParentRight="true" - android:layout_height="wrap_content" - android:layout_width="wrap_content"> - - <TextView android:id="@+id/loading_text" - android:gravity="center_vertical" - style="?android:attr/windowTitleStyle" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:paddingRight="5dip" - android:layout_alignParentRight="true" /> - - <ProgressBar android:id="@android:id/progress" - style="?android:attr/progressBarStyleSmallTitle" - android:gravity="center_vertical" - android:paddingRight="5dip" - android:layout_width="wrap_content" - android:layout_height="wrap_content" /> - </LinearLayout> -</RelativeLayout> diff --git a/res/layout/details.xml b/res/layout/details.xml deleted file mode 100644 index 482e567..0000000 --- a/res/layout/details.xml +++ /dev/null @@ -1,159 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" - android:orientation="vertical" - android:padding="10dip" - android:layout_width="fill_parent" - android:layout_height="wrap_content"> - - <LinearLayout - android:orientation="horizontal" - android:layout_width="fill_parent" - android:layout_height="wrap_content"> - - <TextView - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:text="@string/details_title_label" - android:textSize="10sp" - /> - - </LinearLayout> - - <EditText - android:id="@+id/title" - android:layout_width="fill_parent" - android:layout_height="wrap_content" - android:text="@string/details_title_text" - android:autoText="true" - android:capitalize="words" - android:textSize="10sp" - android:textColor="#FF661700" - /> - - <TextView - android:layout_width="fill_parent" - android:layout_height="wrap_content" - android:text="@string/details_description_label" - android:textSize="10sp" - /> - - <EditText - android:id="@+id/description" - android:layout_width="fill_parent" - android:layout_height="wrap_content" - android:text="@string/details_description_text" - android:autoText="true" - android:capitalize="sentences" - android:textSize="10sp" - android:textColor="#FF661700" - /> - - <TextView android:id="@+id/tags_label" - android:layout_width="fill_parent" - android:layout_height="wrap_content" - android:text="@string/details_tags_label" - android:textSize="10sp" - android:visibility="gone" - /> - - <EditText - android:id="@+id/tags" - android:layout_width="fill_parent" - android:layout_height="wrap_content" - android:text="@string/details_tags_text" - android:textSize="10sp" - android:textColor="#FF661700" - android:autoText="false" - android:capitalize="none" - android:visibility="gone" - /> - - <LinearLayout android:id="@+id/categories" - android:orientation="horizontal" - android:visibility="gone" - android:layout_width="fill_parent" - android:layout_height="wrap_content"> - - <TextView - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:text="@string/details_category_label" - android:textSize="10sp" - /> - - <Spinner android:id="@+id/category" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:drawSelectorOnTop="false" - android:textSize="10sp" - /> - </LinearLayout> - - <LinearLayout android:id="@+id/languages" - android:orientation="horizontal" - android:visibility="gone" - android:layout_width="fill_parent" - android:layout_height="wrap_content"> - - <TextView - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:text="@string/details_language_label" - android:textSize="10sp" - /> - - <Spinner android:id="@+id/language" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:drawSelectorOnTop="false" - android:textSize="10sp" - /> - </LinearLayout> - - <LinearLayout - android:orientation="horizontal" - android:layout_width="fill_parent" - android:layout_height="wrap_content"> - - <RadioGroup android:id="@+id/publicprivate" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:orientation="horizontal"> - <RadioButton android:id="@+id/publicView" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:checked="false" - android:text="@string/details_publicView_text" - /> - - <RadioButton android:id="@+id/privateView" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:checked="false" - android:text="@string/details_privateView_text" - /> - </RadioGroup> - - <Button android:id="@+id/save" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:text="@string/details_save_text" - android:layout_alignParentRight="true" - /> - </LinearLayout> -</LinearLayout> diff --git a/res/layout/detailsview.xml b/res/layout/detailsview.xml deleted file mode 100644 index e28f06c..0000000 --- a/res/layout/detailsview.xml +++ /dev/null @@ -1,166 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- Copyright (C) 2008 The Android Open Source Project - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. ---> - -<ScrollView xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/scroll_view" - android:orientation="vertical" - android:layout_width="300dip" - android:layout_height="fill_parent"> - - <LinearLayout - android:orientation="vertical" - android:layout_width="fill_parent" - android:layout_height="wrap_content" - android:paddingLeft="5dip" - android:paddingRight="5dip" - android:paddingBottom="10dp"> - - <LinearLayout - android:orientation="horizontal" - android:gravity="center_vertical" - android:layout_width="fill_parent" - android:layout_height="wrap_content"> - - <LinearLayout - android:orientation="horizontal" - android:gravity="center_vertical" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:background="@drawable/detail_photo_border"> - <ImageView - android:id="@+id/details_thumbnail_image" - android:layout_width="64dip" - android:layout_height="64dip"/> - </LinearLayout> - - <TextView - android:id="@+id/details_image_title" - android:layout_height="wrap_content" - android:layout_width="wrap_content" - android:textAppearance="?android:attr/textAppearanceMedium" - android:paddingLeft="6dip" - android:layout_weight="1"/> - - </LinearLayout> - - <TableLayout - android:layout_width="fill_parent" - android:layout_height="wrap_content" - android:paddingLeft="5dip" - android:layout_marginTop="10dip"> - - <TableRow> - <TextView - android:gravity="right" - android:textAppearance="?android:attr/textAppearanceSmall" - android:text="@string/details_file_size"/> - <TextView - android:id="@+id/details_file_size_value" - android:textAppearance="?android:attr/textAppearanceSmall" - android:paddingLeft="5dip" - android:textColor="?android:attr/textColorPrimary"/> - </TableRow> - - <TableRow> - <TextView - android:gravity="right" - android:textAppearance="?android:attr/textAppearanceSmall" - android:text="@string/details_image_resolution"/> - <TextView - android:id="@+id/details_resolution_value" - android:layout_height="wrap_content" - android:layout_width="fill_parent" - android:textAppearance="?android:attr/textAppearanceSmall" - android:paddingLeft="5dip" - android:textColor="?android:attr/textColorPrimary"/> - </TableRow> - <TableRow - android:id="@+id/details_duration_row"> - <TextView - android:gravity="right" - android:textAppearance="?android:attr/textAppearanceSmall" - android:text="@string/details_duration"/> - <TextView - android:id="@+id/details_duration_value" - android:textAppearance="?android:attr/textAppearanceSmall" - android:paddingLeft="5dip" - android:textColor="?android:attr/textColorPrimary"/> - </TableRow> - <TableRow - android:id="@+id/details_frame_rate_row"> - <TextView - android:gravity="right" - android:textAppearance="?android:attr/textAppearanceSmall" - android:text="@string/details_frame_rate"/> - <TextView - android:id="@+id/details_frame_rate_value" - android:textAppearance="?android:attr/textAppearanceSmall" - android:paddingLeft="5dip" - android:textColor="?android:attr/textColorPrimary"/> - </TableRow> - - <TableRow - android:id="@+id/details_bit_rate_row"> - <TextView - android:gravity="right" - android:textAppearance="?android:attr/textAppearanceSmall" - android:text="@string/details_bit_rate"/> - <TextView - android:id="@+id/details_bit_rate_value" - android:textAppearance="?android:attr/textAppearanceSmall" - android:paddingLeft="5dip" - android:textColor="?android:attr/textColorPrimary"/> - </TableRow> - <TableRow - android:id="@+id/details_format_row"> - <TextView - android:gravity="right" - android:textAppearance="?android:attr/textAppearanceSmall" - android:text="@string/details_format"/> - <TextView - android:id="@+id/details_format_value" - android:textAppearance="?android:attr/textAppearanceSmall" - android:paddingLeft="5dip" - android:textColor="?android:attr/textColorPrimary"/> - </TableRow> - <TableRow - android:id="@+id/details_codec_row"> - <TextView - android:gravity="right" - android:textAppearance="?android:attr/textAppearanceSmall" - android:text="@string/details_codec"/> - <TextView - android:id="@+id/details_codec_value" - android:textAppearance="?android:attr/textAppearanceSmall" - android:paddingLeft="5dip" - android:textColor="?android:attr/textColorPrimary"/> - </TableRow> - <TableRow - android:id="@+id/details_date_taken_row"> - <TextView - android:gravity="right" - android:textAppearance="?android:attr/textAppearanceSmall" - android:text="@string/details_date_taken"/> - <TextView - android:id="@+id/details_date_taken_value" - android:textAppearance="?android:attr/textAppearanceSmall" - android:paddingLeft="5dip" - android:textColor="?android:attr/textColorPrimary"/> - </TableRow> - </TableLayout> - - </LinearLayout> - -</ScrollView> diff --git a/res/layout/gallery.xml b/res/layout/gallery.xml deleted file mode 100644 index 61a0db2..0000000 --- a/res/layout/gallery.xml +++ /dev/null @@ -1,58 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:orientation="horizontal"> - - <View android:background="#FF000000" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:layout_alignParentTop="true" - android:layout_alignParentLeft="true" - /> - - <ImageView android:id="@+id/switcher1" - android:background="#FF000000" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:layout_alignParentTop="true" - android:layout_alignParentLeft="true" - android:visibility="invisible" - /> - - <ImageView android:id="@+id/switcher2" - android:background="#55000000" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:layout_alignParentTop="true" - android:layout_alignParentLeft="true" - android:visibility="invisible" - /> - - <Gallery android:id="@+id/gallery" - android:background="#55000000" - android:layout_width="fill_parent" - android:layout_height="wrap_content" - android:layout_alignParentBottom="true" - android:layout_alignParentLeft="true" - - android:gravity="center_vertical" - android:spacing="16dp" - /> - -</RelativeLayout> diff --git a/res/layout/gallery_picker_item.xml b/res/layout/gallery_picker_item.xml deleted file mode 100644 index 62d8333..0000000 --- a/res/layout/gallery_picker_item.xml +++ /dev/null @@ -1,38 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- Copyright (C) 2008 The Android Open Source Project - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. ---> - -<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" - android:orientation="vertical" - android:layout_width="148dp" - android:layout_height="wrap_content" - android:gravity="center_horizontal"> - - <com.android.camera.GalleryPickerItem android:id="@+id/thumbnail" - android:layout_width="142dip" - android:layout_height="142dip" - android:scaleType="centerCrop" /> - - <TextView android:id="@+id/title" - android:paddingTop="3dip" - android:paddingBottom="9dip" - android:layout_width="wrap_content" - android:textSize="14sp" - android:singleLine="true" - android:textColor="#ffffffff" - android:ellipsize="middle" - android:layout_height="wrap_content" /> - -</LinearLayout> diff --git a/res/layout/gallerypicker.xml b/res/layout/gallerypicker.xml deleted file mode 100644 index 4bc7789..0000000 --- a/res/layout/gallerypicker.xml +++ /dev/null @@ -1,61 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/root" - android:layout_width="fill_parent" - android:layout_height="fill_parent"> - <GridView xmlns:android="http://schemas.android.com/apk/res/android" - android:id="@+id/albums" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:paddingTop="2dip" - android:numColumns="auto_fit" - android:columnWidth="148dp" - android:stretchMode="spacingWidthUniform" - android:drawSelectorOnTop="false" - android:cacheColorHint="#000000" - android:background="#000000"/> - - <RelativeLayout android:id="@+id/no_images" - android:visibility="gone" - android:orientation="vertical" - android:layout_centerInParent="true" - android:layout_width="fill_parent" - android:layout_height="fill_parent"> - - <ImageView - android:id="@+id/no_pictures_image" - android:layout_centerInParent="true" - android:layout_gravity="center" - android:background="@drawable/ic_gallery_empty2" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - /> - - <TextView - android:layout_below="@id/no_pictures_image" - android:layout_centerHorizontal="true" - android:paddingTop="5dip" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:layout_gravity="center" - android:text="@string/image_gallery_NoImageView_text" - android:textColor="#FFBEBEBE" - android:textSize="18dip" - /> - </RelativeLayout> - -</RelativeLayout> diff --git a/res/layout/grid.xml b/res/layout/grid.xml deleted file mode 100644 index 2bdbc8a..0000000 --- a/res/layout/grid.xml +++ /dev/null @@ -1,44 +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. - */ ---> - -<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:background="#FFFFFF"> - - <ImageSwitcher android:id="@+id/switcher" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:layout_alignParentTop="true" - android:layout_alignParentLeft="true" - /> - - <GridView android:id="@+id/gallery" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - - android:padding="0dp" - android:verticalSpacing="0dp" - android:horizontalSpacing="0dp" - android:stretchMode="columnWidth" - - android:gravity="center" - /> - -</RelativeLayout> - diff --git a/res/layout/image_gallery_2.xml b/res/layout/image_gallery_2.xml deleted file mode 100644 index d7158a9..0000000 --- a/res/layout/image_gallery_2.xml +++ /dev/null @@ -1,58 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:id="@+id/root" - android:layout_width="fill_parent" - android:layout_height="fill_parent"> - - <view class="com.android.camera.ImageGallery2$GridViewSpecial" - android:id="@+id/grid" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:listSelector="@drawable/grid_background" - /> - - <RelativeLayout android:id="@+id/no_images" - android:visibility="gone" - android:orientation="vertical" - android:layout_centerInParent="true" - android:layout_width="fill_parent" - android:layout_height="fill_parent"> - - <ImageView - android:id="@+id/no_pictures_image" - android:layout_centerInParent="true" - android:layout_gravity="center" - android:background="@drawable/ic_gallery_empty2" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - /> - - <TextView - android:layout_below="@id/no_pictures_image" - android:layout_centerHorizontal="true" - android:paddingTop="5dip" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:layout_gravity="center" - android:text="@string/image_gallery_NoImageView_text" - android:textColor="#FFBEBEBE" - android:textSize="18dip" - /> - </RelativeLayout> - -</RelativeLayout> - diff --git a/res/layout/movie_view.xml b/res/layout/movie_view.xml deleted file mode 100644 index 6344d8b..0000000 --- a/res/layout/movie_view.xml +++ /dev/null @@ -1,48 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" - android:layout_width="fill_parent" - android:layout_height="fill_parent"> - - <VideoView - android:id="@+id/surface_view" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:layout_centerInParent="true" - /> - - <LinearLayout android:id="@+id/progress_indicator" - android:orientation="vertical" - android:layout_centerInParent="true" - android:layout_width="fill_parent" - android:layout_height="wrap_content"> - - <ProgressBar android:id="@android:id/progress" - style="?android:attr/progressBarStyleLarge" - android:layout_gravity="center" - android:layout_width="wrap_content" - android:layout_height="wrap_content" /> - - <TextView android:paddingTop="5dip" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:layout_gravity="center" - android:text="@string/loading_video" android:textSize="14sp" - android:textColor="#ffffffff" /> - </LinearLayout> - -</RelativeLayout> diff --git a/res/layout/on_screen_hint.xml b/res/layout/on_screen_hint.xml deleted file mode 100644 index a56b728..0000000 --- a/res/layout/on_screen_hint.xml +++ /dev/null @@ -1,38 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* -** Copyright 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. -*/ ---> - -<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:orientation="vertical" - android:background="@drawable/on_screen_hint_frame"> - - <TextView - android:id="@+id/message" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:layout_weight="1" - android:textAppearance="@style/OnScreenHintTextAppearance.Small" - android:textColor="#ffffffff" - android:shadowColor="#BB000000" - android:shadowRadius="2.75" - /> -</LinearLayout> - - diff --git a/res/layout/photo_frame.xml b/res/layout/photo_frame.xml deleted file mode 100644 index 5537b1e..0000000 --- a/res/layout/photo_frame.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<ImageView xmlns:android="http://schemas.android.com/apk/res/android" - android:id="@+id/photo" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:scaleType="center" - android:cropToPadding="true" - android:background="@drawable/photo_frame" - /> diff --git a/res/layout/post_picture_panel.xml b/res/layout/post_picture_panel.xml deleted file mode 100644 index 17cafe2..0000000 --- a/res/layout/post_picture_panel.xml +++ /dev/null @@ -1,39 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" - android:visibility="gone" - android:id="@+id/post_picture_panel" - android:layout_alignBottom="@id/shutter_button" - android:layout_toLeftOf="@id/shutter_button" - android:layout_marginRight="15dip" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:orientation="horizontal"> - - <com.android.camera.ActionMenuButton - android:id="@+id/attach" - android:drawableTop="@drawable/ic_menu_attach" - android:text="@string/camera_attach" - style="@style/OnscreenActionIcon" - /> - <com.android.camera.ActionMenuButton - android:id="@+id/cancel" - android:drawableTop="@drawable/ic_menu_cancel" - android:text="@string/camera_cancel" - style="@style/OnscreenActionIcon" - /> -</LinearLayout> diff --git a/res/layout/slide_show.xml b/res/layout/slide_show.xml deleted file mode 100644 index e9bfe0f..0000000 --- a/res/layout/slide_show.xml +++ /dev/null @@ -1,27 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" - android:layout_width="fill_parent" - android:layout_height="fill_parent"> - - <view android:id="@+id/imageview" - class="com.android.camera.SlideShow$ImageViewTouch" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - /> - -</FrameLayout> diff --git a/res/layout/video_camera.xml b/res/layout/video_camera.xml deleted file mode 100644 index da37bcd..0000000 --- a/res/layout/video_camera.xml +++ /dev/null @@ -1,127 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:orientation="horizontal"> - - <com.android.camera.VideoPreview - android:id="@+id/camera_preview" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:layout_centerInParent="true" - /> - - <ImageView - android:id="@+id/video_frame" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:visibility="gone" - /> - - <ImageView - android:id="@+id/blackout" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:visibility="invisible" - /> - - <com.android.camera.ShutterButton - android:id="@+id/shutter_button" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:src="@drawable/ic_camera_indicator_video" - android:background="@drawable/ic_btn_camera_background" - android:clickable="true" - android:focusable="true" - android:layout_alignParentRight="true" - android:layout_alignParentTop="true" - android:layout_marginRight="50dip" - android:layout_marginTop="10dip" - android:scaleType="center"/> - - <!-- Note: In this TextView the paddingRight="2" - attribute is required because otherwise the - text's drop shadow will be clipped. --> - <TextView - android:id="@+id/recording_time" - android:layout_width="90dip" - android:layout_height="wrap_content" - android:layout_toLeftOf="@id/shutter_button" - android:layout_alignTop="@id/shutter_button" - android:layout_marginTop="20dip" - android:layout_marginRight="6dip" - android:paddingRight="2dip" - android:shadowColor="#c0000000" - android:shadowDx="1" - android:shadowDy="1" - android:shadowRadius="1" - android:gravity="right" - android:textColor="#ffffffff" - android:textSize="20dip" - android:textStyle="bold" - android:visibility="gone"/> - - <LinearLayout - android:visibility="gone" - android:id="@+id/post_picture_panel" - android:layout_alignTop="@id/shutter_button" - android:layout_toLeftOf="@id/shutter_button" - android:layout_marginRight="15dip" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:orientation="horizontal"> - - <com.android.camera.ActionMenuButton - android:id="@+id/gallery" - android:drawableTop="@drawable/ic_menu_gallery" - android:text="@string/camera_gallery" - style="@style/OnscreenActionIcon" - /> - <com.android.camera.ActionMenuButton - android:id="@+id/play" - android:drawableTop="@drawable/ic_menu_camera_play" - android:text="@string/camera_play" - style="@style/OnscreenActionIcon" - /> - <com.android.camera.ActionMenuButton - android:id="@+id/share" - android:drawableTop="@drawable/ic_menu_share" - android:text="@string/camera_share" - style="@style/OnscreenActionIcon" - /> - <com.android.camera.ActionMenuButton - android:id="@+id/discard" - android:drawableTop="@drawable/ic_menu_delete" - android:text="@string/camera_toss" - style="@style/OnscreenActionIcon" - /> - <com.android.camera.ActionMenuButton - android:id="@+id/attach" - android:drawableTop="@drawable/ic_menu_attach" - android:text="@string/camera_attach" - style="@style/OnscreenActionIcon" - /> - <com.android.camera.ActionMenuButton - android:id="@+id/cancel" - android:drawableTop="@drawable/ic_menu_cancel" - android:text="@string/camera_cancel" - style="@style/OnscreenActionIcon" - /> - </LinearLayout> -</RelativeLayout> - diff --git a/res/layout/viewimage.xml b/res/layout/viewimage.xml deleted file mode 100644 index 99d76b0..0000000 --- a/res/layout/viewimage.xml +++ /dev/null @@ -1,160 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" - android:id="@+id/rootLayout" - android:layout_width="fill_parent" - android:layout_height="fill_parent"> - - <AbsoluteLayout android:id="@+id/slideShowContainer" - android:layout_width="fill_parent" - android:layout_height="fill_parent"> - <view android:id="@+id/image1_slideShow" - class="com.android.camera.ViewImage$ImageViewTouch" - android:background="#00000000" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - /> - <view android:id="@+id/image2_slideShow" - class="com.android.camera.ViewImage$ImageViewTouch" - android:background="#00000000" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - /> - </AbsoluteLayout> - - <AbsoluteLayout android:id="@+id/abs" - android:layout_width="fill_parent" - android:layout_height="fill_parent"> - <view class="com.android.camera.ViewImage$ScrollHandler" android:id="@+id/scroller" - android:layout_width="fill_parent" - android:layout_height="fill_parent" - android:orientation="horizontal" - - android:background="#FF000000" - android:layout_x="0dip" - android:layout_y="0dip"> - - <view android:id="@+id/image1" - class="com.android.camera.ViewImage$ImageViewTouch" - android:background="#FF000000" - android:layout_width="0dip" - android:layout_height="fill_parent" /> - - <View android:id="@+id/padding1" - android:layout_height="fill_parent" - android:layout_width="0dip" /> - - <view android:id="@+id/image2" - class="com.android.camera.ViewImage$ImageViewTouch" - android:background="#FF000000" - android:layout_width="0dip" - android:layout_height="fill_parent"/> - - <View android:id="@+id/padding2" - android:layout_height="fill_parent" - android:layout_width="0dip" /> - - <view android:id="@+id/image3" - class="com.android.camera.ViewImage$ImageViewTouch" - android:background="#FF000000" - android:layout_width="0dip" - android:layout_height="fill_parent"/> - </view> - </AbsoluteLayout> - - <ImageView - android:visibility="gone" - android:id="@+id/shutter_button" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:src="@drawable/ic_camera_indicator_photo" - android:background="@drawable/ic_btn_camera_background" - android:clickable="true" - android:focusable="true" - android:layout_alignParentRight="true" - android:layout_alignParentTop="true" - android:layout_marginRight="50dip" - android:layout_marginTop="10dip" - android:scaleType="center"/> - - <LinearLayout - android:visibility="gone" - android:id="@+id/action_icon_panel" - android:layout_alignBottom="@id/shutter_button" - android:layout_toLeftOf="@id/shutter_button" - android:layout_marginRight="15dip" - android:layout_width="wrap_content" - android:layout_height="wrap_content" - android:orientation="horizontal"> - - <com.android.camera.ActionMenuButton - android:id="@+id/gallery" - android:drawableTop="@drawable/ic_menu_gallery" - android:text="@string/camera_gallery" - style="@style/OnscreenActionIcon" - /> - <com.android.camera.ActionMenuButton - android:id="@+id/setas" - android:drawableTop="@drawable/ic_menu_set_as" - android:text="@string/camera_set" - style="@style/OnscreenActionIcon" - /> - <com.android.camera.ActionMenuButton - android:id="@+id/share" - android:drawableTop="@drawable/ic_menu_share" - android:text="@string/camera_share" - style="@style/OnscreenActionIcon" - /> - <com.android.camera.ActionMenuButton - android:id="@+id/discard" - android:drawableTop="@drawable/ic_menu_delete" - android:text="@string/camera_toss" - style="@style/OnscreenActionIcon" - /> - <com.android.camera.ActionMenuButton - android:id="@+id/attach" - android:drawableTop="@drawable/ic_menu_attach" - android:text="@string/camera_attach" - style="@style/OnscreenActionIcon" - /> - <com.android.camera.ActionMenuButton - android:id="@+id/cancel" - android:drawableTop="@drawable/ic_menu_cancel" - android:text="@string/camera_cancel" - style="@style/OnscreenActionIcon" - /> - </LinearLayout> - <ImageView android:id="@+id/prev_image" - android:clickable="true" - android:layout_width="wrap_content" android:layout_height="wrap_content" - android:layout_alignParentLeft="true" - android:layout_centerVertical="true" - android:visibility="invisible" - android:src="@drawable/btn_camera_arrow_left" - /> - - <ImageView android:id="@+id/next_image" - android:clickable="true" - android:layout_width="wrap_content" android:layout_height="wrap_content" - android:layout_alignParentRight="true" - android:layout_centerVertical="true" - android:visibility="invisible" - android:src="@drawable/btn_camera_arrow_right" - /> - -</RelativeLayout> - diff --git a/res/raw/camera_click.ogg b/res/raw/camera_click.ogg Binary files differdeleted file mode 100644 index 0a769ff..0000000 --- a/res/raw/camera_click.ogg +++ /dev/null diff --git a/res/values-cs/arrays.xml b/res/values-cs/arrays.xml deleted file mode 100644 index dfbf090..0000000 --- a/res/values-cs/arrays.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <!-- no translation found for pref_camera_videoquality_entries:0 (4155278146225809483) --> - <!-- no translation found for pref_camera_videoquality_entries:1 (2439895494739176281) --> - <string-array name="pref_camera_videoquality_entryvalues"> - <item>"0"</item> - <item>"1"</item> - </string-array> -</resources> diff --git a/res/values-cs/strings.xml b/res/values-cs/strings.xml deleted file mode 100644 index d720d15..0000000 --- a/res/values-cs/strings.xml +++ /dev/null @@ -1,151 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <string name="all_images">"Všechny fotografie"</string> - <string name="all_videos">"Všechna videa"</string> - <string name="camera_label">"Fotoaparát"</string> - <string name="gallery_picker_label">"Galerie"</string> - <string name="gallery_camera_bucket_name">"Pořízené fotografie"</string> - <string name="gallery_camera_videos_bucket_name">"Pořízená videa"</string> - <string name="switch_to_video_lable">"Přepnout do režimu video"</string> - <string name="switch_to_camera_lable">"Přepnout do režimu fotoaparát"</string> - <string name="crop_label">"Oříznout fotografii"</string> - <string name="view_label">"Zobrazit fotografii"</string> - <string name="preferences_label">"Nastavení fotoaparátu"</string> - <string name="wait">"Čekejte prosím..."</string> - <string name="no_storage">"Než začnete používat fotoaparát, vložte kartu SD."</string> - <string name="not_enough_space">"Vaše karta SD je plná."</string> - <string name="preparing_sd">"Příprava karty SD..."</string> - <string name="wallpaper">"Nastavování tapety, čekejte prosím..."</string> - <string name="savingImage">"Ukládání fotografie..."</string> - <string name="runningFaceDetection">"Čekejte prosím..."</string> - <string name="flip_orientation">"Změnit orientaci"</string> - <string name="settings">"Nastavení"</string> - <string name="view">"Zobrazit"</string> - <string name="details">"Podrobnosti"</string> - <string name="rotate">"Otočit"</string> - <string name="rotate_left">"Otočit doleva"</string> - <string name="rotate_right">"Otočit doprava"</string> - <string name="slide_show">"Prezentace"</string> - <string name="capture_picture">"Fotografovat"</string> - <string name="capture_video">"Natočit video"</string> - <string name="crop_save_text">"Uložit"</string> - <string name="crop_discard_text">"Zahodit"</string> - <string name="confirm_delete_title">"Smazat"</string> - <string name="confirm_delete_message">"Fotografie bude smazána."</string> - <string name="confirm_delete_video_message">"Video bude smazáno."</string> - <string name="camera_toss">"Smazat"</string> - <string name="camera_gallery">"Galerie"</string> - <string name="camera_share">"Sdílet"</string> - <string name="camera_set">"Použít jako"</string> - <string name="camera_play">"Přehrát"</string> - <string name="camera_attach">"Připojit přílohu"</string> - <string name="camera_cancel">"Zrušit"</string> - <string name="camera_crop">"Oříznout"</string> - <string name="camera_tossing">"Mazání..."</string> - <string name="no_way_to_share_image">"Tuto fotografii nelze sdílet."</string> - <string name="no_way_to_share_video">"Toto video nelze sdílet."</string> - <string name="camera_gallery_photos_text">"Galerie"</string> - <string name="camera_pick_wallpaper">"Fotografie"</string> - <string name="camera_setas_wallpaper">"Tapeta"</string> - <string name="pref_gallery_category">"Obecné nastavení"</string> - <string name="pref_slideshow_category">"Nastavení prezentace"</string> - <string name="pref_camera_general_settings_category">"Obecné nastavení"</string> - <string name="pref_gallery_size_title">"Zobrazovaná velikost"</string> - <string name="pref_gallery_size_summary">"Vyberte zobrazovanou velikost obrázků a videí"</string> - <string name="pref_gallery_size_dialogtitle">"Velikost fotografie"</string> - <string-array name="pref_gallery_size_choices"> - <item>"Velké"</item> - <item>"Malé"</item> - </string-array> - <string name="pref_gallery_sort_title">"Řazení"</string> - <string name="pref_gallery_sort_summary">"Vyberte způsob řazení obrázků a videí"</string> - <string name="pref_gallery_sort_dialogtitle">"Řazení fotografií"</string> - <string-array name="pref_gallery_sort_choices"> - <item>"Od nejnovějších"</item> - <item>"Od nejstarších"</item> - </string-array> - <string name="pref_gallery_slideshow_interval_title">"Interval prezentace"</string> - <string name="pref_gallery_slideshow_interval_summary">"Vyberte, jak dlouho má být zobrazen každý snímek"</string> - <string name="pref_gallery_slideshow_interval_dialogtitle">"Interval prezentace"</string> - <string-array name="pref_gallery_slideshow_interval_choices"> - <item>"2 sekundy"</item> - <item>"3 sekundy"</item> - <item>"4 sekundy"</item> - </string-array> - <string name="pref_gallery_slideshow_transition_title">"Přechod v prezentaci"</string> - <string name="pref_gallery_slideshow_transition_summary">"Vyberte efekt, který má být použit při přechodu z jednoho snímku na další"</string> - <string name="pref_gallery_slideshow_transition_dialogtitle">"Přechod v prezentaci"</string> - <string-array name="pref_gallery_slideshow_transition_choices"> - <item>"Prolínat"</item> - <item>"Posouvat zleva doprava"</item> - <item>"Posouvat shora dolů"</item> - <item>"Náhodný výběr"</item> - </string-array> - <string name="pref_gallery_slideshow_repeat_title">"Opakovat prezentaci"</string> - <string name="pref_gallery_slideshow_repeat_summary">"Přehrát prezentaci více než jednou"</string> - <string name="pref_gallery_slideshow_shuffle_title">"Náhodné pořadí snímků"</string> - <string name="pref_gallery_slideshow_shuffle_summary">"Zobrazit fotografie v náhodném pořadí"</string> - <string name="pref_camera_recordlocation_title">"K fotografiím ukládat místo pořízení"</string> - <string name="pref_camera_recordlocation_summary">"V datech fotografie zaznamenat místo pořízení"</string> - <string name="pref_camera_videoquality_category">"Kvalita videa"</string> - <string name="pref_camera_videoquality_title">"Vybrat kvalitu videa"</string> - <string name="pref_camera_videoquality_entry_0">"Nízká (pro zprávy MMS)"</string> - <string name="pref_camera_videoquality_entry_1">"Vysoká (pro kartu SD)"</string> - <string name="pref_camera_videoquality_dialogtitle">"Kvalita videa"</string> - <string name="camerasettings">"Nastavení"</string> - <string name="image_gallery_NoImageView_text">"Žádná média nebyla nalezena."</string> - <string name="pref_gallery_confirm_delete_title">"Potvrdit smazání"</string> - <string name="pref_gallery_confirm_delete_summary">"Žádat potvrzení před smazáním obrázku nebo videa"</string> - <string name="details_panel_title">"Podrobnosti"</string> - <string name="details_file_size">"Velikost souboru:"</string> - <string name="details_image_resolution">"Rozlišení:"</string> - <string name="details_duration">"Délka:"</string> - <string name="details_date_taken">"Datum pořízení:"</string> - <string name="details_frame_rate">"Počet snímků za sekundu:"</string> - <string name="details_bit_rate">"Bitová rychlost:"</string> - <string name="details_codec">"Kodek:"</string> - <string name="details_format">"Formát:"</string> - <string name="details_dimension_x">"%1$d x %2$d"</string> - <string name="details_ms">"%1$02d:%2$02d"</string> - <string name="details_hms">"%1$d:%2$02d:%3$02d"</string> - <string name="details_fps">"%1$d snímků/s"</string> - <string name="details_kbps">"%1$d Kb/s"</string> - <string name="details_mbps">"%1$g Mb/s"</string> - <string name="details_ok">"OK"</string> - <string name="context_menu_header">"Možnosti fotografií"</string> - <string name="video_context_menu_header">"Možnosti videa"</string> - <string name="multiface_crop_help">"Začněte klepnutím na obličej."</string> - <string name="photos_gallery_title">"Galerie"</string> - <string name="pick_photos_gallery_title">"Vyberte fotografii"</string> - <string name="videos_gallery_title">"Galerie"</string> - <string name="pick_videos_gallery_title">"Vybrat video"</string> - <string name="loading_progress_format_string">"Zbývá <xliff:g id="COUNTER">%d</xliff:g>"</string> - <string name="sendImage">"Sdílet fotografii pomocí"</string> - <string name="setImage">"Fotografie bude použita jako"</string> - <string name="sendVideo">"Sdílet video pomocí"</string> - <string name="movieviewlabel">"Filmy"</string> - <string name="loading_video">"Načítání videa..."</string> - <string name="spaceIsLow_title">"Dochází volné místo"</string> - <string name="spaceIsLow_content">"Na vaší kartě SD je málo místa. Změňte nastavení kvality nebo smažte položky z Galerie."</string> - <string name="resume_playing_title">"Pokračovat v přehrávání videa"</string> - <string name="resume_playing_message">"Pokračovat v přehrávání od %s?"</string> - <string name="resume_playing_resume">"Pokračovat v přehrávání"</string> - <string name="resume_playing_restart">"Začít znovu"</string> - <string name="gadget_title">"Rámeček fotografie"</string> - <string name="video_file_name_format">"\'video\'-yyyy-MM-dd-HH-mm-ss"</string> -</resources> diff --git a/res/values-de/arrays.xml b/res/values-de/arrays.xml deleted file mode 100644 index dfbf090..0000000 --- a/res/values-de/arrays.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <!-- no translation found for pref_camera_videoquality_entries:0 (4155278146225809483) --> - <!-- no translation found for pref_camera_videoquality_entries:1 (2439895494739176281) --> - <string-array name="pref_camera_videoquality_entryvalues"> - <item>"0"</item> - <item>"1"</item> - </string-array> -</resources> diff --git a/res/values-de/strings.xml b/res/values-de/strings.xml deleted file mode 100644 index 765659f..0000000 --- a/res/values-de/strings.xml +++ /dev/null @@ -1,151 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <string name="all_images">"Alle Bilder"</string> - <string name="all_videos">"Alle Videos"</string> - <string name="camera_label">"Kamera"</string> - <string name="gallery_picker_label">"Galerie"</string> - <string name="gallery_camera_bucket_name">"Kamerabilder"</string> - <string name="gallery_camera_videos_bucket_name">"Kameravideos"</string> - <string name="switch_to_video_lable">"Zu Video wechseln"</string> - <string name="switch_to_camera_lable">"Zu Kamera wechseln"</string> - <string name="crop_label">"Bild zuschneiden"</string> - <string name="view_label">"Bild anzeigen"</string> - <string name="preferences_label">"Kameraeinstellungen"</string> - <string name="wait">"Bitte warten..."</string> - <string name="no_storage">"Legen Sie vor Verwendung der Kamera eine SD-Karte ein."</string> - <string name="not_enough_space">"Ihre SD-Karte ist voll."</string> - <string name="preparing_sd">"SD-Karte wird vorbereitet..."</string> - <string name="wallpaper">"Hintergrund wird eingestellt, bitte warten..."</string> - <string name="savingImage">"Bild wird gespeichert..."</string> - <string name="runningFaceDetection">"Bitte warten..."</string> - <string name="flip_orientation">"Ausrichtung drehen"</string> - <string name="settings">"Einstellungen"</string> - <string name="view">"Anzeigen"</string> - <string name="details">"Details"</string> - <string name="rotate">"Drehen"</string> - <string name="rotate_left">"Nach links drehen"</string> - <string name="rotate_right">"Nach rechts drehen"</string> - <string name="slide_show">"Diashow"</string> - <string name="capture_picture">"Bild aufnehmen"</string> - <string name="capture_video">"Video aufnehmen"</string> - <string name="crop_save_text">"Speichern"</string> - <string name="crop_discard_text">"Verwerfen"</string> - <string name="confirm_delete_title">"Löschen"</string> - <string name="confirm_delete_message">"Das Bild wird gelöscht."</string> - <string name="confirm_delete_video_message">"Das Video wird gelöscht."</string> - <string name="camera_toss">"Löschen"</string> - <string name="camera_gallery">"Galerie"</string> - <string name="camera_share">"Senden"</string> - <string name="camera_set">"Festlegen als"</string> - <string name="camera_play">"Wiedergeben"</string> - <string name="camera_attach">"Anhängen"</string> - <string name="camera_cancel">"Abbrechen"</string> - <string name="camera_crop">"Zuschneiden"</string> - <string name="camera_tossing">"Löschvorgang..."</string> - <string name="no_way_to_share_image">"Dieses Bild kann nicht weitergeleitet werden."</string> - <string name="no_way_to_share_video">"Dieses Video kann nicht weitergeleitet werden."</string> - <string name="camera_gallery_photos_text">"Galerie"</string> - <string name="camera_pick_wallpaper">"Bilder"</string> - <string name="camera_setas_wallpaper">"Hintergrund"</string> - <string name="pref_gallery_category">"Allgemeine Einstellungen"</string> - <string name="pref_slideshow_category">"Einstellungen für Diashow"</string> - <string name="pref_camera_general_settings_category">"Allgemeine Einstellungen"</string> - <string name="pref_gallery_size_title">"Anzeigegröße"</string> - <string name="pref_gallery_size_summary">"Anzeigegröße für Bilder und Videos auswählen"</string> - <string name="pref_gallery_size_dialogtitle">"Bildgröße"</string> - <string-array name="pref_gallery_size_choices"> - <item>"Groß"</item> - <item>"Klein"</item> - </string-array> - <string name="pref_gallery_sort_title">"Sortierreihenfolge"</string> - <string name="pref_gallery_sort_summary">"Sortierreihenfolge für Bilder und Videos auswählen"</string> - <string name="pref_gallery_sort_dialogtitle">"Sortierreihenfolge für Bilder"</string> - <string-array name="pref_gallery_sort_choices"> - <item>"Neue zuerst"</item> - <item>"Neue zuletzt"</item> - </string-array> - <string name="pref_gallery_slideshow_interval_title">"Diashow-Intervall"</string> - <string name="pref_gallery_slideshow_interval_summary">"Auswählen, wie lange jedes Bild in der Diashow angezeigt werden soll"</string> - <string name="pref_gallery_slideshow_interval_dialogtitle">"Diashow-Intervall"</string> - <string-array name="pref_gallery_slideshow_interval_choices"> - <item>"2 Sekunden"</item> - <item>"3 Sekunden"</item> - <item>"4 Sekunden"</item> - </string-array> - <string name="pref_gallery_slideshow_transition_title">"Diashow - Übergang"</string> - <string name="pref_gallery_slideshow_transition_summary">"Effekt auswählen, der beim Wechsel zum nächsten Bild angewendet wird"</string> - <string name="pref_gallery_slideshow_transition_dialogtitle">"Diashow - Übergang"</string> - <string-array name="pref_gallery_slideshow_transition_choices"> - <item>"Ein- und ausblenden"</item> - <item>"Einblendung von links - rechts"</item> - <item>"Einblendung von oben - unten"</item> - <item>"Zufällige Auswahl"</item> - </string-array> - <string name="pref_gallery_slideshow_repeat_title">"Diashow erneut anzeigen?"</string> - <string name="pref_gallery_slideshow_repeat_summary">"Diashow mehrmals anzeigen"</string> - <string name="pref_gallery_slideshow_shuffle_title">"Bilder mischen"</string> - <string name="pref_gallery_slideshow_shuffle_summary">"Bilder in zufälliger Reihenfolge anzeigen"</string> - <string name="pref_camera_recordlocation_title">"Aufnahmeort in Bildern speichern"</string> - <string name="pref_camera_recordlocation_summary">"Aufnahmeort in Bilddaten speichern"</string> - <string name="pref_camera_videoquality_category">"Videoqualität"</string> - <string name="pref_camera_videoquality_title">"Videoqualität auswählen"</string> - <string name="pref_camera_videoquality_entry_0">"Niedrig (für MMS-Mitteilungen)"</string> - <string name="pref_camera_videoquality_entry_1">"Hoch (für SD-Karte)"</string> - <string name="pref_camera_videoquality_dialogtitle">"Videoqualität"</string> - <string name="camerasettings">"Einstellungen"</string> - <string name="image_gallery_NoImageView_text">"Keine Medien gefunden."</string> - <string name="pref_gallery_confirm_delete_title">"Löschvorgang bestätigen"</string> - <string name="pref_gallery_confirm_delete_summary">"Bestätigung vor dem Löschen eines Bildes oder Videos anzeigen"</string> - <string name="details_panel_title">"Details"</string> - <string name="details_file_size">"Dateigröße:"</string> - <string name="details_image_resolution">"Auflösung:"</string> - <string name="details_duration">"Dauer:"</string> - <string name="details_date_taken">"Aufnahmedatum:"</string> - <string name="details_frame_rate">"Framerate:"</string> - <string name="details_bit_rate">"Bitrate:"</string> - <string name="details_codec">"Codec:"</string> - <string name="details_format">"Format:"</string> - <string name="details_dimension_x">"%1$d x %2$d"</string> - <string name="details_ms">"%1$02d:%2$02d"</string> - <string name="details_hms">"%1$d:%2$02d:%3$02d"</string> - <string name="details_fps">"%1$d fps"</string> - <string name="details_kbps">"%1$d Kbit/s"</string> - <string name="details_mbps">"%1$g Mbit/s"</string> - <string name="details_ok">"OK"</string> - <string name="context_menu_header">"Bildoptionen"</string> - <string name="video_context_menu_header">"Videooptionen"</string> - <string name="multiface_crop_help">"Tippen Sie zum Beginnen auf ein Gesicht."</string> - <string name="photos_gallery_title">"Galerie"</string> - <string name="pick_photos_gallery_title">"Bild auswählen"</string> - <string name="videos_gallery_title">"Galerie"</string> - <string name="pick_videos_gallery_title">"Video auswählen"</string> - <string name="loading_progress_format_string">"noch <xliff:g id="COUNTER">%d</xliff:g>"</string> - <string name="sendImage">"Bild senden via"</string> - <string name="setImage">"Bild festlegen als"</string> - <string name="sendVideo">"Video weiterleiten via"</string> - <string name="movieviewlabel">"Filme"</string> - <string name="loading_video">"Video wird geladen..."</string> - <string name="spaceIsLow_title">"Geringer Speicherplatz"</string> - <string name="spaceIsLow_content">"Auf Ihrer SD-Karte ist nicht mehr genügend Speicherplatz vorhanden. Ändern Sie die Qualitätseinstellung oder löschen Sie Elemente aus der Galerie."</string> - <string name="resume_playing_title">"Mit Video fortfahren"</string> - <string name="resume_playing_message">"Mit Wiedergabe fortfahren ab %s ?"</string> - <string name="resume_playing_resume">"Mit Wiedergabe fortfahren"</string> - <string name="resume_playing_restart">"Starten"</string> - <string name="gadget_title">"Bildrahmen"</string> - <string name="video_file_name_format">"\'video\'-yyyy-MM-dd-HH-mm-ss"</string> -</resources> diff --git a/res/values-es/arrays.xml b/res/values-es/arrays.xml deleted file mode 100644 index dfbf090..0000000 --- a/res/values-es/arrays.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <!-- no translation found for pref_camera_videoquality_entries:0 (4155278146225809483) --> - <!-- no translation found for pref_camera_videoquality_entries:1 (2439895494739176281) --> - <string-array name="pref_camera_videoquality_entryvalues"> - <item>"0"</item> - <item>"1"</item> - </string-array> -</resources> diff --git a/res/values-es/strings.xml b/res/values-es/strings.xml deleted file mode 100644 index ae347e9..0000000 --- a/res/values-es/strings.xml +++ /dev/null @@ -1,151 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <string name="all_images">"Todas las imágenes"</string> - <string name="all_videos">"Todos los vídeos"</string> - <string name="camera_label">"Cámara"</string> - <string name="gallery_picker_label">"Galería"</string> - <string name="gallery_camera_bucket_name">"Imágenes de cámara"</string> - <string name="gallery_camera_videos_bucket_name">"Vídeos de cámara"</string> - <string name="switch_to_video_lable">"Cambiar a vídeo"</string> - <string name="switch_to_camera_lable">"Cambiar a cámara"</string> - <string name="crop_label">"Recortar imagen"</string> - <string name="view_label">"Ver imagen"</string> - <string name="preferences_label">"Configuración de cámara"</string> - <string name="wait">"Por favor, espera..."</string> - <string name="no_storage">"Antes de utilizar la cámara, debes insertar una tarjeta SD."</string> - <string name="not_enough_space">"La tarjeta SD está llena."</string> - <string name="preparing_sd">"Preparando tarjeta SD…"</string> - <string name="wallpaper">"Estableciendo fondo de pantalla; por favor, espera..."</string> - <string name="savingImage">"Guardando imagen..."</string> - <string name="runningFaceDetection">"Por favor, espera..."</string> - <string name="flip_orientation">"Cambiar orientación"</string> - <string name="settings">"Ajustes"</string> - <string name="view">"Ver"</string> - <string name="details">"Detalles"</string> - <string name="rotate">"Girar"</string> - <string name="rotate_left">"Girar a la izquierda"</string> - <string name="rotate_right">"Girar a la derecha"</string> - <string name="slide_show">"Presentación"</string> - <string name="capture_picture">"Capturar imagen"</string> - <string name="capture_video">"Capturar vídeo"</string> - <string name="crop_save_text">"Guardar"</string> - <string name="crop_discard_text">"Descartar"</string> - <string name="confirm_delete_title">"Suprimir"</string> - <string name="confirm_delete_message">"Se eliminará la imagen."</string> - <string name="confirm_delete_video_message">"Se eliminará el vídeo."</string> - <string name="camera_toss">"Suprimir"</string> - <string name="camera_gallery">"Galería"</string> - <string name="camera_share">"Compartir"</string> - <string name="camera_set">"Establecer como"</string> - <string name="camera_play">"Reproducir"</string> - <string name="camera_attach">"Adjuntar"</string> - <string name="camera_cancel">"Cancelar"</string> - <string name="camera_crop">"Recortar"</string> - <string name="camera_tossing">"Eliminando..."</string> - <string name="no_way_to_share_image">"Esta imagen no se puede compartir."</string> - <string name="no_way_to_share_video">"Este vídeo no se puede compartir."</string> - <string name="camera_gallery_photos_text">"Galería"</string> - <string name="camera_pick_wallpaper">"Imágenes"</string> - <string name="camera_setas_wallpaper">"Fondo de pantalla"</string> - <string name="pref_gallery_category">"Configuración general"</string> - <string name="pref_slideshow_category">"Configuración de presentación"</string> - <string name="pref_camera_general_settings_category">"Configuración general"</string> - <string name="pref_gallery_size_title">"Tamaño de visualización"</string> - <string name="pref_gallery_size_summary">"Seleccionar el tamaño de visualización de imágenes y vídeos"</string> - <string name="pref_gallery_size_dialogtitle">"Tamaño de imagen"</string> - <string-array name="pref_gallery_size_choices"> - <item>"Grande"</item> - <item>"Pequeña"</item> - </string-array> - <string name="pref_gallery_sort_title">"Orden"</string> - <string name="pref_gallery_sort_summary">"Seleccionar el orden de imágenes y vídeos"</string> - <string name="pref_gallery_sort_dialogtitle">"Ordenación de imágenes"</string> - <string-array name="pref_gallery_sort_choices"> - <item>"Más recientes primero"</item> - <item>"Más recientes al final"</item> - </string-array> - <string name="pref_gallery_slideshow_interval_title">"Intervalo de presentación"</string> - <string name="pref_gallery_slideshow_interval_summary">"Seleccionar la duración de cada diapositiva"</string> - <string name="pref_gallery_slideshow_interval_dialogtitle">"Intervalo de presentación"</string> - <string-array name="pref_gallery_slideshow_interval_choices"> - <item>"2 segundos"</item> - <item>"3 segundos"</item> - <item>"4 segundos"</item> - </string-array> - <string name="pref_gallery_slideshow_transition_title">"Transición de diapositivas"</string> - <string name="pref_gallery_slideshow_transition_summary">"Seleccionar el efecto que se aplicará al pasar de una diapositiva a otra"</string> - <string name="pref_gallery_slideshow_transition_dialogtitle">"Transición de diapositivas"</string> - <string-array name="pref_gallery_slideshow_transition_choices"> - <item>"Fundido de entrada y salida"</item> - <item>"Transición de izquierda a derecha"</item> - <item>"Transición de arriba a abajo"</item> - <item>"Selección aleatoria"</item> - </string-array> - <string name="pref_gallery_slideshow_repeat_title">"Repetir presentación"</string> - <string name="pref_gallery_slideshow_repeat_summary">"Mostrar presentación más de una vez"</string> - <string name="pref_gallery_slideshow_shuffle_title">"Reproducir diapositivas en orden aleatorio"</string> - <string name="pref_gallery_slideshow_shuffle_summary">"Mostrar imágenes en orden aleatorio"</string> - <string name="pref_camera_recordlocation_title">"Almacenar ubicación en imágenes"</string> - <string name="pref_camera_recordlocation_summary">"Registrar ubicación en datos de imagen"</string> - <string name="pref_camera_videoquality_category">"Calidad de vídeo"</string> - <string name="pref_camera_videoquality_title">"Seleccionar calidad de vídeo"</string> - <string name="pref_camera_videoquality_entry_0">"Baja (para mensajes MMS)"</string> - <string name="pref_camera_videoquality_entry_1">"Alta (para tarjeta SD)"</string> - <string name="pref_camera_videoquality_dialogtitle">"Calidad de vídeo"</string> - <string name="camerasettings">"Ajustes"</string> - <string name="image_gallery_NoImageView_text">"No se ha encontrado ningún medio."</string> - <string name="pref_gallery_confirm_delete_title">"Confirmar eliminaciones"</string> - <string name="pref_gallery_confirm_delete_summary">"Mostrar confirmación antes de eliminar una imagen o un vídeo"</string> - <string name="details_panel_title">"Detalles"</string> - <string name="details_file_size">"Tamaño de archivo:"</string> - <string name="details_image_resolution">"Resolución:"</string> - <string name="details_duration">"Duración:"</string> - <string name="details_date_taken">"Fecha de realización:"</string> - <string name="details_frame_rate">"Frecuencia de imagen:"</string> - <string name="details_bit_rate">"Velocidad binaria:"</string> - <string name="details_codec">"Códec:"</string> - <string name="details_format">"Formato:"</string> - <string name="details_dimension_x">"%1$d x %2$d"</string> - <string name="details_ms">"%1$02d:%2$02d"</string> - <string name="details_hms">"%1$d:%2$02d:%3$02d"</string> - <string name="details_fps">"%1$d fps"</string> - <string name="details_kbps">"%1$d Kbps"</string> - <string name="details_mbps">"%1$g Mbps"</string> - <string name="details_ok">"Aceptar"</string> - <string name="context_menu_header">"Opciones de imagen"</string> - <string name="video_context_menu_header">"Opciones de vídeo"</string> - <string name="multiface_crop_help">"Selecciona una cara para empezar."</string> - <string name="photos_gallery_title">"Galería"</string> - <string name="pick_photos_gallery_title">"Seleccionar imagen"</string> - <string name="videos_gallery_title">"Galería"</string> - <string name="pick_videos_gallery_title">"Seleccionar vídeo"</string> - <string name="loading_progress_format_string">"<xliff:g id="COUNTER">%d</xliff:g> restantes"</string> - <string name="sendImage">"Compartir imagen por"</string> - <string name="setImage">"Establecer imagen como"</string> - <string name="sendVideo">"Compartir vídeo a través de"</string> - <string name="movieviewlabel">"Películas"</string> - <string name="loading_video">"Cargando vídeo…"</string> - <string name="spaceIsLow_title">"Poco espacio"</string> - <string name="spaceIsLow_content">"No queda espacio en la tarjeta SD. Cambia la configuración de calidad o elimina elementos de la galería."</string> - <string name="resume_playing_title">"Reanudar vídeo"</string> - <string name="resume_playing_message">"Reanudar reproducción a partir de %s ?"</string> - <string name="resume_playing_resume">"Reanudar reproducción"</string> - <string name="resume_playing_restart">"Volver a reproducir"</string> - <string name="gadget_title">"Picture frame"</string> - <string name="video_file_name_format">"\'video\'-yyyy-MM-dd-HH-mm-ss"</string> -</resources> diff --git a/res/values-fr/arrays.xml b/res/values-fr/arrays.xml deleted file mode 100644 index dfbf090..0000000 --- a/res/values-fr/arrays.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <!-- no translation found for pref_camera_videoquality_entries:0 (4155278146225809483) --> - <!-- no translation found for pref_camera_videoquality_entries:1 (2439895494739176281) --> - <string-array name="pref_camera_videoquality_entryvalues"> - <item>"0"</item> - <item>"1"</item> - </string-array> -</resources> diff --git a/res/values-fr/strings.xml b/res/values-fr/strings.xml deleted file mode 100644 index a416bb1..0000000 --- a/res/values-fr/strings.xml +++ /dev/null @@ -1,151 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <string name="all_images">"Toutes les images"</string> - <string name="all_videos">"Toutes les vidéos"</string> - <string name="camera_label">"Caméra"</string> - <string name="gallery_picker_label">"Galerie"</string> - <string name="gallery_camera_bucket_name">"Photos de l\'appareil photo"</string> - <string name="gallery_camera_videos_bucket_name">"Vidéos de l\'appareil photo"</string> - <string name="switch_to_video_lable">"Passer en mode vidéo"</string> - <string name="switch_to_camera_lable">"Passer en mode appareil photo"</string> - <string name="crop_label">"Rogner l\'image"</string> - <string name="view_label">"Afficher l\'image"</string> - <string name="preferences_label">"Paramètres de la caméra"</string> - <string name="wait">"Veuillez patienter..."</string> - <string name="no_storage">"Veuillez insérer une carte SD avant d\'utiliser la caméra."</string> - <string name="not_enough_space">"Votre carte SD est pleine."</string> - <string name="preparing_sd">"Préparation de la carte SD..."</string> - <string name="wallpaper">"Configuration de l\'arrière-plan en cours. Veuillez patienter..."</string> - <string name="savingImage">"Enregistrement de l\'image"</string> - <string name="runningFaceDetection">"Veuillez patienter..."</string> - <string name="flip_orientation">"Changer l\'orientation"</string> - <string name="settings">"Paramètres"</string> - <string name="view">"Afficher"</string> - <string name="details">"Détails"</string> - <string name="rotate">"Faire pivoter"</string> - <string name="rotate_left">"Faire pivoter à gauche"</string> - <string name="rotate_right">"Faire pivoter à droite"</string> - <string name="slide_show">"Diaporama"</string> - <string name="capture_picture">"Prendre une photo"</string> - <string name="capture_video">"Faire une vidéo"</string> - <string name="crop_save_text">"Enregistrer"</string> - <string name="crop_discard_text">"Annuler"</string> - <string name="confirm_delete_title">"Supprimer"</string> - <string name="confirm_delete_message">"L\'image sera supprimée."</string> - <string name="confirm_delete_video_message">"La vidéo va être supprimée."</string> - <string name="camera_toss">"Supprimer"</string> - <string name="camera_gallery">"Galerie"</string> - <string name="camera_share">"Partager"</string> - <string name="camera_set">"Définir en tant que"</string> - <string name="camera_play">"Lire"</string> - <string name="camera_attach">"Joindre"</string> - <string name="camera_cancel">"Annuler"</string> - <string name="camera_crop">"Rogner"</string> - <string name="camera_tossing">"Suppression..."</string> - <string name="no_way_to_share_image">"Impossible de partager cette image."</string> - <string name="no_way_to_share_video">"Cette vidéo ne peut pas être partagée."</string> - <string name="camera_gallery_photos_text">"Galerie"</string> - <string name="camera_pick_wallpaper">"Images"</string> - <string name="camera_setas_wallpaper">"Arrière-plan"</string> - <string name="pref_gallery_category">"Paramètres généraux"</string> - <string name="pref_slideshow_category">"Paramètres du diaporama"</string> - <string name="pref_camera_general_settings_category">"Paramètres généraux"</string> - <string name="pref_gallery_size_title">"Taille d\'affichage"</string> - <string name="pref_gallery_size_summary">"Sélectionner la taille d\'affichage des images et des vidéos"</string> - <string name="pref_gallery_size_dialogtitle">"Taille de l\'image"</string> - <string-array name="pref_gallery_size_choices"> - <item>"Grande"</item> - <item>"Petite"</item> - </string-array> - <string name="pref_gallery_sort_title">"Ordre de tri"</string> - <string name="pref_gallery_sort_summary">"Sélectionner l\'ordre de tri des images et des vidéos"</string> - <string name="pref_gallery_sort_dialogtitle">"Trier les images"</string> - <string-array name="pref_gallery_sort_choices"> - <item>"Les plus récentes d\'abord"</item> - <item>"La plus récente en dernier"</item> - </string-array> - <string name="pref_gallery_slideshow_interval_title">"Intervalle du diaporama"</string> - <string name="pref_gallery_slideshow_interval_summary">"Sélectionner la durée d\'affichage de chaque diapositive dans le diaporama"</string> - <string name="pref_gallery_slideshow_interval_dialogtitle">"Intervalle du diaporama"</string> - <string-array name="pref_gallery_slideshow_interval_choices"> - <item>"2 secondes"</item> - <item>"3 secondes"</item> - <item>"4 secondes"</item> - </string-array> - <string name="pref_gallery_slideshow_transition_title">"Transition du diaporama"</string> - <string name="pref_gallery_slideshow_transition_summary">"Sélectionner l\'effet utilisé lors de la transition d\'une diapositive à une autre"</string> - <string name="pref_gallery_slideshow_transition_dialogtitle">"Transition du diaporama"</string> - <string-array name="pref_gallery_slideshow_transition_choices"> - <item>"Ouverture et fermeture en fondu"</item> - <item>"Glisser vers la gauche - la droite"</item> - <item>"Glisser vers le haut - le bas"</item> - <item>"Sélection aléatoire"</item> - </string-array> - <string name="pref_gallery_slideshow_repeat_title">"Rejouer le diaporama"</string> - <string name="pref_gallery_slideshow_repeat_summary">"Rejouer le diaporama plusieurs fois"</string> - <string name="pref_gallery_slideshow_shuffle_title">"Lecture aléatoire des diapositives"</string> - <string name="pref_gallery_slideshow_shuffle_summary">"Afficher les images"</string> - <string name="pref_camera_recordlocation_title">"Enregistrer un emplacement dans les images"</string> - <string name="pref_camera_recordlocation_summary">"Enregistrer un emplacement dans les données d\'image"</string> - <string name="pref_camera_videoquality_category">"Qualité vidéo"</string> - <string name="pref_camera_videoquality_title">"Sélectionnez le niveau de qualité vidéo"</string> - <string name="pref_camera_videoquality_entry_0">"Basse (pour les MMS)"</string> - <string name="pref_camera_videoquality_entry_1">"Haute (pour la carte SD)"</string> - <string name="pref_camera_videoquality_dialogtitle">"Qualité vidéo"</string> - <string name="camerasettings">"Paramètres"</string> - <string name="image_gallery_NoImageView_text">"Aucun fichier média trouvé."</string> - <string name="pref_gallery_confirm_delete_title">"Confirmer les suppressions"</string> - <string name="pref_gallery_confirm_delete_summary">"Afficher une confirmation avant de supprimer une image ou une vidéo"</string> - <string name="details_panel_title">"Détails"</string> - <string name="details_file_size">"Taille du fichier :"</string> - <string name="details_image_resolution">"Résolution :"</string> - <string name="details_duration">"Durée :"</string> - <string name="details_date_taken">"Date de création :"</string> - <string name="details_frame_rate">"Fréquence d\'images :"</string> - <string name="details_bit_rate">"Débit :"</string> - <string name="details_codec">"Codec :"</string> - <string name="details_format">"Format :"</string> - <string name="details_dimension_x">"%1$d x %2$d"</string> - <string name="details_ms">"%1$02d:%2$02d"</string> - <string name="details_hms">"%1$d:%2$02d:%3$02d"</string> - <string name="details_fps">"%1$d fps"</string> - <string name="details_kbps">"%1$d Kbits/s"</string> - <string name="details_mbps">"%1$g Mbits/s"</string> - <string name="details_ok">"OK"</string> - <string name="context_menu_header">"Options de l\'image"</string> - <string name="video_context_menu_header">"Options vidéo"</string> - <string name="multiface_crop_help">"Cliquez sur un visage pour commencer."</string> - <string name="photos_gallery_title">"Galerie"</string> - <string name="pick_photos_gallery_title">"Sélectionner l\'image"</string> - <string name="videos_gallery_title">"Galerie"</string> - <string name="pick_videos_gallery_title">"Sélectionnez une vidéo"</string> - <string name="loading_progress_format_string">"<xliff:g id="COUNTER">%d</xliff:g> vignettes restantes"</string> - <string name="sendImage">"Partager l\'image via"</string> - <string name="setImage">"Définir l\'image en tant que"</string> - <string name="sendVideo">"Partager la vidéo via"</string> - <string name="movieviewlabel">"Films"</string> - <string name="loading_video">"Chargement de la vidéo..."</string> - <string name="spaceIsLow_title">"L\'espace restant est faible"</string> - <string name="spaceIsLow_content">"Votre carte SD est pleine. Modifiez le paramètre de qualité ou supprimez des éléments de la galerie."</string> - <string name="resume_playing_title">"Reprendre la vidéo"</string> - <string name="resume_playing_message">"Reprendre la lecture à partir de %s ?"</string> - <string name="resume_playing_resume">"Reprendre la lecture"</string> - <string name="resume_playing_restart">"Démarrer"</string> - <string name="gadget_title">"Cadre d\'image"</string> - <string name="video_file_name_format">"\'video\'-yyyy-MM-dd-HH-mm-ss"</string> -</resources> diff --git a/res/values-it/arrays.xml b/res/values-it/arrays.xml deleted file mode 100644 index dfbf090..0000000 --- a/res/values-it/arrays.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <!-- no translation found for pref_camera_videoquality_entries:0 (4155278146225809483) --> - <!-- no translation found for pref_camera_videoquality_entries:1 (2439895494739176281) --> - <string-array name="pref_camera_videoquality_entryvalues"> - <item>"0"</item> - <item>"1"</item> - </string-array> -</resources> diff --git a/res/values-it/strings.xml b/res/values-it/strings.xml deleted file mode 100644 index 23bd952..0000000 --- a/res/values-it/strings.xml +++ /dev/null @@ -1,151 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <string name="all_images">"Tutte le foto"</string> - <string name="all_videos">"Tutti i video"</string> - <string name="camera_label">"Fotocamera"</string> - <string name="gallery_picker_label">"Galleria"</string> - <string name="gallery_camera_bucket_name">"Foto"</string> - <string name="gallery_camera_videos_bucket_name">"Video fotocamera"</string> - <string name="switch_to_video_lable">"Passa a video"</string> - <string name="switch_to_camera_lable">"Passa a fotocamera"</string> - <string name="crop_label">"Ritaglia foto"</string> - <string name="view_label">"Visualizza foto"</string> - <string name="preferences_label">"Impostazioni fotocamera"</string> - <string name="wait">"Attendere..."</string> - <string name="no_storage">"Per usare la fotocamera devi inserire una scheda SD."</string> - <string name="not_enough_space">"La scheda SD è piena."</string> - <string name="preparing_sd">"Preparazione scheda SD…"</string> - <string name="wallpaper">"Impostazione sfondo, attendi..."</string> - <string name="savingImage">"Salvataggio foto..."</string> - <string name="runningFaceDetection">"Attendere..."</string> - <string name="flip_orientation">"Capovolgi orientamento"</string> - <string name="settings">"Impostazioni"</string> - <string name="view">"Visualizza"</string> - <string name="details">"Dettagli"</string> - <string name="rotate">"Ruota"</string> - <string name="rotate_left">"Ruota a sinistra"</string> - <string name="rotate_right">"Ruota a destra"</string> - <string name="slide_show">"Presentazione"</string> - <string name="capture_picture">"Scatta foto"</string> - <string name="capture_video">"Registra video"</string> - <string name="crop_save_text">"Salva"</string> - <string name="crop_discard_text">"Ignora"</string> - <string name="confirm_delete_title">"Elimina"</string> - <string name="confirm_delete_message">"La foto verrà eliminata."</string> - <string name="confirm_delete_video_message">"Il video verrà eliminato."</string> - <string name="camera_toss">"Elimina"</string> - <string name="camera_gallery">"Galleria"</string> - <string name="camera_share">"Condividi"</string> - <string name="camera_set">"Imposta come"</string> - <string name="camera_play">"Riproduci"</string> - <string name="camera_attach">"Allega"</string> - <string name="camera_cancel">"Annulla"</string> - <string name="camera_crop">"Ritaglia"</string> - <string name="camera_tossing">"Eliminazione..."</string> - <string name="no_way_to_share_image">"Impossibile condividere la foto."</string> - <string name="no_way_to_share_video">"Impossibile condividere il video."</string> - <string name="camera_gallery_photos_text">"Galleria"</string> - <string name="camera_pick_wallpaper">"Foto"</string> - <string name="camera_setas_wallpaper">"Sfondo"</string> - <string name="pref_gallery_category">"Impostazioni generali"</string> - <string name="pref_slideshow_category">"Impostazioni presentazione"</string> - <string name="pref_camera_general_settings_category">"Impostazioni generali"</string> - <string name="pref_gallery_size_title">"Dimensioni schermo"</string> - <string name="pref_gallery_size_summary">"Seleziona dimensioni di visualizz. di foto e video"</string> - <string name="pref_gallery_size_dialogtitle">"Dimensioni foto"</string> - <string-array name="pref_gallery_size_choices"> - <item>"Grandi"</item> - <item>"Piccole"</item> - </string-array> - <string name="pref_gallery_sort_title">"Ordinamento"</string> - <string name="pref_gallery_sort_summary">"Seleziona l\'ordinamento di foto e video"</string> - <string name="pref_gallery_sort_dialogtitle">"Ordine foto"</string> - <string-array name="pref_gallery_sort_choices"> - <item>"Da più recente"</item> - <item>"Da meno recente"</item> - </string-array> - <string name="pref_gallery_slideshow_interval_title">"Intervallo presentazione"</string> - <string name="pref_gallery_slideshow_interval_summary">"Seleziona la durata di ogni diapositiva"</string> - <string name="pref_gallery_slideshow_interval_dialogtitle">"Intervallo presentazione"</string> - <string-array name="pref_gallery_slideshow_interval_choices"> - <item>"2 secondi"</item> - <item>"3 secondi"</item> - <item>"4 secondi"</item> - </string-array> - <string name="pref_gallery_slideshow_transition_title">"Transizione presentazione"</string> - <string name="pref_gallery_slideshow_transition_summary">"Seleziona l\'effetto da usare per passare da una diapositiva all\'altra"</string> - <string name="pref_gallery_slideshow_transition_dialogtitle">"Transizione presentazione"</string> - <string-array name="pref_gallery_slideshow_transition_choices"> - <item>"Dissolvenza"</item> - <item>"Da sinistra a destra"</item> - <item>"Dall\'alto verso il basso"</item> - <item>"Selezione casuale"</item> - </string-array> - <string name="pref_gallery_slideshow_repeat_title">"Ripeti presentazione"</string> - <string name="pref_gallery_slideshow_repeat_summary">"Riproduci più volte la presentazione"</string> - <string name="pref_gallery_slideshow_shuffle_title">"Riproduzione casuale"</string> - <string name="pref_gallery_slideshow_shuffle_summary">"Mostra le foto in ordine casuale"</string> - <string name="pref_camera_recordlocation_title">"Salva località nelle foto"</string> - <string name="pref_camera_recordlocation_summary">"Registra località nei dati della foto"</string> - <string name="pref_camera_videoquality_category">"Qualità video"</string> - <string name="pref_camera_videoquality_title">"Seleziona la qualità video"</string> - <string name="pref_camera_videoquality_entry_0">"Bassa (per MMS)"</string> - <string name="pref_camera_videoquality_entry_1">"Alta (per scheda SD)"</string> - <string name="pref_camera_videoquality_dialogtitle">"Qualità video"</string> - <string name="camerasettings">"Impostazioni"</string> - <string name="image_gallery_NoImageView_text">"Nessun media trovato."</string> - <string name="pref_gallery_confirm_delete_title">"Conferma eliminazioni"</string> - <string name="pref_gallery_confirm_delete_summary">"Mostra conferma prima di eliminare una foto o un video"</string> - <string name="details_panel_title">"Dettagli"</string> - <string name="details_file_size">"Dim. file:"</string> - <string name="details_image_resolution">"Risoluzione:"</string> - <string name="details_duration">"Durata:"</string> - <string name="details_date_taken">"Data scatto:"</string> - <string name="details_frame_rate">"Frequenza fotogrammi:"</string> - <string name="details_bit_rate">"Velocità in bit:"</string> - <string name="details_codec">"Codec:"</string> - <string name="details_format">"Formato:"</string> - <string name="details_dimension_x">"%1$d x %2$d"</string> - <string name="details_ms">"%1$02d:%2$02d"</string> - <string name="details_hms">"%1$d:%2$02d:%3$02d"</string> - <string name="details_fps">"%1$d fps"</string> - <string name="details_kbps">"%1$d Kbps"</string> - <string name="details_mbps">"%1$g Mbps"</string> - <string name="details_ok">"OK"</string> - <string name="context_menu_header">"Opzioni foto"</string> - <string name="video_context_menu_header">"Opzioni video"</string> - <string name="multiface_crop_help">"Tocca un viso per iniziare."</string> - <string name="photos_gallery_title">"Galleria"</string> - <string name="pick_photos_gallery_title">"Seleziona foto"</string> - <string name="videos_gallery_title">"Galleria"</string> - <string name="pick_videos_gallery_title">"Seleziona video"</string> - <string name="loading_progress_format_string">"<xliff:g id="COUNTER">%d</xliff:g> rimanenti"</string> - <string name="sendImage">"Condividi foto via"</string> - <string name="setImage">"Imposta foto come"</string> - <string name="sendVideo">"Condividi video via"</string> - <string name="movieviewlabel">"Film"</string> - <string name="loading_video">"Caricamento video..."</string> - <string name="spaceIsLow_title">"Spazio in esaurimento"</string> - <string name="spaceIsLow_content">"Lo spazio della scheda SD si sta esaurendo. Cambia l\'impostazione di qualità o elimina elementi nella galleria."</string> - <string name="resume_playing_title">"Riprendi video"</string> - <string name="resume_playing_message">"Riprendi riproduzione da %s ?"</string> - <string name="resume_playing_resume">"Riprendi riproduzione"</string> - <string name="resume_playing_restart">"Ricomincia"</string> - <string name="gadget_title">"Cornice immagine"</string> - <string name="video_file_name_format">"\'video\'-yyyy-MM-dd-HH-mm-ss"</string> -</resources> diff --git a/res/values-ja/arrays.xml b/res/values-ja/arrays.xml deleted file mode 100644 index dfbf090..0000000 --- a/res/values-ja/arrays.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <!-- no translation found for pref_camera_videoquality_entries:0 (4155278146225809483) --> - <!-- no translation found for pref_camera_videoquality_entries:1 (2439895494739176281) --> - <string-array name="pref_camera_videoquality_entryvalues"> - <item>"0"</item> - <item>"1"</item> - </string-array> -</resources> diff --git a/res/values-ja/strings.xml b/res/values-ja/strings.xml deleted file mode 100644 index 928ec24..0000000 --- a/res/values-ja/strings.xml +++ /dev/null @@ -1,151 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <string name="all_images">"すべての写真"</string> - <string name="all_videos">"すべての動画"</string> - <string name="camera_label">"カメラ"</string> - <string name="gallery_picker_label">"ギャラリー"</string> - <string name="gallery_camera_bucket_name">"カメラ (写真)"</string> - <string name="gallery_camera_videos_bucket_name">"カメラ (動画)"</string> - <string name="switch_to_video_lable">"ムービーに切替"</string> - <string name="switch_to_camera_lable">"写真に切替"</string> - <string name="crop_label">"写真のトリミング"</string> - <string name="view_label">"写真を表示"</string> - <string name="preferences_label">"カメラ設定"</string> - <string name="wait">"お待ちください..."</string> - <string name="no_storage">"カメラを使用する前にSDカードを挿入してください。"</string> - <string name="not_enough_space">"SDカードがいっぱいです。"</string> - <string name="preparing_sd">"SDカードの準備中..."</string> - <string name="wallpaper">"壁紙を設定しています。しばらくお待ちください..."</string> - <string name="savingImage">"写真を保存中..."</string> - <string name="runningFaceDetection">"お待ちください..."</string> - <string name="flip_orientation">"画面の向きを変更"</string> - <string name="settings">"設定"</string> - <string name="view">"表示"</string> - <string name="details">"詳細"</string> - <string name="rotate">"回転"</string> - <string name="rotate_left">"左に回転"</string> - <string name="rotate_right">"右に回転"</string> - <string name="slide_show">"スライドショー"</string> - <string name="capture_picture">"写真撮影"</string> - <string name="capture_video">"ムービー撮影"</string> - <string name="crop_save_text">"保存"</string> - <string name="crop_discard_text">"破棄"</string> - <string name="confirm_delete_title">"削除"</string> - <string name="confirm_delete_message">"写真を削除します。"</string> - <string name="confirm_delete_video_message">"動画を削除します。"</string> - <string name="camera_toss">"削除"</string> - <string name="camera_gallery">"ギャラリー"</string> - <string name="camera_share">"共有"</string> - <string name="camera_set">"設定"</string> - <string name="camera_play">"再生"</string> - <string name="camera_attach">"添付"</string> - <string name="camera_cancel">"キャンセル"</string> - <string name="camera_crop">"トリミング"</string> - <string name="camera_tossing">"削除中..."</string> - <string name="no_way_to_share_image">"この写真は共有できません。"</string> - <string name="no_way_to_share_video">"この動画は共有できません。"</string> - <string name="camera_gallery_photos_text">"ギャラリー"</string> - <string name="camera_pick_wallpaper">"写真"</string> - <string name="camera_setas_wallpaper">"壁紙"</string> - <string name="pref_gallery_category">"全般設定"</string> - <string name="pref_slideshow_category">"スライドショー設定"</string> - <string name="pref_camera_general_settings_category">"全般設定"</string> - <string name="pref_gallery_size_title">"表示サイズ"</string> - <string name="pref_gallery_size_summary">"写真と動画の表示サイズを選択"</string> - <string name="pref_gallery_size_dialogtitle">"写真サイズ"</string> - <string-array name="pref_gallery_size_choices"> - <item>"大"</item> - <item>"小"</item> - </string-array> - <string name="pref_gallery_sort_title">"並び替え順"</string> - <string name="pref_gallery_sort_summary">"写真と動画の並び替え順を選択"</string> - <string name="pref_gallery_sort_dialogtitle">"写真の並べ替え"</string> - <string-array name="pref_gallery_sort_choices"> - <item>"日付の新しい順"</item> - <item>"日付の古い順"</item> - </string-array> - <string name="pref_gallery_slideshow_interval_title">"スライドショーの間隔"</string> - <string name="pref_gallery_slideshow_interval_summary">"各スライドの表示時間"</string> - <string name="pref_gallery_slideshow_interval_dialogtitle">"スライドショーの間隔"</string> - <string-array name="pref_gallery_slideshow_interval_choices"> - <item>"2秒"</item> - <item>"3秒"</item> - <item>"4秒"</item> - </string-array> - <string name="pref_gallery_slideshow_transition_title">"スライドショーのトランジション"</string> - <string name="pref_gallery_slideshow_transition_summary">"スライドが切り替わるときの効果を選択"</string> - <string name="pref_gallery_slideshow_transition_dialogtitle">"スライドショーのトランジション"</string> - <string-array name="pref_gallery_slideshow_transition_choices"> - <item>"フェードイン&アウト"</item> - <item>"左右にスライド"</item> - <item>"上下にスライド"</item> - <item>"ランダムに選択"</item> - </string-array> - <string name="pref_gallery_slideshow_repeat_title">"スライドショーを繰り返す"</string> - <string name="pref_gallery_slideshow_repeat_summary">"スライドショーを繰り返す"</string> - <string name="pref_gallery_slideshow_shuffle_title">"スライドのシャッフル"</string> - <string name="pref_gallery_slideshow_shuffle_summary">"写真をランダムに表示"</string> - <string name="pref_camera_recordlocation_title">"位置情報を写真に記録する"</string> - <string name="pref_camera_recordlocation_summary">"写真データに位置情報を記録します"</string> - <string name="pref_camera_videoquality_category">"動画のクオリティ"</string> - <string name="pref_camera_videoquality_title">"動画の画質を選択"</string> - <string name="pref_camera_videoquality_entry_0">"低 (MMSメッセージ向け)"</string> - <string name="pref_camera_videoquality_entry_1">"高 (SDカード向け)"</string> - <string name="pref_camera_videoquality_dialogtitle">"動画のクオリティ"</string> - <string name="camerasettings">"設定"</string> - <string name="image_gallery_NoImageView_text">"メディアが見つかりません。"</string> - <string name="pref_gallery_confirm_delete_title">"削除を確認"</string> - <string name="pref_gallery_confirm_delete_summary">"写真や動画を削除する前に確認メッセージを表示"</string> - <string name="details_panel_title">"詳細"</string> - <string name="details_file_size">"ファイルサイズ:"</string> - <string name="details_image_resolution">"解像度:"</string> - <string name="details_duration">"再生時間:"</string> - <string name="details_date_taken">"撮影日:"</string> - <string name="details_frame_rate">"フレームレート:"</string> - <string name="details_bit_rate">"ビットレート:"</string> - <string name="details_codec">"コーデック:"</string> - <string name="details_format">"形式:"</string> - <string name="details_dimension_x">"%1$dx%2$d"</string> - <string name="details_ms">"%1$02d:%2$02d"</string> - <string name="details_hms">"%1$d:%2$02d:%3$02d"</string> - <string name="details_fps">"%1$dfps"</string> - <string name="details_kbps">"%1$dKbps"</string> - <string name="details_mbps">"%1$gMbps"</string> - <string name="details_ok">"OK"</string> - <string name="context_menu_header">"写真オプション"</string> - <string name="video_context_menu_header">"動画オプション"</string> - <string name="multiface_crop_help">"顔をタップして開始します。"</string> - <string name="photos_gallery_title">"ギャラリー"</string> - <string name="pick_photos_gallery_title">"写真を選択"</string> - <string name="videos_gallery_title">"ギャラリー"</string> - <string name="pick_videos_gallery_title">"動画を選択"</string> - <string name="loading_progress_format_string">"残り<xliff:g id="COUNTER">%d</xliff:g>件"</string> - <string name="sendImage">"写真を共有"</string> - <string name="setImage">"写真を設定"</string> - <string name="sendVideo">"動画を共有"</string> - <string name="movieviewlabel">"映画"</string> - <string name="loading_video">"動画を読み込み中..."</string> - <string name="spaceIsLow_title">"空き容量が残り少なくなっています"</string> - <string name="spaceIsLow_content">"SDカードの容量が足りません。クオリティ設定を変更するか、ギャラリーからアイテムを削除してください。"</string> - <string name="resume_playing_title">"動画の再開"</string> - <string name="resume_playing_message">"再生を%sから再開しますか?"</string> - <string name="resume_playing_resume">"再生を再開"</string> - <string name="resume_playing_restart">"最初から再生"</string> - <string name="gadget_title">"写真フレーム"</string> - <string name="video_file_name_format">"\'video\'-yyyy-MM-dd-HH-mm-ss"</string> -</resources> diff --git a/res/values-ko/arrays.xml b/res/values-ko/arrays.xml deleted file mode 100644 index dfbf090..0000000 --- a/res/values-ko/arrays.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <!-- no translation found for pref_camera_videoquality_entries:0 (4155278146225809483) --> - <!-- no translation found for pref_camera_videoquality_entries:1 (2439895494739176281) --> - <string-array name="pref_camera_videoquality_entryvalues"> - <item>"0"</item> - <item>"1"</item> - </string-array> -</resources> diff --git a/res/values-ko/strings.xml b/res/values-ko/strings.xml deleted file mode 100644 index 4f4980a..0000000 --- a/res/values-ko/strings.xml +++ /dev/null @@ -1,151 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <string name="all_images">"모든 사진"</string> - <string name="all_videos">"모든 동영상"</string> - <string name="camera_label">"카메라"</string> - <string name="gallery_picker_label">"갤러리"</string> - <string name="gallery_camera_bucket_name">"카메라 사진"</string> - <string name="gallery_camera_videos_bucket_name">"카메라 동영상"</string> - <string name="switch_to_video_lable">"동영상으로 전환"</string> - <string name="switch_to_camera_lable">"카메라로 전환"</string> - <string name="crop_label">"사진 자르기"</string> - <string name="view_label">"사진 보기"</string> - <string name="preferences_label">"카메라 설정"</string> - <string name="wait">"잠시 기다려 주세요..."</string> - <string name="no_storage">"카메라를 사용하기 전에 먼저 SD 카드를 넣으세요."</string> - <string name="not_enough_space">"SD 카드가 꽉 찼습니다."</string> - <string name="preparing_sd">"SD 카드 준비중..."</string> - <string name="wallpaper">"배경화면 설정 중. 잠시 기다려 주세요..."</string> - <string name="savingImage">"사진 저장 중..."</string> - <string name="runningFaceDetection">"잠시 기다려 주세요..."</string> - <string name="flip_orientation">"방향 바꾸기"</string> - <string name="settings">"설정"</string> - <string name="view">"보기"</string> - <string name="details">"상세정보"</string> - <string name="rotate">"회전"</string> - <string name="rotate_left">"왼쪽으로 회전"</string> - <string name="rotate_right">"오른쪽으로 회전"</string> - <string name="slide_show">"슬라이드쇼"</string> - <string name="capture_picture">"사진촬영"</string> - <string name="capture_video">"동영상 캡처"</string> - <string name="crop_save_text">"저장"</string> - <string name="crop_discard_text">"무시"</string> - <string name="confirm_delete_title">"삭제"</string> - <string name="confirm_delete_message">"사진이 삭제됩니다."</string> - <string name="confirm_delete_video_message">"동영상이 삭제됩니다."</string> - <string name="camera_toss">"삭제"</string> - <string name="camera_gallery">"갤러리"</string> - <string name="camera_share">"공유"</string> - <string name="camera_set">"사진 설정"</string> - <string name="camera_play">"재생"</string> - <string name="camera_attach">"첨부"</string> - <string name="camera_cancel">"취소"</string> - <string name="camera_crop">"자르기"</string> - <string name="camera_tossing">"삭제 중..."</string> - <string name="no_way_to_share_image">"공유할 수 없는 사진입니다."</string> - <string name="no_way_to_share_video">"공유할 수 없는 동영상입니다."</string> - <string name="camera_gallery_photos_text">"갤러리"</string> - <string name="camera_pick_wallpaper">"사진"</string> - <string name="camera_setas_wallpaper">"배경화면"</string> - <string name="pref_gallery_category">"일반 설정"</string> - <string name="pref_slideshow_category">"슬라이드쇼 설정"</string> - <string name="pref_camera_general_settings_category">"일반 설정"</string> - <string name="pref_gallery_size_title">"디스플레이 크기"</string> - <string name="pref_gallery_size_summary">"사진 및 동영상 표시 크기 선택"</string> - <string name="pref_gallery_size_dialogtitle">"사진 크기"</string> - <string-array name="pref_gallery_size_choices"> - <item>"크게"</item> - <item>"작게"</item> - </string-array> - <string name="pref_gallery_sort_title">"정렬 순서"</string> - <string name="pref_gallery_sort_summary">"사진 및 동영상 정렬 순서 선택"</string> - <string name="pref_gallery_sort_dialogtitle">"사진 정렬"</string> - <string-array name="pref_gallery_sort_choices"> - <item>"가장 최근 사진 먼저"</item> - <item>"가장 최근 사진 마지막에"</item> - </string-array> - <string name="pref_gallery_slideshow_interval_title">"슬라이드쇼 간격"</string> - <string name="pref_gallery_slideshow_interval_summary">"쇼에서 각 슬라이드를 표시할 시간 선택"</string> - <string name="pref_gallery_slideshow_interval_dialogtitle">"슬라이드쇼 간격"</string> - <string-array name="pref_gallery_slideshow_interval_choices"> - <item>"2초"</item> - <item>"3초"</item> - <item>"4초"</item> - </string-array> - <string name="pref_gallery_slideshow_transition_title">"슬라이드쇼 화면전환"</string> - <string name="pref_gallery_slideshow_transition_summary">"슬라이드 간에 이동할 때 사용할 효과 선택"</string> - <string name="pref_gallery_slideshow_transition_dialogtitle">"슬라이드쇼 화면전환"</string> - <string-array name="pref_gallery_slideshow_transition_choices"> - <item>"페이드 인/아웃"</item> - <item>"왼쪽에서 오른쪽으로/오른쪽에서 왼쪽으로"</item> - <item>"위에서 아래로/아래에서 위로"</item> - <item>"무작위 선택"</item> - </string-array> - <string name="pref_gallery_slideshow_repeat_title">"슬라이드쇼 반복"</string> - <string name="pref_gallery_slideshow_repeat_summary">"슬라이드쇼를 한 번 이상 재생"</string> - <string name="pref_gallery_slideshow_shuffle_title">"슬라이드 섞기"</string> - <string name="pref_gallery_slideshow_shuffle_summary">"사진을 무작위 순서로 표시"</string> - <string name="pref_camera_recordlocation_title">"사진에 위치 저장"</string> - <string name="pref_camera_recordlocation_summary">"사진 데이터에 위치 기록"</string> - <string name="pref_camera_videoquality_category">"동영상 화질"</string> - <string name="pref_camera_videoquality_title">"동영상 화질 선택"</string> - <string name="pref_camera_videoquality_entry_0">"낮음(MMS 메시지용)"</string> - <string name="pref_camera_videoquality_entry_1">"높음(SD 카드용)"</string> - <string name="pref_camera_videoquality_dialogtitle">"동영상 화질"</string> - <string name="camerasettings">"설정"</string> - <string name="image_gallery_NoImageView_text">"미디어 파일이 없습니다."</string> - <string name="pref_gallery_confirm_delete_title">"삭제 확인"</string> - <string name="pref_gallery_confirm_delete_summary">"사진 및 동영상 삭제 전 확인 표시"</string> - <string name="details_panel_title">"상세정보"</string> - <string name="details_file_size">"파일 크기:"</string> - <string name="details_image_resolution">"해상도:"</string> - <string name="details_duration">"재생 시간:"</string> - <string name="details_date_taken">"찍은 날짜:"</string> - <string name="details_frame_rate">"프레임 속도:"</string> - <string name="details_bit_rate">"비트 전송률:"</string> - <string name="details_codec">"코덱:"</string> - <string name="details_format">"형식:"</string> - <string name="details_dimension_x">"%1$d x %2$d"</string> - <string name="details_ms">"%1$02d:%2$02d"</string> - <string name="details_hms">"%1$d:%2$02d:%3$02d"</string> - <string name="details_fps">"%1$dfps"</string> - <string name="details_kbps">"%1$dKbps"</string> - <string name="details_mbps">"%1$gMbps"</string> - <string name="details_ok">"확인"</string> - <string name="context_menu_header">"사진 옵션"</string> - <string name="video_context_menu_header">"동영상 옵션"</string> - <string name="multiface_crop_help">"시작하려면 얼굴을 탭하세요."</string> - <string name="photos_gallery_title">"갤러리"</string> - <string name="pick_photos_gallery_title">"사진 선택"</string> - <string name="videos_gallery_title">"갤러리"</string> - <string name="pick_videos_gallery_title">"동영상 선택"</string> - <string name="loading_progress_format_string">"<xliff:g id="COUNTER">%d</xliff:g>개 남음"</string> - <string name="sendImage">"사진 공유 응용프로그램"</string> - <string name="setImage">"사진 설정"</string> - <string name="sendVideo">"동영상 공유 응용프로그램"</string> - <string name="movieviewlabel">"영화"</string> - <string name="loading_video">"동영상 로드 중..."</string> - <string name="spaceIsLow_title">"공간부족"</string> - <string name="spaceIsLow_content">"SD 카드의 공간이 부족합니다. 화질 설정을 변경하거나 갤러리에서 항목을 삭제하세요."</string> - <string name="resume_playing_title">"동영상 다시 시작"</string> - <string name="resume_playing_message">"%s에서 재생을 다시 시작하시겠습니까?"</string> - <string name="resume_playing_resume">"재생 다시 시작"</string> - <string name="resume_playing_restart">"시작"</string> - <string name="gadget_title">"사진 프레임"</string> - <string name="video_file_name_format">"\'video\'-yyyy-MM-dd-HH-mm-ss"</string> -</resources> diff --git a/res/values-nb/strings.xml b/res/values-nb/strings.xml deleted file mode 100644 index 7359acf..0000000 --- a/res/values-nb/strings.xml +++ /dev/null @@ -1,152 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <string name="all_images">"Alle bilder"</string> - <string name="all_videos">"Alle videoer"</string> - <string name="camera_label">"Kamera"</string> - <string name="gallery_picker_label">"Galleri"</string> - <string name="gallery_camera_bucket_name">"Bilder fra kamera"</string> - <string name="gallery_camera_videos_bucket_name">"Videoer fra kamera"</string> - <string name="switch_to_video_lable">"Bytt til video"</string> - <string name="switch_to_camera_lable">"Bytt til kamera"</string> - <string name="crop_label">"Beskjær bilde"</string> - <string name="view_label">"Se på bilde"</string> - <string name="preferences_label">"Kamerainnstillinger"</string> - <string name="wait">"Vent litt…"</string> - <string name="no_storage">"Sett inn et minnekort før du bruker kameraet."</string> - <string name="not_enough_space">"Minnekortet er fullt."</string> - <string name="preparing_sd">"Forbereder minnekort…"</string> - <string name="wallpaper">"Setter bakgrunnsbilde, vent litt…"</string> - <string name="savingImage">"Lagrer bilde…"</string> - <string name="runningFaceDetection">"Vent litt…"</string> - <string name="flip_orientation">"Roter skjerm"</string> - <string name="settings">"Innstillinger"</string> - <string name="view">"Vis"</string> - <string name="details">"Detaljer"</string> - <string name="rotate">"Roter"</string> - <string name="rotate_left">"Roter mot venstre"</string> - <string name="rotate_right">"Roter mot høyre"</string> - <string name="slide_show">"Lysbildevisning"</string> - <string name="capture_picture">"Ta bilde"</string> - <string name="capture_video">"Ta opp video"</string> - <string name="crop_save_text">"Lagre"</string> - <string name="crop_discard_text">"Forkast"</string> - <string name="confirm_delete_title">"Slett"</string> - <string name="confirm_delete_message">"Bildet vil bli slettet."</string> - <string name="confirm_delete_video_message">"Videoen vil bli slettet."</string> - <string name="camera_toss">"Slett"</string> - <string name="camera_gallery">"Galleri"</string> - <string name="camera_share">"Del"</string> - <string name="camera_set">"Bruk som"</string> - <string name="camera_play">"Spill"</string> - <string name="camera_attach">"Legg ved"</string> - <string name="camera_cancel">"Avbryt"</string> - <string name="camera_crop">"Beskjær"</string> - <string name="camera_tossing">"Sletter…"</string> - <string name="no_way_to_share_image">"Bildet kan ikke deles."</string> - <string name="no_way_to_share_video">"Videoen kan ikke deles."</string> - <string name="camera_gallery_photos_text">"Galleri"</string> - <string name="camera_pick_wallpaper">"Bilder"</string> - <string name="camera_setas_wallpaper">"Bakgrunnsbilder"</string> - <string name="pref_gallery_category">"Generelle innstillinger"</string> - <string name="pref_slideshow_category">"Innstillinger for lysbildevisning"</string> - <string name="pref_camera_general_settings_category">"Generelle innstillinger"</string> - <string name="pref_gallery_size_title">"Bildestørrelse"</string> - <string name="pref_gallery_size_summary">"Velg hvor stort bilder skal vises"</string> - <string name="pref_gallery_size_dialogtitle">"Bildestørrelse"</string> - <string-array name="pref_gallery_size_choices"> - <item>"Stor"</item> - <item>"Liten"</item> - </string-array> - <string name="pref_gallery_sort_title">"Bildesortering"</string> - <string name="pref_gallery_sort_summary">"Velg i hvilken rekkefølge bildene skal sorteres"</string> - <string name="pref_gallery_sort_dialogtitle">"Bildesortering"</string> - <string-array name="pref_gallery_sort_choices"> - <item>"Nyeste først"</item> - <item>"Nyeste sist"</item> - </string-array> - <string name="pref_gallery_slideshow_interval_title">"Pause i lysbildevisning"</string> - <string name="pref_gallery_slideshow_interval_summary">"Velg hvor lenge hvert lysbilde skal vises"</string> - <string name="pref_gallery_slideshow_interval_dialogtitle">"Pause i lysbildevisning"</string> - <string-array name="pref_gallery_slideshow_interval_choices"> - <item>"2 sekunder"</item> - <item>"3 sekunder"</item> - <item>"4 sekunder"</item> - </string-array> - <string name="pref_gallery_slideshow_transition_title">"Lysbildeovergang"</string> - <string name="pref_gallery_slideshow_transition_summary">"Velg effekten som skal brukes mellom lysbilder"</string> - <string name="pref_gallery_slideshow_transition_dialogtitle">"Lysbildevergang"</string> - <string-array name="pref_gallery_slideshow_transition_choices"> - <item>"Ton inn og ut"</item> - <item>"Skli venstre - høyre"</item> - <item>"Skli opp - ned"</item> - <item>"Tilfeldig"</item> - </string-array> - <string name="pref_gallery_slideshow_repeat_title">"Gjenta lysbildeserie"</string> - <string name="pref_gallery_slideshow_repeat_summary">"Vis lydbildeserie mer enn en gang"</string> - <string name="pref_gallery_slideshow_shuffle_title">"Stokk lysbilder"</string> - <string name="pref_gallery_slideshow_shuffle_summary">"Vis bilder i tilfeldig rekkefølge"</string> - <string name="pref_camera_recordlocation_title">"Lagre sted i bilder"</string> - <string name="pref_camera_recordlocation_summary">"Lagre sted i bildedata"</string> - <string name="pref_camera_videoquality_category">"Videokvalitet"</string> - <string name="pref_camera_videoquality_title">"Videokvalitet"</string> - <string name="pref_camera_videoquality_entry_0">"Lav (for MMS-meldinger)"</string> - <string name="pref_camera_videoquality_entry_1">"Høy (for minnekort)"</string> - <string name="pref_camera_videoquality_dialogtitle">"Videokvalitet"</string> - <string name="camerasettings">"Innstillinger"</string> - <string name="image_gallery_NoImageView_text">"Fant ingen bilder."</string> - <string name="pref_gallery_confirm_delete_title">"Bekreft sletting"</string> - <string name="pref_gallery_confirm_delete_summary">"Vis bekreftelse før bilder slettes"</string> - <string name="details_panel_title">"Detaljer"</string> - <string name="details_file_size">"Filstørrelse:"</string> - <string name="details_image_resolution">"Oppløsning:"</string> - <string name="details_duration">"Varighet:"</string> - <string name="details_date_taken">"Dato tatt:"</string> - <string name="details_frame_rate">"Bildefrekvens:"</string> - <string name="details_bit_rate">"Bitrate:"</string> - <string name="details_codec">"Kodek:"</string> - <string name="details_format">"Format:"</string> - <string name="details_dimension_x">"%1$d x %2$d"</string> - <string name="details_ms">"%1$02d:%2$02d"</string> - <string name="details_hms">"%1$d:%2$02d:%3$02d"</string> - <string name="details_fps">"%1$d fps"</string> - <string name="details_kbps">"%1$d kbps"</string> - <string name="details_mbps">"%1$g Mbps"</string> - <string name="details_ok">"OK"</string> - <string name="context_menu_header">"Bildeinnstillinger"</string> - <string name="video_context_menu_header">"Videoinnstillinger"</string> - <string name="multiface_crop_help">"Trykk på et ansikt for å begynne."</string> - <string name="photos_gallery_title">"Galleri"</string> - <string name="pick_photos_gallery_title">"Velg bilde"</string> - <string name="videos_gallery_title">"Galleri"</string> - <string name="pick_videos_gallery_title">"Velg video"</string> - <string name="loading_progress_format_string">"<xliff:g id="COUNTER">%d</xliff:g> gjenstår"</string> - <string name="sendImage">"Del bilde via"</string> - <string name="setImage">"Bruk bilde som"</string> - <string name="sendVideo">"Del video via"</string> - <string name="movieviewlabel">"Filmer"</string> - <string name="loading_video">"Laster video…"</string> - <string name="spaceIsLow_title">"Lite plass"</string> - <string name="spaceIsLow_content">"Minnekortet begynner å gå tom for plass. Endre kvalitetsinnstillingen eller slett bilder fra galleriet."</string> - <string name="resume_playing_title">"Fortsett avspilling"</string> - <string name="resume_playing_message">"Fortsett avspilling fra %s?"</string> - <string name="resume_playing_resume">"Fortsett avspilling"</string> - <string name="resume_playing_restart">"Begynn på nytt"</string> - <string name="gadget_title">"Bilderamme"</string> - <!-- no translation found for video_file_name_format (8555507706353616970) --> - <skip /> -</resources> diff --git a/res/values-nl/arrays.xml b/res/values-nl/arrays.xml deleted file mode 100644 index dfbf090..0000000 --- a/res/values-nl/arrays.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <!-- no translation found for pref_camera_videoquality_entries:0 (4155278146225809483) --> - <!-- no translation found for pref_camera_videoquality_entries:1 (2439895494739176281) --> - <string-array name="pref_camera_videoquality_entryvalues"> - <item>"0"</item> - <item>"1"</item> - </string-array> -</resources> diff --git a/res/values-nl/strings.xml b/res/values-nl/strings.xml deleted file mode 100644 index c48f738..0000000 --- a/res/values-nl/strings.xml +++ /dev/null @@ -1,151 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <string name="all_images">"Alle foto\'s"</string> - <string name="all_videos">"Alle video\'s"</string> - <string name="camera_label">"Camera"</string> - <string name="gallery_picker_label">"Galerij"</string> - <string name="gallery_camera_bucket_name">"Camerafoto\'s"</string> - <string name="gallery_camera_videos_bucket_name">"Cameravideo\'s"</string> - <string name="switch_to_video_lable">"Overschakelen naar video"</string> - <string name="switch_to_camera_lable">"Overschakelen naar camera"</string> - <string name="crop_label">"Foto bijsnijden"</string> - <string name="view_label">"Foto weergeven"</string> - <string name="preferences_label">"Camera-instellingen"</string> - <string name="wait">"Een ogenblik geduld..."</string> - <string name="no_storage">"Plaats een SD-kaart voordat u de camera gebruikt."</string> - <string name="not_enough_space">"De SD-kaart is vol."</string> - <string name="preparing_sd">"SD-kaart voorbereiden…"</string> - <string name="wallpaper">"Achtergrond wordt ingesteld. Een ogenblik geduld..."</string> - <string name="savingImage">"Foto opslaan..."</string> - <string name="runningFaceDetection">"Een ogenblik geduld..."</string> - <string name="flip_orientation">"Stand draaien"</string> - <string name="settings">"Instellingen"</string> - <string name="view">"Weergeven"</string> - <string name="details">"Details"</string> - <string name="rotate">"Draaien"</string> - <string name="rotate_left">"Linksom draaien"</string> - <string name="rotate_right">"Rechtsom draaien"</string> - <string name="slide_show">"Diavoorstelling"</string> - <string name="capture_picture">"Foto nemen"</string> - <string name="capture_video">"Video opnemen"</string> - <string name="crop_save_text">"Opslaan"</string> - <string name="crop_discard_text">"Ongedaan maken"</string> - <string name="confirm_delete_title">"Verwijderen"</string> - <string name="confirm_delete_message">"De foto wordt verwijderd."</string> - <string name="confirm_delete_video_message">"De video wordt verwijderd"</string> - <string name="camera_toss">"Verwijderen"</string> - <string name="camera_gallery">"Galerij"</string> - <string name="camera_share">"Delen"</string> - <string name="camera_set">"Instellen als"</string> - <string name="camera_play">"Afspelen"</string> - <string name="camera_attach">"Bijvoegen"</string> - <string name="camera_cancel">"Annuleren"</string> - <string name="camera_crop">"Bijsnijden"</string> - <string name="camera_tossing">"Verwijderen..."</string> - <string name="no_way_to_share_image">"Deze foto kan niet worden gedeeld."</string> - <string name="no_way_to_share_video">"Deze video kan niet worden gedeeld."</string> - <string name="camera_gallery_photos_text">"Galerij"</string> - <string name="camera_pick_wallpaper">"Foto\'s"</string> - <string name="camera_setas_wallpaper">"Achtergrond"</string> - <string name="pref_gallery_category">"Algemene instellingen"</string> - <string name="pref_slideshow_category">"Instellingen van diavoorstelling"</string> - <string name="pref_camera_general_settings_category">"Algemene instellingen"</string> - <string name="pref_gallery_size_title">"Weergavegrootte"</string> - <string name="pref_gallery_size_summary">"De weergavegrootte van foto\'s en video\'s selecteren"</string> - <string name="pref_gallery_size_dialogtitle">"Grootte van foto"</string> - <string-array name="pref_gallery_size_choices"> - <item>"Groot"</item> - <item>"Klein"</item> - </string-array> - <string name="pref_gallery_sort_title">"Sorteervolgorde"</string> - <string name="pref_gallery_sort_summary">"De sorteervolgorde van foto\'s en video\'s selecteren"</string> - <string name="pref_gallery_sort_dialogtitle">"Foto\'s sorteren"</string> - <string-array name="pref_gallery_sort_choices"> - <item>"Nieuwste eerst"</item> - <item>"Nieuwste eerst"</item> - </string-array> - <string name="pref_gallery_slideshow_interval_title">"Interval in diavoorstelling"</string> - <string name="pref_gallery_slideshow_interval_summary">"Selecteren hoe lang elke dia wordt weergegeven in de voorstelling"</string> - <string name="pref_gallery_slideshow_interval_dialogtitle">"Interval in diavoorstelling"</string> - <string-array name="pref_gallery_slideshow_interval_choices"> - <item>"2 seconden"</item> - <item>"3 seconden"</item> - <item>"4 seconden"</item> - </string-array> - <string name="pref_gallery_slideshow_transition_title">"Overgangen in diavoorstellingen"</string> - <string name="pref_gallery_slideshow_transition_summary">"Het effect selecteren dat wordt gebruikt om naar de volgende dia te gaan"</string> - <string name="pref_gallery_slideshow_transition_dialogtitle">"Overgangen in diavoorstellingen"</string> - <string-array name="pref_gallery_slideshow_transition_choices"> - <item>"Infaden/uitfaden"</item> - <item>"Dia vanaf linkerkant/rechterkant"</item> - <item>"Dia vanaf bovenkant/onderkant"</item> - <item>"Willekeurige selectie"</item> - </string-array> - <string name="pref_gallery_slideshow_repeat_title">"Diavoorstelling herhalen"</string> - <string name="pref_gallery_slideshow_repeat_summary">"Diavoorstelling meerdere keren afspelen"</string> - <string name="pref_gallery_slideshow_shuffle_title">"Dia\'s in willekeurige volgorde weergeven"</string> - <string name="pref_gallery_slideshow_shuffle_summary">"Foto\'s in willekeurige volgorde weergeven"</string> - <string name="pref_camera_recordlocation_title">"Locatie opslaan in foto\'s"</string> - <string name="pref_camera_recordlocation_summary">"Locatie vastleggen in de gegevens van de foto"</string> - <string name="pref_camera_videoquality_category">"Videokwaliteit"</string> - <string name="pref_camera_videoquality_title">"Videokwaliteit selecteren"</string> - <string name="pref_camera_videoquality_entry_0">"Laag (voor MMS-berichten)"</string> - <string name="pref_camera_videoquality_entry_1">"Hoog (voor SD-kaart)"</string> - <string name="pref_camera_videoquality_dialogtitle">"Videokwaliteit"</string> - <string name="camerasettings">"Instellingen"</string> - <string name="image_gallery_NoImageView_text">"Geen medium gevonden."</string> - <string name="pref_gallery_confirm_delete_title">"Verwijderen bevestigen"</string> - <string name="pref_gallery_confirm_delete_summary">"Bevestiging weergeven voordat een foto of video wordt verwijderd"</string> - <string name="details_panel_title">"Details"</string> - <string name="details_file_size">"Bestandsgrootte:"</string> - <string name="details_image_resolution">"Resolutie:"</string> - <string name="details_duration">"Duur:"</string> - <string name="details_date_taken">"Gemaakt op:"</string> - <string name="details_frame_rate">"Framesnelheid:"</string> - <string name="details_bit_rate">"Bitsnelheid:"</string> - <string name="details_codec">"Codec:"</string> - <string name="details_format">"Indeling:"</string> - <string name="details_dimension_x">"%1$d x %2$d"</string> - <string name="details_ms">"%1$02d:%2$02d"</string> - <string name="details_hms">"%1$d:%2$02d:%3$02d"</string> - <string name="details_fps">"%1$d fps"</string> - <string name="details_kbps">"%1$d Kbps"</string> - <string name="details_mbps">"%1$g Mbps"</string> - <string name="details_ok">"OK"</string> - <string name="context_menu_header">"Opties voor foto\'s"</string> - <string name="video_context_menu_header">"Video-opties"</string> - <string name="multiface_crop_help">"Tik op een gezicht om te beginnen."</string> - <string name="photos_gallery_title">"Galerij"</string> - <string name="pick_photos_gallery_title">"Foto selecteren"</string> - <string name="videos_gallery_title">"Galerij"</string> - <string name="pick_videos_gallery_title">"Video selecteren"</string> - <string name="loading_progress_format_string">"<xliff:g id="COUNTER">%d</xliff:g> resterend"</string> - <string name="sendImage">"Foto delen via"</string> - <string name="setImage">"Foto instellen als"</string> - <string name="sendVideo">"Video delen via"</string> - <string name="movieviewlabel">"Films"</string> - <string name="loading_video">"Video laden..."</string> - <string name="spaceIsLow_title">"Er is weinig ruimte"</string> - <string name="spaceIsLow_content">"Er is weinig ruimte beschikbaar op uw SD-kaart. U kunt de kwaliteitsinstelling wijzigen of items uit de galerij verwijderen."</string> - <string name="resume_playing_title">"Video hervatten"</string> - <string name="resume_playing_message">"Afspelen hervatten vanaf %s ?"</string> - <string name="resume_playing_resume">"Afspelen hervatten"</string> - <string name="resume_playing_restart">"Opnieuw starten"</string> - <string name="gadget_title">"Fotolijstje"</string> - <string name="video_file_name_format">"\'video\'-yyyy-MM-dd-HH-mm-ss"</string> -</resources> diff --git a/res/values-pl/arrays.xml b/res/values-pl/arrays.xml deleted file mode 100644 index dfbf090..0000000 --- a/res/values-pl/arrays.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <!-- no translation found for pref_camera_videoquality_entries:0 (4155278146225809483) --> - <!-- no translation found for pref_camera_videoquality_entries:1 (2439895494739176281) --> - <string-array name="pref_camera_videoquality_entryvalues"> - <item>"0"</item> - <item>"1"</item> - </string-array> -</resources> diff --git a/res/values-pl/strings.xml b/res/values-pl/strings.xml deleted file mode 100644 index 8a35c58..0000000 --- a/res/values-pl/strings.xml +++ /dev/null @@ -1,151 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <string name="all_images">"Wszystkie zdjęcia"</string> - <string name="all_videos">"Wszystkie filmy wideo"</string> - <string name="camera_label">"Aparat"</string> - <string name="gallery_picker_label">"Galeria"</string> - <string name="gallery_camera_bucket_name">"Zdjęcia z aparatu"</string> - <string name="gallery_camera_videos_bucket_name">"Filmy wideo z aparatu"</string> - <string name="switch_to_video_lable">"Przełącz na wideo"</string> - <string name="switch_to_camera_lable">"Przełącz na aparat fotograficzny"</string> - <string name="crop_label">"Przytnij zdjęcie"</string> - <string name="view_label">"Wyświetl zdjęcie"</string> - <string name="preferences_label">"Ustawienia aparatu"</string> - <string name="wait">"Poczekaj…"</string> - <string name="no_storage">"Zanim zaczniesz korzystać z aparatu fotograficznego, włóż kartę SD."</string> - <string name="not_enough_space">"Karta SD jest pełna."</string> - <string name="preparing_sd">"Przygotowywanie karty SD..."</string> - <string name="wallpaper">"Ustawianie tapety, poczekaj…"</string> - <string name="savingImage">"Trwa zapisywanie zdjęcia…"</string> - <string name="runningFaceDetection">"Poczekaj…"</string> - <string name="flip_orientation">"Zmień orientację"</string> - <string name="settings">"Ustawienia"</string> - <string name="view">"Wyświetl"</string> - <string name="details">"Szczegóły"</string> - <string name="rotate">"Obróć"</string> - <string name="rotate_left">"Obróć w lewo"</string> - <string name="rotate_right">"Obróć w prawo"</string> - <string name="slide_show">"Pokaz slajdów"</string> - <string name="capture_picture">"Zrób zdjęcie"</string> - <string name="capture_video">"Nagraj film wideo"</string> - <string name="crop_save_text">"Zapisz"</string> - <string name="crop_discard_text">"Odrzuć"</string> - <string name="confirm_delete_title">"Usuń"</string> - <string name="confirm_delete_message">"Zdjęcie zostanie usunięte."</string> - <string name="confirm_delete_video_message">"Film wideo zostanie usunięty."</string> - <string name="camera_toss">"Usuń"</string> - <string name="camera_gallery">"Galeria"</string> - <string name="camera_share">"Prześlij"</string> - <string name="camera_set">"Ustaw jako"</string> - <string name="camera_play">"Odtwórz"</string> - <string name="camera_attach">"Załącz"</string> - <string name="camera_cancel">"Anuluj"</string> - <string name="camera_crop">"Przytnij"</string> - <string name="camera_tossing">"Trwa usuwanie…"</string> - <string name="no_way_to_share_image">"Nie można przesłać tego zdjęcia."</string> - <string name="no_way_to_share_video">"Nie można przesłać tego filmu."</string> - <string name="camera_gallery_photos_text">"Galeria"</string> - <string name="camera_pick_wallpaper">"Zdjęcia"</string> - <string name="camera_setas_wallpaper">"Tapeta"</string> - <string name="pref_gallery_category">"Ustawienia ogólne"</string> - <string name="pref_slideshow_category">"Ustawienia pokazu slajdów"</string> - <string name="pref_camera_general_settings_category">"Ustawienia ogólne"</string> - <string name="pref_gallery_size_title">"Rozmiar wyświetlacza"</string> - <string name="pref_gallery_size_summary">"Ustaw wyświetlany rozmiar zdjęć i filmów"</string> - <string name="pref_gallery_size_dialogtitle">"Rozmiar zdjęć"</string> - <string-array name="pref_gallery_size_choices"> - <item>"Duży"</item> - <item>"Mały"</item> - </string-array> - <string name="pref_gallery_sort_title">"Kolejność sortowania"</string> - <string name="pref_gallery_sort_summary">"Wybierz kolejność sortowania zdjęć i filmów"</string> - <string name="pref_gallery_sort_dialogtitle">"Sortowanie zdjęć"</string> - <string-array name="pref_gallery_sort_choices"> - <item>"Najpierw najnowsze"</item> - <item>"Od najstarszego"</item> - </string-array> - <string name="pref_gallery_slideshow_interval_title">"Pokaz slajdów — odstęp czasu"</string> - <string name="pref_gallery_slideshow_interval_summary">"Wybierz, jak długo mają być wyświetlane poszczególne zdjęcia w pokazie slajdów"</string> - <string name="pref_gallery_slideshow_interval_dialogtitle">"Pokaz slajdów — odstęp czasu"</string> - <string-array name="pref_gallery_slideshow_interval_choices"> - <item>"2 sekundy"</item> - <item>"3 sekundy"</item> - <item>"4 sekundy"</item> - </string-array> - <string name="pref_gallery_slideshow_transition_title">"Pokaz slajdów — efekt przejścia"</string> - <string name="pref_gallery_slideshow_transition_summary">"Wybierz efekt używany przy przejściu z jednego zdjęcia do kolejnego"</string> - <string name="pref_gallery_slideshow_transition_dialogtitle">"Pokaz slajdów — efekt przejścia"</string> - <string-array name="pref_gallery_slideshow_transition_choices"> - <item>"Wyłanianie się i zanikanie zdjęć"</item> - <item>"Przesuwanie z lewa w prawo"</item> - <item>"Przesuwanie z góry na dół"</item> - <item>"Wybór losowy"</item> - </string-array> - <string name="pref_gallery_slideshow_repeat_title">"Powtórz pokaz slajdów"</string> - <string name="pref_gallery_slideshow_repeat_summary">"Wyświetlaj pokaz slajdów więcej niż raz"</string> - <string name="pref_gallery_slideshow_shuffle_title">"Losowa kolejność"</string> - <string name="pref_gallery_slideshow_shuffle_summary">"Wyświetlaj zdjęcia w kolejności losowej"</string> - <string name="pref_camera_recordlocation_title">"Zapisuj lokalizację w zdjęciach"</string> - <string name="pref_camera_recordlocation_summary">"Zapisz lokalizację w danych zdjęcia"</string> - <string name="pref_camera_videoquality_category">"Jakość wideo"</string> - <string name="pref_camera_videoquality_title">"Wybierz jakość wideo"</string> - <string name="pref_camera_videoquality_entry_0">"Niska (dla wiadomości MMS)"</string> - <string name="pref_camera_videoquality_entry_1">"Wysoka (dla karty SD)"</string> - <string name="pref_camera_videoquality_dialogtitle">"Jakość wideo"</string> - <string name="camerasettings">"Ustawienia"</string> - <string name="image_gallery_NoImageView_text">"Nie znaleziono nośnika."</string> - <string name="pref_gallery_confirm_delete_title">"Potwierdzanie usuwania"</string> - <string name="pref_gallery_confirm_delete_summary">"Wyświetl potwierdzenie przed usunięciem zdjęcia lub filmu"</string> - <string name="details_panel_title">"Szczegóły"</string> - <string name="details_file_size">"Rozmiar pliku:"</string> - <string name="details_image_resolution">"Rozdzielczość:"</string> - <string name="details_duration">"Czas trwania:"</string> - <string name="details_date_taken">"Data zrobienia zdjęcia:"</string> - <string name="details_frame_rate">"Szybkość klatek:"</string> - <string name="details_bit_rate">"Szybkość transmisji:"</string> - <string name="details_codec">"Kodek:"</string> - <string name="details_format">"Format:"</string> - <string name="details_dimension_x">"%1$d x %2$d"</string> - <string name="details_ms">"%1$02d:%2$02d"</string> - <string name="details_hms">"%1$d:%2$02d:%3$02d"</string> - <string name="details_fps">"%1$d ramek/s"</string> - <string name="details_kbps">"%1$d Kb/s"</string> - <string name="details_mbps">"%1$g Mb/s"</string> - <string name="details_ok">"OK"</string> - <string name="context_menu_header">"Opcje zdjęć"</string> - <string name="video_context_menu_header">"Opcje wideo"</string> - <string name="multiface_crop_help">"Dotknij twarzy, aby rozpocząć"</string> - <string name="photos_gallery_title">"Galeria"</string> - <string name="pick_photos_gallery_title">"Wybierz zdjęcie"</string> - <string name="videos_gallery_title">"Galeria"</string> - <string name="pick_videos_gallery_title">"Wybierz film wideo"</string> - <string name="loading_progress_format_string">"Pozostało <xliff:g id="COUNTER">%d</xliff:g>"</string> - <string name="sendImage">"Prześlij zdjęcie następującą drogą:"</string> - <string name="setImage">"Ustaw zdjęcie jako"</string> - <string name="sendVideo">"Prześlij film następującą drogą:"</string> - <string name="movieviewlabel">"Filmy"</string> - <string name="loading_video">"Ładowanie filmu wideo..."</string> - <string name="spaceIsLow_title">"Miejsca jest mało"</string> - <string name="spaceIsLow_content">"Na karcie SD brakuje miejsca. Zmień ustawienie jakości lub usuń elementy z Galerii."</string> - <string name="resume_playing_title">"Wznów film"</string> - <string name="resume_playing_message">"Wznowić odtwarzanie od %s?"</string> - <string name="resume_playing_resume">"Wznów odtwarzanie"</string> - <string name="resume_playing_restart">"Rozpocznij"</string> - <string name="gadget_title">"Ramka zdjęcia"</string> - <string name="video_file_name_format">"\'video\'-yyyy-MM-dd-HH-mm-ss"</string> -</resources> diff --git a/res/values-ru/arrays.xml b/res/values-ru/arrays.xml deleted file mode 100644 index dfbf090..0000000 --- a/res/values-ru/arrays.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <!-- no translation found for pref_camera_videoquality_entries:0 (4155278146225809483) --> - <!-- no translation found for pref_camera_videoquality_entries:1 (2439895494739176281) --> - <string-array name="pref_camera_videoquality_entryvalues"> - <item>"0"</item> - <item>"1"</item> - </string-array> -</resources> diff --git a/res/values-ru/strings.xml b/res/values-ru/strings.xml deleted file mode 100644 index f3fb789..0000000 --- a/res/values-ru/strings.xml +++ /dev/null @@ -1,151 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <string name="all_images">"Все изображения"</string> - <string name="all_videos">"Все видео"</string> - <string name="camera_label">"Камера"</string> - <string name="gallery_picker_label">"Галерея"</string> - <string name="gallery_camera_bucket_name">"Фотографии с камеры"</string> - <string name="gallery_camera_videos_bucket_name">"Видео с камеры"</string> - <string name="switch_to_video_lable">"Перейти в режим видео"</string> - <string name="switch_to_camera_lable">"Перейти в режим камеры"</string> - <string name="crop_label">"Обрезать изображение"</string> - <string name="view_label">"Просмотреть изображение"</string> - <string name="preferences_label">"Настройки камеры"</string> - <string name="wait">"Подождите…"</string> - <string name="no_storage">"Перед использованием камеры вставьте карту SD."</string> - <string name="not_enough_space">"Карта SD заполнена."</string> - <string name="preparing_sd">"Подготовка карты SD..."</string> - <string name="wallpaper">"Установка фонового рисунка, подождите…"</string> - <string name="savingImage">"Идет сохранение изображения…"</string> - <string name="runningFaceDetection">"Подождите…"</string> - <string name="flip_orientation">"Изменить ориентацию"</string> - <string name="settings">"Настройки"</string> - <string name="view">"Просмотреть"</string> - <string name="details">"Сведения"</string> - <string name="rotate">"Повернуть"</string> - <string name="rotate_left">"Повернуть налево"</string> - <string name="rotate_right">"Повернуть направо"</string> - <string name="slide_show">"Слайд-шоу"</string> - <string name="capture_picture">"Сделать фотографию"</string> - <string name="capture_video">"Снять видео"</string> - <string name="crop_save_text">"Сохранить"</string> - <string name="crop_discard_text">"Отменить"</string> - <string name="confirm_delete_title">"Удаление"</string> - <string name="confirm_delete_message">"Изображение будет удалено."</string> - <string name="confirm_delete_video_message">"Видео будет удалено."</string> - <string name="camera_toss">"Удаление"</string> - <string name="camera_gallery">"Галерея"</string> - <string name="camera_share">"Отправить"</string> - <string name="camera_set">"Установить как"</string> - <string name="camera_play">"Воспроизвести"</string> - <string name="camera_attach">"Вложить"</string> - <string name="camera_cancel">"Отмена"</string> - <string name="camera_crop">"Обрезать"</string> - <string name="camera_tossing">"Идет удаление…"</string> - <string name="no_way_to_share_image">"Отправить это изображение нельзя."</string> - <string name="no_way_to_share_video">"Отправить это видео нельзя."</string> - <string name="camera_gallery_photos_text">"Галерея"</string> - <string name="camera_pick_wallpaper">"Изображения"</string> - <string name="camera_setas_wallpaper">"Фоновый рисунок"</string> - <string name="pref_gallery_category">"Общие настройки"</string> - <string name="pref_slideshow_category">"Настройки слайд-шоу"</string> - <string name="pref_camera_general_settings_category">"Общие настройки"</string> - <string name="pref_gallery_size_title">"Отображаемый размер"</string> - <string name="pref_gallery_size_summary">"Выбор отображаемого размера изображений и видео"</string> - <string name="pref_gallery_size_dialogtitle">"Размер изображения"</string> - <string-array name="pref_gallery_size_choices"> - <item>"Крупный"</item> - <item>"Мелкий"</item> - </string-array> - <string name="pref_gallery_sort_title">"Порядок сортировки"</string> - <string name="pref_gallery_sort_summary">"Выберите порядок сортировки изображений и видео"</string> - <string name="pref_gallery_sort_dialogtitle">"Сортировка изображений"</string> - <string-array name="pref_gallery_sort_choices"> - <item>"Начиная с новых"</item> - <item>"Заканчивая новыми"</item> - </string-array> - <string name="pref_gallery_slideshow_interval_title">"Интервал слайд-шоу"</string> - <string name="pref_gallery_slideshow_interval_summary">"Выберите время отображения каждого слайда"</string> - <string name="pref_gallery_slideshow_interval_dialogtitle">"Интервал слайд-шоу"</string> - <string-array name="pref_gallery_slideshow_interval_choices"> - <item>"2 секунды"</item> - <item>"3 секунды"</item> - <item>"4 секунды"</item> - </string-array> - <string name="pref_gallery_slideshow_transition_title">"Переходы слайд-шоу"</string> - <string name="pref_gallery_slideshow_transition_summary">"Выберите эффект для перехода от одного слайда к другому"</string> - <string name="pref_gallery_slideshow_transition_dialogtitle">"Переходы слайд-шоу"</string> - <string-array name="pref_gallery_slideshow_transition_choices"> - <item>"Затемнение"</item> - <item>"Слайды слева направо"</item> - <item>"Слайды сверху вниз"</item> - <item>"Случайный выбор"</item> - </string-array> - <string name="pref_gallery_slideshow_repeat_title">"Повторить слайд-шоу"</string> - <string name="pref_gallery_slideshow_repeat_summary">"Воспроизвести слайд-шоу несколько раз"</string> - <string name="pref_gallery_slideshow_shuffle_title">"Перемешать слайды"</string> - <string name="pref_gallery_slideshow_shuffle_summary">"Показывать изображения в случайном порядке"</string> - <string name="pref_camera_recordlocation_title">"Сохранять адрес в изображениях"</string> - <string name="pref_camera_recordlocation_summary">"Записывать адрес в данные изображения"</string> - <string name="pref_camera_videoquality_category">"Качество видео"</string> - <string name="pref_camera_videoquality_title">"Выбор качества видео"</string> - <string name="pref_camera_videoquality_entry_0">"Низкое (для MMS)"</string> - <string name="pref_camera_videoquality_entry_1">"Высокое (для карты SD)"</string> - <string name="pref_camera_videoquality_dialogtitle">"Качество видео"</string> - <string name="camerasettings">"Настройки"</string> - <string name="image_gallery_NoImageView_text">"Нет мультимедийных материалов."</string> - <string name="pref_gallery_confirm_delete_title">"Подтверждение удаления"</string> - <string name="pref_gallery_confirm_delete_summary">"Запрашивать подтверждения перед удалением изображения или видео"</string> - <string name="details_panel_title">"Сведения"</string> - <string name="details_file_size">"Размер файла:"</string> - <string name="details_image_resolution">"Разрешение:"</string> - <string name="details_duration">"Продолжительность:"</string> - <string name="details_date_taken">"Дата съемки:"</string> - <string name="details_frame_rate">"Частота кадров:"</string> - <string name="details_bit_rate">"Битрейт:"</string> - <string name="details_codec">"Кодек:"</string> - <string name="details_format">"Формат:"</string> - <string name="details_dimension_x">"%1$d на %2$d"</string> - <string name="details_ms">"%1$02d:%2$02d"</string> - <string name="details_hms">"%1$d:%2$02d:%3$02d"</string> - <string name="details_fps">"%1$d кадров/с"</string> - <string name="details_kbps">"%1$d кбит/с"</string> - <string name="details_mbps">"%1$g мбит/с"</string> - <string name="details_ok">"ОК"</string> - <string name="context_menu_header">"Параметры изображения"</string> - <string name="video_context_menu_header">"Параметры видео"</string> - <string name="multiface_crop_help">"Чтобы начать, выберите лицо."</string> - <string name="photos_gallery_title">"Галерея"</string> - <string name="pick_photos_gallery_title">"Выбор изображения"</string> - <string name="videos_gallery_title">"Галерея"</string> - <string name="pick_videos_gallery_title">"Выбрать видео"</string> - <string name="loading_progress_format_string">"Осталось: <xliff:g id="COUNTER">%d</xliff:g>"</string> - <string name="sendImage">"Отправить изображение при помощи"</string> - <string name="setImage">"Установить изображение как"</string> - <string name="sendVideo">"Отправить видео при помощи"</string> - <string name="movieviewlabel">"Фильмы"</string> - <string name="loading_video">"Идет загрузка видео…"</string> - <string name="spaceIsLow_title">"Осталось мало места"</string> - <string name="spaceIsLow_content">"Место на карте SD заканчивается. Измените настройки качества или удалите элементы из галереи."</string> - <string name="resume_playing_title">"Продолжение просмотра видео"</string> - <string name="resume_playing_message">"Продолжить воспроизведение с %s ?"</string> - <string name="resume_playing_resume">"Продолжить воспроизведение"</string> - <string name="resume_playing_restart">"Начать с начала"</string> - <string name="gadget_title">"Рамка фотографии"</string> - <string name="video_file_name_format">"\'video\'-yyyy-MM-dd-HH-mm-ss"</string> -</resources> diff --git a/res/values-zh-rCN/arrays.xml b/res/values-zh-rCN/arrays.xml deleted file mode 100644 index dfbf090..0000000 --- a/res/values-zh-rCN/arrays.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <!-- no translation found for pref_camera_videoquality_entries:0 (4155278146225809483) --> - <!-- no translation found for pref_camera_videoquality_entries:1 (2439895494739176281) --> - <string-array name="pref_camera_videoquality_entryvalues"> - <item>"0"</item> - <item>"1"</item> - </string-array> -</resources> diff --git a/res/values-zh-rCN/strings.xml b/res/values-zh-rCN/strings.xml deleted file mode 100644 index 67104a0..0000000 --- a/res/values-zh-rCN/strings.xml +++ /dev/null @@ -1,151 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <string name="all_images">"所有图片"</string> - <string name="all_videos">"所有视频"</string> - <string name="camera_label">"相机"</string> - <string name="gallery_picker_label">"图片库"</string> - <string name="gallery_camera_bucket_name">"相机照片"</string> - <string name="gallery_camera_videos_bucket_name">"相机视频"</string> - <string name="switch_to_video_lable">"切换到视频"</string> - <string name="switch_to_camera_lable">"切换到相机"</string> - <string name="crop_label">"裁切图片"</string> - <string name="view_label">"查看图片"</string> - <string name="preferences_label">"相机设置"</string> - <string name="wait">"请稍候..."</string> - <string name="no_storage">"请在使用相机之前插入 SD 卡。"</string> - <string name="not_enough_space">"您的 SD 卡已满。"</string> - <string name="preparing_sd">"正在准备 SD 卡..."</string> - <string name="wallpaper">"正在设置壁纸,请稍候..."</string> - <string name="savingImage">"正在保存图片..."</string> - <string name="runningFaceDetection">"请稍候..."</string> - <string name="flip_orientation">"反转方向"</string> - <string name="settings">"设置"</string> - <string name="view">"查看"</string> - <string name="details">"详细信息"</string> - <string name="rotate">"旋转"</string> - <string name="rotate_left">"向左旋转"</string> - <string name="rotate_right">"向右旋转"</string> - <string name="slide_show">"幻灯片演示"</string> - <string name="capture_picture">"拍摄照片"</string> - <string name="capture_video">"拍摄视频"</string> - <string name="crop_save_text">"保存"</string> - <string name="crop_discard_text">"放弃"</string> - <string name="confirm_delete_title">"删除"</string> - <string name="confirm_delete_message">"会删除该图片。"</string> - <string name="confirm_delete_video_message">"会删除该视频。"</string> - <string name="camera_toss">"删除"</string> - <string name="camera_gallery">"图片库"</string> - <string name="camera_share">"共享"</string> - <string name="camera_set">"设置为"</string> - <string name="camera_play">"播放"</string> - <string name="camera_attach">"附加"</string> - <string name="camera_cancel">"取消"</string> - <string name="camera_crop">"裁切"</string> - <string name="camera_tossing">"正在删除..."</string> - <string name="no_way_to_share_image">"无法共享此图片。"</string> - <string name="no_way_to_share_video">"无法共享此视频。"</string> - <string name="camera_gallery_photos_text">"图片库"</string> - <string name="camera_pick_wallpaper">"图片"</string> - <string name="camera_setas_wallpaper">"壁纸"</string> - <string name="pref_gallery_category">"常规设置"</string> - <string name="pref_slideshow_category">"幻灯片演示设置"</string> - <string name="pref_camera_general_settings_category">"常规设置"</string> - <string name="pref_gallery_size_title">"显示大小"</string> - <string name="pref_gallery_size_summary">"选择图片和视频的显示大小"</string> - <string name="pref_gallery_size_dialogtitle">"图片大小"</string> - <string-array name="pref_gallery_size_choices"> - <item>"大"</item> - <item>"小"</item> - </string-array> - <string name="pref_gallery_sort_title">"排序顺序"</string> - <string name="pref_gallery_sort_summary">"选择图片和视频的排序顺序"</string> - <string name="pref_gallery_sort_dialogtitle">"图片排序"</string> - <string-array name="pref_gallery_sort_choices"> - <item>"最新的在最前面"</item> - <item>"最新的在最后面"</item> - </string-array> - <string name="pref_gallery_slideshow_interval_title">"幻灯片演示间隔"</string> - <string name="pref_gallery_slideshow_interval_summary">"选择每张幻灯片在演示中显示的时间长度"</string> - <string name="pref_gallery_slideshow_interval_dialogtitle">"幻灯片演示间隔"</string> - <string-array name="pref_gallery_slideshow_interval_choices"> - <item>"2 秒"</item> - <item>"3 秒"</item> - <item>"4 秒"</item> - </string-array> - <string name="pref_gallery_slideshow_transition_title">"幻灯片演示过渡"</string> - <string name="pref_gallery_slideshow_transition_summary">"选择从一张幻灯片移动到下一张时使用的效果"</string> - <string name="pref_gallery_slideshow_transition_dialogtitle">"幻灯片演示过渡"</string> - <string-array name="pref_gallery_slideshow_transition_choices"> - <item>"逐渐增强和逐渐减弱"</item> - <item>"自左至右滑动"</item> - <item>"自上至下滑动"</item> - <item>"随机选择"</item> - </string-array> - <string name="pref_gallery_slideshow_repeat_title">"重复幻灯片演示"</string> - <string name="pref_gallery_slideshow_repeat_summary">"多次播放幻灯片演示"</string> - <string name="pref_gallery_slideshow_shuffle_title">"随机演示幻灯片"</string> - <string name="pref_gallery_slideshow_shuffle_summary">"以随机顺序显示图片"</string> - <string name="pref_camera_recordlocation_title">"在图片中存储位置"</string> - <string name="pref_camera_recordlocation_summary">"通过图片数据记录位置"</string> - <string name="pref_camera_videoquality_category">"视频质量"</string> - <string name="pref_camera_videoquality_title">"选择视频质量"</string> - <string name="pref_camera_videoquality_entry_0">"低(对于彩信)"</string> - <string name="pref_camera_videoquality_entry_1">"高(对于 SD 卡)"</string> - <string name="pref_camera_videoquality_dialogtitle">"视频质量"</string> - <string name="camerasettings">"设置"</string> - <string name="image_gallery_NoImageView_text">"找不到媒体。"</string> - <string name="pref_gallery_confirm_delete_title">"确认删除"</string> - <string name="pref_gallery_confirm_delete_summary">"在删除图片或视频前显示确认"</string> - <string name="details_panel_title">"详细信息"</string> - <string name="details_file_size">"文件大小:"</string> - <string name="details_image_resolution">"分辨率:"</string> - <string name="details_duration">"持续时间:"</string> - <string name="details_date_taken">"拍摄日期:"</string> - <string name="details_frame_rate">"帧频:"</string> - <string name="details_bit_rate">"比特率:"</string> - <string name="details_codec">"编解码器:"</string> - <string name="details_format">"格式:"</string> - <string name="details_dimension_x">"%1$d x %2$d"</string> - <string name="details_ms">"%1$02d:%2$02d"</string> - <string name="details_hms">"%1$d:%2$02d:%3$02d"</string> - <string name="details_fps">"%1$d fps"</string> - <string name="details_kbps">"%1$d Kbps"</string> - <string name="details_mbps">"%1$g Mbps"</string> - <string name="details_ok">"确定"</string> - <string name="context_menu_header">"图片选项"</string> - <string name="video_context_menu_header">"视频选项"</string> - <string name="multiface_crop_help">"轻击一张脸开始裁切。"</string> - <string name="photos_gallery_title">"图片库"</string> - <string name="pick_photos_gallery_title">"选择图片"</string> - <string name="videos_gallery_title">"图片库"</string> - <string name="pick_videos_gallery_title">"选择视频"</string> - <string name="loading_progress_format_string">"还剩 <xliff:g id="COUNTER">%d</xliff:g>"</string> - <string name="sendImage">"共享图片的方式"</string> - <string name="setImage">"将图片设置为"</string> - <string name="sendVideo">"共享视频的方式"</string> - <string name="movieviewlabel">"电影"</string> - <string name="loading_video">"正在载入视频..."</string> - <string name="spaceIsLow_title">"空间不足"</string> - <string name="spaceIsLow_content">"您的 SD 卡已满。请更改质量设置或删除图片库中的内容。"</string> - <string name="resume_playing_title">"重新播放视频"</string> - <string name="resume_playing_message">"从 %s 开始重新播放?"</string> - <string name="resume_playing_resume">"重新播放"</string> - <string name="resume_playing_restart">"重新开始"</string> - <string name="gadget_title">"相框"</string> - <string name="video_file_name_format">"\'video\'-yyyy-MM-dd-HH-mm-ss"</string> -</resources> diff --git a/res/values-zh-rTW/arrays.xml b/res/values-zh-rTW/arrays.xml deleted file mode 100644 index dfbf090..0000000 --- a/res/values-zh-rTW/arrays.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <!-- no translation found for pref_camera_videoquality_entries:0 (4155278146225809483) --> - <!-- no translation found for pref_camera_videoquality_entries:1 (2439895494739176281) --> - <string-array name="pref_camera_videoquality_entryvalues"> - <item>"0"</item> - <item>"1"</item> - </string-array> -</resources> diff --git a/res/values-zh-rTW/strings.xml b/res/values-zh-rTW/strings.xml deleted file mode 100644 index 4ddb816..0000000 --- a/res/values-zh-rTW/strings.xml +++ /dev/null @@ -1,151 +0,0 @@ -<?xml version="1.0" encoding="UTF-8"?> -<!-- 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. ---> -<resources xmlns:android="http://schemas.android.com/apk/res/android" - xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <string name="all_images">"所有相片"</string> - <string name="all_videos">"所有影片"</string> - <string name="camera_label">"相機"</string> - <string name="gallery_picker_label">"圖庫"</string> - <string name="gallery_camera_bucket_name">"攝影機圖片"</string> - <string name="gallery_camera_videos_bucket_name">"攝影機影片"</string> - <string name="switch_to_video_lable">"切換為影片"</string> - <string name="switch_to_camera_lable">"切換為攝影機"</string> - <string name="crop_label">"裁切相片"</string> - <string name="view_label">"檢視相片"</string> - <string name="preferences_label">"相機設定"</string> - <string name="wait">"請稍候…"</string> - <string name="no_storage">"使用相機前請先插入 SD 卡。"</string> - <string name="not_enough_space">"SD 卡已滿。"</string> - <string name="preparing_sd">"正在準備 SD 卡..."</string> - <string name="wallpaper">"設定桌布中,請稍候…"</string> - <string name="savingImage">"儲存相片中…"</string> - <string name="runningFaceDetection">"請稍候…"</string> - <string name="flip_orientation">"旋轉方向"</string> - <string name="settings">"設定"</string> - <string name="view">"檢視"</string> - <string name="details">"詳細資料"</string> - <string name="rotate">"旋轉"</string> - <string name="rotate_left">"向左旋轉"</string> - <string name="rotate_right">"向右旋轉"</string> - <string name="slide_show">"投影片"</string> - <string name="capture_picture">"拍攝圖片"</string> - <string name="capture_video">"拍攝影片"</string> - <string name="crop_save_text">"儲存"</string> - <string name="crop_discard_text">"放棄"</string> - <string name="confirm_delete_title">"刪除"</string> - <string name="confirm_delete_message">"此相片會被刪除。"</string> - <string name="confirm_delete_video_message">"將刪除此影片。"</string> - <string name="camera_toss">"刪除"</string> - <string name="camera_gallery">"圖庫"</string> - <string name="camera_share">"分享"</string> - <string name="camera_set">"設為"</string> - <string name="camera_play">"播放"</string> - <string name="camera_attach">"附加"</string> - <string name="camera_cancel">"取消"</string> - <string name="camera_crop">"裁切"</string> - <string name="camera_tossing">"刪除中…"</string> - <string name="no_way_to_share_image">"此相片無法分享。"</string> - <string name="no_way_to_share_video">"此影片無法分享。"</string> - <string name="camera_gallery_photos_text">"圖庫"</string> - <string name="camera_pick_wallpaper">"相片"</string> - <string name="camera_setas_wallpaper">"桌布"</string> - <string name="pref_gallery_category">"一般設定"</string> - <string name="pref_slideshow_category">"投影片設定"</string> - <string name="pref_camera_general_settings_category">"一般設定"</string> - <string name="pref_gallery_size_title">"顯示大小"</string> - <string name="pref_gallery_size_summary">"選取相片和影片顯示大小"</string> - <string name="pref_gallery_size_dialogtitle">"相片大小"</string> - <string-array name="pref_gallery_size_choices"> - <item>"大"</item> - <item>"小"</item> - </string-array> - <string name="pref_gallery_sort_title">"排序順序"</string> - <string name="pref_gallery_sort_summary">"選取相片和影片排序順序"</string> - <string name="pref_gallery_sort_dialogtitle">"圖片排序"</string> - <string-array name="pref_gallery_sort_choices"> - <item>"最新的優先"</item> - <item>"最舊的優先"</item> - </string-array> - <string name="pref_gallery_slideshow_interval_title">"投影片顯示間隔"</string> - <string name="pref_gallery_slideshow_interval_summary">"選取每張投影片顯示時間"</string> - <string name="pref_gallery_slideshow_interval_dialogtitle">"投影片顯示間隔"</string> - <string-array name="pref_gallery_slideshow_interval_choices"> - <item>"2 秒"</item> - <item>"3 秒"</item> - <item>"4 秒"</item> - </string-array> - <string name="pref_gallery_slideshow_transition_title">"投影片轉場效果"</string> - <string name="pref_gallery_slideshow_transition_summary">"選取相片更換時的轉場效果"</string> - <string name="pref_gallery_slideshow_transition_dialogtitle">"投影片轉場效果"</string> - <string-array name="pref_gallery_slideshow_transition_choices"> - <item>"淡入淡出"</item> - <item>"左右滑動"</item> - <item>"上下滑動"</item> - <item>"隨機選取"</item> - </string-array> - <string name="pref_gallery_slideshow_repeat_title">"重複播放投影片"</string> - <string name="pref_gallery_slideshow_repeat_summary">"播放投影片多次"</string> - <string name="pref_gallery_slideshow_shuffle_title">"隨機播放投影片"</string> - <string name="pref_gallery_slideshow_shuffle_summary">"隨機顯示相片"</string> - <string name="pref_camera_recordlocation_title">"在相片儲存位置資訊"</string> - <string name="pref_camera_recordlocation_summary">"在相片中紀錄位置資訊"</string> - <string name="pref_camera_videoquality_category">"影片品質"</string> - <string name="pref_camera_videoquality_title">"選取影片品質"</string> - <string name="pref_camera_videoquality_entry_0">"低 (適用於多媒體簡訊)"</string> - <string name="pref_camera_videoquality_entry_1">"高 (適用於 SD 卡)"</string> - <string name="pref_camera_videoquality_dialogtitle">"影片品質"</string> - <string name="camerasettings">"設定"</string> - <string name="image_gallery_NoImageView_text">"找不到媒體。"</string> - <string name="pref_gallery_confirm_delete_title">"刪除確認"</string> - <string name="pref_gallery_confirm_delete_summary">"刪除相片或影片前要顯示確認"</string> - <string name="details_panel_title">"詳細資料"</string> - <string name="details_file_size">"檔案大小:"</string> - <string name="details_image_resolution">"解析度:"</string> - <string name="details_duration">"所需時間:"</string> - <string name="details_date_taken">"拍攝日期:"</string> - <string name="details_frame_rate">"影格速率:"</string> - <string name="details_bit_rate">"位元速率:"</string> - <string name="details_codec">"編碼器:"</string> - <string name="details_format">"格式:"</string> - <string name="details_dimension_x">"%1$d x %2$d"</string> - <string name="details_ms">"%1$02d:%2$02d"</string> - <string name="details_hms">"%1$d:%2$02d:%3$02d"</string> - <string name="details_fps">"%1$d fps"</string> - <string name="details_kbps">"%1$d Kbps"</string> - <string name="details_mbps">"%1$g Mbps"</string> - <string name="details_ok">"確定"</string> - <string name="context_menu_header">"圖片選項"</string> - <string name="video_context_menu_header">"影片選項"</string> - <string name="multiface_crop_help">"選取版面開始裁切"</string> - <string name="photos_gallery_title">"圖庫"</string> - <string name="pick_photos_gallery_title">"選取相片"</string> - <string name="videos_gallery_title">"圖庫"</string> - <string name="pick_videos_gallery_title">"選取影片"</string> - <string name="loading_progress_format_string">"還有 <xliff:g id="COUNTER">%d</xliff:g> 張"</string> - <string name="sendImage">"透過…分享圖片"</string> - <string name="setImage">"設定相片為…"</string> - <string name="sendVideo">"透過…分享影片"</string> - <string name="movieviewlabel">"電影"</string> - <string name="loading_video">"正在載入影片…"</string> - <string name="spaceIsLow_title">"空間不足"</string> - <string name="spaceIsLow_content">"您的 SD 卡空間已快用完。請變更品質設定或刪除圖庫中的項目。"</string> - <string name="resume_playing_title">"繼續播放影片"</string> - <string name="resume_playing_message">"要從 %s 繼續播放嗎?"</string> - <string name="resume_playing_resume">"繼續播放"</string> - <string name="resume_playing_restart">"重新開始"</string> - <string name="gadget_title">"相框"</string> - <string name="video_file_name_format">"\'video\'-yyyy-MM-dd-HH-mm-ss"</string> -</resources> diff --git a/res/values/arrays.xml b/res/values/arrays.xml deleted file mode 100644 index 95501e4..0000000 --- a/res/values/arrays.xml +++ /dev/null @@ -1,31 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - --> - -<resources> - <!-- Camera Preferences Video Quality dialog box entries --> - <string-array name="pref_camera_videoquality_entries"> - <item>@string/pref_camera_videoquality_entry_0</item> - <item>@string/pref_camera_videoquality_entry_1</item> - </string-array> - - <!-- Do not localize entryvalues --> - <string-array name="pref_camera_videoquality_entryvalues"> - <item>0</item> - <item>1</item> - </string-array> - -</resources> diff --git a/res/values/colors.xml b/res/values/colors.xml deleted file mode 100644 index d07f3b9..0000000 --- a/res/values/colors.xml +++ /dev/null @@ -1,22 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* //device/apps/common/assets/res/any/colors.xml -** -** Copyright 2008, The Android Open Source Project -** -** Licensed under the Apache License, Version 2.0 (the "License"); -** you may not use this file except in compliance with the License. -** You may obtain a copy of the License at -** -** http://www.apache.org/licenses/LICENSE-2.0 -** -** Unless required by applicable law or agreed to in writing, software -** distributed under the License is distributed on an "AS IS" BASIS, -** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -** See the License for the specific language governing permissions and -** limitations under the License. -*/ ---> -<resources> - <color name="bubble_dark_background">#B2191919</color> -</resources> diff --git a/res/values/dimens.xml b/res/values/dimens.xml deleted file mode 100644 index 5ec105b..0000000 --- a/res/values/dimens.xml +++ /dev/null @@ -1,22 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* //device/apps/common/assets/res/any/dimens.xml -** -** Copyright 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. -*/ ---> -<resources> - <dimen name="hint_y_offset">64dip</dimen> -</resources> diff --git a/res/values/ids.xml b/res/values/ids.xml deleted file mode 100644 index 367bfa2..0000000 --- a/res/values/ids.xml +++ /dev/null @@ -1,22 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -** -** Copyright 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. -*/ ---> -<resources> -</resources> - - diff --git a/res/values/strings.xml b/res/values/strings.xml deleted file mode 100644 index ab7d88e..0000000 --- a/res/values/strings.xml +++ /dev/null @@ -1,458 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2"> - <!-- General strings --> - - <!-- label for the icon meaning 'show me all the images' --> - <string name="all_images">All pictures</string> - - <!-- label for the icon meaning 'show me all the videos' --> - <string name="all_videos">All videos</string> - - <!-- label for the icon meaning 'show me all the images that were taken with the camera' --> - <string name="camera_label">Camera</string> - - <!-- label for the 'pictures application shown in the top level 'all applications' --> - <string name="gallery_picker_label">Gallery</string> - - <!-- unused (do not translate) --> - <string name="gallery_label">Pictures</string> - - <!-- label for the folder that contains Camera pictures in the gallery --> - <string name="gallery_camera_bucket_name">Camera pictures</string> - - <!-- label for the folder that contains Camera videos in the gallery --> - <string name="gallery_camera_videos_bucket_name">Camera videos</string> - - <!-- menu pick: switch to Video cam mode --> - <string name="switch_to_video_lable">Switch to video</string> - - <!-- menu pick: switch to camera mode --> - <string name="switch_to_camera_lable">Switch to camera</string> - - <!-- menu pick: crop the currently selected image --> - <string name="crop_label">Crop picture</string> - - <!-- menu pick: view the currently selected image --> - <string name="view_label">View picture</string> - - <!-- menu pick: go to the preferences screen for the camera or image gallery --> - <string name="preferences_label">Camera settings</string> - - <!-- alert to the user to wait for some operation to complete --> - <string name="wait">Please wait\u2026</string> - - <!-- alert to the user to that an SD card must be installed before using the camera --> - <string name="no_storage">Please insert an SD card before using the camera.</string> - - <!-- alert to the user to that the SD card is too full to complete the operation --> - <string name="not_enough_space">Your SD card is full.</string> - - <!-- alert to the user to that the SD card is being disk-checked --> - <string name="preparing_sd">Preparing SD card\u2026</string> - - <!-- Toast/alert after saving wallpaper --> - <string name="wallpaper">Setting wallpaper, please wait\u2026</string> - - <!-- Settings stuff --> - - <!-- Toast/alert that the image is being saved to the SD card --> - <string name="savingImage">Saving picture\u2026</string> - - <!-- Toast/alert that the face detection is being run --> - <string name="runningFaceDetection">Please wait\u2026</string> - - - <!-- Menu items: --> - <!-- menu pick to change the orientation of the screen --> - <string name="flip_orientation">Flip orientation</string> - - <!-- menu pick to go to the settings screen --> - <string name="settings">Settings</string> - - <!-- menu pick to view the currently selected image --> - <string name="view">View</string> - - <!-- menu pick to view the details of the currently selected image --> - <string name="details">Details</string> - - <!-- menu pick to rotate the currently selected image (brings up submenu) --> - <string name="rotate">Rotate</string> - - <!-- menu pick to rotate the currently selected image to the left --> - <string name="rotate_left">Rotate left</string> - - <!-- menu pick to rotate the currently selected image to the right --> - <string name="rotate_right">Rotate right</string> - - <!-- menu pick to start a slide show --> - <string name="slide_show">Slideshow</string> - - <!-- menu pick to go to camera mode to capture a picture --> - <string name="capture_picture">Capture picture</string> - <!-- menu pick to go to video mode to capture a video --> - <string name="capture_video">Capture video</string> - - <!-- button indicating that the cropped image should be saved --> - <string name="crop_save_text">Save</string> - <!-- button indicating that the cropped image should be reverted back to the original --> - <string name="crop_discard_text">Discard</string> - - <!-- Confirmation dialog title after deleting a picture --> - <string name="confirm_delete_title">Delete</string> - <!-- Confirmation dialog message after deleting a picture --> - <string name="confirm_delete_message">The picture will be deleted.</string> - <!-- Confirmation dialog message after deleting a video --> - <string name="confirm_delete_video_message">The video will be deleted.</string> - <!-- button indicating that the picture just taken should be deleted --> - <string name="camera_toss">Delete</string> - - <!-- Lable for the button that takes the user to the camera pictures Gallery --> - <string name="camera_gallery">Gallery</string> - - <!-- button indicating that the picture just taken should be shared by email, mms, etc --> - <string name="camera_share">Share</string> - - <!-- button indicating that the picture just taken should be set as a contact photo, wallpaper, etc --> - <string name="camera_set">Set as</string> - - <!-- button indicating that the video just taken should be played --> - <string name="camera_play">Play</string> - - <!-- button indicating that the video just taken should be accepted as an attachment --> - <string name="camera_attach">Attach</string> - - <!-- button indicating that the video recording session should be canceled --> - <string name="camera_cancel">Cancel</string> - - <!-- button indicating that the picture just taken should be cropped --> - <string name="camera_crop">Crop</string> - - <!-- Toast after deleting a picture --> - <string name="camera_tossing">Deleting\u2026</string> - - <!-- Toast after trying to share a picture indicating that there are no applications which are capable of so doing. --> - <string name="no_way_to_share_image">This picture cannot be shared.</string> - - <!-- Toast after trying to share a video indicating that there are no applications which are capable of so doing. --> - <string name="no_way_to_share_video">This video cannot be shared.</string> - - <!-- Do not translate --> - <string name="video_play">Play</string> - - <!-- Button indicating to go to the image gallery --> - <string name="camera_gallery_photos_text">Gallery</string> - - <!-- String indicating an action of picking a picture to use as wallpaper (e.g. set wallpaper from "Pictures") --> - <string name="camera_pick_wallpaper">Pictures</string> - <string name="camera_setas_wallpaper">Wallpaper</string> - - <!-- Settings screen, section heading --> - <string name="pref_gallery_category">General settings</string> - - <!-- Settings screen, section heading --> - <string name="pref_slideshow_category">Slideshow settings</string> - <string name="pref_camera_general_settings_category">General settings</string> - - <!-- Settings screen, setting summary text --> - <string name="pref_gallery_size_title">Display size</string> - - <!-- Settings screen, title for preference for image size to be used in the im --> - <string name="pref_gallery_size_summary">Select the display size of pictures and videos</string> - <!-- Title of dialog that appears after selecting Picture size setting option --> - <string name="pref_gallery_size_dialogtitle">Picture size</string> - <!-- Options in dialog that appears after selecting Picture size setting option --> - <string-array name="pref_gallery_size_choices"> - <!-- size choice of "large" --> - <item>Large</item> - <!-- size choice of "small" --> - <item>Small</item> - </string-array> - <!-- Do not translate. Option values in dialog that appears after selecting Picture size setting option --> - <string-array name="pref_gallery_size_values"> - <!-- do not translate --> - <item>1</item> - <!-- do not translate --> - <item>0</item> - </string-array> - <!-- Do not translate. Default option value in dialog that appears after selecting Picture size setting option --> - <string name="default_value_pref_gallery_size">1</string> - <!-- Settings screen, setting option name --> - <string name="pref_gallery_sort_title">Sort order</string> - <!-- Settings screen, setting summary text --> - <string name="pref_gallery_sort_summary">Select the sort order of pictures and videos</string> - <!-- Title of dialog that appears after selecting Picture sort setting option --> - <string name="pref_gallery_sort_dialogtitle">Picture sort</string> - <!-- Options in dialog that appears after selecting Picture sort setting option --> - <string-array name="pref_gallery_sort_choices"> - <!-- Preference choice to show "newest first" --> - <item>Newest first</item> - <!-- Preference choice to show "newest last" --> - <item>Newest last</item> - </string-array> - <!-- Do not translate. Option values in dialog that appears after selecting Picture sort setting option --> - <string-array name="pref_gallery_sort_values"> - <!-- do not translate --> - <item>descending</item> - <!-- do not translate --> - <item>ascending</item> - </string-array> - <!-- Do not translate. Default option value in dialog that appears after selecting Picture sort setting option --> - <string name="default_value_pref_gallery_sort">descending</string> - <!-- Settings screen, setting option name --> - <string name="pref_gallery_slideshow_interval_title">Slideshow interval</string> - <!-- Settings screen, setting summary text --> - <string name="pref_gallery_slideshow_interval_summary">Select how long each slide displays in the show</string> - <!-- Title of dialog that appears after selecting Slideshow interval setting option --> - <string name="pref_gallery_slideshow_interval_dialogtitle">Slideshow interval</string> - <!-- Options in dialog that appears after selecting Slideshow interval - setting option --> - <string-array name="pref_gallery_slideshow_interval_choices"> - <!-- slide show interval "N seconds" where N is 2 --> - <item>2 seconds</item> - <!-- slide show interval "N seconds" where N is 3 --> - <item>3 seconds</item> - <!-- slide show interval "N seconds" where N is 4 --> - <item>4 seconds</item> - </string-array> - <!-- Do not translate. Option values in dialog that appears after selecting Slideshow interval setting option --> - <string-array name="pref_gallery_slideshow_interval_values"> - <!-- do not translate --> - <item>"2"</item> - <!-- do not translate --> - <item>"3"</item> - <!-- do not translate --> - <item>"4"</item> - </string-array> - <!-- Do not translate. Default option value in dialog that appears after selecting Slideshow interval setting option --> - <string name="default_value_pref_gallery_slideshow_interval">"2"</string> - <!-- Settings screen, setting option name --> - <string name="pref_gallery_slideshow_transition_title">Slideshow transition</string> - <!-- Settings screen, setting summary text --> - <string name="pref_gallery_slideshow_transition_summary">Select the effect used when moving from one slide to the next</string> - <!-- Title of dialog that appears after selecting Slideshow transition setting option --> - <string name="pref_gallery_slideshow_transition_dialogtitle">Slideshow transition</string> - <!-- Options in dialog that appears after selecting Slideshow transition - setting option --> - <string-array name="pref_gallery_slideshow_transition_choices"> - <!-- Slide show transition to fade in and fade out --> - <item>Fade in & out</item> - <!-- Slide show transition to slide in and out from the left and right --> - <item>Slide left - right</item> - <!-- Slide show transition to slide in and out from the top and bottom --> - <item>Slide up - down</item> - <!-- Slide show transition to be chosen randomly --> - <item>Random selection</item> - </string-array> - <!-- Do not translate. Option values in dialog that appears after selecting Slideshow transition setting option --> - <string-array name="pref_gallery_slideshow_transition_values"> - <!-- do not translate --> - <item>"0"</item> - <!-- do not translate --> - <item>"1"</item> - <!-- do not translate --> - <item>"2"</item> - <!-- do not translate --> - <item>"-1"</item> - </string-array> - <!-- Do not translate. Default option value in dialog that appears after selecting Slideshow transition setting option --> - <string name="default_value_pref_gallery_slideshow_transition">"0"</string> - - <!-- Settings screen, setting check box name --> - <string name="pref_gallery_slideshow_repeat_title">Repeat slideshow</string> - - <!-- Settings screen, setting summary text --> - <string name="pref_gallery_slideshow_repeat_summary">Play slideshow more than once</string> - - <!-- Settings screen, setting check box name --> - <string name="pref_gallery_slideshow_shuffle_title">Shuffle slides</string> - - <!-- Settings screen, setting summary text --> - <string name="pref_gallery_slideshow_shuffle_summary">Show pictures in random order</string> - - <!-- Settings screen, setting title text --> - <string name="pref_camera_recordlocation_title">Store location in pictures</string> - - <!-- Settings screen, setting summary text --> - <string name="pref_camera_recordlocation_summary">Record location in picture data</string> - - <!-- Do not translate --> - <string name="pref_camera_upload_albumname_title">Picasa album name</string> - - <!-- Do not translate --> - <string name="pref_camera_upload_albumname_summary">Name the destination album for your pictures (<xliff:g id="summary">%s</xliff:g>)</string> - - <!-- Do not translate --> - <string name="pref_camera_upload_albumname_dialogtitle">Picasa album name</string> - - <!-- Settings screen, Video quality category title --> - <string name="pref_camera_videoquality_category">Video quality</string> - - <!-- Default video quality setting. A numerical value. Do not translate. --> - <string name="pref_camera_videoquality_default">1</string> - - <!-- Settings screen, Select Video quality title --> - <string name="pref_camera_videoquality_title">Select video quality</string> - - <!-- Settings screen, Video quality dialog radio button choices --> - <string name="pref_camera_videoquality_entry_0">Low (for MMS messages)</string> - <string name="pref_camera_videoquality_entry_1">High (for SD card)</string> - - <!-- Settings screen, Video codec dialog title --> - <string name="pref_camera_videoquality_dialogtitle">Video quality</string> - - <!-- Menu item to go to the settings screen --> - <string name="camerasettings">Settings</string> - - <!-- Text message indicating that there are no pictures or videos in a particular - bucket on the SD card --> - <string name="image_gallery_NoImageView_text">No media found.</string> - - <!-- Preference title for whether the user should be prompted form confirmation when deleting images --> - <string name="pref_gallery_confirm_delete_title">Confirm deletions</string> - - <!-- Preference summary for whether the user should be prompted form confirmation when deleting images --> - <string name="pref_gallery_confirm_delete_summary">Show confirmation before deleting a picture or video</string> - - <!-- Details stuff --> - <!-- Do not translate --> - <string name="details_title_text">myvideo</string> - <!-- Do not translate --> - <string name="details_tags_text">monster</string> - <!-- Do not translate --> - <string name="details_category_label">Category:</string> - <!-- Do not translate --> - <string name="details_description_label">Description:</string> - <!-- Do not translate --> - <string name="details_publicView_text">Public</string> - <!-- Do not translate --> - <string name="details_tags_label">Tags:</string> - <!-- Do not translate --> - <string name="details_description_text">testdescription</string> - <!-- Do not translate --> - <string name="details_title_label">Title:</string> - <!-- Do not translate --> - <string name="details_save_text">Save</string> - <!-- Do not translate --> - <string name="details_language_label">Language:</string> - <!-- Do not translate --> - <string name="details_privateView_text">Private</string> - - <!-- Title of Details dialog --> - <string name="details_panel_title">Details</string> - <!-- Label in message of Details dialog --> - <string name="details_file_size">File size:</string> - <!-- Label in message of Details dialog --> - <string name="details_image_resolution">Resolution:</string> - <!-- Label in message of Details dialog --> - <string name="details_duration">Duration:</string> - <!-- Label in message of Details dialog --> - <string name="details_date_taken">Date taken:</string> - <!-- Label in message of Details dialog --> - <string name="details_frame_rate">Frame rate:</string> - <!-- Label in message of Details dialog --> - <string name="details_bit_rate">Bit rate:</string> - <!-- Label in message of Details dialog --> - <string name="details_codec">Codec:</string> - <!-- Label in message of Details dialog --> - <string name="details_format">Format:</string> - - <!-- Used to format image dimensions in Details dialog. e.g. 64 x 64 --> - <string name="details_dimension_x">%1$d x %2$d</string> - <!-- Used to format short video duration in Details dialog. minutes:seconds e.g. 00:30 --> - <string name="details_ms">%1$02d:%2$02d</string> - <!-- Used to format video duration in Details dialog. hours:minutes:seconds e.g. 0:21:30 --> - <string name="details_hms">%1$d:%2$02d:%3$02d</string> - <!-- Unit of measure in the Details dialog frames per second. e.g. 20 fps --> - <string name="details_fps">%1$d fps</string> - <!-- Unit of measure in the Details dialog K bits per second. e.g. 192 Kbps --> - <string name="details_kbps">%1$d Kbps</string> - <!-- Unit of measure in the Details dialog M bits per second. e.g. 2.3 Mbps --> - <string name="details_mbps">%1$g Mbps</string> - <!-- Details dialog "OK" button. Dismisses dialog. --> - <string name="details_ok">OK</string> - - <!-- Text of context menu when an image is selected --> - <string name="context_menu_header">Picture options</string> - <!-- Text of context menu when a video is selected --> - <string name="video_context_menu_header">Video options</string> - <!-- Hint that appears when cropping an image with more than one face --> - <string name="multiface_crop_help">Tap a face to begin.</string> - - <!-- Activity title when in the image gallery to see pictures --> - <string name="photos_gallery_title">Gallery</string> - - <!-- Activity title when in the image gallery to select a picture --> - <string name="pick_photos_gallery_title">Select picture</string> - - <!-- Activity title when in the image gallery to see videos --> - <string name="videos_gallery_title">Gallery</string> - - <!-- Activity title when in the image gallery to select a video --> - <string name="pick_videos_gallery_title">Select video</string> - - <!-- onscreen text indicating the progress of generating thumbnails. Basically some number followed by the word "remaining" --> - <string name="loading_progress_format_string"><xliff:g id="counter">%d</xliff:g> remaining</string> - - <!-- Displayed in the title of the dialog for things to do with a picture that - is to be sent to another application: --> - <string name="sendImage">Share picture via</string> - - <!-- Displayed in the title of the dialog for things to do with a picture that - is to be "set as" (e.g. set as contact photo or set as wallpaper) --> - <string name="setImage">Set picture as</string> - - <!-- Displayed in the title of the dialog for things to do with a video that - is to be sent to another application. --> - <string name="sendVideo">Share video via</string> - - <!-- Activity label. This might show up in the activity-picker --> - <string name="movieviewlabel">Movies</string> - <!-- shown in the video player view while the video is being loaded, before it starts playing --> - <string name="loading_video">Loading video\u2026</string> - - <!-- Low-memory dialog title --> - <string name="spaceIsLow_title">Space is low</string> - <!-- Low-memory dialog message --> - <string name="spaceIsLow_content">Your SD card is running out of space. Change the quality setting or delete items from Gallery.</string> - - <!-- Movie View Resume Playing dialog title --> - <string name="resume_playing_title">Resume video</string> - - <!-- Movie View Start Playing dialog title --> - <string name="resume_playing_message">Resume playing from %s ?</string> - - <!-- Movie View Start Playing button "Resume from bookmark" --> - <string name="resume_playing_resume">Resume playing</string> - - <!-- Movie View Start Playing button "Beginning" --> - <string name="resume_playing_restart">Start over</string> - - <!-- Title for picture frame gadget to show in list of all available gadgets --> - <string name="gadget_title">Picture frame</string> - - <!-- Video Camera format string for new video files. Passed to java.text.SimpleDateFormat. - Do not localize --> - <string name="video_file_name_format">"'video'-yyyy-MM-dd-HH-mm-ss"</string> - - <!-- Title for the file information dialog --> - <string name="file_info_title">File info:</string> - - <!-- The video is execeed the size limit of a MMS, and suggest user to record a shorter length clip --> - <string name="video_exceed_mms_limit">The video you recorded is too large to send via MMS. Try recording a shorter length clip.</string> - -</resources> diff --git a/res/values/styles.xml b/res/values/styles.xml deleted file mode 100644 index bad65fe..0000000 --- a/res/values/styles.xml +++ /dev/null @@ -1,54 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- -/* -* Copyright (C) 2008 The Android Open Source Project -* -* Licensed under the Apache License, Version 2.0 (the "License"); -* you may not use this file except in compliance with the License. -* You may obtain a copy of the License at -* -* http://www.apache.org/licenses/LICENSE-2.0 -* -* Unless required by applicable law or agreed to in writing, software -* distributed under the License is distributed on an "AS IS" BASIS, -* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -* See the License for the specific language governing permissions and -* limitations under the License. -*/ ---> - -<resources xmlns:android="http://schemas.android.com/apk/res/android"> - <style name="OnScreenHintTextAppearance"> - <item name="android:textColor">@android:color/primary_text_dark</item> - <item name="android:textColorHighlight">#FFFF9200</item> - <item name="android:textColorHint">#808080</item> - <item name="android:textColorLink">#5C5CFF</item> - <item name="android:textSize">16sp</item> - <item name="android:textStyle">normal</item> - </style> - <style name="OnScreenHintTextAppearance.Small"> - <item name="android:textSize">14sp</item> - <item name="android:textStyle">normal</item> - <item name="android:textColor">@android:color/secondary_text_dark</item> - </style> - <style name="Animation" /> - <style name="Animation.OnScreenHint"> - <item name="android:windowEnterAnimation">@anim/on_screen_hint_enter</item> - <item name="android:windowExitAnimation">@anim/on_screen_hint_exit</item> - </style> - <style name="OnscreenActionIcon"> - <item name="android:focusable">true</item> - <item name="android:clickable">true</item> - <item name="android:textSize">13dip</item> - <item name="android:singleLine">true</item> - <item name="android:ellipsize">marquee</item> - <item name="android:shadowColor">#FF000000</item> - <item name="android:shadowRadius">2.0</item> - <item name="android:textColor">#FFF</item> - <item name="android:gravity">center_horizontal</item> - <item name="android:layout_width">wrap_content</item> - <item name="android:layout_height">wrap_content</item> - <item name="android:layout_marginLeft">30dip</item> - <item name="android:drawablePadding">3dip</item> - </style> -</resources> diff --git a/res/xml/camera_preferences.xml b/res/xml/camera_preferences.xml deleted file mode 100644 index 4d8b7b7..0000000 --- a/res/xml/camera_preferences.xml +++ /dev/null @@ -1,42 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- Copyright (C) 2008 The Android Open Source Project - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. ---> - -<!-- This is a primitive example showing the different types of preferences available. --> -<PreferenceScreen - xmlns:android="http://schemas.android.com/apk/res/android"> - - <PreferenceCategory - android:title="@string/pref_camera_general_settings_category"> - - <CheckBoxPreference - android:key="pref_camera_recordlocation_key" - android:title="@string/pref_camera_recordlocation_title" - android:summary="@string/pref_camera_recordlocation_summary" - android:defaultValue="false"/> - </PreferenceCategory> - - <PreferenceCategory - android:title="@string/pref_camera_videoquality_category"> - <!-- android:summary is filled in by CameraSettings --> - <ListPreference - android:key="pref_camera_videoquality_key" - android:defaultValue="@string/pref_camera_videoquality_default" - android:title="@string/pref_camera_videoquality_title" - android:entries="@array/pref_camera_videoquality_entries" - android:entryValues="@array/pref_camera_videoquality_entryvalues" - android:dialogTitle="@string/pref_camera_videoquality_dialogtitle" /> - </PreferenceCategory> -</PreferenceScreen> diff --git a/res/xml/gadget_info.xml b/res/xml/gadget_info.xml deleted file mode 100644 index 5efaddd..0000000 --- a/res/xml/gadget_info.xml +++ /dev/null @@ -1,24 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- 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. ---> - -<gadget-provider xmlns:android="http://schemas.android.com/apk/res/android" - android:minWidth="146dip" - android:minHeight="146dip" - android:updatePeriodMillis="0" - android:initialLayout="@layout/photo_frame" - android:configure="com.android.camera.PhotoGadgetConfigure" - > -</gadget-provider> diff --git a/res/xml/gallery_preferences.xml b/res/xml/gallery_preferences.xml deleted file mode 100644 index 0ddc166..0000000 --- a/res/xml/gallery_preferences.xml +++ /dev/null @@ -1,89 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- Copyright (C) 2008 The Android Open Source Project - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. ---> - -<!-- This is a primitive example showing the different types of preferences available. --> -<PreferenceScreen - xmlns:android="http://schemas.android.com/apk/res/android"> - - <PreferenceCategory - android:title="@string/pref_gallery_category"> - - <ListPreference - android:key="pref_gallery_size_key" - android:title="@string/pref_gallery_size_title" - android:summary="@string/pref_gallery_size_summary" - android:entries="@array/pref_gallery_size_choices" - android:entryValues="@array/pref_gallery_size_values" - android:dialogTitle="@string/pref_gallery_size_dialogtitle" - android:defaultValue="@string/default_value_pref_gallery_size" /> - - <ListPreference - android:key="pref_gallery_sort_key" - android:title="@string/pref_gallery_sort_title" - android:summary="@string/pref_gallery_sort_summary" - android:entries="@array/pref_gallery_sort_choices" - android:entryValues="@array/pref_gallery_sort_values" - android:dialogTitle="@string/pref_gallery_sort_dialogtitle" - android:defaultValue="@string/default_value_pref_gallery_sort" /> - - <CheckBoxPreference - android:key="pref_gallery_confirm_delete_key" - android:title="@string/pref_gallery_confirm_delete_title" - android:summary="@string/pref_gallery_confirm_delete_summary" - android:defaultValue="true"/> -<!-- - <EditTextPreference - android:key="pref_camera_upload_albumname_key" - android:title="@string/pref_camera_upload_albumname_title" - android:summary="@string/pref_camera_upload_albumname_summary" - android:dialogTitle="@string/pref_camera_upload_albumname_dialogtitle" - android:singleLine="true" /> ---> - </PreferenceCategory> - <PreferenceCategory - android:title="@string/pref_slideshow_category"> - <ListPreference - android:key="pref_gallery_slideshow_interval_key" - android:title="@string/pref_gallery_slideshow_interval_title" - android:summary="@string/pref_gallery_slideshow_interval_summary" - android:entries="@array/pref_gallery_slideshow_interval_choices" - android:entryValues="@array/pref_gallery_slideshow_interval_values" - android:dialogTitle="@string/pref_gallery_slideshow_interval_dialogtitle" - android:defaultValue="@string/default_value_pref_gallery_slideshow_interval" /> - - <ListPreference - android:key="pref_gallery_slideshow_transition_key" - android:title="@string/pref_gallery_slideshow_transition_title" - android:summary="@string/pref_gallery_slideshow_transition_summary" - android:entries="@array/pref_gallery_slideshow_transition_choices" - android:entryValues="@array/pref_gallery_slideshow_transition_values" - android:dialogTitle="@string/pref_gallery_slideshow_transition_dialogtitle" - android:defaultValue="@string/default_value_pref_gallery_slideshow_transition" /> - - <CheckBoxPreference - android:key="pref_gallery_slideshow_repeat_key" - android:title="@string/pref_gallery_slideshow_repeat_title" - android:summary="@string/pref_gallery_slideshow_repeat_summary" - android:defaultValue="false"/> - - <CheckBoxPreference - android:key="pref_gallery_slideshow_shuffle_key" - android:title="@string/pref_gallery_slideshow_shuffle_title" - android:summary="@string/pref_gallery_slideshow_shuffle_summary" - android:defaultValue="false"/> - - </PreferenceCategory> -</PreferenceScreen> diff --git a/src/com/android/camera/ActionMenuButton.java b/src/com/android/camera/ActionMenuButton.java deleted file mode 100644 index 65e1f0e..0000000 --- a/src/com/android/camera/ActionMenuButton.java +++ /dev/null @@ -1,83 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.camera; - -import android.content.Context; -import android.graphics.Canvas; -import android.graphics.Paint; -import android.graphics.RectF; -import android.text.Layout; -import android.util.AttributeSet; -import android.widget.TextView; - -/** - * TextView that draws a bubble behind the text. We cannot use a LineBackgroundSpan - * because we want to make the bubble taller than the text and TextView's clip is - * too aggressive. - */ -public class ActionMenuButton extends TextView { - private static final float CORNER_RADIUS = 8.0f; - private static final float PADDING_H = 5.0f; - private static final float PADDING_V = 1.0f; - - private final RectF mRect = new RectF(); - private Paint mPaint; - - public ActionMenuButton(Context context) { - super(context); - init(); - } - - public ActionMenuButton(Context context, AttributeSet attrs) { - super(context, attrs); - init(); - } - - public ActionMenuButton(Context context, AttributeSet attrs, int defStyle) { - super(context, attrs, defStyle); - init(); - } - - private void init() { - setFocusable(true); - - mPaint = new Paint(Paint.ANTI_ALIAS_FLAG); - mPaint.setColor(getContext().getResources().getColor(R.color.bubble_dark_background)); - } - - @Override - protected void drawableStateChanged() { - invalidate(); - super.drawableStateChanged(); - } - - @Override - public void draw(Canvas canvas) { - final Layout layout = getLayout(); - final RectF rect = mRect; - final int left = getCompoundPaddingLeft(); - final int top = getExtendedPaddingTop(); - - rect.set(left + layout.getLineLeft(0) - PADDING_H, - top + layout.getLineTop(0) - PADDING_V, - Math.min(left + layout.getLineRight(0) + PADDING_H, mScrollX + mRight - mLeft), - top + layout.getLineBottom(0) + PADDING_V); - canvas.drawRoundRect(rect, CORNER_RADIUS, CORNER_RADIUS, mPaint); - - super.draw(canvas); - } -} diff --git a/src/com/android/camera/Camera.java b/src/com/android/camera/Camera.java deleted file mode 100644 index 04a30cf..0000000 --- a/src/com/android/camera/Camera.java +++ /dev/null @@ -1,1812 +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.camera; - -import java.io.BufferedInputStream; -import java.io.BufferedOutputStream; -import java.io.DataInputStream; -import java.io.DataOutputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; -import java.io.FileOutputStream; -import java.io.IOException; -import java.io.OutputStream; -import java.util.ArrayList; - -import android.app.Activity; -import android.app.ProgressDialog; -import android.content.BroadcastReceiver; -import android.content.ContentResolver; -import android.content.Context; -import android.content.Intent; -import android.content.IntentFilter; -import android.content.SharedPreferences; -import android.content.pm.ActivityInfo; -import android.content.res.AssetFileDescriptor; -import android.content.res.Resources; -import android.graphics.Bitmap; -import android.graphics.BitmapFactory; -import android.graphics.Matrix; -import android.graphics.drawable.BitmapDrawable; -import android.graphics.drawable.Drawable; -import android.graphics.drawable.LayerDrawable; -import android.graphics.drawable.TransitionDrawable; -import android.hardware.Camera.PictureCallback; -import android.hardware.Camera.Size; -import android.location.Location; -import android.location.LocationManager; -import android.location.LocationProvider; -import android.media.AudioManager; -import android.media.MediaPlayer; -import android.media.ToneGenerator; -import android.net.Uri; -import android.os.Bundle; -import android.os.Debug; -import android.os.Environment; -import android.os.Handler; -import android.os.Message; -import android.os.SystemClock; -import android.preference.PreferenceManager; -import android.provider.MediaStore; -import android.text.format.DateFormat; -import android.util.Config; -import android.util.Log; -import android.view.KeyEvent; -import android.view.Menu; -import android.view.MenuItem; -import android.view.MenuItem.OnMenuItemClickListener; -import android.view.OrientationEventListener; -import android.view.SurfaceHolder; -import android.view.View; -import android.view.ViewGroup; -import android.view.ViewGroup.LayoutParams; -import android.view.Window; -import android.view.WindowManager; -import android.view.animation.AlphaAnimation; -import android.view.animation.Animation; -import android.view.animation.AnimationUtils; -import android.widget.ImageView; -import android.widget.Toast; - -public class Camera extends Activity implements View.OnClickListener, - ShutterButton.OnShutterButtonListener, SurfaceHolder.Callback { - - private static final String TAG = "camera"; - - private static final boolean DEBUG = false; - private static final boolean DEBUG_TIME_OPERATIONS = DEBUG && false; - - private static final int CROP_MSG = 1; - private static final int KEEP = 2; - private static final int RESTART_PREVIEW = 3; - private static final int CLEAR_SCREEN_DELAY = 4; - - private static final int SCREEN_DELAY = 2 * 60 * 1000; - private static final int FOCUS_BEEP_VOLUME = 100; - - public static final int MENU_SWITCH_TO_VIDEO = 0; - public static final int MENU_SWITCH_TO_CAMERA = 1; - public static final int MENU_FLASH_SETTING = 2; - public static final int MENU_FLASH_AUTO = 3; - public static final int MENU_FLASH_ON = 4; - public static final int MENU_FLASH_OFF = 5; - public static final int MENU_SETTINGS = 6; - public static final int MENU_GALLERY_PHOTOS = 7; - public static final int MENU_GALLERY_VIDEOS = 8; - public static final int MENU_SAVE_SELECT_PHOTOS = 30; - public static final int MENU_SAVE_NEW_PHOTO = 31; - public static final int MENU_SAVE_GALLERY_PHOTO = 34; - public static final int MENU_SAVE_GALLERY_VIDEO_PHOTO = 35; - public static final int MENU_SAVE_CAMERA_DONE = 36; - public static final int MENU_SAVE_CAMERA_VIDEO_DONE = 37; - - private Toast mToast; - private OrientationEventListener mOrientationListener; - private int mLastOrientation = OrientationEventListener.ORIENTATION_UNKNOWN; - private SharedPreferences mPreferences; - - private static final int IDLE = 1; - private static final int SNAPSHOT_IN_PROGRESS = 2; - private static final int SNAPSHOT_COMPLETED = 3; - - private int mStatus = IDLE; - private static final String sTempCropFilename = "crop-temp"; - - private android.hardware.Camera mCameraDevice; - private android.hardware.Camera.Parameters mParameters; - private VideoPreview mSurfaceView; - private SurfaceHolder mSurfaceHolder = null; - private View mBlackout = null; - - private int mOriginalViewFinderWidth, mOriginalViewFinderHeight; - private int mViewFinderWidth, mViewFinderHeight; - private boolean mPreviewing = false; - - private MediaPlayer mClickSound; - - private Capturer mCaptureObject; - private ImageCapture mImageCapture = null; - - private boolean mPausing = false; - - private boolean mIsFocusing = false; - private boolean mIsFocused = false; - private boolean mIsFocusButtonPressed = false; - private boolean mCaptureOnFocus = false; - - private static ContentResolver mContentResolver; - private boolean mDidRegister = false; - - private ArrayList<MenuItem> mGalleryItems = new ArrayList<MenuItem>(); - - private boolean mMenuSelectionMade; - - private ImageView mLastPictureButton; - private LayerDrawable mVignette; - private Animation mShowLastPictureButtonAnimation = new AlphaAnimation(0F, 1F); - private boolean mShouldShowLastPictureButton; - private TransitionDrawable mThumbnailTransition; - private Drawable[] mThumbnails; - private boolean mShouldTransitionThumbnails; - private Uri mLastPictureUri; - private Bitmap mLastPictureThumb; - private LocationManager mLocationManager = null; - - private ShutterButton mShutterButton; - - private Animation mFocusBlinkAnimation; - private View mFocusIndicator; - private ToneGenerator mFocusToneGenerator; - - - private ShutterCallback mShutterCallback = new ShutterCallback(); - private RawPictureCallback mRawPictureCallback = new RawPictureCallback(); - private AutoFocusCallback mAutoFocusCallback = new AutoFocusCallback(); - private long mShutterPressTime; - private int mPicturesRemaining; - - private boolean mKeepAndRestartPreview; - - // mPostCaptureAlert is non-null only if isImageCaptureIntent() is true. - private View mPostCaptureAlert; - - - private Handler mHandler = new MainHandler(); - private ProgressDialog mSavingProgress; - - private interface Capturer { - Uri getLastCaptureUri(); - void onSnap(); - void dismissFreezeFrame(boolean keep); - void cancelSave(); - void cancelAutoDismiss(); - void setDone(boolean wait); - } - - private void cancelSavingNotification() { - if (mToast != null) { - mToast.cancel(); - mToast = null; - } - } - - /** This Handler is used to post message back onto the main thread of the application */ - private class MainHandler extends Handler { - @Override - public void handleMessage(Message msg) { - switch (msg.what) { - case KEEP: { - keep(); - if (mSavingProgress != null) { - mSavingProgress.cancel(); - mSavingProgress = null; - } - - mKeepAndRestartPreview = true; - - if (msg.obj != null) { - mHandler.post((Runnable)msg.obj); - } - break; - } - - case RESTART_PREVIEW: { - if (mStatus == SNAPSHOT_IN_PROGRESS) { - // We are still in the processing of taking the picture, wait. - // This is is strange. Why are we polling? - // TODO remove polling - mHandler.sendEmptyMessageDelayed(RESTART_PREVIEW, 100); - } else if (mStatus == SNAPSHOT_COMPLETED){ - mCaptureObject.dismissFreezeFrame(true); - hidePostCaptureAlert(); - } - break; - } - - case CLEAR_SCREEN_DELAY: { - getWindow().clearFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON); - break; - } - } - } - }; - - LocationListener [] mLocationListeners = new LocationListener[] { - new LocationListener(LocationManager.GPS_PROVIDER), - new LocationListener(LocationManager.NETWORK_PROVIDER) - }; - - - private final BroadcastReceiver mReceiver = new BroadcastReceiver() { - @Override - public void onReceive(Context context, Intent intent) { - String action = intent.getAction(); - if (action.equals(Intent.ACTION_MEDIA_MOUNTED)) { - // SD card available - updateStorageHint(); - } else if (action.equals(Intent.ACTION_MEDIA_UNMOUNTED) || - action.equals(Intent.ACTION_MEDIA_CHECKING)) { - // SD card unavailable - mPicturesRemaining = MenuHelper.NO_STORAGE_ERROR; - updateStorageHint(mPicturesRemaining); - } else if (action.equals(Intent.ACTION_MEDIA_SCANNER_STARTED)) { - Toast.makeText(Camera.this, getResources().getString(R.string.wait), 5000); - } else if (action.equals(Intent.ACTION_MEDIA_SCANNER_FINISHED)) { - updateStorageHint(); - } - } - }; - - private class LocationListener implements android.location.LocationListener { - Location mLastLocation; - boolean mValid = false; - String mProvider; - - public LocationListener(String provider) { - mProvider = provider; - mLastLocation = new Location(mProvider); - } - - public void onLocationChanged(Location newLocation) { - if (newLocation.getLatitude() == 0.0 && newLocation.getLongitude() == 0.0) { - // Hack to filter out 0.0,0.0 locations - return; - } - mLastLocation.set(newLocation); - mValid = true; - } - - public void onProviderEnabled(String provider) { - } - - public void onProviderDisabled(String provider) { - mValid = false; - } - - public void onStatusChanged(String provider, int status, Bundle extras) { - if (status == LocationProvider.OUT_OF_SERVICE) { - mValid = false; - } - } - - public Location current() { - return mValid ? mLastLocation : null; - } - }; - - private long mRawPictureCallbackTime; - - private boolean mImageSavingItem = false; - - private final class ShutterCallback implements android.hardware.Camera.ShutterCallback { - public void onShutter() { - if (DEBUG_TIME_OPERATIONS) { - long now = System.currentTimeMillis(); - Log.v(TAG, "********** Total shutter lag " + (now - mShutterPressTime) + " ms"); - } - if (mClickSound != null) { - mClickSound.start(); - } - } - }; - - private final class RawPictureCallback implements PictureCallback { - public void onPictureTaken(byte [] rawData, android.hardware.Camera camera) { - if (Config.LOGV) - Log.v(TAG, "got RawPictureCallback..."); - mRawPictureCallbackTime = System.currentTimeMillis(); - mBlackout.setVisibility(View.GONE); - } - }; - - private final class JpegPictureCallback implements PictureCallback { - Location mLocation; - - public JpegPictureCallback(Location loc) { - mLocation = loc; - } - - public void onPictureTaken(byte [] jpegData, android.hardware.Camera camera) { - if (Config.LOGV) - Log.v(TAG, "got JpegPictureCallback..."); - - mImageCapture.storeImage(jpegData, camera, mLocation); - - mStatus = SNAPSHOT_COMPLETED; - - if (mKeepAndRestartPreview) { - long delay = 1500 - (System.currentTimeMillis() - mRawPictureCallbackTime); - mHandler.sendEmptyMessageDelayed(RESTART_PREVIEW, Math.max(delay, 0)); - } - } - }; - - private final class AutoFocusCallback implements android.hardware.Camera.AutoFocusCallback { - public void onAutoFocus(boolean focused, android.hardware.Camera camera) { - mIsFocusing = false; - mIsFocused = focused; - if (focused) { - if (mCaptureOnFocus && mCaptureObject != null) { - // No need to play the AF sound if we're about to play the shutter sound - mCaptureObject.onSnap(); - clearFocus(); - } else { - ToneGenerator tg = mFocusToneGenerator; - if (tg != null) - tg.startTone(ToneGenerator.TONE_PROP_BEEP2); - } - mCaptureOnFocus = false; - } - updateFocusIndicator(); - } - }; - - private class ImageCapture implements Capturer { - - private boolean mCancel = false; - private boolean mCapturing = false; - - private Uri mLastContentUri; - private ImageManager.IAddImage_cancelable mAddImageCancelable; - - Bitmap mCaptureOnlyBitmap; - - /** These member variables are used for various debug timings */ - private long mThreadTimeStart; - private long mThreadTimeEnd; - private long mWallTimeStart; - private long mWallTimeEnd; - - - public ImageCapture() { - } - - /** - * This method sets whether or not we are capturing a picture. This method must be called - * with the ImageCapture.this lock held. - */ - public void setCapturingLocked(boolean capturing) { - mCapturing = capturing; - } - - /* - * Tell the ImageCapture thread to exit when possible. - */ - public void setDone(boolean wait) { - } - - /* - * Tell the image capture thread to not "dismiss" the current - * capture when the current image is stored, etc. - */ - public void cancelAutoDismiss() { - } - - public void dismissFreezeFrame(boolean keep) { - if (keep) { - cancelSavingNotification(); - } else { - Toast.makeText(Camera.this, R.string.camera_tossing, Toast.LENGTH_SHORT).show(); - } - - if (mStatus == SNAPSHOT_IN_PROGRESS) { - // If we are still in the process of taking a picture, then just post a message. - mHandler.sendEmptyMessage(RESTART_PREVIEW); - } else { - restartPreview(); - } - } - - private void startTiming() { - mWallTimeStart = SystemClock.elapsedRealtime(); - mThreadTimeStart = Debug.threadCpuTimeNanos(); - } - - private void stopTiming() { - mThreadTimeEnd = Debug.threadCpuTimeNanos(); - mWallTimeEnd = SystemClock.elapsedRealtime(); - } - - private void storeImage(byte[] data, Location loc) { - try { - if (DEBUG_TIME_OPERATIONS) { - startTiming(); - } - long dateTaken = System.currentTimeMillis(); - String name = createName(dateTaken) + ".jpg"; - mLastContentUri = ImageManager.instance().addImage( - Camera.this, - mContentResolver, - name, - "", - dateTaken, - // location for the database goes here - loc, - 0, // the dsp will use the right orientation so don't "double set it" - ImageManager.CAMERA_IMAGE_BUCKET_NAME, - name); - - if (mLastContentUri == null) { - // this means we got an error - mCancel = true; - } - if (!mCancel) { - mAddImageCancelable = ImageManager.instance().storeImage(mLastContentUri, - Camera.this, mContentResolver, 0, null, data); - mAddImageCancelable.get(); - mAddImageCancelable = null; - } - - if (DEBUG_TIME_OPERATIONS) { - stopTiming(); - Log.d(TAG, "Storing image took " + (mWallTimeEnd - mWallTimeStart) + " ms. " + - "Thread time was " + ((mThreadTimeEnd - mThreadTimeStart) / 1000000) + - " ms."); - } - } catch (Exception ex) { - Log.e(TAG, "Exception while compressing image.", ex); - } - } - - public void storeImage(byte[] data, android.hardware.Camera camera, Location loc) { - boolean captureOnly = isImageCaptureIntent(); - - if (!captureOnly) { - storeImage(data, loc); - sendBroadcast(new Intent("com.android.camera.NEW_PICTURE", mLastContentUri)); - setLastPictureThumb(data, mCaptureObject.getLastCaptureUri()); - dismissFreezeFrame(true); - } else { - BitmapFactory.Options options = new BitmapFactory.Options(); - options.inSampleSize = 4; - - if (DEBUG_TIME_OPERATIONS) { - startTiming(); - } - - mCaptureOnlyBitmap = BitmapFactory.decodeByteArray(data, 0, data.length, options); - - if (DEBUG_TIME_OPERATIONS) { - stopTiming(); - Log.d(TAG, "Decoded mCaptureOnly bitmap (" + mCaptureOnlyBitmap.getWidth() + - "x" + mCaptureOnlyBitmap.getHeight() + " ) in " + - (mWallTimeEnd - mWallTimeStart) + " ms. Thread time was " + - ((mThreadTimeEnd - mThreadTimeStart) / 1000000) + " ms."); - } - - showPostCaptureAlert(); - cancelAutomaticPreviewRestart(); - } - - mCapturing = false; - if (mPausing) { - closeCamera(); - } - } - - /* - * Tells the image capture thread to abort the capture of the - * current image. - */ - public void cancelSave() { - if (!mCapturing) { - return; - } - - mCancel = true; - - if (mAddImageCancelable != null) { - mAddImageCancelable.cancel(); - } - dismissFreezeFrame(false); - } - - /* - * Initiate the capture of an image. - */ - public void initiate(boolean captureOnly) { - if (mCameraDevice == null) { - return; - } - - mCancel = false; - mCapturing = true; - - capture(captureOnly); - } - - public Uri getLastCaptureUri() { - return mLastContentUri; - } - - public Bitmap getLastBitmap() { - return mCaptureOnlyBitmap; - } - - private void capture(boolean captureOnly) { - mPreviewing = false; - mCaptureOnlyBitmap = null; - - final int latchedOrientation = ImageManager.roundOrientation(mLastOrientation + 90); - - Boolean recordLocation = mPreferences.getBoolean("pref_camera_recordlocation_key", false); - Location loc = recordLocation ? getCurrentLocation() : null; - // Quality 75 has visible artifacts, and quality 90 looks great but the files begin to - // get large. 85 is a good compromise between the two. - mParameters.set("jpeg-quality", 85); - mParameters.set("rotation", latchedOrientation); - - mParameters.remove("gps-latitude"); - mParameters.remove("gps-longitude"); - mParameters.remove("gps-altitude"); - mParameters.remove("gps-timestamp"); - - if (loc != null) { - double lat = loc.getLatitude(); - double lon = loc.getLongitude(); - boolean hasLatLon = (lat != 0.0d) || (lon != 0.0d); - - if (hasLatLon) { - String latString = String.valueOf(lat); - String lonString = String.valueOf(lon); - mParameters.set("gps-latitude", latString); - mParameters.set("gps-longitude", lonString); - if (loc.hasAltitude()) - mParameters.set("gps-altitude", String.valueOf(loc.getAltitude())); - if (loc.getTime() != 0) { - // Location.getTime() is UTC in milliseconds. - // gps-timestamp is UTC in seconds. - long utcTimeSeconds = loc.getTime() / 1000; - mParameters.set("gps-timestamp", String.valueOf(utcTimeSeconds)); - } - } else { - loc = null; - } - } - - - Size pictureSize = mParameters.getPictureSize(); - - // resize the SurfaceView to the aspect-ratio of the still image - // and so that we can see the full image that was taken - mSurfaceView.setAspectRatio(pictureSize.width, pictureSize.height); - - mCameraDevice.setParameters(mParameters); - - mCameraDevice.takePicture(mShutterCallback, mRawPictureCallback, new JpegPictureCallback(loc)); - // Prepare the sound to play in shutter callback. - if (mClickSound != null) { - mClickSound.seekTo(0); - } - - mBlackout.setVisibility(View.VISIBLE); - // Comment this out for now until we can decode the preview frame. This currently - // just animates black-on-black because the surface flinger blacks out the surface - // when the camera driver detaches the buffers. - if (false) { - Animation a = new android.view.animation.TranslateAnimation(mBlackout.getWidth(), 0 , 0, 0); - a.setDuration(450); - a.startNow(); - mBlackout.setAnimation(a); - } - } - - public void onSnap() { - // If we are already in the middle of taking a snapshot then we should just save - // the image after we have returned from the camera service. - if (mStatus == SNAPSHOT_IN_PROGRESS || mStatus == SNAPSHOT_COMPLETED) { - mKeepAndRestartPreview = true; - mHandler.sendEmptyMessage(RESTART_PREVIEW); - return; - } - - // Don't check the filesystem here, we can't afford the latency. Instead, check the - // cached value which was calculated when the preview was restarted. - if (DEBUG_TIME_OPERATIONS) mShutterPressTime = System.currentTimeMillis(); - if (mPicturesRemaining < 1) { - updateStorageHint(mPicturesRemaining); - return; - } - - mStatus = SNAPSHOT_IN_PROGRESS; - - mKeepAndRestartPreview = true; - - boolean getContentAction = isImageCaptureIntent(); - if (getContentAction) { - mImageCapture.initiate(true); - } else { - mImageCapture.initiate(false); - } - } - } - - private void setLastPictureThumb(byte[] data, Uri uri) { - BitmapFactory.Options options = new BitmapFactory.Options(); - options.inSampleSize = 16; - - Bitmap lastPictureThumb = BitmapFactory.decodeByteArray(data, 0, data.length, options); - - setLastPictureThumb(lastPictureThumb, uri); - } - - private void setLastPictureThumb(Bitmap lastPictureThumb, Uri uri) { - - final int PADDING_WIDTH = 2; - final int PADDING_HEIGHT = 2; - LayoutParams layoutParams = mLastPictureButton.getLayoutParams(); - // Make the mini-thumbnail size smaller than the button size so that the image corners - // don't peek out from the rounded corners of the frame_thumbnail graphic: - final int miniThumbWidth = layoutParams.width - 2 * PADDING_WIDTH; - final int miniThumbHeight = layoutParams.height - 2 * PADDING_HEIGHT; - - lastPictureThumb = ImageManager.extractMiniThumb(lastPictureThumb, - miniThumbWidth, miniThumbHeight); - - Drawable[] vignetteLayers = new Drawable[2]; - vignetteLayers[1] = getResources().getDrawable(R.drawable.frame_thumbnail); - if (mThumbnails == null) { - mThumbnails = new Drawable[2]; - mThumbnails[1] = new BitmapDrawable(lastPictureThumb); - vignetteLayers[0] = mThumbnails[1]; - } else { - mThumbnails[0] = mThumbnails[1]; - mThumbnails[1] = new BitmapDrawable(lastPictureThumb); - mThumbnailTransition = new TransitionDrawable(mThumbnails); - mShouldTransitionThumbnails = true; - vignetteLayers[0] = mThumbnailTransition; - } - - mVignette = new LayerDrawable(vignetteLayers); - mVignette.setLayerInset(0, PADDING_WIDTH, PADDING_HEIGHT, - PADDING_WIDTH, PADDING_HEIGHT); - mLastPictureButton.setImageDrawable(mVignette); - - if (mLastPictureButton.getVisibility() != View.VISIBLE) { - mShouldShowLastPictureButton = true; - } - mLastPictureThumb = lastPictureThumb; - mLastPictureUri = uri; - } - - static private String createName(long dateTaken) { - return DateFormat.format("yyyy-MM-dd kk.mm.ss", dateTaken).toString(); - } - - static public Matrix GetDisplayMatrix(Bitmap b, ImageView v) { - Matrix m = new Matrix(); - float bw = (float)b.getWidth(); - float bh = (float)b.getHeight(); - float vw = (float)v.getWidth(); - float vh = (float)v.getHeight(); - float scale, x, y; - if (bw*vh > vw*bh) { - scale = vh / bh; - x = (vw - scale*bw)*0.5F; - y = 0; - } else { - scale = vw / bw; - x = 0; - y = (vh - scale*bh)*0.5F; - } - m.setScale(scale, scale, 0.5F, 0.5F); - m.postTranslate(x, y); - return m; - } - - private void postAfterKeep(final Runnable r) { - Resources res = getResources(); - - if (mSavingProgress != null) { - mSavingProgress = ProgressDialog.show(this, res.getString(R.string.savingImage), - res.getString(R.string.wait)); - } - - Message msg = mHandler.obtainMessage(KEEP); - msg.obj = r; - msg.sendToTarget(); - } - - /** Called with the activity is first created. */ - @Override - public void onCreate(Bundle icicle) { - super.onCreate(icicle); - - // To reduce startup time, we open camera device in another thread. - // We make sure the camera is opened at the end of onCreate. - Thread openCameraThread = new Thread(new Runnable() { - public void run() { - mCameraDevice = android.hardware.Camera.open(); - } - }); - openCameraThread.start(); - - // To reduce startup time, we run some service creation code in another thread. - // We make sure the services are loaded at the end of onCreate(). - Thread loadServiceThread = new Thread(new Runnable() { - public void run() { - mLocationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE); - mOrientationListener = new OrientationEventListener(Camera.this) { - public void onOrientationChanged(int orientation) { - mLastOrientation = orientation; - } - }; - } - }); - loadServiceThread.start(); - - mPreferences = PreferenceManager.getDefaultSharedPreferences(this); - mContentResolver = getContentResolver(); - - Window win = getWindow(); - win.addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON); - setContentView(R.layout.camera); - - mSurfaceView = (VideoPreview) findViewById(R.id.camera_preview); - - // don't set mSurfaceHolder here. We have it set ONLY within - // surfaceCreated / surfaceDestroyed, other parts of the code - // assume that when it is set, the surface is also set. - SurfaceHolder holder = mSurfaceView.getHolder(); - holder.addCallback(this); - holder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS); - - mBlackout = findViewById(R.id.blackout); - - if (!isImageCaptureIntent()) { - mLastPictureButton = (ImageView) findViewById(R.id.last_picture_button); - mLastPictureButton.setOnClickListener(this); - loadLastThumb(); - } - - mShutterButton = (ShutterButton) findViewById(R.id.shutter_button); - mShutterButton.setOnShutterButtonListener(this); - - try { - mClickSound = new MediaPlayer(); - AssetFileDescriptor afd = getResources().openRawResourceFd(R.raw.camera_click); - - mClickSound.setDataSource(afd.getFileDescriptor(), - afd.getStartOffset(), - afd.getLength()); - - if (mClickSound != null) { - mClickSound.setAudioStreamType(AudioManager.STREAM_ALARM); - mClickSound.prepare(); - } - } catch (Exception ex) { - Log.w(TAG, "Couldn't create click sound", ex); - } - - mFocusIndicator = findViewById(R.id.focus_indicator); - mFocusBlinkAnimation = AnimationUtils.loadAnimation(this, R.anim.auto_focus_blink); - mFocusBlinkAnimation.setRepeatCount(Animation.INFINITE); - mFocusBlinkAnimation.setRepeatMode(Animation.REVERSE); - - // We load the post_picture_panel layout only if it is needed. - if (isImageCaptureIntent()) { - ViewGroup cameraView = (ViewGroup)findViewById(R.id.camera); - getLayoutInflater().inflate(R.layout.post_picture_panel, - cameraView); - mPostCaptureAlert = findViewById(R.id.post_picture_panel); - } - - // Make sure the services are loaded. - try { - openCameraThread.join(); - loadServiceThread.join(); - } catch (InterruptedException ex) { - } - - ImageManager.ensureOSXCompatibleFolder(); - } - - @Override - public void onStart() { - super.onStart(); - - Thread t = new Thread(new Runnable() { - public void run() { - final boolean storageOK = calculatePicturesRemaining() > 0; - - if (!storageOK) { - mHandler.post(new Runnable() { - public void run() { - updateStorageHint(mPicturesRemaining); - } - }); - } - } - }); - t.start(); - } - - public void onClick(View v) { - switch (v.getId()) { - case R.id.last_picture_button: - viewLastImage(); - break; - case R.id.attach: - doAttach(); - break; - case R.id.cancel: - doCancel(); - } - } - - private void doAttach() { - Bitmap bitmap = mImageCapture.getLastBitmap(); - mCaptureObject.setDone(true); - - String cropValue = null; - Uri saveUri = null; - - Bundle myExtras = getIntent().getExtras(); - if (myExtras != null) { - saveUri = (Uri) myExtras.getParcelable(MediaStore.EXTRA_OUTPUT); - cropValue = myExtras.getString("crop"); - } - - - if (cropValue == null) { - /* - * First handle the no crop case -- just return the value. If the caller - * specifies a "save uri" then write the data to it's stream. Otherwise, - * pass back a scaled down version of the bitmap directly in the extras. - */ - if (saveUri != null) { - OutputStream outputStream = null; - try { - outputStream = mContentResolver.openOutputStream(saveUri); - bitmap.compress(Bitmap.CompressFormat.JPEG, 75, outputStream); - outputStream.close(); - - setResult(RESULT_OK); - finish(); - } catch (IOException ex) { - // - } finally { - if (outputStream != null) { - try { - outputStream.close(); - } catch (IOException ex) { - - } - } - } - } else { - float scale = .5F; - Matrix m = new Matrix(); - m.setScale(scale, scale); - - bitmap = Bitmap.createBitmap(bitmap, 0, 0, - bitmap.getWidth(), - bitmap.getHeight(), - m, true); - - setResult(RESULT_OK, new Intent("inline-data").putExtra("data", bitmap)); - finish(); - } - } - else { - /* - * Save the image to a temp file and invoke the cropper - */ - Uri tempUri = null; - FileOutputStream tempStream = null; - try { - File path = getFileStreamPath(sTempCropFilename); - path.delete(); - tempStream = openFileOutput(sTempCropFilename, 0); - bitmap.compress(Bitmap.CompressFormat.JPEG, 75, tempStream); - tempStream.close(); - tempUri = Uri.fromFile(path); - } catch (FileNotFoundException ex) { - setResult(Activity.RESULT_CANCELED); - finish(); - return; - } catch (IOException ex) { - setResult(Activity.RESULT_CANCELED); - finish(); - return; - } finally { - if (tempStream != null) { - try { - tempStream.close(); - } catch (IOException ex) { - - } - } - } - - Bundle newExtras = new Bundle(); - if (cropValue.equals("circle")) - newExtras.putString("circleCrop", "true"); - if (saveUri != null) - newExtras.putParcelable(MediaStore.EXTRA_OUTPUT, saveUri); - else - newExtras.putBoolean("return-data", true); - - Intent cropIntent = new Intent(); - cropIntent.setClass(Camera.this, CropImage.class); - cropIntent.setData(tempUri); - cropIntent.putExtras(newExtras); - - startActivityForResult(cropIntent, CROP_MSG); - } - } - - private void doCancel() { - setResult(RESULT_CANCELED, new Intent()); - finish(); - } - - public void onShutterButtonFocus(ShutterButton button, boolean pressed) { - switch (button.getId()) { - case R.id.shutter_button: - doFocus(pressed); - break; - } - } - - public void onShutterButtonClick(ShutterButton button) { - switch (button.getId()) { - case R.id.shutter_button: - doSnap(false); - break; - } - } - - private void updateStorageHint() { - updateStorageHint(MenuHelper.calculatePicturesRemaining()); - } - - private OnScreenHint mStorageHint; - - private void updateStorageHint(int remaining) { - String noStorageText = null; - - if (remaining == MenuHelper.NO_STORAGE_ERROR) { - String state = Environment.getExternalStorageState(); - if (state == Environment.MEDIA_CHECKING) { - noStorageText = getString(R.string.preparing_sd); - } else { - noStorageText = getString(R.string.no_storage); - } - } else if (remaining < 1) { - noStorageText = getString(R.string.not_enough_space); - } - - if (noStorageText != null) { - if (mStorageHint == null) { - mStorageHint = OnScreenHint.makeText(this, noStorageText); - } else { - mStorageHint.setText(noStorageText); - } - mStorageHint.show(); - } else if (mStorageHint != null) { - mStorageHint.cancel(); - mStorageHint = null; - } - } - - @Override - public void onResume() { - super.onResume(); - mHandler.sendEmptyMessageDelayed(CLEAR_SCREEN_DELAY, SCREEN_DELAY); - - mPausing = false; - mOrientationListener.enable(); - - // install an intent filter to receive SD card related events. - IntentFilter intentFilter = new IntentFilter(Intent.ACTION_MEDIA_MOUNTED); - intentFilter.addAction(Intent.ACTION_MEDIA_UNMOUNTED); - intentFilter.addAction(Intent.ACTION_MEDIA_SCANNER_STARTED); - intentFilter.addAction(Intent.ACTION_MEDIA_SCANNER_FINISHED); - intentFilter.addAction(Intent.ACTION_MEDIA_CHECKING); - intentFilter.addDataScheme("file"); - registerReceiver(mReceiver, intentFilter); - mDidRegister = true; - - mImageCapture = new ImageCapture(); - - restartPreview(); - - if (mPreferences.getBoolean("pref_camera_recordlocation_key", false)) - startReceivingLocationUpdates(); - - updateFocusIndicator(); - - try { - mFocusToneGenerator = new ToneGenerator(AudioManager.STREAM_SYSTEM, FOCUS_BEEP_VOLUME); - } catch (RuntimeException e) { - Log.w(TAG, "Exception caught while creating local tone generator: " + e); - mFocusToneGenerator = null; - } - - mBlackout.setVisibility(View.GONE); - } - - private ImageManager.DataLocation dataLocation() { - return ImageManager.DataLocation.EXTERNAL; - } - - private static final int BUFSIZE = 4096; - - // Stores the thumbnail and URI of last-picture-taken to SD card, so we can - // load it the next time the Camera app starts. - private void storeLastThumb() { - if (mLastPictureUri != null && mLastPictureThumb != null) { - try { - FileOutputStream f = new FileOutputStream(ImageManager.getLastThumbPath()); - try { - BufferedOutputStream b = new BufferedOutputStream(f, BUFSIZE); - try { - DataOutputStream d = new DataOutputStream(b); - try { - d.writeUTF(mLastPictureUri.toString()); - mLastPictureThumb.compress(Bitmap.CompressFormat.PNG, 100, d); - } finally { - d.close(); - b = null; - f = null; - } - } finally { - if (b != null) { - b.close(); - f = null; - } - } - } finally { - if (f != null) { - f.close(); - } - } - } catch (IOException e) { - } - } - } - - // Loads the thumbnail and URI of last-picture-taken from SD card. - private void loadLastThumb() { - try { - FileInputStream f = new FileInputStream(ImageManager.getLastThumbPath()); - try { - BufferedInputStream b = new BufferedInputStream(f, BUFSIZE); - try { - DataInputStream d = new DataInputStream(b); - try { - Uri lastUri = Uri.parse(d.readUTF()); - Bitmap lastThumb = BitmapFactory.decodeStream(d); - setLastPictureThumb(lastThumb, lastUri); - } finally { - d.close(); - b = null; - f = null; - } - } finally { - if (b != null) { - b.close(); - f = null; - } - } - } finally { - if (f != null) { - f.close(); - } - } - } catch (IOException e) { - } - } - - @Override - public void onStop() { - keep(); - stopPreview(); - closeCamera(); - mHandler.removeMessages(CLEAR_SCREEN_DELAY); - super.onStop(); - } - - @Override - protected void onPause() { - keep(); - - mPausing = true; - mOrientationListener.disable(); - - stopPreview(); - - if (!mImageCapture.mCapturing) { - closeCamera(); - } - if (mDidRegister) { - unregisterReceiver(mReceiver); - mDidRegister = false; - } - stopReceivingLocationUpdates(); - - if (mFocusToneGenerator != null) { - mFocusToneGenerator.release(); - mFocusToneGenerator = null; - } - - storeLastThumb(); - if (mStorageHint != null) { - mStorageHint.cancel(); - mStorageHint = null; - } - super.onPause(); - } - - @Override - protected void onActivityResult(int requestCode, int resultCode, Intent data) { - switch (requestCode) { - case CROP_MSG: { - Intent intent = new Intent(); - if (data != null) { - Bundle extras = data.getExtras(); - if (extras != null) { - intent.putExtras(extras); - } - } - setResult(resultCode, intent); - finish(); - - File path = getFileStreamPath(sTempCropFilename); - path.delete(); - - break; - } - } - } - - private void autoFocus() { - updateFocusIndicator(); - if (!mIsFocusing) { - if (mCameraDevice != null) { - mIsFocusing = true; - mIsFocused = false; - mCameraDevice.autoFocus(mAutoFocusCallback); - } - } - } - - private void clearFocus() { - mIsFocusing = false; - mIsFocused = false; - mIsFocusButtonPressed = false; - } - - private void updateFocusIndicator() { - mHandler.post(new Runnable() { - public void run() { - if (mIsFocusing || !mIsFocusButtonPressed) { - mFocusIndicator.setVisibility(View.GONE); - mFocusIndicator.clearAnimation(); - } else { - if (mIsFocused) { - mFocusIndicator.setVisibility(View.VISIBLE); - mFocusIndicator.clearAnimation(); - } else { - mFocusIndicator.setVisibility(View.VISIBLE); - mFocusIndicator.startAnimation(mFocusBlinkAnimation); - } - } - } - }); - } - - - @Override - public boolean onKeyDown(int keyCode, KeyEvent event) { - mHandler.sendEmptyMessageDelayed(CLEAR_SCREEN_DELAY, SCREEN_DELAY); - getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON); - - switch (keyCode) { - case KeyEvent.KEYCODE_BACK: - if (mStatus == SNAPSHOT_IN_PROGRESS) { - // ignore backs while we're taking a picture - return true; - } - break; - case KeyEvent.KEYCODE_FOCUS: - if (event.getRepeatCount() == 0) { - doFocus(true); - } - return true; - case KeyEvent.KEYCODE_CAMERA: - if (event.getRepeatCount() == 0) { - doSnap(false); - } - return true; - case KeyEvent.KEYCODE_DPAD_CENTER: - // If we get a dpad center event without any focused view, move the - // focus to the shutter button and press it. - if (event.getRepeatCount() == 0) { - // Start auto-focus immediately to reduce shutter lag. After the shutter button - // gets the focus, doFocus() will be called again but it is fine. - doFocus(true); - if (mShutterButton.isInTouchMode()) { - mShutterButton.requestFocusFromTouch(); - } else { - mShutterButton.requestFocus(); - } - mShutterButton.setPressed(true); - } - return true; - } - - return super.onKeyDown(keyCode, event); - } - - @Override - public boolean onKeyUp(int keyCode, KeyEvent event) { - switch (keyCode) { - case KeyEvent.KEYCODE_FOCUS: - doFocus(false); - return true; - } - return super.onKeyUp(keyCode, event); - } - - private void doSnap(boolean needAutofocus) { - // The camera operates in focus-priority mode, meaning that we take a picture - // when focusing completes, and only if it completes successfully. If the user - // has half-pressed the shutter and already locked focus, we can take the photo - // right away, otherwise we need to start AF. - if (mIsFocused || !mPreviewing) { - // doesn't get set until the idler runs - if (mCaptureObject != null) { - mCaptureObject.onSnap(); - } - clearFocus(); - updateFocusIndicator(); - } else { - // Half pressing the shutter (i.e. the focus button event) will already have - // requested AF for us, so just request capture on focus here. If AF has - // already failed, we don't want to trigger it again. - mCaptureOnFocus = true; - if (needAutofocus && !mIsFocusButtonPressed) { - // But we do need to start AF for DPAD_CENTER - autoFocus(); - } - } - } - - private void doFocus(boolean pressed) { - if (pressed) { - mIsFocusButtonPressed = true; - mCaptureOnFocus = false; - if (mPreviewing) { - autoFocus(); - } else if (mCaptureObject != null) { - // Save and restart preview - mCaptureObject.onSnap(); - } - } else { - clearFocus(); - updateFocusIndicator(); - } - } - - public void surfaceChanged(SurfaceHolder holder, int format, int w, int h) { - // if we're creating the surface, start the preview as well. - boolean preview = holder.isCreating(); - setViewFinder(w, h, preview); - mCaptureObject = mImageCapture; - } - - public void surfaceCreated(SurfaceHolder holder) { - mSurfaceHolder = holder; - } - - public void surfaceDestroyed(SurfaceHolder holder) { - stopPreview(); - mSurfaceHolder = null; - } - - private void closeCamera() { - if (mCameraDevice != null) { - mCameraDevice.release(); - mCameraDevice = null; - mPreviewing = false; - } - } - - private boolean ensureCameraDevice() { - if (mCameraDevice == null) { - mCameraDevice = android.hardware.Camera.open(); - } - return mCameraDevice != null; - } - - private void restartPreview() { - VideoPreview surfaceView = mSurfaceView; - - // make sure the surfaceview fills the whole screen when previewing - surfaceView.setAspectRatio(VideoPreview.DONT_CARE); - setViewFinder(mOriginalViewFinderWidth, mOriginalViewFinderHeight, true); - mStatus = IDLE; - - // Calculate this in advance of each shot so we don't add to shutter latency. It's true that - // someone else could write to the SD card in the mean time and fill it, but that could have - // happened between the shutter press and saving the JPEG too. - // TODO: The best longterm solution is to write a reserve file of maximum JPEG size, always - // let the user take a picture, and delete that file if needed to save the new photo. - calculatePicturesRemaining(); - - if (mShouldShowLastPictureButton) { - mShouldShowLastPictureButton = false; - mLastPictureButton.setVisibility(View.VISIBLE); - Animation a = mShowLastPictureButtonAnimation; - a.setDuration(500); - mLastPictureButton.setAnimation(a); - } - - if (mShouldTransitionThumbnails) { - mShouldTransitionThumbnails = false; - mThumbnailTransition.startTransition(500); - } - } - - private void setViewFinder(int w, int h, boolean startPreview) { - if (mPausing) - return; - - if (mPreviewing && - w == mViewFinderWidth && - h == mViewFinderHeight) { - return; - } - - if (!ensureCameraDevice()) - return; - - if (mSurfaceHolder == null) - return; - - if (isFinishing()) - return; - - if (mPausing) - return; - - // remember view finder size - mViewFinderWidth = w; - mViewFinderHeight = h; - if (mOriginalViewFinderHeight == 0) { - mOriginalViewFinderWidth = w; - mOriginalViewFinderHeight = h; - } - - if (startPreview == false) - return; - - /* - * start the preview if we're asked to... - */ - - // we want to start the preview and we're previewing already, - // stop the preview first (this will blank the screen). - if (mPreviewing) - stopPreview(); - - // this blanks the screen if the surface changed, no-op otherwise - try { - mCameraDevice.setPreviewDisplay(mSurfaceHolder); - } catch (IOException exception) { - mCameraDevice.release(); - mCameraDevice = null; - // TODO: add more exception handling logic here - return; - } - - // request the preview size, the hardware may not honor it, - // if we depended on it we would have to query the size again - mParameters = mCameraDevice.getParameters(); - mParameters.setPreviewSize(w, h); - try { - mCameraDevice.setParameters(mParameters); - } catch (IllegalArgumentException e) { - // Ignore this error, it happens in the simulator. - } - - - final long wallTimeStart = SystemClock.elapsedRealtime(); - final long threadTimeStart = Debug.threadCpuTimeNanos(); - - final Object watchDogSync = new Object(); - Thread watchDog = new Thread(new Runnable() { - public void run() { - int next_warning = 1; - while (true) { - try { - synchronized (watchDogSync) { - watchDogSync.wait(1000); - } - } catch (InterruptedException ex) { - // - } - if (mPreviewing) - break; - - int delay = (int) (SystemClock.elapsedRealtime() - wallTimeStart) / 1000; - if (delay >= next_warning) { - if (delay < 120) { - Log.e(TAG, "preview hasn't started yet in " + delay + " seconds"); - } else { - Log.e(TAG, "preview hasn't started yet in " + (delay / 60) + " minutes"); - } - if (next_warning < 60) { - next_warning <<= 1; - if (next_warning == 16) { - next_warning = 15; - } - } else { - next_warning += 60; - } - } - } - } - }); - - watchDog.start(); - - if (Config.LOGV) - Log.v(TAG, "calling mCameraDevice.startPreview"); - try { - mCameraDevice.startPreview(); - } catch (Throwable e) { - // TODO: change Throwable to IOException once android.hardware.Camera.startPreview - // properly declares that it throws IOException. - } - mPreviewing = true; - - synchronized (watchDogSync) { - watchDogSync.notify(); - } - - long threadTimeEnd = Debug.threadCpuTimeNanos(); - long wallTimeEnd = SystemClock.elapsedRealtime(); - if ((wallTimeEnd - wallTimeStart) > 3000) { - Log.w(TAG, "startPreview() to " + (wallTimeEnd - wallTimeStart) + " ms. Thread time was" - + (threadTimeEnd - threadTimeStart) / 1000000 + " ms."); - } - } - - private void stopPreview() { - if (mCameraDevice != null && mPreviewing) { - mCameraDevice.stopPreview(); - } - mPreviewing = false; - } - - void gotoGallery() { - MenuHelper.gotoCameraImageGallery(this); - } - - private void viewLastImage() { - Uri targetUri = mLastPictureUri; - if (targetUri != null) { - targetUri = targetUri.buildUpon(). - appendQueryParameter("bucketId", ImageManager.CAMERA_IMAGE_BUCKET_ID).build(); - Intent intent = new Intent(Intent.ACTION_VIEW, targetUri); - intent.putExtra(MediaStore.EXTRA_SCREEN_ORIENTATION, - ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE); - intent.putExtra(MediaStore.EXTRA_FULL_SCREEN, true); - intent.putExtra(MediaStore.EXTRA_SHOW_ACTION_ICONS, true); - intent.putExtra("com.android.camera.ReviewMode", true); - - try { - startActivity(intent); - } catch (android.content.ActivityNotFoundException ex) { - // ignore. - } - } - } - - void keep() { - cancelSavingNotification(); - if (mCaptureObject != null) { - mCaptureObject.dismissFreezeFrame(true); - } - }; - - void toss() { - cancelSavingNotification(); - if (mCaptureObject != null) { - mCaptureObject.cancelSave(); - } - }; - - private ImageManager.IImage getImageForURI(Uri uri) { - ImageManager.IImageList list = ImageManager.instance().allImages( - this, - mContentResolver, - dataLocation(), - ImageManager.INCLUDE_IMAGES, - ImageManager.SORT_ASCENDING); - ImageManager.IImage image = list.getImageForUri(uri); - list.deactivate(); - return image; - } - - - private void startReceivingLocationUpdates() { - if (mLocationManager != null) { - try { - mLocationManager.requestLocationUpdates( - LocationManager.NETWORK_PROVIDER, - 1000, - 0F, - mLocationListeners[1]); - } catch (java.lang.SecurityException ex) { - // ok - } catch (IllegalArgumentException ex) { - if (Config.LOGD) { - Log.d(TAG, "provider does not exist " + ex.getMessage()); - } - } - try { - mLocationManager.requestLocationUpdates( - LocationManager.GPS_PROVIDER, - 1000, - 0F, - mLocationListeners[0]); - } catch (java.lang.SecurityException ex) { - // ok - } catch (IllegalArgumentException ex) { - if (Config.LOGD) { - Log.d(TAG, "provider does not exist " + ex.getMessage()); - } - } - } - } - - private void stopReceivingLocationUpdates() { - if (mLocationManager != null) { - for (int i = 0; i < mLocationListeners.length; i++) { - try { - mLocationManager.removeUpdates(mLocationListeners[i]); - } catch (Exception ex) { - // ok - } - } - } - } - - private Location getCurrentLocation() { - Location l = null; - - // go in best to worst order - for (int i = 0; i < mLocationListeners.length; i++) { - l = mLocationListeners[i].current(); - if (l != null) - break; - } - - return l; - } - - @Override - public void onOptionsMenuClosed(Menu menu) { - super.onOptionsMenuClosed(menu); - if (mImageSavingItem && !mMenuSelectionMade) { - // save the image if we presented the "advanced" menu - // which happens if "menu" is pressed while in - // SNAPSHOT_IN_PROGRESS or SNAPSHOT_COMPLETED modes - keep(); - mHandler.sendEmptyMessage(RESTART_PREVIEW); - } - } - - @Override - public boolean onMenuOpened(int featureId, Menu menu) { - if (featureId == Window.FEATURE_OPTIONS_PANEL) { - if (mStatus == SNAPSHOT_IN_PROGRESS) { - cancelAutomaticPreviewRestart(); - mMenuSelectionMade = false; - } - } - return super.onMenuOpened(featureId, menu); - } - - @Override - public boolean onPrepareOptionsMenu(Menu menu) { - super.onPrepareOptionsMenu(menu); - - mMenuSelectionMade = false; - - for (int i = 1; i <= MenuHelper.MENU_ITEM_MAX; i++) { - if (i != MenuHelper.GENERIC_ITEM) { - menu.setGroupVisible(i, false); - } - } - - if (mStatus == SNAPSHOT_IN_PROGRESS || mStatus == SNAPSHOT_COMPLETED) { - menu.setGroupVisible(MenuHelper.IMAGE_SAVING_ITEM, true); - mImageSavingItem = true; - } else { - menu.setGroupVisible(MenuHelper.IMAGE_MODE_ITEM, true); - mImageSavingItem = false; - } - - if (mCaptureObject != null) - mCaptureObject.cancelAutoDismiss(); - - return true; - } - - private void cancelAutomaticPreviewRestart() { - mKeepAndRestartPreview = false; - mHandler.removeMessages(RESTART_PREVIEW); - } - - private boolean isImageCaptureIntent() { - String action = getIntent().getAction(); - return (MediaStore.ACTION_IMAGE_CAPTURE.equals(action)); - } - - private void showPostCaptureAlert() { - if (isImageCaptureIntent()) { - mPostCaptureAlert.setVisibility(View.VISIBLE); - int[] pickIds = {R.id.attach, R.id.cancel}; - for(int id : pickIds) { - View view = mPostCaptureAlert.findViewById(id); - view.setOnClickListener(this); - Animation animation = new AlphaAnimation(0F, 1F); - animation.setDuration(500); - view.setAnimation(animation); - } - } - } - - private void hidePostCaptureAlert() { - if (isImageCaptureIntent()) { - mPostCaptureAlert.setVisibility(View.INVISIBLE); - } - } - - @Override - public boolean onCreateOptionsMenu(Menu menu) { - super.onCreateOptionsMenu(menu); - - if (isImageCaptureIntent()) { - // No options menu for attach mode. - return false; - } else { - addBaseMenuItems(menu); - MenuHelper.addImageMenuItems( - menu, - MenuHelper.INCLUDE_ALL & ~MenuHelper.INCLUDE_ROTATE_MENU, - true, - Camera.this, - mHandler, - - // Handler for deletion - new Runnable() { - public void run() { - if (mCaptureObject != null) { - mCaptureObject.cancelSave(); - Uri uri = mCaptureObject.getLastCaptureUri(); - if (uri != null) { - mContentResolver.delete(uri, null, null); - } - } - } - }, - new MenuHelper.MenuInvoker() { - public void run(final MenuHelper.MenuCallback cb) { - mMenuSelectionMade = true; - postAfterKeep(new Runnable() { - public void run() { - cb.run(mSelectedImageGetter.getCurrentImageUri(), mSelectedImageGetter.getCurrentImage()); - if (mCaptureObject != null) - mCaptureObject.dismissFreezeFrame(true); - } - }); - } - }); - - MenuItem gallery = menu.add(MenuHelper.IMAGE_SAVING_ITEM, MENU_SAVE_GALLERY_PHOTO, 0, R.string.camera_gallery_photos_text).setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - postAfterKeep(new Runnable() { - public void run() { - gotoGallery(); - } - }); - return true; - } - }); - gallery.setIcon(android.R.drawable.ic_menu_gallery); - } - return true; - } - - SelectedImageGetter mSelectedImageGetter = - new SelectedImageGetter() { - public ImageManager.IImage getCurrentImage() { - return getImageForURI(getCurrentImageUri()); - } - public Uri getCurrentImageUri() { - keep(); - return mCaptureObject.getLastCaptureUri(); - } - }; - - private int calculatePicturesRemaining() { - mPicturesRemaining = MenuHelper.calculatePicturesRemaining(); - return mPicturesRemaining; - } - - private void addBaseMenuItems(Menu menu) { - MenuHelper.addSwitchModeMenuItem(menu, this, true); - { - MenuItem gallery = menu.add(MenuHelper.IMAGE_MODE_ITEM, MENU_GALLERY_PHOTOS, 0, R.string.camera_gallery_photos_text).setOnMenuItemClickListener(new OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - gotoGallery(); - return true; - } - }); - gallery.setIcon(android.R.drawable.ic_menu_gallery); - mGalleryItems.add(gallery); - } - { - MenuItem gallery = menu.add(MenuHelper.VIDEO_MODE_ITEM, MENU_GALLERY_VIDEOS, 0, R.string.camera_gallery_photos_text).setOnMenuItemClickListener(new OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - gotoGallery(); - return true; - } - }); - gallery.setIcon(android.R.drawable.ic_menu_gallery); - mGalleryItems.add(gallery); - } - - MenuItem item = menu.add(MenuHelper.GENERIC_ITEM, MENU_SETTINGS, 0, R.string.settings).setOnMenuItemClickListener(new OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - Intent intent = new Intent(); - intent.setClass(Camera.this, CameraSettings.class); - startActivity(intent); - return true; - } - }); - item.setIcon(android.R.drawable.ic_menu_preferences); - } -} - diff --git a/src/com/android/camera/CameraButtonIntentReceiver.java b/src/com/android/camera/CameraButtonIntentReceiver.java deleted file mode 100644 index 5e4d3c3..0000000 --- a/src/com/android/camera/CameraButtonIntentReceiver.java +++ /dev/null @@ -1,41 +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.camera; - -import android.content.Context; -import android.content.Intent; -import android.content.BroadcastReceiver; -import android.view.KeyEvent; - -public class CameraButtonIntentReceiver extends BroadcastReceiver { - public CameraButtonIntentReceiver() { - } - - @Override - public void onReceive(Context context, Intent intent) { - KeyEvent event = (KeyEvent) intent.getParcelableExtra(Intent.EXTRA_KEY_EVENT); - - if (event == null) { - return; - } - - Intent i = new Intent(Intent.ACTION_MAIN); - i.setClass(context, Camera.class); - i.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); - context.startActivity(i); - } -} diff --git a/src/com/android/camera/CameraSettings.java b/src/com/android/camera/CameraSettings.java deleted file mode 100644 index 0145d64..0000000 --- a/src/com/android/camera/CameraSettings.java +++ /dev/null @@ -1,93 +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.camera; - -import android.content.SharedPreferences; -import android.content.SharedPreferences.OnSharedPreferenceChangeListener; -import android.os.Bundle; -import android.preference.ListPreference; -import android.preference.PreferenceActivity; - -/** - * CameraSettings - */ -public class CameraSettings extends PreferenceActivity - implements OnSharedPreferenceChangeListener -{ - public static final String KEY_VIDEO_QUALITY = "pref_camera_videoquality_key"; - public static final boolean DEFAULT_VIDEO_QUALITY_VALUE = true; - - private ListPreference mVideoQuality; - - public CameraSettings() - { - } - - /** Called with the activity is first created. */ - @Override - public void onCreate(Bundle icicle) - { - super.onCreate(icicle); - addPreferencesFromResource(R.xml.camera_preferences); - - initUI(); - } - - @Override - protected void onResume() { - super.onResume(); - updateVideoQuality(); - } - - private void initUI() { - mVideoQuality = (ListPreference) findPreference(KEY_VIDEO_QUALITY); - getPreferenceScreen().getSharedPreferences().registerOnSharedPreferenceChangeListener(this); - } - - private void updateVideoQuality() { - boolean vidQualityValue = getBooleanPreference(mVideoQuality, DEFAULT_VIDEO_QUALITY_VALUE); - int vidQualityIndex = vidQualityValue ? 1 : 0; - String[] vidQualities = - getResources().getStringArray(R.array.pref_camera_videoquality_entries); - String vidQuality = vidQualities[vidQualityIndex]; - mVideoQuality.setSummary(vidQuality); - } - - private static int getIntPreference(ListPreference preference, int defaultValue) { - String s = preference.getValue(); - int result = defaultValue; - try { - result = Integer.parseInt(s); - } catch (NumberFormatException e) { - // Ignore, result is already the default value. - } - return result; - } - - private boolean getBooleanPreference(ListPreference preference, boolean defaultValue) { - return getIntPreference(preference, defaultValue ? 1 : 0) != 0; - } - - public void onSharedPreferenceChanged(SharedPreferences sharedPreferences, - String key) { - if (key.equals(KEY_VIDEO_QUALITY)) { - updateVideoQuality(); - } - - } -} - diff --git a/src/com/android/camera/CameraThread.java b/src/com/android/camera/CameraThread.java deleted file mode 100644 index ba888bf..0000000 --- a/src/com/android/camera/CameraThread.java +++ /dev/null @@ -1,95 +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.camera; - -import android.os.Process; - -public class CameraThread { - private Thread mThread; - private int mTid; - private boolean mTidSet; - private boolean mFinished; - - synchronized private void setTid(int tid) { - mTid = tid; - mTidSet = true; - CameraThread.this.notifyAll(); - } - - synchronized private void setFinished() { - mFinished = true; - } - - public CameraThread(final Runnable r) { - Runnable wrapper = new Runnable() { - public void run() { - setTid(Process.myTid()); - try { - r.run(); - } finally { - setFinished(); - } - } - }; - - mThread = new Thread(wrapper); - } - - synchronized public void start() { - mThread.start(); - } - - synchronized public void setName(String name) { - mThread.setName(name); - } - - public void join() { - try { - mThread.join(); - } catch (InterruptedException ex) { - // ok? - } - } - - public long getId() { - return mThread.getId(); - } - - public Thread realThread() { - return mThread; - } - - synchronized public void setPriority(int androidOsPriority) { - while (!mTidSet) { - try { - CameraThread.this.wait(); - } catch (InterruptedException ex) { - // ok, try again - } - } - if (!mFinished) - Process.setThreadPriority(mTid, androidOsPriority); - } - - synchronized public void toBackground() { - setPriority(Process.THREAD_PRIORITY_BACKGROUND); - } - - synchronized public void toForeground() { - setPriority(Process.THREAD_PRIORITY_FOREGROUND); - } -} diff --git a/src/com/android/camera/CropImage.java b/src/com/android/camera/CropImage.java deleted file mode 100644 index cefaf83..0000000 --- a/src/com/android/camera/CropImage.java +++ /dev/null @@ -1,802 +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.camera; - -import android.app.Activity; -import android.app.ProgressDialog; -import android.content.ContentResolver; -import android.content.Context; -import android.content.Intent; -import android.graphics.Bitmap; -import android.graphics.Canvas; -import android.graphics.Matrix; -import android.graphics.Paint; -import android.graphics.PointF; -import android.graphics.PorterDuff; -import android.graphics.PorterDuffXfermode; -import android.graphics.Rect; -import android.graphics.RectF; -import android.graphics.Region; -import android.media.FaceDetector; -import android.net.Uri; -import android.os.Bundle; -import android.os.Handler; -import android.provider.MediaStore; -import android.util.AttributeSet; -import android.util.Config; -import android.util.Log; -import android.view.Menu; -import android.view.MotionEvent; -import android.view.View; -import android.view.Window; -import android.widget.Toast; - -import java.io.IOException; -import java.io.OutputStream; -import java.io.FileOutputStream; -import java.util.ArrayList; - -public class CropImage extends Activity { - private static final String TAG = "CropImage"; - private ProgressDialog mFaceDetectionDialog = null; - private ProgressDialog mSavingProgressDialog = null; - private ImageManager.IImageList mAllImages; - private Bitmap.CompressFormat mSaveFormat = Bitmap.CompressFormat.JPEG; // only used with mSaveUri - private Uri mSaveUri = null; - private int mAspectX, mAspectY; - private int mOutputX, mOutputY; - private boolean mDoFaceDetection = true; - private boolean mCircleCrop = false; - private boolean mWaitingToPick; - private boolean mScale; - private boolean mSaving; - private boolean mScaleUp = true; - - CropImageView mImageView; - ContentResolver mContentResolver; - - Bitmap mBitmap; - Bitmap mCroppedImage; - HighlightView mCrop; - - ImageManager.IImage mImage; - - public CropImage() { - } - - @Override - public boolean onCreateOptionsMenu(Menu menu) { - return super.onCreateOptionsMenu(menu); - } - - static public class CropImageView extends ImageViewTouchBase { - ArrayList<HighlightView> mHighlightViews = new ArrayList<HighlightView>(); - HighlightView mMotionHighlightView = null; - float mLastX, mLastY; - int mMotionEdge; - - public CropImageView(Context context) { - super(context); - } - - @Override - protected boolean doesScrolling() { - return false; - } - - @Override - protected void onLayout(boolean changed, int left, int top, int right, int bottom) { - super.onLayout(changed, left, top, right, bottom); - if (mBitmapDisplayed != null) { - for (HighlightView hv : mHighlightViews) { - hv.mMatrix.set(getImageMatrix()); - hv.invalidate(); - if (hv.mIsFocused) { - centerBasedOnHighlightView(hv); - } - } - } - } - - public CropImageView(Context context, AttributeSet attrs) { - super(context, attrs); - } - - protected void zoomTo(float scale, float centerX, float centerY) { - super.zoomTo(scale, centerX, centerY); - for (HighlightView hv : mHighlightViews) { - hv.mMatrix.set(getImageMatrix()); - hv.invalidate(); - } - } - - protected void zoomIn() { - super.zoomIn(); - for (HighlightView hv : mHighlightViews) { - hv.mMatrix.set(getImageMatrix()); - hv.invalidate(); - } - } - - protected void zoomOut() { - super.zoomOut(); - for (HighlightView hv : mHighlightViews) { - hv.mMatrix.set(getImageMatrix()); - hv.invalidate(); - } - } - - - @Override - protected boolean usePerfectFitBitmap() { - return false; - } - - @Override - protected void postTranslate(float deltaX, float deltaY) { - super.postTranslate(deltaX, deltaY); - for (int i = 0; i < mHighlightViews.size(); i++) { - HighlightView hv = mHighlightViews.get(i); - hv.mMatrix.postTranslate(deltaX, deltaY); - hv.invalidate(); - } - } - - private void recomputeFocus(MotionEvent event) { - for (int i = 0; i < mHighlightViews.size(); i++) { - HighlightView hv = mHighlightViews.get(i); - hv.setFocus(false); - hv.invalidate(); - } - - for (int i = 0; i < mHighlightViews.size(); i++) { - HighlightView hv = mHighlightViews.get(i); - int edge = hv.getHit(event.getX(), event.getY()); - if (edge != HighlightView.GROW_NONE) { - if (!hv.hasFocus()) { - hv.setFocus(true); - hv.invalidate(); - } - break; - } - } - invalidate(); - } - - @Override - public boolean onTouchEvent(MotionEvent event) { - CropImage cropImage = (CropImage)mContext; - if (cropImage.mSaving) - return false; - - switch (event.getAction()) { - case MotionEvent.ACTION_DOWN: - if (cropImage.mWaitingToPick) { - recomputeFocus(event); - } else { - for (int i = 0; i < mHighlightViews.size(); i++) { - HighlightView hv = mHighlightViews.get(i); - int edge = hv.getHit(event.getX(), event.getY()); - if (edge != HighlightView.GROW_NONE) { - mMotionEdge = edge; - mMotionHighlightView = hv; - mLastX = event.getX(); - mLastY = event.getY(); - mMotionHighlightView.setMode(edge == HighlightView.MOVE - ? HighlightView.ModifyMode.Move - : HighlightView.ModifyMode.Grow); - break; - } - } - } - break; - case MotionEvent.ACTION_UP: - if (cropImage.mWaitingToPick) { - for (int i = 0; i < mHighlightViews.size(); i++) { - HighlightView hv = mHighlightViews.get(i); - if (hv.hasFocus()) { - cropImage.mCrop = hv; - for (int j = 0; j < mHighlightViews.size(); j++) { - if (j == i) - continue; - mHighlightViews.get(j).setHidden(true); - } - centerBasedOnHighlightView(hv); - ((CropImage)mContext).mWaitingToPick = false; - return true; - } - } - } else if (mMotionHighlightView != null) { - centerBasedOnHighlightView(mMotionHighlightView); - mMotionHighlightView.setMode(HighlightView.ModifyMode.None); - } - mMotionHighlightView = null; - break; - case MotionEvent.ACTION_MOVE: - if (cropImage.mWaitingToPick) { - recomputeFocus(event); - } else if (mMotionHighlightView != null) { - mMotionHighlightView.handleMotion(mMotionEdge, event.getX()-mLastX, event.getY()-mLastY); - mLastX = event.getX(); - mLastY = event.getY(); - - if (true) { - // This section of code is optional. It has some user - // benefit in that moving the crop rectangle against - // the edge of the screen causes scrolling but it means - // that the crop rectangle is no longer fixed under - // the user's finger. - ensureVisible(mMotionHighlightView); - } - } - break; - } - - switch (event.getAction()) { - case MotionEvent.ACTION_UP: - center(true, true, true); - break; - case MotionEvent.ACTION_MOVE: - // if we're not zoomed then there's no point in even allowing - // the user to move the image around. This call to center - // puts it back to the normalized location (with false meaning - // don't animate). - if (getScale() == 1F) - center(true, true, false); - break; - } - - return true; - } - - private void ensureVisible(HighlightView hv) { - Rect r = hv.mDrawRect; - - int panDeltaX1 = Math.max(0, mLeft - r.left); - int panDeltaX2 = Math.min(0, mRight - r.right); - - int panDeltaY1 = Math.max(0, mTop - r.top); - int panDeltaY2 = Math.min(0, mBottom - r.bottom); - - int panDeltaX = panDeltaX1 != 0 ? panDeltaX1 : panDeltaX2; - int panDeltaY = panDeltaY1 != 0 ? panDeltaY1 : panDeltaY2; - - if (panDeltaX != 0 || panDeltaY != 0) - panBy(panDeltaX, panDeltaY); - } - - private void centerBasedOnHighlightView(HighlightView hv) { - Rect drawRect = hv.mDrawRect; - - float width = drawRect.width(); - float height = drawRect.height(); - - float thisWidth = getWidth(); - float thisHeight = getHeight(); - - float z1 = thisWidth / width * .6F; - float z2 = thisHeight / height * .6F; - - float zoom = Math.min(z1, z2); - zoom = zoom * this.getScale(); - zoom = Math.max(1F, zoom); - - if ((Math.abs(zoom - getScale()) / zoom) > .1) { - float [] coordinates = new float[] { hv.mCropRect.centerX(), hv.mCropRect.centerY() }; - getImageMatrix().mapPoints(coordinates); - zoomTo(zoom, coordinates[0], coordinates[1], 300F); - } - - ensureVisible(hv); - } - - @Override - protected void onDraw(Canvas canvas) { - super.onDraw(canvas); - for (int i = 0; i < mHighlightViews.size(); i++) { - mHighlightViews.get(i).draw(canvas); - } - } - - public HighlightView get(int i) { - return mHighlightViews.get(i); - } - - public int size() { - return mHighlightViews.size(); - } - - public void add(HighlightView hv) { - mHighlightViews.add(hv); - invalidate(); - } - } - - private void fillCanvas(int width, int height, Canvas c) { - Paint paint = new Paint(); - paint.setColor(0x00000000); // pure alpha - paint.setStyle(android.graphics.Paint.Style.FILL); - paint.setAntiAlias(true); - paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.CLEAR)); - c.drawRect(0F, 0F, width, height, paint); - } - - @Override - public void onCreate(Bundle icicle) { - super.onCreate(icicle); - mContentResolver = getContentResolver(); - - requestWindowFeature(Window.FEATURE_NO_TITLE); - setContentView(R.layout.cropimage); - - mImageView = (CropImageView) findViewById(R.id.image); - - MenuHelper.showStorageToast(this); - - try { - android.content.Intent intent = getIntent(); - Bundle extras = intent.getExtras(); - if (Config.LOGV) - Log.v(TAG, "extras are " + extras); - if (extras != null) { - for (String s: extras.keySet()) { - if (Config.LOGV) - Log.v(TAG, "" + s + " >>> " + extras.get(s)); - } - if (extras.getString("circleCrop") != null) { - mCircleCrop = true; - mAspectX = 1; - mAspectY = 1; - } - mSaveUri = (Uri) extras.getParcelable(MediaStore.EXTRA_OUTPUT); - if (mSaveUri != null) { - String compressFormatString = extras.getString("outputFormat"); - if (compressFormatString != null) - mSaveFormat = Bitmap.CompressFormat.valueOf(compressFormatString); - } - mBitmap = (Bitmap) extras.getParcelable("data"); - mAspectX = extras.getInt("aspectX"); - mAspectY = extras.getInt("aspectY"); - mOutputX = extras.getInt("outputX"); - mOutputY = extras.getInt("outputY"); - mScale = extras.getBoolean("scale", true); - mScaleUp = extras.getBoolean("scaleUpIfNeeded", true); - mDoFaceDetection = extras.containsKey("noFaceDetection") ? !extras.getBoolean("noFaceDetection") : true; - } - - if (mBitmap == null) { - Uri target = intent.getData(); - mAllImages = ImageManager.makeImageList(target, CropImage.this, ImageManager.SORT_ASCENDING); - mImage = mAllImages.getImageForUri(target); - if(mImage != null) { - // don't read in really large bitmaps. max out at 1000. - // TODO when saving the resulting bitmap use the decode/crop/encode - // api so we don't lose any resolution - mBitmap = mImage.thumbBitmap(); - if (Config.LOGV) - Log.v(TAG, "thumbBitmap returned " + mBitmap); - } - } - - if (mBitmap == null) { - finish(); - return; - } - - mHandler.postDelayed(new Runnable() { - public void run() { - if (isFinishing()) { - return; - } - mFaceDetectionDialog = ProgressDialog.show(CropImage.this, - null, - getResources().getString(R.string.runningFaceDetection), - true, false); - mImageView.setImageBitmapResetBase(mBitmap, true, true); - if (mImageView.getScale() == 1F) - mImageView.center(true, true, false); - - new Thread(new Runnable() { - public void run() { - final Bitmap b = mImage != null ? mImage.fullSizeBitmap(500) : mBitmap; - if (Config.LOGV) - Log.v(TAG, "back from mImage.fullSizeBitmap(500) with bitmap of size " + b.getWidth() + " / " + b.getHeight()); - mHandler.post(new Runnable() { - public void run() { - if (b != mBitmap && b != null) { - mBitmap = b; - mImageView.setImageBitmapResetBase(b, true, false); - } - if (mImageView.getScale() == 1F) - mImageView.center(true, true, false); - - new Thread(mRunFaceDetection).start(); - } - }); - } - }).start(); - }}, 100); - } catch (Exception e) { - Log.e(TAG, "Failed to load bitmap", e); - finish(); - } - - findViewById(R.id.discard).setOnClickListener(new android.view.View.OnClickListener() { - public void onClick(View v) { - setResult(RESULT_CANCELED); - finish(); - } - }); - - findViewById(R.id.save).setOnClickListener(new android.view.View.OnClickListener() { - public void onClick(View v) { - // TODO this code needs to change to use the decode/crop/encode single - // step api so that we don't require that the whole (possibly large) bitmap - // doesn't have to be read into memory - mSaving = true; - if (mCroppedImage == null) { - if (mCrop == null) { - if (Config.LOGV) - Log.v(TAG, "no cropped image..."); - return; - } - - Rect r = mCrop.getCropRect(); - - int width = r.width(); - int height = r.height(); - - // if we're circle cropping we'll want alpha which is the third param here - mCroppedImage = Bitmap.createBitmap(width, height, - mCircleCrop ? - Bitmap.Config.ARGB_8888 : - Bitmap.Config.RGB_565); - Canvas c1 = new Canvas(mCroppedImage); - c1.drawBitmap(mBitmap, r, new Rect(0, 0, width, height), null); - - if (mCircleCrop) { - // OK, so what's all this about? - // Bitmaps are inherently rectangular but we want to return something - // that's basically a circle. So we fill in the area around the circle - // with alpha. Note the all important PortDuff.Mode.CLEAR. - Canvas c = new Canvas (mCroppedImage); - android.graphics.Path p = new android.graphics.Path(); - p.addCircle(width/2F, height/2F, width/2F, android.graphics.Path.Direction.CW); - c.clipPath(p, Region.Op.DIFFERENCE); - - fillCanvas(width, height, c); - } - } - - /* If the output is required to a specific size then scale or fill */ - if (mOutputX != 0 && mOutputY != 0) { - - if (mScale) { - - /* Scale the image to the required dimensions */ - mCroppedImage = ImageLoader.transform(new Matrix(), - mCroppedImage, mOutputX, mOutputY, mScaleUp); - } else { - - /* Don't scale the image crop it to the size requested. - * Create an new image with the cropped image in the center and - * the extra space filled. - */ - - /* Don't scale the image but instead fill it so it's the required dimension */ - Bitmap b = Bitmap.createBitmap(mOutputX, mOutputY, Bitmap.Config.RGB_565); - Canvas c1 = new Canvas(b); - - /* Draw the cropped bitmap in the center */ - Rect r = mCrop.getCropRect(); - int left = (mOutputX / 2) - (r.width() / 2); - int top = (mOutputY / 2) - (r.width() / 2); - c1.drawBitmap(mBitmap, r, new Rect(left, top, left - + r.width(), top + r.height()), null); - - /* Set the cropped bitmap as the new bitmap */ - mCroppedImage = b; - } - } - - Bundle myExtras = getIntent().getExtras(); - if (myExtras != null && (myExtras.getParcelable("data") != null || myExtras.getBoolean("return-data"))) { - Bundle extras = new Bundle(); - extras.putParcelable("data", mCroppedImage); - setResult(RESULT_OK, - (new Intent()).setAction("inline-data").putExtras(extras)); - finish(); - } else { - if (!isFinishing()) { - mSavingProgressDialog = ProgressDialog.show(CropImage.this, - null, - getResources().getString(R.string.savingImage), - true, true); - } - Runnable r = new Runnable() { - public void run() { - if (mSaveUri != null) { - OutputStream outputStream = null; - try { - String scheme = mSaveUri.getScheme(); - if (scheme.equals("file")) { - outputStream = new FileOutputStream(mSaveUri.toString().substring(scheme.length()+":/".length())); - } else { - outputStream = mContentResolver.openOutputStream(mSaveUri); - } - if (outputStream != null) - mCroppedImage.compress(mSaveFormat, 75, outputStream); - - } catch (IOException ex) { - if (Config.LOGV) - Log.v(TAG, "got IOException " + ex); - } finally { - if (outputStream != null) { - try { - outputStream.close(); - } catch (IOException ex) { - - } - } - } - Bundle extras = new Bundle(); - setResult(RESULT_OK, - (new Intent()) - .setAction(mSaveUri.toString()) - .putExtras(extras)); - } else { - Bundle extras = new Bundle(); - extras.putString("rect", mCrop.getCropRect().toString()); - - // here we decide whether to create a new image or - // modify the existing image - if (false) { - /* - // this is the "modify" case - ImageManager.IGetBoolean_cancelable cancelable = - mImage.saveImageContents(mCroppedImage, null, null, null, mImage.getDateTaken(), 0, false); - boolean didSave = cancelable.get(); - extras.putString("thumb1uri", mImage.thumbUri().toString()); - setResult(RESULT_OK, - (new Intent()).setAction(mImage.fullSizeImageUri().toString()) - .putExtras(extras)); - */ - } else { - // this is the "new image" case - java.io.File oldPath = new java.io.File(mImage.getDataPath()); - java.io.File directory = new java.io.File(oldPath.getParent()); - - int x = 0; - String fileName = oldPath.getName(); - fileName = fileName.substring(0, fileName.lastIndexOf(".")); - - while (true) { - x += 1; - String candidate = directory.toString() + "/" + fileName + "-" + x + ".jpg"; - if (Config.LOGV) - Log.v(TAG, "candidate is " + candidate); - boolean exists = (new java.io.File(candidate)).exists(); - if (!exists) - break; - } - - try { - Uri newUri = ImageManager.instance().addImage( - CropImage.this, - getContentResolver(), - mImage.getTitle(), - mImage.getDescription(), - mImage.getDateTaken(), - null, // TODO this null is going to cause us to lose the location (gps) - 0, // TODO this is going to cause the orientation to reset - directory.toString(), - fileName + "-" + x + ".jpg"); - - ImageManager.IAddImage_cancelable cancelable = ImageManager.instance().storeImage( - newUri, - CropImage.this, - getContentResolver(), - 0, // TODO fix this orientation - mCroppedImage, - null); - - cancelable.get(); - setResult(RESULT_OK, - (new Intent()).setAction(newUri.toString()) - .putExtras(extras)); - } catch (Exception ex) { - // basically ignore this or put up - // some ui saying we failed - } - } - } - finish(); - } - }; - Thread t = new Thread(r); - t.start(); - } - } - }); - } - - @Override - public void onResume() { - super.onResume(); - } - - Handler mHandler = new Handler(); - - Runnable mRunFaceDetection = new Runnable() { - float mScale = 1F; - RectF mUnion = null; - Matrix mImageMatrix; - FaceDetector.Face[] mFaces = new FaceDetector.Face[3]; - int mNumFaces; - - private void handleFace(FaceDetector.Face f) { - PointF midPoint = new PointF(); - - int r = ((int)(f.eyesDistance() * mScale)) * 2 ; - f.getMidPoint(midPoint); - midPoint.x *= mScale; - midPoint.y *= mScale; - - int midX = (int) midPoint.x; - int midY = (int) midPoint.y; - - HighlightView hv = makeHighlightView(); - - int width = mBitmap.getWidth(); - int height = mBitmap.getHeight(); - - Rect imageRect = new Rect(0, 0, width, height); - - RectF faceRect = new RectF(midX, midY, midX, midY); - faceRect.inset(-r, -r); - if (faceRect.left < 0) - faceRect.inset(-faceRect.left, -faceRect.left); - - if (faceRect.top < 0) - faceRect.inset(-faceRect.top, -faceRect.top); - - if (faceRect.right > imageRect.right) - faceRect.inset(faceRect.right - imageRect.right, faceRect.right - imageRect.right); - - if (faceRect.bottom > imageRect.bottom) - faceRect.inset(faceRect.bottom - imageRect.bottom, faceRect.bottom - imageRect.bottom); - - hv.setup(mImageMatrix, imageRect, faceRect, mCircleCrop, mAspectX != 0 && mAspectY != 0); - - if (mUnion == null) { - mUnion = new RectF(faceRect); - } else { - mUnion.union(faceRect); - } - - mImageView.add(hv); - } - - private HighlightView makeHighlightView() { - return new HighlightView(mImageView); - } - - private void makeDefault() { - HighlightView hv = makeHighlightView(); - - int width = mBitmap.getWidth(); - int height = mBitmap.getHeight(); - - Rect imageRect = new Rect(0, 0, width, height); - - // make the default size about 4/5 of the width or height - int cropWidth = Math.min(width, height) * 4 / 5; - int cropHeight = cropWidth; - - if (mAspectX != 0 && mAspectY != 0) { - if (mAspectX > mAspectY) { - cropHeight = cropWidth * mAspectY / mAspectX; -// Log.v(TAG, "adjusted cropHeight to " + cropHeight); - } else { - cropWidth = cropHeight * mAspectX / mAspectY; -// Log.v(TAG, "adjusted cropWidth to " + cropWidth); - } - } - - int x = (width - cropWidth) / 2; - int y = (height - cropHeight) / 2; - - RectF cropRect = new RectF(x, y, x + cropWidth, y + cropHeight); - hv.setup(mImageMatrix, imageRect, cropRect, mCircleCrop, mAspectX != 0 && mAspectY != 0); - mImageView.add(hv); - } - - private Bitmap prepareBitmap() { - if (mBitmap == null) - return null; - - // scale the image down for faster face detection - // 256 pixels wide is enough. - if (mBitmap.getWidth() > 256) { - mScale = 256.0F / (float) mBitmap.getWidth(); - } - Matrix matrix = new Matrix(); - matrix.setScale(mScale, mScale); - Bitmap faceBitmap = Bitmap.createBitmap(mBitmap, 0, 0, mBitmap - .getWidth(), mBitmap.getHeight(), matrix, true); - return faceBitmap; - } - - public void run() { - mImageMatrix = mImageView.getImageMatrix(); - Bitmap faceBitmap = prepareBitmap(); - - mScale = 1.0F / mScale; - if (faceBitmap != null && mDoFaceDetection) { - FaceDetector detector = new FaceDetector(faceBitmap.getWidth(), - faceBitmap.getHeight(), mFaces.length); - mNumFaces = detector.findFaces(faceBitmap, mFaces); - if (Config.LOGV) - Log.v(TAG, "numFaces is " + mNumFaces); - } - mHandler.post(new Runnable() { - public void run() { - mWaitingToPick = mNumFaces > 1; - if (mNumFaces > 0) { - for (int i = 0; i < mNumFaces; i++) { - handleFace(mFaces[i]); - } - } else { - makeDefault(); - } - mImageView.invalidate(); - if (mImageView.mHighlightViews.size() == 1) { - mCrop = mImageView.mHighlightViews.get(0); - mCrop.setFocus(true); - } - - closeProgressDialog(); - - if (mNumFaces > 1) { - Toast t = Toast.makeText(CropImage.this, R.string.multiface_crop_help, Toast.LENGTH_SHORT); - t.show(); - } - } - }); - - } - }; - - @Override - public void onStop() { - closeProgressDialog(); - super.onStop(); - if (mAllImages != null) - mAllImages.deactivate(); - } - - private synchronized void closeProgressDialog() { - if (mFaceDetectionDialog != null) { - mFaceDetectionDialog.dismiss(); - mFaceDetectionDialog = null; - } - if (mSavingProgressDialog != null) { - mSavingProgressDialog.dismiss(); - mSavingProgressDialog = null; - } - } -} diff --git a/src/com/android/camera/DrmWallpaper.java b/src/com/android/camera/DrmWallpaper.java deleted file mode 100644 index 10f33dc..0000000 --- a/src/com/android/camera/DrmWallpaper.java +++ /dev/null @@ -1,35 +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.camera; - - -import android.content.Intent; -import android.content.pm.PackageManager; -import android.util.Log; - - -/** - * Wallpaper picker for DRM images. This just redirects to the standard pick action. - */ -public class DrmWallpaper extends Wallpaper { - - protected void formatIntent(Intent intent) { - super.formatIntent(intent); - intent.putExtra("pick-drm", true); - } - -} diff --git a/src/com/android/camera/ErrorScreen.java b/src/com/android/camera/ErrorScreen.java deleted file mode 100644 index 1018eb7..0000000 --- a/src/com/android/camera/ErrorScreen.java +++ /dev/null @@ -1,95 +0,0 @@ -/* - * Copyright (C) 2006 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.camera; - -import android.content.Intent; -import android.app.Activity; -import android.os.Handler; -import android.os.SystemClock; -import android.os.Bundle; -import android.widget.TextView; - - -/** - * - */ -public class ErrorScreen extends Activity -{ - int mError; - boolean mLogoutOnExit; - boolean mReconnectOnExit; - Handler mHandler = new Handler(); - - Runnable mCloseScreenCallback = new Runnable() { - public void run() { - finish(); - } - }; - - @Override public void onCreate(Bundle icicle) { - super.onCreate(icicle); - - resolveIntent(); - - String errMsg = null; - - // PENDING: resourcify error messages! - - switch (mError) { - default: - errMsg = "You need to setup your Picassa Web account first."; - break; - } - - TextView tv = new TextView(this); - tv.setText(errMsg); - setContentView(tv); - } - - @Override public void onResume() { - super.onResume(); - - mHandler.postAtTime(mCloseScreenCallback, - SystemClock.uptimeMillis() + 5000); - - } - - @Override public void onStop() { - super.onStop(); - mHandler.removeCallbacks(mCloseScreenCallback); -// startNextActivity(); - } - - void resolveIntent() { - Intent intent = getIntent(); - mError = intent.getIntExtra("error", mError); - - mLogoutOnExit = intent.getBooleanExtra("logout", mLogoutOnExit); - mReconnectOnExit = intent.getBooleanExtra("reconnect", mReconnectOnExit); - } - -// void startNextActivity() { -// GTalkApp app = GTalkApp.getInstance(); -// -// if (mLogoutOnExit) { -// app.logout(); -// } -// else if (mReconnectOnExit) { -// app.showLogin(false); -// } -// } -} diff --git a/src/com/android/camera/ExifInterface.java b/src/com/android/camera/ExifInterface.java deleted file mode 100644 index 2db021a..0000000 --- a/src/com/android/camera/ExifInterface.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.camera; - -import java.util.HashMap; -import java.util.Iterator; - -import android.util.Config; -import android.util.Log; - -// Wrapper for native Exif library - -public class ExifInterface { - - private String mFilename; - - // Constants used for the Orientation Exif tag. - static final int ORIENTATION_UNDEFINED = 0; - static final int ORIENTATION_NORMAL = 1; - static final int ORIENTATION_FLIP_HORIZONTAL = 2; // left right reversed mirror - static final int ORIENTATION_ROTATE_180 = 3; - static final int ORIENTATION_FLIP_VERTICAL = 4; // upside down mirror - static final int ORIENTATION_TRANSPOSE = 5; // flipped about top-left <--> bottom-right axis - static final int ORIENTATION_ROTATE_90 = 6; // rotate 90 cw to right it - static final int ORIENTATION_TRANSVERSE = 7; // flipped about top-right <--> bottom-left axis - static final int ORIENTATION_ROTATE_270 = 8; // rotate 270 to right it - - // The Exif tag names - static final String TAG_ORIENTATION = "Orientation"; - static final String TAG_DATE_TIME_ORIGINAL = "DateTimeOriginal"; - static final String TAG_MAKE = "Make"; - static final String TAG_MODEL = "Model"; - static final String TAG_FLASH = "Flash"; - static final String TAG_IMAGE_WIDTH = "ImageWidth"; - static final String TAG_IMAGE_LENGTH = "ImageLength"; - - static final String TAG_GPS_LATITUDE = "GPSLatitude"; - static final String TAG_GPS_LONGITUDE = "GPSLongitude"; - - static final String TAG_GPS_LATITUDE_REF = "GPSLatitudeRef"; - static final String TAG_GPS_LONGITUDE_REF = "GPSLongitudeRef"; - - private boolean mSavedAttributes = false; - private boolean mHasThumbnail = false; - private HashMap<String, String> mCachedAttributes = null; - - static { - System.loadLibrary("exif"); - } - - public ExifInterface(String fileName) { - mFilename = fileName; - } - - /** - * Given a HashMap of Exif tags and associated values, an Exif section in the JPG file - * is created and loaded with the tag data. saveAttributes() is expensive because it involves - * copying all the JPG data from one file to another and deleting the old file and renaming the other. - * It's best to collect all the attributes to write and make a single call rather than multiple - * calls for each attribute. You must call "commitChanges()" at some point to commit the changes. - */ - public void saveAttributes(HashMap<String, String> attributes) { - // format of string passed to native C code: - // "attrCnt attr1=valueLen value1attr2=value2Len value2..." - // example: "4 attrPtr ImageLength=4 1024Model=6 FooImageWidth=4 1280Make=3 FOO" - StringBuilder sb = new StringBuilder(); - int size = attributes.size(); - if (attributes.containsKey("hasThumbnail")) { - --size; - } - sb.append(size + " "); - Iterator keyIterator = attributes.keySet().iterator(); - while (keyIterator.hasNext()) { - String key = (String)keyIterator.next(); - if (key.equals("hasThumbnail")) { - continue; // this is a fake attribute not saved as an exif tag - } - String val = (String)attributes.get(key); - sb.append(key + "="); - sb.append(val.length() + " "); - sb.append(val); - } - String s = sb.toString(); - if (android.util.Config.LOGV) - android.util.Log.v("camera", "saving exif data: " + s); - saveAttributesNative(mFilename, s); - mSavedAttributes = true; - } - - /** - * Returns a HashMap loaded with the Exif attributes of the file. The key is the standard - * tag name and the value is the tag's value: e.g. Model -> Nikon. Numeric values are - * returned as strings. - */ - public HashMap<String, String> getAttributes() { - if (mCachedAttributes != null) { - return mCachedAttributes; - } - // format of string passed from native C code: - // "attrCnt attr1=valueLen value1attr2=value2Len value2..." - // example: "4 attrPtr ImageLength=4 1024Model=6 FooImageWidth=4 1280Make=3 FOO" - mCachedAttributes = new HashMap<String, String>(); - - String attrStr = getAttributesNative(mFilename); - - // get count - int ptr = attrStr.indexOf(' '); - int count = Integer.parseInt(attrStr.substring(0, ptr)); - ++ptr; // skip past the space between item count and the rest of the attributes - - for (int i = 0; i < count; i++) { - // extract the attribute name - int equalPos = attrStr.indexOf('=', ptr); - String attrName = attrStr.substring(ptr, equalPos); - ptr = equalPos + 1; // skip past = - - // extract the attribute value length - int lenPos = attrStr.indexOf(' ', ptr); - int attrLen = Integer.parseInt(attrStr.substring(ptr, lenPos)); - ptr = lenPos + 1; // skip pas the space - - // extract the attribute value - String attrValue = attrStr.substring(ptr, ptr + attrLen); - ptr += attrLen; - - if (attrName.equals("hasThumbnail")) { - mHasThumbnail = attrValue.equalsIgnoreCase("true"); - } else { - mCachedAttributes.put(attrName, attrValue); - } - } - return mCachedAttributes; - } - - /** - * Given a numerical orientation, return a human-readable string describing the orientation. - */ - static public String orientationToString(int orientation) { - // TODO: this function needs to be localized and use string resource ids rather than strings - String orientationString; - switch (orientation) { - case ORIENTATION_NORMAL: orientationString = "Normal"; break; - case ORIENTATION_FLIP_HORIZONTAL: orientationString = "Flipped horizontal"; break; - case ORIENTATION_ROTATE_180: orientationString = "Rotated 180 degrees"; break; - case ORIENTATION_FLIP_VERTICAL: orientationString = "Upside down mirror"; break; - case ORIENTATION_TRANSPOSE: orientationString = "Transposed"; break; - case ORIENTATION_ROTATE_90: orientationString = "Rotated 90 degrees"; break; - case ORIENTATION_TRANSVERSE: orientationString = "Transversed"; break; - case ORIENTATION_ROTATE_270: orientationString = "Rotated 270 degrees"; break; - default: orientationString = "Undefined"; break; - } - return orientationString; - } - - /** - * Copies the thumbnail data out of the filename and puts it in the Exif data associated - * with the file used to create this object. You must call "commitChanges()" at some point - * to commit the changes. - */ - public boolean appendThumbnail(String thumbnailFileName) { - if (!mSavedAttributes) { - throw new RuntimeException("Must call saveAttributes before calling appendThumbnail"); - } - mHasThumbnail = appendThumbnailNative(mFilename, thumbnailFileName); - return mHasThumbnail; - } - - /** - * Saves the changes (added Exif tags, added thumbnail) to the JPG file. You have to call - * saveAttributes() before committing the changes. - */ - public void commitChanges() { - if (!mSavedAttributes) { - throw new RuntimeException("Must call saveAttributes before calling commitChanges"); - } - commitChangesNative(mFilename); - } - - public boolean hasThumbnail() { - if (!mSavedAttributes) { - getAttributes(); - } - return mHasThumbnail; - } - - public byte[] getThumbnail() { - return getThumbnailNative(mFilename); - } - - static public String convertRationalLatLonToDecimalString(String rationalString, String ref, boolean usePositiveNegative) { - try { - String [] parts = rationalString.split(","); - - String [] pair; - pair = parts[0].split("/"); - int degrees = (int) (Float.parseFloat(pair[0].trim()) / Float.parseFloat(pair[1].trim())); - - pair = parts[1].split("/"); - int minutes = (int) ((Float.parseFloat(pair[0].trim()) / Float.parseFloat(pair[1].trim()))); - - pair = parts[2].split("/"); - float seconds = Float.parseFloat(pair[0].trim()) / Float.parseFloat(pair[1].trim()); - - float result = degrees + (minutes/60F) + (seconds/(60F*60F)); - - String preliminaryResult = String.valueOf(result); - if (usePositiveNegative) { - String neg = (ref.equals("S") || ref.equals("E")) ? "-" : ""; - return neg + preliminaryResult; - } else { - return preliminaryResult + String.valueOf((char)186) + " " + ref; - } - } catch (Exception ex) { - // if for whatever reason we can't parse the lat long then return null - return null; - } - } - - static public String makeLatLongString(double d) { - d = Math.abs(d); - - int degrees = (int) d; - - double remainder = d - (double)degrees; - int minutes = (int) (remainder * 60D); - int seconds = (int) (((remainder * 60D) - minutes) * 60D * 1000D); // really seconds * 1000 - - String retVal = degrees + "/1," + minutes + "/1," + (int)seconds + "/1000"; - return retVal; - } - - static public String makeLatStringRef(double lat) { - return lat >= 0D ? "N" : "S"; - } - - static public String makeLonStringRef(double lon) { - return lon >= 0D ? "W" : "E"; - } - - private native boolean appendThumbnailNative(String fileName, String thumbnailFileName); - - private native void saveAttributesNative(String fileName, String compressedAttributes); - - private native String getAttributesNative(String fileName); - - private native void commitChangesNative(String fileName); - - private native byte[] getThumbnailNative(String fileName); -} diff --git a/src/com/android/camera/GalleryPicker.java b/src/com/android/camera/GalleryPicker.java deleted file mode 100644 index 9c687c8..0000000 --- a/src/com/android/camera/GalleryPicker.java +++ /dev/null @@ -1,728 +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.camera; - -import android.app.Activity; -import android.app.Dialog; -import android.app.ProgressDialog; -import android.content.BroadcastReceiver; -import android.content.Context; -import android.content.Intent; -import android.content.IntentFilter; -import android.content.SharedPreferences; -import android.content.res.Resources; -import android.graphics.Bitmap; -import android.graphics.Canvas; -import android.graphics.Matrix; -import android.graphics.Paint; -import android.graphics.Rect; -import android.graphics.drawable.Drawable; -import android.net.Uri; -import android.os.Bundle; -import android.os.Environment; -import android.os.Handler; -import android.os.StatFs; -import android.preference.PreferenceManager; -import android.provider.MediaStore.Images; -import android.util.Config; -import android.util.Log; -import android.util.SparseArray; -import android.view.ContextMenu; -import android.view.LayoutInflater; -import android.view.Menu; -import android.view.MenuItem; -import android.view.View; -import android.view.ViewGroup; -import android.view.MenuItem.OnMenuItemClickListener; -import android.widget.AdapterView; -import android.widget.BaseAdapter; -import android.widget.GridView; -import android.widget.TextView; -import android.widget.Toast; -import android.widget.AdapterView.AdapterContextMenuInfo; - -import java.util.ArrayList; -import java.util.HashMap; -import java.util.Map; - -public class GalleryPicker extends Activity { - static private final String TAG = "GalleryPicker"; - - private View mNoImagesView; - GridView mGridView; - Drawable mFrameGalleryMask; - Drawable mCellOutline; - Drawable mVideoOverlay; - - BroadcastReceiver mReceiver; - GalleryPickerAdapter mAdapter; - - Dialog mMediaScanningDialog; - - SharedPreferences mPrefs; - - boolean mPausing = false; - - private static long LOW_STORAGE_THRESHOLD = 1024 * 1024 * 2; - - public GalleryPicker() { - } - - private void rebake(boolean unmounted, boolean scanning) { - if (mMediaScanningDialog != null) { - mMediaScanningDialog.cancel(); - mMediaScanningDialog = null; - } - if (scanning) { - mMediaScanningDialog = ProgressDialog.show( - this, - null, - getResources().getString(R.string.wait), - true, - true); - } - if (mAdapter != null) { - mAdapter.notifyDataSetChanged(); - mAdapter.init(!unmounted && !scanning); - } - - if (!unmounted) { - // Warn the user if space is getting low - Thread t = new Thread(new Runnable() { - public void run() { - - // Check available space only if we are writable - if (ImageManager.hasStorage()) { - String storageDirectory = Environment.getExternalStorageDirectory().toString(); - StatFs stat = new StatFs(storageDirectory); - long remaining = (long)stat.getAvailableBlocks() * (long)stat.getBlockSize(); - if (remaining < LOW_STORAGE_THRESHOLD) { - - mHandler.post(new Runnable() { - public void run() { - Toast.makeText(GalleryPicker.this.getApplicationContext(), - R.string.not_enough_space, 5000).show(); - } - }); - } - } - } - }); - t.start(); - } - - // If we just have zero or one folder, open it. (We shouldn't have just one folder - // any more, but we can have zero folders.) - mNoImagesView.setVisibility(View.GONE); - if (!scanning) { - int numItems = mAdapter.mItems.size(); - if (numItems == 0) { - mNoImagesView.setVisibility(View.VISIBLE); - } else if (numItems == 1) { - mAdapter.mItems.get(0).launch(this); - finish(); - return; - } - } - } - - @Override - public void onCreate(Bundle icicle) { - super.onCreate(icicle); - - mPrefs = PreferenceManager.getDefaultSharedPreferences(this); - - setContentView(R.layout.gallerypicker); - - mNoImagesView = findViewById(R.id.no_images); - mGridView = (GridView) findViewById(R.id.albums); - mGridView.setSelector(android.R.color.transparent); - - mReceiver = new BroadcastReceiver() { - - @Override - public void onReceive(Context context, Intent intent) { - if (Config.LOGV) Log.v(TAG, "onReceiveIntent " + intent.getAction()); - String action = intent.getAction(); - if (action.equals(Intent.ACTION_MEDIA_MOUNTED)) { - // SD card available - // TODO put up a "please wait" message - // TODO also listen for the media scanner finished message - } else if (action.equals(Intent.ACTION_MEDIA_UNMOUNTED)) { - // SD card unavailable - if (Config.LOGV) Log.v(TAG, "sd card no longer available"); - Toast.makeText(GalleryPicker.this, getResources().getString(R.string.wait), 5000); - rebake(true, false); - } else if (action.equals(Intent.ACTION_MEDIA_SCANNER_STARTED)) { - Toast.makeText(GalleryPicker.this, getResources().getString(R.string.wait), 5000); - rebake(false, true); - } else if (action.equals(Intent.ACTION_MEDIA_SCANNER_FINISHED)) { - if (Config.LOGV) - Log.v(TAG, "rebake because of ACTION_MEDIA_SCANNER_FINISHED"); - rebake(false, false); - } else if (action.equals(Intent.ACTION_MEDIA_EJECT)) { - if (Config.LOGV) - Log.v(TAG, "rebake because of ACTION_MEDIA_EJECT"); - rebake(true, false); - } - } - }; - - mGridView.setOnItemClickListener(new AdapterView.OnItemClickListener() { - public void onItemClick(AdapterView<?> parent, View view, int position, long id) { - launchFolderGallery(position); - } - }); - mGridView.setOnCreateContextMenuListener(new View.OnCreateContextMenuListener() { - public void onCreateContextMenu(ContextMenu menu, View v, final ContextMenu.ContextMenuInfo menuInfo) { - int position = ((AdapterContextMenuInfo)menuInfo).position; - menu.setHeaderTitle(mAdapter.baseTitleForPosition(position)); - if ((mAdapter.getIncludeMediaTypes(position) & ImageManager.INCLUDE_IMAGES) != 0) { - menu.add(0, 207, 0, R.string.slide_show) - .setOnMenuItemClickListener(new OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - AdapterView.AdapterContextMenuInfo info = (AdapterView.AdapterContextMenuInfo)menuInfo; - int position = info.position; - - Uri targetUri; - synchronized (mAdapter.mItems) { - if (position < 0 || position >= mAdapter.mItems.size()) { - return true; - } - // the mFirstImageUris list includes the "all" uri - targetUri = mAdapter.mItems.get(position).mFirstImageUri; - } - if (targetUri != null && position > 0) { - targetUri = targetUri.buildUpon().appendQueryParameter("bucketId", - mAdapter.mItems.get(info.position).mId).build(); - } - // Log.v(TAG, "URI to launch slideshow " + targetUri); - Intent intent = new Intent(Intent.ACTION_VIEW, targetUri); - intent.putExtra("slideshow", true); - startActivity(intent); - return true; - } - }); - } - menu.add(0, 208, 0, R.string.view) - .setOnMenuItemClickListener(new OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - AdapterView.AdapterContextMenuInfo info = (AdapterView.AdapterContextMenuInfo)menuInfo; - launchFolderGallery(info.position); - return true; - } - }); - } - }); - - ImageManager.ensureOSXCompatibleFolder(); - } - - private void launchFolderGallery(int position) { - mAdapter.mItems.get(position).launch(this); - } - - class ItemInfo { - Bitmap bitmap; - int count; - } - - static class Item implements Comparable<Item>{ - // The type is also used as the sort order - public final static int TYPE_NONE = -1; - public final static int TYPE_ALL_IMAGES = 0; - public final static int TYPE_ALL_VIDEOS = 1; - public final static int TYPE_CAMERA_IMAGES = 2; - public final static int TYPE_CAMERA_VIDEOS = 3; - public final static int TYPE_NORMAL_FOLDERS = 4; - - public int mType; - public String mId; - public String mName; - public Uri mFirstImageUri; - public ItemInfo mThumb; - - public Item(int type, String id, String name) { - mType = type; - mId = id; - mName = name; - } - - public boolean needsBucketId() { - return mType >= TYPE_CAMERA_IMAGES; - } - - public void launch(Activity activity) { - android.net.Uri uri = Images.Media.INTERNAL_CONTENT_URI; - if (needsBucketId()) { - uri = uri.buildUpon().appendQueryParameter("bucketId",mId).build(); - } - Intent intent = new Intent(Intent.ACTION_VIEW, uri); - intent.putExtra("windowTitle", mName); - intent.putExtra("mediaTypes", getIncludeMediaTypes()); - activity.startActivity(intent); - } - - public int getIncludeMediaTypes() { - return convertItemTypeToIncludedMediaType(mType); - } - - public static int convertItemTypeToIncludedMediaType(int itemType) { - switch (itemType) { - case TYPE_ALL_IMAGES: - case TYPE_CAMERA_IMAGES: - return ImageManager.INCLUDE_IMAGES; - case TYPE_ALL_VIDEOS: - case TYPE_CAMERA_VIDEOS: - return ImageManager.INCLUDE_VIDEOS; - case TYPE_NORMAL_FOLDERS: - default: - return ImageManager.INCLUDE_IMAGES | ImageManager.INCLUDE_VIDEOS; - } - } - - public int getOverlay() { - switch (mType) { - case TYPE_ALL_IMAGES: - case TYPE_CAMERA_IMAGES: - return R.drawable.frame_overlay_gallery_camera; - case TYPE_ALL_VIDEOS: - case TYPE_CAMERA_VIDEOS: - return R.drawable.frame_overlay_gallery_video; - case TYPE_NORMAL_FOLDERS: - return R.drawable.frame_overlay_gallery_folder; - default: - return -1; - } - } - - // sort based on the sort order, then the case-insensitive display name, then the id. - public int compareTo(Item other) { - int x = mType - other.mType; - if (x == 0) { - x = mName.compareToIgnoreCase(other.mName); - if (x == 0) { - x = mId.compareTo(other.mId); - } - } - return x; - } - } - - class GalleryPickerAdapter extends BaseAdapter { - ArrayList<Item> mItems = new ArrayList<Item>(); - - boolean mDone = false; - CameraThread mWorkerThread; - - public void init(boolean assumeMounted) { - mItems.clear(); - - ImageManager.IImageList images; - if (assumeMounted) { - images = ImageManager.instance().allImages( - GalleryPicker.this, - getContentResolver(), - ImageManager.DataLocation.ALL, - ImageManager.INCLUDE_IMAGES | ImageManager.INCLUDE_VIDEOS, - ImageManager.SORT_DESCENDING); - } else { - images = ImageManager.instance().emptyImageList(); - } - - if (mWorkerThread != null) { - try { - mDone = true; - if (Config.LOGV) - Log.v(TAG, "about to call join on thread " + mWorkerThread.getId()); - mWorkerThread.join(); - } finally { - mWorkerThread = null; - } - } - - String cameraItem = ImageManager.CAMERA_IMAGE_BUCKET_ID; - final HashMap<String, String> hashMap = images.getBucketIds(); - String cameraBucketId = null; - for (Map.Entry<String, String> entry: hashMap.entrySet()) { - String key = entry.getKey(); - if (key == null) { - continue; - } - if (key.equals(cameraItem)) { - cameraBucketId = key; - } else { - mItems.add(new Item(Item.TYPE_NORMAL_FOLDERS, key, entry.getValue())); - } - } - images.deactivate(); - notifyDataSetInvalidated(); - - // Conditionally add all-images and all-videos folders. - addBucket(Item.TYPE_ALL_IMAGES, null, - Item.TYPE_CAMERA_IMAGES, cameraBucketId, R.string.all_images); - addBucket(Item.TYPE_ALL_VIDEOS, null, - Item.TYPE_CAMERA_VIDEOS, cameraBucketId, R.string.all_videos); - - if (cameraBucketId != null) { - addBucket(Item.TYPE_CAMERA_IMAGES, cameraBucketId, - R.string.gallery_camera_bucket_name); - addBucket(Item.TYPE_CAMERA_VIDEOS, cameraBucketId, - R.string.gallery_camera_videos_bucket_name); - } - - java.util.Collections.sort(mItems); - - mDone = false; - mWorkerThread = new CameraThread(new Runnable() { - public void run() { - try { - // no images, nothing to do - if (mItems.size() == 0) - return; - - for (int i = 0; i < mItems.size() && !mDone; i++) { - final Item item = mItems.get(i); - ImageManager.IImageList list = createImageList( - item.getIncludeMediaTypes(), item.mId); - try { - if (mPausing) { - break; - } - if (list.getCount() > 0) - item.mFirstImageUri = list.getImageAt(0).fullSizeImageUri(); - - final Bitmap b = makeMiniThumbBitmap(142, 142, list); - final int pos = i; - final int count = list.getCount(); - final Thread currentThread = Thread.currentThread(); - mHandler.post(new Runnable() { - public void run() { - if (mPausing || currentThread != mWorkerThread.realThread()) { - if (b != null) { - b.recycle(); - } - return; - } - - ItemInfo info = new ItemInfo(); - info.bitmap = b; - info.count = count; - item.mThumb = info; - - final GridView grid = GalleryPicker.this.mGridView; - final int firstVisible = grid.getFirstVisiblePosition(); - - // Minor optimization -- only notify if the specified position is visible - if ((pos >= firstVisible) && (pos < firstVisible + grid.getChildCount())) { - GalleryPickerAdapter.this.notifyDataSetChanged(); - } - } - }); - } finally { - list.deactivate(); - } - } - } catch (Exception ex) { - Log.e(TAG, "got exception generating collage views ", ex); - } - } - }); - mWorkerThread.start(); - mWorkerThread.toBackground(); - } - - /** - * Add a bucket, but only if it's interesting. - * Interesting means non-empty and not duplicated by the - * corresponding camera bucket. - */ - private void addBucket(int itemType, String bucketId, - int cameraItemType, String cameraBucketId, - int labelId) { - int itemCount = bucketItemCount( - Item.convertItemTypeToIncludedMediaType(itemType), bucketId); - if (itemCount == 0) { - return; // Bucket is empty, so don't show it. - } - int cameraItemCount = 0; - if (cameraBucketId != null) { - cameraItemCount = bucketItemCount( - Item.convertItemTypeToIncludedMediaType(cameraItemType), cameraBucketId); - } - if (cameraItemCount == itemCount) { - return; // Bucket is the same as the camera bucket, so don't show it. - } - mItems.add(new Item(itemType, bucketId, getResources().getString(labelId))); - } - - /** - * Add a bucket, but only if it's interesting. - * Interesting means non-empty. - */ - private void addBucket(int itemType, String bucketId, - int labelId) { - if (!isEmptyBucket(Item.convertItemTypeToIncludedMediaType(itemType), bucketId)) { - mItems.add(new Item(itemType, bucketId, getResources().getString(labelId))); - } - } - - public int getCount() { - return mItems.size(); - } - - public Object getItem(int position) { - return null; - } - - public long getItemId(int position) { - return position; - } - - private String baseTitleForPosition(int position) { - return mItems.get(position).mName; - } - - private int getIncludeMediaTypes(int position) { - return mItems.get(position).getIncludeMediaTypes(); - } - - public View getView(final int position, View convertView, ViewGroup parent) { - View v; - - if (convertView == null) { - LayoutInflater vi = (LayoutInflater)getSystemService(Context.LAYOUT_INFLATER_SERVICE); - v = vi.inflate(R.layout.gallery_picker_item, null); - } else { - v = convertView; - } - - TextView titleView = (TextView) v.findViewById(R.id.title); - - GalleryPickerItem iv = (GalleryPickerItem) v.findViewById(R.id.thumbnail); - iv.setOverlay(mItems.get(position).getOverlay()); - ItemInfo info = mItems.get(position).mThumb; - if (info != null) { - iv.setImageBitmap(info.bitmap); - String title = baseTitleForPosition(position) + " (" + info.count + ")"; - titleView.setText(title); - } else { - iv.setImageResource(android.R.color.transparent); - titleView.setText(baseTitleForPosition(position)); - } - - return v; - } - }; - - @Override - public void onPause() { - super.onPause(); - mPausing = true; - unregisterReceiver(mReceiver); - - // free up some ram - mAdapter = null; - mGridView.setAdapter(null); - System.gc(); - } - - @Override - public void onResume() { - super.onResume(); - mPausing = false; - - mAdapter = new GalleryPickerAdapter(); - mGridView.setAdapter(mAdapter); - setBackgrounds(getResources()); - - boolean scanning = ImageManager.isMediaScannerScanning(this); - rebake(false, scanning); - - // install an intent filter to receive SD card related events. - IntentFilter intentFilter = new IntentFilter(Intent.ACTION_MEDIA_MOUNTED); - intentFilter.addAction(Intent.ACTION_MEDIA_UNMOUNTED); - intentFilter.addAction(Intent.ACTION_MEDIA_SCANNER_STARTED); - intentFilter.addAction(Intent.ACTION_MEDIA_SCANNER_FINISHED); - intentFilter.addAction(Intent.ACTION_MEDIA_EJECT); - intentFilter.addDataScheme("file"); - - registerReceiver(mReceiver, intentFilter); - MenuHelper.requestOrientation(this, mPrefs); - } - - - - private void setBackgrounds(Resources r) { - mFrameGalleryMask = r.getDrawable(R.drawable.frame_gallery_preview_album_mask); - - mCellOutline = r.getDrawable(android.R.drawable.gallery_thumb); - mVideoOverlay = r.getDrawable(R.drawable.ic_gallery_video_overlay); - } - - Handler mHandler = new Handler(); - - private void placeImage(Bitmap image, Canvas c, Paint paint, int imageWidth, int widthPadding, int imageHeight, int heightPadding, int offsetX, int offsetY, int pos) { - int row = pos / 2; - int col = pos - (row * 2); - - int xPos = (col * (imageWidth + widthPadding)) - offsetX; - int yPos = (row * (imageHeight + heightPadding)) - offsetY; - - c.drawBitmap(image, xPos, yPos, paint); - } - - private Bitmap makeMiniThumbBitmap(int width, int height, ImageManager.IImageList images) { - int count = images.getCount(); - // We draw three different version of the folder image depending on the number of images in the folder. - // For a single image, that image draws over the whole folder. - // For two or three images, we draw the two most recent photos. - // For four or more images, we draw four photos. - final int padding = 4; - int imageWidth = width; - int imageHeight = height; - int offsetWidth = 0; - int offsetHeight = 0; - - imageWidth = (imageWidth - padding) / 2; // 2 here because we show two images - imageHeight = (imageHeight - padding) / 2; // per row and column - - final Paint p = new Paint(); - final Bitmap b = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888); - final Canvas c = new Canvas(b); - - final Matrix m = new Matrix(); - - // draw the whole canvas as transparent - p.setColor(0x00000000); - c.drawPaint(p); - - // draw the mask normally - p.setColor(0xFFFFFFFF); - mFrameGalleryMask.setBounds(0, 0, width, height); - mFrameGalleryMask.draw(c); - - Paint pdpaint = new Paint(); - pdpaint.setXfermode(new android.graphics.PorterDuffXfermode( - android.graphics.PorterDuff.Mode.SRC_IN)); - - pdpaint.setStyle(Paint.Style.FILL); - c.drawRect(0, 0, width, height, pdpaint); - - for (int i = 0; i < 4; i++) { - if (mPausing) { - return null; - } - - Bitmap temp = null; - ImageManager.IImage image = i < count ? images.getImageAt(i) : null; - - if (image != null) { - temp = image.miniThumbBitmap(); - } - - if (temp != null) { - if (ImageManager.isVideo(image)) { - Bitmap newMap = temp.copy(temp.getConfig(), true); - Canvas overlayCanvas = new Canvas(newMap); - int overlayWidth = mVideoOverlay.getIntrinsicWidth(); - int overlayHeight = mVideoOverlay.getIntrinsicHeight(); - int left = (newMap.getWidth() - overlayWidth) / 2; - int top = (newMap.getHeight() - overlayHeight) / 2; - Rect newBounds = new Rect(left, top, left + overlayWidth, top + overlayHeight); - mVideoOverlay.setBounds(newBounds); - mVideoOverlay.draw(overlayCanvas); - temp.recycle(); - temp = newMap; - } - - Bitmap temp2 = ImageLoader.transform(m, temp, imageWidth, imageHeight, true); - if (temp2 != temp) - temp.recycle(); - temp = temp2; - } - - Bitmap thumb = Bitmap.createBitmap(imageWidth, imageHeight, Bitmap.Config.ARGB_8888); - Canvas tempCanvas = new Canvas(thumb); - if (temp != null) - tempCanvas.drawBitmap(temp, new Matrix(), new Paint()); - mCellOutline.setBounds(0, 0, imageWidth, imageHeight); - mCellOutline.draw(tempCanvas); - - placeImage(thumb, c, pdpaint, imageWidth, padding, imageHeight, padding, offsetWidth, offsetHeight, i); - - thumb.recycle(); - - if (temp != null) - temp.recycle(); - } - - return b; - } - - @Override - public boolean onCreateOptionsMenu(Menu menu) { - super.onCreateOptionsMenu(menu); - - MenuHelper.addCaptureMenuItems(menu, this); - - menu.add(0, 0, 5, R.string.camerasettings) - .setOnMenuItemClickListener(new OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - Intent preferences = new Intent(); - preferences.setClass(GalleryPicker.this, GallerySettings.class); - startActivity(preferences); - return true; - } - }) - .setAlphabeticShortcut('p') - .setIcon(android.R.drawable.ic_menu_preferences); - - return true; - } - - private boolean isEmptyBucket(int mediaTypes, String bucketId) { - // TODO: Find a more efficient way of calculating this - ImageManager.IImageList list = createImageList(mediaTypes, bucketId); - try { - return list.isEmpty(); - } - finally { - list.deactivate(); - } - } - - private int bucketItemCount(int mediaTypes, String bucketId) { - // TODO: Find a more efficient way of calculating this - ImageManager.IImageList list = createImageList(mediaTypes, bucketId); - try { - return list.getCount(); - } - finally { - list.deactivate(); - } - } - private ImageManager.IImageList createImageList(int mediaTypes, String bucketId) { - return ImageManager.instance().allImages( - this, - getContentResolver(), - ImageManager.DataLocation.ALL, - mediaTypes, - ImageManager.SORT_DESCENDING, - bucketId); - } -} diff --git a/src/com/android/camera/GalleryPickerItem.java b/src/com/android/camera/GalleryPickerItem.java deleted file mode 100644 index c3b5df1..0000000 --- a/src/com/android/camera/GalleryPickerItem.java +++ /dev/null @@ -1,99 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.camera; - -import android.content.Context; -import android.graphics.Canvas; -import android.graphics.Rect; -import android.graphics.drawable.Drawable; -import android.util.AttributeSet; -import android.widget.ImageView; - -public class GalleryPickerItem extends ImageView { - - private Drawable mFrame; - private Rect mFrameBounds = new Rect(); - private Drawable mOverlay; - - public GalleryPickerItem(Context context) { - this(context, null); - } - - public GalleryPickerItem(Context context, AttributeSet attrs) { - this(context, attrs, 0); - } - - public GalleryPickerItem(Context context, AttributeSet attrs, int defStyle) { - super(context, attrs, defStyle); - - mFrame = getResources().getDrawable(R.drawable.frame_gallery_preview); - mFrame.setCallback(this); - } - - @Override - protected boolean verifyDrawable(Drawable who) { - return super.verifyDrawable(who) || (who == mFrame) || (who == mOverlay); - } - - @Override - protected void drawableStateChanged() { - super.drawableStateChanged(); - if (mFrame != null) { - int[] drawableState = getDrawableState(); - mFrame.setState(drawableState); - } - } - - @Override - protected void onDraw(Canvas canvas) { - super.onDraw(canvas); - final Rect frameBounds = mFrameBounds; - if (frameBounds.isEmpty()) { - final int w = getWidth(); - final int h = getHeight(); - - frameBounds.set(0, 0, w, h); - mFrame.setBounds(frameBounds); - if (mOverlay != null) { - mOverlay.setBounds(w - mOverlay.getIntrinsicWidth(), - h - mOverlay.getIntrinsicHeight(), w, h); - } - } - - mFrame.draw(canvas); - if (mOverlay != null) { - mOverlay.draw(canvas); - } - } - - - @Override - protected void onSizeChanged(int w, int h, int oldw, int oldh) { - super.onSizeChanged(w, h, oldw, oldh); - - mFrameBounds.setEmpty(); - } - - public void setOverlay(int overlayId) { - if (overlayId >= 0) { - mOverlay = getResources().getDrawable(overlayId); - mFrameBounds.setEmpty(); - } else { - mOverlay = null; - } - } -} diff --git a/src/com/android/camera/GallerySettings.java b/src/com/android/camera/GallerySettings.java deleted file mode 100644 index 14cff3a..0000000 --- a/src/com/android/camera/GallerySettings.java +++ /dev/null @@ -1,39 +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.camera; - -import android.os.Bundle; -import android.preference.PreferenceActivity; - -/** - * GallerySettings - */ -public class GallerySettings extends PreferenceActivity -{ - public GallerySettings() - { - } - - /** Called with the activity is first created. */ - @Override - public void onCreate(Bundle icicle) - { - super.onCreate(icicle); - addPreferencesFromResource(R.xml.gallery_preferences); - } -} - diff --git a/src/com/android/camera/HighlightView.java b/src/com/android/camera/HighlightView.java deleted file mode 100644 index 408beab..0000000 --- a/src/com/android/camera/HighlightView.java +++ /dev/null @@ -1,428 +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.camera; - -import android.graphics.Canvas; -import android.graphics.Matrix; -import android.graphics.Paint; -import android.graphics.Path; -import android.graphics.Rect; -import android.graphics.RectF; -import android.graphics.Region; -import android.graphics.drawable.Drawable; -import android.util.Config; -import android.util.Log; -import android.view.KeyEvent; -import android.view.View; - - -public class HighlightView -{ - private static final String TAG = "CropImage"; - View mContext; - Path mPath; - Rect mViewDrawingRect = new Rect(); - - int mMotionMode; - - public static final int GROW_NONE = (1 << 0); - public static final int GROW_LEFT_EDGE = (1 << 1); - public static final int GROW_RIGHT_EDGE = (1 << 2); - public static final int GROW_TOP_EDGE = (1 << 3); - public static final int GROW_BOTTOM_EDGE = (1 << 4); - public static final int MOVE = (1 << 5); - - public HighlightView(View ctx) - { - super(); - mContext = ctx; - mPath = new Path(); - } - - private void initHighlightView() { - android.content.res.Resources resources = mContext.getResources(); - mResizeDrawableWidth = resources.getDrawable(R.drawable.camera_crop_width); - mResizeDrawableHeight = resources.getDrawable(R.drawable.camera_crop_height); - mResizeDrawableDiagonal = resources.getDrawable(R.drawable.indicator_autocrop); - } - - boolean mIsFocused; - boolean mHidden; - - public boolean hasFocus() { - return mIsFocused; - } - - public void setFocus(boolean f) { - mIsFocused = f; - } - - public void setHidden(boolean hidden) { - mHidden = hidden; - } - - protected void draw(Canvas canvas) { - if (mHidden) - return; - - canvas.save(); - mPath.reset(); - if (!hasFocus()) { - mOutlinePaint.setColor(0xFF000000); - canvas.drawRect(mDrawRect, mOutlinePaint); - } else { - mContext.getDrawingRect(mViewDrawingRect); - if (mCircle) { - float width = mDrawRect.width() - (getPaddingLeft() + getPaddingRight()); - float height = mDrawRect.height() - (getPaddingTop() + getPaddingBottom()); - mPath.addCircle( - mDrawRect.left + getPaddingLeft() + (width / 2), - mDrawRect.top + getPaddingTop() + (height / 2), - width / 2, - Path.Direction.CW); - mOutlinePaint.setColor(0xFFEF04D6); - } else { - mPath.addRect(new RectF(mDrawRect), Path.Direction.CW); - mOutlinePaint.setColor(0xFFFF8A00); - } - canvas.clipPath(mPath, Region.Op.DIFFERENCE); - canvas.drawRect(mViewDrawingRect, hasFocus() ? mFocusPaint : mNoFocusPaint); - - canvas.restore(); - canvas.drawPath(mPath, mOutlinePaint); - - if (mMode == ModifyMode.Grow) { - if (mCircle) { - int width = mResizeDrawableDiagonal.getIntrinsicWidth(); - int height = mResizeDrawableDiagonal.getIntrinsicHeight(); - - int d = (int) Math.round(Math.cos(/*45deg*/Math.PI/4D) * (mDrawRect.width() / 2D)); - int x = mDrawRect.left + (mDrawRect.width() / 2) + d - width/2; - int y = mDrawRect.top + (mDrawRect.height() / 2) - d - height/2; - mResizeDrawableDiagonal.setBounds(x, y, x + mResizeDrawableDiagonal.getIntrinsicWidth(), y + mResizeDrawableDiagonal.getIntrinsicHeight()); - mResizeDrawableDiagonal.draw(canvas); - } else { - int left = mDrawRect.left + 1; - int right = mDrawRect.right + 1; - int top = mDrawRect.top + 4; - int bottom = mDrawRect.bottom + 3; - - int widthWidth = mResizeDrawableWidth.getIntrinsicWidth() / 2; - int widthHeight = mResizeDrawableWidth.getIntrinsicHeight()/ 2; - int heightHeight = mResizeDrawableHeight.getIntrinsicHeight()/ 2; - int heightWidth = mResizeDrawableHeight.getIntrinsicWidth()/ 2; - - int xMiddle = mDrawRect.left + ((mDrawRect.right - mDrawRect.left) / 2); - int yMiddle = mDrawRect.top + ((mDrawRect.bottom - mDrawRect.top ) / 2); - - mResizeDrawableWidth.setBounds(left-widthWidth, yMiddle-widthHeight, left+widthWidth, yMiddle+widthHeight); - mResizeDrawableWidth.draw(canvas); - - mResizeDrawableWidth.setBounds(right-widthWidth, yMiddle-widthHeight, right+widthWidth, yMiddle+widthHeight); - mResizeDrawableWidth.draw(canvas); - - mResizeDrawableHeight.setBounds(xMiddle-heightWidth, top-heightHeight, xMiddle+heightWidth, top+heightHeight); - mResizeDrawableHeight.draw(canvas); - - mResizeDrawableHeight.setBounds(xMiddle-heightWidth, bottom-heightHeight, xMiddle+heightWidth, bottom+heightHeight); - mResizeDrawableHeight.draw(canvas); - } - } - } - - } - - float getPaddingTop() { return 0F; } - float getPaddingBottom() { return 0F; } - float getPaddingLeft() { return 0F; } - float getPaddingRight() { return 0F; } - - public ModifyMode getMode() { - return mMode; - } - - public void setMode(ModifyMode mode) - { - if (mode != mMode) { - mMode = mode; - mContext.invalidate(); - } - } - - public int getHit(float x, float y) { - Rect r = computeLayout(); - final float hysteresis = 20F; - int retval = GROW_NONE; - - if (mCircle) { - float distX = x - r.centerX(); - float distY = y - r.centerY(); - int distanceFromCenter = (int) Math.sqrt(distX*distX + distY*distY); - int radius = (int) (mDrawRect.width() - getPaddingLeft()) / 2; - int delta = distanceFromCenter - radius; - if (Math.abs(delta) <= hysteresis) { - if (Math.abs(distY) > Math.abs(distX)) { - if (distY < 0) - retval = GROW_TOP_EDGE; - else - retval = GROW_BOTTOM_EDGE; - } else { - if (distX < 0) - retval = GROW_LEFT_EDGE; - else - retval = GROW_RIGHT_EDGE; - } - } else if (distanceFromCenter < radius) { - retval = MOVE; - } else { - retval = GROW_NONE; - } -// Log.v(TAG, "radius: " + radius + "; touchRadius: " + distanceFromCenter + "; distX: " + distX + "; distY: " + distY + "; retval: " + retval); - } else { - boolean verticalCheck = (y >= r.top - hysteresis) && (y < r.bottom + hysteresis); - boolean horizCheck = (x >= r.left - hysteresis) && (x < r.right + hysteresis); - - if ((Math.abs(r.left - x) < hysteresis) && verticalCheck) - retval |= GROW_LEFT_EDGE; - if ((Math.abs(r.right - x) < hysteresis) && verticalCheck) - retval |= GROW_RIGHT_EDGE; - if ((Math.abs(r.top - y) < hysteresis) && horizCheck) - retval |= GROW_TOP_EDGE; - if ((Math.abs(r.bottom - y) < hysteresis) && horizCheck) - retval |= GROW_BOTTOM_EDGE; - - if (retval == GROW_NONE && r.contains((int)x, (int)y)) - retval = MOVE; - } - return retval; - } - - void handleMotion(int edge, float dx, float dy) { - Rect r = computeLayout(); - if (edge == GROW_NONE) { - return; - } else if (edge == MOVE) { - moveBy(dx * (mCropRect.width() / r.width()), - dy * (mCropRect.height() / r.height())); - } else { - if (((GROW_LEFT_EDGE | GROW_RIGHT_EDGE) & edge) == 0) - dx = 0; - - if (((GROW_TOP_EDGE | GROW_BOTTOM_EDGE) & edge) == 0) - dy = 0; - - float xDelta = dx * (mCropRect.width() / r.width()); - float yDelta = dy * (mCropRect.height() / r.height()); - growBy((((edge & GROW_LEFT_EDGE) != 0) ? -1 : 1) * xDelta, - (((edge & GROW_TOP_EDGE) != 0) ? -1 : 1) * yDelta); - - } -// Log.v(TAG, "ratio is now " + this.mCropRect.width() / this.mCropRect.height()); - } - - void moveBy(float dx, float dy) { - Rect invalRect = new Rect(mDrawRect); - - mCropRect.offset(dx, dy); - mCropRect.offset( - Math.max(0, mImageRect.left - mCropRect.left), - Math.max(0, mImageRect.top - mCropRect.top)); - - mCropRect.offset( - Math.min(0, mImageRect.right - mCropRect.right), - Math.min(0, mImageRect.bottom - mCropRect.bottom)); - - mDrawRect = computeLayout(); - invalRect.union(mDrawRect); - invalRect.inset(-10, -10); - mContext.invalidate(invalRect); - } - - private void shift(RectF r, float dx, float dy) { - r.left += dx; - r.right += dx; - r.top += dy; - r.bottom += dy; - } - - void growBy(float dx, float dy) { -// Log.v(TAG, "growBy: " + dx + " " + dy + "; rect w/h is " + mCropRect.width() + " / " + mCropRect.height()); - if (mMaintainAspectRatio) { - if (dx != 0) { - dy = dx / mInitialAspectRatio; - } else if (dy != 0) { - dx = dy * mInitialAspectRatio; - } - } - - RectF r = new RectF(mCropRect); - if (dx > 0F && r.width() + 2 * dx > mImageRect.width()) { - float adjustment = (mImageRect.width() - r.width()) / 2F; - dx = adjustment; - if (mMaintainAspectRatio) - dy = dx / mInitialAspectRatio; - } - if (dy > 0F && r.height() + 2 * dy > mImageRect.height()) { - float adjustment = (mImageRect.height() - r.height()) / 2F; - dy = adjustment; - if (mMaintainAspectRatio) - dx = dy * mInitialAspectRatio; - } - - r.inset(-dx, -dy); - - float widthCap = 25F; - if (r.width() < 25) { - r.inset(-(25F-r.width())/2F, 0F); - } - float heightCap = mMaintainAspectRatio ? (widthCap / mInitialAspectRatio) : widthCap; - if (r.height() < heightCap) { - r.inset(0F, -(heightCap-r.height())/2F); - } - - if (r.left < mImageRect.left) { - shift(r, mImageRect.left - r.left, 0F); - } else if (r.right > mImageRect.right) { - shift(r, -(r.right - mImageRect.right), 0); - } - if (r.top < mImageRect.top) { - shift(r, 0F, mImageRect.top - r.top); - } else if (r.bottom > mImageRect.bottom) { - shift(r, 0F, -(r.bottom - mImageRect.bottom)); - } -/* - RectF rCandidate = new RectF(r); - r.intersect(mImageRect); - if (mMaintainAspectRatio) { - if (r.left != rCandidate.left) { - Log.v(TAG, "bail 1"); - return; - } - if (r.right != rCandidate.right) { - Log.v(TAG, "bail 2"); - return; - } - if (r.top != rCandidate.top) { - Log.v(TAG, "bail 3"); - return; - } - if (r.bottom != rCandidate.bottom) { - Log.v(TAG, "bail 4"); - return; - } - } -*/ - mCropRect.set(r); - mDrawRect = computeLayout(); - mContext.invalidate(); - } - - public Rect getCropRect() { - return new Rect((int)mCropRect.left, (int)mCropRect.top, (int)mCropRect.right, (int)mCropRect.bottom); - } - - private Rect computeLayout() { - RectF r = new RectF(mCropRect.left, mCropRect.top, mCropRect.right, mCropRect.bottom); - mMatrix.mapRect(r); - return new Rect(Math.round(r.left), Math.round(r.top), Math.round(r.right), Math.round(r.bottom)); - } - - public void invalidate() { - mDrawRect = computeLayout(); - } - - public void setup(Matrix m, Rect imageRect, RectF cropRect, boolean circle, boolean maintainAspectRatio) { - if (Config.LOGV) Log.v(TAG, "setup... " + imageRect + "; " + cropRect + "; maintain " + maintainAspectRatio + "; circle " + circle); - if (circle) - maintainAspectRatio = true; - mMatrix = new Matrix(m); - - mCropRect = cropRect; - mImageRect = new RectF(imageRect); - mMaintainAspectRatio = maintainAspectRatio; - mCircle = circle; - - mInitialAspectRatio = mCropRect.width() / mCropRect.height(); - mDrawRect = computeLayout(); - - mFocusPaint.setARGB(125, 50, 50, 50); - mNoFocusPaint.setARGB(125, 50, 50, 50); - mOutlinePaint.setStrokeWidth(3F); - mOutlinePaint.setStyle(Paint.Style.STROKE); - mOutlinePaint.setAntiAlias(true); - - mMode = ModifyMode.None; - initHighlightView(); - } - - public void modify(int keyCode, long repeatCount) - { - float factor = Math.max(.01F, Math.min(.1F, repeatCount * .01F)); - float widthUnits = factor * (float)mContext.getWidth(); - float heightUnits = widthUnits; - - switch (keyCode) - { - case KeyEvent.KEYCODE_DPAD_LEFT: - if (mMode == ModifyMode.Move) - moveBy(-widthUnits, 0); - else if (mMode == ModifyMode.Grow) - growBy(-widthUnits, 0); - break; - - case KeyEvent.KEYCODE_DPAD_RIGHT: - if (mMode == ModifyMode.Move) - moveBy(widthUnits, 0); - else if (mMode == ModifyMode.Grow) - growBy(widthUnits, 0); - break; - - case KeyEvent.KEYCODE_DPAD_UP: - if (mMode == ModifyMode.Move) - moveBy(0, -heightUnits); - else if (mMode == ModifyMode.Grow) - growBy(0, -heightUnits); - break; - - case KeyEvent.KEYCODE_DPAD_DOWN: - if (mMode == ModifyMode.Move) - moveBy(0, heightUnits); - else if (mMode == ModifyMode.Grow) - growBy(0, heightUnits); - break; - } - } - - enum ModifyMode { None, Move,Grow }; - - ModifyMode mMode = ModifyMode.None; - - Rect mDrawRect; - RectF mImageRect; - RectF mCropRect; - Matrix mMatrix; - - boolean mMaintainAspectRatio = false; - float mInitialAspectRatio; - boolean mCircle = false; - - Drawable mResizeDrawableWidth, mResizeDrawableHeight, mResizeDrawableDiagonal; - - Paint mFocusPaint = new Paint(); - Paint mNoFocusPaint = new Paint(); - Paint mOutlinePaint = new Paint(); -} diff --git a/src/com/android/camera/ImageGallery2.java b/src/com/android/camera/ImageGallery2.java deleted file mode 100644 index 008eb21..0000000 --- a/src/com/android/camera/ImageGallery2.java +++ /dev/null @@ -1,1848 +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.camera; - -import android.content.BroadcastReceiver; -import android.app.Activity; -import android.app.Dialog; -import android.app.AlertDialog; -import android.app.ProgressDialog; -import android.content.Context; -import android.content.DialogInterface; -import android.content.Intent; -import android.content.IntentFilter; -import android.content.SharedPreferences; -import android.content.pm.ActivityInfo; -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.drawable.Drawable; -import android.net.Uri; -import android.os.Bundle; -import android.os.Handler; -import android.os.PowerManager; -import android.util.AttributeSet; -import android.util.Config; -import android.util.Log; -import android.view.ContextMenu; -import android.view.GestureDetector; -import android.view.GestureDetector.SimpleOnGestureListener; -import android.view.KeyEvent; -import android.view.Menu; -import android.view.MenuItem; -import android.view.MotionEvent; -import android.view.View; -import android.view.ViewConfiguration; -import android.view.Window; -import android.widget.TextView; -import android.widget.Toast; -import android.preference.PreferenceManager; -import android.provider.MediaStore; -import android.widget.Scroller; - -import java.util.Calendar; -import java.util.GregorianCalendar; - -import com.android.camera.ImageManager.IImage; - -public class ImageGallery2 extends Activity { - private static final String TAG = "ImageGallery2"; - private ImageManager.IImageList mAllImages; - private int mInclusion; - private boolean mSortAscending = false; - private View mNoImagesView; - public final static int CROP_MSG = 2; - public final static int VIEW_MSG = 3; - private static final String INSTANCE_STATE_TAG = "scrollY"; - - private Dialog mMediaScanningDialog; - - private MenuItem mSlideShowItem; - private SharedPreferences mPrefs; - private long mVideoSizeLimit = Long.MAX_VALUE; - - public ImageGallery2() { - } - - BroadcastReceiver mReceiver = null; - - Handler mHandler = new Handler(); - boolean mLayoutComplete; - boolean mPausing = false; - boolean mStopThumbnailChecking = false; - - CameraThread mThumbnailCheckThread; - GridViewSpecial mGvs; - - @Override - public void onCreate(Bundle icicle) { - if (Config.LOGV) Log.v(TAG, "onCreate"); - super.onCreate(icicle); - - mPrefs = PreferenceManager.getDefaultSharedPreferences(this); - - requestWindowFeature(Window.FEATURE_CUSTOM_TITLE); // must be called before setContentView() - setContentView(R.layout.image_gallery_2); - - getWindow().setFeatureInt(Window.FEATURE_CUSTOM_TITLE, R.layout.custom_gallery_title); - if (Config.LOGV) - Log.v(TAG, "findView... " + findViewById(R.id.loading_indicator)); - - mGvs = (GridViewSpecial) findViewById(R.id.grid); - mGvs.requestFocus(); - - if (isPickIntent()) { - mVideoSizeLimit = getIntent().getLongExtra( - MediaStore.EXTRA_SIZE_LIMIT, Long.MAX_VALUE); - mGvs.mVideoSizeLimit = mVideoSizeLimit; - } else { - mVideoSizeLimit = Long.MAX_VALUE; - mGvs.mVideoSizeLimit = mVideoSizeLimit; - mGvs.setOnCreateContextMenuListener(new View.OnCreateContextMenuListener() { - public void onCreateContextMenu(ContextMenu menu, View v, ContextMenu.ContextMenuInfo menuInfo) { - if (mSelectedImageGetter.getCurrentImage() == null) - return; - - boolean isImage = ImageManager.isImage(mSelectedImageGetter.getCurrentImage()); - if (isImage) { - menu.add(0, 0, 0, R.string.view).setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - mGvs.onSelect(mGvs.mCurrentSelection); - return true; - } - }); - } - - menu.setHeaderTitle(isImage ? R.string.context_menu_header - : R.string.video_context_menu_header); - if ((mInclusion & (ImageManager.INCLUDE_IMAGES | ImageManager.INCLUDE_VIDEOS)) != 0) { - MenuHelper.MenuItemsResult r = MenuHelper.addImageMenuItems( - menu, - MenuHelper.INCLUDE_ALL, - isImage, - ImageGallery2.this, - mHandler, - mDeletePhotoRunnable, - new MenuHelper.MenuInvoker() { - public void run(MenuHelper.MenuCallback cb) { - cb.run(mSelectedImageGetter.getCurrentImageUri(), mSelectedImageGetter.getCurrentImage()); - - mGvs.clearCache(); - mGvs.invalidate(); - mGvs.requestLayout(); - mGvs.start(); - mNoImagesView.setVisibility(mAllImages.getCount() > 0 ? View.GONE : View.VISIBLE); - } - }); - if (r != null) - r.gettingReadyToOpen(menu, mSelectedImageGetter.getCurrentImage()); - - if (isImage) { - addSlideShowMenu(menu, 1000); - } - } - } - }); - } - } - - private MenuItem addSlideShowMenu(Menu menu, int position) { - return menu.add(0, 207, position, R.string.slide_show) - .setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - ImageManager.IImage img = mSelectedImageGetter.getCurrentImage(); - if (img == null) { - img = mAllImages.getImageAt(0); - if (img == null) { - return true; - } - } - Uri targetUri = img.fullSizeImageUri(); - Uri thisUri = getIntent().getData(); - if (thisUri != null) { - String bucket = thisUri.getQueryParameter("bucketId"); - if (bucket != null) { - targetUri = targetUri.buildUpon().appendQueryParameter("bucketId", bucket).build(); - } - } - Intent intent = new Intent(Intent.ACTION_VIEW, targetUri); - intent.putExtra("slideshow", true); - startActivity(intent); - return true; - } - }) - .setIcon(android.R.drawable.ic_menu_slideshow); - } - - private Runnable mDeletePhotoRunnable = new Runnable() { - public void run() { - mGvs.clearCache(); - IImage currentImage = mSelectedImageGetter.getCurrentImage(); - if (currentImage != null) { - mAllImages.removeImage(currentImage); - } - mGvs.invalidate(); - mGvs.requestLayout(); - mGvs.start(); - mNoImagesView.setVisibility(mAllImages.isEmpty() ? View.VISIBLE : View.GONE); - } - }; - - private SelectedImageGetter mSelectedImageGetter = new SelectedImageGetter() { - public Uri getCurrentImageUri() { - ImageManager.IImage image = getCurrentImage(); - if (image != null) - return image.fullSizeImageUri(); - else - return null; - } - public ImageManager.IImage getCurrentImage() { - int currentSelection = mGvs.mCurrentSelection; - if (currentSelection < 0 || currentSelection >= mAllImages.getCount()) - return null; - else - return mAllImages.getImageAt(currentSelection); - } - }; - - @Override - public void onConfigurationChanged(android.content.res.Configuration newConfig) { - super.onConfigurationChanged(newConfig); - mTargetScroll = mGvs.getScrollY(); - } - - private Runnable mLongPressCallback = new Runnable() { - public void run() { - mGvs.select(-2, false); - mGvs.showContextMenu(); - } - }; - - @Override - public boolean onKeyUp(int keyCode, KeyEvent event) { - if (keyCode == KeyEvent.KEYCODE_DPAD_CENTER) { - mGvs.select(-2, false); - // The keyUp doesn't get called when the longpress menu comes up. We only get here when the user - // lets go of the center key before the longpress menu comes up. - mHandler.removeCallbacks(mLongPressCallback); - - // open the photo - if (mSelectedImageGetter.getCurrentImage() != null) { - mGvs.onSelect(mGvs.mCurrentSelection); - } - return true; - } - return super.onKeyUp(keyCode, event); - } - - @Override - public boolean onKeyDown(int keyCode, KeyEvent event) { - boolean handled = true; - int sel = mGvs.mCurrentSelection; - int columns = mGvs.mCurrentSpec.mColumns; - int count = mAllImages.getCount(); - boolean pressed = false; - if (mGvs.mShowSelection) { - switch (keyCode) { - case KeyEvent.KEYCODE_DPAD_RIGHT: - if (sel != count && (sel % columns < columns - 1)) { - sel += 1; - } - break; - case KeyEvent.KEYCODE_DPAD_LEFT: - if (sel > 0 && (sel % columns != 0)) { - sel -= 1; - } - break; - case KeyEvent.KEYCODE_DPAD_UP: - if ((sel / columns) != 0) { - sel -= columns; - } - break; - case KeyEvent.KEYCODE_DPAD_DOWN: - if ((sel / columns) != (sel+columns / columns)) { - sel = Math.min(count-1, sel + columns); - } - break; - case KeyEvent.KEYCODE_DPAD_CENTER: - pressed = true; - mHandler.postDelayed(mLongPressCallback, ViewConfiguration.getLongPressTimeout()); - break; - case KeyEvent.KEYCODE_DEL: - MenuHelper.deleteImage(this, mDeletePhotoRunnable, - mSelectedImageGetter.getCurrentImage()); - break; - default: - handled = false; - break; - } - } else { - switch (keyCode) { - case KeyEvent.KEYCODE_DPAD_RIGHT: - case KeyEvent.KEYCODE_DPAD_LEFT: - case KeyEvent.KEYCODE_DPAD_UP: - case KeyEvent.KEYCODE_DPAD_DOWN: - int [] range = new int[2]; - GridViewSpecial.ImageBlockManager ibm = mGvs.mImageBlockManager; - if (ibm != null) { - mGvs.mImageBlockManager.getVisibleRange(range); - int topPos = range[0]; - android.graphics.Rect r = mGvs.getRectForPosition(topPos); - if (r.top < mGvs.getScrollY()) - topPos += columns; - topPos = Math.min(count - 1, topPos); - sel = topPos; - } - break; - default: - handled = false; - break; - } - } - if (handled) { - mGvs.select(sel, pressed); - return true; - } - else - return super.onKeyDown(keyCode, event); - } - - private boolean isPickIntent() { - String action = getIntent().getAction(); - return (Intent.ACTION_PICK.equals(action) || Intent.ACTION_GET_CONTENT.equals(action)); - } - - private void launchCropperOrFinish(ImageManager.IImage img) { - Bundle myExtras = getIntent().getExtras(); - - if (MenuHelper.getImageFileSize(img) > mVideoSizeLimit) { - - DialogInterface.OnClickListener buttonListener = - new DialogInterface.OnClickListener() { - public void onClick(DialogInterface dialog, int which) { - dialog.dismiss(); - } - }; - new AlertDialog.Builder(this) - .setIcon(android.R.drawable.ic_dialog_info) - .setTitle(R.string.file_info_title) - .setMessage(R.string.video_exceed_mms_limit) - .setNeutralButton(R.string.details_ok, buttonListener) - .show(); - return; - } - - String cropValue = myExtras != null ? myExtras.getString("crop") : null; - if (cropValue != null) { - Bundle newExtras = new Bundle(); - if (cropValue.equals("circle")) - newExtras.putString("circleCrop", "true"); - - Intent cropIntent = new Intent(); - cropIntent.setData(img.fullSizeImageUri()); - cropIntent.setClass(this, CropImage.class); - cropIntent.putExtras(newExtras); - - /* pass through any extras that were passed in */ - cropIntent.putExtras(myExtras); - if (Config.LOGV) Log.v(TAG, "startSubActivity " + cropIntent); - startActivityForResult(cropIntent, CROP_MSG); - } else { - Intent result = new Intent(null, img.fullSizeImageUri()); - if (myExtras != null && myExtras.getString("return-data") != null) { - Bitmap bitmap = img.fullSizeBitmap(1000); - if (bitmap != null) - result.putExtra("data", bitmap); - } - setResult(RESULT_OK, result); - finish(); - } - } - - @Override - protected void onActivityResult(int requestCode, int resultCode, Intent data) { - if (Config.LOGV) - Log.v(TAG, "onActivityResult: " + requestCode + "; resultCode is " + resultCode + "; data is " + data); - switch (requestCode) { - case MenuHelper.RESULT_COMMON_MENU_CROP: { - if (resultCode == RESULT_OK) { - // The CropImage activity passes back the Uri of the cropped image as - // the Action rather than the Data. - Uri dataUri = Uri.parse(data.getAction()); - rebake(false,false); - IImage image = mAllImages.getImageForUri(dataUri); - if (image != null ) { - int rowId = image.getRow(); - mGvs.select(rowId, false); - } - } - break; - } - case CROP_MSG: { - if (Config.LOGV) Log.v(TAG, "onActivityResult " + data); - if (resultCode == RESULT_OK) { - setResult(resultCode, data); - finish(); - } - break; - } - case VIEW_MSG: { - if (Config.LOGV) - Log.v(TAG, "got VIEW_MSG with " + data); - ImageManager.IImage img = mAllImages.getImageForUri(data.getData()); - launchCropperOrFinish(img); - break; - } - } - } - - @Override - public void onPause() { - super.onPause(); - mPausing = true; - stopCheckingThumbnails(); - mGvs.onPause(); - - if (mReceiver != null) { - unregisterReceiver(mReceiver); - mReceiver = null; - } - // Now that we've paused the threads that are using the cursor it is safe - // to deactivate it. - mAllImages.deactivate(); - } - - private void rebake(boolean unmounted, boolean scanning) { - stopCheckingThumbnails(); - mGvs.clearCache(); - if (mAllImages != null) { - mAllImages.deactivate(); - mAllImages = null; - } - if (mMediaScanningDialog != null) { - mMediaScanningDialog.cancel(); - mMediaScanningDialog = null; - } - if (scanning) { - mMediaScanningDialog = ProgressDialog.show( - this, - null, - getResources().getString(R.string.wait), - true, - true); - mAllImages = ImageManager.instance().emptyImageList(); - } else { - mAllImages = allImages(!unmounted); - if (Config.LOGV) - Log.v(TAG, "mAllImages is now " + mAllImages); - mGvs.init(mHandler); - mGvs.start(); - mGvs.requestLayout(); - checkThumbnails(); - } - } - - @Override - protected void onSaveInstanceState(Bundle state) { - super.onSaveInstanceState(state); - mTargetScroll = mGvs.getScrollY(); - state.putInt(INSTANCE_STATE_TAG, mTargetScroll); - } - - @Override - protected void onRestoreInstanceState(Bundle state) { - super.onRestoreInstanceState(state); - mTargetScroll = state.getInt(INSTANCE_STATE_TAG, 0); - } - - int mTargetScroll; - - @Override - public void onResume() { - super.onResume(); - - try { - mGvs.setSizeChoice(Integer.parseInt(mPrefs.getString("pref_gallery_size_key", "1")), mTargetScroll); - - String sortOrder = mPrefs.getString("pref_gallery_sort_key", null); - if (sortOrder != null) { - mSortAscending = sortOrder.equals("ascending"); - } - } catch (Exception ex) { - - } - mPausing = false; - - // install an intent filter to receive SD card related events. - IntentFilter intentFilter = new IntentFilter(Intent.ACTION_MEDIA_MOUNTED); - intentFilter.addAction(Intent.ACTION_MEDIA_UNMOUNTED); - intentFilter.addAction(Intent.ACTION_MEDIA_SCANNER_STARTED); - intentFilter.addAction(Intent.ACTION_MEDIA_SCANNER_FINISHED); - intentFilter.addAction(Intent.ACTION_MEDIA_EJECT); - intentFilter.addDataScheme("file"); - - mReceiver = new BroadcastReceiver() { - @Override - public void onReceive(Context context, Intent intent) { - if (Config.LOGV) Log.v(TAG, "onReceiveIntent " + intent.getAction()); - String action = intent.getAction(); - if (action.equals(Intent.ACTION_MEDIA_MOUNTED)) { - // SD card available - // TODO put up a "please wait" message - // TODO also listen for the media scanner finished message - } else if (action.equals(Intent.ACTION_MEDIA_UNMOUNTED)) { - // SD card unavailable - if (Config.LOGV) Log.v(TAG, "sd card no longer available"); - Toast.makeText(ImageGallery2.this, getResources().getString(R.string.wait), 5000); - rebake(true, false); - } else if (action.equals(Intent.ACTION_MEDIA_SCANNER_STARTED)) { - Toast.makeText(ImageGallery2.this, getResources().getString(R.string.wait), 5000); - rebake(false, true); - } else if (action.equals(Intent.ACTION_MEDIA_SCANNER_FINISHED)) { - if (Config.LOGV) - Log.v(TAG, "rebake because of ACTION_MEDIA_SCANNER_FINISHED"); - rebake(false, false); - } else if (action.equals(Intent.ACTION_MEDIA_EJECT)) { - if (Config.LOGV) - Log.v(TAG, "rebake because of ACTION_MEDIA_EJECT"); - rebake(true, false); - } - } - }; - registerReceiver(mReceiver, intentFilter); - - MenuHelper.requestOrientation(this, mPrefs); - - rebake(false, ImageManager.isMediaScannerScanning(this)); - } - - private void stopCheckingThumbnails() { - mStopThumbnailChecking = true; - if (mThumbnailCheckThread != null) { - mThumbnailCheckThread.join(); - } - mStopThumbnailChecking = false; - } - - private void checkThumbnails() { - final long startTime = System.currentTimeMillis(); - final long t1 = System.currentTimeMillis(); - mThumbnailCheckThread = new CameraThread(new Runnable() { - public void run() { - android.content.res.Resources resources = getResources(); - final TextView progressTextView = (TextView) findViewById(R.id.loading_text); - final String progressTextFormatString = resources.getString(R.string.loading_progress_format_string); - - PowerManager pm = (PowerManager)getSystemService(Context.POWER_SERVICE); - PowerManager.WakeLock mWakeLock = - pm.newWakeLock(PowerManager.SCREEN_BRIGHT_WAKE_LOCK, - "ImageGallery2.checkThumbnails"); - mWakeLock.acquire(); - ImageManager.IImageList.ThumbCheckCallback r = new ImageManager.IImageList.ThumbCheckCallback() { - boolean mDidSetProgress = false; - - public boolean checking(final int count, final int maxCount) { - if (mStopThumbnailChecking) { - return false; - } - - if (!mLayoutComplete) { - return true; - } - - if (!mDidSetProgress) { - mHandler.post(new Runnable() { - public void run() { - findViewById(R.id.loading_indicator).setVisibility(View.VISIBLE); - } - }); - mDidSetProgress = true; - } - mGvs.postInvalidate(); - - if (System.currentTimeMillis() - startTime > 1000) { - mHandler.post(new Runnable() { - public void run() { - String s = String.format(progressTextFormatString, maxCount - count); - progressTextView.setText(s); - } - }); - } - - return !mPausing; - } - }; - ImageManager.IImageList imageList = allImages(true); - imageList.checkThumbnails(r, imageList.getCount()); - mWakeLock.release(); - mThumbnailCheckThread = null; - mHandler.post(new Runnable() { - public void run() { - findViewById(R.id.loading_indicator).setVisibility(View.GONE); - } - }); - long t2 = System.currentTimeMillis(); - if (Config.LOGV) - Log.v(TAG, "check thumbnails thread finishing; took " + (t2-t1)); - } - }); - - mThumbnailCheckThread.setName("check_thumbnails"); - mThumbnailCheckThread.start(); - mThumbnailCheckThread.toBackground(); - - ImageManager.IImageList list = allImages(true); - mNoImagesView.setVisibility(list.getCount() > 0 ? View.GONE : View.VISIBLE); - } - - @Override - public boolean onCreateOptionsMenu(android.view.Menu menu) { - MenuItem item; - if (! isPickIntent()) { - MenuHelper.addCaptureMenuItems(menu, this); - if ((mInclusion & ImageManager.INCLUDE_IMAGES) != 0) { - mSlideShowItem = addSlideShowMenu(menu, 5); - - } - } - - item = menu.add(0, 0, 1000, R.string.camerasettings); - item.setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - Intent preferences = new Intent(); - preferences.setClass(ImageGallery2.this, GallerySettings.class); - startActivity(preferences); - return true; - } - }); - item.setAlphabeticShortcut('p'); - item.setIcon(android.R.drawable.ic_menu_preferences); - - return true; - } - - @Override - public boolean onPrepareOptionsMenu(android.view.Menu menu) { - if ((mInclusion & ImageManager.INCLUDE_IMAGES) != 0) { - boolean videoSelected = isVideoSelected(); - // TODO: Only enable slide show if there is at least one image in the folder. - if (mSlideShowItem != null) { - mSlideShowItem.setEnabled(!videoSelected); - } - } - - return true; - } - - private boolean isImageSelected() { - IImage image = mSelectedImageGetter.getCurrentImage(); - return (image != null) && ImageManager.isImage(image); - } - - private boolean isVideoSelected() { - IImage image = mSelectedImageGetter.getCurrentImage(); - return (image != null) && ImageManager.isVideo(image); - } - - private synchronized ImageManager.IImageList allImages(boolean assumeMounted) { - if (mAllImages == null) { - mNoImagesView = findViewById(R.id.no_images); - - mInclusion = ImageManager.INCLUDE_IMAGES | ImageManager.INCLUDE_VIDEOS; - - Intent intent = getIntent(); - if (intent != null) { - String type = intent.resolveType(this); - if (Config.LOGV) - Log.v(TAG, "allImages... type is " + type); - TextView leftText = (TextView) findViewById(R.id.left_text); - if (type != null) { - if (type.equals("vnd.android.cursor.dir/image") || type.equals("image/*")) { - mInclusion = ImageManager.INCLUDE_IMAGES; - if (isPickIntent()) - leftText.setText(R.string.pick_photos_gallery_title); - else - leftText.setText(R.string.photos_gallery_title); - } - if (type.equals("vnd.android.cursor.dir/video") || type.equals("video/*")) { - mInclusion = ImageManager.INCLUDE_VIDEOS; - if (isPickIntent()) - leftText.setText(R.string.pick_videos_gallery_title); - else - leftText.setText(R.string.videos_gallery_title); - } - } - Bundle extras = intent.getExtras(); - String title = extras!= null ? extras.getString("windowTitle") : null; - if (title != null && title.length() > 0) { - leftText.setText(title); - } - - if (extras != null) { - mInclusion = (ImageManager.INCLUDE_IMAGES | ImageManager.INCLUDE_VIDEOS) - & extras.getInt("mediaTypes", mInclusion); - } - - if (extras != null && extras.getBoolean("pick-drm")) { - Log.d(TAG, "pick-drm is true"); - mInclusion = ImageManager.INCLUDE_DRM_IMAGES; - } - } - if (Config.LOGV) - Log.v(TAG, "computing images... mSortAscending is " + mSortAscending - + "; assumeMounted is " + assumeMounted); - Uri uri = getIntent().getData(); - if (!assumeMounted) { - mAllImages = ImageManager.instance().emptyImageList(); - } else { - mAllImages = ImageManager.instance().allImages( - ImageGallery2.this, - getContentResolver(), - ImageManager.DataLocation.NONE, - mInclusion, - mSortAscending ? ImageManager.SORT_ASCENDING : ImageManager.SORT_DESCENDING, - uri != null ? uri.getQueryParameter("bucketId") : null); - } - } - return mAllImages; - } - - public static class GridViewSpecial extends View { - private ImageGallery2 mGallery; - private Paint mGridViewPaint = new Paint(); - - private ImageBlockManager mImageBlockManager; - private Handler mHandler; - - private LayoutSpec mCurrentSpec; - private boolean mShowSelection = false; - private int mCurrentSelection = -1; - private boolean mCurrentSelectionPressed; - - private boolean mDirectionBiasDown = true; - private final static boolean sDump = false; - - private long mVideoSizeLimit; - - class LayoutSpec { - LayoutSpec(int cols, int w, int h, int leftEdgePadding, int rightEdgePadding, int intercellSpacing) { - mColumns = cols; - mCellWidth = w; - mCellHeight = h; - mLeftEdgePadding = leftEdgePadding; - mRightEdgePadding = rightEdgePadding; - mCellSpacing = intercellSpacing; - } - int mColumns; - int mCellWidth, mCellHeight; - int mLeftEdgePadding, mRightEdgePadding; - int mCellSpacing; - }; - - private LayoutSpec [] mCellSizeChoices = new LayoutSpec[] { - new LayoutSpec(0, 67, 67, 14, 14, 8), - new LayoutSpec(0, 92, 92, 14, 14, 8), - }; - private int mSizeChoice = 1; - - // Use a number like 100 or 200 here to allow the user to - // overshoot the start (top) or end (bottom) of the gallery. - // After overshooting the gallery will animate back to the - // appropriate location. - private int mMaxOvershoot = 0; // 100; - private int mMaxScrollY; - private int mMinScrollY; - - private boolean mFling = true; - private Scroller mScroller = null; - - private GestureDetector mGestureDetector; - - public void dump() { - if (Config.LOGV){ - Log.v(TAG, "mSizeChoice is " + mCellSizeChoices[mSizeChoice]); - Log.v(TAG, "mCurrentSpec.width / mCellHeight are " + mCurrentSpec.mCellWidth + " / " + mCurrentSpec.mCellHeight); - } - mImageBlockManager.dump(); - } - - private void init(Context context) { - mGridViewPaint.setColor(0xFF000000); - mGallery = (ImageGallery2) context; - - setVerticalScrollBarEnabled(true); - initializeScrollbars(context.obtainStyledAttributes(android.R.styleable.View)); - - mGestureDetector = new GestureDetector(context, new SimpleOnGestureListener() { - @Override - public boolean onDown(MotionEvent e) { - if (mScroller != null && !mScroller.isFinished()) { - mScroller.forceFinished(true); - return false; - } - - int pos = computeSelectedIndex(e); - if (pos >= 0 && pos < mGallery.mAllImages.getCount()) { - select(pos, true); - } else { - select(-1, false); - } - if (mImageBlockManager != null) - mImageBlockManager.repaintSelection(mCurrentSelection); - invalidate(); - return true; - } - - @Override - public boolean onFling(MotionEvent e1, MotionEvent e2, float velocityX, float velocityY) { - final float maxVelocity = 2500; - if (velocityY > maxVelocity) - velocityY = maxVelocity; - else if (velocityY < -maxVelocity) - velocityY = -maxVelocity; - - select(-1, false); - if (mFling) { - mScroller = new Scroller(getContext()); - mScroller.fling(0, mScrollY, 0, -(int)velocityY, 0, 0, 0, mMaxScrollY); - computeScroll(); - } - return true; - } - - @Override - public void onLongPress(MotionEvent e) { - performLongClick(); - } - - @Override - public boolean onScroll(MotionEvent e1, MotionEvent e2, float distanceX, float distanceY) { - select(-1, false); - scrollBy(0, (int)distanceY); - invalidate(); - return true; - } - - @Override - public void onShowPress(MotionEvent e) { - super.onShowPress(e); - } - - @Override - public boolean onSingleTapUp(MotionEvent e) { - select(mCurrentSelection, false); - int index = computeSelectedIndex(e); - if (index >= 0 && index < mGallery.mAllImages.getCount()) { - onSelect(index); - return true; - } - return false; - } - }); -// mGestureDetector.setIsLongpressEnabled(false); - } - - public GridViewSpecial(Context context, AttributeSet attrs, int defStyle) { - super(context, attrs, defStyle); - init(context); - } - - public GridViewSpecial(Context context, AttributeSet attrs) { - super(context, attrs); - init(context); - } - - public GridViewSpecial(Context context) { - super(context); - init(context); - } - - @Override - protected int computeVerticalScrollRange() { - return mMaxScrollY + getHeight(); - } - - public void setSizeChoice(int choice, int scrollY) { - mSizeChoice = choice; - clearCache(); - scrollTo(0, scrollY); - requestLayout(); - invalidate(); - } - - /** - * - * @param newSel -2 means use old selection, -1 means remove selection - * @param newPressed - */ - public void select(int newSel, boolean newPressed) { - if (newSel == -2) { - newSel = mCurrentSelection; - } - int oldSel = mCurrentSelection; - if ((oldSel == newSel) && (mCurrentSelectionPressed == newPressed)) - return; - - mShowSelection = (newSel != -1); - mCurrentSelection = newSel; - mCurrentSelectionPressed = newPressed; - if (mImageBlockManager != null) { - mImageBlockManager.repaintSelection(oldSel); - mImageBlockManager.repaintSelection(newSel); - } - - if (newSel != -1) - ensureVisible(newSel); - } - - private void ensureVisible(int pos) { - android.graphics.Rect r = getRectForPosition(pos); - int top = getScrollY(); - int bot = top + getHeight(); - - if (r.bottom > bot) { - mScroller = new Scroller(getContext()); - mScroller.startScroll(mScrollX, mScrollY, 0, r.bottom - getHeight() - mScrollY, 200); - computeScroll(); - } else if (r.top < top) { - mScroller = new Scroller(getContext()); - mScroller.startScroll(mScrollX, mScrollY, 0, r.top - mScrollY, 200); - computeScroll(); - } - invalidate(); - } - - public void start() { - if (mGallery.mLayoutComplete) { - if (mImageBlockManager == null) { - mImageBlockManager = new ImageBlockManager(); - mImageBlockManager.moveDataWindow(true, true); - } - } - } - - public void onPause() { - mScroller = null; - if (mImageBlockManager != null) { - mImageBlockManager.onPause(); - mImageBlockManager = null; - } - } - - public void clearCache() { - if (mImageBlockManager != null) { - mImageBlockManager.onPause(); - mImageBlockManager = null; - } - } - - - @Override - public void onLayout(boolean changed, int left, int top, int right, int bottom) { - super.onLayout(changed, left, top, right, bottom); - - if (mGallery.isFinishing() || mGallery.mPausing) { - return; - } - - clearCache(); - - mCurrentSpec = mCellSizeChoices[mSizeChoice]; - int oldColumnCount = mCurrentSpec.mColumns; - - int width = right - left; - mCurrentSpec.mColumns = 1; - width -= mCurrentSpec.mCellWidth; - mCurrentSpec.mColumns += width / (mCurrentSpec.mCellWidth + mCurrentSpec.mCellSpacing); - - mCurrentSpec.mLeftEdgePadding = ((right - left) - ((mCurrentSpec.mColumns - 1) * mCurrentSpec.mCellSpacing) - (mCurrentSpec.mColumns * mCurrentSpec.mCellWidth)) / 2; - mCurrentSpec.mRightEdgePadding = mCurrentSpec.mLeftEdgePadding; - - int rows = (mGallery.mAllImages.getCount() + mCurrentSpec.mColumns - 1) / mCurrentSpec.mColumns; - mMaxScrollY = mCurrentSpec.mCellSpacing + (rows * (mCurrentSpec.mCellSpacing + mCurrentSpec.mCellHeight)) - (bottom - top) + mMaxOvershoot; - mMinScrollY = 0 - mMaxOvershoot; - - mGallery.mLayoutComplete = true; - - start(); - - if (mGallery.mSortAscending && mGallery.mTargetScroll == 0) { - scrollTo(0, mMaxScrollY - mMaxOvershoot); - } else { - if (oldColumnCount != 0) { - int y = mGallery.mTargetScroll * oldColumnCount / mCurrentSpec.mColumns; - Log.v(TAG, "target was " + mGallery.mTargetScroll + " now " + y); - scrollTo(0, y); - } - } - } - - Bitmap scaleTo(int width, int height, Bitmap b) { - Matrix m = new Matrix(); - m.setScale((float)width/64F, (float)height/64F); - Bitmap b2 = Bitmap.createBitmap(b, 0, 0, b.getWidth(), b.getHeight(), m, false); - if (b2 != b) - b.recycle(); - return b2; - } - - private class ImageBlockManager { - private ImageLoader mLoader; - private int mBlockCacheFirstBlockNumber = 0; - - // mBlockCache is an array with a starting point which is not necessaryily - // zero. The first element of the array is indicated by mBlockCacheStartOffset. - private int mBlockCacheStartOffset = 0; - private ImageBlock [] mBlockCache; - - private static final int sRowsPerPage = 6; // should compute this - - private static final int sPagesPreCache = 2; - private static final int sPagesPostCache = 2; - - private int mWorkCounter = 0; - private boolean mDone = false; - - private Thread mWorkerThread; - private Bitmap mMissingImageThumbnailBitmap; - private Bitmap mMissingVideoThumbnailBitmap; - - private Drawable mVideoOverlay; - private Drawable mVideoMmsErrorOverlay; - - public void dump() { - synchronized (ImageBlockManager.this) { - StringBuilder line1 = new StringBuilder(); - StringBuilder line2 = new StringBuilder(); - if (Config.LOGV) - Log.v(TAG, ">>> mBlockCacheFirstBlockNumber: " + mBlockCacheFirstBlockNumber + " " + mBlockCacheStartOffset); - for (int i = 0; i < mBlockCache.length; i++) { - int index = (mBlockCacheStartOffset + i) % mBlockCache.length; - ImageBlock block = mBlockCache[index]; - block.dump(line1, line2); - } - if (Config.LOGV){ - Log.v(TAG, line1.toString()); - Log.v(TAG, line2.toString()); - } - } - } - - ImageBlockManager() { - mLoader = new ImageLoader(mHandler, 1); - - mBlockCache = new ImageBlock[sRowsPerPage * (sPagesPreCache + sPagesPostCache + 1)]; - for (int i = 0; i < mBlockCache.length; i++) { - mBlockCache[i] = new ImageBlock(); - } - - mWorkerThread = new Thread(new Runnable() { - public void run() { - while (true) { - int workCounter; - synchronized (ImageBlockManager.this) { - workCounter = mWorkCounter; - } - if (mDone) { - if (Config.LOGV) - Log.v(TAG, "stopping the loader here " + Thread.currentThread().getName()); - if (mLoader != null) { - mLoader.stop(); - } - if (mBlockCache != null) { - for (int i = 0; i < mBlockCache.length; i++) { - ImageBlock block = mBlockCache[i]; - if (block != null) { - block.recycleBitmaps(); - mBlockCache[i] = null; - } - } - } - mBlockCache = null; - mBlockCacheStartOffset = 0; - mBlockCacheFirstBlockNumber = 0; - - break; - } - - loadNext(); - - synchronized (ImageBlockManager.this) { - if ((workCounter == mWorkCounter) && (! mDone)) { - try { - ImageBlockManager.this.wait(); - } catch (InterruptedException ex) { - } - } - } - } - } - }); - mWorkerThread.setName("image-block-manager"); - mWorkerThread.start(); - } - - // Create this bitmap lazily, and only once for all the ImageBlocks to use - public Bitmap getErrorBitmap(ImageManager.IImage image) { - if (ImageManager.isImage(image)) { - if (mMissingImageThumbnailBitmap == null) { - mMissingImageThumbnailBitmap = BitmapFactory.decodeResource(GridViewSpecial.this.getResources(), - R.drawable.ic_missing_thumbnail_picture); - } - return mMissingImageThumbnailBitmap; - } else { - if (mMissingVideoThumbnailBitmap == null) { - mMissingVideoThumbnailBitmap = BitmapFactory.decodeResource(GridViewSpecial.this.getResources(), - R.drawable.ic_missing_thumbnail_video); - } - return mMissingVideoThumbnailBitmap; - } - } - - private ImageBlock getBlockForPos(int pos) { - synchronized (ImageBlockManager.this) { - int blockNumber = pos / mCurrentSpec.mColumns; - int delta = blockNumber - mBlockCacheFirstBlockNumber; - if (delta >= 0 && delta < mBlockCache.length) { - int index = (mBlockCacheStartOffset + delta) % mBlockCache.length; - ImageBlock b = mBlockCache[index]; - return b; - } - } - return null; - } - - private void repaintSelection(int pos) { - synchronized (ImageBlockManager.this) { - ImageBlock b = getBlockForPos(pos); - if (b != null) { - b.repaintSelection(); - } - } - } - - private void onPause() { - synchronized (ImageBlockManager.this) { - mDone = true; - ImageBlockManager.this.notify(); - } - if (mWorkerThread != null) { - try { - mWorkerThread.join(); - mWorkerThread = null; - } catch (InterruptedException ex) { - // - } - } - Log.v(TAG, "/ImageBlockManager.onPause"); - } - - private void getVisibleRange(int [] range) { - // try to work around a possible bug in the VM wherein this appears to be null - try { - synchronized (ImageBlockManager.this) { - int blockLength = mBlockCache.length; - boolean lookingForStart = true; - ImageBlock prevBlock = null; - for (int i = 0; i < blockLength; i++) { - int index = (mBlockCacheStartOffset + i) % blockLength; - ImageBlock block = mBlockCache[index]; - if (lookingForStart) { - if (block.mIsVisible) { - range[0] = block.mBlockNumber * mCurrentSpec.mColumns; - lookingForStart = false; - } - } else { - if (!block.mIsVisible || i == blockLength - 1) { - range[1] = (prevBlock.mBlockNumber * mCurrentSpec.mColumns) + mCurrentSpec.mColumns - 1; - break; - } - } - prevBlock = block; - } - } - } catch (NullPointerException ex) { - Log.e(TAG, "this is somewhat null, what up?"); - range[0] = range[1] = 0; - } - } - - private void loadNext() { - final int blockHeight = (mCurrentSpec.mCellSpacing + mCurrentSpec.mCellHeight); - - final int firstVisBlock = Math.max(0, (mScrollY - mCurrentSpec.mCellSpacing) / blockHeight); - final int lastVisBlock = (mScrollY - mCurrentSpec.mCellSpacing + getHeight()) / blockHeight; - -// Log.v(TAG, "firstVisBlock == " + firstVisBlock + "; lastVisBlock == " + lastVisBlock); - - synchronized (ImageBlockManager.this) { - ImageBlock [] blocks = mBlockCache; - int numBlocks = blocks.length; - if (mDirectionBiasDown) { - int first = (mBlockCacheStartOffset + (firstVisBlock - mBlockCacheFirstBlockNumber)) % blocks.length; - for (int i = 0; i < numBlocks; i++) { - int j = first + i; - if (j >= numBlocks) - j -= numBlocks; - ImageBlock b = blocks[j]; - if (b.startLoading() > 0) - break; - } - } else { - int first = (mBlockCacheStartOffset + (lastVisBlock - mBlockCacheFirstBlockNumber)) % blocks.length; - for (int i = 0; i < numBlocks; i++) { - int j = first - i; - if (j < 0) - j += numBlocks; - ImageBlock b = blocks[j]; - if (b.startLoading() > 0) - break; - } - } - if (sDump) - this.dump(); - } - } - - private void moveDataWindow(boolean directionBiasDown, boolean forceRefresh) { - final int blockHeight = (mCurrentSpec.mCellSpacing + mCurrentSpec.mCellHeight); - - final int firstVisBlock = (mScrollY - mCurrentSpec.mCellSpacing) / blockHeight; - final int lastVisBlock = (mScrollY - mCurrentSpec.mCellSpacing + getHeight()) / blockHeight; - - final int preCache = sPagesPreCache; - final int startBlock = Math.max(0, firstVisBlock - (preCache * sRowsPerPage)); - -// Log.v(TAG, "moveDataWindow directionBiasDown == " + directionBiasDown + "; preCache is " + preCache); - synchronized (ImageBlockManager.this) { - boolean any = false; - ImageBlock [] blocks = mBlockCache; - int numBlocks = blocks.length; - - int delta = startBlock - mBlockCacheFirstBlockNumber; - - mBlockCacheFirstBlockNumber = startBlock; - if (Math.abs(delta) > numBlocks || forceRefresh) { - for (int i = 0; i < numBlocks; i++) { - int blockNum = startBlock + i; - blocks[i].setStart(blockNum); - any = true; - } - mBlockCacheStartOffset = 0; - } else if (delta > 0) { - mBlockCacheStartOffset += delta; - if (mBlockCacheStartOffset >= numBlocks) - mBlockCacheStartOffset -= numBlocks; - - for (int i = delta; i > 0; i--) { - int index = (mBlockCacheStartOffset + numBlocks - i) % numBlocks; - int blockNum = mBlockCacheFirstBlockNumber + numBlocks - i; - blocks[index].setStart(blockNum); - any = true; - } - } else if (delta < 0) { - mBlockCacheStartOffset += delta; - if (mBlockCacheStartOffset < 0) - mBlockCacheStartOffset += numBlocks; - - for (int i = 0; i < -delta; i++) { - int index = (mBlockCacheStartOffset + i) % numBlocks; - int blockNum = mBlockCacheFirstBlockNumber + i; - blocks[index].setStart(blockNum); - any = true; - } - } - - for (int i = 0; i < numBlocks; i++) { - int index = (mBlockCacheStartOffset + i) % numBlocks; - ImageBlock block = blocks[index]; - int blockNum = block.mBlockNumber; // mBlockCacheFirstBlockNumber + i; - boolean isVis = blockNum >= firstVisBlock && blockNum <= lastVisBlock; -// Log.v(TAG, "blockNum " + blockNum + " setting vis to " + isVis); - block.setVisibility(isVis); - } - - if (sDump) - mImageBlockManager.dump(); - - if (any) { - ImageBlockManager.this.notify(); - mWorkCounter += 1; - } - } - if (sDump) - dump(); - } - - private void check() { - ImageBlock [] blocks = mBlockCache; - int blockLength = blocks.length; - - // check the results - for (int i = 0; i < blockLength; i++) { - int index = (mBlockCacheStartOffset + i) % blockLength; - if (blocks[index].mBlockNumber != mBlockCacheFirstBlockNumber + i) { - if (blocks[index].mBlockNumber != -1) - Log.e(TAG, "at " + i + " block cache corrupted; found " + blocks[index].mBlockNumber + " but wanted " + (mBlockCacheFirstBlockNumber + i) + "; offset is " + mBlockCacheStartOffset); - } - } - if (true) { - StringBuilder sb = new StringBuilder(); - for (int i = 0; i < blockLength; i++) { - int index = (mBlockCacheStartOffset + i) % blockLength; - ImageBlock b = blocks[index]; - if (b.mRequestedMask != 0) - sb.append("X"); - else - sb.append(String.valueOf(b.mBlockNumber) + " "); - } - if (Config.LOGV) - Log.v(TAG, "moveDataWindow " + sb.toString()); - } - } - - void doDraw(Canvas canvas) { - synchronized (ImageBlockManager.this) { - ImageBlockManager.ImageBlock [] blocks = mBlockCache; - int blockCount = 0; - - if (blocks[0] == null) { - return; - } - - final int thisHeight = getHeight(); - final int thisWidth = getWidth(); - final int height = blocks[0].mBitmap.getHeight(); - final int scrollPos = mScrollY; - - int currentBlock = (scrollPos < 0) ? ((scrollPos-height+1) / height) : (scrollPos / height); - - while (true) { - final int yPos = currentBlock * height; - if (yPos >= scrollPos + thisHeight) - break; - - if (currentBlock < 0) { - canvas.drawRect(0, yPos, thisWidth, 0, mGridViewPaint); - currentBlock += 1; - continue; - } - int effectiveOffset = (mBlockCacheStartOffset + (currentBlock++ - mBlockCacheFirstBlockNumber)) % blocks.length; - if (effectiveOffset < 0 || effectiveOffset >= blocks.length) { - break; - } - - ImageBlock block = blocks[effectiveOffset]; - if (block == null) { - break; - } - synchronized (block) { - Bitmap b = block.mBitmap; - if (b == null) { - break; - } - canvas.drawBitmap(b, 0, yPos, mGridViewPaint); - blockCount += 1; - } - } - } - } - - int blockHeight() { - return mCurrentSpec.mCellSpacing + mCurrentSpec.mCellHeight; - } - - private class ImageBlock { - Drawable mCellOutline; - Bitmap mBitmap = Bitmap.createBitmap(getWidth(), blockHeight(), - Bitmap.Config.RGB_565);; - Canvas mCanvas = new Canvas(mBitmap); - Paint mPaint = new Paint(); - - int mBlockNumber; - int mRequestedMask; // columns which have been requested to the loader - int mCompletedMask; // columns which have been completed from the loader - boolean mIsVisible; - - public void dump(StringBuilder line1, StringBuilder line2) { - synchronized (ImageBlock.this) { -// Log.v(TAG, "block " + mBlockNumber + " isVis == " + mIsVisible); - line2.append(mCompletedMask != 0xF ? 'L' : '_'); - line1.append(mIsVisible ? 'V' : ' '); - } - } - - ImageBlock() { - mPaint.setTextSize(14F); - mPaint.setStyle(Paint.Style.FILL); - - mBlockNumber = -1; - mCellOutline = GridViewSpecial.this.getResources().getDrawable(android.R.drawable.gallery_thumb); - } - - private void recycleBitmaps() { - synchronized (ImageBlock.this) { - mBitmap.recycle(); - mBitmap = null; - } - } - - private void cancelExistingRequests() { - synchronized (ImageBlock.this) { - for (int i = 0; i < mCurrentSpec.mColumns; i++) { - int mask = (1 << i); - if ((mRequestedMask & mask) != 0) { - int pos = (mBlockNumber * mCurrentSpec.mColumns) + i; - if (mLoader.cancel(mGallery.mAllImages.getImageAt(pos))) { - mRequestedMask &= ~mask; - } - } - } - } - } - - private void setStart(final int blockNumber) { - synchronized (ImageBlock.this) { - if (blockNumber == mBlockNumber) - return; - - cancelExistingRequests(); - - mBlockNumber = blockNumber; - mRequestedMask = 0; - mCompletedMask = 0; - mCanvas.drawColor(0xFF000000); - mPaint.setColor(0xFFDDDDDD); - int imageNumber = blockNumber * mCurrentSpec.mColumns; - int lastImageNumber = mGallery.mAllImages.getCount() - 1; - - int spacing = mCurrentSpec.mCellSpacing; - int leftSpacing = mCurrentSpec.mLeftEdgePadding; - - final int yPos = spacing; - - for (int col = 0; col < mCurrentSpec.mColumns; col++) { - if (imageNumber++ >= lastImageNumber) - break; - final int xPos = leftSpacing + (col * (mCurrentSpec.mCellWidth + spacing)); - mCanvas.drawRect(xPos, yPos, xPos+mCurrentSpec.mCellWidth, yPos+mCurrentSpec.mCellHeight, mPaint); - paintSel(0, xPos, yPos); - } - } - } - - private boolean setVisibility(boolean isVis) { - synchronized (ImageBlock.this) { - boolean retval = mIsVisible != isVis; - mIsVisible = isVis; - return retval; - } - } - - private int startLoading() { - synchronized (ImageBlock.this) { - final int startRow = mBlockNumber; - int count = mGallery.mAllImages.getCount(); - - if (startRow == -1) - return 0; - - if ((startRow * mCurrentSpec.mColumns) >= count) { - return 0; - } - - int retVal = 0; - int base = (mBlockNumber * mCurrentSpec.mColumns); - for (int col = 0; col < mCurrentSpec.mColumns; col++) { - if ((mCompletedMask & (1 << col)) != 0) { - continue; - } - - int spacing = mCurrentSpec.mCellSpacing; - int leftSpacing = mCurrentSpec.mLeftEdgePadding; - final int yPos = spacing; - final int xPos = leftSpacing + (col * (mCurrentSpec.mCellWidth + spacing)); - - int pos = base + col; - if (pos >= count) - break; - - ImageManager.IImage image = mGallery.mAllImages.getImageAt(pos); - if (image != null) { -// Log.v(TAG, "calling loadImage " + (base + col)); - loadImage(base, col, image, xPos, yPos); - retVal += 1; - } - } - return retVal; - - } - } - - Bitmap resizeBitmap(Bitmap b) { - // assume they're both square for now - if (b == null || (b.getWidth() == mCurrentSpec.mCellWidth && b.getHeight() == mCurrentSpec.mCellHeight)) { - return b; - } - float scale = (float) mCurrentSpec.mCellWidth / (float)b.getWidth(); - Matrix m = new Matrix(); - m.setScale(scale, scale, b.getWidth(), b.getHeight()); - Bitmap b2 = Bitmap.createBitmap(b, 0, 0, b.getWidth(), b.getHeight(), m, false); - return b2; - } - - private void drawBitmap(ImageManager.IImage image, int base, int baseOffset, Bitmap b, int xPos, int yPos) { - mCanvas.setBitmap(mBitmap); - if (b != null) { - // if the image is close to the target size then crop, otherwise scale - // both the bitmap and the view should be square but I suppose that could - // change in the future. - int w = mCurrentSpec.mCellWidth; - int h = mCurrentSpec.mCellHeight; - - int bw = b.getWidth(); - int bh = b.getHeight(); - - int deltaW = bw - w; - int deltaH = bh - h; - - if (deltaW < 10 && deltaH < 10) { - int halfDeltaW = deltaW / 2; - int halfDeltaH = deltaH / 2; - android.graphics.Rect src = new android.graphics.Rect(0+halfDeltaW, 0+halfDeltaH, bw-halfDeltaW, bh-halfDeltaH); - android.graphics.Rect dst = new android.graphics.Rect(xPos, yPos, xPos+w, yPos+h); - if (src.width() != dst.width() || src.height() != dst.height()) { - if (Config.LOGV){ - Log.v(TAG, "nope... width doesn't match " + src.width() + " " + dst.width()); - Log.v(TAG, "nope... height doesn't match " + src.height() + " " + dst.height()); - } - } - mCanvas.drawBitmap(b, src, dst, mPaint); - } else { - android.graphics.Rect src = new android.graphics.Rect(0, 0, bw, bh); - android.graphics.Rect dst = new android.graphics.Rect(xPos, yPos, xPos+w, yPos+h); - mCanvas.drawBitmap(b, src, dst, mPaint); - } - } else { - // If the thumbnail cannot be drawn, put up an error icon instead - Bitmap error = mImageBlockManager.getErrorBitmap(image); - int width = error.getWidth(); - int height = error.getHeight(); - Rect source = new Rect(0, 0, width, height); - int left = (mCurrentSpec.mCellWidth - width) / 2 + xPos; - int top = (mCurrentSpec.mCellHeight - height) / 2 + yPos; - Rect dest = new Rect(left, top, left + width, top + height); - mCanvas.drawBitmap(error, source, dest, mPaint); - } - if (ImageManager.isVideo(image)) { - Drawable overlay = null; - if (MenuHelper.getImageFileSize(image) <= mVideoSizeLimit) { - if (mVideoOverlay == null) { - mVideoOverlay = getResources().getDrawable( - R.drawable.ic_gallery_video_overlay); - } - overlay = mVideoOverlay; - } else { - if (mVideoMmsErrorOverlay == null) { - mVideoMmsErrorOverlay = getResources().getDrawable( - R.drawable.ic_error_mms_video_overlay); - } - overlay = mVideoMmsErrorOverlay; - Paint paint = new Paint(); - paint.setARGB(0x80, 0x00, 0x00, 0x00); - mCanvas.drawRect(xPos, yPos, xPos + mCurrentSpec.mCellWidth, - yPos + mCurrentSpec.mCellHeight, paint); - } - int width = overlay.getIntrinsicWidth(); - int height = overlay.getIntrinsicHeight(); - int left = (mCurrentSpec.mCellWidth - width) / 2 + xPos; - int top = (mCurrentSpec.mCellHeight - height) / 2 + yPos; - Rect newBounds = new Rect(left, top, left + width, top + height); - overlay.setBounds(newBounds); - overlay.draw(mCanvas); - } - paintSel(base + baseOffset, xPos, yPos); - } - - private void repaintSelection() { - int count = mGallery.mAllImages.getCount(); - int startPos = mBlockNumber * mCurrentSpec.mColumns; - synchronized (ImageBlock.this) { - for (int i = 0; i < mCurrentSpec.mColumns; i++) { - int pos = startPos + i; - - if (pos >= count) - break; - - int row = 0; // i / mCurrentSpec.mColumns; - int col = i - (row * mCurrentSpec.mColumns); - - // this is duplicated from getOrKick (TODO: don't duplicate this code) - int spacing = mCurrentSpec.mCellSpacing; - int leftSpacing = mCurrentSpec.mLeftEdgePadding; - final int yPos = spacing + (row * (mCurrentSpec.mCellHeight + spacing)); - final int xPos = leftSpacing + (col * (mCurrentSpec.mCellWidth + spacing)); - - paintSel(pos, xPos, yPos); - } - } - } - - private void paintSel(int pos, int xPos, int yPos) { - int[] stateSet = EMPTY_STATE_SET; - if (pos == mCurrentSelection && mShowSelection) { - if (mCurrentSelectionPressed) { - stateSet = PRESSED_ENABLED_FOCUSED_SELECTED_WINDOW_FOCUSED_STATE_SET; - } else { - stateSet = ENABLED_FOCUSED_SELECTED_WINDOW_FOCUSED_STATE_SET; - } - } - - mCellOutline.setState(stateSet); - mCanvas.setBitmap(mBitmap); - mCellOutline.setBounds(xPos, yPos, xPos+mCurrentSpec.mCellWidth, yPos+mCurrentSpec.mCellHeight); - mCellOutline.draw(mCanvas); - } - - private void loadImage( - final int base, - final int baseOffset, - final ImageManager.IImage image, - final int xPos, - final int yPos) { - synchronized (ImageBlock.this) { - final int startBlock = mBlockNumber; - final int pos = base + baseOffset; - final ImageLoader.LoadedCallback r = new ImageLoader.LoadedCallback() { - public void run(Bitmap b) { - boolean more = false; - synchronized (ImageBlock.this) { - if (startBlock != mBlockNumber) { -// Log.v(TAG, "wanted block " + mBlockNumber + " but got " + startBlock); - return; - } - - if (mBitmap == null) { - return; - } - - drawBitmap(image, base, baseOffset, b, xPos, yPos); - - int mask = (1 << baseOffset); - mRequestedMask &= ~mask; - mCompletedMask |= mask; - - // Log.v(TAG, "for " + mBlockNumber + " mRequestedMask is " + String.format("%x", mRequestedMask) + " and mCompletedMask is " + String.format("%x", mCompletedMask)); - - if (mRequestedMask == 0) { - if (mIsVisible) { - postInvalidate(); - } - more = true; - } - } - if (b != null) - b.recycle(); - - if (more) { - synchronized (ImageBlockManager.this) { - ImageBlockManager.this.notify(); - mWorkCounter += 1; - } - } - if (sDump) - ImageBlockManager.this.dump(); - } - }; - mRequestedMask |= (1 << baseOffset); - mLoader.getBitmap(image, pos, r, mIsVisible, false); - } - } - } - } - - public void init(Handler handler) { - mHandler = handler; - } - - public void onDraw(Canvas canvas) { - super.onDraw(canvas); - if (false) { - canvas.drawRect(0, 0, getWidth(), getHeight(), mGridViewPaint); - if (Config.LOGV) - Log.v(TAG, "painting background w/h " + getWidth() + " / " + getHeight()); - return; - } - - if (mImageBlockManager != null) { - mImageBlockManager.doDraw(canvas); - mImageBlockManager.moveDataWindow(mDirectionBiasDown, false); - } - } - - @Override - public void computeScroll() { - if (mScroller != null) { - boolean more = mScroller.computeScrollOffset(); - scrollTo(0, (int)mScroller.getCurrY()); - if (more) { - postInvalidate(); // So we draw again - } else { - mScroller = null; - } - } else { - super.computeScroll(); - } - } - - private android.graphics.Rect getRectForPosition(int pos) { - int row = pos / mCurrentSpec.mColumns; - int col = pos - (row * mCurrentSpec.mColumns); - - int left = mCurrentSpec.mLeftEdgePadding + (col * mCurrentSpec.mCellWidth) + (Math.max(0, col-1) * mCurrentSpec.mCellSpacing); - int top = (row * mCurrentSpec.mCellHeight) + (row * mCurrentSpec.mCellSpacing); - - return new android.graphics.Rect(left, top, left + mCurrentSpec.mCellWidth + mCurrentSpec.mCellWidth, top + mCurrentSpec.mCellHeight + mCurrentSpec.mCellSpacing); - } - - int computeSelectedIndex(android.view.MotionEvent ev) { - int spacing = mCurrentSpec.mCellSpacing; - int leftSpacing = mCurrentSpec.mLeftEdgePadding; - - int x = (int) ev.getX(); - int y = (int) ev.getY(); - int row = (mScrollY + y - spacing) / (mCurrentSpec.mCellHeight + spacing); - int col = Math.min(mCurrentSpec.mColumns - 1, (x - leftSpacing) / (mCurrentSpec.mCellWidth + spacing)); - return (row * mCurrentSpec.mColumns) + col; - } - - @Override - public boolean onTouchEvent(android.view.MotionEvent ev) { - mGestureDetector.onTouchEvent(ev); - return true; - } - - private void onSelect(int index) { - if (index >= 0 && index < mGallery.mAllImages.getCount()) { - ImageManager.IImage img = mGallery.mAllImages.getImageAt(index); - if (img == null) - return; - - if (mGallery.isPickIntent()) { - mGallery.launchCropperOrFinish(img); - } else { - Uri targetUri = img.fullSizeImageUri(); - Uri thisUri = mGallery.getIntent().getData(); - if (thisUri != null) { - String bucket = thisUri.getQueryParameter("bucketId"); - if (bucket != null) { - targetUri = targetUri.buildUpon().appendQueryParameter("bucketId", bucket).build(); - } - } - Intent intent = new Intent(Intent.ACTION_VIEW, targetUri); - - if (img instanceof ImageManager.VideoObject) { - intent.putExtra(MediaStore.EXTRA_SCREEN_ORIENTATION, - ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE); - } - - try { - mContext.startActivity(intent); - } catch (Exception ex) { - // sdcard removal?? - } - } - } - } - - @Override - public void scrollBy(int x, int y) { - scrollTo(x, mScrollY + y); - } - - Toast mDateLocationToast; - int [] mDateRange = new int[2]; - - private String month(int month) { - String text = ""; - switch (month) { - case 0: text = "January"; break; - case 1: text = "February"; break; - case 2: text = "March"; break; - case 3: text = "April"; break; - case 4: text = "May"; break; - case 5: text = "June"; break; - case 6: text = "July"; break; - case 7: text = "August"; break; - case 8: text = "September"; break; - case 9: text = "October"; break; - case 10: text = "November"; break; - case 11: text = "December"; break; - } - return text; - } - - Runnable mToastRunnable = new Runnable() { - public void run() { - if (mDateLocationToast != null) { - mDateLocationToast.cancel(); - mDateLocationToast = null; - } - - int count = mGallery.mAllImages.getCount(); - if (count == 0) - return; - - GridViewSpecial.this.mImageBlockManager.getVisibleRange(mDateRange); - - ImageManager.IImage firstImage = mGallery.mAllImages.getImageAt(mDateRange[0]); - int lastOffset = Math.min(count-1, mDateRange[1]); - ImageManager.IImage lastImage = mGallery.mAllImages.getImageAt(lastOffset); - - GregorianCalendar dateStart = new GregorianCalendar(); - GregorianCalendar dateEnd = new GregorianCalendar(); - - dateStart.setTimeInMillis(firstImage.getDateTaken()); - dateEnd.setTimeInMillis(lastImage.getDateTaken()); - - String text1 = month(dateStart.get(Calendar.MONTH)) + " " + dateStart.get(Calendar.YEAR); - String text2 = month(dateEnd .get(Calendar.MONTH)) + " " + dateEnd .get(Calendar.YEAR); - - String text = text1; - if (!text2.equals(text1)) - text = text + " : " + text2; - - mDateLocationToast = Toast.makeText(mContext, text, Toast.LENGTH_LONG); - mDateLocationToast.show(); - } - }; - - @Override - public void scrollTo(int x, int y) { - y = Math.min(mMaxScrollY, y); - y = Math.max(mMinScrollY, y); - if (y > mScrollY) - mDirectionBiasDown = true; - else if (y < mScrollY) - mDirectionBiasDown = false; - super.scrollTo(x, y); - } - } -} diff --git a/src/com/android/camera/ImageLoader.java b/src/com/android/camera/ImageLoader.java deleted file mode 100644 index e398fba..0000000 --- a/src/com/android/camera/ImageLoader.java +++ /dev/null @@ -1,342 +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.camera; - -import java.util.ArrayList; - -import android.graphics.Bitmap; -import android.graphics.Canvas; -import android.graphics.Matrix; -import android.graphics.Rect; -import android.net.Uri; -import android.util.Config; -import android.util.Log; - -class ImageLoader { - private static final String TAG = "ImageLoader"; - - // queue of work to do in the worker thread - private ArrayList<WorkItem> mQueue = new ArrayList<WorkItem>(); - private ArrayList<WorkItem> mInProgress = new ArrayList<WorkItem>(); - - // the worker thread and a done flag so we know when to exit - // currently we only exit from finalize - private boolean mDone; - private ArrayList<Thread> mDecodeThreads = new ArrayList<Thread>(); - private android.os.Handler mHandler; - - private int mThreadCount = 1; - - synchronized void clear(Uri uri) { - } - - synchronized public void dump() { - synchronized (mQueue) { - if (Config.LOGV) - Log.v(TAG, "Loader queue length is " + mQueue.size()); - } - } - - public interface LoadedCallback { - public void run(Bitmap result); - } - - public void pushToFront(final ImageManager.IImage image) { - synchronized (mQueue) { - WorkItem w = new WorkItem(image, 0, null, false); - - int existing = mQueue.indexOf(w); - if (existing >= 1) { - WorkItem existingWorkItem = mQueue.remove(existing); - mQueue.add(0, existingWorkItem); - mQueue.notifyAll(); - } - } - } - - public boolean cancel(final ImageManager.IImage image) { - synchronized (mQueue) { - WorkItem w = new WorkItem(image, 0, null, false); - - int existing = mQueue.indexOf(w); - if (existing >= 0) { - mQueue.remove(existing); - return true; - } - return false; - } - } - - public Bitmap getBitmap(final ImageManager.IImage image, final LoadedCallback imageLoadedRunnable, final boolean postAtFront, boolean postBack) { - return getBitmap(image, 0, imageLoadedRunnable, postAtFront, postBack); - } - - public Bitmap getBitmap(final ImageManager.IImage image, int tag, final LoadedCallback imageLoadedRunnable, final boolean postAtFront, boolean postBack) { - synchronized (mDecodeThreads) { - if (mDecodeThreads.size() == 0) { - start(); - } - } - long t1 = System.currentTimeMillis(); - long t2,t3,t4; - synchronized (mQueue) { - t2 = System.currentTimeMillis(); - WorkItem w = new WorkItem(image, tag, imageLoadedRunnable, postBack); - - if (!mInProgress.contains(w)) { - boolean contains = mQueue.contains(w); - if (contains) { - if (postAtFront) { - // move this item to the front - mQueue.remove(w); - mQueue.add(0, w); - } - } else { - if (postAtFront) - mQueue.add(0, w); - else - mQueue.add(w); - mQueue.notifyAll(); - } - } - if (false) - dumpQueue("+" + (postAtFront ? "F " : "B ") + tag + ": "); - t3 = System.currentTimeMillis(); - } - t4 = System.currentTimeMillis(); -// Log.v(TAG, "getBitmap breakdown: tot= " + (t4-t1) + "; " + "; " + (t4-t3) + "; " + (t3-t2) + "; " + (t2-t1)); - return null; - } - - private void dumpQueue(String s) { - synchronized (mQueue) { - StringBuilder sb = new StringBuilder(s); - for (int i = 0; i < mQueue.size(); i++) { - sb.append(mQueue.get(i).mTag + " "); - } - if (Config.LOGV) - Log.v(TAG, sb.toString()); - } - } - - long bitmapSize(Bitmap b) { - return b.getWidth() * b.getHeight() * 4; - } - - class WorkItem { - ImageManager.IImage mImage; - int mTargetX, mTargetY; - int mTag; - LoadedCallback mOnLoadedRunnable; - boolean mPostBack; - - WorkItem(ImageManager.IImage image, int tag, LoadedCallback onLoadedRunnable, boolean postBack) { - mImage = image; - mTag = tag; - mOnLoadedRunnable = onLoadedRunnable; - mPostBack = postBack; - } - - public boolean equals(Object other) { - WorkItem otherWorkItem = (WorkItem) other; - if (otherWorkItem.mImage != mImage) - return false; - - return true; - } - - public int hashCode() { - return mImage.fullSizeImageUri().hashCode(); - } - } - - public ImageLoader(android.os.Handler handler, int threadCount) { - mThreadCount = threadCount; - mHandler = handler; - start(); - } - - synchronized private void start() { - if (Config.LOGV) - Log.v(TAG, "ImageLoader.start() <<<<<<<<<<<<<<<<<<<<<<<<<<<<"); - - synchronized (mDecodeThreads) { - if (mDecodeThreads.size() > 0) - return; - - mDone = false; - for (int i = 0;i < mThreadCount; i++) { - Thread t = new Thread(new Runnable() { - // pick off items on the queue, one by one, and compute their bitmap. - // place the resulting bitmap in the cache. then post a notification - // back to the ui so things can get updated appropriately. - public void run() { - while (!mDone) { - WorkItem workItem = null; - synchronized (mQueue) { - if (mQueue.size() > 0) { - workItem = mQueue.remove(0); - mInProgress.add(workItem); - } - else { - try { - mQueue.wait(); - } catch (InterruptedException ex) { - } - } - } - if (workItem != null) { - if (false) - dumpQueue("-" + workItem.mTag + ": "); - Bitmap b = null; - try { - b = workItem.mImage.miniThumbBitmap(); - } catch (Exception ex) { - if (Config.LOGV) Log.v(TAG, "couldn't load miniThumbBitmap " + ex.toString()); - // sd card removal or sd card full - } - if (b == null) { - if (Config.LOGV) Log.v(TAG, "unable to read thumbnail for " + workItem.mImage.fullSizeImageUri()); - } - - synchronized (mQueue) { - mInProgress.remove(workItem); - } - - if (workItem.mOnLoadedRunnable != null) { - if (workItem.mPostBack) { - final WorkItem w1 = workItem; - final Bitmap bitmap = b; - if (!mDone) { - mHandler.post(new Runnable() { - public void run() { - w1.mOnLoadedRunnable.run(bitmap); - } - }); - } - } else { - workItem.mOnLoadedRunnable.run(b); - } - } - } - } - } - }); - t.setName("image-loader-" + i); - mDecodeThreads.add(t); - t.start(); - } - } - } - - public static Bitmap transform(Matrix scaler, Bitmap source, int targetWidth, int targetHeight, - boolean scaleUp) { - int deltaX = source.getWidth() - targetWidth; - int deltaY = source.getHeight() - targetHeight; - if (!scaleUp && (deltaX < 0 || deltaY < 0)) { - /* - * In this case the bitmap is smaller, at least in one dimension, than the - * target. Transform it by placing as much of the image as possible into - * the target and leaving the top/bottom or left/right (or both) black. - */ - Bitmap b2 = Bitmap.createBitmap(targetWidth, targetHeight, Bitmap.Config.ARGB_8888); - Canvas c = new Canvas(b2); - - int deltaXHalf = Math.max(0, deltaX/2); - int deltaYHalf = Math.max(0, deltaY/2); - Rect src = new Rect( - deltaXHalf, - deltaYHalf, - deltaXHalf + Math.min(targetWidth, source.getWidth()), - deltaYHalf + Math.min(targetHeight, source.getHeight())); - int dstX = (targetWidth - src.width()) / 2; - int dstY = (targetHeight - src.height()) / 2; - Rect dst = new Rect( - dstX, - dstY, - targetWidth - dstX, - targetHeight - dstY); - if (Config.LOGV) - Log.v(TAG, "draw " + src.toString() + " ==> " + dst.toString()); - c.drawBitmap(source, src, dst, null); - return b2; - } - float bitmapWidthF = source.getWidth(); - float bitmapHeightF = source.getHeight(); - - float bitmapAspect = bitmapWidthF / bitmapHeightF; - float viewAspect = (float) targetWidth / (float) targetHeight; - - if (bitmapAspect > viewAspect) { - float scale = targetHeight / bitmapHeightF; - if (scale < .9F || scale > 1F) { - scaler.setScale(scale, scale); - } else { - scaler = null; - } - } else { - float scale = targetWidth / bitmapWidthF; - if (scale < .9F || scale > 1F) { - scaler.setScale(scale, scale); - } else { - scaler = null; - } - } - - Bitmap b1; - if (scaler != null) { - // this is used for minithumb and crop, so we want to filter here. - b1 = Bitmap.createBitmap(source, 0, 0, - source.getWidth(), source.getHeight(), scaler, true); - } else { - b1 = source; - } - - int dx1 = Math.max(0, b1.getWidth() - targetWidth); - int dy1 = Math.max(0, b1.getHeight() - targetHeight); - - Bitmap b2 = Bitmap.createBitmap( - b1, - dx1/2, - dy1/2, - targetWidth, - targetHeight); - - if (b1 != source) - b1.recycle(); - - return b2; - } - - public void stop() { - if (Config.LOGV) - Log.v(TAG, "ImageLoader.stop " + mDecodeThreads.size() + " threads"); - mDone = true; - synchronized (mQueue) { - mQueue.notifyAll(); - } - while (mDecodeThreads.size() > 0) { - Thread t = mDecodeThreads.get(0); - try { - t.join(); - mDecodeThreads.remove(0); - } catch (InterruptedException ex) { - // so now what? - } - } - } -} diff --git a/src/com/android/camera/ImageManager.java b/src/com/android/camera/ImageManager.java deleted file mode 100755 index cc76e83..0000000 --- a/src/com/android/camera/ImageManager.java +++ /dev/null @@ -1,4195 +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.camera; - -import android.content.Context; -import android.content.ContentResolver; -import android.content.ContentValues; -import android.content.ContentUris; -import android.database.ContentObserver; -import android.database.Cursor; -import android.database.DataSetObserver; -import android.graphics.Bitmap; -import android.graphics.BitmapFactory; -import android.graphics.Canvas; -import android.graphics.Matrix; -import android.location.Location; -import android.media.MediaMetadataRetriever; -import android.media.MediaPlayer; -import android.net.Uri; -import android.os.Environment; -import android.os.Handler; -import android.os.ParcelFileDescriptor; -import android.provider.BaseColumns; -import android.provider.DrmStore; -import android.provider.MediaStore; -import android.provider.MediaStore.Images.ImageColumns; -import android.provider.MediaStore.Images.Thumbnails; -import android.provider.MediaStore.Video.VideoColumns; -import android.provider.MediaStore.Images; -import android.provider.MediaStore.MediaColumns; -import android.provider.MediaStore.Video; -import android.util.Config; -import android.util.Log; - -import java.io.File; -import java.io.FileNotFoundException; -import java.io.IOException; -import java.io.InputStream; -import java.io.OutputStream; -import java.io.RandomAccessFile; -import java.util.ArrayList; -import java.util.HashMap; - -/** - * - * ImageManager is used to retrieve and store images - * in the media content provider. - * - */ -public class ImageManager { - public static final String CAMERA_IMAGE_BUCKET_NAME = - Environment.getExternalStorageDirectory().toString() + "/DCIM/Camera"; - public static final String CAMERA_IMAGE_BUCKET_ID = getBucketId(CAMERA_IMAGE_BUCKET_NAME); - - /** - * Matches code in MediaProvider.computeBucketValues. Should be a common function. - */ - - public static String getBucketId(String path) { - return String.valueOf(path.toLowerCase().hashCode()); - } - - /** - * OSX requires plugged-in USB storage to have path /DCIM/NNNAAAAA to be imported. - * This is a temporary fix for bug#1655552. - */ - public static void ensureOSXCompatibleFolder() { - File nnnAAAAA = new File( - Environment.getExternalStorageDirectory().toString() + "/DCIM/100ANDRO"); - if ((!nnnAAAAA.exists()) && (!nnnAAAAA.mkdir())) { - Log.e(TAG, "create NNNAAAAA file: "+ nnnAAAAA.getPath()+" failed"); - } - } - - // To enable verbose logging for this class, change false to true. The other logic ensures that - // this logging can be disabled by turned off DEBUG and lower, and that it can be enabled by - // "setprop log.tag.ImageManager VERBOSE" if desired. - // - // IMPORTANT: Never check in this file set to true! - private static final boolean VERBOSE = Config.LOGD && (false || Config.LOGV); - private static final String TAG = "ImageManager"; - - private static final int MINI_THUMB_DATA_FILE_VERSION = 3; - - static public void debug_where(String tag, String msg) { - try { - throw new Exception(); - } catch (Exception ex) { - if (msg != null) { - Log.v(tag, msg); - } - boolean first = true; - for (StackTraceElement s : ex.getStackTrace()) { - if (first) - first = false; - else - Log.v(tag, s.toString()); - } - } - } - - /* - * Compute the sample size as a function of the image size and the target. - * Scale the image down so that both the width and height are just above - * the target. If this means that one of the dimension goes from above - * the target to below the target (e.g. given a width of 480 and an image - * width of 600 but sample size of 2 -- i.e. new width 300 -- bump the - * sample size down by 1. - */ - private static int computeSampleSize(BitmapFactory.Options options, int target) { - int w = options.outWidth; - int h = options.outHeight; - - int candidateW = w / target; - int candidateH = h / target; - int candidate = Math.max(candidateW, candidateH); - - if (candidate == 0) - return 1; - - if (candidate > 1) { - if ((w > target) && (w / candidate) < target) - candidate -= 1; - } - - if (candidate > 1) { - if ((h > target) && (h / candidate) < target) - candidate -= 1; - } - - if (VERBOSE) - Log.v(TAG, "for w/h " + w + "/" + h + " returning " + candidate + "(" + (w/candidate) + " / " + (h/candidate)); - - return candidate; - } - /* - * All implementors of ICancelable should inherit from BaseCancelable - * since it provides some convenience methods such as acknowledgeCancel - * and checkCancel. - */ - public abstract class BaseCancelable implements ICancelable { - boolean mCancel = false; - boolean mFinished = false; - - /* - * Subclasses should call acknowledgeCancel when they're finished with - * their operation. - */ - protected void acknowledgeCancel() { - synchronized (this) { - mFinished = true; - if (!mCancel) - return; - if (mCancel) { - this.notify(); - } - } - } - - public boolean cancel() { - synchronized (this) { - if (mCancel) { - return false; - } - if (mFinished) { - return false; - } - mCancel = true; - boolean retVal = doCancelWork(); - - try { - this.wait(); - } catch (InterruptedException ex) { - // now what??? TODO - } - - return retVal; - } - } - - /* - * Subclasses can call this to see if they have been canceled. - * This is the polling model. - */ - protected void checkCanceled() throws CanceledException { - synchronized (this) { - if (mCancel) - throw new CanceledException(); - } - } - - /* - * Subclasses implement this method to take whatever action - * is necessary when getting canceled. Sometimes it's not - * possible to do anything in which case the "checkCanceled" - * polling model may be used (or some combination). - */ - public abstract boolean doCancelWork(); - } - - private static final int sBytesPerMiniThumb = 10000; - static final private byte [] sMiniThumbData = new byte[sBytesPerMiniThumb]; - - /** - * Represents a particular image and provides access - * to the underlying bitmap and two thumbnail bitmaps - * as well as other information such as the id, and - * the path to the actual image data. - */ - abstract class BaseImage implements IImage { - protected ContentResolver mContentResolver; - protected long mId, mMiniThumbMagic; - protected BaseImageList mContainer; - protected HashMap<String, String> mExifData; - protected int mCursorRow; - - protected BaseImage(long id, long miniThumbId, ContentResolver cr, BaseImageList container, int cursorRow) { - mContentResolver = cr; - mId = id; - mMiniThumbMagic = miniThumbId; - mContainer = container; - mCursorRow = cursorRow; - } - - abstract Bitmap.CompressFormat compressionType(); - - public void commitChanges() { - Cursor c = getCursor(); - synchronized (c) { - if (c.moveToPosition(getRow())) { - c.commitUpdates(); - c.requery(); - } - } - } - - /** - * Take a given bitmap and compress it to a file as described - * by the Uri parameter. - * - * @param bitmap the bitmap to be compressed/stored - * @param uri where to store the bitmap - * @return true if we succeeded - */ - protected IGetBoolean_cancelable compressImageToFile( - final Bitmap bitmap, - final byte [] jpegData, - final Uri uri) { - class CompressImageToFile extends BaseCancelable implements IGetBoolean_cancelable { - ThreadSafeOutputStream mOutputStream = null; - - public boolean doCancelWork() { - if (mOutputStream != null) { - try { - mOutputStream.close(); - return true; - } catch (IOException ex) { - // TODO what to do here - } - } - return false; - } - - public boolean get() { - try { - long t1 = System.currentTimeMillis(); - OutputStream delegate = mContentResolver.openOutputStream(uri); - synchronized (this) { - checkCanceled(); - mOutputStream = new ThreadSafeOutputStream(delegate); - } - long t2 = System.currentTimeMillis(); - if (bitmap != null) { - bitmap.compress(compressionType(), 75, mOutputStream); - } else { - long x1 = System.currentTimeMillis(); - mOutputStream.write(jpegData); - long x2 = System.currentTimeMillis(); - if (VERBOSE) Log.v(TAG, "done writing... " + jpegData.length + " bytes took " + (x2-x1)); - } - long t3 = System.currentTimeMillis(); - if (VERBOSE) Log.v(TAG, String.format("CompressImageToFile.get took %d (%d, %d)",(t3-t1),(t2-t1),(t3-t2))); - return true; - } catch (FileNotFoundException ex) { - return false; - } catch (CanceledException ex) { - return false; - } catch (IOException ex) { - return false; - } - finally { - if (mOutputStream != null) { - try { - mOutputStream.close(); - } catch (IOException ex) { - // not much we can do here so ignore - } - } - acknowledgeCancel(); - } - } - } - return new CompressImageToFile(); - } - - @Override - public boolean equals(Object other) { - if (other == null) - return false; - if (!(other instanceof Image)) - return false; - - return fullSizeImageUri().equals(((Image)other).fullSizeImageUri()); - } - - public Bitmap fullSizeBitmap(int targetWidthHeight) { - return fullSizeBitmap(targetWidthHeight, true); - } - - protected Bitmap fullSizeBitmap(int targetWidthHeight, boolean rotateAsNeeded) { - Uri url = mContainer.contentUri(mId); - if (VERBOSE) Log.v(TAG, "getCreateBitmap for " + url); - if (url == null) - return null; - - Bitmap b = null; - if (b == null) { - b = makeBitmap(targetWidthHeight, url); - if (b != null && rotateAsNeeded) { - b = rotate(b, getDegreesRotated()); - } - } - return b; - } - - - public IGetBitmap_cancelable fullSizeBitmap_cancelable(final int targetWidthHeight) { - final class LoadBitmapCancelable extends BaseCancelable implements IGetBitmap_cancelable { - ParcelFileDescriptor mPFD; - BitmapFactory.Options mOptions = new BitmapFactory.Options(); - long mCancelInitiationTime; - - public LoadBitmapCancelable(ParcelFileDescriptor pfdInput) { - mPFD = pfdInput; - } - - public boolean doCancelWork() { - if (VERBOSE) - Log.v(TAG, "requesting bitmap load cancel"); - mCancelInitiationTime = System.currentTimeMillis(); - mOptions.requestCancelDecode(); - return true; - } - - public Bitmap get() { - try { - Bitmap b = makeBitmap(targetWidthHeight, fullSizeImageUri(), mPFD, mOptions); - if (mCancelInitiationTime != 0) { - if (VERBOSE) - Log.v(TAG, "cancelation of bitmap load success==" + (b == null ? "TRUE" : "FALSE") + " -- took " + (System.currentTimeMillis() - mCancelInitiationTime)); - } - if (b != null) { - int degrees = getDegreesRotated(); - if (degrees != 0) { - Matrix m = new Matrix(); - m.setRotate(degrees, (float) b.getWidth() / 2, (float) b.getHeight() / 2); - Bitmap b2 = Bitmap.createBitmap(b, 0, 0, b.getWidth(), b.getHeight(), m, true); - if (b != b2) - b.recycle(); - b = b2; - } - } - return b; - } catch (Exception ex) { - return null; - } finally { - acknowledgeCancel(); - } - } - } - - try { - ParcelFileDescriptor pfdInput = mContentResolver.openFileDescriptor(fullSizeImageUri(), "r"); - return new LoadBitmapCancelable(pfdInput); - } catch (FileNotFoundException ex) { - return null; - } catch (UnsupportedOperationException ex) { - return null; - } - } - - public InputStream fullSizeImageData() { - try { - InputStream input = mContentResolver.openInputStream( - fullSizeImageUri()); - return input; - } catch (IOException ex) { - return null; - } - } - - public long fullSizeImageId() { - return mId; - } - - public Uri fullSizeImageUri() { - return mContainer.contentUri(mId); - } - - public IImageList getContainer() { - return mContainer; - } - - Cursor getCursor() { - return mContainer.getCursor(); - } - - public long getDateTaken() { - if (mContainer.indexDateTaken() < 0) return 0; - Cursor c = getCursor(); - synchronized (c) { - c.moveToPosition(getRow()); - return c.getLong(mContainer.indexDateTaken()); - } - } - - protected int getDegreesRotated() { - return 0; - } - - public String getMimeType() { - if (mContainer.indexMimeType() < 0) { - Cursor c = null; - try { - c = mContentResolver.query( - fullSizeImageUri(), - new String[] { "_id", Images.Media.MIME_TYPE }, - null, - null, null); - if (c != null && c.moveToFirst()) { - return c.getString(1); - } else { - return ""; - } - } finally { - if (c != null) - c.close(); - } - } else { - String mimeType = null; - Cursor c = getCursor(); - synchronized(c) { - if (c.moveToPosition(getRow())) { - mimeType = c.getString(mContainer.indexMimeType()); - } - } - return mimeType; - } - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#getDescription() - */ - public String getDescription() { - if (mContainer.indexDescription() < 0) { - Cursor c = null; - try { - c = mContentResolver.query( - fullSizeImageUri(), - new String[] { "_id", Images.Media.DESCRIPTION }, - null, - null, null); - if (c != null && c.moveToFirst()) { - return c.getString(1); - } else { - return ""; - } - } finally { - if (c != null) - c.close(); - } - } else { - String description = null; - Cursor c = getCursor(); - synchronized(c) { - if (c.moveToPosition(getRow())) { - description = c.getString(mContainer.indexDescription()); - } - } - return description; - } - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#getIsPrivate() - */ - public boolean getIsPrivate() { - if (mContainer.indexPrivate() < 0) return false; - boolean isPrivate = false; - Cursor c = getCursor(); - synchronized(c) { - if (c.moveToPosition(getRow())) { - isPrivate = c.getInt(mContainer.indexPrivate()) != 0; - } - } - return isPrivate; - } - - public double getLatitude() { - if (mContainer.indexLatitude() < 0) return 0D; - Cursor c = getCursor(); - synchronized (c) { - c.moveToPosition(getRow()); - return c.getDouble(mContainer.indexLatitude()); - } - } - - public double getLongitude() { - if (mContainer.indexLongitude() < 0) return 0D; - Cursor c = getCursor(); - synchronized (c) { - c.moveToPosition(getRow()); - return c.getDouble(mContainer.indexLongitude()); - } - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#getTitle() - */ - public String getTitle() { - String name = null; - Cursor c = getCursor(); - synchronized(c) { - if (c.moveToPosition(getRow())) { - if (mContainer.indexTitle() != -1) { - name = c.getString(mContainer.indexTitle()); - } - } - } - return name != null && name.length() > 0 ? name : String.valueOf(mId); - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#getDisplayName() - */ - public String getDisplayName() { - if (mContainer.indexDisplayName() < 0) { - Cursor c = null; - try { - c = mContentResolver.query( - fullSizeImageUri(), - new String[] { "_id", Images.Media.DISPLAY_NAME }, - null, - null, null); - if (c != null && c.moveToFirst()) { - return c.getString(1); - } - } finally { - if (c != null) - c.close(); - } - } else { - String name = null; - Cursor c = getCursor(); - synchronized(c) { - if (c.moveToPosition(getRow())) { - name = c.getString(mContainer.indexDisplayName()); - } - } - if (name != null && name.length() > 0) - return name; - } - return String.valueOf(mId); - } - - public String getPicasaId() { - /* - if (mContainer.indexPicasaWeb() < 0) return null; - Cursor c = getCursor(); - synchronized (c) { - c.moveTo(getRow()); - return c.getString(mContainer.indexPicasaWeb()); - } - */ - return null; - } - - public int getRow() { - return mCursorRow; - } - - public int getWidth() { - ParcelFileDescriptor input = null; - try { - Uri uri = fullSizeImageUri(); - input = mContentResolver.openFileDescriptor(uri, "r"); - BitmapFactory.Options options = new BitmapFactory.Options(); - options.inJustDecodeBounds = true; - BitmapFactory.decodeFileDescriptor(input.getFileDescriptor(), null, options); - return options.outWidth; - } catch (IOException ex) { - return 0; - } finally { - try { - if (input != null) { - input.close(); - } - } catch (IOException ex) { - } - } - } - - public int getHeight() { - ParcelFileDescriptor input = null; - try { - Uri uri = fullSizeImageUri(); - input = mContentResolver.openFileDescriptor(uri, "r"); - BitmapFactory.Options options = new BitmapFactory.Options(); - options.inJustDecodeBounds = true; - BitmapFactory.decodeFileDescriptor(input.getFileDescriptor(), null, options); - return options.outHeight; - } catch (IOException ex) { - return 0; - } finally { - try { - if (input != null) { - input.close(); - } - } catch (IOException ex) { - } - } - } - - public boolean hasLatLong() { - if (mContainer.indexLatitude() < 0 || mContainer.indexLongitude() < 0) return false; - Cursor c = getCursor(); - synchronized (c) { - c.moveToPosition(getRow()); - return !c.isNull(mContainer.indexLatitude()) && !c.isNull(mContainer.indexLongitude()); - } - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#imageId() - */ - public long imageId() { - return mId; - } - - /** - * Make a bitmap from a given Uri. - * - * @param uri - */ - private Bitmap makeBitmap(int targetWidthOrHeight, Uri uri) { - ParcelFileDescriptor input = null; - try { - input = mContentResolver.openFileDescriptor(uri, "r"); - return makeBitmap(targetWidthOrHeight, uri, input, null); - } catch (IOException ex) { - return null; - } finally { - try { - if (input != null) { - input.close(); - } - } catch (IOException ex) { - } - } - } - - protected Bitmap makeBitmap(int targetWidthHeight, Uri uri, ParcelFileDescriptor pfdInput, BitmapFactory.Options options) { - return mContainer.makeBitmap(targetWidthHeight, uri, pfdInput, options); - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#thumb1() - */ - public Bitmap miniThumbBitmap() { - try { - long id = mId; - long dbMagic = mMiniThumbMagic; - if (dbMagic == 0 || dbMagic == id) { - dbMagic = ((BaseImageList)getContainer()).checkThumbnail(this, getCursor(), getRow()); - if (VERBOSE) Log.v(TAG, "after computing thumbnail dbMagic is " + dbMagic); - } - - synchronized(sMiniThumbData) { - dbMagic = mMiniThumbMagic; - byte [] data = mContainer.getMiniThumbFromFile(id, sMiniThumbData, dbMagic); - if (data == null) { - byte[][] createdThumbData = new byte[1][]; - try { - dbMagic = ((BaseImageList)getContainer()).checkThumbnail(this, getCursor(), - getRow(), createdThumbData); - } catch (IOException ex) { - // Typically IOException because the sd card is full. - // But createdThumbData may have been filled in, so continue on. - } - data = createdThumbData[0]; - } - if (data == null) { - data = mContainer.getMiniThumbFromFile(id, sMiniThumbData, dbMagic); - } - if (data == null) { - if (VERBOSE) - Log.v(TAG, "unable to get miniThumbBitmap, data is null"); - } - if (data != null) { - Bitmap b = BitmapFactory.decodeByteArray(data, 0, data.length); - if (b == null) { - if (VERBOSE) { - Log.v(TAG, "couldn't decode byte array for mini thumb, length was " + data.length); - } - } - return b; - } - } - return null; - } catch (Exception ex) { - // Typically IOException because the sd card is full. - if (VERBOSE) { - Log.e(TAG, "miniThumbBitmap got exception " + ex.toString()); - for (StackTraceElement s : ex.getStackTrace()) - Log.e(TAG, "... " + s.toString()); - } - return null; - } - } - - public void onRemove() { - mContainer.mCache.remove(mId); - } - - protected void saveMiniThumb(Bitmap source) throws IOException { - mContainer.saveMiniThumbToFile(source, fullSizeImageId(), 0); - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#setName() - */ - public void setDescription(String description) { - if (mContainer.indexDescription() < 0) return; - Cursor c = getCursor(); - synchronized (c) { - if (c.moveToPosition(getRow())) { - c.updateString(mContainer.indexDescription(), description); - } - } - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#setIsPrivate() - */ - public void setIsPrivate(boolean isPrivate) { - if (mContainer.indexPrivate() < 0) return; - Cursor c = getCursor(); - synchronized (c) { - if (c.moveToPosition(getRow())) { - c.updateInt(mContainer.indexPrivate(), isPrivate ? 1 : 0); - } - } - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#setName() - */ - public void setName(String name) { - Cursor c = getCursor(); - synchronized (c) { - if (c.moveToPosition(getRow())) { - c.updateString(mContainer.indexTitle(), name); - } - } - } - - public void setPicasaId(String id) { - Cursor c = null; - try { - c = mContentResolver.query( - fullSizeImageUri(), - new String[] { "_id", Images.Media.PICASA_ID }, - null, - null, null); - if (c != null && c.moveToFirst()) { - if (VERBOSE) { - Log.v(TAG, "storing picasaid " + id + " for " + fullSizeImageUri()); - } - c.updateString(1, id); - c.commitUpdates(); - if (VERBOSE) { - Log.v(TAG, "updated image with picasa id " + id); - } - } - } finally { - if (c != null) - c.close(); - } - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#thumbUri() - */ - public Uri thumbUri() { - Uri uri = fullSizeImageUri(); - // The value for the query parameter cannot be null :-(, so using a dummy "1" - uri = uri.buildUpon().appendQueryParameter("thumb", "1").build(); - return uri; - } - - @Override - public String toString() { - return fullSizeImageUri().toString(); - } - } - - abstract static class BaseImageList implements IImageList { - Context mContext; - ContentResolver mContentResolver; - Uri mBaseUri, mUri; - int mSort; - String mBucketId; - boolean mDistinct; - Cursor mCursor; - boolean mCursorDeactivated; - protected HashMap<Long, IImage> mCache = new HashMap<Long, IImage>(); - - IImageList.OnChange mListener = null; - Handler mHandler; - protected RandomAccessFile mMiniThumbData; - protected Uri mThumbUri; - - public BaseImageList(Context ctx, ContentResolver cr, Uri uri, int sort, String bucketId) { - mContext = ctx; - mSort = sort; - mUri = uri; - mBaseUri = uri; - mBucketId = bucketId; - - mContentResolver = cr; - } - - String randomAccessFilePath(int version) { - String directoryName = Environment.getExternalStorageDirectory().toString() + "/DCIM/.thumbnails"; - String path = directoryName + "/.thumbdata" + version + "-" + mUri.hashCode(); - return path; - } - - RandomAccessFile miniThumbDataFile() { - if (mMiniThumbData == null) { - String path = randomAccessFilePath(MINI_THUMB_DATA_FILE_VERSION); - File directory = new File(new File(path).getParent()); - if (!directory.isDirectory()) { - if (!directory.mkdirs()) { - Log.e(TAG, "!!!! unable to create .thumbnails directory " + directory.toString()); - } - } - File f = new File(path); - if (VERBOSE) Log.v(TAG, "file f is " + f.toString()); - try { - mMiniThumbData = new RandomAccessFile(f, "rw"); - } catch (IOException ex) { - - } - } - return mMiniThumbData; - } - - /** - * Store a given thumbnail in the database. - */ - protected Bitmap storeThumbnail(Bitmap thumb, long imageId) { - if (thumb == null) - return null; - - try { - Uri uri = getThumbnailUri(imageId, thumb.getWidth(), thumb.getHeight()); - if (uri == null) { - return thumb; - } - OutputStream thumbOut = mContentResolver.openOutputStream(uri); - thumb.compress(Bitmap.CompressFormat.JPEG, 60, thumbOut); - thumbOut.close(); - return thumb; - } - catch (Exception ex) { - if (VERBOSE) Log.d(TAG, "unable to store thumbnail: " + ex); - return thumb; - } - } - - /** - * Store a JPEG thumbnail from the EXIF header in the database. - */ - protected boolean storeThumbnail(byte[] jpegThumbnail, long imageId, int width, int height) { - if (jpegThumbnail == null) - return false; - - Uri uri = getThumbnailUri(imageId, width, height); - if (uri == null) { - return false; - } - try { - OutputStream thumbOut = mContentResolver.openOutputStream(uri); - thumbOut.write(jpegThumbnail); - thumbOut.close(); - return true; - } - catch (FileNotFoundException ex) { - return false; - } - catch (IOException ex) { - return false; - } - } - - private Uri getThumbnailUri(long imageId, int width, int height) { - // we do not store thumbnails for DRM'd images - if (mThumbUri == null) { - return null; - } - - Uri uri = null; - Cursor c = null; - try { - c = mContentResolver.query( - mThumbUri, - THUMB_PROJECTION, - Thumbnails.IMAGE_ID + "=?", - new String[]{String.valueOf(imageId)}, - null); - if (c != null && c.moveToFirst()) { - // If, for some reaosn, we already have a row with a matching - // image id, then just update that row rather than creating a - // new row. - uri = ContentUris.withAppendedId(mThumbUri, c.getLong(indexThumbId())); - c.commitUpdates(); - } - } finally { - if (c != null) - c.close(); - } - if (uri == null) { - ContentValues values = new ContentValues(4); - values.put(Images.Thumbnails.KIND, Images.Thumbnails.MINI_KIND); - values.put(Images.Thumbnails.IMAGE_ID, imageId); - values.put(Images.Thumbnails.HEIGHT, height); - values.put(Images.Thumbnails.WIDTH, width); - uri = mContentResolver.insert(mThumbUri, values); - } - return uri; - } - - java.util.Random mRandom = new java.util.Random(System.currentTimeMillis()); - - protected SomewhatFairLock mLock = new SomewhatFairLock(); - - class SomewhatFairLock { - private Object mSync = new Object(); - private boolean mLocked = false; - private ArrayList<Thread> mWaiting = new ArrayList<Thread>(); - - void lock() { -// if (VERBOSE) Log.v(TAG, "lock... thread " + Thread.currentThread().getId()); - synchronized (mSync) { - while (mLocked) { - try { -// if (VERBOSE) Log.v(TAG, "waiting... thread " + Thread.currentThread().getId()); - mWaiting.add(Thread.currentThread()); - mSync.wait(); - if (mWaiting.get(0) == Thread.currentThread()) { - mWaiting.remove(0); - break; - } - } catch (InterruptedException ex) { - // - } - } -// if (VERBOSE) Log.v(TAG, "locked... thread " + Thread.currentThread().getId()); - mLocked = true; - } - } - - void unlock() { -// if (VERBOSE) Log.v(TAG, "unlocking... thread " + Thread.currentThread().getId()); - synchronized (mSync) { - mLocked = false; - mSync.notifyAll(); - } - } - } - - // If the photo has an EXIF thumbnail and it's big enough, extract it and save that JPEG as - // the large thumbnail without re-encoding it. We still have to decompress it though, in - // order to generate the minithumb. - private Bitmap createThumbnailFromEXIF(String filePath, long id) { - if (filePath != null) { - byte [] thumbData = null; - synchronized (ImageManager.instance()) { - thumbData = (new ExifInterface(filePath)).getThumbnail(); - } - if (thumbData != null) { - // Sniff the size of the EXIF thumbnail before decoding it. Photos from the - // device will pass, but images that are side loaded from other cameras may not. - BitmapFactory.Options options = new BitmapFactory.Options(); - options.inJustDecodeBounds = true; - BitmapFactory.decodeByteArray(thumbData, 0, thumbData.length, options); - int width = options.outWidth; - int height = options.outHeight; - if (width >= THUMBNAIL_TARGET_SIZE && height >= THUMBNAIL_TARGET_SIZE) { - if (storeThumbnail(thumbData, id, width, height)) { - // this is used for *encoding* the minithumb, so - // we don't want to dither or convert to 565 here. - // - // Decode with a scaling factor - // to match MINI_THUMB_TARGET_SIZE closely - // which will produce much better scaling quality - // and is significantly faster. - options.inSampleSize = computeSampleSize(options, THUMBNAIL_TARGET_SIZE); - - if (VERBOSE) { - Log.v(TAG, "in createThumbnailFromExif using inSampleSize of " + options.inSampleSize); - } - options.inDither = false; - options.inPreferredConfig = Bitmap.Config.ARGB_8888; - options.inJustDecodeBounds = false; - return BitmapFactory.decodeByteArray(thumbData, 0, thumbData.length, options); - } - } - } - } - return null; - } - - // The fallback case is to decode the original photo to thumbnail size, then encode it as a - // JPEG. We return the thumbnail Bitmap in order to create the minithumb from it. - private Bitmap createThumbnailFromUri(Cursor c, long id) { - Uri uri = ContentUris.withAppendedId(mBaseUri, id); - Bitmap bitmap = makeBitmap(THUMBNAIL_TARGET_SIZE, uri, null, null); - if (bitmap != null) { - storeThumbnail(bitmap, id); - } else { - uri = ContentUris.withAppendedId(mBaseUri, id); - bitmap = makeBitmap(MINI_THUMB_TARGET_SIZE, uri, null, null); - } - return bitmap; - } - - // returns id - public long checkThumbnail(BaseImage existingImage, Cursor c, int i) throws IOException { - return checkThumbnail(existingImage, c, i, null); - } - - /** - * Checks to see if a mini thumbnail exists in the cache. If not, tries to create it and - * add it to the cache. - * @param existingImage - * @param c - * @param i - * @param createdThumbnailData if this parameter is non-null, and a new mini-thumbnail - * bitmap is created, the new bitmap's data will be stored in createdThumbnailData[0]. - * Note that if the sdcard is full, it's possible that - * createdThumbnailData[0] will be set even if the method throws an IOException. This is - * actually useful, because it allows the caller to use the created thumbnail even if - * the sdcard is full. - * @return - * @throws IOException - */ - public long checkThumbnail(BaseImage existingImage, Cursor c, int i, - byte[][] createdThumbnailData) throws IOException { - long magic, fileMagic = 0, id; - try { - mLock.lock(); - if (existingImage == null) { - // if we don't have an Image object then get the id and magic from - // the cursor. Synchronize on the cursor object. - synchronized (c) { - if (!c.moveToPosition(i)) { - return -1; - } - magic = c.getLong(indexMiniThumbId()); - id = c.getLong(indexId()); - } - } else { - // if we have an Image object then ask them for the magic/id - magic = existingImage.mMiniThumbMagic; - id = existingImage.fullSizeImageId(); - } - - if (magic != 0) { - // check the mini thumb file for the right data. Right is defined as - // having the right magic number at the offset reserved for this "id". - RandomAccessFile r = miniThumbDataFile(); - if (r != null) { - synchronized (r) { - long pos = id * sBytesPerMiniThumb; - try { - // check that we can read the following 9 bytes (1 for the "status" and 8 for the long) - if (r.length() >= pos + 1 + 8) { - r.seek(pos); - if (r.readByte() == 1) { - fileMagic = r.readLong(); - if (fileMagic == magic && magic != 0 && magic != id) { - return magic; - } - } - } - } catch (IOException ex) { - Log.v(TAG, "got exception checking file magic: " + ex); - } - } - } - if (VERBOSE) { - Log.v(TAG, "didn't verify... fileMagic: " + fileMagic + "; magic: " + magic + "; id: " + id + "; "); - } - } - - // If we can't retrieve the thumbnail, first check if there is one embedded in the - // EXIF data. If not, or it's not big enough, decompress the full size image. - Bitmap bitmap = null; - String filePath = null; - synchronized (c) { - if (c.moveToPosition(i)) { - filePath = c.getString(indexData()); - } - } - if (filePath != null) { - String mimeType = c.getString(indexMimeType()); - boolean isVideo = isVideoMimeType(mimeType); - if (isVideo) { - bitmap = createVideoThumbnail(filePath); - } else { - bitmap = createThumbnailFromEXIF(filePath, id); - if (bitmap == null) { - bitmap = createThumbnailFromUri(c, id); - } - } - synchronized (c) { - int degrees = 0; - if (c.moveToPosition(i)) { - int column = indexOrientation(); - if (column >= 0) - degrees = c.getInt(column); - } - if (degrees != 0) { - Bitmap b2 = rotate(bitmap, degrees); - if (b2 != bitmap) - bitmap.recycle(); - bitmap = b2; - } - } - } - - // make a new magic number since things are out of sync - do { - magic = mRandom.nextLong(); - } while (magic == 0); - if (bitmap != null) { - byte [] data = miniThumbData(bitmap); - if (createdThumbnailData != null) { - createdThumbnailData[0] = data; - } - saveMiniThumbToFile(data, id, magic); - } - - synchronized (c) { - c.moveToPosition(i); - c.updateLong(indexMiniThumbId(), magic); - c.commitUpdates(); - c.requery(); - c.moveToPosition(i); - - if (existingImage != null) { - existingImage.mMiniThumbMagic = magic; - } - return magic; - } - } finally { - mLock.unlock(); - } - } - - public void checkThumbnails(ThumbCheckCallback cb, int totalThumbnails) { - Cursor c = Images.Media.query( - mContentResolver, - mBaseUri, - new String[] { "_id", "mini_thumb_magic" }, - thumbnailWhereClause(), - thumbnailWhereClauseArgs(), - "_id ASC"); - - int count = c.getCount(); - if (VERBOSE) - Log.v(TAG, ">>>>>>>>>>> need to check " + c.getCount() + " rows"); - - c.close(); - - if (!ImageManager.hasStorage()) { - if (VERBOSE) - Log.v(TAG, "bailing from the image checker thread -- no storage"); - return; - } - - String oldPath = randomAccessFilePath(MINI_THUMB_DATA_FILE_VERSION - 1); - File oldFile = new File(oldPath); - - if (count == 0) { - // now check that we have the right thumbs file -// Log.v(TAG, "count is zero but oldFile.exists() is " + oldFile.exists()); - if (!oldFile.exists()) { - return; - } - } - - c = getCursor(); - try { - if (VERBOSE) Log.v(TAG, "checkThumbnails found " + c.getCount()); - int current = 0; - for (int i = 0; i < c.getCount(); i++) { - try { - checkThumbnail(null, c, i); - } catch (Exception ex) { - Log.e(TAG, "!!!!! failed to check thumbnail... was the sd card removed?"); - break; - } - if (cb != null) { - if (!cb.checking(current, totalThumbnails)) { - if (VERBOSE) Log.v(TAG, "got false from checking... break <<<<<<<<<<<<<<<<<<<<<<<<"); - break; - } - } - current += 1; - } - } finally { - if (VERBOSE) Log.v(TAG, "checkThumbnails existing after reaching count " + c.getCount()); - try { - oldFile.delete(); - } catch (Exception ex) { - // ignore - } - } - } - - protected String thumbnailWhereClause() { - return sMiniThumbIsNull + " and " + sWhereClause; - } - - protected String[] thumbnailWhereClauseArgs() { - return sAcceptableImageTypes; - } - - public void commitChanges() { - synchronized (mCursor) { - mCursor.commitUpdates(); - requery(); - } - } - protected Uri contentUri(long id) { - try { - // does our uri already have an id (single image query)? - // if so just return it - long existingId = ContentUris.parseId(mBaseUri); - if (existingId != id) - Log.e(TAG, "id mismatch"); - return mBaseUri; - } catch (NumberFormatException ex) { - // otherwise tack on the id - return ContentUris.withAppendedId(mBaseUri, id); - } - } - - public void deactivate() { - mCursorDeactivated = true; - try { - mCursor.deactivate(); - } catch (IllegalStateException e) { - // IllegalStateException may be thrown if the cursor is stale. - Log.e(TAG, "Caught exception while deactivating cursor.", e); - } - if (mMiniThumbData != null) { - try { - mMiniThumbData.close(); - mMiniThumbData = null; - } catch (IOException ex) { - - } - } - } - - public void dump(String msg) { - int count = getCount(); - if (VERBOSE) Log.v(TAG, "dump ImageList (count is " + count + ") " + msg); - for (int i = 0; i < count; i++) { - IImage img = getImageAt(i); - if (img == null) - if (VERBOSE) Log.v(TAG, " " + i + ": " + "null"); - else - if (VERBOSE) Log.v(TAG, " " + i + ": " + img.toString()); - } - if (VERBOSE) Log.v(TAG, "end of dump container"); - } - public int getCount() { - Cursor c = getCursor(); - synchronized (c) { - try { - return c.getCount(); - } catch (Exception ex) { - } - return 0; - } - } - - public boolean isEmpty() { - return getCount() == 0; - } - - protected Cursor getCursor() { - synchronized (mCursor) { - if (mCursorDeactivated) { - activateCursor(); - } - return mCursor; - } - } - - protected void activateCursor() { - requery(); - } - - public IImage getImageAt(int i) { - Cursor c = getCursor(); - synchronized (c) { - boolean moved; - try { - moved = c.moveToPosition(i); - } catch (Exception ex) { - return null; - } - if (moved) { - try { - long id = c.getLong(0); - long miniThumbId = 0; - int rotation = 0; - if (indexMiniThumbId() != -1) { - miniThumbId = c.getLong(indexMiniThumbId()); - } - if (indexOrientation() != -1) { - rotation = c.getInt(indexOrientation()); - } - long timestamp = c.getLong(1); - IImage img = mCache.get(id); - if (img == null) { - img = make(id, miniThumbId, mContentResolver, this, timestamp, i, rotation); - mCache.put(id, img); - } - return img; - } catch (Exception ex) { - Log.e(TAG, "got this exception trying to create image object: " + ex); - return null; - } - } else { - Log.e(TAG, "unable to moveTo to " + i + "; count is " + c.getCount()); - return null; - } - } - } - public IImage getImageForUri(Uri uri) { - // TODO make this a hash lookup - for (int i = 0; i < getCount(); i++) { - if (getImageAt(i).fullSizeImageUri().equals(uri)) { - return getImageAt(i); - } - } - return null; - } - private byte [] getMiniThumbFromFile(long id, byte [] data, long magicCheck) { - RandomAccessFile r = miniThumbDataFile(); - if (r == null) - return null; - - long pos = id * sBytesPerMiniThumb; - RandomAccessFile f = r; - synchronized (f) { - try { - f.seek(pos); - if (f.readByte() == 1) { - long magic = f.readLong(); - if (magic != magicCheck) { - if (VERBOSE) Log.v(TAG, "for id " + id + "; magic: " + magic + "; magicCheck: " + magicCheck + " (fail)"); - return null; - } - int length = f.readInt(); - f.read(data, 0, length); - return data; - } else { - return null; - } - } catch (IOException ex) { - long fileLength; - try { - fileLength = f.length(); - } catch (IOException ex1) { - fileLength = -1; - } - if (VERBOSE) { - Log.e(TAG, "couldn't read thumbnail for " + id + "; " + ex.toString() + "; pos is " + pos + "; length is " + fileLength); - } - return null; - } - } - } - protected int getRowFor(IImage imageObj) { - Cursor c = getCursor(); - synchronized (c) { - int index = 0; - long targetId = imageObj.fullSizeImageId(); - if (c.moveToFirst()) { - do { - if (c.getLong(0) == targetId) { - return index; - } - index += 1; - } while (c.moveToNext()); - } - return -1; - } - } - - protected abstract int indexOrientation(); - protected abstract int indexDateTaken(); - protected abstract int indexDescription(); - protected abstract int indexMimeType(); - protected abstract int indexData(); - protected abstract int indexId(); - protected abstract int indexLatitude(); - protected abstract int indexLongitude(); - protected abstract int indexMiniThumbId(); - protected abstract int indexPicasaWeb(); - protected abstract int indexPrivate(); - protected abstract int indexTitle(); - protected abstract int indexDisplayName(); - protected abstract int indexThumbId(); - - protected IImage make(long id, long miniThumbId, ContentResolver cr, IImageList list, long timestamp, int index, int rotation) { - return null; - } - - protected abstract Bitmap makeBitmap(int targetWidthHeight, Uri uri, ParcelFileDescriptor pfdInput, BitmapFactory.Options options); - - public boolean removeImage(IImage image) { - Cursor c = getCursor(); - synchronized (c) { - /* - * TODO: consider putting the image in a holding area so - * we can get it back as needed - * TODO: need to delete the thumbnails as well - */ - boolean moved; - try { - moved = c.moveToPosition(image.getRow()); - } catch (Exception ex) { - Log.e(TAG, "removeImage got exception " + ex.toString()); - return false; - } - if (moved) { - Uri u = image.fullSizeImageUri(); - mContentResolver.delete(u, null, null); - image.onRemove(); - requery(); - } - } - return true; - } - - - /* (non-Javadoc) - * @see com.android.camera.IImageList#removeImageAt(int) - */ - public void removeImageAt(int i) { - Cursor c = getCursor(); - synchronized (c) { - /* - * TODO: consider putting the image in a holding area so - * we can get it back as needed - * TODO: need to delete the thumbnails as well - */ - dump("before delete"); - IImage image = getImageAt(i); - boolean moved; - try { - moved = c.moveToPosition(i); - } catch (Exception ex) { - return; - } - if (moved) { - Uri u = image.fullSizeImageUri(); - mContentResolver.delete(u, null, null); - requery(); - image.onRemove(); - } - dump("after delete"); - } - } - - public void removeOnChangeListener(OnChange changeCallback) { - if (changeCallback == mListener) - mListener = null; - } - - protected void requery() { - mCache.clear(); - mCursor.requery(); - mCursorDeactivated = false; - } - - protected void saveMiniThumbToFile(Bitmap bitmap, long id, long magic) throws IOException { - byte[] data = miniThumbData(bitmap); - saveMiniThumbToFile(data, id, magic); - } - - protected void saveMiniThumbToFile(byte[] data, long id, long magic) throws IOException { - RandomAccessFile r = miniThumbDataFile(); - if (r == null) - return; - - long pos = id * sBytesPerMiniThumb; - long t0 = System.currentTimeMillis(); - synchronized (r) { - try { - long t1 = System.currentTimeMillis(); - long t2 = System.currentTimeMillis(); - if (data != null) { - if (data.length > sBytesPerMiniThumb) { - if (VERBOSE) Log.v(TAG, "!!!!!!!!!!!!!!!!!!!!!!!!!!! " + data.length + " > " + sBytesPerMiniThumb); - return; - } - r.seek(pos); - r.writeByte(0); // we have no data in this slot - - // if magic is 0 then leave it alone - if (magic == 0) - r.skipBytes(8); - else - r.writeLong(magic); - r.writeInt(data.length); - r.write(data); - // f.flush(); - r.seek(pos); - r.writeByte(1); // we have data in this slot - long t3 = System.currentTimeMillis(); - - if (VERBOSE) Log.v(TAG, "saveMiniThumbToFile took " + (t3-t0) + "; " + (t1-t0) + " " + (t2-t1) + " " + (t3-t2)); - } - } catch (IOException ex) { - Log.e(TAG, "couldn't save mini thumbnail data for " + id + "; " + ex.toString()); - throw ex; - } - } - } - - public void setOnChangeListener(OnChange changeCallback, Handler h) { - mListener = changeCallback; - mHandler = h; - } - } - - public class CanceledException extends Exception { - - } - public enum DataLocation { NONE, INTERNAL, EXTERNAL, ALL } - - public interface IAddImage_cancelable extends ICancelable { - public void get(); - } - - /* - * The model for canceling an in-progress image save is this. For any - * given part of the task of saving return an ICancelable. The "result" - * from an ICancelable can be retrieved using the get* method. If the - * operation was canceled then null is returned. The act of canceling - * is to call "cancel" -- from another thread. - * - * In general an object which implements ICancelable will need to - * check, periodically, whether they are canceled or not. This works - * well for some things and less well for others. - * - * Right now the actual jpeg encode does not check cancelation but - * the part of encoding which writes the data to disk does. Note, - * though, that there is what appears to be a bug in the jpeg encoder - * in that if the stream that's being written is closed it crashes - * rather than returning an error. TODO fix that. - * - * When an object detects that it is canceling it must, before exiting, - * call acknowledgeCancel. This is necessary because the caller of - * cancel() will block until acknowledgeCancel is called. - */ - public interface ICancelable { - /* - * call cancel() when the unit of work in progress needs to be - * canceled. This should return true if it was possible to - * cancel and false otherwise. If this returns false the caller - * may still be able to cleanup and simulate cancelation. - */ - public boolean cancel(); - } - - public interface IGetBitmap_cancelable extends ICancelable { - // returns the bitmap or null if there was an error or we were canceled - public Bitmap get(); - }; - public interface IGetBoolean_cancelable extends ICancelable { - public boolean get(); - } - public interface IImage { - - public abstract void commitChanges(); - - /** - * Get the bitmap for the full size image. - * @return the bitmap for the full size image. - */ - public abstract Bitmap fullSizeBitmap(int targetWidthOrHeight); - - /** - * - * @return an object which can be canceled while the bitmap is loading - */ - public abstract IGetBitmap_cancelable fullSizeBitmap_cancelable(int targetWidthOrHeight); - - /** - * Gets the input stream associated with a given full size image. - * This is used, for example, if one wants to email or upload - * the image. - * @return the InputStream associated with the image. - */ - public abstract InputStream fullSizeImageData(); - public abstract long fullSizeImageId(); - public abstract Uri fullSizeImageUri(); - public abstract IImageList getContainer(); - public abstract long getDateTaken(); - - /** - * Gets the description of the image. - * @return the description of the image. - */ - public abstract String getDescription(); - public abstract String getMimeType(); - public abstract int getHeight(); - - /** - * Gets the flag telling whether this video/photo is private or public. - * @return the description of the image. - */ - public abstract boolean getIsPrivate(); - - public abstract double getLatitude(); - - public abstract double getLongitude(); - - /** - * Gets the name of the image. - * @return the name of the image. - */ - public abstract String getTitle(); - - public abstract String getDisplayName(); - - public abstract String getPicasaId(); - - public abstract int getRow(); - - public abstract int getWidth(); - - public abstract boolean hasLatLong(); - - public abstract long imageId(); - - public abstract boolean isReadonly(); - - public abstract boolean isDrm(); - - public abstract Bitmap miniThumbBitmap(); - - public abstract void onRemove(); - - public abstract boolean rotateImageBy(int degrees); - - /** - * Sets the description of the image. - */ - public abstract void setDescription(String description); - - /** - * Sets whether the video/photo is private or public. - */ - public abstract void setIsPrivate(boolean isPrivate); - - /** - * Sets the name of the image. - */ - public abstract void setName(String name); - - public abstract void setPicasaId(String id); - - /** - * Get the bitmap for the medium thumbnail. - * @return the bitmap for the medium thumbnail. - */ - public abstract Bitmap thumbBitmap(); - - public abstract Uri thumbUri(); - - public abstract String getDataPath(); - } - - public interface IImageList { - public HashMap<String, String> getBucketIds(); - - public interface OnChange { - public void onChange(IImageList list); - } - - public interface ThumbCheckCallback { - public boolean checking(int current, int count); - } - - public abstract void checkThumbnails(ThumbCheckCallback cb, int totalCount); - - public abstract void commitChanges(); - - public abstract void deactivate(); - - /** - * Returns the count of image objects. - * - * @return the number of images - */ - public abstract int getCount(); - - /** - * @return true if the count of image objects is zero. - */ - - public abstract boolean isEmpty(); - - /** - * Returns the image at the ith position. - * - * @param i the position - * @return the image at the ith position - */ - public abstract IImage getImageAt(int i); - - /** - * Returns the image with a particular Uri. - * - * @param uri - * @return the image with a particular Uri. - */ - public abstract IImage getImageForUri(Uri uri);; - - /** - * - * @param image - * @return true if the image was removed. - */ - public abstract boolean removeImage(IImage image); - /** - * Removes the image at the ith position. - * @param i the position - */ - public abstract void removeImageAt(int i); - - public abstract void removeOnChangeListener(OnChange changeCallback); - public abstract void setOnChangeListener(OnChange changeCallback, Handler h); - } - - class Image extends BaseImage implements IImage { - int mRotation; - - protected Image(long id, long miniThumbId, ContentResolver cr, BaseImageList container, int cursorRow, int rotation) { - super(id, miniThumbId, cr, container, cursorRow); - mRotation = rotation; - } - - public String getDataPath() { - String path = null; - Cursor c = getCursor(); - synchronized (c) { - if (c.moveToPosition(getRow())) { - int column = ((ImageList)getContainer()).indexData(); - if (column >= 0) - path = c.getString(column); - } - } - return path; - } - - protected int getDegreesRotated() { - return mRotation; - } - - protected void setDegreesRotated(int degrees) { - Cursor c = getCursor(); - mRotation = degrees; - synchronized (c) { - if (c.moveToPosition(getRow())) { - int column = ((ImageList)getContainer()).indexOrientation(); - if (column >= 0) { - c.updateInt(column, degrees); - getContainer().commitChanges(); - } - } - } - } - - protected Bitmap.CompressFormat compressionType() { - String mimeType = getMimeType(); - if (mimeType == null) - return Bitmap.CompressFormat.JPEG; - - if (mimeType.equals("image/png")) - return Bitmap.CompressFormat.PNG; - else if (mimeType.equals("image/png")) - return Bitmap.CompressFormat.PNG; - - return Bitmap.CompressFormat.JPEG; - } - - /** - * Does not replace the tag if already there. Otherwise, adds to the exif tags. - * @param tag - * @param value - */ - public void addExifTag(String tag, String value) { - if (mExifData == null) { - mExifData = new HashMap<String, String>(); - } - if (!mExifData.containsKey(tag)) { - mExifData.put(tag, value); - } else { - if (VERBOSE) Log.v(TAG, "addExifTag where the key already was there: " + tag + " = " + value); - } - } - - /** - * Return the value of the Exif tag as an int. Returns 0 on any type of error. - * @param tag - * @return - */ - public int getExifTagInt(String tag) { - if (mExifData != null) { - String tagValue = mExifData.get(tag); - if (tagValue != null) { - return Integer.parseInt(tagValue); - } - } - return 0; - } - - public boolean isReadonly() { - String mimeType = getMimeType(); - return !"image/jpeg".equals(mimeType) && !"image/png".equals(mimeType); - } - - public boolean isDrm() { - return false; - } - - /** - * Remove tag if already there. Otherwise, does nothing. - * @param tag - */ - public void removeExifTag(String tag) { - if (mExifData == null) { - mExifData = new HashMap<String, String>(); - } - mExifData.remove(tag); - } - - /** - * Replaces the tag if already there. Otherwise, adds to the exif tags. - * @param tag - * @param value - */ - public void replaceExifTag(String tag, String value) { - if (mExifData == null) { - mExifData = new HashMap<String, String>(); - } - if (!mExifData.containsKey(tag)) { - mExifData.remove(tag); - } - mExifData.put(tag, value); - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#saveModifiedImage(android.graphics.Bitmap) - */ - public IGetBoolean_cancelable saveImageContents( - final Bitmap image, - final byte [] jpegData, - final int orientation, - final boolean newFile, - final Cursor cursor) { - final class SaveImageContentsCancelable extends BaseCancelable implements IGetBoolean_cancelable { - IGetBoolean_cancelable mCurrentCancelable = null; - - SaveImageContentsCancelable() { - } - - public boolean doCancelWork() { - synchronized (this) { - if (mCurrentCancelable != null) - mCurrentCancelable.cancel(); - } - return true; - } - - public boolean get() { - try { - Bitmap thumbnail = null; - - long t1 = System.currentTimeMillis(); - Uri uri = mContainer.contentUri(mId); - synchronized (this) { - checkCanceled(); - mCurrentCancelable = compressImageToFile(image, jpegData, uri); - } - - long t2 = System.currentTimeMillis(); - if (!mCurrentCancelable.get()) - return false; - - synchronized (this) { - String filePath; - synchronized (cursor) { - cursor.moveToPosition(0); - filePath = cursor.getString(2); - } - // TODO: If thumbData is present and usable, we should call the version - // of storeThumbnail which takes a byte array, rather than re-encoding - // a new JPEG of the same dimensions. - byte [] thumbData = null; - synchronized (ImageManager.instance()) { - thumbData = (new ExifInterface(filePath)).getThumbnail(); - } - if (VERBOSE) Log.v(TAG, "for file " + filePath + " thumbData is " + thumbData + "; length " + (thumbData!=null ? thumbData.length : -1)); - if (thumbData != null) { - thumbnail = BitmapFactory.decodeByteArray(thumbData, 0, thumbData.length); - if (VERBOSE) Log.v(TAG, "embedded thumbnail bitmap " + thumbnail.getWidth() + "/" + thumbnail.getHeight()); - } - if (thumbnail == null && image != null) { - thumbnail = image; - } - if (thumbnail == null && jpegData != null) { - thumbnail = BitmapFactory.decodeByteArray(jpegData, 0, jpegData.length); - } - } - - long t3 = System.currentTimeMillis(); - mContainer.storeThumbnail(thumbnail, Image.this.fullSizeImageId()); - long t4 = System.currentTimeMillis(); - checkCanceled(); - if (VERBOSE) Log.v(TAG, ">>>>>>>>>>>>>>>>>>>>> rotating by " + orientation); - try { - saveMiniThumb(rotate(thumbnail, orientation)); - } catch (IOException e) { - // Ignore if unable to save thumb. - } - long t5 = System.currentTimeMillis(); - checkCanceled(); - - if (VERBOSE) Log.v(TAG, String.format("Timing data %d %d %d %d", t2-t1, t3-t2, t4-t3, t5-t4)); - return true; - } catch (CanceledException ex) { - if (VERBOSE) Log.v(TAG, "got canceled... need to cleanup"); - return false; - } finally { - /* - Cursor c = getCursor(); - synchronized (c) { - if (c.moveTo(getRow())) { - mContainer.requery(); - } - } - */ - acknowledgeCancel(); - } - } - } - return new SaveImageContentsCancelable(); - } - - private void setExifRotation(int degrees) { - try { - Cursor c = getCursor(); - String filePath; - synchronized (c) { - filePath = c.getString(mContainer.indexData()); - } - synchronized (ImageManager.instance()) { - ExifInterface exif = new ExifInterface(filePath); - if (mExifData == null) { - mExifData = exif.getAttributes(); - } - if (degrees < 0) - degrees += 360; - - int orientation = ExifInterface.ORIENTATION_NORMAL; - switch (degrees) { - case 0: - orientation = ExifInterface.ORIENTATION_NORMAL; - break; - case 90: - orientation = ExifInterface.ORIENTATION_ROTATE_90; - break; - case 180: - orientation = ExifInterface.ORIENTATION_ROTATE_180; - break; - case 270: - orientation = ExifInterface.ORIENTATION_ROTATE_270; - break; - } - - replaceExifTag(ExifInterface.TAG_ORIENTATION, Integer.toString(orientation)); - replaceExifTag("UserComment", "saveRotatedImage comment orientation: " + orientation); - exif.saveAttributes(mExifData); - exif.commitChanges(); - } - } catch (Exception ex) { - Log.e(TAG, "unable to save exif data with new orientation " + fullSizeImageUri()); - } - } - - /** - * Save the rotated image by updating the Exif "Orientation" tag. - * @param degrees - * @return - */ - public boolean rotateImageBy(int degrees) { - int newDegrees = getDegreesRotated() + degrees; - setExifRotation(newDegrees); - setDegreesRotated(newDegrees); - - // setting this to zero will force the call to checkCursor to generate fresh thumbs - mMiniThumbMagic = 0; - try { - mContainer.checkThumbnail(this, mContainer.getCursor(), this.getRow()); - } catch (IOException e) { - // Ignore inability to store mini thumbnail. - } - - return true; - } - - public Bitmap thumbBitmap() { - Bitmap bitmap = null; - Cursor c = null; - if (mContainer.mThumbUri != null) { - try { - c = mContentResolver.query( - mContainer.mThumbUri, - THUMB_PROJECTION, - Thumbnails.IMAGE_ID + "=?", - new String[] { String.valueOf(fullSizeImageId()) }, - null); - if (c != null && c.moveToFirst()) { - Uri thumbUri = ContentUris.withAppendedId(mContainer.mThumbUri, c.getLong(((ImageList)mContainer).INDEX_THUMB_ID)); - ParcelFileDescriptor pfdInput; - try { - BitmapFactory.Options options = new BitmapFactory.Options(); - options.inDither = false; - options.inPreferredConfig = Bitmap.Config.ARGB_8888; - pfdInput = mContentResolver.openFileDescriptor(thumbUri, "r"); - bitmap = BitmapFactory.decodeFileDescriptor(pfdInput.getFileDescriptor(), null, options); - pfdInput.close(); - } catch (FileNotFoundException ex) { - Log.e(TAG, "couldn't open thumbnail " + thumbUri + "; " + ex); - } catch (IOException ex) { - Log.e(TAG, "couldn't open thumbnail " + thumbUri + "; " + ex); - } catch (NullPointerException ex) { - // we seem to get this if the file doesn't exist anymore - Log.e(TAG, "couldn't open thumbnail " + thumbUri + "; " + ex); - } - } - } catch (Exception ex) { - // sdcard removed? - return null; - } finally { - if (c != null) - c.close(); - } - } - - if (bitmap == null) { - bitmap = fullSizeBitmap(THUMBNAIL_TARGET_SIZE, false); - if (VERBOSE) { - Log.v(TAG, "no thumbnail found... storing new one for " + fullSizeImageId()); - } - bitmap = mContainer.storeThumbnail(bitmap, fullSizeImageId()); - } - - if (bitmap != null) { - int degrees = getDegreesRotated(); - if (degrees != 0) { - Matrix m = new Matrix(); - m.setRotate(degrees, (float) bitmap.getWidth() / 2, (float) bitmap.getHeight() / 2); - bitmap = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(), bitmap.getHeight(), - m, true); - } - } - - long elapsed = System.currentTimeMillis(); - return bitmap; - } - - } - - final static private String sWhereClause = "(" + Images.Media.MIME_TYPE + "=? or " + Images.Media.MIME_TYPE + "=?" + ")"; - final static private String[] sAcceptableImageTypes = new String[] { "image/jpeg", "image/png" }; - final static private String sMiniThumbIsNull = "mini_thumb_magic isnull"; - - private static final String[] IMAGE_PROJECTION = new String[] { - "_id", - "_data", - ImageColumns.DATE_TAKEN, - ImageColumns.MINI_THUMB_MAGIC, - ImageColumns.ORIENTATION, - ImageColumns.MIME_TYPE - }; - - /** - * Represents an ordered collection of Image objects. - * Provides an api to add and remove an image. - */ - class ImageList extends BaseImageList implements IImageList { - final int INDEX_ID = indexOf(IMAGE_PROJECTION, "_id"); - final int INDEX_DATA = indexOf(IMAGE_PROJECTION, "_data"); - final int INDEX_MIME_TYPE = indexOf(IMAGE_PROJECTION, MediaColumns.MIME_TYPE); - final int INDEX_DATE_TAKEN = indexOf(IMAGE_PROJECTION, ImageColumns.DATE_TAKEN); - final int INDEX_MINI_THUMB_MAGIC = indexOf(IMAGE_PROJECTION, ImageColumns.MINI_THUMB_MAGIC); - final int INDEX_ORIENTATION = indexOf(IMAGE_PROJECTION, ImageColumns.ORIENTATION); - - final int INDEX_THUMB_ID = indexOf(THUMB_PROJECTION, BaseColumns._ID); - final int INDEX_THUMB_IMAGE_ID = indexOf(THUMB_PROJECTION, Images.Thumbnails.IMAGE_ID); - final int INDEX_THUMB_WIDTH = indexOf(THUMB_PROJECTION, Images.Thumbnails.WIDTH); - final int INDEX_THUMB_HEIGHT = indexOf(THUMB_PROJECTION, Images.Thumbnails.HEIGHT); - - boolean mIsRegistered = false; - ContentObserver mContentObserver; - DataSetObserver mDataSetObserver; - - public HashMap<String, String> getBucketIds() { - Cursor c = Images.Media.query( - mContentResolver, - mBaseUri.buildUpon().appendQueryParameter("distinct", "true").build(), - new String[] { - ImageColumns.BUCKET_DISPLAY_NAME, - ImageColumns.BUCKET_ID - }, - whereClause(), - whereClauseArgs(), - sortOrder()); - - HashMap<String, String> hash = new HashMap<String, String>(); - if (c != null && c.moveToFirst()) { - do { - hash.put(c.getString(1), c.getString(0)); - } while (c.moveToNext()); - } - return hash; - } - /** - * ImageList constructor. - * @param cr ContentResolver - */ - public ImageList(Context ctx, ContentResolver cr, Uri imageUri, Uri thumbUri, int sort, String bucketId) { - super(ctx, cr, imageUri, sort, bucketId); - mBaseUri = imageUri; - mThumbUri = thumbUri; - mSort = sort; - - mContentResolver = cr; - - mCursor = createCursor(); - if (mCursor == null) { - Log.e(TAG, "unable to create image cursor for " + mBaseUri); - throw new UnsupportedOperationException(); - } - - if (VERBOSE) { - Log.v(TAG, "for " + mBaseUri.toString() + " got cursor " + mCursor + " with length " + (mCursor != null ? mCursor.getCount() : "-1")); - } - - final Runnable updateRunnable = new Runnable() { - public void run() { - // handling these external updates is causing ANR problems that are unresolved. - // For now ignore them since there shouldn't be anyone modifying the database on the fly. - if (true) - return; - - synchronized (mCursor) { - requery(); - } - if (mListener != null) - mListener.onChange(ImageList.this); - } - }; - - mContentObserver = new ContentObserver(null) { - @Override - public boolean deliverSelfNotifications() { - return false; - } - - @Override - public void onChange(boolean selfChange) { - if (VERBOSE) Log.v(TAG, "MyContentObserver.onChange; selfChange == " + selfChange); - updateRunnable.run(); - } - }; - - mDataSetObserver = new DataSetObserver() { - @Override - public void onChanged() { - if (VERBOSE) Log.v(TAG, "MyDataSetObserver.onChanged"); -// updateRunnable.run(); - } - - @Override - public void onInvalidated() { - if (VERBOSE) Log.v(TAG, "MyDataSetObserver.onInvalidated: " + mCursorDeactivated); - } - }; - - registerObservers(); - } - - private void registerObservers() { - if (mIsRegistered) - return; - - mCursor.registerContentObserver(mContentObserver); - mCursor.registerDataSetObserver(mDataSetObserver); - mIsRegistered = true; - } - - private void unregisterObservers() { - if (!mIsRegistered) - return; - - mCursor.unregisterContentObserver(mContentObserver); - mCursor.unregisterDataSetObserver(mDataSetObserver); - mIsRegistered = false; - } - - public void deactivate() { - super.deactivate(); - unregisterObservers(); - } - - protected void activateCursor() { - super.activateCursor(); - registerObservers(); - } - - protected String whereClause() { - if (mBucketId != null) { - return sWhereClause + " and " + Images.Media.BUCKET_ID + " = '" + mBucketId + "'"; - } else { - return sWhereClause; - } - } - - protected String[] whereClauseArgs() { - return sAcceptableImageTypes; - } - - protected Cursor createCursor() { - Cursor c = - Images.Media.query( - mContentResolver, - mBaseUri, - IMAGE_PROJECTION, - whereClause(), - whereClauseArgs(), - sortOrder()); - if (VERBOSE) - Log.v(TAG, "createCursor got cursor with count " + (c == null ? -1 : c.getCount())); - return c; - } - - protected int indexOrientation() { return INDEX_ORIENTATION; } - protected int indexDateTaken() { return INDEX_DATE_TAKEN; } - protected int indexDescription() { return -1; } - protected int indexMimeType() { return INDEX_MIME_TYPE; } - protected int indexData() { return INDEX_DATA; } - protected int indexId() { return INDEX_ID; } - protected int indexLatitude() { return -1; } - protected int indexLongitude() { return -1; } - protected int indexMiniThumbId() { return INDEX_MINI_THUMB_MAGIC; } - - protected int indexPicasaWeb() { return -1; } - protected int indexPrivate() { return -1; } - protected int indexTitle() { return -1; } - protected int indexDisplayName() { return -1; } - protected int indexThumbId() { return INDEX_THUMB_ID; } - - @Override - protected IImage make(long id, long miniThumbId, ContentResolver cr, IImageList list, long timestamp, int index, int rotation) { - return new Image(id, miniThumbId, mContentResolver, this, index, rotation); - } - - protected Bitmap makeBitmap(int targetWidthHeight, Uri uri, ParcelFileDescriptor pfd, BitmapFactory.Options options) { - Bitmap b = null; - - try { - if (pfd == null) - pfd = makeInputStream(uri); - - if (pfd == null) - return null; - - if (options == null) - options = new BitmapFactory.Options(); - - java.io.FileDescriptor fd = pfd.getFileDescriptor(); - options.inSampleSize = 1; - if (targetWidthHeight != -1) { - options.inJustDecodeBounds = true; - long t1 = System.currentTimeMillis(); - BitmapFactory.decodeFileDescriptor(fd, null, options); - long t2 = System.currentTimeMillis(); - if (options.mCancel || options.outWidth == -1 || options.outHeight == -1) { - return null; - } - options.inSampleSize = computeSampleSize(options, targetWidthHeight); - options.inJustDecodeBounds = false; - } - - options.inDither = false; - options.inPreferredConfig = Bitmap.Config.ARGB_8888; - long t1 = System.currentTimeMillis(); - b = BitmapFactory.decodeFileDescriptor(fd, null, options); - long t2 = System.currentTimeMillis(); - if (VERBOSE) { - Log.v(TAG, "A: got bitmap " + b + " with sampleSize " + options.inSampleSize + " took " + (t2-t1)); - } - pfd.close(); - } catch (IOException ex) { - if (VERBOSE) Log.v(TAG, "got io exception " + ex); - return null; - } - return b; - } - - private ParcelFileDescriptor makeInputStream(Uri uri) { - try { - return mContentResolver.openFileDescriptor(uri, "r"); - } catch (IOException ex) { - return null; - } - } - - private String sortOrder() { - // add id to the end so that we don't ever get random sorting - // which could happen, I suppose, if the first two values were - // duplicated - String ascending = (mSort == SORT_ASCENDING ? " ASC" : " DESC"); - return - Images.Media.DATE_TAKEN + ascending + "," + - Images.Media._ID + ascending; - } - - } - - /** - * Represents an ordered collection of Image objects from the DRM provider. - */ - class DrmImageList extends ImageList implements IImageList { - private final String[] DRM_IMAGE_PROJECTION = new String[] { - DrmStore.Audio._ID, - DrmStore.Audio.DATA, - DrmStore.Audio.MIME_TYPE, - }; - - final int INDEX_ID = indexOf(DRM_IMAGE_PROJECTION, DrmStore.Audio._ID); - final int INDEX_MIME_TYPE = indexOf(DRM_IMAGE_PROJECTION, DrmStore.Audio.MIME_TYPE); - - public DrmImageList(Context ctx, ContentResolver cr, Uri imageUri, int sort, String bucketId) { - super(ctx, cr, imageUri, null, sort, bucketId); - } - - protected Cursor createCursor() { - return mContentResolver.query(mBaseUri, DRM_IMAGE_PROJECTION, null, null, sortOrder()); - } - - @Override - public void checkThumbnails(ThumbCheckCallback cb, int totalCount) { - // do nothing - } - - @Override - public long checkThumbnail(BaseImage existingImage, Cursor c, int i) { - return 0; - } - - class DrmImage extends Image { - protected DrmImage(long id, ContentResolver cr, BaseImageList container, int cursorRow) { - super(id, 0, cr, container, cursorRow, 0); - } - - public boolean isDrm() { - return true; - } - - public boolean isReadonly() { - return true; - } - - public Bitmap miniThumbBitmap() { - return fullSizeBitmap(MINI_THUMB_TARGET_SIZE); - } - - public Bitmap thumbBitmap() { - return fullSizeBitmap(THUMBNAIL_TARGET_SIZE); - } - - public String getDisplayName() { - return getTitle(); - } - } - - @Override - protected IImage make(long id, long miniThumbId, ContentResolver cr, IImageList list, long timestamp, int index, int rotation) { - return new DrmImage(id, mContentResolver, this, index); - } - - protected int indexOrientation() { return -1; } - protected int indexDateTaken() { return -1; } - protected int indexDescription() { return -1; } - protected int indexMimeType() { return -1; } - protected int indexId() { return -1; } - protected int indexLatitude() { return -1; } - protected int indexLongitude() { return -1; } - protected int indexMiniThumbId() { return -1; } - protected int indexPicasaWeb() { return -1; } - protected int indexPrivate() { return -1; } - protected int indexTitle() { return -1; } - protected int indexDisplayName() { return -1; } - protected int indexThumbId() { return -1; } - - // TODO review this probably should be based on DATE_TAKEN same as images - private String sortOrder() { - String ascending = (mSort == SORT_ASCENDING ? " ASC" : " DESC"); - return - DrmStore.Images.TITLE + ascending + "," + - DrmStore.Images._ID; - } - } - - class ImageListUber implements IImageList { - private IImageList [] mSubList; - private int mSort; - private IImageList.OnChange mListener = null; - Handler mHandler; - - // This is an array of Longs wherein each Long consists of - // two components. The first component indicates the number of - // consecutive entries that belong to a given sublist. - // The second component indicates which sublist we're referring - // to (an int which is used to index into mSubList). - ArrayList<Long> mSkipList = null; - - int [] mSkipCounts = null; - - public HashMap<String, String> getBucketIds() { - HashMap<String, String> hashMap = new HashMap<String, String>(); - for (IImageList list: mSubList) { - hashMap.putAll(list.getBucketIds()); - } - return hashMap; - } - - public ImageListUber(IImageList [] sublist, int sort) { - mSubList = sublist.clone(); - mSort = sort; - - if (mListener != null) { - for (IImageList list: sublist) { - list.setOnChangeListener(new OnChange() { - public void onChange(IImageList list) { - if (mListener != null) { - mListener.onChange(ImageListUber.this); - } - } - }, mHandler); - } - } - } - - public void checkThumbnails(ThumbCheckCallback cb, int totalThumbnails) { - for (IImageList i : mSubList) { - int count = i.getCount(); - i.checkThumbnails(cb, totalThumbnails); - totalThumbnails -= count; - } - } - - public void commitChanges() { - final IImageList sublist[] = mSubList; - final int length = sublist.length; - for (int i = 0; i < length; i++) - sublist[i].commitChanges(); - } - - public void deactivate() { - final IImageList sublist[] = mSubList; - final int length = sublist.length; - int pos = -1; - while (++pos < length) { - IImageList sub = sublist[pos]; - sub.deactivate(); - } - } - - public int getCount() { - final IImageList sublist[] = mSubList; - final int length = sublist.length; - int count = 0; - for (int i = 0; i < length; i++) - count += sublist[i].getCount(); - return count; - } - - public boolean isEmpty() { - final IImageList sublist[] = mSubList; - final int length = sublist.length; - for (int i = 0; i < length; i++) { - if (! sublist[i].isEmpty()) { - return false; - } - } - return true; - } - - // mSkipCounts is used to tally the counts as we traverse - // the mSkipList. It's a member variable only so that - // we don't have to allocate each time through. Otherwise - // it could just as easily be a local. - - public synchronized IImage getImageAt(int index) { - if (index < 0 || index > getCount()) - throw new IndexOutOfBoundsException("index " + index + " out of range max is " + getCount()); - - // first make sure our allocations are in order - if (mSkipCounts == null || mSubList.length > mSkipCounts.length) - mSkipCounts = new int[mSubList.length]; - - if (mSkipList == null) - mSkipList = new ArrayList<Long>(); - - // zero out the mSkipCounts since that's only used for the - // duration of the function call - for (int i = 0; i < mSubList.length; i++) - mSkipCounts[i] = 0; - - // a counter of how many images we've skipped in - // trying to get to index. alternatively we could - // have decremented index but, alas, I liked this - // way more. - int skipCount = 0; - - // scan the existing mSkipList to see if we've computed - // enough to just return the answer - for (int i = 0; i < mSkipList.size(); i++) { - long v = mSkipList.get(i); - - int offset = (int) (v & 0xFFFF); - int which = (int) (v >> 32); - - if (skipCount + offset > index) { - int subindex = mSkipCounts[which] + (index - skipCount); - IImage img = mSubList[which].getImageAt(subindex); - return img; - } - - skipCount += offset; - mSkipCounts[which] += offset; - } - - // if we get here we haven't computed the answer for - // "index" yet so keep computing. This means running - // through the list of images and either modifying the - // last entry or creating a new one. - long count = 0; - while (true) { - long maxTimestamp = mSort == SORT_ASCENDING ? Long.MAX_VALUE : Long.MIN_VALUE; - int which = -1; - for (int i = 0; i < mSubList.length; i++) { - int pos = mSkipCounts[i]; - IImageList list = mSubList[i]; - if (pos < list.getCount()) { - IImage image = list.getImageAt(pos); - // this should never be null but sometimes the database is - // causing problems and it is null - if (image != null) { - long timestamp = image.getDateTaken(); - if (mSort == SORT_ASCENDING ? (timestamp < maxTimestamp) : (timestamp > maxTimestamp)) { - maxTimestamp = timestamp; - which = i; - } - } - } - } - - if (which == -1) { - if (VERBOSE) Log.v(TAG, "which is -1, returning null"); - return null; - } - - boolean done = false; - count = 1; - if (mSkipList.size() > 0) { - int pos = mSkipList.size() - 1; - long oldEntry = mSkipList.get(pos); - if ((oldEntry >> 32) == which) { - long newEntry = oldEntry + 1; - mSkipList.set(pos, newEntry); - done = true; - } - } - if (!done) { - long newEntry = ((long)which << 32) | count; - if (VERBOSE) { - Log.v(TAG, "new entry is " + Long.toHexString(newEntry)); - } - mSkipList.add(newEntry); - } - - if (skipCount++ == index) { - return mSubList[which].getImageAt(mSkipCounts[which]); - } - mSkipCounts[which] += 1; - } - } - - public IImage getImageForUri(Uri uri) { - // TODO perhaps we can preflight the base of the uri - // against each sublist first - for (int i = 0; i < mSubList.length; i++) { - IImage img = mSubList[i].getImageForUri(uri); - if (img != null) - return img; - } - return null; - } - - /** - * Modify the skip list when an image is deleted by finding - * the relevant entry in mSkipList and decrementing the - * counter. This is simple because deletion can never - * cause change the order of images. - */ - public void modifySkipCountForDeletedImage(int index) { - int skipCount = 0; - - for (int i = 0; i < mSkipList.size(); i++) { - long v = mSkipList.get(i); - - int offset = (int) (v & 0xFFFF); - int which = (int) (v >> 32); - - if (skipCount + offset > index) { - mSkipList.set(i, v-1); - break; - } - - skipCount += offset; - } - } - - public boolean removeImage(IImage image) { - IImageList parent = image.getContainer(); - int pos = -1; - int baseIndex = 0; - while (++pos < mSubList.length) { - IImageList sub = mSubList[pos]; - if (sub == parent) { - if (sub.removeImage(image)) { - modifySkipCountForDeletedImage(baseIndex); - return true; - } else { - break; - } - } - baseIndex += sub.getCount(); - } - return false; - } - - public void removeImageAt(int index) { - IImage img = getImageAt(index); - if (img != null) { - IImageList list = img.getContainer(); - if (list != null) { - list.removeImage(img); - modifySkipCountForDeletedImage(index); - } - } - } - - public void removeOnChangeListener(OnChange changeCallback) { - if (changeCallback == mListener) - mListener = null; - } - - public void setOnChangeListener(OnChange changeCallback, Handler h) { - mListener = changeCallback; - mHandler = h; - } - - } - - public static abstract class SimpleBaseImage implements IImage { - public void commitChanges() { - throw new UnsupportedOperationException(); - } - - public InputStream fullSizeImageData() { - throw new UnsupportedOperationException(); - } - - public long fullSizeImageId() { - return 0; - } - - public Uri fullSizeImageUri() { - throw new UnsupportedOperationException(); - } - - public IImageList getContainer() { - return null; - } - - public long getDateTaken() { - return 0; - } - - public String getMimeType() { - throw new UnsupportedOperationException(); - } - - public String getDescription() { - throw new UnsupportedOperationException(); - } - - public boolean getIsPrivate() { - throw new UnsupportedOperationException(); - } - - public double getLatitude() { - return 0D; - } - - public double getLongitude() { - return 0D; - } - - public String getTitle() { - throw new UnsupportedOperationException(); - } - - public String getDisplayName() { - throw new UnsupportedOperationException(); - } - - public String getPicasaId() { - return null; - } - - public int getRow() { - throw new UnsupportedOperationException(); - } - - public int getHeight() { - return 0; - } - - public int getWidth() { - return 0; - } - - public boolean hasLatLong() { - return false; - } - - public boolean isReadonly() { - return true; - } - - public boolean isDrm() { - return false; - } - - public void onRemove() { - throw new UnsupportedOperationException(); - } - - public boolean rotateImageBy(int degrees) { - return false; - } - - public void setDescription(String description) { - throw new UnsupportedOperationException(); - } - - public void setIsPrivate(boolean isPrivate) { - throw new UnsupportedOperationException(); - } - - public void setName(String name) { - throw new UnsupportedOperationException(); - } - - public void setPicasaId(long id) { - } - - public void setPicasaId(String id) { - } - - public Uri thumbUri() { - throw new UnsupportedOperationException(); - } - } - - class SingleImageList extends BaseImageList implements IImageList { - private IImage mSingleImage; - private ContentResolver mContentResolver; - private Uri mUri; - - class UriImage extends SimpleBaseImage { - - UriImage() { - } - - public String getDataPath() { - return mUri.getPath(); - } - - InputStream getInputStream() { - try { - if (mUri.getScheme().equals("file")) { - String path = mUri.getPath(); - if (VERBOSE) - Log.v(TAG, "path is " + path); - return new java.io.FileInputStream(mUri.getPath()); - } else { - return mContentResolver.openInputStream(mUri); - } - } catch (FileNotFoundException ex) { - return null; - } - } - - ParcelFileDescriptor getPFD() { - try { - if (mUri.getScheme().equals("file")) { - String path = mUri.getPath(); - if (VERBOSE) - Log.v(TAG, "path is " + path); - return ParcelFileDescriptor.open(new File(path), ParcelFileDescriptor.MODE_READ_ONLY); - } else { - return mContentResolver.openFileDescriptor(mUri, "r"); - } - } catch (FileNotFoundException ex) { - return null; - } - } - - /* (non-Javadoc) - * @see com.android.camera.ImageManager.IImage#fullSizeBitmap(int) - */ - public Bitmap fullSizeBitmap(int targetWidthHeight) { - try { - ParcelFileDescriptor pfdInput = getPFD(); - BitmapFactory.Options options = new BitmapFactory.Options(); - options.inJustDecodeBounds = true; - BitmapFactory.decodeFileDescriptor(pfdInput.getFileDescriptor(), null, options); - - if (targetWidthHeight != -1) - options.inSampleSize = computeSampleSize(options, targetWidthHeight); - - options.inJustDecodeBounds = false; - options.inDither = false; - options.inPreferredConfig = Bitmap.Config.ARGB_8888; - - Bitmap b = BitmapFactory.decodeFileDescriptor(pfdInput.getFileDescriptor(), null, options); - if (VERBOSE) { - Log.v(TAG, "B: got bitmap " + b + " with sampleSize " + options.inSampleSize); - } - pfdInput.close(); - return b; - } catch (Exception ex) { - Log.e(TAG, "got exception decoding bitmap " + ex.toString()); - return null; - } - } - - public IGetBitmap_cancelable fullSizeBitmap_cancelable(final int targetWidthOrHeight) { - final class LoadBitmapCancelable extends BaseCancelable implements IGetBitmap_cancelable { - ParcelFileDescriptor pfdInput; - BitmapFactory.Options mOptions = new BitmapFactory.Options(); - long mCancelInitiationTime; - - public LoadBitmapCancelable(ParcelFileDescriptor pfd) { - pfdInput = pfd; - } - - public boolean doCancelWork() { - if (VERBOSE) - Log.v(TAG, "requesting bitmap load cancel"); - mCancelInitiationTime = System.currentTimeMillis(); - mOptions.requestCancelDecode(); - return true; - } - - public Bitmap get() { - try { - Bitmap b = makeBitmap(targetWidthOrHeight, fullSizeImageUri(), pfdInput, mOptions); - if (b == null && mCancelInitiationTime != 0) { - if (VERBOSE) - Log.v(TAG, "cancel returned null bitmap -- took " + (System.currentTimeMillis()-mCancelInitiationTime)); - } - if (VERBOSE) Log.v(TAG, "b is " + b); - return b; - } catch (Exception ex) { - return null; - } finally { - acknowledgeCancel(); - } - } - } - - try { - ParcelFileDescriptor pfdInput = getPFD(); - if (pfdInput == null) - return null; - if (VERBOSE) Log.v(TAG, "inputStream is " + pfdInput); - return new LoadBitmapCancelable(pfdInput); - } catch (UnsupportedOperationException ex) { - return null; - } - } - - @Override - public Uri fullSizeImageUri() { - return mUri; - } - - @Override - public InputStream fullSizeImageData() { - return getInputStream(); - } - - public long imageId() { - return 0; - } - - public Bitmap miniThumbBitmap() { - return thumbBitmap(); - } - - @Override - public String getTitle() { - return mUri.toString(); - } - - @Override - public String getDisplayName() { - return getTitle(); - } - - @Override - public String getDescription() { - return ""; - } - - public Bitmap thumbBitmap() { - Bitmap b = fullSizeBitmap(THUMBNAIL_TARGET_SIZE); - if (b != null) { - Matrix m = new Matrix(); - float scale = Math.min(1F, THUMBNAIL_TARGET_SIZE / (float) b.getWidth()); - m.setScale(scale, scale); - Bitmap scaledBitmap = Bitmap.createBitmap(b, 0, 0, b.getWidth(), b.getHeight(), m, true); - return scaledBitmap; - } else { - return null; - } - } - - private BitmapFactory.Options snifBitmapOptions() { - ParcelFileDescriptor input = getPFD(); - if (input == null) - return null; - try { - Uri uri = fullSizeImageUri(); - BitmapFactory.Options options = new BitmapFactory.Options(); - options.inJustDecodeBounds = true; - BitmapFactory.decodeFileDescriptor(input.getFileDescriptor(), null, options); - return options; - } finally { - try { - if (input != null) { - input.close(); - } - } catch (IOException ex) { - } - } - } - - @Override - public String getMimeType() { - BitmapFactory.Options options = snifBitmapOptions(); - return (options!=null) ? options.outMimeType : ""; - } - - @Override - public int getHeight() { - BitmapFactory.Options options = snifBitmapOptions(); - return (options!=null) ? options.outHeight : 0; - } - - @Override - public int getWidth() { - BitmapFactory.Options options = snifBitmapOptions(); - return (options!=null) ? options.outWidth : 0; - } - } - - public SingleImageList(ContentResolver cr, Uri uri) { - super(null, cr, uri, ImageManager.SORT_ASCENDING, null); - mContentResolver = cr; - mUri = uri; - mSingleImage = new UriImage(); - } - - public HashMap<String, String> getBucketIds() { - throw new UnsupportedOperationException(); - } - - public void deactivate() { - // nothing to do here - } - - public int getCount() { - return 1; - } - - public boolean isEmpty() { - return false; - } - - public IImage getImageAt(int i) { - if (i == 0) - return mSingleImage; - - return null; - } - - public IImage getImageForUri(Uri uri) { - if (uri.equals(mUri)) - return mSingleImage; - else - return null; - } - - public IImage getImageWithId(long id) { - throw new UnsupportedOperationException(); - } - - @Override - protected int indexOrientation() { - return -1; - } - - @Override - protected int indexDateTaken() { - return -1; - } - - @Override - protected int indexMimeType() { - return -1; - } - - @Override - protected int indexDescription() { - return -1; - } - - @Override - protected int indexId() { - return -1; - } - - @Override - protected int indexData() { - return -1; - } - - @Override - protected int indexLatitude() { - return -1; - } - - @Override - protected int indexLongitude() { - return -1; - } - - @Override - protected int indexMiniThumbId() { - return -1; - } - - @Override - protected int indexPicasaWeb() { - return -1; - } - - @Override - protected int indexPrivate() { - return -1; - } - - @Override - protected int indexTitle() { - return -1; - } - - @Override - protected int indexDisplayName() { - return -1; - } - - @Override - protected int indexThumbId() { - return -1; - } - - private InputStream makeInputStream(Uri uri) { - InputStream input = null; - try { - input = mContentResolver.openInputStream(uri); - return input; - } catch (IOException ex) { - return null; - } - } - - @Override - protected Bitmap makeBitmap(int targetWidthHeight, Uri uri, ParcelFileDescriptor pfdInput, BitmapFactory.Options options) { - Bitmap b = null; - - try { - if (options == null) - options = new BitmapFactory.Options(); - options.inSampleSize = 1; - - if (targetWidthHeight != -1) { - options.inJustDecodeBounds = true; - BitmapFactory.decodeFileDescriptor(pfdInput.getFileDescriptor(), null, options); - - options.inSampleSize = computeSampleSize(options, targetWidthHeight); - options.inJustDecodeBounds = false; - } - b = BitmapFactory.decodeFileDescriptor(pfdInput.getFileDescriptor(), null, options); - if (VERBOSE) { - Log.v(TAG, "C: got bitmap " + b + " with sampleSize " + options.inSampleSize); - } - pfdInput.close(); - } catch (IOException ex) { - if (VERBOSE) Log.v(TAG, "got io exception " + ex); - return null; - } - return b; - } - } - - class ThreadSafeOutputStream extends OutputStream { - java.io.OutputStream mDelegateStream; - boolean mClosed; - - public ThreadSafeOutputStream(OutputStream delegate) { - mDelegateStream = delegate; - } - - @Override - synchronized public void close() throws IOException { - try { - mClosed = true; - mDelegateStream.close(); - } catch (IOException ex) { - - } - } - - @Override - synchronized public void flush() throws IOException { - super.flush(); - } - - @Override - public void write(byte[] b, int offset, int length) throws IOException { - /* - mDelegateStream.write(b, offset, length); - return; - */ - while (length > 0) { - synchronized (this) { - if (mClosed) - return; - - int writeLength = Math.min(8192, length); - mDelegateStream.write(b, offset, writeLength); - offset += writeLength; - length -= writeLength; - } - } - } - - @Override - synchronized public void write(int oneByte) throws IOException { - if (mClosed) - return; - mDelegateStream.write(oneByte); - } - } - - class VideoList extends BaseImageList implements IImageList { - private final String[] sProjection = new String[] { - Video.Media._ID, - Video.Media.DATA, - Video.Media.DATE_TAKEN, - Video.Media.TITLE, - Video.Media.DISPLAY_NAME, - Video.Media.DESCRIPTION, - Video.Media.IS_PRIVATE, - Video.Media.TAGS, - Video.Media.CATEGORY, - Video.Media.LANGUAGE, - Video.Media.LATITUDE, - Video.Media.LONGITUDE, - Video.Media.MINI_THUMB_MAGIC, - Video.Media.MIME_TYPE, - }; - - final int INDEX_ID = indexOf(sProjection, Video.Media._ID); - final int INDEX_DATA = indexOf(sProjection, Video.Media.DATA); - final int INDEX_DATE_TAKEN = indexOf(sProjection, Video.Media.DATE_TAKEN); - final int INDEX_TITLE = indexOf(sProjection, Video.Media.TITLE); - final int INDEX_DISPLAY_NAME = indexOf(sProjection, Video.Media.DISPLAY_NAME); - final int INDEX_MIME_TYPE = indexOf(sProjection, Video.Media.MIME_TYPE); - final int INDEX_DESCRIPTION = indexOf(sProjection, Video.Media.DESCRIPTION); - final int INDEX_PRIVATE = indexOf(sProjection, Video.Media.IS_PRIVATE); - final int INDEX_TAGS = indexOf(sProjection, Video.Media.TAGS); - final int INDEX_CATEGORY = indexOf(sProjection, Video.Media.CATEGORY); - final int INDEX_LANGUAGE = indexOf(sProjection, Video.Media.LANGUAGE); - final int INDEX_LATITUDE = indexOf(sProjection, Video.Media.LATITUDE); - final int INDEX_LONGITUDE = indexOf(sProjection, Video.Media.LONGITUDE); - final int INDEX_MINI_THUMB_MAGIC = indexOf(sProjection, Video.Media.MINI_THUMB_MAGIC); - final int INDEX_THUMB_ID = indexOf(sProjection, BaseColumns._ID); - - public VideoList(Context ctx, ContentResolver cr, Uri uri, Uri thumbUri, - int sort, String bucketId) { - super(ctx, cr, uri, sort, bucketId); - - mCursor = createCursor(); - if (mCursor == null) { - Log.e(TAG, "unable to create video cursor for " + mBaseUri); - throw new UnsupportedOperationException(); - } - - if (Config.LOGV) { - Log.v(TAG, "for " + mUri.toString() + " got cursor " + mCursor + " with length " - + (mCursor != null ? mCursor.getCount() : -1)); - } - - if (mCursor == null) { - throw new UnsupportedOperationException(); - } - if (mCursor != null && mCursor.moveToFirst()) { - int row = 0; - do { - long imageId = mCursor.getLong(indexId()); - long dateTaken = mCursor.getLong(indexDateTaken()); - long miniThumbId = mCursor.getLong(indexMiniThumbId()); - mCache.put(imageId, new VideoObject(imageId, miniThumbId, mContentResolver, - this, dateTaken, row++)); - } while (mCursor.moveToNext()); - } - } - - public HashMap<String, String> getBucketIds() { - Cursor c = Images.Media.query( - mContentResolver, - mBaseUri.buildUpon().appendQueryParameter("distinct", "true").build(), - new String[] { - VideoColumns.BUCKET_DISPLAY_NAME, - VideoColumns.BUCKET_ID - }, - whereClause(), - whereClauseArgs(), - sortOrder()); - - HashMap<String, String> hash = new HashMap<String, String>(); - if (c != null && c.moveToFirst()) { - do { - hash.put(c.getString(1), c.getString(0)); - } while (c.moveToNext()); - } - return hash; - } - - protected String whereClause() { - if (mBucketId != null) { - return Images.Media.BUCKET_ID + " = '" + mBucketId + "'"; - } else { - return null; - } - } - - protected String[] whereClauseArgs() { - return null; - } - - @Override - protected String thumbnailWhereClause() { - return sMiniThumbIsNull; - } - - @Override - protected String[] thumbnailWhereClauseArgs() { - return null; - } - - protected Cursor createCursor() { - Cursor c = - Images.Media.query( - mContentResolver, - mBaseUri, - sProjection, - whereClause(), - whereClauseArgs(), - sortOrder()); - if (VERBOSE) - Log.v(TAG, "createCursor got cursor with count " + (c == null ? -1 : c.getCount())); - return c; - } - - protected int indexOrientation() { return -1; } - protected int indexDateTaken() { return INDEX_DATE_TAKEN; } - protected int indexDescription() { return INDEX_DESCRIPTION; } - protected int indexMimeType() { return INDEX_MIME_TYPE; } - protected int indexData() { return INDEX_DATA; } - protected int indexId() { return INDEX_ID; } - protected int indexLatitude() { return INDEX_LATITUDE; } - protected int indexLongitude() { return INDEX_LONGITUDE; } - protected int indexMiniThumbId() { return INDEX_MINI_THUMB_MAGIC; } - protected int indexPicasaWeb() { return -1; } - protected int indexPrivate() { return INDEX_PRIVATE; } - protected int indexTitle() { return INDEX_TITLE; } - protected int indexDisplayName() { return -1; } - protected int indexThumbId() { return INDEX_THUMB_ID; } - - @Override - protected IImage make(long id, long miniThumbId, ContentResolver cr, IImageList list, - long timestamp, int index, int rotation) { - return new VideoObject(id, miniThumbId, mContentResolver, this, timestamp, index); - } - - @Override - protected Bitmap makeBitmap(int targetWidthHeight, Uri uri, ParcelFileDescriptor pfdInput, - BitmapFactory.Options options) { - MediaPlayer mp = new MediaPlayer(); - Bitmap thumbnail = sDefaultThumbnail; - try { - mp.setDataSource(mContext, uri); -// int duration = mp.getDuration(); -// int at = duration > 2000 ? 1000 : duration / 2; - int at = 1000; - thumbnail = mp.getFrameAt(at); - if (Config.LOGV) { - if ( thumbnail != null) { - Log.v(TAG, "getFrameAt @ " + at + " returned " + thumbnail + "; " + - thumbnail.getWidth() + " " + thumbnail.getHeight()); - } else { - Log.v(TAG, "getFrame @ " + at + " failed for " + uri); - } - } - } catch (IOException ex) { - } catch (IllegalArgumentException ex) { - } catch (SecurityException ex) { - } finally { - mp.release(); - } - return thumbnail; - } - - - private String sortOrder() { - return Video.Media.DATE_TAKEN + (mSort == SORT_ASCENDING ? " ASC " : " DESC"); - } - } - - private final static Bitmap sDefaultThumbnail = Bitmap.createBitmap(32, 32, Bitmap.Config.RGB_565); - - /** - * Represents a particular video and provides access - * to the underlying data and two thumbnail bitmaps - * as well as other information such as the id, and - * the path to the actual video data. - */ - class VideoObject extends BaseImage implements IImage { - /** - * Constructor. - * - * @param id the image id of the image - * @param cr the content resolver - */ - protected VideoObject(long id, long miniThumbId, ContentResolver cr, VideoList container, - long dateTaken, int row) { - super(id, miniThumbId, cr, container, row); - } - - protected Bitmap.CompressFormat compressionType() { - return Bitmap.CompressFormat.JPEG; - } - - @Override - public boolean equals(Object other) { - if (other == null) - return false; - if (!(other instanceof VideoObject)) - return false; - - return fullSizeImageUri().equals(((VideoObject)other).fullSizeImageUri()); - } - - public String getDataPath() { - String path = null; - Cursor c = getCursor(); - synchronized (c) { - if (c.moveToPosition(getRow())) { - int column = ((VideoList)getContainer()).indexData(); - if (column >= 0) - path = c.getString(column); - } - } - return path; - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#fullSizeBitmap() - */ - public Bitmap fullSizeBitmap(int targetWidthHeight) { - return sNoImageBitmap; - } - - public IGetBitmap_cancelable fullSizeBitmap_cancelable(int targetWidthHeight) { - return null; - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#fullSizeImageData() - */ - public InputStream fullSizeImageData() { - try { - InputStream input = mContentResolver.openInputStream( - fullSizeImageUri()); - return input; - } catch (IOException ex) { - return null; - } - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#fullSizeImageId() - */ - public long fullSizeImageId() { - return mId; - } - - public String getCategory() { - return getStringEntry(((VideoList)mContainer).INDEX_CATEGORY); - } - - public int getHeight() { - return 0; - } - - public String getLanguage() { - return getStringEntry(((VideoList)mContainer).INDEX_LANGUAGE); - } - - public String getPicasaId() { - return null; - } - - private String getStringEntry(int entryName) { - String entry = null; - Cursor c = getCursor(); - synchronized(c) { - if (c.moveToPosition(getRow())) { - entry = c.getString(entryName); - } - } - return entry; - } - - public String getTags() { - return getStringEntry(((VideoList)mContainer).INDEX_TAGS); - } - - public int getWidth() { - return 0; - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#imageId() - */ - public long imageId() { - return mId; - } - - public boolean isReadonly() { - return false; - } - - public boolean isDrm() { - return false; - } - - public boolean rotateImageBy(int degrees) { - return false; - } - - public void setCategory(String category) { - setStringEntry(category, ((VideoList)mContainer).INDEX_CATEGORY); - } - - public void setLanguage(String language) { - setStringEntry(language, ((VideoList)mContainer).INDEX_LANGUAGE); - } - - private void setStringEntry(String entry, int entryName) { - Cursor c = getCursor(); - synchronized (c) { - if (c.moveToPosition(getRow())) { - c.updateString(entryName, entry); - } - } - } - - public void setTags(String tags) { - setStringEntry(tags, ((VideoList)mContainer).INDEX_TAGS); - } - - /* (non-Javadoc) - * @see com.android.camera.IImage#thumb1() - */ - public Bitmap thumbBitmap() { - return fullSizeBitmap(320); - } - - @Override - public String toString() { - StringBuilder sb = new StringBuilder(); - sb.append("" + mId); - return sb.toString(); - } - } - - private final static Bitmap sNoImageBitmap = Bitmap.createBitmap(1, 1, Bitmap.Config.RGB_565); - - /* - * How much quality to use when storing the thumbnail. - */ - private static ImageManager sInstance = null; - private static final int MINI_THUMB_TARGET_SIZE = 96; - private static final int THUMBNAIL_TARGET_SIZE = 320; - - private static final String[] THUMB_PROJECTION = new String[] { - BaseColumns._ID, // 0 - Images.Thumbnails.IMAGE_ID, // 1 - Images.Thumbnails.WIDTH, - Images.Thumbnails.HEIGHT - }; - - private static Uri sStorageURI = Images.Media.EXTERNAL_CONTENT_URI; - - private static Uri sThumbURI = Images.Thumbnails.EXTERNAL_CONTENT_URI; - - private static Uri sVideoStorageURI = Uri.parse("content://media/external/video/media"); - - private static Uri sVideoThumbURI = Uri.parse("content://media/external/video/thumbnails"); - /** - * Returns an ImageList object that contains - * all of the images. - * @param cr - * @param location - * @param includeImages - * @param includeVideo - * @return the singleton ImageList - */ - static final public int SORT_ASCENDING = 1; - - static final public int SORT_DESCENDING = 2; - - static final public int INCLUDE_IMAGES = (1 << 0); - static final public int INCLUDE_DRM_IMAGES = (1 << 1); - static final public int INCLUDE_VIDEOS = (1 << 2); - - static public DataLocation getDefaultDataLocation() { - return DataLocation.EXTERNAL; - } - private static int indexOf(String [] array, String s) { - for (int i = 0; i < array.length; i++) { - if (array[i].equals(s)) { - return i; - } - } - return -1; - } - - /** - * Returns the singleton instance of the ImageManager. - * @return the ImageManager instance. - */ - public static ImageManager instance() { - if (sInstance == null) { - sInstance = new ImageManager(); - } - return sInstance; - } - - /** - * Creates a byte[] for a given bitmap of the desired size. Recycles the input bitmap. - */ - static public byte[] miniThumbData(Bitmap source) { - if (source == null) - return null; - - Bitmap miniThumbnail = extractMiniThumb(source, MINI_THUMB_TARGET_SIZE, - MINI_THUMB_TARGET_SIZE); - java.io.ByteArrayOutputStream miniOutStream = new java.io.ByteArrayOutputStream(); - miniThumbnail.compress(Bitmap.CompressFormat.JPEG, 75, miniOutStream); - miniThumbnail.recycle(); - - try { - miniOutStream.close(); - byte [] data = miniOutStream.toByteArray(); - return data; - } catch (java.io.IOException ex) { - Log.e(TAG, "got exception ex " + ex); - } - return null; - } - - /** - * Creates a centered bitmap of the desired size. Recycles the input. - * @param source - * @return - */ - static public Bitmap extractMiniThumb(Bitmap source, int width, int height) { - if (source == null) { - return null; - } - - float scale; - if (source.getWidth() < source.getHeight()) { - scale = width / (float)source.getWidth(); - } else { - scale = height / (float)source.getHeight(); - } - Matrix matrix = new Matrix(); - matrix.setScale(scale, scale); - Bitmap miniThumbnail = ImageLoader.transform(matrix, source, - width, height, false); - - if (miniThumbnail != source) { - source.recycle(); - } - return miniThumbnail; - } - - static Bitmap rotate(Bitmap b, int degrees) { - if (degrees != 0 && b != null) { - Matrix m = new Matrix(); - m.setRotate(degrees, (float) b.getWidth() / 2, (float) b.getHeight() / 2); - - Bitmap b2 = Bitmap.createBitmap(b, 0, 0, b.getWidth(), b.getHeight(), m, true); - // TODO should recycle here but that needs more testing/verification -// b.recycle(); - b = b2; - } - return b; - } - - public static int roundOrientation(int orientationInput) { - int orientation = orientationInput; - if (orientation == -1) - orientation = 0; - - orientation = orientation % 360; - int retVal; - if (orientation < (0*90) + 45) { - retVal = 0; - } else if (orientation < (1*90) + 45) { - retVal = 90; - } else if (orientation < (2*90) + 45) { - retVal = 180; - } else if (orientation < (3*90) + 45) { - retVal = 270; - } else { - retVal = 0; - } - - if (VERBOSE) Log.v(TAG, "map orientation " + orientationInput + " to " + retVal); - return retVal; - } - - - /** - * @return true if the mimetype is an image mimetype. - */ - public static boolean isImageMimeType(String mimeType) { - return mimeType.startsWith("image/"); - } - - /** - * @return true if the mimetype is a video mimetype. - */ - public static boolean isVideoMimeType(String mimeType) { - return mimeType.startsWith("video/"); - } - - /** - * @return true if the image is an image. - */ - public static boolean isImage(IImage image) { - return isImageMimeType(image.getMimeType()); - } - - /** - * @return true if the image is a video. - */ - public static boolean isVideo(IImage image) { - return isVideoMimeType(image.getMimeType()); - } - - public Uri addImage( - final Context ctx, - final ContentResolver cr, - final String imageName, - final String description, - final long dateTaken, - final Location location, - final int orientation, - final String directory, - final String filename) { - ContentValues values = new ContentValues(7); - values.put(Images.Media.TITLE, imageName); - values.put(Images.Media.DISPLAY_NAME, imageName); - values.put(Images.Media.DESCRIPTION, description); - values.put(Images.Media.DATE_TAKEN, dateTaken); - values.put(Images.Media.MIME_TYPE, "image/jpeg"); - values.put(Images.Media.ORIENTATION, orientation); - - File parentFile = new File(directory); - // Lowercase the path for hashing. This avoids duplicate buckets if the filepath - // case is changed externally. - // Keep the original case for display. - String path = parentFile.toString().toLowerCase(); - String name = parentFile.getName(); - - if (VERBOSE) Log.v(TAG, "addImage id is " + path.hashCode() + "; name " + name + "; path is " + path); - - if (location != null) { - if (VERBOSE) { - Log.v(TAG, "lat long " + location.getLatitude() + " / " + location.getLongitude()); - } - values.put(Images.Media.LATITUDE, location.getLatitude()); - values.put(Images.Media.LONGITUDE, location.getLongitude()); - } - - if (directory != null && filename != null) { - String value = directory + "/" + filename; - values.put("_data", value); - } - - long t3 = System.currentTimeMillis(); - Uri uri = cr.insert(sStorageURI, values); - - // The line above will create a filename that ends in .jpg - // That filename is what will be handed to gmail when a user shares a photo. - // Gmail gets the name of the picture attachment from the "DISPLAY_NAME" field. - // Extract the filename and jam it into the display name. - Cursor c = cr.query( - uri, - new String [] { ImageColumns._ID, Images.Media.DISPLAY_NAME, "_data" }, - null, - null, - null); - if (c.moveToFirst()) { - String filePath = c.getString(2); - if (filePath != null) { - int pos = filePath.lastIndexOf("/"); - if (pos >= 0) { - filePath = filePath.substring(pos + 1); // pick off the filename - c.updateString(1, filePath); - c.commitUpdates(); - } - } - } - c.close(); - return uri; - } - - public IAddImage_cancelable storeImage( - final Uri uri, - final Context ctx, - final ContentResolver cr, - final int orientation, - final Bitmap source, - final byte [] jpegData) { - class AddImageCancelable extends BaseCancelable implements IAddImage_cancelable { - private IGetBoolean_cancelable mSaveImageCancelable; - - public boolean doCancelWork() { - if (VERBOSE) { - Log.v(TAG, "calling AddImageCancelable.cancel() " + mSaveImageCancelable); - } - - if (mSaveImageCancelable != null) { - mSaveImageCancelable.cancel(); - } - return true; - } - - public void get() { - if (source == null && jpegData == null) { - throw new IllegalArgumentException("source cannot be null"); - } - - try { - long t1 = System.currentTimeMillis(); - synchronized (this) { - if (mCancel) { - throw new CanceledException(); - } - } - long id = ContentUris.parseId(uri); - - BaseImageList il = new ImageList(ctx, cr, sStorageURI, sThumbURI, SORT_ASCENDING, null); - ImageManager.Image image = new Image(id, 0, cr, il, il.getCount(), 0); - long t5 = System.currentTimeMillis(); - Cursor c = cr.query( - uri, - new String [] { ImageColumns._ID, ImageColumns.MINI_THUMB_MAGIC, "_data" }, - null, - null, - null); - c.moveToPosition(0); - - synchronized (this) { - checkCanceled(); - mSaveImageCancelable = image.saveImageContents(source, jpegData, orientation, true, c); - } - - if (mSaveImageCancelable.get()) { - long t6 = System.currentTimeMillis(); - if (VERBOSE) Log.v(TAG, "saveImageContents took " + (t6-t5)); - if (VERBOSE) Log.v(TAG, "updating new picture with id " + id); - c.updateLong(1, id); - c.commitUpdates(); - c.close(); - long t7 = System.currentTimeMillis(); - if (VERBOSE) Log.v(TAG, "commit updates to save mini thumb took " + (t7-t6)); - } - else { - c.close(); - throw new CanceledException(); - } - } catch (CanceledException ex) { - if (VERBOSE) { - Log.v(TAG, "caught CanceledException"); - } - if (uri != null) { - if (VERBOSE) { - Log.v(TAG, "canceled... cleaning up this uri: " + uri); - } - cr.delete(uri, null, null); - } - acknowledgeCancel(); - } - } - } - return new AddImageCancelable(); - } - - static public IImageList makeImageList(Uri uri, Context ctx, int sort) { - ContentResolver cr = ctx.getContentResolver(); - String uriString = (uri != null) ? uri.toString() : ""; - // TODO we need to figure out whether we're viewing - // DRM images in a better way. Is there a constant - // for content://drm somewhere?? - IImageList imageList; - - if (uriString.startsWith("content://drm")) { - imageList = ImageManager.instance().allImages( - ctx, - cr, - ImageManager.DataLocation.ALL, - ImageManager.INCLUDE_DRM_IMAGES, - sort); - } else if (!uriString.startsWith(MediaStore.Images.Media.EXTERNAL_CONTENT_URI.toString()) - && !uriString.startsWith(MediaStore.Images.Media.INTERNAL_CONTENT_URI.toString())) { - imageList = ImageManager.instance().new SingleImageList(cr, uri); - } else { - String bucketId = uri.getQueryParameter("bucketId"); - if (VERBOSE) Log.v(TAG, "bucketId is " + bucketId); - imageList = ImageManager.instance().allImages( - ctx, - cr, - ImageManager.DataLocation.ALL, - ImageManager.INCLUDE_IMAGES, - sort, - bucketId); - } - return imageList; - } - - public IImageList emptyImageList() { - return - new IImageList() { - public void checkThumbnails(ImageManager.IImageList.ThumbCheckCallback cb, - int totalThumbnails) { - } - - public void commitChanges() { - } - - public void deactivate() { - } - - public HashMap<String, String> getBucketIds() { - return new HashMap<String,String>(); - } - - public int getCount() { - return 0; - } - - public boolean isEmpty() { - return true; - } - - public IImage getImageAt(int i) { - return null; - } - - public IImage getImageForUri(Uri uri) { - return null; - } - - public boolean removeImage(IImage image) { - return false; - } - - public void removeImageAt(int i) { - } - - public void removeOnChangeListener(ImageManager.IImageList.OnChange changeCallback) { - } - - public void setOnChangeListener(ImageManager.IImageList.OnChange changeCallback, - Handler h) { - } - - }; - } - - public IImageList allImages(Context ctx, ContentResolver cr, DataLocation location, int inclusion, int sort) { - return allImages(ctx, cr, location, inclusion, sort, null, null); - } - - public IImageList allImages(Context ctx, ContentResolver cr, DataLocation location, int inclusion, int sort, String bucketId) { - return allImages(ctx, cr, location, inclusion, sort, bucketId, null); - } - - public IImageList allImages(Context ctx, ContentResolver cr, DataLocation location, int inclusion, int sort, String bucketId, Uri specificImageUri) { - if (VERBOSE) { - Log.v(TAG, "allImages " + location + " " + ((inclusion&INCLUDE_IMAGES)!=0) + " + v=" + ((inclusion&INCLUDE_VIDEOS)!=0)); - } - - if (cr == null) { - return null; - } else { - // false ==> don't require write access - boolean haveSdCard = hasStorage(false); - - if (true) { - // use this code to merge videos and stills into the same list - ArrayList<IImageList> l = new ArrayList<IImageList>(); - - if (VERBOSE) { - Log.v(TAG, "initializing ... haveSdCard == " + haveSdCard + "; inclusion is " + String.format("%x", inclusion)); - } - if (specificImageUri != null) { - try { - if (specificImageUri.getScheme().equalsIgnoreCase("content")) - l.add(new ImageList(ctx, cr, specificImageUri, sThumbURI, sort, bucketId)); - else - l.add(new SingleImageList(cr, specificImageUri)); - } catch (UnsupportedOperationException ex) { - } - } else { - if (haveSdCard && location != DataLocation.INTERNAL) { - if ((inclusion & INCLUDE_IMAGES) != 0) { - try { - l.add(new ImageList(ctx, cr, sStorageURI, sThumbURI, sort, bucketId)); - } catch (UnsupportedOperationException ex) { - } - } - if ((inclusion & INCLUDE_VIDEOS) != 0) { - try { - l.add(new VideoList(ctx, cr, sVideoStorageURI, sVideoThumbURI, sort, bucketId)); - } catch (UnsupportedOperationException ex) { - } - } - } - if (location == DataLocation.INTERNAL || location == DataLocation.ALL) { - if ((inclusion & INCLUDE_IMAGES) != 0) { - try { - l.add(new ImageList(ctx, cr, Images.Media.INTERNAL_CONTENT_URI, - Images.Thumbnails.INTERNAL_CONTENT_URI, sort, bucketId)); - } catch (UnsupportedOperationException ex) { - } - } - if ((inclusion & INCLUDE_DRM_IMAGES) != 0) { - try { - l.add(new DrmImageList(ctx, cr, DrmStore.Images.CONTENT_URI, sort, bucketId)); - } catch (UnsupportedOperationException ex) { - } - } - } - } - - IImageList [] imageList = l.toArray(new IImageList[l.size()]); - return new ImageListUber(imageList, sort); - } else { - if (haveSdCard && location != DataLocation.INTERNAL) { - return new ImageList(ctx, cr, sStorageURI, sThumbURI, sort, bucketId); - } else { - return new ImageList(ctx, cr, Images.Media.INTERNAL_CONTENT_URI, - Images.Thumbnails.INTERNAL_CONTENT_URI, sort, bucketId); - } - } - } - } - - // Create a temporary file to see whether a volume is really writeable. It's important not to - // put it in the root directory which may have a limit on the number of files. - static private boolean checkFsWritable() { - String directoryName = Environment.getExternalStorageDirectory().toString() + "/DCIM"; - File directory = new File(directoryName); - if (!directory.isDirectory()) { - if (!directory.mkdirs()) { - return false; - } - } - File f = new File(directoryName, ".probe"); - try { - // Remove stale file if any - if (f.exists()) { - f.delete(); - } - if (!f.createNewFile()) - return false; - f.delete(); - return true; - } catch (IOException ex) { - return false; - } - } - - static public boolean hasStorage() { - return hasStorage(true); - } - - static public boolean hasStorage(boolean requireWriteAccess) { - String state = Environment.getExternalStorageState(); - if (VERBOSE) Log.v(TAG, "state is " + state); - if (Environment.MEDIA_MOUNTED.equals(state)) { - if (requireWriteAccess) { - boolean writable = checkFsWritable(); - if (VERBOSE) Log.v(TAG, "writable is " + writable); - return writable; - } else { - return true; - } - } else if (!requireWriteAccess && Environment.MEDIA_MOUNTED_READ_ONLY.equals(state)) { - return true; - } - return false; - } - - public static Cursor query(Context context, Uri uri, String[] projection, - String selection, String[] selectionArgs, String sortOrder) { - try { - ContentResolver resolver = context.getContentResolver(); - if (resolver == null) { - return null; - } - return resolver.query(uri, projection, selection, selectionArgs, sortOrder); - } catch (UnsupportedOperationException ex) { - return null; - } - - } - - public static boolean isMediaScannerScanning(Context context) { - boolean result = false; - Cursor cursor = query(context, MediaStore.getMediaScannerUri(), - new String [] { MediaStore.MEDIA_SCANNER_VOLUME }, null, null, null); - if (cursor != null) { - if (cursor.getCount() == 1) { - cursor.moveToFirst(); - result = "external".equals(cursor.getString(0)); - } - cursor.close(); - } - - if (VERBOSE) - Log.v(TAG, ">>>>>>>>>>>>>>>>>>>>>>>>> isMediaScannerScanning returning " + result); - return result; - } - - /** - * Create a video thumbnail for a video. May return null if the video is corrupt. - * @param filePath - * @return - */ - public static Bitmap createVideoThumbnail(String filePath) { - Bitmap bitmap = null; - MediaMetadataRetriever retriever = new MediaMetadataRetriever(); - try { - retriever.setMode(MediaMetadataRetriever.MODE_CAPTURE_FRAME_ONLY); - retriever.setDataSource(filePath); - bitmap = retriever.captureFrame(); - } catch(IllegalArgumentException ex) { - // Assume this is a corrupt video file - } catch (RuntimeException ex) { - // Assume this is a corrupt video file. - } finally { - try { - retriever.release(); - } catch (RuntimeException ex) { - // Ignore failures while cleaning up. - } - } - return bitmap; - } - - public static String getLastThumbPath() { - return Environment.getExternalStorageDirectory().toString() + - "/DCIM/.thumbnails/camera_last_thumb"; - } -} diff --git a/src/com/android/camera/ImageViewTouchBase.java b/src/com/android/camera/ImageViewTouchBase.java deleted file mode 100644 index 1774e46..0000000 --- a/src/com/android/camera/ImageViewTouchBase.java +++ /dev/null @@ -1,559 +0,0 @@ -package com.android.camera; - -import android.content.Context; -import android.graphics.Bitmap; -import android.graphics.Canvas; -import android.graphics.Matrix; -import android.graphics.Paint; -import android.graphics.drawable.Drawable; -import android.os.Handler; -import android.os.SystemClock; -import android.util.AttributeSet; -import android.util.Config; -import android.util.Log; -import android.view.animation.Animation; -import android.view.animation.TranslateAnimation; -import android.view.KeyEvent; -import android.widget.ImageView; - -abstract public class ImageViewTouchBase extends ImageView { - private static final String TAG = "ImageViewTouchBase"; - - // if we're animating these images, it may be faster to cache the image - // at its target size first. to do this set this variable to true. - // currently we're not animating images, so we don't need to do this - // extra work. - private final boolean USE_PERFECT_FIT_OPTIMIZATION = false; - - // This is the base transformation which is used to show the image - // initially. The current computation for this shows the image in - // it's entirety, letterboxing as needed. One could chose to - // show the image as cropped instead. - // - // This matrix is recomputed when we go from the thumbnail image to - // the full size image. - protected Matrix mBaseMatrix = new Matrix(); - - // This is the supplementary transformation which reflects what - // the user has done in terms of zooming and panning. - // - // This matrix remains the same when we go from the thumbnail image - // to the full size image. - protected Matrix mSuppMatrix = new Matrix(); - - // This is the final matrix which is computed as the concatentation - // of the base matrix and the supplementary matrix. - private Matrix mDisplayMatrix = new Matrix(); - - // Temporary buffer used for getting the values out of a matrix. - private float[] mMatrixValues = new float[9]; - - // The current bitmap being displayed. - protected Bitmap mBitmapDisplayed; - - // The thumbnail bitmap. - protected Bitmap mThumbBitmap; - - // The full size bitmap which should be used once we start zooming. - private Bitmap mFullBitmap; - - // The bitmap which is exactly sized to what we need. The decoded bitmap is - // drawn into the mPerfectFitBitmap so that animation is faster. - protected Bitmap mPerfectFitBitmap; - - // True if the image is the thumbnail. - protected boolean mBitmapIsThumbnail; - - // True if the user is zooming -- use the full size image - protected boolean mIsZooming; - - // Paint to use to clear the "mPerfectFitBitmap" - protected Paint mPaint = new Paint(); - - static boolean sNewZoomControl = false; - - int mThisWidth = -1, mThisHeight = -1; - - float mMaxZoom; - - @Override - protected void onLayout(boolean changed, int left, int top, int right, int bottom) { - super.onLayout(changed, left, top, right, bottom); - mThisWidth = right - left; - mThisHeight = bottom - top; - Runnable r = mOnLayoutRunnable; - if (r != null) { - mOnLayoutRunnable = null; - r.run(); - } - if (mBitmapDisplayed != null) { - setBaseMatrix(mBitmapDisplayed, mBaseMatrix); - setImageMatrix(getImageViewMatrix()); - } - } - - @Override - public boolean onKeyDown(int keyCode, KeyEvent event) { - if (keyCode == KeyEvent.KEYCODE_BACK && getScale() > 1.0f) { - // If we're zoomed in, pressing Back jumps out to show the entire image, otherwise Back - // returns the user to the gallery. - zoomTo(1.0f); - return true; - } - return super.onKeyDown(keyCode, event); - } - - protected Handler mHandler = new Handler(); - - protected int mLastXTouchPos; - protected int mLastYTouchPos; - - protected boolean doesScrolling() { - return true; - } - - // Translate a given point through a given matrix. - static private void translatePoint(Matrix matrix, float [] xy) { - matrix.mapPoints(xy); - } - - // Return the mapped x coordinate through the matrix. - static int mapXPoint(Matrix matrix, int point) { - // Matrix's mapPoints takes an array of x/y coordinates. - // That's why we have to allocte an array of length two - // even though we don't use the y coordinate. - float [] xy = new float[2]; - xy[0] = point; - xy[1] = 0F; - matrix.mapPoints(xy); - return (int) xy[0]; - } - - @Override - public void setImageBitmap(Bitmap bitmap) { - throw new NullPointerException(); - } - - public void setImageBitmap(Bitmap bitmap, boolean isThumbnail) { - super.setImageBitmap(bitmap); - Drawable d = getDrawable(); - if (d != null) - d.setDither(true); - mBitmapDisplayed = bitmap; - mBitmapIsThumbnail = isThumbnail; - } - - protected boolean usePerfectFitBitmap() { - return USE_PERFECT_FIT_OPTIMIZATION && !mIsZooming; - } - - public void recycleBitmaps() { - if (mFullBitmap != null) { - if (Config.LOGV) - Log.v(TAG, "recycling mFullBitmap " + mFullBitmap + "; this == " + this.hashCode()); - mFullBitmap.recycle(); - mFullBitmap = null; - } - if (mThumbBitmap != null) { - if (Config.LOGV) - Log.v(TAG, "recycling mThumbBitmap" + mThumbBitmap + "; this == " + this.hashCode()); - mThumbBitmap.recycle(); - mThumbBitmap = null; - } - - // mBitmapDisplayed is either mPerfectFitBitmap or mFullBitmap (in the case of zooming) - setImageBitmap(null, true); - } - - public void clear() { - mBitmapDisplayed = null; - recycleBitmaps(); - } - - private Runnable mOnLayoutRunnable = null; - - public void setImageBitmapResetBase(final Bitmap bitmap, final boolean resetSupp, final boolean isThumb) { - if ((bitmap != null) && (bitmap == mPerfectFitBitmap)) { - // TODO: this should be removed in production - throw new IllegalArgumentException("bitmap must not be mPerfectFitBitmap"); - } - - final int viewWidth = getWidth(); - final int viewHeight = getHeight(); - - if (viewWidth <= 0) { - mOnLayoutRunnable = new Runnable() { - public void run() { - setImageBitmapResetBase(bitmap, resetSupp, isThumb); - } - }; - return; - } - - if (isThumb && mThumbBitmap != bitmap) { - if (mThumbBitmap != null) { - mThumbBitmap.recycle(); - } - mThumbBitmap = bitmap; - } else if (!isThumb && mFullBitmap != bitmap) { - if (mFullBitmap != null) { - mFullBitmap.recycle(); - } - mFullBitmap = bitmap; - } - mBitmapIsThumbnail = isThumb; - - if (bitmap != null) { - if (!usePerfectFitBitmap()) { - setScaleType(ImageView.ScaleType.MATRIX); - setBaseMatrix(bitmap, mBaseMatrix); - setImageBitmap(bitmap, isThumb); - } else { - Matrix matrix = new Matrix(); - setBaseMatrix(bitmap, matrix); - if ((mPerfectFitBitmap == null) || - mPerfectFitBitmap.getWidth() != mThisWidth || - mPerfectFitBitmap.getHeight() != mThisHeight) { - if (mPerfectFitBitmap != null) { - if (Config.LOGV) - Log.v(TAG, "recycling mPerfectFitBitmap " + mPerfectFitBitmap.hashCode()); - mPerfectFitBitmap.recycle(); - } - mPerfectFitBitmap = Bitmap.createBitmap(mThisWidth, mThisHeight, Bitmap.Config.RGB_565); - } - Canvas canvas = new Canvas(mPerfectFitBitmap); - // clear the bitmap which may be bigger than the image and - // contain the the previous image. - canvas.drawColor(0xFF000000); - - final int bw = bitmap.getWidth(); - final int bh = bitmap.getHeight(); - final float widthScale = Math.min(viewWidth / (float)bw, 1.0f); - final float heightScale = Math.min(viewHeight/ (float)bh, 1.0f); - int translateX, translateY; - if (widthScale > heightScale) { - translateX = (int)((viewWidth -(float)bw*heightScale)*0.5f); - translateY = (int)((viewHeight-(float)bh*heightScale)*0.5f); - } else { - translateX = (int)((viewWidth -(float)bw*widthScale)*0.5f); - translateY = (int)((viewHeight-(float)bh*widthScale)*0.5f); - } - - android.graphics.Rect src = new android.graphics.Rect(0, 0, bw, bh); - android.graphics.Rect dst = new android.graphics.Rect( - translateX, translateY, - mThisWidth - translateX, mThisHeight - translateY); - canvas.drawBitmap(bitmap, src, dst, mPaint); - - setImageBitmap(mPerfectFitBitmap, isThumb); - setScaleType(ImageView.ScaleType.MATRIX); - setImageMatrix(null); - } - } else { - mBaseMatrix.reset(); - setImageBitmap(null, isThumb); - } - - if (resetSupp) - mSuppMatrix.reset(); - setImageMatrix(getImageViewMatrix()); - mMaxZoom = maxZoom(); - } - - // Center as much as possible in one or both axis. Centering is - // defined as follows: if the image is scaled down below the - // view's dimensions then center it (literally). If the image - // is scaled larger than the view and is translated out of view - // then translate it back into view (i.e. eliminate black bars). - protected void center(boolean vertical, boolean horizontal, boolean animate) { - if (mBitmapDisplayed == null) - return; - - Matrix m = getImageViewMatrix(); - - float [] topLeft = new float[] { 0, 0 }; - float [] botRight = new float[] { mBitmapDisplayed.getWidth(), mBitmapDisplayed.getHeight() }; - - translatePoint(m, topLeft); - translatePoint(m, botRight); - - float height = botRight[1] - topLeft[1]; - float width = botRight[0] - topLeft[0]; - - float deltaX = 0, deltaY = 0; - - if (vertical) { - int viewHeight = getHeight(); - if (height < viewHeight) { - deltaY = (viewHeight - height)/2 - topLeft[1]; - } else if (topLeft[1] > 0) { - deltaY = -topLeft[1]; - } else if (botRight[1] < viewHeight) { - deltaY = getHeight() - botRight[1]; - } - } - - if (horizontal) { - int viewWidth = getWidth(); - if (width < viewWidth) { - deltaX = (viewWidth - width)/2 - topLeft[0]; - } else if (topLeft[0] > 0) { - deltaX = -topLeft[0]; - } else if (botRight[0] < viewWidth) { - deltaX = viewWidth - botRight[0]; - } - } - - postTranslate(deltaX, deltaY); - if (animate) { - Animation a = new TranslateAnimation(-deltaX, 0, -deltaY, 0); - a.setStartTime(SystemClock.elapsedRealtime()); - a.setDuration(250); - setAnimation(a); - } - setImageMatrix(getImageViewMatrix()); - } - - public void copyFrom(ImageViewTouchBase other) { - mSuppMatrix.set(other.mSuppMatrix); - mBaseMatrix.set(other.mBaseMatrix); - - if (mThumbBitmap != null) - mThumbBitmap.recycle(); - - if (mFullBitmap != null) - mFullBitmap.recycle(); - - // copy the data - mThumbBitmap = other.mThumbBitmap; - mFullBitmap = null; - - if (other.mFullBitmap != null) - other.mFullBitmap.recycle(); - - // transfer "ownership" - other.mThumbBitmap = null; - other.mFullBitmap = null; - other.mBitmapIsThumbnail = true; - - setImageMatrix(other.getImageMatrix()); - setScaleType(other.getScaleType()); - - setImageBitmapResetBase(mThumbBitmap, true, true); - } - - @Override - public void setImageDrawable(android.graphics.drawable.Drawable d) { - super.setImageDrawable(d); - } - - public ImageViewTouchBase(Context context) { - super(context); - init(); - } - - public ImageViewTouchBase(Context context, AttributeSet attrs) { - super(context, attrs); - init(); - } - - private void init() { - setScaleType(ImageView.ScaleType.MATRIX); - mPaint.setDither(true); - mPaint.setFilterBitmap(true); - } - - protected float getValue(Matrix matrix, int whichValue) { - matrix.getValues(mMatrixValues); - return mMatrixValues[whichValue]; - } - - // Get the scale factor out of the matrix. - protected float getScale(Matrix matrix) { - return getValue(matrix, Matrix.MSCALE_X); - } - - protected float getScale() { - return getScale(mSuppMatrix); - } - - protected float getTranslateX() { - return getValue(mSuppMatrix, Matrix.MTRANS_X); - } - - protected float getTranslateY() { - return getValue(mSuppMatrix, Matrix.MTRANS_Y); - } - - // Setup the base matrix so that the image is centered and scaled properly. - private void setBaseMatrix(Bitmap bitmap, Matrix matrix) { - float viewWidth = getWidth(); - float viewHeight = getHeight(); - - matrix.reset(); - float widthScale = Math.min(viewWidth / (float)bitmap.getWidth(), 1.0f); - float heightScale = Math.min(viewHeight / (float)bitmap.getHeight(), 1.0f); - float scale; - if (widthScale > heightScale) { - scale = heightScale; - } else { - scale = widthScale; - } - matrix.setScale(scale, scale); - matrix.postTranslate( - (viewWidth - ((float)bitmap.getWidth() * scale))/2F, - (viewHeight - ((float)bitmap.getHeight() * scale))/2F); - } - - // Combine the base matrix and the supp matrix to make the final matrix. - protected Matrix getImageViewMatrix() { - mDisplayMatrix.set(mBaseMatrix); - mDisplayMatrix.postConcat(mSuppMatrix); - return mDisplayMatrix; - } - - private void onZoom() { - mIsZooming = true; - if (mFullBitmap != null && mFullBitmap != mBitmapDisplayed) { - setImageBitmapResetBase(mFullBitmap, false, mBitmapIsThumbnail); - } - } - - private String describe(Bitmap b) { - StringBuilder sb = new StringBuilder(); - if (b == null) { - sb.append("NULL"); - } else if (b.isRecycled()) { - sb.append(String.format("%08x: RECYCLED", b.hashCode())); - } else { - sb.append(String.format("%08x: LIVE", b.hashCode())); - sb.append(String.format("%d x %d (size == %d)", b.getWidth(), b.getHeight(), b.getWidth()*b.getHeight()*2)); - } - return sb.toString(); - } - - public void dump() { - if (Config.LOGV) { - Log.v(TAG, "dump ImageViewTouchBase " + this); - Log.v(TAG, "... mBitmapDisplayed = " + describe(mBitmapDisplayed)); - Log.v(TAG, "... mThumbBitmap = " + describe(mThumbBitmap)); - Log.v(TAG, "... mFullBitmap = " + describe(mFullBitmap)); - Log.v(TAG, "... mPerfectFitBitmap = " + describe(mPerfectFitBitmap)); - Log.v(TAG, "... mIsThumb = " + mBitmapIsThumbnail); - } - } - - static final float sPanRate = 7; - static final float sScaleRate = 1.25F; - - // Sets the maximum zoom, which is a scale relative to the base matrix. It is calculated to show - // the image at 400% zoom regardless of screen or image orientation. If in the future we decode - // the full 3 megapixel image, rather than the current 1024x768, this should be changed down to - // 200%. - protected float maxZoom() { - if (mBitmapDisplayed == null) - return 1F; - - float fw = (float) mBitmapDisplayed.getWidth() / (float)mThisWidth; - float fh = (float) mBitmapDisplayed.getHeight() / (float)mThisHeight; - float max = Math.max(fw, fh) * 4; -// Log.v(TAG, "Bitmap " + mBitmapDisplayed.getWidth() + "x" + mBitmapDisplayed.getHeight() + -// " view " + mThisWidth + "x" + mThisHeight + " max zoom " + max); - return max; - } - - protected void zoomTo(float scale, float centerX, float centerY) { - if (scale > mMaxZoom) { - scale = mMaxZoom; - } - onZoom(); - - float oldScale = getScale(); - float deltaScale = scale / oldScale; - - mSuppMatrix.postScale(deltaScale, deltaScale, centerX, centerY); - setImageMatrix(getImageViewMatrix()); - center(true, true, false); - } - - protected void zoomTo(final float scale, final float centerX, final float centerY, final float durationMs) { - final float incrementPerMs = (scale - getScale()) / durationMs; - final float oldScale = getScale(); - final long startTime = System.currentTimeMillis(); - - mHandler.post(new Runnable() { - public void run() { - long now = System.currentTimeMillis(); - float currentMs = Math.min(durationMs, (float)(now - startTime)); - float target = oldScale + (incrementPerMs * currentMs); - zoomTo(target, centerX, centerY); - - if (currentMs < durationMs) { - mHandler.post(this); - } - } - }); - } - - protected void zoomTo(float scale) { - float width = getWidth(); - float height = getHeight(); - - zoomTo(scale, width/2F, height/2F); - } - - protected void zoomIn() { - zoomIn(sScaleRate); - } - - protected void zoomOut() { - zoomOut(sScaleRate); - } - - protected void zoomIn(float rate) { - if (getScale() >= mMaxZoom) { - return; // Don't let the user zoom into the molecular level. - } - if (mBitmapDisplayed == null) { - return; - } - float width = getWidth(); - float height = getHeight(); - - mSuppMatrix.postScale(rate, rate, width/2F, height/2F); - setImageMatrix(getImageViewMatrix()); - - onZoom(); - } - - protected void zoomOut(float rate) { - if (mBitmapDisplayed == null) { - return; - } - - float width = getWidth(); - float height = getHeight(); - - Matrix tmp = new Matrix(mSuppMatrix); - tmp.postScale(1F/sScaleRate, 1F/sScaleRate, width/2F, height/2F); - if (getScale(tmp) < 1F) { - mSuppMatrix.setScale(1F, 1F, width/2F, height/2F); - } else { - mSuppMatrix.postScale(1F/rate, 1F/rate, width/2F, height/2F); - } - setImageMatrix(getImageViewMatrix()); - center(true, true, false); - - onZoom(); - } - - protected void postTranslate(float dx, float dy) { - mSuppMatrix.postTranslate(dx, dy); - } - - protected void panBy(float dx, float dy) { - postTranslate(dx, dy); - setImageMatrix(getImageViewMatrix()); - } -} - diff --git a/src/com/android/camera/MenuHelper.java b/src/com/android/camera/MenuHelper.java deleted file mode 100644 index ffb99ef..0000000 --- a/src/com/android/camera/MenuHelper.java +++ /dev/null @@ -1,718 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.camera; - -import java.io.Closeable; -import java.util.ArrayList; - -import android.app.Activity; -import android.app.AlertDialog; -import android.content.ActivityNotFoundException; -import android.content.DialogInterface; -import android.content.Intent; -import android.content.SharedPreferences; -import android.content.res.Configuration; -import android.media.MediaMetadataRetriever; -import android.net.Uri; -import android.os.Environment; -import android.os.Handler; -import android.os.StatFs; -import android.provider.MediaStore; -import android.provider.MediaStore.Images; -import android.util.Config; -import android.util.Log; -import android.view.Menu; -import android.view.MenuItem; -import android.view.SubMenu; -import android.view.View; -import android.view.MenuItem.OnMenuItemClickListener; -import android.widget.ImageView; -import android.widget.TextView; -import android.widget.Toast; - -import com.android.camera.ImageManager.IImage; - -public class MenuHelper { - static private final String TAG = "MenuHelper"; - - static public final int GENERIC_ITEM = 1; - static public final int IMAGE_SAVING_ITEM = 2; - static public final int VIDEO_SAVING_ITEM = 3; - static public final int IMAGE_MODE_ITEM = 4; - static public final int VIDEO_MODE_ITEM = 5; - static public final int MENU_ITEM_MAX = 5; - - static public final int INCLUDE_ALL = 0xFFFFFFFF; - static public final int INCLUDE_VIEWPLAY_MENU = (1 << 0); - static public final int INCLUDE_SHARE_MENU = (1 << 1); - static public final int INCLUDE_SET_MENU = (1 << 2); - static public final int INCLUDE_CROP_MENU = (1 << 3); - static public final int INCLUDE_DELETE_MENU = (1 << 4); - static public final int INCLUDE_ROTATE_MENU = (1 << 5); - static public final int INCLUDE_DETAILS_MENU = (1 << 5); - - static public final int MENU_SWITCH_CAMERA_MODE = 0; - static public final int MENU_CAPTURE_PICTURE = 1; - static public final int MENU_CAPTURE_VIDEO = 2; - static public final int MENU_IMAGE_SHARE = 10; - static public final int MENU_IMAGE_SET = 14; - static public final int MENU_IMAGE_SET_WALLPAPER = 15; - static public final int MENU_IMAGE_SET_CONTACT = 16; - static public final int MENU_IMAGE_SET_MYFAVE = 17; - static public final int MENU_IMAGE_CROP = 18; - static public final int MENU_IMAGE_ROTATE = 19; - static public final int MENU_IMAGE_ROTATE_LEFT = 20; - static public final int MENU_IMAGE_ROTATE_RIGHT = 21; - static public final int MENU_IMAGE_TOSS = 22; - static public final int MENU_VIDEO_PLAY = 23; - static public final int MENU_VIDEO_SHARE = 24; - static public final int MENU_VIDEO_TOSS = 27; - - public static final int NO_STORAGE_ERROR = -1; - public static final int CANNOT_STAT_ERROR = -2; - - /** Activity result code used to report crop results. - */ - public static final int RESULT_COMMON_MENU_CROP = 490; - - public interface MenuItemsResult { - public void gettingReadyToOpen(Menu menu, ImageManager.IImage image); - public void aboutToCall(MenuItem item, ImageManager.IImage image); - } - - public interface MenuInvoker { - public void run(MenuCallback r); - } - - public interface MenuCallback { - public void run(Uri uri, ImageManager.IImage image); - } - - private static void closeSilently(Closeable target) { - try { - if (target != null) target.close(); - } catch (Throwable t) { - // ignore all exceptions, that's what silently means - } - } - - public static long getImageFileSize(ImageManager.IImage image) { - java.io.InputStream data = image.fullSizeImageData(); - try { - return data.available(); - } catch (java.io.IOException ex) { - return -1; - } finally { - closeSilently(data); - } - } - - static MenuItemsResult addImageMenuItems( - Menu menu, - int inclusions, - final boolean isImage, - final Activity activity, - final Handler handler, - final Runnable onDelete, - final MenuInvoker onInvoke) { - final ArrayList<MenuItem> requiresWriteAccessItems = new ArrayList<MenuItem>(); - final ArrayList<MenuItem> requiresNoDrmAccessItems = new ArrayList<MenuItem>(); - - if (isImage && ((inclusions & INCLUDE_ROTATE_MENU) != 0)) { - SubMenu rotateSubmenu = menu.addSubMenu(IMAGE_SAVING_ITEM, MENU_IMAGE_ROTATE, - 40, R.string.rotate).setIcon(android.R.drawable.ic_menu_rotate); - // Don't show the rotate submenu if the item at hand is read only - // since the items within the submenu won't be shown anyway. This is - // really a framework bug in that it shouldn't show the submenu if - // the submenu has no visible items. - requiresWriteAccessItems.add(rotateSubmenu.getItem()); - if (rotateSubmenu != null) { - requiresWriteAccessItems.add(rotateSubmenu.add(0, MENU_IMAGE_ROTATE_LEFT, 50, R.string.rotate_left).setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - onInvoke.run(new MenuCallback() { - public void run(Uri u, ImageManager.IImage image) { - if (image == null || image.isReadonly()) - return; - image.rotateImageBy(-90); - } - }); - return true; - } - }).setAlphabeticShortcut('l')); - requiresWriteAccessItems.add(rotateSubmenu.add(0, MENU_IMAGE_ROTATE_RIGHT, 60, R.string.rotate_right).setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - onInvoke.run(new MenuCallback() { - public void run(Uri u, ImageManager.IImage image) { - if (image == null || image.isReadonly()) - return; - - image.rotateImageBy(90); - } - }); - return true; - } - }).setAlphabeticShortcut('r')); - } - } - - if (isImage && ((inclusions & INCLUDE_CROP_MENU) != 0)) { - MenuItem autoCrop = menu.add(IMAGE_SAVING_ITEM, MENU_IMAGE_CROP, 73, - R.string.camera_crop).setOnMenuItemClickListener( - new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - onInvoke.run(new MenuCallback() { - public void run(Uri u, ImageManager.IImage image) { - if (u == null) - return; - - Intent cropIntent = new Intent(); - cropIntent.setClass(activity, CropImage.class); - cropIntent.setData(u); - activity.startActivityForResult(cropIntent, RESULT_COMMON_MENU_CROP); - } - }); - return true; - } - }); - autoCrop.setIcon(android.R.drawable.ic_menu_crop); - requiresWriteAccessItems.add(autoCrop); - } - - if (isImage && ((inclusions & INCLUDE_SET_MENU) != 0)) { - MenuItem setMenu = menu.add(IMAGE_SAVING_ITEM, MENU_IMAGE_SET, 75, R.string.camera_set); - setMenu.setIcon(android.R.drawable.ic_menu_set_as); - - setMenu.setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - onInvoke.run(new MenuCallback() { - public void run(Uri u, ImageManager.IImage image) { - if (u == null || image == null) - return; - - if (Config.LOGV) - Log.v(TAG, "in callback u is " + u + "; mime type is " + image.getMimeType()); - Intent intent = new Intent(Intent.ACTION_ATTACH_DATA); - intent.setDataAndType(u, image.getMimeType()); - intent.putExtra("mimeType", image.getMimeType()); - activity.startActivity(Intent.createChooser(intent, activity.getText(R.string.setImage))); - } - }); - return true; - } - }); - } - - if ((inclusions & INCLUDE_SHARE_MENU) != 0) { - if (Config.LOGV) - Log.v(TAG, ">>>>> add share"); - MenuItem item1 = menu.add(IMAGE_SAVING_ITEM, MENU_IMAGE_SHARE, 10, - R.string.camera_share).setOnMenuItemClickListener( - new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - onInvoke.run(new MenuCallback() { - public void run(Uri u, ImageManager.IImage image) { - if (image == null) - return; - Intent intent = new Intent(); - intent.setAction(Intent.ACTION_SEND); - String mimeType = image.getMimeType(); - intent.setType(mimeType); - intent.putExtra(Intent.EXTRA_STREAM, u); - boolean isImage = ImageManager.isImageMimeType(mimeType); - try { - activity.startActivity(Intent.createChooser(intent, - activity.getText( - isImage ? R.string.sendImage : R.string.sendVideo))); - } catch (android.content.ActivityNotFoundException ex) { - Toast.makeText(activity, - isImage ? R.string.no_way_to_share_image - : R.string.no_way_to_share_video, - Toast.LENGTH_SHORT).show(); - } - } - }); - return true; - } - }); - item1.setIcon(android.R.drawable.ic_menu_share); - MenuItem item = item1; - requiresNoDrmAccessItems.add(item); - } - - if ((inclusions & INCLUDE_DELETE_MENU) != 0) { - MenuItem deleteItem = menu.add(IMAGE_SAVING_ITEM, MENU_IMAGE_TOSS, 70, R.string.camera_toss); - requiresWriteAccessItems.add(deleteItem); - deleteItem.setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - deleteImageImpl(activity, onDelete, isImage); - return true; - } - }) - .setAlphabeticShortcut('d') - .setIcon(android.R.drawable.ic_menu_delete); - } - - if ((inclusions & INCLUDE_DETAILS_MENU) != 0) { - MenuItem detailsMenu = menu.add(0, 0, 80, R.string.details).setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - onInvoke.run(new MenuCallback() { - public void run(Uri u, ImageManager.IImage image) { - if (image == null) - return; - - AlertDialog.Builder builder = new AlertDialog.Builder(activity); - - final View d = View.inflate(activity, R.layout.detailsview, null); - - ImageView imageView = (ImageView) d.findViewById(R.id.details_thumbnail_image); - imageView.setImageBitmap(image.miniThumbBitmap()); - - TextView textView = (TextView) d.findViewById(R.id.details_image_title); - textView.setText(image.getDisplayName()); - - long length = getImageFileSize(image); - String lengthString = lengthString = length < 0 ? "" - : android.text.format.Formatter.formatFileSize(activity, length); - ((TextView)d.findViewById(R.id.details_file_size_value)) - .setText(lengthString); - - int dimensionWidth = 0; - int dimensionHeight = 0; - if (isImage) { - dimensionWidth = image.getWidth(); - dimensionHeight = image.getHeight(); - d.findViewById(R.id.details_duration_row).setVisibility(View.GONE); - d.findViewById(R.id.details_frame_rate_row).setVisibility(View.GONE); - d.findViewById(R.id.details_bit_rate_row).setVisibility(View.GONE); - d.findViewById(R.id.details_format_row).setVisibility(View.GONE); - d.findViewById(R.id.details_codec_row).setVisibility(View.GONE); - } else { - MediaMetadataRetriever retriever = new MediaMetadataRetriever(); - try { - retriever.setMode(MediaMetadataRetriever.MODE_GET_METADATA_ONLY); - retriever.setDataSource(image.getDataPath()); - try { - dimensionWidth = Integer.parseInt( - retriever.extractMetadata( - MediaMetadataRetriever.METADATA_KEY_VIDEO_WIDTH)); - dimensionHeight = Integer.parseInt( - retriever.extractMetadata( - MediaMetadataRetriever.METADATA_KEY_VIDEO_HEIGHT)); - } catch (NumberFormatException e) { - dimensionWidth = 0; - dimensionHeight = 0; - } - - try { - int durationMs = Integer.parseInt(retriever.extractMetadata( - MediaMetadataRetriever.METADATA_KEY_DURATION)); - String durationValue = formatDuration( - activity, durationMs); - ((TextView)d.findViewById(R.id.details_duration_value)) - .setText(durationValue); - } catch (NumberFormatException e) { - d.findViewById(R.id.details_frame_rate_row) - .setVisibility(View.GONE); - } - - try { - String frame_rate = String.format( - activity.getString(R.string.details_fps), - Integer.parseInt( - retriever.extractMetadata( - MediaMetadataRetriever.METADATA_KEY_FRAME_RATE))); - ((TextView)d.findViewById(R.id.details_frame_rate_value)) - .setText(frame_rate); - } catch (NumberFormatException e) { - d.findViewById(R.id.details_frame_rate_row) - .setVisibility(View.GONE); - } - - try { - long bitRate = Long.parseLong(retriever.extractMetadata( - MediaMetadataRetriever.METADATA_KEY_BIT_RATE)); - String bps; - if (bitRate < 1000000) { - bps = String.format( - activity.getString(R.string.details_kbps), - bitRate / 1000); - } else { - bps = String.format( - activity.getString(R.string.details_mbps), - ((double) bitRate) / 1000000.0); - } - ((TextView)d.findViewById(R.id.details_bit_rate_value)) - .setText(bps); - } catch (NumberFormatException e) { - d.findViewById(R.id.details_bit_rate_row) - .setVisibility(View.GONE); - } - - String format = retriever.extractMetadata( - MediaMetadataRetriever.METADATA_KEY_VIDEO_FORMAT); - ((TextView)d.findViewById(R.id.details_format_value)) - .setText(format); - - String codec = retriever.extractMetadata( - MediaMetadataRetriever.METADATA_KEY_CODEC); - - if (codec == null) { - d.findViewById(R.id.details_codec_row). - setVisibility(View.GONE); - } else { - ((TextView)d.findViewById(R.id.details_codec_value)) - .setText(codec); - } - } catch(RuntimeException ex) { - // Assume this is a corrupt video file. - } finally { - try { - retriever.release(); - } catch (RuntimeException ex) { - // Ignore failures while cleaning up. - } - } - } - - String dimensionsString = String.format( - activity.getString(R.string.details_dimension_x), - dimensionWidth, dimensionHeight); - ((TextView)d.findViewById(R.id.details_resolution_value)) - .setText(dimensionsString); - - String dateString = ""; - long dateTaken = image.getDateTaken(); - if (dateTaken != 0) { - java.util.Date date = new java.util.Date(image.getDateTaken()); - java.text.SimpleDateFormat dateFormat = new java.text.SimpleDateFormat(); - dateString = dateFormat.format(date); - - ((TextView)d.findViewById(R.id.details_date_taken_value)) - .setText(dateString); - } else { - d.findViewById(R.id.details_date_taken_row) - .setVisibility(View.GONE); - } - - builder.setNeutralButton(R.string.details_ok, - new DialogInterface.OnClickListener() { - public void onClick(DialogInterface dialog, int which) { - dialog.dismiss(); - } - }); - - builder.setIcon(android.R.drawable.ic_dialog_info) - .setTitle(R.string.details_panel_title) - .setView(d) - .show(); - - } - }); - return true; - } - }); - detailsMenu.setIcon(R.drawable.ic_menu_view_details); - } - - if ((!isImage) && ((inclusions & INCLUDE_VIEWPLAY_MENU) != 0)) { - menu.add(VIDEO_SAVING_ITEM, MENU_VIDEO_PLAY, 0, R.string.video_play) - .setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - onInvoke.run(new MenuCallback() { - public void run(Uri uri, IImage image) { - Intent intent = new Intent(Intent.ACTION_VIEW, - image.fullSizeImageUri()); - activity.startActivity(intent); - }}); - return true; - } - }); - } - - - return new MenuItemsResult() { - public void gettingReadyToOpen(Menu menu, ImageManager.IImage image) { - // protect against null here. this isn't strictly speaking required - // but if a client app isn't handling sdcard removal properly it - // could happen - if (image == null) { - return; - } - boolean readOnly = image.isReadonly(); - boolean isDrm = image.isDrm(); - if (Config.LOGV) - Log.v(TAG, "readOnly: " + readOnly + "; drm: " + isDrm); - for (MenuItem item: requiresWriteAccessItems) { - if (Config.LOGV) - Log.v(TAG, "item is " + item.toString()); - item.setVisible(!readOnly); - item.setEnabled(!readOnly); - } - for (MenuItem item: requiresNoDrmAccessItems) { - if (Config.LOGV) - Log.v(TAG, "item is " + item.toString()); - item.setVisible(!isDrm); - item.setEnabled(!isDrm); - } - } - public void aboutToCall(MenuItem menu, ImageManager.IImage image) { - } - }; - } - - static void deletePhoto(Activity activity, Runnable onDelete) { - deleteImageImpl(activity, onDelete, true); - } - - static void deleteImage(Activity activity, Runnable onDelete, IImage image) { - if (image != null) { - deleteImageImpl(activity, onDelete, ImageManager.isImage(image)); - } - } - - private static void deleteImageImpl(Activity activity, final Runnable onDelete, boolean isPhoto) { - boolean confirm = android.preference.PreferenceManager.getDefaultSharedPreferences(activity).getBoolean("pref_gallery_confirm_delete_key", true); - if (!confirm) { - if (onDelete != null) - onDelete.run(); - } else { - displayDeleteDialog(activity, onDelete, isPhoto); - } - } - - public static void displayDeleteDialog(Activity activity, - final Runnable onDelete, boolean isPhoto) { - android.app.AlertDialog.Builder b = new android.app.AlertDialog.Builder(activity); - b.setIcon(android.R.drawable.ic_dialog_alert); - b.setTitle(R.string.confirm_delete_title); - b.setMessage(isPhoto? R.string.confirm_delete_message - : R.string.confirm_delete_video_message); - b.setPositiveButton(android.R.string.ok, new android.content.DialogInterface.OnClickListener() { - public void onClick(android.content.DialogInterface v, int x) { - if (onDelete != null) - onDelete.run(); - } - }); - b.setNegativeButton(android.R.string.cancel, new android.content.DialogInterface.OnClickListener() { - public void onClick(android.content.DialogInterface v, int x) { - - } - }); - b.create().show(); - } - - static void addSwitchModeMenuItem(Menu menu, final Activity activity, - final boolean switchToVideo) { - int group = switchToVideo ? MenuHelper.IMAGE_MODE_ITEM : MenuHelper.VIDEO_MODE_ITEM; - int labelId = switchToVideo ? R.string.switch_to_video_lable - : R.string.switch_to_camera_lable; - int iconId = switchToVideo ? R.drawable.ic_menu_camera_video_view - : android.R.drawable.ic_menu_camera; - MenuItem item = menu.add(group, MENU_SWITCH_CAMERA_MODE, 0, - labelId).setOnMenuItemClickListener( - new OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - String action = switchToVideo ? MediaStore.INTENT_ACTION_VIDEO_CAMERA - : MediaStore.INTENT_ACTION_STILL_IMAGE_CAMERA; - Intent intent = new Intent(action); - intent.addFlags(Intent.FLAG_ACTIVITY_FORWARD_RESULT); - activity.finish(); - activity.startActivity(intent); - return true; - } - }); - item.setIcon(iconId); - } - - static void gotoStillImageCapture(Activity activity) { - Intent intent = new Intent(MediaStore.INTENT_ACTION_STILL_IMAGE_CAMERA); - intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP); - try { - activity.startActivity(intent); - } catch (ActivityNotFoundException e) { - Log.e(TAG, "Could not start still image capture activity", e); - } - } - - static void gotoCameraImageGallery(Activity activity) { - gotoGallery(activity, R.string.gallery_camera_bucket_name, ImageManager.INCLUDE_IMAGES); - } - - static void gotoCameraVideoGallery(Activity activity) { - gotoGallery(activity, R.string.gallery_camera_videos_bucket_name, - ImageManager.INCLUDE_VIDEOS); - } - - static private void gotoGallery(Activity activity, int windowTitleId, int mediaTypes) { - Uri target = Images.Media.INTERNAL_CONTENT_URI.buildUpon().appendQueryParameter("bucketId", - ImageManager.CAMERA_IMAGE_BUCKET_ID).build(); - Intent intent = new Intent(Intent.ACTION_VIEW, target); - intent.putExtra("windowTitle", activity.getString(windowTitleId)); - intent.putExtra("mediaTypes", mediaTypes); - // Request unspecified so that we match the current camera orientation rather than - // matching the "flip orientation" preference. - // Disabled because people don't care for it. Also it's - // not as compelling now that we have implemented have quick orientation flipping. - // intent.putExtra(MediaStore.EXTRA_SCREEN_ORIENTATION, - // android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED); - try { - activity.startActivity(intent); - } catch (ActivityNotFoundException e) { - Log.e(TAG, "Could not start gallery activity", e); - } - } - - static void addCaptureMenuItems(Menu menu, final Activity activity) { - - menu.add(0, MENU_CAPTURE_PICTURE, 1, R.string.capture_picture) - .setOnMenuItemClickListener( - new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - Intent intent = new Intent(MediaStore.INTENT_ACTION_STILL_IMAGE_CAMERA); - try { - activity.startActivity(intent); - } catch (android.content.ActivityNotFoundException e) { - // Ignore exception - } - return true; - } - }) - .setIcon(android.R.drawable.ic_menu_camera); - - menu.add(0, MENU_CAPTURE_VIDEO, 2, R.string.capture_video) - .setOnMenuItemClickListener( - new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - Intent intent = new Intent(MediaStore.INTENT_ACTION_VIDEO_CAMERA); - try { - activity.startActivity(intent); - } catch (android.content.ActivityNotFoundException e) { - // Ignore exception - } - return true; - } - }) - .setIcon(R.drawable.ic_menu_camera_video_view); - } - static MenuItem addFlipOrientation(Menu menu, final Activity activity, final SharedPreferences prefs) { - // position 41 after rotate - // D - return menu - .add(Menu.CATEGORY_SECONDARY, 304, 41, R.string.flip_orientation) - .setOnMenuItemClickListener( - new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - // Check what our actual orientation is - int current = activity.getResources().getConfiguration().orientation; - int newOrientation = android.content.pm.ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE; - if (current == Configuration.ORIENTATION_LANDSCAPE) { - newOrientation = android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED; - } - SharedPreferences.Editor editor = prefs.edit(); - editor.putInt("nuorientation", newOrientation); - editor.commit(); - requestOrientation(activity, prefs, true); - return true; - } - }) - .setIcon(android.R.drawable.ic_menu_always_landscape_portrait); - } - - static void requestOrientation(Activity activity, SharedPreferences prefs) { - requestOrientation(activity, prefs, false); - } - - static private void requestOrientation(Activity activity, SharedPreferences prefs, - boolean ignoreIntentExtra) { - int req = prefs.getInt("nuorientation", - android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED); - // A little trick: use USER instead of UNSPECIFIED, so we ignore the - // orientation set by the activity below. It may have forced a landscape - // orientation, which the user has now cleared here. - if (req == android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED) { - req = android.content.pm.ActivityInfo.SCREEN_ORIENTATION_USER; - } - if (! ignoreIntentExtra) { - Intent intent = activity.getIntent(); - req = intent.getIntExtra(MediaStore.EXTRA_SCREEN_ORIENTATION, req); - } - activity.setRequestedOrientation(req); - } - - static void setFlipOrientationEnabled(Activity activity, MenuItem flipItem) { - int keyboard = activity.getResources().getConfiguration().hardKeyboardHidden; - flipItem.setEnabled(keyboard != android.content.res.Configuration.HARDKEYBOARDHIDDEN_NO); - } - - public static String formatDuration(final Activity activity, int durationMs) { - int duration = durationMs / 1000; - 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( - activity.getString(R.string.details_ms), m, s); - } else { - durationValue = String.format( - activity.getString(R.string.details_hms), h, m, s); - } - return durationValue; - } - - public static void showStorageToast(Activity activity) { - showStorageToast(activity, calculatePicturesRemaining()); - } - - public static void showStorageToast(Activity activity, int remaining) { - String noStorageText = null; - - if (remaining == MenuHelper.NO_STORAGE_ERROR) { - String state = Environment.getExternalStorageState(); - if (state == Environment.MEDIA_CHECKING) { - noStorageText = activity.getString(R.string.preparing_sd); - } else { - noStorageText = activity.getString(R.string.no_storage); - } - } else if (remaining < 1) { - noStorageText = activity.getString(R.string.not_enough_space); - } - - if (noStorageText != null) { - Toast.makeText(activity, noStorageText, 5000).show(); - } - } - - public static int calculatePicturesRemaining() { - try { - if (!ImageManager.hasStorage()) { - return NO_STORAGE_ERROR; - } else { - String storageDirectory = Environment.getExternalStorageDirectory().toString(); - StatFs stat = new StatFs(storageDirectory); - float remaining = ((float)stat.getAvailableBlocks() * (float)stat.getBlockSize()) / 400000F; - return (int)remaining; - } - } catch (Exception ex) { - // if we can't stat the filesystem then we don't know how many - // pictures are remaining. it might be zero but just leave it - // blank since we really don't know. - return CANNOT_STAT_ERROR; - } - } -} - diff --git a/src/com/android/camera/MovieView.java b/src/com/android/camera/MovieView.java deleted file mode 100644 index 091cc28..0000000 --- a/src/com/android/camera/MovieView.java +++ /dev/null @@ -1,243 +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.camera; - - -import android.app.Activity; -import android.app.AlertDialog; -import android.content.ContentValues; -import android.content.DialogInterface; -import android.content.Intent; -import android.content.DialogInterface.OnCancelListener; -import android.content.DialogInterface.OnClickListener; -import android.content.pm.ActivityInfo; -import android.database.Cursor; -import android.database.sqlite.SQLiteException; -import android.media.MediaPlayer; -import android.net.Uri; -import android.os.Bundle; -import android.os.Handler; -import android.os.Message; -import android.provider.MediaStore; -import android.provider.MediaStore.Video; -import android.view.View; -import android.widget.MediaController; -import android.widget.VideoView; - -public class MovieView extends Activity implements MediaPlayer.OnErrorListener, MediaPlayer.OnCompletionListener -{ - private static final String TAG = "MovieView"; - // Copied from MediaPlaybackService in the Music Player app. Should be public, but isn't. - private static final String SERVICECMD = "com.android.music.musicservicecommand"; - private static final String CMDNAME = "command"; - private static final String CMDPAUSE = "pause"; - - private VideoView mVideoView; - private View mProgressView; - private boolean mFinishOnCompletion; - private Uri mUri; - - // State maintained for proper onPause/OnResume behaviour. - private int mPositionWhenPaused = -1; - private boolean mWasPlayingWhenPaused = false; - - public MovieView() - { - } - - @Override - public void onCreate(Bundle icicle) - { - super.onCreate(icicle); - - setContentView(R.layout.movie_view); - - mVideoView = (VideoView) findViewById(R.id.surface_view); - mProgressView = findViewById(R.id.progress_indicator); - Intent intent = getIntent(); - if (intent.hasExtra(MediaStore.EXTRA_SCREEN_ORIENTATION)) { - int orientation = intent.getIntExtra(MediaStore.EXTRA_SCREEN_ORIENTATION, - ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED); - if (orientation != getRequestedOrientation()) { - setRequestedOrientation(orientation); - } - } - mFinishOnCompletion = intent.getBooleanExtra(MediaStore.EXTRA_FINISH_ON_COMPLETION, true); - mUri = intent.getData(); - - // 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)) { - mHandler.postDelayed(mPlayingChecker, 250); - } else { - mProgressView.setVisibility(View.GONE); - } - - mVideoView.setOnErrorListener(this); - mVideoView.setOnCompletionListener(this); - mVideoView.setVideoURI(mUri); - mVideoView.setMediaController(new MediaController(this)); - mVideoView.requestFocus(); // make the video view handle keys for seeking and pausing - - Intent i = new Intent(SERVICECMD); - i.putExtra(CMDNAME, CMDPAUSE); - sendBroadcast(i); - { - final Integer bookmark = getBookmark(); - if (bookmark != null) { - AlertDialog.Builder builder = new AlertDialog.Builder(this); - builder.setTitle(R.string.resume_playing_title); - builder.setMessage(String.format( - getString(R.string.resume_playing_message), - MenuHelper.formatDuration(this, bookmark))); - builder.setOnCancelListener(new OnCancelListener() { - public void onCancel(DialogInterface dialog) { - finish(); - }}); - builder.setPositiveButton(R.string.resume_playing_resume, - new OnClickListener(){ - public void onClick(DialogInterface dialog, int which) { - mVideoView.seekTo(bookmark); - mVideoView.start(); - }}); - builder.setNegativeButton(R.string.resume_playing_restart, new OnClickListener(){ - public void onClick(DialogInterface dialog, int which) { - mVideoView.start(); - }}); - builder.show(); - } else { - mVideoView.start(); - } - } - } - - private Integer getBookmark() { - String scheme = mUri.getScheme(); - if ("content".equalsIgnoreCase(scheme)) { - String[] projection = new String[]{Video.VideoColumns.DURATION, - Video.VideoColumns.BOOKMARK}; - try { - Cursor cursor = getContentResolver().query(mUri, projection, null, null, null); - if (cursor != null) { - try { - if ( cursor.moveToFirst() ) { - int duration = getCursorInteger(cursor, 0); - int bookmark = getCursorInteger(cursor, 1); - final int ONE_MINUTE = 60 * 1000; - final int TWO_MINUTES = 2 * ONE_MINUTE; - final int FIVE_MINUTES = 5 * ONE_MINUTE; - if ((bookmark < TWO_MINUTES) - || (duration < FIVE_MINUTES) - || (bookmark > (duration - ONE_MINUTE))) { - return null; - } - - return new Integer(bookmark); - } - } finally { - cursor.close(); - } - } - } catch (SQLiteException e) { - // ignore - } - } - return null; - } - - private int getCursorInteger(Cursor cursor, int index) { - try { - return cursor.getInt(index); - } catch (SQLiteException e) { - return 0; - } catch (NumberFormatException e) { - return 0; - } - - } - - private void setBookmark(int bookmark) { - String scheme = mUri.getScheme(); - if ("content".equalsIgnoreCase(scheme)) { - ContentValues values = new ContentValues(); - values.put(Video.VideoColumns.BOOKMARK, Integer.toString(bookmark)); - try { - getContentResolver().update(mUri, values, null, null); - } catch (SecurityException ex) { - // Ignore, can happen if we try to set the bookmark on a read-only resource - // such as a video attached to GMail. - } catch (SQLiteException e) { - // ignore. can happen if the content doesn't support a bookmark column. - } - } - } - - @Override - public void onPause() { - mHandler.removeCallbacksAndMessages(null); - setBookmark(mVideoView.getCurrentPosition()); - - mPositionWhenPaused = mVideoView.getCurrentPosition(); - mWasPlayingWhenPaused = mVideoView.isPlaying(); - mVideoView.stopPlayback(); - - super.onPause(); - } - - @Override - public void onResume() { - if (mPositionWhenPaused >= 0) { - mVideoView.setVideoURI(mUri); - mVideoView.seekTo(mPositionWhenPaused); - if (mWasPlayingWhenPaused) { - mVideoView.start(); - } - } - - super.onResume(); - } - - Handler mHandler = new Handler() { - @Override - public void handleMessage(Message msg) { - } - }; - - Runnable mPlayingChecker = new Runnable() { - public void run() { - if (mVideoView.isPlaying()) { - mProgressView.setVisibility(View.GONE); - } else { - mHandler.postDelayed(mPlayingChecker, 250); - } - } - }; - - public boolean onError(MediaPlayer player, int arg1, int arg2) { - mHandler.removeCallbacksAndMessages(null); - mProgressView.setVisibility(View.GONE); - return false; - } - - public void onCompletion(MediaPlayer mp) { - if (mFinishOnCompletion) { - finish(); - } - } -} diff --git a/src/com/android/camera/OnScreenHint.java b/src/com/android/camera/OnScreenHint.java deleted file mode 100644 index 96190a0..0000000 --- a/src/com/android/camera/OnScreenHint.java +++ /dev/null @@ -1,296 +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.camera; - -import android.app.INotificationManager; -import android.app.ITransientNotification; -import android.content.Context; -import android.content.res.Resources; -import android.graphics.PixelFormat; -import android.os.RemoteException; -import android.os.Handler; -import android.os.ServiceManager; -import android.util.Log; -import android.view.Gravity; -import android.view.LayoutInflater; -import android.view.View; -import android.view.WindowManager; -import android.widget.TextView; - -/** - * A on-screen hint is a view containing a little message for the user and will - * be shown on the screen continuously. This class helps you create and show - * those. - * - * <p> - * When the view is shown to the user, appears as a floating view over the - * application. - * <p> - * The easiest way to use this class is to call one of the static methods that - * constructs everything you need and returns a new OnScreenHint object. - */ -public class OnScreenHint { - static final String TAG = "OnScreenHint"; - static final boolean localLOGV = false; - - final Context mContext; - int mGravity = Gravity.CENTER_HORIZONTAL | Gravity.BOTTOM; - int mX, mY; - float mHorizontalMargin; - float mVerticalMargin; - View mView; - View mNextView; - - private final WindowManager.LayoutParams mParams = new WindowManager.LayoutParams(); - private WindowManager mWM; - private final Handler mHandler = new Handler(); - - /** - * Construct an empty OnScreenHint object. You must call {@link #setView} before you - * can call {@link #show}. - * - * @param context The context to use. Usually your {@link android.app.Application} - * or {@link android.app.Activity} object. - */ - public OnScreenHint(Context context) { - mContext = context; - mWM = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE); - mY = context.getResources().getDimensionPixelSize(R.dimen.hint_y_offset); - - mParams.height = WindowManager.LayoutParams.WRAP_CONTENT; - mParams.width = WindowManager.LayoutParams.WRAP_CONTENT; - mParams.flags = WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE - | WindowManager.LayoutParams.FLAG_NOT_TOUCHABLE; - mParams.format = PixelFormat.TRANSLUCENT; - mParams.windowAnimations = R.style.Animation_OnScreenHint; - mParams.type = WindowManager.LayoutParams.TYPE_APPLICATION_PANEL; - mParams.setTitle("OnScreenHint"); - } - - /** - * Show the view on the screen. - */ - public void show() { - if (mNextView == null) { - throw new RuntimeException("setView must have been called"); - } - if (localLOGV) Log.v(TAG, "SHOW: " + this); - mHandler.post(mShow); - } - - /** - * Close the view if it's showing. - */ - public void cancel() { - if (localLOGV) Log.v(TAG, "HIDE: " + this); - mHandler.post(mHide); - } - - /** - * Set the view to show. - * @see #getView - */ - public void setView(View view) { - mNextView = view; - } - - /** - * Return the view. - * @see #setView - */ - public View getView() { - return mNextView; - } - - /** - * Set the margins of the view. - * - * @param horizontalMargin The horizontal margin, in percentage of the - * container width, between the container's edges and the - * notification - * @param verticalMargin The vertical margin, in percentage of the - * container height, between the container's edges and the - * notification - */ - public void setMargin(float horizontalMargin, float verticalMargin) { - mHorizontalMargin = horizontalMargin; - mVerticalMargin = verticalMargin; - } - - /** - * Return the horizontal margin. - */ - public float getHorizontalMargin() { - return mHorizontalMargin; - } - - /** - * Return the vertical margin. - */ - public float getVerticalMargin() { - return mVerticalMargin; - } - - /** - * Set the location at which the notification should appear on the screen. - * @see android.view.Gravity - * @see #getGravity - */ - public void setGravity(int gravity, int xOffset, int yOffset) { - mGravity = gravity; - mX = xOffset; - mY = yOffset; - } - - /** - * Get the location at which the notification should appear on the screen. - * @see android.view.Gravity - * @see #getGravity - */ - public int getGravity() { - return mGravity; - } - - /** - * Return the X offset in pixels to apply to the gravity's location. - */ - public int getXOffset() { - return mX; - } - - /** - * Return the Y offset in pixels to apply to the gravity's location. - */ - public int getYOffset() { - return mY; - } - - /** - * Make a standard hint that just contains a text view. - * - * @param context The context to use. Usually your {@link android.app.Application} - * or {@link android.app.Activity} object. - * @param text The text to show. Can be formatted text. - * - */ - public static OnScreenHint makeText(Context context, CharSequence text) { - OnScreenHint result = new OnScreenHint(context); - - LayoutInflater inflate = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE); - View v = inflate.inflate(R.layout.on_screen_hint, null); - TextView tv = (TextView)v.findViewById(R.id.message); - tv.setText(text); - - result.mNextView = v; - - return result; - } - - /** - * Make a standard hint that just contains a text view with the text from a resource. - * - * @param context The context to use. Usually your {@link android.app.Application} - * or {@link android.app.Activity} object. - * @param resId The resource id of the string resource to use. Can be formatted text. - * - * @throws Resources.NotFoundException if the resource can't be found. - */ - public static OnScreenHint makeText(Context context, int resId) - throws Resources.NotFoundException { - return makeText(context, context.getResources().getText(resId)); - } - - /** - * Update the text in a OnScreenHint that was previously created using one of the makeText() methods. - * @param resId The new text for the OnScreenHint. - */ - public void setText(int resId) { - setText(mContext.getText(resId)); - } - - /** - * Update the text in a OnScreenHint that was previously created using one of the makeText() methods. - * @param s The new text for the OnScreenHint. - */ - public void setText(CharSequence s) { - if (mNextView == null) { - throw new RuntimeException("This OnScreenHint was not created with OnScreenHint.makeText()"); - } - TextView tv = (TextView) mNextView.findViewById(R.id.message); - if (tv == null) { - throw new RuntimeException("This OnScreenHint was not created with OnScreenHint.makeText()"); - } - tv.setText(s); - } - - private synchronized void handleShow() { - if (localLOGV) Log.v(TAG, "HANDLE SHOW: " + this + " mView=" + mView - + " mNextView=" + mNextView); - if (mView != mNextView) { - // remove the old view if necessary - handleHide(); - mView = mNextView; - final int gravity = mGravity; - mParams.gravity = gravity; - if ((gravity & Gravity.HORIZONTAL_GRAVITY_MASK) == Gravity.FILL_HORIZONTAL) { - mParams.horizontalWeight = 1.0f; - } - if ((gravity & Gravity.VERTICAL_GRAVITY_MASK) == Gravity.FILL_VERTICAL) { - mParams.verticalWeight = 1.0f; - } - mParams.x = mX; - mParams.y = mY; - mParams.verticalMargin = mVerticalMargin; - mParams.horizontalMargin = mHorizontalMargin; - if (mView.getParent() != null) { - if (localLOGV) Log.v( - TAG, "REMOVE! " + mView + " in " + this); - mWM.removeView(mView); - } - if (localLOGV) Log.v(TAG, "ADD! " + mView + " in " + this); - mWM.addView(mView, mParams); - } - } - - private synchronized void handleHide() { - if (localLOGV) Log.v(TAG, "HANDLE HIDE: " + this + " mView=" + mView); - if (mView != null) { - // note: checking parent() just to make sure the view has - // been added... i have seen cases where we get here when - // the view isn't yet added, so let's try not to crash. - if (mView.getParent() != null) { - if (localLOGV) Log.v( - TAG, "REMOVE! " + mView + " in " + this); - mWM.removeView(mView); - } - mView = null; - } - } - - private Runnable mShow = new Runnable() { - public void run() { - handleShow(); - } - }; - - private Runnable mHide = new Runnable() { - public void run() { - handleHide(); - } - }; -} - diff --git a/src/com/android/camera/PhotoGadgetConfigure.java b/src/com/android/camera/PhotoGadgetConfigure.java deleted file mode 100644 index a94b5a3..0000000 --- a/src/com/android/camera/PhotoGadgetConfigure.java +++ /dev/null @@ -1,97 +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.camera; - -import com.android.camera.PhotoGadgetProvider.PhotoDatabaseHelper; - -import android.app.Activity; -import android.content.ContentValues; -import android.content.Intent; -import android.database.sqlite.SQLiteDatabase; -import android.gadget.GadgetManager; -import android.graphics.Bitmap; -import android.os.Bundle; -import android.os.Parcelable; -import android.util.Log; -import android.widget.RemoteViews; - -import java.io.ByteArrayOutputStream; -import java.io.IOException; - -public class PhotoGadgetConfigure extends Activity { - static final private String TAG = "PhotoGadgetConfigure"; - - static final int REQUEST_GET_PHOTO = 2; - - int gadgetId = -1; - - @Override - protected void onCreate(Bundle icicle) { - super.onCreate(icicle); - - // Someone is requesting that we configure the given gadgetId, which means - // we prompt the user to pick and crop a photo. - - gadgetId = getIntent().getIntExtra(GadgetManager.EXTRA_GADGET_ID, -1); - if (gadgetId == -1) { - setResult(Activity.RESULT_CANCELED); - finish(); - } - - // TODO: get these values from constants somewhere - // TODO: Adjust the PhotoFrame's image size to avoid on the fly scaling - Intent intent = new Intent(Intent.ACTION_GET_CONTENT, null); - intent.setType("image/*"); - intent.putExtra("crop", "true"); - intent.putExtra("aspectX", 1); - intent.putExtra("aspectY", 1); - intent.putExtra("outputX", 192); - intent.putExtra("outputY", 192); - intent.putExtra("noFaceDetection", true); - intent.putExtra("return-data", true); - - startActivityForResult(intent, REQUEST_GET_PHOTO); - } - - @Override - protected void onActivityResult(int requestCode, int resultCode, Intent data) { - if (resultCode == RESULT_OK && gadgetId != -1) { - // Store the cropped photo in our database - Bitmap bitmap = (Bitmap) data.getParcelableExtra("data"); - - PhotoDatabaseHelper helper = new PhotoDatabaseHelper(this); - if (helper.setPhoto(gadgetId, bitmap)) { - resultCode = Activity.RESULT_OK; - - // Push newly updated gadget to surface - RemoteViews views = PhotoGadgetProvider.buildUpdate(this, gadgetId, helper); - GadgetManager gadgetManager = GadgetManager.getInstance(this); - gadgetManager.updateGadget(new int[] { gadgetId }, views); - } - helper.close(); - } else { - resultCode = Activity.RESULT_CANCELED; - } - - // Make sure we pass back the original gadgetId - Intent resultValue = new Intent(); - resultValue.putExtra(GadgetManager.EXTRA_GADGET_ID, gadgetId); - setResult(resultCode, resultValue); - finish(); - } - -} diff --git a/src/com/android/camera/PhotoGadgetProvider.java b/src/com/android/camera/PhotoGadgetProvider.java deleted file mode 100644 index b03217d..0000000 --- a/src/com/android/camera/PhotoGadgetProvider.java +++ /dev/null @@ -1,223 +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.camera; - -import com.android.internal.util.XmlUtils; - -import org.xmlpull.v1.XmlPullParser; -import org.xmlpull.v1.XmlPullParserException; - -import android.app.Activity; -import android.app.PendingIntent; -import android.content.BroadcastReceiver; -import android.content.ComponentName; -import android.content.ContentResolver; -import android.content.ContentValues; -import android.content.Context; -import android.content.Intent; -import android.content.pm.ActivityInfo; -import android.content.pm.PackageManager; -import android.database.Cursor; -import android.database.SQLException; -import android.database.sqlite.SQLiteDatabase; -import android.database.sqlite.SQLiteException; -import android.database.sqlite.SQLiteOpenHelper; -import android.gadget.GadgetManager; -import android.gadget.GadgetProvider; -import android.graphics.Bitmap; -import android.graphics.BitmapFactory; -import android.net.Uri; -import android.os.Environment; -import android.provider.Settings; -import android.provider.Calendar.Attendees; -import android.provider.Calendar.Calendars; -import android.provider.Calendar.Instances; -import android.text.format.DateFormat; -import android.text.format.DateUtils; -import android.util.Config; -import android.util.Log; -import android.util.Xml; -import android.view.View; -import android.widget.RemoteViews; - -import java.io.ByteArrayOutputStream; -import java.io.File; -import java.io.FileNotFoundException; -import java.io.FileReader; -import java.io.IOException; - -/** - * Simple gadget to show a user-selected picture. - */ -public class PhotoGadgetProvider extends GadgetProvider { - static final String TAG = "PhotoGadgetProvider"; - static final boolean LOGD = Config.LOGD || true; - - @Override - public void onUpdate(Context context, GadgetManager gadgetManager, int[] gadgetIds) { - // Update each requested gadgetId with its unique photo - PhotoDatabaseHelper helper = new PhotoDatabaseHelper(context); - for (int gadgetId : gadgetIds) { - int[] specificGadget = new int[] { gadgetId }; - RemoteViews views = buildUpdate(context, gadgetId, helper); - if (LOGD) Log.d(TAG, "sending out views="+views+" for id="+gadgetId); - gadgetManager.updateGadget(specificGadget, views); - } - helper.close(); - } - - @Override - public void onDeleted(Context context, int[] gadgetIds) { - // Clean deleted photos out of our database - PhotoDatabaseHelper helper = new PhotoDatabaseHelper(context); - for (int gadgetId : gadgetIds) { - helper.deletePhoto(gadgetId); - } - helper.close(); - } - - /** - * Load photo for given gadget and build {@link RemoteViews} for it. - */ - static RemoteViews buildUpdate(Context context, int gadgetId, PhotoDatabaseHelper helper) { - RemoteViews views = null; - Bitmap bitmap = helper.getPhoto(gadgetId); - if (bitmap != null) { - views = new RemoteViews(context.getPackageName(), R.layout.photo_frame); - views.setImageViewBitmap(R.id.photo, bitmap); - } - return views; - } - - static class PhotoDatabaseHelper extends SQLiteOpenHelper { - private final Context mContext; - - private static final String DATABASE_NAME = "launcher.db"; - - private static final int DATABASE_VERSION = 1; - - static final String TABLE_PHOTOS = "photos"; - static final String FIELD_GADGET_ID = "gadgetId"; - static final String FIELD_PHOTO_BLOB = "photoBlob"; - - PhotoDatabaseHelper(Context context) { - super(context, DATABASE_NAME, null, DATABASE_VERSION); - mContext = context; - } - - @Override - public void onCreate(SQLiteDatabase db) { - db.execSQL("CREATE TABLE " + TABLE_PHOTOS + " (" + - FIELD_GADGET_ID + " INTEGER PRIMARY KEY," + - FIELD_PHOTO_BLOB + " BLOB" + - ");"); - } - - @Override - public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) { - int version = oldVersion; - - if (version != DATABASE_VERSION) { - Log.w(TAG, "Destroying all old data."); - db.execSQL("DROP TABLE IF EXISTS " + TABLE_PHOTOS); - onCreate(db); - } - } - - /** - * Store the given bitmap in this database for the given gadgetId. - */ - public boolean setPhoto(int gadgetId, Bitmap bitmap) { - boolean success = false; - 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.flush(); - out.close(); - - ContentValues values = new ContentValues(); - values.put(PhotoDatabaseHelper.FIELD_GADGET_ID, gadgetId); - values.put(PhotoDatabaseHelper.FIELD_PHOTO_BLOB, out.toByteArray()); - - SQLiteDatabase db = getWritableDatabase(); - db.insertOrThrow(PhotoDatabaseHelper.TABLE_PHOTOS, null, values); - - success = true; - } catch (SQLiteException e) { - Log.e(TAG, "Could not open database", e); - } catch (IOException e) { - Log.e(TAG, "Could not serialize photo", e); - } - if (LOGD) Log.d(TAG, "setPhoto success="+success); - return success; - } - - static final String[] PHOTOS_PROJECTION = { - FIELD_PHOTO_BLOB, - }; - - static final int INDEX_PHOTO_BLOB = 0; - - /** - * Inflate and return a bitmap for the given gadgetId. - */ - public Bitmap getPhoto(int gadgetId) { - Cursor c = null; - Bitmap bitmap = null; - try { - SQLiteDatabase db = getReadableDatabase(); - String selection = String.format("%s=%d", FIELD_GADGET_ID, gadgetId); - c = db.query(TABLE_PHOTOS, PHOTOS_PROJECTION, selection, null, - null, null, null, null); - - if (c != null && LOGD) Log.d(TAG, "getPhoto query count="+c.getCount()); - - if (c != null && c.moveToFirst()) { - byte[] data = c.getBlob(INDEX_PHOTO_BLOB); - if (data != null) { - bitmap = BitmapFactory.decodeByteArray(data, 0, data.length); - } - } - } catch (SQLiteException e) { - Log.e(TAG, "Could not load photo from database", e); - } finally { - if (c != null) { - c.close(); - } - } - return bitmap; - } - - /** - * Remove any bitmap associated with the given gadgetId. - */ - public void deletePhoto(int gadgetId) { - try { - SQLiteDatabase db = getWritableDatabase(); - String whereClause = String.format("%s=%d", FIELD_GADGET_ID, gadgetId); - db.delete(TABLE_PHOTOS, whereClause, null); - } catch (SQLiteException e) { - Log.e(TAG, "Could not delete photo from database", e); - } - } - } - -} - diff --git a/src/com/android/camera/PickWallpaper.java b/src/com/android/camera/PickWallpaper.java deleted file mode 100644 index e1fe784..0000000 --- a/src/com/android/camera/PickWallpaper.java +++ /dev/null @@ -1,23 +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.camera; - -/** - * Wallpaper picker for the camera application. This just redirects to the standard pick action. - */ -public class PickWallpaper extends Wallpaper { -} diff --git a/src/com/android/camera/SelectedImageGetter.java b/src/com/android/camera/SelectedImageGetter.java deleted file mode 100644 index 9e8fb96..0000000 --- a/src/com/android/camera/SelectedImageGetter.java +++ /dev/null @@ -1,25 +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.camera; - -import android.net.Uri; - -interface SelectedImageGetter { - ImageManager.IImage getCurrentImage(); - Uri getCurrentImageUri(); -} - diff --git a/src/com/android/camera/ShutterButton.java b/src/com/android/camera/ShutterButton.java deleted file mode 100644 index bd8d042..0000000 --- a/src/com/android/camera/ShutterButton.java +++ /dev/null @@ -1,115 +0,0 @@ -/* - * Copyright (C) 2008 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package com.android.camera; - -import android.content.Context; -import android.util.AttributeSet; -import android.widget.ImageView; - -/** - * A button designed to be used for the on-screen shutter button. - * It's currently an ImageView that can call a delegate when the pressed state changes. - */ -public class ShutterButton extends ImageView { - /** - * Interface definition for a callback to be invoked when a ModeButton's pressed state changes. - */ - public interface OnShutterButtonListener { - /** - * Called when a ShutterButton has been pressed. - * - * @param b The ShutterButton that was pressed. - */ - void onShutterButtonFocus(ShutterButton b, boolean pressed); - void onShutterButtonClick(ShutterButton b); - } - - private OnShutterButtonListener mListener; - private boolean mOldPressed; - - public ShutterButton(Context context) { - super(context); - } - - public ShutterButton(Context context, AttributeSet attrs) { - super(context, attrs); - } - - public ShutterButton(Context context, AttributeSet attrs, int defStyle) { - super(context, attrs, defStyle); - } - - public void setOnShutterButtonListener(OnShutterButtonListener listener) { - mListener = listener; - } - - /** - * Hook into the drawable state changing to get changes to isPressed -- the - * onPressed listener doesn't always get called when the pressed state changes. - */ - @Override - protected void drawableStateChanged() { - super.drawableStateChanged(); - final boolean pressed = isPressed(); - if (pressed != mOldPressed) { - if (!pressed) { - // When pressing the physical camera button the sequence of events is: - // focus pressed, optional camera pressed, focus released. - // We want to emulate this sequence of events with the shutter button. - // When clicking using a trackball button, the view system changes - // the the drawable state before posting click notification, so the - // sequence of events is: - // pressed(true), optional click, pressed(false) - // When clicking using touch events, the view system changes the - // drawable state after posting click notification, so the sequence of - // events is: - // pressed(true), pressed(false), optional click - // Since we're emulating the physical camera button, we want to have the - // same order of events. So we want the optional click callback to be delivered - // before the pressed(false) callback. - // - // To do this, we delay the posting of the pressed(false) event slightly by - // pushing it on the event queue. This moves it after the optional click - // notification, so our client always sees events in this sequence: - // pressed(true), optional click, pressed(false) - post(new Runnable() { - public void run() { - callShutterButtonFocus(pressed); - } - }); - } else { - callShutterButtonFocus(pressed); - } - mOldPressed = pressed; - } - } - - private void callShutterButtonFocus(boolean pressed) { - if (mListener != null) { - mListener.onShutterButtonFocus(this, pressed); - } - } - - @Override - public boolean performClick() { - boolean result = super.performClick(); - if (mListener != null) { - mListener.onShutterButtonClick(this); - } - return result; - } -} diff --git a/src/com/android/camera/SlideShow.java b/src/com/android/camera/SlideShow.java deleted file mode 100644 index 23c7d4a..0000000 --- a/src/com/android/camera/SlideShow.java +++ /dev/null @@ -1,429 +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.camera; - -import static android.view.WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON; -import android.app.Activity; -import android.content.Context; -import android.graphics.Bitmap; -import android.graphics.BitmapFactory; -import android.graphics.Paint; -import android.graphics.Canvas; -import android.graphics.Matrix; -import android.graphics.drawable.BitmapDrawable; -import android.net.Uri; -import android.os.Environment; -import android.os.Handler; -import android.os.Bundle; -import android.util.AttributeSet; -import android.util.Log; -import android.view.KeyEvent; -import android.os.Message; -import android.view.View; -import android.view.Window; -import android.widget.ImageView; -import android.widget.ViewSwitcher; -import android.widget.Gallery.LayoutParams; - -import android.view.WindowManager; - -import java.io.File; -import java.util.ArrayList; -import java.util.HashMap; - -import com.android.camera.ImageManager.IGetBitmap_cancelable; -import com.android.camera.ImageManager.IImage; -import com.android.camera.ImageManager.IImageList; - -import android.view.MotionEvent; - -public class SlideShow extends Activity implements ViewSwitcher.ViewFactory -{ - static final private String TAG = "SlideShow"; - static final int sLag = 2000; - static final int sNextImageInterval = 3000; - private ImageManager.IImageList mImageList; - private int mCurrentPosition = 0; - private ImageView mSwitcher; - private boolean mPosted = false; - - @Override - protected void onCreate(Bundle icicle) - { - super.onCreate(icicle); - Window wp = getWindow(); - wp.setFlags(FLAG_KEEP_SCREEN_ON, FLAG_KEEP_SCREEN_ON); - - setContentView(R.layout.slide_show); - - mSwitcher = (ImageView)findViewById(R.id.imageview); - if (android.util.Config.LOGV) - Log.v(TAG, "mSwitcher " + mSwitcher); - } - - @Override - protected void onResume() - { - super.onResume(); - - if (mImageList == null) { - mImageList = new FileImageList(); - mCurrentPosition = 0; - } - loadImage(); - } - - @Override - protected void onPause() { - super.onPause(); - cancelPost(); - } - - static public class ImageViewTouch extends ImageView { - class xy { - public xy(float xIn, float yIn) { - x = xIn; - y = yIn; - timeAdded = System.currentTimeMillis(); - } - public xy(MotionEvent e) { - x = e.getX(); - y = e.getY(); - timeAdded = System.currentTimeMillis(); - } - float x,y; - long timeAdded; - } - - SlideShow mSlideShow; - Paint mPaints[] = new Paint[1]; - ArrayList<xy> mPoints = new ArrayList<xy>(); - boolean mDown; - - public ImageViewTouch(Context context) { - super(context); - mSlideShow = (SlideShow) context; - setScaleType(ImageView.ScaleType.CENTER); - setupPaint(); - } - - public ImageViewTouch(Context context, AttributeSet attrs) { - super(context, attrs); - mSlideShow = (SlideShow) context; - setScaleType(ImageView.ScaleType.CENTER); - setupPaint(); - } - - private void setupPaint() { - for (int i = 0; i < mPaints.length; i++) { - Paint p = new Paint(); - p.setARGB(255, 255, 255, 0); - p.setAntiAlias(true); - p.setStyle(Paint.Style.FILL); - p.setStrokeWidth(3F); - mPaints[i] = p; - } - } - - private void addEvent(MotionEvent event) { - long now = System.currentTimeMillis(); - mPoints.add(new xy(event)); - for (int i = 0; i < event.getHistorySize(); i++) - mPoints.add(new xy(event.getHistoricalX(i), event.getHistoricalY(i))); - while (mPoints.size() > 0) { - xy ev = mPoints.get(0); - if (now - ev.timeAdded < sLag) - break; - mPoints.remove(0); - } - } - - public boolean onTouchEvent(MotionEvent event) { - addEvent(event); - switch (event.getAction()) { - case MotionEvent.ACTION_DOWN: - mDown = true; - mSlideShow.cancelPost(); - postInvalidate(); - break; - case MotionEvent.ACTION_UP: - mDown = false; - postInvalidate(); - break; - case MotionEvent.ACTION_MOVE: - mSlideShow.cancelPost(); - postInvalidate(); - break; - } - return true; - } - - protected void onDraw(Canvas canvas) { - super.onDraw(canvas); - - boolean didPaint = false; - long now = System.currentTimeMillis(); - for (xy ev: mPoints) { - Paint p = mPaints[0]; - long delta = now - ev.timeAdded; - if (delta > sLag) - continue; - - int alpha2 = Math.max(0, 255 - (255 * (int)delta / sLag)); - if (alpha2 == 0) - continue; - p.setAlpha(alpha2); - canvas.drawCircle(ev.x, ev.y, 2, p); - didPaint = true; - } - if (didPaint && !mDown) - postInvalidate(); - } - } - - - @Override - public boolean onKeyDown(int keyCode, KeyEvent event) { - switch (keyCode) { - case KeyEvent.KEYCODE_DPAD_LEFT: - cancelPost(); - loadPreviousImage(); - return true; - - case KeyEvent.KEYCODE_DPAD_RIGHT: - cancelPost(); - loadNextImage(); - return true; - - case KeyEvent.KEYCODE_DPAD_CENTER: - if (mPosted) - cancelPost(); - else - loadNextImage(); - return true; - } - return super.onKeyDown(keyCode, event); - } - - private void cancelPost() { - mHandler.removeCallbacks(mNextImageRunnable); - mPosted = false; - } - - private void post() { - mHandler.postDelayed(mNextImageRunnable, sNextImageInterval); - mPosted = true; - } - - private void loadImage() { - ImageManager.IImage image = mImageList.getImageAt(mCurrentPosition); - if (image == null) - return; - - Bitmap bitmap = image.thumbBitmap(); - if (bitmap == null) - return; - - mSwitcher.setImageDrawable(new BitmapDrawable(bitmap)); - post(); - } - - private Runnable mNextImageRunnable = new Runnable() { - public void run() { - if (android.util.Config.LOGV) - Log.v(TAG, "mNextImagerunnable called"); - loadNextImage(); - } - }; - - private void loadNextImage() { - if (++mCurrentPosition >= mImageList.getCount()) - mCurrentPosition = 0; - loadImage(); - } - - private void loadPreviousImage() { - if (mCurrentPosition == 0) - mCurrentPosition = mImageList.getCount() - 1; - else - mCurrentPosition -= 1; - - loadImage(); - } - - public View makeView() { - ImageView i = new ImageView(this); - i.setBackgroundColor(0xFF000000); - i.setScaleType(ImageView.ScaleType.FIT_CENTER); - i.setLayoutParams(new LayoutParams(LayoutParams.FILL_PARENT, LayoutParams.FILL_PARENT)); - return i; - } - - private final Handler mHandler = new Handler() { - @Override - public void handleMessage(Message msg) { - } - }; - - class FileImageList implements IImageList { - public HashMap<String, String> getBucketIds() { - throw new UnsupportedOperationException(); - } - - public void checkThumbnails(ThumbCheckCallback cb, int totalThumbnails) { - // TODO Auto-generated method stub - - } - - public void commitChanges() { - // TODO Auto-generated method stub - - } - - public void removeOnChangeListener(OnChange changeCallback) { - // TODO Auto-generated method stub - - } - - public void setOnChangeListener(OnChange changeCallback, Handler h) { - // TODO Auto-generated method stub - - } - - private ArrayList<FileImage> mImages = new ArrayList<FileImage>(); - // image uri ==> Image object - private HashMap<Long, IImage> mCache = new HashMap<Long, IImage>(); - - class FileImage extends ImageManager.SimpleBaseImage { - long mId; - String mPath; - - FileImage(long id, String path) { - mId = id; - mPath = path; - } - - public long imageId() { - return mId; - } - - public String getDataPath() { - return mPath; - } - - public Bitmap fullSizeBitmap(int targetWidthOrHeight) { - return BitmapFactory.decodeFile(mPath); - } - - public IGetBitmap_cancelable fullSizeBitmap_cancelable(int targetWidthOrHeight) { - return null; - } - - public Bitmap thumbBitmap() { - Bitmap b = fullSizeBitmap(320); - Matrix m = new Matrix(); - float scale = 320F / (float) b.getWidth(); - m.setScale(scale, scale); - Bitmap scaledBitmap = Bitmap.createBitmap(b, 0, 0, b.getWidth(), b.getHeight(), m, true); - return scaledBitmap; - } - - public Bitmap miniThumbBitmap() { - return thumbBitmap(); - } - - public long fullSizeImageId() { - return mId; - } - } - - private void enumerate(String path, ArrayList<String> list) { - File f = new File(path); - if (f.isDirectory()) { - String [] children = f.list(); - if (children != null) { - for (int i = 0; i < children.length; i++) { - if (children[i].charAt(0) != '.') - enumerate(path + "/" + children[i], list); - } - } - } else { - if (path.endsWith(".jpeg") || path.endsWith(".jpg") || path.endsWith(".png")) { - if (f.length() > 0) { - list.add(path); - } - } - } - } - - public FileImageList() { - ArrayList<String> list = new ArrayList<String>(); - enumerate(Environment.getExternalStorageDirectory().getPath(), list); - enumerate("/data/images", list); - - for (int i = 0; i < list.size(); i++) { - FileImage img = new FileImage(i, list.get(i)); - mCache.put((long)i, img); - mImages.add(img); - } - } - - public IImage getImageAt(int i) { - if (i >= mImages.size()) - return null; - - return mImages.get(i); - } - - public IImage getImageForUri(Uri uri) { - // TODO make this a hash lookup - int count = getCount(); - for (int i = 0; i < count; i++) { - IImage image = getImageAt(i); - if (image.fullSizeImageUri().equals(uri)) { - return image; - } - } - return null; - } - - public IImage getImageWithId(long id) { - throw new UnsupportedOperationException(); - } - - public void removeImageAt(int i) { - throw new UnsupportedOperationException(); - } - - public boolean removeImage(IImage image) { - throw new UnsupportedOperationException(); - } - - public int getCount() { - return mImages.size(); - } - - public boolean isEmpty() { - return mImages.isEmpty(); - } - - public void deactivate() { - // nothing to do here - } - } - -} diff --git a/src/com/android/camera/VideoCamera.java b/src/com/android/camera/VideoCamera.java deleted file mode 100644 index 05e33a6..0000000 --- a/src/com/android/camera/VideoCamera.java +++ /dev/null @@ -1,1014 +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.camera; - -import java.io.File; -import java.io.FileDescriptor; -import java.io.IOException; -import java.io.InputStream; -import java.io.OutputStream; -import java.text.SimpleDateFormat; -import java.util.ArrayList; -import java.util.Date; - -import android.app.Activity; -import android.app.AlertDialog; -import android.content.BroadcastReceiver; -import android.content.ContentResolver; -import android.content.ContentValues; -import android.content.Context; -import android.content.Intent; -import android.content.IntentFilter; -import android.content.SharedPreferences; -import android.graphics.Bitmap; -import android.graphics.drawable.ColorDrawable; -import android.graphics.drawable.Drawable; -import android.location.LocationManager; -import android.media.MediaMetadataRetriever; -import android.media.MediaRecorder; -import android.net.Uri; -import android.os.Bundle; -import android.os.Environment; -import android.os.Handler; -import android.os.Message; -import android.os.StatFs; -import android.os.SystemClock; -import android.preference.PreferenceManager; -import android.provider.MediaStore; -import android.provider.MediaStore.Video; -import android.text.format.DateFormat; -import android.util.Log; -import android.view.KeyEvent; -import android.view.Menu; -import android.view.MenuItem; -import android.view.SurfaceHolder; -import android.view.View; -import android.view.Window; -import android.view.WindowManager; -import android.view.MenuItem.OnMenuItemClickListener; -import android.view.animation.AlphaAnimation; -import android.view.animation.Animation; -import android.widget.ImageView; -import android.widget.TextView; -import android.widget.Toast; - -public class VideoCamera extends Activity implements View.OnClickListener, - ShutterButton.OnShutterButtonListener, SurfaceHolder.Callback { - - private static final String TAG = "videocamera"; - - private static final boolean DEBUG = true; - private static final boolean DEBUG_SUPPRESS_AUDIO_RECORDING = DEBUG && false; - private static final boolean DEBUG_DO_NOT_REUSE_MEDIA_RECORDER = DEBUG && true; - private static final boolean DEBUG_LOG_APP_LIFECYCLE = DEBUG && false; - - private static final int CLEAR_SCREEN_DELAY = 4; - private static final int UPDATE_RECORD_TIME = 5; - - private static final int SCREEN_DELAY = 2 * 60 * 1000; - - private static final long NO_STORAGE_ERROR = -1L; - private static final long CANNOT_STAT_ERROR = -2L; - private static final long LOW_STORAGE_THRESHOLD = 512L * 1024L; - - public static final int MENU_SETTINGS = 6; - public static final int MENU_GALLERY_PHOTOS = 7; - public static final int MENU_GALLERY_VIDEOS = 8; - public static final int MENU_SAVE_GALLERY_PHOTO = 34; - public static final int MENU_SAVE_PLAY_VIDEO = 35; - public static final int MENU_SAVE_SELECT_VIDEO = 36; - public static final int MENU_SAVE_NEW_VIDEO = 37; - - SharedPreferences mPreferences; - - private static final float VIDEO_ASPECT_RATIO = 176.0f / 144.0f; - VideoPreview mVideoPreview; - SurfaceHolder mSurfaceHolder = null; - ImageView mBlackout = null; - ImageView mVideoFrame; - Bitmap mVideoFrameBitmap; - - private MediaRecorder mMediaRecorder; - private boolean mMediaRecorderRecording = false; - private boolean mNeedToRegisterRecording; - private long mRecordingStartTime; - // The video file that the hardware camera is about to record into - // (or is recording into.) - private String mCameraVideoFilename; - private FileDescriptor mCameraVideoFileDescriptor; - - // The video file that has already been recorded, and that is being - // examined by the user. - private String mCurrentVideoFilename; - private Uri mCurrentVideoUri; - private ContentValues mCurrentVideoValues; - - boolean mPausing = false; - - static ContentResolver mContentResolver; - boolean mDidRegister = false; - - int mCurrentZoomIndex = 0; - - private ShutterButton mShutterButton; - private TextView mRecordingTimeView; - private boolean mHasSdCard; - - ArrayList<MenuItem> mGalleryItems = new ArrayList<MenuItem>(); - - View mPostPictureAlert; - LocationManager mLocationManager = null; - - private Handler mHandler = new MainHandler(); - - /** This Handler is used to post message back onto the main thread of the application */ - private class MainHandler extends Handler { - @Override - public void handleMessage(Message msg) { - switch (msg.what) { - - case CLEAR_SCREEN_DELAY: { - clearScreenOnFlag(); - break; - } - - case UPDATE_RECORD_TIME: { - if (mMediaRecorderRecording) { - long now = SystemClock.uptimeMillis(); - long delta = now - mRecordingStartTime; - long seconds = delta / 1000; - long minutes = seconds / 60; - long hours = minutes / 60; - long remainderMinutes = minutes - (hours * 60); - long remainderSeconds = seconds - (minutes * 60); - - String secondsString = Long.toString(remainderSeconds); - if (secondsString.length() < 2) { - secondsString = "0" + secondsString; - } - String minutesString = Long.toString(remainderMinutes); - if (minutesString.length() < 2) { - minutesString = "0" + minutesString; - } - String text = minutesString + ":" + secondsString; - if (hours > 0) { - String hoursString = Long.toString(hours); - if (hoursString.length() < 2) { - hoursString = "0" + hoursString; - } - text = hoursString + ":" + text; - } - mRecordingTimeView.setText(text); - // Work around a limitation of the T-Mobile G1: The T-Mobile - // hardware blitter can't pixel-accurately scale and clip at the same time, - // and the SurfaceFlinger doesn't attempt to work around this limitation. - // In order to avoid visual corruption we must manually refresh the entire - // surface view when changing any overlapping view's contents. - mVideoPreview.invalidate(); - mHandler.sendEmptyMessageDelayed(UPDATE_RECORD_TIME, 1000); - } - break; - } - - default: - Log.v(TAG, "Unhandled message: " + msg.what); - break; - } - } - }; - - private final BroadcastReceiver mReceiver = new BroadcastReceiver() { - @Override - public void onReceive(Context context, Intent intent) { - String action = intent.getAction(); - if (action.equals(Intent.ACTION_MEDIA_MOUNTED)) { - // SD card available - // TODO put up a "please wait" message - // TODO also listen for the media scanner finished message - updateStorageHint(); - mHasSdCard = true; - } else if (action.equals(Intent.ACTION_MEDIA_UNMOUNTED)) { - // SD card unavailable - updateStorageHint(); - mHasSdCard = false; - } else if (action.equals(Intent.ACTION_MEDIA_SCANNER_STARTED)) { - Toast.makeText(VideoCamera.this, getResources().getString(R.string.wait), 5000); - } else if (action.equals(Intent.ACTION_MEDIA_SCANNER_FINISHED)) { - updateStorageHint(); - } - } - }; - - static private String createName(long dateTaken) { - return DateFormat.format("yyyy-MM-dd kk.mm.ss", dateTaken).toString(); - } - - /** Called with the activity is first created. */ - @Override - public void onCreate(Bundle icicle) { - if (DEBUG_LOG_APP_LIFECYCLE) { - Log.v(TAG, "onCreate " + this.hashCode()); - } - super.onCreate(icicle); - - mLocationManager = (LocationManager) getSystemService(Context.LOCATION_SERVICE); - - mPreferences = PreferenceManager.getDefaultSharedPreferences(this); - mContentResolver = getContentResolver(); - - //setDefaultKeyMode(DEFAULT_KEYS_SHORTCUT); - requestWindowFeature(Window.FEATURE_PROGRESS); - setContentView(R.layout.video_camera); - - mVideoPreview = (VideoPreview) findViewById(R.id.camera_preview); - mVideoPreview.setAspectRatio(VIDEO_ASPECT_RATIO); - - // don't set mSurfaceHolder here. We have it set ONLY within - // surfaceCreated / surfaceDestroyed, other parts of the code - // assume that when it is set, the surface is also set. - SurfaceHolder holder = mVideoPreview.getHolder(); - holder.addCallback(this); - holder.setType(SurfaceHolder.SURFACE_TYPE_PUSH_BUFFERS); - - mBlackout = (ImageView) findViewById(R.id.blackout); - mBlackout.setBackgroundDrawable(new ColorDrawable(0xFF000000)); - - mPostPictureAlert = findViewById(R.id.post_picture_panel); - - int[] ids = new int[]{R.id.play, R.id.share, R.id.discard, - R.id.cancel, R.id.attach}; - for (int id : ids) { - findViewById(id).setOnClickListener(this); - } - - mShutterButton = (ShutterButton) findViewById(R.id.shutter_button); - mShutterButton.setOnShutterButtonListener(this); - mRecordingTimeView = (TextView) findViewById(R.id.recording_time); - mVideoFrame = (ImageView) findViewById(R.id.video_frame); - } - - @Override - public void onStart() { - if (DEBUG_LOG_APP_LIFECYCLE) { - Log.v(TAG, "onStart " + this.hashCode()); - } - super.onStart(); - - Thread t = new Thread(new Runnable() { - public void run() { - final boolean storageOK = getAvailableStorage() >= LOW_STORAGE_THRESHOLD; - - if (!storageOK) { - mHandler.post(new Runnable() { - public void run() { - updateStorageHint(); - } - }); - } - } - }); - t.start(); - } - - public void onClick(View v) { - switch (v.getId()) { - - case R.id.gallery: - MenuHelper.gotoCameraVideoGallery(this); - break; - - case R.id.attach: - doReturnToCaller(true); - break; - - case R.id.cancel: - doReturnToCaller(false); - break; - - case R.id.discard: { - discardCurrentVideoAndStartPreview(); - break; - } - - case R.id.share: { - Intent intent = new Intent(); - intent.setAction(Intent.ACTION_SEND); - intent.setType("video/3gpp"); - intent.putExtra(Intent.EXTRA_STREAM, mCurrentVideoUri); - try { - startActivity(Intent.createChooser(intent, getText(R.string.sendVideo))); - } catch (android.content.ActivityNotFoundException ex) { - Toast.makeText(VideoCamera.this, R.string.no_way_to_share_video, Toast.LENGTH_SHORT).show(); - } - - break; - } - - case R.id.play: { - doPlayCurrentVideo(); - break; - } - } - } - - public void onShutterButtonFocus(ShutterButton button, boolean pressed) { - switch (button.getId()) { - case R.id.shutter_button: - if (pressed) { - if (mMediaRecorderRecording) { - stopVideoRecordingAndDisplayDialog(); - } else if (mVideoFrame.getVisibility() == View.VISIBLE) { - doStartCaptureMode(); - } else { - startVideoRecording(); - } - } - break; - } - } - - public void onShutterButtonClick(ShutterButton button) { - // Do nothing (everything happens in onShutterButtonFocus). - } - - private void doStartCaptureMode() { - if (isVideoCaptureIntent()) { - discardCurrentVideoAndStartPreview(); - } else { - hideVideoFrameAndStartPreview(); - } - } - - private void doPlayCurrentVideo() { - Log.e(TAG, "Playing current video: " + mCurrentVideoUri); - Intent intent = new Intent(Intent.ACTION_VIEW, mCurrentVideoUri); - try { - startActivity(intent); - } catch (android.content.ActivityNotFoundException ex) { - Log.e(TAG, "Couldn't view video " + mCurrentVideoUri, ex); - } - } - - private void discardCurrentVideoAndStartPreview() { - deleteCurrentVideo(); - hideVideoFrameAndStartPreview(); - } - - private OnScreenHint mStorageHint; - - private void updateStorageHint() { - long remaining = getAvailableStorage(); - String errorMessage = null; - if (remaining == NO_STORAGE_ERROR) { - errorMessage = getString(R.string.no_storage); - } else if (remaining < LOW_STORAGE_THRESHOLD) { - errorMessage = getString(R.string.spaceIsLow_content); - if (mStorageHint != null) { - mStorageHint.cancel(); - mStorageHint = null; - } - } - if (errorMessage != null) { - if (mStorageHint == null) { - mStorageHint = OnScreenHint.makeText(this, errorMessage); - } else { - mStorageHint.setText(errorMessage); - } - mStorageHint.show(); - } else if (mStorageHint != null) { - mStorageHint.cancel(); - mStorageHint = null; - } - } - - @Override - public void onResume() { - if (DEBUG_LOG_APP_LIFECYCLE) { - Log.v(TAG, "onResume " + this.hashCode()); - } - super.onResume(); - - setScreenTimeoutLong(); - - mPausing = false; - - // install an intent filter to receive SD card related events. - IntentFilter intentFilter = new IntentFilter(Intent.ACTION_MEDIA_MOUNTED); - intentFilter.addAction(Intent.ACTION_MEDIA_UNMOUNTED); - intentFilter.addAction(Intent.ACTION_MEDIA_SCANNER_STARTED); - intentFilter.addAction(Intent.ACTION_MEDIA_SCANNER_FINISHED); - intentFilter.addDataScheme("file"); - registerReceiver(mReceiver, intentFilter); - mDidRegister = true; - mHasSdCard = ImageManager.hasStorage(); - - mBlackout.setVisibility(View.INVISIBLE); - if (mVideoFrameBitmap == null) { - initializeVideo(); - } else { - showPostRecordingAlert(); - } - } - - @Override - public void onStop() { - if (DEBUG_LOG_APP_LIFECYCLE) { - Log.v(TAG, "onStop " + this.hashCode()); - } - stopVideoRecording(); - setScreenTimeoutSystemDefault(); - super.onStop(); - } - - @Override - protected void onPause() { - if (DEBUG_LOG_APP_LIFECYCLE) { - Log.v(TAG, "onPause " + this.hashCode()); - } - super.onPause(); - - stopVideoRecording(); - hidePostPictureAlert(); - - mPausing = true; - - if (mDidRegister) { - unregisterReceiver(mReceiver); - mDidRegister = false; - } - mBlackout.setVisibility(View.VISIBLE); - setScreenTimeoutSystemDefault(); - - if (mStorageHint != null) { - mStorageHint.cancel(); - mStorageHint = null; - } - } - - @Override - public boolean onKeyDown(int keyCode, KeyEvent event) { - setScreenTimeoutLong(); - - switch (keyCode) { - case KeyEvent.KEYCODE_BACK: - if (mMediaRecorderRecording) { - Log.v(TAG, "onKeyBack"); - stopVideoRecordingAndDisplayDialog(); - return true; - } else if(isPostRecordingAlertVisible()) { - hideVideoFrameAndStartPreview(); - return true; - } - break; - case KeyEvent.KEYCODE_CAMERA: - if (event.getRepeatCount() == 0) { - // If we get a dpad center event without any focused view, move the - // focus to the shutter button and press it. - if (mShutterButton.isInTouchMode()) { - mShutterButton.requestFocusFromTouch(); - } else { - mShutterButton.requestFocus(); - } - mShutterButton.setPressed(true); - return true; - } - return true; - case KeyEvent.KEYCODE_DPAD_CENTER: - if (event.getRepeatCount() == 0) { - // If we get a dpad center event without any focused view, move the - // focus to the shutter button and press it. - if (mShutterButton.isInTouchMode()) { - mShutterButton.requestFocusFromTouch(); - } else { - mShutterButton.requestFocus(); - } - mShutterButton.setPressed(true); - } - break; - case KeyEvent.KEYCODE_MENU: - if (mMediaRecorderRecording) { - stopVideoRecordingAndDisplayDialog(); - return true; - } - break; - } - - return super.onKeyDown(keyCode, event); - } - - @Override - public boolean onKeyUp(int keyCode, KeyEvent event) { - switch(keyCode) { - case KeyEvent.KEYCODE_CAMERA: - mShutterButton.setPressed(false); - return true; - } - return super.onKeyUp(keyCode, event); - } - - public void surfaceChanged(SurfaceHolder holder, int format, int w, int h) { - stopVideoRecording(); - initializeVideo(); - } - - public void surfaceCreated(SurfaceHolder holder) { - mSurfaceHolder = holder; - } - - public void surfaceDestroyed(SurfaceHolder holder) { - mSurfaceHolder = null; - } - - void gotoGallery() { - MenuHelper.gotoCameraVideoGallery(this); - } - - @Override - public boolean onPrepareOptionsMenu(Menu menu) { - super.onPrepareOptionsMenu(menu); - - for (int i = 1; i <= MenuHelper.MENU_ITEM_MAX; i++) { - if (i != MenuHelper.GENERIC_ITEM) { - menu.setGroupVisible(i, false); - } - } - - menu.setGroupVisible(MenuHelper.VIDEO_MODE_ITEM, true); - return true; - } - - @Override - public boolean onCreateOptionsMenu(Menu menu) { - super.onCreateOptionsMenu(menu); - - if (isVideoCaptureIntent()) { - // No options menu for attach mode. - return false; - } else { - addBaseMenuItems(menu); - MenuHelper.addImageMenuItems( - menu, - MenuHelper.INCLUDE_ALL & ~MenuHelper.INCLUDE_ROTATE_MENU, - false, - VideoCamera.this, - mHandler, - - // Handler for deletion - new Runnable() { - public void run() { - // What do we do here? - // mContentResolver.delete(uri, null, null); - } - }, - new MenuHelper.MenuInvoker() { - public void run(final MenuHelper.MenuCallback cb) { - } - }); - - MenuItem gallery = menu.add(MenuHelper.IMAGE_SAVING_ITEM, MENU_SAVE_GALLERY_PHOTO, 0, - R.string.camera_gallery_photos_text).setOnMenuItemClickListener( - new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - gotoGallery(); - return true; - } - }); - gallery.setIcon(android.R.drawable.ic_menu_gallery); - } - return true; - } - - private boolean isVideoCaptureIntent() { - String action = getIntent().getAction(); - return (MediaStore.ACTION_VIDEO_CAPTURE.equals(action)); - } - - private void doReturnToCaller(boolean success) { - Intent resultIntent = new Intent(); - int resultCode; - if (success) { - resultCode = RESULT_OK; - resultIntent.setData(mCurrentVideoUri); - } else { - resultCode = RESULT_CANCELED; - } - setResult(resultCode, resultIntent); - finish(); - } - - /** - * Returns - * @return number of bytes available, or an ERROR code. - */ - private static long getAvailableStorage() { - try { - if (!ImageManager.hasStorage()) { - return NO_STORAGE_ERROR; - } else { - String storageDirectory = Environment.getExternalStorageDirectory().toString(); - StatFs stat = new StatFs(storageDirectory); - return ((long)stat.getAvailableBlocks() * (long)stat.getBlockSize()); - } - } catch (Exception ex) { - // if we can't stat the filesystem then we don't know how many - // free bytes exist. It might be zero but just leave it - // blank since we really don't know. - return CANNOT_STAT_ERROR; - } - } - - private void cleanupEmptyFile() { - if (mCameraVideoFilename != null) { - File f = new File(mCameraVideoFilename); - if (f.length() == 0 && f.delete()) { - Log.v(TAG, "Empty video file deleted: " + mCameraVideoFilename); - mCameraVideoFilename = null; - } - } - } - - private void initializeVideo() { - Log.v(TAG, "initializeVideo"); - boolean isCaptureIntent = isVideoCaptureIntent(); - Intent intent = getIntent(); - Bundle myExtras = intent.getExtras(); - - if (isCaptureIntent && myExtras != null) { - Uri saveUri = (Uri) myExtras.getParcelable(MediaStore.EXTRA_OUTPUT); - if (saveUri != null) { - try { - mCameraVideoFileDescriptor = mContentResolver. - openFileDescriptor(saveUri, "rw").getFileDescriptor(); - mCurrentVideoUri = saveUri; - } - catch (java.io.FileNotFoundException ex) { - // invalid uri - Log.e(TAG, ex.toString()); - } - } - } - releaseMediaRecorder(); - - if (mSurfaceHolder == null) { - Log.v(TAG, "SurfaceHolder is null"); - return; - } - - mMediaRecorder = new MediaRecorder(); - mNeedToRegisterRecording = false; - - if (DEBUG_SUPPRESS_AUDIO_RECORDING) { - Log.v(TAG, "DEBUG_SUPPRESS_AUDIO_RECORDING is true."); - } else { - mMediaRecorder.setAudioSource(MediaRecorder.AudioSource.MIC); - } - mMediaRecorder.setVideoSource(MediaRecorder.VideoSource.CAMERA); - mMediaRecorder.setOutputFormat(MediaRecorder.OutputFormat.THREE_GPP); - - // We try Uri in intent first. If it doesn't work, use our own instead. - if (mCameraVideoFileDescriptor != null) { - mMediaRecorder.setOutputFile(mCameraVideoFileDescriptor); - } else { - createVideoPath(); - mMediaRecorder.setOutputFile(mCameraVideoFilename); - } - - boolean videoQualityHigh = getBooleanPreference(CameraSettings.KEY_VIDEO_QUALITY, - CameraSettings.DEFAULT_VIDEO_QUALITY_VALUE); - - - if (intent.hasExtra(MediaStore.EXTRA_VIDEO_QUALITY)) { - int extraVideoQuality = intent.getIntExtra(MediaStore.EXTRA_VIDEO_QUALITY, 0); - videoQualityHigh = (extraVideoQuality > 0); - } - - // Use the same frame rate for both, since internally - // if the frame rate is too large, it can cause camera to become - // unstable. We need to fix the MediaRecorder to disable the support - // of setting frame rate for now. - mMediaRecorder.setVideoFrameRate(20); - if (videoQualityHigh) { - mMediaRecorder.setVideoSize(352,288); - } else { - mMediaRecorder.setVideoSize(176,144); - } - mMediaRecorder.setVideoEncoder(MediaRecorder.VideoEncoder.H263); - if (!DEBUG_SUPPRESS_AUDIO_RECORDING) { - mMediaRecorder.setAudioEncoder(MediaRecorder.AudioEncoder.AMR_NB); - } - mMediaRecorder.setPreviewDisplay(mSurfaceHolder.getSurface()); - try { - mMediaRecorder.prepare(); - } catch (IOException exception) { - Log.e(TAG, "prepare failed for " + mCameraVideoFilename); - releaseMediaRecorder(); - // TODO: add more exception handling logic here - return; - } - mMediaRecorderRecording = false; - } - - private void releaseMediaRecorder() { - Log.v(TAG, "Releasing media recorder."); - if (mMediaRecorder != null) { - cleanupEmptyFile(); - mMediaRecorder.reset(); - mMediaRecorder.release(); - mMediaRecorder = null; - } - } - - private void restartPreview() { - if (DEBUG_DO_NOT_REUSE_MEDIA_RECORDER) { - Log.v(TAG, "DEBUG_DO_NOT_REUSE_MEDIA_RECORDER recreating mMediaRecorder."); - initializeVideo(); - } else { - try { - mMediaRecorder.prepare(); - } catch (IOException exception) { - Log.e(TAG, "prepare failed for " + mCameraVideoFilename); - releaseMediaRecorder(); - // TODO: add more exception handling logic here - } - } - } - - private int getIntPreference(String key, int defaultValue) { - String s = mPreferences.getString(key, ""); - int result = defaultValue; - try { - result = Integer.parseInt(s); - } catch (NumberFormatException e) { - // Ignore, result is already the default value. - } - return result; - } - - private boolean getBooleanPreference(String key, boolean defaultValue) { - return getIntPreference(key, defaultValue ? 1 : 0) != 0; - } - - private void createVideoPath() { - long dateTaken = System.currentTimeMillis(); - String title = createName(dateTaken); - String displayName = title + ".3gp"; // Used when emailing. - String cameraDirPath = ImageManager.CAMERA_IMAGE_BUCKET_NAME; - File cameraDir = new File(cameraDirPath); - cameraDir.mkdirs(); - SimpleDateFormat dateFormat = new SimpleDateFormat( - getString(R.string.video_file_name_format)); - Date date = new Date(dateTaken); - String filepart = dateFormat.format(date); - String filename = cameraDirPath + "/" + filepart + ".3gp"; - ContentValues values = new ContentValues(7); - values.put(Video.Media.TITLE, title); - values.put(Video.Media.DISPLAY_NAME, displayName); - values.put(Video.Media.DESCRIPTION, ""); - values.put(Video.Media.DATE_TAKEN, dateTaken); - values.put(Video.Media.MIME_TYPE, "video/3gpp"); - values.put(Video.Media.DATA, filename); - mCameraVideoFilename = filename; - Log.v(TAG, "Current camera video filename: " + mCameraVideoFilename); - mCurrentVideoValues = values; - } - - private void registerVideo() { - if (mCameraVideoFileDescriptor == null) { - Uri videoTable = Uri.parse("content://media/external/video/media"); - mCurrentVideoUri = mContentResolver.insert(videoTable, - mCurrentVideoValues); - Log.v(TAG, "Current video URI: " + mCurrentVideoUri); - } - mCurrentVideoValues = null; - } - - private void deleteCurrentVideo() { - if (mCurrentVideoFilename != null) { - deleteVideoFile(mCurrentVideoFilename); - mCurrentVideoFilename = null; - } - if (mCurrentVideoUri != null) { - mContentResolver.delete(mCurrentVideoUri, null, null); - mCurrentVideoUri = null; - } - } - - private void deleteVideoFile(String fileName) { - Log.v(TAG, "Deleting video " + fileName); - File f = new File(fileName); - if (! f.delete()) { - Log.v(TAG, "Could not delete " + fileName); - } - } - - private void addBaseMenuItems(Menu menu) { - MenuHelper.addSwitchModeMenuItem(menu, this, false); - { - MenuItem gallery = menu.add(MenuHelper.IMAGE_MODE_ITEM, MENU_GALLERY_PHOTOS, 0, R.string.camera_gallery_photos_text).setOnMenuItemClickListener(new OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - gotoGallery(); - return true; - } - }); - gallery.setIcon(android.R.drawable.ic_menu_gallery); - mGalleryItems.add(gallery); - } - { - MenuItem gallery = menu.add(MenuHelper.VIDEO_MODE_ITEM, MENU_GALLERY_VIDEOS, 0, R.string.camera_gallery_photos_text).setOnMenuItemClickListener(new OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - gotoGallery(); - return true; - } - }); - gallery.setIcon(android.R.drawable.ic_menu_gallery); - mGalleryItems.add(gallery); - } - - MenuItem item = menu.add(MenuHelper.GENERIC_ITEM, MENU_SETTINGS, 0, R.string.settings).setOnMenuItemClickListener(new OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - Intent intent = new Intent(); - intent.setClass(VideoCamera.this, CameraSettings.class); - startActivity(intent); - return true; - } - }); - item.setIcon(android.R.drawable.ic_menu_preferences); - } - - private void startVideoRecording() { - Log.v(TAG, "startVideoRecording"); - if (!mMediaRecorderRecording) { - - if (mStorageHint != null) { - Log.v(TAG, "Storage issue, ignore the start request"); - return; - } - - // Check mMediaRecorder to see whether it is initialized or not. - if (mMediaRecorder == null) { - initializeVideo(); - } - try { - mMediaRecorder.start(); // Recording is now started - } catch (RuntimeException e) { - Log.e(TAG, "Could not start media recorder. ", e); - return; - } - mMediaRecorderRecording = true; - mRecordingStartTime = SystemClock.uptimeMillis(); - updateRecordingIndicator(true); - mRecordingTimeView.setText(""); - mRecordingTimeView.setVisibility(View.VISIBLE); - mHandler.sendEmptyMessage(UPDATE_RECORD_TIME); - setScreenTimeoutInfinite(); - } - } - - private void updateRecordingIndicator(boolean showRecording) { - int drawableId = showRecording ? R.drawable.ic_camera_bar_indicator_record - : R.drawable.ic_camera_indicator_video; - Drawable drawable = getResources().getDrawable(drawableId); - mShutterButton.setImageDrawable(drawable); - } - - private void stopVideoRecordingAndDisplayDialog() { - Log.v(TAG, "stopVideoRecordingAndDisplayDialog"); - if (mMediaRecorderRecording) { - stopVideoRecording(); - acquireAndShowVideoFrame(); - showPostRecordingAlert(); - } - } - - private void showPostRecordingAlert() { - int[] pickIds = {R.id.attach, R.id.cancel}; - int[] normalIds = {R.id.gallery, R.id.share, R.id.discard}; - int[] alwaysOnIds = {R.id.play}; - int[] hideIds = pickIds; - int[] connectIds = normalIds; - if (isVideoCaptureIntent()) { - hideIds = normalIds; - connectIds = pickIds; - } - for(int id : hideIds) { - mPostPictureAlert.findViewById(id).setVisibility(View.GONE); - } - connectAndFadeIn(connectIds); - connectAndFadeIn(alwaysOnIds); - mPostPictureAlert.setVisibility(View.VISIBLE); - } - - private void connectAndFadeIn(int[] connectIds) { - for(int id : connectIds) { - View view = mPostPictureAlert.findViewById(id); - view.setOnClickListener(this); - Animation animation = new AlphaAnimation(0F, 1F); - animation.setDuration(500); - view.setAnimation(animation); - } - } - - private void hidePostPictureAlert() { - mPostPictureAlert.setVisibility(View.INVISIBLE); - } - - private boolean isPostRecordingAlertVisible() { - return mPostPictureAlert.getVisibility() == View.VISIBLE; - } - - private void stopVideoRecording() { - Log.v(TAG, "stopVideoRecording"); - if (mMediaRecorderRecording || mMediaRecorder != null) { - if (mMediaRecorderRecording && mMediaRecorder != null) { - mMediaRecorder.stop(); - mCurrentVideoFilename = mCameraVideoFilename; - Log.v(TAG, "Setting current video filename: " + mCurrentVideoFilename); - mNeedToRegisterRecording = true; - mMediaRecorderRecording = false; - } - releaseMediaRecorder(); - updateRecordingIndicator(false); - mRecordingTimeView.setVisibility(View.GONE); - setScreenTimeoutLong(); - } - if (mNeedToRegisterRecording) { - registerVideo(); - mNeedToRegisterRecording = false; - } - mCameraVideoFilename = null; - mCameraVideoFileDescriptor = null; - } - - private void setScreenTimeoutSystemDefault() { - mHandler.removeMessages(CLEAR_SCREEN_DELAY); - clearScreenOnFlag(); - } - - private void setScreenTimeoutLong() { - mHandler.removeMessages(CLEAR_SCREEN_DELAY); - setScreenOnFlag(); - mHandler.sendEmptyMessageDelayed(CLEAR_SCREEN_DELAY, SCREEN_DELAY); - } - - private void setScreenTimeoutInfinite() { - mHandler.removeMessages(CLEAR_SCREEN_DELAY); - setScreenOnFlag(); - } - - private void clearScreenOnFlag() { - Window w = getWindow(); - final int keepScreenOnFlag = WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON; - if ((w.getAttributes().flags & keepScreenOnFlag) != 0) { - w.clearFlags(keepScreenOnFlag); - } - } - - private void setScreenOnFlag() { - Window w = getWindow(); - final int keepScreenOnFlag = WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON; - if ((w.getAttributes().flags & keepScreenOnFlag) == 0) { - w.addFlags(keepScreenOnFlag); - } - } - - private void hideVideoFrameAndStartPreview() { - hidePostPictureAlert(); - hideVideoFrame(); - restartPreview(); - } - - private void acquireAndShowVideoFrame() { - recycleVideoFrameBitmap(); - mVideoFrameBitmap = ImageManager.createVideoThumbnail(mCurrentVideoFilename); - mVideoFrame.setImageBitmap(mVideoFrameBitmap); - mVideoFrame.setVisibility(View.VISIBLE); - } - - private void hideVideoFrame() { - recycleVideoFrameBitmap(); - mVideoFrame.setVisibility(View.GONE); - } - - private void recycleVideoFrameBitmap() { - if (mVideoFrameBitmap != null) { - mVideoFrame.setImageDrawable(null); - mVideoFrameBitmap.recycle(); - mVideoFrameBitmap = null; - } - } -} - diff --git a/src/com/android/camera/VideoPreview.java b/src/com/android/camera/VideoPreview.java deleted file mode 100644 index aed1e89..0000000 --- a/src/com/android/camera/VideoPreview.java +++ /dev/null @@ -1,99 +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.camera; - -import android.content.Context; -import android.util.AttributeSet; -import android.util.Log; -import android.view.SurfaceView; -import android.view.View.MeasureSpec; - -class VideoPreview extends SurfaceView { - private float mAspectRatio; - private int mHorizontalTileSize = 1; - private int mVerticalTileSize = 1; - - /** - * Setting the aspect ratio to this value means to not enforce an aspect ratio. - */ - public static float DONT_CARE = 0.0f; - - public VideoPreview(Context context) { - super(context); - } - - public VideoPreview(Context context, AttributeSet attrs) { - super(context, attrs); - } - - public VideoPreview(Context context, AttributeSet attrs, int defStyle) { - super(context, attrs, defStyle); - } - - public void setTileSize(int horizontalTileSize, int verticalTileSize) { - if ((mHorizontalTileSize != horizontalTileSize) - || (mVerticalTileSize != verticalTileSize)) { - mHorizontalTileSize = horizontalTileSize; - mVerticalTileSize = verticalTileSize; - requestLayout(); - invalidate(); - } - } - - public void setAspectRatio(int width, int height) { - setAspectRatio(((float) width) / ((float) height)); - } - - public void setAspectRatio(float aspectRatio) { - if (mAspectRatio != aspectRatio) { - mAspectRatio = aspectRatio; - requestLayout(); - invalidate(); - } - } - - @Override - protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) { - if (mAspectRatio != DONT_CARE) { - int widthSpecSize = MeasureSpec.getSize(widthMeasureSpec); - int heightSpecSize = MeasureSpec.getSize(heightMeasureSpec); - - int width = widthSpecSize; - int height = heightSpecSize; - - if (width > 0 && height > 0) { - float defaultRatio = ((float) width) / ((float) height); - if (defaultRatio < mAspectRatio) { - // Need to reduce height - height = (int) (width / mAspectRatio); - } else if (defaultRatio > mAspectRatio) { - width = (int) (height * mAspectRatio); - } - width = roundUpToTile(width, mHorizontalTileSize, widthSpecSize); - height = roundUpToTile(height, mVerticalTileSize, heightSpecSize); - Log.i("VideoPreview", "ar " + mAspectRatio + " setting size: " + width + 'x' + height); - setMeasuredDimension(width, height); - return; - } - } - super.onMeasure(widthMeasureSpec, heightMeasureSpec); - } - - private int roundUpToTile(int dimension, int tileSize, int maxDimension) { - return Math.min(((dimension + tileSize - 1) / tileSize) * tileSize, maxDimension); - } -} diff --git a/src/com/android/camera/ViewImage.java b/src/com/android/camera/ViewImage.java deleted file mode 100644 index ad27ae3..0000000 --- a/src/com/android/camera/ViewImage.java +++ /dev/null @@ -1,1643 +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.camera; - -import java.util.Random; - -import android.app.Activity; -import android.content.Context; -import android.content.Intent; -import android.content.SharedPreferences; -import android.content.pm.ActivityInfo; -import android.graphics.Bitmap; -import android.graphics.Matrix; -import android.net.Uri; -import android.os.Bundle; -import android.os.Handler; -import android.os.Message; -import android.preference.PreferenceManager; -import android.provider.MediaStore; -import android.util.AttributeSet; -import android.util.Config; -import android.util.Log; -import android.view.GestureDetector; -import android.view.KeyEvent; -import android.view.Menu; -import android.view.MenuItem; -import android.view.MotionEvent; -import android.view.View; -import android.view.Window; -import android.view.WindowManager; -import android.view.animation.AlphaAnimation; -import android.view.animation.Animation; -import android.view.animation.AnimationUtils; -import android.widget.LinearLayout; -import android.widget.Scroller; -import android.widget.Toast; -import android.widget.ZoomRingController; - -import com.android.camera.ImageManager.IImage; - -public class ViewImage extends Activity implements View.OnClickListener -{ - static final String TAG = "ViewImage"; - private ImageGetter mGetter; - - static final boolean sSlideShowHidesStatusBar = true; - - // Choices for what adjacents to load. - static private final int[] sOrder_adjacents = new int[] { 0, 1, -1 }; - static private final int[] sOrder_slideshow = new int[] { 0 }; - - Handler mHandler = new Handler() { - @Override - public void handleMessage(Message msg) { - } - }; - - private Random mRandom = new Random(System.currentTimeMillis()); - private int [] mShuffleOrder; - private boolean mUseShuffleOrder = false; - private boolean mSlideShowLoop = false; - - private static final int MODE_NORMAL = 1; - private static final int MODE_SLIDESHOW = 2; - private int mMode = MODE_NORMAL; - private boolean mFullScreenInNormalMode; - private boolean mShowActionIcons; - private View mActionIconPanel; - private View mShutterButton; - - private boolean mSortAscending = false; - private int mSlideShowInterval; - private int mLastSlideShowImage; - private boolean mFirst = true; - private int mCurrentPosition = 0; - private boolean mLayoutComplete = false; - - // represents which style animation to use - private int mAnimationIndex; - private Animation [] mSlideShowInAnimation; - private Animation [] mSlideShowOutAnimation; - - private SharedPreferences mPrefs; - - private View mNextImageView, mPrevImageView; - private Animation mHideNextImageViewAnimation = new AlphaAnimation(1F, 0F); - private Animation mHidePrevImageViewAnimation = new AlphaAnimation(1F, 0F); - private Animation mShowNextImageViewAnimation = new AlphaAnimation(0F, 1F); - private Animation mShowPrevImageViewAnimation = new AlphaAnimation(0F, 1F); - - - static final int sPadding = 20; - static final int sHysteresis = sPadding * 2; - static final int sBaseScrollDuration = 1000; // ms - - private ImageManager.IImageList mAllImages; - - private int mSlideShowImageCurrent = 0; - private ImageViewTouch [] mSlideShowImageViews = new ImageViewTouch[2]; - - - // Array of image views. The center view is the one the user is focused - // on. The one at the zeroth position and the second position reflect - // the images to the left/right of the center image. - private ImageViewTouch[] mImageViews = new ImageViewTouch[3]; - - // Container for the three image views. This guy can be "scrolled" - // to reveal the image prior to and after the center image. - private ScrollHandler mScroller; - - private MenuHelper.MenuItemsResult mImageMenuRunnable; - - private Runnable mDismissOnScreenControlsRunnable; - private boolean mCameraReviewMode; - - public ViewImage() { - } - - private void updateNextPrevControls() { - boolean showPrev = mCurrentPosition > 0; - boolean showNext = mCurrentPosition < mAllImages.getCount() - 1; - - boolean prevIsVisible = mPrevImageView.getVisibility() == View.VISIBLE; - boolean nextIsVisible = mNextImageView.getVisibility() == View.VISIBLE; - - if (showPrev && !prevIsVisible) { - Animation a = mShowPrevImageViewAnimation; - a.setDuration(500); - a.startNow(); - mPrevImageView.setAnimation(a); - mPrevImageView.setVisibility(View.VISIBLE); - } else if (!showPrev && prevIsVisible) { - Animation a = mHidePrevImageViewAnimation; - a.setDuration(500); - a.startNow(); - mPrevImageView.setAnimation(a); - mPrevImageView.setVisibility(View.GONE); - } - - if (showNext && !nextIsVisible) { - Animation a = mShowNextImageViewAnimation; - a.setDuration(500); - a.startNow(); - mNextImageView.setAnimation(a); - mNextImageView.setVisibility(View.VISIBLE); - } else if (!showNext && nextIsVisible) { - Animation a = mHideNextImageViewAnimation; - a.setDuration(500); - a.startNow(); - mNextImageView.setAnimation(a); - mNextImageView.setVisibility(View.GONE); - } - } - - private void showOnScreenControls() { - updateNextPrevControls(); - scheduleDismissOnScreenControls(); - } - - @Override - public boolean dispatchTouchEvent(MotionEvent m) { - boolean sup = super.dispatchTouchEvent(m); - if (sup == false) { - if (mMode == MODE_SLIDESHOW) { - mSlideShowImageViews[mSlideShowImageCurrent].handleTouchEvent(m); - } else if (mMode == MODE_NORMAL){ - mImageViews[1].handleTouchEvent(m); - } - return true; - } - return true; - } - - private void scheduleDismissOnScreenControls() { - mHandler.removeCallbacks(mDismissOnScreenControlsRunnable); - mHandler.postDelayed(mDismissOnScreenControlsRunnable, 1500); - } - - public void setupDismissOnScreenControlRunnable() { - mDismissOnScreenControlsRunnable = new Runnable() { - public void run() { - if (!mShowActionIcons) { - if (mNextImageView.getVisibility() == View.VISIBLE) { - Animation a = mHideNextImageViewAnimation; - a.setDuration(500); - a.startNow(); - mNextImageView.setAnimation(a); - mNextImageView.setVisibility(View.INVISIBLE); - } - - if (mPrevImageView.getVisibility() == View.VISIBLE) { - Animation a = mHidePrevImageViewAnimation; - a.setDuration(500); - a.startNow(); - mPrevImageView.setAnimation(a); - mPrevImageView.setVisibility(View.INVISIBLE); - } - } - } - }; - } - - private boolean isPickIntent() { - String action = getIntent().getAction(); - return (Intent.ACTION_PICK.equals(action) || Intent.ACTION_GET_CONTENT.equals(action)); - } - - private static final boolean sUseBounce = false; - private static final boolean sAnimateTransitions = false; - - static public class ImageViewTouch extends ImageViewTouchBase { - private ViewImage mViewImage; - private boolean mEnableTrackballScroll; - private GestureDetector mGestureDetector; - - private static int TOUCH_AREA_WIDTH = 60; - - // Returns current scale step (numbered from 0 to 10). - private int getCurrentStep() { - float s = getScale(); - float b = sScaleRate; - int step = (int)Math.round(Math.log(s) / Math.log(b)); - return Math.max(0, Math.min(10, step)); - } - - // Returns the max scale step this image can use. - private int getMaxStep() { - float s = maxZoom(); - float b = sScaleRate; - int step = (int)Math.ceil(Math.log(s) / Math.log(b)); - return Math.max(0, Math.min(10, step)); - } - - // The setup we use here is to have 12 steps (only 0 to 10 are used), - // each separated by angle PI/6. We allow clockwise rotation (zoom-in) - // from the beginning position only. So we set counter clockwise bound - // to 0 and set clockwise bound to (2 - N/6) * PI. (clockwise angle - // is negative, and we need to mod 2*PI for the API to work.) - private void setZoomRingBounds() { - int max_step = getMaxStep(); - float max_angle = (2 - max_step / 6F) * (float)Math.PI; - mZoomRingController.setResetThumbAutomatically(false); - mZoomRingController.setThumbClockwiseBound(max_angle); - mZoomRingController.setThumbCounterclockwiseBound(0); - } - - // The zoom ring is set to visible by a double tap. - private ZoomRingController mZoomRingController; - private ZoomRingController.OnZoomListener mZoomListener = - new ZoomRingController.OnZoomListener() { - public void onCenter(int x, int y) { - } - - public void onBeginPan() { - } - - public boolean onPan(int deltaX, int deltaY) { - postTranslate(-deltaX, -deltaY, sUseBounce); - ImageViewTouch.this.center(true, true, false); - return true; - } - - public void onEndPan() { - } - - // The clockwise angle is negative, so we need to mod 2*PI - private float stepToAngle(int step) { - float angle = step * (float)Math.PI / 6; - angle = (float)Math.PI * 2 - angle; - return angle; - } - - private int angleToStep(double angle) { - angle = Math.PI * 2 - angle; - int step = (int)Math.round(angle / (Math.PI / 6)); - return step; - } - - public void onVisibilityChanged(boolean visible) { - if (visible) { - int step = getCurrentStep(); - float angle = stepToAngle(step); - mZoomRingController.setThumbAngle(angle); - } - } - - public void onBeginDrag() { - setZoomRingBounds(); - } - - public void onEndDrag() { - } - - public boolean onDragZoom(int deltaZoomLevel, int centerX, - int centerY, float startAngle, float curAngle) { - setZoomRingBounds(); - int deltaStep = angleToStep(curAngle) - getCurrentStep(); - if ((deltaZoomLevel > 0) && (deltaStep < 0)) return false; - if ((deltaZoomLevel < 0) && (deltaStep > 0)) return false; - if ((deltaZoomLevel == 0) || (deltaStep == 0)) return false; - - float oldScale = getScale(); - - // First move centerX/centerY to the center of the view. - int deltaX = getWidth() / 2 - centerX; - int deltaY = getHeight() / 2 - centerY; - panBy(deltaX, deltaY); - - // Do zoom in/out. - while (deltaStep > 0) { - zoomIn(); - deltaStep--; - } - while (deltaStep < 0) { - zoomOut(); - deltaStep++; - } - - // Reverse the first centering. - panBy(-deltaX, -deltaY); - - // Return true if the zoom succeeds. - return (oldScale != getScale()); - } - - public void onSimpleZoom(boolean zoomIn) { - if (zoomIn) zoomIn(); - else zoomOut(); - } - }; - - public ImageViewTouch(Context context) { - super(context); - setup(context); - } - - public ImageViewTouch(Context context, AttributeSet attrs) { - super(context, attrs); - setup(context); - } - - private void setup(Context context) { - mViewImage = (ViewImage) context; - mZoomRingController = new ZoomRingController(context, this); - mZoomRingController.setCallback(mZoomListener); - mGestureDetector = new GestureDetector(new MyGestureListener()); - mGestureDetector.setOnDoubleTapListener(new MyDoubleTapListener()); - } - - public void setEnableTrackballScroll(boolean enable) { - mEnableTrackballScroll = enable; - } - - protected void postTranslate(float dx, float dy, boolean bounceOK) { - super.postTranslate(dx, dy); - if (dx != 0F || dy != 0F) - mViewImage.showOnScreenControls(); - - if (!sUseBounce) { - center(true, false, false); - } - } - - protected ScrollHandler scrollHandler() { - return mViewImage.mScroller; - } - - public boolean handleTouchEvent(MotionEvent m) { - return mGestureDetector.onTouchEvent(m); - } - - private class MyGestureListener extends GestureDetector.SimpleOnGestureListener { - public boolean onScroll(MotionEvent e1, MotionEvent e2, - float distanceX, float distanceY) { - if (getScale() > 1F) { - postTranslate(-distanceX, -distanceY, sUseBounce); - ImageViewTouch.this.center(true, true, false); - } - return true; - } - } - - private class MyDoubleTapListener implements GestureDetector.OnDoubleTapListener { - // On single tap, we show the arrows. We also change to the - // prev/next image if the user taps on the left/right region. - public boolean onSingleTapConfirmed(MotionEvent e) { - ViewImage viewImage = mViewImage; - - int viewWidth = getWidth(); - int x = (int) e.getX(); - int y = (int) e.getY(); - if (x < TOUCH_AREA_WIDTH) { - viewImage.moveNextOrPrevious(-1); - } else if (x > viewWidth - TOUCH_AREA_WIDTH) { - viewImage.moveNextOrPrevious(1); - } - - viewImage.setMode(MODE_NORMAL); - viewImage.showOnScreenControls(); - - return true; - } - - // On double tap, we show the zoom ring control. - public boolean onDoubleTapEvent(MotionEvent e) { - mViewImage.setMode(MODE_NORMAL); - mZoomRingController.setVisible(true); - return true; - } - } - - @Override - public boolean onKeyDown(int keyCode, KeyEvent event) - { - // Don't respond to arrow keys if trackball scrolling is not enabled - if (!mEnableTrackballScroll) { - if ((keyCode >= KeyEvent.KEYCODE_DPAD_UP) - && (keyCode <= KeyEvent.KEYCODE_DPAD_RIGHT)) { - return super.onKeyDown(keyCode, event); - } - } - - int current = mViewImage.mCurrentPosition; - - int nextImagePos = -2; // default no next image - try { - switch (keyCode) { - case KeyEvent.KEYCODE_DPAD_CENTER: { - if (mViewImage.isPickIntent()) { - ImageManager.IImage img = mViewImage.mAllImages.getImageAt(mViewImage.mCurrentPosition); - mViewImage.setResult(RESULT_OK, - new Intent().setData(img.fullSizeImageUri())); - mViewImage.finish(); - } - break; - } - case KeyEvent.KEYCODE_DPAD_LEFT: { - panBy(sPanRate, 0); - int maxOffset = (current == 0) ? 0 : sHysteresis; - if (getScale() <= 1F || isShiftedToNextImage(true, maxOffset)) { - nextImagePos = current - 1; - } else { - center(true, false, true); - } - return true; - } - case KeyEvent.KEYCODE_DPAD_RIGHT: { - panBy(-sPanRate, 0); - int maxOffset = (current == mViewImage.mAllImages.getCount()-1) ? 0 : sHysteresis; - if (getScale() <= 1F || isShiftedToNextImage(false, maxOffset)) { - nextImagePos = current + 1; - } else { - center(true, false, true); - } - return true; - } - case KeyEvent.KEYCODE_DPAD_UP: { - panBy(0, sPanRate); - center(true, false, false); - return true; - } - case KeyEvent.KEYCODE_DPAD_DOWN: { - panBy(0, -sPanRate); - center(true, false, false); - return true; - } - case KeyEvent.KEYCODE_DEL: - MenuHelper.deletePhoto(mViewImage, mViewImage.mDeletePhotoRunnable); - break; - } - } finally { - if (nextImagePos >= 0 && nextImagePos < mViewImage.mAllImages.getCount()) { - synchronized (mViewImage) { - mViewImage.setMode(MODE_NORMAL); - mViewImage.setImage(nextImagePos); - } - } else if (nextImagePos != -2) { - center(true, true, false); - } - } - - return super.onKeyDown(keyCode, event); - } - - protected boolean isShiftedToNextImage(boolean left, int maxOffset) { - boolean retval; - Bitmap bitmap = mBitmapDisplayed; - Matrix m = getImageViewMatrix(); - if (left) { - float [] t1 = new float[] { 0, 0 }; - m.mapPoints(t1); - retval = t1[0] > maxOffset; - } else { - int width = bitmap != null ? bitmap.getWidth() : getWidth(); - float [] t1 = new float[] { width, 0 }; - m.mapPoints(t1); - retval = t1[0] + maxOffset < getWidth(); - } - return retval; - } - - protected void scrollX(int deltaX) { - scrollHandler().scrollBy(deltaX, 0); - } - - protected int getScrollOffset() { - return scrollHandler().getScrollX(); - } - - @Override - protected void onDetachedFromWindow() { - mZoomRingController.setVisible(false); - } - - } - - static class ScrollHandler extends LinearLayout { - private Runnable mFirstLayoutCompletedCallback = null; - private Scroller mScrollerHelper; - private int mWidth = -1; - - public ScrollHandler(Context context) { - super(context); - mScrollerHelper = new Scroller(context); - } - - public ScrollHandler(Context context, AttributeSet attrs) { - super(context, attrs); - mScrollerHelper = new Scroller(context); - } - - public void setLayoutCompletedCallback(Runnable r) { - mFirstLayoutCompletedCallback = r; - } - - public void startScrollTo(int newX, int newY) { - int oldX = getScrollX(); - int oldY = getScrollY(); - - int deltaX = newX - oldX; - int deltaY = newY - oldY; - - if (mWidth == -1) { - mWidth = findViewById(R.id.image2).getWidth(); - } - int viewWidth = mWidth; - - int duration = viewWidth > 0 - ? sBaseScrollDuration * Math.abs(deltaX) / viewWidth - : 0; - mScrollerHelper.startScroll(oldX, oldY, deltaX, deltaY, duration); - invalidate(); - } - - @Override - public void computeScroll() { - if (mScrollerHelper.computeScrollOffset()) { - scrollTo(mScrollerHelper.getCurrX(), mScrollerHelper.getCurrY()); - postInvalidate(); // So we draw again - } - } - - @Override - protected void onLayout(boolean changed, int left, int top, int right, int bottom) { - int width = right - left; - int x = 0; - for (View v : new View[] { - findViewById(R.id.image1), - findViewById(R.id.image2), - findViewById(R.id.image3) }) { - v.layout(x, 0, x + width, bottom); - x += (width + sPadding); - } - - findViewById(R.id.padding1).layout(width, 0, width + sPadding, bottom); - findViewById(R.id.padding2).layout(width+sPadding+width, 0, width+sPadding+width+sPadding, bottom); - - if (changed) { - if (mFirstLayoutCompletedCallback != null) { - mFirstLayoutCompletedCallback.run(); - } - } - } - } - - private void animateScrollTo(int xNew, int yNew) { - mScroller.startScrollTo(xNew, yNew); - } - - @Override - public boolean onCreateOptionsMenu(Menu menu) - { - super.onCreateOptionsMenu(menu); - - if (! mCameraReviewMode) { - MenuItem item = menu.add(Menu.CATEGORY_SECONDARY, 203, 0, R.string.slide_show); - item.setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - setMode(MODE_SLIDESHOW); - mLastSlideShowImage = mCurrentPosition; - loadNextImage(mCurrentPosition, 0, true); - return true; - } - }); - item.setIcon(android.R.drawable.ic_menu_slideshow); - } - - final SelectedImageGetter selectedImageGetter = new SelectedImageGetter() { - public ImageManager.IImage getCurrentImage() { - return mAllImages.getImageAt(mCurrentPosition); - } - - public Uri getCurrentImageUri() { - return mAllImages.getImageAt(mCurrentPosition).fullSizeImageUri(); - } - }; - - mImageMenuRunnable = MenuHelper.addImageMenuItems( - menu, - MenuHelper.INCLUDE_ALL, - true, - ViewImage.this, - mHandler, - mDeletePhotoRunnable, - new MenuHelper.MenuInvoker() { - public void run(MenuHelper.MenuCallback cb) { - setMode(MODE_NORMAL); - cb.run(selectedImageGetter.getCurrentImageUri(), selectedImageGetter.getCurrentImage()); - for (ImageViewTouchBase iv: mImageViews) { - iv.recycleBitmaps(); - iv.setImageBitmap(null, true); - } - setImage(mCurrentPosition); - } - }); - - if (true) { - MenuItem item = menu.add(Menu.CATEGORY_SECONDARY, 203, 1000, R.string.camerasettings); - item.setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - Intent preferences = new Intent(); - preferences.setClass(ViewImage.this, GallerySettings.class); - startActivity(preferences); - return true; - } - }); - item.setAlphabeticShortcut('p'); - item.setIcon(android.R.drawable.ic_menu_preferences); - } - - // Hidden menu just so the shortcut will bring up the zoom controls - menu.add(Menu.CATEGORY_SECONDARY, 203, 0, R.string.camerasettings) // the string resource is a placeholder - .setOnMenuItemClickListener(new MenuItem.OnMenuItemClickListener() { - public boolean onMenuItemClick(MenuItem item) { - showOnScreenControls(); - return true; - } - }) - .setAlphabeticShortcut('z') - .setVisible(false); - - - return true; - } - - protected Runnable mDeletePhotoRunnable = new Runnable() { - public void run() { - mAllImages.removeImageAt(mCurrentPosition); - if (mAllImages.getCount() == 0) { - finish(); - } else { - if (mCurrentPosition == mAllImages.getCount()) { - mCurrentPosition -= 1; - } - } - for (ImageViewTouchBase iv: mImageViews) { - iv.setImageBitmapResetBase(null, true, true); - } - setImage(mCurrentPosition); - } - }; - - @Override - public boolean onPrepareOptionsMenu(Menu menu) - { - super.onPrepareOptionsMenu(menu); - setMode(MODE_NORMAL); - - if (mImageMenuRunnable != null) { - mImageMenuRunnable.gettingReadyToOpen(menu, mAllImages.getImageAt(mCurrentPosition)); - } - - menu.findItem(MenuHelper.MENU_IMAGE_SHARE).setEnabled(isCurrentImageShareable()); - - return true; - } - - private boolean isCurrentImageShareable() { - IImage image = mAllImages.getImageAt(mCurrentPosition); - if (image != null){ - Uri uri = image.fullSizeImageUri(); - String fullUri = uri.toString(); - return fullUri.startsWith(MediaStore.Images.Media.INTERNAL_CONTENT_URI.toString()) || - fullUri.startsWith(MediaStore.Images.Media.EXTERNAL_CONTENT_URI.toString()); - } - return true; - } - - @Override - public void onConfigurationChanged(android.content.res.Configuration newConfig) { - super.onConfigurationChanged(newConfig); - if (newConfig.orientation != getResources().getConfiguration().orientation) { - for (ImageViewTouchBase iv: mImageViews) { - iv.setImageBitmapResetBase(null, false, true); - } - MenuHelper.requestOrientation(this, mPrefs); - } - } - - @Override - public boolean onMenuItemSelected(int featureId, MenuItem item) { - boolean b = super.onMenuItemSelected(featureId, item); - if (mImageMenuRunnable != null) - mImageMenuRunnable.aboutToCall(item, mAllImages.getImageAt(mCurrentPosition)); - return b; - } - - /* - * Here's the loading strategy. For any given image, load the thumbnail - * into memory and post a callback to display the resulting bitmap. - * - * Then proceed to load the full image bitmap. Three things can - * happen at this point: - * - * 1. the image fails to load because the UI thread decided - * to move on to a different image. This "cancellation" happens - * by virtue of the UI thread closing the stream containing the - * image being decoded. BitmapFactory.decodeStream returns null - * in this case. - * - * 2. the image loaded successfully. At that point we post - * a callback to the UI thread to actually show the bitmap. - * - * 3. when the post runs it checks to see if the image that was - * loaded is still the one we want. The UI may have moved on - * to some other image and if so we just drop the newly loaded - * bitmap on the floor. - */ - - interface ImageGetterCallback { - public void imageLoaded(int pos, int offset, Bitmap bitmap, boolean isThumb); - public boolean wantsThumbnail(int pos, int offset); - public boolean wantsFullImage(int pos, int offset); - public int fullImageSizeToUse(int pos, int offset); - public void completed(boolean wasCanceled); - public int [] loadOrder(); - } - - class ImageGetter { - // The thread which does the work. - private Thread mGetterThread; - - // The base position that's being retrieved. The actual images retrieved - // are this base plus each of the offets. - private int mCurrentPosition = -1; - - // The callback to invoke for each image. - private ImageGetterCallback mCB; - - // This is the loader cancelable that gets set while we're loading an image. - // If we change position we can cancel the current load using this. - private ImageManager.IGetBitmap_cancelable mLoad; - - // True if we're canceling the current load. - private boolean mCancelCurrent = false; - - // True when the therad should exit. - private boolean mDone = false; - - // True when the loader thread is waiting for work. - private boolean mReady = false; - - private void cancelCurrent() { - synchronized (this) { - if (!mReady) { - mCancelCurrent = true; - ImageManager.IGetBitmap_cancelable load = mLoad; - if (load != null) { - if (Config.LOGV) - Log.v(TAG, "canceling load object"); - load.cancel(); - } - mCancelCurrent = false; - } - } - } - - public ImageGetter() { - mGetterThread = new Thread(new Runnable() { - - private Runnable callback(final int position, final int offset, final boolean isThumb, final Bitmap bitmap) { - return new Runnable() { - public void run() { - // check for inflight callbacks that aren't applicable any longer - // before delivering them - if (!isCanceled() && position == mCurrentPosition) { - mCB.imageLoaded(position, offset, bitmap, isThumb); - } else { - if (bitmap != null) - bitmap.recycle(); - } - } - }; - } - - private Runnable completedCallback(final boolean wasCanceled) { - return new Runnable() { - public void run() { - mCB.completed(wasCanceled); - } - }; - } - - public void run() { - int lastPosition = -1; - while (!mDone) { - synchronized (ImageGetter.this) { - mReady = true; - ImageGetter.this.notify(); - - if (mCurrentPosition == -1 || lastPosition == mCurrentPosition) { - try { - ImageGetter.this.wait(); - } catch (InterruptedException ex) { - continue; - } - } - - lastPosition = mCurrentPosition; - mReady = false; - } - - if (lastPosition != -1) { - int imageCount = mAllImages.getCount(); - - int [] order = mCB.loadOrder(); - for (int i = 0; i < order.length; i++) { - int offset = order[i]; - int imageNumber = lastPosition + offset; - if (imageNumber >= 0 && imageNumber < imageCount) { - ImageManager.IImage image = mAllImages.getImageAt(lastPosition + offset); - if (image == null || isCanceled()) { - break; - } - if (mCB.wantsThumbnail(lastPosition, offset)) { - if (Config.LOGV) - Log.v(TAG, "starting THUMBNAIL load at offset " + offset); - Bitmap b = image.thumbBitmap(); - mHandler.post(callback(lastPosition, offset, true, b)); - } - } - } - - for (int i = 0; i < order.length; i++) { - int offset = order[i]; - int imageNumber = lastPosition + offset; - if (imageNumber >= 0 && imageNumber < imageCount) { - ImageManager.IImage image = mAllImages.getImageAt(lastPosition + offset); - if (mCB.wantsFullImage(lastPosition, offset)) { - if (Config.LOGV) - Log.v(TAG, "starting FULL IMAGE load at offset " + offset); - int sizeToUse = mCB.fullImageSizeToUse(lastPosition, offset); - if (image != null && !isCanceled()) { - mLoad = image.fullSizeBitmap_cancelable(sizeToUse); - } - if (mLoad != null) { - long t1; - if (Config.LOGV) t1 = System.currentTimeMillis(); - - Bitmap b = null; - try { - b = mLoad.get(); - } catch (OutOfMemoryError e) { - Log.e(TAG, "couldn't load full size bitmap for " + ""); - } - if (Config.LOGV && b != null) { - long t2 = System.currentTimeMillis(); - Log.v(TAG, "loading full image for " + image.fullSizeImageUri() - + " with requested size " + sizeToUse - + " took " + (t2-t1) - + " and returned a bitmap with size " - + b.getWidth() + " / " + b.getHeight()); - } - - mLoad = null; - if (b != null) { - if (isCanceled()) { - b.recycle(); - } else { - mHandler.post(callback(lastPosition, offset, false, b)); - } - } - } - } - } - } - mHandler.post(completedCallback(isCanceled())); - } - } - } - }); - mGetterThread.setName("ImageGettter"); - mGetterThread.start(); - } - - private boolean isCanceled() { - synchronized (this) { - return mCancelCurrent; - } - } - - public void setPosition(int position, ImageGetterCallback cb) { - synchronized (this) { - if (!mReady) { - try { - mCancelCurrent = true; - ImageManager.IGetBitmap_cancelable load = mLoad; - if (load != null) { - load.cancel(); - } - // if the thread is waiting before loading the full size - // image then this will free it up - ImageGetter.this.notify(); - ImageGetter.this.wait(); - mCancelCurrent = false; - } catch (InterruptedException ex) { - // not sure what to do here - } - } - } - - mCurrentPosition = position; - mCB = cb; - - synchronized (this) { - ImageGetter.this.notify(); - } - } - - public void stop() { - synchronized (this) { - mDone = true; - ImageGetter.this.notify(); - } - try { - mGetterThread.join(); - } catch (InterruptedException ex) { - - } - } - } - - private void setImage(int pos) { - if (!mLayoutComplete) { - return; - } - - final boolean left = mCurrentPosition > pos; - - mCurrentPosition = pos; - - ImageViewTouchBase current = mImageViews[1]; - current.mSuppMatrix.reset(); - current.setImageMatrix(current.getImageViewMatrix()); - - if (false) { - Log.v(TAG, "before..."); - for (ImageViewTouchBase ivtb : mImageViews) - ivtb.dump(); - } - - if (!mFirst) { - if (left) { - mImageViews[2].copyFrom(mImageViews[1]); - mImageViews[1].copyFrom(mImageViews[0]); - } else { - mImageViews[0].copyFrom(mImageViews[1]); - mImageViews[1].copyFrom(mImageViews[2]); - } - } - if (false) { - Log.v(TAG, "after copy..."); - for (ImageViewTouchBase ivtb : mImageViews) - ivtb.dump(); - } - - for (ImageViewTouchBase ivt: mImageViews) { - ivt.mIsZooming = false; - } - int width = mImageViews[1].getWidth(); - int from; - int to = width + sPadding; - if (mFirst) { - from = to; - mFirst = false; - } else { - from = left ? (width + sPadding) + mScroller.getScrollX() - : mScroller.getScrollX() - (width + sPadding); - } - - if (sAnimateTransitions) { - mScroller.scrollTo(from, 0); - animateScrollTo(to, 0); - } else { - mScroller.scrollTo(to, 0); - } - - ImageGetterCallback cb = new ImageGetterCallback() { - public void completed(boolean wasCanceled) { - if (!mShowActionIcons) { - mImageViews[1].setFocusableInTouchMode(true); - mImageViews[1].requestFocus(); - } - } - - public boolean wantsThumbnail(int pos, int offset) { - ImageViewTouchBase ivt = mImageViews[1 + offset]; - return ivt.mThumbBitmap == null; - } - - public boolean wantsFullImage(int pos, int offset) { - ImageViewTouchBase ivt = mImageViews[1 + offset]; - if (ivt.mBitmapDisplayed != null && !ivt.mBitmapIsThumbnail) { - return false; - } - if (offset != 0) { - return false; - } - return true; - } - - public int fullImageSizeToUse(int pos, int offset) { - // TODO - // this number should be bigger so that we can zoom. we may need to - // get fancier and read in the fuller size image as the user starts - // to zoom. use -1 to get the full full size image. - // for now use 480 so we don't run out of memory - final int imageViewSize = 480; - return imageViewSize; - } - - public int [] loadOrder() { - return sOrder_adjacents; - } - - public void imageLoaded(int pos, int offset, Bitmap bitmap, boolean isThumb) { - ImageViewTouchBase ivt = mImageViews[1 + offset]; - ivt.setImageBitmapResetBase(bitmap, isThumb, isThumb); - } - }; - - // Could be null if we're stopping a slide show in the course of pausing - if (mGetter != null) { - mGetter.setPosition(pos, cb); - } - showOnScreenControls(); - } - - @Override - public void onCreate(Bundle instanceState) - { - super.onCreate(instanceState); - Intent intent = getIntent(); - mCameraReviewMode = intent.getBooleanExtra("com.android.camera.ReviewMode", false); - mFullScreenInNormalMode = intent.getBooleanExtra(MediaStore.EXTRA_FULL_SCREEN, true); - mShowActionIcons = intent.getBooleanExtra(MediaStore.EXTRA_SHOW_ACTION_ICONS, false); - - mPrefs = PreferenceManager.getDefaultSharedPreferences(this); - - setDefaultKeyMode(DEFAULT_KEYS_SHORTCUT); - requestWindowFeature(Window.FEATURE_NO_TITLE); - setContentView(R.layout.viewimage); - - mImageViews[0] = (ImageViewTouch) findViewById(R.id.image1); - mImageViews[1] = (ImageViewTouch) findViewById(R.id.image2); - mImageViews[2] = (ImageViewTouch) findViewById(R.id.image3); - - for(ImageViewTouch v : mImageViews) { - v.setEnableTrackballScroll(!mShowActionIcons); - } - - mScroller = (ScrollHandler)findViewById(R.id.scroller); - makeGetter(); - - mAnimationIndex = -1; - - mSlideShowInAnimation = new Animation[] { - makeInAnimation(R.anim.transition_in), - makeInAnimation(R.anim.slide_in), - makeInAnimation(R.anim.slide_in_vertical), - }; - - mSlideShowOutAnimation = new Animation[] { - makeOutAnimation(R.anim.transition_out), - makeOutAnimation(R.anim.slide_out), - makeOutAnimation(R.anim.slide_out_vertical), - }; - - mSlideShowImageViews[0] = (ImageViewTouch) findViewById(R.id.image1_slideShow); - mSlideShowImageViews[1] = (ImageViewTouch) findViewById(R.id.image2_slideShow); - for (ImageViewTouch v : mSlideShowImageViews) { - v.setImageBitmapResetBase(null, true, true); - v.setVisibility(View.INVISIBLE); - v.setEnableTrackballScroll(!mShowActionIcons); - } - - mActionIconPanel = findViewById(R.id.action_icon_panel); - { - int[] pickIds = {R.id.attach, R.id.cancel}; - int[] normalIds = {R.id.gallery, R.id.setas, R.id.share, R.id.discard}; - int[] hideIds = pickIds; - int[] connectIds = normalIds; - if (isPickIntent()) { - hideIds = normalIds; - connectIds = pickIds; - } - for(int id : hideIds) { - mActionIconPanel.findViewById(id).setVisibility(View.GONE); - } - for(int id : connectIds) { - View view = mActionIconPanel.findViewById(id); - view.setOnClickListener(this); - Animation animation = new AlphaAnimation(0F, 1F); - animation.setDuration(500); - view.setAnimation(animation); - } - } - mShutterButton = findViewById(R.id.shutter_button); - mShutterButton.setOnClickListener(this); - - Uri uri = getIntent().getData(); - - if (Config.LOGV) - Log.v(TAG, "uri is " + uri); - if (instanceState != null) { - if (instanceState.containsKey("uri")) { - uri = Uri.parse(instanceState.getString("uri")); - } - } - if (uri == null) { - finish(); - return; - } - init(uri); - - Bundle b = getIntent().getExtras(); - - boolean slideShow = b != null ? b.getBoolean("slideshow", false) : false; - if (slideShow) { - setMode(MODE_SLIDESHOW); - loadNextImage(mCurrentPosition, 0, true); - } else { - if (mFullScreenInNormalMode) { - getWindow().addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN); - } - if (mShowActionIcons) { - mActionIconPanel.setVisibility(View.VISIBLE); - mShutterButton.setVisibility(View.VISIBLE); - } - } - - setupDismissOnScreenControlRunnable(); - - mNextImageView = findViewById(R.id.next_image); - mPrevImageView = findViewById(R.id.prev_image); - mNextImageView.setOnClickListener(this); - mPrevImageView.setOnClickListener(this); - - if (mShowActionIcons) { - mNextImageView.setFocusable(true); - mPrevImageView.setFocusable(true); - } - - setOrientation(); - - // Show a tutorial for the new zoom interaction (the method ensure we only show it once) - ZoomRingController.showZoomTutorialOnce(this); - } - - private void setOrientation() { - Intent intent = getIntent(); - if (intent.hasExtra(MediaStore.EXTRA_SCREEN_ORIENTATION)) { - int orientation = intent.getIntExtra(MediaStore.EXTRA_SCREEN_ORIENTATION, - ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED); - if (orientation != getRequestedOrientation()) { - setRequestedOrientation(orientation); - } - } else { - MenuHelper.requestOrientation(this, mPrefs); - } - } - - private Animation makeInAnimation(int id) { - Animation inAnimation = AnimationUtils.loadAnimation(this, id); - return inAnimation; - } - - private Animation makeOutAnimation(int id) { - Animation outAnimation = AnimationUtils.loadAnimation(this, id); - return outAnimation; - } - - private void setMode(int mode) { - if (mMode == mode) { - return; - } - - findViewById(R.id.slideShowContainer).setVisibility(mode == MODE_SLIDESHOW ? View.VISIBLE : View.GONE); - findViewById(R.id.abs) .setVisibility(mode == MODE_NORMAL ? View.VISIBLE : View.GONE); - - Window win = getWindow(); - mMode = mode; - if (mode == MODE_SLIDESHOW) { - win.addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN - | WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON); - if (sSlideShowHidesStatusBar) { - win.addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN); - } - for (ImageViewTouchBase ivt: mImageViews) { - ivt.clear(); - } - mActionIconPanel.setVisibility(View.GONE); - mShutterButton.setVisibility(View.GONE); - - if (false) { - Log.v(TAG, "current is " + this.mSlideShowImageCurrent); - this.mSlideShowImageViews[0].dump(); - this.mSlideShowImageViews[0].dump(); - } - - findViewById(R.id.slideShowContainer).getRootView().requestLayout(); - mUseShuffleOrder = mPrefs.getBoolean("pref_gallery_slideshow_shuffle_key", false); - mSlideShowLoop = mPrefs.getBoolean("pref_gallery_slideshow_repeat_key", false); - try { - mAnimationIndex = Integer.parseInt(mPrefs.getString("pref_gallery_slideshow_transition_key", "0")); - } catch (Exception ex) { - Log.e(TAG, "couldn't parse preference: " + ex.toString()); - mAnimationIndex = 0; - } - try { - mSlideShowInterval = Integer.parseInt(mPrefs.getString("pref_gallery_slideshow_interval_key", "3")) * 1000; - } catch (Exception ex) { - Log.e(TAG, "couldn't parse preference: " + ex.toString()); - mSlideShowInterval = 3000; - } - - if (Config.LOGV) { - Log.v(TAG, "read prefs... shuffle: " + mUseShuffleOrder); - Log.v(TAG, "read prefs... loop: " + mSlideShowLoop); - Log.v(TAG, "read prefs... animidx: " + mAnimationIndex); - Log.v(TAG, "read prefs... interval: " + mSlideShowInterval); - } - - if (mUseShuffleOrder) { - generateShuffleOrder(); - } - } else { - if (Config.LOGV) - Log.v(TAG, "slide show mode off, mCurrentPosition == " + mCurrentPosition); - win.clearFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON); - if (mFullScreenInNormalMode) { - win.addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN); - } else { - win.clearFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN); - } - - if (mGetter != null) - mGetter.cancelCurrent(); - - if (sSlideShowHidesStatusBar) { - win.clearFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN); - } - if (mShowActionIcons) { - mActionIconPanel.setVisibility(View.VISIBLE); - mShutterButton.setVisibility(View.VISIBLE); - } - - ImageViewTouchBase dst = mImageViews[1]; - dst.mLastXTouchPos = -1; - dst.mLastYTouchPos = -1; - - for (ImageViewTouchBase ivt: mSlideShowImageViews) { - ivt.clear(); - } - - mShuffleOrder = null; - - // mGetter null is a proxy for being paused - if (mGetter != null) { - mFirst = true; // don't animate - setImage(mCurrentPosition); - } - } - - // this line shouldn't be necessary but the view hierarchy doesn't - // seem to realize that the window layout changed - mScroller.requestLayout(); - } - - private void generateShuffleOrder() { - if (mShuffleOrder == null || mShuffleOrder.length != mAllImages.getCount()) { - mShuffleOrder = new int[mAllImages.getCount()]; - } - - for (int i = 0; i < mShuffleOrder.length; i++) { - mShuffleOrder[i] = i; - } - - for (int i = mShuffleOrder.length - 1; i > 0; i--) { - int r = mRandom.nextInt(i); - int tmp = mShuffleOrder[r]; - mShuffleOrder[r] = mShuffleOrder[i]; - mShuffleOrder[i] = tmp; - } - } - - private void loadNextImage(final int requestedPos, final long delay, final boolean firstCall) { - if (firstCall && mUseShuffleOrder) { - generateShuffleOrder(); - } - - final long targetDisplayTime = System.currentTimeMillis() + delay; - - ImageGetterCallback cb = new ImageGetterCallback() { - public void completed(boolean wasCanceled) { - } - - public boolean wantsThumbnail(int pos, int offset) { - return true; - } - - public boolean wantsFullImage(int pos, int offset) { - return false; - } - - public int [] loadOrder() { - return sOrder_slideshow; - } - - public int fullImageSizeToUse(int pos, int offset) { - return 480; // TODO compute this - } - - public void imageLoaded(final int pos, final int offset, final Bitmap bitmap, final boolean isThumb) { - long timeRemaining = Math.max(0, targetDisplayTime - System.currentTimeMillis()); - mHandler.postDelayed(new Runnable() { - public void run() { - if (mMode == MODE_NORMAL) { - return; - } - - ImageViewTouchBase oldView = mSlideShowImageViews[mSlideShowImageCurrent]; - - if (++mSlideShowImageCurrent == mSlideShowImageViews.length) { - mSlideShowImageCurrent = 0; - } - - ImageViewTouchBase newView = mSlideShowImageViews[mSlideShowImageCurrent]; - newView.setVisibility(View.VISIBLE); - newView.setImageBitmapResetBase(bitmap, isThumb, isThumb); - newView.bringToFront(); - - int animation = 0; - - if (mAnimationIndex == -1) { - int n = mRandom.nextInt(mSlideShowInAnimation.length); - animation = n; - } else { - animation = mAnimationIndex; - } - - Animation aIn = mSlideShowInAnimation[animation]; - newView.setAnimation(aIn); - newView.setVisibility(View.VISIBLE); - aIn.startNow(); - - Animation aOut = mSlideShowOutAnimation[animation]; - oldView.setVisibility(View.INVISIBLE); - oldView.setAnimation(aOut); - aOut.startNow(); - - mCurrentPosition = requestedPos; - - mHandler.post(new Runnable() { - public void run() { - if (mCurrentPosition == mLastSlideShowImage && !firstCall) { - if (mSlideShowLoop) { - if (mUseShuffleOrder) { - generateShuffleOrder(); - } - } else { - setMode(MODE_NORMAL); - return; - } - } - - if (Config.LOGV) - Log.v(TAG, "mCurrentPosition is now " + mCurrentPosition); - loadNextImage((mCurrentPosition + 1) % mAllImages.getCount(), mSlideShowInterval, false); - } - }); - } - }, timeRemaining); - } - }; - // Could be null if we're stopping a slide show in the course of pausing - if (mGetter != null) { - int pos = requestedPos; - if (mShuffleOrder != null) { - pos = mShuffleOrder[pos]; - } - mGetter.setPosition(pos, cb); - } - } - - private void makeGetter() { - mGetter = new ImageGetter(); - } - - private boolean desiredSortOrder() { - String sortOrder = mPrefs.getString("pref_gallery_sort_key", null); - boolean sortAscending = false; - if (sortOrder != null) { - sortAscending = sortOrder.equals("ascending"); - } - if (mCameraReviewMode) { - // Force left-arrow older pictures, right-arrow newer pictures. - sortAscending = true; - } - return sortAscending; - } - - private void init(Uri uri) { - mSortAscending = desiredSortOrder(); - int sort = mSortAscending ? ImageManager.SORT_ASCENDING : ImageManager.SORT_DESCENDING; - mAllImages = ImageManager.makeImageList(uri, this, sort); - - uri = uri.buildUpon().query(null).build(); - // TODO smarter/faster here please - for (int i = 0; i < mAllImages.getCount(); i++) { - ImageManager.IImage image = mAllImages.getImageAt(i); - if (image.fullSizeImageUri().equals(uri)) { - mCurrentPosition = i; - mLastSlideShowImage = mCurrentPosition; - break; - } - } - } - - @Override - public void onSaveInstanceState(Bundle b) { - super.onSaveInstanceState(b); - ImageManager.IImage image = mAllImages.getImageAt(mCurrentPosition); - - if (image != null){ - Uri uri = image.fullSizeImageUri(); - String bucket = null; - if(getIntent()!= null && getIntent().getData()!=null) - bucket = getIntent().getData().getQueryParameter("bucketId"); - - if(bucket!=null) - uri = uri.buildUpon().appendQueryParameter("bucketId", bucket).build(); - - b.putString("uri", uri.toString()); - } - if (mMode == MODE_SLIDESHOW) - b.putBoolean("slideshow", true); - } - - @Override - public void onResume() - { - super.onResume(); - - // normally this will never be zero but if one "backs" into this - // activity after removing the sdcard it could be zero. in that - // case just "finish" since there's nothing useful that can happen. - if (mAllImages.getCount() == 0) { - finish(); - } - - ImageManager.IImage image = mAllImages.getImageAt(mCurrentPosition); - - if (desiredSortOrder() != mSortAscending) { - init(image.fullSizeImageUri()); - } - - if (mGetter == null) { - makeGetter(); - } - - for (ImageViewTouchBase iv: mImageViews) { - iv.setImageBitmap(null, true); - } - - mFirst = true; - mScroller.setLayoutCompletedCallback(new Runnable() { - public void run() { - mLayoutComplete = true; - setImage(mCurrentPosition); - } - }); - setImage(mCurrentPosition); - - setOrientation(); - } - - @Override - public void onPause() - { - super.onPause(); - - mGetter.cancelCurrent(); - mGetter.stop(); - mGetter = null; - setMode(MODE_NORMAL); - - mAllImages.deactivate(); - - for (ImageViewTouch iv: mImageViews) { - iv.recycleBitmaps(); - iv.setImageBitmap(null, true); - } - - for (ImageViewTouch iv: mSlideShowImageViews) { - iv.recycleBitmaps(); - iv.setImageBitmap(null, true); - } - } - - @Override - public void onStop() { - super.onStop(); - } - - public void onClick(View v) { - switch (v.getId()) { - - case R.id.shutter_button: { - if (mCameraReviewMode) { - finish(); - } else { - MenuHelper.gotoStillImageCapture(this); - } - } - break; - - case R.id.gallery: { - MenuHelper.gotoCameraImageGallery(this); - } - break; - - case R.id.discard: { - if (mCameraReviewMode) { - mDeletePhotoRunnable.run(); - } else { - MenuHelper.deletePhoto(this, mDeletePhotoRunnable); - } - } - break; - - case R.id.share: { - Uri u = mAllImages.getImageAt(mCurrentPosition).fullSizeImageUri(); - Intent intent = new Intent(); - intent.setAction(Intent.ACTION_SEND); - intent.setType("image/jpeg"); - intent.putExtra(Intent.EXTRA_STREAM, u); - try { - startActivity(Intent.createChooser(intent, getText(R.string.sendImage))); - } catch (android.content.ActivityNotFoundException ex) { - Toast.makeText(this, R.string.no_way_to_share_image, Toast.LENGTH_SHORT).show(); - } - } - break; - - case R.id.setas: { - Uri u = mAllImages.getImageAt(mCurrentPosition).fullSizeImageUri(); - Intent intent = new Intent(Intent.ACTION_ATTACH_DATA, u); - try { - startActivity(Intent.createChooser(intent, getText(R.string.setImage))); - } catch (android.content.ActivityNotFoundException ex) { - Toast.makeText(this, R.string.no_way_to_share_video, Toast.LENGTH_SHORT).show(); - } - } - break; - - case R.id.next_image: { - moveNextOrPrevious(1); - } - break; - - case R.id.prev_image: { - moveNextOrPrevious(-1); - } - break; - } - } - - private void moveNextOrPrevious(int delta) { - int nextImagePos = mCurrentPosition + delta; - if ((0 <= nextImagePos) && (nextImagePos < mAllImages.getCount())) { - setImage(nextImagePos); - } - } - - @Override - protected void onActivityResult(int requestCode, int resultCode, Intent data) { - switch (requestCode) { - case MenuHelper.RESULT_COMMON_MENU_CROP: - if (resultCode == RESULT_OK) { - // The CropImage activity passes back the Uri of the cropped image as - // the Action rather than the Data. - Uri dataUri = Uri.parse(data.getAction()); - init(dataUri); - } - break; - } - } -} diff --git a/src/com/android/camera/Wallpaper.java b/src/com/android/camera/Wallpaper.java deleted file mode 100644 index 5c7d0e5..0000000 --- a/src/com/android/camera/Wallpaper.java +++ /dev/null @@ -1,206 +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.camera; - - -import android.app.Activity; -import android.app.ProgressDialog; -import android.content.Context; -import android.content.Intent; -import android.graphics.Bitmap; -import android.graphics.BitmapFactory; -import android.net.Uri; -import android.os.Bundle; -import android.os.Handler; -import android.os.Message; -import android.provider.MediaStore; -import android.util.Log; - -import java.io.IOException; -import java.io.InputStream; -import java.io.File; -import java.io.FileInputStream; -import java.io.FileNotFoundException; - -/** - * Wallpaper picker for the camera application. This just redirects to the standard pick action. - */ -public class Wallpaper extends Activity { - private static final String LOG_TAG = "Camera"; - static final int PHOTO_PICKED = 1; - static final int CROP_DONE = 2; - - static final int SHOW_PROGRESS = 0; - static final int FINISH = 1; - - static final String sDoLaunchIcicle = "do_launch"; - static final String sTempFilePathIcicle = "temp_file_path"; - - private ProgressDialog mProgressDialog = null; - private boolean mDoLaunch = true; - private String mTempFilePath; - - private Handler mHandler = new Handler() { - @Override - public void handleMessage(Message msg) { - switch (msg.what) { - case SHOW_PROGRESS: { - CharSequence c = getText(R.string.wallpaper); - mProgressDialog = ProgressDialog.show(Wallpaper.this, "", c, true, false); - break; - } - - case FINISH: { - closeProgressDialog(); - setResult(RESULT_OK); - finish(); - break; - } - } - } - }; - - static class SetWallpaperThread extends Thread { - private final Bitmap mBitmap; - private final Handler mHandler; - private final Context mContext; - private final File mFile; - - public SetWallpaperThread(Bitmap bitmap, Handler handler, Context context, File file) { - mBitmap = bitmap; - mHandler = handler; - mContext = context; - mFile = file; - } - - @Override - public void run() { - try { - mContext.setWallpaper(mBitmap); - } catch (IOException e) { - Log.e(LOG_TAG, "Failed to set wallpaper.", e); - } finally { - mHandler.sendEmptyMessage(FINISH); - mFile.delete(); - } - } - } - - private synchronized void closeProgressDialog() { - if (mProgressDialog != null) { - mProgressDialog.dismiss(); - mProgressDialog = null; - } - } - - @Override - protected void onCreate(Bundle icicle) { - super.onCreate(icicle); - if (icicle != null) { - mDoLaunch = icicle.getBoolean(sDoLaunchIcicle); - mTempFilePath = icicle.getString(sTempFilePathIcicle); - } - } - - @Override - protected void onSaveInstanceState(Bundle icicle) { - icicle.putBoolean(sDoLaunchIcicle, mDoLaunch); - icicle.putString(sTempFilePathIcicle, mTempFilePath); - } - - @Override - protected void onPause() { - closeProgressDialog(); - super.onPause(); - } - - @Override - protected void onResume() { - super.onResume(); - - if (!mDoLaunch) { - return; - } - Uri imageToUse = getIntent().getData(); - if (imageToUse != null) { - Intent intent = new Intent(); - intent.setClassName("com.android.camera", "com.android.camera.CropImage"); - intent.setData(imageToUse); - formatIntent(intent); - startActivityForResult(intent, CROP_DONE); - } else { - Intent intent = new Intent(Intent.ACTION_GET_CONTENT, null); - intent.setType("image/*"); - intent.putExtra("crop", "true"); - formatIntent(intent); - startActivityForResult(intent, PHOTO_PICKED); - } - } - - protected void formatIntent(Intent intent) { - // TODO: A temporary file is NOT necessary - // The CropImage intent should be able to set the wallpaper directly - // without writing to a file, which we then need to read here to write - // it again as the final wallpaper, this is silly - File f = getFileStreamPath("temp-wallpaper"); - (new File(f.getParent())).mkdirs(); - mTempFilePath = f.toString(); - f.delete(); - - int width = getWallpaperDesiredMinimumWidth(); - int height = getWallpaperDesiredMinimumHeight(); - intent.putExtra("outputX", width); - intent.putExtra("outputY", height); - intent.putExtra("aspectX", width); - intent.putExtra("aspectY", height); - intent.putExtra("scale", true); - intent.putExtra("noFaceDetection", true); - intent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.parse("file:/" + mTempFilePath)); - intent.putExtra("outputFormat", Bitmap.CompressFormat.PNG.name()); - // TODO: we should have an extra called "setWallpaper" to ask CropImage to - // set the cropped image as a wallpaper directly - // This means the SetWallpaperThread should be moved out of this class to CropImage - } - - @Override - protected void onActivityResult(int requestCode, int resultCode, Intent data) { - if ((requestCode == PHOTO_PICKED || requestCode == CROP_DONE) && (resultCode == RESULT_OK) - && (data != null)) { - try { - File tempFile = new File(mTempFilePath); - InputStream s = new FileInputStream(tempFile); - Bitmap bitmap = BitmapFactory.decodeStream(s); - if (bitmap == null) { - Log.e(LOG_TAG, "Failed to set wallpaper. Couldn't get bitmap for path " + mTempFilePath); - } else { - if (android.util.Config.LOGV) - Log.v(LOG_TAG, "bitmap size is " + bitmap.getWidth() + " / " + bitmap.getHeight()); - mHandler.sendEmptyMessage(SHOW_PROGRESS); - new SetWallpaperThread(bitmap, mHandler, this, tempFile).start(); - } - mDoLaunch = false; - } catch (FileNotFoundException ex) { - - } catch (IOException ex) { - - } - } else { - setResult(RESULT_CANCELED); - finish(); - } - } -} diff --git a/tests/Android.mk b/tests/Android.mk deleted file mode 100644 index f5972cb..0000000 --- a/tests/Android.mk +++ /dev/null @@ -1,19 +0,0 @@ -LOCAL_PATH:= $(call my-dir) -include $(CLEAR_VARS) - -# We only want this apk build for tests. -LOCAL_MODULE_TAGS := tests -LOCAL_CERTIFICATE := media - -LOCAL_JAVA_LIBRARIES := android.test.runner - -# Include all test java files. -LOCAL_SRC_FILES := $(call all-java-files-under, src) - -LOCAL_PACKAGE_NAME := CameraTests - -LOCAL_INSTRUMENTATION_FOR := Camera - -include $(BUILD_PACKAGE) - - diff --git a/tests/AndroidManifest.xml b/tests/AndroidManifest.xml deleted file mode 100644 index 1b7abd2..0000000 --- a/tests/AndroidManifest.xml +++ /dev/null @@ -1,34 +0,0 @@ -<?xml version="1.0" encoding="utf-8"?> -<!-- Copyright (C) 2008 The Android Open Source Project - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. ---> - -<manifest xmlns:android="http://schemas.android.com/apk/res/android" - package="com.android.camera.tests"> - - <application> - <uses-library android:name="android.test.runner" /> - </application> - - <instrumentation android:name="CameraLaunchPerformance" - android:targetPackage="com.android.camera" - android:label="Camera Launch Performance"> - </instrumentation> - - <instrumentation android:name=".CameraStressTestRunner" - android:targetPackage="com.android.camera" - android:label="Camera Stress Test InstrumentationRunner"> - </instrumentation> - -</manifest> diff --git a/tests/src/com/android/camera/CameraLaunchPerformance.java b/tests/src/com/android/camera/CameraLaunchPerformance.java deleted file mode 100644 index 8c76f00..0000000 --- a/tests/src/com/android/camera/CameraLaunchPerformance.java +++ /dev/null @@ -1,53 +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.camera.tests; - -import android.app.Activity; -import android.test.LaunchPerformanceBase; -import android.os.Bundle; - -import java.util.Map; - -/** - * Instrumentation class for Camera launch performance testing. - */ -public class CameraLaunchPerformance extends LaunchPerformanceBase { - - public static final String LOG_TAG = "CameraLaunchPerformance"; - - public CameraLaunchPerformance() { - super(); - } - - @Override - public void onCreate(Bundle arguments) { - super.onCreate(arguments); - - mIntent.setClassName(getTargetContext(), "com.android.camera.Camera"); - start(); - } - - /** - * Calls LaunchApp and finish. - */ - @Override - public void onStart() { - super.onStart(); - LaunchApp(); - finish(Activity.RESULT_OK, mResults); - } -} diff --git a/tests/src/com/android/camera/CameraStressTestRunner.java b/tests/src/com/android/camera/CameraStressTestRunner.java deleted file mode 100755 index e34204c..0000000 --- a/tests/src/com/android/camera/CameraStressTestRunner.java +++ /dev/null @@ -1,50 +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.camera.tests; - -import android.test.InstrumentationTestRunner; -import android.test.InstrumentationTestSuite; -import com.android.camera.tests.stress.SwitchPreview; -import com.android.camera.tests.stress.ImageCapture; - -import junit.framework.TestSuite; - - -/** - * Instrumentation Test Runner for all Camera tests. - * - * Running all tests: - * - * adb shell am instrument -w \ - * com.android.camera.tests/.CameraStressTestRunner - */ - -public class CameraStressTestRunner extends InstrumentationTestRunner { - - @Override - public TestSuite getAllTests() { - TestSuite suite = new InstrumentationTestSuite(this); - suite.addTestSuite(SwitchPreview.class); - suite.addTestSuite(ImageCapture.class); - return suite; - } - - @Override - public ClassLoader getLoader() { - return CameraStressTestRunner.class.getClassLoader(); - } -} diff --git a/tests/src/com/android/camera/stress/ImageCapture.java b/tests/src/com/android/camera/stress/ImageCapture.java deleted file mode 100755 index dbb1f64..0000000 --- a/tests/src/com/android/camera/stress/ImageCapture.java +++ /dev/null @@ -1,96 +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.camera.tests.stress; - -import android.app.Activity; -import android.app.Instrumentation; -import android.test.ActivityInstrumentationTestCase2; -import android.util.Log; -import android.view.KeyEvent; -import android.test.suitebuilder.annotation.LargeTest; - -import com.android.camera.Camera; - -/** - * Junit / Instrumentation test case for camera test - * - */ - -public class ImageCapture extends ActivityInstrumentationTestCase2 <Camera> { - private String TAG = "ImageCapture"; - private static final int TOTAL_NUMBER_OF_IMAGECAPTURE = 100; - private static final int TOTAL_NUMBER_OF_VIDEOCAPTURE = 100; - private static final long WAIT_FOR_IMAGE_CAPTURE_TO_BE_TAKEN = 1000; - private static final long WAIT_FOR_VIDEO_CAPTURE_TO_BE_TAKEN = 50000; //50seconds - private static final long WAIT_FOR_PREVIEW = 1000; //1 seconds - - public ImageCapture() { - super("com.android.camera", Camera.class); - } - - @Override - protected void setUp() throws Exception { - getActivity(); - super.setUp(); - } - - @Override - protected void tearDown() throws Exception { - super.tearDown(); - } - - @LargeTest - public void testImageCapture() { - Instrumentation inst = getInstrumentation(); - try { - for (int i = 0; i < TOTAL_NUMBER_OF_IMAGECAPTURE; i++) { - Thread.sleep(WAIT_FOR_IMAGE_CAPTURE_TO_BE_TAKEN); - inst.sendKeyDownUpSync(KeyEvent.KEYCODE_DPAD_UP); - inst.sendKeyDownUpSync(KeyEvent.KEYCODE_DPAD_CENTER); - Thread.sleep(WAIT_FOR_IMAGE_CAPTURE_TO_BE_TAKEN); - } - } catch (Exception e) { - Log.v(TAG, e.toString()); - } - assertTrue("testImageCapture", true); - } - - @LargeTest - public void testVideoCapture() { - Instrumentation inst = getInstrumentation(); - //Switch to the video mode - inst.sendKeyDownUpSync(KeyEvent.KEYCODE_MENU); - inst.sendKeyDownUpSync(KeyEvent.KEYCODE_DPAD_CENTER); - try { - for (int i = 0; i < TOTAL_NUMBER_OF_VIDEOCAPTURE; i++) { - Thread.sleep(WAIT_FOR_PREVIEW); - inst.sendKeyDownUpSync(KeyEvent.KEYCODE_DPAD_UP); - //record an video - inst.sendKeyDownUpSync(KeyEvent.KEYCODE_DPAD_CENTER); - Thread.sleep(WAIT_FOR_VIDEO_CAPTURE_TO_BE_TAKEN); - inst.sendKeyDownUpSync(KeyEvent.KEYCODE_DPAD_CENTER); - Thread.sleep(WAIT_FOR_PREVIEW); - inst.sendKeyDownUpSync(KeyEvent.KEYCODE_DPAD_CENTER); - } - } catch (Exception e) { - Log.v(TAG, e.toString()); - } - assertTrue("testVideoCapture", true); - } - -} - diff --git a/tests/src/com/android/camera/stress/SwitchPreview.java b/tests/src/com/android/camera/stress/SwitchPreview.java deleted file mode 100755 index c00e553..0000000 --- a/tests/src/com/android/camera/stress/SwitchPreview.java +++ /dev/null @@ -1,74 +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.camera.tests.stress; - -import android.app.Activity; -import android.app.Instrumentation; -import android.test.ActivityInstrumentationTestCase2; -import android.util.Log; -import android.view.KeyEvent; -import android.test.suitebuilder.annotation.LargeTest; - -import com.android.camera.Camera; -import com.android.camera.VideoCamera; - -/** - * Junit / Instrumentation test case for camera test - * - */ - -public class SwitchPreview extends ActivityInstrumentationTestCase2 <VideoCamera>{ - private String TAG = "SwitchPreview"; - private static final int TOTAL_NUMBER_OF_SWITCHING = 200; - private static final long WAIT_FOR_PREVIEW = 2000; - - - public SwitchPreview() { - super("com.android.camera", VideoCamera.class); - } - - @Override - protected void setUp() throws Exception { - getActivity(); - super.setUp(); - } - - @Override - protected void tearDown() throws Exception { - getActivity().finish(); - super.tearDown(); - } - - @LargeTest - public void testSwitchMode() { - //Switching the video and the video recorder mode - Instrumentation inst = getInstrumentation(); - try{ - for (int i=0; i< TOTAL_NUMBER_OF_SWITCHING; i++) { - Thread.sleep(WAIT_FOR_PREVIEW); - inst.sendKeyDownUpSync(KeyEvent.KEYCODE_MENU); - inst.sendKeyDownUpSync(KeyEvent.KEYCODE_DPAD_LEFT); - inst.sendKeyDownUpSync(KeyEvent.KEYCODE_DPAD_CENTER); - Thread.sleep(WAIT_FOR_PREVIEW); - } - } catch (Exception e){ - Log.v(TAG, e.toString()); - } - assertTrue("testSwitchMode",true); - } -} - |