am cd54e35a: (-s ours) am df2a0ab1: Import revised translations. DO NOT MERGE
* commit 'cd54e35ae9d1f6f0f7b4d08f2200b30ed275fefd':
Import revised translations. DO NOT MERGE
diff --git a/Android.mk b/Android.mk
index e015dda..a5a47b3 100644
--- a/Android.mk
+++ b/Android.mk
@@ -4,7 +4,8 @@
LOCAL_MODULE_TAGS := optional
LOCAL_STATIC_JAVA_LIBRARIES := \
- android-common
+ android-common \
+ guava
LOCAL_SRC_FILES := \
$(call all-java-files-under, src) \
@@ -12,6 +13,8 @@
LOCAL_PACKAGE_NAME := Browser
+LOCAL_PROGUARD_FLAG_FILES := proguard.flags
+
LOCAL_EMMA_COVERAGE_FILTER := *,-com.android.common.*
include $(BUILD_PACKAGE)
diff --git a/AndroidManifest.xml b/AndroidManifest.xml
index dc8f599..f88dfd9 100644
--- a/AndroidManifest.xml
+++ b/AndroidManifest.xml
@@ -25,24 +25,29 @@
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
- <uses-permission android:name="com.android.launcher.permission.INSTALL_SHORTCUT"/>
+ <uses-permission android:name="android.permission.GET_ACCOUNTS"/>
+ <uses-permission android:name="android.permission.USE_CREDENTIALS"/>
<uses-permission android:name="android.permission.INTERNET" />
+ <uses-permission android:name="android.permission.SEND_DOWNLOAD_COMPLETED_INTENTS" />
<uses-permission android:name="android.permission.SET_WALLPAPER" />
<uses-permission android:name="android.permission.WAKE_LOCK"/>
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission android:name="android.permission.WRITE_SETTINGS" />
+ <uses-permission android:name="android.permission.READ_SYNC_SETTINGS" />
+ <uses-permission android:name="android.permission.WRITE_SYNC_SETTINGS" />
<uses-permission android:name="com.android.browser.permission.READ_HISTORY_BOOKMARKS"/>
<uses-permission android:name="com.android.browser.permission.WRITE_HISTORY_BOOKMARKS"/>
- <uses-permission android:name="android.permission.SEND_DOWNLOAD_COMPLETED_INTENTS" />
+ <uses-permission android:name="com.android.launcher.permission.INSTALL_SHORTCUT"/>
<application android:name="Browser"
android:label="@string/application_name"
- android:icon="@drawable/ic_launcher_browser"
+ android:icon="@mipmap/ic_launcher_browser"
android:backupAgent=".BrowserBackupAgent"
+ android:hardwareAccelerated="true"
android:taskAffinity="android.task.browser" >
- <provider android:name="BrowserProvider"
- android:authorities="browser"
+ <provider android:name=".provider.BrowserProvider2"
+ android:authorities="com.android.browser;browser"
android:multiprocess="true"
android:readPermission="com.android.browser.permission.READ_HISTORY_BOOKMARKS"
android:writePermission="com.android.browser.permission.WRITE_HISTORY_BOOKMARKS">
@@ -53,8 +58,9 @@
android:label="@string/application_name"
android:launchMode="singleTask"
android:alwaysRetainTaskState="true"
- android:configChanges="orientation|keyboardHidden"
+ android:configChanges="orientation|keyboardHidden|keyboard"
android:theme="@style/BrowserTheme"
+ android:hardwareAccelerated="false"
android:windowSoftInputMode="adjustResize" >
<intent-filter>
<action android:name="android.speech.action.VOICE_SEARCH_RESULTS" />
@@ -85,6 +91,16 @@
<data android:mimeType="application/xhtml+xml"/>
<data android:mimeType="application/vnd.wap.xhtml+xml"/>
</intent-filter>
+ <!-- For viewing saved web archives. -->
+ <intent-filter>
+ <action android:name="android.intent.action.VIEW" />
+ <category android:name="android.intent.category.BROWSABLE" />
+ <category android:name="android.intent.category.DEFAULT" />
+ <data android:scheme="http" />
+ <data android:scheme="https" />
+ <data android:scheme="file" />
+ <data android:mimeType="application/x-webarchive-xml"/>
+ </intent-filter>
<!-- We are also the main entry point of the browser. -->
<intent-filter>
<action android:name="android.intent.action.MAIN" />
@@ -120,47 +136,19 @@
android:resource="@xml/searchable" />
</activity>
- <activity android:name="CombinedBookmarkHistoryActivity" android:label="@string/bookmarks"
- android:excludeFromRecents="true"
- android:launchMode="singleTop" android:configChanges="orientation|keyboardHidden"
- android:theme="@style/BookmarkTheme" >
- <meta-data android:name="android.app.default_searchable"
- android:value=".BrowserActivity" />
- <intent-filter>
- <action android:name="android.intent.action.MAIN" />
- </intent-filter>
- </activity>
-
- <activity android:name="BrowserBookmarksPage" android:label="@string/bookmarks"
- android:launchMode="singleTop" android:configChanges="orientation|keyboardHidden">
- </activity>
-
- <activity-alias android:name="ShortcutBookmarksPage"
- android:targetActivity="BrowserBookmarksPage"
+ <activity android:name="ShortcutActivity"
+ android:theme="@style/ShortcutTheme"
android:label="@string/shortcut_bookmark"
- android:icon="@drawable/ic_launcher_shortcut_browser_bookmark">
+ android:icon="@mipmap/ic_launcher_shortcut_browser_bookmark">
<intent-filter>
<action android:name="android.intent.action.CREATE_SHORTCUT" />
<category android:name="android.intent.category.DEFAULT" />
</intent-filter>
- </activity-alias>
-
- <activity android:name="BrowserDownloadPage" android:label=""
- android:configChanges="orientation|keyboardHidden">
</activity>
- <activity android:name="BrowserPreferencesPage" android:label="@string/menu_preferences"
- android:configChanges="orientation|keyboardHidden">
- </activity>
-
- <activity android:name="BrowserHistoryPage" android:label=""
- android:configChanges="orientation|keyboardHidden">
- </activity>
-
- <activity android:name="WebsiteSettingsActivity" android:label=""
- android:configChanges="orientation|keyboardHidden">
+ <activity android:name="BrowserPreferencesPage" android:label="@string/menu_preferences">
</activity>
<activity android:name="BookmarkSearch"
@@ -176,8 +164,10 @@
android:resource="@xml/bookmarks_searchable" />
</activity>
- <activity android:name="AddBookmarkPage" android:label="Save bookmark" android:theme="@android:style/Theme.Dialog"
- android:configChanges="orientation|keyboardHidden" android:windowSoftInputMode="stateHidden">
+ <activity android:name="AddBookmarkPage" android:label="Save bookmark"
+ android:theme="@style/Dialog"
+ android:configChanges="orientation|keyboardHidden"
+ android:windowSoftInputMode="stateHidden|adjustPan">
<intent-filter>
<action android:name="android.intent.action.INSERT" />
<category android:name="android.intent.category.DEFAULT" />
@@ -185,22 +175,52 @@
</intent-filter>
</activity>
- <!--receiver android:name=".widget.BookmarkWidgetProvider" android:label="@string/bookmarks">
+ <!-- Bookmark thumbnail homescreen widget -->
+ <receiver
+ android:name=".widget.BookmarkThumbnailWidgetProvider"
+ android:label="@string/bookmarks">
<intent-filter>
- <action android:name="android.appwidget.action.APPWIDGET_UPDATE" />
+ <action
+ android:name="android.appwidget.action.APPWIDGET_UPDATE" />
+ <action
+ android:name="com.android.browser.BOOKMARK_APPWIDGET_UPDATE" />
</intent-filter>
- <meta-data android:name="android.appwidget.provider" android:resource="@xml/bookmarkwidget"/>
+ <meta-data
+ android:name="android.appwidget.provider"
+ android:resource="@xml/bookmarkthumbnailwidget_info" />
</receiver>
-
- <service android:name=".widget.BookmarkWidgetService" /-->
+ <service
+ android:name=".widget.BookmarkThumbnailWidgetService"
+ android:permission="android.permission.BIND_REMOTEVIEWS"
+ android:exported="false" />
<!-- Makes .BrowserActivity the search target for any activity in Browser -->
<meta-data android:name="android.app.default_searchable" android:value=".BrowserActivity" />
+ <!-- Application code for RLZ tracking. RLZ assigns non-unique, non-personally identifiable
+ tracking labels to client products; these labels sometimes appear in Google search
+ queries. See http://code.google.com/p/rlz for more info.
+
+ This value signifies to the RLZ client that this application uses RLZ tracking. -->
+ <meta-data android:name="com.google.android.partnersetup.RLZ_ACCESS_POINT"
+ android:value="@string/rlz_access_point" />
+
<receiver android:name=".OpenDownloadReceiver">
<intent-filter>
<action android:name="android.intent.action.DOWNLOAD_NOTIFICATION_CLICKED"/>
- <data android:scheme="content" android:mimeType="vnd.android.cursor.item/download"/>
+ </intent-filter>
+ </receiver>
+
+ <!-- For custom home pages (like most visited) -->
+ <provider
+ android:name=".homepages.HomeProvider"
+ android:authorities="com.android.browser.home"
+ android:readPermission="com.android.browser.permission.READ_HISTORY_BOOKMARKS"
+ android:exported="false" />
+
+ <receiver android:name=".AccountsChangedReceiver">
+ <intent-filter>
+ <action android:name="android.accounts.LOGIN_ACCOUNTS_CHANGED" />
</intent-filter>
</receiver>
</application>
diff --git a/CleanSpec.mk b/CleanSpec.mk
index b84e1b6..722b4a4 100644
--- a/CleanSpec.mk
+++ b/CleanSpec.mk
@@ -43,6 +43,7 @@
#$(call add-clean-step, rm -rf $(OUT_DIR)/target/common/obj/JAVA_LIBRARIES/core_intermediates)
#$(call add-clean-step, find $(OUT_DIR) -type f -name "IGTalkSession*" -print0 | xargs -0 rm -f)
#$(call add-clean-step, rm -rf $(PRODUCT_OUT)/data/*)
+$(call add-clean-step, rm -rf $(OUT_DIR)/target/common/obj/APPS/Browser_intermediates)
# ************************************************
# NEWER CLEAN STEPS MUST BE AT THE END OF THE LIST
diff --git a/proguard.flags b/proguard.flags
new file mode 100644
index 0000000..888c238
--- /dev/null
+++ b/proguard.flags
@@ -0,0 +1,2 @@
+# Most of the classes in this package are fragments only referenced from XML
+-keep class com.android.browser.preferences.*
diff --git a/res/anim/dialog_enter.xml b/res/anim/dialog_enter.xml
deleted file mode 100644
index f98d845..0000000
--- a/res/anim/dialog_enter.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.
--->
-
-<set xmlns:android="http://schemas.android.com/apk/res/android"
- android:interpolator="@android:anim/decelerate_interpolator">
- <translate android:fromYDelta="25%" android:toYDelta="0" android:duration="75"/>
- <alpha android:fromAlpha="0.0" android:toAlpha="1.0" android:duration="75" />
-</set>
diff --git a/res/anim/dialog_exit.xml b/res/anim/dialog_exit.xml
deleted file mode 100644
index dacb5c3..0000000
--- a/res/anim/dialog_exit.xml
+++ /dev/null
@@ -1,22 +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.
--->
-
-<set xmlns:android="http://schemas.android.com/apk/res/android"
- android:interpolator="@android:anim/accelerate_interpolator">
- <translate android:fromYDelta="0" android:toYDelta="50%" android:duration="50"/>
- <alpha android:fromAlpha="1.0" android:toAlpha="0.0" android:duration="50" />
-</set>
-
diff --git a/res/drawable-hdpi/appwidget_bg.9.png b/res/drawable-hdpi/appwidget_bg.9.png
deleted file mode 100644
index 3b29eae..0000000
--- a/res/drawable-hdpi/appwidget_bg.9.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/bg_bookmark_widget_holo.9.png b/res/drawable-hdpi/bg_bookmark_widget_holo.9.png
new file mode 100644
index 0000000..adb57a4
--- /dev/null
+++ b/res/drawable-hdpi/bg_bookmark_widget_holo.9.png
Binary files differ
diff --git a/res/drawable-hdpi/bookmarks_widget_thumb_selector_pressed.9.png b/res/drawable-hdpi/bookmarks_widget_thumb_selector_pressed.9.png
new file mode 100644
index 0000000..a329b19
--- /dev/null
+++ b/res/drawable-hdpi/bookmarks_widget_thumb_selector_pressed.9.png
Binary files differ
diff --git a/res/drawable-hdpi/border_thumb_bookmarks_widget_holo.9.png b/res/drawable-hdpi/border_thumb_bookmarks_widget_holo.9.png
new file mode 100644
index 0000000..ab0ece8
--- /dev/null
+++ b/res/drawable-hdpi/border_thumb_bookmarks_widget_holo.9.png
Binary files differ
diff --git a/res/drawable-hdpi/browsertab_add.png b/res/drawable-hdpi/browsertab_add.png
new file mode 100644
index 0000000..1e52bb1
--- /dev/null
+++ b/res/drawable-hdpi/browsertab_add.png
Binary files differ
diff --git a/res/drawable-hdpi/browsertab_inactive.png b/res/drawable-hdpi/browsertab_inactive.png
new file mode 100644
index 0000000..60ebb2b
--- /dev/null
+++ b/res/drawable-hdpi/browsertab_inactive.png
Binary files differ
diff --git a/res/drawable-hdpi/btn_ic_back_bookmark_widget_holo_dark.png b/res/drawable-hdpi/btn_ic_back_bookmark_widget_holo_dark.png
new file mode 100644
index 0000000..5f975e5
--- /dev/null
+++ b/res/drawable-hdpi/btn_ic_back_bookmark_widget_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/btn_ic_bookmark_bookmark_widget_holo_dark.png b/res/drawable-hdpi/btn_ic_bookmark_bookmark_widget_holo_dark.png
new file mode 100644
index 0000000..722f3b8
--- /dev/null
+++ b/res/drawable-hdpi/btn_ic_bookmark_bookmark_widget_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/crumb_divider.9.png b/res/drawable-hdpi/crumb_divider.9.png
new file mode 100644
index 0000000..f748ffa
--- /dev/null
+++ b/res/drawable-hdpi/crumb_divider.9.png
Binary files differ
diff --git a/res/drawable-hdpi/default_video_poster.png b/res/drawable-hdpi/default_video_poster.png
new file mode 100644
index 0000000..9bbaf9c
--- /dev/null
+++ b/res/drawable-hdpi/default_video_poster.png
Binary files differ
diff --git a/res/drawable-hdpi/dialog_divider_horizontal_light.9.png b/res/drawable-hdpi/dialog_divider_horizontal_light.9.png
deleted file mode 100644
index 8659acf..0000000
--- a/res/drawable-hdpi/dialog_divider_horizontal_light.9.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_add_string.png b/res/drawable-hdpi/ic_add_string.png
new file mode 100644
index 0000000..0775776
--- /dev/null
+++ b/res/drawable-hdpi/ic_add_string.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_back_disabled_holo_dark.png b/res/drawable-hdpi/ic_back_disabled_holo_dark.png
new file mode 100644
index 0000000..eca8a56
--- /dev/null
+++ b/res/drawable-hdpi/ic_back_disabled_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_back_hierarchy_holo_dark.png b/res/drawable-hdpi/ic_back_hierarchy_holo_dark.png
new file mode 100644
index 0000000..ed99557
--- /dev/null
+++ b/res/drawable-hdpi/ic_back_hierarchy_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_back_holo_dark.png b/res/drawable-hdpi/ic_back_holo_dark.png
new file mode 100644
index 0000000..5e31b19
--- /dev/null
+++ b/res/drawable-hdpi/ic_back_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_bookmark_off_holo_dark.png b/res/drawable-hdpi/ic_bookmark_off_holo_dark.png
new file mode 100644
index 0000000..9ec0a44
--- /dev/null
+++ b/res/drawable-hdpi/ic_bookmark_off_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_bookmark_on_holo_dark.png b/res/drawable-hdpi/ic_bookmark_on_holo_dark.png
new file mode 100644
index 0000000..1d67f1a
--- /dev/null
+++ b/res/drawable-hdpi/ic_bookmark_on_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_bookmark_widget_bookmark_holo_dark.png b/res/drawable-hdpi/ic_bookmark_widget_bookmark_holo_dark.png
new file mode 100644
index 0000000..d7c9bd9
--- /dev/null
+++ b/res/drawable-hdpi/ic_bookmark_widget_bookmark_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_bookmarks_history_holo_dark.png b/res/drawable-hdpi/ic_bookmarks_history_holo_dark.png
new file mode 100644
index 0000000..df527a2
--- /dev/null
+++ b/res/drawable-hdpi/ic_bookmarks_history_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_bookmarks_holo_dark.png b/res/drawable-hdpi/ic_bookmarks_holo_dark.png
new file mode 100644
index 0000000..d3070bf
--- /dev/null
+++ b/res/drawable-hdpi/ic_bookmarks_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_browser_bookmark_widget_holo.png b/res/drawable-hdpi/ic_browser_bookmark_widget_holo.png
new file mode 100644
index 0000000..e583acd
--- /dev/null
+++ b/res/drawable-hdpi/ic_browser_bookmark_widget_holo.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_btn_bookmarks.png b/res/drawable-hdpi/ic_btn_bookmarks.png
deleted file mode 100644
index 092590b..0000000
--- a/res/drawable-hdpi/ic_btn_bookmarks.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_btn_close_panel.png b/res/drawable-hdpi/ic_btn_close_panel.png
deleted file mode 100644
index a1327c2..0000000
--- a/res/drawable-hdpi/ic_btn_close_panel.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_btn_copy.png b/res/drawable-hdpi/ic_btn_copy.png
index 04fda7f..847cf7e 100644
--- a/res/drawable-hdpi/ic_btn_copy.png
+++ b/res/drawable-hdpi/ic_btn_copy.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_btn_find.png b/res/drawable-hdpi/ic_btn_find.png
old mode 100755
new mode 100644
index 20e1fbc..0da38a1
--- a/res/drawable-hdpi/ic_btn_find.png
+++ b/res/drawable-hdpi/ic_btn_find.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_btn_find_next.png b/res/drawable-hdpi/ic_btn_find_next.png
deleted file mode 100644
index b696a6b..0000000
--- a/res/drawable-hdpi/ic_btn_find_next.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_btn_find_prev.png b/res/drawable-hdpi/ic_btn_find_prev.png
deleted file mode 100644
index 5550c5a..0000000
--- a/res/drawable-hdpi/ic_btn_find_prev.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_btn_select_all.png b/res/drawable-hdpi/ic_btn_select_all.png
index 839915b..9545a53 100644
--- a/res/drawable-hdpi/ic_btn_select_all.png
+++ b/res/drawable-hdpi/ic_btn_select_all.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_btn_share.png b/res/drawable-hdpi/ic_btn_share.png
deleted file mode 100644
index 44db9b1..0000000
--- a/res/drawable-hdpi/ic_btn_share.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_chevron.png b/res/drawable-hdpi/ic_chevron.png
new file mode 100644
index 0000000..6dc842f
--- /dev/null
+++ b/res/drawable-hdpi/ic_chevron.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_clear_search.png b/res/drawable-hdpi/ic_clear_search.png
new file mode 100644
index 0000000..e8e67b4
--- /dev/null
+++ b/res/drawable-hdpi/ic_clear_search.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_close_window_holo_dark.png b/res/drawable-hdpi/ic_close_window_holo_dark.png
new file mode 100644
index 0000000..d459352
--- /dev/null
+++ b/res/drawable-hdpi/ic_close_window_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_downloads_holo_dark.png b/res/drawable-hdpi/ic_downloads_holo_dark.png
new file mode 100644
index 0000000..ac2f6bd
--- /dev/null
+++ b/res/drawable-hdpi/ic_downloads_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_folder_holo_dark.png b/res/drawable-hdpi/ic_folder_holo_dark.png
new file mode 100644
index 0000000..139d79b
--- /dev/null
+++ b/res/drawable-hdpi/ic_folder_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_forward_disabled_holo_dark.png b/res/drawable-hdpi/ic_forward_disabled_holo_dark.png
new file mode 100644
index 0000000..9330b92
--- /dev/null
+++ b/res/drawable-hdpi/ic_forward_disabled_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_forward_holo_dark.png b/res/drawable-hdpi/ic_forward_holo_dark.png
new file mode 100644
index 0000000..d5a5fa7
--- /dev/null
+++ b/res/drawable-hdpi/ic_forward_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_go_holo_dark.png b/res/drawable-hdpi/ic_go_holo_dark.png
new file mode 100644
index 0000000..b1412e8
--- /dev/null
+++ b/res/drawable-hdpi/ic_go_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_gps_denied_holo_dark.png b/res/drawable-hdpi/ic_gps_denied_holo_dark.png
new file mode 100644
index 0000000..5bd9c39
--- /dev/null
+++ b/res/drawable-hdpi/ic_gps_denied_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_gps_on_holo_dark.png b/res/drawable-hdpi/ic_gps_on_holo_dark.png
new file mode 100644
index 0000000..e736362
--- /dev/null
+++ b/res/drawable-hdpi/ic_gps_on_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_history_holo_dark.png b/res/drawable-hdpi/ic_history_holo_dark.png
new file mode 100644
index 0000000..7972a81
--- /dev/null
+++ b/res/drawable-hdpi/ic_history_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_home_holo_dark.png b/res/drawable-hdpi/ic_home_holo_dark.png
new file mode 100644
index 0000000..f355507
--- /dev/null
+++ b/res/drawable-hdpi/ic_home_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_incognito_holo_dark.png b/res/drawable-hdpi/ic_incognito_holo_dark.png
new file mode 100644
index 0000000..f4997ae
--- /dev/null
+++ b/res/drawable-hdpi/ic_incognito_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_launcher_browser.png b/res/drawable-hdpi/ic_launcher_browser.png
deleted file mode 100644
index f11581f..0000000
--- a/res/drawable-hdpi/ic_launcher_browser.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_launcher_drm_file.png b/res/drawable-hdpi/ic_launcher_drm_file.png
deleted file mode 100644
index 9df1c55..0000000
--- a/res/drawable-hdpi/ic_launcher_drm_file.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_launcher_shortcut_browser_bookmark_icon.png b/res/drawable-hdpi/ic_launcher_shortcut_browser_bookmark_icon.png
deleted file mode 100644
index 57fc915..0000000
--- a/res/drawable-hdpi/ic_launcher_shortcut_browser_bookmark_icon.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_list_bookmark.png b/res/drawable-hdpi/ic_list_bookmark.png
deleted file mode 100644
index 13f8067..0000000
--- a/res/drawable-hdpi/ic_list_bookmark.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_list_gps_denied.png b/res/drawable-hdpi/ic_list_gps_denied.png
deleted file mode 100644
index 97dbc9b..0000000
--- a/res/drawable-hdpi/ic_list_gps_denied.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_list_gps_on.png b/res/drawable-hdpi/ic_list_gps_on.png
deleted file mode 100644
index 2c02e58..0000000
--- a/res/drawable-hdpi/ic_list_gps_on.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_list_new_window.png b/res/drawable-hdpi/ic_list_new_window.png
deleted file mode 100644
index e5e4645..0000000
--- a/res/drawable-hdpi/ic_list_new_window.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_list_view_holo_dark.png b/res/drawable-hdpi/ic_list_view_holo_dark.png
new file mode 100644
index 0000000..89d63de
--- /dev/null
+++ b/res/drawable-hdpi/ic_list_view_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_add_bookmark.png b/res/drawable-hdpi/ic_menu_add_bookmark.png
deleted file mode 100644
index c54eb7e..0000000
--- a/res/drawable-hdpi/ic_menu_add_bookmark.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_bookmarks.png b/res/drawable-hdpi/ic_menu_bookmarks.png
deleted file mode 100755
index fd63499..0000000
--- a/res/drawable-hdpi/ic_menu_bookmarks.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_findonpage_normal.png b/res/drawable-hdpi/ic_menu_findonpage_normal.png
new file mode 100644
index 0000000..f4f8f85
--- /dev/null
+++ b/res/drawable-hdpi/ic_menu_findonpage_normal.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_list.png b/res/drawable-hdpi/ic_menu_list.png
deleted file mode 100644
index 2b921b3..0000000
--- a/res/drawable-hdpi/ic_menu_list.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_new_window.png b/res/drawable-hdpi/ic_menu_new_window.png
index 36aee01..fa498e7 100644
--- a/res/drawable-hdpi/ic_menu_new_window.png
+++ b/res/drawable-hdpi/ic_menu_new_window.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_thumbnail.png b/res/drawable-hdpi/ic_menu_thumbnail.png
deleted file mode 100644
index 705b02b..0000000
--- a/res/drawable-hdpi/ic_menu_thumbnail.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_menu_windows.png b/res/drawable-hdpi/ic_menu_windows.png
deleted file mode 100644
index 0e80009..0000000
--- a/res/drawable-hdpi/ic_menu_windows.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_most_visited_holo_dark.png b/res/drawable-hdpi/ic_most_visited_holo_dark.png
new file mode 100644
index 0000000..bbb0bf6
--- /dev/null
+++ b/res/drawable-hdpi/ic_most_visited_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_new_window_holo_dark.png b/res/drawable-hdpi/ic_new_window_holo_dark.png
new file mode 100644
index 0000000..bc4017a
--- /dev/null
+++ b/res/drawable-hdpi/ic_new_window_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_pageinfo_holo_dark.png b/res/drawable-hdpi/ic_pageinfo_holo_dark.png
new file mode 100644
index 0000000..39b8201
--- /dev/null
+++ b/res/drawable-hdpi/ic_pageinfo_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_partial_secure.png b/res/drawable-hdpi/ic_partial_secure.png
new file mode 100644
index 0000000..76ba96a
--- /dev/null
+++ b/res/drawable-hdpi/ic_partial_secure.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_pie_back.png b/res/drawable-hdpi/ic_pie_back.png
new file mode 100644
index 0000000..32b3ea7
--- /dev/null
+++ b/res/drawable-hdpi/ic_pie_back.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_pie_bookmarks.png b/res/drawable-hdpi/ic_pie_bookmarks.png
new file mode 100644
index 0000000..2536856
--- /dev/null
+++ b/res/drawable-hdpi/ic_pie_bookmarks.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_pie_close_tab.png b/res/drawable-hdpi/ic_pie_close_tab.png
new file mode 100644
index 0000000..108f8da
--- /dev/null
+++ b/res/drawable-hdpi/ic_pie_close_tab.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_pie_forward.png b/res/drawable-hdpi/ic_pie_forward.png
new file mode 100644
index 0000000..4e5f08e
--- /dev/null
+++ b/res/drawable-hdpi/ic_pie_forward.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_pie_more.png b/res/drawable-hdpi/ic_pie_more.png
new file mode 100644
index 0000000..0833ee2
--- /dev/null
+++ b/res/drawable-hdpi/ic_pie_more.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_pie_new_tab.png b/res/drawable-hdpi/ic_pie_new_tab.png
new file mode 100644
index 0000000..18f49ef
--- /dev/null
+++ b/res/drawable-hdpi/ic_pie_new_tab.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_pie_refresh.png b/res/drawable-hdpi/ic_pie_refresh.png
new file mode 100644
index 0000000..f0a5d7a
--- /dev/null
+++ b/res/drawable-hdpi/ic_pie_refresh.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_pie_search.png b/res/drawable-hdpi/ic_pie_search.png
new file mode 100644
index 0000000..f1c8825
--- /dev/null
+++ b/res/drawable-hdpi/ic_pie_search.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_pie_tabs.png b/res/drawable-hdpi/ic_pie_tabs.png
new file mode 100644
index 0000000..b941285
--- /dev/null
+++ b/res/drawable-hdpi/ic_pie_tabs.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_refresh_holo_dark.png b/res/drawable-hdpi/ic_refresh_holo_dark.png
new file mode 100644
index 0000000..1da3ea8
--- /dev/null
+++ b/res/drawable-hdpi/ic_refresh_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_search_holo_dark.png b/res/drawable-hdpi/ic_search_holo_dark.png
new file mode 100644
index 0000000..688ef5d
--- /dev/null
+++ b/res/drawable-hdpi/ic_search_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_secure_holo_dark.png b/res/drawable-hdpi/ic_secure_holo_dark.png
new file mode 100644
index 0000000..72a40dd
--- /dev/null
+++ b/res/drawable-hdpi/ic_secure_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_settings_holo_dark.png b/res/drawable-hdpi/ic_settings_holo_dark.png
new file mode 100644
index 0000000..ac3f40c
--- /dev/null
+++ b/res/drawable-hdpi/ic_settings_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_share_holo_dark.png b/res/drawable-hdpi/ic_share_holo_dark.png
new file mode 100644
index 0000000..2094394
--- /dev/null
+++ b/res/drawable-hdpi/ic_share_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_stop_holo_dark.png b/res/drawable-hdpi/ic_stop_holo_dark.png
new file mode 100644
index 0000000..e31dd22
--- /dev/null
+++ b/res/drawable-hdpi/ic_stop_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_tab_bookmarks_selected.png b/res/drawable-hdpi/ic_tab_bookmarks_selected.png
deleted file mode 100644
index 8e1c3ae..0000000
--- a/res/drawable-hdpi/ic_tab_bookmarks_selected.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_tab_bookmarks_unselected.png b/res/drawable-hdpi/ic_tab_bookmarks_unselected.png
deleted file mode 100644
index 95efcb1..0000000
--- a/res/drawable-hdpi/ic_tab_bookmarks_unselected.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_tab_close.png b/res/drawable-hdpi/ic_tab_close.png
new file mode 100644
index 0000000..e501486
--- /dev/null
+++ b/res/drawable-hdpi/ic_tab_close.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_tab_history_selected.png b/res/drawable-hdpi/ic_tab_history_selected.png
deleted file mode 100644
index e23a0fc..0000000
--- a/res/drawable-hdpi/ic_tab_history_selected.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_tab_history_unselected.png b/res/drawable-hdpi/ic_tab_history_unselected.png
deleted file mode 100644
index 663ff46..0000000
--- a/res/drawable-hdpi/ic_tab_history_unselected.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_tab_most_visited_selected.png b/res/drawable-hdpi/ic_tab_most_visited_selected.png
deleted file mode 100644
index 04ffd57..0000000
--- a/res/drawable-hdpi/ic_tab_most_visited_selected.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_tab_most_visited_unselected.png b/res/drawable-hdpi/ic_tab_most_visited_unselected.png
deleted file mode 100644
index 6127920..0000000
--- a/res/drawable-hdpi/ic_tab_most_visited_unselected.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/ic_voice_search_holo_dark.png b/res/drawable-hdpi/ic_voice_search_holo_dark.png
new file mode 100644
index 0000000..73bcafc
--- /dev/null
+++ b/res/drawable-hdpi/ic_voice_search_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_web_holo_dark.png b/res/drawable-hdpi/ic_web_holo_dark.png
new file mode 100644
index 0000000..d936c2c
--- /dev/null
+++ b/res/drawable-hdpi/ic_web_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/ic_windows_holo_dark.png b/res/drawable-hdpi/ic_windows_holo_dark.png
new file mode 100644
index 0000000..98d5693
--- /dev/null
+++ b/res/drawable-hdpi/ic_windows_holo_dark.png
Binary files differ
diff --git a/res/drawable-hdpi/list_divider_vert.9.png b/res/drawable-hdpi/list_divider_vert.9.png
new file mode 100644
index 0000000..d99730a
--- /dev/null
+++ b/res/drawable-hdpi/list_divider_vert.9.png
Binary files differ
diff --git a/res/drawable-hdpi/overlay_url_bookmark_widget_holo.9.png b/res/drawable-hdpi/overlay_url_bookmark_widget_holo.9.png
new file mode 100644
index 0000000..570d238
--- /dev/null
+++ b/res/drawable-hdpi/overlay_url_bookmark_widget_holo.9.png
Binary files differ
diff --git a/res/drawable-hdpi/progress.9.png b/res/drawable-hdpi/progress.9.png
new file mode 100644
index 0000000..398bee4
--- /dev/null
+++ b/res/drawable-hdpi/progress.9.png
Binary files differ
diff --git a/res/drawable-hdpi/row_activated_bookmark_widget_holo.9.png b/res/drawable-hdpi/row_activated_bookmark_widget_holo.9.png
new file mode 100644
index 0000000..5af3f6a
--- /dev/null
+++ b/res/drawable-hdpi/row_activated_bookmark_widget_holo.9.png
Binary files differ
diff --git a/res/drawable-hdpi/ssl_icon.png b/res/drawable-hdpi/ssl_icon.png
deleted file mode 100644
index 666debc..0000000
--- a/res/drawable-hdpi/ssl_icon.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-hdpi/text_field_results.9.png b/res/drawable-hdpi/text_field_results.9.png
new file mode 100644
index 0000000..bd4bcc5
--- /dev/null
+++ b/res/drawable-hdpi/text_field_results.9.png
Binary files differ
diff --git a/res/drawable-hdpi/textfield_active_holo_dark.9.png b/res/drawable-hdpi/textfield_active_holo_dark.9.png
new file mode 100644
index 0000000..d023d75
--- /dev/null
+++ b/res/drawable-hdpi/textfield_active_holo_dark.9.png
Binary files differ
diff --git a/res/drawable-hdpi/textfield_default_holo_dark.9.png b/res/drawable-hdpi/textfield_default_holo_dark.9.png
new file mode 100644
index 0000000..39a16cc
--- /dev/null
+++ b/res/drawable-hdpi/textfield_default_holo_dark.9.png
Binary files differ
diff --git a/res/drawable-hdpi/thumb_bookmark_widget_folder_back_holo.png b/res/drawable-hdpi/thumb_bookmark_widget_folder_back_holo.png
new file mode 100644
index 0000000..ad262d5
--- /dev/null
+++ b/res/drawable-hdpi/thumb_bookmark_widget_folder_back_holo.png
Binary files differ
diff --git a/res/drawable-hdpi/thumb_bookmark_widget_folder_holo.png b/res/drawable-hdpi/thumb_bookmark_widget_folder_holo.png
new file mode 100644
index 0000000..c91ef9b
--- /dev/null
+++ b/res/drawable-hdpi/thumb_bookmark_widget_folder_holo.png
Binary files differ
diff --git a/res/drawable-hdpi/trashcan.png b/res/drawable-hdpi/trashcan.png
new file mode 100644
index 0000000..89b23ee
--- /dev/null
+++ b/res/drawable-hdpi/trashcan.png
Binary files differ
diff --git a/res/drawable-hdpi/urlbar_bg.9.png b/res/drawable-hdpi/urlbar_bg.9.png
new file mode 100644
index 0000000..c35383e
--- /dev/null
+++ b/res/drawable-hdpi/urlbar_bg.9.png
Binary files differ
diff --git a/res/drawable-mdpi/app_web_browser_sm.png b/res/drawable-mdpi/app_web_browser_sm.png
index dbb460a..21245c2 100644
--- a/res/drawable-mdpi/app_web_browser_sm.png
+++ b/res/drawable-mdpi/app_web_browser_sm.png
Binary files differ
diff --git a/res/drawable-mdpi/appwidget_bg.9.png b/res/drawable-mdpi/appwidget_bg.9.png
deleted file mode 100644
index afe41b6..0000000
--- a/res/drawable-mdpi/appwidget_bg.9.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/bg_bookmark_widget_holo.9.png b/res/drawable-mdpi/bg_bookmark_widget_holo.9.png
new file mode 100644
index 0000000..d95f8d3
--- /dev/null
+++ b/res/drawable-mdpi/bg_bookmark_widget_holo.9.png
Binary files differ
diff --git a/res/drawable-mdpi/bookmarks_widget_thumb_selector_longpressed.9.png b/res/drawable-mdpi/bookmarks_widget_thumb_selector_longpressed.9.png
new file mode 100644
index 0000000..2aee937
--- /dev/null
+++ b/res/drawable-mdpi/bookmarks_widget_thumb_selector_longpressed.9.png
Binary files differ
diff --git a/res/drawable-mdpi/bookmarks_widget_thumb_selector_pressed.9.png b/res/drawable-mdpi/bookmarks_widget_thumb_selector_pressed.9.png
new file mode 100644
index 0000000..6ec1576
--- /dev/null
+++ b/res/drawable-mdpi/bookmarks_widget_thumb_selector_pressed.9.png
Binary files differ
diff --git a/res/drawable-mdpi/border_thumb_bookmarks_widget_holo.9.png b/res/drawable-mdpi/border_thumb_bookmarks_widget_holo.9.png
new file mode 100644
index 0000000..486e5e8
--- /dev/null
+++ b/res/drawable-mdpi/border_thumb_bookmarks_widget_holo.9.png
Binary files differ
diff --git a/res/drawable-mdpi/browser_thumbnail.png b/res/drawable-mdpi/browser_thumbnail.png
index 2d54e07..f59bec5 100644
--- a/res/drawable-mdpi/browser_thumbnail.png
+++ b/res/drawable-mdpi/browser_thumbnail.png
Binary files differ
diff --git a/res/drawable-mdpi/browsertab_add.png b/res/drawable-mdpi/browsertab_add.png
new file mode 100644
index 0000000..f960c1d
--- /dev/null
+++ b/res/drawable-mdpi/browsertab_add.png
Binary files differ
diff --git a/res/drawable-mdpi/browsertab_inactive.png b/res/drawable-mdpi/browsertab_inactive.png
new file mode 100644
index 0000000..d441604
--- /dev/null
+++ b/res/drawable-mdpi/browsertab_inactive.png
Binary files differ
diff --git a/res/drawable-mdpi/btn_ic_back_bookmark_widget_holo_dark.png b/res/drawable-mdpi/btn_ic_back_bookmark_widget_holo_dark.png
new file mode 100644
index 0000000..d8697b8
--- /dev/null
+++ b/res/drawable-mdpi/btn_ic_back_bookmark_widget_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/btn_ic_bookmark_bookmark_widget_holo_dark.png b/res/drawable-mdpi/btn_ic_bookmark_bookmark_widget_holo_dark.png
new file mode 100644
index 0000000..21a2cc3
--- /dev/null
+++ b/res/drawable-mdpi/btn_ic_bookmark_bookmark_widget_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/crumb_divider.9.png b/res/drawable-mdpi/crumb_divider.9.png
new file mode 100644
index 0000000..8c8fd43
--- /dev/null
+++ b/res/drawable-mdpi/crumb_divider.9.png
Binary files differ
diff --git a/res/drawable/default_video_poster.png b/res/drawable-mdpi/default_video_poster.png
similarity index 100%
rename from res/drawable/default_video_poster.png
rename to res/drawable-mdpi/default_video_poster.png
Binary files differ
diff --git a/res/drawable-mdpi/dialog_divider_horizontal_light.9.png b/res/drawable-mdpi/dialog_divider_horizontal_light.9.png
deleted file mode 100755
index b69619b..0000000
--- a/res/drawable-mdpi/dialog_divider_horizontal_light.9.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_add_string.png b/res/drawable-mdpi/ic_add_string.png
new file mode 100644
index 0000000..e3b95cb
--- /dev/null
+++ b/res/drawable-mdpi/ic_add_string.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_back_disabled_holo_dark.png b/res/drawable-mdpi/ic_back_disabled_holo_dark.png
new file mode 100644
index 0000000..aca4345
--- /dev/null
+++ b/res/drawable-mdpi/ic_back_disabled_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_back_hierarchy_holo_dark.png b/res/drawable-mdpi/ic_back_hierarchy_holo_dark.png
new file mode 100644
index 0000000..13d20ce
--- /dev/null
+++ b/res/drawable-mdpi/ic_back_hierarchy_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_back_holo_dark.png b/res/drawable-mdpi/ic_back_holo_dark.png
new file mode 100644
index 0000000..8977423
--- /dev/null
+++ b/res/drawable-mdpi/ic_back_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_bookmark_off_holo_dark.png b/res/drawable-mdpi/ic_bookmark_off_holo_dark.png
new file mode 100644
index 0000000..7446bdf
--- /dev/null
+++ b/res/drawable-mdpi/ic_bookmark_off_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_bookmark_on_holo_dark.png b/res/drawable-mdpi/ic_bookmark_on_holo_dark.png
new file mode 100644
index 0000000..79a183f
--- /dev/null
+++ b/res/drawable-mdpi/ic_bookmark_on_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_bookmark_widget_bookmark_holo_dark.png b/res/drawable-mdpi/ic_bookmark_widget_bookmark_holo_dark.png
new file mode 100644
index 0000000..70477aa
--- /dev/null
+++ b/res/drawable-mdpi/ic_bookmark_widget_bookmark_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_bookmarks_history_holo_dark.png b/res/drawable-mdpi/ic_bookmarks_history_holo_dark.png
new file mode 100644
index 0000000..4933165
--- /dev/null
+++ b/res/drawable-mdpi/ic_bookmarks_history_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_bookmarks_holo_dark.png b/res/drawable-mdpi/ic_bookmarks_holo_dark.png
new file mode 100644
index 0000000..ea45051
--- /dev/null
+++ b/res/drawable-mdpi/ic_bookmarks_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_browser_bookmark_widget_holo.png b/res/drawable-mdpi/ic_browser_bookmark_widget_holo.png
new file mode 100644
index 0000000..0d9e49d
--- /dev/null
+++ b/res/drawable-mdpi/ic_browser_bookmark_widget_holo.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_btn_bookmarks.png b/res/drawable-mdpi/ic_btn_bookmarks.png
deleted file mode 100644
index c307fee..0000000
--- a/res/drawable-mdpi/ic_btn_bookmarks.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_btn_close_panel.png b/res/drawable-mdpi/ic_btn_close_panel.png
deleted file mode 100644
index b6e1ce1..0000000
--- a/res/drawable-mdpi/ic_btn_close_panel.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_btn_find_next.png b/res/drawable-mdpi/ic_btn_find_next.png
deleted file mode 100644
index abdc247..0000000
--- a/res/drawable-mdpi/ic_btn_find_next.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_btn_find_prev.png b/res/drawable-mdpi/ic_btn_find_prev.png
deleted file mode 100644
index 4e3da1d..0000000
--- a/res/drawable-mdpi/ic_btn_find_prev.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_btn_share.png b/res/drawable-mdpi/ic_btn_share.png
deleted file mode 100644
index 7262acf..0000000
--- a/res/drawable-mdpi/ic_btn_share.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_chevron.png b/res/drawable-mdpi/ic_chevron.png
new file mode 100644
index 0000000..786899a
--- /dev/null
+++ b/res/drawable-mdpi/ic_chevron.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_clear_search.png b/res/drawable-mdpi/ic_clear_search.png
new file mode 100644
index 0000000..e8e67b4
--- /dev/null
+++ b/res/drawable-mdpi/ic_clear_search.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_close_window_holo_dark.png b/res/drawable-mdpi/ic_close_window_holo_dark.png
new file mode 100644
index 0000000..9bb8e87
--- /dev/null
+++ b/res/drawable-mdpi/ic_close_window_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_downloads_holo_dark.png b/res/drawable-mdpi/ic_downloads_holo_dark.png
new file mode 100644
index 0000000..8f01c41
--- /dev/null
+++ b/res/drawable-mdpi/ic_downloads_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_folder_holo_dark.png b/res/drawable-mdpi/ic_folder_holo_dark.png
new file mode 100644
index 0000000..a9bebb9
--- /dev/null
+++ b/res/drawable-mdpi/ic_folder_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_forward_disabled_holo_dark.png b/res/drawable-mdpi/ic_forward_disabled_holo_dark.png
new file mode 100644
index 0000000..5cd3f7f
--- /dev/null
+++ b/res/drawable-mdpi/ic_forward_disabled_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_forward_holo_dark.png b/res/drawable-mdpi/ic_forward_holo_dark.png
new file mode 100644
index 0000000..7f60012
--- /dev/null
+++ b/res/drawable-mdpi/ic_forward_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_go_holo_dark.png b/res/drawable-mdpi/ic_go_holo_dark.png
new file mode 100644
index 0000000..2e2a449
--- /dev/null
+++ b/res/drawable-mdpi/ic_go_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_gps_denied_holo_dark.png b/res/drawable-mdpi/ic_gps_denied_holo_dark.png
new file mode 100644
index 0000000..3a48b47
--- /dev/null
+++ b/res/drawable-mdpi/ic_gps_denied_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_gps_on_holo_dark.png b/res/drawable-mdpi/ic_gps_on_holo_dark.png
new file mode 100644
index 0000000..505e29a
--- /dev/null
+++ b/res/drawable-mdpi/ic_gps_on_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_history_holo_dark.png b/res/drawable-mdpi/ic_history_holo_dark.png
new file mode 100644
index 0000000..44f2245
--- /dev/null
+++ b/res/drawable-mdpi/ic_history_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_home_holo_dark.png b/res/drawable-mdpi/ic_home_holo_dark.png
new file mode 100644
index 0000000..8884eaa
--- /dev/null
+++ b/res/drawable-mdpi/ic_home_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_incognito_holo_dark.png b/res/drawable-mdpi/ic_incognito_holo_dark.png
new file mode 100644
index 0000000..dfb380a
--- /dev/null
+++ b/res/drawable-mdpi/ic_incognito_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_launcher_browser.png b/res/drawable-mdpi/ic_launcher_browser.png
deleted file mode 100644
index b76c169..0000000
--- a/res/drawable-mdpi/ic_launcher_browser.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_launcher_drm_file.png b/res/drawable-mdpi/ic_launcher_drm_file.png
deleted file mode 100644
index 57378b2..0000000
--- a/res/drawable-mdpi/ic_launcher_drm_file.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_launcher_shortcut_browser_bookmark_icon.png b/res/drawable-mdpi/ic_launcher_shortcut_browser_bookmark_icon.png
deleted file mode 100644
index ba82911..0000000
--- a/res/drawable-mdpi/ic_launcher_shortcut_browser_bookmark_icon.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_list_bookmark.png b/res/drawable-mdpi/ic_list_bookmark.png
deleted file mode 100644
index 8e75121..0000000
--- a/res/drawable-mdpi/ic_list_bookmark.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_list_gps_denied.png b/res/drawable-mdpi/ic_list_gps_denied.png
deleted file mode 100644
index d53a5c1..0000000
--- a/res/drawable-mdpi/ic_list_gps_denied.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_list_gps_on.png b/res/drawable-mdpi/ic_list_gps_on.png
deleted file mode 100644
index 15ff6ee..0000000
--- a/res/drawable-mdpi/ic_list_gps_on.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_list_new_window.png b/res/drawable-mdpi/ic_list_new_window.png
deleted file mode 100644
index 61c3e63..0000000
--- a/res/drawable-mdpi/ic_list_new_window.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_list_view_holo_dark.png b/res/drawable-mdpi/ic_list_view_holo_dark.png
new file mode 100644
index 0000000..319635e
--- /dev/null
+++ b/res/drawable-mdpi/ic_list_view_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_add_bookmark.png b/res/drawable-mdpi/ic_menu_add_bookmark.png
deleted file mode 100644
index ce451b3..0000000
--- a/res/drawable-mdpi/ic_menu_add_bookmark.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_bookmarks.png b/res/drawable-mdpi/ic_menu_bookmarks.png
deleted file mode 100644
index c6a3cdb..0000000
--- a/res/drawable-mdpi/ic_menu_bookmarks.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_findonpage_normal.png b/res/drawable-mdpi/ic_menu_findonpage_normal.png
new file mode 100644
index 0000000..bea6e44
--- /dev/null
+++ b/res/drawable-mdpi/ic_menu_findonpage_normal.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_list.png b/res/drawable-mdpi/ic_menu_list.png
deleted file mode 100644
index 36bf8d6..0000000
--- a/res/drawable-mdpi/ic_menu_list.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_new_window.png b/res/drawable-mdpi/ic_menu_new_window.png
index 4fdea6c..c495162 100644
--- a/res/drawable-mdpi/ic_menu_new_window.png
+++ b/res/drawable-mdpi/ic_menu_new_window.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_thumbnail.png b/res/drawable-mdpi/ic_menu_thumbnail.png
deleted file mode 100644
index be4ed5e..0000000
--- a/res/drawable-mdpi/ic_menu_thumbnail.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_menu_windows.png b/res/drawable-mdpi/ic_menu_windows.png
deleted file mode 100644
index c33de2b..0000000
--- a/res/drawable-mdpi/ic_menu_windows.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_most_visited_holo_dark.png b/res/drawable-mdpi/ic_most_visited_holo_dark.png
new file mode 100644
index 0000000..52082bd
--- /dev/null
+++ b/res/drawable-mdpi/ic_most_visited_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_new_window_holo_dark.png b/res/drawable-mdpi/ic_new_window_holo_dark.png
new file mode 100644
index 0000000..b16aacc
--- /dev/null
+++ b/res/drawable-mdpi/ic_new_window_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_pageinfo_holo_dark.png b/res/drawable-mdpi/ic_pageinfo_holo_dark.png
new file mode 100644
index 0000000..fd9b1c0
--- /dev/null
+++ b/res/drawable-mdpi/ic_pageinfo_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_partial_secure.png b/res/drawable-mdpi/ic_partial_secure.png
new file mode 100644
index 0000000..b3ca0cc
--- /dev/null
+++ b/res/drawable-mdpi/ic_partial_secure.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_pie_back.png b/res/drawable-mdpi/ic_pie_back.png
new file mode 100644
index 0000000..daddaea
--- /dev/null
+++ b/res/drawable-mdpi/ic_pie_back.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_pie_bookmarks.png b/res/drawable-mdpi/ic_pie_bookmarks.png
new file mode 100644
index 0000000..ffa430d
--- /dev/null
+++ b/res/drawable-mdpi/ic_pie_bookmarks.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_pie_close_tab.png b/res/drawable-mdpi/ic_pie_close_tab.png
new file mode 100644
index 0000000..62396f4
--- /dev/null
+++ b/res/drawable-mdpi/ic_pie_close_tab.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_pie_forward.png b/res/drawable-mdpi/ic_pie_forward.png
new file mode 100644
index 0000000..bd8dcac
--- /dev/null
+++ b/res/drawable-mdpi/ic_pie_forward.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_pie_more.png b/res/drawable-mdpi/ic_pie_more.png
new file mode 100644
index 0000000..c96c6a4
--- /dev/null
+++ b/res/drawable-mdpi/ic_pie_more.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_pie_new_tab.png b/res/drawable-mdpi/ic_pie_new_tab.png
new file mode 100644
index 0000000..206675a
--- /dev/null
+++ b/res/drawable-mdpi/ic_pie_new_tab.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_pie_refresh.png b/res/drawable-mdpi/ic_pie_refresh.png
new file mode 100644
index 0000000..5980f8b
--- /dev/null
+++ b/res/drawable-mdpi/ic_pie_refresh.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_pie_search.png b/res/drawable-mdpi/ic_pie_search.png
new file mode 100644
index 0000000..6981697
--- /dev/null
+++ b/res/drawable-mdpi/ic_pie_search.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_pie_tabs.png b/res/drawable-mdpi/ic_pie_tabs.png
new file mode 100644
index 0000000..fda262a
--- /dev/null
+++ b/res/drawable-mdpi/ic_pie_tabs.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_pie_web.png b/res/drawable-mdpi/ic_pie_web.png
new file mode 100644
index 0000000..86e41ff
--- /dev/null
+++ b/res/drawable-mdpi/ic_pie_web.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_refresh_holo_dark.png b/res/drawable-mdpi/ic_refresh_holo_dark.png
new file mode 100644
index 0000000..0aec8a0
--- /dev/null
+++ b/res/drawable-mdpi/ic_refresh_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_search_category_bookmark.png b/res/drawable-mdpi/ic_search_category_bookmark.png
old mode 100755
new mode 100644
index d228408..4b3bd2d
--- a/res/drawable-mdpi/ic_search_category_bookmark.png
+++ b/res/drawable-mdpi/ic_search_category_bookmark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_search_category_browser.png b/res/drawable-mdpi/ic_search_category_browser.png
index da8d4e3..d721425 100644
--- a/res/drawable-mdpi/ic_search_category_browser.png
+++ b/res/drawable-mdpi/ic_search_category_browser.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_search_category_history.png b/res/drawable-mdpi/ic_search_category_history.png
old mode 100755
new mode 100644
index 12cd51c..1a3fc98
--- a/res/drawable-mdpi/ic_search_category_history.png
+++ b/res/drawable-mdpi/ic_search_category_history.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_search_category_suggest.png b/res/drawable-mdpi/ic_search_category_suggest.png
old mode 100755
new mode 100644
index a4ed7aa..0216581
--- a/res/drawable-mdpi/ic_search_category_suggest.png
+++ b/res/drawable-mdpi/ic_search_category_suggest.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_search_holo_dark.png b/res/drawable-mdpi/ic_search_holo_dark.png
new file mode 100644
index 0000000..a84edf3
--- /dev/null
+++ b/res/drawable-mdpi/ic_search_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_secure_holo_dark.png b/res/drawable-mdpi/ic_secure_holo_dark.png
new file mode 100644
index 0000000..7b10b65
--- /dev/null
+++ b/res/drawable-mdpi/ic_secure_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_settings_holo_dark.png b/res/drawable-mdpi/ic_settings_holo_dark.png
new file mode 100644
index 0000000..2ab07c4
--- /dev/null
+++ b/res/drawable-mdpi/ic_settings_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_share_holo_dark.png b/res/drawable-mdpi/ic_share_holo_dark.png
new file mode 100644
index 0000000..d02cbad
--- /dev/null
+++ b/res/drawable-mdpi/ic_share_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_stop_holo_dark.png b/res/drawable-mdpi/ic_stop_holo_dark.png
new file mode 100644
index 0000000..61edb02
--- /dev/null
+++ b/res/drawable-mdpi/ic_stop_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_tab_bookmarks_selected.png b/res/drawable-mdpi/ic_tab_bookmarks_selected.png
deleted file mode 100644
index f5e0100..0000000
--- a/res/drawable-mdpi/ic_tab_bookmarks_selected.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_tab_bookmarks_unselected.png b/res/drawable-mdpi/ic_tab_bookmarks_unselected.png
deleted file mode 100644
index 598b098..0000000
--- a/res/drawable-mdpi/ic_tab_bookmarks_unselected.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_tab_close.png b/res/drawable-mdpi/ic_tab_close.png
new file mode 100644
index 0000000..b86c714
--- /dev/null
+++ b/res/drawable-mdpi/ic_tab_close.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_tab_history_selected.png b/res/drawable-mdpi/ic_tab_history_selected.png
deleted file mode 100644
index 211e23f..0000000
--- a/res/drawable-mdpi/ic_tab_history_selected.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_tab_history_unselected.png b/res/drawable-mdpi/ic_tab_history_unselected.png
deleted file mode 100644
index df6b14b..0000000
--- a/res/drawable-mdpi/ic_tab_history_unselected.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_tab_most_visited_selected.png b/res/drawable-mdpi/ic_tab_most_visited_selected.png
deleted file mode 100644
index 50564ec..0000000
--- a/res/drawable-mdpi/ic_tab_most_visited_selected.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_tab_most_visited_unselected.png b/res/drawable-mdpi/ic_tab_most_visited_unselected.png
deleted file mode 100644
index 105ff2e..0000000
--- a/res/drawable-mdpi/ic_tab_most_visited_unselected.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/ic_voice_search_holo_dark.png b/res/drawable-mdpi/ic_voice_search_holo_dark.png
new file mode 100644
index 0000000..e7e4f68
--- /dev/null
+++ b/res/drawable-mdpi/ic_voice_search_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_web_holo_dark.png b/res/drawable-mdpi/ic_web_holo_dark.png
new file mode 100644
index 0000000..fcf6785
--- /dev/null
+++ b/res/drawable-mdpi/ic_web_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/ic_windows_holo_dark.png b/res/drawable-mdpi/ic_windows_holo_dark.png
new file mode 100644
index 0000000..7eabd08
--- /dev/null
+++ b/res/drawable-mdpi/ic_windows_holo_dark.png
Binary files differ
diff --git a/res/drawable-mdpi/list_divider_vert.9.png b/res/drawable-mdpi/list_divider_vert.9.png
new file mode 100644
index 0000000..d99730a
--- /dev/null
+++ b/res/drawable-mdpi/list_divider_vert.9.png
Binary files differ
diff --git a/res/drawable-mdpi/overlay_url_bookmark_widget_holo.9.png b/res/drawable-mdpi/overlay_url_bookmark_widget_holo.9.png
new file mode 100644
index 0000000..a72900d
--- /dev/null
+++ b/res/drawable-mdpi/overlay_url_bookmark_widget_holo.9.png
Binary files differ
diff --git a/res/drawable-mdpi/progress.9.png b/res/drawable-mdpi/progress.9.png
new file mode 100644
index 0000000..08de04c
--- /dev/null
+++ b/res/drawable-mdpi/progress.9.png
Binary files differ
diff --git a/res/drawable-mdpi/row_activated_bookmark_widget_holo.9.png b/res/drawable-mdpi/row_activated_bookmark_widget_holo.9.png
new file mode 100644
index 0000000..ed8760f
--- /dev/null
+++ b/res/drawable-mdpi/row_activated_bookmark_widget_holo.9.png
Binary files differ
diff --git a/res/drawable-mdpi/ssl_icon.png b/res/drawable-mdpi/ssl_icon.png
deleted file mode 100644
index 032e683..0000000
--- a/res/drawable-mdpi/ssl_icon.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable-mdpi/text_field_results.9.png b/res/drawable-mdpi/text_field_results.9.png
new file mode 100644
index 0000000..167c42d
--- /dev/null
+++ b/res/drawable-mdpi/text_field_results.9.png
Binary files differ
diff --git a/res/drawable-mdpi/textfield_active_holo_dark.9.png b/res/drawable-mdpi/textfield_active_holo_dark.9.png
new file mode 100644
index 0000000..7ca771f
--- /dev/null
+++ b/res/drawable-mdpi/textfield_active_holo_dark.9.png
Binary files differ
diff --git a/res/drawable-mdpi/textfield_default_holo_dark.9.png b/res/drawable-mdpi/textfield_default_holo_dark.9.png
new file mode 100644
index 0000000..621d024
--- /dev/null
+++ b/res/drawable-mdpi/textfield_default_holo_dark.9.png
Binary files differ
diff --git a/res/drawable-mdpi/thumb_bookmark_widget_folder_back_holo.png b/res/drawable-mdpi/thumb_bookmark_widget_folder_back_holo.png
new file mode 100644
index 0000000..681fb22
--- /dev/null
+++ b/res/drawable-mdpi/thumb_bookmark_widget_folder_back_holo.png
Binary files differ
diff --git a/res/drawable-mdpi/thumb_bookmark_widget_folder_holo.png b/res/drawable-mdpi/thumb_bookmark_widget_folder_holo.png
new file mode 100644
index 0000000..495598d
--- /dev/null
+++ b/res/drawable-mdpi/thumb_bookmark_widget_folder_holo.png
Binary files differ
diff --git a/res/drawable-mdpi/thumbnail_bookmarks_widget_no_bookmark_holo.png b/res/drawable-mdpi/thumbnail_bookmarks_widget_no_bookmark_holo.png
new file mode 100644
index 0000000..6ac18e7
--- /dev/null
+++ b/res/drawable-mdpi/thumbnail_bookmarks_widget_no_bookmark_holo.png
Binary files differ
diff --git a/res/drawable-mdpi/trashcan.png b/res/drawable-mdpi/trashcan.png
new file mode 100644
index 0000000..f32bf27
--- /dev/null
+++ b/res/drawable-mdpi/trashcan.png
Binary files differ
diff --git a/res/drawable-mdpi/urlbar_bg.9.png b/res/drawable-mdpi/urlbar_bg.9.png
new file mode 100644
index 0000000..18b49e7
--- /dev/null
+++ b/res/drawable-mdpi/urlbar_bg.9.png
Binary files differ
diff --git a/res/drawable-nodpi/bg_browser.png b/res/drawable-nodpi/bg_browser.png
new file mode 100644
index 0000000..c7907d7
--- /dev/null
+++ b/res/drawable-nodpi/bg_browser.png
Binary files differ
diff --git a/res/drawable-nodpi/bg_browsertabs.png b/res/drawable-nodpi/bg_browsertabs.png
new file mode 100644
index 0000000..15d3365
--- /dev/null
+++ b/res/drawable-nodpi/bg_browsertabs.png
Binary files differ
diff --git a/res/drawable-nodpi/bg_urlbar.png b/res/drawable-nodpi/bg_urlbar.png
new file mode 100644
index 0000000..ff173c4
--- /dev/null
+++ b/res/drawable-nodpi/bg_urlbar.png
Binary files differ
diff --git a/res/drawable/bookmark_list_favicon_bg.xml b/res/drawable/bookmark_list_favicon_bg.xml
new file mode 100644
index 0000000..ceb545d
--- /dev/null
+++ b/res/drawable/bookmark_list_favicon_bg.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2011 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+
+<shape xmlns:android="http://schemas.android.com/apk/res/android"
+ android:shape="rectangle">
+ <solid android:color="@color/bookmarkListFaviconBackground" />
+ <padding
+ android:left="@dimen/list_favicon_padding"
+ android:right="@dimen/list_favicon_padding"
+ android:top="@dimen/list_favicon_padding"
+ android:bottom="@dimen/list_favicon_padding" />
+ <corners android:radius="@dimen/list_favicon_corner_radius" />
+</shape>
diff --git a/res/drawable/browser_visited_tab.xml b/res/drawable/bookmark_thumb_selector.xml
similarity index 69%
copy from res/drawable/browser_visited_tab.xml
copy to res/drawable/bookmark_thumb_selector.xml
index b9d6eb7..59d9405 100644
--- a/res/drawable/browser_visited_tab.xml
+++ b/res/drawable/bookmark_thumb_selector.xml
@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2009 The Android Open Source Project
+<!-- Copyright (C) 2010 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -13,8 +13,10 @@
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_selected="true" android:drawable="@drawable/ic_tab_most_visited_selected"/>
- <item android:state_selected="false" android:drawable="@drawable/ic_tab_most_visited_unselected"/>
+
+<selector xmlns:android="http://schemas.android.com/apk/res/android"
+ android:exitFadeDuration="@android:integer/config_mediumAnimTime">
+ <item android:state_pressed="true" android:drawable="@drawable/bookmark_thumb_selector_transition" />
+ <item android:drawable="@android:color/transparent" />
</selector>
diff --git a/res/xml/bookmarkwidget.xml b/res/drawable/bookmark_thumb_selector_transition.xml
similarity index 66%
copy from res/xml/bookmarkwidget.xml
copy to res/drawable/bookmark_thumb_selector_transition.xml
index adbe5f2..07ad281 100644
--- a/res/xml/bookmarkwidget.xml
+++ b/res/drawable/bookmark_thumb_selector_transition.xml
@@ -14,11 +14,8 @@
limitations under the License.
-->
-<!-- 4x4 Widget displaying the user's bookmarks as thumbnails. -->
-<appwidget-provider xmlns:android="http://schemas.android.com/apk/res/android"
- android:minWidth="294dip"
- android:minHeight="294dip"
- android:updatePeriodMillis="3600000"
- android:initialLayout="@layout/bookmarkwidget"
- >
-</appwidget-provider>
+<transition xmlns:android="http://schemas.android.com/apk/res/android">
+ <item android:drawable="@drawable/bookmarks_widget_thumb_selector_pressed" />
+ <item android:drawable="@drawable/bookmarks_widget_thumb_selector_longpressed" />
+</transition>
+
diff --git a/res/drawable/browser_visited_tab.xml b/res/drawable/bookmark_widget_thumb_selector.xml
similarity index 69%
copy from res/drawable/browser_visited_tab.xml
copy to res/drawable/bookmark_widget_thumb_selector.xml
index b9d6eb7..d34a55d 100644
--- a/res/drawable/browser_visited_tab.xml
+++ b/res/drawable/bookmark_widget_thumb_selector.xml
@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2009 The Android Open Source Project
+<!-- Copyright (C) 2011 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -13,8 +13,10 @@
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_selected="true" android:drawable="@drawable/ic_tab_most_visited_selected"/>
- <item android:state_selected="false" android:drawable="@drawable/ic_tab_most_visited_unselected"/>
+
+<selector xmlns:android="http://schemas.android.com/apk/res/android"
+ android:exitFadeDuration="@android:integer/config_mediumAnimTime">
+ <item android:state_pressed="true" android:drawable="@drawable/bookmarks_widget_thumb_selector_pressed" />
+ <item android:drawable="@android:color/transparent" />
</selector>
diff --git a/res/drawable/browser_bookmark_tab.xml b/res/drawable/browser_bookmark_tab.xml
deleted file mode 100644
index 49b66c7..0000000
--- a/res/drawable/browser_bookmark_tab.xml
+++ /dev/null
@@ -1,20 +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.
--->
-<selector xmlns:android="http://schemas.android.com/apk/res/android">
- <item android:state_selected="true" android:drawable="@drawable/ic_tab_bookmarks_selected"/>
- <item android:state_selected="false" android:drawable="@drawable/ic_tab_bookmarks_unselected"/>
-</selector>
-
diff --git a/res/drawable/browser_widget_preview.png b/res/drawable/browser_widget_preview.png
new file mode 100644
index 0000000..7a2af05
--- /dev/null
+++ b/res/drawable/browser_widget_preview.png
Binary files differ
diff --git a/res/drawable/browser_visited_tab.xml b/res/drawable/btn_checkbox_star.xml
similarity index 71%
copy from res/drawable/browser_visited_tab.xml
copy to res/drawable/btn_checkbox_star.xml
index b9d6eb7..08a8699 100644
--- a/res/drawable/browser_visited_tab.xml
+++ b/res/drawable/btn_checkbox_star.xml
@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2009 The Android Open Source Project
+<!-- 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.
@@ -13,8 +13,10 @@
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_selected="true" android:drawable="@drawable/ic_tab_most_visited_selected"/>
- <item android:state_selected="false" android:drawable="@drawable/ic_tab_most_visited_unselected"/>
-</selector>
+<selector xmlns:android="http://schemas.android.com/apk/res/android">
+ <item android:state_checked="true"
+ android:drawable="@drawable/ic_bookmark_on_holo_dark" />
+ <item android:state_checked="false"
+ android:drawable="@drawable/ic_bookmark_off_holo_dark" />
+</selector>
diff --git a/res/drawable/browser_visited_tab.xml b/res/drawable/btn_imageview_star.xml
similarity index 71%
rename from res/drawable/browser_visited_tab.xml
rename to res/drawable/btn_imageview_star.xml
index b9d6eb7..c1bfb5d 100644
--- a/res/drawable/browser_visited_tab.xml
+++ b/res/drawable/btn_imageview_star.xml
@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2009 The Android Open Source Project
+<!-- 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.
@@ -13,8 +13,10 @@
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_selected="true" android:drawable="@drawable/ic_tab_most_visited_selected"/>
- <item android:state_selected="false" android:drawable="@drawable/ic_tab_most_visited_unselected"/>
-</selector>
+<selector xmlns:android="http://schemas.android.com/apk/res/android">
+ <item android:state_activated="true"
+ android:drawable="@drawable/ic_bookmark_on_holo_dark" />
+ <item android:state_activated="false"
+ android:drawable="@drawable/ic_bookmark_off_holo_dark" />
+</selector>
diff --git a/res/drawable/button_bg_selected.xml b/res/drawable/button_bg_selected.xml
new file mode 100644
index 0000000..d0c677b
--- /dev/null
+++ b/res/drawable/button_bg_selected.xml
@@ -0,0 +1,18 @@
+<?xml version="1.0" encoding="utf-8"?>
+ <!--
+ Copyright (C) 2010 The Android Open Source Project Licensed under the
+ Apache License, Version 2.0 (the "License"); you may not use this file
+ except in compliance with the License. You may obtain a copy of the
+ License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+ applicable law or agreed to in writing, software distributed under the
+ License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+ CONDITIONS OF ANY KIND, either express or implied. See the License for
+ the specific language governing permissions and limitations under the
+ License.
+ -->
+<shape
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:shape="rectangle">
+ <solid
+ android:color="#ff4d83ba" />
+</shape>
\ No newline at end of file
diff --git a/res/xml/bookmarkwidget.xml b/res/drawable/clear.xml
similarity index 66%
copy from res/xml/bookmarkwidget.xml
copy to res/drawable/clear.xml
index adbe5f2..267db10 100644
--- a/res/xml/bookmarkwidget.xml
+++ b/res/drawable/clear.xml
@@ -14,11 +14,10 @@
limitations under the License.
-->
-<!-- 4x4 Widget displaying the user's bookmarks as thumbnails. -->
-<appwidget-provider xmlns:android="http://schemas.android.com/apk/res/android"
- android:minWidth="294dip"
- android:minHeight="294dip"
- android:updatePeriodMillis="3600000"
- android:initialLayout="@layout/bookmarkwidget"
- >
-</appwidget-provider>
+<!-- Used by browserbarbutton to show a clear background for the non pressed
+ state -->
+<shape xmlns:android="http://schemas.android.com/apk/res/android">
+ <solid android:color="#00000000"/>
+ <padding android:left="4dp" android:top="4dp"
+ android:right="4dp" android:bottom="4dp" />
+</shape>
diff --git a/res/drawable/item_background_holo_dark.xm b/res/drawable/item_background_holo_dark.xm
new file mode 100644
index 0000000..d5fa3c0
--- /dev/null
+++ b/res/drawable/item_background_holo_dark.xm
@@ -0,0 +1,49 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2011 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+
+<selector
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:exitFadeDuration="@android:integer/config_mediumAnimTime">
+ <item
+ android:state_window_focused="false"
+ android:drawable="@color/transparent" />
+ <!--
+ Even though these two point to the same resource, have two states so the
+ drawable will invalidate itself when coming out of pressed state.
+ -->
+ <item
+ android:state_focused="true"
+ android:state_enabled="false"
+ android:state_pressed="true"
+ android:drawable="@drawable/list_selector_disabled_holo_dark" />
+ <item
+ android:state_focused="true"
+ android:state_enabled="false"
+ android:drawable="@drawable/list_selector_disabled_holo_dark" />
+ <item
+ android:state_focused="true"
+ android:state_pressed="true"
+ android:drawable="@drawable/list_selector_background_transition_holo_dark" />
+ <item
+ android:state_focused="false"
+ android:state_pressed="true"
+ android:drawable="@drawable/list_selector_background_transition_holo_dark" />
+ <item
+ android:state_focused="true"
+ android:drawable="@drawable/list_focused_holo" />
+ <item
+ android:drawable="@color/transparent" />
+</selector>
\ No newline at end of file
diff --git a/res/drawable/pattern_carbon_fiber_dark.png b/res/drawable/pattern_carbon_fiber_dark.png
deleted file mode 100644
index 07af4b6..0000000
--- a/res/drawable/pattern_carbon_fiber_dark.png
+++ /dev/null
Binary files differ
diff --git a/res/drawable/browser_visited_tab.xml b/res/drawable/suggest_item_selector.xml
similarity index 67%
copy from res/drawable/browser_visited_tab.xml
copy to res/drawable/suggest_item_selector.xml
index b9d6eb7..301584f 100644
--- a/res/drawable/browser_visited_tab.xml
+++ b/res/drawable/suggest_item_selector.xml
@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2009 The Android Open Source Project
+<!-- Copyright (C) 2010 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -13,8 +13,10 @@
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_selected="true" android:drawable="@drawable/ic_tab_most_visited_selected"/>
- <item android:state_selected="false" android:drawable="@drawable/ic_tab_most_visited_unselected"/>
-</selector>
+<selector xmlns:android="http://schemas.android.com/apk/res/android"
+ android:exitFadeDuration="@android:integer/config_mediumAnimTime">
+ <item android:state_pressed="true"
+ android:drawable="@drawable/row_activated_bookmark_widget_holo" />
+ <item android:state_pressed="false" android:drawable="@drawable/clear" />
+</selector>
diff --git a/res/drawable/browser_visited_tab.xml b/res/drawable/url_background.xml
similarity index 63%
copy from res/drawable/browser_visited_tab.xml
copy to res/drawable/url_background.xml
index b9d6eb7..f719c29 100644
--- a/res/drawable/browser_visited_tab.xml
+++ b/res/drawable/url_background.xml
@@ -1,5 +1,5 @@
<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2009 The Android Open Source Project
+<!-- Copyright (C) 2011 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -13,8 +13,13 @@
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_selected="true" android:drawable="@drawable/ic_tab_most_visited_selected"/>
- <item android:state_selected="false" android:drawable="@drawable/ic_tab_most_visited_unselected"/>
-</selector>
+<selector
+ xmlns:android="http://schemas.android.com/apk/res/android">
+ <item
+ android:state_focused="true"
+ android:drawable="@drawable/textfield_active_holo_dark" />
+ <item
+ android:state_focused="false"
+ android:drawable="@drawable/textfield_default_holo_dark" />
+</selector>
\ No newline at end of file
diff --git a/res/layout-land/http_authentication.xml b/res/layout-land/http_authentication.xml
index c008ceb..3fa7e4f 100644
--- a/res/layout-land/http_authentication.xml
+++ b/res/layout-land/http_authentication.xml
@@ -18,7 +18,7 @@
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
- android:orientation="vertical">
+ android:orientation="vertical" >
<TableLayout
android:layout_width="match_parent"
@@ -28,15 +28,11 @@
<TableRow>
<TextView android:id="@+id/username_view"
- android:textSize="18sp"
- android:textColor="@color/username_text"
android:text="@string/username"
android:gravity="right"
android:layout_marginLeft="20dip" />
<EditText android:id="@+id/username_edit"
- android:textSize="18sp"
- android:textColor="@color/username_edit"
android:scrollHorizontally="true"
android:autoText="false"
android:capitalize="none"
@@ -49,15 +45,11 @@
<TableRow>
<TextView android:id="@+id/password_view"
- android:textSize="18sp"
- android:textColor="@color/password_text"
android:text="@string/password"
android:gravity="right"
android:layout_marginLeft="20dip" />
<EditText android:id="@+id/password_edit"
- android:textSize="18sp"
- android:textColor="@color/password_edit"
android:scrollHorizontally="true"
android:autoText="false"
android:capitalize="none"
diff --git a/res/layout-land/ssl_certificate.xml b/res/layout-land/ssl_certificate.xml
index 44c5904..6505fe5 100644
--- a/res/layout-land/ssl_certificate.xml
+++ b/res/layout-land/ssl_certificate.xml
@@ -56,8 +56,6 @@
android:id="@+id/issued_to_header"
android:text="@string/issued_to"
android:textStyle="bold"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:layout_marginLeft="20dip"
@@ -69,15 +67,11 @@
<TextView
android:id="@+id/to_common_header"
android:text="@string/common_name"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip" />
<TextView
android:id="@+id/to_common"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="10dip"
android:layout_marginRight="20dip"
@@ -89,15 +83,11 @@
<TextView
android:id="@+id/to_org_header"
android:text="@string/org_name"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip" />
<TextView
android:id="@+id/to_org"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="10dip"
android:layout_marginRight="20dip"
@@ -109,15 +99,11 @@
<TextView
android:id="@+id/to_org_unit_header"
android:text="@string/org_unit"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip" />
<TextView
android:id="@+id/to_org_unit"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="10dip"
android:layout_marginRight="20dip"
@@ -129,8 +115,6 @@
android:id="@+id/issued_to_header"
android:text="@string/issued_by"
android:textStyle="bold"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:layout_marginLeft="20dip"
@@ -142,15 +126,11 @@
<TextView
android:id="@+id/by_common_header"
android:text="@string/common_name"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip" />
<TextView
android:id="@+id/by_common"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="10dip"
android:layout_marginRight="20dip"
@@ -162,15 +142,11 @@
<TextView
android:id="@+id/by_org_header"
android:text="@string/org_name"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip" />
<TextView
android:id="@+id/by_org"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="10dip"
android:layout_marginRight="20dip"
@@ -182,15 +158,11 @@
<TextView
android:id="@+id/by_org_unit_header"
android:text="@string/org_unit"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip" />
<TextView
android:id="@+id/by_org_unit"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="10dip"
android:layout_marginRight="20dip"
@@ -204,8 +176,6 @@
android:layout_width="wrap_content"
android:text="@string/validity_period"
android:textStyle="bold"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
android:layout_marginBottom="7dip" />
@@ -217,8 +187,6 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/issued_on"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip" />
@@ -226,8 +194,6 @@
android:id="@+id/issued_on"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="10dip"
android:layout_marginRight="20dip"
@@ -242,8 +208,6 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/expires_on"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip" />
@@ -251,8 +215,6 @@
android:id="@+id/expires_on"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="10dip"
android:layout_marginRight="20dip"
diff --git a/res/layout-xlarge/pick_bookmark.xml b/res/layout-xlarge/pick_bookmark.xml
new file mode 100644
index 0000000..b35dbb9
--- /dev/null
+++ b/res/layout-xlarge/pick_bookmark.xml
@@ -0,0 +1,37 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<LinearLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:orientation="vertical"
+ android:divider="?android:attr/dividerHorizontal"
+ android:showDividers="middle"
+ android:dividerPadding="16dip">
+
+ <fragment class="com.android.browser.BrowserBookmarksPage"
+ android:id="@+id/bookmarks"
+ android:layout_width="match_parent"
+ android:layout_height="0dip"
+ android:layout_weight="1"/>
+
+ <Button android:id="@+id/cancel"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@android:string/cancel"
+ style="?android:attr/buttonBarButtonStyle" />
+
+</LinearLayout>
diff --git a/res/layout/add_new_bookmark.xml b/res/layout/add_new_bookmark.xml
index d11a68a..53f7554 100644
--- a/res/layout/add_new_bookmark.xml
+++ b/res/layout/add_new_bookmark.xml
@@ -31,7 +31,7 @@
android:layout_marginLeft="5dip"
android:layout_marginRight="11dip"
android:focusable="false"
- android:src="@drawable/ic_list_bookmark"
+ android:src="@drawable/ic_bookmark_on_holo_dark"
android:scaleType="fitCenter"
/>
<LinearLayout
diff --git a/res/layout/empty_history.xml b/res/layout/add_to_option.xml
similarity index 69%
rename from res/layout/empty_history.xml
rename to res/layout/add_to_option.xml
index 4484a16..4cfa9f8 100644
--- a/res/layout/empty_history.xml
+++ b/res/layout/add_to_option.xml
@@ -1,26 +1,21 @@
<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2008 The Android Open Source Project
+<!-- Copyright (C) 2011 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
-
+
http://www.apache.org/licenses/LICENSE-2.0
-
+
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
-->
-
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
- android:id="@+id/empty_view"
android:layout_width="match_parent"
- android:layout_height="match_parent"
- android:text="@string/empty_history"
- android:background="@color/black"
- android:textColor="@color/white"
- android:gravity="center"
- android:textStyle="bold"
- />
+ android:layout_height="wrap_content"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:gravity="center_vertical"
+ android:minHeight="?android:attr/listPreferredItemHeight" />
diff --git a/res/layout/autofill_settings_fragment.xml b/res/layout/autofill_settings_fragment.xml
new file mode 100644
index 0000000..b92c149
--- /dev/null
+++ b/res/layout/autofill_settings_fragment.xml
@@ -0,0 +1,268 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+
+<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent">
+
+ <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:orientation="vertical">
+
+ <View
+ android:layout_height="10dip"
+ android:layout_width="match_parent" />
+
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:text="@string/autofill_profile_editor_heading" />
+
+ <View
+ android:layout_height="12dip"
+ android:layout_width="match_parent" />
+
+ <TableLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:shrinkColumns="1"
+ android:stretchColumns="1">
+ <TableRow>
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:text="@string/autofill_profile_editor_name" />
+ <EditText android:id="@+id/autofill_profile_editor_name_edit"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:inputType="textPersonName|textCapWords"
+ android:singleLine="true" />
+ </TableRow>
+ <TableRow>
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:text="@string/autofill_profile_editor_company_name" />
+ <EditText android:id="@+id/autofill_profile_editor_company_name_edit"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:inputType="textCapWords"
+ android:singleLine="true" />
+ </TableRow>
+ <TableRow>
+ <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_margin="2dip"
+ android:orientation="vertical">
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:text="@string/autofill_profile_editor_address_line_1" />
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:textAppearance="?android:attr/textAppearanceSmall"
+ android:text="@string/autofill_profile_editor_address_line_1_hint" />
+ </LinearLayout>
+ <EditText android:id="@+id/autofill_profile_editor_address_line_1_edit"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:inputType="textCapWords"
+ android:singleLine="true" />
+ </TableRow>
+ <TableRow>
+ <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_margin="2dip"
+ android:orientation="vertical">
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:text="@string/autofill_profile_editor_address_line_2" />
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:textAppearance="?android:attr/textAppearanceSmall"
+ android:text="@string/autofill_profile_editor_address_line_2_hint" />
+ </LinearLayout>
+ <EditText android:id="@+id/autofill_profile_editor_address_line_2_edit"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:gravity="bottom"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:inputType="textCapWords"
+ android:singleLine="true" />
+ </TableRow>
+ <TableRow>
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:text="@string/autofill_profile_editor_city" />
+ <EditText android:id="@+id/autofill_profile_editor_city_edit"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:inputType="textCapWords"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:singleLine="true" />
+ </TableRow>
+ <TableRow>
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:text="@string/autofill_profile_editor_state" />
+ <EditText android:id="@+id/autofill_profile_editor_state_edit"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:inputType="textCapWords"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:singleLine="true" />
+ </TableRow>
+ <TableRow>
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:text="@string/autofill_profile_editor_zip_code" />
+ <EditText android:id="@+id/autofill_profile_editor_zip_code_edit"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:inputType="textCapCharacters"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:singleLine="true" />
+ </TableRow>
+ <TableRow>
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:text="@string/autofill_profile_editor_country" />
+ <EditText android:id="@+id/autofill_profile_editor_country_edit"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:inputType="textCapWords"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:singleLine="true" />
+ </TableRow>
+ <TableRow>
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:text="@string/autofill_profile_editor_phone_number" />
+ <EditText android:id="@+id/autofill_profile_editor_phone_number_edit"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:singleLine="true"
+ android:phoneNumber="true" />
+ </TableRow>
+ <TableRow>
+ <TextView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:text="@string/autofill_profile_editor_email_address" />
+ <EditText android:id="@+id/autofill_profile_editor_email_address_edit"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:layout_margin="2dip"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:inputType="textEmailAddress"
+ android:singleLine="true" />
+ </TableRow>
+ </TableLayout>
+
+ <View
+ android:layout_height="12dip"
+ android:layout_width="match_parent" />
+
+ <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="horizontal"
+ android:gravity="center">
+ <Button
+ android:id="@+id/autofill_profile_editor_save_button"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:text="@string/autofill_profile_editor_save_profile"
+ android:textAppearance="?android:attr/textAppearanceMedium" />
+
+ <Button
+ android:id="@+id/autofill_profile_editor_cancel_button"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:text="@string/cancel"
+ android:textAppearance="?android:attr/textAppearanceMedium" />
+
+ <Button
+ android:id="@+id/autofill_profile_editor_delete_button"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:text="@string/autofill_profile_editor_delete_profile"
+ android:textAppearance="?android:attr/textAppearanceMedium" />
+ </LinearLayout>
+ </LinearLayout>
+</ScrollView>
diff --git a/res/layout/bookmark_list.xml b/res/layout/bookmark_list.xml
new file mode 100644
index 0000000..7413ca8
--- /dev/null
+++ b/res/layout/bookmark_list.xml
@@ -0,0 +1,42 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+
+<LinearLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:id="@+id/list_item"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:minHeight="@dimen/widgetItemMinHeight"
+ android:orientation="horizontal"
+ android:paddingLeft="16dip">
+ <ImageView
+ android:id="@+id/favicon"
+ android:layout_height="32dip"
+ android:layout_width="32dip"
+ android:layout_gravity="center_vertical"
+ android:background="@drawable/bookmark_list_favicon_bg"
+ android:scaleType="fitXY" />
+ <TextView
+ android:id="@+id/label"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_gravity="center_vertical"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:paddingLeft="16dip"
+ android:maxLines="1"
+ android:scrollHorizontally="true"
+ android:ellipsize="marquee"/>
+</LinearLayout>
diff --git a/res/layout/bookmark_thumbnail.xml b/res/layout/bookmark_thumbnail.xml
index 1f017d0..c545fa4 100644
--- a/res/layout/bookmark_thumbnail.xml
+++ b/res/layout/bookmark_thumbnail.xml
@@ -21,59 +21,42 @@
android:padding="0dip"
>
- <ImageView android:id="@+id/thumb"
+ <ImageView
+ android:id="@+id/thumb"
android:src="@drawable/browser_thumbnail"
- android:scaleType="center"
- android:layout_height="wrap_content"
- android:layout_width="wrap_content"
- android:layout_gravity="center"
+ android:scaleType="centerCrop"
+ android:layout_height="@dimen/bookmarkThumbnailHeight"
+ android:layout_width="@dimen/bookmarkThumbnailWidth"
+ android:layout_centerHorizontal="true"
+ android:background="@drawable/border_thumb_bookmarks_widget_holo"
/>
- <!-- FIXME: Want to have a gradient over the thumb -->
-
- <!-- This holds the star for addbookmark -->
- <LinearLayout android:id="@+id/holder"
- android:layout_height="match_parent"
- android:layout_width="match_parent"
- android:orientation="horizontal"
- android:background="#99000000"
- android:gravity="center"
- android:layout_alignBottom="@+id/thumb"
- android:layout_alignTop="@+id/thumb"
- >
- <ImageView
- android:layout_height="wrap_content"
- android:layout_width="wrap_content"
- android:src="@drawable/ic_list_bookmark"
- />
- <TextView
- android:layout_height="wrap_content"
- android:layout_width="wrap_content"
- android:textAppearance="?android:attr/textAppearanceSmall"
- android:textStyle="bold"
- android:textColor="@color/white"
- android:text="@string/add_bookmark_short"
- />
- </LinearLayout>
+ <ImageView
+ android:id="@+id/divider"
+ android:src="?android:attr/dividerVertical"
+ android:layout_width="wrap_content"
+ android:layout_height="24dip"
+ android:layout_below="@+id/thumb"
+ android:layout_alignLeft="@+id/thumb"
+ android:scaleType="fitXY"
+ android:layout_marginTop="12dip"
+ />
<TextView android:id="@+id/label"
android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:layout_gravity="bottom"
- android:textAppearance="?android:attr/textAppearanceSmall"
- android:textStyle="bold"
- android:textColor="@color/white"
- android:maxLines="1"
- android:paddingLeft="2dip"
- android:paddingRight="2dip"
- android:paddingTop="0dip"
- android:paddingBottom="0dip"
- android:layout_marginTop="0dip"
- android:scrollHorizontally="true"
- android:ellipsize="marquee"
- android:layout_below="@+id/thumb"
- android:layout_alignLeft="@+id/thumb"
+ android:layout_height="match_parent"
+ android:layout_toRightOf="@id/divider"
+ android:layout_alignTop="@id/divider"
+ android:layout_alignBottom="@id/divider"
android:layout_alignRight="@+id/thumb"
+ android:paddingLeft="8dip"
+ android:paddingRight="2dip"
+ android:gravity="center_vertical"
+ android:singleLine="true"
+ android:ellipsize="marquee"
+ android:typeface="sans"
+ android:textSize="14sp"
+ android:textColor="#AAAAAA"
/>
</RelativeLayout>
diff --git a/res/layout/bookmarks.xml b/res/layout/bookmarks.xml
new file mode 100644
index 0000000..81327e4
--- /dev/null
+++ b/res/layout/bookmarks.xml
@@ -0,0 +1,69 @@
+<?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:id="@+id/bookmarks"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:orientation="vertical"
+ android:paddingTop="@dimen/combo_paddingTop"
+ android:paddingLeft="@dimen/combo_paddingLeftRight"
+ android:paddingRight="@dimen/combo_paddingLeftRight">
+
+ <FrameLayout
+ android:id="@+id/header_container"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:visibility="gone" />
+
+ <FrameLayout
+ android:layout_width="match_parent"
+ android:layout_height="match_parent">
+ <GridView
+ android:id="@+id/grid"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ android:layout_gravity="center_horizontal"
+ android:horizontalSpacing="@dimen/combo_horizontalSpacing"
+ android:verticalSpacing="40dip"
+ android:scrollbarStyle="insideInset"
+ android:listSelector="@drawable/bookmark_thumb_selector"
+ android:drawSelectorOnTop="true"
+ android:focusable="true"
+ android:focusableInTouchMode="true"
+ android:numColumns="auto_fit"
+ android:stretchMode="spacingWidth" />
+ <ListView
+ android:id="@+id/list"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:listSelector="@drawable/bookmark_thumb_selector"
+ android:drawSelectorOnTop="true"
+ android:focusable="true"
+ android:focusableInTouchMode="true"
+ android:visibility="gone"/>
+ <TextView
+ android:id="@android:id/empty"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_gravity="center"
+ android:textAppearance="?android:attr/textAppearanceLarge"
+ android:text="@string/empty_bookmarks_folder"
+ android:visibility="gone" />
+ </FrameLayout>
+
+</LinearLayout>
diff --git a/res/xml/bookmarkwidget.xml b/res/layout/bookmarks_header.xml
similarity index 66%
rename from res/xml/bookmarkwidget.xml
rename to res/layout/bookmarks_header.xml
index adbe5f2..ba8cf2c 100644
--- a/res/xml/bookmarkwidget.xml
+++ b/res/layout/bookmarks_header.xml
@@ -14,11 +14,8 @@
limitations under the License.
-->
-<!-- 4x4 Widget displaying the user's bookmarks as thumbnails. -->
-<appwidget-provider xmlns:android="http://schemas.android.com/apk/res/android"
- android:minWidth="294dip"
- android:minHeight="294dip"
- android:updatePeriodMillis="3600000"
- android:initialLayout="@layout/bookmarkwidget"
- >
-</appwidget-provider>
+<com.android.browser.BreadCrumbView
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:id="@+id/crumbs"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent" />
diff --git a/res/drawable/browser_history_tab.xml b/res/layout/bookmarks_history.xml
similarity index 70%
rename from res/drawable/browser_history_tab.xml
rename to res/layout/bookmarks_history.xml
index 1fbd0ce..5622917 100644
--- a/res/drawable/browser_history_tab.xml
+++ b/res/layout/bookmarks_history.xml
@@ -4,17 +4,18 @@
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
-
+
http://www.apache.org/licenses/LICENSE-2.0
-
+
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT 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_selected="true" android:drawable="@drawable/ic_tab_history_selected"/>
- <item android:state_selected="false" android:drawable="@drawable/ic_tab_history_unselected"/>
-</selector>
-
+<FrameLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:id="@+id/fragment"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:background="@drawable/bg_browser" />
diff --git a/res/layout/bookmarkthumbnailwidget.xml b/res/layout/bookmarkthumbnailwidget.xml
new file mode 100644
index 0000000..12191e8
--- /dev/null
+++ b/res/layout/bookmarkthumbnailwidget.xml
@@ -0,0 +1,52 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<RelativeLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:paddingTop="4dip"
+ android:paddingBottom="20dip"
+ android:paddingLeft="12dip"
+ android:paddingRight="12dip">
+ <GridView
+ android:id="@+id/bookmarks_list"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:numColumns="2"
+ android:paddingBottom="6dip"
+ android:paddingRight="3dip"
+ android:paddingLeft="3dip"
+ android:stretchMode="columnWidth"
+ android:horizontalSpacing="@dimen/widgetHorizontalSpacing"
+ android:verticalSpacing="@dimen/widgetVerticalSpacing"
+ android:drawSelectorOnTop="true"
+ android:listSelector="@drawable/bookmark_widget_thumb_selector"
+ android:fadingEdgeLength="24dp"
+ android:scrollbarStyle="outsideOverlay" />
+
+ <ImageButton
+ android:id="@+id/app_shortcut"
+ android:layout_width="56dip"
+ android:layout_height="56dip"
+ android:layout_alignParentBottom="true"
+ android:layout_alignParentRight="true"
+ android:layout_marginRight="4dip"
+ android:layout_marginBottom="6dip"
+ android:scaleType="centerInside"
+ android:src="@mipmap/ic_launcher_browser"
+ android:background="@drawable/bookmark_widget_thumb_selector"
+ android:padding="4dip" />
+</RelativeLayout>
diff --git a/res/layout/bookmarkthumbnailwidget_item.xml b/res/layout/bookmarkthumbnailwidget_item.xml
new file mode 100644
index 0000000..b67b386
--- /dev/null
+++ b/res/layout/bookmarkthumbnailwidget_item.xml
@@ -0,0 +1,61 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+
+<RelativeLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:id="@+id/list_item"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content">
+ <ImageView
+ android:id="@+id/thumb"
+ android:src="@drawable/browser_thumbnail"
+ android:layout_width="match_parent"
+ android:layout_height="@dimen/widgetThumbnailHeight"
+ android:scaleType="centerCrop"
+ android:cropToPadding="true"
+ android:background="@drawable/border_thumb_bookmarks_widget_holo" />
+ <LinearLayout
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:layout_alignBottom="@id/thumb"
+ android:background="@drawable/overlay_url_bookmark_widget_holo"
+ android:layout_marginLeft="2dip"
+ android:layout_marginRight="2dip"
+ android:layout_marginBottom="2dip">
+ <ImageView
+ android:id="@+id/favicon"
+ android:src="@drawable/app_web_browser_sm"
+ android:layout_width="@dimen/favicon_size"
+ android:layout_height="@dimen/favicon_size"
+ android:layout_gravity="center_vertical"
+ android:layout_marginLeft="4dip"
+ android:layout_marginRight="8dip"
+ android:layout_marginTop="4dip"
+ android:layout_marginBottom="4dip"
+ android:scaleType="centerInside" />
+ <TextView
+ android:id="@+id/label"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:layout_gravity="center_vertical"
+ android:singleLine="true"
+ android:ellipsize="end"
+ android:textSize="14sp"
+ android:typeface="sans"
+ android:textStyle="bold"
+ android:textColor="@android:color/white" />
+ </LinearLayout>
+</RelativeLayout>
diff --git a/res/layout/bookmarkwidget.xml b/res/layout/bookmarkwidget.xml
deleted file mode 100644
index 2416e4f..0000000
--- a/res/layout/bookmarkwidget.xml
+++ /dev/null
@@ -1,79 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2010 The Android Open Source Project
-
- Licensed under the Apache License, Version 2.0 (the "License");
- you may not use this file except in compliance with the License.
- You may obtain a copy of the License at
-
- http://www.apache.org/licenses/LICENSE-2.0
-
- Unless required by applicable law or agreed to in writing, software
- distributed under the License is distributed on an "AS IS" BASIS,
- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- See the License for the specific language governing permissions and
- limitations under the License.
--->
-
-<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:layout_width="match_parent"
- android:layout_height="match_parent"
- android:padding="8dip"
- android:orientation="vertical"
- android:background="@drawable/appwidget_bg" >
-
- <LinearLayout
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:orientation="horizontal" >
-
- <ImageView
- android:id="@+id/previous"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:padding="10dip"
- android:src="@drawable/ic_btn_find_prev" />
-
- <TextView
- android:id="@+id/title"
- android:layout_width="0dip"
- android:layout_height="wrap_content"
- android:layout_weight="1"
- android:gravity="center"
- android:layout_gravity="center"
- android:text="@string/title_bar_loading"
- android:textAppearance="?android:attr/textAppearanceMedium"
- android:textColor="?android:attr/textColorPrimary" />
-
- <ImageView
- android:id="@+id/next"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:padding="10dip"
- android:src="@drawable/ic_btn_find_next" />
-
- </LinearLayout>
-
- <ImageView
- android:id="@+id/image"
- android:visibility="gone"
- android:layout_width="match_parent"
- android:layout_height="match_parent"
- android:scaleType="fitXY"
- android:padding="5dip"
- android:gravity="center" />
-
- <RelativeLayout
- android:id="@+id/progress"
- android:visibility="visible"
- android:layout_width="match_parent"
- android:layout_height="match_parent"
- android:gravity="center" >
-
- <ProgressBar
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:indeterminateOnly="true" />
-
- </RelativeLayout>
-
-</LinearLayout>
diff --git a/res/layout/browser_add_bookmark.xml b/res/layout/browser_add_bookmark.xml
index e8a08a4..f5c09a9 100644
--- a/res/layout/browser_add_bookmark.xml
+++ b/res/layout/browser_add_bookmark.xml
@@ -15,72 +15,190 @@
-->
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:layout_width="match_parent"
+ android:layout_width="@dimen/add_bookmark_width"
android:layout_height="wrap_content"
android:orientation="vertical"
>
-
- <ImageView android:id="@+id/titleDivider"
- android:layout_width="match_parent"
- android:layout_height="1dip"
- android:scaleType="fitXY"
- android:gravity="fill_horizontal"
- android:src="@drawable/dialog_divider_horizontal_light"
- android:layout_marginLeft="10dip"
- android:layout_marginRight="10dip"/>
-
- <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ <RelativeLayout android:id="@+id/crumb_holder"
android:layout_width="match_parent"
android:layout_height="wrap_content"
+ android:minHeight="?android:attr/listPreferredItemHeight"
+ android:gravity="center_vertical"
+ android:visibility="gone"
+ android:paddingLeft="5dip"
+ android:paddingRight="5dip"
+ >
+ <com.android.browser.BreadCrumbView android:id="@+id/crumbs"
+ android:layout_width="wrap_content"
+ android:layout_height="?android:attr/listPreferredItemHeight"
+ android:layout_alignParentLeft="true"
+ android:layout_toLeftOf="@+id/add_divider"
+ android:layout_centerVertical="true"
+ />
+ <TextView
+ android:id="@+id/add_new_folder"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_alignParentRight="true"
+ android:layout_alignBaseline="@+id/crumbs"
+ android:drawableLeft="@drawable/ic_add_string"
+ android:gravity="center_vertical"
+ android:text="@string/new_folder"
+ android:visibility="gone"
+ android:layout_centerVertical="true"
+ android:textAppearance="?android:attr/textAppearanceMedium" />
+ <ImageView android:id="@+id/add_divider"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_toLeftOf="@+id/add_new_folder"
+ android:src="@drawable/crumb_divider"
+ android:layout_centerVertical="true"
+ />
+ </RelativeLayout>
+ <LinearLayout android:id="@+id/title_holder"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="horizontal"
+ android:minHeight="?android:attr/listPreferredItemHeight"
+ android:paddingLeft="5dip"
+ android:paddingRight="5dip"
+ >
+ <TextView android:id="@+id/fake_title"
+ android:layout_width="0dip"
+ android:layout_weight="1"
+ android:layout_height="wrap_content"
+ android:layout_gravity="center_vertical"
+ android:gravity="center_vertical"
+ android:drawableLeft="@drawable/ic_bookmark_on_holo_dark"
+ android:text="@string/bookmark_this_page"
+ android:textAppearance="?android:attr/textAppearanceMedium" />
+ <ImageView android:id="@+id/remove_divider"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_gravity="center_vertical"
+ android:src="@drawable/crumb_divider"
+ android:layout_centerVertical="true"
+ android:visibility="gone"
+ />
+ <TextView android:id="@+id/remove"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_gravity="center_vertical"
+ android:gravity="center_vertical"
+ android:text="@string/remove"
+ android:drawableLeft="@drawable/trashcan"
+ android:visibility="gone"
+ android:textAppearance="?android:attr/textAppearanceMedium" />
+ </LinearLayout>
+ <View android:id="@+id/titleDivider"
+ android:layout_width="match_parent"
+ android:layout_height="1dip"
+ android:gravity="fill_horizontal"
+ android:background="?android:attr/colorForeground"
+ />
+
+ <TableLayout android:id="@+id/default_view"
+ android:layout_width="match_parent"
+ android:layout_height="@dimen/folder_selector_height"
android:layout_weight="1"
- android:orientation="vertical"
- android:paddingTop="5dip"
- android:paddingBottom="13dip"
+ android:stretchColumns="1"
+ android:shrinkColumns="1"
+ android:paddingTop="20dip"
android:paddingLeft="20dip"
android:paddingRight="20dip" >
-
+ <TableRow>
<TextView
android:id="@+id/titleText"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
+ android:layout_marginBottom="40dip"
android:text="@string/name"
- android:gravity="left"
android:textAppearance="?android:attr/textAppearanceMedium" />
<EditText
android:id="@+id/title"
android:layout_height="wrap_content"
- android:layout_width="250dip"
+ android:layout_width="wrap_content"
+ android:layout_marginRight="20dip"
+ android:layout_marginLeft="20dip"
android:gravity="fill_horizontal"
android:inputType="textCapSentences"
- android:selectAllOnFocus="true"
+ android:ellipsize="end"
android:textAppearance="?android:attr/textAppearanceMedium" />
-
+ </TableRow>
-
+ <TableRow
+ android:id="@+id/row_address">
<TextView
android:id="@+id/addressText"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:text="@string/location"
android:gravity="left"
+ android:layout_marginBottom="40dip"
android:textAppearance="?android:attr/textAppearanceMedium" />
<EditText
android:id="@+id/address"
android:layout_height="wrap_content"
- android:layout_width="250dip"
+ android:layout_width="wrap_content"
+ android:layout_marginRight="20dip"
+ android:layout_marginLeft="20dip"
android:hint="@string/http"
android:gravity="fill_horizontal"
android:inputType="textUri"
- android:selectAllOnFocus="true"
+ android:ellipsize="end"
+ android:textAppearance="?android:attr/textAppearanceMedium" />
+ </TableRow>
+ <TableRow>
+ <TextView
+ android:id="@+id/add_to"
+ android:layout_height="wrap_content"
+ android:layout_width="wrap_content"
+ android:text="@string/containing_folder"
+ android:textAppearance="?android:attr/textAppearanceMedium" />
+
+ <view class="com.android.browser.addbookmark.FolderSpinner"
+ android:id="@+id/folder"
+ android:layout_height="wrap_content"
+ android:layout_width="wrap_content"
+ android:layout_marginRight="20dip"
+ android:layout_marginLeft="20dip"
+ android:spinnerMode="dropdown"
+ android:gravity="center_vertical"
+ />
+ </TableRow>
+ </TableLayout>
+
+ <LinearLayout android:id="@+id/folder_selector"
+ android:layout_width="match_parent"
+ android:layout_height="@dimen/folder_selector_height"
+ android:orientation="vertical"
+ android:visibility="gone"
+ >
+
+ <view class="com.android.browser.AddBookmarkPage$CustomListView"
+ android:id="@+id/list"
+ android:layout_marginLeft="16dip"
+ android:layout_marginRight="16dip"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ />
+ <TextView
+ android:id="@+id/empty"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:visibility="gone"
+ android:layout_marginLeft="16dip"
+ android:layout_marginTop="16dip"
+ android:text="@string/no_subfolders"
+ android:textStyle="italic"
android:textAppearance="?android:attr/textAppearanceMedium" />
</LinearLayout>
-
+
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
- android:background="#c6c3c6"
android:minHeight="54dip"
android:orientation="horizontal"
android:paddingTop="4dip"
@@ -103,4 +221,3 @@
</LinearLayout>
</LinearLayout>
-
diff --git a/res/layout/browser_find.xml b/res/layout/browser_find.xml
deleted file mode 100644
index e2f0cf6..0000000
--- a/res/layout/browser_find.xml
+++ /dev/null
@@ -1,76 +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:id="@+id/findControls"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:paddingTop="5dip"
- android:paddingLeft="4dip"
- android:paddingRight="4dip"
- android:paddingBottom="1dip"
- android:background="@android:drawable/bottom_bar">
- <ImageButton
- android:src="@drawable/ic_btn_find_prev"
- android:id="@+id/previous"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- />
-
- <ImageButton
- android:src="@drawable/ic_btn_find_next"
- android:id="@+id/next"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- />
-
- <LinearLayout
- android:layout_height="wrap_content"
- android:layout_width="0dip"
- android:layout_weight="1"
- android:orientation="vertical"
- android:layout_marginRight="6dip"
- >
- <EditText android:id="@+id/edit"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:scrollHorizontally="true"
- android:inputType="text"
- android:hint="@string/find_dot"
- />
- <LinearLayout android:id="@+id/matches_view"
- android:layout_height="wrap_content"
- android:layout_width="wrap_content"
- android:orientation="horizontal"
- android:layout_gravity="right"
- android:visibility="invisible"
- >
- <TextView android:id="@+id/matches"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:layout_gravity="right"
- android:textAppearance="?android:attr/textAppearanceSmall"
- android:textColor="?android:attr/textColorSecondaryInverse"
- />
- </LinearLayout>
- </LinearLayout>
- <ImageButton android:id="@+id/done"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- android:src="@drawable/ic_btn_close_panel"
- />
-</LinearLayout>
-
diff --git a/res/layout/browser_select.xml b/res/layout/browser_select.xml
deleted file mode 100644
index b30be8d..0000000
--- a/res/layout/browser_select.xml
+++ /dev/null
@@ -1,67 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2010 The Android Open Source Project
-
- Licensed under the Apache License, Version 2.0 (the "License");
- you may not use this file except in compliance with the License.
- You may obtain a copy of the License at
-
- http://www.apache.org/licenses/LICENSE-2.0
-
- Unless required by applicable law or agreed to in writing, software
- distributed under the License is distributed on an "AS IS" BASIS,
- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- See the License for the specific language governing permissions and
- limitations under the License.
--->
-
-<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
- android:id="@+id/selectControls"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- android:paddingTop="5dip"
- android:paddingLeft="4dip"
- android:paddingRight="4dip"
- android:paddingBottom="1dip"
- android:background="@android:drawable/bottom_bar">
- <ImageButton
- android:src="@drawable/ic_btn_copy"
- android:id="@+id/copy"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- />
-
- <ImageButton
- android:src="@drawable/ic_btn_share"
- android:id="@+id/share"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- />
-
- <ImageButton
- android:src="@drawable/ic_btn_select_all"
- android:id="@+id/select_all"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- />
-
- <ImageButton
- android:src="@drawable/ic_btn_find"
- android:id="@+id/find"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- />
-
- <LinearLayout
- android:layout_height="fill_parent"
- android:layout_width="fill_parent"
- android:layout_weight="1"
- />
-
- <ImageButton
- android:src="@drawable/ic_btn_close_panel"
- android:id="@+id/done"
- android:layout_width="wrap_content"
- android:layout_height="wrap_content"
- />
-</LinearLayout>
-
diff --git a/res/layout/browser_subwindow.xml b/res/layout/browser_subwindow.xml
index adf3284..a3868cd 100644
--- a/res/layout/browser_subwindow.xml
+++ b/res/layout/browser_subwindow.xml
@@ -28,12 +28,6 @@
android:layout_height="match_parent"
android:orientation="vertical"
android:background="@android:drawable/dialog_frame" >
- <WebView android:id="@+id/webview"
- android:layout_width="match_parent"
- android:layout_height="match_parent"
- android:fadeScrollbars="true"
- android:scrollbarStyle="outsideOverlay"
- android:layout_weight="1" />
</LinearLayout>
</FrameLayout>
<LinearLayout
diff --git a/res/layout/custom_screen.xml b/res/layout/custom_screen.xml
index 90dc324..525f30c 100644
--- a/res/layout/custom_screen.xml
+++ b/res/layout/custom_screen.xml
@@ -22,6 +22,7 @@
android:layout_height="match_parent"
/>
<LinearLayout android:orientation="vertical"
+ android:id="@+id/vertical_layout"
android:layout_width="match_parent"
android:layout_height="match_parent">
diff --git a/res/layout/folder_list_item.xml b/res/layout/folder_list_item.xml
new file mode 100644
index 0000000..46cda37
--- /dev/null
+++ b/res/layout/folder_list_item.xml
@@ -0,0 +1,37 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<LinearLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="horizontal">
+ <ImageView
+ android:id="@+id/icon1"
+ style="@style/HoloIcon"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:minHeight="?android:attr/listPreferredItemHeight"
+ android:src="@drawable/ic_folder_holo_dark" />
+ <TextView
+ android:id="@android:id/text1"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:gravity="center_vertical"
+ android:paddingLeft="6dip"
+ android:minHeight="?android:attr/listPreferredItemHeight" />
+</LinearLayout>
diff --git a/res/layout/history.xml b/res/layout/history.xml
new file mode 100644
index 0000000..f7d2c7c
--- /dev/null
+++ b/res/layout/history.xml
@@ -0,0 +1,37 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+
+<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent"
+>
+
+ <ViewStub
+ android:id="@+id/pref_stub"
+ android:layout_height="match_parent"
+ android:layout_width="match_parent"
+ android:inflatedId="@+id/history" />
+
+ <TextView android:id="@android:id/empty"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_gravity="center"
+ android:textAppearance="?android:attr/textAppearanceLarge"
+ android:text="@string/empty_history"
+ android:visibility="gone"
+ />
+
+</FrameLayout>
diff --git a/res/layout/history_header.xml b/res/layout/history_header.xml
index e03b009..f77a697 100644
--- a/res/layout/history_header.xml
+++ b/res/layout/history_header.xml
@@ -21,4 +21,5 @@
android:textAppearance="?android:attr/textAppearanceMedium"
android:paddingLeft="35dip"
android:gravity="center_vertical"
- />
\ No newline at end of file
+ android:background="?android:attr/activatedBackgroundIndicator"
+ />
diff --git a/res/layout/history_item.xml b/res/layout/history_item.xml
index a0b031a..3b3dd7a 100644
--- a/res/layout/history_item.xml
+++ b/res/layout/history_item.xml
@@ -19,22 +19,22 @@
android:layout_height="wrap_content"
android:minHeight="?android:attr/listPreferredItemHeight"
android:orientation="horizontal"
- android:paddingLeft="6dip"
- android:gravity="center_vertical"
+ android:paddingLeft="20dip"
>
<ImageView android:id="@+id/favicon"
- android:layout_width="20dip"
- android:layout_height="20dip"
- android:layout_marginLeft="5dip"
- android:layout_marginRight="11dip"
- android:padding="2dip"
- android:background="@drawable/fav_icn_background"
+ android:layout_width="32dip"
+ android:layout_height="32dip"
+ android:layout_gravity="center_vertical"
+ android:scaleType="fitXY"
+ android:background="@drawable/bookmark_list_favicon_bg"
android:src="@drawable/app_web_browser_sm"
/>
<LinearLayout android:layout_width="0dip"
android:layout_weight="1"
android:layout_height="wrap_content"
android:orientation="vertical"
+ android:paddingLeft="16dip"
+ android:layout_gravity="center_vertical"
>
<TextView android:id="@+id/title"
android:textAppearance="?android:attr/textAppearanceMedium"
@@ -55,9 +55,13 @@
</LinearLayout>
<CheckBox android:id="@+id/star"
android:layout_width="wrap_content"
- android:layout_height="fill_parent"
- android:paddingRight="6dip"
+ android:layout_height="wrap_content"
+ android:paddingTop="16dip"
+ android:paddingBottom="16dip"
+ android:paddingRight="20dip"
+ android:paddingLeft="16dip"
android:focusable="false"
- android:button="@android:drawable/btn_star"
+ android:button="@drawable/btn_checkbox_star"
+ android:layout_gravity="center_vertical"
/>
</LinearLayout>
diff --git a/res/layout/http_authentication.xml b/res/layout/http_authentication.xml
index cc785c9..cee3a42 100644
--- a/res/layout/http_authentication.xml
+++ b/res/layout/http_authentication.xml
@@ -18,14 +18,13 @@
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="center_horizontal"
- android:orientation="vertical">
+ android:orientation="vertical"
+ >
<TextView
android:id="@+id/username_view"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
- android:textSize="18sp"
- android:textColor="@color/username_text"
android:text="@string/username"
android:gravity="left"
android:layout_marginTop="12dip"
@@ -34,8 +33,6 @@
<EditText
android:id="@+id/username_edit"
- android:textSize="18sp"
- android:textColor="@color/username_edit"
android:scrollHorizontally="true"
android:inputType="text"
android:gravity="fill_horizontal"
@@ -48,8 +45,6 @@
android:id="@+id/password_view"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
- android:textSize="18sp"
- android:textColor="@color/password_text"
android:text="@string/password"
android:gravity="left"
android:layout_marginLeft="20dip"
@@ -57,8 +52,6 @@
<EditText
android:id="@+id/password_edit"
- android:textSize="18sp"
- android:textColor="@color/password_edit"
android:scrollHorizontally="true"
android:inputType="textPassword"
android:gravity="fill_horizontal"
diff --git a/res/layout/import_bookmarks_dialog.xml b/res/layout/import_bookmarks_dialog.xml
new file mode 100644
index 0000000..f10f35d
--- /dev/null
+++ b/res/layout/import_bookmarks_dialog.xml
@@ -0,0 +1,47 @@
+<?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:layout_width="match_parent"
+ android:layout_height="match_parent"
+ android:orientation="vertical"
+ android:padding="8dip"
+>
+ <TextView
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/import_bookmarks_dialog_description"
+ />
+
+ <LinearLayout android:id="@+id/accountList"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="vertical"
+ />
+
+ <Button android:id="@+id/remove"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/import_bookmarks_dialog_remove"
+ android:maxLines="2"
+ />
+
+ <Button android:id="@+id/cancel"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@android:string/cancel"
+ />
+</LinearLayout>
\ No newline at end of file
diff --git a/res/menu/bookmarks.xml b/res/layout/import_bookmarks_dialog_button.xml
similarity index 69%
copy from res/menu/bookmarks.xml
copy to res/layout/import_bookmarks_dialog_button.xml
index a8781c2..cf8f628 100644
--- a/res/menu/bookmarks.xml
+++ b/res/layout/import_bookmarks_dialog_button.xml
@@ -14,10 +14,9 @@
limitations under the License.
-->
-<menu xmlns:android="http://schemas.android.com/apk/res/android">
- <item android:id="@+id/new_context_menu_id"
- android:icon="@drawable/ic_menu_add_bookmark"
- android:title="@string/bookmark_page" />
- <item android:id="@+id/switch_mode_menu_id"
- />
-</menu>
+<Button xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:text="@string/import_bookmarks_dialog_remove"
+ android:maxLines="2"
+/>
diff --git a/res/layout/new_folder_layout.xml b/res/layout/new_folder_layout.xml
new file mode 100644
index 0000000..230dd3d
--- /dev/null
+++ b/res/layout/new_folder_layout.xml
@@ -0,0 +1,55 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<!-- Keep in sync with folder_list_item.xml -->
+<LinearLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="horizontal">
+ <ImageView
+ android:id="@+id/icon1"
+ style="@style/HoloIcon"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:minHeight="?android:attr/listPreferredItemHeight"
+ android:src="@drawable/ic_folder_holo_dark" />
+ <LinearLayout
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:background="@*android:drawable/edit_text_holo_dark"
+ android:gravity="center_vertical"
+ android:paddingBottom="5dip"
+ android:orientation="horizontal">
+ <EditText
+ android:id="@+id/folder_namer"
+ android:layout_width="0dip"
+ android:layout_height="wrap_content"
+ android:layout_weight="1"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:background="@null"
+ android:gravity="center_vertical"
+ android:paddingLeft="6dip"
+ />
+ <ImageView
+ android:id="@+id/close"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:gravity="center_vertical"
+ android:src="@drawable/ic_tab_close"
+ />
+ </LinearLayout>
+</LinearLayout>
diff --git a/res/layout/page_info.xml b/res/layout/page_info.xml
index 275fcf4..7feb24e 100644
--- a/res/layout/page_info.xml
+++ b/res/layout/page_info.xml
@@ -31,8 +31,6 @@
android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:textStyle="bold"
- android:textSize="14sp"
- android:textColor="@color/white"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
android:layout_marginTop="12dip"
@@ -49,8 +47,6 @@
android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:text="@string/page_info_address"
- android:textSize="14sp"
- android:textColor="@color/white"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
@@ -60,8 +56,6 @@
android:id="@+id/address"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
- android:textSize="14sp"
- android:textColor="@color/white"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
diff --git a/res/xml/bookmarkwidget.xml b/res/layout/pick_bookmark.xml
similarity index 64%
copy from res/xml/bookmarkwidget.xml
copy to res/layout/pick_bookmark.xml
index adbe5f2..9636c4a 100644
--- a/res/xml/bookmarkwidget.xml
+++ b/res/layout/pick_bookmark.xml
@@ -13,12 +13,14 @@
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="match_parent"
+ android:layout_height="match_parent">
-<!-- 4x4 Widget displaying the user's bookmarks as thumbnails. -->
-<appwidget-provider xmlns:android="http://schemas.android.com/apk/res/android"
- android:minWidth="294dip"
- android:minHeight="294dip"
- android:updatePeriodMillis="3600000"
- android:initialLayout="@layout/bookmarkwidget"
- >
-</appwidget-provider>
+ <fragment class="com.android.browser.BrowserBookmarksPage"
+ android:id="@+id/bookmarks"
+ android:layout_width="match_parent"
+ android:layout_height="match_parent" />
+
+</FrameLayout>
diff --git a/res/layout/pref_homepage_buttons.xml b/res/layout/pref_homepage_buttons.xml
new file mode 100644
index 0000000..fe21beb
--- /dev/null
+++ b/res/layout/pref_homepage_buttons.xml
@@ -0,0 +1,39 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+
+
+ This layout provides the structure for a browser tab. A tab contains the
+ WebView and any number of other UI elements specific to that tab.
+ Currently, the only such element is the Geolocation permissions prompt.
+-->
+
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ android:orientation="horizontal"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_gravity="center_horizontal">
+
+ <Button android:id="@+id/use_current"
+ android:text="@string/pref_use_current"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_marginRight="16dp" />
+
+ <Button android:id="@+id/use_default"
+ android:text="@string/pref_use_default"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content" />
+
+</LinearLayout>
diff --git a/res/layout/setup_autofill_dialog.xml b/res/layout/setup_autofill_dialog.xml
new file mode 100644
index 0000000..084ae7a
--- /dev/null
+++ b/res/layout/setup_autofill_dialog.xml
@@ -0,0 +1,37 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2011 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:orientation="vertical"
+ android:paddingTop="20dip" >
+
+ <TextView
+ android:text="@string/autofill_setup_dialog_message"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:paddingBottom="5dip" />
+
+ <CheckBox android:id="@+id/setup_autofill_dialog_disable_autofill"
+ android:text="@string/disable_autofill"
+ android:textAppearance="?android:attr/textAppearanceSmall"
+ android:layout_gravity="left"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content" />
+
+</LinearLayout>
diff --git a/res/layout/ssl_certificate.xml b/res/layout/ssl_certificate.xml
index a137d66..28f50a3 100644
--- a/res/layout/ssl_certificate.xml
+++ b/res/layout/ssl_certificate.xml
@@ -57,8 +57,6 @@
android:layout_width="wrap_content"
android:text="@string/issued_to"
android:textStyle="bold"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
android:layout_marginBottom="10dip" />
@@ -69,8 +67,6 @@
android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:text="@string/common_name"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip" />
@@ -79,8 +75,6 @@
android:id="@+id/to_common"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
@@ -92,8 +86,6 @@
android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:text="@string/org_name"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip" />
@@ -102,8 +94,6 @@
android:id="@+id/to_org"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
@@ -115,8 +105,6 @@
android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:text="@string/org_unit"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip" />
@@ -125,8 +113,6 @@
android:id="@+id/to_org_unit"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
@@ -139,8 +125,6 @@
android:layout_width="wrap_content"
android:text="@string/issued_by"
android:textStyle="bold"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
android:layout_marginBottom="10dip" />
@@ -151,8 +135,6 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/common_name"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip" />
@@ -161,8 +143,6 @@
android:id="@+id/by_common"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
@@ -174,8 +154,6 @@
android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:text="@string/org_name"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip" />
@@ -184,8 +162,6 @@
android:id="@+id/by_org"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
@@ -197,8 +173,6 @@
android:layout_height="wrap_content"
android:layout_width="wrap_content"
android:text="@string/org_unit"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip" />
@@ -207,8 +181,6 @@
android:id="@+id/by_org_unit"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
@@ -221,8 +193,6 @@
android:layout_width="wrap_content"
android:text="@string/validity_period"
android:textStyle="bold"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
android:layout_marginBottom="10dip" />
@@ -233,8 +203,6 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/issued_on"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip" />
@@ -243,8 +211,6 @@
android:id="@+id/issued_on"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
@@ -256,8 +222,6 @@
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/expires_on"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_label"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip" />
@@ -266,8 +230,6 @@
android:id="@+id/expires_on"
android:layout_height="wrap_content"
android:layout_width="wrap_content"
- android:textSize="14sp"
- android:textColor="@color/ssl_text_value"
android:gravity="left"
android:layout_marginLeft="20dip"
android:layout_marginRight="20dip"
diff --git a/res/layout/ssl_success.xml b/res/layout/ssl_success.xml
index e819f23..16f7f58 100644
--- a/res/layout/ssl_success.xml
+++ b/res/layout/ssl_success.xml
@@ -34,8 +34,7 @@
android:layout_width="wrap_content"
android:gravity="left"
android:layout_weight="1"
- android:textSize="18sp"
- android:textColor="@color/ssl_text_label"
+ android:textAppearance="?android:attr/textAppearanceLarge"
android:layout_marginLeft="10dip"
android:layout_marginRight="20dip"
android:layout_marginBottom="12dip" />
diff --git a/res/layout/ssl_warning.xml b/res/layout/ssl_warning.xml
index 285c189..749629d 100644
--- a/res/layout/ssl_warning.xml
+++ b/res/layout/ssl_warning.xml
@@ -31,8 +31,7 @@
android:id="@+id/warning"
android:gravity="left"
android:layout_weight="1"
- android:textSize="18sp"
- android:textColor="@color/ssl_text_label"
+ android:textAppearance="?android:attr/textAppearanceLarge"
android:layout_marginLeft="10dip"
android:layout_marginRight="20dip"
android:layout_marginBottom="12dip" />
diff --git a/res/layout/ssl_warnings.xml b/res/layout/ssl_warnings.xml
index 7e43256..3fe73d3 100644
--- a/res/layout/ssl_warnings.xml
+++ b/res/layout/ssl_warnings.xml
@@ -30,8 +30,7 @@
android:id="@+id/warnings_header"
android:layout_height="wrap_content"
android:layout_width="match_parent"
- android:textSize="18sp"
- android:textColor="@color/ssl_text_label"
+ android:textAppearance="?android:attr/textAppearanceLarge"
android:gravity="left"
android:text="@string/ssl_warnings_header"
android:layout_marginRight="20dip"
diff --git a/res/layout/suggestion_item.xml b/res/layout/suggestion_item.xml
new file mode 100644
index 0000000..b85911f
--- /dev/null
+++ b/res/layout/suggestion_item.xml
@@ -0,0 +1,81 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/* //device/apps/common/assets/res/any/layout/simple_spinner_item.xml
+**
+** Copyright 2010, The Android Open Source Project
+**
+** Licensed under the Apache License, Version 2.0 (the "License");
+** you may not use this file except in compliance with the License.
+** You may obtain a copy of the License at
+**
+** http://www.apache.org/licenses/LICENSE-2.0
+**
+** Unless required by applicable law or agreed to in writing, software
+** distributed under the License is distributed on an "AS IS" BASIS,
+** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+** See the License for the specific language governing permissions and
+** limitations under the License.
+*/
+-->
+
+<LinearLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="match_parent"
+ android:layout_height="48dip"
+ android:orientation="horizontal"
+ android:gravity="center_vertical"
+ android:baselineAligned="false"
+ >
+ <LinearLayout
+ android:id="@+id/suggestion"
+ android:layout_width="0dip"
+ android:layout_height="match_parent"
+ android:layout_weight="1"
+ android:orientation="horizontal"
+ android:background="@drawable/suggest_item_selector">
+ <ImageView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:id="@+id/icon1"
+ android:layout_gravity="center_vertical"
+ style="@style/HoloIcon"
+ android:layout_marginRight="16dip" />
+ <LinearLayout
+ android:layout_width="0dip"
+ android:layout_height="wrap_content"
+ android:layout_weight="1"
+ android:layout_gravity="center_vertical"
+ android:orientation="vertical">
+ <TextView
+ android:id="@android:id/text1"
+ style="@style/SuggestionLineMedium"
+ android:singleLine="true"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content" />
+ <TextView
+ android:id="@android:id/text2"
+ style="@style/SuggestionLineSmall"
+ android:singleLine="true"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:textColor="@color/urlTextColor" />
+ </LinearLayout>
+ </LinearLayout>
+ <ImageView
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ android:id="@+id/divider"
+ android:scaleType="center"
+ android:background="@*android:drawable/list_divider_holo_light"
+ />
+ <ImageView
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:id="@+id/icon2"
+ android:scaleType="center"
+ android:src="@drawable/ic_add_string"
+ android:background="?android:attr/activatedBackgroundIndicator"
+ style="@style/HoloButton"
+ android:layout_marginRight="16dip"
+ />
+</LinearLayout>
diff --git a/res/layout/tab_bar.xml b/res/layout/tab_bar.xml
new file mode 100644
index 0000000..d3683b1
--- /dev/null
+++ b/res/layout/tab_bar.xml
@@ -0,0 +1,34 @@
+<?xml version="1.0" encoding="utf-8"?>
+ <!--
+ Copyright 2010, The Android Open Source Project Licensed under the
+ Apache License, Version 2.0 (the "License"); you may not use this file
+ except in compliance with the License. You may obtain a copy of the
+ License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+ applicable law or agreed to in writing, software distributed under the
+ License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+ CONDITIONS OF ANY KIND, either express or implied. See the License for
+ the specific language governing permissions and limitations under the
+ License.
+ -->
+<merge
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:id="@+id/tabbarcontent"
+ android:layout_width="match_parent"
+ android:layout_height="56dip"
+ android:orientation="horizontal"
+ style="@style/ActionBarStyle"
+ >
+ <com.android.browser.TabScrollView
+ android:id="@+id/tabs"
+ android:layout_width="0dip"
+ android:layout_height="44dip"
+ android:layout_weight="1.0"
+ android:orientation="horizontal" />
+ <ImageButton
+ android:id="@+id/newtab"
+ android:src="@drawable/ic_menu_new_window"
+ android:layout_width="wrap_content"
+ android:layout_height="44dip"
+ style="@style/HoloButton"
+ android:background="@drawable/browsertab_add" />
+</merge>
\ No newline at end of file
diff --git a/res/layout/tab_title.xml b/res/layout/tab_title.xml
new file mode 100644
index 0000000..e2c6d0a
--- /dev/null
+++ b/res/layout/tab_title.xml
@@ -0,0 +1,63 @@
+<?xml version="1.0" encoding="utf-8"?>
+ <!--
+ Copyright 2010, The Android Open Source Project Licensed under the
+ Apache License, Version 2.0 (the "License"); you may not use this file
+ except in compliance with the License. You may obtain a copy of the
+ License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+ applicable law or agreed to in writing, software distributed under the
+ License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+ CONDITIONS OF ANY KIND, either express or implied. See the License for
+ the specific language governing permissions and limitations under the
+ License.
+ -->
+<merge
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ android:gravity="center_vertical"
+ android:orientation="horizontal">
+ <ImageView
+ android:id="@+id/chevron"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ android:gravity="center_vertical"
+ android:src="@drawable/ic_chevron"
+ android:visibility="gone" />
+ <ImageView
+ android:id="@+id/incognito"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ android:gravity="center_vertical"
+ android:src="@drawable/ic_incognito_holo_dark"
+ android:visibility="gone" />
+ <ImageView
+ android:id="@+id/favicon"
+ android:layout_width="20dip"
+ android:layout_height="20dip"
+ android:layout_marginLeft="8dip"
+ android:layout_marginRight="8dip" />
+ <ImageView
+ android:id="@+id/lock"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:visibility="gone" />
+ <TextView
+ android:id="@+id/title"
+ android:layout_height="match_parent"
+ android:layout_width="0dip"
+ android:layout_weight="1.0"
+ android:paddingLeft="8dip"
+ android:paddingRight="8dip"
+ android:textAppearance="?android:attr/textAppearanceSmall"
+ android:textColor="@color/white"
+ android:gravity="center_vertical"
+ android:scrollHorizontally="true"
+ android:lines="1"
+ android:singleLine="true" />
+ <ImageButton
+ android:id="@+id/close"
+ android:background="?android:attr/selectableItemBackground"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:src="@drawable/ic_tab_close" />
+</merge>
diff --git a/res/layout/tab_view_add_incognito_tab.xml b/res/layout/tab_view_add_incognito_tab.xml
new file mode 100644
index 0000000..43fcb43
--- /dev/null
+++ b/res/layout/tab_view_add_incognito_tab.xml
@@ -0,0 +1,39 @@
+<?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:layout_height="wrap_content"
+ android:minHeight="?android:attr/listPreferredItemHeight"
+ android:layout_width="match_parent"
+ android:orientation="horizontal"
+ android:gravity="center_vertical"
+ >
+ <ImageView
+ android:layout_width="40dip"
+ android:layout_height="40dip"
+ android:layout_marginLeft="8dip"
+ android:layout_marginRight="8dip"
+ android:src="@drawable/ic_new_window_holo_dark"/>
+ <TextView
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:maxLines="1"
+ android:singleLine="true"
+ android:ellipsize="end"
+ android:text="@string/new_incognito_tab"
+ />
+</LinearLayout>
diff --git a/res/layout/tab_view_add_tab.xml b/res/layout/tab_view_add_tab.xml
index f69865e..f4e0f02 100644
--- a/res/layout/tab_view_add_tab.xml
+++ b/res/layout/tab_view_add_tab.xml
@@ -26,7 +26,7 @@
android:layout_height="40dip"
android:layout_marginLeft="8dip"
android:layout_marginRight="8dip"
- android:src="@drawable/ic_list_new_window"/>
+ android:src="@drawable/ic_new_window_holo_dark"/>
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
diff --git a/res/layout/tabs.xml b/res/layout/tabs.xml
deleted file mode 100644
index c212547..0000000
--- a/res/layout/tabs.xml
+++ /dev/null
@@ -1,37 +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.
--->
-<TabHost xmlns:android="http://schemas.android.com/apk/res/android"
- android:id="@android:id/tabhost"
- android:layout_width="match_parent"
- android:layout_height="match_parent">
-
- <LinearLayout
- android:orientation="vertical"
- android:layout_width="match_parent"
- android:layout_height="match_parent">
-
- <TabWidget android:id="@android:id/tabs"
- android:layout_width="match_parent"
- android:layout_height="wrap_content"
- />
-
- <FrameLayout android:id="@android:id/tabcontent"
- android:layout_width="match_parent"
- android:layout_height="0dip"
- android:layout_weight="1"
- />
- </LinearLayout>
-</TabHost>
diff --git a/res/layout/title_bar.xml b/res/layout/title_bar.xml
index 9f0cb51..9bfba35 100644
--- a/res/layout/title_bar.xml
+++ b/res/layout/title_bar.xml
@@ -65,8 +65,6 @@
android:layout_width="0dip"
android:layout_weight="1.0"
android:layout_marginLeft="3dip"
- android:textAppearance="?android:attr/textAppearanceMedium"
- android:textColor="@color/black"
android:gravity="center_vertical"
android:singleLine="true"
android:ellipsize="end"
@@ -90,7 +88,7 @@
android:layout_marginRight="-5dip"
android:scaleType="center"
android:background="@drawable/btn_bookmark"
- android:src="@drawable/ic_btn_bookmarks"
+ android:src="@drawable/ic_bookmark_on_holo_dark"
/>
</LinearLayout>
</LinearLayout>
diff --git a/res/layout/url_bar.xml b/res/layout/url_bar.xml
new file mode 100644
index 0000000..526e44c
--- /dev/null
+++ b/res/layout/url_bar.xml
@@ -0,0 +1,143 @@
+<?xml version="1.0" encoding="utf-8"?>
+ <!--
+ Copyright 2010, The Android Open Source Project Licensed under the
+ Apache License, Version 2.0 (the "License"); you may not use this file
+ except in compliance with the License. You may obtain a copy of the
+ License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+ applicable law or agreed to in writing, software distributed under the
+ License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+ CONDITIONS OF ANY KIND, either express or implied. See the License for
+ the specific language governing permissions and limitations under the
+ License.
+ -->
+<LinearLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:id="@+id/content"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:orientation="vertical">
+ <LinearLayout
+ android:id="@+id/taburlbar"
+ android:layout_width="match_parent"
+ android:layout_height="48dip"
+ android:orientation="horizontal"
+ android:background="@drawable/bg_urlbar">
+ <ImageButton
+ android:id="@+id/back"
+ android:src="@drawable/ic_back_holo_dark"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ android:paddingLeft="16dip"
+ style="@style/HoloButton" />
+ <ImageButton
+ android:id="@+id/forward"
+ android:src="@drawable/ic_forward_holo_dark"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ style="@style/HoloButton" />
+ <ImageButton
+ android:id="@+id/stop"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ style="@style/HoloButton"
+ android:gravity="center_vertical"
+ android:src="@drawable/ic_stop_holo_dark" />
+ <LinearLayout
+ android:id="@+id/urlbar_focused"
+ android:layout_width="0dip"
+ android:layout_height="match_parent"
+ android:layout_weight="1.0"
+ android:layout_marginLeft="8dip"
+ android:layout_marginRight="8dip"
+ android:orientation="horizontal"
+ android:background="@drawable/url_background">
+ <ImageView
+ android:id="@+id/web_icon"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ android:src="@drawable/ic_web_holo_dark"
+ style="@style/HoloIcon" />
+ <ImageView
+ android:id="@+id/voice_icon"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ android:src="@drawable/ic_search_holo_dark"
+ style="@style/HoloIcon"
+ android:visibility="gone" />
+ <ImageView
+ android:id="@+id/lock"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ style="@style/HoloIcon"
+ android:visibility="gone" />
+ <com.android.browser.UrlInputView
+ android:id="@+id/url_focused"
+ android:focusable="true"
+ android:layout_width="0dip"
+ android:layout_weight="1.0"
+ android:layout_height="match_parent"
+ android:layout_marginLeft="16dip"
+ android:paddingLeft="0dip"
+ android:paddingRight="0dip"
+ android:background="@null"
+ android:textAppearance="?android:attr/textAppearanceMedium"
+ android:hint="@string/search_hint"
+ android:singleLine="true"
+ android:ellipsize="end"
+ android:lines="1"
+ android:scrollHorizontally="true"
+ android:inputType="textUri"
+ android:imeOptions="actionGo"
+ style="@style/Suggestions" />
+ <ImageButton
+ android:id="@+id/star"
+ android:src="@drawable/btn_imageview_star"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ style="@style/HoloButton" />
+ <ImageButton
+ android:id="@+id/clear"
+ android:src="@drawable/ic_stop_holo_dark"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ style="@style/HoloButton" />
+ </LinearLayout>
+ <ImageButton
+ android:id="@+id/go"
+ android:src="@drawable/ic_go_holo_dark"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ android:visibility="gone"
+ android:gravity="center_vertical"
+ style="@style/HoloButton" />
+ <ImageButton
+ android:id="@+id/voicesearch"
+ android:src="@drawable/ic_voice_search_holo_dark"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ style="@style/HoloButton" />
+ <ImageButton
+ android:id="@+id/search"
+ android:src="@drawable/ic_search_holo_dark"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ android:gravity="center_vertical"
+ style="@style/HoloButton" />
+ <ImageButton
+ android:id="@+id/all_btn"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ android:scaleType="center"
+ android:paddingRight="16dip"
+ style="@style/HoloButton"
+ android:src="@drawable/ic_bookmarks_history_holo_dark" />
+ </LinearLayout>
+ <com.android.browser.PageProgressView
+ android:id="@+id/progress"
+ android:layout_width="match_parent"
+ android:layout_height="22dip"
+ android:background="@null"
+ android:src="@drawable/progress"
+ android:layout_marginTop="-11dip"
+ android:visibility="gone" />
+</LinearLayout>
diff --git a/res/layout/website_settings.xml b/res/layout/website_settings.xml
new file mode 100644
index 0000000..ed95148
--- /dev/null
+++ b/res/layout/website_settings.xml
@@ -0,0 +1,41 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+** Copyright 2010, The Android Open Source Project
+**
+** Licensed under the Apache License, Version 2.0 (the "License");
+** you may not use this file except in compliance with the License.
+** You may obtain a copy of the License at
+**
+** http://www.apache.org/licenses/LICENSE-2.0
+**
+** Unless required by applicable law or agreed to in writing, software
+** distributed under the License is distributed on an "AS IS" BASIS,
+** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+** See the License for the specific language governing permissions and
+** limitations under the License.
+*/
+-->
+
+<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
+ android:orientation="vertical"
+ android:layout_height="match_parent"
+ android:layout_width="match_parent"
+ android:background="@android:color/transparent">
+
+ <ListView android:id="@android:id/list"
+ android:layout_width="match_parent"
+ android:layout_height="0px"
+ android:layout_weight="1"
+ android:clipToPadding="false"
+ android:drawSelectorOnTop="false"
+ android:cacheColorHint="@android:color/transparent"
+ android:scrollbarAlwaysDrawVerticalTrack="true" />
+
+ <Button android:id="@+id/clear_all_button"
+ android:layout_width="150dip"
+ android:layout_height="wrap_content"
+ android:layout_margin="5dip"
+ android:text="@string/website_settings_clear_all"
+ android:visibility="gone" />
+</LinearLayout>
diff --git a/res/menu-xlarge/browser.xml b/res/menu-xlarge/browser.xml
new file mode 100644
index 0000000..1b52c9a
--- /dev/null
+++ b/res/menu-xlarge/browser.xml
@@ -0,0 +1,93 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+
+<menu xmlns:android="http://schemas.android.com/apk/res/android">
+ <group android:id="@+id/MAIN_MENU">
+ <item android:id="@+id/new_tab_menu_id"
+ android:icon="@drawable/ic_menu_new_window"
+ android:title="@string/new_tab"
+ android:showAsAction="never"
+ android:alphabeticShortcut="n" />
+ <item android:id="@+id/incognito_menu_id"
+ android:title="@string/new_incognito_tab"
+ android:icon="@drawable/ic_incognito_holo_dark" />
+ <item android:id="@+id/find_menu_id"
+ android:title="@*android:string/find_on_page"
+ android:icon="@drawable/ic_menu_findonpage_normal"
+ android:alphabeticShortcut="f" />
+ <item android:id="@+id/share_page_menu_id"
+ android:title="@string/share_page"
+ android:icon="@drawable/ic_share_holo_dark"
+ android:alphabeticShortcut="s" />
+ <item android:id="@+id/page_info_menu_id"
+ android:title="@string/page_info"
+ android:icon="@drawable/ic_pageinfo_holo_dark"
+ android:alphabeticShortcut="g" />
+ <item android:id="@+id/view_downloads_menu_id"
+ android:title="@string/menu_view_download"
+ android:icon="@drawable/ic_downloads_holo_dark"
+ android:alphabeticShortcut="j" />
+ <item android:id="@+id/preferences_menu_id"
+ android:title="@string/menu_preferences"
+ android:icon="@drawable/ic_settings_holo_dark"
+ android:alphabeticShortcut="p" />
+ <!-- followings are debug only -->
+ <item android:id="@+id/dump_nav_menu_id"
+ android:title="@string/dump_nav"
+ android:visible="false" />
+ <item android:id="@+id/dump_counters_menu_id"
+ android:title="@string/dump_counters"
+ android:visible="false" />
+ </group>
+ <group android:id="@+id/MAIN_SHORTCUT_MENU" android:visible="false">
+ <item android:id="@+id/homepage_menu_id"
+ android:alphabeticShortcut=" " />
+ <item android:id="@+id/classic_history_menu_id"
+ android:alphabeticShortcut="h" />
+ <item android:id="@+id/zoom_in_menu_id"
+ android:alphabeticShortcut="i" />
+ <item android:id="@+id/zoom_out_menu_id"
+ android:alphabeticShortcut="o" />
+ <item android:id="@+id/window_one_menu_id"
+ android:alphabeticShortcut="1" />
+ <item android:id="@+id/window_two_menu_id"
+ android:alphabeticShortcut="2" />
+ <item android:id="@+id/window_three_menu_id"
+ android:alphabeticShortcut="3" />
+ <item android:id="@+id/window_four_menu_id"
+ android:alphabeticShortcut="4" />
+ <item android:id="@+id/window_five_menu_id"
+ android:alphabeticShortcut="5" />
+ <item android:id="@+id/window_six_menu_id"
+ android:alphabeticShortcut="6" />
+ <item android:id="@+id/window_seven_menu_id"
+ android:alphabeticShortcut="7" />
+ <item android:id="@+id/window_eight_menu_id"
+ android:alphabeticShortcut="8" />
+ <item android:id="@+id/back_menu_id" />
+ <item android:id="@+id/forward_menu_id" />
+ <item android:id="@+id/bookmarks_menu_id"
+ android:alphabeticShortcut="b" />
+ <item android:id="@+id/add_bookmark_menu_id"
+ android:alphabeticShortcut="d" />
+ <item android:id="@+id/stop_reload_menu_id"
+ android:alphabeticShortcut="r" />
+ <item android:id="@+id/goto_menu_id"
+ android:alphabeticShortcut="l" />
+ <item android:id="@+id/close_menu_id"
+ android:alphabeticShortcut="w" />
+ </group>
+</menu>
diff --git a/res/menu/bookmark.xml b/res/menu/bookmark.xml
new file mode 100644
index 0000000..b761779
--- /dev/null
+++ b/res/menu/bookmark.xml
@@ -0,0 +1,37 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+
+<menu xmlns:android="http://schemas.android.com/apk/res/android">
+ <item
+ android:id="@+id/add_bookmark"
+ android:icon="@drawable/ic_bookmark_off_holo_dark"
+ android:title="@string/add_new_bookmark"
+ android:showAsAction="always|withText" />
+ <item
+ android:id="@+id/go_home"
+ android:icon="@drawable/ic_home_holo_dark"
+ android:showAsAction="always" />
+ <item
+ android:id="@+id/thumbnail_view"
+ android:title="@string/bookmark_thumbnail_view"/>
+ <item
+ android:id="@+id/list_view"
+ android:title="@string/bookmark_list_view"/>
+ <item
+ android:id="@+id/preferences_menu_id"
+ android:title="@string/menu_preferences"
+ android:alphabeticShortcut="p" />
+</menu>
diff --git a/res/menu/bookmarkscontext.xml b/res/menu/bookmarkscontext.xml
index badbb00..3a13b9a 100644
--- a/res/menu/bookmarkscontext.xml
+++ b/res/menu/bookmarkscontext.xml
@@ -15,11 +15,8 @@
-->
<menu xmlns:android="http://schemas.android.com/apk/res/android">
- <group android:id="@+id/ADD_MENU">
- <item android:id="@+id/new_context_menu_id"
- android:title="@string/save_to_bookmarks"/>
- </group>
- <group android:id="@+id/CONTEXT_MENU">
+ <group android:id="@+id/BOOKMARK_CONTEXT_MENU"
+ android:visible="false">
<item android:id="@+id/open_context_menu_id"
android:title="@string/open_bookmark"/>
<item android:id="@+id/new_window_context_menu_id"
@@ -37,4 +34,13 @@
<item android:id="@+id/homepage_context_menu_id"
android:title="@string/set_as_homepage"/>
</group>
+ <group android:id="@+id/FOLDER_CONTEXT_MENU"
+ android:visible="false">
+ <item android:id="@+id/new_window_context_menu_id"
+ android:title="@string/open_all_in_new_window"/>
+ <item android:id="@+id/edit_context_menu_id"
+ android:title="@string/edit_folder"/>
+ <item android:id="@+id/delete_context_menu_id"
+ android:title="@string/delete_folder"/>
+ </group>
</menu>
diff --git a/res/menu/browser.xml b/res/menu/browser.xml
index 4793c21..beaa8f3 100644
--- a/res/menu/browser.xml
+++ b/res/menu/browser.xml
@@ -23,39 +23,39 @@
<item android:id="@+id/bookmarks_menu_id"
android:title="@string/bookmarks"
android:alphabeticShortcut="b"
- android:icon="@drawable/ic_menu_bookmarks"
- />
+ android:icon="@drawable/ic_bookmarks_holo_dark" />
<item android:id="@+id/active_tabs_menu_id"
android:title="@string/active_tabs"
- android:icon="@drawable/ic_menu_windows"
+ android:icon="@drawable/ic_windows_holo_dark"
android:alphabeticShortcut="t" />
<item android:id="@+id/stop_reload_menu_id"
android:alphabeticShortcut="r" />
<item android:id="@+id/forward_menu_id"
android:title="@string/forward"
- android:alphabeticShortcut="k"
android:icon="@*android:drawable/ic_menu_forward" />
<item android:id="@+id/add_bookmark_menu_id"
android:title="@string/save_to_bookmarks"
- android:icon="@drawable/ic_menu_add_bookmark"
- android:alphabeticShortcut="a" />
+ android:icon="@drawable/ic_bookmark_on_holo_dark"
+ android:alphabeticShortcut="d" />
<item android:id="@+id/find_menu_id"
- android:title="@string/find_dot"
+ android:title="@*android:string/find_on_page"
+ android:icon="@*android:drawable/ic_menu_find"
android:alphabeticShortcut="f" />
- <item android:id="@+id/select_text_id"
- android:title="@string/select_dot"
- android:alphabeticShortcut="e" />
- <item android:id="@+id/page_info_menu_id"
- android:title="@string/page_info"
- android:alphabeticShortcut="g" />
<item android:id="@+id/share_page_menu_id"
android:title="@string/share_page"
+ android:icon="@drawable/ic_share_holo_dark"
android:alphabeticShortcut="s" />
+ <item android:id="@+id/page_info_menu_id"
+ android:title="@string/page_info"
+ android:icon="@drawable/ic_pageinfo_holo_dark"
+ android:alphabeticShortcut="g" />
<item android:id="@+id/view_downloads_menu_id"
android:title="@string/menu_view_download"
- android:alphabeticShortcut="d" />
+ android:icon="@drawable/ic_downloads_holo_dark"
+ android:alphabeticShortcut="j" />
<item android:id="@+id/preferences_menu_id"
android:title="@string/menu_preferences"
+ android:icon="@drawable/ic_settings_holo_dark"
android:alphabeticShortcut="p" />
<!-- followings are debug only -->
<item android:id="@+id/dump_nav_menu_id"
@@ -90,17 +90,10 @@
android:alphabeticShortcut="7" />
<item android:id="@+id/window_eight_menu_id"
android:alphabeticShortcut="8" />
- <item android:id="@+id/back_menu_id"
- android:title="@string/back"
- android:drawable="@*android:drawable/ic_menu_back"
- android:alphabeticShortcut="j" />
+ <item android:id="@+id/back_menu_id" />
<item android:id="@+id/goto_menu_id"
- android:title="@string/goto_dot"
- android:alphabeticShortcut="l"
- android:icon="@android:drawable/ic_menu_search"/>
+ android:alphabeticShortcut="l" />
<item android:id="@+id/close_menu_id"
- android:icon="@drawable/ic_btn_close_panel"
- android:title="@string/tab_picker_remove_tab"
android:alphabeticShortcut="w" />
</group>
<!-- these items are toggled in and out of @+id/stop_reload_menu_id -->
diff --git a/res/menu/browsercontext.xml b/res/menu/browsercontext.xml
index 70cf8d4..a8ae5c8 100644
--- a/res/menu/browsercontext.xml
+++ b/res/menu/browsercontext.xml
@@ -40,12 +40,8 @@
android:title="@string/contextmenu_openlink"/>
<item android:id="@+id/open_newtab_context_menu_id"
android:title="@string/contextmenu_openlink_newwindow"/>
- <item android:id="@+id/bookmark_context_menu_id"
- android:title="@string/contextmenu_bookmark_thislink"/>
<item android:id="@+id/save_link_context_menu_id"
android:title="@string/contextmenu_savelink"/>
- <item android:id="@+id/share_link_context_menu_id"
- android:title="@string/contextmenu_sharelink"/>
<item android:id="@+id/copy_link_context_menu_id"
android:title="@string/contextmenu_copylink"/>
</group>
@@ -57,5 +53,9 @@
<item android:id="@+id/set_wallpaper_context_menu_id"
android:title="@string/contextmenu_set_wallpaper"/>
</group>
+ <group android:id="@+id/SELECT_TEXT_MENU">
+ <item android:id="@+id/select_text_menu_id"
+ android:title="@string/select_dot"/>
+ </group>
</menu>
diff --git a/res/menu/history.xml b/res/menu/history.xml
index 3bb30a0..5b029b5 100644
--- a/res/menu/history.xml
+++ b/res/menu/history.xml
@@ -18,4 +18,8 @@
<item android:id="@+id/clear_history_menu_id"
android:title="@string/clear_history"
android:icon="@android:drawable/ic_menu_close_clear_cancel" />
+ <item android:id="@+id/preferences_menu_id"
+ android:title="@string/menu_preferences"
+ android:icon="@drawable/ic_settings_holo_dark"
+ android:alphabeticShortcut="p" />
</menu>
diff --git a/res/menu/historycontext.xml b/res/menu/historycontext.xml
index bd4ede4..3eaeb20 100644
--- a/res/menu/historycontext.xml
+++ b/res/menu/historycontext.xml
@@ -15,6 +15,7 @@
-->
<menu xmlns:android="http://schemas.android.com/apk/res/android">
+ <group android:id="@+id/CONTEXT_MENU">
<item android:id="@+id/open_context_menu_id"
android:title="@string/contextmenu_openlink"/>
<item android:id="@+id/new_window_context_menu_id"
@@ -29,4 +30,5 @@
android:title="@string/remove_history_item"/>
<item android:id="@+id/homepage_context_menu_id"
android:title="@string/set_as_homepage"/>
+ </group>
</menu>
diff --git a/res/menu/bookmarks.xml b/res/menu/url_selection.xml
similarity index 72%
rename from res/menu/bookmarks.xml
rename to res/menu/url_selection.xml
index a8781c2..8f4a93c 100644
--- a/res/menu/bookmarks.xml
+++ b/res/menu/url_selection.xml
@@ -1,12 +1,12 @@
<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2008 The Android Open Source Project
+<!-- Copyright (C) 2010 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
-
+
http://www.apache.org/licenses/LICENSE-2.0
-
+
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
@@ -15,9 +15,10 @@
-->
<menu xmlns:android="http://schemas.android.com/apk/res/android">
- <item android:id="@+id/new_context_menu_id"
- android:icon="@drawable/ic_menu_add_bookmark"
- android:title="@string/bookmark_page" />
- <item android:id="@+id/switch_mode_menu_id"
+ <item android:id="@+id/share"
+ android:icon="@drawable/ic_share_holo_dark"
+ android:title="@string/menu_share_url"
+ android:showAsAction="always|withText"
/>
</menu>
+
diff --git a/res/menu/websitesettings.xml b/res/menu/websitesettings.xml
deleted file mode 100644
index 5acc8a5..0000000
--- a/res/menu/websitesettings.xml
+++ /dev/null
@@ -1,21 +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.
--->
-
-<menu xmlns:android="http://schemas.android.com/apk/res/android">
- <item android:id="@+id/website_settings_menu_clear_all"
- android:title="@string/website_settings_clear_all"
- android:icon="@android:drawable/ic_menu_close_clear_cancel" />
-</menu>
-
diff --git a/res/mipmap-hdpi/ic_launcher_browser.png b/res/mipmap-hdpi/ic_launcher_browser.png
new file mode 100644
index 0000000..1f3e584
--- /dev/null
+++ b/res/mipmap-hdpi/ic_launcher_browser.png
Binary files differ
diff --git a/res/mipmap-hdpi/ic_launcher_shortcut_browser_bookmark.png b/res/mipmap-hdpi/ic_launcher_shortcut_browser_bookmark.png
new file mode 100644
index 0000000..7b2c680
--- /dev/null
+++ b/res/mipmap-hdpi/ic_launcher_shortcut_browser_bookmark.png
Binary files differ
diff --git a/res/mipmap-mdpi/ic_launcher_browser.png b/res/mipmap-mdpi/ic_launcher_browser.png
new file mode 100644
index 0000000..93c83d4
--- /dev/null
+++ b/res/mipmap-mdpi/ic_launcher_browser.png
Binary files differ
diff --git a/res/mipmap-mdpi/ic_launcher_shortcut_browser_bookmark.png b/res/mipmap-mdpi/ic_launcher_shortcut_browser_bookmark.png
new file mode 100644
index 0000000..aa05683
--- /dev/null
+++ b/res/mipmap-mdpi/ic_launcher_shortcut_browser_bookmark.png
Binary files differ
diff --git a/res/raw/favicon_amazon.ico b/res/raw/favicon_amazon.ico
new file mode 100644
index 0000000..20a959c
--- /dev/null
+++ b/res/raw/favicon_amazon.ico
Binary files differ
diff --git a/res/raw/favicon_bbc.ico b/res/raw/favicon_bbc.ico
new file mode 100644
index 0000000..8f62b07
--- /dev/null
+++ b/res/raw/favicon_bbc.ico
Binary files differ
diff --git a/res/raw/favicon_cnn.ico b/res/raw/favicon_cnn.ico
new file mode 100644
index 0000000..4a8421d
--- /dev/null
+++ b/res/raw/favicon_cnn.ico
Binary files differ
diff --git a/res/raw/favicon_ebay.ico b/res/raw/favicon_ebay.ico
new file mode 100644
index 0000000..d7c8a5e
--- /dev/null
+++ b/res/raw/favicon_ebay.ico
Binary files differ
diff --git a/res/raw/favicon_espn.ico b/res/raw/favicon_espn.ico
new file mode 100644
index 0000000..2dbe28a
--- /dev/null
+++ b/res/raw/favicon_espn.ico
Binary files differ
diff --git a/res/raw/favicon_facebook.ico b/res/raw/favicon_facebook.ico
new file mode 100644
index 0000000..ea0c6a3
--- /dev/null
+++ b/res/raw/favicon_facebook.ico
Binary files differ
diff --git a/res/raw/favicon_google.ico b/res/raw/favicon_google.ico
new file mode 100644
index 0000000..ee7c943
--- /dev/null
+++ b/res/raw/favicon_google.ico
Binary files differ
diff --git a/res/raw/favicon_msn.ico b/res/raw/favicon_msn.ico
new file mode 100644
index 0000000..b2279f5
--- /dev/null
+++ b/res/raw/favicon_msn.ico
Binary files differ
diff --git a/res/raw/favicon_nytimes.ico b/res/raw/favicon_nytimes.ico
new file mode 100644
index 0000000..fb4d000
--- /dev/null
+++ b/res/raw/favicon_nytimes.ico
Binary files differ
diff --git a/res/raw/favicon_picasa.ico b/res/raw/favicon_picasa.ico
new file mode 100644
index 0000000..22133b8
--- /dev/null
+++ b/res/raw/favicon_picasa.ico
Binary files differ
diff --git a/res/raw/favicon_twitter.ico b/res/raw/favicon_twitter.ico
new file mode 100644
index 0000000..00450d4
--- /dev/null
+++ b/res/raw/favicon_twitter.ico
Binary files differ
diff --git a/res/raw/favicon_weatherchannel.ico b/res/raw/favicon_weatherchannel.ico
new file mode 100644
index 0000000..5a56818
--- /dev/null
+++ b/res/raw/favicon_weatherchannel.ico
Binary files differ
diff --git a/res/raw/favicon_wikipedia.ico b/res/raw/favicon_wikipedia.ico
new file mode 100644
index 0000000..31b0e38
--- /dev/null
+++ b/res/raw/favicon_wikipedia.ico
Binary files differ
diff --git a/res/raw/favicon_yahoo.ico b/res/raw/favicon_yahoo.ico
new file mode 100644
index 0000000..d7761e5
--- /dev/null
+++ b/res/raw/favicon_yahoo.ico
Binary files differ
diff --git a/res/raw/most_visited.ktpl b/res/raw/most_visited.ktpl
new file mode 100644
index 0000000..04b9eee
--- /dev/null
+++ b/res/raw/most_visited.ktpl
@@ -0,0 +1,85 @@
+<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
+
+<html>
+<head>
+<title><%@ string/new_tab %></title>
+<meta name="viewport" content="width=device-width; initial-scale=1.0;" />
+
+<style type="text/css">
+
+* {
+ padding: 0;
+ margin: 0;
+}
+
+body {
+ text-align: center;
+ margin: 16px auto;
+ padding: 0 8px 0 8px;
+ max-width: <%@ dimen/mv_max_width %>px;
+}
+
+#most_visited h3 {
+ text-align: center;
+ padding: 0;
+ margin: 5px 0 5px 0px;
+}
+
+.thumbwrap li {
+ display: inline-block;
+ margin: 0 7px 15px 7px;
+ padding: 0;
+}
+
+@media all and (orientation:portrait) {
+.thumbwrap li {
+ width: <%@ dimen/mv_item_width_portrait %>px;
+}
+}
+
+@media all and (orientation:landscape) {
+.thumbwrap li {
+ width: <%@ dimen/mv_item_width %>px;
+}
+}
+
+.thumbwrap a {
+ display: block;
+ text-decoration: none;
+ color: #000;
+}
+
+.thumbwrap img {
+ border: <%@ dimen/mv_border_width %>px solid #e0e0e0;
+ border-radius: 5px;
+ width: 100%;
+}
+
+.thumbwrap .caption {
+ margin-top: 2px;
+ margin-left: 4px;
+ white-space: nowrap;
+ overflow: hidden;
+ text-overflow: ellipsis;
+ display: block;
+ font-size: .8em;
+ text-align: left;
+}
+
+</style>
+
+</head>
+<body>
+ <h3><%@ string/tab_most_visited %></h3>
+ <ul class="thumbwrap">
+ <%{ most_visited %>
+ <li>
+ <a href="<%= url %>">
+ <img class="wrimg" src="<%= thumbnail %>" />
+ <span class="caption"><%= title %></span>
+ </a>
+ </li>
+ <%} most_visited %>
+ </ul>
+</body>
+</html>
diff --git a/res/raw/thumb_amazon.png b/res/raw/thumb_amazon.png
new file mode 100644
index 0000000..4dd2f35
--- /dev/null
+++ b/res/raw/thumb_amazon.png
Binary files differ
diff --git a/res/raw/thumb_bbc.png b/res/raw/thumb_bbc.png
new file mode 100644
index 0000000..dff0424
--- /dev/null
+++ b/res/raw/thumb_bbc.png
Binary files differ
diff --git a/res/raw/thumb_cnn.png b/res/raw/thumb_cnn.png
new file mode 100644
index 0000000..3d6fdc9
--- /dev/null
+++ b/res/raw/thumb_cnn.png
Binary files differ
diff --git a/res/raw/thumb_ebay.png b/res/raw/thumb_ebay.png
new file mode 100644
index 0000000..023f678
--- /dev/null
+++ b/res/raw/thumb_ebay.png
Binary files differ
diff --git a/res/raw/thumb_espn.png b/res/raw/thumb_espn.png
new file mode 100644
index 0000000..c0882eb
--- /dev/null
+++ b/res/raw/thumb_espn.png
Binary files differ
diff --git a/res/raw/thumb_facebook.png b/res/raw/thumb_facebook.png
new file mode 100644
index 0000000..a8c047f
--- /dev/null
+++ b/res/raw/thumb_facebook.png
Binary files differ
diff --git a/res/raw/thumb_google.png b/res/raw/thumb_google.png
new file mode 100644
index 0000000..c54e6ea
--- /dev/null
+++ b/res/raw/thumb_google.png
Binary files differ
diff --git a/res/raw/thumb_msn.png b/res/raw/thumb_msn.png
new file mode 100644
index 0000000..4ad710f
--- /dev/null
+++ b/res/raw/thumb_msn.png
Binary files differ
diff --git a/res/raw/thumb_nytimes.png b/res/raw/thumb_nytimes.png
new file mode 100644
index 0000000..d6849c3
--- /dev/null
+++ b/res/raw/thumb_nytimes.png
Binary files differ
diff --git a/res/raw/thumb_picasa.png b/res/raw/thumb_picasa.png
new file mode 100644
index 0000000..5ec2d7a
--- /dev/null
+++ b/res/raw/thumb_picasa.png
Binary files differ
diff --git a/res/raw/thumb_twitter.png b/res/raw/thumb_twitter.png
new file mode 100644
index 0000000..95e247f
--- /dev/null
+++ b/res/raw/thumb_twitter.png
Binary files differ
diff --git a/res/raw/thumb_weatherchannel.png b/res/raw/thumb_weatherchannel.png
new file mode 100644
index 0000000..a190a0c
--- /dev/null
+++ b/res/raw/thumb_weatherchannel.png
Binary files differ
diff --git a/res/raw/thumb_wikipedia.png b/res/raw/thumb_wikipedia.png
new file mode 100644
index 0000000..7929468
--- /dev/null
+++ b/res/raw/thumb_wikipedia.png
Binary files differ
diff --git a/res/raw/thumb_yahoo.png b/res/raw/thumb_yahoo.png
new file mode 100644
index 0000000..08dd759
--- /dev/null
+++ b/res/raw/thumb_yahoo.png
Binary files differ
diff --git a/res/values-ar-xlarge/strings.xml b/res/values-ar-xlarge/strings.xml
new file mode 100644
index 0000000..db12504
--- /dev/null
+++ b/res/values-ar-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"علامة تبويب جديدة"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"علامة تبويب جديدة للتصفح المتخفي"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"علامات التبويب"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"فتح في علامة تبويب جديدة"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"فتح في علامة تبويب جديدة في الخلفية"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"فتح الكل في علامات تبويب جديدة"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"فتح علامات تبويب جديدة وراء علامة التبويب الحالية"</string>
+</resources>
diff --git a/res/values-ar/strings.xml b/res/values-ar/strings.xml
index 38e4eb8..fd97a7f 100644
--- a/res/values-ar/strings.xml
+++ b/res/values-ar/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"المتصفح"</string>
<string name="choose_upload" msgid="3649366287575002063">"اختر ملفًا لتحميله"</string>
<string name="new_tab" msgid="4505722538297295141">"نافذة جديدة"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"نافذة جديدة للتصفح المتخفي"</string>
<string name="active_tabs" msgid="3050623868203544623">"نظام التشغيل Windows"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"الإشارات"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"الأكثر زيارة"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"المتصفح"</string>
<string name="cancel" msgid="3017274947407233702">"إلغاء"</string>
<string name="ok" msgid="1509280796718850364">"موافق"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"ليس هناك أية مطابقات"</item>
- <item quantity="one" msgid="4352019729062956802">"مطابقة واحدة"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> من المطابقات"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> من المطابقات"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"جارٍ التحميل…"</string>
<string name="page_info" msgid="4048529256302257195">"معلومات الصفحة"</string>
<string name="page_info_view" msgid="5303490449842635158">"عرض معلومات الصفحة"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"متابعة"</string>
<string name="security_warning" msgid="6607795404322797541">"تحذير أمان"</string>
<string name="view_certificate" msgid="1472768887529093862">"عرض الشهادة"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"رجوع"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"هذه الشهادة ليست من جهة موثوق بها."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"اسم الموقع لا يتطابق مع الاسم على الشهادة."</string>
<string name="ssl_expired" msgid="5739349389499575559">"انتهت صلاحية هذه الشهادة."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"إعادة توجيه"</string>
<string name="save" msgid="5922311934992468496">"موافق"</string>
<string name="do_not_save" msgid="6777633870113477714">"إلغاء"</string>
- <string name="location" msgid="969988560160364559">"الموقع"</string>
- <string name="name" msgid="5990326151488445481">"الاسم"</string>
+ <string name="location" msgid="3411848697912600125">"العنوان"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"إضافة إلى"</string>
+ <string name="new_folder" msgid="7743540149088867917">"مجلد جديد"</string>
+ <string name="edit_folder" msgid="621817453133656156">"تعديل مجلد"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"حذف مجلد"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"ليس هناك أي مجلدات فرعية"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"الإشارات"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"الشاشة الرئيسية"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"مجلد آخر…"</string>
+ <string name="name" msgid="5462672162695365387">"التصنيف"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"إضافة إشارة"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"إضافة إلى الإشارات"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"وضع إشارة على هذه الصفحة"</string>
+ <string name="remove" msgid="7820112494467011374">"إزالة"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"تعديل الإشارة"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"إضافة اختصار إلى الصفحة الرئيسية"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"إضافة اختصار إلى الصفحة الرئيسية"</string>
<string name="open_bookmark" msgid="8473581305759935790">"فتح"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"حذف الإشارة"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"إزالة من الإشارات"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"لا يمكن وضع إشارة على عنوان URL هذا."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"حذف"</string>
<string name="bookmark_page" msgid="6845189305130307274">"وضع إشارة على آخر صفحة تم عرضها"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"عرض صورة مصغرة"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"عرض القائمة"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"الصور المصغرة"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"قائمة"</string>
<string name="current_page" msgid="7510129573681663135">"من "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"سيتم حذف الإشارة \"<xliff:g id="BOOKMARK">%s</xliff:g>\"."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"فتح في نافذة جديدة"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"فتح الكل في نوافذ جديدة"</string>
<string name="goto_dot" msgid="3895839050522602723">"تنفيذ"</string>
- <string name="find_dot" msgid="6259312434696611957">"بحث في الصفحة"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"فتح علامة تبويب جديدة للتصفح المتخفي"</string>
<string name="select_dot" msgid="6299170761900561967">"تحديد نص"</string>
<string name="tab_picker_title" msgid="864478399057782913">"النوافذ الحالية"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"إغلاق"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"التنزيلات"</string>
<string name="copy_page_url" msgid="7635062169011319208">"نسخ عنوان URL للصفحة"</string>
<string name="share_page" msgid="593756995297268343">"مشاركة الصفحة"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"حفظ كأرشيف ويب"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"تم حفظ أرشيف الويب."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"أخفق حفظ أرشيف الويب."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> من الإشارات المرجعية"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"المجلد فارغ"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"فتح"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"فتح في نافذة جديدة"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"وضع إشارة على الرابط"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"فتح في نافذة جديدة في الخلفية"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"حفظ الرابط"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"مشاركة الرابط"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"نسخ"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"تعيين الصفحة الرئيسية"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"تعين محرك بحث"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"تحديد محرك بحث"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"استخدام الصفحة الحالية"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"تعيين على..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"الصفحة الحالية"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"صفحة فارغة"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"الصفحة الافتراضية"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"احتواء تلقائي للصفحات"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"تنسيق صفحات الويب لاحتوائها في الشاشة"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"عرض أفقي فقط"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"عرض الصور في اتجاه الشاشة الأعرض الأفقي فقط"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"إعدادات الخصوصية"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"إعدادات عامة"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"المزامنة"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"الملء التلقائي"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"المزامنة مع Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"مشاركة الإشارات والبيانات الأخرى بين متصفح Android وGoogle Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"حساب Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"مزامنة الإشارات"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"مزامنة الإشارات بين متصفح Android وGoogle Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"بدء المزامنة"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"تحديد حساب Google لمشاركته مع"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"الملء التلقائي للنموذج"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"ملء نماذج الويب بنقرة واحدة"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"إعدادات الملء التلقائي"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"إعداد وإدارة البيانات للنماذج التي يتم ملؤها تلقائيًا"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"تسجيل الدخول تلقائيًا إلى Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"لم يتم العثور على أي حسابات."</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"تسجيل الدخول إلى مواقع Google تلقائيًا باستخدام <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"تسجيل الدخول إلى مواقع Google باستخدام <xliff:g id="ID_1">%s</xliff:g>"\n"تتحكم إعدادات الخصوصية والأمان في تسجيل الدخول التلقائي إلى Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"عدم تسجيل الدخول تلقائيًا"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"سيستخدم الملء التلقائي ملفك الشخصي لمساعدتك على إكمال نماذج الويب بنقرة واحدة."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"الاسم بالكامل:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"البريد الإلكتروني:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"اسم الشركة:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"سطر العنوان 2:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"عنوان الشارع، صندوق البريد، الجهة المقصودة"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"سطر العنوان 1:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"شقة، جناح، وحدة، مبنى، طابق إلخ."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"مدينة/بلدة:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"الولاية/الإقليم/المنطقة:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"الرمز البريدي:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"البلد:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"الهاتف:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"رقم الهاتف غير صالح."</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"حفظ الملف الشخصي"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"تم حفظ الملف الشخصي"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"تم حذف الملف الشخصي"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"حذف الملف الشخصي"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"يستطيع المتصفح إكمال نماذج ويب مثل هذا النموذج. هل تريد إعداد ملفك الشخصي؟"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"يمكن تهيئة الملء التلقائي دائمًا عبر إعدادات المتصفح."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"تعطيل الملء التلقائي"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"الخصوصية والأمان"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"محو ذاكرة التخزين المؤقت"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"محو قواعد البيانات والمحتوى المخزن مؤقتًا محليًا"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"سيتم حذف قواعد البيانات والمحتوى المخزن مؤقتًا محليًا."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"ملفات تعريف الارتباط"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"محو جميع بيانات ملف تعريف الارتباط"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"محو جميع ملفات تعريف ارتباط المتصفح"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"سيتم حذف جميع ملفات تعريف الارتباط."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"محو السجل"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"محو سجل تنقل المتصفح"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"سيتم حذف سجل تنقل المتصفح."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"بيانات النموذج"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"محو بيانات النموذج"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"محو كل بيانات النموذج المحفوظة"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"سيتم حذف جميع بيانات النموذج المحفوظة."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"محو كلمات المرور"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"محو جميع كلمات المرور المحفوظة"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"سيتم حذف جميع كلمات المرور المحفوظة."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"الموقع"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"تمكين الموقع"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"السماح للمواقع الإلكترونية بطلب الدخول إلى موقعك الجغرافي"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"محو إمكانية الدخول إلى الموقع الجغرافي"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"محو إمكانية الدخول إلى الموقع الجغرافي بالنسبة إلى جميع مواقع الويب"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"محو إمكانية الدخول إلى الموقع الجغرافي بالنسبة إلى جميع مواقع الويب"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"إعدادات الأمان"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"كلمات المرور"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"تذكّر كلمات المرور"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"حفظ أسماء المستخدمين وكلمات المرور لمواقع الويب"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"تذكر بيانات النموذج"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"التكبير/التصغير الافتراضي"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"فتح الصفحات في النظرة العامة"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"عرض نظرة عامة حول الصفحات التي تم فتحها حديثًا"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"الإعدادات المتقدمة"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"خيارات متقدمة"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"إعدادات موقع الويب"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"الإعدادات المتقدمة لمواقع الويب الفردية"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"إعادة تعيين الإعدادات الافتراضية"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"إعادة تعيين إلى الافتراضي"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"استعادة الإعدادات الافتراضية"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"ستتم إعادة الإعدادات إلى القيم الافتراضية."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"اليابانية (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"اليابانية (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"اليابانية (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"الكورية (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"تشفير النص"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"الميزات الاختبارية"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"عناصر التحكم السريعة"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"مرر الإبهام من الحافة اليسرى أو اليمنى للدخول إلى عناصر التحكم السريعة."</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"الصفحة الرئيسية الأكثر زيارة"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"لتعيين صفحتك الرئيسية لعرض الصفحات الأكثر زيارة."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"مشكلة في اتصال البيانات"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"مشكلة في الملف"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"تأكيد"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"حذف جميع البيانات"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"إلغاء"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"جارٍ إعداد الخلفية..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"الإشارات"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"ليس هناك أي إشارات"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"اختيار حساب"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"المزامنة مع حساب Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"لم يتم إقران إشارات Android مع حساب Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"إزالة إشارات Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"إضافة إشارات Android إلى إشارات <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"مشاركة"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"لا يتوفر المزيد من علامات التبويب"</string>
</resources>
diff --git a/res/values-bg-xlarge/strings.xml b/res/values-bg-xlarge/strings.xml
new file mode 100644
index 0000000..91bd88b
--- /dev/null
+++ b/res/values-bg-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Нов раздел"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Нов раздел „инкогнито“"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Раздели"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Отваряне в нов раздел"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Отваряне в нов раздел на заден план"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Отваряне на всички в нови раздели"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Отваряне на нови раздели зад текущия"</string>
+</resources>
diff --git a/res/values-bg/strings.xml b/res/values-bg/strings.xml
index 43eb32a..993d1d1 100644
--- a/res/values-bg/strings.xml
+++ b/res/values-bg/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Браузър"</string>
<string name="choose_upload" msgid="3649366287575002063">"Избор на файл за качване"</string>
<string name="new_tab" msgid="4505722538297295141">"Нов прозорец"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Нов прозорец „инкогнито“"</string>
<string name="active_tabs" msgid="3050623868203544623">"Прозорци"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Отметки"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Най-посещавани"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Браузър"</string>
<string name="cancel" msgid="3017274947407233702">"Отказ"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Няма съответствия"</item>
- <item quantity="one" msgid="4352019729062956802">"1 съответствие"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> съответствия"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> съответствия"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Зарежда се…"</string>
<string name="page_info" msgid="4048529256302257195">"Данни за страницата"</string>
<string name="page_info_view" msgid="5303490449842635158">"Преглед на данните за страницата"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Напред"</string>
<string name="security_warning" msgid="6607795404322797541">"Предупреждение относно защитата"</string>
<string name="view_certificate" msgid="1472768887529093862">"Преглед на сертификата"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Назад"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Сертификатът не е от надежден орган."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Името на сайта не съответства на името в сертификата."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Сертификатът е изтекъл."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"Напред"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Отказ"</string>
- <string name="location" msgid="969988560160364559">"Местоположение"</string>
- <string name="name" msgid="5990326151488445481">"Име"</string>
+ <string name="location" msgid="3411848697912600125">"Адрес"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Добавяне към"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Нова папка"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Редактиране на папката"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Изтриване на папката"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Няма подпапки"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Отметки"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Начален екран"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Друга папка..."</string>
+ <string name="name" msgid="5462672162695365387">"Етикет"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Добавяне на отметка"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Добавяне към отметките"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Запазване на тази страница като отметка"</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"Редактиране на отметката"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Добавяне на пряк път до „Начало“"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Добавяне на пряк път до „Начало“"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Отваряне"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Изтриване на отметка"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Премахване от отметки"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Не може да бъде създадена отметка към този URL адрес."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Изтриване"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Отметка към последно разглежданата страница"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Изглед с миниизображения"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Списъчен изглед"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Миниизображения"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Списък"</string>
<string name="current_page" msgid="7510129573681663135">"от "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Отметката „<xliff:g id="BOOKMARK">%s</xliff:g>“ ще бъде изтрита."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Отваряне в нов прозорец"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Отваряне на всички в нови прозорци"</string>
<string name="goto_dot" msgid="3895839050522602723">"Старт"</string>
- <string name="find_dot" msgid="6259312434696611957">"Търсене в страницата"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Нов раздел „инкогнито“"</string>
<string name="select_dot" msgid="6299170761900561967">"Избиране на текст"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Текущ прозорец"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Затваряне"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Изтеглени"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Копиране на URL адреса на страницата"</string>
<string name="share_page" msgid="593756995297268343">"Споделяне на страницата"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Запазване като уеб архив"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Уеб архивът бе запазен."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Запазването на уеб архив не бе успешно."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> отметки"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Празна папка"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Отваряне"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Отваряне в нов прозорец"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Отметка за връзка"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Отваряне в нов прозорец на заден план"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Запазване на връзката"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Споделяне на връзката"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Копиране"</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Задаване на начална страница"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Задаване на търсеща машина"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Избор на търсеща машина"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Използване на текущата страница"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Задаване на..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Текущата страница"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Празна страница"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Страницата по подразбиране"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Автоматично побиране на страници"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Уеб страниците се форматират до размера на екрана"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Показване само в хоризонтален режим"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Показване на страниците само в по-широката, хоризонтална ориентация на екрана"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Настройки за поверителност"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Общи"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Синхронизиране"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Автоматично попълване"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Синхронизиране с Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Споделяйте отметки и други данни между браузъра в Android и Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Профил в Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Синхронизиране на отметките"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Синхронизирайте отметки между браузъра в Android и Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Старт на синхрона"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Избор на профил в Google, с който да се споделя"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Авт. попълване на формуляри"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Попълвайте формуляри в мрежата с едно кликване"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Настройки за авт. попълване"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Настройка и управление на данните за формуляри с автоматично попълване"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Автоматичен вход в Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Няма намерени профили"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Автоматично влизане в сайтовете на Google посредством <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Влизате в сайтове на Google посредством <xliff:g id="ID_1">%s</xliff:g>"\n"Настройките ви за поверителност и сигурност контролират автоматичния вход в Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Да не се влиза автоматично"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Автоматичното попълване ще използва потребителския ви профил, за да ви помогне да попълвате уеб формуляри с едно кликване."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Пълно име:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Имейл адрес:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Име на фирмата:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Първи ред на адреса:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Пощенски адрес, пощенска кутия, чрез"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Втори ред на адреса:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Апартамент, вход, блок, етаж и др."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Град:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Област / щат / провинция:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Пощенски код:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Държава:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Телефон:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Невалиден телефонен номер"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Запазване на профила"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Потребителският профил бе запазен"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Потребителският профил бе изтрит"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Изтриване на профила"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Браузърът може автоматично да попълва уеб формуляри като този. Искате ли да настроите потребителския си профил?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Автоматичното попълване винаги може да се конфигурира от „Настройки на браузъра“."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Деактивиране на автоматичното попълване"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Поверителност и сигурност"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Изчистване на кеша"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Изчистване на съдържанието и базите от данни от локалния кеш"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Съдържанието и базите от данни в локалния кеш ще бъдат изтрити."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"„Бисквитки“"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Изчистване на всички данни за „бисквитки“"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Изчистване на всички „бисквитки“ на браузъра"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Всички „бисквитки“ ще бъдат изтрити."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Изчистване на историята"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Изчистване на навигационната история на браузъра"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Историята на сърфиране на браузъра ще бъде изтрита."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Данни за формуляри"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Изчистване на данни за формуляри"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Изчистване на всички запазени данни за формуляри"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Всички запазени данни за формуляри ще бъдат изтрити."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Изчистване на пароли"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Изчистване на всички запазени пароли"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Всички запазени пароли ще бъдат изтрити."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Местоположение"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Активиране на местоположение"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Разрешаване на сайтове да искат достъп до местопол. ви"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Изчистване на достъпа до местопол."</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Изчистване на достъпа на всички уебсайтове до местопол. ви"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Изчистване на достъпа на всички уебсайтове до местопол. ви"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Защитни настройки"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Пароли"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Запомняне на пароли"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Запазване на потребителските имена и паролите за уебсайтове"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Запомняне на данни за формуляри"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Стандартна промяна на мащаба"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Отваряне на страници за общ преглед"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Показване на общ преглед на новоотворени страници"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Разширени настройки"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Разширени"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Настройки за уебсайтове"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Разширени настройки за отделни уебсайтове"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Възстановяване на стандартните настройки"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Възстановяване на стандартните"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Възстановяване на стандартните настройки"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Настройките ще възвърнат стандартните си стойности."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"Японски (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Японски (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Японски (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Корейски (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Текстово кодиране"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Лаборатория"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Бързи контроли"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Прокарайте палец от левия или десния край за достъп до бързите контроли"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Най-посещавана начална страница"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Задава началната ви страница да показва най-посещаваните страници."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Проблем с обмен на данни"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Проблем с файла"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Потвърждаване"</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Изтриване на всички данни"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Отказ"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Тапетът се задава..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Отметки"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Няма отметки"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Изберете профил"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Синхронизиране с профил в Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Отметките ви в Android не са свързани с профил в Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Премахване на отметките ви в Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Добавяне на отметките ви в Android към тези на <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Споделяне"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Не се предлагат повече раздели"</string>
</resources>
diff --git a/res/values-ca-xlarge/strings.xml b/res/values-ca-xlarge/strings.xml
new file mode 100644
index 0000000..783e2f4
--- /dev/null
+++ b/res/values-ca-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Nova pestanya"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Nova pestanya d\'incògnit"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Pestanyes"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Obre en una pestanya nova"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Obre en una pestanya de fons nova"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Obre-ho tot en pestanyes noves"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Obre les pestanyes noves darrere l\'actual"</string>
+</resources>
diff --git a/res/values-ca/strings.xml b/res/values-ca/strings.xml
index f643112..3e33f4c 100644
--- a/res/values-ca/strings.xml
+++ b/res/values-ca/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Navegador"</string>
<string name="choose_upload" msgid="3649366287575002063">"Trieu un fitxer per penjar-lo"</string>
<string name="new_tab" msgid="4505722538297295141">"Finestra nova"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nova finestra d\'incògnit"</string>
<string name="active_tabs" msgid="3050623868203544623">"Windows"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Adreces d\'interès"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Més visitats"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Navegador"</string>
<string name="cancel" msgid="3017274947407233702">"Cancel·la"</string>
<string name="ok" msgid="1509280796718850364">"D\'acord"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Cap coincidència"</item>
- <item quantity="one" msgid="4352019729062956802">"1 coincidència"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> coincidències"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> coincidències"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"S\'està carregant…"</string>
<string name="page_info" msgid="4048529256302257195">"Informació de la pàgina"</string>
<string name="page_info_view" msgid="5303490449842635158">"Visualitza la informació de la pàgina"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Continua"</string>
<string name="security_warning" msgid="6607795404322797541">"Advertiment de seguretat"</string>
<string name="view_certificate" msgid="1472768887529093862">"Visualitza el certificat"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Enrere"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Aquest certificat no és d\'una autoritat de confiança."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"El nom del lloc no coincideix amb el nom que consta al certificat."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Aquest certificat ha caducat."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"Següent"</string>
<string name="save" msgid="5922311934992468496">"D\'acord"</string>
<string name="do_not_save" msgid="6777633870113477714">"Cancel·la"</string>
- <string name="location" msgid="969988560160364559">"Ubicació"</string>
- <string name="name" msgid="5990326151488445481">"Nom"</string>
+ <string name="location" msgid="3411848697912600125">"Adreça"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Afegeix a"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Nova carpeta"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Edita la carpeta"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Suprimeix la carpeta"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"No hi ha subcarpetes"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Marcadors"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Pàgina d\'inici"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Una altra carpeta..."</string>
+ <string name="name" msgid="5462672162695365387">"Etiqueta"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Afegeix una adreça d\'interès"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Afegeix als marcadors"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Af. pàg. a marc."</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"Edita l\'adreça d\'interès"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Afegeix una drecera a la pàgina d\'inici"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Afegeix una drecera a la pàgina d\'inici"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Obre"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Suprimeix l\'adreça d\'interès"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Elimina de les adreces d\'interès"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Aquest URL no es pot afegir a les adreces d\'interès."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Supressió"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Afegeix l\'última pàgina visualitzada a les adreces d\'interès"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Visualització en miniatura"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Visualització de llista"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniatures"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Llista"</string>
<string name="current_page" msgid="7510129573681663135">"de "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Se suprimirà l\'adreça d\'interès \"<xliff:g id="BOOKMARK">%s</xliff:g>\"."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Obre en una finestra nova"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Obre-ho tot en finestres noves"</string>
<string name="goto_dot" msgid="3895839050522602723">"Vés"</string>
- <string name="find_dot" msgid="6259312434696611957">"Troba-ho a la pàgina"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Obre una nova pest. d\'incògnit"</string>
<string name="select_dot" msgid="6299170761900561967">"Selecciona text"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Finestres actuals"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Tanca"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Baixades"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Copia l\'URL de la pàgina"</string>
<string name="share_page" msgid="593756995297268343">"Comparteix la pàgina"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Desa com a arxiu web"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Arxiu web desat."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Error en desar l\'arxiu web."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> marcadors"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Carpeta buida"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Obre"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Obre en una finestra nova"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Afegeix l\'enllaç a les adreces d\'interès"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Obre en una finestra de fons nova"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Desa l\'enllaç"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Comparteix l\'enllaç"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Copia"</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Defineix la pàgina d\'inici"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Defineix el motor de cerca"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Selecciona un motor de cerca"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Utilitza la pàgina actual"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Defineix com a..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Pàgina actual"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Pàgina en blanc"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Pàgina predeterminada"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Ajusta les pàgines automàticament"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Formata les pàgines web perquè s\'ajustin a la pantalla"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Visualització només horitzontal"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Visualitza les pàgines només en l\'orientació de pantalla horitzontal, que és més ampla"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Configuració de privadesa"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"General"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sincronització"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Emplenament automàtic"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sincronitza amb Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Comparteix els marcadors i altres dades entre el navegador d\'Android i Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Compte de Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sincronitza els marcadors"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sincronitza els marcadors entre el navegador d\'Android i Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Inicia la sincron."</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Selecciona el Compte de Google amb el qual vols compartir"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Emplenament automàtic del formulari"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Emplena formularis web amb un simple clic"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Configuració d\'emplenament automàtic"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Configura i gestiona les dades per a formularis emplenats automàticament"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Inici sessió automàtic a Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"No s\'ha trobat cap compte"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Inicia la sessió a Llocs web de Google automàticament mitjançant <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"S\'està iniciant la sessió a Llocs web de Google amb <xliff:g id="ID_1">%s</xliff:g>"\n"La configuració de privadesa i de seguretat controla l\'inici de sessió automàtic de Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"No iniciïs la sessió automàticament"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Emplenament automàtic utilitzarà el teu perfil per ajudar-te a emplenar formularis web amb un sol clic."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Nom complet:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Correu electrònic:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Nom de l\'empresa:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Línia d\'adreça 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Adreça postal, apartat de correus, a l\'atenció de"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Línia d\'adreça 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Apartament, pis, unitat, edifici, planta, etc."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Ciutat / Població:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Estat / Província / Regió:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Codi postal:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"País:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telèfon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"El número de telèfon no és vàlid"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Desa el perfil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"S\'ha desat el perfil"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"S\'ha suprimit el perfil"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Suprimeix el perfil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"El navegador pot emplenar formularis web com aquest automàticament. Vols configurar el teu perfil?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"L\'emplenament automàtic sempre es pot establir mitjançant la configuració del navegador."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Desactiva l\'emplenament automàtic"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Privadesa i seguretat"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Esborra la memòria cau"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Esborra el contingut i les bases de dades de la memòria cau local"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Se suprimiran el contingut i les bases de dades de la memòria cau local."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Galetes"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Esborra totes les dades de les galetes"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Esborra totes les galetes del navegador"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Se suprimiran totes les galetes."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Esborra l\'historial"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Esborra l\'historial de navegació del navegador"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Se suprimirà l\'historial de navegació del navegador."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Dades del formulari"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Esborra les dades dels formularis"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Esborra totes les dades de formulari desades"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Se suprimiran totes les dades de formularis desades."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Esborra les contrasenyes"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Esborra totes les contrasenyes desades"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Totes les contrasenyes desades se suprimiran."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Ubicació"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Activa la ubicació"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Permet als llocs sol·licitar accés a la vostra ubicació"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Esborra l\'accés a la ubicació"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Esborra l\'accés a la ubicació per a tots els llocs web"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Esborra l\'accés a la ubicació per a tots els llocs web"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Configuració de seguretat"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Contrasenyes"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Recorda les contrasenyes"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Desa els noms d\'usuari i les contrasenyes dels llocs"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Recorda les dades del formulari"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Zoom predeterminat"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Obre un resum de les pàgines"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Mostra un resum de les pàgines que s\'han obert darrerament"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Configuració avançada"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Avançada"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Configuració del lloc web"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Configuració avançada de llocs web individuals"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Restabliment dels valors predeterminats"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Restableix al valor predeterminat"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Restaura la configuració predeterminada"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"La configuració tornarà als valors predeterminats."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"Japonès (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japonès (MAJ_JIS)"</item>
<item msgid="7356792686950371843">"Japonès (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Coreà (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codificació del text"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Controls ràpids"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Fes lliscar el polze cap a la dreta o cap a l\'esquerra per accedir als controls ràpids"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Pàgina principal més visitada"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Estableix la pàgina d\'inici perquè mostri les pàgines més visitades."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problema de connectivitat de dades"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problema amb el fitxer"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Confirma"</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Suprimeix totes les dades"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Cancel·la"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"S\'està definint l\'empaperat..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Marcadors"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"No hi ha marcadors"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Tria d\'un compte"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sincronitza amb el Compte de Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Els teus marcadors d\'Android no estan associades amb un Compte de Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Elimina els teus marcadors d\'Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Afegeix els marcadors d\'Android als marcadors de <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Comparteix"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"No hi ha cap més pestanya disponible"</string>
</resources>
diff --git a/res/values-cs-xlarge/strings.xml b/res/values-cs-xlarge/strings.xml
new file mode 100644
index 0000000..9f47093
--- /dev/null
+++ b/res/values-cs-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Nová karta"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Nová anonymní karta"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Karty"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Otevřít na nové kartě"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Otevřít na nové kartě na pozadí"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Otevřít vše na nových kartách"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Otevírat nové karty za aktuální kartou"</string>
+</resources>
diff --git a/res/values-cs/strings.xml b/res/values-cs/strings.xml
index 4e05771..c83ae1f 100644
--- a/res/values-cs/strings.xml
+++ b/res/values-cs/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Prohlížeč"</string>
<string name="choose_upload" msgid="3649366287575002063">"Zvolit soubor, který chcete nahrát."</string>
<string name="new_tab" msgid="4505722538297295141">"Nové okno"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nové anonymní okno"</string>
<string name="active_tabs" msgid="3050623868203544623">"Okna"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Záložky"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Nejnavštěvovanější"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Prohlížeč"</string>
<string name="cancel" msgid="3017274947407233702">"Zrušit"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Žádné shody"</item>
- <item quantity="one" msgid="4352019729062956802">"Shoda"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> shod"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> shod"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Načítání..."</string>
<string name="page_info" msgid="4048529256302257195">"Informace o stránce"</string>
<string name="page_info_view" msgid="5303490449842635158">"Zobrazit informace o stránce"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Pokračovat"</string>
<string name="security_warning" msgid="6607795404322797541">"Upozornění zabezpečení"</string>
<string name="view_certificate" msgid="1472768887529093862">"Zobrazit certifikát"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Přejít zpět"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Tento certifikát nepochází od důvěryhodné autority."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Název webu se neshoduje s názvem uvedeným v certifikátu."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Platnost certifikátu vypršela."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Předat dál"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Zrušit"</string>
- <string name="location" msgid="969988560160364559">"Místo"</string>
- <string name="name" msgid="5990326151488445481">"Jméno"</string>
+ <string name="location" msgid="3411848697912600125">"Adresa"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Přidat do složky"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Nová složka"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Upravit složku"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Smazat složku"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Žádné podsložky"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Záložky"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Plocha"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Jiná složka..."</string>
+ <string name="name" msgid="5462672162695365387">"Štítek"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Přidat záložku"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Přidat k záložkám"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Přidat stránku do záložek"</string>
+ <string name="remove" msgid="7820112494467011374">"Odstranit"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Upravit záložku"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Přidat odkaz na plochu"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Přidat zástupce na plochu"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Otevřít"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Smazat záložku"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Zrušit přístup k poloze"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Tuto adresu URL nelze přidat do záložek."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Smazat"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Přidat poslední zobrazenou stránku do záložek"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Zobrazit jako miniatury"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Zrušit přístup k poloze"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniatury"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Seznam"</string>
<string name="current_page" msgid="7510129573681663135">"od "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Záložka <xliff:g id="BOOKMARK">%s</xliff:g> bude smazána."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Otevřít v novém okně"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Otevřít vše v nových oknech"</string>
<string name="goto_dot" msgid="3895839050522602723">"Přejít"</string>
- <string name="find_dot" msgid="6259312434696611957">"Vyhledat na stránce"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Otevřít novou anonymní kartu"</string>
<string name="select_dot" msgid="6299170761900561967">"Vybrat text"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Aktuální okna"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Zavřít"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Stažené"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Kopírovat adresu URL stránky"</string>
<string name="share_page" msgid="593756995297268343">"Sdílet stránku"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Uložit jako webový archiv"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Webový archiv byl uložen."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Uložení webového archivu se nezdařilo."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"Počet záložek: <xliff:g id="BOOKMARK_COUNT">%d</xliff:g>"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Prázdná složka"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Otevřít"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Otevřít v novém okně"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Přidat odkaz do záložek"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Otevřít v novém okně na pozadí"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Uložit odkaz"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Sdílet odkaz"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopírovat"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Nastavit domovskou stránku"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Nastavit vyhledávač"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Výběr vyhledávače"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Použít aktuální stránku"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Nastavit na..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Aktuální stránka"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Prázdná stránka"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Výchozí stránka"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Automaticky přizpůsobit"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Přizpůsobit velikost webových stránek obrazovce"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Zobrazení pouze na šířku"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Zobrazit stránky pouze s displejem otočeným na šířku"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Nastavení ochrany osobních údajů"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Obecné"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Synchronizace"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Automatické vyplňování"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synchronizovat s prohlížečem Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Sdílet záložky a jiná data mezi Prohlížečem systému Android a aplikací Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Účet Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synchronizovat záložky"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synchronizovat záložky mezi Prohlížečem systému Android a aplikací Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Synchronizovat"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Vyberte účet Google pro sdílení"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Automatické vyplňování formulářů"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Vyplňování webových formulářů jediným kliknutím"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Nastavení autom. vyplňování"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Nastavení a správa automaticky vyplněných formulářů"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Automatické přihlášení do Googlu"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Nebyly nalezeny žádné účty"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Automaticky se přihlašovat k webům Google pomocí účtu <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Přihlášení na stránky Google pomocí uživatelského jména <xliff:g id="ID_1">%s</xliff:g>"\n" Automatické přihlášení Google se řídí vaším nastavením ochrany osobních údajů a zabezpečení"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Nepřihlašovat se automaticky"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Automatické vyplňování umožňuje vyplnit webové formuláře jediným kliknutím pomocí údajů z vašeho profilu."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Jméno a příjmení:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-mail:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Název společnosti:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"1. řádek adresy:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Adresa, č.p., P.O. box"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"2. řádek adresy:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Pokoj, apartmá, buňka, budova, podlaží apod."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Město:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Stát / Provincie / Oblast:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"PSČ:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Země:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Neplatné telefonní číslo"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Uložit profil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profil uložen"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profil byl smazán."</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Smazat profil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Podobné webové formuláře může prohlížeč vyplňovat automaticky. Chcete nastavit profil?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Automatické vyplňování lze vždy nakonfigurovat prostřednictvím nastavení prohlížeče."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Deaktivovat Automatické vyplňování"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Ochrana osobních údajů a zabezpečení"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Vymazat mezipaměť"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Vymazat všechen obsah a databáze uložené do místní mezipaměti"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Obsah a databáze uložené v místní mezipaměti budou vymazány."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Soubory cookie"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Vymazat soubory cookie"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Vymazat všechny soubory cookie prohlížeče"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Všechny soubory cookie budou vymazány."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Vymazat historii"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Vymazat historii navigace v prohlížeči"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Historie navigace v prohlížeči bude vymazána."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Data formulářů"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Vymazat data formulářů"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Vymazat všechna uložená data formulářů"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Všechna uložená data formulářů budou vymazána."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Vymazat hesla"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Vymazat všechna uložená hesla"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Všechna uložená hesla budou vymazána."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Místo"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Povolit polohu"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Povolit webovým stránkám žádat o přístup k informacím o vaší poloze"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Zrušit přístup k poloze"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Zrušit všem webovým stránkám přístup k poloze"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Zrušit všem webovým stránkám přístup k poloze"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Nastavení zabezpečení"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Hesla"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Zapamatovat hesla"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Ukládat uživatelská jména a hesla pro webové stránky"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Zapamatovat data formulářů"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Výchozí přiblížení"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Otevírat stránky v náhledu"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Zobrazit náhled nově otevřených stránek"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Upřesnit nastavení"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Pokročilé"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Zrušit přístup k poloze"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Pokročilá nastavení pro jednotlivé webové stránky"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Obnovit výchozí"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Obnovit výchozí"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Obnovit výchozí nastavení"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Budou obnoveny výchozí hodnoty nastavení."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japonština (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japonština (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japonština (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Korejština (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Kódování textu"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Laboratoř Google"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Rychlé ovládací prvky"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Posunutím palce z levého nebo pravého okraje otevřete rychlé ovládací prvky."</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Nejnavštěvovanější domovská stránka"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Nastaví domovskou stránku tak, aby zobrazovala nejčastěji navštěvované stránky."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problémy s datovým připojením"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problém se souborem"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Potvrdit"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Vymazat všechna data"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Zrušit"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Nastavení tapety..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Záložky"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Žádné záložky k zobrazení"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Vyberte účet"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synchronizovat s účtem Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Vaše záložky v systému Android nejsou přidruženy k účtu Google."</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Odebrat záložky systému Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Přidat všechny záložky systému Android do záložek účtu <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Sdílet"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Žádné další karty nejsou k dispozici"</string>
</resources>
diff --git a/res/values-da-xlarge/strings.xml b/res/values-da-xlarge/strings.xml
new file mode 100644
index 0000000..ab581c7
--- /dev/null
+++ b/res/values-da-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Ny fane"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Ny inkognitofane"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Faner"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Åbn i ny fane"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Åbn på ny fane i baggrunden"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Åbn alle i nye faner"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Åbn nye faner bag den aktive"</string>
+</resources>
diff --git a/res/values-da/strings.xml b/res/values-da/strings.xml
index 1e9d0af..74c1333 100644
--- a/res/values-da/strings.xml
+++ b/res/values-da/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Browser"</string>
<string name="choose_upload" msgid="3649366287575002063">"Vælg fil til upload"</string>
<string name="new_tab" msgid="4505722538297295141">"Nyt vindue"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nyt inkognitovindue"</string>
<string name="active_tabs" msgid="3050623868203544623">"Vinduer"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Bogmærker"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Mest besøgte"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Browser"</string>
<string name="cancel" msgid="3017274947407233702">"Annuller"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Der er ingen matches"</item>
- <item quantity="one" msgid="4352019729062956802">"1 match"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> matches"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> matches"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Indlæser ..."</string>
<string name="page_info" msgid="4048529256302257195">"Sideoplysninger"</string>
<string name="page_info_view" msgid="5303490449842635158">"Vis sideoplysninger"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Fortsæt"</string>
<string name="security_warning" msgid="6607795404322797541">"Sikkerhedsadvarsel"</string>
<string name="view_certificate" msgid="1472768887529093862">"Vis certifikat"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Tilbage"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Dette certifikat stammer ikke fra en troværdig kilde."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Navnet på dette websted stemmer ikke overens med navnet på certifikatet."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Dette certifikat er udløbet."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Fremad"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Annuller"</string>
- <string name="location" msgid="969988560160364559">"Placering"</string>
- <string name="name" msgid="5990326151488445481">"Navn"</string>
+ <string name="location" msgid="3411848697912600125">"Adresse"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Føj til"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Ny mappe"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Rediger mappen"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Slet mappen"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Ingen undermapper"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Bogmærker"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Startskærm"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Anden mappe…"</string>
+ <string name="name" msgid="5462672162695365387">"Etiket"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Tilføj bogmærke"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Føj til bogmærker"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Tilføj side som bogmærke"</string>
+ <string name="remove" msgid="7820112494467011374">"Fjern"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Rediger bogmærke"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Føj genvej til Start"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Føj genvej til startskærm"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Åbn"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Slet bogmærke"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Fjern fra bogmærker"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Denne webadresse kan ikke tilføjes som bogmærke."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Slet"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Opret bogmærke for sidst viste side"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Miniaturevisning"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Listevisning"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniaturebilleder"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Liste"</string>
<string name="current_page" msgid="7510129573681663135">"fra "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Bogmærket \"<xliff:g id="BOOKMARK">%s</xliff:g>\" slettes."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Åbn i et nyt vindue"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Åbn alle i nye vinduer"</string>
<string name="goto_dot" msgid="3895839050522602723">"Gå"</string>
- <string name="find_dot" msgid="6259312434696611957">"Find på side"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Åbn ny inkognitofane"</string>
<string name="select_dot" msgid="6299170761900561967">"Vælg tekst"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Aktuelle vinduer"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Luk"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Downloads"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Kopier sidens webadresse"</string>
<string name="share_page" msgid="593756995297268343">"Del side"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Gem som webarkiv"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Webarkivet blev gemt."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Webarkivet blev ikke gemt."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> bogmærker"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Mappen er tom"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Åbn"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Åbn i et nyt vindue"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Opret et bogmærke for linket"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Åbn i et nyt vindue i baggrunden"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Gem link"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Del link"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopier"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Angiv startside"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Angiv søgemaskine"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Vælg en søgemaskine"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Brug aktuel side"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Angiv som..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Aktuel side"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Tom side"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Standardside"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Tilpas sider automatisk"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Tilpas websider, så de passer til skærmen"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Kun liggende visning"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Vis kun sider i den brede liggende retning"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Indstillinger for fortrolighed"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Generelt"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Synkronisering"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"AutoFyld"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synkroniser med Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Del bogmærker og andre data mellem Android-browser og Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google-konto"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synkroniser bogmærker"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synkroniser bogmærker mellem Android-browser og Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Start synkronisering"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Vælg Google-konto at dele med"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"AutoFyld-formular"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Udfyld webformularer med et enkelt klik"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Indstillinger for AutoFyld"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Konfigurer og administrer data for AutoFyld-formularer"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Automatisk Google-login"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Der blev ikke fundet nogen konti"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Log automatisk ind på Googles websteder med <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Logger ind på Google-websteder ved hjælp af <xliff:g id="ID_1">%s</xliff:g>"\n"Dine indstillinger for sikkerhed og beskyttelse af personlige oplysninger kontrollerer automatisk login til Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Log ikke ind automatisk"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"AutoFyld bruger din profil til at hjælpe dig med at udfylde webformularer med et enkelt klik."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Fulde navn:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-mail:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Virksomhedsnavn:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Adresselinje 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Adresse, postboks, c/o"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Adresselinje 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Lejlighed, suite, afdeling, bygning, etage osv."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"By:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Stat/provins/region:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Postnummer:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Land:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Ugyldigt telefonnummer"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Gem profil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profilen er gemt"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profilen er slettet"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Slet profil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Browseren kan automatisk udfylde webformularer som denne. Vil du konfigurere din profil?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"AutoFyld kan altid konfigureres via indstillingerne for Browser."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Deaktiver AutoFyld"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Sikkerhed og beskyttelse af personlige oplysninger"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Ryd cache"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Ryd lokalt cachelagret indhold og databaser"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Lokalt cachelagret indhold og databaser slettes."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookies"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Ryd alle cookiedata"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Ryd alle browsercookies"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Alle cookies slettes."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Ryd oversigt"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Ryd browserens navigationsoversigt"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Browserens navigationsoversigt slettes."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Formulardata"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Ryd formulardata"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Ryd alle gemte formulardata"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Alle gemte formulardata ryddes."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Ryd adgangskoder"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Ryd alle gemte adgangskoder"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Alle gemte adgangskoder slettes."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Placering"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Aktiver placering"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Tillad, at websteder anmoder om adgang til din placering"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Ryd placeringsadgang"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Ryd placeringsadgang for alle websteder"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Ryd placeringsadgang for alle websteder"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Sikkerhedsindstillinger"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Adgangskoder"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Husk adgangskoder"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Gem brugernavne og adgangskoder til websteder"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Husk formulardata"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Standardzoom"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Åbn sider i oversigt"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Vis oversigt over sider, som er åbnet for nylig"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Avancerede indstillinger"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Avanceret"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Indstillinger for websteder"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Avancerede indstillinger for individuelle websteder"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Gendannelse af standardindstillinger"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Nulstil til standard"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Gendan standardindstillinger"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Indstillingerne vil blive gendannet til standardværdierne."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japansk (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japansk (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japansk (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Koreansk (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Tekstkodning"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Hurtig betjening"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Lad tommelfingeren glide hurtigt fra venstre eller højre side for at få adgang til hurtig betjening"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Mest besøgte hjemmeside"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Indstiller din hjemmeside til at vise de mest besøgte sider."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Dataforbindelsesproblem"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Der er et problem med filen"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Bekræft"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Slet alle data"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Annuller"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Indstiller tapet ..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Bogmærker"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Der er ingen bogmærker"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Vælg konto"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synkroniser med Google-konto"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Dine Android-bogmærker er ikke tilknyttet en Google-konto"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Fjern dine Android-bogmærker"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Føj dine Android-bogmærker til bogmærker for <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Del"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Der er ikke flere tilgængelige faner"</string>
</resources>
diff --git a/res/values-de-xlarge/strings.xml b/res/values-de-xlarge/strings.xml
new file mode 100644
index 0000000..71c5fa3
--- /dev/null
+++ b/res/values-de-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Neuer Tab"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Neuer Inkognito-Tab"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Tabs"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"In neuem Tab öffnen"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"In neuem Hintergrundtab öffnen"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Alle in jeweils neuem Tab öffnen"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Neue Tabs hinter dem aktuellen Tab öffnen"</string>
+</resources>
diff --git a/res/values-de/strings.xml b/res/values-de/strings.xml
index e50878e..2c7a909 100644
--- a/res/values-de/strings.xml
+++ b/res/values-de/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Browser"</string>
<string name="choose_upload" msgid="3649366287575002063">"Datei zum Hochladen auswählen"</string>
<string name="new_tab" msgid="4505722538297295141">"Neues Fenster"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Neues Inkognito-Fenster"</string>
<string name="active_tabs" msgid="3050623868203544623">"Fenster"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Lesezeichen"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Meistbesucht"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Browser"</string>
<string name="cancel" msgid="3017274947407233702">"Abbrechen"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Keine Treffer"</item>
- <item quantity="one" msgid="4352019729062956802">"1 Treffer"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> Treffer"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> Treffer"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Wird geladen..."</string>
<string name="page_info" msgid="4048529256302257195">"Seiteninfo"</string>
<string name="page_info_view" msgid="5303490449842635158">"Seiteninfo anzeigen"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Fortfahren"</string>
<string name="security_warning" msgid="6607795404322797541">"Sicherheitswarnung"</string>
<string name="view_certificate" msgid="1472768887529093862">"Zertifikat anzeigen"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Zurück"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Dieses Zertifikat wurde nicht von einer vertrauenswürdigen Stelle ausgegeben."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Der Name der Website stimmt nicht mit dem Namen auf dem Zertifikat überein."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Dieses Zertifikat ist abgelaufen."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Vorwärts"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Abbrechen"</string>
- <string name="location" msgid="969988560160364559">"URL"</string>
- <string name="name" msgid="5990326151488445481">"Name"</string>
+ <string name="location" msgid="3411848697912600125">"Adresse"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Hinzufügen zu"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Neuer Ordner"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Ordner bearbeiten"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Ordner löschen"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Keine Unterordner"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Lesezeichen"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Startbildschirm"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Anderer Ordner..."</string>
+ <string name="name" msgid="5462672162695365387">"Label"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Lesezeichen hinzufügen"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Zu Lesezeichen hinzufügen"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Diese Seite als Lesezeichen speichern"</string>
+ <string name="remove" msgid="7820112494467011374">"Entfernen"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Lesezeichen bearbeiten"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Verknüpfung auf dem Startbildschirm erstellen"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Verknüpfung auf dem Startbildschirm erstellen"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Öffnen"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Lesezeichen löschen"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Aus Lesezeichen entfernen"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Diese URL kann nicht als Lesezeichen gespeichert werden."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Löschen"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Lesezeichen für zuletzt besuchte Seite"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Miniaturansicht"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Listenansicht"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniaturansichten"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Liste"</string>
<string name="current_page" msgid="7510129573681663135">"von "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Lesezeichen \"<xliff:g id="BOOKMARK">%s</xliff:g>\" wird gelöscht."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"In neuem Fenster öffnen"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Alle in jeweils neuem Fenster öffnen"</string>
<string name="goto_dot" msgid="3895839050522602723">"Los"</string>
- <string name="find_dot" msgid="6259312434696611957">"Auf Seite suchen"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Neuen Inkognito-Tab öffnen"</string>
<string name="select_dot" msgid="6299170761900561967">"Text auswählen"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Aktuelle Fenster"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Schließen"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Downloads"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Seiten-URL kopieren"</string>
<string name="share_page" msgid="593756995297268343">"Seitenlink weiterleiten"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Als Webarchiv speichern"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Webarchiv gespeichert."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Das Webarchiv wurde nicht gespeichert."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> Lesezeichen"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Leerer Ordner"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Öffnen"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"In neuem Fenster öffnen"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Link zu Lesezeichen hinzufügen"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"In neuem Hintergrundfenster öffnen"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Link speichern"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Link weiterleiten"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopieren"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Startseite festlegen"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Suchmaschine festlegen"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Suchmaschine auswählen"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Aktuelle Seite verwenden"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Eingestellt auf..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Aktuelle Seite"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Leere Seite"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Standardseite"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Autom. Anpassung"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Webseiten an den Bildschirm anpassen"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Anzeige nur im Querformat"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Seiten nur im Querformat anzeigen"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Datenschutzeinstellungen"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Allgemein"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Synchronisierung"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"AutoFill"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Mit Google Chrome synchronisieren"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Lesezeichen und andere Daten zwischen Android-Browser und Google Chrome austauschen"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google-Konto"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Lesezeichen synchronisieren"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Lesezeichen zwischen Android-Browser und Google Chrome synchronisieren"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Synchronis. starten"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Google-Konto wählen"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Formulare automatisch ausfüllen"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Onlineformulare mit einem einzigen Klick ausfüllen"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"AutoFill-Einstellungen"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Angaben für das automatische Ausfüllen von Formularen festlegen und verwalten"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Automatische Google-Anmeldung"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Keine Konten gefunden"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Bei Google-Websites automatisch mit <xliff:g id="ID_1">%s</xliff:g> anmelden"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Die Anmeldung auf Google-Websites anhand <xliff:g id="ID_1">%s</xliff:g>"\n"Ihrer Einstellungen für Datenschutz und Sicherheit steuert die automatische Google-Anmeldung."</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Nicht automatisch anmelden"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"AutoFill verwendet Ihr Profil, damit Sie Onlineformulare mit einem einzigen Klick ausfüllen können."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Vollständiger Name:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-Mail:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Name des Unternehmens:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Adresszeile 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Straße, Postfach usw."</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Adresszeile 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Apartment, Wohnung, Gebäude, Etage usw."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Stadt:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Bundesland:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Postleitzahl:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Land:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Ungültige Telefonnummer"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Profil speichern"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profil wurde gespeichert."</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profil gelöscht"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Profil löschen"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Browser können solche Webformulare automatisch vervollständigen. Möchten Sie Ihr Profil anlegen?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"AutoFill kann stets über die Browsereinstellungen konfiguriert werden."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"AutoFill deaktivieren"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Datenschutz und Sicherheit"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Cache löschen"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Content und Datenbanken aus dem lokalen Cache löschen"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Content und Datenbanken werden aus dem lokalen Cache gelöscht."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookies"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Cookie-Daten löschen"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Alle Browser-Cookies löschen"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Alle Cookies werden gelöscht."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Verlauf löschen"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Navigationsverlauf des Browsers löschen"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Der Navigationsverlauf des Browsers wird gelöscht."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Formulardaten"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Formulardaten löschen"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Alle gespeicherten Formulardaten löschen"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Alle gespeicherten Formulardaten werden gelöscht."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Passwörter löschen"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Alle gespeicherten Passwörter löschen"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Alle gespeicherten Passwörter werden gelöscht."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Standort"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Standort aktivieren"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Standortzugriff für Websites zulassen"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Standortzugriff löschen"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Standortzugriff für alle Websites löschen"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Standortzugriff für alle Websites löschen"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Sicherheitseinstellungen"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Passwörter"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Passwörter merken"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Nutzernamen und Passwörter für Websites speichern"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Formulardaten merken"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Standard-Zoom"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Seitenübersicht"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Neue Seiten in der Übersicht anzeigen"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Erweiterte Einstellungen"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Erweitert"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Website-Einstellungen"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Erweiterte Einstellungen für einzelne Websites"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Auf Standardwerte zurücksetzen"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Zurück auf Standard"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Standardeinstellungen wiederherstellen"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Die Einstellungen werden auf die Standardeinstellung zurückgesetzt."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japanisch (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japanisch (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japanisch (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Koreanisch (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Textcodierung"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Schnellsteuerung"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Daumen zum Zugriff auf Schnellsteuerung von linker oder rechte Ecke ziehen"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Startseite - am häufigsten besucht"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Legt fest, dass auf der Starts. die am häufigsten besuchten Seiten angez. werden"</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Datenverbindungsproblem"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problem mit Datei"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Bestätigen"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Alle Daten löschen"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Abbrechen"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Hintergrund wird eingestellt..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Lesezeichen"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Es sind keine Lesezeichen vorhanden."</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Konto auswählen"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Mit Google-Konto synchronisieren"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Ihre Android-Lesezeichen sind mit keinem Google-Konto verknüpft."</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Android-Lesezeichen entfernen"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Ihre Android-Lesezeichen den Lesezeichen für <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g> hinzufügen"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Weitergeben"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Es sind keine weiteren Tabs verfügbar."</string>
</resources>
diff --git a/res/values-el-xlarge/strings.xml b/res/values-el-xlarge/strings.xml
new file mode 100644
index 0000000..17411be
--- /dev/null
+++ b/res/values-el-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Νέα καρτέλα"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Νέα καρτέλα ανών. περιήγησης"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Καρτέλες"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Άνοιγμα σε νέα καρτέλα"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Άνοιγμα σε νέα καρτέλα στο παρασκήνιο"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Άνοιγμα όλων σε νέες καρτέλες"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Άνοιγμα νέων καρτελών πίσω από την τρέχουσα"</string>
+</resources>
diff --git a/res/values-el/strings.xml b/res/values-el/strings.xml
index 493ec48..b43d812 100644
--- a/res/values-el/strings.xml
+++ b/res/values-el/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Internet"</string>
<string name="choose_upload" msgid="3649366287575002063">"Επιλογή αρχείου για μεταφόρτωση"</string>
<string name="new_tab" msgid="4505722538297295141">"Νέο παράθυρο"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Νέο παράθυρο για ανώνυμη περιήγηση"</string>
<string name="active_tabs" msgid="3050623868203544623">"Παράθυρα"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Σελιδοδείκτες"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Οι πιο δημοφιλείς"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Internet"</string>
<string name="cancel" msgid="3017274947407233702">"Ακύρωση"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Δεν υπάρχουν αποτελέσματα"</item>
- <item quantity="one" msgid="4352019729062956802">"1 αποτέλεσμα"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> αποτελέσματα"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> αποτελέσματα"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Φόρτωση..."</string>
<string name="page_info" msgid="4048529256302257195">"Πληροφορίες σελίδας"</string>
<string name="page_info_view" msgid="5303490449842635158">"Προβολή πληροφοριών σελίδας"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Συνέχεια"</string>
<string name="security_warning" msgid="6607795404322797541">"Προειδοποίηση ασφαλείας"</string>
<string name="view_certificate" msgid="1472768887529093862">"Προβολή πιστοποιητικού"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Επιστροφή"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Αυτό το πιστοποιητικό δεν είναι από έμπιστη αρχή."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Το όνομα του ιστότοπου δεν αντιστοιχεί στο όνομα του πιστοποιητικού."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Αυτό το πιστοποιητικό έχει λήξει."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Εμπρός"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Ακύρωση"</string>
- <string name="location" msgid="969988560160364559">"Τοποθεσία"</string>
- <string name="name" msgid="5990326151488445481">"Όνομα"</string>
+ <string name="location" msgid="3411848697912600125">"Διεύθυνση"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Προσθήκη σε"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Νέος φάκελος"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Επεξεργασία φακέλου"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Διαγραφή φακέλου"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Δεν υπάρχουν υποφάκελοι"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Σελιδοδείκτες"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Αρχική οθόνη"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Άλλος φάκελος…"</string>
+ <string name="name" msgid="5462672162695365387">"Ετικέτα"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Προσθήκη σελιδοδείκτη"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Προσθήκη στους σελιδοδείκτες"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Προσθήκη στους σελιδοδείκτες"</string>
+ <string name="remove" msgid="7820112494467011374">"Κατάργηση"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Επεξεργασία σελιδοδείκτη"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Προσθήκη συντόμευσης στην αρχική οθόνη"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Προσθήκη συντόμευσης στην αρχική οθόνη"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Άνοιγμα"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Διαγραφή σελιδοδείκτη"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Κατάργηση από τους σελιδοδείκτες"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Η διεύθυνση URL δεν ήταν δυνατό να προστεθεί στους σελιδοδείκτες."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Διαγραφή"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Προσθήκη της τελευταίας σελίδας που προβλήθηκε στους σελιδοδείκτες"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Προβολή μικρογραφίας"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Προβολή λίστας"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Μικρογραφίες"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Λίστα"</string>
<string name="current_page" msgid="7510129573681663135">"από "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Ο σελιδοδείκτης \"<xliff:g id="BOOKMARK">%s</xliff:g>\" θα διαγραφεί."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Άνοιγμα σε νέο παράθυρο"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Άνοιγμα όλων σε νέα παράθυρα"</string>
<string name="goto_dot" msgid="3895839050522602723">"Μετάβαση"</string>
- <string name="find_dot" msgid="6259312434696611957">"Εύρεση στη σελίδα"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Άνοιγμα νέας καρτέλας ανώνυμης περιήγησης"</string>
<string name="select_dot" msgid="6299170761900561967">"Επιλογή κειμένου"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Τρέχοντα παράθυρα"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Κλείσιμο"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Λήψεις"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Αντιγραφή διεύθυνσης url της σελίδας"</string>
<string name="share_page" msgid="593756995297268343">"Κοινή χρήση σελίδας"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Αποθήκευση ως αρχείου ιστού"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Το αρχείο ιστού αποθηκεύθηκε."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Η αποθήκευση του αρχείου ιστού απέτυχε."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> σελιδοδείκτες"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Κενός φάκελος"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Άνοιγμα"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Άνοιγμα σε νέο παράθυρο"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Πρόσθεση συνδέσμου στους σελιδοδείκτες"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Άνοιγμα σε νέο παράθυρο στο παρασκήνιο"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Αποθήκευση συνδέσμου"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Κοινή χρήση συνδέσμου"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Αντιγραφή"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Ορισμός ως αρχική σελίδα"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Ορισμός μηχανής αναζήτησης"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Επιλέξτε μηχανή αναζήτησης"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Χρήση τρέχουσας σελίδας"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Ορισμός σε..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Τρέχουσα σελίδα"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Κενή σελίδα"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Προεπιλεγμένη σελίδα"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Αυτόματη προσαρμογή σελίδων"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Μορφοποίηση ιστοσελίδων για την προσαρμογή τους στο μέγεθος της οθόνης"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Προβολή μόνο σε τοπίο"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Προβολή σελίδων μόνο στον ευρύτερο προσανατολισμό τοπίου στην οθόνη"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Ρυθμίσεις απορρήτου"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Γενικές"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Συγχρονισμός"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Αυτόματη συμπλήρωση"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Συγχρονισμός με Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Κάντε κοινή χρήση σελιδοδεικτών και άλλων δεδομένων μεταξύ του Προγράμματος περιήγησης του Android και του Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Λογαριασμός Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Συγχρονισμός σελιδοδεικτών"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Συγχρονισμός σελιδοδεικτών μεταξύ του Προγράμματος περιήγησης του Android και του Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Έναρξη συγχρονισμού"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Επιλογή λογαριασμού"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Αυτόματη συμπλήρωση φόρμας"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Συμπληρώστε φόρμες ιστού με ένα κλικ"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Ρυθμίσεις αυτόματης συμπλήρωσης"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Ρύθμιση και διαχείριση δεδομένων για φόρμες Αυτόματης συμπλήρωσης"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Αυτόματη σύνδεση στο Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Δεν βρέθηκαν λογαριασμοί"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Συνδεθείτε αυτόματα σε Ιστότοπους Google χρησιμοποιώντας το λογαριασμό <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Σύνδεση σε Ιστότοπους Google χρησιμοποιώντας το αναγνωριστικό <xliff:g id="ID_1">%s</xliff:g>"\n"Οι ρυθμίσεις Απόρρητο και Ασφάλεια ελέγχουν την αυτόματη σύνδεση στο Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Να μην γίνεται αυτόματη σύνδεση"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Η Αυτόματη Συμπλήρωση θα χρησιμοποιήσει το προφίλ σας για να σας βοηθήσει να συμπληρώσετε φόρμες ιστού με ένα κλικ."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Πλήρες όνομα:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Ηλεκτρονικό ταχυδρομείο:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Επωνυμία εταιρείας:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Γραμμή διεύθυνσης 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Διεύθυνση, ταχυδρομική θυρίδα, υπόψη"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Γραμμή διεύθυνσης 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Διαμέρισμα, σουίτα, αριθμός, κτίριο, όροφος κ.ά."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Πόλη:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Νομός / Επαρχία / Περιοχή:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Ταχυδρομικός κώδικας:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Χώρα:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Τηλέφωνο:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Μη έγκυρος αριθμός τηλεφώνου"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Αποθήκευση προφίλ"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Το προφίλ αποθηκεύτηκε"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Το προφίλ διαγράφηκε"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Διαγραφή προφίλ"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Το πρόγραμμα περιήγησης μπορεί να ολοκληρώσει αυτόματα φόρμες ιστού σαν αυτήν. Θα θέλατε να δημιουργήσετε το δικό σας προφίλ;"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Μπορείτε να διαμορφώσετε τη λειτουργία αυτόματης συμπλήρωσης μέσα από τις ρυθμίσεις του προγράμματος περιήγησης."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Απενεργοποίηση αυτόματης συμπλήρωσης"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Απόρρητο και Ασφάλεια"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Εκκαθάριση προσωρινής μνήμης"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Εκκαθάριση τοπικά αποθηκευμένου στη μνήμη cache περιεχομένου και βάσεων δεδομένων"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Περιεχόμενο και βάσεις δεδομένων που έχουν αποθηκευτεί στην τοπική προσωρινή μνήμη θα διαγραφούν."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookie"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Εκκαθάριση όλων των δεδομένων cookie"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Εκκαθάριση όλων των cookie του προγράμματος περιήγησης"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Όλα τα cookie θα διαγραφούν."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Εκκαθάριση ιστορικού"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Εκκαθάριση του ιστορικού πλοήγησης του προγράμματος περιήγησης"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Θα γίνει διαγραφή του ιστορικού πλοήγησης του προγράμματος περιήγησης."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Δεδομένα φόρμας"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Εκκαθάριση δεδομένων φόρμας"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Εκκαθάριση όλων των αποθηκευμένων δεδομένων φόρμας"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Θα γίνει διαγραφή όλων των αποθηκευμένων δεδομένων φόρμας."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Εκκαθάριση κωδικών πρόσβασης"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Απαλοιφή όλων των αποθηκευμένων κωδικών πρόσβασης"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Θα γίνει διαγραφή όλων των αποθηκευμένων κωδικών πρόσβασης."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Τοποθεσία"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Ενεργοποίηση τοποθεσίας"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Να επιτρέπεται σε ιστότοπους το αίτημα πρόσβασης στην τοποθεσία σας"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Εκκαθάριση πρόσβασης τοποθεσίας"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Εκκαθάριση πρόσβασης τοποθεσίας για όλους τους ιστότοπους"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Εκκαθάριση πρόσβασης τοποθεσίας για όλους τους ιστότοπους"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Ρυθμίσεις ασφαλείας"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Κωδικοί πρόσβασης"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Απομνημόνευση κωδικών πρόσβασης"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Αποθήκευση ονομάτων χρήστη και κωδικών πρόσβασης για ιστότοπους"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Απομνημόνευση δεδομένων φόρμας"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Προεπιλεγμένο ζουμ"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Άνοιγμα σελίδων στην επισκόπιση"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Εμφάνιση επισκόπισης σελίδων που ανοίξατε πρόσφατα"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Σύνθετες ρυθμίσεις"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Για προχωρημένους"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Ρυθμίσεις ιστότοπου"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Σύνθετες ρυθμίσεις για μεμονωμένους ιστότοπους"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Επαναφορά προεπιλογών"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Επαναφορά προεπιλογών"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Επαναφορά προεπιλεγμένων ρυθμίσεων"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Θα γίνει επαναφορά των ρυθμίσεων στις προεπιλεγμένες τιμές."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Ιαπωνικά (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Ιαπωνικά (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Ιαπωνικά (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Κορεατικά (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Κωδικοποίηση κειμένου"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Εργαστήρια"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Στοιχεία γρήγορου ελέγχου"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Σύρετε τον αντίχειρα από αριστερά ή δεξιά για τα στοιχεία γρήγορου ελέγχου"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Αρχική σελίδα με τις περισ. επισκέψεις"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Ορίζει στην αρχική σελίδα την εμφάνιση των σελίδων με τις περισσότ. επισκέψεις"</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Πρόβλημα σύνδεσης δεδομένων"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Υπάρχει πρόβλημα με το αρχείο"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Επιβεβαίωση"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Διαγραφή όλων των δεδομένων"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Ακύρωση"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Ρύθμιση ταπετσαρίας..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Σελιδοδείκτες"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Δεν υπάρχουν σελιδοδείκτες"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Επιλογή λογαριασμού"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Συγχρον. με Λογαριασμό Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Οι σελιδοδείκτες σας Android δεν σχετίζονται με κάποιον Λογαριασμό Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Καταργήστε τους σελιδοδείκτες σας Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Προσθ. τους σελιδοδείκτες Android στους σελιδοδείκτες του <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Κοινή χρήση"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Δεν υπάρχουν άλλες διαθέσιμες καρτέλες"</string>
</resources>
diff --git a/res/values-en-rGB-xlarge/strings.xml b/res/values-en-rGB-xlarge/strings.xml
new file mode 100644
index 0000000..ee70575
--- /dev/null
+++ b/res/values-en-rGB-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"New tab"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"New incognito tab"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Tabs"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Open in new tab"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Open in new background tab"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Open all in new tabs"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Open new tabs behind the current one"</string>
+</resources>
diff --git a/res/values-en-rGB/strings.xml b/res/values-en-rGB/strings.xml
index 76e4c25..e2bb5fe 100644
--- a/res/values-en-rGB/strings.xml
+++ b/res/values-en-rGB/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Browser"</string>
<string name="choose_upload" msgid="3649366287575002063">"Choose file for upload"</string>
<string name="new_tab" msgid="4505722538297295141">"New window"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"New incognito window"</string>
<string name="active_tabs" msgid="3050623868203544623">"Windows"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Bookmarks"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Most visited"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Browser"</string>
<string name="cancel" msgid="3017274947407233702">"Cancel"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"No matches"</item>
- <item quantity="one" msgid="4352019729062956802">"1 Match"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> matches"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> matches"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Loading…"</string>
<string name="page_info" msgid="4048529256302257195">"Page info"</string>
<string name="page_info_view" msgid="5303490449842635158">"View page info"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Continue"</string>
<string name="security_warning" msgid="6607795404322797541">"Security warning"</string>
<string name="view_certificate" msgid="1472768887529093862">"View certificate"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Go back"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"This certificate is not from a trusted authority."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"The name of the site does not match the name on the certificate."</string>
<string name="ssl_expired" msgid="5739349389499575559">"This certificate has expired."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Forward"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Cancel"</string>
- <string name="location" msgid="969988560160364559">"Location"</string>
- <string name="name" msgid="5990326151488445481">"Name"</string>
+ <string name="location" msgid="3411848697912600125">"Address"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Add to"</string>
+ <string name="new_folder" msgid="7743540149088867917">"New folder"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Edit folder"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Delete folder"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"No sub-folders"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Bookmarks"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Home screen"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Other folder…"</string>
+ <string name="name" msgid="5462672162695365387">"Label"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Add bookmark"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Add to Bookmarks"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Bookmark this page"</string>
+ <string name="remove" msgid="7820112494467011374">"Remove"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Edit bookmark"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Add shortcut to Home"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Add shortcut to home"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Open"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Delete bookmark"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Remove from bookmarks"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"This URL cannot be bookmarked."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Delete"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Bookmark last viewed page"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Thumbnail view"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"List View"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Thumbnails"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"List"</string>
<string name="current_page" msgid="7510129573681663135">"from "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Bookmark \"<xliff:g id="BOOKMARK">%s</xliff:g>\" will be deleted."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Open in new window"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Open all in new windows"</string>
<string name="goto_dot" msgid="3895839050522602723">"Go"</string>
- <string name="find_dot" msgid="6259312434696611957">"Find on page"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Open new incognito tab"</string>
<string name="select_dot" msgid="6299170761900561967">"Select text"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Current windows"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Close"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Downloads"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Copy page URL"</string>
<string name="share_page" msgid="593756995297268343">"Share page"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Save as Web Archive"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Web archive saved."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Failed to save web archive."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> bookmarks"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Empty folder"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Open"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Open in new window"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Bookmark link"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Open in new background window"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Save link"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Share link"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Copy"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Set homepage"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Set search engine"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Select a search engine"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Use current page"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Set to…"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Current page"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Blank page"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Default page"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Auto-fit pages"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Format web pages to fit the screen"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Landscape-only display"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Display pages only in the wider, landscape-screen orientation"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Privacy settings"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"General"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sync"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Auto-fill"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sync with Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Share bookmarks & other data between Android Browser and Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google account"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sync bookmarks"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sync bookmarks between Android Browser and Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Start syncing"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Select Google account to share with"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Form AutoFill"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Fill in web forms with a single click"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"AutoFill Settings"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Set up & manage data for AutoFilled forms"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Automatic Google sign-in"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"No accounts found"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Sign in to Google sites automatically, using <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Signing into Google sites, using <xliff:g id="ID_1">%s</xliff:g>"\n"Your Privacy & Security settings control automatic Google sign-in"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Don\'t sign in automatically"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"AutoFill will use your profile to help you complete web forms with a single click."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Full name:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Email:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Company name:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Address line 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Street address, P.O. box, c/o"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Address line 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Flat, suite, unit, building, floor, etc."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"City/Town:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"County/State/Province/Region:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Postcode:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Country:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Phone:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Invalid phone number"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Save profile"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profile saved"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profile deleted"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Delete profile"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Browser can complete web forms like this one automatically. Would you like to set up your profile?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Auto-Fill can always be configured through Browser Settings."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Disable Auto-Fill"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Privacy & Security"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Clear cache"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Clear locally cached content and databases"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Locally cached content and databases will be deleted."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookies"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Clear all cookie data"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Clear all browser cookies"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"All cookies will be deleted."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Clear history"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Clear the browser navigation history"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"The browser navigation history will be deleted."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Form data"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Clear form data"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Clear all the saved form data"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"All saved form data will be deleted."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Clear passwords"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Clear all saved passwords"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"All saved passwords will be deleted."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Location"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Enable location"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Allow sites to request access to your location"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Clear location access"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Clear location access for all websites"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Clear location access for all websites"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Security settings"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Passwords"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Remember passwords"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Save usernames and passwords for websites"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Remember form data"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Default zoom"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Open pages in overview"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Show overview of newly opened pages"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Advanced settings"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Advanced"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Website settings"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Advanced settings for individual websites"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Reset defaults"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Reset to default"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Restore default settings"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Settings will revert to default values."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japanese (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japanese (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japanese (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Korean (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Text encoding"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Quick Controls"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Swipe thumb from left or right edge to access quick controls"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Most Visited Homepage"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Sets your homepage to show the most visited pages."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Data connectivity problem"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problem with file"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Confirm"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Delete all data"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Cancel"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Setting wallpaper..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Bookmarks"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"There are no bookmarks"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Choose account"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sync with Google account"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Your Android bookmarks are not associated with a Google account"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Remove your Android bookmarks"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Add your Android bookmarks to bookmarks for <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Share"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"No more tabs available"</string>
</resources>
diff --git a/res/values-es-rUS-xlarge/strings.xml b/res/values-es-rUS-xlarge/strings.xml
new file mode 100644
index 0000000..096451d
--- /dev/null
+++ b/res/values-es-rUS-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Pestaña nueva"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Nueva pestaña de incógnito"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Pestañas"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Abrir en una ventana nueva"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Abrir en una nueva pestaña de fondo"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Abrir todos en pestañas nuevas"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Abrir nuevas pestañas detrás de la actual"</string>
+</resources>
diff --git a/res/values-es-rUS/strings.xml b/res/values-es-rUS/strings.xml
index 9958b89..829e5c4 100644
--- a/res/values-es-rUS/strings.xml
+++ b/res/values-es-rUS/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Navegador"</string>
<string name="choose_upload" msgid="3649366287575002063">"Elegir el archivo para cargar"</string>
<string name="new_tab" msgid="4505722538297295141">"Ventana nueva"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nueva ventana de incógnito"</string>
<string name="active_tabs" msgid="3050623868203544623">"Ventanas"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Marcadores"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Más visitados"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Navegador"</string>
<string name="cancel" msgid="3017274947407233702">"Cancelar"</string>
<string name="ok" msgid="1509280796718850364">"Aceptar"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Sin coincidencias"</item>
- <item quantity="one" msgid="4352019729062956802">"1 coincidencia"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> coincide"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> coincide"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Cargando…"</string>
<string name="page_info" msgid="4048529256302257195">"Información de la página"</string>
<string name="page_info_view" msgid="5303490449842635158">"Ver información de la página"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Continuar"</string>
<string name="security_warning" msgid="6607795404322797541">"Advertencia de seguridad"</string>
<string name="view_certificate" msgid="1472768887529093862">"Ver certificado"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Volver"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Este certificado no proviene de una fuente confiable."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"El nombre del sitio no coincide con el nombre del certificado."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Este certificado ha expirado."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Siguiente"</string>
<string name="save" msgid="5922311934992468496">"Aceptar"</string>
<string name="do_not_save" msgid="6777633870113477714">"Cancelar"</string>
- <string name="location" msgid="969988560160364559">"Ubicación"</string>
- <string name="name" msgid="5990326151488445481">"Nombre"</string>
+ <string name="location" msgid="3411848697912600125">"Dirección"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Agregar a"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Carpeta nueva"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Editar carpeta"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Eliminar carpeta"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"No hay subcarpetas"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Marcadores"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Pantalla principal"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Otra carpeta…"</string>
+ <string name="name" msgid="5462672162695365387">"Etiqueta"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Agregar marcador"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Agregar a Favoritos"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Agregar esta página a Favoritos"</string>
+ <string name="remove" msgid="7820112494467011374">"Eliminar"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Editar marcador"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Agregar acceso directo a la página de inicio"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Agregar acceso directo a la página de inicio"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Abrir"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Eliminar marcador"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Eliminar de marcadores"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"No se puede agregar esta URL a los marcadores."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Eliminar"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Última página vista del marcador"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Vista en miniatura"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Vista de lista"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniaturas"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Lista"</string>
<string name="current_page" msgid="7510129573681663135">"de "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"El marcador \"<xliff:g id="BOOKMARK">%s</xliff:g>\" se eliminará."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Abrir en una ventana nueva"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Abrir todos en ventanas nuevas"</string>
<string name="goto_dot" msgid="3895839050522602723">"Ir"</string>
- <string name="find_dot" msgid="6259312434696611957">"Buscar en la página"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Abrir nueva pestaña de incógnito"</string>
<string name="select_dot" msgid="6299170761900561967">"Seleccionar texto"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Ventana actual"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Cerrar"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Descargas"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Copiar URL de la página"</string>
<string name="share_page" msgid="593756995297268343">"Compartir página"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Guardar como Archivo web"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Archivo web guardado."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Error al guardar el archivo web."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> Marcadores"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Vaciar carpeta"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Abrir"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Abrir en una ventana nueva"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Enlace del marcador"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Abrir en una nueva ventana de fondo"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Guardar enlace"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Compartir vínculo"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Copiar"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Definir página de inicio"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Establecer el motor de búsqueda"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Seleccionar un motor de búsqueda"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Utilizar la página actual"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Configurado en"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Página actual"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Página en blanco"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Página predeterminada"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Ajuste automát. de pág."</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Formatea las páginas web para que se ajusten a la pantalla"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Visualización horizontal solamente"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Mostrar páginas sólo en la orientación de pantalla horizontal más ancha"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Configuración de privacidad"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"General"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sincronización"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Autocompletar"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sincronización con Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Compartir favoritos & otros datos entre el navegador Android y Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Cuenta de Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sincronizar favoritos"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sincronizar favoritos entre el navegador Android y Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Iniciar la sincr."</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Selec cta Google p/comp"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Formulario de autollenado"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Completa formularios web con un clic"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Configuración de autollenado"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Configurar y administrar datos para los formularios de autollenado"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Acceso automático a Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"No se encontraron las cuentas"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Acceder automáticamente a sitios de Google utilizando <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Accediendo a Google Sites utilizando<xliff:g id="ID_1">%s</xliff:g>"\n"Tu control de configuración de seguridad & privacidad automático para acceso a Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"No accedas de manera automática"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"La función Autocompletar utilizará tu perfil para ayudarte a rellenar formularios web con un solo clic."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Nombre completo:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Correo electrónico:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Nombre de la empresa:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Dirección línea 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Dirección postal, código postal, A/A"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Dirección línea 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Apartamento, suite, unidad, edificio, suelo, etc."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Ciudad/Pueblo:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Estado / Provincia / Región:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Código postal:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"País:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Teléfono:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Número de teléfono no válido"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Guardar perfil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Perfil guardado"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Perfil eliminado"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Eliminar perfil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"El navegador puede completar formularios web como este de forma automática. ¿Deseas configurar tu perfil?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Autocompletar siempre se puede configurar mediante los Parámetros de configuración del navegador."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Desactivar Autocompletar"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Privacidad y seguridad"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Borrar memoria caché"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Borrar el contenido y las bases de datos de la memoria caché local"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Se suprimirá el contenido y las bases de datos de la memoria caché local."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookies"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Borrar datos de cookies"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Eliminar todas las cookies del navegador"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Se suprimirán todas las cookies."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Borrar historial"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Borrar el historial de navegación del navegador"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Se suprimirá el historial del navegador."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Datos de formulario"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Borrar datos del formulario"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Borrar todos los datos guardados del formulario"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Se suprimirán todos los datos guardados del formulario."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Borrar contraseñas"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Eliminar todas las contraseñas guardadas"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Se suprimirán todas las contraseñas guardadas."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Ubicación"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Activar ubicación"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Permitir que los sitios soliciten acceso a tu ubicación"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Borrar acceso a la ubicación"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Borrar acceso a la ubicación para todos los sitios web"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Borrar acceso a la ubicación para todos los sitios web"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Configuración de seguridad"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Contraseñas"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Recordar contraseñas"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Guardar los nombres de usuario y las contraseñas de los sitios web"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Recordar datos del form."</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Predeterminar zoom"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Abrir las páginas en descripción general"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Mostrar la descripción general de las páginas nuevas abiertas"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Configuración avanzada"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Avanzado"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Configuración del sitio web"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Configuración avanzada para sitios web individuales"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Restablecer valores predeterminados"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Restabl. a valores predet."</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Restaurar configuración predeterminada"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"La configuración volverá a los valores predeterminados."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japonés (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japonés (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japonés (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Coreano (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codificación de texto"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Controles rápidos"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Desliza el pulgar del borde izquierdo o derecho y accede a los controles rápidos."</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Página de inicio más visitada"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Configura tu página principal para que muestre las páginas más visitadas."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problema de conectividad de datos"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problema con el archivo"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Confirmar"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Eliminar todos los datos"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Cancelar"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Estableciendo fondo de pantalla..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Marcadores"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"No hay ningún marcador"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Seleccionar la cuenta"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sincronización con cta de Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Tus favoritos de Android no están asociados con una cuenta de Google."</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Eliminar tus favoritos de Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Agrega tus favoritos de Android a tus favoritos para <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>."</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Compartir"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"No hay más pestañas disponibles."</string>
</resources>
diff --git a/res/values-es-xlarge/strings.xml b/res/values-es-xlarge/strings.xml
new file mode 100644
index 0000000..c4bdd3e
--- /dev/null
+++ b/res/values-es-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Nueva pestaña"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Nueva pestaña de incógnito"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Pestañas"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Abrir en una pestaña nueva"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Abrir en una nueva pestaña en segundo plano"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Abrir todo en pestañas nuevas"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Abrir nuevas pestañas detrás de la actual"</string>
+</resources>
diff --git a/res/values-es/strings.xml b/res/values-es/strings.xml
index 457b5eb..49c56f7 100644
--- a/res/values-es/strings.xml
+++ b/res/values-es/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Navegador"</string>
<string name="choose_upload" msgid="3649366287575002063">"Seleccionar archivo para subir"</string>
<string name="new_tab" msgid="4505722538297295141">"Nueva ventana"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nueva ventana de incógnito"</string>
<string name="active_tabs" msgid="3050623868203544623">"Ventanas"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Marcadores"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Más visitados"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Navegador"</string>
<string name="cancel" msgid="3017274947407233702">"Cancelar"</string>
<string name="ok" msgid="1509280796718850364">"Aceptar"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"No hay coincidencias"</item>
- <item quantity="one" msgid="4352019729062956802">"Una coincidencia"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> coincidencias"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> coincidencias"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Cargando..."</string>
<string name="page_info" msgid="4048529256302257195">"Información de página"</string>
<string name="page_info_view" msgid="5303490449842635158">"Ver información de página"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Continuar"</string>
<string name="security_warning" msgid="6607795404322797541">"Advertencia de seguridad"</string>
<string name="view_certificate" msgid="1472768887529093862">"Ver certificado"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Volver"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Este certificado no procede de una entidad de certificación de confianza."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"El nombre del sitio no coincide con el del certificado."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Este certificado ha caducado."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Siguiente"</string>
<string name="save" msgid="5922311934992468496">"Aceptar"</string>
<string name="do_not_save" msgid="6777633870113477714">"Cancelar"</string>
- <string name="location" msgid="969988560160364559">"Ubicación"</string>
- <string name="name" msgid="5990326151488445481">"Nombre"</string>
+ <string name="location" msgid="3411848697912600125">"Dirección"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Añadir a"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Nueva carpeta"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Editar carpeta"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Eliminar carpeta"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Sin subcarpetas"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Marcadores"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Escritorio"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Otra carpeta…"</string>
+ <string name="name" msgid="5462672162695365387">"Etiqueta"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Añadir marcador"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Añadir a marcadores"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Añadir esta página a marcadores"</string>
+ <string name="remove" msgid="7820112494467011374">"Eliminar"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Editar marcador"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Añadir acceso directo al escritorio"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Añadir acceso directo al escritorio"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Abrir"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Eliminar marcador"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Eliminar de marcadores"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Esta URL no se puede añadir a marcadores."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Eliminar"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Marcar como última página vista"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Vista de miniaturas"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Vista de lista"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniaturas"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Lista"</string>
<string name="current_page" msgid="7510129573681663135">"de "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Se eliminará el marcador \"<xliff:g id="BOOKMARK">%s</xliff:g>\"."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Abrir en ventana nueva"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Abrir todo en ventanas nuevas"</string>
<string name="goto_dot" msgid="3895839050522602723">"Ir"</string>
- <string name="find_dot" msgid="6259312434696611957">"Buscar en la página"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Abrir nueva pestaña de incógnito"</string>
<string name="select_dot" msgid="6299170761900561967">"Seleccionar texto"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Ventanas actuales"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Cerrar"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Descargas"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Copiar URL de página"</string>
<string name="share_page" msgid="593756995297268343">"Compartir página"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Guardar como archivo web"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Archivo web guardado"</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Error al guardar archivo web"</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> marcadores"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Carpeta vacía"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Abrir"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Abrir en ventana nueva"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Marcar enlace"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Abrir en una nueva ventana en segundo plano"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Guardar enlace"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Compartir enlace"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Copiar"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Escritorio"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Establecer motor de búsqueda"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Seleccionar un motor de búsqueda"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Utilizar página actual"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Establecer como…"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Página actual"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Página en blanco"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Página predeterminada"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Ajustar páginas automát."</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Configurar las páginas web para ajustarlas a la pantalla"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Vista solo horizontal"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Mostrar solo las páginas con la orientación de pantalla horizontal"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Ajustes de privacidad"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"General"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sincronización"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Autocompletar"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sincronizar con Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Compartir marcadores y otros datos entre el navegador de Android y Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Cuenta de Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sincronizar marcadores"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sincronizar marcadores entre el navegador de Android y Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Iniciar sincronización"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Elegir cuenta para compartir"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Autocompletar formulario"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Rellenar formularios web con un solo clic"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Ajustes de autocompletado"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Configurar y administrar los datos de los formularios rellenados automáticamente"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Acceso automático a Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"No se han encontrado cuentas."</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Accede a los sitios de Google de forma automática mediante la cuenta <xliff:g id="ID_1">%s</xliff:g>."</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Accediendo a Google Sites mediante el <xliff:g id="ID_1">%s</xliff:g>"\n"acceso automático de Google de control de los ajustes de seguridad y de privacidad"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"No acceder automáticamente"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"La función Autocompletar utilizará tu perfil para ayudarte a rellenar formularios web con un solo clic."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Nombre completo:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Email:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Nombre de la empresa:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Línea 1 de la dirección:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Dirección postal, apartado postal, c/o"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Línea 2 de la dirección:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Apartamento, piso, bloque, edificio, planta, etc."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Ciudad/población:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Estado/provincia/región:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Código postal:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"País:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Teléfono:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Número de teléfono no válido"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Guardar perfil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Perfil guardado"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Perfil eliminado"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Eliminar perfil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"El navegador puede completar de forma automática formularios web como este. ¿Te gustaría configurar tu perfil?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"La función Autocompletar se puede configurar en cualquier momento a través de los ajustes del navegador."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Inhabilitar Autocompletar"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Privacidad y seguridad"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Borrar caché"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Borrar bases de datos y contenido de la memoria caché local"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Las bases de datos y el contenido se eliminarán de la memoria caché local."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookies"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Borrar datos de cookies"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Borrar todas las cookies del navegador"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Se eliminarán todas las cookies."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Borrar historial"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Borrar el historial de exploración del navegador"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Se eliminará el historial de exploración del navegador."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Datos de formulario"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Borrar datos formulario"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Borrar todos los datos de formulario guardados"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Se eliminarán todos los datos de formulario guardados."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Borrar contraseñas"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Borrar todas las contraseñas guardadas"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Se eliminarán todas las contraseñas guardadas."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Ubicación"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Habilitar ubicación"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Permitir que los sitios soliciten acceso a tu ubicación"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Permitir acceso a la ubicación"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Permitir que todos los sitios web accedan a la ubicación"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Permitir que todos los sitios web accedan a la ubicación"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Ajustes de seguridad"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Contraseñas"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Recordar contraseñas"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Guardar nombres de usuario y contraseñas de sitios web"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Recordar formularios"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Zoom predeterminado"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Abrir en visión general"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Mostrar información general de las páginas abiertas recientemente"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Ajustes avanzados"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Avanzados"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Ajustes del sitio web"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Ajustes avanzados de sitios web individuales"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Restablecer valores predeterminados"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Restablecer valores predeterminados"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Restaurar ajustes predeterminados"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Se restablecerán los ajustes predeterminados."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japonés (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japonés (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japonés (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Coreano (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codificación de texto"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Controles rápidos"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Desliza el pulgar de izquierda a derecha para acceder a los controles rápidos."</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Página principal más visitada"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Configura tu página principal para que muestre las páginas más visitadas."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problema de conectividad de datos"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problema con archivo"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"OK"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Eliminar todos los datos"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Cancelar"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Estableciendo fondo de pantalla..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Marcadores"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"No hay ningún marcador."</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Seleccionar cuenta"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sincronizar con cuenta de Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Tus marcadores de Android no se han asociado a una cuenta de Google."</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Eliminar los marcadores de Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Añadir tus marcadores de Android a marcadores de <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Compartir"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"No hay más pestañas disponibles."</string>
</resources>
diff --git a/res/values-fa-xlarge/strings.xml b/res/values-fa-xlarge/strings.xml
new file mode 100644
index 0000000..cd670ff
--- /dev/null
+++ b/res/values-fa-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"برگه جدید"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"زبانه ناشناخته جدید"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"برگه ها"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"باز کردن در برگه جدید"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"باز کردن در برگه جدید در پس زمینه"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"باز کردن همه در برگه های جدید"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"باز کردن برگه های جدید پشت برگه فعلی"</string>
+</resources>
diff --git a/res/values-fa/strings.xml b/res/values-fa/strings.xml
index 2cb5e5c..71f9aae 100644
--- a/res/values-fa/strings.xml
+++ b/res/values-fa/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"مرورگر"</string>
<string name="choose_upload" msgid="3649366287575002063">"انتخاب فایل برای آپلود"</string>
<string name="new_tab" msgid="4505722538297295141">"پنجره جدید"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"پنجره ناشناخته جدید"</string>
<string name="active_tabs" msgid="3050623868203544623">"پنجره ها"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"نشانک ها"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"بیشتر بازدید شده"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"مرورگر"</string>
<string name="cancel" msgid="3017274947407233702">"لغو"</string>
<string name="ok" msgid="1509280796718850364">"تأیید"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"مورد منطبقی موجود نیست"</item>
- <item quantity="one" msgid="4352019729062956802">"1 مورد منطبق"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> مورد منطبق"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> مورد منطبق"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"در حال بارگیری..."</string>
<string name="page_info" msgid="4048529256302257195">"اطلاعات صفحه"</string>
<string name="page_info_view" msgid="5303490449842635158">"مشاهده اطلاعات صفحه"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"ادامه"</string>
<string name="security_warning" msgid="6607795404322797541">"اخطار امنیتی"</string>
<string name="view_certificate" msgid="1472768887529093862">"مشاهده گواهی"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"برگشت به عقب"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"این گواهی از یک منبع مورد اطمینان صادر نشده است."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"نام سایت با نام موجود در گواهی مطابقت ندارد."</string>
<string name="ssl_expired" msgid="5739349389499575559">"این گواهی منقضی شده است."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"هدایت"</string>
<string name="save" msgid="5922311934992468496">"تأیید"</string>
<string name="do_not_save" msgid="6777633870113477714">"لغو"</string>
- <string name="location" msgid="969988560160364559">"موقعیت مکانی"</string>
- <string name="name" msgid="5990326151488445481">"نام"</string>
+ <string name="location" msgid="3411848697912600125">"آدرس"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"افزودن به"</string>
+ <string name="new_folder" msgid="7743540149088867917">"پوشه جدید"</string>
+ <string name="edit_folder" msgid="621817453133656156">"ویرایشگر پوشه"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"حذف پوشه"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"پوشه فرعی وجود ندارد"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"نشانک ها"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"صفحه اصلی"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"پوشه دیگر..."</string>
+ <string name="name" msgid="5462672162695365387">"برچسب"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"افزودن نشانک"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"افزودن به نشانک ها"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"این صفحه نشانک گذاری شود"</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"ویرایش نشانک"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"افزودن میانبر به صفحه اصلی"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"افزودن میانبر به صفحه اصلی"</string>
<string name="open_bookmark" msgid="8473581305759935790">"باز کردن"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"حذف نشانک"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"حذف از نشانک ها"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"این URL قابل نشانک گذاری نمی باشد."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"حذف"</string>
<string name="bookmark_page" msgid="6845189305130307274">"نشانک گذاری آخرین صفحه مشاهده شده"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"مشاهده تصاویر کوچک"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"نمای لیست"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"تصاویر کوچک"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"لیست"</string>
<string name="current_page" msgid="7510129573681663135">"از "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"نشانک \"<xliff:g id="BOOKMARK">%s</xliff:g>\" حذف می شود."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"باز کردن در پنجره جدید"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"باز کردن همه در پنجره های جدید"</string>
<string name="goto_dot" msgid="3895839050522602723">"برو"</string>
- <string name="find_dot" msgid="6259312434696611957">"یافتن در صفحه"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"باز کردن زبانه ناشناخته جدید"</string>
<string name="select_dot" msgid="6299170761900561967">"انتخاب متن"</string>
<string name="tab_picker_title" msgid="864478399057782913">"پنجره های فعلی"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"بستن"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"دانلودها"</string>
<string name="copy_page_url" msgid="7635062169011319208">"کپی url صفحه"</string>
<string name="share_page" msgid="593756995297268343">"اشتراک گذاری صفحه"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"ذخیره به عنوان بایگانی وب"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"بایگانی وب ذخیره شد."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"ذخیره بایگانی وب ناموفق بود."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> نشانک"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"پوشه خالی"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"باز کردن"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"باز کردن در پنجره جدید"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"نشانک گذاری پیوند"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"باز کردن در پنجره جدید در پس زمینه"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"ذخیره پیوند"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"اشتراک گذاری پیوند"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"کپی"</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"تنظیم صفحه اصلی"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"تنظیم موتور جستجو"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"انتخاب یک موتور جستجو"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"استفاده از صفحه فعلی"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"تنظیم به..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"صفحه فعلی"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"صفحه خالی"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"صفحه پیش فرض"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"تنظیم خودکار صفحات"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"قالب صفحات وب متناسب با صفحه"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"نمایش فقط افقی"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"نمایش صفحات فقط در صفحه افقی پهن تر"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"تنظیمات رازداری"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"عمومی"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"همگامسازی"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"تکمیل خودکار"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"همگام سازی با Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"اشتراک گذاری نشانک ها و سایر داده ها بین مرورگر Android و Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"حساب Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"همگام سازی نشانک ها"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"همگام سازی نشانک ها بین مرورگر Android و Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"شروع همگام سازی"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"انتخاب حساب Google جهت اشتراک گذاری"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"تکمیل خودکار فرم"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"تکمیل کردن فرم ها با یک کلیک"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"تنظیمات تکمیل خودکار"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"تنظیم و مدیریت داده برای فرم های تکمیل شده به طور خودکار"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"ورود به سیستم خودکار Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"حسابی یافت نشد"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"با استفاده از <xliff:g id="ID_1">%s</xliff:g> به صورت خودکار به سایت های Google وارد شوید"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"ورود به سایت های Google با استفاده از <xliff:g id="ID_1">%s</xliff:g>"\n"تنظیمات حریم خصوصی و امنیت خود، ورود به سیستم خودکار Google را کنترل می کند"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"به صورت خودکار به سیستم وارد نشوید"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"تکمیل خودکار از نمایه شما استفاده می کند تا به شما کمک کند فرم های وب را با یک کلیک پر کنید."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"نام کامل:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"ایمیل:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"نام شرکت:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"خط آدرس 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"آدرس خیابان، صندوق پستی، c/o"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"خط آدرس 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"آپارتمان، سوئیت، واحد، ساختمان، طبقه، غیره"</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"شهر / شهرک:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"ایالت / استان / منطقه:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"کد پستی:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"کشور:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"تلفن:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"شماره تلفن نامعتبر"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"ذخیره نمایه"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"نمایه ذخیره شد"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"نمایه حذف شد"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"حذف نمایه"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"مرورگر می تواند بصورت خودکار فرم های وب مانند این یکی را پر کند. دوست دارید نمایه خود را تنظیم کنید؟"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"تکمیل خودکار را همیشه می توانید از طریق تنظیمات مرورگر پیکربندی کنید."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"غیرفعال کردن تکمیل خودکار"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"حریم خصوصی و ایمنی"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"پاک کردن حافظه پنهان"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"پاک کردن پایگاه های داده و محتوای موجود در حافظه پنهان محلی"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"پایگاه داده ها و محتوای موجود در حافظه پنهان محلی حذف می شوند."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"کوکی ها"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"پاک کردن همه داده های کوکی"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"پاک کردن همه کوکی های مرورگر"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"همه کوکی ها حذف خواهند شد."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"پاک کردن سابقه"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"پاک کردن سابقه پیمایش مرورگر"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"سابقه پیمایش مرورگر حذف می شود."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"اطلاعات فرم"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"پاک کردن داده های فرم"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"پاک کردن همه داده های فرم ذخیره شده"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"همه داده های فرم ذخیره شده حذف خواهد شد."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"پاک کردن رمزهای ورود"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"پاک کردن همه رمزهای ورود ذخیره شده"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"همه رمزهای ورود ذخیره شده حذف می شوند."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"موقعیت مکانی"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"فعال کردن موقعیت مکانی"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"اجازه به سایت ها برای درخواست دسترسی به موقعیت مکانی شما"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"پاک کردن دسترسی به موقعیت مکانی"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"پاک کردن دسترسی به موقعیت مکانی برای همه وب سایت ها"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"پاک کردن دسترسی به موقعیت مکانی برای همه وب سایت ها"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"تظیمات امنیتی"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"رمزهای ورود"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"به خاطر سپردن رمزهای ورود"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"ذخیره نام های کاربری و رمزهای ورود برای وب سایت ها"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"به خاطر سپردن داده های فرم"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"بزرگنمایی پیش فرض"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"باز کردن صفحات در نمای کلی"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"نمایش نمای کلی صفحاتی که به تازگی باز شده اند"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"تنظیمات پیشرفته"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"پیشرفته"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"تنظیمات وب سایت"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"تنظیمات پیشرفته برای وب سایت های تکی"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"تنظیم مجدد پیش فرض ها"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"بازنشانی به پیش فرض"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"بازیابی تنظیمات پیش فرض"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"تنظیمات به مقادیر پیش فرض باز می گردند."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"ژاپنی (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"ژاپنی (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"ژاپنی (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"کره ای (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"رمزگذاری متن"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"کنترل های سریع"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"برای دسترسی به کنترل های سریع، انگشت شست خود را در لبه های چپ یا راست جابجا کنید"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"صفحه اصلی بیشتر بازدید شده"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"صفحه اصلی شما را برای نمایش صفحات بیشتر بازدید شده تنظیم می کند."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"مشکل اتصال داده"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"مشکل در فایل"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"تأیید"</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"حذف همه داده ها"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"لغو"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"تنظیم تصویر زمینه..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"نشانک ها"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"نشانکی وجود ندارد"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"انتخاب حساب"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"همگام سازی با حساب Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"نشانک های Android شما با حساب Google مرتبط نیستند"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"حذف نشانک های Android خود"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"افزودن نشانک های Android خود به نشانک های <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"اشتراک گذاری"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"برگه بیشتری در دسترس نیست"</string>
</resources>
diff --git a/res/values-fi-xlarge/strings.xml b/res/values-fi-xlarge/strings.xml
new file mode 100644
index 0000000..a1246d4
--- /dev/null
+++ b/res/values-fi-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Uusi välilehti"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Uusi incognito-välilehti"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Välilehdet"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Avaa uudessa välilehdessä"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Avaa uudessa välilehdessä taustalla"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Avaa kaikki uusiin välilehtiin"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Avaa uudet välilehdet nykyisen taakse"</string>
+</resources>
diff --git a/res/values-fi/strings.xml b/res/values-fi/strings.xml
index 736a171..6bfe70e 100644
--- a/res/values-fi/strings.xml
+++ b/res/values-fi/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Selain"</string>
<string name="choose_upload" msgid="3649366287575002063">"Valitse lähetettävä tiedosto"</string>
<string name="new_tab" msgid="4505722538297295141">"Uusi ikkuna"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Uusi incognito-ikkuna"</string>
<string name="active_tabs" msgid="3050623868203544623">"Windows"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Kirjanmerkit"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Useimmin avatut"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Selain"</string>
<string name="cancel" msgid="3017274947407233702">"Peruuta"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Ei tuloksia"</item>
- <item quantity="one" msgid="4352019729062956802">"1 tulos"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> osumaa"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> osumaa"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Ladataan…"</string>
<string name="page_info" msgid="4048529256302257195">"Sivun tiedot"</string>
<string name="page_info_view" msgid="5303490449842635158">"Näytä sivun tiedot"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Jatka"</string>
<string name="security_warning" msgid="6607795404322797541">"Suojausvaroitus"</string>
<string name="view_certificate" msgid="1472768887529093862">"Näytä varmenne"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Takaisin"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Varmenteen myöntäjä ei ole luotettava taho."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Sivuston nimi ei vastaa varmenteessa olevaa nimeä."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Varmenne ei ole enää voimassa."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Seuraava"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Peruuta"</string>
- <string name="location" msgid="969988560160364559">"Sijainti"</string>
- <string name="name" msgid="5990326151488445481">"Nimi"</string>
+ <string name="location" msgid="3411848697912600125">"Osoite"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Lisää kansioon"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Uusi kansio"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Muokkaa kansiota"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Poista kansio"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Ei alakansioita"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Kirjanmerkit"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Etusivu"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Muu kansio..."</string>
+ <string name="name" msgid="5462672162695365387">"Tunniste"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Lisää kirjanmerkki"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Lisää kirjanmerkkeihin"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Lisää sivu kirjanmerkkeihin"</string>
+ <string name="remove" msgid="7820112494467011374">"Poista"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Muokkaa kirjanmerkkiä"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Lisää pikakuvake etusivulle"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Lisää pikakuvake etusivulle"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Avaa"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Poista kirjanmerkki"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Poista kirjanmerkeistä"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Tätä URL-osoitetta ei voi lisätä kirjanmerkkeihin."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Poista"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Lisää viimeksi avattu sivu kirjanmerkkeihin"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Pikkukuvanäkymä"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Luettelonäkymä"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Pikkukuvat"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Luettelo"</string>
<string name="current_page" msgid="7510129573681663135">"kohteesta "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Kirjanmerkki \"<xliff:g id="BOOKMARK">%s</xliff:g>\" poistetaan."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Avaa uudessa ikkunassa"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Avaa kaikki uusissa ikkunoissa"</string>
<string name="goto_dot" msgid="3895839050522602723">"Siirry"</string>
- <string name="find_dot" msgid="6259312434696611957">"Etsi sivulta"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Avaa uusi incognito-välilehti"</string>
<string name="select_dot" msgid="6299170761900561967">"Tekstin valinta"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Nykyiset ikkunat"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Sulje"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Lataukset"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Kopioi sivun URL-osoite"</string>
<string name="share_page" msgid="593756995297268343">"Jaa sivu"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Tallenna verkkoarkistona"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Verkkoarkisto tallennettu."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Verkkoarkiston tallentaminen epäonnistui."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> kirjanmerkkiä"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Tyhjä kansio"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Avaa"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Avaa uudessa ikkunassa"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Lisää linkki kirjanmerkkeihin"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Avaa uudessa ikkunassa taustalla"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Tallenna linkki"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Jaa linkki"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopioi"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Aseta aloitussivu"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Aseta hakukone"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Valitse hakukone"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Käytä nykyistä sivua"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Aseta etusivuksi..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Nykyinen sivu"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Tyhjä sivu"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Oletussivu"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Automaattinen sovitus"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Sovita verkkosivut näytölle"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Vain vaakasuuntainen näyttö"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Näytä sivut vain leveässä, vaakasuuntaisessa näkymässä"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Tietosuoja-asetukset"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Yleinen"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Synkronointi"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Automaattinen täyttö"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synkronoi Google Chromen kanssa"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Jaa kirjanmerkkejä ja muita tietoja Android-selaimen ja Google Chromen välillä"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google-tili"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synkronoi kirjanmerkit"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synkronoi kirjanmerkit Android-selaimen ja Google Chromen välillä"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Aloita synkronointi"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Valitse, minkä Google-tilin kanssa jaetaan"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Lomakkeen automaattinen täyttö"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Täytä verkkolomakkeita yhdellä napsautuksella"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Automaattisen täytön asetukset"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Aseta automaattisesti täytettyjen lomakkeiden tiedot ja hallinnoi tietoja"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Automaattinen Google-sisäänkirjaus"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Ei tilejä"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Kirjaudu sisään Googlen sivustoihin automaattisesti käyttäen tiliä <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Kirjaudutaan sisään Googlen sivustoihin käyttäen tiliä <xliff:g id="ID_1">%s</xliff:g>"\n"Automaattista Google-sisäänkirjautumista säätelevät tietosuoja- ja turvallisuusasetuksesi"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Älä kirjaudu sisään automaattisesti"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Automaattinen täyttö käyttää profiiliasi, jotta voit täyttää verkkolomakkeita yhdellä napsautuksella."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Koko nimi:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Sähköposti:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Yrityksen nimi:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Osoiterivi 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Katuosoite, postilokero"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Osoiterivi 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Asunto, rakennus, kerros jne."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Kaupunki:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Maakunta/lääni:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Postinumero:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Maa:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Puhelin:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Virheellinen puhelinnumero"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Tallenna profiili"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profiili tallennettu"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profiili poistettu."</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Poista profiili"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Selain voi täydentää automaattisesti tämän kaltaisia verkkolomakkeita. Haluatko luoda profiilin?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Automaattisen täytön asetuksia voi aina muuttaa selainasetuksista."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Poista automaattinen täyttö käytöstä"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Tietosuoja ja turvallisuus"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Tyhjennä välimuisti"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Poista paikallisen välimuistin sisältö ja tietokannat"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Paikallisen välimuistin sisältö ja tietokannat poistetaan."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Evästeet"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Poista kaikki evästetiedot"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Poista selaimen kaikki evästeet"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Kaikki evästeet poistetaan."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Tyhjennä historia"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Tyhjennä selaimen selaushistoria"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Selaimen selaushistoria poistetaan."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Lomakkeen tiedot"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Poista lomaketiedot"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Poista kaikki tallennetut lomaketiedot"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Kaikki tallennetut lomaketiedot poistetaan."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Poista salasanat"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Poista kaikki tallennetut salasanat"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Kaikki tallennetut salasanat poistetaan."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Sijainti"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Ota sijaintitiedot käyttöön"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Salli sivustojen pyytää sijaintitietojesi käyttöoikeutta"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Poista sijaintitietojen käyttöoikeus"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Poista sijaintitietojen käyttöoikeus kaikilta sivustoilta"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Poista sijaintitietojen käyttöoikeus kaikilta sivustoilta"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Suojausasetukset"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Salasanat"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Tallenna salasanat"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Tallenna sivustojen käyttäjänimet ja salasanat"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Tallenna lomaketiedot"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Oletuszoomaus"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Avaa sivut yleiskatsauksessa"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Näytä äskettäin avattujen sivujen yleiskatsaus"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Lisäasetukset"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Lisäasetukset"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Sivustoasetukset"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Yksittäisten sivustojen lisäasetukset"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Palauta oletukset"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Palauta oletukseksi"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Palauta oletusasetukset"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Asetukset palautetaan oletusarvoihinsa."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"japani (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"japani (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"japani (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"korea (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Tekstin koodaus"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Pikasäätimet"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Saat pikasäätimet käyttöösi liu\'uttamalla vasemmalta tai oikealta reunalta"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Useimmin napsautetut etusivulla"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Asettaa etusivusi näyttämään vierailluimmat sivut."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Datayhteysongelma"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Tiedosto-ongelma"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Vahvista"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Poista kaikki tiedot"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Peruuta"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Asetetaan taustakuvaa…"</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Kirjanmerkit"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Ei kirjanmerkkejä"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Valitse tili"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synkronoi Google-tilin kanssa"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Android-kirjanmerkkejä ei ole yhdistetty Google-tiliin"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Poista Android-kirjanmerkkisi"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Lisää Android-kirjanmerkit tilin <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g> kirjanmerkkeihin"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Jaa"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Välilehtiä ei ole enempää saatavilla"</string>
</resources>
diff --git a/res/values-fr-xlarge/strings.xml b/res/values-fr-xlarge/strings.xml
new file mode 100644
index 0000000..2975ed5
--- /dev/null
+++ b/res/values-fr-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Nouvel onglet"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Nouvel onglet Navigation privée"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Onglets"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Ouvrir dans un nouvel onglet"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Ouvrir dans un nouvel onglet d\'arrière-plan"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Toujours ouvrir dans un nouvel onglet"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Ouvrir nouveaux onglets derrière onglet actuel"</string>
+</resources>
diff --git a/res/values-fr/strings.xml b/res/values-fr/strings.xml
index 6c3f3de..dbdb331 100644
--- a/res/values-fr/strings.xml
+++ b/res/values-fr/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Navigateur"</string>
<string name="choose_upload" msgid="3649366287575002063">"Choisir le fichier à importer"</string>
<string name="new_tab" msgid="4505722538297295141">"Nouvelle fenêtre"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Fenêtre de navigation privée"</string>
<string name="active_tabs" msgid="3050623868203544623">"Fenêtres"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Favoris"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Les + visités"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Navigateur"</string>
<string name="cancel" msgid="3017274947407233702">"Annuler"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Aucune correspondance"</item>
- <item quantity="one" msgid="4352019729062956802">"1 correspondance"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> correspondances"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> correspondances"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Chargement…"</string>
<string name="page_info" msgid="4048529256302257195">"Infos sur la page"</string>
<string name="page_info_view" msgid="5303490449842635158">"Afficher les infos sur la page"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Continuer"</string>
<string name="security_warning" msgid="6607795404322797541">"Avertissement de sécurité"</string>
<string name="view_certificate" msgid="1472768887529093862">"Afficher le certificat"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Retour"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Ce certificat provient d\'une autorité non approuvée."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Le nom du site ne correspond pas au nom indiqué dans le certificat."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Le certificat a expiré."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Suivant"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Annuler"</string>
- <string name="location" msgid="969988560160364559">"Emplacement"</string>
- <string name="name" msgid="5990326151488445481">"Nom"</string>
+ <string name="location" msgid="3411848697912600125">"Adresse"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Ajouter à"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Nouveau dossier"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Modifier le dossier"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Supprimer le dossier"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Aucun sous-dossier"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Favoris"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Écran d\'accueil"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Autre dossier…"</string>
+ <string name="name" msgid="5462672162695365387">"Libellé"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Ajouter un favori"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Ajouter aux favoris"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Ajouter cette page aux favoris"</string>
+ <string name="remove" msgid="7820112494467011374">"Supprimer"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Modifier le favori"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Raccourci (page d\'accueil)"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Créer un raccourci sur la page d\'accueil"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Ouverture"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Supprimer le favori"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Supprimer des favoris"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Impossible d\'ajouter cette URL à vos favoris."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Supprimer"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Ajouter la dernière page consultée"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Miniatures"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Liste"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Vignettes"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Liste"</string>
<string name="current_page" msgid="7510129573681663135">"de "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Le favori \"<xliff:g id="BOOKMARK">%s</xliff:g>\" sera supprimé."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Nouvelle fenêtre"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Toujours ouvrir dans une nouvelle fenêtre"</string>
<string name="goto_dot" msgid="3895839050522602723">"OK"</string>
- <string name="find_dot" msgid="6259312434696611957">"Rechercher sur la page"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Ouvrir un onglet de navigation privée"</string>
<string name="select_dot" msgid="6299170761900561967">"Sélectionner le texte"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Fenêtres actuelles"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Fermer"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Téléchargements"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Copier l\'URL de la page"</string>
<string name="share_page" msgid="593756995297268343">"Partager la page"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Enregistrer comme archive Web"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Archive Web enregistrée"</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Échec de l\'enregistrement de l\'archive Web"</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> favori(s)"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Dossier vide"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Ouvrir"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Nouvelle fenêtre"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Lien du favori"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Ouvrir dans une nouvelle fenêtre d\'arrière-plan"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Enregistrer le lien"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Partager le lien"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Copier"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Page d\'accueil"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Définir le moteur de recherche"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Sélectionnez un moteur de recherche."</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Utiliser la page actuelle"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Définir comme..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Page en cours"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Page vierge"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Page par défaut"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Redimensionner"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Configurer les pages Web pour qu\'elles s\'ajustent à l\'écran"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Mode Paysage"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Toujours afficher les pages dans le sens de la largeur (orientation paysage)"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Paramètres de confidentialité"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Général"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Synchronisation"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Saisie automatique"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synchroniser avec Google Voice"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Partager les favoris et d\'autres données entre le navigateur Android et Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Compte Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synchroniser les favoris"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synchroniser les favoris entre le navigateur Android et Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Démarrer la synchro"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Sélection du compte Google"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Remplissage auto des formulaires"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Remplissez les formulaires Web en un clic."</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Paramètres de saisie automatique"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Configurez et gérez les données de remplissage automatique des formulaires."</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Connexion automatique à Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Aucun compte trouvé"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Se connecter automatiquement à Google Sites à l\'aide de <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Connexion à Google Sites avec <xliff:g id="ID_1">%s</xliff:g>"\n"Vos paramètres de confidentialité et de sécurité contrôlent la connexion automatique à Google."</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Ne pas se connecter automatiquement"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"La fonctionnalité de saisie automatique utilise les données de votre profil pour vous aider à remplir les formulaires Web en un seul clic."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Nom et prénom :"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Adresse e-mail :"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Nom de la société :"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Ligne d\'adresse 1 :"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Adresse postale, boîte postale, \"À l\'attention de\""</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Ligne d\'adresse 2 :"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Résidence, bloc, bâtiment, appartement, étage, etc."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Ville :"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"État/Province/Région :"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Code postal :"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Pays :"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Téléphone :"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Numéro de téléphone incorrect"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Enregistrer le profil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profil enregistré"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profil supprimé"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Supprimer le profil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Le navigateur peut remplir automatiquement des formulaires Web tels que celui-ci. Voulez-vous configurer votre profil ?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"La saisie automatique peut être configurée dans les paramètres du navigateur."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Désactiver la saisie automatique"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Confidentialité et sécurité"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Effacer le cache"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Supprimer les bases de données et le contenu localement en cache"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Les bases de données et le contenu mis localement en cache vont être supprimés."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookies"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Effacer tous les cookies"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Effacer tous les cookies du navigateur"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Tous les cookies vont être supprimés."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Effacer l\'historique"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Effacer l\'historique du navigateur"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"L\'historique du navigateur sera supprimé."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Données de formulaire"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Eff. données formulaires"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Effacer toutes les données de formulaire enregistrées"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Toutes les données de formulaire enregistrées seront supprimées."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Eff. les mots de passe"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Effacer tous les mots de passe enregistrés"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Tous les mots de passe enregistrés seront effacés."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Lieu"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Activer la localisation"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Autoriser les sites à demander l\'accès à vos données de localisation"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Supprimer l\'accès"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Supprimer l\'accès aux données de localisation pour tous les sites Web"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Supprimer l\'accès aux données de localisation pour tous les sites Web"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Paramètres de sécurité"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Mots de passe"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Mém. mots de passe"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Enregistrer les noms d\'utilisateur et les mots de passe pour les sites Web"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Données de formulaires"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Zoom par défaut"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Aperçu des pages"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Afficher un aperçu des pages ouvertes récemment"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Paramètres avancés"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Options avancées"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Paramètres du site Web"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Paramètres avancés de sites Web individuels"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Réinitialiser les valeurs par défaut"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Valeurs par défaut"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Rétablir les paramètres par défaut"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Les paramètres par défaut seront rétablis."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japonais (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japonais (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japonais (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Coréen (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codage du texte"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Commandes rapides"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Glisser votre pouce vers la droite ou la gauche pour accéder aux commandes rapides"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Page d\'accueil Les plus visitées"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Votre page d\'accueil affiche les pages les plus visitées."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problème de connectivité des données"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problème de fichier"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Confirmer"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Supprimer toutes les données"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Annuler"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Définition du fond d\'écran..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Favoris"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Aucun favori"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Choisir un compte"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synchronisation avec un compte Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Vos favoris Android ne sont associés à aucun compte Google."</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Supprimer vos favoris Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Ajouter vos favoris Android à ceux de <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Partagez"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Plus aucun onglet n\'est disponible."</string>
</resources>
diff --git a/res/values-hr-xlarge/strings.xml b/res/values-hr-xlarge/strings.xml
new file mode 100644
index 0000000..e61c130
--- /dev/null
+++ b/res/values-hr-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Nova kartica"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Nova kartica anonimno"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Kartice"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Otvori u novoj kartici"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Otvori u novoj pozadinskoj kartici"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Otvori sve na novim karticama"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Otvori nove kartice iza trenutne"</string>
+</resources>
diff --git a/res/values-hr/strings.xml b/res/values-hr/strings.xml
index 1f594d8..21d76bb 100644
--- a/res/values-hr/strings.xml
+++ b/res/values-hr/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Preglednik"</string>
<string name="choose_upload" msgid="3649366287575002063">"Odaberite datoteku za prijenos"</string>
<string name="new_tab" msgid="4505722538297295141">"Novi prozor"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Novi prozor anonimno"</string>
<string name="active_tabs" msgid="3050623868203544623">"Windows"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Oznake"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Najposjećenije"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Preglednik"</string>
<string name="cancel" msgid="3017274947407233702">"Odustani"</string>
<string name="ok" msgid="1509280796718850364">"U redu"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Nema rezultata"</item>
- <item quantity="one" msgid="4352019729062956802">"1 podudaranje"</item>
- <item quantity="few" msgid="5544267486978946555">"Podudaranja: <xliff:g id="NUMBER">%d</xliff:g>"</item>
- <item quantity="other" msgid="6616125067364315405">"Podudaranja: <xliff:g id="NUMBER">%d</xliff:g>"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Učitavanje…"</string>
<string name="page_info" msgid="4048529256302257195">"Informacije o stranici"</string>
<string name="page_info_view" msgid="5303490449842635158">"Prikaz informacija o stranici"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Nastavi"</string>
<string name="security_warning" msgid="6607795404322797541">"Upozorenje o sigurnosti"</string>
<string name="view_certificate" msgid="1472768887529093862">"Prikaži certifikat"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Vrati se"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Ovaj certifikat ne potječe iz pouzdanog izvora."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Naziv web-lokacije ne podudara se s nazivom na certifikatu."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Ovaj je certifikat istekao."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"Proslijedi"</string>
<string name="save" msgid="5922311934992468496">"U redu"</string>
<string name="do_not_save" msgid="6777633870113477714">"Odustani"</string>
- <string name="location" msgid="969988560160364559">"Lokacija"</string>
- <string name="name" msgid="5990326151488445481">"Ime"</string>
+ <string name="location" msgid="3411848697912600125">"Adresa"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Dodaj u grupu"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Nova mapa"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Uredi mapu"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Izbriši mapu"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Nema podmapa"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Oznake"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Početni zaslon"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Druga mapa…"</string>
+ <string name="name" msgid="5462672162695365387">"Oznaka"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Dodaj oznaku"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Dodavanje oznakama"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Označi ovu stranicu"</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"Uredi knjižnu oznaku"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Dodaj prečac Početnoj stranici"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Dodaj prečac početnoj stranici"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Otvori"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Izbriši oznaku"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Ukloni iz oznaka"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Ovaj se URL ne može zabilježiti kao knjižna oznaka."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Izbriši"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Označi posljednju prikazanu stranicu"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Prikaz sličice"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Prikaz popisa"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Minijature"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Popis"</string>
<string name="current_page" msgid="7510129573681663135">"s lokacije "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Oznaka \"<xliff:g id="BOOKMARK">%s</xliff:g>\" izbrisat će se."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Otvori u novom prozoru"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Otvori sve u novim prozorima"</string>
<string name="goto_dot" msgid="3895839050522602723">"Idi"</string>
- <string name="find_dot" msgid="6259312434696611957">"Pronađi na stranici"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Otvori novu karticu anonimno"</string>
<string name="select_dot" msgid="6299170761900561967">"Odabir teksta"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Trenutni prozori"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Zatvori"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Preuzimanja"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Kopiraj url stranice"</string>
<string name="share_page" msgid="593756995297268343">"Dijeli stranicu"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Spremi web-arhivu"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Web-arhiva spremljena."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Spremanje web-arhive nije uspjelo."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"Br. oznaka: <xliff:g id="BOOKMARK_COUNT">%d</xliff:g>"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Prazna mapa"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Otvori"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Otvori u novom prozoru"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Veza za oznaku"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Otvori u novom pozadinskom prozoru"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Spremi vezu"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Dijeli vezu"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopiraj"</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Postavi početnu stranicu"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Postavljanje tražilice"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Odabir tražilice"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Upotrijebi trenutnu stranicu"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Postavi na…"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Trenutačna stranica"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Prazna stranica"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Zadana stranica"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Automatsko prilagođavanje stranicama"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Formatirajte web-stranice kako bi odgovarale zaslonu"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Samo pejzažni prikaz"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Slike prikaži samo u široj, pejzažnoj orijentaciji zaslona"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Postavke privatnosti"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Općenito"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sinkronizacija"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Automatska ispuna"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sinkronizacija s uslugom Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Dijeljenje oznaka & ostalih podataka među uslugama Android preglednik i Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google Račun"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Spremanje oznaka"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sinkroniziranje oznaka među uslugama Android preglednik i Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Počni sinkronizaciju"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Odaberite Google Račun s kojim ćete dijeliti"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Oblikuj automatsko popunjavanje"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Ispunite web-obrasce jednim klikom"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Postavke automat. popunjavanja"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Postavljanje & upravljanja podacima za oblike automatskog popunjavanja"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Automatska prijava na Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Nema pronađenih računa"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Prijavite se na Googleove web-lokacije automatski koristeći <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Prijavljivanjem u Google Web-lokacije pomoću postavki <xliff:g id="ID_1">%s</xliff:g>"\n"Vaša privatnost i sigurnost nadzire se automatska prijava na Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Nemojte se automatski prijavljivati"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Automatsko ispunjavanje upotrebljavat će vaš profil kako biste lakše ispunili web-obrasce jednim klikom."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Puno ime:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-pošta:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Naziv tvrtke:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"1. red adrese:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Ulica, poštanski pretinac, na ruke"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"2. red adrese:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Stan, apartman, jedinica, zgrada, kat itd."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Grad/mjesto:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Država/pokrajina/regija:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Poštanski broj:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Zemlja:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Broj telefona nije valjan"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Spremi profil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profil spremljen"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profil izbrisan"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Izbriši profil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Preglednik može automatski popunjavati web-obrasce poput ovog. Želite li postaviti svoj profil?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Automatsko popunjavanje može se konfigurirati u bilo kojem trenutku putem Postavki preglednika."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Onemogući automatsko popunjavanje"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Privatnost i sigurnost"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Očisti predmemoriju"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Izbriši sadržaj i baze podataka spremljene u lokalnu predmemoriju"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Izbrisat će se sadržaj i baze podataka koji su spremljeni u lokalnu predmemoriju."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Kolačići"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Izbriši sve podatke o kolačićima"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Izbriši sve kolačiće iz preglednika"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Svi će se kolačići izbrisati."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Izbriši povijest"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Izbriši povijest navigacije u pregledniku"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Izbrisat će se povijest navigacije u pregledniku."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Podaci obrasca"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Izbriši podatke iz obrasca"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Izbriši sve spremljene podatke o obrascima"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Svi će se spremljeni podaci iz obrasca izbrisati."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Izbriši zaporke"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Izbriši sve spremljene zaporke"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Sve će se spremljene zaporke izbrisati."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Lokacija"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Omogući lokaciju"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Dopustite web-lokacijama da zatraže pristup vašoj lokaciji"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Izbriši pristup lokaciji"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Izbriši pristup lokaciji za sve web-lokacije"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Izbriši pristup lokaciji za sve web-lokacije"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Sigurnosne postavke"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Zaporke"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Zapamti zaporke"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Spremi korisnička imena i zaporke za web-lokacije"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Zapamti podatke o obrascu"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Zadano povećanje/smanjenje"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Otvori stranice u pregledu"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Pokaži pregled novootvorenih stranica"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Napredne postavke"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Napredno"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Postavke web-lokacije"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Napredne postavke za pojedinačne web-lokacije"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Vrati na zadano"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Ponovo postavi na zadano"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Vrati na zadane postavke"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Postavke će se vratiti na zadane vrijednosti."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"Japanski (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japanski (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japanski (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"korejski (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Kodiranje teksta"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Brze kontrole"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Pomaknite se slijeva ili zdesna kako biste pristupili brzim kontrolama"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Najposjećenija početna stranica"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Na vašoj početnoj stranici postavlja najposjećenije stranice."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problem s podatkovnom povezivošću"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problem s datotekom"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Potvrdi"</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Izbriši sve podatke"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Odustani"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Postavljanje pozadinske slike..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Oznake"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Nema oznaka"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Odaberite račun"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sinkronizacija s Google Računom"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Vaše Android oznake nisu povezane s Google Računom"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Izbrišite oznake programa Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Dodajte svoje Android oznake oznakama za <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Dijeli"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Nema više rasp. kartica"</string>
</resources>
diff --git a/res/values-hu-xlarge/strings.xml b/res/values-hu-xlarge/strings.xml
new file mode 100644
index 0000000..76d05c5
--- /dev/null
+++ b/res/values-hu-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Új lap"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Új inkognitólap"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Lapok"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Megnyitás új lapon"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Megnyitás új lapon a háttérben"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Összes megnyitása új lapon"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Új lapok megnyitása a jelenlegi mögött"</string>
+</resources>
diff --git a/res/values-hu/strings.xml b/res/values-hu/strings.xml
index 24d5e72..496bd20 100644
--- a/res/values-hu/strings.xml
+++ b/res/values-hu/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Böngésző"</string>
<string name="choose_upload" msgid="3649366287575002063">"Válassza ki a feltölteni kívánt fájlt"</string>
<string name="new_tab" msgid="4505722538297295141">"Új ablak"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Új inkognitóablak"</string>
<string name="active_tabs" msgid="3050623868203544623">"Ablakok"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Könyvjelzők"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Leggyakrabban felkeresett"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Böngésző"</string>
<string name="cancel" msgid="3017274947407233702">"Mégse"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Nincs találat"</item>
- <item quantity="one" msgid="4352019729062956802">"1 találat"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> találat"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> találat"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Betöltés…"</string>
<string name="page_info" msgid="4048529256302257195">"Oldaladatok"</string>
<string name="page_info_view" msgid="5303490449842635158">"Az oldal adatainak megtekintése"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Folytatás"</string>
<string name="security_warning" msgid="6607795404322797541">"Biztonsági figyelmeztetés"</string>
<string name="view_certificate" msgid="1472768887529093862">"Tanúsítvány megtekintése"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Vissza"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Ez a tanúsítvány nem hiteles tanúsítványkibocsátótól származik."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"A webhely neve nem egyezik a tanúsítványon lévő névvel."</string>
<string name="ssl_expired" msgid="5739349389499575559">"A tanúsítvány lejárt."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Előre"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Mégse"</string>
- <string name="location" msgid="969988560160364559">"URL"</string>
- <string name="name" msgid="5990326151488445481">"Név"</string>
+ <string name="location" msgid="3411848697912600125">"Cím"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Mentés ide:"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Új mappa"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Mappa szerkesztése"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Mappa törlése"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Nincs almappa"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Könyvjelzők"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Kezdőképernyő"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Másik mappa..."</string>
+ <string name="name" msgid="5462672162695365387">"Címke"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Könyvjelző hozzáadása"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Hozzáadás a könyvjelzőkhöz"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Oldal felvétele a könyvjelzők közé"</string>
+ <string name="remove" msgid="7820112494467011374">"Eltávolítás"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Könyvjelző szerkesztése"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Parancsikon a főoldalra"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Parancsikon a főoldalra"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Megnyitás"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Könyvjelző törlése"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Eltávolítás a könyvjelzők közül"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Ezt az URL-t nem lehet a könyvjelzők közé tenni."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Törlés"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Az utoljára megtekintett oldal felvétele a könyvjelzők közé"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Indexkép nézet"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Lista nézet"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Indexképek"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Lista"</string>
<string name="current_page" msgid="7510129573681663135">"innen: "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"A(z) \"<xliff:g id="BOOKMARK">%s</xliff:g>\" könyvjelző törlésre kerül."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Megnyitás új ablakban"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Összes megnyitása új ablakban"</string>
<string name="goto_dot" msgid="3895839050522602723">"Ugrás"</string>
- <string name="find_dot" msgid="6259312434696611957">"Keresés az oldalon"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Új inkognitólap megnyitása"</string>
<string name="select_dot" msgid="6299170761900561967">"Szöveg kijelölése"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Jelenlegi ablakok"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Bezárás"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Letöltések"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Az oldal URL-jének másolása"</string>
<string name="share_page" msgid="593756995297268343">"Oldal megosztása"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Mentés internetes archívumként"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Az internetes archívum elmentve."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Nem sikerült menteni az internetes archívumot."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> könyvjelző"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Üres mappa"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Megnyitás"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Megnyitás új ablakban"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Link felvétele a könyvjelzők közé"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Megnyitás új ablakban a háttérben"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Link mentése"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Link megosztása"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Másolás"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Főoldal beállítása"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Keresőmotor beállítása"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Válasszon ki egy keresőmotort"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"A jelenlegi oldal használata"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Beállítás a következőre:"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Jelenlegi oldal"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Üres oldal"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Alapértelmezett oldal"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Oldalak automatikus igazítása"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"A képernyőhöz igazítja a weboldalakat"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Megjelenítés csak fekvő tájolással"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Csak a szélesebb, fekvő helyzetben jeleníti meg az oldalakat"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Adatvédelmi beállítások"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Általános"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Szinkronizálás"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Automatikus kitöltés"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Szinkronizálás a Google Chrome-mal"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Könyvjelzők és egyéb adatok megosztása az Android böngészője és a Google Chrome között"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google Fiók"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Könyvjelzők szinkronizálása"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Az Android böngésző és a Google Chrome könyvjelzőinek szinkronizálása"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Szinkronizálás most"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Fiók kiválasztása"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Űrlap automatikus kitöltése"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Internetes űrlapok kitöltése egyetlen kattintással"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Automatikus kitöltés beállításai"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Automatikusan kitöltött űrlapadatok megadása és kezelése"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Automatikus Google-bejelentkezés"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Nem található fiók"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Automatikus bejelentkezés a Google-webhelyekre <xliff:g id="ID_1">%s</xliff:g> fiókkal"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Bejelentkezés a Google webhelyeire a következő használatával: <xliff:g id="ID_1">%s</xliff:g>"\n"Az automatikus Google-bejelentkezést adatvédelmi és biztonsági beállításai szabályozzák"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Ne lépjen be automatikusan"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Az Automatikus kitöltés az Ön profilja alapján egyetlen kattintással kitölti a webes űrlapokat."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Teljes név:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-mail:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Vállalat neve:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Cím 1. sora:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Utcanév, postafiókszám, levelezési cím"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Cím 2. sora:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Lakás, lakosztály, lépcsőház, épület, emelet stb."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Város/helység:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Állam / megye / régió:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Irányítószám:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Ország:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Érvénytelen telefonszám"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Profil mentése"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"A profil elmentve"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"A profil törölve."</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Profil törlése"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"A böngésző automatikusan ki tudja tölteni az ilyen internetes űrlapokat. Beállítja a profilját?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Az Automatikus kitöltést bármikor konfigurálhatja a Böngésző beállításai között."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Automatikus kitöltés kikapcsolása"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Adatvédelem és biztonság"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"A gyorsítótár törlése"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"A helyileg gyorsítótárazott tartalmak és adatbázisok törlése"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"A helyileg gyorsítótárazott tartalmak és adatbázisok törlésre kerülnek."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookie-k"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Az összes cookie törlése"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"A böngésző összes cookie-jának törlése"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Minden cookie törlésre kerül."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Előzmények törlése"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"A böngésző navigációs előzményeinek törlése"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"A böngésző navigációs előzményei törlésre kerülnek."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Űrlapadatok"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Űrlapadatok törlése"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Minden mentett űrlapadat törlése"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Az összes mentett űrlapadat törlésre kerül."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Jelszavak törlése"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Az összes mentett jelszó törlése"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Az összes mentett jelszó törlésre kerül."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Hely"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Helyadatok engedélyezése"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"A webhelyek hozzáférést kérhetnek a tartózkodási helyéhez"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Helyhozzáférés letiltása"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Helyhozzáférés letiltása minden webhelynél"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Helyhozzáférés letiltása minden webhelynél"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Biztonsági beállítások"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Jelszavak"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Jelszavak megjegyzése"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Menti a webhelyekhez tartozó felhasználóneveket és jelszavakat"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Űrlapadatok megjegyzése"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Alapértelmezett nagyítás"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Oldalak megnyitása áttekintő nézetben"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Áttekintést ad az újonnan megnyitott oldalakról"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Speciális beállítások"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Speciális"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Webhelyek beállításai"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Speciális beállítások az egyes webhelyekhez"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Alapértékek visszaállítása"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Visszaállítás alaphelyzetbe"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Alapértelmezett beállítások visszaállítása"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"A beállítások visszaállnak az alapértelmezett értékekre."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japán (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japán (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japán (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Koreai (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Szöveg kódolása"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Gyorsvezérlők"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"A gyorsvezérlők eléréséhez csúsztassa hüvelykujját befelé a bal vagy jobb széltől"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"A leglátogatottabb honlap"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Kezdőlap beállítása, hogy a leglátogatottabb oldalakat mutassa."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Adatkapcsolat-probléma"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Probléma van a fájllal"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Megerősítés"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Minden adat törlése"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Mégse"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Háttérkép beállítása..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Könyvjelzők"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Nincsenek könyvjelzők"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Fiók kiválasztása"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Szinkronizálás Google Fiókkal"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Androidos könyvjelzői nincsenek Google Fiókhoz társítva"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Az Androidos könyvjelzők törlése"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Az Androidos könyvjelzők hozzáadása <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g> fiók könyvjelzőihez"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Megosztás"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Nem nyitható meg több lap"</string>
</resources>
diff --git a/res/values-in-xlarge/strings.xml b/res/values-in-xlarge/strings.xml
new file mode 100644
index 0000000..785a17b
--- /dev/null
+++ b/res/values-in-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Tab baru"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Tab penyamaran baru"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Tab"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Buka di tab baru"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Buka di tab latar belakang baru"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Buka semua di tab baru"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Buka tab baru di belakang tab ini"</string>
+</resources>
diff --git a/res/values-in/strings.xml b/res/values-in/strings.xml
index 568dc61..206edba 100644
--- a/res/values-in/strings.xml
+++ b/res/values-in/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Peramban"</string>
<string name="choose_upload" msgid="3649366287575002063">"Pilih berkas untuk diunggah"</string>
<string name="new_tab" msgid="4505722538297295141">"Jendela baru"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Jendela penyamaran baru"</string>
<string name="active_tabs" msgid="3050623868203544623">"Windows"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Bookmark"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Paling sering dikunjungi"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Peramban"</string>
<string name="cancel" msgid="3017274947407233702">"Batal"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Tidak ada kecocokan"</item>
- <item quantity="one" msgid="4352019729062956802">"1 kecocokan"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> kecocokan"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> kecocokan"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Memuat…"</string>
<string name="page_info" msgid="4048529256302257195">"Info laman"</string>
<string name="page_info_view" msgid="5303490449842635158">"Lihat info laman"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Lanjutkan"</string>
<string name="security_warning" msgid="6607795404322797541">"Peringatan sertifikat"</string>
<string name="view_certificate" msgid="1472768887529093862">"Lihat sertifikat"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Kembali"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Sertifikat ini dari otoritas yang tidak dipercaya."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Nama situs tidak cocok dengan nama pada sertifikat."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Sertifikat ini telah kedaluwarsa."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"Teruskan"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Batal"</string>
- <string name="location" msgid="969988560160364559">"Lokasi"</string>
- <string name="name" msgid="5990326151488445481">"Nama"</string>
+ <string name="location" msgid="3411848697912600125">"Alamat"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Tambahkan ke"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Map baru"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Edit map"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Hapus map"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Tanpa submap"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Bookmark"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Layar utama"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Map lainnya..."</string>
+ <string name="name" msgid="5462672162695365387">"Label"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Tambahkan bookmark"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Tambahkan ke Bookmark"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Bookmark laman ini"</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"Edit bookmark"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Tambahkan pintasan ke Beranda"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Tambahkan pintasan ke beranda"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Buka"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Hapus bookmark"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Hapus dari bookmark"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"URL ini tidak dapat di-bookmark."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Hapus"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Bookmark laman yang terakhir dilihat."</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Tampilan thumbnail"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Tampilan daftar"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Thumbnail"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Daftar"</string>
<string name="current_page" msgid="7510129573681663135">"dari "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Bookmark \"<xliff:g id="BOOKMARK">%s</xliff:g>\" akan dihapus."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Buka di jendela baru"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Buka semua di jendela baru"</string>
<string name="goto_dot" msgid="3895839050522602723">"Buka"</string>
- <string name="find_dot" msgid="6259312434696611957">"Temukan pada laman"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Buka tab penyamaran baru"</string>
<string name="select_dot" msgid="6299170761900561967">"Pilih teks"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Jendela saat ini"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Tutup"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Unduhan"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Salin URL laman"</string>
<string name="share_page" msgid="593756995297268343">"Bagikan lama"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Simpan sebagai Arsip Web"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Arsip web disimpan."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Gagal menyimpan arsip web."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> bookmark"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Map kosong"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Buka"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Buka di jendela baru"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Bookmark tautan"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Buka di jendela latar belakang baru"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Simpan tautan"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Bagikan tautan"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Salin"</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Setel beranda"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Setel mesin telusur"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Pilih mesin telusur"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Gunakan laman ini"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Setel ke..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Laman ini"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Laman kosong"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Laman bawaan"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Sesuaikan dengan laman secara otomatis"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Format laman web agar sesuai dengan layar"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Tampilan lanskap saja"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Tampilkan laman hanya pada orientasi layar lanskap dan lebar"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Setelan privasi"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Umum"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sinkronisasi"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"IsiOtomatis"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sinkronkan dengan Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Bagikan bookmark & dan data lain antara Peramban Android dan Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Akun Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sinkronkan bookmark"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sinkronkan bookmark antara Peramban Android dan Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Mulai sinkronisasi"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Pilih akun Google untuk berbagi dengan"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"IsiOtomatis Formulir"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Isi formulir web dengan sekali klik"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Setelan IsiOtomatis"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Menyiapkan & mengelola data untuk formulir IsiOtomatis"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Masuk ke Google secara otomatis"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Tidak ada akun yang ditemukan"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Masuk ke situs Google secara otomatis menggunakan <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Masuk ke situs Google menggunakan <xliff:g id="ID_1">%s</xliff:g>"\n"setelan Privasi & Keamanan mengontrol aktivitas masuk otomatis ke Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Jangan masuk secara otomatis"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"IsiOtomatis akan menggunakan profil Anda untuk membantu mengisi formulir web dengan sekali klik."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Nama lengkap:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Email:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Nama perusahaan:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Baris alamat 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Alamat jalan, P.O. box, c/o"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Baris alamat 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Apartemen, suite, unit, bangunan, lantai dll."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Kota:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Negara Bagian / Provinsi / Daerah:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Kode pos:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Negara:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telepon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Nomor telepon tidak valid"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Simpan profil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profil disimpan"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profil dihapus"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Hapus profil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Peramban dapat melengkapi formulir web seperti ini. Apakah Anda ingin menyiapkan profil?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"IsiOtomatis selalu dapat dikonfigurasi melalui Setelan Peramban."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Nonaktifkan IsiOtomatis"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Privasi & Keamanan"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Hapus tembolok"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Hapus konten dan database yang disimpan dalam tembolok secara lokal"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Konten dan database yang disimpan dalam tembolok secara lokal akan dihapus."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Kuki"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Hapus semua data kuki"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Hapus semua kuki peramban"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Semua kuki akan dihapus."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Hapus riwayat"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Hapus riwayat navigasi peramban"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Riwayat navigasi peramban akan dihapus."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Data formulir"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Hapus data formulir"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Hapus semua data formulir tersimpan"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Semua data formulir yang tersimpan akan dihapus."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Hapus sandi"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Hapus semua sandi tersimpan"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Semua data sandi yang tersimpan akan dihapus."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Lokasi"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Aktifkan lokasi"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Izinkan situs meminta akses ke lokasi Anda"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Hapus akses lokasi"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Hapus akses lokasi untuk semua situs web"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Hapus akses lokasi untuk semua situs web"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Setelan sertifikat"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Sandi"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Ingat sandi"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Simpan nama pengguna dan sandi untuk situs web"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Ingat data formulir"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Zoom bawaan"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Buka laman di ikhtisar"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Tampilkan ikhtisar laman yang baru dibuka"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Setelan lanjutan"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Lanjutan"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Setelan situs web"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Setelan lanjutan untuk masing-masing situs web"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Setel ulang bawaan"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Setel ulang ke bawaan"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Pulihkan setelan bawaan"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Setelan akan kembali ke nilai bawaan."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"Jepang (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Jepang (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Jepang (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Korea (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Penyandiaksaraan teks"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Kontrol Cepat"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Gesek ibu jari dari tepi kiri atau kanan untuk mengakses kontrol cepat"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Beranda yang Paling Sering Dikunjungi"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Menyetel beranda Anda untuk menampilkan laman yang paling sering dikunjungi."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Masalah konektivitas data"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Masalah dengan berkas"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Konfirmasi"</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Hapus semua data"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Batal"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Menyetel wallpaper..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Bookmark"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Tidak ada bookmark"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Pilih akun"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sinkronkan dengan akun Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Bookmark Android Anda tidak terkait dengan akun Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Hapus bookmark Android Anda"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Tambahkan bookmark Android ke bookmark untuk <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Bagikan"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Tidak ada lagi tab yang tersedia"</string>
</resources>
diff --git a/res/values-it-xlarge/strings.xml b/res/values-it-xlarge/strings.xml
new file mode 100644
index 0000000..d2dc0e6
--- /dev/null
+++ b/res/values-it-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Nuova scheda"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Nuova scheda in incognito"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Schede"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Apri in una nuova scheda"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Apri in una nuova scheda in secondo piano"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Apri tutto in nuove schede"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Apri le nuove schede dietro la scheda corrente"</string>
+</resources>
diff --git a/res/values-it/strings.xml b/res/values-it/strings.xml
index b1a8729..6bf732a 100644
--- a/res/values-it/strings.xml
+++ b/res/values-it/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Browser"</string>
<string name="choose_upload" msgid="3649366287575002063">"Scegli il file per il caricamento"</string>
<string name="new_tab" msgid="4505722538297295141">"Nuova finestra"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nuova finestra in incognito"</string>
<string name="active_tabs" msgid="3050623868203544623">"Finestre"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Segnalibri"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"I più visitati"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Browser"</string>
<string name="cancel" msgid="3017274947407233702">"Annulla"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Nessuna corrispondenza"</item>
- <item quantity="one" msgid="4352019729062956802">"1 corrispondenza"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> corrispondenze"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> corrispondenze"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Caricamento..."</string>
<string name="page_info" msgid="4048529256302257195">"Info pagina"</string>
<string name="page_info_view" msgid="5303490449842635158">"Visualizza info pagina"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Continua"</string>
<string name="security_warning" msgid="6607795404322797541">"Avviso di protezione"</string>
<string name="view_certificate" msgid="1472768887529093862">"Visualizza certificato"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Indietro"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Questo certificato non proviene da un\'autorità attendibile."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Il nome del sito non corrisponde al nome nel certificato."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Il certificato è scaduto."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Avanti"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Annulla"</string>
- <string name="location" msgid="969988560160364559">"URL"</string>
- <string name="name" msgid="5990326151488445481">"Nome"</string>
+ <string name="location" msgid="3411848697912600125">"Indirizzo"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Aggiungi a"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Nuova cartella"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Modifica cartella"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Elimina cartella"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Nessuna sottocartella"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Segnalibri"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Schermata Home"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Altra cartella…"</string>
+ <string name="name" msgid="5462672162695365387">"Etichetta"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Aggiungi segnalibro"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Aggiungi ai segnalibri"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Aggiungi pagina ai segnalibri"</string>
+ <string name="remove" msgid="7820112494467011374">"Rimuovi"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Modifica segnalibro"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Aggiungi scorciatoia su Home"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Aggiungi scorciatoia a Home"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Apri"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Elimina segnalibro"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Rimuovi dai segnalibri"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"L\'URL non può essere aggiunto ai segnalibri."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Elimina"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Aggiungi ultima pagina visualizzata ai segnalibri"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Visualizzazione miniatura"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Visualizzazione elenco"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniature"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Elenco"</string>
<string name="current_page" msgid="7510129573681663135">"da "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Il segnalibro \"<xliff:g id="BOOKMARK">%s</xliff:g>\" verrà eliminato."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Apri in nuova finestra"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Apri tutto in nuove finestre"</string>
<string name="goto_dot" msgid="3895839050522602723">"Vai"</string>
- <string name="find_dot" msgid="6259312434696611957">"Trova nella pagina"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Apri nuova scheda in incognito"</string>
<string name="select_dot" msgid="6299170761900561967">"Seleziona testo"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Finestre correnti"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Chiudi"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Download"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Copia URL della pagina"</string>
<string name="share_page" msgid="593756995297268343">"Condividi pagina"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Salva come archivio web"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Archivio web salvato"</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Salvataggio archivio web non riuscito."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> segnalibri"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Cartella vuota"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Apri"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Apri in nuova finestra"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Aggiungi link in segnalibri"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Apri in nuova finestra in secondo piano"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Salva link"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Condividi link"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Copia"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Imposta home page"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Imposta motore di ricerca"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Seleziona un motore di ricerca"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Utilizza pagina corrente"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Imposta su..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Pagina corrente"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Pagina vuota"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Pagina predefinita"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Adatta autom. pagine"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Adatta le pagine web allo schermo"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Visual. solo orizzontale"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Visualizza le pagine solo con l\'orientamento dello schermo orizzontale più largo"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Impostazioni privacy"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Generali"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sincronizzazione"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Compilazione automatica"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sincronizza con Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Condividi Segnalibri e altri dati tra il Browser di Android e Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Account Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sincronizza Segnalibri"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sincronizza Segnalibri tra il Browser di Android e Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Avvia sincronizzazione"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Seleziona account Google"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Compilazione automatica moduli"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Compila i moduli web con un clic"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Impost. Compilazione automatica"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Imposta e gestisci i dati per i moduli compilati automaticamente"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Accesso Google automatico"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Nessun account trovato"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Accedi automaticamente ai siti Google utilizzando <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Accesso ai siti di Google con <xliff:g id="ID_1">%s</xliff:g>"\n"L\'accesso automatico a Google è controllato dalle tue impostazioni di privacy e sicurezza"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Non accedere automaticamente"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"La Compilazione automatica utilizzerà il tuo profilo per aiutarti a completare i moduli web con un solo clic."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Nome e cognome:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Email:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Nome azienda:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Riga indirizzo 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Indirizzo, casella postale, c/o"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Riga indirizzo 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Appartamento, suite, unità, edificio, piano ecc."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Città:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Stato/Provincia/Regione:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Codice postale:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Paese:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefono:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Numero di telefono non valido"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Salva profilo"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profilo salvato"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profilo eliminato"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Elimina profilo"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Il browser può compilare automaticamente i moduli web come questo. Vuoi impostare il tuo profilo?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"È sempre possibile configurare la compilazione automatica tramite le impostazioni del browser."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Disabilita compilazione automatica"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Privacy e sicurezza"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Cancella cache"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Cancella i contenuti e i database memorizzati localmente nella cache"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"I contenuti e i database memorizzati localmente nella cache verranno eliminati."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookie"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Cancella cookie"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Cancella tutti i cookie del browser"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Verranno eliminati tutti i cookie."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Cancella cronologia"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Cancella la cronologia di esplorazione del browser"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"La cronologia di navigazione del browser verrà eliminata."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Dati modulo"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Cancella dati moduli"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Cancella tutti i dati dei moduli salvati"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Tutti i dati dei moduli salvati verranno eliminati."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Cancella password"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Cancella tutte le password salvate"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Tutte le password salvate verranno eliminate."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Posizione"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Attiva posizione"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Consenti ai siti di richiedere l\'accesso alla tua posizione"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Cancella accesso a posiz."</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Cancella l\'accesso alla posizione per tutti i siti web"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Cancella l\'accesso alla posizione per tutti i siti web"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Impostazioni di protezione"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Password"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Memorizza le password"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Salva nomi utente e password per i siti web"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Memorizza dati moduli"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Zoom predefinito"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Apri pag. in panoramica"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Visualizza la panoramica delle pagine appena aperte"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Impostazioni avanzate"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Avanzate"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Impostazioni siti web"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Impostazioni avanzate dei singoli siti web"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Ripristina impostazioni predefinite"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Ripristina valori predef."</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Ripristina impostazioni predefinite"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Verranno ripristinate le impostazioni predefinite."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Giapponese (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Giapponese (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Giapponese (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Coreano (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codifica testo"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Controlli rapidi"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Fai scorrere il pollice dal bordo sinistro/destro per accedere ai controlli rapidi"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Home page più visitata"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Imposta la tua home page per mostrare le pagine più visitate."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problema di connettività dati"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problemi con il file"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Conferma"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Elimina tutti i dati"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Annulla"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Impostazione sfondo in corso..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Segnalibri"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Nessun segnalibro disponibile"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Scegli account"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sincronizza con l\'account Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"I tuoi Segnalibri Android non sono associati a un account Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Rimuovi i tuoi Segnalibri Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Aggiungi i tuoi Segnalibri Android a quelli per <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Condividi"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Nessun\'altra scheda disponibile"</string>
</resources>
diff --git a/res/values-iw-xlarge/strings.xml b/res/values-iw-xlarge/strings.xml
new file mode 100644
index 0000000..1ea3357
--- /dev/null
+++ b/res/values-iw-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"כרטיסיה חדשה"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"כרטיסיה חדשה של גלישה בסתר"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"כרטיסיות"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"פתח בכרטיסייה חדשה"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"פתח בכרטיסיית רקע חדשה"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"פתח את הכל בכרטיסיות חדשות"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"פתח כרטיסיות חדשות מאחורי הכרטיסייה הנוכחית"</string>
+</resources>
diff --git a/res/values-iw/strings.xml b/res/values-iw/strings.xml
index f5c65cb..47a3e20 100644
--- a/res/values-iw/strings.xml
+++ b/res/values-iw/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"דפדפן"</string>
<string name="choose_upload" msgid="3649366287575002063">"בחר קובץ להעלאה"</string>
<string name="new_tab" msgid="4505722538297295141">"חלון חדש"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"חלון חדש של גלישה בסתר"</string>
<string name="active_tabs" msgid="3050623868203544623">"חלונות"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"סימניות"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"אתרים שבהם אתה מבקר בתדירות הגבוהה ביותר"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"דפדפן"</string>
<string name="cancel" msgid="3017274947407233702">"ביטול"</string>
<string name="ok" msgid="1509280796718850364">"אישור"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"אין התאמות"</item>
- <item quantity="one" msgid="4352019729062956802">"התאמה אחת"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> התאמות"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> התאמות"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"טוען…"</string>
<string name="page_info" msgid="4048529256302257195">"פרטי דף"</string>
<string name="page_info_view" msgid="5303490449842635158">"הצג את פרטי הדף"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"המשך"</string>
<string name="security_warning" msgid="6607795404322797541">"אזהרת אבטחה"</string>
<string name="view_certificate" msgid="1472768887529093862">"הצג אישור"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"חזור"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"אישור זה אינו מרשות אמינה."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"שם האתר לא תואם לשם באישור."</string>
<string name="ssl_expired" msgid="5739349389499575559">"פג תוקפו של אישור זה."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"העבר"</string>
<string name="save" msgid="5922311934992468496">"אישור"</string>
<string name="do_not_save" msgid="6777633870113477714">"ביטול"</string>
- <string name="location" msgid="969988560160364559">"מיקום"</string>
- <string name="name" msgid="5990326151488445481">"שם"</string>
+ <string name="location" msgid="3411848697912600125">"כתובת"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"הוסף אל"</string>
+ <string name="new_folder" msgid="7743540149088867917">"תיקיה חדשה"</string>
+ <string name="edit_folder" msgid="621817453133656156">"ערוך תיקיה"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"מחק תיקיה"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"אין תיקיות משנה"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"סימניות"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"מסך דף הבית"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"תיקיה אחרת..."</string>
+ <string name="name" msgid="5462672162695365387">"תווית"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"הוסף סימניה"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"הוסף לסימניות"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"הוסף דף זה לסימניות"</string>
+ <string name="remove" msgid="7820112494467011374">"הסר"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"ערוך סימניה"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"הוסף קיצור דרך לדף הבית"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"הוסף קיצור דרך לדף הבית"</string>
<string name="open_bookmark" msgid="8473581305759935790">"פתח"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"מחק סימניה"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"הסר מסימניות"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"לא ניתן להפוך כתובת אתר זו לסימניה."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"מחק"</string>
<string name="bookmark_page" msgid="6845189305130307274">"סמן בסימניה את הדף האחרון שהוצג"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"תצוגת תמונה ממוזערת"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"תצוגת רשימה"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"תמונות ממוזערות"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"רשימה"</string>
<string name="current_page" msgid="7510129573681663135">"מ "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"הסימניה \"<xliff:g id="BOOKMARK">%s</xliff:g>\" תימחק."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"פתח בחלון חדש"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"פתח הכל בחלונות חדשים"</string>
<string name="goto_dot" msgid="3895839050522602723">"בצע"</string>
- <string name="find_dot" msgid="6259312434696611957">"מצא בדף"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"פתח כרטיסיה חדשה של גלישה בסתר"</string>
<string name="select_dot" msgid="6299170761900561967">"בחר טקסט"</string>
<string name="tab_picker_title" msgid="864478399057782913">"חלונות נוכחיים"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"סגור"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"הורדות"</string>
<string name="copy_page_url" msgid="7635062169011319208">"העתק כתובת אתר של דף"</string>
<string name="share_page" msgid="593756995297268343">"שתף דף"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"שמור כארכיון אינטרנט"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"ארכיון אינטרנט נשמר."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"נכשלה שמירת ארכיון אינטרנט."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> סימניות"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"תיקיה ריקה"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"פתח"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"פתח בחלון חדש"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"קישור סימניה"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"פתח בחלון רקע חדש"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"שמור קישור"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"שתף קישור"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"העתק"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"הגדר דף בית"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"הגדר מנוע חיפוש"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"בחר מנוע חיפוש"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"השתמש בדף הנוכחי"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"הוגדר ל..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"דף נוכחי"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"דף ריק"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"דף ברירת מחדל"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"התאם דפים באופן אוטומטי"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"עצב דפי אינטרנט כך שיתאימו למסך"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"תצוגה לרוחב בלבד"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"הצג דפים רק בפריסת מסך הרחבה, לרוחב"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"הגדרות פרטיות"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"כללי"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"סנכרון"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"מילוי אוטומטי"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"סנכרן עם Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"שתף סימניות ונתונים אחרים בין דפדפן Android ו-Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"חשבון Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"סנכרן סימניות"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"סנכרן סימניות בין דפדפן Android ובין Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"התחל סנכרון"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"בחר חשבון Google לשיתוף"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"מילוי אוטומטי של טפסים"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"מלא טופסי אינטרנט בלחיצה אחת"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"הגדרות מילוי אוטומטי"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"הגדר ונהל נתונים לטפסים במילוי אוטומטי"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"כניסה אוטומטית ל-Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"לא נמצאו חשבונות"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"היכנס ל-Google Sites באופן אוטומטי באמצעות <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"כניסה ל-Google Sites בעזרת <xliff:g id="ID_1">%s</xliff:g>"\n"הגדרות הפרטיות והאבטחה שלך שולטות בכניסה האוטומטית ל-Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"אל תיכנס באופן אוטומטי"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"\'מילוי אוטומטי\' ישתמש בפרופיל שלך כדי לעזור לך להשלים טופסי אינטרנט בלחיצה אחת."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"שם מלא:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"דוא\"ל:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"שם חברה:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"שורה 1 של כתובת:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"כתובת רחוב, תא דואר, אצל"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"שורה 2 של כתובת:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"דירה, סוויטה, יחידה, בניין, קומה וכדומה"</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"עיר / יישוב:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"מדינה / מחוז / אזור:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"מיקוד:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"ארץ:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"טלפון:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"מספר טלפון לא חוקי"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"שמור פרופיל"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"הפרופיל נשמר"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"הפרופיל נמחק"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"מחק את הפרופיל"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"הדפדפן יכול למלא טופסי אינטרנט כמו זה באופן אוטומטי. האם תרצה להגדיר את הפרופיל שלך?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"ניתן תמיד להגדיר את \'מילוי אוטומטי\' דרך \'הגדרות דפדפן\'."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"הפוך \'מילוי אוטומטי\' ללא זמין"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"פרטיות ואבטחה"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"נקה קובץ שמור"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"נקה תוכן ומסדי נתונים בקובץ השמור המקומי"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"תוכן ומסדי נתונים בקובץ השמור המקומי יימחקו."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"קובצי cookie"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"נקה את כל הנתונים של קובצי cookie"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"נקה את כל קובצי ה-cookies של הדפדפן"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"כל קובצי ה-cookies יימחקו."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"נקה היסטוריה"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"נקה את היסטוריית הניווט של הדפדפן"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"היסטוריית הניווט של הדפדפן תימחק."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"נתוני טופס"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"נקה נתוני טופס"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"נקה את כל נתוני הטפסים שנשמרו"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"כל נתוני הטפסים השמורים יימחקו."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"נקה סיסמאות"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"נקה את כל הסיסמאות השמורות"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"כל הסיסמאות השמורות יימחקו."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"מיקום"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"הפוך מיקום לפעיל"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"אפשר לאתרים לבקש גישה למיקומך"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"נקה גישה למיקום"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"נקה גישה למיקום לכל אתרי האינטרנט"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"נקה גישה למיקום לכל אתרי האינטרנט"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"הגדרות אבטחה"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"סיסמאות"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"זכור סיסמאות"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"שמור שמות משתמש וסיסמאות של אתרים"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"זכור את נתוני הטופס"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"ברירת מחדל של מרחק מתצוגה"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"פתח דפים בסקירה"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"הצג סקירה של דפים שנפתחו לאחרונה"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"הגדרות מתקדמות"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"מתקדם"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"הגדרות אתר"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"הגדרות מתקדמות לאתרים נפרדים"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"איפוס ברירות מחדל"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"אפס לברירת מחדל"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"שחזר הגדרות ברירת מחדל"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"ההגדרות יוחזרו לערכי ברירת המחדל."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"יפנית (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"יפנית (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"יפנית (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"קוריאנית (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"קידוד טקסט"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"פקדים מהירים"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"החלק את האגודל מהקצה הימני או השמאלי כדי לגשת לפקדים המהירים"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"דף הבית הפופולרי ביותר"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"מגדיר את דף הבית שלך להציג את הדפים הפופולריים ביותר."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"בעיה בקישוריות נתונים"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"בעיה בקובץ"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"אשר"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"מחק את כל הנתונים"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"ביטול"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"מגדיר טפט..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"סימניות"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"אין סימניות"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"בחירת חשבון"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"סנכרן עם חשבון Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"סימניות Android שלך אינן משויכות לחשבון Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"הסר את הסימניות של Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"הוסף את סימניות Android לסימניות של <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"שתף"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"אין עוד כרטיסיות זמינות"</string>
</resources>
diff --git a/res/values-ja-xlarge/strings.xml b/res/values-ja-xlarge/strings.xml
new file mode 100644
index 0000000..7e75d86
--- /dev/null
+++ b/res/values-ja-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"新しいタブ"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"新しいシークレットタブ"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"タブ"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"新しいタブで開く"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"新しいバックグラウンドタブで開く"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"常に新しいタブで開く"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"現在のタブの後ろに新しいタブを開く"</string>
+</resources>
diff --git a/res/values-ja/donottranslate_strings.xml b/res/values-ja/donottranslate_strings.xml
index cbda8f2..026d57a 100644
--- a/res/values-ja/donottranslate_strings.xml
+++ b/res/values-ja/donottranslate_strings.xml
@@ -17,5 +17,5 @@
<resources xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="pref_default_text_encoding_default">SHIFT_JIS</string>
+ <string name="pref_default_text_encoding_default" translatable="false">SHIFT_JIS</string>
</resources>
diff --git a/res/values-ja/strings.xml b/res/values-ja/strings.xml
index 862bdab..d45b0ef 100644
--- a/res/values-ja/strings.xml
+++ b/res/values-ja/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"ブラウザ"</string>
<string name="choose_upload" msgid="3649366287575002063">"アップロードするファイルを選択"</string>
<string name="new_tab" msgid="4505722538297295141">"新しいウィンドウ"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"新しいシークレットウインドウ"</string>
<string name="active_tabs" msgid="3050623868203544623">"ウィンドウ"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"ブックマーク"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"よく使用"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"ブラウザ"</string>
<string name="cancel" msgid="3017274947407233702">"キャンセル"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"該当なし"</item>
- <item quantity="one" msgid="4352019729062956802">"1件一致"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g>件一致"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g>件一致"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"読み込み中..."</string>
<string name="page_info" msgid="4048529256302257195">"ページ情報"</string>
<string name="page_info_view" msgid="5303490449842635158">"ページ情報を表示"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"続行"</string>
<string name="security_warning" msgid="6607795404322797541">"セキュリティ警告"</string>
<string name="view_certificate" msgid="1472768887529093862">"証明書を表示"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"戻る"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"この証明書は信頼できる認証機関のものではありません。"</string>
<string name="ssl_mismatch" msgid="558688832420069896">"サイト名と証明書上の名前が一致しません。"</string>
<string name="ssl_expired" msgid="5739349389499575559">"この証明書は有効期限切れです。"</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"進む"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"キャンセル"</string>
- <string name="location" msgid="969988560160364559">"場所"</string>
- <string name="name" msgid="5990326151488445481">"名前"</string>
+ <string name="location" msgid="3411848697912600125">"アドレス"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"追加先"</string>
+ <string name="new_folder" msgid="7743540149088867917">"新しいフォルダ"</string>
+ <string name="edit_folder" msgid="621817453133656156">"フォルダを編集"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"フォルダを削除"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"サブフォルダなし"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"ブックマーク"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"ホーム画面"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"その他のフォルダ..."</string>
+ <string name="name" msgid="5462672162695365387">"ラベル"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"ブックマークを追加"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"ブックマークに追加"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"このページをブックマークに追加"</string>
+ <string name="remove" msgid="7820112494467011374">"削除"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"編集"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"ショートカットを作成"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"ホームにショートカットを追加"</string>
<string name="open_bookmark" msgid="8473581305759935790">"開く"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"削除"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"ブックマークから削除"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"このURLはブックマークに追加できません。"</string>
<string name="delete_bookmark" msgid="2422989994934201992">"削除"</string>
<string name="bookmark_page" msgid="6845189305130307274">"最後に表示したページをブックマークする"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"サムネイル表示"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"リスト表示"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"サムネイル"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"リスト"</string>
<string name="current_page" msgid="7510129573681663135">"URL "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"ブックマーク「<xliff:g id="BOOKMARK">%s</xliff:g>」を削除します。"</string>
<string name="open_in_new_window" msgid="6596775546468054510">"新しいウィンドウで開く"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"常に新しいウィンドウで開く"</string>
<string name="goto_dot" msgid="3895839050522602723">"移動"</string>
- <string name="find_dot" msgid="6259312434696611957">"ページ内検索"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"新しいシークレットタブを開く"</string>
<string name="select_dot" msgid="6299170761900561967">"テキストを選択してコピー"</string>
<string name="tab_picker_title" msgid="864478399057782913">"現在のウィンドウ"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"閉じる"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"ダウンロード履歴"</string>
<string name="copy_page_url" msgid="7635062169011319208">"ページのURLをコピー"</string>
<string name="share_page" msgid="593756995297268343">"ページを共有"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"ウェブアーカイブとして保存"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"ウェブアーカイブを保存しました。"</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"ウェブアーカイブを保存できませんでした。"</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g>件のブックマーク"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"空のフォルダ"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"開く"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"新しいウィンドウで開く"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"リンクをブックマーク"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"新しいバックグラウンドウィンドウで開く"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"リンクを保存"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"リンクを共有"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"コピー"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"ホームページ設定"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"検索エンジンの設定"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"検索エンジンを選択する"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"現在のページを使用"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"設定先..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"現在のページ"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"空白ページ"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"デフォルトページ"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"ページの自動調整"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"画面に合わせてウェブページをフォーマットする"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"常に横向きに表示"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"ページを常に横向きに表示する"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"プライバシー設定"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"全般"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"同期"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"自動入力"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Google Chromeと同期する"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"AndroidブラウザとGoogle Chromeの間でブックマークなどのデータを共有する"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Googleアカウント"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"ブックマークを同期する"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"AndroidブラウザとGoogle Chromeの間でブックマークを同期"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"同期を開始"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Googleアカウントを選択"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"フォームの自動入力"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"1回タップするだけでウェブフォームに入力できます"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"自動入力設定"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"自動入力フォーム用のデータの設定と管理"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Googleへの自動ログイン"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"アカウントが見つかりません"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"<xliff:g id="ID_1">%s</xliff:g>で自動的にGoogleにログインする"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"<xliff:g id="ID_1">%s</xliff:g>を使用してGoogleサイトにログインしています"\n"Googleへの自動ログインは、プライバシーとセキュリティの設定で管理されます"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"自動的にログインしない"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"プロフィールは自動入力機能で使用され、1回タップするだけでウェブフォームに入力することができます。"</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"氏名:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"メール:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"会社名:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"住所1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"番地、私書箱、気付など"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"住所2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"建物名、アパート/マンション名、部屋番号など"</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"市区町村:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"都道府県:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"郵便番号:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"国:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"電話:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"電話番号が正しくありません"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"プロフィールを保存"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"プロフィールが保存されました"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"プロフィールを削除しました"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"プロフィールを削除"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"このようなウェブフォームにブラウザで自動入力できます。プロフィールを設定しますか?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"自動入力はいつでもブラウザの[設定]から設定できます。"</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"自動入力を無効にする"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"プライバシーとセキュリティ"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"キャッシュを消去"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"ローカルにキャッシュしたコンテンツとデータベースを消去する"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"ローカルにキャッシュしたコンテンツとデータベースを削除します。"</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookie"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Cookieをすべて消去"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"すべてのブラウザCookieを消去する"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"すべてのCookieを削除します。"</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"履歴消去"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"ブラウザの閲覧履歴を消去する"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"ブラウザの閲覧履歴を削除します。"</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"フォームデータ"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"フォームデータを消去"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"保存されているフォームデータをすべて消去する"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"保存されているすべてのフォームデータが削除されます。"</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"パスワードを消去"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"保存されているすべてのパスワードを消去する"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"保存されているすべてのパスワードを削除します。"</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"現在地情報"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"位置情報を有効にする"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"サイトに現在地情報へのアクセスを許可する"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"位置情報アクセスをクリア"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"すべてのウェブサイトの位置情報アクセスをクリアする"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"すべてのウェブサイトの位置情報アクセスをクリア"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"セキュリティ設定"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"パスワード"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"パスワードを保存"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"ウェブサイトのユーザー名とパスワードを保存する"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"フォームデータを保存"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"デフォルトの倍率"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"ページを全体表示で開く"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"新しく開いたページを全体表示する"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"詳細設定"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"高度な設定"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"ウェブサイト設定"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"個々のウェブサイトの詳細設定"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"初期設定にリセット"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"初期設定にリセット"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"初期設定に戻す"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"設定を初期値に戻します。"</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"日本語(ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"日本語(SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"日本語(EUC-JP)"</item>
+ <item msgid="2193955365569270096">"韓国語(EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"テキストエンコード"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"クイックコントロール"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"クイックコントロールにアクセスするには左端または右端から親指をスワイプします"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"アクセス数が最も多いホームページ"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"アクセス数が最も多いページが表示されるようにホームページを設定します。"</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"データアクセスエラー"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"ファイルに問題があります"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"確認"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"すべてのデータを削除"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"キャンセル"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"壁紙を設定中..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"ブックマーク"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"ブックマークはありません"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"アカウントの選択"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Googleアカウントと同期"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"AndroidのブックマークはGoogleアカウントに関連付けられていません"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Androidのブックマークを削除"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Androidのブックマークを<xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>のブックマークに追加"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"共有"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"タブ数が上限に達しました"</string>
</resources>
diff --git a/res/values-ko-xlarge/strings.xml b/res/values-ko-xlarge/strings.xml
new file mode 100644
index 0000000..63bd6a1
--- /dev/null
+++ b/res/values-ko-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"새 탭"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"새 시크릿 창"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"탭"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"새 탭에서 열기"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"새 배경 탭에서 열기"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"새 탭에서 모두 열기"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"현재 탭 뒤에 새 탭 열기"</string>
+</resources>
diff --git a/res/values-ko/strings.xml b/res/values-ko/strings.xml
index d587530..5aad619 100644
--- a/res/values-ko/strings.xml
+++ b/res/values-ko/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"인터넷"</string>
<string name="choose_upload" msgid="3649366287575002063">"업로드할 파일 선택"</string>
<string name="new_tab" msgid="4505722538297295141">"새 창"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"새 시크릿 창"</string>
<string name="active_tabs" msgid="3050623868203544623">"창"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"북마크"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"자주 방문한 페이지"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"브라우저"</string>
<string name="cancel" msgid="3017274947407233702">"취소"</string>
<string name="ok" msgid="1509280796718850364">"확인"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"검색결과 없음"</item>
- <item quantity="one" msgid="4352019729062956802">"검색결과 1개"</item>
- <item quantity="few" msgid="5544267486978946555">"검색결과 <xliff:g id="NUMBER">%d</xliff:g>개"</item>
- <item quantity="other" msgid="6616125067364315405">"검색결과 <xliff:g id="NUMBER">%d</xliff:g>개"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"로드 중..."</string>
<string name="page_info" msgid="4048529256302257195">"페이지 정보"</string>
<string name="page_info_view" msgid="5303490449842635158">"페이지 정보 보기"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"계속"</string>
<string name="security_warning" msgid="6607795404322797541">"보안 경고"</string>
<string name="view_certificate" msgid="1472768887529093862">"인증서 보기"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"뒤로"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"신뢰할 수 있는 인증 기관에서 발급한 인증서가 아닙니다."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"사이트 이름이 인증서에 있는 것과 일치하지 않습니다."</string>
<string name="ssl_expired" msgid="5739349389499575559">"인증서가 만료되었습니다."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"앞으로"</string>
<string name="save" msgid="5922311934992468496">"확인"</string>
<string name="do_not_save" msgid="6777633870113477714">"취소"</string>
- <string name="location" msgid="969988560160364559">"URL"</string>
- <string name="name" msgid="5990326151488445481">"이름"</string>
+ <string name="location" msgid="3411848697912600125">"주소"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"추가할 위치"</string>
+ <string name="new_folder" msgid="7743540149088867917">"새 폴더"</string>
+ <string name="edit_folder" msgid="621817453133656156">"폴더 수정"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"폴더 삭제"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"하위 폴더 없음"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"북마크"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"홈 화면"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"기타 폴더…"</string>
+ <string name="name" msgid="5462672162695365387">"라벨"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"북마크에 추가"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"북마크에 추가"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"페이지 북마크"</string>
+ <string name="remove" msgid="7820112494467011374">"삭제"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"북마크 수정"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"홈에 바로가기 추가"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"홈에 바로가기 추가"</string>
<string name="open_bookmark" msgid="8473581305759935790">"열기"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"북마크 삭제"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"북마크에서 삭제"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"URL을 북마크에 추가할 수 없습니다."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"삭제"</string>
<string name="bookmark_page" msgid="6845189305130307274">"마지막으로 본 페이지를 북마크 설정"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"미리보기 이미지 보기"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"목록 보기"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"미리보기 이미지"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"목록"</string>
<string name="current_page" msgid="7510129573681663135">"북마크할 페이지 "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"\'<xliff:g id="BOOKMARK">%s</xliff:g>\' 북마크가 삭제됩니다."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"새 창에서 열기"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"새 창에서 모두 열기"</string>
<string name="goto_dot" msgid="3895839050522602723">"이동"</string>
- <string name="find_dot" msgid="6259312434696611957">"페이지에서 찾기"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"새 시크릿 탭 열기"</string>
<string name="select_dot" msgid="6299170761900561967">"텍스트 선택"</string>
<string name="tab_picker_title" msgid="864478399057782913">"현재 창"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"닫기"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"다운로드"</string>
<string name="copy_page_url" msgid="7635062169011319208">"페이지 URL 복사"</string>
<string name="share_page" msgid="593756995297268343">"페이지 공유"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"웹 아카이브로 저장"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"웹 아카이브를 저장했습니다."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"웹 아카이브를 저장하지 못했습니다."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"북마크 <xliff:g id="BOOKMARK_COUNT">%d</xliff:g>개"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"빈 폴더"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"열기"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"새 창에서 열기"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"링크를 북마크에 추가"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"새 배경 창에서 열기"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"링크 저장"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"링크 공유"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"복사"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"홈페이지 설정"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"검색 엔진 설정"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"검색 엔진 선택"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"현재 페이지 사용"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"다음으로 설정:"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"현재 페이지"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"빈 페이지"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"기본 페이지"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"페이지 자동 맞춤"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"화면에 맞게 웹페이지 형식 지정"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"가로 표시 전용"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"넓은 가로 방향 화면으로만 페이지 표시"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"개인정보 설정"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"기본설정"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"동기화"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"자동완성"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Google 크롬과 동기화"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Android 브라우저와 Google 크롬 간에 북마크 및 기타 데이터 공유"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google 계정"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"북마크 동기화"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Android 브라우저와 Google 크롬 간의 북마크 동기화"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"동기화 시작"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"공유할 Google 계정 선택"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"양식 자동완성"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"클릭 한 번으로 웹 양식 작성"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"자동완성 설정"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"자동완성된 양식의 데이터 설정 및 관리"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"자동 Google 로그인"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"계정이 없습니다."</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"<xliff:g id="ID_1">%s</xliff:g>을(를) 사용하여 Google 사이트에 자동으로 로그인"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"개인정보 및 보안 설정 컨트롤<xliff:g id="ID_1">%s</xliff:g>"\n"자동 Google 로그인을 사용하여 Google 사이트에 로그인"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"자동 로그인 안함"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"자동완성 기능은 사용자의 프로필을 사용하여 단 한번의 클릭으로 웹 양식을 작성할 수 있도록 도와줍니다."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"이름:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"이메일:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"회사 이름:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"주소 입력란 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"번지, 사서함, c/o"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"주소 입력란 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"아파트, 빌딩, 층 등"</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"도시:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"시/도/지역:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"우편번호:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"국가:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"전화:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"잘못된 전화번호"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"프로필 저장"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"프로필 저장됨"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"프로필이 삭제되었습니다."</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"프로필 삭제"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"브라우저에서 이 양식과 같은 웹 양식을 자동으로 완성할 수 있습니다. 프로필을 설정하시겠습니까?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"브라우저 설정에서 언제든지 자동완성을 구성할 수 있습니다."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"자동완성 사용 안함"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"개인정보 보호 및 보안"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"캐시 지우기"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"로컬로 캐시된 콘텐츠 및 데이터베이스 삭제"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"로컬로 캐시된 콘텐츠 및 데이터베이스가 삭제됩니다."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"쿠키"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"모든 쿠키 데이터 지우기"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"모든 브라우저 쿠키 지우기"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"쿠키가 모두 삭제됩니다."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"기록 지우기"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"브라우저 탐색 기록 지우기"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"브라우저 탐색 기록이 삭제됩니다."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"양식 데이터"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"양식 데이터 지우기"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"저장된 양식 데이터 모두 지우기"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"저장된 양식 데이터가 모두 삭제됩니다."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"비밀번호 삭제"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"저장된 모든 비밀번호 삭제"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"저장된 비밀번호가 모두 삭제됩니다."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"위치"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"위치 정보 사용"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"사이트의 위치 정보 액세스 요청 허용"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"위치 정보 액세스 삭제"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"모든 웹사이트의 위치 정보 액세스 삭제"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"모든 웹사이트의 위치 정보 액세스 삭제"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"보안 설정"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"비밀번호"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"비밀번호 저장"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"웹사이트에 대해 사용자 이름 및 비밀번호 저장"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"양식 데이터 기억"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"기본 확대/축소"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"페이지 전체보기"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"새 창을 열 때 페이지 전체 표시"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"고급 설정"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"고급"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"웹사이트 설정"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"개별 웹사이트의 고급 설정"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"초기화"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"초기화"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"기본 설정값 복원"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"설정이 기본값으로 되돌아갑니다."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"일본어(ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"일본어(SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"일본어(EUC-JP)"</item>
+ <item msgid="2193955365569270096">"한국어(EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"텍스트 인코딩"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"실험실"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"빠른 컨트롤"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"왼쪽이나 오른쪽 끝에서 엄지손가락으로 스와이프하여 빠른 컨트롤에 액세스"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"자주 방문한 홈페이지"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"자주 방문한 페이지를 표시하도록 홈페이지를 설정합니다."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"데이터 연결에 문제 발생"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"파일 문제 발생"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"확인"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"모든 데이터 삭제"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"취소"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"배경화면을 설정하는 중..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"북마크"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"북마크가 없습니다."</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"계정 선택"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Google 계정과 동기화"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"사용자의 Android 북마크는 Google 계정과 연결되지 않았습니다."</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Android 북마크 삭제"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"<xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>에 대한 북마크에 Android 북마크 추가"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"공유"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"탭이 더 이상 없습니다."</string>
</resources>
diff --git a/res/values-lt-xlarge/strings.xml b/res/values-lt-xlarge/strings.xml
new file mode 100644
index 0000000..7fedc78
--- /dev/null
+++ b/res/values-lt-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Naujas skirtukas"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Naujas inkognito skirtukas"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Skirtukai"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Atidaryti naujame skirtuke"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Atidaryti naujame fono skirtuko lape"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Atidaryti visas naujuose skirtukų lapuose"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Atidaroma naujų skirtukų lapų už dabartinio"</string>
+</resources>
diff --git a/res/values-lt/strings.xml b/res/values-lt/strings.xml
index e24d157..30bac67 100644
--- a/res/values-lt/strings.xml
+++ b/res/values-lt/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Naršyklė"</string>
<string name="choose_upload" msgid="3649366287575002063">"Pasirinkti failą, kurį norite įkelti"</string>
<string name="new_tab" msgid="4505722538297295141">"Naujas langas"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Naujas inkognito langas"</string>
<string name="active_tabs" msgid="3050623868203544623">"Windows"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Žymės"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Dažniausiai lankomos"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Naršyklė"</string>
<string name="cancel" msgid="3017274947407233702">"Atšaukti"</string>
<string name="ok" msgid="1509280796718850364">"Gerai"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Nėra atitikčių"</item>
- <item quantity="one" msgid="4352019729062956802">"1 atitiktis"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> atitiktys (-čių)"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> atitiktys (-čių)"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Įkeliama…"</string>
<string name="page_info" msgid="4048529256302257195">"Puslapio informacija"</string>
<string name="page_info_view" msgid="5303490449842635158">"Žiūrėti puslapio informaciją"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Tęsti"</string>
<string name="security_warning" msgid="6607795404322797541">"Saugos įspėjimas"</string>
<string name="view_certificate" msgid="1472768887529093862">"Žiūrėti sertifikatą"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Atgal"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Šį sertifikatą išdavė nepatikima įstaiga."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Svetainės pavadinimas neatitinka sertifikate nurodyto pavadinimo."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Šio sertifikato galiojimo laikas baigėsi."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"Persiųsti"</string>
<string name="save" msgid="5922311934992468496">"Gerai"</string>
<string name="do_not_save" msgid="6777633870113477714">"Atšaukti"</string>
- <string name="location" msgid="969988560160364559">"Vieta"</string>
- <string name="name" msgid="5990326151488445481">"Pavadinimas"</string>
+ <string name="location" msgid="3411848697912600125">"Adresas"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Pridėti prie"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Naujas aplankas"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Redaguoti aplanką"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Ištrinti aplanką"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Nėra poaplankių"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Žymės"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Pagrindinis ekranas"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Kitas aplankas..."</string>
+ <string name="name" msgid="5462672162695365387">"Etiketė"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Pridėti žymę"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Pridėti prie žymių"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Žymėti šį puslapį"</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"Redaguoti žymę"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Prie pagrindinio puslapio pridėti spartųjį klavišą"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Prie pagrindinio psl. pridėti spartųjį klavišą"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Atidaryti"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Ištrinti žymę"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Pašalinti iš žymių"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Negalima žymėti URL."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Ištrinti"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Žymėti paskutinį peržiūrėtą puslapį"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Miniatiūros rodinys"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Sąrašo rodinys"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniatiūros"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Sąrašas"</string>
<string name="current_page" msgid="7510129573681663135">"nuo "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Žymė „<xliff:g id="BOOKMARK">%s</xliff:g>“ bus ištrinta."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Atidaryti naujame lange"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Atidaryti visas naujuose languose"</string>
<string name="goto_dot" msgid="3895839050522602723">"Pradėti"</string>
- <string name="find_dot" msgid="6259312434696611957">"Rasti puslapyje"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Atidaryti naują inkogn. skirt."</string>
<string name="select_dot" msgid="6299170761900561967">"Pasirinkti tekstą"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Dabartiniai langai"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Uždaryti"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Atsisiuntimai"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Kopijuoti puslapio URL"</string>
<string name="share_page" msgid="593756995297268343">"Bendrinti puslapį"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Išsaugoti kaip žiniatinklio archyvą"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Žiniatinklio archyvas išsaugotas."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Nepavyko išsaugoti žiniatinklio archyvo."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"Žymių: <xliff:g id="BOOKMARK_COUNT">%d</xliff:g>"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Tuščias aplankas"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Atidaryti"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Atidaryti naujame lange"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Žymėti nuorodą"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Atidaryti naujame fono lange"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Išsaugoti nuorodą"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Bendrinti nuorodą"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopijuoti"</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Nustatyti pagrindinį puslapį"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Nustatyti paieškos variklį"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Pasirinkti paieškos variklį"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Naudoti dabartinį puslapį"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Nustatyti…"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Dabartinis puslapis"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Tuščias puslapis"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Numatytasis puslapis"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Automatiškai talpinti puslapius"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Formatuoti tinklalapius, kad tilptų ekrane"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Tik gulsčia pateiktis"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Pateikti tik platesnės gulsčios ekrano padėties puslapius"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Privatumo nustatymai"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Bendra"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sinchronizavimas"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Automatinis užpildymas"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sinchronizuoti su „Google Chrome“"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Bendrinti žymes ir kitus duomenis tarp „Android“ naršyklės ir „Google Chrome“"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"„Google“ paskyra"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sinchronizuoti žymes"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sinchronizuoti žymes tarp „Android“ naršyklės ir „Google Chrome“"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Pradėti sinchroniz."</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Pas. bendr. „Google“ pask."</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Automatinio pildymo forma"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Vienu paspaudimu užpildykite žiniatinklio formas"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Automatinio pildymo nustatymai"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Nustatyti ir valdyti automatinio pildymo formų duomenis"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Autom. prisijung. prie „Google“"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Nerasta jokių paskyrų"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Automatiškai prisijunkite prie „Google“ svetainių naudodami „<xliff:g id="ID_1">%s</xliff:g>“"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Prisijungiama prie „Google“ svetainių naudojant <xliff:g id="ID_1">%s</xliff:g>"\n"Automatinis prisijungimas prie „Google“ valdomas pagal „Privatumo ir saugos“ nustatymus"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Neprisijungti automatiškai"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Naudojant automatinį pildymą bus naudojamas profilis, kad galėtumėte vos vienu paspaudimu užpildyti žiniatinklio formas."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Vardas ir pavardė:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"El. paštas:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Įmonės pavadinimas:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"1 adreso eilutė:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Adresas, pašto dėžutė, kilmės sertifikatas"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"2 adreso eilutė:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Apartamentai, liukso kambariai, blokas, pastatas, aukštas ir kt."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Miestas / miestelis:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Valstija / provincija / regionas:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Pašto kodas:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Šalis:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefonas:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Netinkamas telefono numeris"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Išsaugoti profilį"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profilis išsaugotas"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profilis ištrintas"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Ištrinti profilį"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Naršyklė gali automatiškai užpildyti į šią panašias žiniatinklio formas. Ar norite nustatyti profilį?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Automatinį pildymą visada galima konfigūruoti apsilankius skiltyje „Naršyklės nustatymai“."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Neleisti automatinio pildymo"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Privatumas ir sauga"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Išvalyti talpyklą"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Išvalyti vietinėje talpykloje saugomą turinį ir duomenis"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Vietinėje talpykloje saugomas turinys ir duomenys bus ištrinti."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Slapukai"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Išvalyti visus slapukų duomenis"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Išvalyti visus naršyklės slapukus"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Bus ištrinti visi slapukai."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Išvalyti istoriją"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Išvalyti naršyklės naršymo istoriją"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Bus ištrinta naršyklės navigacijos istorija."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Formos duomenys"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Išvalyti formos duomenis"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Išvalyti visus išsaugotus formos duomenis"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Bus ištrinti visi išsaugoti formos duomenys."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Išvalyti slaptažodžius"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Išvalyti visus išsaugotus slaptažodžius"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Visi išsaugoti slaptažodžiai bus ištrinti."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Vieta"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Įgalinti vietą"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Leisti svetainėms teikti užklausas dėl prieigos prie jūsų vietovės"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Išvalyti prieigą prie vietos"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Išvalyti visų svetainių vietų prieigą"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Išvalyti visų svetainių vietų prieigą"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Saugos nustatymai"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Slaptažodžiai"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Atsiminti slaptažodžius"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Išsaugoti svetainių naudotojų vardus ir slaptažodžius"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Atsiminti formos duomenis"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Numatytasis mastelio keitimas"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Atidaryti puslapius apžvalgai"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Rodyti naujai atidarytų puslapių apžvalgas"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Išplėstiniai nustatymai"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Išplėstinis"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Svetainės nustatymai"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Išplėstiniai atskirų svetainių nustatymai"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Iš naujo nustatyti numatytuosius nustatymus"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Nustatyti iš naujo į numatytuosius nustatymus"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Atkurti numatytuosius nustatymus"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Nustatymai bus grąžinti į numatytąsias vertes."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"Japonų (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japonų (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japonų (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Korėjiečių (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Teksto koduotė"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Laboratorijos"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Spartieji valdikliai"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Braukite nykščiu iš kairiojo ar dešiniojo krašto, kad pasiektumėte sparč. vald."</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Lankomiausias pagrindinis puslapis"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Nustatoma, kad pagrindiniame puslapyje būtų rodomi lankomiausi puslapiai."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Duomenų jungiamumo problema"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Failo problema"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Patvirtinti"</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Ištrinti visus duomenis"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Atšaukti"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Nustatomas darbalaukio fonas..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Žymės"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Nėra žymių"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Pasirinkite paskyrą"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sinchron. su „Google“ paskyra"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"„Android“ žymės nėra susietos su „Google“ paskyra"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Pašalinti „Android“ žymes"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Pridėkite „Android“ žymes prie <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g> žymių"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Bendrinti"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Daugiau galimų skirtukų nėra"</string>
</resources>
diff --git a/res/values-lv-xlarge/strings.xml b/res/values-lv-xlarge/strings.xml
new file mode 100644
index 0000000..75c6059
--- /dev/null
+++ b/res/values-lv-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Jauna cilne"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Jauna inkognito cilne"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Cilnes"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Atvērt jaunā cilnē"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Atvērt jaunā fona cilnē"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Atvērt visas jaunās cilnēs"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Atvērt jaunas cilnes aiz pašreizējās"</string>
+</resources>
diff --git a/res/values-lv/strings.xml b/res/values-lv/strings.xml
index 1167768..277d82b 100644
--- a/res/values-lv/strings.xml
+++ b/res/values-lv/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Pārlūkprogramma"</string>
<string name="choose_upload" msgid="3649366287575002063">"Izvēlieties augšupielādējamo failu"</string>
<string name="new_tab" msgid="4505722538297295141">"Jauns logs"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Jauns inkognito logs"</string>
<string name="active_tabs" msgid="3050623868203544623">"Logi"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Grāmatzīmes"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Visvairāk apmeklētās"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Pārlūkprogramma"</string>
<string name="cancel" msgid="3017274947407233702">"Atcelt"</string>
<string name="ok" msgid="1509280796718850364">"Labi"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Nav nevienas atbilstības."</item>
- <item quantity="one" msgid="4352019729062956802">"1 atbilstība"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> atbilstības"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> atbilstība(-as)"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Notiek ielāde…"</string>
<string name="page_info" msgid="4048529256302257195">"Lapas informācija"</string>
<string name="page_info_view" msgid="5303490449842635158">"Skatīt lapas informāciju"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Turpināt"</string>
<string name="security_warning" msgid="6607795404322797541">"Drošības brīdinājums"</string>
<string name="view_certificate" msgid="1472768887529093862">"Skatīt sertifikātu"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Atpakaļ"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Šo sertifikātu nav izsniegusi uzticama iestāde."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Vietnes nosaukums neatbilst nosaukumam sertifikātā."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Šī sertifikāta derīguma termiņš ir beidzies."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"Tālāk"</string>
<string name="save" msgid="5922311934992468496">"Labi"</string>
<string name="do_not_save" msgid="6777633870113477714">"Atcelt"</string>
- <string name="location" msgid="969988560160364559">"Atrašanās vieta"</string>
- <string name="name" msgid="5990326151488445481">"Nosaukums"</string>
+ <string name="location" msgid="3411848697912600125">"Adrese"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Pievienot:"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Jauna mape"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Rediģēt mapi"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Dzēst mapi"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Nav apakšmapju"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Grāmatzīmes"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Sākuma ekrāns"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Cita mape..."</string>
+ <string name="name" msgid="5462672162695365387">"Iezīmēt"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Pievienot grāmatzīmi"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Pievienot grāmatzīmēm"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Saglabāt šo lapu kā grāmatzīmi"</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"Rediģēt grāmatzīmi"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Pievienot saīsni uz sākuma ekrānu"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Pievienot saīsni uz sākumu"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Atvērt"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Dzēst grāmatzīmi"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Noņemt no grāmatzīmēm"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Šo URL nevar atzīmēt ar grāmatzīmi."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Dzēst"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Atzīmēt ar grāmatzīmi pēdējo skatīto lapu"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Sīktēlu skatījums"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Saraksta skatījums"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Sīktēli"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Saraksts"</string>
<string name="current_page" msgid="7510129573681663135">"no "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Grāmatzīme “<xliff:g id="BOOKMARK">%s</xliff:g>” tiks dzēsta."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Atvērt jaunā logā"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Atvērt visas jaunos logos"</string>
<string name="goto_dot" msgid="3895839050522602723">"Sākt"</string>
- <string name="find_dot" msgid="6259312434696611957">"Atrast lapā"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Atvērt jaunu inkognito cilni"</string>
<string name="select_dot" msgid="6299170761900561967">"Atlasīt tekstu"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Pašreizējie logi"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Aizvērt"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Lejupielādes"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Kopēt lapas URL"</string>
<string name="share_page" msgid="593756995297268343">"Kopīgot lapu"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Saglabāt kā tīmekļa arhīvu"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Tīmekļa arhīvs ir saglabāts."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Neizdevās saglabāt tīmekļa arhīvu."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> grāmatzīmes"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Tukša mape"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Atvērt"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Atvērt jaunā logā"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Atzīmēt saiti ar grāmatzīmi"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Atvērt jaunā fona logā"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Saglabāt saiti"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Kopīgot saiti"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopēt"</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Iestatīt mājaslapu"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Iestatīt meklētājprogrammu"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Atlasīt meklētājprogrammu"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Izmantot pašreizējo lapu"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Iestatīt uz…"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Pašreizējā lapa"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Tukša lapa"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Noklusējuma lapa"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Automātiski pielāgot lapas"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Formatēt tīmekļa lapas, lai tās ietilptu ekrānā"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Attēlot tikai ainavorientācijā"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Attēlot lapas tikai plašajā ekrāna ainavorientācijā."</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Konfidencialitātes iestatījumi"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Vispārīgi"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sinhronizācija"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Automātiskā aizpilde"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sinhronizēt ar Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Kopīgot grāmatzīmes un citus datus Android pārlūkprogrammā un pārlūkprogrammā Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google konts"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sinhronizēt grāmatzīmes"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sinhronizēt Android pārlūkprogrammas un Google Chrome grāmatzīmes"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Sākt sinhronizāciju"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Kopīg. Google konts"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Veidot automātisko aizpildi"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Tīmekļa veidlapas aizpildīšana ar vienu klikšķi"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Autom. aizpildes iestatījumi"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Iestatīt un pārvaldīt automātiski aizpildīto veidlapu datus"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Autom. pierakst. vietnē Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Netika atrasts neviens konts."</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Automātiski pierakstieties Google vietnēs, izmantojot <xliff:g id="ID_1">%s</xliff:g>."</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Pierakstīšanās Google vietnēs, izmantojot <xliff:g id="ID_1">%s</xliff:g>"\n" Jūsu konfidencialitātes un drošības iestatījumi nosaka automātisko pierakstīšanos Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Nepierakstīties automātiski"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Automātiskās aizpildes funkcija izmantos profilā sniegto informāciju, lai ātri aizpildītu tīmekļa veidlapas."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Vārds, uzvārds:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-pasta adrese:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Uzņēmuma nosaukums:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Adreses 1. rindiņa:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Ielas adrese, pastkastītes numurs, c/o"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Adreses 2. rindiņa:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Dzīvoklis, numurs, korpuss, ēka, stāvs, adresāts"</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Pilsēta:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Štats/province/reģions:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Pasta indekss:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Valsts:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Tālrunis:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Nepareizs tālruņa numurs"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Saglabāt profilu"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profils ir saglabāts"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profils ir dzēsts"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Dzēst profilu"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Pārlūkprogramma var automātiski aizpildīt šāda veida tīmekļa veidlapas. Vai vēlaties iestatīt savu profilu?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Automātisko aizpildi var konfigurēt jebkurā laikā, izmantojot pārlūkprogrammas iestatījumus."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Atspējot automātisko aizpildi"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Konfidencialitāte un drošība"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Notīrīt kešatmiņu"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Notīrīt lokālajā kešatmiņā saglabāto saturu un datu bāzes"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Lokālajā kešatmiņā ievietots saturs un datu bāzes tiks dzēstas."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Sīkfaili"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Notīrīt visus sīkfailu datus"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Notīrīt visus pārlūkprogrammas sīkfailus"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Visi sīkfaili tiks dzēsti."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Notīrīt vēsturi"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Notīrīt pārlūkprogrammas navigācijas vēsturi"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Pārlūkprogrammas navigācijas vēsture tiks dzēsta."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Veidlapas dati"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Notīrīt veidlapu datus"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Notīrīt visus saglabātos veidlapu datus"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Visi saglabātie veidlapu dati tiks dzēsti."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Notīrīt paroles"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Notīrīt visas saglabātās paroles"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Visas saglabātās paroles tiks dzēstas."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Atrašanās vieta"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Iespējot atrašanās vietu"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Atļaut vietnēm pieprasīt piekļuvi jūsu atrašanās vietai"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Atrašanās vietas piekļuves atļaujas notīrīšana"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Notīrīt atrašanās vietas piekļuves atļauju visām vietnēm"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Notīrīt atrašanās vietas piekļuves atļauju visām vietnēm"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Drošības iestatījumi"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Paroles"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Atcerēties paroles"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Saglabāt vietņu lietotājvārdus un paroles"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Atcerēties veidlapu datus"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Noklusējuma tālummaiņa"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Atvērt lapas kā pārskatus"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Rādīt tikko atvērtu lapu pārskatu"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Papildu iestatījumi"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Papildu"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Vietnes iestatījumi"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Atsevišķām vietnēm paredzēti papildu iestatījumi"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Noklusējuma vērtību atiestatīšana"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Atiestatīt noklusējuma vērtības"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Atjaunot noklusējuma iestatījumus"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Tiks atjaunotas iestatījumu noklusējuma vērtības."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"Japāņu (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japāņu (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japāņu (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Korejiešu (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Teksta kodējums"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Laboratorijas"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Ātrās vadīklas"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Lai piekļūtu ātrajām vadīklām, velciet īkšķi no kreisās malas uz labo."</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Visvairāk apmeklētā mājaslapa"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Iestata mājaslapu, lai tiktu parādītas visvairāk apmeklētās lapas."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Datu savienojamības problēma"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Faila problēma"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Apstiprināt"</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Dzēst visus datus"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Atcelt"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Notiek tapetes iestatīšana..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Grāmatzīmes"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Nav nevienas grāmatzīmes."</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Konta izvēle"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sinhronizācija ar Google kontu"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Jūsu Android grāmatzīmes nav saistītas ar jūsu Google kontu."</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Noņemt Android grāmatzīmes"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Pievienot Android grāmatzīmes konta <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g> grāmatzīmēm"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Kopīgot"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Vairs nav pieejamu ciļņu"</string>
</resources>
diff --git a/res/values-nb-xlarge/strings.xml b/res/values-nb-xlarge/strings.xml
new file mode 100644
index 0000000..67ab1b6
--- /dev/null
+++ b/res/values-nb-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Ny fane"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Ny inkognitofane"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Faner"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Åpne i ny fane"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Åpne i ny bakgrunnsfane"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Åpne alle i nye faner"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Åpne nye faner bak den gjeldende"</string>
+</resources>
diff --git a/res/values-nb/strings.xml b/res/values-nb/strings.xml
index 34947fe..0584755 100644
--- a/res/values-nb/strings.xml
+++ b/res/values-nb/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Nettleser"</string>
<string name="choose_upload" msgid="3649366287575002063">"Velg fil for opplasting"</string>
<string name="new_tab" msgid="4505722538297295141">"Ny fane"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nytt inkognitovindu"</string>
<string name="active_tabs" msgid="3050623868203544623">"Vinduer"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Bokmerker"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Mest besøkt"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Nettleser"</string>
<string name="cancel" msgid="3017274947407233702">"Avbryt"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Ingen treff"</item>
- <item quantity="one" msgid="4352019729062956802">"Ett treff"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> treff"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> treff"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Laster inn ..."</string>
<string name="page_info" msgid="4048529256302257195">"Sideinfo"</string>
<string name="page_info_view" msgid="5303490449842635158">"Vis sideinformasjon"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Fortsett"</string>
<string name="security_warning" msgid="6607795404322797541">"Sikkerhetsadvarsel"</string>
<string name="view_certificate" msgid="1472768887529093862">"Vis sertifikat"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Tilbake"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Dette sertifikatet er ikke fra en autoritet du stoler på."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Navnet på siden stemmer ikke med navnet på sertifikatet."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Sertifikatet er utløpt."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Fremover"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Avbryt"</string>
- <string name="location" msgid="969988560160364559">"Adresse"</string>
- <string name="name" msgid="5990326151488445481">"Navn"</string>
+ <string name="location" msgid="3411848697912600125">"Adresse"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Legg til i"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Ny mappe"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Rediger mappe"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Slett mappe"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Ingen undermapper"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Bokmerker"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Startside"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Annen mappe"</string>
+ <string name="name" msgid="5462672162695365387">"Etikett"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Legg til bokmerke"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Legg til i bokmerker"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Bokmerk denne siden"</string>
+ <string name="remove" msgid="7820112494467011374">"Fjern"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Rediger bokmerke"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Lag snarvei på skrivebordet"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Legg til snarvei til startside"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Åpne"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Slett bokmerke"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Fjern fra bokmerker"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Kan ikke legge til et bokmerke for denne nettadressen."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Slett"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Bokmerk sist viste side"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Miniatyrbildevisning"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Listevisning"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniatyrbilder"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Liste"</string>
<string name="current_page" msgid="7510129573681663135">"fra "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Bokmerket \"<xliff:g id="BOOKMARK">%s</xliff:g>\" vil bli slettet."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Åpne i nytt vindu"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Åpne alle i nye vinduer"</string>
<string name="goto_dot" msgid="3895839050522602723">"Gå til"</string>
- <string name="find_dot" msgid="6259312434696611957">"Finn på siden"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Åpne ny inkognitofane"</string>
<string name="select_dot" msgid="6299170761900561967">"Velg tekst"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Gjeldende vinduer"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Lukk"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Nedlastinger"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Kopier nettstedsadresse"</string>
<string name="share_page" msgid="593756995297268343">"Del side"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Lagre som nettarkiv"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Nettarkiv lagret."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Kunne ikke lagre nettarkivet."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> bokmerker"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Tøm mappe"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Åpne"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Åpne i nytt vindu"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Bokmerk kobling"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Åpne melding i nytt bakgrunnsvindu"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Lagre kobling"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Del kobling"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopier"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Angi startside"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Angi søkemotor"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Velg en søkemotor"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Bruk nåværende side"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Satt til"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Gjeldende side"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Tom side"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Standardside"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Tilpass sider automatisk"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Tilpass nettsteder til skjermen"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Bare liggende visning"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Les alltid sider i bred, liggende skjermretning"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Personvernsinnstillinger"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Generelt"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Synkronisering"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Autofyll"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synkroniser med Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Lagre bokmerker og andre data mellom Android-nettleseren og Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google-konto"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synkroniser bokmerker"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synkroniser bokmerker mellom Android-nettleseren og Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Start synkronisering"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Velg kto. å dele med"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Autoutfylling av skjemaer"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Fyll ut nettskjemaer med ett enkelt klikk"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Innstillinger for autofyll"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Konfigurer og vedlikehold data for automatisk utfylte skjemaer"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Automatisk Google-pålogging"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Finner ingen kontoer"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Logg deg på Google-nettsteder automatisk ved å bruke <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Pålogging for Google-nettsteder med <xliff:g id="ID_1">%s</xliff:g>"\n"dine innstillinger for personvern og sikkerhet styrer automatisk Google-pålogging"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Ikke logg deg på automatisk"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Autofyll bruker din profil til å hjelpe deg med å fullføre nettskjemaer ved hjelp av ett enkelt klikk."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Fullt navn:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-post:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Firmanavn:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Adresselinje 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Gateadresse, postboksadresse, c/o-adresse"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Adresselinje 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Leilighet, suite, enhet, bygning, etasje osv."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Poststed:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Delstat/provins/område:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Postnummer:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Land:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Ugyldig telefonnummer"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Lagre profil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profilen er lagret"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profilen ble slettet"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Slett profil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Nettleseren kan automatisk fylle ut slike nettskjemaer. Vil du konfigurere profilen din?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Autofyll kan alltid konfigureres via Nettleserinnstillinger."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Deaktiver Autofyll"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Personvern og sikkerhet"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Fjern hurtiglager"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Fjern lokalt bufret innhold og databaser"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Lokalt bufret innhold og databaser vil bli fjernet."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Informasjonskapsler"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Fjern alle infokapsler"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Fjern alle informasjonskapsler"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Alle informasjonskapsler vil bli slettet."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Slett loggen"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Slett navigeringsloggen"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Nettleserens navigeringslogg vil bli slettet."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Skjemadata"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Fjern skjemadata"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Slett alle lagrede skjemadata"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Alle lagrede skjemadata vil bli slettet."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Fjern passord"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Fjern alle lagrede passord"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Alle lagrede passord vil bli slettet."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Posisjon"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Aktiver posisjon"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"La nettsteder be om tilgang til posisjonen din"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Deaktiver posisjonstilgang"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Deaktiver posisjonstilgang for alle nettsteder"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Deaktiver posisjonstilgang for alle nettsteder"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Sikkerhetsinnstillinger"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Passord"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Husk passord"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Lagre brukernavn og passord for nettsteder"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Husk skjemadata"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Standardzoom"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Når en side lastes inn:"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Vis oversikt over siden"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Avanserte innstillinger"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Avansert"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Nettstedsinnstillinger"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Avanserte innstillinger for individuelle nettsteder"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Tilbakestill standardinnstillinger"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Tilbakestill til standard"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Gjenoppretter til standardinnstillinger"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Tilbakestiller innstillingene til standardverdier."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japansk (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japansk (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japansk (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Koreansk (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Tekstkoding"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Prøvefunksjoner"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Hurtigkontroller"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Sveip tommelen fra venstre el. høyre kant for å få tilgang til hurtigkontroller"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Mest besøkte startside"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Angir at hjemmesiden din skal vise de mest besøkte sidene."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Datatilkoblingsproblem"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problem med fil"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Bekreft"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Slett alle data"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Avbryt"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Angir bakgrunn ..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Bokmerker"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Det er ingen bokmerker"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Velg konto"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synkroniser med Google-konto"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Dine Android-bokmerker er ikke tilknyttet en Google-konto"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Fjern Android-bokmerkene"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Legg til Android-bokmerker i bokmerker for <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Del"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Ingen flere faner tilgjengelig"</string>
</resources>
diff --git a/res/values-nl-xlarge/strings.xml b/res/values-nl-xlarge/strings.xml
new file mode 100644
index 0000000..ea78890
--- /dev/null
+++ b/res/values-nl-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Nieuw tabblad"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Nieuw incognitotabblad"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Tabbladen"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Openen op nieuw tabblad"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Openen op een nieuw tabblad op de achtergrond"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Alle bladwijzers openen op nieuwe tabbladen"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Nieuwe tabbladen openen achter het huidige tabblad"</string>
+</resources>
diff --git a/res/values-nl/strings.xml b/res/values-nl/strings.xml
index a3b0034..6152107 100644
--- a/res/values-nl/strings.xml
+++ b/res/values-nl/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Browser"</string>
<string name="choose_upload" msgid="3649366287575002063">"Bestand selecteren voor uploaden"</string>
<string name="new_tab" msgid="4505722538297295141">"Nieuw venster"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nieuw incognitovenster"</string>
<string name="active_tabs" msgid="3050623868203544623">"Vensters"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Bladwijzers"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Meest bezocht"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Browser"</string>
<string name="cancel" msgid="3017274947407233702">"Annuleren"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Geen overeenkomsten"</item>
- <item quantity="one" msgid="4352019729062956802">"1 overeenkomst"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> overeenkomsten"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> overeenkomsten"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Laden..."</string>
<string name="page_info" msgid="4048529256302257195">"Pagina-informatie"</string>
<string name="page_info_view" msgid="5303490449842635158">"Pagina-informatie weergeven"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Doorgaan"</string>
<string name="security_warning" msgid="6607795404322797541">"Beveiligingsmelding"</string>
<string name="view_certificate" msgid="1472768887529093862">"Certificaat weergeven"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Ga terug"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Dit is geen certificaat van een vertrouwde autoriteit."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"De naam van deze site komt niet overeen met de naam op het certificaat."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Dit certificaat is verlopen."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Volgende"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Annuleren"</string>
- <string name="location" msgid="969988560160364559">"Locatie"</string>
- <string name="name" msgid="5990326151488445481">"Naam"</string>
+ <string name="location" msgid="3411848697912600125">"Adres"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Toevoegen aan"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Nieuwe map"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Map bewerken"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Map verwijderen"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Geen submappen"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Bladwijzers"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Startscherm"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Andere map..."</string>
+ <string name="name" msgid="5462672162695365387">"Label"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Bladwijzer toevoegen"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Toevoegen aan bladwijzers"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Bladwijzer instellen voor deze pagina"</string>
+ <string name="remove" msgid="7820112494467011374">"Verwijderen"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Bladwijzer bewerken"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Snelkoppeling naar startpagina toevoegen"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Snelkoppeling naar startpagina toevoegen"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Openen"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Bladwijzer verwijderen"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Verwijderen uit bladwijzers"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"U kunt geen bladwijzer instellen voor deze URL."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Verwijderen"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Bladwijzer voor laatst weergegeven pagina"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Miniatuurweergave"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Lijstweergave"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniaturen"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Lijst"</string>
<string name="current_page" msgid="7510129573681663135">"van "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Bladwijzer \'<xliff:g id="BOOKMARK">%s</xliff:g>\' wordt verwijderd."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Openen in een nieuw venster"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Alle bladwijzers openen in nieuwe vensters"</string>
<string name="goto_dot" msgid="3895839050522602723">"Ga"</string>
- <string name="find_dot" msgid="6259312434696611957">"Zoeken op pagina"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Nieuw incognitotabblad openen"</string>
<string name="select_dot" msgid="6299170761900561967">"Tekst selecteren"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Huidige vensters"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Sluiten"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Downloads"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Pagina-URL kopiëren"</string>
<string name="share_page" msgid="593756995297268343">"Pagina delen"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Opslaan als webarchief"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Webarchief opgeslagen."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Opslaan van webarchief is mislukt."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> bladwijzers"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Lege map"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Openen"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Openen in een nieuw venster"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Bladwijzer maken van link"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Openen in een nieuw venster op de achtergrond"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Link opslaan"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Link delen"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopiëren"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Startpagina instellen"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Zoekmachine instellen"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Selecteer een zoekmachine"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Huidige pagina gebruiken"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Ingesteld op..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Huidige pagina"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Lege pagina"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Standaardpagina"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Pagina\'s passend maken"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Webpagina\'s zo indelen dat deze op het scherm passen"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Altijd liggende weergave"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Pagina\'s alleen liggend weergeven"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Privacyinstellingen"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Algemeen"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Synchronisatie"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Automatisch aanvullen"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synchroniseren met Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Bladwijzers en andere gegevens delen tussen Android Browser en Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google-account"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Bladwijzers synchroniseren"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Bladwijzers synchroniseren tussen Android Browser en Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Synchr. starten"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Selecteer Google-account voor delen"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Formulieren autom. aanvullen"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Webformulier invullen met één klik"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Instellingen voor auto-aanvullen"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Gegevens instellen en beheren voor automatisch ingevulde formulieren"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Automatische Google-aanmelding"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Geen accounts gevonden"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Automatisch aanmelden bij Google-sites met <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Aanmelden bij Google-sites met <xliff:g id="ID_1">%s</xliff:g>"\n"Uw instellingen voor Privacy en beveiliging zijn van toepassing op uw automatische Google-aanmelding"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Niet automatisch aanmelden"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Automatisch aanvullen gebruikt uw profiel om u te helpen met één klik formulieren in te vullen."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Volledige naam:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-mail:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Bedrijfsnaam:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Adresregel 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Adres, postbus, t.a.v."</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Adresregel 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Appartement, suite, afdeling, gebouw, etage, enz."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Plaats:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Provincie/staat/regio:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Postcode:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Land:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefoon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Ongeldig telefoonnummer"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Profiel opslaan"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profiel opgeslagen"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profiel verwijderd"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Profiel verwijderen"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"De browser kan webformulieren zoals dit formulier automatisch invullen. Wilt u uw profiel instellen?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"U kunt Automatisch aanvullen altijd configureren via de browserinstellingen."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Automatisch aanvullen uitschakelen"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Privacy en beveiliging"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Cache wissen"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Lokaal opgeslagen inhoud en databases wissen"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Lokaal opgeslagen inhoud en databases worden gewist."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookies"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Alle cookiedata wissen"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Alle browsercookies wissen"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Alle cookies worden gewist."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Geschiedenis wissen"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Navigatiegeschiedenis van de browser wissen"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"De navigatiegeschiedenis van de browser wordt gewist."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Formuliergegevens"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Formulierdata wissen"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Alle opgeslagen formuliergegevens wissen"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Alle opgeslagen formuliergegevens worden gewist."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Wachtwoorden wissen"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Alle opgeslagen wachtwoorden wissen"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Alle opgeslagen wachtwoorden worden gewist."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Locatie"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Locatie inschakelen"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Sites toestaan om toegang te vragen tot uw locatie"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Locatietoegang stoppen"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Locatietoegang voor alle websites ongedaan maken"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Locatietoegang voor alle websites ongedaan maken"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Beveiligingsinstellingen"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Wachtwoorden"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Wachtwoorden opslaan"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Gebruikersnamen en wachtwoorden voor websites opslaan"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Formulierdata onthouden"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Standaardzoom"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Paginaoverzicht"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Overzicht weergeven van pas geopende pagina\'s"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Geavanceerde instellingen"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Geavanceerd"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Website-instellingen"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Geavanceerde instellingen voor afzonderlijke websites"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Standaardinstellingen herstellen"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Standaardinstellingen"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Standaardinstellingen terugzetten"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"De instellingen worden teruggezet op de standaardwaarden."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japans (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japans (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japans (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Koreaans (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Tekstcodering"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Quick Controls"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Veeg met uw duim van de linker- of rechterkant voor toegang tot Quick Controls"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Most Visited Homepage"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Stelt uw startpagina in op het weergeven van de meest bezochte pagina\'s."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Probleem met gegevensverbinding"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Probleem met bestand"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Bevestigen"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Alle gegevens wissen"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Annuleren"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Achtergrond instellen..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Bladwijzers"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Er zijn geen bladwijzers"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"J1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Account selecteren"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synchroniseren met Google-account"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Uw Android-bladwijzers zijn niet gekoppeld aan een Google-account"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Uw Android-bladwijzers verwijderen"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Uw Android-bladwijzers toevoegen aan bladwijzers voor <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Delen"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Er zijn niet meer tabbladen beschikbaar"</string>
</resources>
diff --git a/res/values-pl-xlarge/strings.xml b/res/values-pl-xlarge/strings.xml
new file mode 100644
index 0000000..d5fe8e5
--- /dev/null
+++ b/res/values-pl-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Nowa karta"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Nowa karta incognito"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Karty"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Otwórz w nowej karcie"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Otwórz w nowej karcie tła"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Otwórz wszystkie w nowych kartach"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Otwieraj nowe karty za bieżącą"</string>
+</resources>
diff --git a/res/values-pl/strings.xml b/res/values-pl/strings.xml
index bee5c18..3f8c0fd 100644
--- a/res/values-pl/strings.xml
+++ b/res/values-pl/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Internet"</string>
<string name="choose_upload" msgid="3649366287575002063">"Wybierz plik do przesłania"</string>
<string name="new_tab" msgid="4505722538297295141">"Nowe okno"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nowe okno incognito"</string>
<string name="active_tabs" msgid="3050623868203544623">"Okna"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Zakładki"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Popularne"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Przeglądarka"</string>
<string name="cancel" msgid="3017274947407233702">"Anuluj"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Brak wyników"</item>
- <item quantity="one" msgid="4352019729062956802">"1 wynik"</item>
- <item quantity="few" msgid="5544267486978946555">"Wyników: <xliff:g id="NUMBER">%d</xliff:g>"</item>
- <item quantity="other" msgid="6616125067364315405">"Wyników: <xliff:g id="NUMBER">%d</xliff:g>"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Trwa wczytywanie..."</string>
<string name="page_info" msgid="4048529256302257195">"Informacje o stronie"</string>
<string name="page_info_view" msgid="5303490449842635158">"Informacje o stronie"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Dalej"</string>
<string name="security_warning" msgid="6607795404322797541">"Ostrzeżenie zabezpieczeń"</string>
<string name="view_certificate" msgid="1472768887529093862">"Wyświetl certyfikat"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Wróć"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Ten certyfikat nie pochodzi od zaufanego urzędu."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Nazwa witryny nie odpowiada nazwie podanej w certyfikacie."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Ten certyfikat wygasł."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Dalej"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Anuluj"</string>
- <string name="location" msgid="969988560160364559">"Adres"</string>
- <string name="name" msgid="5990326151488445481">"Nazwa"</string>
+ <string name="location" msgid="3411848697912600125">"Adres"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Dodaj do"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Nowy folder"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Edytuj folder"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Usuń folder"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Brak podfolderów"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Zakładki"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Ekran główny"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Inny folder…"</string>
+ <string name="name" msgid="5462672162695365387">"Etykieta"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Dodaj zakładkę"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Dodaj do Zakładek"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Dodaj tę stronę do zakładek"</string>
+ <string name="remove" msgid="7820112494467011374">"Usuń"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Edytuj zakładkę"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Dodaj skrót do strony głównej"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Dodaj skrót do ekranu głównego"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Otwórz"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Usuń zakładkę"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Usuń z zakładek"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Nie można dodać tego adresu URL do zakładek."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Usuń"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Dodaj do zakładek ostatnio wyświetlaną stronę"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Widok miniatur"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Widok listy"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniaturki"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Lista"</string>
<string name="current_page" msgid="7510129573681663135">"z "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Zakładka „<xliff:g id="BOOKMARK">%s</xliff:g>” zostanie usunięta."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Otwórz w nowym oknie"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Otwórz wszystkie w nowych oknach"</string>
<string name="goto_dot" msgid="3895839050522602723">"OK"</string>
- <string name="find_dot" msgid="6259312434696611957">"Znajdź na stronie"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Otwórz nową kartę incognito"</string>
<string name="select_dot" msgid="6299170761900561967">"Zaznacz tekst"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Bieżące okna"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Zamknij"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Pobrane"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Kopiuj adres URL strony"</string>
<string name="share_page" msgid="593756995297268343">"Udostępnij stronę"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Zapisz jako archiwum internetowe"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Archiwum internetowe zostało zapisane."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Nie można zapisać archiwum internetowego."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"Zakładki: <xliff:g id="BOOKMARK_COUNT">%d</xliff:g>"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Pusty folder"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Otwórz"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Otwórz w nowym oknie"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Dodaj link do zakładek"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Otwórz wiadomość w nowym oknie tła"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Zapisz link"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Udostępnij link"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopiuj"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Ustaw stronę główną"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Ustaw wyszukiwarkę"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Wybierz wyszukiwarkę"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Użyj bieżącej strony"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Ustaw"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Bieżąca strona"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Pusta strona"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Domyślna strona"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Autodopasowanie stron"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Formatuj strony internetowe w celu dopasowania do ekranu"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Zawsze w poziomie"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Wyświetlaj strony tylko w szerszej, poziomej orientacji ekranu"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Ustawienia prywatności"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Ogólne"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Synchronizacja"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Autouzupełnianie"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synchronizuj z przeglądarką Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Udostępniaj zakładki i inne dane między przeglądarką w systemie Android i przeglądarką Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Konto Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synchronizuj zakładki"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synchronizuj zakładki między przeglądarką w systemie Android i przeglądarką Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Synchronizuj"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Wybierz konto Google dla udostępniania"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Autouzupełnianie formularzy"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Wypełniaj formularze internetowe za pomocą jednego kliknięcia"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Ustawienia autouzupełniania"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Skonfiguruj dane dla automatycznie uzupełnianych formularzy i zarządzaj nimi"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Automatyczne logowanie do Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Nie znaleziono kont"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Automatycznie loguj się do witryn Google, używając konta <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Logowanie do witryn Google przy użyciu identyfikatora <xliff:g id="ID_1">%s</xliff:g>"\n"Ustawienia automatycznego logowania do Google znajdują się w sekcji Prywatność i bezpieczeństwo."</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Nie loguj automatycznie"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Twój profil będzie używany w funkcji autouzupełniania do wypełniania formularzy internetowych za pomocą jednego kliknięcia."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Imię i nazwisko:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-mail:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Nazwa firmy:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Adres, wiersz 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Adres, skrzynka pocztowa, adres korespondencyjny"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Adres, wiersz 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Mieszkanie, apartament, wydział, budynek, piętro itp."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Miasto / miejscowość:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Województwo / region:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Kod pocztowy:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Kraj:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Nieprawidłowy numer telefonu"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Zapisz profil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profil został zapisany"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profil usunięto"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Usuń profil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Takie formularze internetowe mogą być automatycznie wypełniane w przeglądarce. Czy chcesz skonfigurować swój profil?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Autouzupełnianie można zawsze skonfigurować w opcjach przeglądarki."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Wyłącz autouzupełnianie"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Prywatność i bezpieczeństwo"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Wyczyść pamięć podręczną"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Wyczyść zawartość lokalnej pamięci podręcznej i baz danych"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Zawartość lokalnej pamięci podręcznej i baz danych zostanie usunięta."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Pliki cookie"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Wyczyść pliki cookie"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Wyczyść wszystkie pliki cookie przeglądarki"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Wszystkie pliki cookie zostaną usunięte."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Wyczyść historię"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Wyczyść historię przeglądania"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Historia nawigacji w przeglądarce zostanie usunięta."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Dane formularzy"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Wyczyść dane formularzy"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Usuń wszystkie zapisane dane formularzy"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Wszystkie zapisane dane formularzy zostaną usunięte."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Wyczyść hasła"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Wyczyść wszystkie zapisane hasła"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Wszystkie zapisane hasła zostaną usunięte."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Lokalizacja"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Włącz obsługę lokalizacji"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Zezwalaj witrynom na żądanie dostępu do informacji o lokalizacji"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Wyczyść dostęp do lokalizacji"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Anuluj ustawienia dostępu do lokalizacji dla witryn"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Wyczyść ustawienia dostępu witryn do informacji o lokalizacji"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Ustawienia zabezpieczeń"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Hasła"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Pamiętaj hasła"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Zapisz nazwy użytkowników i hasła używane w witrynach"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Pamiętaj wpisane dane"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Powiększenie domyślne"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Podgląd otwartej strony"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Po otwarciu nowa strona jest widoczna na całym ekranie"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Ustawienia zaawansowane"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Zaawansowane"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Ustawienia witryn"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Ustawienia zaawansowane dla poszczególnych witryn"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Ustawienia domyślne"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Przywróć wartości domyślne"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Przywróć ustawienia domyślne"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Zostaną przywrócone wartości domyślne ustawień."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"japoński (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"japoński (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"japoński (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"koreański (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Kodowanie tekstu"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Laboratorium"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Szybkie sterowanie"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Przesuń kciukiem od lewej lub prawej krawędzi, aby przejść do szybkiego sterowania"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Strona główna Popularne"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Ustawia wyświetlanie popularnych stron na stronie głównej."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problem z łącznością danych"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problem z plikiem"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Potwierdzenie"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Usuń wszystkie dane"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Anuluj"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Trwa ustawianie tapety..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Zakładki"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Brak zakładek"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Wybierz konto"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synchronizuj z kontem Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Zakładki w systemie Android nie są powiązane z kontem Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Usuń zakładki w systemie Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Dodaj zakładki z systemu Android do zakładek na koncie <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Udostępnij"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Brak dostępnych kart"</string>
</resources>
diff --git a/res/values-pt-rPT-xlarge/strings.xml b/res/values-pt-rPT-xlarge/strings.xml
new file mode 100644
index 0000000..5c45d17
--- /dev/null
+++ b/res/values-pt-rPT-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Novo separador"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Novo sep. de navegação anónima"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Separadores"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Abrir em novo separador"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Abrir em novo separador em segundo plano"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Abrir tudo em separadores novos"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Abrir novos separadores atrás do actual"</string>
+</resources>
diff --git a/res/values-pt-rPT/strings.xml b/res/values-pt-rPT/strings.xml
index e63c7ef..5846b16 100644
--- a/res/values-pt-rPT/strings.xml
+++ b/res/values-pt-rPT/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Navegad."</string>
<string name="choose_upload" msgid="3649366287575002063">"Escolher ficheiro a carregar"</string>
<string name="new_tab" msgid="4505722538297295141">"Nova janela"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nova janela de naveg. anónima"</string>
<string name="active_tabs" msgid="3050623868203544623">"Janelas"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Marcadores"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Os mais visitados"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Navegad."</string>
<string name="cancel" msgid="3017274947407233702">"Cancelar"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Sem correspondência"</item>
- <item quantity="one" msgid="4352019729062956802">"1 correspondência"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> correspondências"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> correspondências"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"A carregar..."</string>
<string name="page_info" msgid="4048529256302257195">"Informações da página"</string>
<string name="page_info_view" msgid="5303490449842635158">"Ver informações da página"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Continuar"</string>
<string name="security_warning" msgid="6607795404322797541">"Aviso de segurança"</string>
<string name="view_certificate" msgid="1472768887529093862">"Ver certificado"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Retroceder"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Este certificado não pertence a uma autoridade fidedigna."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"O nome do site não corresponde ao nome constante no certificado."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Este certificado expirou."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Avançar"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Cancelar"</string>
- <string name="location" msgid="969988560160364559">"Local"</string>
- <string name="name" msgid="5990326151488445481">"Nome"</string>
+ <string name="location" msgid="3411848697912600125">"Endereço"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Adicionar a"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Nova pasta"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Editar pasta"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Eliminar pasta"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Não há subpastas"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Marcadores"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Ecrã principal"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Outra pasta…"</string>
+ <string name="name" msgid="5462672162695365387">"Etiqueta"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Adicionar marcador"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Adicionar aos marcadores"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Adicionar esta página aos marcadores"</string>
+ <string name="remove" msgid="7820112494467011374">"Remover"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Editar marcador"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Adicionar atalho à página inicial"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Adicionar atalho à página inicial"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Abrir"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Eliminar marcador"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Remover dos marcadores"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Este URL não pode ser adicionado aos marcadores."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Eliminar"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Adicionar aos marcadores a última página visualizada"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Vista de miniatura"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Vista de lista"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniaturas"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Lista"</string>
<string name="current_page" msgid="7510129573681663135">"de "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"O marcador \"<xliff:g id="BOOKMARK">%s</xliff:g>\" será eliminado."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Abrir numa janela nova"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Abrir tudo em janelas novas"</string>
<string name="goto_dot" msgid="3895839050522602723">"Ir"</string>
- <string name="find_dot" msgid="6259312434696611957">"Encontrar na página"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Abrir novo separador de navegação anónima"</string>
<string name="select_dot" msgid="6299170761900561967">"Seleccionar texto"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Janelas actuais"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Fechar"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Transferências"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Copiar URL da página"</string>
<string name="share_page" msgid="593756995297268343">"Partilhar página"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Guardar como arquivo Web"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Arquivo Web guardado."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Não foi possível guardar o arquivo Web."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> marcadores"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Pasta vazia"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Abrir"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Abrir numa janela nova"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Adicionar link aos marcadores"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Abrir em nova janela em segundo plano"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Guardar link"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Partilhar link"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Copiar"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Definir página inicial"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Definir motor de pesquisa"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Seleccionar um motor de pesquisa"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Utilizar página actual"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Definido para..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Página actual"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Página em branco"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Página predefinida"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Ajuste auto de páginas"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Formatar páginas Web para se ajustarem ao ecrã"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Apresentação apenas na horizontal"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Mostrar páginas só na orientação horizontal do ecrã (mais larga)"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Definições de privacidade"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Gerais"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sincronizar"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Preenchimento automático"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sincronizar com o Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Partilhar marcadores e outros dados entre o navegador do Android e o Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Conta Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sincronizar marcadores"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sincronizar marcadores entre o navegador do Android e o Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Inic. sincronização"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Selec. conta Google p/ partilhar c/"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Preench. autom. do formulário"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Preencher formulários Web com um único clique"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Def. do preenchimento automático"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Configurar e gerir dados para formulários preenchidos automaticamente"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Início sessão automático Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Nenhuma conta encontrada"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Iniciar sessão automaticamente nos Web sites da Google utilizando <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Iniciar sessão em sites Google utilizando <xliff:g id="ID_1">%s</xliff:g>"\n"o início de sessão automático do Google do controlo de definições de Privacidade e Segurança"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Não iniciar sessão automaticamente"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"O preenchimento automático vai utilizar o seu perfil para o ajudar a preencher formulários Web com um único clique."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Nome completo:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-mail:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Nome da empresa:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Linha de endereço 1"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Endereço, caixa postal, c/o"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Linha de endereço 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Apartamento, suite, unidade, edifício, piso, etc."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Cidade/Vila:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Estado / Província / Região:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Código postal:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"País:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefone:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Número de telefone inválido"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Guardar perfil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Perfil guardado"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Perfil eliminado"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Eliminar perfil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"O navegador pode preencher automaticamente os formulários Web deste tipo. Pretende configurar o seu perfil?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"O Preenchimento automático pode sempre ser configurado através das Definições do navegador."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Desactivar preenchimento automático"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Privacidade e segurança"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Limpar cache"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Limpar bases de dados e conteúdos colocados em cache localmente"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"As bases de dados e os conteúdos colocados em cache localmente serão eliminados."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookies"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Limpar os dados de cookies"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Limpar todos os cookies do browser"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Todos os cookies serão eliminados."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Limpar histórico"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Limpar o histórico de navegação do browser"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"O histórico de navegação do browser será eliminado."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Dados do formulário"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Limpar dados de formulário"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Limpar todos os dados de formulário guardados"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Todos os dados de formulário guardados serão eliminados."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Limpar palavras-passe"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Limpar todas as palavras-passe guardadas"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Todas as palavras-passe guardadas serão eliminadas."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Localização"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Activar localização"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Permitir que os sites solicitem acesso à sua localização"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Limpar acesso à localização"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Limpar acesso à localização para todos os Web sites"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Limpar o acesso à localização para todos os Web sites"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Definições de segurança"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Palavras-passe"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Lembrar palavras-passe"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Guardar nomes de utilizador e palavras-passe de Web sites"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Lembrar dados formulário"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Zoom predefinido"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Abrir páginas na vista geral"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Mostrar descrição geral de páginas abertas recentemente"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Definições avançadas"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Avançadas"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Definições de Web site"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Definições avançadas para Web sites individuais"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Repor predefinições"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Repor as predefinições"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Restaurar predefinições"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"As definições assumirão os valores predefinidos."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japonês (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japonês (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japonês (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Coreano (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codificação do texto"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Controlos rápidos"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Passe o polegar na margem esquerda ou direita para aceder aos controlos rápidos"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Página inicial mais visitada"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Define a sua página inicial para mostrar as páginas mais visitadas."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problema de conectividade de dados"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problemas com o ficheiro"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Confirmar"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Eliminar todos os dados"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Cancelar"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"A definir imagem de fundo..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Marcadores"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Não existem marcadores"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Escolher conta"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sincronizar com conta Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Os seus marcadores do Android não estão associados a uma conta Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Remover marcadores do Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Adicionar os seus marcadores do Android aos marcadores da <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Partilhar"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Atingiu o limite de separadores"</string>
</resources>
diff --git a/res/values-pt-xlarge/strings.xml b/res/values-pt-xlarge/strings.xml
new file mode 100644
index 0000000..73dfece
--- /dev/null
+++ b/res/values-pt-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Nova guia"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Nova guia anônima"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Guias"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Abrir em uma nova guia"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Abrir em uma nova guia em segundo plano"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Abrir todos em novas abas"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Abrir novas guias atrás da guia atual"</string>
+</resources>
diff --git a/res/values-pt/strings.xml b/res/values-pt/strings.xml
index c25e758..86ddbff 100644
--- a/res/values-pt/strings.xml
+++ b/res/values-pt/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Navegador"</string>
<string name="choose_upload" msgid="3649366287575002063">"Escolha o arquivo para envio"</string>
<string name="new_tab" msgid="4505722538297295141">"Nova janela"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nova janela anônima"</string>
<string name="active_tabs" msgid="3050623868203544623">"Janelas"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Favoritos"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Mais visitados"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Navegador"</string>
<string name="cancel" msgid="3017274947407233702">"Cancelar"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Sem correspondências"</item>
- <item quantity="one" msgid="4352019729062956802">"1 correspondência"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> correspondências"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> correspondências"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Carregando..."</string>
<string name="page_info" msgid="4048529256302257195">"Informações da página"</string>
<string name="page_info_view" msgid="5303490449842635158">"Visualizar informações da página"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Continuar"</string>
<string name="security_warning" msgid="6607795404322797541">"Aviso de segurança"</string>
<string name="view_certificate" msgid="1472768887529093862">"Visualizar certificado"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Voltar"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Este certificado não é de uma autoridade confiável."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"O nome do site não corresponde ao nome no certificado."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Este certificado expirou."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Avançar"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Cancelar"</string>
- <string name="location" msgid="969988560160364559">"Local"</string>
- <string name="name" msgid="5990326151488445481">"Nome"</string>
+ <string name="location" msgid="3411848697912600125">"Endereço"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Adicionar a"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Nova pasta"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Editar pasta"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Excluir pasta"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Nenhuma subpasta"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Favoritos"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Tela inicial"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Outra pasta…"</string>
+ <string name="name" msgid="5462672162695365387">"Marcador"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Adicionar favorito"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Adicionar aos favoritos"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Adicionar esta página aos favoritos"</string>
+ <string name="remove" msgid="7820112494467011374">"Remover"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Editar favorito"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Adicionar atalho à Página inicial"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Adicionar atalho à página inicial"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Abrir"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Excluir favorito"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Remover dos favoritos"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Este URL não pode ser adicionado como favorito."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Excluir"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Adicionar última página visualizada aos favoritos"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Visualização em miniatura"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Visualização em lista"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniaturas"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Lista"</string>
<string name="current_page" msgid="7510129573681663135">"de "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"O favorito \"<xliff:g id="BOOKMARK">%s</xliff:g>\" será excluído."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Abrir em uma nova janela"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Abrir todos em novas janelas"</string>
<string name="goto_dot" msgid="3895839050522602723">"Ir"</string>
- <string name="find_dot" msgid="6259312434696611957">"Localizar na página"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Abrir nova guia anônima"</string>
<string name="select_dot" msgid="6299170761900561967">"Selecionar texto"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Janelas atuais"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Fechar"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Downloads"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Copiar URL da página"</string>
<string name="share_page" msgid="593756995297268343">"Compartilhar página"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Salvar como arquivo da web"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Arquivo da web salvo."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Falha ao salvar arquivo da web."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> favoritos"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Pasta vazia"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Abrir"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Abrir em uma nova janela"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Link do favorito"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Abrir em uma nova janela em segundo plano"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Salvar link"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Compartilhar link"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Copiar"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Definir a página inicial"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Definir mecanismo de pesquisa"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Selecionar um mecanismo de pesquisa"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Usar a página atual"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Definir para..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Página atual"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Página em branco"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Página padrão"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Ajustar automaticamente"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Formatar páginas da web para se ajustarem à tela"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Apenas modo paisagem"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Exibir páginas apenas na orientação mais larga, com a tela no modo paisagem"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Configurações de privacidade"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Geral"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sincronização"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Preencher automaticamente"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sincronizar com o Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Compartilhar favoritos e outros dados entre o navegador do Android e o Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Conta do Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sincronizar favoritos"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sincronizar favoritos entre o navegador do Android e o Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Iniciar sincroniz."</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Sel. conta p/ comp."</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Preench. autom. de formulários"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Preencher formulários da web com apenas um clique"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Config. de Preench. automático"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Configurar e gerenciar os dados de formulários preenchidos automaticamente"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Login automático do Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Nenhuma conta encontrada"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Faça login automaticamente em sites do Google usando <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Fazendo login no Google Sites usando o login automático do Google de controle de configurações de <xliff:g id="ID_1">%s</xliff:g>"\n"Privacidade e Segurança &"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Não fazer login automaticamente"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"O preenchimento automático usará seu perfil para ajudá-lo a preencher formulários na web com um único clique."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Nome completo:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-mail:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Nome da empresa:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Linha de endereço 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Endereço, caixa postal, \"aos cuidados de\""</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Linha de endereço 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Apartamento, suíte, unidade, edifício, andar etc."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Cidade:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Estado/província/região:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"CEP:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"País:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefone:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Número de telefone inválido"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Salvar perfil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Perfil salvo"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Perfil excluído"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Excluir perfil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"O navegador pode preencher automaticamente formulários da web como este. Gostaria de configurar seu perfil?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"O Preenchimento automático sempre pode ser configurado através das Configurações do Navegador."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Desativar o Preenchimento automático"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Privacidade e segurança"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Limpar cache"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Limpar conteúdo e bancos de dados armazenados localmente em cache"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"O conteúdo e os bancos de dados armazenados localmente em cache serão excluídos."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookies"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Limpar dados de cookie"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Limpar todos os cookies do navegador"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Todos os cookies serão excluídos."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Limpar histórico"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Limpar o histórico de navegação do navegador"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"O histórico de navegação do navegador será excluído."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Dados do formulário"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Limpar dados de form."</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Limpar todos os dados de formulário salvos"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Todos os dados de formulário salvos serão excluídos."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Limpar senhas"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Limpar todas as senhas salvas"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Todas as senhas salvas serão excluídas."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Local"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Ativar localização"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Permitir que os sites solicitem acesso à sua localização"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Limpar acesso ao local"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Limpar acesso à localização para todos os sites"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Limpar acesso à localização para todos os sites"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Configurações de segurança"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Senhas"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Lembrar senhas"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Salvar nomes de usuário e senhas para sites"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Lembrar dados de form."</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Zoom padrão"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Abrir em visão geral"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Exibir visão geral de páginas que acabaram de ser abertas"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Configurações avançadas"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Avançado"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Configurações do site"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Configurações avançadas para sites individuais."</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Redefinir padrões"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Redefinir para o padrão"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Restaurar as configurações padrão"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"As configurações voltarão para os valores padrão."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japonês (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japonês (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japonês (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Coreano (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codificação de texto"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Google Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Controles rápidos"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Passe o polegar da margem esquerda ou direita para acessar os controles rápidos"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Página inicial mais visitada"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Definir sua página inicial para mostrar as páginas mais visitadas."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problema de conectividade de dados"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problema com o arquivo"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Confirmar"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Excluir todos os dados"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Cancelar"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Definindo o plano de fundo..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Favoritos"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Não há nenhum favorito"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Escolher conta"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sincronizar com Conta do Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Seus favoritos do Android não estão associados a uma Conta do Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Remover os favoritos do Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Adicionar favoritos do Android aos favoritos de <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Compartilhar"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Não há mais guias disponíveis"</string>
</resources>
diff --git a/res/values-rm/strings.xml b/res/values-rm/strings.xml
index ce441bf..777e778 100644
--- a/res/values-rm/strings.xml
+++ b/res/values-rm/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Navigatur"</string>
<string name="choose_upload" msgid="3649366287575002063">"Tscherner ina datoteca per importar"</string>
<string name="new_tab" msgid="4505722538297295141">"Nova fanestra"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nova fanestra incognito"</string>
<string name="active_tabs" msgid="3050623868203544623">"Fanestra"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Segnapaginas"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Visità il pli savens"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Navigatur"</string>
<string name="cancel" msgid="3017274947407233702">"Interrumper"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Naginas correspundenzas"</item>
- <item quantity="one" msgid="4352019729062956802">"1 correspundenza"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> correspundenzas"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> correspundenzas"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Chargiar…"</string>
<string name="page_info" msgid="4048529256302257195">"Infos davart la pagina"</string>
<string name="page_info_view" msgid="5303490449842635158">"Mussar las infurmaziuns da la pagina"</string>
@@ -46,6 +41,8 @@
<string name="ssl_continue" msgid="8031515015829358457">"Cuntinuar"</string>
<string name="security_warning" msgid="6607795404322797541">"Avertiment da segirezza"</string>
<string name="view_certificate" msgid="1472768887529093862">"Mussar il certificat"</string>
+ <!-- no translation found for ssl_go_back (4598951822061593819) -->
+ <skip />
<string name="ssl_untrusted" msgid="5369967226521102194">"Quest certificat n\'è betg vegnì emess dad in post da certificaziun fidà."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Il num da la website na correspunda betg al num sin il certificat."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Quest certificat è scrudà."</string>
@@ -67,12 +64,31 @@
<string name="forward" msgid="4288210890526641577">"Vinavant"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Interrumper"</string>
- <string name="location" msgid="969988560160364559">"Adressa"</string>
- <string name="name" msgid="5990326151488445481">"Num"</string>
+ <!-- outdated translation 969988560160364559 --> <string name="location" msgid="3411848697912600125">"Adressa"</string>
+ <!-- no translation found for containing_folder (6771180232953030479) -->
+ <skip />
+ <!-- no translation found for new_folder (7743540149088867917) -->
+ <skip />
+ <!-- no translation found for edit_folder (621817453133656156) -->
+ <skip />
+ <!-- no translation found for delete_folder (2046483129024501116) -->
+ <skip />
+ <!-- no translation found for no_subfolders (5880411440592452802) -->
+ <skip />
+ <!-- no translation found for add_to_bookmarks_menu_option (4449323955122214389) -->
+ <skip />
+ <!-- no translation found for add_to_homescreen_menu_option (1461447829242963790) -->
+ <skip />
+ <!-- no translation found for add_to_other_folder_menu_option (5450890093372998187) -->
+ <skip />
+ <!-- outdated translation 5990326151488445481 --> <string name="name" msgid="5462672162695365387">"Num"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Agiuntar in segnapagina"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Agiuntar als segnapaginas"</string>
+ <!-- no translation found for bookmark_this_page (7530739804320811054) -->
+ <skip />
+ <string name="remove" msgid="7820112494467011374">"Allontanar"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Modifitgar il segnapagina"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Crear scursanidas sin il visur da partenza"</string>
+ <!-- outdated translation 4528337239019328891 --> <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Agiuntar a la pagina da partenza"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Avrir"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Stizzar il segnapagina"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Stizzar dals segnapaginas"</string>
@@ -87,13 +103,17 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Impussibel d\'agiuntar questa URL a Voss segnapaginas."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Stizzar"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Segnapagina per l\'ultima pagina visitada"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Miniaturas"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Vista da glista"</string>
+ <!-- no translation found for bookmark_thumbnail_view (3164068314718522138) -->
+ <skip />
+ <!-- no translation found for bookmark_list_view (7848510619500937839) -->
+ <skip />
<string name="current_page" msgid="7510129573681663135">"da "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"\"Il segnapagina \"\"<xliff:g id="BOOKMARK">%s</xliff:g>\"\" vegn stizzà.\""</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Avrir en ina nova fanestra"</string>
+ <!-- no translation found for open_all_in_new_window (6514602245828366045) -->
+ <skip />
<string name="goto_dot" msgid="3895839050522602723">"Dai"</string>
- <string name="find_dot" msgid="6259312434696611957">"Tschertgar en la pagina:"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Avrir in nov tab incognito"</string>
<string name="select_dot" msgid="6299170761900561967">"Selecziunar text"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Fanestras actualas"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Serrar"</string>
@@ -103,9 +123,17 @@
<string name="menu_view_download" msgid="2124570321712995120">"Telechargiadas"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Copiar la URL da la pagina"</string>
<string name="share_page" msgid="593756995297268343">"Barattar la pagina"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Memorisar sco archiv web"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Memorisà archiv da web"</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Betg reussì da memorisar l\'archiv da web."</string>
+ <!-- no translation found for contextheader_folder_bookmarkcount (353987136645619089) -->
+ <skip />
+ <!-- no translation found for contextheader_folder_empty (974171637803391651) -->
+ <skip />
<string name="contextmenu_openlink" msgid="7237961252214188935">"Avrir"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Avrir en ina nova fanestra"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Agiuntar la colliaziun als segnapaginas"</string>
+ <!-- no translation found for contextmenu_openlink_newwindow_background (5556131402560251639) -->
+ <skip />
<string name="contextmenu_savelink" msgid="5508554930832538184">"Memorisar la colliaziun"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Barattar la colliaziun"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Copiar"</string>
@@ -140,33 +168,125 @@
<skip />
<!-- no translation found for pref_content_search_engine_summary (5162667665858487316) -->
<skip />
- <string name="pref_use_current" msgid="1493179933653044553">"Utilisar la pagina actuala"</string>
+ <!-- no translation found for pref_set_homepage_to (7196350233061395098) -->
+ <skip />
+ <!-- outdated translation 1493179933653044553 --> <string name="pref_use_current" msgid="1778622474040406672">"Utilisar la pagina actuala"</string>
+ <!-- no translation found for pref_use_blank (8503238592551111169) -->
+ <skip />
+ <!-- no translation found for pref_use_default (192587563274735878) -->
+ <skip />
<string name="pref_content_autofit" msgid="8260474534053660809">"Adattar las paginas auto."</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Adattar las paginas web al visur"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Visualisaziun mo en il format orizontal"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Mussar las paginas mo en il format pli lad orizontal"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Parameters da la protecziun da datas"</string>
+ <!-- no translation found for pref_general_title (1946872771219249323) -->
+ <skip />
+ <!-- no translation found for pref_general_sync_title (3138637035975860324) -->
+ <skip />
+ <!-- no translation found for pref_general_autofill_title (64638897890112873) -->
+ <skip />
+ <!-- no translation found for pref_personal_sync_with_chrome (1695182180332194033) -->
+ <skip />
+ <!-- no translation found for pref_personal_sync_with_chrome_summary (7414133931827321055) -->
+ <skip />
+ <!-- no translation found for pref_personal_google_account (952360133341490071) -->
+ <skip />
+ <!-- no translation found for pref_personal_sync_bookmarks (59237515966184432) -->
+ <skip />
+ <!-- no translation found for pref_personal_sync_bookmarks_summary (4791767605662205482) -->
+ <skip />
+ <!-- no translation found for pref_personal_start_syncing (6046972042512655232) -->
+ <skip />
+ <!-- no translation found for pref_personal_account_dialog_title (1390867119887955530) -->
+ <skip />
+ <!-- no translation found for pref_autofill_enabled (1174197447388234595) -->
+ <skip />
+ <!-- no translation found for pref_autofill_enabled_summary (422640696197018914) -->
+ <skip />
+ <!-- no translation found for pref_autofill_profile_editor (1350709161524642663) -->
+ <skip />
+ <!-- no translation found for pref_autofill_profile_editor_summary (6748434431641768870) -->
+ <skip />
+ <!-- no translation found for pref_autologin_title (2362827272595366379) -->
+ <skip />
+ <!-- no translation found for pref_autologin_no_account (4409223615542478868) -->
+ <skip />
+ <!-- no translation found for pref_autologin_summary (8168866316823968574) -->
+ <skip />
+ <!-- no translation found for pref_autologin_progress (8643826219376543293) -->
+ <skip />
+ <!-- no translation found for pref_autologin_disable (3342145058494577628) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_heading (5009490178189728877) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_name (8566130291459685955) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_email_address (7967585896612797173) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_company_name (2813443159949210417) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_address_line_1 (836433242509243081) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_address_line_1_hint (5965659598509327172) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_address_line_2 (8194745202893822479) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_address_line_2_hint (2048330295853546405) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_city (4193225955409148508) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_state (8549739922338171458) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_zip_code (283668573295656671) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_country (7234470301239156656) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_phone_number (4938852821413729276) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_phone_number_invalid (7166394872369167580) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_save_profile (8349915287435262888) -->
+ <skip />
+ <!-- no translation found for autofill_profile_successful_save (6834102203944938409) -->
+ <skip />
+ <!-- no translation found for autofill_profile_successful_delete (2421442112954362732) -->
+ <skip />
+ <!-- no translation found for autofill_profile_editor_delete_profile (2754563301088418752) -->
+ <skip />
+ <!-- no translation found for autofill_setup_dialog_message (6605682320156223114) -->
+ <skip />
+ <!-- no translation found for autofill_setup_dialog_negative_toast (4337372830506338827) -->
+ <skip />
+ <!-- no translation found for disable_autofill (3706426217720202898) -->
+ <skip />
+ <!-- no translation found for pref_privacy_security_title (1705642466867300373) -->
+ <skip />
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Stizzar il cache"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Stizzar las bancas da datas ed il cuntegn ord il cache local"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Las bancas da datas ed ils cuntegns en il cache local vegnan stizzads."</string>
+ <!-- no translation found for pref_privacy_cookies_title (6763274282214830526) -->
+ <skip />
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Stizzar tut ils cookies"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Stizzar tut ils cookies dal navigatur"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Tut ils cookies vegnan stizzads."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Stizzar la cronologia"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Stizzar la cronologia dal navigatur"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"La cronologia dal navigatur vegn stizzada."</string>
+ <!-- no translation found for pref_privacy_formdata_title (6549813837982050424) -->
+ <skip />
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Stizzar datas da formular"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Stizzar tut las datas da formular memorisadas"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Tut las datas da formulars memorisadas vegnan stizzadas."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Stizzar ils pleds-clav"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Stizzar tut ils pleds-clav memorisads"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Tut ils pleds-clav memorisads vegnan stizzads."</string>
+ <!-- no translation found for pref_privacy_location_title (7458378016606081067) -->
+ <skip />
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Activar la posiziun"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Autorisar las websites da dumandar l\'access a Vossa posiziun"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Stizzar l\'access a datas da posiziun"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Stizzar l\'access a datas da posiziun per tut las websites."</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Stizzar l\'access a datas da posiziun per tut las websites"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Parameters da segirezza"</string>
+ <!-- no translation found for pref_security_passwords_title (5734190542383756711) -->
+ <skip />
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Memorisar ils pleds-clav"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Memorisar ils nums d\'utilisader ed ils pleds-clav per las websites"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Memorisar las datas da formular"</string>
@@ -193,9 +313,11 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Zoom predefinì"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Avrir las paginas en la survista"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Mussar ina survista da las paginas novas"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Parameters avanzads"</string>
+ <!-- outdated translation 3091250467679722382 --> <string name="pref_extras_title" msgid="7075456173747370647">"Parameters avanzads"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Parameters per websites"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Parameters avanzads per singulas websites"</string>
+ <!-- no translation found for pref_extras_reset_default_title (3579760449455761762) -->
+ <skip />
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Reinizialisar il standard"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Restaurar ils parameters predefinids"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Ils parameters da standard vegnan restituids."</string>
@@ -210,8 +332,19 @@
<item msgid="891615911084608570">"Giapunais (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Giapunais (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Giapunais (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Corean (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codaziun dal text"</string>
+ <!-- no translation found for pref_lab_title (5571091610359629423) -->
+ <skip />
+ <!-- no translation found for pref_lab_quick_controls (2105979166017257647) -->
+ <skip />
+ <!-- no translation found for pref_lab_quick_controls_summary (8025196176636589803) -->
+ <skip />
+ <!-- no translation found for pref_lab_most_visited_homepage (547134501893835512) -->
+ <skip />
+ <!-- no translation found for pref_lab_most_visited_homepage_summary (6857702350834122532) -->
+ <skip />
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problem da connectivitad da datas"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problem da datoteca"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Confermar"</string>
@@ -299,4 +432,23 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Stizzar tut las datas"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Interrumper"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Il maletg dal fund davos vegn endrizzà…"</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Segnapaginas"</string>
+ <!-- no translation found for empty_bookmarks_folder (7843361614634930942) -->
+ <skip />
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <!-- no translation found for account_chooser_dialog_title (3314204833188808194) -->
+ <!-- no translation found for account_chooser_dialog_title (4833571985009544332) -->
+ <skip />
+ <!-- no translation found for import_bookmarks_dialog_title (3325557652271172128) -->
+ <skip />
+ <!-- no translation found for import_bookmarks_dialog_description (2187665745413495303) -->
+ <skip />
+ <!-- no translation found for import_bookmarks_dialog_remove (8105572409059113340) -->
+ <skip />
+ <!-- no translation found for import_bookmarks_dialog_import (6933613853573899218) -->
+ <skip />
+ <!-- no translation found for menu_share_url (5851814357333739700) -->
+ <skip />
+ <!-- no translation found for max_tabs_warning (4122034303809457570) -->
+ <skip />
</resources>
diff --git a/res/values-ro-xlarge/strings.xml b/res/values-ro-xlarge/strings.xml
new file mode 100644
index 0000000..a7d3698
--- /dev/null
+++ b/res/values-ro-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Filă nouă"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Filă incognito nouă"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"File"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Deschideţi în filă nouă"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Deschideţi într-o filă nouă în fundal"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Deschideţi-le pe toate în file noi"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Deschideţi file noi în spatele celei curente"</string>
+</resources>
diff --git a/res/values-ro/strings.xml b/res/values-ro/strings.xml
index 7f05c36..1d22788 100644
--- a/res/values-ro/strings.xml
+++ b/res/values-ro/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Browser"</string>
<string name="choose_upload" msgid="3649366287575002063">"Alegeţi fişierul pentru a fi încărcat"</string>
<string name="new_tab" msgid="4505722538297295141">"Fereastră nouă"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Fereastră incognito nouă"</string>
<string name="active_tabs" msgid="3050623868203544623">"Windows"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Marcaje"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Cele mai vizitate"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Browser"</string>
<string name="cancel" msgid="3017274947407233702">"Anulaţi"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Nicio potrivire"</item>
- <item quantity="one" msgid="4352019729062956802">"1 potrivire"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> (de) potriviri"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> (de) potriviri"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Se încarcă…"</string>
<string name="page_info" msgid="4048529256302257195">"Informaţii pagină"</string>
<string name="page_info_view" msgid="5303490449842635158">"Vizualizaţi informaţiile paginii"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Continuaţi"</string>
<string name="security_warning" msgid="6607795404322797541">"Avertisment de securitate"</string>
<string name="view_certificate" msgid="1472768887529093862">"Vizualizaţi certificatul"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Înapoi"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Acest certificat nu provine de la o autoritate de încredere."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Numele acestui site nu se potriveşte cu numele de pe certificat."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Acest certificat a expirat."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"Redirecţionaţi"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Anulaţi"</string>
- <string name="location" msgid="969988560160364559">"Locaţie"</string>
- <string name="name" msgid="5990326151488445481">"Nume"</string>
+ <string name="location" msgid="3411848697912600125">"Adresă"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Adăugaţi la"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Dosar nou"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Editaţi dosarul"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Ştergeţi dosarul"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Nu există subdosare"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Marcaje"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Ecran de pornire"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Alt dosar..."</string>
+ <string name="name" msgid="5462672162695365387">"Etichetă"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Adăugaţi marcaj"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Adăugaţi la marcaje"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Marcaţi această pagină"</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"Modificaţi marcajul"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Adăugaţi o comandă rapidă pe ecranul de pornire"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Adăugaţi o comandă rapidă pe ecranul de pornire"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Deschideţi"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Ştergeţi marcajul"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Eliminaţi din marcaje"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Această adresă URL nu poate fi marcată."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Ştergeţi"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Marcaţi ultima pagină afişată"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Vizualizare miniaturi"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Vizualizare listă"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniaturi"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Listă"</string>
<string name="current_page" msgid="7510129573681663135">"din "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Marcajul „<xliff:g id="BOOKMARK">%s</xliff:g>” va fi şters."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Deschideţi într-o fereastră nouă"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Deschideţi-le pe toate în ferestre noi"</string>
<string name="goto_dot" msgid="3895839050522602723">"Accesaţi"</string>
- <string name="find_dot" msgid="6259312434696611957">"Găsiţi pe pagină"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Deschideţi filă incognito nouă"</string>
<string name="select_dot" msgid="6299170761900561967">"Selectaţi text"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Ferestre curente"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Închideţi"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Descărcări"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Copiaţi adresa URL a paginii"</string>
<string name="share_page" msgid="593756995297268343">"Distribuiţi pagina"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Salvaţi ca arhivă web"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Arhiva web a fost salvată."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Salvarea arhivei web nu a reuşit."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> (de) marcaje"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Dosar gol"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Deschideţi"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Deschideţi într-o fereastră nouă"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Marcaţi linkul"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Deschideţi într-o fereastră nouă în fundal"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Salvaţi linkul"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Distribuiţi linkul"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Copiaţi"</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Setaţi pagina de pornire"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Setaţi motorul de căutare"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Selectaţi un motor de căutare"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Utilizaţi pagina curentă"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Setaţi la..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Pagina curentă"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Pagină goală"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Pagina prestabilită"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Potriviţi paginile automat"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Formataţi paginile web pentru a se potrivi cu ecranul"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Afişaj numai în modul peisaj"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Afişaţi paginile numai pe ecran lat cu orientare de tip peisaj"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Setări privind confidenţialitatea"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"General"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sincronizaţi"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Completare automată"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sincronizaţi cu Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Distribuiţi marcaje şi alte date între browserul Android şi Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Cont Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sincronizaţi marcaje"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sincronizaţi marcaje între browserul Android şi Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Începeţi sincroniz."</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Sel. cont pt. dist."</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Completare automată formulare"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Completaţi formulare web cu un singur clic"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Setări Completare automată"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Configuraţi şi gestionaţi date pentru formularele cu completare automată"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Conectare automată la Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Nu au fost găsite conturi"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Conectaţi-vă automat la site-urile Google utilizând <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Se face conectarea la site-urile Google utilizând <xliff:g id="ID_1">%s</xliff:g>"\n"Setările dvs. de confidenţialitate şi securitate controlează conectarea automată la Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Nu doresc să mă conectez automat"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Completarea automată va utiliza informaţiile din profilul dvs. pentru a vă ajuta să completaţi formularele de pe web cu un singur clic."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Numele complet:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-mail:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Numele companiei:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Linie de adresă 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Stradă, număr, căsuţă poştală"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Linie de adresă 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Bloc, scară, etaj, apartament etc."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Oraş:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Stat/Provincie/Regiune:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Codul poştal:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Ţară:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Număr de telefon nevalid"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Salvaţi profilul"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profilul a fost salvat"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profilul a fost şters"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Ştergeţi profilul"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Browserul poate completa în mod automat formulare web ca acesta. Doriţi să vă configuraţi profilul?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Completarea automată poate fi configurată oricând din Setările browserului."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Dezactivaţi Completarea automată"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Confidenţialitate şi securitate"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Goliţi memoria cache"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Ştergeţi conţinutul memoriei cache şi bazele de date"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Conţinutul local al memoriei cache şi bazele de date se vor şterge."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookie-uri"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Ştergeţi toate datele despre cookie-uri"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Ştergeţi toate cookie-urile din browser"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Toate cookie-urile vor fi şterse."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Ştergeţi istoricul"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Ştergeţi istoricul de navigare din browser"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Istoricul de navigare din browser va fi şters."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Date din formular"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Ştergeţi datele din formular"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Ştergeţi toate datele din formulare"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Toate datele salvate în formular vor fi şterse."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Ştergeţi parolele"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Ştergeţi toate parolele salvate"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Toate parolele salvate vor fi şterse."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Locaţie"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Activaţi locaţia"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Permiteţi site-urilor să solicite accesul la locaţia dvs."</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Opriţi accesul la locaţie"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Opriţi accesul tuturor site-urilor web la locaţia dvs."</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Opriţi accesul tuturor site-urilor web la locaţia dvs."</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Setări de securitate"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Parole"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Activaţi reţinerea parolelor"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Salvaţi numele de utilizatori şi parolele pentru site-urile web"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Reţineţi datele din formular"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Zoom prestabilit"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Deschideţi paginile ca prezentare generală"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Afişaţi prezentarea generală a paginilor deschise recent"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Setări avansate"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Avansat"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Setări site web"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Setări avansate pentru site-uri web individuale"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Resetaţi la setările prestabilite"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Resetaţi la valorile prestabilite"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Restabiliţi setările prestabilite"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Setările vor fi aduse la valorile prestabilite."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"Japoneză (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japoneză (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japoneză (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Coreeană (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Codificare text"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Laborator"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Comenzi rapide"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Glisaţi degetul dinspre marg. din st. sau din dr. pt. a accesa comenzile rapide"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Pagina de pornire Cele mai vizitate"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Vă setează pagina de pornire pentru a afişa cele mai vizitate pagini."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Există o problemă de conexiune la date"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problemă cu fişierul"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Confirmaţi"</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Ştergeţi toate datele"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Anulaţi"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Se setează imaginea de fundal..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Marcaje"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Nu există marcaje"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Alegeţi un cont"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sincronizaţi cu un Cont Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Marcajele dvs. Android nu sunt asociate unui Cont Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Eliminaţi marcajele Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Adăugaţi marcajele Android la marcajele <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Distribuiţi"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Nu mai există file disponibile"</string>
</resources>
diff --git a/res/values-ru-xlarge/strings.xml b/res/values-ru-xlarge/strings.xml
new file mode 100644
index 0000000..517957e
--- /dev/null
+++ b/res/values-ru-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Новая вкладка"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Новая вкладка инкогнито"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Вкладки"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Открыть в новой вкладке"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Открыть в фоновой вкладке"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Открыть все в новых вкладках"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Открывать новые вкладки под текущей вкладкой"</string>
+</resources>
diff --git a/res/values-ru/strings.xml b/res/values-ru/strings.xml
index fd9d614..9cf16ca 100644
--- a/res/values-ru/strings.xml
+++ b/res/values-ru/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Браузер"</string>
<string name="choose_upload" msgid="3649366287575002063">"Выберите файл для загрузки"</string>
<string name="new_tab" msgid="4505722538297295141">"Новое окно"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Новое окно в режиме инкогнито"</string>
<string name="active_tabs" msgid="3050623868203544623">"Окна"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Закладки"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Часто посещаемые"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Браузер"</string>
<string name="cancel" msgid="3017274947407233702">"Отмена"</string>
<string name="ok" msgid="1509280796718850364">"ОК"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Соответствий нет"</item>
- <item quantity="one" msgid="4352019729062956802">"1 соответствие"</item>
- <item quantity="few" msgid="5544267486978946555">"Соответствий: <xliff:g id="NUMBER">%d</xliff:g>"</item>
- <item quantity="other" msgid="6616125067364315405">"Соответствий: <xliff:g id="NUMBER">%d</xliff:g>"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Загрузка…"</string>
<string name="page_info" msgid="4048529256302257195">"Информация о странице"</string>
<string name="page_info_view" msgid="5303490449842635158">"Информация о странице"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Продолжить"</string>
<string name="security_warning" msgid="6607795404322797541">"Угроза безопасности"</string>
<string name="view_certificate" msgid="1472768887529093862">"Просмотреть сертификат"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Назад"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Этот сертификат получен из ненадежных источников."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Название сайта не соответствует названию в сертификате."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Срок действия сертификата истек."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Вперед"</string>
<string name="save" msgid="5922311934992468496">"ОК"</string>
<string name="do_not_save" msgid="6777633870113477714">"Отмена"</string>
- <string name="location" msgid="969988560160364559">"URL-адрес"</string>
- <string name="name" msgid="5990326151488445481">"Имя"</string>
+ <string name="location" msgid="3411848697912600125">"Адрес"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Добавить в"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Новая папка"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Изменить папку"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Удалить папку"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Нет подпапок"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Закладки"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Главный экран"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Другая папка…"</string>
+ <string name="name" msgid="5462672162695365387">"Ярлык"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Добавить закладку"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Добавить в Закладки"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Закладка для этой страницы"</string>
+ <string name="remove" msgid="7820112494467011374">"Удалить"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Изменить закладку"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Добавить ярлык на главную страницу"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Добавить ярлык на главную"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Открыть"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Удалить закладку"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Удалить из закладок"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Невозможно добавить этот URL в закладки"</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Удалить"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Добавить в закладки последнюю просмотренную страницу"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Уменьшенные изображения"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"В виде списка"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Изображения"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Список"</string>
<string name="current_page" msgid="7510129573681663135">"на "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Закладка \"<xliff:g id="BOOKMARK">%s</xliff:g>\" будет удалена."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Открыть в новом окне"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Открыть все в новых окнах"</string>
<string name="goto_dot" msgid="3895839050522602723">"Поиск"</string>
- <string name="find_dot" msgid="6259312434696611957">"Найти на странице"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Открыть новую вкладку в режиме инкогнито"</string>
<string name="select_dot" msgid="6299170761900561967">"Выбрать текст"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Открытые окна"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Закрыть"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Загрузки"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Копировать URL страницы"</string>
<string name="share_page" msgid="593756995297268343">"Отправить страницу"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Сохранить как веб-архив"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Веб-архив сохранен."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Не удалось сохранить веб-архив."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"Закладок: <xliff:g id="BOOKMARK_COUNT">%d</xliff:g>"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Папка пуста"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Открыть"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Открыть в новом окне"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Добавить ссылку в закладки"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Открыть в фоновом окне"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Сохранить ссылку"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Отправить ссылку"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Копировать"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Домашняя страница"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Поисковая система"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Выберите поисковую систему"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Использовать текущую страницу"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"При запуске браузера"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Показывать текущую страницу"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Показывать пустую страницу"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Показывать страницу по умолчанию"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Мобильный вид"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Адаптировать контент к размеру экрана мобильного устройства"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Только горизонтально"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Показывать страницы только в горизонтальной ориентации"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Настройки конфиденциальности"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Общие"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Синхронизация"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Автозаполнение"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Синхронизировать с Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Совместно использовать закладки и другие данные в браузере Android и Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Аккаунт Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Синхронизировать закладки"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Синхронизировать закладки браузера Android и Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Синхронизировать"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Выберите аккаунт Google"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Автозаполнение форм"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Заполнение веб-форм одним кликом"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Настройки автозаполнения"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Настройка и управление данными для автозаполняемых форм"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Автоматический вход в Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Аккаунты не найдены"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Автоматически входить на сайты Google с помощью аккаунта <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Вход на сайты Google с использованием <xliff:g id="ID_1">%s</xliff:g>"\n"настроек функции \"Конфиденциальность и безопасность\" для автоматического входа в Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Запретить автоматический вход"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Автозаполнение будет использовать ваш профиль, чтобы вы могли заполнять веб-формы одним щелчком."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Полное имя:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Эл. почта:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Название компании:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Адресная строка 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Адрес, почтовый ящик, адрес до востребования"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Адресная строка 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Квартира, офис, блок, здание, этаж и т. д."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Город:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Штат / провинция / регион:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Почтовый индекс:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Страна:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Номер телефона:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Недопустимый номер телефона"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Сохранить профиль"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Профиль сохранен"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Профиль удален"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Удалить профиль"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Браузер может заполнять такие формы автоматически. Настроить профиль автозаполнения?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Автозаполнение настраивается в диалоговом окне \"Настройки браузера\""</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Отключить автозаполнение"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Конфиденциальность и безопасность"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Очистить кэш"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Удалить контент и данные, сохраненные браузером"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Контент и данные, сохраненные браузером, будут удалены."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Файлы cookie"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Удалить cookie"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Удалить все файлы cookie браузера"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Все файлы cookie будут удалены."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Очистить историю"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Очистить список посещенных в Интернете страниц"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"История браузера будет очищена."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Данные форм"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Очистить данные формы"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Очистить все сохраненные данные форм"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Все данные сохраненных форм будут удалены."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Очистить пароли"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Удалить все сохраненные пароли"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Все сохраненные пароли будут удалены."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Местоположение"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Доступ к геоданным"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Разрешить сайтам запрашивать доступ к данным о вашем местоположении"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Закрыть геоданные"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Очистить список сайтов, имеющих доступ к данным о вашем местоположении"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Очистить список сайтов, имеющих доступ к данным о вашем местоположении"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Настройки безопасности"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Пароли"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Сохранять пароли"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Сохранять имена пользователей и пароли веб-сайтов"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Сохранять данные форм"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Масштаб по умолчанию"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Обзор страниц"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Открывать страницы в мелком маштабе для ознакомления"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Расширенные настройки"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Расширенный"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Настройки веб-сайта"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Дополнительные настройки для отдельных сайтов"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Настройки по умолчанию"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Сброс настроек"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Восстановить значения по умолчанию"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Будут восстановлены значения по умолчанию."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Японская (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Японская (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Японская (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Корейская (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Кодировка текста"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Лаборатория Google"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Быстрое управление"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Листайте налево или направо, чтобы использовать быстрое управление"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Главная страница \"Часто посещаемых\""</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Настройка отображения часто посещаемых страниц на главной странице."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Проблема с подключением"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Проблема с файлом"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Подтвердить"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Удалить все данные"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Отмена"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Установка фонового рисунка..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Закладки"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Нет закладок"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Выберите аккаунт"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Синхронизация с аккаунтом Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Закладки Android не связаны с аккаунтом Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Удалить закладки Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Добавить закладки Android в аккаунт <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Отправить"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Достигнут предел количества вкладок"</string>
</resources>
diff --git a/res/values-sk-xlarge/strings.xml b/res/values-sk-xlarge/strings.xml
new file mode 100644
index 0000000..d1be7da
--- /dev/null
+++ b/res/values-sk-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Nová karta"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Nová karta v režime inkognito"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Karty"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Otvoriť na novej karte"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Otvoriť na novej karte na pozadí"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Otvoriť všetky na nových kartách"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Otvárať nové karty za aktuálnou kartou"</string>
+</resources>
diff --git a/res/values-sk/strings.xml b/res/values-sk/strings.xml
index ee2edc8..edd1253 100644
--- a/res/values-sk/strings.xml
+++ b/res/values-sk/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Prehliadač"</string>
<string name="choose_upload" msgid="3649366287575002063">"Zvoliť súbor, ktorý chcete odovzdať"</string>
<string name="new_tab" msgid="4505722538297295141">"Nové okno"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nové okno inkognito"</string>
<string name="active_tabs" msgid="3050623868203544623">"Windows"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Záložky"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Najviac navštevované"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Prehliadač"</string>
<string name="cancel" msgid="3017274947407233702">"Zrušiť"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Žiadne zhody"</item>
- <item quantity="one" msgid="4352019729062956802">"Počet zhôd: 1"</item>
- <item quantity="few" msgid="5544267486978946555">"Počet zhôd: <xliff:g id="NUMBER">%d</xliff:g>"</item>
- <item quantity="other" msgid="6616125067364315405">"Počet zhôd: <xliff:g id="NUMBER">%d</xliff:g>"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Prebieha načítavanie…"</string>
<string name="page_info" msgid="4048529256302257195">"Informácie o stránke"</string>
<string name="page_info_view" msgid="5303490449842635158">"Zobraziť informácie o stránke"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Pokračovať"</string>
<string name="security_warning" msgid="6607795404322797541">"Upozornenie zabezpečenia"</string>
<string name="view_certificate" msgid="1472768887529093862">"Zobraziť certifikát"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Prejsť späť"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Tento certifikát nepochádza od dôveryhodnej autority."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Názov webu sa nezhoduje s názvom uvedeným v certifikáte."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Platnosť certifikátu skončila."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"Poslať ďalej"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Zrušiť"</string>
- <string name="location" msgid="969988560160364559">"Poloha"</string>
- <string name="name" msgid="5990326151488445481">"Meno"</string>
+ <string name="location" msgid="3411848697912600125">"Adresa"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Pridať do"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Nový priečinok"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Upraviť priečinok"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Odstrániť priečinok"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Žiadne podpriečinky"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Záložky"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Plocha"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Iný priečinok..."</string>
+ <string name="name" msgid="5462672162695365387">"Menovka"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Pridať záložku"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Pridať medzi záložky"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Uložiť stránku ako záložku"</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"Upraviť záložku"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Pridať odkaz na plochu"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Pridať odkaz na plochu"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Otvoriť"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Odstrániť záložku"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Odstrániť zo záložiek"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Túto adresu URL nemožno pridať do záložiek."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Odstrániť"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Pridať poslednú zobrazenú stránku medzi záložky"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Zobraziť ako miniatúry"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Zobraziť zoznam"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniatúry"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Zoznam"</string>
<string name="current_page" msgid="7510129573681663135">"od "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Záložka <xliff:g id="BOOKMARK">%s</xliff:g> bude odstránená."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Otvoriť v novom okne"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Otvoriť všetky v nových oknách"</string>
<string name="goto_dot" msgid="3895839050522602723">"Hľadať"</string>
- <string name="find_dot" msgid="6259312434696611957">"Vyhľadať na stránke"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Nová karta v režime inkognito"</string>
<string name="select_dot" msgid="6299170761900561967">"Vybrať text"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Aktuálne okná"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Zavrieť"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Prevzatia"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Kopírovať adresu URL stránky"</string>
<string name="share_page" msgid="593756995297268343">"Zdieľať stránku"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Uložiť ako webový archív"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Webový archív bol uložený."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Uloženie webového archívu zlyhalo."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"Počet záložiek: <xliff:g id="BOOKMARK_COUNT">%d</xliff:g>"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Prázdny priečinok"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Otvoriť"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Otvoriť v novom okne"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Pridať odkaz medzi záložky"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Otvoriť v novom okne na pozadí"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Uložiť odkaz"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Zdieľať odkaz"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopírovať"</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Nastaviť domovskú stránku"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Nastaviť vyhľadávací nástroj"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Výber vyhľadávacieho nástroja"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Použiť aktuálnu stránku"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Nastaviť na..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Aktuálna stránka"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Prázdna stránka"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Predvolená stránka"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Automaticky prispôsobiť"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Prispôsobiť veľkosť webových stránok obrazovke"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Zobrazenie iba na šírku"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Zobraziť stránky iba s displejom otočeným na šírku"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Nastavenia ochrany osobných údajov"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Všeobecné"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Synchronizácia"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Automatické dopĺňanie"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synchronizovať s prehliadačom Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Zdieľať záložky a iné údaje medzi Prehliadačom systému Android a prehliadačom Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Účet Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synchronizovať záložky"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synchronizovať záložky medzi Prehliadačom systému Android a aplikáciou Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Synchronizovať"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Vyberte účet Google na zdieľ."</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Automatické dopĺňanie formulárov"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Vyplňovanie webových formulárov jediným kliknutím"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Nastavenia autom. dopĺňania"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Nastavenie a správa automaticky doplnených formulárov"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Automatické prihlasovanie Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Neboli nájdené žiadne účty"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Na webových stránkach Google sa automaticky prihlasovať pomocou účtu <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Prihlásenie na stránky služby Google pomocou <xliff:g id="ID_1">%s</xliff:g>"\n"Automatického prihlásenia Google s vašimi nastaveniami ochrany osobných údajov a zabezpečenia"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Neprihlasovať sa automaticky"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Funkcia Automatické dopĺňanie bude používať váš profil na dokončenie webových formulárov jediným kliknutím."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Celé meno:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-mail:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Názov spoločnosti:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"1. riadok adresy:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Adresa, č.p., P.O. box"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"2. riadok adresy:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Izba, apartmán, bunka, budova, poschodie a pod."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Mesto:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Štát / Provincia / Región:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"PSČ:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Krajina:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefón:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Neplatné telefónne číslo"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Uložiť profil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profil uložený"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profil bol odstránený."</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Odstrániť profil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Prehliadač dokáže automaticky vyplniť webové formuláre, ako je tento. Chcete nastaviť svoj profil?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Automatické dopĺňanie môžete kedykoľvek nakonfigurovať v Nastaveniach prehliadača."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Zakázať Automatické dopĺňanie"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Ochrana osobných údajov a zabezpečenie"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Vymazať medzipamäť"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Vymazať všetok obsah a databázy uložené do miestnej medzipamäte"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Obsah a databázy uložené v miestnej medzipamäti budú odstránené."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Súbory cookie"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Vymazať údaje súborov cookie"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Vymazať všetky súbory cookie prehliadača"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Všetky súbory cookie budú odstránené."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Vymazať históriu"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Vymazať históriu navigácie v prehliadači"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"História navigácie v prehliadači bude odstránená."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Údaje formulára"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Vymazať údaje formulárov"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Vymazať všetky uložené údaje formulárov"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Všetky uložené údaje formulárov budú vymazané."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Vymazať heslá"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Vymazať všetky uložené heslá"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Všetky uložené heslá budú odstránené."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Poloha"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Povoliť polohu"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Povoliť webovým stránkam žiadať o prístup k informáciám o vašej polohe"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Zrušiť prístup k polohe"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Zrušiť všetkým webovým stránkam prístup k polohe"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Zrušiť všetkým webovým stránkam prístup k polohe"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Nastavenia zabezpečenia"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Heslá"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Zapamätať heslá"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Ukladať používateľské mená a heslá pre webové stránky"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Zapamätať údaje formulárov"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Predvolené priblíženie"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Otvárať stránky v náhľade"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Zobraziť náhľad novo otvorených stránok"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Rozšírené nastavenia"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Rozšírené"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Zrušiť prístup k polohe"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Rozšírené nastavenia pre jednotlivé webové stránky"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Obnoviť predvolené"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Obnoviť predvolené"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Obnoviť predvolené nastavenia"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Budú obnovené predvolené hodnoty nastavení."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"Japončina (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japončina (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japončina (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Kórejčina (EUC–KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Kódovanie textu"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Rýchle ovládacie prvky"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Posunutím palca z ľavého alebo pravého okraja pristúpite k rýchlym ovl. prvkom"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Najnavštevovanejšie na domovskej stránke"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Nastaví na domovskej stránke zobrazovanie najviac navštevovaných stránok."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problémy s dátovým pripojením"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problém so súborom"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Potvrdiť"</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Odstrániť všetky údaje"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Zrušiť"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Prebieha nastavenie tapety..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Záložky"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Žiadne záložky na zobrazenie"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Vyberte účet"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synchronizovať s účtom Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Vaše záložky v systéme Android nie sú priradené k účtu Google."</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Odstrániť záložky systému Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Pridať všetky záložky systému Android medzi záložky účtu <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Zdieľať"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"K dispozícii nie sú žiadne ďalšie záložky"</string>
</resources>
diff --git a/res/values-sl-xlarge/strings.xml b/res/values-sl-xlarge/strings.xml
new file mode 100644
index 0000000..55a76e4
--- /dev/null
+++ b/res/values-sl-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Nov zavihek"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Nov zavihek brez bel. zgod."</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Zavihki"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Odpri v novem zavihku"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Odpri v novem zavihku v ozadju"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Odpri vse v novih zavihkih"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Odpri nove zavihke za trenutnim"</string>
+</resources>
diff --git a/res/values-sl/strings.xml b/res/values-sl/strings.xml
index 1de8573..212d883 100644
--- a/res/values-sl/strings.xml
+++ b/res/values-sl/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Brskalnik"</string>
<string name="choose_upload" msgid="3649366287575002063">"Izberite datoteko za prenos v strežnik"</string>
<string name="new_tab" msgid="4505722538297295141">"Novo okno"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Novo okno brez belež. zgod."</string>
<string name="active_tabs" msgid="3050623868203544623">"Okna"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Zaznamki"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Najpogosteje obiskovano"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Brskalnik"</string>
<string name="cancel" msgid="3017274947407233702">"Prekliči"</string>
<string name="ok" msgid="1509280796718850364">"V redu"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Ni zadetkov"</item>
- <item quantity="one" msgid="4352019729062956802">"1 ujemanje"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> ujemanj"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> ujemanj"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Nalaganje …"</string>
<string name="page_info" msgid="4048529256302257195">"Podatki o strani"</string>
<string name="page_info_view" msgid="5303490449842635158">"Prikaži podatke o strani"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Naprej"</string>
<string name="security_warning" msgid="6607795404322797541">"Varnostno opozorilo"</string>
<string name="view_certificate" msgid="1472768887529093862">"Prikaži potrdilo"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Nazaj"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Potrdila ni izdal zaupanja vreden overitelj."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Ime mesta se ne ujema z imenom potrdila."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Potrdilo je poteklo."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"Posreduj"</string>
<string name="save" msgid="5922311934992468496">"V redu"</string>
<string name="do_not_save" msgid="6777633870113477714">"Prekliči"</string>
- <string name="location" msgid="969988560160364559">"Lokacija"</string>
- <string name="name" msgid="5990326151488445481">"Ime"</string>
+ <string name="location" msgid="3411848697912600125">"Naslov"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Dodaj v skupino"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Nova mapa"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Uredi mapo"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Izbriši mapo"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Ni podmap"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Zaznamki"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Začetni zaslon"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Druga mapa ..."</string>
+ <string name="name" msgid="5462672162695365387">"Oznaka"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Dodaj zaznamek"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Dodaj med zaznamke"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Zaznamuj to stran"</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"Uredi zaznamek"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Dodaj bližnjico do domače strani"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Dodaj bližnjico do domače strani"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Odpri"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Izbriši zaznamek"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Odstrani iz zaznamkov"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"URL-ja ni mogoče označiti z zaznamkom."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Izbriši"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Zaznamuj nazadnje ogledano stran"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Pogled sličic"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Pogled seznama"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Sličice"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Seznam"</string>
<string name="current_page" msgid="7510129573681663135">"od "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Zaznamek »<xliff:g id="BOOKMARK">%s</xliff:g>« bo izbrisan"</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Odpri v novem oknu"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Odpri vse v novih oknih"</string>
<string name="goto_dot" msgid="3895839050522602723">"Pojdi"</string>
- <string name="find_dot" msgid="6259312434696611957">"Najdi na strani"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Odpri nov zav. brez bel. zg."</string>
<string name="select_dot" msgid="6299170761900561967">"Izberi besedilo"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Trenutna okna"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Zapri"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Prenosi"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Kopiraj URL strani"</string>
<string name="share_page" msgid="593756995297268343">"Stran deli z drugimi"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Shrani kot spletni arhiv"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Spletni arhiv je shranjen."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Spletnega arhiva ni bilo mogoče shraniti."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"Število zaznamkov: <xliff:g id="BOOKMARK_COUNT">%d</xliff:g>"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Prazna mapa"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Odpri"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Odpri v novem oknu"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Povezava zaznamka"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Odpri v novem oknu v ozadju"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Shrani povezavo"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Skupna raba povezave"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopiraj"</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Nastavi domačo stran"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Nastavi iskalnik"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Izberi iskalnik"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Uporabi trenutno stran"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Nastavi na ..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Trenutna stran"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Prazna stran"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Privzeta stran"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Samodejno prilagodi velikost strani"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Oblikuj spletne strani, da se prilegajo zaslonu"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Prikaz samo ležeče"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Prikaži strani samo v širšem, ležečem zaslonskem pogledu"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Nastavitve zasebnosti"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Splošno"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sinhronizacija"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Samodejno izpolnjevanje"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Sinhroniziraj z Google Chromom"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Delite si zaznamke in druge podatke med brskalnikom Android in Google Chromom"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google Račun"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Sinhroniziraj zaznamke"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Sinhroniziraj zaznamke med brskalnikom Android in Google Chromom"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Začni sinhronizacijo"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Google rač. za delj."</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Samodejno izpolnjevanje obrazcev"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Izpolnite spletne obrazce z enim klikom"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Nastavitve za sam. izpolnjevanje"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Nastavi in upravljaj podatke za samodejno izpolnjene obrazce"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Samodejna prijava v Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Ni računov"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Samodejna prijava v spletna mesta Google z računom <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Samodejna prijava v Googlova spletna mesta z <xliff:g id="ID_1">%s</xliff:g>"\n"Samodejna prijava v Google je določena v nastavitvah zasebnosti in varnosti"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Brez samodejne prijave"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"AutoFill bo uporabil vaš profil za izpolnjevanje spletnih obrazcev z enim klikom."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Polno ime:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-pošta:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Ime podjetja:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Vrstica naslova 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Ulični naslov, poštni predal, c/o"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Vrstica naslova 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Stanovanje, enota, stavba, nadstropje ipd."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Kraj/mesto:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Država/pokrajina/regija"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Poštna številka:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Država:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Neveljavna telefonska številka"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Shrani profil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profil je shranjen"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profil je izbrisan"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Izbriši profil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Brskalnik lahko samodejno izpolni spletne obrazce, kot je ta. Ali želite prilagoditi svoj profil?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Samodejno izpolnjevanje lahko nastavite v nastavitvah brskalnika."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Onemogoči samodejno izpolnjevanje"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Zasebnost in varnost"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Počisti predpomnilnik"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Počisti lokalno predpomnjeno vsebino in zbirke podatkov"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Lokalno predpomnjena vsebina in zbirke podatkov bodo izbrisane."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Piškotki"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Počisti vse podatke piškotkov"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Počisti vse piškotke brskalnika"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Vsi piškotki bodo izbrisani."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Počisti zgodovino"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Počisti zgodovino krmarjenja brskalnika"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Zgodovina krmarjenja brskalnika bo izbrisana."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Podatki iz obrazcev"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Počisti podatke obrazca"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Počisti vse shranjene podatke obrazcev"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Vsi shranjeni podatki obrazcev bodo izbrisani."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Počisti gesla"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Počisti vsa shranjena gesla"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Vsa shranjena gesla bodo preklicana."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Lokacija"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Omogoči lokacijo"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Dovoli mestom, da zahtevajo dostop do moje lokacije"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Počisti dostop do lokacije"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Počisti dostop do lokacije za vsa spletna mesta"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Počisti dostop do lokacije za vsa spletna mesta"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Varnostne nastavitve"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Gesla"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Zapomni si gesla"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Shrani uporabniška imena in gesla za spletna mesta"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Zapomni si podatke obrazcev"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Privzeta povečava/pomanjšava"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Odpri strani v pregledu"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Pokaži pregled na novo odprtih strani"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Dodatne nastavitve"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Dodatno"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Nastavitve spletnega mesta"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Dodatne nastavitve za posamezna spletna mesta"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Ponastavitev privzetih"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Ponastavi na privzeto"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Obnovitev privzetih nastavitev"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Nastavitve bodo povrnjene na privzete vrednosti."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"Japonščina (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japonščina (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japonščina (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Korejščina (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Kodiranje besedila"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Laboratoriji"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Hitro upravljanje"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Za dostop do hitrega upravljanja s palcem podrsajte od levega ali desnega roba"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Najbolj obiskana domača stran"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Nastavi domačo stran za prikaz najbolj obiskanih strani."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Težava s povezljivostjo podatkov"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Težava z datoteko"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Potrdi"</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Izbriši vse podatke"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Prekliči"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Nastavljanje slik za ozadje ..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Zaznamki"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Ni zaznamkov"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Izberite račun"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Sinhroniziraj z Google Računom"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Vaši Androidovi zaznamki niso povezani z Googlovim računom"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Odstranite Androidove zaznamke"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Dodaj Androidove zaznamke k zaznamkom za <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Skupna raba"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Ni več razpoložljivih zavihkov"</string>
</resources>
diff --git a/res/values-sr-xlarge/strings.xml b/res/values-sr-xlarge/strings.xml
new file mode 100644
index 0000000..993e372
--- /dev/null
+++ b/res/values-sr-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Нова картица"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Нова картица без архивирања"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Картице"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Отвори у новој картици"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Отвори у новој позадинској картици"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Отвори све у новим картицама"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Отварање нових картица иза тренутне картице"</string>
+</resources>
diff --git a/res/values-sr/strings.xml b/res/values-sr/strings.xml
index 83e554c..cd76430 100644
--- a/res/values-sr/strings.xml
+++ b/res/values-sr/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Прегледач"</string>
<string name="choose_upload" msgid="3649366287575002063">"Одаберите датотеку за отпремање"</string>
<string name="new_tab" msgid="4505722538297295141">"Нови прозор"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Нов прозор без архивирања"</string>
<string name="active_tabs" msgid="3050623868203544623">"Прозори"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Обележивачи"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Најпосећенији"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Прегледач"</string>
<string name="cancel" msgid="3017274947407233702">"Откажи"</string>
<string name="ok" msgid="1509280796718850364">"Потврди"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Нема подударања"</item>
- <item quantity="one" msgid="4352019729062956802">"1 подударање"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> подударања"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> подударања"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Учитавање…"</string>
<string name="page_info" msgid="4048529256302257195">"Информације о страници"</string>
<string name="page_info_view" msgid="5303490449842635158">"Прикажи информације о страници"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Настави"</string>
<string name="security_warning" msgid="6607795404322797541">"Безбедносно упозорење"</string>
<string name="view_certificate" msgid="1472768887529093862">"Прикажи сертификат"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Назад"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Овај сертификат не потиче од поузданог ауторитета."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Назив сајта се не подудара са називом на сертификату."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Овај сертификат је истекао."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"Проследи"</string>
<string name="save" msgid="5922311934992468496">"Потврди"</string>
<string name="do_not_save" msgid="6777633870113477714">"Откажи"</string>
- <string name="location" msgid="969988560160364559">"Локација"</string>
- <string name="name" msgid="5990326151488445481">"Назив"</string>
+ <string name="location" msgid="3411848697912600125">"Адреса"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Додај у"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Нов директоријум"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Измени директоријум"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Избриши директоријум"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Нема поддиректоријума"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Обележивачи"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Почетни екран"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Други директоријум…"</string>
+ <string name="name" msgid="5462672162695365387">"Ознака"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Додај обележивач"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Додај у обележиваче"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Обележавање ове странице"</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"Измени обележивач"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Додај пречицу на почетну"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Додај пречицу на почетну"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Отвори"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Избриши обележивач"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Уклони из обележивача"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Ова URL адреса не може да се обележи."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Брисање"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Обележи последњу приказану страницу"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Приказ сличица"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Прикажи листу"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Сличице"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Листа"</string>
<string name="current_page" msgid="7510129573681663135">"са "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Обележивач „<xliff:g id="BOOKMARK">%s</xliff:g>“ ће бити избрисан."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Отвори у новом прозору"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Отвори све у новим прозорима"</string>
<string name="goto_dot" msgid="3895839050522602723">"Иди"</string>
- <string name="find_dot" msgid="6259312434696611957">"Пронађи на страници"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Нова картица без архивирања"</string>
<string name="select_dot" msgid="6299170761900561967">"Изабери текст"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Тренутни прозори"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Затвори"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Преузимања"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Копирај URL адресу странице"</string>
<string name="share_page" msgid="593756995297268343">"Дели страницу"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Сачувај као веб архиву"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Сачувана је Веб архива"</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Неуспешно чување Веб архиве."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> обележивача"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Празан директоријум"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Отвори"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Отвори у новом прозору"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Обележи везу"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Отвори у новом позадинском прозору"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Сачувај везу"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Дели везу"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Копирај"</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Постави почетну страницу"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Подешавање претраживача"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Изаберите претраживач"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Користи тренутну страницу"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Подеси на…"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Тренутна страница"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Празна страница"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Подразумевана страница"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Аутоматски уклопи странице"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Подешавање формата веб страница тако да се уклопе на екран"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Само хоризонтални приказ"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Приказивање страница само у широм, хоризонталном положају екрана"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Подешавања приватности"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Општa"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Синхронизација"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Аутоматско попуњавање"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Синхронизуј са програмом Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Делите обележиваче и друге податке између Android прегледача и програма Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google налог"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Синхронизуј обележиваче"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Синхронизуј обележиваче између Android прегледача и програма Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Започни синхронизацију"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Изаберите Google налог са којим ћете делити"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Аутоматско попуњавање обрасца"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Попуните Веб обрасце само једним кликом"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Подешавања аутоматског попуњавања"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Подешавајте и управљајте подацима за аутоматски попуњене обрасце"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Аутоматска пријава на Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Није пронађен ниједан налог"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Пријавите се на Google сајтове аутоматски помоћу налога <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Пријављивање на Google сајтове помоћу <xliff:g id="ID_1">%s</xliff:g>"\n"Подешавања приватности и безбедности контролишу аутоматско Google пријављивање"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Не пријављуј ме аутоматски"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Аутоматско попуњавање ће користити ваш профил како би вам помогло у попуњавању веб образаца једним кликом."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Пуно име:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Е-пошта:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Назив предузећа:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"1. ред за адресу:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Адреса, поштански број, посредник"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"2. ред за адресу:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Апартман, стан, јединица, улаз, спрат итд."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Град/место:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Држава/покрајина/регион"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Поштански број:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Земља:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Телефон:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Неважећи број телефона"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Сачувај профил"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Профил је сачуван"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Профил је избрисан"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Избриши профил"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Прегледач може аутоматски да попуњава веб обрасце попут овог. Желите ли да подесите профил?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Аутоматско попуњавање увек можете да конфигуришете у Подешавањима прегледача."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Онемогући аутоматско попуњавање"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Приватност и безбедност"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Обриши кеш"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Брисање садржаја и база података из локалног кеша"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Садржај и базе података биће избрисани из локалног кеша."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Колачићи"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Избриши све податке колачића"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Брисање свих колачића из прегледача"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Сви колачићи биће избрисани."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Обриши историју"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Брисање историје навигације у прегледачу"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Историја навигације у прегледачу биће избрисана."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Подаци обрасца"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Обриши податке из обрасца"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Брисање свих сачуваних података образаца"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Сви сачувани подаци за обрасце биће избрисани."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Обриши лозинке"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Брисање свих сачуваних лозинки"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Све сачуване лозинке биће избрисане."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Локација"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Омогући локацију"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Омогућавање да сајтови захтевају приступ вашој локацији"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Обриши приступ локацији"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Брисање приступа локацији за све веб сајтове"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Брисање приступа локацији за све веб сајтове"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Безбедносна подешавања"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Лозинке"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Запамти лозинке"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Чување корисничких имена и лозинки за веб сајтове"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Запамти податке из обрасца"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Подразумевано зумирање"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Отвори странице у прегледу"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Приказивање прегледа новоотворених страница"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Напредна подешавања"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Напредно"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Подешавања веб сајта"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Напредна подешавања за појединачне веб сајтове"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Враћање подразумеваних вредности"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Поново постави подразумевано"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Враћање подразумеваних подешавања"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Поново ће бити постављене подразумеване вредности подешавања."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"јапански (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"јапански (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"јапански (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"корејски (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Кодирање текста"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Брзе контроле"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Листајте палцем са леве или десне ивице да бисте приступили брзим контролама"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Најпосећеније на почетној страници"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Подешава почетну страницу тако да се на њој приказују најпосећеније странице."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Проблем при повезивању са подацима"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Проблем са датотеком"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Потврда"</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Избриши све податке"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Откажи"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Постављање позадине..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Обележивачи"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Нема обележивача"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Избор налога"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Синхронизуј са Google налогом"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Android обележивачи нису повезани са Google налогом"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Уклоните Android обележиваче"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Додајте Android обележиваче у обележиваче за <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Дели"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Нема више доступних картица"</string>
</resources>
diff --git a/res/values-sv-xlarge/strings.xml b/res/values-sv-xlarge/strings.xml
new file mode 100644
index 0000000..0e3cd5b
--- /dev/null
+++ b/res/values-sv-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Ny flik"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Ny inkognitoflik"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Flikar"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Öppna i ny flik"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Öppna i ny flik i bakgrunden"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Öppna alla på en ny flik"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Öppna nya flikar bakom den aktiva"</string>
+</resources>
diff --git a/res/values-sv/strings.xml b/res/values-sv/strings.xml
index 76d3d0a..6e23ccb 100644
--- a/res/values-sv/strings.xml
+++ b/res/values-sv/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Webbläs."</string>
<string name="choose_upload" msgid="3649366287575002063">"Välj filen som du vill överföra"</string>
<string name="new_tab" msgid="4505722538297295141">"Nytt fönster"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Nytt inkognitofönster"</string>
<string name="active_tabs" msgid="3050623868203544623">"Fönster"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Bokmärken"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Mest besökta"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Webbläsare"</string>
<string name="cancel" msgid="3017274947407233702">"Avbryt"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Inga träffar"</item>
- <item quantity="one" msgid="4352019729062956802">"1 träff"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> träffar"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> träffar"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Hämtar…"</string>
<string name="page_info" msgid="4048529256302257195">"Sidinformation"</string>
<string name="page_info_view" msgid="5303490449842635158">"Visa sidinformation"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Fortsätt"</string>
<string name="security_warning" msgid="6607795404322797541">"Säkerhetsvarning"</string>
<string name="view_certificate" msgid="1472768887529093862">"Visa certifikat"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Föregående"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Detta certifikat kommer inte från en betrodd utfärdare."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Webbplatsens namn stämmer inte med namnet på certifikatet."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Certifikatet har upphört att gälla."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"Framåt"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Avbryt"</string>
- <string name="location" msgid="969988560160364559">"Plats"</string>
- <string name="name" msgid="5990326151488445481">"Namn"</string>
+ <string name="location" msgid="3411848697912600125">"Adress"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Lägg till"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Ny mapp"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Redigera mapp"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Ta bort mapp"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Inga undermappar"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Bokmärken"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Startsida"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"En annan mapp"</string>
+ <string name="name" msgid="5462672162695365387">"Etikett"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Lägg till bokmärke"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Lägg till i bokmärken"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Lägg till bokmärke för den här sidan"</string>
+ <string name="remove" msgid="7820112494467011374">"Ta bort"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Redigera bokmärke"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Lägg till genväg till startsidan"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Lägg till genväg på startsidan"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Öppna"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Ta bort bokmärke"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Ta bort från bokmärken"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Det går inte att spara webbadressen som ett bokmärke"</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Ta bort"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Skapa bokmärke för den senast visade sidan"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Miniatyrvy"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Listvy"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Miniatyrer"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Lista"</string>
<string name="current_page" msgid="7510129573681663135">"från "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Bokmärket <xliff:g id="BOOKMARK">%s</xliff:g> tas bort."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Öppna i nytt fönster"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Öppna alla i nytt ett fönster"</string>
<string name="goto_dot" msgid="3895839050522602723">"Kör"</string>
- <string name="find_dot" msgid="6259312434696611957">"Sök på sidan"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Öppna ny inkognitoflik"</string>
<string name="select_dot" msgid="6299170761900561967">"Markera text"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Aktuellt fönster"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Stäng"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Hämtningar"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Kopiera sidans webbadress"</string>
<string name="share_page" msgid="593756995297268343">"Dela sida"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Spara som webbarkiv"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Webbarkivet har sparats"</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Det gick inte att spara webbarkivet."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> bokmärken"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Tom mapp"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Öppna"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Öppna i nytt fönster"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Skapa ett bokmärke av länken"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Öppna i nytt fönster i bakgrunden"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Spara länk"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Dela länk"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopiera"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Ange startsida"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Ange sökmotor"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Välj en sökmotor"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Använd aktuell sida"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Ställ in på..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Aktuell sida"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Tom sida"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Standardsida"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Autoanpassa sidor"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Anpassa webbsidor efter skärmen"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Endast liggande"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Visa bara sidor i det bredare, liggande formatet"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Sekretessinställningar"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Allmänt"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Synka"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Autofyll"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Synkronisera med Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Dela bokmärken och andra data mellan Androids webbläsare och Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google-konto"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Synkronisera bokmärken"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Synkronisera bokmärken mellan Androids webbläsare och Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Synkronisera nu"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Välj Google-konto"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Automatisk ifyllning av formulär"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Fyll i webbformulär med ett enda klick"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Inställningar för Autofyll"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Konfigurera och hantera data för automatisk ifyllning av formulär"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Automatiskt inloggning på Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Inga konton hittades"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Logga in automatiskt på Googles webbplatser med <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Loggar in på Googles webbplatser med <xliff:g id="ID_1">%s</xliff:g>"\n"Automatisk inloggning på Google styrs med inställningarna i Sekretess och säkerhet"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Logga inte in automatiskt"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Autofyll använder din profil och hjälper dig att fylla i webbformulär med ett enda klick."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Fullständigt namn:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-post:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Företagsnamn:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Adressrad 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Gatuadress, postboxadress, c/o"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Adressrad 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Lägenhetsnummer, byggnad, våning med mera"</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Stad:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Stat/provins/region:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Postnummer:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Land:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Ogiltigt telefonnummer"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Spara profil"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profilen har sparats"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profilen har tagits bort"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Ta bort profil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Webbläsaren kan fylla i den här typen av formulär automatiskt. Vill du skapa en profil?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Du kan när som helst ändra inställningarna för Autofyll under webbläsarens inställningar."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Inaktivera Autofyll"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Sekretess och säkerhet"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Rensa cacheminne"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Ta bort innehåll och databaser som cachelagrats lokalt"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Innehåll och databaser som cachelagrats lokalt tas bort."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookies"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Ta bort alla cookie-data"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Ta bort alla webbläsarens cookies"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Alla cookies tas bort."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Rensa historik"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Rensa webbläsarhistoriken"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Webbläsarhistoriken kommer att tas bort."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Formulärdata"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Rensa data i formulär"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Rensa data från alla sparade formulär"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Alla sparade formulärdata kommer att tas bort."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Ta bort lösenord"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Ta bort alla sparade lösenord"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Alla sparade lösenord tas bort."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Plats"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Aktivera plats"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Tillåt att webbplatser begär åtkomst till din plats"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Ta bort platsåtkomst"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Ta bort platsåtkomst för alla webbplatser"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Ta bort platsåtkomst för alla webbplatser"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Säkerhetsinställningar"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Lösenord"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Kom ihåg lösenord"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Spara användarnamn och lösenord för webbplatser"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Spara formulärdata"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Standardinställning för zoom"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Öppna sidor i översikt"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Visa översikt över nyligen öppnade sidor"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Avancerade inställningar"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Avancerat"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Webbplatsinställningar"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Avancerade inställningar för enskilda webbplatser"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Återställ standardvärden"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Återställ standardinställningarna"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Återställ standardinställningar"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Standardvärdena för inställningarna återställs."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japansk (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japansk (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japansk (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"koreanska (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Textkodning"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Snabbkontroller"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Svep tummen från vänster eller höger kant så kommer du åt snabbkontrollerna"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Startsida med de mest besökta sidorna"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"De mest besökta sidorna visas på startsidan."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problem med dataanslutning"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problem med filen"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Bekräfta"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Ta bort alla data"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Avbryt"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Anger bakgrund..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Bokmärken"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Det finns inga bokmärken"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Välj konto"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Synkronisera med Google-konto"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Dina Android-bokmärken har inte kopplats till något Google-konto"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Ta bort dina Android-bokmärken"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Lägg till dina Android-bokmärken i bokmärkena för <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Dela"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Det finnns inga fler flikar"</string>
</resources>
diff --git a/res/values-th-xlarge/strings.xml b/res/values-th-xlarge/strings.xml
new file mode 100644
index 0000000..7eb654b
--- /dev/null
+++ b/res/values-th-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"แท็บใหม่"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"แท็บใหม่ที่ไม่ระบุตัวตน"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"แท็บ"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"เปิดในแท็บใหม่"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"เปิดในแท็บพื้นหลังใหม่"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"เปิดทั้งหมดในแท็บใหม่"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"เปิดแท็บใหม่หลังแท็บปัจจุบัน"</string>
+</resources>
diff --git a/res/values-th/strings.xml b/res/values-th/strings.xml
index 5c4652f..cd74d53 100644
--- a/res/values-th/strings.xml
+++ b/res/values-th/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"เบราว์เซอร์"</string>
<string name="choose_upload" msgid="3649366287575002063">"เลือกไฟล์ที่จะอัปโหลด"</string>
<string name="new_tab" msgid="4505722538297295141">"หน้าต่างใหม่"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"หน้าต่างใหม่ที่ไม่ระบุตัวตน"</string>
<string name="active_tabs" msgid="3050623868203544623">"Windows"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"บุ๊กมาร์ก"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"เข้าชมมากที่สุด"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"เบราว์เซอร์"</string>
<string name="cancel" msgid="3017274947407233702">"ยกเลิก"</string>
<string name="ok" msgid="1509280796718850364">"ตกลง"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"ไม่พบรายการที่ตรงกัน"</item>
- <item quantity="one" msgid="4352019729062956802">"1 รายการที่ตรงกัน"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> รายการที่ตรงกัน"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> รายการที่ตรงกัน"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"กำลังโหลด…"</string>
<string name="page_info" msgid="4048529256302257195">"ข้อมูลหน้าเว็บ"</string>
<string name="page_info_view" msgid="5303490449842635158">"ดูข้อมูลหน้าเว็บ"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"ดำเนินการต่อ"</string>
<string name="security_warning" msgid="6607795404322797541">"คำเตือนเกี่ยวกับความปลอดภัย"</string>
<string name="view_certificate" msgid="1472768887529093862">"ดูใบรับรอง"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"ย้อนกลับ"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"ใบรับรองนี้ไม่ได้มาจากผู้ออกที่เชื่อถือได้"</string>
<string name="ssl_mismatch" msgid="558688832420069896">"ชื่อไซต์ไม่ตรงกับในใบรับรอง"</string>
<string name="ssl_expired" msgid="5739349389499575559">"ใบรับรองนี้หมดอายุแล้ว"</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"ส่งต่อ"</string>
<string name="save" msgid="5922311934992468496">"ตกลง"</string>
<string name="do_not_save" msgid="6777633870113477714">"ยกเลิก"</string>
- <string name="location" msgid="969988560160364559">"ตำแหน่ง"</string>
- <string name="name" msgid="5990326151488445481">"ชื่อ"</string>
+ <string name="location" msgid="3411848697912600125">"ที่อยู่"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"เพิ่มใน"</string>
+ <string name="new_folder" msgid="7743540149088867917">"โฟลเดอร์ใหม่"</string>
+ <string name="edit_folder" msgid="621817453133656156">"แก้ไขโฟลเดอร์"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"ลบโฟลเดอร์"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"ไม่มีโฟลเดอร์ย่อย"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"บุ๊กมาร์ก"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"หน้าจอหลัก"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"โฟลเดอร์อื่นๆ…"</string>
+ <string name="name" msgid="5462672162695365387">"ป้ายกำกับ"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"เพิ่มบุ๊กมาร์ก"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"เพิ่มลงในบุ๊กมาร์ก"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"บุ๊กมาร์กหน้าเว็บนี้"</string>
+ <string name="remove" msgid="7820112494467011374">"ลบออก"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"แก้ไขบุ๊กมาร์ก"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"เพิ่มทางลัดไปหน้าแรก"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"เพิ่มทางลัดไปหน้าแรก"</string>
<string name="open_bookmark" msgid="8473581305759935790">"เปิด"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"ลบบุ๊กมาร์ก"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"นำออกจากบุ๊กมาร์ก"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"ไม่สามารถบุ๊กมาร์ก URL นี้ได้"</string>
<string name="delete_bookmark" msgid="2422989994934201992">"ลบ"</string>
<string name="bookmark_page" msgid="6845189305130307274">"บุ๊กมาร์กหน้าที่เพิ่งดูล่าสุด"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"มุมมองภาพขนาดย่อ"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"มุมมองรายการ"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"ภาพขนาดย่อ"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"รายการ"</string>
<string name="current_page" msgid="7510129573681663135">"จาก "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"บุ๊กมาร์ก \"<xliff:g id="BOOKMARK">%s</xliff:g>\" จะถูกลบ"</string>
<string name="open_in_new_window" msgid="6596775546468054510">"เปิดในหน้าต่างใหม่"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"เปิดทั้งหมดในหน้าต่างใหม่"</string>
<string name="goto_dot" msgid="3895839050522602723">"ไป"</string>
- <string name="find_dot" msgid="6259312434696611957">"ค้นหาบนหน้า"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"เปิดแท็บใหม่ที่ไม่ระบุตัวตน"</string>
<string name="select_dot" msgid="6299170761900561967">"เลือกข้อความ"</string>
<string name="tab_picker_title" msgid="864478399057782913">"หน้าต่างปัจจุบัน"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"ปิด"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"สิ่งที่ดาวน์โหลด"</string>
<string name="copy_page_url" msgid="7635062169011319208">"คัดลอก URL หน้าเว็บ"</string>
<string name="share_page" msgid="593756995297268343">"แบ่งปันหน้าเว็บ"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"บันทึกเป็นที่เก็บถาวรเว็บ"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"บันทึกที่เก็บถาวรเว็บแล้ว"</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"บันทึกที่เก็บถาวรเว็บไม่สำเร็จ"</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"บุ๊กมาร์ก <xliff:g id="BOOKMARK_COUNT">%d</xliff:g> รายการ"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"โฟลเดอร์ว่าง"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"เปิด"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"เปิดในหน้าต่างใหม่"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"ลิงก์บุ๊กมาร์ก"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"เปิดในหน้าต่างพื้นหลังใหม่"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"บันทึกลิงก์"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"แบ่งปันลิงก์"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"คัดลอก"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"ตั้งค่าหน้าแรก"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"ตั้งค่าเครื่องมือค้นหา"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"เลือกเครื่องมือค้นหา"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"ใช้หน้าปัจจุบัน"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"ตั้งค่าเป็น ..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"หน้าเว็บปัจจุบัน"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"หน้าว่าง"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"หน้าเว็บเริ่มต้น"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"ปรับหน้าให้พอดีอัตโนมัติ"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"ปรับรูปแบบหน้าเว็บให้พอดีกับหน้าจอ"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"แสดงในแนวนอนเท่านั้น"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"แสดงหน้าตามหน้าจอแนวนอนที่กว้างกว่าปกติเท่านั้น"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"การตั้งค่าข้อมูลส่วนบุคคล"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"ทั่วไป"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"ซิงค์"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"ป้อนอัตโนมัติ"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"ซิงค์กับ Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"แบ่งปันบุ๊กมาร์กและข้อมูลอื่นๆ ระหว่างเบราว์เซอร์ Android กับ Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"บัญชี Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"ซิงค์บุ๊กมาร์ก"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"ซิงค์บุ๊กมาร์กระหว่างเบราว์เซอร์ Android และ Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"เริ่มการซิงค์"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"เลือกบัญชี Google ที่จะแบ่งปัน"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"ป้อนข้อมูลฟอร์มอัตโนมัติ"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"กรอกข้อมูลเว็บฟอร์มได้ในคลิกเดียว"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"การตั้งค่าป้อนอัตโนมัติ"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"ตั้งค่าและจัดการข้อมูลสำหรับฟอร์มที่ป้อนข้อมูลอัตโนมัติ"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"ลงชื่อเข้าใช้ Google อัตโนมัติ"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"ไม่พบบัญชี"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"ลงชื่อเข้าใช้ Google Sites อัตโนมัติโดยใช้ <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"กำลังลงชื่อเข้าใช้ Google Sites ด้วย <xliff:g id="ID_1">%s</xliff:g>"\n"การตั้งค่าข้อมูลส่วนบุคคลและความปลอดภัยจะควบคุมการลงชื่อเข้าใช้อัตโนมัติของ Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"อย่าลงชื่อเข้าใช้โดยอัตโนมัติ"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"การป้อนอัตโนมัติจะใช้โปรไฟล์ของคุณเพื่อช่วยให้คุณกรอกเว็บฟอร์มได้ในคลิกเดียว"</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"ชื่อเต็ม:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"อีเมล:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"ชื่อบริษัท:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"บรรทัดที่อยู่ 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"เลขที่ ตู้ป.ณ. ชื่อผู้รับ"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"บรรทัดที่อยู่ 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"อพาร์ทเมนท์ ห้องชุด ห้อง อาคาร ชั้น ฯลฯ"</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"เมือง:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"รัฐ/จังหวัด/ภูมิภาค:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"รหัสไปรษณีย์:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"ประเทศ:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"โทรศัพท์:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"หมายเลขโทรศัพท์ไม่ถูกต้อง"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"บันทึกโปรไฟล์"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"บันทึกโปรไฟล์แล้ว"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"ลบโปรไฟล์แล้ว"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"ลบโปรไฟล์"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"เบราว์เซอร์จะกรอกเว็บฟอร์มให้โดยอัตโนมัติเช่นฟอร์มนี้ คุณต้องการตั้งค่าโปรไฟล์ของคุณหรือไม่"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"ป้อนอัตโนมัติ สามารถกำหนดค่าผ่านการตั้งค่าเบราว์เซอร์"</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"ปิดใช้งานการป้อนอัตโนมัติ"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"ข้อมูลส่วนบุคคลและความปลอดภัย"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"ล้างแคช"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"ล้างเนื้อหาและฐานข้อมูลที่เก็บไว้ในเครื่อง"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"เนื้อหาและฐานข้อมูลที่เก็บไว้ในเครื่องจะถูกลบ"</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"คุกกี้"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"ล้างข้อมูลคุกกี้ทั้งหมด"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"ล้างคุกกี้ทั้งหมดของเบราว์เซอร์"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"คุกกี้ทั้งหมดจะถูกลบ"</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"ล้างประวัติ"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"ล้างประวัติการนำทางเบราว์เซอร์"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"ประวัติการนำทางของเบราว์เซอร์จะถูกลบ"</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"ข้อมูลฟอร์ม"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"ล้างข้อมูลในฟอร์ม"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"ล้างข้อมูลในฟอร์มที่บันทึกไว้ทั้งหมด"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"ข้อมูลในฟอร์มที่บันทึกไว้ทั้งหมดจะถูกลบ"</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"ล้างรหัสผ่าน"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"ล้างรหัสผ่านที่บันทึกไว้ทั้งหมด"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"รหัสผ่านทั้งหมดที่บันทึกไว้จะถูกลบ"</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"ตำแหน่ง"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"เปิดการใช้งานตำแหน่ง"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"อนุญาตให้ไซต์ขอเข้าถึงตำแหน่งของคุณ"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"ล้างการเข้าถึงตำแหน่ง"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"ล้างการเข้าถึงตำแหน่งสำหรับทุกเว็บไซต์"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"ล้างการเข้าถึงตำแหน่งสำหรับทุกเว็บไซต์"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"การตั้งค่าความปลอดภัย"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"รหัสผ่าน"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"จำรหัสผ่าน"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"บันทึกชื่อผู้ใช้และรหัสผ่านสำหรับเว็บไซต์"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"จำข้อมูลในฟอร์ม"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"การซูมเริ่มต้น"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"เปิดหน้าในภาพรวม"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"แสดงภาพรวมจากหน้าที่เพิ่งเปิดใหม่"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"การตั้งค่าขั้นสูง"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"ขั้นสูง"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"การตั้งค่าเว็บไซต์"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"การตั้งค่าขั้นสูงสำหรับเว็บไซต์แต่ละเว็บ"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"รีเซ็ตค่าเริ่มต้น"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"รีเซ็ตเป็นค่าเริ่มต้น"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"คืนค่าเริ่มต้น"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"การตั้งค่าจะกลับไปเป็นค่าเริ่มต้น"</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japanese (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japanese (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japanese (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"เกาหลี (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"การเข้ารหัสข้อความ"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"การควบคุมอย่างรวดเร็ว"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"กวาดนิ้วหัวแม่มือจากขอบซ้ายหรือขวาเพื่อเข้าถึงการควบคุมอย่างรวดเร็ว"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"หน้าแรกที่มีผู้เข้าชมสูงสุด"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"ตั้งหน้าแรกของคุณให้แสดงหน้าเว็บที่มีผู้เข้าชมมากที่สุด"</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"ปัญหาการเชื่อมต่อข้อมูล"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"ปัญหาเกี่ยวกับไฟล์"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"ยืนยัน"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"ลบข้อมูลทั้งหมด"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"ยกเลิก"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"กำลังตั้งค่าวอลเปเปอร์..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"บุ๊กมาร์ก"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"ไม่มีบุ๊กมาร์ก"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"เลือกบัญชี"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"ซิงค์กับบัญชี Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"บุ๊กมาร์ก Android ของคุณไม่เชื่อมโยงกับบัญชี Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"ลบบุ๊กมาร์ก Android ของคุณ"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"เพิ่มบุ๊กมาร์ก Android ของคุณลงในบุ๊กมาร์กสำหรับ <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"แบ่งปัน"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"ไม่สามารถใช้แท็บเพิ่มได้"</string>
</resources>
diff --git a/res/values-tl-xlarge/strings.xml b/res/values-tl-xlarge/strings.xml
new file mode 100644
index 0000000..069d6eb
--- /dev/null
+++ b/res/values-tl-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Bagong tab"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Bagong incognito tab"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Mga Tab"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Buksan sa bagong tab"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Buksan sa bagong tab na background"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Buksan sa lahat ng mga bagong tab"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Buksan ang mga bagong tab sa likod ng kasalukuyan"</string>
+</resources>
diff --git a/res/values-tl/strings.xml b/res/values-tl/strings.xml
index 48138c4..04ff6c2 100644
--- a/res/values-tl/strings.xml
+++ b/res/values-tl/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Browser"</string>
<string name="choose_upload" msgid="3649366287575002063">"Pumili ng file para sa pag-upload"</string>
<string name="new_tab" msgid="4505722538297295141">"Bagong window"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Bagong incognito window"</string>
<string name="active_tabs" msgid="3050623868203544623">"Windows"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Mga Bookmark"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Pinaka-binibisita"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Browser"</string>
<string name="cancel" msgid="3017274947407233702">"Kanselahin"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Walang mga tugma"</item>
- <item quantity="one" msgid="4352019729062956802">"1 tugma"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> (na) tugma"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> (na) tugma"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Naglo-load…"</string>
<string name="page_info" msgid="4048529256302257195">"Impormasyon ng pahina"</string>
<string name="page_info_view" msgid="5303490449842635158">"Tingnan ang impormasyon ng pahina"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Magpatuloy"</string>
<string name="security_warning" msgid="6607795404322797541">"Babala sa seguridad"</string>
<string name="view_certificate" msgid="1472768887529093862">"Tingnan ang certificate"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Bumalik"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Hindi nagmula ang certificate na ito sa isang pinagkakatiwalaang kinauukulan."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Hindi tumutugma ang pangalan ng site sa pangalan sa certificate."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Nag-expire na ang certificate na ito."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"Ipasa"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Kanselahin"</string>
- <string name="location" msgid="969988560160364559">"Lokasyon"</string>
- <string name="name" msgid="5990326151488445481">"Pangalan"</string>
+ <string name="location" msgid="3411848697912600125">"Address"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Idagdag sa"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Bagong folder"</string>
+ <string name="edit_folder" msgid="621817453133656156">"I-edit ang folder"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Tanggalin ang folder"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Walang mga subfolder"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Mga Bookmark"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Home screen"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Ibang folder…"</string>
+ <string name="name" msgid="5462672162695365387">"Label"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Magdagdag ng bookmark"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Idagdag sa Mga Bookmark"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"I-bookmark ang pahinang ito"</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"I-edit ang bookmark"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Magdagdag ng shortcut sa Home"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Magdagdag ng shortcut sa Home"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Buksan"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Tanggalin ang bookmark"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Alisin mula sa mga bookmark"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Hindi mabu-bookmark ang URL na ito."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Tanggalin"</string>
<string name="bookmark_page" msgid="6845189305130307274">"I-bookmark ang huling tiningnang pahina"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Thumbnail na view"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Listahang view"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Mga Thumbnail"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Listahan"</string>
<string name="current_page" msgid="7510129573681663135">"mula sa "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Tatanggalin ang bookmark na \"<xliff:g id="BOOKMARK">%s</xliff:g>\"."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Buksan sa bagong window"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Buksan lahat sa bagong windows"</string>
<string name="goto_dot" msgid="3895839050522602723">"Pumunta"</string>
- <string name="find_dot" msgid="6259312434696611957">"Maghanap sa pahina"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Magbukas ng bago incognito tab"</string>
<string name="select_dot" msgid="6299170761900561967">"Pumili ng teksto"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Kasalukuyang windows"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Isara"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Mga Pag-download"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Kopyahin ang url ng pahina"</string>
<string name="share_page" msgid="593756995297268343">"Ibahagi ang pahina"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"I-save bilang Web Archive"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Na-save na ang web archive."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Nabigong i-save ang web archive."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> (na) bookmark"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Walang lamang folder"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Buksan"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Buksan sa bagong window"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"I-bookmark ang link"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Buksan sa bagong window ng background"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"I-save ang link"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Ibahagi ang link"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopyahin"</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Itakda ang home page"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Itakda ang search engine"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Pumili ng search engine"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Gamitin ang kasalukuyang pahina"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Itakda sa…"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Kasalukuyang pahina"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Blangkong pahina"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Default na pahina"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Mga auto-fit na pahina"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"I-format ang mga web page upang iakma sa screen"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Display na landscape-only"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Ipakita lang ang mga pahina sa mas malapad, landscape screen na oryentasyon"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Mga setting ng privacy"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Pangkalahatan"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Sync"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Autofill"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Mag-sync sa Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Ibahagi ang mga bookmark & iba pang data sa pagitan ng Android Browser at Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google account"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"I-sync ang mga bookmark"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"I-sync ang mga bookmark sa pagitan ng Android Browser at Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Simulan ang pag-sync"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Pili Google account"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Form AutoFill"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Punan ang mga web form sa isang click"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Mga Setting ng AutoFill"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"I-set up & pamahalaan ang data para sa mga Na-AutoFill na form"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Awtomatiko pag-sign in sa Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Walang nakitang mga account"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Awtomatikong mag-sign in sa mga site ng Google gamit ang <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Nagsa-sign in sa mga site ng Google gamit ang <xliff:g id="ID_1">%s</xliff:g>"\n"Kinokontrol ng iyong mga setting ng Privacy at Seguridad ang awtomatikong pag-sign-in ng Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Huwag awtomatikong mag-sign in"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Gagamitin ng AutoFill ang iyong profile upang matulungan kang makumpleto ang mga form ng web sa isahang pag-click."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Buong pangalan:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Email:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Pangalan ng Kompanya:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Linya ng address 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Address ng kalye, P.O. box, c/o"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Linya ng address 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Apartment, suite, unit, building, floor atbp."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Lungsod / Bayan:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Estado / Probinsiya / Rehiyon:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Zip code:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Bansa:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telepono:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Di-wastong numero ng telepono"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"I-save ang Profile"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Na-save na ang profile"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Natanggal na ang profile"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Tanggalin ang profile"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Maaaring awtomatikong kumpletuhin ng browser ang mga form ng web katulad nito. Gusto mo bang i-set up ang iyong profile?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Palaging mako-configure ang AutoFill sa pamamagitan ng Mga Setting ng Browser."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Huwag paganahin ang AutoFill"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Privacy at Seguridad"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"I-clear ang cache"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"I-clear ang lokal na naka-cache na nilalaman at mga database"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Tatanggalin ang lokal na na-cache na nilalaman at mga database."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookies"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"I-clear ang lahat ng data ng cookie"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"I-clear ang lahat ng cookies ng browser"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Tatanggalin ang lahat ng cookies."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"I-clear ang kasaysayan"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"I-clear ang kasaysayan ng nabigasyon ng browser"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Tatanggalin ang kasaysayan ng nabigasyon ng browser."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Form data"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"I-clear ang data ng form"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"I-clear ang lahat ng naka-save na data ng form"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Tatanggalin ang lahat ng naka-save na data ng form."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"I-clear ang mga password"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"I-clear ang lahat ng mga naka-save na password"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Tatanggalin ang lahat ng mga naka-save na password."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Lokasyon"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Paganahin ang lokasyon"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Payagan ang mga site na humiling ng access sa iyong lokasyon"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"I-clear ang access sa lokasyon"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"I-clear ang access ng lokasyon para sa lahat ng mga website"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"I-clear ang access ng lokasyon para sa lahat ng mga website"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Mga setting ng seguridad"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Mga Password"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Tandaan ang mga password"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"I-save ang mga username at password para sa mga website"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Tandaan ang data ng form"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Default zoom"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Buksan ang mga pahina sa pangkalahatang-ideya"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Ipakita ang pangkalahatang-ideya ng mga bagong bukas na pahina"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Mga advanced na setting"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Advanced"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Mga setting ng website"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Mga advanced na setting para sa mga indibidwal na website"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"I-reset ang mga default"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Itakda muli bilang default"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Ibalik ang mga default na setting"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Babalik ang mga setting sa mga default na halaga."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"Japanese (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japanese (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japanese (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Korean (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Pag-encode ng teksto"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Mga Lab"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Mga Mabilisang Control"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"I-swipe ang hinlalaki mula sa kaliwa hanggang sa kanang kanto upang ma-access ang mga mabilisang control"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Pinaka-binibisitang Homepage"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Itakda ang iyong homepage upang ipakita ang pinaka-binibisitang mga pahina."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Problema sa pagkakakonekta ng data"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Problema sa file"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Kumpirmahin"</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Tanggalin ang lahat ng data"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Kanselahin"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Itinatakda ang wallpaper..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Mga Bookmark"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Walang mga bookmark"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Pumili ng account"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Mag-sync sa Google account"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Walang kaugnayan ang iyong mga Android bookmark sa isang Google account"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Alisin ang iyong mga Android bookmark"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Idagdag ang iyong mga Android bookmark sa mga bookmark para sa <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Ibahagi"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Wala nang available na mga tab"</string>
</resources>
diff --git a/res/values-tr-xlarge/strings.xml b/res/values-tr-xlarge/strings.xml
new file mode 100644
index 0000000..ad88d26
--- /dev/null
+++ b/res/values-tr-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Yeni sekme"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Yeni gizli sekme"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Sekmeler"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Yeni sekmede aç"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Yeni arka plan sekmesinde aç"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Tümünü yeni sekmelerde aç"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Yeni sekmeleri geçerli sekmenin arkasında aç"</string>
+</resources>
diff --git a/res/values-tr/strings.xml b/res/values-tr/strings.xml
index e120a3b..9ca233a 100644
--- a/res/values-tr/strings.xml
+++ b/res/values-tr/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Tarayıcı"</string>
<string name="choose_upload" msgid="3649366287575002063">"Yükleme için dosya seçin"</string>
<string name="new_tab" msgid="4505722538297295141">"Yeni pencere"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Yeni gizli pencere"</string>
<string name="active_tabs" msgid="3050623868203544623">"Pencereler"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Favoriler"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"En çok ziyaret edilenler"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Tarayıcı"</string>
<string name="cancel" msgid="3017274947407233702">"İptal"</string>
<string name="ok" msgid="1509280796718850364">"Tamam"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Eşleşme yok"</item>
- <item quantity="one" msgid="4352019729062956802">"1 eşleşme"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> eşleşme"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> eşleşme"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Yükleniyor…"</string>
<string name="page_info" msgid="4048529256302257195">"Sayfa bilgileri"</string>
<string name="page_info_view" msgid="5303490449842635158">"Sayfa bilgilerini görüntüle"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Devam Et"</string>
<string name="security_warning" msgid="6607795404322797541">"Güvenlik uyarısı"</string>
<string name="view_certificate" msgid="1472768887529093862">"Sertifikayı görüntüle"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Geri git"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Bu sertifika güvenilir bir yetkiliden değil."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Sitenin adı sertifika üzerindeki adla eşleşmiyor."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Bu sertifikanın süresi dolmuş."</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"İleri"</string>
<string name="save" msgid="5922311934992468496">"Tamam"</string>
<string name="do_not_save" msgid="6777633870113477714">"İptal"</string>
- <string name="location" msgid="969988560160364559">"Konum"</string>
- <string name="name" msgid="5990326151488445481">"Ad"</string>
+ <string name="location" msgid="3411848697912600125">"Adres"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Şu klasöre ekle"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Yeni klasör"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Klasörü düzenle"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Klasörü sil"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Alt klasör yok"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Yer işaretleri"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Ana ekran"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Diğer klasör..."</string>
+ <string name="name" msgid="5462672162695365387">"Etiket"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Favori ekle"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Yer İşaretlerine Ekle"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Bu sayfaya yer işareti koy"</string>
+ <string name="remove" msgid="7820112494467011374">"Kaldır"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"Favorileri düzenle"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Ana ekrana kısayol ekle"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Ana ekrana kısayol ekle"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Aç"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Favoriyi sil"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Favorilerden kaldır"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Bu URL yer işareti olarak eklenemez."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Sil"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Son görüntülenen sayfayı favori olarak işaretle"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Küçük resim görünümü"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Liste görünümü"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Küçük resimler"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Liste"</string>
<string name="current_page" msgid="7510129573681663135">"kaynak: "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Favori \"<xliff:g id="BOOKMARK">%s</xliff:g>\" silinecek."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Yeni pencerede aç"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Tümünü yeni pencerelerde aç"</string>
<string name="goto_dot" msgid="3895839050522602723">"Git"</string>
- <string name="find_dot" msgid="6259312434696611957">"Sayfada bul"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Yeni gizli sekme aç"</string>
<string name="select_dot" msgid="6299170761900561967">"Metin seç"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Geçerli pencereler"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Kapat"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"İndirme işlemleri"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Sayfa url\'sini kopyala"</string>
<string name="share_page" msgid="593756995297268343">"Sayfayı paylaş"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Web Arşivi olarak Kaydet"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Web arşivi kaydedildi."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Web arşivi kaydedilemedi."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> yer işareti"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Boş klasör"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Aç"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Yeni pencerede aç"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Favori bağlantısı"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Yeni arka plan penceresinde aç"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Bağlantıyı kaydet"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Bağlantıyı paylaş"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Kopyala"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Ana sayfayı ayarla"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Arama motoru ayarlayın"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Arama moturu seçin"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Geçerli sayfayı kullan"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Ana sayfayı ayarla..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Mevcut sayfa"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Boş sayfa"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Varsayılan sayfa"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Sayfaları otomatik sığdır"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Web sayfalarını ekrana sığacak şekilde biçimlendir"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Yalnızca yatay görüntü"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Sayfaları yalnızca daha geniş, yatay ekran yönünde görüntüle"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Gizlilik ayarları"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Genel"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Senkronizasyon"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Otomatik Doldur"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Google Chrome ile senkronize et"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Yer işaretlerini ve diğer verileri Android Tarayıcı ile Google Chrome arasında paylaş"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google hesabı"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Yer işaretlerini senkronize et"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Yer işaretlerini Android Tarayıcı ve Google Chrome arasında senkronize et"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Senk. başlat"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Paylaşım için Google hesabını seçin"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Formu Otomatik Doldur"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Web formlarını tek bir tıklamayla doldurun"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Otomatik Doldurma Ayarları"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Otomatik Doldurulan formlara ilişkin verileri ayarlayın ve yönetin"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Otomatik Google oturumu açma"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Hesap bulunamadı"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"<xliff:g id="ID_1">%s</xliff:g> adını kullanarak Google Sites\'da otomatik olarak oturum aç"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"<xliff:g id="ID_1">%s</xliff:g> hesabı ile Google Sites hizmetinde oturum açılıyor"\n"Google\'da otomatik oturum açmanız Gizlilik ve Güvenlik ayarlarınız tarafından denetlenir."</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Otomatik olarak oturum açma"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Otomatik Doldurma özelliği web formlarını tek bir tıklamayla doldurmanıza yardımcı olmak için profilinizi kullanır."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Tam ad:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"E-posta:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Şirket adı:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Adres satırı 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Sokak adresi, posta kutusu, alıcı"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Adres satırı 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Apartman, blok, daire, bina, kat vb."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Şehir / Kasaba:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Eyalet / Vilayet / Bölge:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Posta kodu:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Ülke:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Telefon:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Geçersiz telefon numarası"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Profili kaydet"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Profil kaydedildi"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Profil silindi"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Profili sil"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Tarayıcı bunun gibi web formlarını otomatik olarak tamamlayabilir. Profilinizi ayarlamak ister misiniz?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Otomatik Doldurma\'yı istediğiniz zaman Tarayıcı Ayarları\'ndan yapılandırabilirsiniz."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Otomatik Doldurma\'yı devre dışı bırak"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Gizlilik ve Güvenlik"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Önbelleği temizle"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Yerel olarak önbelleğe alınmış içeriği ve veritabanlarını temizle"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Yerel olarak önbelleğe alınmış içerik ve veritabanları silinecek."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Çerezler"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Tüm çerez verilerini temizle"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Tüm tarayıcı çerezlerini temizle"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Tüm çerezler silinecek."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Geçmişi temizle"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Tarayıcı gezinme geçmişini temizle"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Tarayıcının gezinme geçmişi silinecek."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Form verileri"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Form verilerini temizle"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Tüm kayıtlı form verilerini temizle"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Tüm kayıtlı form verileri silinecek."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Şifreleri temizle"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Kayıtlı tüm şifreleri temizle"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Kayıtlı tüm şifreler silinecek."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Konum"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Konumu etkinleştir"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Sitelerin konumunuza erişmek istemesine izin verin"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Konum erişimini temizle"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Tüm web siteleri için konum erişimini temizle"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Tüm web siteleri için konum erişimini temizle"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Güvenlik ayarları"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Şifreler"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Şifreleri hatırla"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Web siteleri için kullanıcı adlarını ve şifreleri kaydet"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Form verilerini hatırla"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Varsayılan zum"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Sayfaları genel görünümde aç"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Yeni açılan sayfaların genel görünümünü göster"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Gelişmiş ayarlar"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Gelişmiş"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Web sitesi ayarları"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Her web sitesi için ayrı düzenlenebilen gelişmiş ayarlar"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Varsayılanları sıfırla"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Varsayılana sıfırla"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Varsayılan ayarları geri yükle"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Ayarlar, varsayılan değerlere döndürülecek."</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"Japonca (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Japonca (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Japonca (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Korece (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Metin kodlama"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Labs"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Hızlı Denetimler"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Hızlı denetimlere erişmek için başparmağınızı soldan sağa doğru hızla kaydırın"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"En Çok Ziyaret Edilenler Ana Sayfası"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Ana sayfanızı en çok ziyaret edilen sayfaları gösterecek şekilde ayarlar."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Veri bağlantısı sorunu"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Sorunlu dosya"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Doğrula"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Tüm verileri sil"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"İptal"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Duvar kağıdı ayarlanıyor..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Yer işaretleri"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Hiçbir yer işareti yok"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Hesap seçin"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Google hesabı ile senkronize et"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Android yer işaretleriniz bir Google hesabı ile ilişkilendirilmemiş"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Android yer işaretlerinizi kaldırın"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Android yer işaretlerinizi <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g> yer işaretlerine ekleyin"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Paylaş"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Kullanılabilir başka sekme yok"</string>
</resources>
diff --git a/res/values-uk-xlarge/strings.xml b/res/values-uk-xlarge/strings.xml
new file mode 100644
index 0000000..036aeaf
--- /dev/null
+++ b/res/values-uk-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Нова вкладка"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Нова анонімна вкладка"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Вкладки"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Відкрити в новій вкладці"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Відкрити в новій фоновій вкладці"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Відкрити все в нових вкладках"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Відкривати нові вкладки за поточною"</string>
+</resources>
diff --git a/res/values-uk/strings.xml b/res/values-uk/strings.xml
index 768c9ed..b774d03 100644
--- a/res/values-uk/strings.xml
+++ b/res/values-uk/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Переглядач"</string>
<string name="choose_upload" msgid="3649366287575002063">"Вибер. файл для завантаж."</string>
<string name="new_tab" msgid="4505722538297295141">"Нове вікно"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Нове анонімне вікно"</string>
<string name="active_tabs" msgid="3050623868203544623">"Вікна"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Закладки"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Часто відвідувані"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Переглядач"</string>
<string name="cancel" msgid="3017274947407233702">"Скасувати"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Жодних збігів"</item>
- <item quantity="one" msgid="4352019729062956802">"1 збіг"</item>
- <item quantity="few" msgid="5544267486978946555">"Збіги: <xliff:g id="NUMBER">%d</xliff:g>"</item>
- <item quantity="other" msgid="6616125067364315405">"Збіги: <xliff:g id="NUMBER">%d</xliff:g>"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Завант-ня…"</string>
<string name="page_info" msgid="4048529256302257195">"Інфо про стор."</string>
<string name="page_info_view" msgid="5303490449842635158">"Інфо про стор."</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Продовжити"</string>
<string name="security_warning" msgid="6607795404322797541">"Застереж. про небезп."</string>
<string name="view_certificate" msgid="1472768887529093862">"Переглянути сертиф."</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Повернутися"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Сертиф-т походить від ненадійн. центру сертиф-ції."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Назва сайту не відповідає назві в сертифікаті."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Термін дії сертиф. завершився."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"Уперед"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Скасувати"</string>
- <string name="location" msgid="969988560160364559">"Місцезнах."</string>
- <string name="name" msgid="5990326151488445481">"Назва"</string>
+ <string name="location" msgid="3411848697912600125">"Адреса"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Додати до"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Нова папка"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Редагувати папку"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Видалити папку"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Немає підпапок"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Закладки"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Головний екран"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Вибрати іншу папку…"</string>
+ <string name="name" msgid="5462672162695365387">"Мітка"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Додати закладку"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Додати до закладок"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Дод.стор. до закладок"</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"Редаг. закладку"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Додати ярлик на Головну"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Додати ярлик на головний екран"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Відкр."</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Видалити закладку"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Видалити із закладок"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Закладка для цієї URL-адр. неможлива"</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Видалити"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Створ. закладку для ост. стор."</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Перегляд ескізів"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Перегляд списку"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Ескізи"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Список"</string>
<string name="current_page" msgid="7510129573681663135">"з "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Закладку \"<xliff:g id="BOOKMARK">%s</xliff:g>\" буде видалено."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Відкрити в нов. вікні"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Відкрити все в нових вікнах"</string>
<string name="goto_dot" msgid="3895839050522602723">"Викон."</string>
- <string name="find_dot" msgid="6259312434696611957">"Знайти на стор."</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Відкрити нову анонімну вкладку"</string>
<string name="select_dot" msgid="6299170761900561967">"Вибрати текст"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Поточні вікна"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Закрити"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Завантаження"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Копіюв. URL стор."</string>
<string name="share_page" msgid="593756995297268343">"Надісл. стор."</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Зберегти як веб-архів"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Веб-архів збережено."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Помилка збереження веб-архіву."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"Закладок: <xliff:g id="BOOKMARK_COUNT">%d</xliff:g>"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Порожня папка"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Відкр."</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Відкрити в нов. вікні"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Закладка для посил."</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Відкрити в новому фоновому вікні"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Збер. посил."</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Надісл. посил."</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Копіюв."</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Устан. дом. стор."</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Налашт. пошук. сист."</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Виберіть пошукову систему"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Викор. поточну стор."</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Установити…"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Поточну сторінку"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Порожню сторінку"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Сторінку за умовчанням"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Автомат. припасув."</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Форматув. сторінки до розмірів екрана"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Лише в альбом. режимі"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Відображати сторінки лише в ширшій альбомній орієнтації"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Налашт. конфіденц."</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Загальні"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Синхронізація"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Автозаповнення"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Синхронізувати з Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Здійснювати обмін закладками й іншими даними між веб-переглядачем Android і Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Облік. запис Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Синхронізувати закладки"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Синхронізуйте закладки у веб-переглядачі Android і Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Почати синхронізацію"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Вибрати обл.зап. Google для надсил."</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Автозаповнення форм"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Заповнюйте веб-форми за допомогою лише одного кліка"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Налаштування автозаповнення"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Налаштовуйте дані для автозаповнення форм і керуйте ними"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Автоматичний вхід у Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Облікових записів не знайдено"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Автоматично ввійти в Google Sites за допомогою <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Вхід у Google Sites за допомогою <xliff:g id="ID_1">%s</xliff:g>"\n"Ваші налаштування конфіденційності та безпеки контролюють автоматичний вхід у Google"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Не входити автоматично"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Функція \"Автозаповнення\" буде використовувати ваш профіль, щоб заповнювати веб-форми за допомогою лише одного кліка."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Повне ім\'я:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Електронна адреса:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Назва компанії:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Адреса, рядок 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Назва вулиці, поштова скринька, отримувач"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Адреса, рядок 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Кімната, квартира, під\'їзд, будівля, поверх тощо"</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Місто чи містечко:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Штат, провінція чи область:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Поштовий індекс:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Країна:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Телефон:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Неправильний номер телефону"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Зберегти профіль"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Профіль збережено"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Профіль видалено"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Видалити профіль"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Веб-переглядач може автоматично заповнювати подібні веб-форми. Налаштувати ваш профіль?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Автозаповнення завжди можна налаштувати в налаштуваннях веб-переглядача."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Вимкнути автозаповнення"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Конфіденційність і безпека"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Очистити кеш"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Очистити локально кешов. вміст і бази даних"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Локально кешований вміст і бази даних буде видалено."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Файли сookie"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Очист. всі дані файлів cookie"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Очист. всі файли cookie перегл-ча"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Усі файли cookie буде видалено."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Очистити історію"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Очистити історію навігації переглядача"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Історію навігації переглядача буде видалено."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Дані форм"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Очист. дані форми"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Очистити всі збережені дані форм"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Усі збережені дані форм буде видалено."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Очистити паролі"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Очист. всі збережені паролі"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Усі збережені паролі буде видалено."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Місцезнаходження"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Увімкнути місцезн."</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Дозволити сайтам запитувати доступ до місцезн."</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Очист. доступ до місцезн."</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Очист. доступ до місцезн. для всіх сайтів"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Очист. доступ до місцезн. для всіх сайтів"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Налаштув-ня безпеки"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Паролі"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Пам\'ятати паролі"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Зберігати імена корист. і паролі для сайтів"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Запам\'ят. дані форми"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Масштаб за умовч."</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Відкривати огляд сторінок"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Відображ. огляд щойно відкритих стор."</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Розширені налашт-ня"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Розширені"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Налашт-ня сайту"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Розширені налаштування для окремих сайтів"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Скинути налаштування за умовчанням"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Віднов. налашт. за умовч."</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Відновити налашт. за умовч."</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Буде відновлено налашт-ня за умовчанням."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"Japanese (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Японська (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Японська (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Корейська (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Кодування тексту"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Лабораторії"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Елементи швидкого керування"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Проведіть пальцем від лівого/правого краю для доступу до елем. швидк. керування"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Дом. стор. функції \"Часто відвідувані\""</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Налаштовує на домашній сторінці показ найчастіше відвідуваних сторінок."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Проблема з доступом до даних"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Проблема з файлом"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Підтверд."</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Видалити всі дані"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Скасувати"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Встановл. фонового мал…"</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Закладки"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Немає закладок"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Виберіть обліковий запис"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Синхроніз. з обл. записом Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Ваші закладки Android не пов\'язано з обліковим записом Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Видалити закладки Android"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Додати закладки Android до закладок для <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Надіслати"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Більше немає вкладок"</string>
</resources>
diff --git a/res/values-vi-xlarge/strings.xml b/res/values-vi-xlarge/strings.xml
new file mode 100644
index 0000000..5e74c13
--- /dev/null
+++ b/res/values-vi-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"Tab mới"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"Tab ẩn danh mới"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"Tab"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"Mở trong tab mới"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"Mở trong tab nền mới"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"Mở tất cả trong tab mới"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"Mở tab mới phía sau tab hiện tại"</string>
+</resources>
diff --git a/res/values-vi/strings.xml b/res/values-vi/strings.xml
index 1b93e0a..b24c8b4 100644
--- a/res/values-vi/strings.xml
+++ b/res/values-vi/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"Trình duyệt"</string>
<string name="choose_upload" msgid="3649366287575002063">"Chọn tệp để tải lên"</string>
<string name="new_tab" msgid="4505722538297295141">"Cửa sổ mới"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"Cửa sổ ẩn danh mới"</string>
<string name="active_tabs" msgid="3050623868203544623">"Windows"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"Dấu trang"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"Truy cập nhiều nhất"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"Trình duyệt"</string>
<string name="cancel" msgid="3017274947407233702">"Huỷ"</string>
<string name="ok" msgid="1509280796718850364">"OK"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"Không có kết quả nào phù hợp"</item>
- <item quantity="one" msgid="4352019729062956802">"1 kết quả phù hợp"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> kết quả phù hợp"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> kết quả phù hợp"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"Đang tải…"</string>
<string name="page_info" msgid="4048529256302257195">"Thông tin trang"</string>
<string name="page_info_view" msgid="5303490449842635158">"Xem thông tin trang"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"Tiếp tục"</string>
<string name="security_warning" msgid="6607795404322797541">"Cảnh báo bảo mật"</string>
<string name="view_certificate" msgid="1472768887529093862">"Xem chứng chỉ"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"Quay lại"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"Chứng chỉ này không xuất phát từ tổ chức phát hành tin cậy."</string>
<string name="ssl_mismatch" msgid="558688832420069896">"Tên của trang web không khớp với tên trên chứng chỉ."</string>
<string name="ssl_expired" msgid="5739349389499575559">"Chứng chỉ này đã hết hạn."</string>
@@ -67,12 +63,23 @@
<string name="forward" msgid="4288210890526641577">"Chuyển tiếp"</string>
<string name="save" msgid="5922311934992468496">"OK"</string>
<string name="do_not_save" msgid="6777633870113477714">"Huỷ"</string>
- <string name="location" msgid="969988560160364559">"Vị trí"</string>
- <string name="name" msgid="5990326151488445481">"Tên"</string>
+ <string name="location" msgid="3411848697912600125">"Địa chỉ"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"Thêm vào"</string>
+ <string name="new_folder" msgid="7743540149088867917">"Thư mục mới"</string>
+ <string name="edit_folder" msgid="621817453133656156">"Chỉnh sửa thư mục"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"Xóa thư mục"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"Không có thư mục con"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"Dấu trang"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"Màn hình chính"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"Thư mục khác…"</string>
+ <string name="name" msgid="5462672162695365387">"Nhãn"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"Thêm dấu trang"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"Thêm vào dấu trang"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"Đánh dấu trang này"</string>
+ <!-- no translation found for remove (7820112494467011374) -->
+ <skip />
<string name="edit_bookmark" msgid="5024089053490231905">"Chỉnh sửa dấu trang"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"Thêm lối tắt tới Màn hình trang chủ"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"Thêm lối tắt tới màn hình trang chủ"</string>
<string name="open_bookmark" msgid="8473581305759935790">"Mở"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"Xoá dấu trang"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"Xoá khỏi dấu trang"</string>
@@ -87,13 +94,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"Không thể đánh dấu URL này."</string>
<string name="delete_bookmark" msgid="2422989994934201992">"Xoá"</string>
<string name="bookmark_page" msgid="6845189305130307274">"Đánh dấu trang xem lần cuối"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"Chế độ xem hình thu nhỏ"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"Chế độ xem danh sách"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"Hình thu nhỏ"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"Danh sách"</string>
<string name="current_page" msgid="7510129573681663135">"từ "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"Dấu trang \"<xliff:g id="BOOKMARK">%s</xliff:g>\" sẽ bị xoá."</string>
<string name="open_in_new_window" msgid="6596775546468054510">"Mở trong cửa sổ mới"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"Mở tất cả trong cửa sổ mới"</string>
<string name="goto_dot" msgid="3895839050522602723">"Đến"</string>
- <string name="find_dot" msgid="6259312434696611957">"Tìm kiếm trên trang"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"Mở tab ẩn danh mới"</string>
<string name="select_dot" msgid="6299170761900561967">"Chọn văn bản"</string>
<string name="tab_picker_title" msgid="864478399057782913">"Cửa sổ hiện tại"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"Đóng"</string>
@@ -103,9 +111,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"Nội dung tải xuống"</string>
<string name="copy_page_url" msgid="7635062169011319208">"Sao chép url của trang"</string>
<string name="share_page" msgid="593756995297268343">"Chia sẻ trang"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"Lưu dưới dạng Lưu trữ web"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"Đã lưu kho lưu trữ web."</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"Không thể lưu kho lưu trữ web."</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> dấu trang"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"Thư mục trống"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"Mở"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"Mở trong cửa sổ mới"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"Đánh dấu liên kết"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"Mở trong cửa sổ nền mới"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"Lưu liên kết"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"Chia sẻ liên kết"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"Sao chép"</string>
@@ -138,33 +151,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"Đặt trang chủ"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"Đặt công cụ tìm kiếm"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"Chọn công cụ tìm kiếm"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"Sử dụng trang hiện tại"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"Đặt thành…"</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"Trang hiện tại"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"Trang trống"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"Trang mặc định"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"Tự động điều chỉnh kích thước các trang"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"Định dạng trang web để vừa với màn hình"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"Hiển thị chỉ theo khổ ngang"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"Chỉ hiển thị trang theo hướng màn hình ngang và rộng hơn"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"Cài đặt bảo mật"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"Chung"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"Đồng bộ hóa"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"Tự động điền"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"Đồng bộ hóa với Google Chrome"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"Chia sẻ dấu trang & các dữ liệu khác giữa Trình duyệt Android và Google Chrome"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Tài khoản Google"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"Đồng bộ hóa dấu trang"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"Đồng bộ hóa dấu trang giữa Trình duyệt Android và Google Chrome"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"Bắt đầu đồng bộ hóa"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"Chọn tk Google để c.sẻ"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"Tự động điền biểu mẫu"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"Điền biểu mẫu web chỉ với một cú nhấp"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"Cài đặt tự động điền"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"Thiết lập & quản lý dữ liệu cho biểu mẫu Tự động điền"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"Tự động đăng nhập Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"Không tìm thấy tài khoản nào"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"Tự động đăng nhập vào các trang của Google bằng <xliff:g id="ID_1">%s</xliff:g>"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"Đang đăng nhập vào các trang web của Google bằng <xliff:g id="ID_1">%s</xliff:g>"\n"Cài đặt Riêng tư & Bảo mật kiểm soát đăng nhập Google tự động"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"Không đăng nhập tự động"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"Tự động điền sẽ sử dụng tiểu sử của bạn để giúp bạn hoàn thành biểu mẫu web chỉ bằng một cú nhấp chuột."</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"Tên đầy đủ:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"Email:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"Tên công ty:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"Dòng địa chỉ 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"Địa chỉ đường phố, hộp thư bưu điện, c/o"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"Dòng địa chỉ 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"Căn hộ, phòng, bộ phận, tòa nhà, tầng, v.v.."</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"Thành phố / Thị trấn:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"Tiểu bang / Tỉnh / Vùng:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"Mã zip:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"Quốc gia:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"Điện thoại:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"Số điện thoại không hợp lệ"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"Lưu tiểu sử"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"Đã lưu tiểu sử"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"Đã xóa tiểu sử"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"Xóa tiểu sử"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"Trình duyệt có thể tự động hoàn thành biểu mẫu web như biểu mẫu này. Bạn có muốn thiết lập cấu hình của mình không?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"Luôn có thể định cấu hình tính năng Tự động điền thông qua Cài đặt trình duyệt."</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"Tắt Tự động điền"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"Quyền riêng tư & Bảo mật"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"Xoá bộ nhớ cache"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"Xoá nội dung và cơ sở dữ liệu được lưu trong bộ nhớ cache cục bộ"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"Nội dung và cơ sở dữ liệu được lưu trong bộ nhớ cache cục bộ sẽ bị xoá."</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookie"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"Xoá tất cả dữ liệu cookie"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"Xoá tất cả cookie của trình duyệt"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"Tất cả cookie sẽ bị xoá."</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"Xoá lịch sử"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"Xoá lịch sử điều hướng của trình duyệt"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"Lịch sử điều hướng của trình duyệt sẽ bị xoá."</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"Dữ liệu biểu mẫu"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"Xoá dữ liệu biểu mẫu"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"Xoá tất cả dữ liệu biểu mẫu đã lưu"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"Tất cả dữ liệu biểu mẫu đã lưu sẽ bị xoá."</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"Xoá mật khẩu"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"Xoá tất cả mật khẩu đã lưu"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"Tât cả mật khẩu đã lưu sẽ bị xoá."</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"Vị trí"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"Bật vị trí"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"Cho phép trang web yêu cầu quyền truy cập vào vị trí của bạn"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"Xoá truy cập vị trí"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"Xoá truy cập vị trí cho tất cả trang web"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"Xoá truy cập vị trí cho tất cả trang web"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"Cài đặt bảo mật"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"Mật khẩu"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"Nhớ mật khẩu"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"Lưu tên người dùng và mật khẩu cho trang web"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"Nhớ dữ liệu biểu mẫu"</string>
@@ -191,9 +248,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"Thu phóng mặc định"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"Mở các trang trong chế độ xem tổng quan"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"Hiển thị tổng quan về các trang mới mở"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"Cài đặt nâng cao"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"Nâng cao"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"Cài đặt trang web"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"Cài đặt nâng cao cho các trang web riêng lẻ"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"Đặt lại về mặc định"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"Đặt lại về mặc định"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"Khôi phục cài đặt mặc định"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"Cài đặt sẽ hoàn nguyên về giá trị mặc định."</string>
@@ -208,8 +266,14 @@
<item msgid="891615911084608570">"Tiếng Nhật (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"Tiếng Nhật (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"Tiếng Nhật (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"Tiếng Hàn (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"Mã hoá văn bản"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"Lab"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"Điều khiển nhanh"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"Ấn ngón tay từ cạnh trái hoặc phải để truy cập điều khiển nhanh"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"Trang chủ được truy cập nhiều nhất"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"Đặt trang chủ của bạn để hiển thị các trang được truy cập nhiều nhất."</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"Sự cố kết nối dữ liệu"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"Sự cố với tệp"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"Xác nhận"</string>
@@ -296,4 +360,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"Xoá tất cả dữ liệu"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"Huỷ"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"Đang đặt hình nền..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"Dấu trang"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"Không có dấu trang"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"Chọn tài khoản"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"Đồng bộ hóa với tài khoản Google"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Dấu trang Android của bạn không được kết hợp với tài khoản Google"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"Xóa dấu trang Android của bạn"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"Thêm dấu trang Android của bạn vào dấu trang cho <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g>"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"Chia sẻ"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"Không có thêm tab nào"</string>
</resources>
diff --git a/res/values-xlarge-port/dimensions.xml b/res/values-xlarge-port/dimensions.xml
new file mode 100644
index 0000000..f891396
--- /dev/null
+++ b/res/values-xlarge-port/dimensions.xml
@@ -0,0 +1,19 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ Copyright (C) 2010 The Android Open Source Project Licensed under the
+ Apache License, Version 2.0 (the "License"); you may not use this file
+ except in compliance with the License. You may obtain a copy of the
+ License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+ applicable law or agreed to in writing, software distributed under the
+ License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+ CONDITIONS OF ANY KIND, either express or implied. See the License for
+ the specific language governing permissions and limitations under the
+ License.
+-->
+<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <dimen name="widgetThumbnailHeight">84dip</dimen>
+ <dimen name="widgetHorizontalSpacing">10dip</dimen>
+ <dimen name="widgetVerticalSpacing">10dip</dimen>
+ <dimen name="combo_paddingLeftRight">16dip</dimen>
+ <dimen name="combo_horizontalSpacing">8dip</dimen>
+</resources>
diff --git a/res/values-xlarge/dimensions.xml b/res/values-xlarge/dimensions.xml
new file mode 100644
index 0000000..27c1ce2
--- /dev/null
+++ b/res/values-xlarge/dimensions.xml
@@ -0,0 +1,29 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ Copyright (C) 2010 The Android Open Source Project Licensed under the
+ Apache License, Version 2.0 (the "License"); you may not use this file
+ except in compliance with the License. You may obtain a copy of the
+ License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+ applicable law or agreed to in writing, software distributed under the
+ License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+ CONDITIONS OF ANY KIND, either express or implied. See the License for
+ the specific language governing permissions and limitations under the
+ License.
+-->
+<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <dimen name="bookmarkThumbnailWidth">180dip</dimen>
+ <dimen name="bookmarkThumbnailHeight">120dip</dimen>
+ <dimen name="widgetThumbnailHeight">104dip</dimen>
+ <dimen name="widgetHorizontalSpacing">14dip</dimen>
+ <dimen name="widgetVerticalSpacing">12dip</dimen>
+ <dimen name="favicon_padded_size">28dip</dimen>
+ <!-- For the most visited page -->
+ <dimen name="mv_max_width">1010dp</dimen>
+ <dimen name="mv_item_width">231dp</dimen>
+ <dimen name="mv_item_width_portrait">213dp</dimen>
+ <dimen name="mv_border_width">3dp</dimen>
+ <!-- For the combined Bookmarks History view -->
+ <dimen name="combo_paddingTop">50dip</dimen>
+ <dimen name="combo_paddingLeftRight">134dip</dimen>
+ <dimen name="combo_horizontalSpacing">20dip</dimen>
+</resources>
diff --git a/res/values-xlarge/strings.xml b/res/values-xlarge/strings.xml
new file mode 100644
index 0000000..92646a4
--- /dev/null
+++ b/res/values-xlarge/strings.xml
@@ -0,0 +1,35 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <!-- Name of menu item of a new tab.
+ Also used in the title bar when displaying a new tab [CHAR LIMIT=30] -->
+ <string name="new_tab">New tab</string>
+ <!-- Name of menu item of a new incognito tab. Also used in the
+ title bar when displaying a new tab [CHAR LIMIT=30] -->
+ <string name="new_incognito_tab">New incognito tab</string>
+ <!-- Name of menu item which brings up a list of the currently active tabs -->
+ <string name="active_tabs">Tabs</string>
+ <!-- Context Menu item to open the currently selected link in a new
+ window. [CHAR LIMIT=30] -->
+ <string name="contextmenu_openlink_newwindow">Open in new tab</string>
+ <!-- Context Menu item to open the currently selected link in a new
+ background window. [CHAR LIMIT=50] -->
+ <string name="contextmenu_openlink_newwindow_background">Open in new background tab</string>
+ <!-- Context menu item to open every bookmark in a folder in new tabs [CHAR LIMIT=50] -->
+ <string name="open_all_in_new_window">Open all in new tabs</string>
+ <!-- Settings summary CHAR LIMIT=50]-->
+ <string name="pref_content_open_in_background_summary">Open new tabs behind the current one</string>
+</resources>
diff --git a/res/values-xlarge/styles.xml b/res/values-xlarge/styles.xml
new file mode 100644
index 0000000..473b170
--- /dev/null
+++ b/res/values-xlarge/styles.xml
@@ -0,0 +1,63 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+/*
+ *
+ * Copyright 2006,2007,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>
+ <style name="BrowserTheme" parent="@android:Theme.Holo">
+ <item name="android:windowBackground">@color/white</item>
+ <item name="android:colorBackground">#FFFFFFFF</item>
+ <item name="android:windowActionBar">true</item>
+ <item name="android:windowNoTitle">false</item>
+ <item name="android:actionBarStyle">@style/ActionBarStyle</item>
+ <item name="android:actionButtonStyle">@style/ActionButton</item>
+ </style>
+ <style name="Dialog" parent="@android:style/Theme.Holo.Dialog" >
+ <item name="android:windowActionBar">false</item>
+ </style>
+ <style name="BookmarkTheme" parent="@android:Theme.Holo">
+ <item name="android:windowActionBar">false</item>
+ <item name="android:windowNoTitle">true</item>
+ <item name="android:colorBackgroundCacheHint">@null</item>
+ <item name="android:windowFrame">@null</item>
+ <item name="android:windowContentOverlay">@null</item>
+ <item name="android:windowIsFloating">true</item>
+ <item name="android:backgroundDimEnabled">false</item>
+ <item name="android:windowIsTranslucent">true</item>
+ </style>
+ <style name="ShortCutTheme" parent="@android:Theme.Holo">
+ </style>
+ <style name="ActionBarStyle">
+ <item name="android:height">56dip</item>
+ <item name="android:background">@drawable/bg_browsertabs</item>
+ <item name="android:displayOptions"></item>
+ </style>
+ <style name="ActionButton">
+ <item name="android:background">?android:attr/selectableItemBackground</item>
+ </style>
+ <style name="Suggestions" parent="@android:style/Widget.Holo.Light.AutoCompleteTextView">
+ </style>
+ <style name="SuggestionLineMedium"
+ parent="@android:style/TextAppearance.Holo.Medium.Inverse">
+ <item name="android:textSize">16sp</item>
+ </style>
+ <style name="SuggestionLineSmall"
+ parent="@android:style/TextAppearance.Holo.Small.Inverse">
+ <item name="android:textSize">12sp</item>
+ </style>
+</resources>
diff --git a/res/values-zh-rCN-xlarge/strings.xml b/res/values-zh-rCN-xlarge/strings.xml
new file mode 100644
index 0000000..b64a476
--- /dev/null
+++ b/res/values-zh-rCN-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"新建标签页"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"新建隐身标签页"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"标签页"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"在新标签页中打开"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"在新的后台标签页中打开"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"在新标签页中打开全部书签"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"在当前标签页后方打开新标签页"</string>
+</resources>
diff --git a/res/values-zh-rCN/strings.xml b/res/values-zh-rCN/strings.xml
index 41fa828..16bee5c 100644
--- a/res/values-zh-rCN/strings.xml
+++ b/res/values-zh-rCN/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"浏览器"</string>
<string name="choose_upload" msgid="3649366287575002063">"选择要上传的文件"</string>
<string name="new_tab" msgid="4505722538297295141">"新窗口"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"新隐身窗口"</string>
<string name="active_tabs" msgid="3050623868203544623">"窗口"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"书签"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"访问最多"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"浏览器"</string>
<string name="cancel" msgid="3017274947407233702">"取消"</string>
<string name="ok" msgid="1509280796718850364">"确定"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"没有匹配项"</item>
- <item quantity="one" msgid="4352019729062956802">"1 个匹配项"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> 个匹配项"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> 个匹配项"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"正在载入..."</string>
<string name="page_info" msgid="4048529256302257195">"网页信息"</string>
<string name="page_info_view" msgid="5303490449842635158">"查看网页信息"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"继续"</string>
<string name="security_warning" msgid="6607795404322797541">"安全警告"</string>
<string name="view_certificate" msgid="1472768887529093862">"查看证书"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"返回"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"该证书并非来自可信的授权中心。"</string>
<string name="ssl_mismatch" msgid="558688832420069896">"网站的名称与证书上的名称不一致。"</string>
<string name="ssl_expired" msgid="5739349389499575559">"该证书已过期。"</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"前进"</string>
<string name="save" msgid="5922311934992468496">"确定"</string>
<string name="do_not_save" msgid="6777633870113477714">"取消"</string>
- <string name="location" msgid="969988560160364559">"地点"</string>
- <string name="name" msgid="5990326151488445481">"姓名"</string>
+ <string name="location" msgid="3411848697912600125">"地址"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"添加到"</string>
+ <string name="new_folder" msgid="7743540149088867917">"新建文件夹"</string>
+ <string name="edit_folder" msgid="621817453133656156">"修改文件夹"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"删除文件夹"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"无子文件夹"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"书签"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"主屏幕"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"其他文件夹..."</string>
+ <string name="name" msgid="5462672162695365387">"标签"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"添加书签"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"添加到书签"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"将此页加为书签"</string>
+ <string name="remove" msgid="7820112494467011374">"删除"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"编辑书签"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"向主屏幕添加快捷方式"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"向主屏幕添加快捷方式"</string>
<string name="open_bookmark" msgid="8473581305759935790">"打开"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"删除书签"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"从书签中删除"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"无法将此网址添加到书签。"</string>
<string name="delete_bookmark" msgid="2422989994934201992">"删除"</string>
<string name="bookmark_page" msgid="6845189305130307274">"将上次查看过的网页加为书签"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"缩略图视图"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"列表视图"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"缩略图"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"列表"</string>
<string name="current_page" msgid="7510129573681663135">"来源 "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"将会删除书签“<xliff:g id="BOOKMARK">%s</xliff:g>”。"</string>
<string name="open_in_new_window" msgid="6596775546468054510">"在新窗口中打开"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"在新窗口中打开全部书签"</string>
<string name="goto_dot" msgid="3895839050522602723">"转至"</string>
- <string name="find_dot" msgid="6259312434696611957">"页内查找"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"打开新的隐身标签页"</string>
<string name="select_dot" msgid="6299170761900561967">"选择文本"</string>
<string name="tab_picker_title" msgid="864478399057782913">"当前窗口"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"关闭"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"下载内容"</string>
<string name="copy_page_url" msgid="7635062169011319208">"复制网页网址"</string>
<string name="share_page" msgid="593756995297268343">"分享网页"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"另存为网络存档"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"网络存档已保存。"</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"无法保存网络存档。"</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> 个书签"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"空文件夹"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"打开"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"在新窗口中打开"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"将链接加入书签"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"在新的后台窗口中打开"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"保存链接"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"分享链接"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"复制"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"设置主页"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"设置搜索引擎"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"选择搜索引擎"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"使用当前页面"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"设置为..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"当前页"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"空白页"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"默认页"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"自动调整页面"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"调整网页版面以适合屏幕大小"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"仅以横向模式显示"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"仅以横向宽屏模式显示网页"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"隐私权设置"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"常规"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"同步"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"自动填充"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"与谷歌浏览器同步"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"在 Android 浏览器和谷歌浏览器之间共享书签和其他数据"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google 帐户"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"同步书签"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"在 Android 浏览器和谷歌浏览器之间同步书签"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"开始同步"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"选择要与其共享数据的 Google 帐户"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"表单自动填充"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"只需点击一下,即可填完网络表单"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"自动填充设置"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"设置和管理自动填充表单的数据"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"自动登录 Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"未找到帐户"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"使用 <xliff:g id="ID_1">%s</xliff:g> 自动登录 Google 网站"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"使用 <xliff:g id="ID_1">%s</xliff:g> 登录 Google 网站"\n"您的“隐私权与安全”设置会控制 Google 自动登录功能"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"不自动登录"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"只需点击一下,自动填充功能即可使用您的个人资料帮助您完成网络表单。"</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"全名:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"电子邮件地址:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"公司名称:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"地址行 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"街道地址、邮政信箱、转交"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"地址行 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"公寓、套房、单元、楼栋、楼层等等。"</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"城市/乡镇:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"州或省/直辖市/自治区:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"邮政编码:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"国家/地区:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"电话:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"电话号码无效"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"保存个人资料"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"个人资料已保存"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"个人资料已删除"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"删除个人资料"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"浏览器可自动填充网络表单(例如该表单)。您希望设置个人资料吗?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"您可以随时通过“浏览器设置”对自动填充功能进行配置。"</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"停用自动填充"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"隐私与安全"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"清除缓存"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"清除存储在本地缓存中的内容和数据库"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"此操作将会刪除存储在本地缓存中的内容和数据库。"</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookie"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"清除所有 Cookie 数据"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"清除所有浏览器 Cookie"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"此操作将会删除所有 Cookie。"</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"清除历史记录"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"清除浏览器导航历史记录"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"此操作将会删除浏览器导航历史记录。"</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"表单数据"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"清除表单数据"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"清除所有已保存的表单数据"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"此操作将会删除所有已保存的表单数据。"</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"清除密码"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"清除所有保存的密码"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"此操作将会刪除所有已保存的密码。"</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"位置"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"启用位置信息功能"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"允许网站访问您的位置信息"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"取消位置信息访问权限"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"取消所有网站访问位置信息的权限"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"取消所有网站访问位置信息的权限"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"安全设置"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"密码"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"记住密码"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"保存网站的用户名和密码"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"记住表单数据"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"默认缩放设置"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"以概览模式打开网页"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"显示新打开网页的概览"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"高级设置"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"高级"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"网站设置"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"各网站的高级设置"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"重置默认设置"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"重置为默认设置"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"还原默认设置"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"设置将恢复为默认值。"</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"日语 (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"日语 (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"日语 (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"韩语 (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"文字编码"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"实验室"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"快速控制"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"从左侧或右侧边缘滑动拇指以使用快速控制"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"“访问最多”首页"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"设置您的主页,以显示访问最多的页面。"</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"数据连接性问题"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"文件有问题"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"确认"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"删除所有数据"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"取消"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"正在设置壁纸..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"书签"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"无书签"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"选择帐户"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"与 Google 帐户同步"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"Android 书签尚未与 Google 帐户关联"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"删除 Android 书签"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"将 Android 书签添加到 <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g> 的书签中"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"分享"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"没有更多标签可用"</string>
</resources>
diff --git a/res/values-zh-rTW-xlarge/strings.xml b/res/values-zh-rTW-xlarge/strings.xml
new file mode 100644
index 0000000..32c2158
--- /dev/null
+++ b/res/values-zh-rTW-xlarge/strings.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+ -->
+
+<resources xmlns:android="http://schemas.android.com/apk/res/android"
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <string name="new_tab" msgid="7275656655054293038">"新分頁"</string>
+ <string name="new_incognito_tab" msgid="5149742197322201152">"新無痕式分頁"</string>
+ <string name="active_tabs" msgid="5324492165541331128">"分頁"</string>
+ <string name="contextmenu_openlink_newwindow" msgid="1061831678814826192">"於新分頁開啟連結"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5625314148071601758">"在新背景分頁中開啟連結"</string>
+ <string name="open_all_in_new_window" msgid="8498279523071618315">"於新分頁開啟所有書籤"</string>
+ <string name="pref_content_open_in_background_summary" msgid="7653600574808720292">"在目前分頁的後面開啟新分頁"</string>
+</resources>
diff --git a/res/values-zh-rTW/strings.xml b/res/values-zh-rTW/strings.xml
index 5d4201a..e5df8ec 100644
--- a/res/values-zh-rTW/strings.xml
+++ b/res/values-zh-rTW/strings.xml
@@ -19,6 +19,7 @@
<string name="application_name" msgid="1935869255545976415">"瀏覽器"</string>
<string name="choose_upload" msgid="3649366287575002063">"選擇要上載的檔案"</string>
<string name="new_tab" msgid="4505722538297295141">"新視窗"</string>
+ <string name="new_incognito_tab" msgid="5821404839654751753">"新的無痕式視窗"</string>
<string name="active_tabs" msgid="3050623868203544623">"視窗"</string>
<string name="tab_bookmarks" msgid="2305793036003473653">"書籤"</string>
<string name="tab_most_visited" msgid="1077402532455000703">"常用網頁"</string>
@@ -32,12 +33,6 @@
<string name="bookmarks_search" msgid="5229596268214362873">"瀏覽器"</string>
<string name="cancel" msgid="3017274947407233702">"取消"</string>
<string name="ok" msgid="1509280796718850364">"確定"</string>
- <plurals name="matches_found">
- <item quantity="zero" msgid="6242659159545399963">"沒有相配項"</item>
- <item quantity="one" msgid="4352019729062956802">"1 個相配項"</item>
- <item quantity="few" msgid="5544267486978946555">"<xliff:g id="NUMBER">%d</xliff:g> 個相符項目"</item>
- <item quantity="other" msgid="6616125067364315405">"<xliff:g id="NUMBER">%d</xliff:g> 個相符項目"</item>
- </plurals>
<string name="title_bar_loading" msgid="7438217780834640678">"載入中..."</string>
<string name="page_info" msgid="4048529256302257195">"頁面資訊"</string>
<string name="page_info_view" msgid="5303490449842635158">"檢視頁面資訊"</string>
@@ -46,6 +41,7 @@
<string name="ssl_continue" msgid="8031515015829358457">"繼續"</string>
<string name="security_warning" msgid="6607795404322797541">"安全性警告"</string>
<string name="view_certificate" msgid="1472768887529093862">"檢視憑證"</string>
+ <string name="ssl_go_back" msgid="4598951822061593819">"返回"</string>
<string name="ssl_untrusted" msgid="5369967226521102194">"此憑證來自未信任的機構。"</string>
<string name="ssl_mismatch" msgid="558688832420069896">"網站名稱與憑證不符。"</string>
<string name="ssl_expired" msgid="5739349389499575559">"此憑證已過期"</string>
@@ -67,12 +63,22 @@
<string name="forward" msgid="4288210890526641577">"下一頁"</string>
<string name="save" msgid="5922311934992468496">"確定"</string>
<string name="do_not_save" msgid="6777633870113477714">"取消"</string>
- <string name="location" msgid="969988560160364559">"位置"</string>
- <string name="name" msgid="5990326151488445481">"名稱"</string>
+ <string name="location" msgid="3411848697912600125">"地址"</string>
+ <string name="containing_folder" msgid="6771180232953030479">"新增至"</string>
+ <string name="new_folder" msgid="7743540149088867917">"新資料夾"</string>
+ <string name="edit_folder" msgid="621817453133656156">"編輯資料夾"</string>
+ <string name="delete_folder" msgid="2046483129024501116">"刪除資料夾"</string>
+ <string name="no_subfolders" msgid="5880411440592452802">"沒有子資料夾"</string>
+ <string name="add_to_bookmarks_menu_option" msgid="4449323955122214389">"書籤"</string>
+ <string name="add_to_homescreen_menu_option" msgid="1461447829242963790">"主螢幕"</string>
+ <string name="add_to_other_folder_menu_option" msgid="5450890093372998187">"其他資料夾..."</string>
+ <string name="name" msgid="5462672162695365387">"標籤"</string>
<string name="http" msgid="2163722670597250102">"http://"</string>
- <string name="save_to_bookmarks" msgid="588165100024086565">"新增書籤"</string>
+ <string name="save_to_bookmarks" msgid="6101482434920313244">"加入書籤"</string>
+ <string name="bookmark_this_page" msgid="7530739804320811054">"將這個網頁加入書籤"</string>
+ <string name="remove" msgid="7820112494467011374">"移除"</string>
<string name="edit_bookmark" msgid="5024089053490231905">"編輯書籤"</string>
- <string name="create_shortcut_bookmark" msgid="9202323987633899835">"新增捷徑至主螢幕"</string>
+ <string name="create_shortcut_bookmark" msgid="1995095662095484289">"新增捷徑至主螢幕"</string>
<string name="open_bookmark" msgid="8473581305759935790">"開啟"</string>
<string name="remove_bookmark" msgid="8407495852801410891">"刪除書籤"</string>
<string name="remove_from_bookmarks" msgid="4374080666576982775">"從書籤中移除"</string>
@@ -87,13 +93,14 @@
<string name="bookmark_cannot_save_url" msgid="791722768778386941">"無法將此網址加入書籤。"</string>
<string name="delete_bookmark" msgid="2422989994934201992">"刪除"</string>
<string name="bookmark_page" msgid="6845189305130307274">"將最後瀏覽的網頁加入書籤"</string>
- <string name="switch_to_thumbnails" msgid="5493351529609043151">"縮圖檢視"</string>
- <string name="switch_to_list" msgid="8900531247982121055">"清單檢視"</string>
+ <string name="bookmark_thumbnail_view" msgid="3164068314718522138">"縮圖"</string>
+ <string name="bookmark_list_view" msgid="7848510619500937839">"清單"</string>
<string name="current_page" msgid="7510129573681663135">"來源 "</string>
<string name="delete_bookmark_warning" msgid="758043186202032205">"刪除「<xliff:g id="BOOKMARK">%s</xliff:g>」書籤?"</string>
<string name="open_in_new_window" msgid="6596775546468054510">"在新視窗開啟"</string>
+ <string name="open_all_in_new_window" msgid="6514602245828366045">"於新視窗開啟所有書籤"</string>
<string name="goto_dot" msgid="3895839050522602723">"前往"</string>
- <string name="find_dot" msgid="6259312434696611957">"在頁面中尋找"</string>
+ <string name="incognito_tab" msgid="5419458065370134289">"開啟新的無痕式分頁"</string>
<string name="select_dot" msgid="6299170761900561967">"選取文字"</string>
<string name="tab_picker_title" msgid="864478399057782913">"目前視窗"</string>
<string name="tab_picker_remove_tab" msgid="630087809802479397">"關閉"</string>
@@ -103,9 +110,14 @@
<string name="menu_view_download" msgid="2124570321712995120">"下載"</string>
<string name="copy_page_url" msgid="7635062169011319208">"複製網頁網址"</string>
<string name="share_page" msgid="593756995297268343">"分享網頁"</string>
+ <string name="menu_save_webarchive" msgid="3934652434001459581">"另存為網頁封存"</string>
+ <string name="webarchive_saved" msgid="7045250341467345007">"已儲存網頁封存。"</string>
+ <string name="webarchive_failed" msgid="2880998204746620260">"無法儲存網頁封存。"</string>
+ <string name="contextheader_folder_bookmarkcount" msgid="353987136645619089">"<xliff:g id="BOOKMARK_COUNT">%d</xliff:g> 個書籤"</string>
+ <string name="contextheader_folder_empty" msgid="974171637803391651">"空資料夾"</string>
<string name="contextmenu_openlink" msgid="7237961252214188935">"開啟"</string>
<string name="contextmenu_openlink_newwindow" msgid="992765050093960353">"在新視窗開啟"</string>
- <string name="contextmenu_bookmark_thislink" msgid="8095373680616870021">"將連結加入書籤"</string>
+ <string name="contextmenu_openlink_newwindow_background" msgid="5556131402560251639">"在新背景視窗中開啟連結"</string>
<string name="contextmenu_savelink" msgid="5508554930832538184">"儲存連結"</string>
<string name="contextmenu_sharelink" msgid="5392275392280130331">"分享連結"</string>
<string name="contextmenu_copy" msgid="398860586635404030">"複製"</string>
@@ -138,33 +150,77 @@
<string name="pref_content_homepage" msgid="6082437160778559806">"設定首頁"</string>
<string name="pref_content_search_engine" msgid="1620101310821644144">"設定搜尋引擎"</string>
<string name="pref_content_search_engine_summary" msgid="5162667665858487316">"選取搜尋引擎"</string>
- <string name="pref_use_current" msgid="1493179933653044553">"使用目前的網頁"</string>
+ <string name="pref_set_homepage_to" msgid="7196350233061395098">"設為..."</string>
+ <string name="pref_use_current" msgid="1778622474040406672">"目前網頁"</string>
+ <string name="pref_use_blank" msgid="8503238592551111169">"空白網頁"</string>
+ <string name="pref_use_default" msgid="192587563274735878">"預設網頁"</string>
<string name="pref_content_autofit" msgid="8260474534053660809">"自動調整頁面"</string>
<string name="pref_content_autofit_summary" msgid="4587831659894879986">"配合螢幕大小調整網頁版面"</string>
- <string name="pref_content_landscape_only" msgid="2022546812766219672">"僅以水平模式顯示"</string>
- <string name="pref_content_landscape_only_summary" msgid="1008238895535428855">"僅以橫向寬螢幕瀏覽模式顯示網頁"</string>
- <string name="pref_privacy_title" msgid="1052470980370846151">"隱私設定"</string>
+ <string name="pref_general_title" msgid="1946872771219249323">"一般設定"</string>
+ <string name="pref_general_sync_title" msgid="3138637035975860324">"同步處理"</string>
+ <string name="pref_general_autofill_title" msgid="64638897890112873">"自動填入功能"</string>
+ <string name="pref_personal_sync_with_chrome" msgid="1695182180332194033">"與Google 瀏覽器保持同步"</string>
+ <string name="pref_personal_sync_with_chrome_summary" msgid="7414133931827321055">"共享「Android 瀏覽器」和「Google 瀏覽器」之間的書籤及其他資料"</string>
+ <string name="pref_personal_google_account" msgid="952360133341490071">"Google 帳戶"</string>
+ <string name="pref_personal_sync_bookmarks" msgid="59237515966184432">"同步處理書籤"</string>
+ <string name="pref_personal_sync_bookmarks_summary" msgid="4791767605662205482">"同步處理「Android 瀏覽器」和「Google 瀏覽器」之間的書籤"</string>
+ <string name="pref_personal_start_syncing" msgid="6046972042512655232">"開始同步"</string>
+ <string name="pref_personal_account_dialog_title" msgid="1390867119887955530">"請選取要與其共用的 Google 帳戶"</string>
+ <string name="pref_autofill_enabled" msgid="1174197447388234595">"表單自動填入"</string>
+ <string name="pref_autofill_enabled_summary" msgid="422640696197018914">"輕按一下即可填妥網頁表單"</string>
+ <string name="pref_autofill_profile_editor" msgid="1350709161524642663">"自動填入設定"</string>
+ <string name="pref_autofill_profile_editor_summary" msgid="6748434431641768870">"設定和管理自動填入的表單資料"</string>
+ <string name="pref_autologin_title" msgid="2362827272595366379">"自動登入 Google"</string>
+ <string name="pref_autologin_no_account" msgid="4409223615542478868">"找不到帳戶"</string>
+ <string name="pref_autologin_summary" msgid="8168866316823968574">"自動使用 <xliff:g id="ID_1">%s</xliff:g> 登入 Google 網站"</string>
+ <string name="pref_autologin_progress" msgid="8643826219376543293">"使用 <xliff:g id="ID_1">%s</xliff:g> 登入 Google 網站"\n"可讓您運用「隱私權與安全性」設定來控制 Google 自動登入程序"</string>
+ <string name="pref_autologin_disable" msgid="3342145058494577628">"不要自動登入"</string>
+ <string name="autofill_profile_editor_heading" msgid="5009490178189728877">"自動填入功能會運用您的設定檔,讓您輕按一下即可填妥網頁表單。"</string>
+ <string name="autofill_profile_editor_name" msgid="8566130291459685955">"全名:"</string>
+ <string name="autofill_profile_editor_email_address" msgid="7967585896612797173">"電子郵件:"</string>
+ <string name="autofill_profile_editor_company_name" msgid="2813443159949210417">"公司名稱:"</string>
+ <string name="autofill_profile_editor_address_line_1" msgid="836433242509243081">"地址行 1:"</string>
+ <string name="autofill_profile_editor_address_line_1_hint" msgid="5965659598509327172">"路街巷弄、郵政信箱、代收人"</string>
+ <string name="autofill_profile_editor_address_line_2" msgid="8194745202893822479">"地址行 2:"</string>
+ <string name="autofill_profile_editor_address_line_2_hint" msgid="2048330295853546405">"門牌號碼、樓層等"</string>
+ <string name="autofill_profile_editor_city" msgid="4193225955409148508">"市區鄉鎮:"</string>
+ <string name="autofill_profile_editor_state" msgid="8549739922338171458">"州/省/地區:"</string>
+ <string name="autofill_profile_editor_zip_code" msgid="283668573295656671">"郵遞區號:"</string>
+ <string name="autofill_profile_editor_country" msgid="7234470301239156656">"國家/地區:"</string>
+ <string name="autofill_profile_editor_phone_number" msgid="4938852821413729276">"電話:"</string>
+ <string name="autofill_profile_editor_phone_number_invalid" msgid="7166394872369167580">"無效的電話號碼"</string>
+ <string name="autofill_profile_editor_save_profile" msgid="8349915287435262888">"儲存設定檔"</string>
+ <string name="autofill_profile_successful_save" msgid="6834102203944938409">"設定檔已儲存"</string>
+ <string name="autofill_profile_successful_delete" msgid="2421442112954362732">"個人資料已刪除"</string>
+ <string name="autofill_profile_editor_delete_profile" msgid="2754563301088418752">"刪除設定檔"</string>
+ <string name="autofill_setup_dialog_message" msgid="6605682320156223114">"瀏覽器可以自動填寫這類網路表單,您要建立個人資料嗎?"</string>
+ <string name="autofill_setup_dialog_negative_toast" msgid="4337372830506338827">"您可隨時透過 [瀏覽器設定] 設定自動填入功能。"</string>
+ <string name="disable_autofill" msgid="3706426217720202898">"停用自動填入功能"</string>
+ <string name="pref_privacy_security_title" msgid="1705642466867300373">"隱私權與安全性"</string>
<string name="pref_privacy_clear_cache" msgid="3380316479925886998">"清除快取"</string>
<string name="pref_privacy_clear_cache_summary" msgid="2216463577207991454">"清除本機快取內容與資料庫"</string>
<string name="pref_privacy_clear_cache_dlg" msgid="5541011591300753881">"即將刪除本機快取內容與資料庫。"</string>
+ <string name="pref_privacy_cookies_title" msgid="6763274282214830526">"Cookie"</string>
<string name="pref_privacy_clear_cookies" msgid="3095583579133780331">"清除所有 Cookie"</string>
<string name="pref_privacy_clear_cookies_summary" msgid="6962742063990677520">"清除瀏覽器中所有 Cookie"</string>
<string name="pref_privacy_clear_cookies_dlg" msgid="552855688091432682">"即將刪除所有 Cookie。"</string>
<string name="pref_privacy_clear_history" msgid="8723795508825198477">"清除記錄"</string>
<string name="pref_privacy_clear_history_summary" msgid="6868501330708940734">"清除瀏覽記錄"</string>
<string name="pref_privacy_clear_history_dlg" msgid="544903007914753853">"即將刪除瀏覽器的瀏覽記錄。"</string>
+ <string name="pref_privacy_formdata_title" msgid="6549813837982050424">"表單資料"</string>
<string name="pref_privacy_clear_form_data" msgid="4232668196344383987">"清除表單資料"</string>
<string name="pref_privacy_clear_form_data_summary" msgid="1790390894719517167">"清除所有表單資料"</string>
<string name="pref_privacy_clear_form_data_dlg" msgid="4443621086781197928">"即將刪除所有已儲存的表單資料。"</string>
<string name="pref_privacy_clear_passwords" msgid="4750234112289277480">"清除密碼"</string>
<string name="pref_privacy_clear_passwords_summary" msgid="8856782718942903335">"清除所有已儲存密碼"</string>
<string name="pref_privacy_clear_passwords_dlg" msgid="2083869328824248255">"即將刪除所有儲存的密碼"</string>
+ <string name="pref_privacy_location_title" msgid="7458378016606081067">"位置"</string>
<string name="pref_privacy_enable_geolocation" msgid="1395040170290765686">"啟用定位功能"</string>
<string name="pref_privacy_enable_geolocation_summary" msgid="8437020934664306205">"允許網站向您要求位置資訊存取權"</string>
<string name="pref_privacy_clear_geolocation_access" msgid="6649680770030042980">"清除位置資訊存取權"</string>
<string name="pref_privacy_clear_geolocation_access_summary" msgid="7750143359497314679">"清除所有網站的位置資訊存取權"</string>
<string name="pref_privacy_clear_geolocation_access_dlg" msgid="7327063124488827244">"清除所有網站的位置資訊存取權"</string>
- <string name="pref_security_title" msgid="5763978646932160021">"安全性設定"</string>
+ <string name="pref_security_passwords_title" msgid="5734190542383756711">"密碼"</string>
<string name="pref_security_remember_passwords" msgid="6492957683454529549">"記住密碼"</string>
<string name="pref_security_remember_passwords_summary" msgid="256388703356349137">"儲存您的使用者名稱和密碼"</string>
<string name="pref_security_save_form_data" msgid="1213669802810198893">"儲存表單資料"</string>
@@ -191,9 +247,10 @@
<string name="pref_default_zoom_dialogtitle" msgid="6095974367125109021">"預設縮放"</string>
<string name="pref_content_load_page" msgid="2219810141690955452">"以總覽模式開啟網頁"</string>
<string name="pref_content_load_page_summary" msgid="8792093504054149369">"顯示新開啟網頁的總覽畫面"</string>
- <string name="pref_extras_title" msgid="3091250467679722382">"進階設定"</string>
+ <string name="pref_extras_title" msgid="7075456173747370647">"進階"</string>
<string name="pref_extras_website_settings" msgid="67866640052455549">"網站設定"</string>
<string name="pref_extras_website_settings_summary" msgid="1656771443223494406">"個別網站的進階設定"</string>
+ <string name="pref_extras_reset_default_title" msgid="3579760449455761762">"重設預設值"</string>
<string name="pref_extras_reset_default" msgid="8904000515846202110">"還原至初始設定"</string>
<string name="pref_extras_reset_default_summary" msgid="4247870778270414501">"還原預設設定"</string>
<string name="pref_extras_reset_default_dlg" msgid="6640261575874704022">"設定會還原為預設值。"</string>
@@ -208,8 +265,14 @@
<item msgid="891615911084608570">"日文 (ISO-2022-JP)"</item>
<item msgid="5589150448475151241">"日文 (SHIFT_JIS)"</item>
<item msgid="7356792686950371843">"日文 (EUC-JP)"</item>
+ <item msgid="2193955365569270096">"韓文 (EUC-KR)"</item>
</string-array>
<string name="pref_default_text_encoding_dialogtitle" msgid="5508255018084978547">"文字編碼"</string>
+ <string name="pref_lab_title" msgid="5571091610359629423">"研究室"</string>
+ <string name="pref_lab_quick_controls" msgid="2105979166017257647">"快速控制項"</string>
+ <string name="pref_lab_quick_controls_summary" msgid="8025196176636589803">"從左側或右側邊緣滑動拇指即可存取快速控制項"</string>
+ <string name="pref_lab_most_visited_homepage" msgid="547134501893835512">"以造訪最多的網頁為首頁"</string>
+ <string name="pref_lab_most_visited_homepage_summary" msgid="6857702350834122532">"將造訪次數最多的網頁設為您要顯示的首頁。"</string>
<string name="browserFrameNetworkErrorLabel" msgid="126892350904924893">"資料連線問題"</string>
<string name="browserFrameFileErrorLabel" msgid="8063691502792670367">"檔案有問題"</string>
<string name="browserFrameFormResubmitLabel" msgid="2685923472682180360">"確認"</string>
@@ -296,4 +359,14 @@
<string name="website_settings_clear_all_dialog_ok_button" msgid="6401582240627669431">"刪除所有資料"</string>
<string name="website_settings_clear_all_dialog_cancel_button" msgid="1896757051856611674">"取消"</string>
<string name="progress_dialog_setting_wallpaper" msgid="4871900779338536674">"設定桌布..."</string>
+ <string name="defaultBookmarksUpButton" msgid="2303951020715704735">"書籤"</string>
+ <string name="empty_bookmarks_folder" msgid="7843361614634930942">"沒有任何書籤"</string>
+ <string name="rlz_access_point" msgid="7165847807377650632">"Y1"</string>
+ <string name="account_chooser_dialog_title" msgid="3314204833188808194">"選擇帳戶"</string>
+ <string name="import_bookmarks_dialog_title" msgid="3325557652271172128">"與 Google 帳戶保持同步"</string>
+ <string name="import_bookmarks_dialog_description" msgid="2187665745413495303">"您的 Android 書籤未與任何 Google 帳戶建立關聯"</string>
+ <string name="import_bookmarks_dialog_remove" msgid="8105572409059113340">"移除您的 Android 書籤"</string>
+ <string name="import_bookmarks_dialog_import" msgid="6933613853573899218">"將您的 Android 書籤新增至 <xliff:g id="GOOGLE_ACCOUNT">%s</xliff:g> 的書籤"</string>
+ <string name="menu_share_url" msgid="5851814357333739700">"分享"</string>
+ <string name="max_tabs_warning" msgid="4122034303809457570">"已無分頁可供使用"</string>
</resources>
diff --git a/res/values/all_search_engines.xml b/res/values/all_search_engines.xml
index 08cf763..14aba39 100644
--- a/res/values/all_search_engines.xml
+++ b/res/values/all_search_engines.xml
@@ -208,9 +208,9 @@
<item>Google</item>
<item>google.com</item>
<item>http://www.google.com/favicon.ico</item>
- <item>http://www.google.com/m?hl={language}&ie={inputEncoding}&source=android-browser&q={searchTerms}</item>
+ <item>http://www.google.com/search?hl={language}&ie={inputEncoding}&source=android-browser&q={searchTerms}</item>
<item>UTF-8</item>
- <item>http://www.google.com/complete/search?hl={language}&json=true&q={searchTerms}</item>
+ <item>http://www.google.com/complete/search?hl={language}&client=android&q={searchTerms}</item>
</string-array>
<string-array name="bing_en_NZ" translatable="false">
<item>Bing</item>
diff --git a/res/values/bookmarks_icons.xml b/res/values/bookmarks_icons.xml
new file mode 100644
index 0000000..5d8e85a
--- /dev/null
+++ b/res/values/bookmarks_icons.xml
@@ -0,0 +1,33 @@
+<?xml version="1.0" encoding="utf-8"?>
+<resources>
+ <array name="bookmark_preloads">
+ <item>@raw/favicon_google</item>
+ <item>@raw/thumb_google</item>
+ <item>@raw/favicon_picasa</item>
+ <item>@raw/thumb_picasa</item>
+ <item>@raw/favicon_yahoo</item>
+ <item>@raw/thumb_yahoo</item>
+ <item>@raw/favicon_msn</item>
+ <item>@raw/thumb_msn</item>
+ <item>@raw/favicon_twitter</item>
+ <item>@raw/thumb_twitter</item>
+ <item>@raw/favicon_facebook</item>
+ <item>@raw/thumb_facebook</item>
+ <item>@raw/favicon_wikipedia</item>
+ <item>@raw/thumb_wikipedia</item>
+ <item>@raw/favicon_ebay</item>
+ <item>@raw/thumb_ebay</item>
+ <item>@raw/favicon_cnn</item>
+ <item>@raw/thumb_cnn</item>
+ <item>@raw/favicon_nytimes</item>
+ <item>@raw/thumb_nytimes</item>
+ <item>@raw/favicon_espn</item>
+ <item>@raw/thumb_espn</item>
+ <item>@raw/favicon_amazon</item>
+ <item>@raw/thumb_amazon</item>
+ <item>@raw/favicon_weatherchannel</item>
+ <item>@raw/thumb_weatherchannel</item>
+ <item>@raw/favicon_bbc</item>
+ <item>@raw/thumb_bbc</item>
+ </array>
+</resources>
diff --git a/res/values/colors.xml b/res/values/colors.xml
index 68bf253..68b58f7 100644
--- a/res/values/colors.xml
+++ b/res/values/colors.xml
@@ -20,19 +20,19 @@
<!-- FIXME: Change the name of this file! It is now being used generically
for the browser -->
<resources>
- <color name="username_text">#ffffffff</color>
- <color name="username_edit">#ff000000</color>
-
- <color name="password_text">#ffffffff</color>
- <color name="password_edit">#ff000000</color>
-
- <color name="ssl_text_label">#ffffffff</color>
- <color name="ssl_text_value">#ffffffff</color>
-
<color name="white">#ffffffff</color>
<color name="black">#ff000000</color>
-
-
<color name="geolocation_permissions_prompt_background">#ffdddddd</color>
+
+ <color name="bookmarkWidgetHeader">#383847</color>
+ <color name="bookmarkWidgetDivider">#383847</color>
+ <color name="bookmarkWidgetItemBackground">#2b2b3c</color>
+ <color name="bookmarkWidgetFolderBackground">#A0383847</color>
+ <color name="qc_slice_normal">#E0A0A0A0</color>
+ <color name="qc_slice_active">#E02090FF</color>
+ <color name="bookmarkWidgetFaviconBackground">#23ffffff</color>
+ <color name="bookmarkListFaviconBackground">#23ffffff</color>
+ <color name="urlTextColor">#0E774A</color>
+ <color name="tabFaviconBackground">#FF555555</color>
</resources>
diff --git a/res/values/dimensions.xml b/res/values/dimensions.xml
new file mode 100644
index 0000000..300714b
--- /dev/null
+++ b/res/values/dimensions.xml
@@ -0,0 +1,48 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ Copyright (C) 2010 The Android Open Source Project Licensed under the
+ Apache License, Version 2.0 (the "License"); you may not use this file
+ except in compliance with the License. You may obtain a copy of the
+ License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+ applicable law or agreed to in writing, software distributed under the
+ License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+ CONDITIONS OF ANY KIND, either express or implied. See the License for
+ the specific language governing permissions and limitations under the
+ License.
+-->
+<resources
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <!-- The width of a selected tab -->
+ <dimen name="tab_width_selected">280dp</dimen>
+ <!-- The width of an unselected tab -->
+ <dimen name="tab_width_unselected">240dp</dimen>
+ <dimen name="tab_height">44dp</dimen>
+ <dimen name="tab_overlap">8dp</dimen>
+ <dimen name="tab_addoverlap">14dp</dimen>
+ <dimen name="tab_slice">15.5dp</dimen>
+ <dimen name="tab_padding">16dp</dimen>
+ <dimen name="max_tab_width">300dp</dimen>
+ <dimen name="bookmarkThumbnailWidth">90dip</dimen>
+ <dimen name="bookmarkThumbnailHeight">80dip</dimen>
+ <dimen name="add_bookmark_width">500dip</dimen>
+ <dimen name="folder_selector_height">230dip</dimen>
+ <dimen name="widgetItemMinHeight">48dip</dimen>
+ <dimen name="favicon_size">16dip</dimen>
+ <dimen name="favicon_padded_size">20dip</dimen>
+ <dimen name="qc_radius">130dip</dimen>
+ <dimen name="qc_radius_inc">100dip</dimen>
+ <dimen name="qc_slop">15dip</dimen>
+ <dimen name="bookmark_widget_thumb_size">32dip</dimen>
+ <dimen name="bookmark_widget_favicon_size">26dip</dimen>
+ <!-- For the most visited page -->
+ <dimen name="mv_max_width">830dp</dimen>
+ <dimen name="mv_item_width">96dp</dimen>
+ <dimen name="mv_item_width_portrait">96dp</dimen>
+ <dimen name="mv_border_width">3dp</dimen>
+ <dimen name="tab_padding_top">12dp</dimen>
+ <dimen name="tab_first_padding_left">12dp</dimen>
+ <dimen name="list_favicon_padding">5dip</dimen>
+ <dimen name="list_favicon_corner_radius">3dip</dimen>
+ <dimen name="tab_favicon_corner_radius">2dip</dimen>
+ <dimen name="dropdown_offset">8dip</dimen>
+</resources>
diff --git a/res/values/integers.xml b/res/values/integers.xml
new file mode 100644
index 0000000..a0b7ae3
--- /dev/null
+++ b/res/values/integers.xml
@@ -0,0 +1,26 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!--
+ Copyright (C) 2010 The Android Open Source Project Licensed under the
+ Apache License, Version 2.0 (the "License"); you may not use this file
+ except in compliance with the License. You may obtain a copy of the
+ License at http://www.apache.org/licenses/LICENSE-2.0 Unless required by
+ applicable law or agreed to in writing, software distributed under the
+ License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR
+ CONDITIONS OF ANY KIND, either express or implied. See the License for
+ the specific language governing permissions and limitations under the
+ License.
+-->
+<resources
+ xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
+ <!-- The number of lines in the suggestions dropdown in landscape -->
+ <integer name="max_suggest_lines_landscape">5</integer>
+ <!-- The number of lines in the suggestions dropdown in portrait -->
+ <integer name="max_suggest_lines_portrait">12</integer>
+ <!-- The maximum number of open tabs -->
+ <integer name="max_tabs">16</integer>
+ <!-- The duration of the tab animations in millisecs -->
+ <integer name="tab_animation_duration">200</integer>
+ <integer name="max_width_crumb">200</integer>
+ <!-- The maximum number of most visited URLs in the history tab -->
+ <integer name="most_visits_limit">10</integer>
+</resources>
diff --git a/res/values/strings.xml b/res/values/strings.xml
index fc0d68b..75762a0 100644
--- a/res/values/strings.xml
+++ b/res/values/strings.xml
@@ -20,6 +20,9 @@
<string name="choose_upload">Choose file for upload</string>
<!-- Name of menu item of a new tab. Also used in the title bar when displaying a new tab -->
<string name="new_tab">New window</string>
+ <!-- Name of menu item of a new incognito tab. Also used in the
+ title bar when displaying a new tab [CHAR LIMIT=30] -->
+ <string name="new_incognito_tab">New incognito window</string>
<!-- Name of menu item which brings up a list of the currently active tabs -->
<string name="active_tabs">Windows</string>
<!-- Name of tab containing bookmarks -->
@@ -44,25 +47,11 @@
<string name="action">Sign in</string>
<!-- The name of the bookmarks and history search suggestion source. -->
<string name="bookmarks_search">Browser</string>
-
<!-- Label for a cancel button. It is used for multiple cancel buttons in different contexts -->
<string name="cancel">Cancel</string>
<!-- Label for a confirm button. Used in multiple contexts. -->
<string name="ok">OK</string>
- <!-- Displayed on the Find dialog to display the number of matches
- found in the current page. -->
- <plurals name="matches_found">
- <!-- Case of no matches -->
- <item quantity="zero">No matches</item>
- <!-- Case of one match -->
- <item quantity="one">1 match</item>
- <!-- Case of "few" (two) matches -->
- <item quantity="few"><xliff:g id="number" example="2">%d</xliff:g> matches</item>
- <!-- Case of several matches -->
- <item quantity="other"><xliff:g id="number" example="137">%d</xliff:g> matches</item>
- </plurals>
-
<!-- Displayed on the title bar while the page is loading -->
<string name="title_bar_loading">Loading\u2026</string>
@@ -86,6 +75,9 @@
<!-- Label for a button on an SSL error dialog that lets the user view the
certificate -->
<string name="view_certificate">View certificate</string>
+ <!-- Label for a button on an SSL error dialog that lets the user go back to
+ the last page they were on instead of continuing to the new page. [CHAR-LIMIT=20] -->
+ <string name="ssl_go_back">Go back</string>
<!-- Message in an SSL Error dialog -->
<string name="ssl_untrusted">This certificate is not from a trusted authority.</string>
@@ -133,17 +125,39 @@
<!-- Button label to cancel saving a bookmark. -->
<string name="do_not_save">Cancel</string>
<!-- Field label in Bookmark dialog box: refers to URL of the page to bookmark -->
- <string name="location">Location</string>
+ <string name="location">Address</string>
+ <!-- Field label in Bookmark dialog box: refers to the folder in which to save the bookmark -->
+ <string name="containing_folder">Add to</string>
+ <!-- Default name for a new folder and label for a button that allows the user to create a new folder
+ in the add bookmark dialog -->
+ <string name="new_folder">New folder</string>
+ <!-- Context menu item to edit a folder [CHAR LIMIT=50] -->
+ <string name="edit_folder">Edit folder</string>
+ <!-- Context menu item to delete a folder [CHAR LIMIT=50] -->
+ <string name="delete_folder">Delete folder</string>
+ <!-- Label stating that the currently open folder has no subfolders
+ in the add bookmark dialog [CHAR-LIMIT=none]-->
+ <string name="no_subfolders">No subfolders</string>
+ <!-- Menu item to use the top level bookmarks folder to save a bookmark in. [CHAR-LIMIT=30]-->
+ <string name="add_to_bookmarks_menu_option">Bookmarks</string>
+ <!-- Menu item to save the newly created bookmark to the home screen. [CHAR-LIMIT=30]-->
+ <string name="add_to_homescreen_menu_option">Home screen</string>
+ <!-- Menu item to open a picker to determine which folder to save a bookmark in. [CHAR-LIMIT=30]-->
+ <string name="add_to_other_folder_menu_option">Other folder\u2026</string>
<!-- Field label in Bookmark dialog box: title that the user wishes to use for the bookmark -->
- <string name="name">Name</string>
+ <string name="name">Label</string>
<!-- Initial value in Location field in Bookmark dialog box -->
<string name="http">http://</string>
- <!-- Menu item that opens a dialog to save a bookmark, initialized with the current page -->
- <string name="save_to_bookmarks">Add bookmark</string>
+ <!-- Menu item that opens a dialog to save a bookmark for the current page [CHAR LIMIT=30] -->
+ <string name="save_to_bookmarks">Add to Bookmarks</string>
+ <!-- Title of the dialog to bookmark a page -->
+ <string name="bookmark_this_page">Bookmark this page</string>
+ <!-- Option on bookmark dialog to remove the bookmark [CHAR LIMIT=30] -->
+ <string name="remove">Remove</string>
<!-- Menu item on the bookmarks page, to edit an existing bookmark -->
<string name="edit_bookmark">Edit bookmark</string>
- <!-- Context menu item to create a shortcut to the bookmark on the desktop -->
- <string name="create_shortcut_bookmark">Add shortcut to Home</string>
+ <!-- Context menu item to create a shortcut to the bookmark on the desktop [CHAR LIMIT=50] -->
+ <string name="create_shortcut_bookmark">Add shortcut to home</string>
<!-- Context menu item to open the currently highlighted bookmark -->
<string name="open_bookmark">Open</string>
<!-- Menu item to remove the currently highlighted bookmark-->
@@ -176,11 +190,11 @@
showing. -->
<string name="bookmark_page">Bookmark last-viewed page</string>
<!-- Menu item in the page that displays all bookmarks. Switches to
- a grid view which shows thumbnails -->
- <string name="switch_to_thumbnails">Thumbnail view</string>
+ a grid view which shows thumbnails [CHAR LIMIT=20] -->
+ <string name="bookmark_thumbnail_view">Thumbnails</string>
<!-- Menu item in the page that displays all bookmarks. Switches to a
- list view which shows titles -->
- <string name="switch_to_list">List view</string>
+ list view which shows titles [CHAR LIMIT=20] -->
+ <string name="bookmark_list_view">List</string>
<!-- Summary text under the New Bookmark item on the Bookmarks screen.
Tells the user that if they select this item, it will bring up a
dialog to bookmark the page that the browser is currently viewing,
@@ -192,11 +206,12 @@
<string name="delete_bookmark_warning">Bookmark \"<xliff:g id="bookmark">%s</xliff:g>\" will be deleted.</string>
<!-- Context Menu item to open the selected link in a new window -->
<string name="open_in_new_window">Open in new window</string>
+ <!-- Context menu item to open every bookmark in a folder in new windows [CHAR LIMIT=50] -->
+ <string name="open_all_in_new_window">Open all in new windows</string>
<!-- Menu item to open a dialog which allows the user to enter a url or do search-->
<string name="goto_dot">Go</string>
- <!-- Menu item that opens up a dialog which allows the user to provide a
- string and search for it on the page. -->
- <string name="find_dot">Find on page</string>
+ <!-- Menu item that opens up a new incognito tab. [CHAR LIMIT=30] -->
+ <string name="incognito_tab">Open new incognito tab</string>
<!-- Menu item to switch to text selection mode for copy and paste. -->
<string name="select_dot">Select text</string>
<!-- Title of current windows screen; appears in title bar -->
@@ -217,20 +232,30 @@
<string name="copy_page_url">Copy page url</string>
<!-- Menu item -->
<string name="share_page">Share page</string>
+ <!-- Menu item for saving a page as a web archive. -->
+ <string name="menu_save_webarchive">Save as Web Archive</string>
+ <!-- Toast informing the user that the page has been saved. -->
+ <string name="webarchive_saved">Web archive saved.</string>
+ <!-- Toast informing the user that saving the page has failed. -->
+ <string name="webarchive_failed">Failed to save web archive.</string>
+ <!-- The number of bookmarks in a folder [CHAR LIMT=50] -->
+ <string name="contextheader_folder_bookmarkcount"><xliff:g id="bookmark_count">%d</xliff:g> bookmarks</string>
+ <!-- No bookmarks in the folder [CHAR LIMIT=50] -->
+ <string name="contextheader_folder_empty">Empty folder</string>
<!-- Context Menu item open the currently selected link in the current
window.-->
<string name="contextmenu_openlink">Open</string>
<!-- Context Menu item to open the currently selected link in a new
window. -->
<string name="contextmenu_openlink_newwindow">Open in new window</string>
- <!-- Context Menu item to create a bookmark for the url of the currently
- selected link. -->
- <string name="contextmenu_bookmark_thislink">Bookmark link</string>
+ <!-- Context Menu item to open the currently selected link in a new
+ background window. [CHAR LIMIT=50] -->
+ <string name="contextmenu_openlink_newwindow_background">Open in new background window</string>
<!-- Context Menu item to save the webpage referred to by this link to the
SD card (external storage) -->
<string name="contextmenu_savelink">Save link</string>
<!-- Context Menu item to send the url of the selected link to someone else,
- via Gmail or another app -->
+ via Gmail or another app [CHAR LIMIT=50] -->
<string name="contextmenu_sharelink">Share link</string>
<!-- Context Menu item -->
<string name="contextmenu_copy">Copy</string>
@@ -301,7 +326,7 @@
<item>ON_DEMAND</item>
<item>OFF</item>
</string-array>
- <!-- Settings summary -->
+ <!-- Settings summary [CHAR LIMIT=50]-->
<string name="pref_content_open_in_background_summary">Open new windows behind the current one</string>
<!-- Settings label -->
<string name="pref_content_homepage">Set home page</string>
@@ -309,24 +334,118 @@
<string name="pref_content_search_engine">Set search engine</string>
<!-- Settings summary -->
<string name="pref_content_search_engine_summary">Select a search engine</string>
- <!-- Settings button label -->
- <string name="pref_use_current">Use current page</string>
+ <!-- Settings button label that to pick what to set the homepage to [CHAR LIMIT=40] -->
+ <string name="pref_set_homepage_to">Set to\u2026</string>
+ <!-- Settings button label to set the homepage to the current page [CHAR LIMIT=40] -->
+ <string name="pref_use_current">Current page</string>
+ <!-- Settings button label to set the homepage to a blank page [CHAR LIMIT=40] -->
+ <string name="pref_use_blank">Blank page</string>
+ <!-- Settings button label to set the homepage to the default page [CHAR LIMIT=40] -->
+ <string name="pref_use_default">Default page</string>
<!-- Settings label -->
<string name="pref_content_autofit">Auto-fit pages</string>
<!-- Settings summary -->
<string name="pref_content_autofit_summary">Format web pages to fit the screen</string>
- <!-- Settings label for enabling a mode where the browser is always set to landscape mode -->
- <string name="pref_content_landscape_only">Landscape-only display</string>
- <!-- Settings summary -->
- <string name="pref_content_landscape_only_summary">Display pages only in the wider, landscape screen orientation</string>
- <!-- Settings screen, section title -->
- <string name="pref_privacy_title">Privacy settings</string>
+
+ <!-- Settings screen & section title for "General settings". These include things like
+ configuring bookmark syncing to Google servers and form auto fill settings. [CHAR-LIMIT=32] -->
+ <string name="pref_general_title">General</string>
+ <!-- Settings category for sync under general settings. This includes bookmark sync with Chrome [CHAR-LIMIT=50] -->
+ <string name="pref_general_sync_title">Sync</string>
+ <!-- Settings category for autofill under general. [CHAR-LIMIT=50] -->
+ <string name="pref_general_autofill_title">Autofill</string>
+ <!-- Checkbox setting to enable or disable syncing bookmarks and other data with Google Chrome. [CHAR-LIMIT=48] -->
+ <string name="pref_personal_sync_with_chrome">Sync with Google Chrome</string>
+ <!-- Checkbox setting to enable or disable syncing bookmarks and other data with Google Chrome. [CHAR-LIMIT=none] -->
+ <string name="pref_personal_sync_with_chrome_summary">Share bookmarks & other data between Android Browser and Google Chrome</string>
+ <!-- Label indicating which Google account is being used to sync bookmarks between Android and Chrome [CHAR-LIMIT=20] -->
+ <string name="pref_personal_google_account">Google account</string>
+ <!-- Checkbox setting to enable or disable syncing bookmarks with Google Chrome. [CHAR-LIMIT=32] -->
+ <string name="pref_personal_sync_bookmarks">Sync bookmarks</string>
+ <!-- Summary for a checkbox setting to enable or disable syncing bookmarks with Google Chrome. [CHAR-LIMIT=none] -->
+ <string name="pref_personal_sync_bookmarks_summary">Sync bookmarks between Android Browser and Google Chrome</string>
+ <!-- Button to start a sync of bookmarks and other data between the Android Browser and Google Chrome [CHAR-LIMIT=20] -->
+ <string name="pref_personal_start_syncing">Start syncing</string>
+ <!-- Dialog title used when asking the user which Google account they want to use to sync data between Android Browser and Google Chrome [CHAR-LIMIT=20] -->
+ <string name="pref_personal_account_dialog_title">Select Google account to share with</string>
+
+ <!-- Checkbox setting for enabling/disabling the form AutoFill feature [CHAR-LIMIT=32] -->
+ <string name="pref_autofill_enabled">Form AutoFill</string>
+ <!-- Settings summary for the form AutoFill feature. [CHAR-LIMIT=none] -->
+ <string name="pref_autofill_enabled_summary">Fill out web forms in a single click</string>
+ <!-- Label for option that when clicked opens the AutoFill settings screen. Also used as the title of that AutoFill Settings screen. [CHAR-LIMIT=32] -->
+ <string name="pref_autofill_profile_editor">AutoFill Settings</string>
+ <!-- Summary for the AutoFill Settings preference [CHAR-LIMIT=none] -->
+ <string name="pref_autofill_profile_editor_summary">Set up & manage data for AutoFilled forms</string>
+
+ <!-- Auto login preference title [CHAR-LIMIT=32] -->
+ <string name="pref_autologin_title">Automatic Google sign-in</string>
+ <!-- Summary when no accounts are found [CHAR-LIMIT=32] -->
+ <string name="pref_autologin_no_account">No accounts found</string>
+ <!-- Summary when there is an account available [CHAR-LIMIT=none] -->
+ <string name="pref_autologin_summary">Sign into Google sites automatically using <xliff:g>%s</xliff:g></string>
+ <!-- Message shown during auto login [CHAR-LIMIT=none] -->
+ <string name="pref_autologin_progress">Signing into Google sites using <xliff:g>%s</xliff:g>\nYour Privacy & Security settings control automatic Google sign-in</string>
+ <!-- Option in account list to disable autologin [CHAR-LIMIT=50] -->
+ <string name="pref_autologin_disable">Don\'t sign in automatically</string>
+
+ <!-- Heading for the AutoFill profile editor to tell the user what AutoFill does and why they should fill out the profile. [CHAR-LIMIT=None] -->
+ <string name="autofill_profile_editor_heading">AutoFill will use your profile to help you complete web forms in a single click.</string>
+ <!-- String for the user's full name in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+ <string name="autofill_profile_editor_name">Full name:</string>
+ <!-- String for the user's e-mail address in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+ <string name="autofill_profile_editor_email_address">Email:</string>
+ <!-- String for the user's company name in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+ <string name="autofill_profile_editor_company_name">Company name:</string>
+ <!-- String for the first line of the user's address in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+ <string name="autofill_profile_editor_address_line_1">Address line 1:</string>
+ <!-- String to suggest to the user the kind of data to be used for the first line of the address. CHAR-LIMIT=64] -->
+ <string name="autofill_profile_editor_address_line_1_hint">Street address, P.O. box, c/o</string>
+ <!-- String for the second line of the user's address in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+ <string name="autofill_profile_editor_address_line_2">Address line 2:</string>
+ <!-- String to suggest to the user the kind of data to be used for the second line of the address. CHAR-LIMIT=64] -->
+ <string name="autofill_profile_editor_address_line_2_hint">Apartment, suite, unit, building, floor etc.</string>
+ <!-- String for the user's city or town in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+ <string name="autofill_profile_editor_city">City / Town:</string>
+ <!-- String for the user's state or province or region in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+ <string name="autofill_profile_editor_state">State / Province / Region:</string>
+ <!-- String for the user's zip code in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+ <string name="autofill_profile_editor_zip_code">Zip code:</string>
+ <!-- String for the user's country in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+ <string name="autofill_profile_editor_country">Country:</string>
+ <!-- String for the user's phone number in the AutoFill profile editor. [CHAR-LIMIT=32] -->
+ <string name="autofill_profile_editor_phone_number">Phone:</string>
+ <!-- String to display in an error tooltip to inform the user the phone number they provided is not valid. [CHAR-LIMIT=32] -->
+ <string name="autofill_profile_editor_phone_number_invalid">Invalid phone number</string>
+
+ <!-- Button text to save the AutoFill profile [CHAR-LIMIT=20] -->
+ <string name="autofill_profile_editor_save_profile">Save profile</string>
+ <!-- Toast message displayed when the profile has been successfully saved [CHAR-LIMIT=none] -->
+ <string name="autofill_profile_successful_save">Profile saved</string>
+ <!-- Toast message displayed when the profile has been successfully deleted [CHAR-LIMIT=none] -->
+ <string name="autofill_profile_successful_delete">Profile deleted</string>
+ <!-- Button text to delete all the AutoFill profile data [CHAR-LIMIT=20] -->
+ <string name="autofill_profile_editor_delete_profile">Delete profile</string>
+
+ <!-- Text on a dialog shown to the user when they are prompted to set up the autofill feature [CHAR-LIMIT=NONE] -->
+ <string name="autofill_setup_dialog_message">Browser can automatically complete web forms like this one. Would you like to set up your profile?</string>
+ <!-- Toast message displayed when the user decides to not set up autofill at this time. We want to remind them that they can configure
+ it through the Browser Settings menu. [CHAR-LIMIT=NONE] -->
+ <string name="autofill_setup_dialog_negative_toast">AutoFill can always be configured through Browser Settings.</string>
+ <!-- Text on a checkbox in the "setup autofill" dialog which is shown to the user when they are prompted to set up the autofill feature.
+ The checkbox allows them to specify they would like to disable the feature altogether [CHAR-LIMIT=NONE] -->
+ <string name="disable_autofill">Disable AutoFill</string>
+
+ <!-- Settings screen, section title [CHAR-LIMIT=50] -->
+ <string name="pref_privacy_security_title">Privacy & Security</string>
<!-- Settings label -->
<string name="pref_privacy_clear_cache">Clear cache</string>
<!-- Settings summary -->
<string name="pref_privacy_clear_cache_summary">Clear locally cached content and databases</string>
<!-- Confirmation dialog message -->
<string name="pref_privacy_clear_cache_dlg">Locally cached content and databases will be deleted.</string>
+ <!-- Cookie settings category [CHAR-LIMIT=50] -->
+ <string name="pref_privacy_cookies_title">Cookies</string>
<!-- Settings label -->
<string name="pref_privacy_clear_cookies">Clear all cookie data</string>
<!-- Settings summary -->
@@ -339,6 +458,8 @@
<string name="pref_privacy_clear_history_summary">Clear the browser navigation history</string>
<!-- Confirmation dialog message -->
<string name="pref_privacy_clear_history_dlg">The browser navigation history will be deleted.</string>
+ <!-- Formdata settings category [CHAR-LIMIT=50] -->
+ <string name="pref_privacy_formdata_title">Form data</string>
<!-- Settings label -->
<string name="pref_privacy_clear_form_data">Clear form data</string>
<!-- Settings summary -->
@@ -351,6 +472,8 @@
<string name="pref_privacy_clear_passwords_summary">Clear all saved passwords</string>
<!-- Confirmation dialog message -->
<string name="pref_privacy_clear_passwords_dlg">All saved passwords will be deleted.</string>
+ <!-- Location settings category [CHAR-LIMIT=50] -->
+ <string name="pref_privacy_location_title">Location</string>
<!-- Settings label -->
<string name="pref_privacy_enable_geolocation">Enable location</string>
<!-- Settings summary -->
@@ -361,8 +484,8 @@
<string name="pref_privacy_clear_geolocation_access_summary">Clear location access for all websites</string>
<!-- Confirmation dialog message -->
<string name="pref_privacy_clear_geolocation_access_dlg">Clear location access for all websites</string>
- <!-- Settings screen, section title -->
- <string name="pref_security_title">Security settings</string>
+ <!-- Passwords settings category [CHAR-LIMIT=50] -->
+ <string name="pref_security_passwords_title">Passwords</string>
<!-- Settings label -->
<string name="pref_security_remember_passwords">Remember passwords</string>
<!-- Settings summary -->
@@ -419,12 +542,14 @@
<string name="pref_content_load_page">Open pages in overview</string>
<!-- Settings summary -->
<string name="pref_content_load_page_summary">Show overview of newly opened pages</string>
- <!-- Settings screen, section title -->
- <string name="pref_extras_title">Advanced settings</string>
+ <!-- Settings screen, section title [CHAR LIMIT=50] -->
+ <string name="pref_extras_title">Advanced</string>
<!-- Settings label -->
<string name="pref_extras_website_settings">Website settings</string>
<!-- Settings summary -->
<string name="pref_extras_website_settings_summary">Advanced settings for individual websites</string>
+ <!-- Settings category label [CHAR-LIMIT=50] -->
+ <string name="pref_extras_reset_default_title">Reset defaults</string>
<!-- Settings label -->
<string name="pref_extras_reset_default">Reset to default</string>
<!-- Settings summary -->
@@ -446,6 +571,8 @@
<!-- Do not tranlsate. Development option -->
<string name="pref_development_nav_dump" translatable="false">Enable nav cache dump</string>
<!-- Do not tranlsate. Development option -->
+ <string name="pref_development_hardware_accel" translatable="false">Enable OpenGL Rendering</string>
+ <!-- Do not tranlsate. Development option -->
<string name="js_engine_flags" translatable="false">Set JS flags</string>
<!-- Do not tranlsate. Development option -->
<string name="pref_development_uastring" translatable="false">UAString</string>
@@ -477,6 +604,8 @@
<item>Japanese (ISO-2022-JP)</item>
<item>Japanese (SHIFT_JIS)</item>
<item>Japanese (EUC-JP)</item>
+ <!-- No need to translate a EUC-KR part, and there is no string length limits. -->
+ <item>Korean (EUC-KR)</item>
<!-- TODO: We should add a lot more encodings. -->
</string-array>
<!-- Dialog box title -->
@@ -490,8 +619,21 @@
<item>ISO-2022-JP</item>
<item>SHIFT_JIS</item>
<item>EUC-JP</item>
+ <item>EUC-KR</item>
</string-array>
<string name="pref_default_text_encoding_default" translatable="false">Latin-1</string>
+ <!-- Title for lab settings [CHAR LIMIT=25] -->
+ <string name="pref_lab_title">Labs</string>
+ <!-- Title for lab quick controls feature [CHAR LIMIT=40] -->
+ <string name="pref_lab_quick_controls">Quick Controls</string>
+ <!-- Summary for lab quick controls feature [CHAR LIMIT=80] -->
+ <string name="pref_lab_quick_controls_summary">
+ Swipe thumb from left or right edge to access quick controls</string>
+ <!-- Title for lab "Most Visited" homepage feature [CHAR LIMIT=40] -->
+ <string name="pref_lab_most_visited_homepage">Most Visited Homepage</string>
+ <!-- Summary for lab "Most Visited" homepage feature [CHAR LIMIT=80] -->
+ <string name="pref_lab_most_visited_homepage_summary">
+ Sets your homepage to show the most visited pages.</string>
<!-- Title for a dialog displayed when the browser has a data connectivity
problem -->
<string name="browserFrameNetworkErrorLabel">Data connectivity problem</string>
@@ -662,22 +804,22 @@
user signs up the device with a Google sites account, the site's
domain will be appended. -->
<string name="homepage_base" translatable="false">
- http://www.google.com/m?client=ms-{CID}&source=android-home</string>
+ http://www.google.com/webhp?client=ms-{CID}&source=android-home</string>
<!-- Bookmarks -->
<string-array name="bookmarks" translatable="false">
<item>Google</item>
<item>http://www.google.com/</item>
<item>Picasa</item>
- <item>http://picasaweb.google.com/m/viewer?source=androidclient</item>
+ <item>http://picasaweb.google.com/</item>
<item>Yahoo!</item>
<item>http://www.yahoo.com/</item>
<item>MSN</item>
<item>http://www.msn.com/</item>
- <item>MySpace</item>
- <item>http://www.myspace.com/</item>
+ <item>Twitter</item>
+ <item>http://twitter.com/</item>
<item>Facebook</item>
- <item>http://www.facebook.com/</item>
+ <item>http://www.facebook.com/?m2w</item>
<item>Wikipedia</item>
<item>http://www.wikipedia.org/</item>
<item>eBay</item>
@@ -689,7 +831,7 @@
<item>ESPN</item>
<item>http://espn.com/</item>
<item>Amazon</item>
- <item>http://www.amazon.com/</item>
+ <item>http://www.amazon.com/?force-full-site=1</item>
<item>Weather Channel</item>
<item>http://www.weather.com/</item>
<item>BBC</item>
@@ -753,4 +895,39 @@
<string name="error_console_eval_text_hint" translatable="false">Evaluate JavaScript</string>
<string name="error_console_eval_button_text" translatable="false">Evaluate</string>
+ <!-- The default state to the "up to parent folder" button in the bookmarks UI. This
+ is displayed when the user is at the highest level and cannot go up [CHAR LIMIT=16] -->
+ <string name="defaultBookmarksUpButton">Bookmarks</string>
+
+ <!-- The string that is displayed when there are no bookmarks to display.
+ This is centered in the middle of the screen [CHAR LIMIT=NONE] -->
+ <string name="empty_bookmarks_folder">There are no bookmarks</string>
+
+ <!-- Access point for RLZ tracking. -->
+ <string name="rlz_access_point">Y1</string>
+
+ <!-- Title for a dialog asking the user which account to sync their bookmarks to [CHAR LIMIT=32] -->
+ <string name="account_chooser_dialog_title" msgid="4833571985009544332">Choose account</string>
+
+ <!-- Title for a dialog asking the user what they want to do with their bookmarks when adding a sync account [CHAR-LIMIT=32] -->
+ <string name="import_bookmarks_dialog_title">Sync with Google account</string>
+
+ <!-- Description for a dialog asking the user what they want to do with their bookmarks when adding a sync account [CHAR-LIMIT=none] -->
+ <string name="import_bookmarks_dialog_description">Your Android bookmarks are not associated with a Google account</string>
+
+ <!-- Button allowing users to remove all of their existing bookmarks when setting up syncing with their bookmarks stored in Google Chrome [CHAR-LIMIT=64] -->
+ <string name="import_bookmarks_dialog_remove">Remove your Android bookmarks</string>
+
+ <!-- Button allowing users to import all of their existing bookmarks into an account when setting up syncing with their bookmarks stored in Google Chrome [CHAR-LIMIT=64] -->
+ <string name="import_bookmarks_dialog_import">Add your Android bookmarks to bookmarks for <xliff:g id="Google account" example="account@example.com">%s</xliff:g></string>
+
+ <!-- Url Selection Action Mode -->
+
+ <!-- Menu item to share URL selection [CHAR LIMIT=30] -->
+ <string name="menu_share_url">Share</string>
+
+ <!-- Toast to inform the user that the maximum number of tabs has been
+ reached. [CHAR LIMIT=50] -->
+ <string name="max_tabs_warning">No more tabs available</string>
+
</resources>
diff --git a/res/values/styles.xml b/res/values/styles.xml
index 2e8510a..a4a27cc 100644
--- a/res/values/styles.xml
+++ b/res/values/styles.xml
@@ -1,38 +1,65 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
-/*
+/*
*
* Copyright 2006,2007,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
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
*
- * http://www.apache.org/licenses/LICENSE-2.0
+ * http://www.apache.org/licenses/LICENSE-2.0
*
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT 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>
<style name="BrowserTheme" parent="@android:Theme.Black">
- <item name="android:windowBackground">@color/white</item>
- <item name="android:colorBackground">#FFFFFFFF</item>
<item name="android:windowNoTitle">true</item>
<item name="android:windowContentOverlay">@null</item>
</style>
-
+ <style name="Dialog" parent="@android:style/Theme.Dialog">
+ <item name="android:background">@color/black</item>
+ </style>
+ <style name="ActionBar" parent="@android:style/Widget.ActionBar">
+ <item name="android:background">@color/black</item>
+ </style>
<style name="BookmarkTheme" parent="@android:Theme.Black">
<item name="android:windowNoTitle">true</item>
<item name="android:windowContentOverlay">@null</item>
</style>
-
+ <style name="ShortcutTheme" parent="@android:Theme.Holo.DialogWhenLarge">
+ <item name="android:windowNoTitle">true</item>
+ <item name="android:windowContentOverlay">@null</item>
+ </style>
<style name="TitleBar">
<item name="android:windowEnterAnimation">@anim/title_bar_enter</item>
<item name="android:windowExitAnimation">@anim/title_bar_exit</item>
</style>
+ <style name="HoloIcon">
+ <item name="android:layout_marginLeft">16dip</item>
+ </style>
+ <style name="HoloButton">
+ <item name="android:background">?android:attr/selectableItemBackground</item>
+ <item name="android:paddingLeft">8dip</item>
+ <item name="android:paddingRight">8dip</item>
+ </style>
+ <style name="TabTitleSelected" parent="@android:style/TextAppearance.Small">
+ <item name="android:textColor">?android:attr/textColorPrimary</item>
+ <item name="android:textStyle">bold</item>
+ </style>
+ <style name="TabTitleUnselected" parent="@android:style/TextAppearance.Small">
+ <item name="android:textColor">?android:attr/textColorSecondary</item>
+ <item name="android:textStyle">normal</item>
+ </style>
+ <style name="Suggestions" parent="@android:style/Widget.AutoCompleteTextView">
+ </style>
+ <style name="SuggestionLineMedium" parent="@android:style/TextAppearance.Medium">
+ </style>
+ <style name="SuggestionLineSmall" parent="@android:style/TextAppearance.Small">
+ </style>
</resources>
-
diff --git a/res/xml/advanced_preferences.xml b/res/xml/advanced_preferences.xml
new file mode 100644
index 0000000..3264d22
--- /dev/null
+++ b/res/xml/advanced_preferences.xml
@@ -0,0 +1,112 @@
+<?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.
+-->
+
+<PreferenceScreen
+ xmlns:android="http://schemas.android.com/apk/res/android">
+
+ <!-- Entries and values in this list are set dynamically. -->
+ <com.android.browser.search.SearchEnginePreference
+ android:key="search_engine"
+ android:title="@string/pref_content_search_engine"
+ android:defaultValue="google"
+ android:summary="@string/pref_content_search_engine_summary"
+ android:dialogTitle="@string/pref_content_search_engine" />
+
+ <CheckBoxPreference
+ android:key="open_in_background"
+ android:defaultValue="false"
+ android:title="@string/pref_content_open_in_background"
+ android:summary="@string/pref_content_open_in_background_summary" />
+
+ <CheckBoxPreference
+ android:key="enable_javascript"
+ android:defaultValue="true"
+ android:title="@string/pref_content_javascript" />
+
+ <ListPreference
+ android:key="plugin_state"
+ android:title="@string/pref_content_plugins"
+ android:defaultValue="ON"
+ android:entries="@array/pref_content_plugins_choices"
+ android:entryValues="@array/pref_content_plugins_values"
+ android:dialogTitle="@string/pref_content_plugins" />
+
+ <PreferenceScreen
+ android:key="website_settings"
+ android:title="@string/pref_extras_website_settings"
+ android:summary="@string/pref_extras_website_settings_summary" />
+
+ <PreferenceCategory android:title="@string/pref_content_title">
+ <ListPreference
+ android:key="text_size"
+ android:title="@string/pref_text_size"
+ android:defaultValue="NORMAL"
+ android:entries="@array/pref_text_size_choices"
+ android:entryValues="@array/pref_text_size_values"
+ android:dialogTitle="@string/pref_text_size_dialogtitle" />
+
+ <ListPreference
+ android:key="default_zoom"
+ android:title="@string/pref_default_zoom"
+ android:defaultValue="MEDIUM"
+ android:entries="@array/pref_default_zoom_choices"
+ android:entryValues="@array/pref_default_zoom_values"
+ android:dialogTitle="@string/pref_default_zoom_dialogtitle" />
+
+ <CheckBoxPreference
+ android:key="load_page"
+ android:defaultValue="true"
+ android:title="@string/pref_content_load_page"
+ android:summary="@string/pref_content_load_page_summary" />
+
+ <CheckBoxPreference
+ android:key="autofit_pages"
+ android:defaultValue="true"
+ android:title="@string/pref_content_autofit"
+ android:summary="@string/pref_content_autofit_summary" />
+
+ <CheckBoxPreference
+ android:key="block_popup_windows"
+ android:defaultValue="true"
+ android:title="@string/pref_content_block_popups" />
+
+ <CheckBoxPreference
+ android:key="load_images"
+ android:defaultValue="true"
+ android:title="@string/pref_content_load_images"
+ android:summary="@string/pref_content_load_images_summary" />
+
+ <ListPreference
+ android:key="default_text_encoding"
+ android:title="@string/pref_default_text_encoding"
+ android:defaultValue="@string/pref_default_text_encoding_default"
+ android:entries="@array/pref_default_text_encoding_choices"
+ android:entryValues="@array/pref_default_text_encoding_values"
+ android:dialogTitle="@string/pref_default_text_encoding_dialogtitle" />
+
+ </PreferenceCategory>
+
+ <PreferenceCategory android:title="@string/pref_extras_reset_default_title">
+ <com.android.browser.BrowserYesNoPreference
+ android:key="reset_default_preferences"
+ android:title="@string/pref_extras_reset_default"
+ android:summary="@string/pref_extras_reset_default_summary"
+ android:dialogMessage="@string/pref_extras_reset_default_dlg"
+ android:dialogTitle="@string/pref_extras_reset_default_dlg_title"
+ android:dialogIcon="@android:drawable/ic_dialog_alert" />
+ </PreferenceCategory>
+
+</PreferenceScreen>
diff --git a/res/xml/bookmarkwidget.xml b/res/xml/bookmarkthumbnailwidget_info.xml
similarity index 64%
copy from res/xml/bookmarkwidget.xml
copy to res/xml/bookmarkthumbnailwidget_info.xml
index adbe5f2..6797f85 100644
--- a/res/xml/bookmarkwidget.xml
+++ b/res/xml/bookmarkthumbnailwidget_info.xml
@@ -14,11 +14,12 @@
limitations under the License.
-->
-<!-- 4x4 Widget displaying the user's bookmarks as thumbnails. -->
-<appwidget-provider xmlns:android="http://schemas.android.com/apk/res/android"
- android:minWidth="294dip"
- android:minHeight="294dip"
- android:updatePeriodMillis="3600000"
- android:initialLayout="@layout/bookmarkwidget"
- >
+<!-- 3x3 Widget displaying the user's bookmarks as a list with favicons. -->
+<appwidget-provider
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:minWidth="219dip"
+ android:minHeight="219dip"
+ android:updatePeriodMillis="0"
+ android:previewImage="@drawable/browser_widget_preview"
+ android:initialLayout="@layout/bookmarkthumbnailwidget">
</appwidget-provider>
diff --git a/res/xml/browser_preferences.xml b/res/xml/browser_preferences.xml
deleted file mode 100644
index 1da85ec..0000000
--- a/res/xml/browser_preferences.xml
+++ /dev/null
@@ -1,216 +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.
--->
-
-<PreferenceScreen
- xmlns:android="http://schemas.android.com/apk/res/android">
-
- <PreferenceCategory
- android:title="@string/pref_content_title">
-
- <ListPreference
- android:key="text_size"
- android:title="@string/pref_text_size"
- android:defaultValue="NORMAL"
- android:entries="@array/pref_text_size_choices"
- android:entryValues="@array/pref_text_size_values"
- android:dialogTitle="@string/pref_text_size_dialogtitle" />
-
- <ListPreference
- android:key="default_zoom"
- android:title="@string/pref_default_zoom"
- android:defaultValue="MEDIUM"
- android:entries="@array/pref_default_zoom_choices"
- android:entryValues="@array/pref_default_zoom_values"
- android:dialogTitle="@string/pref_default_zoom_dialogtitle" />
-
- <CheckBoxPreference
- android:key="load_page"
- android:defaultValue="true"
- android:title="@string/pref_content_load_page"
- android:summary="@string/pref_content_load_page_summary" />
-
- <ListPreference
- android:key="default_text_encoding"
- android:title="@string/pref_default_text_encoding"
- android:defaultValue="@string/pref_default_text_encoding_default"
- android:entries="@array/pref_default_text_encoding_choices"
- android:entryValues="@array/pref_default_text_encoding_values"
- android:dialogTitle="@string/pref_default_text_encoding_dialogtitle" />
-
- <CheckBoxPreference
- android:key="block_popup_windows"
- android:defaultValue="true"
- android:title="@string/pref_content_block_popups" />
-
- <CheckBoxPreference
- android:key="load_images"
- android:defaultValue="true"
- android:title="@string/pref_content_load_images"
- android:summary="@string/pref_content_load_images_summary" />
-
- <CheckBoxPreference
- android:key="autofit_pages"
- android:defaultValue="true"
- android:title="@string/pref_content_autofit"
- android:summary="@string/pref_content_autofit_summary" />
-
- <CheckBoxPreference
- android:key="landscape_only"
- android:defaultValue="false"
- android:title="@string/pref_content_landscape_only"
- android:summary="@string/pref_content_landscape_only_summary" />
-
- <CheckBoxPreference
- android:key="enable_javascript"
- android:defaultValue="true"
- android:title="@string/pref_content_javascript" />
-
- <ListPreference
- android:key="plugin_state"
- android:title="@string/pref_content_plugins"
- android:defaultValue="ON"
- android:entries="@array/pref_content_plugins_choices"
- android:entryValues="@array/pref_content_plugins_values"
- android:dialogTitle="@string/pref_content_plugins" />
-
- <CheckBoxPreference
- android:key="open_in_background"
- android:defaultValue="false"
- android:title="@string/pref_content_open_in_background"
- android:summary="@string/pref_content_open_in_background_summary" />
-
- <com.android.browser.BrowserHomepagePreference
- android:key="homepage"
- android:title="@string/pref_content_homepage"
- android:hint="@string/http"
- android:inputType="textUri|textMultiLine" />
-
- </PreferenceCategory>
-
- <PreferenceCategory
- android:title="@string/pref_privacy_title">
-
- <com.android.browser.BrowserYesNoPreference
- android:key="privacy_clear_cache"
- android:title="@string/pref_privacy_clear_cache"
- android:summary="@string/pref_privacy_clear_cache_summary"
- android:dialogMessage="@string/pref_privacy_clear_cache_dlg"
- android:dialogTitle="@string/clear"
- android:dialogIcon="@android:drawable/ic_dialog_alert" />
-
- <com.android.browser.BrowserYesNoPreference
- android:key="privacy_clear_history"
- android:title="@string/pref_privacy_clear_history"
- android:summary="@string/pref_privacy_clear_history_summary"
- android:dialogMessage="@string/pref_privacy_clear_history_dlg"
- android:dialogTitle="@string/clear"
- android:dialogIcon="@android:drawable/ic_dialog_alert"/>
-
- <CheckBoxPreference
- android:key="accept_cookies"
- android:defaultValue="true"
- android:title="@string/pref_security_accept_cookies"
- android:summary="@string/pref_security_accept_cookies_summary" />
-
- <com.android.browser.BrowserYesNoPreference
- android:key="privacy_clear_cookies"
- android:title="@string/pref_privacy_clear_cookies"
- android:summary="@string/pref_privacy_clear_cookies_summary"
- android:dialogMessage="@string/pref_privacy_clear_cookies_dlg"
- android:dialogTitle="@string/clear"
- android:dialogIcon="@android:drawable/ic_dialog_alert"/>
-
- <CheckBoxPreference
- android:key="save_formdata"
- android:defaultValue="true"
- android:title="@string/pref_security_save_form_data"
- android:summary="@string/pref_security_save_form_data_summary" />
-
- <com.android.browser.BrowserYesNoPreference
- android:key="privacy_clear_form_data"
- android:title="@string/pref_privacy_clear_form_data"
- android:summary="@string/pref_privacy_clear_form_data_summary"
- android:dialogMessage="@string/pref_privacy_clear_form_data_dlg"
- android:dialogTitle="@string/clear"
- android:dialogIcon="@android:drawable/ic_dialog_alert"/>
-
- <CheckBoxPreference
- android:key="enable_geolocation"
- android:defaultValue="true"
- android:title="@string/pref_privacy_enable_geolocation"
- android:summary="@string/pref_privacy_enable_geolocation_summary" />
-
- <com.android.browser.BrowserYesNoPreference
- android:key="privacy_clear_geolocation_access"
- android:dependency="enable_geolocation"
- android:title="@string/pref_privacy_clear_geolocation_access"
- android:summary="@string/pref_privacy_clear_geolocation_access_summary"
- android:dialogMessage="@string/pref_privacy_clear_geolocation_access_dlg"
- android:dialogTitle="@string/clear"
- android:dialogIcon="@android:drawable/ic_dialog_alert"/>
-
- </PreferenceCategory>
-
- <PreferenceCategory
- android:title="@string/pref_security_title">
-
- <CheckBoxPreference
- android:key="remember_passwords"
- android:defaultValue="true"
- android:title="@string/pref_security_remember_passwords"
- android:summary="@string/pref_security_remember_passwords_summary" />
-
- <com.android.browser.BrowserYesNoPreference
- android:key="privacy_clear_passwords"
- android:title="@string/pref_privacy_clear_passwords"
- android:summary="@string/pref_privacy_clear_passwords_summary"
- android:dialogMessage="@string/pref_privacy_clear_passwords_dlg"
- android:dialogTitle="@string/clear"
- android:dialogIcon="@android:drawable/ic_dialog_alert"/>
-
- <CheckBoxPreference
- android:key="show_security_warnings"
- android:defaultValue="true"
- android:title="@string/pref_security_show_security_warning"
- android:summary="@string/pref_security_show_security_warning_summary" />
-
-
- </PreferenceCategory>
- <PreferenceCategory
- android:title="@string/pref_extras_title">
-
- <!-- Entries and values in this list are set dynamically. -->
- <com.android.browser.search.SearchEnginePreference
- android:key="search_engine"
- android:title="@string/pref_content_search_engine"
- android:defaultValue="google"
- android:summary="@string/pref_content_search_engine_summary"
- android:dialogTitle="@string/pref_content_search_engine" />
-
- <PreferenceScreen
- android:key="website_settings"
- android:title="@string/pref_extras_website_settings"
- android:summary="@string/pref_extras_website_settings_summary" />
-
- <com.android.browser.BrowserYesNoPreference
- android:key="reset_default_preferences"
- android:title="@string/pref_extras_reset_default"
- android:summary="@string/pref_extras_reset_default_summary"
- android:dialogMessage="@string/pref_extras_reset_default_dlg"
- android:dialogTitle="@string/pref_extras_reset_default_dlg_title"
- android:dialogIcon="@android:drawable/ic_dialog_alert" />
- </PreferenceCategory>
-</PreferenceScreen>
diff --git a/res/xml/debug_preferences.xml b/res/xml/debug_preferences.xml
index c1ed1e6..50d4c14 100644
--- a/res/xml/debug_preferences.xml
+++ b/res/xml/debug_preferences.xml
@@ -16,59 +16,17 @@
<PreferenceScreen
xmlns:android="http://schemas.android.com/apk/res/android" >
- <PreferenceCategory
- android:title="@string/pref_development_title"
- android:key="debug_menu" >
- <!-- The javascript console is enabled by default when the user has
- also enabled debug mode by navigating to about:debug. -->
- <CheckBoxPreference
- android:key="javascript_console"
- android:defaultValue="true"
- android:title="@string/pref_development_error_console" />
-
- <CheckBoxPreference
- android:key="small_screen"
- android:defaultValue="false"
- android:title="@string/pref_development_single_column_rendering" />
+ <CheckBoxPreference
+ android:key="enable_hardware_accel"
+ android:defaultValue="true"
+ android:title="@string/pref_development_hardware_accel" />
- <CheckBoxPreference
- android:key="wide_viewport"
- android:defaultValue="true"
- android:title="@string/pref_development_viewport" />
-
- <CheckBoxPreference
- android:key="normal_layout"
- android:defaultValue="false"
- android:title="@string/pref_development_normal_rendering" />
-
- <CheckBoxPreference
- android:key="enable_tracing"
- android:defaultValue="false"
- android:title="@string/pref_development_trace" />
-
- <CheckBoxPreference
- android:key="enable_light_touch"
- android:defaultValue="false"
- android:title="Enable light touch" />
-
- <CheckBoxPreference
- android:key="enable_nav_dump"
- android:defaultValue="false"
- android:title="@string/pref_development_nav_dump" />
-
- <EditTextPreference
- android:key="js_engine_flags"
- android:title="@string/js_engine_flags"
- android:singleLine="true" />
-
- <ListPreference
- android:key="user_agent"
- android:title="@string/pref_development_uastring"
- android:entries="@array/pref_development_ua_choices"
- android:entryValues="@array/pref_development_ua_values"
- android:defaultValue="0"/>
-
- </PreferenceCategory>
+ <ListPreference
+ android:key="user_agent"
+ android:title="@string/pref_development_uastring"
+ android:entries="@array/pref_development_ua_choices"
+ android:entryValues="@array/pref_development_ua_values"
+ android:defaultValue="0"/>
</PreferenceScreen>
diff --git a/res/xml/general_preferences.xml b/res/xml/general_preferences.xml
new file mode 100644
index 0000000..92b1f2a
--- /dev/null
+++ b/res/xml/general_preferences.xml
@@ -0,0 +1,46 @@
+<?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.
+-->
+
+<PreferenceScreen xmlns:android="http://schemas.android.com/apk/res/android">
+
+ <com.android.browser.BrowserHomepagePreference
+ android:key="homepage"
+ android:title="@string/pref_content_homepage"
+ android:hint="@string/http"
+ android:inputType="textUri|textMultiLine" />
+
+ <PreferenceCategory android:title="@string/pref_general_sync_title">
+ <Preference android:key="sync_with_chrome"
+ android:title="@string/pref_personal_sync_with_chrome"
+ android:summary="@string/pref_personal_sync_with_chrome_summary"
+ />
+ </PreferenceCategory>
+
+ <PreferenceCategory android:title="@string/pref_general_autofill_title">
+ <CheckBoxPreference android:key="autofill_enabled"
+ android:title="@string/pref_autofill_enabled"
+ android:summary="@string/pref_autofill_enabled_summary"
+ android:defaultValue="true"
+ />
+
+ <PreferenceScreen
+ android:fragment="com.android.browser.AutoFillSettingsFragment"
+ android:key="autofill_profile"
+ android:title="@string/pref_autofill_profile_editor"
+ android:summary="@string/pref_autofill_profile_editor_summary" />
+ </PreferenceCategory>
+
+</PreferenceScreen>
diff --git a/res/xml/hidden_debug_preferences.xml b/res/xml/hidden_debug_preferences.xml
new file mode 100644
index 0000000..6d66eaa
--- /dev/null
+++ b/res/xml/hidden_debug_preferences.xml
@@ -0,0 +1,62 @@
+<?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.
+-->
+
+<PreferenceScreen
+ xmlns:android="http://schemas.android.com/apk/res/android" >
+
+ <!-- The javascript console is enabled by default when the user has
+ also enabled debug mode by navigating to about:debug. -->
+ <CheckBoxPreference
+ android:key="javascript_console"
+ android:defaultValue="true"
+ android:title="@string/pref_development_error_console" />
+
+ <CheckBoxPreference
+ android:key="small_screen"
+ android:defaultValue="false"
+ android:title="@string/pref_development_single_column_rendering" />
+
+ <CheckBoxPreference
+ android:key="wide_viewport"
+ android:defaultValue="true"
+ android:title="@string/pref_development_viewport" />
+
+ <CheckBoxPreference
+ android:key="normal_layout"
+ android:defaultValue="false"
+ android:title="@string/pref_development_normal_rendering" />
+
+ <CheckBoxPreference
+ android:key="enable_tracing"
+ android:defaultValue="false"
+ android:title="@string/pref_development_trace" />
+
+ <CheckBoxPreference
+ android:key="enable_light_touch"
+ android:defaultValue="false"
+ android:title="Enable light touch" />
+
+ <CheckBoxPreference
+ android:key="enable_nav_dump"
+ android:defaultValue="false"
+ android:title="@string/pref_development_nav_dump" />
+
+ <EditTextPreference
+ android:key="js_engine_flags"
+ android:title="@string/js_engine_flags"
+ android:singleLine="true" />
+
+</PreferenceScreen>
diff --git a/res/xml/lab_preferences.xml b/res/xml/lab_preferences.xml
new file mode 100644
index 0000000..16a5169
--- /dev/null
+++ b/res/xml/lab_preferences.xml
@@ -0,0 +1,32 @@
+<?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.
+-->
+
+<PreferenceScreen
+ xmlns:android="http://schemas.android.com/apk/res/android" >
+
+ <CheckBoxPreference
+ android:key="enable_quick_controls"
+ android:defaultValue="false"
+ android:title="@string/pref_lab_quick_controls"
+ android:summary="@string/pref_lab_quick_controls_summary" />
+
+ <CheckBoxPreference
+ android:key="use_most_visited_homepage"
+ android:defaultValue="false"
+ android:title="@string/pref_lab_most_visited_homepage"
+ android:summary="@string/pref_lab_most_visited_homepage_summary" />
+
+</PreferenceScreen>
diff --git a/res/xml/preference_headers.xml b/res/xml/preference_headers.xml
new file mode 100644
index 0000000..cdf259c
--- /dev/null
+++ b/res/xml/preference_headers.xml
@@ -0,0 +1,35 @@
+<?xml version="1.0" encoding="utf-8"?>
+<!-- Copyright (C) 2010 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+
+<preference-headers xmlns:android="http://schemas.android.com/apk/res/android">
+
+ <header android:fragment="com.android.browser.preferences.GeneralPreferencesFragment"
+ android:title="@string/pref_general_title"
+ />
+
+ <header android:fragment="com.android.browser.preferences.PrivacySecurityPreferencesFragment"
+ android:title="@string/pref_privacy_security_title"
+ />
+
+ <header android:fragment="com.android.browser.preferences.AdvancedPreferencesFragment"
+ android:title="@string/pref_extras_title"
+ />
+
+ <header android:fragment="com.android.browser.preferences.LabPreferencesFragment"
+ android:title="@string/pref_lab_title"
+ />
+
+</preference-headers>
diff --git a/res/xml/privacy_security_preferences.xml b/res/xml/privacy_security_preferences.xml
new file mode 100644
index 0000000..9bff4b8
--- /dev/null
+++ b/res/xml/privacy_security_preferences.xml
@@ -0,0 +1,111 @@
+<?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.
+-->
+
+<PreferenceScreen
+ xmlns:android="http://schemas.android.com/apk/res/android">
+
+ <com.android.browser.BrowserYesNoPreference
+ android:key="privacy_clear_cache"
+ android:title="@string/pref_privacy_clear_cache"
+ android:summary="@string/pref_privacy_clear_cache_summary"
+ android:dialogMessage="@string/pref_privacy_clear_cache_dlg"
+ android:dialogTitle="@string/clear"
+ android:dialogIcon="@android:drawable/ic_dialog_alert" />
+
+ <com.android.browser.BrowserYesNoPreference
+ android:key="privacy_clear_history"
+ android:title="@string/pref_privacy_clear_history"
+ android:summary="@string/pref_privacy_clear_history_summary"
+ android:dialogMessage="@string/pref_privacy_clear_history_dlg"
+ android:dialogTitle="@string/clear"
+ android:dialogIcon="@android:drawable/ic_dialog_alert"/>
+
+ <CheckBoxPreference
+ android:key="show_security_warnings"
+ android:defaultValue="true"
+ android:title="@string/pref_security_show_security_warning"
+ android:summary="@string/pref_security_show_security_warning_summary" />
+
+ <ListPreference
+ android:key="autologin_account"
+ android:title="@string/pref_autologin_title" />
+
+ <PreferenceCategory android:title="@string/pref_privacy_cookies_title">
+ <CheckBoxPreference
+ android:key="accept_cookies"
+ android:defaultValue="true"
+ android:title="@string/pref_security_accept_cookies"
+ android:summary="@string/pref_security_accept_cookies_summary" />
+
+ <com.android.browser.BrowserYesNoPreference
+ android:key="privacy_clear_cookies"
+ android:title="@string/pref_privacy_clear_cookies"
+ android:summary="@string/pref_privacy_clear_cookies_summary"
+ android:dialogMessage="@string/pref_privacy_clear_cookies_dlg"
+ android:dialogTitle="@string/clear"
+ android:dialogIcon="@android:drawable/ic_dialog_alert"/>
+ </PreferenceCategory>
+
+ <PreferenceCategory android:title="@string/pref_privacy_formdata_title">
+ <CheckBoxPreference
+ android:key="save_formdata"
+ android:defaultValue="true"
+ android:title="@string/pref_security_save_form_data"
+ android:summary="@string/pref_security_save_form_data_summary" />
+
+ <com.android.browser.BrowserYesNoPreference
+ android:key="privacy_clear_form_data"
+ android:title="@string/pref_privacy_clear_form_data"
+ android:summary="@string/pref_privacy_clear_form_data_summary"
+ android:dialogMessage="@string/pref_privacy_clear_form_data_dlg"
+ android:dialogTitle="@string/clear"
+ android:dialogIcon="@android:drawable/ic_dialog_alert"/>
+ </PreferenceCategory>
+
+ <PreferenceCategory android:title="@string/pref_privacy_location_title">
+ <CheckBoxPreference
+ android:key="enable_geolocation"
+ android:defaultValue="true"
+ android:title="@string/pref_privacy_enable_geolocation"
+ android:summary="@string/pref_privacy_enable_geolocation_summary" />
+
+ <com.android.browser.BrowserYesNoPreference
+ android:key="privacy_clear_geolocation_access"
+ android:dependency="enable_geolocation"
+ android:title="@string/pref_privacy_clear_geolocation_access"
+ android:summary="@string/pref_privacy_clear_geolocation_access_summary"
+ android:dialogMessage="@string/pref_privacy_clear_geolocation_access_dlg"
+ android:dialogTitle="@string/clear"
+ android:dialogIcon="@android:drawable/ic_dialog_alert"/>
+ </PreferenceCategory>
+
+ <PreferenceCategory android:title="@string/pref_security_passwords_title">
+ <CheckBoxPreference
+ android:key="remember_passwords"
+ android:defaultValue="true"
+ android:title="@string/pref_security_remember_passwords"
+ android:summary="@string/pref_security_remember_passwords_summary" />
+
+ <com.android.browser.BrowserYesNoPreference
+ android:key="privacy_clear_passwords"
+ android:title="@string/pref_privacy_clear_passwords"
+ android:summary="@string/pref_privacy_clear_passwords_summary"
+ android:dialogMessage="@string/pref_privacy_clear_passwords_dlg"
+ android:dialogTitle="@string/clear"
+ android:dialogIcon="@android:drawable/ic_dialog_alert"/>
+ </PreferenceCategory>
+
+</PreferenceScreen>
diff --git a/src/com/android/browser/AccountsChangedReceiver.java b/src/com/android/browser/AccountsChangedReceiver.java
new file mode 100644
index 0000000..92d6ad0
--- /dev/null
+++ b/src/com/android/browser/AccountsChangedReceiver.java
@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.accounts.Account;
+import android.accounts.AccountManager;
+import android.content.BroadcastReceiver;
+import android.content.ContentResolver;
+import android.content.Context;
+import android.content.Intent;
+import android.content.SharedPreferences;
+import android.preference.PreferenceManager;
+import android.provider.BrowserContract;
+
+public class AccountsChangedReceiver extends BroadcastReceiver {
+
+ @Override
+ public void onReceive(Context context, Intent intent) {
+ // Validate that the account we are syncing to still exists
+ SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
+ String accountType = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE, null);
+ String accountName = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, null);
+ if (accountType == null || accountName == null) {
+ // Not syncing, nothing to do
+ return;
+ }
+ Account[] accounts = AccountManager.get(context).getAccountsByType(accountType);
+ for (Account a : accounts) {
+ if (accountName.equals(a.name)) {
+ // Still have a valid account, sweet
+ return;
+ }
+ }
+ // Account deleted - disable sync
+ prefs.edit()
+ .remove(BrowserBookmarksPage.PREF_ACCOUNT_TYPE)
+ .remove(BrowserBookmarksPage.PREF_ACCOUNT_NAME)
+ .commit();
+ BrowserContract.Settings.setSyncEnabled(context, false);
+ for (Account a : accounts) {
+ ContentResolver.setSyncAutomatically(a, BrowserContract.AUTHORITY, false);
+ ContentResolver.setIsSyncable(a, BrowserContract.AUTHORITY, 0);
+ }
+ }
+
+}
diff --git a/src/com/android/browser/ActiveTabsPage.java b/src/com/android/browser/ActiveTabsPage.java
index 2de7787..664fd68 100644
--- a/src/com/android/browser/ActiveTabsPage.java
+++ b/src/com/android/browser/ActiveTabsPage.java
@@ -20,7 +20,7 @@
import android.graphics.Bitmap;
import android.os.Handler;
import android.util.AttributeSet;
-import android.view.KeyEvent;
+import android.util.Log;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
@@ -32,16 +32,19 @@
import android.widget.TextView;
public class ActiveTabsPage extends LinearLayout {
- private final BrowserActivity mBrowserActivity;
- private final LayoutInflater mFactory;
- private final TabControl mControl;
- private final TabsListAdapter mAdapter;
- private final ListView mListView;
- public ActiveTabsPage(BrowserActivity context, TabControl control) {
+ private static final String LOGTAG = "TabPicker";
+
+ private final LayoutInflater mFactory;
+ private final UiController mUiController;
+ private final TabControl mControl;
+ private final TabsListAdapter mAdapter;
+ private final ListView mListView;
+
+ public ActiveTabsPage(Context context, UiController control) {
super(context);
- mBrowserActivity = context;
- mControl = control;
+ mUiController = control;
+ mControl = control.getTabControl();
mFactory = LayoutInflater.from(context);
mFactory.inflate(R.layout.active_tabs, this);
mListView = (ListView) findViewById(R.id.list);
@@ -51,21 +54,24 @@
public void onItemClick(AdapterView<?> parent, View view,
int position, long id) {
if (mControl.canCreateNewTab()) {
- position--;
+ position -= 2;
}
boolean needToAttach = false;
- if (position == -1) {
+ if (position == -2) {
// Create a new tab
- mBrowserActivity.openTabToHomePage();
+ mUiController.openTabToHomePage();
+ } else if (position == -1) {
+ // Create a new incognito tab
+ mUiController.openIncognitoTab();
} else {
// Open the corresponding tab
// If the tab is the current one, switchToTab will
// do nothing and return, so we need to make sure
// it gets attached back to its mContentView in
// removeActiveTabPage
- needToAttach = !mBrowserActivity.switchToTab(position);
+ needToAttach = !mUiController.switchToTab(position);
}
- mBrowserActivity.removeActiveTabPage(needToAttach);
+ mUiController.removeActiveTabsPage(needToAttach);
}
});
}
@@ -98,7 +104,7 @@
public int getCount() {
int count = mControl.getTabCount();
if (mControl.canCreateNewTab()) {
- count++;
+ count += 2;
}
// XXX: This is a workaround to be more like a real adapter. Most
// adapters call notifyDataSetChanged() whenever the internal data
@@ -128,23 +134,28 @@
}
public int getItemViewType(int position) {
if (mControl.canCreateNewTab()) {
- position--;
+ position -= 2;
}
// Do not recycle the "add new tab" item.
- return position == -1 ? IGNORE_ITEM_VIEW_TYPE : 1;
+ return position < 0 ? IGNORE_ITEM_VIEW_TYPE : 1;
}
public View getView(int position, View convertView, ViewGroup parent) {
final int tabCount = mControl.getTabCount();
if (mControl.canCreateNewTab()) {
- position--;
+ position -= 2;
}
if (convertView == null) {
- convertView = mFactory.inflate(position == -1 ?
- R.layout.tab_view_add_tab : R.layout.tab_view, null);
+ if (position == -2) {
+ convertView = mFactory.inflate(R.layout.tab_view_add_tab, null);
+ } else if (position == -1) {
+ convertView = mFactory.inflate(R.layout.tab_view_add_incognito_tab, null);
+ } else {
+ convertView = mFactory.inflate(R.layout.tab_view, null);
+ }
}
- if (position != -1) {
+ if (position >= 0) {
TextView title =
(TextView) convertView.findViewById(R.id.title);
TextView url = (TextView) convertView.findViewById(R.id.url);
@@ -152,7 +163,18 @@
(ImageView) convertView.findViewById(R.id.favicon);
View close = convertView.findViewById(R.id.close);
Tab tab = mControl.getTab(position);
- tab.populatePickerData();
+ if (tab.getWebView() == null) {
+ // This means that populatePickerData will have to use the
+ // saved state.
+ Log.w(LOGTAG, "Tab " + position + " has a null WebView and "
+ + (tab.getSavedState() == null ? "null" : "non-null")
+ + " saved state ");
+ }
+ if (tab.getTitle() == null || tab.getTitle().length() == 0) {
+ Log.w(LOGTAG, "Tab " + position + " has no title. "
+ + "Check above in the Logs to see whether it has a "
+ + "null WebView or null WebHistoryItem");
+ }
title.setText(tab.getTitle());
url.setText(tab.getUrl());
Bitmap icon = tab.getFavicon();
@@ -164,11 +186,11 @@
final int closePosition = position;
close.setOnClickListener(new View.OnClickListener() {
public void onClick(View v) {
- mBrowserActivity.closeTab(
+ mUiController.closeTab(
mControl.getTab(closePosition));
if (tabCount == 1) {
- mBrowserActivity.openTabToHomePage();
- mBrowserActivity.removeActiveTabPage(false);
+ mUiController.openTabToHomePage();
+ mUiController.removeActiveTabsPage(false);
} else {
mNotified = true;
notifyDataSetChanged();
diff --git a/src/com/android/browser/AddBookmarkPage.java b/src/com/android/browser/AddBookmarkPage.java
index 594f985..1444862 100644
--- a/src/com/android/browser/AddBookmarkPage.java
+++ b/src/com/android/browser/AddBookmarkPage.java
@@ -16,106 +16,778 @@
package com.android.browser;
+import com.android.browser.provider.BrowserProvider2;
+import com.android.browser.addbookmark.FolderSpinner;
+import com.android.browser.addbookmark.FolderSpinnerAdapter;
+
import android.app.Activity;
+import android.app.LoaderManager;
import android.content.ContentResolver;
+import android.content.ContentUris;
+import android.content.ContentValues;
import android.content.Context;
-import android.content.Intent;
+import android.content.CursorLoader;
+import android.content.Loader;
+import android.content.SharedPreferences;
import android.content.res.Resources;
import android.database.Cursor;
import android.graphics.Bitmap;
+import android.graphics.drawable.Drawable;
import android.net.ParseException;
+import android.net.Uri;
import android.net.WebAddress;
+import android.os.AsyncTask;
import android.os.Bundle;
import android.os.Handler;
import android.os.Message;
-import android.provider.Browser;
+import android.preference.PreferenceManager;
+import android.provider.BrowserContract;
+import android.text.TextUtils;
+import android.util.AttributeSet;
+import android.view.KeyEvent;
+import android.view.LayoutInflater;
import android.view.View;
+import android.view.ViewGroup;
import android.view.Window;
+import android.view.WindowManager;
+import android.view.inputmethod.EditorInfo;
+import android.view.inputmethod.InputMethodManager;
+import android.widget.AdapterView;
+import android.widget.CursorAdapter;
import android.widget.EditText;
+import android.widget.ListView;
import android.widget.TextView;
import android.widget.Toast;
import java.net.URI;
import java.net.URISyntaxException;
-import java.util.Date;
+import java.util.Stack;
-public class AddBookmarkPage extends Activity {
+public class AddBookmarkPage extends Activity
+ implements View.OnClickListener, TextView.OnEditorActionListener,
+ AdapterView.OnItemClickListener, LoaderManager.LoaderCallbacks<Cursor>,
+ BreadCrumbView.Controller, FolderSpinner.OnSetSelectionListener {
+
+ public static final long DEFAULT_FOLDER_ID = -1;
+ public static final String TOUCH_ICON_URL = "touch_icon_url";
+ // Place on an edited bookmark to remove the saved thumbnail
+ public static final String REMOVE_THUMBNAIL = "remove_thumbnail";
+ public static final String USER_AGENT = "user_agent";
+
+ /* package */ static final String EXTRA_EDIT_BOOKMARK = "bookmark";
+ /* package */ static final String EXTRA_IS_FOLDER = "is_folder";
+
+ private static final int MAX_CRUMBS_SHOWN = 2;
private final String LOGTAG = "Bookmarks";
+ // IDs for the CursorLoaders that are used.
+ private final int LOADER_ID_FOLDER_CONTENTS = 0;
+ private final int LOADER_ID_ALL_FOLDERS = 1;
+ private final int LOADER_ID_FIND_ROOT = 2;
+ private final int LOADER_ID_CHECK_FOR_DUPE = 3;
+
private EditText mTitle;
private EditText mAddress;
private TextView mButton;
private View mCancelButton;
private boolean mEditingExisting;
+ private boolean mEditingFolder;
private Bundle mMap;
private String mTouchIconUrl;
- private Bitmap mThumbnail;
private String mOriginalUrl;
+ private FolderSpinner mFolder;
+ private View mDefaultView;
+ private View mFolderSelector;
+ private EditText mFolderNamer;
+ private View mFolderCancel;
+ private boolean mIsFolderNamerShowing;
+ private View mFolderNamerHolder;
+ private View mAddNewFolder;
+ private View mAddSeparator;
+ private long mCurrentFolder;
+ private FolderAdapter mAdapter;
+ private BreadCrumbView mCrumbs;
+ private TextView mFakeTitle;
+ private View mCrumbHolder;
+ private CustomListView mListView;
+ private boolean mSaveToHomeScreen;
+ private long mRootFolder;
+ private TextView mTopLevelLabel;
+ private Drawable mHeaderIcon;
+ private View mRemoveLink;
+ private View mFakeTitleHolder;
+ private static class Folder {
+ String Name;
+ long Id;
+ Folder(String name, long id) {
+ Name = name;
+ Id = id;
+ }
+ }
// Message IDs
private static final int SAVE_BOOKMARK = 100;
+ private static final int TOUCH_ICON_DOWNLOADED = 101;
+ private static final int BOOKMARK_DELETED = 102;
private Handler mHandler;
- private View.OnClickListener mSaveBookmark = new View.OnClickListener() {
- public void onClick(View v) {
- if (save()) {
+ private InputMethodManager getInputMethodManager() {
+ return (InputMethodManager) getSystemService(INPUT_METHOD_SERVICE);
+ }
+
+ private Uri getUriForFolder(long folder) {
+ Uri uri;
+ if (folder == mRootFolder) {
+ uri = BrowserContract.Bookmarks.CONTENT_URI_DEFAULT_FOLDER;
+ } else {
+ uri = BrowserContract.Bookmarks.buildFolderUri(folder);
+ }
+ String[] accountInfo = getAccountNameAndType(this);
+ if (accountInfo != null) {
+ uri = BookmarksLoader.addAccount(uri, accountInfo[1], accountInfo[0]);
+ }
+ return uri;
+ }
+
+ @Override
+ public void onTop(int level, Object data) {
+ if (null == data) return;
+ Folder folderData = (Folder) data;
+ long folder = folderData.Id;
+ LoaderManager manager = getLoaderManager();
+ CursorLoader loader = (CursorLoader) ((Loader) manager.getLoader(
+ LOADER_ID_FOLDER_CONTENTS));
+ loader.setUri(getUriForFolder(folder));
+ loader.forceLoad();
+ if (mIsFolderNamerShowing) {
+ completeOrCancelFolderNaming(true);
+ }
+ setShowBookmarkIcon(level == 1);
+ }
+
+ /**
+ * Show or hide the icon for bookmarks next to "Bookmarks" in the crumb view.
+ * @param show True if the icon should visible, false otherwise.
+ */
+ private void setShowBookmarkIcon(boolean show) {
+ Drawable drawable = show ? mHeaderIcon: null;
+ mTopLevelLabel.setCompoundDrawablesWithIntrinsicBounds(drawable, null, null, null);
+ }
+
+ @Override
+ public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
+ if (v == mFolderNamer) {
+ if (v.getText().length() > 0) {
+ if (actionId == EditorInfo.IME_NULL) {
+ // Only want to do this once.
+ if (event.getAction() == KeyEvent.ACTION_UP) {
+ completeOrCancelFolderNaming(false);
+ }
+ }
+ }
+ // Steal the key press; otherwise a newline will be added
+ return true;
+ }
+ return false;
+ }
+
+ private void switchToDefaultView(boolean changedFolder) {
+ mFolderSelector.setVisibility(View.GONE);
+ mDefaultView.setVisibility(View.VISIBLE);
+ mCrumbHolder.setVisibility(View.GONE);
+ mFakeTitleHolder.setVisibility(View.VISIBLE);
+ if (changedFolder) {
+ Object data = mCrumbs.getTopData();
+ if (data != null) {
+ Folder folder = (Folder) data;
+ mCurrentFolder = folder.Id;
+ if (mCurrentFolder == mRootFolder) {
+ // The Spinner changed to show "Other folder ..." Change
+ // it back to "Bookmarks", which is position 0 if we are
+ // editing a folder, 1 otherwise.
+ mFolder.setSelectionIgnoringSelectionChange(mEditingFolder ? 0 : 1);
+ } else {
+ ((TextView) mFolder.getSelectedView()).setText(folder.Name);
+ }
+ }
+ } else {
+ // The user canceled selecting a folder. Revert back to the earlier
+ // selection.
+ if (mSaveToHomeScreen) {
+ mFolder.setSelectionIgnoringSelectionChange(0);
+ } else {
+ if (mCurrentFolder == mRootFolder) {
+ mFolder.setSelectionIgnoringSelectionChange(mEditingFolder ? 0 : 1);
+ } else {
+ Object data = mCrumbs.getTopData();
+ if (data != null && ((Folder) data).Id == mCurrentFolder) {
+ // We are showing the correct folder heirarchy. The
+ // folder selector will say "Other folder..." Change it
+ // to say the name of the folder once again.
+ ((TextView) mFolder.getSelectedView()).setText(((Folder) data).Name);
+ } else {
+ // We are not be showing the correct folder heirarchy.
+ // Clear the Crumbs and find the proper folder
+ mCrumbs.clear();
+ setupTopCrumb();
+ LoaderManager manager = getLoaderManager();
+ manager.restartLoader(LOADER_ID_ALL_FOLDERS, null, this);
+ manager.restartLoader(LOADER_ID_FOLDER_CONTENTS, null, this);
+
+ }
+ }
+ }
+ }
+ }
+
+ @Override
+ public void onClick(View v) {
+ if (v == mButton) {
+ if (mFolderSelector.getVisibility() == View.VISIBLE) {
+ // We are showing the folder selector.
+ if (mIsFolderNamerShowing) {
+ completeOrCancelFolderNaming(false);
+ } else {
+ // User has selected a folder. Go back to the opening page
+ mSaveToHomeScreen = false;
+ switchToDefaultView(true);
+ }
+ } else if (save()) {
finish();
}
+ } else if (v == mCancelButton) {
+ if (mIsFolderNamerShowing) {
+ completeOrCancelFolderNaming(true);
+ } else if (mFolderSelector.getVisibility() == View.VISIBLE) {
+ switchToDefaultView(false);
+ } else {
+ finish();
+ }
+ } else if (v == mFolderCancel) {
+ completeOrCancelFolderNaming(true);
+ } else if (v == mAddNewFolder) {
+ setShowFolderNamer(true);
+ mFolderNamer.setText(R.string.new_folder);
+ mFolderNamer.requestFocus();
+ mAddNewFolder.setVisibility(View.GONE);
+ mAddSeparator.setVisibility(View.GONE);
+ InputMethodManager imm = getInputMethodManager();
+ // Set the InputMethodManager to focus on the ListView so that it
+ // can transfer the focus to mFolderNamer.
+ imm.focusIn(mListView);
+ imm.showSoftInput(mFolderNamer, InputMethodManager.SHOW_IMPLICIT);
+ } else if (v == mRemoveLink) {
+ if (!mEditingExisting) {
+ throw new AssertionError("Remove button should not be shown for"
+ + " new bookmarks");
+ }
+ long id = mMap.getLong(BrowserContract.Bookmarks._ID);
+ createHandler();
+ Message msg = Message.obtain(mHandler, BOOKMARK_DELETED);
+ BookmarkUtils.displayRemoveBookmarkDialog(id,
+ mTitle.getText().toString(), this, msg);
}
- };
+ }
- private View.OnClickListener mCancel = new View.OnClickListener() {
- public void onClick(View v) {
- finish();
+ // FolderSpinner.OnSetSelectionListener
+
+ @Override
+ public void onSetSelection(long id) {
+ int intId = (int) id;
+ switch (intId) {
+ case FolderSpinnerAdapter.ROOT_FOLDER:
+ mCurrentFolder = mRootFolder;
+ mSaveToHomeScreen = false;
+ break;
+ case FolderSpinnerAdapter.HOME_SCREEN:
+ // Create a short cut to the home screen
+ mSaveToHomeScreen = true;
+ break;
+ case FolderSpinnerAdapter.OTHER_FOLDER:
+ switchToFolderSelector();
+ break;
+ default:
+ break;
}
- };
+ }
+ /**
+ * Finish naming a folder, and close the IME
+ * @param cancel If true, the new folder is not created. If false, the new
+ * folder is created and the user is taken inside it.
+ */
+ private void completeOrCancelFolderNaming(boolean cancel) {
+ if (!cancel && !TextUtils.isEmpty(mFolderNamer.getText())) {
+ String name = mFolderNamer.getText().toString();
+ long id = addFolderToCurrent(mFolderNamer.getText().toString());
+ descendInto(name, id);
+ }
+ setShowFolderNamer(false);
+ mAddNewFolder.setVisibility(View.VISIBLE);
+ mAddSeparator.setVisibility(View.VISIBLE);
+ getInputMethodManager().hideSoftInputFromWindow(
+ mListView.getWindowToken(), 0);
+ }
+
+ private long addFolderToCurrent(String name) {
+ // Add the folder to the database
+ ContentValues values = new ContentValues();
+ values.put(BrowserContract.Bookmarks.TITLE,
+ name);
+ values.put(BrowserContract.Bookmarks.IS_FOLDER, 1);
+ String[] accountInfo = getAccountNameAndType(this);
+ if (accountInfo != null) {
+ values.put(BrowserContract.Bookmarks.ACCOUNT_TYPE, accountInfo[1]);
+ values.put(BrowserContract.Bookmarks.ACCOUNT_NAME, accountInfo[0]);
+ }
+ long currentFolder;
+ Object data = mCrumbs.getTopData();
+ if (data != null) {
+ currentFolder = ((Folder) data).Id;
+ } else {
+ currentFolder = mRootFolder;
+ }
+ values.put(BrowserContract.Bookmarks.PARENT, currentFolder);
+ Uri uri = getContentResolver().insert(
+ BrowserContract.Bookmarks.CONTENT_URI, values);
+ if (uri != null) {
+ return ContentUris.parseId(uri);
+ } else {
+ return -1;
+ }
+ }
+
+ private void switchToFolderSelector() {
+ // Set the list to the top in case it is scrolled.
+ mListView.setSelection(0);
+ mDefaultView.setVisibility(View.GONE);
+ mFolderSelector.setVisibility(View.VISIBLE);
+ mCrumbHolder.setVisibility(View.VISIBLE);
+ mFakeTitleHolder.setVisibility(View.GONE);
+ mAddNewFolder.setVisibility(View.VISIBLE);
+ mAddSeparator.setVisibility(View.VISIBLE);
+ }
+
+ private void descendInto(String foldername, long id) {
+ if (id != DEFAULT_FOLDER_ID) {
+ mCrumbs.pushView(foldername, new Folder(foldername, id));
+ mCrumbs.notifyController();
+ }
+ }
+
+ @Override
+ public Loader<Cursor> onCreateLoader(int id, Bundle args) {
+ String[] projection;
+ switch (id) {
+ case LOADER_ID_CHECK_FOR_DUPE:
+ projection = new String[] {
+ BrowserContract.Bookmarks._ID,
+ BrowserContract.Bookmarks.PARENT,
+ BrowserContract.Bookmarks.TITLE
+ };
+ return new CursorLoader(this,
+ BookmarkUtils.getBookmarksUri(this),
+ projection,
+ BrowserContract.Bookmarks.URL + " = ?",
+ new String[] { mOriginalUrl },
+ null);
+ case LOADER_ID_FIND_ROOT:
+ String name = args.getString(BrowserBookmarksPage.PREF_ACCOUNT_NAME);
+ String type = args.getString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE);
+
+ projection = new String[] { BrowserContract.Bookmarks._ID };
+ String selection = BrowserContract.ChromeSyncColumns.SERVER_UNIQUE + "=? AND "
+ + BrowserContract.Bookmarks.ACCOUNT_NAME + "=? AND "
+ + BrowserContract.Bookmarks.ACCOUNT_TYPE + "=?";
+ String[] selArgs = new String[] {
+ BrowserContract.ChromeSyncColumns.FOLDER_NAME_BOOKMARKS_BAR,
+ name,
+ type
+ };
+ return new CursorLoader(this,
+ BrowserContract.Bookmarks.CONTENT_URI,
+ projection,
+ selection,
+ selArgs,
+ null);
+ case LOADER_ID_ALL_FOLDERS:
+ projection = new String[] {
+ BrowserContract.Bookmarks._ID,
+ BrowserContract.Bookmarks.PARENT,
+ BrowserContract.Bookmarks.TITLE,
+ BrowserContract.Bookmarks.IS_FOLDER
+ };
+ return new CursorLoader(this,
+ BrowserContract.Bookmarks.CONTENT_URI,
+ projection,
+ BrowserContract.Bookmarks.IS_FOLDER + " != 0",
+ null,
+ null);
+ case LOADER_ID_FOLDER_CONTENTS:
+ projection = new String[] {
+ BrowserContract.Bookmarks._ID,
+ BrowserContract.Bookmarks.TITLE,
+ BrowserContract.Bookmarks.IS_FOLDER
+ };
+ String where = BrowserContract.Bookmarks.IS_FOLDER + " != 0";
+ if (mEditingFolder) {
+ where += " AND " + BrowserContract.Bookmarks._ID + " != "
+ + mMap.getLong(BrowserContract.Bookmarks._ID);
+ }
+ return new CursorLoader(this,
+ getUriForFolder(mCurrentFolder),
+ projection,
+ where,
+ null,
+ BrowserContract.Bookmarks._ID + " ASC");
+ default:
+ throw new AssertionError("Asking for nonexistant loader!");
+ }
+ }
+
+ @Override
+ public void onLoadFinished(Loader<Cursor> loader, Cursor cursor) {
+ switch (loader.getId()) {
+ case LOADER_ID_CHECK_FOR_DUPE:
+ if (cursor != null && cursor.moveToFirst()) {
+ // Site is bookmarked.
+ mEditingExisting = true;
+ showRemoveButton();
+ mFakeTitle.setText(R.string.edit_bookmark);
+ int index = cursor.getColumnIndexOrThrow(
+ BrowserContract.Bookmarks.PARENT);
+ mCurrentFolder = cursor.getLong(index);
+ index = cursor.getColumnIndexOrThrow(
+ BrowserContract.Bookmarks.TITLE);
+ String title = cursor.getString(index);
+ mTitle.setText(title);
+ index = cursor.getColumnIndexOrThrow(
+ BrowserContract.Bookmarks._ID);
+ long id = cursor.getLong(index);
+ mMap.putLong(BrowserContract.Bookmarks._ID, id);
+ }
+ onCurrentFolderFound();
+ getLoaderManager().destroyLoader(LOADER_ID_CHECK_FOR_DUPE);
+ break;
+ case LOADER_ID_FIND_ROOT:
+ long root;
+ if (cursor != null && cursor.moveToFirst()) {
+ root = cursor.getLong(0);
+ } else {
+ root = BrowserProvider2.FIXED_ID_ROOT;
+ }
+ onRootFolderFound(root);
+ getLoaderManager().destroyLoader(LOADER_ID_FIND_ROOT);
+ break;
+ case LOADER_ID_FOLDER_CONTENTS:
+ mAdapter.changeCursor(cursor);
+ break;
+ case LOADER_ID_ALL_FOLDERS:
+ long parent = mCurrentFolder;
+ int idIndex = cursor.getColumnIndexOrThrow(
+ BrowserContract.Bookmarks._ID);
+ int titleIndex = cursor.getColumnIndexOrThrow(
+ BrowserContract.Bookmarks.TITLE);
+ int parentIndex = cursor.getColumnIndexOrThrow(
+ BrowserContract.Bookmarks.PARENT);
+ // If the user is editing anything inside the "Other Bookmarks"
+ // folder, we need to stop searching up when we reach its parent.
+ // Find the root folder
+ moveCursorToFolder(cursor, mRootFolder, idIndex);
+ // omniparent is the folder which contains root, and therefore
+ // also the parent of the "Other Bookmarks" folder.
+ long omniparent = cursor.getLong(parentIndex);
+ Stack<Folder> folderStack = new Stack<Folder>();
+ while ((parent != mRootFolder) && (parent != 0) && (parent != omniparent)) {
+ // First, find the folder corresponding to the current
+ // folder
+ moveCursorToFolder(cursor, parent, idIndex);
+ String name = cursor.getString(titleIndex);
+ if (parent == mCurrentFolder) {
+ ((TextView) mFolder.getSelectedView()).setText(name);
+ }
+ folderStack.push(new Folder(name, parent));
+ parent = cursor.getLong(parentIndex);
+ }
+ while (!folderStack.isEmpty()) {
+ Folder thisFolder = folderStack.pop();
+ mCrumbs.pushView(thisFolder.Name, thisFolder);
+ }
+ getLoaderManager().destroyLoader(LOADER_ID_ALL_FOLDERS);
+ break;
+ default:
+ break;
+ }
+ }
+
+ public void onLoaderReset(Loader<Cursor> loader) {
+ switch (loader.getId()) {
+ case LOADER_ID_FOLDER_CONTENTS:
+ mAdapter.changeCursor(null);
+ break;
+ }
+ }
+
+ /**
+ * Move cursor to the position that has folderToFind as its "_id".
+ * @param cursor Cursor containing folders in the bookmarks database
+ * @param folderToFind "_id" of the folder to move to.
+ * @param idIndex Index in cursor of "_id"
+ * @throws AssertionError if cursor is empty or there is no row with folderToFind
+ * as its "_id".
+ */
+ void moveCursorToFolder(Cursor cursor, long folderToFind, int idIndex)
+ throws AssertionError {
+ if (!cursor.moveToFirst()) {
+ throw new AssertionError("No folders in the database!");
+ }
+ long folder;
+ do {
+ folder = cursor.getLong(idIndex);
+ } while (folder != folderToFind && cursor.moveToNext());
+ if (cursor.isAfterLast()) {
+ throw new AssertionError("Folder(id=" + folderToFind
+ + ") holding this bookmark does not exist!");
+ }
+ }
+
+ @Override
+ public void onItemClick(AdapterView<?> parent, View view, int position,
+ long id) {
+ TextView tv = (TextView) view.findViewById(android.R.id.text1);
+ // Switch to the folder that was clicked on.
+ descendInto(tv.getText().toString(), id);
+ }
+
+ private void setShowFolderNamer(boolean show) {
+ if (show != mIsFolderNamerShowing) {
+ mIsFolderNamerShowing = show;
+ if (show) {
+ // Set the selection to the folder namer so it will be in
+ // view.
+ mListView.addFooterView(mFolderNamerHolder);
+ } else {
+ mListView.removeFooterView(mFolderNamerHolder);
+ }
+ // Refresh the list.
+ mListView.setAdapter(mAdapter);
+ if (show) {
+ mListView.setSelection(mListView.getCount() - 1);
+ }
+ }
+ }
+
+ /**
+ * Shows a list of names of folders.
+ */
+ private class FolderAdapter extends CursorAdapter {
+ public FolderAdapter(Context context) {
+ super(context, null);
+ }
+
+ @Override
+ public void bindView(View view, Context context, Cursor cursor) {
+ ((TextView) view.findViewById(android.R.id.text1)).setText(
+ cursor.getString(cursor.getColumnIndexOrThrow(
+ BrowserContract.Bookmarks.TITLE)));
+ }
+
+ @Override
+ public View newView(Context context, Cursor cursor, ViewGroup parent) {
+ View view = LayoutInflater.from(context).inflate(
+ R.layout.folder_list_item, null);
+ view.setBackgroundDrawable(context.getResources().
+ getDrawable(android.R.drawable.list_selector_background));
+ return view;
+ }
+
+ @Override
+ public boolean isEmpty() {
+ // Do not show the empty view if the user is creating a new folder.
+ return super.isEmpty() && !mIsFolderNamerShowing;
+ }
+ }
+
+ @Override
protected void onCreate(Bundle icicle) {
super.onCreate(icicle);
- requestWindowFeature(Window.FEATURE_LEFT_ICON);
+ requestWindowFeature(Window.FEATURE_NO_TITLE);
+
+ mMap = getIntent().getExtras();
+
setContentView(R.layout.browser_add_bookmark);
- setTitle(R.string.save_to_bookmarks);
- getWindow().setFeatureDrawableResource(Window.FEATURE_LEFT_ICON, R.drawable.ic_list_bookmark);
-
+
+ Window window = getWindow();
+
String title = null;
String url = null;
- mMap = getIntent().getExtras();
+
+ mFakeTitle = (TextView) findViewById(R.id.fake_title);
+
if (mMap != null) {
- Bundle b = mMap.getBundle("bookmark");
+ Bundle b = mMap.getBundle(EXTRA_EDIT_BOOKMARK);
if (b != null) {
+ mEditingFolder = mMap.getBoolean(EXTRA_IS_FOLDER, false);
mMap = b;
mEditingExisting = true;
- setTitle(R.string.edit_bookmark);
+ mFakeTitle.setText(R.string.edit_bookmark);
+ if (mEditingFolder) {
+ findViewById(R.id.row_address).setVisibility(View.GONE);
+ } else {
+ showRemoveButton();
+ }
+ } else {
+ int gravity = mMap.getInt("gravity", -1);
+ if (gravity != -1) {
+ WindowManager.LayoutParams l = window.getAttributes();
+ l.gravity = gravity;
+ window.setAttributes(l);
+ }
}
- title = mMap.getString("title");
- url = mOriginalUrl = mMap.getString("url");
- mTouchIconUrl = mMap.getString("touch_icon_url");
- mThumbnail = (Bitmap) mMap.getParcelable("thumbnail");
+ title = mMap.getString(BrowserContract.Bookmarks.TITLE);
+ url = mOriginalUrl = mMap.getString(BrowserContract.Bookmarks.URL);
+ mTouchIconUrl = mMap.getString(TOUCH_ICON_URL);
+ mCurrentFolder = mMap.getLong(BrowserContract.Bookmarks.PARENT, DEFAULT_FOLDER_ID);
}
mTitle = (EditText) findViewById(R.id.title);
mTitle.setText(title);
+
mAddress = (EditText) findViewById(R.id.address);
mAddress.setText(url);
- View.OnClickListener accept = mSaveBookmark;
mButton = (TextView) findViewById(R.id.OK);
- mButton.setOnClickListener(accept);
+ mButton.setOnClickListener(this);
mCancelButton = findViewById(R.id.cancel);
- mCancelButton.setOnClickListener(mCancel);
-
- if (!getWindow().getDecorView().isInTouchMode()) {
+ mCancelButton.setOnClickListener(this);
+
+ mFolder = (FolderSpinner) findViewById(R.id.folder);
+ mFolder.setAdapter(new FolderSpinnerAdapter(!mEditingFolder));
+ mFolder.setOnSetSelectionListener(this);
+
+ mDefaultView = findViewById(R.id.default_view);
+ mFolderSelector = findViewById(R.id.folder_selector);
+
+ mFolderNamerHolder = getLayoutInflater().inflate(R.layout.new_folder_layout, null);
+ mFolderNamer = (EditText) mFolderNamerHolder.findViewById(R.id.folder_namer);
+ mFolderNamer.setOnEditorActionListener(this);
+ mFolderCancel = mFolderNamerHolder.findViewById(R.id.close);
+ mFolderCancel.setOnClickListener(this);
+
+ mAddNewFolder = findViewById(R.id.add_new_folder);
+ mAddNewFolder.setOnClickListener(this);
+ mAddSeparator = findViewById(R.id.add_divider);
+
+ mCrumbs = (BreadCrumbView) findViewById(R.id.crumbs);
+ mCrumbs.setUseBackButton(true);
+ mCrumbs.setController(this);
+ mHeaderIcon = getResources().getDrawable(R.drawable.ic_folder_holo_dark);
+ mCrumbHolder = findViewById(R.id.crumb_holder);
+ mCrumbs.setMaxVisible(MAX_CRUMBS_SHOWN);
+
+ mAdapter = new FolderAdapter(this);
+ mListView = (CustomListView) findViewById(R.id.list);
+ View empty = findViewById(R.id.empty);
+ mListView.setEmptyView(empty);
+ mListView.setAdapter(mAdapter);
+ mListView.setOnItemClickListener(this);
+ mListView.addEditText(mFolderNamer);
+
+ mFakeTitleHolder = findViewById(R.id.title_holder);
+
+ if (!window.getDecorView().isInTouchMode()) {
mButton.requestFocus();
}
+
+ String[] accountInfo = getAccountNameAndType(this);
+ if (accountInfo == null) {
+ onRootFolderFound(BrowserProvider2.FIXED_ID_ROOT);
+ } else {
+ Bundle args = new Bundle();
+ args.putString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, accountInfo[0]);
+ args.putString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE, accountInfo[1]);
+ getLoaderManager().initLoader(LOADER_ID_FIND_ROOT, args, this);
+ }
+
+ }
+
+ private void showRemoveButton() {
+ findViewById(R.id.remove_divider).setVisibility(View.VISIBLE);
+ mRemoveLink = findViewById(R.id.remove);
+ mRemoveLink.setVisibility(View.VISIBLE);
+ mRemoveLink.setOnClickListener(this);
+ }
+
+ // Called once we have determined which folder is the root folder
+ private void onRootFolderFound(long root) {
+ mRootFolder = root;
+ if (mCurrentFolder == DEFAULT_FOLDER_ID) {
+ mCurrentFolder = mRootFolder;
+ }
+ setupTopCrumb();
+ if (mEditingExisting || TextUtils.isEmpty(mOriginalUrl)) {
+ onCurrentFolderFound();
+ } else {
+ // User is attempting to bookmark a site, rather than deliberately
+ // editing a bookmark. Rather than let them create a duplicate
+ // bookmark, see if the bookmark already exists.
+ getLoaderManager().initLoader(LOADER_ID_CHECK_FOR_DUPE, null, this);
+ }
+ }
+
+ private void setupTopCrumb() {
+ String name = getString(R.string.bookmarks);
+ mTopLevelLabel = (TextView) mCrumbs.pushView(name, false,
+ new Folder(name, mRootFolder));
+ // To better match the other folders.
+ mTopLevelLabel.setCompoundDrawablePadding(6);
+ }
+
+ private void onCurrentFolderFound() {
+ LoaderManager manager = getLoaderManager();
+ if (mCurrentFolder != mRootFolder) {
+ // Find all the folders
+ manager.initLoader(LOADER_ID_ALL_FOLDERS, null, this);
+ // Since we're not in the root folder, change the selection to other
+ // folder now. The text will get changed once we select the correct
+ // folder.
+ mFolder.setSelectionIgnoringSelectionChange(mEditingFolder ? 1 : 2);
+ } else {
+ setShowBookmarkIcon(true);
+ if (!mEditingFolder) {
+ // Initially the "Bookmarks" folder should be showing, rather than
+ // the home screen. In the editing folder case, home screen is not
+ // an option, so "Bookmarks" folder is already at the top.
+ mFolder.setSelectionIgnoringSelectionChange(FolderSpinnerAdapter.ROOT_FOLDER);
+ }
+ }
+ // Find the contents of the current folder
+ manager.initLoader(LOADER_ID_FOLDER_CONTENTS, null, this);
+}
+ /**
+ * Get the account name and type of the currently synced account.
+ * @param context Context to access preferences.
+ * @return null if no account name or type. Otherwise, the result will be
+ * an array of two Strings, the accountName and accountType, respectively.
+ */
+ private String[] getAccountNameAndType(Context context) {
+ SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
+ String accountName = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, null);
+ String accountType = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE, null);
+ if (TextUtils.isEmpty(accountName) || TextUtils.isEmpty(accountType)) {
+ return null;
+ }
+ return new String[] { accountName, accountType };
}
/**
* Runnable to save a bookmark, so it can be performed in its own thread.
*/
private class SaveBookmarkRunnable implements Runnable {
+ // FIXME: This should be an async task.
private Message mMessage;
private Context mContext;
public SaveBookmarkRunnable(Context ctx, Message msg) {
@@ -125,18 +797,18 @@
public void run() {
// Unbundle bookmark data.
Bundle bundle = mMessage.getData();
- String title = bundle.getString("title");
- String url = bundle.getString("url");
- boolean invalidateThumbnail = bundle.getBoolean(
- "invalidateThumbnail");
+ String title = bundle.getString(BrowserContract.Bookmarks.TITLE);
+ String url = bundle.getString(BrowserContract.Bookmarks.URL);
+ boolean invalidateThumbnail = bundle.getBoolean(REMOVE_THUMBNAIL);
Bitmap thumbnail = invalidateThumbnail ? null
- : (Bitmap) bundle.getParcelable("thumbnail");
- String touchIconUrl = bundle.getString("touchIconUrl");
+ : (Bitmap) bundle.getParcelable(BrowserContract.Bookmarks.THUMBNAIL);
+ String touchIconUrl = bundle.getString(TOUCH_ICON_URL);
// Save to the bookmarks DB.
try {
final ContentResolver cr = getContentResolver();
- Bookmarks.addBookmark(null, cr, url, title, thumbnail, true);
+ Bookmarks.addBookmark(AddBookmarkPage.this, false, url,
+ title, thumbnail, true, mCurrentFolder);
if (touchIconUrl != null) {
new DownloadTouchIcon(mContext, cr, url).execute(mTouchIconUrl);
}
@@ -148,6 +820,28 @@
}
}
+ private static class UpdateBookmarkTask extends AsyncTask<ContentValues, Void, Void> {
+ Context mContext;
+ Long mId;
+
+ public UpdateBookmarkTask(Context context, long id) {
+ mContext = context;
+ mId = id;
+ }
+
+ @Override
+ protected Void doInBackground(ContentValues... params) {
+ if (params.length != 1) {
+ throw new IllegalArgumentException("No ContentValues provided!");
+ }
+ Uri uri = ContentUris.withAppendedId(BookmarkUtils.getBookmarksUri(mContext), mId);
+ mContext.getContentResolver().update(
+ uri,
+ params[0], null, null);
+ return null;
+ }
+ }
+
private void createHandler() {
if (mHandler == null) {
mHandler = new Handler() {
@@ -163,6 +857,18 @@
Toast.LENGTH_LONG).show();
}
break;
+ case TOUCH_ICON_DOWNLOADED:
+ Bundle b = msg.getData();
+ sendBroadcast(BookmarkUtils.createAddToHomeIntent(
+ AddBookmarkPage.this,
+ b.getString(BrowserContract.Bookmarks.URL),
+ b.getString(BrowserContract.Bookmarks.TITLE),
+ (Bitmap) b.getParcelable(BrowserContract.Bookmarks.TOUCH_ICON),
+ (Bitmap) b.getParcelable(BrowserContract.Bookmarks.FAVICON)));
+ break;
+ case BOOKMARK_DELETED:
+ finish();
+ break;
}
}
};
@@ -176,12 +882,13 @@
createHandler();
String title = mTitle.getText().toString().trim();
- String unfilteredUrl =
- BrowserActivity.fixUrl(mAddress.getText().toString());
+ String unfilteredUrl;
+ unfilteredUrl = UrlUtils.fixUrl(mAddress.getText().toString());
+
boolean emptyTitle = title.length() == 0;
boolean emptyUrl = unfilteredUrl.trim().length() == 0;
Resources r = getResources();
- if (emptyTitle || emptyUrl) {
+ if (emptyTitle || (emptyUrl && !mEditingFolder)) {
if (emptyTitle) {
mTitle.setError(r.getText(R.string.bookmark_needs_title));
}
@@ -189,62 +896,136 @@
mAddress.setError(r.getText(R.string.bookmark_needs_url));
}
return false;
+
}
String url = unfilteredUrl.trim();
- try {
- // We allow bookmarks with a javascript: scheme, but these will in most cases
- // fail URI parsing, so don't try it if that's the kind of bookmark we have.
+ if (!mEditingFolder) {
+ try {
+ // We allow bookmarks with a javascript: scheme, but these will in most cases
+ // fail URI parsing, so don't try it if that's the kind of bookmark we have.
- if (!url.toLowerCase().startsWith("javascript:")) {
- URI uriObj = new URI(url);
- String scheme = uriObj.getScheme();
- if (!Bookmarks.urlHasAcceptableScheme(url)) {
- // If the scheme was non-null, let the user know that we
- // can't save their bookmark. If it was null, we'll assume
- // they meant http when we parse it in the WebAddress class.
- if (scheme != null) {
- mAddress.setError(r.getText(R.string.bookmark_cannot_save_url));
- return false;
+ if (!url.toLowerCase().startsWith("javascript:")) {
+ URI uriObj = new URI(url);
+ String scheme = uriObj.getScheme();
+ if (!Bookmarks.urlHasAcceptableScheme(url)) {
+ // If the scheme was non-null, let the user know that we
+ // can't save their bookmark. If it was null, we'll assume
+ // they meant http when we parse it in the WebAddress class.
+ if (scheme != null) {
+ mAddress.setError(r.getText(R.string.bookmark_cannot_save_url));
+ return false;
+ }
+ WebAddress address;
+ try {
+ address = new WebAddress(unfilteredUrl);
+ } catch (ParseException e) {
+ throw new URISyntaxException("", "");
+ }
+ if (address.getHost().length() == 0) {
+ throw new URISyntaxException("", "");
+ }
+ url = address.toString();
}
- WebAddress address;
- try {
- address = new WebAddress(unfilteredUrl);
- } catch (ParseException e) {
- throw new URISyntaxException("", "");
- }
- if (address.mHost.length() == 0) {
- throw new URISyntaxException("", "");
- }
- url = address.toString();
}
+ } catch (URISyntaxException e) {
+ mAddress.setError(r.getText(R.string.bookmark_url_not_valid));
+ return false;
}
- } catch (URISyntaxException e) {
- mAddress.setError(r.getText(R.string.bookmark_url_not_valid));
- return false;
}
+ if (mSaveToHomeScreen) {
+ mEditingExisting = false;
+ }
+
+ boolean urlUnmodified = url.equals(mOriginalUrl);
+
if (mEditingExisting) {
- mMap.putString("title", title);
- mMap.putString("url", url);
- mMap.putBoolean("invalidateThumbnail", !url.equals(mOriginalUrl));
- setResult(RESULT_OK, (new Intent()).setAction(
- getIntent().toString()).putExtras(mMap));
+ Long id = mMap.getLong(BrowserContract.Bookmarks._ID);
+ ContentValues values = new ContentValues();
+ values.put(BrowserContract.Bookmarks.TITLE, title);
+ values.put(BrowserContract.Bookmarks.PARENT, mCurrentFolder);
+ if (!mEditingFolder) {
+ values.put(BrowserContract.Bookmarks.URL, url);
+ if (!urlUnmodified) {
+ values.putNull(BrowserContract.Bookmarks.THUMBNAIL);
+ }
+ }
+ if (values.size() > 0) {
+ new UpdateBookmarkTask(getApplicationContext(), id).execute(values);
+ }
+ setResult(RESULT_OK);
} else {
- // Post a message to write to the DB.
+ Bitmap thumbnail;
+ Bitmap favicon;
+ if (urlUnmodified) {
+ thumbnail = (Bitmap) mMap.getParcelable(
+ BrowserContract.Bookmarks.THUMBNAIL);
+ favicon = (Bitmap) mMap.getParcelable(
+ BrowserContract.Bookmarks.FAVICON);
+ } else {
+ thumbnail = null;
+ favicon = null;
+ }
+
Bundle bundle = new Bundle();
- bundle.putString("title", title);
- bundle.putString("url", url);
- bundle.putParcelable("thumbnail", mThumbnail);
- bundle.putBoolean("invalidateThumbnail", !url.equals(mOriginalUrl));
- bundle.putString("touchIconUrl", mTouchIconUrl);
- Message msg = Message.obtain(mHandler, SAVE_BOOKMARK);
- msg.setData(bundle);
- // Start a new thread so as to not slow down the UI
- Thread t = new Thread(new SaveBookmarkRunnable(getApplicationContext(), msg));
- t.start();
+ bundle.putString(BrowserContract.Bookmarks.TITLE, title);
+ bundle.putString(BrowserContract.Bookmarks.URL, url);
+ bundle.putParcelable(BrowserContract.Bookmarks.FAVICON, favicon);
+
+ if (mSaveToHomeScreen) {
+ if (mTouchIconUrl != null && urlUnmodified) {
+ Message msg = Message.obtain(mHandler,
+ TOUCH_ICON_DOWNLOADED);
+ msg.setData(bundle);
+ DownloadTouchIcon icon = new DownloadTouchIcon(this, msg,
+ mMap.getString(USER_AGENT));
+ icon.execute(mTouchIconUrl);
+ } else {
+ sendBroadcast(BookmarkUtils.createAddToHomeIntent(this, url,
+ title, null /*touchIcon*/, favicon));
+ }
+ } else {
+ bundle.putParcelable(BrowserContract.Bookmarks.THUMBNAIL, thumbnail);
+ bundle.putBoolean(REMOVE_THUMBNAIL, !urlUnmodified);
+ bundle.putString(TOUCH_ICON_URL, mTouchIconUrl);
+ // Post a message to write to the DB.
+ Message msg = Message.obtain(mHandler, SAVE_BOOKMARK);
+ msg.setData(bundle);
+ // Start a new thread so as to not slow down the UI
+ Thread t = new Thread(new SaveBookmarkRunnable(getApplicationContext(), msg));
+ t.start();
+ }
setResult(RESULT_OK);
LogTag.logBookmarkAdded(url, "bookmarkview");
}
return true;
}
+
+ /*
+ * Class used as a proxy for the InputMethodManager to get to mFolderNamer
+ */
+ public static class CustomListView extends ListView {
+ private EditText mEditText;
+
+ public void addEditText(EditText editText) {
+ mEditText = editText;
+ }
+
+ public CustomListView(Context context) {
+ super(context);
+ }
+
+ public CustomListView(Context context, AttributeSet attrs) {
+ super(context, attrs);
+ }
+
+ public CustomListView(Context context, AttributeSet attrs, int defStyle) {
+ super(context, attrs, defStyle);
+ }
+
+ @Override
+ public boolean checkInputConnectionProxy(View view) {
+ return view == mEditText;
+ }
+ }
}
diff --git a/src/com/android/browser/AutoFillProfileDatabase.java b/src/com/android/browser/AutoFillProfileDatabase.java
new file mode 100644
index 0000000..3345e92
--- /dev/null
+++ b/src/com/android/browser/AutoFillProfileDatabase.java
@@ -0,0 +1,154 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.content.Context;
+import android.database.Cursor;
+import android.database.sqlite.SQLiteDatabase;
+import android.database.sqlite.SQLiteOpenHelper;
+import android.provider.BaseColumns;
+import android.util.Log;
+import android.webkit.WebSettings.AutoFillProfile;
+
+public class AutoFillProfileDatabase {
+
+ static final String LOGTAG = "AutoFillProfileDatabase";
+
+ static final String DATABASE_NAME = "autofill.db";
+ static final int DATABASE_VERSION = 2;
+ static final String PROFILES_TABLE_NAME = "profiles";
+ private AutoFillProfileDatabaseHelper mOpenHelper;
+ private static AutoFillProfileDatabase sInstance;
+
+ public static final class Profiles implements BaseColumns {
+ private Profiles() { }
+
+ static final String FULL_NAME = "fullname";
+ static final String EMAIL_ADDRESS = "email";
+ static final String COMPANY_NAME = "companyname";
+ static final String ADDRESS_LINE_1 = "addressline1";
+ static final String ADDRESS_LINE_2 = "addressline2";
+ static final String CITY = "city";
+ static final String STATE = "state";
+ static final String ZIP_CODE = "zipcode";
+ static final String COUNTRY = "country";
+ static final String PHONE_NUMBER = "phone";
+ }
+
+ private static class AutoFillProfileDatabaseHelper extends SQLiteOpenHelper {
+ AutoFillProfileDatabaseHelper(Context context) {
+ super(context, DATABASE_NAME, null, DATABASE_VERSION);
+ }
+
+ @Override
+ public void onCreate(SQLiteDatabase db) {
+ db.execSQL("CREATE TABLE " + PROFILES_TABLE_NAME + " ("
+ + Profiles._ID + " INTEGER PRIMARY KEY,"
+ + Profiles.FULL_NAME + " TEXT,"
+ + Profiles.EMAIL_ADDRESS + " TEXT,"
+ + Profiles.COMPANY_NAME + " TEXT,"
+ + Profiles.ADDRESS_LINE_1 + " TEXT,"
+ + Profiles.ADDRESS_LINE_2 + " TEXT,"
+ + Profiles.CITY + " TEXT,"
+ + Profiles.STATE + " TEXT,"
+ + Profiles.ZIP_CODE + " TEXT,"
+ + Profiles.COUNTRY + " TEXT,"
+ + Profiles.PHONE_NUMBER + " TEXT"
+ + " );");
+ }
+
+ @Override
+ public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
+ Log.w(LOGTAG, "Upgrading database from version " + oldVersion + " to "
+ + newVersion + ", which will destroy all old data");
+ db.execSQL("DROP TABLE IF EXISTS " + PROFILES_TABLE_NAME);
+ onCreate(db);
+ }
+ }
+
+ private AutoFillProfileDatabase(Context context) {
+ mOpenHelper = new AutoFillProfileDatabaseHelper(context);
+ }
+
+ public static AutoFillProfileDatabase getInstance(Context context) {
+ if (sInstance == null) {
+ sInstance = new AutoFillProfileDatabase(context);
+ }
+ return sInstance;
+ }
+
+ private SQLiteDatabase getDatabase(boolean writable) {
+ return writable ? mOpenHelper.getWritableDatabase() : mOpenHelper.getReadableDatabase();
+ }
+
+ public void addOrUpdateProfile(final int id, AutoFillProfile profile) {
+ final String sql = "INSERT OR REPLACE INTO " + PROFILES_TABLE_NAME + " ("
+ + Profiles._ID + ","
+ + Profiles.FULL_NAME + ","
+ + Profiles.EMAIL_ADDRESS + ","
+ + Profiles.COMPANY_NAME + ","
+ + Profiles.ADDRESS_LINE_1 + ","
+ + Profiles.ADDRESS_LINE_2 + ","
+ + Profiles.CITY + ","
+ + Profiles.STATE + ","
+ + Profiles.ZIP_CODE + ","
+ + Profiles.COUNTRY + ","
+ + Profiles.PHONE_NUMBER
+ + ") VALUES (?,?,?,?,?,?,?,?,?,?,?);";
+ final Object[] params = { id,
+ profile.getFullName(),
+ profile.getEmailAddress(),
+ profile.getCompanyName(),
+ profile.getAddressLine1(),
+ profile.getAddressLine2(),
+ profile.getCity(),
+ profile.getState(),
+ profile.getZipCode(),
+ profile.getCountry(),
+ profile.getPhoneNumber() };
+ getDatabase(true).execSQL(sql, params);
+ }
+
+ public Cursor getProfile(int id) {
+ final String[] cols = {
+ Profiles.FULL_NAME,
+ Profiles.EMAIL_ADDRESS,
+ Profiles.COMPANY_NAME,
+ Profiles.ADDRESS_LINE_1,
+ Profiles.ADDRESS_LINE_2,
+ Profiles.CITY,
+ Profiles.STATE,
+ Profiles.ZIP_CODE,
+ Profiles.COUNTRY,
+ Profiles.PHONE_NUMBER
+ };
+
+ final String[] selectArgs = { Integer.toString(id) };
+ return getDatabase(false).query(PROFILES_TABLE_NAME, cols, Profiles._ID + "=?", selectArgs,
+ null, null, null, "1");
+ }
+
+ public void dropProfile(int id) {
+ final String sql = "DELETE FROM " + PROFILES_TABLE_NAME +" WHERE " + Profiles._ID + " = ?;";
+ final Object[] params = { id };
+ getDatabase(true).execSQL(sql, params);
+ }
+
+ public void close() {
+ mOpenHelper.close();
+ }
+}
diff --git a/src/com/android/browser/AutoFillSettingsFragment.java b/src/com/android/browser/AutoFillSettingsFragment.java
new file mode 100644
index 0000000..3a7ae12
--- /dev/null
+++ b/src/com/android/browser/AutoFillSettingsFragment.java
@@ -0,0 +1,266 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.app.Fragment;
+import android.content.Context;
+import android.os.Bundle;
+import android.os.Handler;
+import android.os.Message;
+import android.text.Editable;
+import android.text.TextWatcher;
+import android.util.Log;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.View.OnClickListener;
+import android.view.LayoutInflater;
+import android.view.inputmethod.InputMethodManager;
+import android.webkit.WebSettings.AutoFillProfile;
+import android.widget.Button;
+import android.widget.EditText;
+import android.widget.Toast;
+
+public class AutoFillSettingsFragment extends Fragment {
+
+ private static final String LOGTAG = "AutoFillSettingsFragment";
+
+ private EditText mFullNameEdit;
+ private EditText mEmailEdit;
+ private EditText mCompanyEdit;
+ private EditText mAddressLine1Edit;
+ private EditText mAddressLine2Edit;
+ private EditText mCityEdit;
+ private EditText mStateEdit;
+ private EditText mZipEdit;
+ private EditText mCountryEdit;
+ private EditText mPhoneEdit;
+
+ private Button mSaveButton;
+
+ // Used to display toast after DB interactions complete.
+ private Handler mHandler;
+
+ private final static int PROFILE_SAVED_MSG = 100;
+ private final static int PROFILE_DELETED_MSG = 101;
+
+ // For now we support just one profile so it's safe to hardcode the
+ // id to 1 here. In the future this unique identifier will be set
+ // dynamically.
+ private int mUniqueId = 1;
+
+ private class PhoneNumberValidator implements TextWatcher {
+ // Keep in sync with kPhoneNumberLength in chrome/browser/autofill/phone_number.cc
+ private static final int PHONE_NUMBER_LENGTH = 7;
+ private static final String PHONE_NUMBER_SEPARATORS_REGEX = "[\\s\\.\\(\\)-]";
+
+ public void afterTextChanged(Editable s) {
+ String phoneNumber = s.toString();
+ int phoneNumberLength = phoneNumber.length();
+
+ // Strip out any phone number separators.
+ phoneNumber = phoneNumber.replaceAll(PHONE_NUMBER_SEPARATORS_REGEX, "");
+
+ int strippedPhoneNumberLength = phoneNumber.length();
+
+ if (phoneNumberLength > 0 && strippedPhoneNumberLength < PHONE_NUMBER_LENGTH) {
+ mPhoneEdit.setError(getResources().getText(
+ R.string.autofill_profile_editor_phone_number_invalid));
+ } else {
+ mPhoneEdit.setError(null);
+ }
+
+ updateButtonState();
+ }
+
+ public void beforeTextChanged(CharSequence s, int start, int count, int after) {
+ }
+
+ public void onTextChanged(CharSequence s, int start, int before, int count) {
+ }
+ }
+
+ private class FieldChangedListener implements TextWatcher {
+ public void afterTextChanged(Editable s) {
+ updateButtonState();
+ }
+
+ public void beforeTextChanged(CharSequence s, int start, int count, int after) {
+ }
+
+ public void onTextChanged(CharSequence s, int start, int before, int count) {
+ }
+
+ }
+
+ private TextWatcher mFieldChangedListener = new FieldChangedListener();
+
+ public AutoFillSettingsFragment() {
+ mHandler = new Handler() {
+ @Override
+ public void handleMessage(Message msg) {
+ switch (msg.what) {
+ case PROFILE_SAVED_MSG:
+ Toast.makeText(getActivity(), R.string.autofill_profile_successful_save,
+ Toast.LENGTH_SHORT).show();
+ break;
+
+ case PROFILE_DELETED_MSG:
+ Toast.makeText(getActivity(), R.string.autofill_profile_successful_delete,
+ Toast.LENGTH_SHORT).show();
+ break;
+ }
+ }
+ };
+ }
+
+ @Override
+ public void onCreate(Bundle savedState) {
+ super.onCreate(savedState);
+ }
+
+ @Override
+ public View onCreateView(LayoutInflater inflater, ViewGroup container,
+ Bundle savedInstanceState) {
+ View v = inflater.inflate(R.layout.autofill_settings_fragment, container, false);
+
+ mFullNameEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_name_edit);
+ mEmailEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_email_address_edit);
+ mCompanyEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_company_name_edit);
+ mAddressLine1Edit = (EditText)v.findViewById(
+ R.id.autofill_profile_editor_address_line_1_edit);
+ mAddressLine2Edit = (EditText)v.findViewById(
+ R.id.autofill_profile_editor_address_line_2_edit);
+ mCityEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_city_edit);
+ mStateEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_state_edit);
+ mZipEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_zip_code_edit);
+ mCountryEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_country_edit);
+ mPhoneEdit = (EditText)v.findViewById(R.id.autofill_profile_editor_phone_number_edit);
+
+ mFullNameEdit.addTextChangedListener(mFieldChangedListener);
+ mEmailEdit.addTextChangedListener(mFieldChangedListener);
+ mCompanyEdit.addTextChangedListener(mFieldChangedListener);
+ mAddressLine1Edit.addTextChangedListener(mFieldChangedListener);
+ mAddressLine2Edit.addTextChangedListener(mFieldChangedListener);
+ mCityEdit.addTextChangedListener(mFieldChangedListener);
+ mStateEdit.addTextChangedListener(mFieldChangedListener);
+ mZipEdit.addTextChangedListener(mFieldChangedListener);
+ mCountryEdit.addTextChangedListener(mFieldChangedListener);
+ mPhoneEdit.addTextChangedListener(new PhoneNumberValidator());
+
+ mSaveButton = (Button)v.findViewById(R.id.autofill_profile_editor_save_button);
+ mSaveButton.setOnClickListener(new OnClickListener() {
+ public void onClick(View button) {
+ AutoFillProfile newProfile = new AutoFillProfile(
+ mUniqueId,
+ mFullNameEdit.getText().toString(),
+ mEmailEdit.getText().toString(),
+ mCompanyEdit.getText().toString(),
+ mAddressLine1Edit.getText().toString(),
+ mAddressLine2Edit.getText().toString(),
+ mCityEdit.getText().toString(),
+ mStateEdit.getText().toString(),
+ mZipEdit.getText().toString(),
+ mCountryEdit.getText().toString(),
+ mPhoneEdit.getText().toString());
+
+ BrowserSettings.getInstance().setAutoFillProfile(getActivity(), newProfile,
+ mHandler.obtainMessage(PROFILE_SAVED_MSG));
+ closeEditor();
+ }
+ });
+
+ Button deleteButton = (Button)v.findViewById(R.id.autofill_profile_editor_delete_button);
+ deleteButton.setOnClickListener(new OnClickListener() {
+ public void onClick(View button) {
+ // Clear the UI.
+ mFullNameEdit.setText("");
+ mEmailEdit.setText("");
+ mCompanyEdit.setText("");
+ mAddressLine1Edit.setText("");
+ mAddressLine2Edit.setText("");
+ mCityEdit.setText("");
+ mStateEdit.setText("");
+ mZipEdit.setText("");
+ mCountryEdit.setText("");
+ mPhoneEdit.setText("");
+
+ // Update browser settings and native with a null profile. This will
+ // trigger the current profile to get deleted from the DB.
+ BrowserSettings.getInstance().setAutoFillProfile(getActivity(), null,
+ mHandler.obtainMessage(PROFILE_DELETED_MSG));
+
+ updateButtonState();
+ }
+ });
+
+ Button cancelButton = (Button)v.findViewById(R.id.autofill_profile_editor_cancel_button);
+ cancelButton.setOnClickListener(new OnClickListener() {
+ public void onClick(View button) {
+ closeEditor();
+ }
+ });
+
+ // Populate the text boxes with any pre existing AutoFill data.
+ AutoFillProfile activeProfile = BrowserSettings.getInstance().getAutoFillProfile();
+ if (activeProfile != null) {
+ mFullNameEdit.setText(activeProfile.getFullName());
+ mEmailEdit.setText(activeProfile.getEmailAddress());
+ mCompanyEdit.setText(activeProfile.getCompanyName());
+ mAddressLine1Edit.setText(activeProfile.getAddressLine1());
+ mAddressLine2Edit.setText(activeProfile.getAddressLine2());
+ mCityEdit.setText(activeProfile.getCity());
+ mStateEdit.setText(activeProfile.getState());
+ mZipEdit.setText(activeProfile.getZipCode());
+ mCountryEdit.setText(activeProfile.getCountry());
+ mPhoneEdit.setText(activeProfile.getPhoneNumber());
+ }
+
+ updateButtonState();
+
+ return v;
+ }
+
+ public void updateButtonState() {
+
+ boolean valid = (mFullNameEdit.getText().toString().length() > 0 ||
+ mEmailEdit.getText().toString().length() > 0 ||
+ mCompanyEdit.getText().toString().length() > 0 ||
+ mAddressLine1Edit.getText().toString().length() > 0 ||
+ mAddressLine2Edit.getText().toString().length() > 0 ||
+ mCityEdit.getText().toString().length() > 0 ||
+ mStateEdit.getText().toString().length() > 0 ||
+ mZipEdit.getText().toString().length() > 0 ||
+ mCountryEdit.getText().toString().length() > 0) &&
+ mPhoneEdit.getError() == null;
+
+ // Only enable the save buttons if we have at least one field completed
+ // and the phone number (if present is valid).
+ mSaveButton.setEnabled(valid);
+ }
+
+ private void closeEditor() {
+ // Hide the IME if the user wants to close while an EditText has focus
+ InputMethodManager imm = (InputMethodManager) getActivity().getSystemService(
+ Context.INPUT_METHOD_SERVICE);
+ imm.hideSoftInputFromWindow(getView().getWindowToken(), 0);
+ if (getFragmentManager().getBackStackEntryCount() > 0) {
+ getFragmentManager().popBackStack();
+ } else {
+ getActivity().finish();
+ }
+ }
+}
diff --git a/src/com/android/browser/BaseUi.java b/src/com/android/browser/BaseUi.java
new file mode 100644
index 0000000..756f8b8
--- /dev/null
+++ b/src/com/android/browser/BaseUi.java
@@ -0,0 +1,685 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.Tab.LockIcon;
+
+import android.app.Activity;
+import android.content.res.Configuration;
+import android.content.res.Resources;
+import android.graphics.Bitmap;
+import android.graphics.BitmapFactory;
+import android.graphics.drawable.Drawable;
+import android.os.Bundle;
+import android.text.TextUtils;
+import android.util.Log;
+import android.view.Gravity;
+import android.view.LayoutInflater;
+import android.view.Menu;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.view.View.OnKeyListener;
+import android.view.ViewGroup;
+import android.view.ViewGroup.LayoutParams;
+import android.view.WindowManager;
+import android.view.inputmethod.InputMethodManager;
+import android.webkit.WebChromeClient;
+import android.webkit.WebView;
+import android.widget.FrameLayout;
+import android.widget.ImageButton;
+import android.widget.LinearLayout;
+import android.widget.Toast;
+
+import java.util.List;
+
+/**
+ * UI interface definitions
+ */
+public abstract class BaseUi implements UI, WebViewFactory {
+
+ private static final String LOGTAG = "BaseUi";
+
+ protected static final FrameLayout.LayoutParams COVER_SCREEN_PARAMS =
+ new FrameLayout.LayoutParams(
+ ViewGroup.LayoutParams.MATCH_PARENT,
+ ViewGroup.LayoutParams.MATCH_PARENT);
+
+ protected static final FrameLayout.LayoutParams COVER_SCREEN_GRAVITY_CENTER =
+ new FrameLayout.LayoutParams(
+ ViewGroup.LayoutParams.MATCH_PARENT,
+ ViewGroup.LayoutParams.MATCH_PARENT,
+ Gravity.CENTER);
+
+ Activity mActivity;
+ UiController mUiController;
+ TabControl mTabControl;
+ private Tab mActiveTab;
+ private InputMethodManager mInputManager;
+
+ private Drawable mSecLockIcon;
+ private Drawable mMixLockIcon;
+
+ private FrameLayout mBrowserFrameLayout;
+ protected FrameLayout mContentView;
+ private FrameLayout mCustomViewContainer;
+
+ private View mCustomView;
+ private WebChromeClient.CustomViewCallback mCustomViewCallback;
+
+ private CombinedBookmarkHistoryView mComboView;
+
+ private LinearLayout mErrorConsoleContainer = null;
+
+ private Toast mStopToast;
+
+ // the default <video> poster
+ private Bitmap mDefaultVideoPoster;
+ // the video progress view
+ private View mVideoProgressView;
+
+ private boolean mActivityPaused;
+
+ public BaseUi(Activity browser, UiController controller) {
+ mActivity = browser;
+ mUiController = controller;
+ mTabControl = controller.getTabControl();
+ Resources res = mActivity.getResources();
+ mInputManager = (InputMethodManager)
+ browser.getSystemService(Activity.INPUT_METHOD_SERVICE);
+ mSecLockIcon = res.getDrawable(R.drawable.ic_secure_holo_dark);
+ mMixLockIcon = res.getDrawable(R.drawable.ic_partial_secure);
+
+ FrameLayout frameLayout = (FrameLayout) mActivity.getWindow()
+ .getDecorView().findViewById(android.R.id.content);
+ mBrowserFrameLayout = (FrameLayout) LayoutInflater.from(mActivity)
+ .inflate(R.layout.custom_screen, null);
+ mContentView = (FrameLayout) mBrowserFrameLayout.findViewById(
+ R.id.main_content);
+ mErrorConsoleContainer = (LinearLayout) mBrowserFrameLayout
+ .findViewById(R.id.error_console);
+ mCustomViewContainer = (FrameLayout) mBrowserFrameLayout
+ .findViewById(R.id.fullscreen_custom_content);
+ frameLayout.addView(mBrowserFrameLayout, COVER_SCREEN_PARAMS);
+ }
+
+ /**
+ * common webview initialization
+ * @param w the webview to initialize
+ */
+ protected void initWebViewSettings(WebView w) {
+ w.setScrollbarFadingEnabled(true);
+ w.setScrollBarStyle(View.SCROLLBARS_OUTSIDE_OVERLAY);
+ w.setMapTrackballToArrowKeys(false); // use trackball directly
+ // Enable the built-in zoom
+ w.getSettings().setBuiltInZoomControls(true);
+
+ // Add this WebView to the settings observer list and update the
+ // settings
+ final BrowserSettings s = BrowserSettings.getInstance();
+ s.addObserver(w.getSettings()).update(s, null);
+ }
+
+ private void cancelStopToast() {
+ if (mStopToast != null) {
+ mStopToast.cancel();
+ mStopToast = null;
+ }
+ }
+
+ // lifecycle
+
+ public void onPause() {
+ if (isCustomViewShowing()) {
+ onHideCustomView();
+ }
+ cancelStopToast();
+ mActivityPaused = true;
+ }
+
+ public void onResume() {
+ mActivityPaused = false;
+ }
+
+ protected boolean isActivityPaused() {
+ return mActivityPaused;
+ }
+
+ public void onConfigurationChanged(Configuration config) {
+ }
+
+ // key handling
+
+ @Override
+ public boolean onBackKey() {
+ if (mComboView != null) {
+ if (!mComboView.onBackPressed()) {
+ mUiController.removeComboView();
+ }
+ return true;
+ }
+ if (mCustomView != null) {
+ mUiController.hideCustomView();
+ return true;
+ }
+ return false;
+ }
+
+ // Tab callbacks
+ @Override
+ public void onTabDataChanged(Tab tab) {
+ setUrlTitle(tab);
+ setFavicon(tab);
+ updateLockIconToLatest(tab);
+ updateNavigationState(tab);
+ }
+
+ @Override
+ public void bookmarkedStatusHasChanged(Tab tab) {
+ // no op in base case
+ }
+
+ @Override
+ public void onPageStopped(Tab tab) {
+ cancelStopToast();
+ if (tab.inForeground()) {
+ mStopToast = Toast
+ .makeText(mActivity, R.string.stopping, Toast.LENGTH_SHORT);
+ mStopToast.show();
+ }
+ }
+
+ @Override
+ public boolean needsRestoreAllTabs() {
+ return false;
+ }
+
+ @Override
+ public void addTab(Tab tab) {
+ }
+
+ @Override
+ public void setActiveTab(Tab tab) {
+ if ((tab != mActiveTab) && (mActiveTab != null)) {
+ removeTabFromContentView(mActiveTab);
+ }
+ mActiveTab = tab;
+ attachTabToContentView(tab);
+ setShouldShowErrorConsole(tab, mUiController.shouldShowErrorConsole());
+ onTabDataChanged(tab);
+ onProgressChanged(tab);
+ boolean incognito = mActiveTab.getWebView().isPrivateBrowsingEnabled();
+ getEmbeddedTitleBar().setIncognitoMode(incognito);
+ getFakeTitleBar().setIncognitoMode(incognito);
+ }
+
+ Tab getActiveTab() {
+ return mActiveTab;
+ }
+
+ @Override
+ public void updateTabs(List<Tab> tabs) {
+ }
+
+ @Override
+ public void removeTab(Tab tab) {
+ if (mActiveTab == tab) {
+ removeTabFromContentView(tab);
+ mActiveTab = null;
+ }
+ }
+
+ @Override
+ public void detachTab(Tab tab) {
+ removeTabFromContentView(tab);
+ }
+
+ @Override
+ public void attachTab(Tab tab) {
+ attachTabToContentView(tab);
+ }
+
+ private void attachTabToContentView(Tab tab) {
+ if ((tab == null) || (tab.getWebView() == null)) {
+ return;
+ }
+ View container = tab.getViewContainer();
+ WebView mainView = tab.getWebView();
+ // Attach the WebView to the container and then attach the
+ // container to the content view.
+ FrameLayout wrapper =
+ (FrameLayout) container.findViewById(R.id.webview_wrapper);
+ ViewGroup parent = (ViewGroup) mainView.getParent();
+ if (parent != wrapper) {
+ if (parent != null) {
+ Log.w(LOGTAG, "mMainView already has a parent in"
+ + " attachTabToContentView!");
+ parent.removeView(mainView);
+ }
+ wrapper.addView(mainView);
+ } else {
+ Log.w(LOGTAG, "mMainView is already attached to wrapper in"
+ + " attachTabToContentView!");
+ }
+ parent = (ViewGroup) container.getParent();
+ if (parent != mContentView) {
+ if (parent != null) {
+ Log.w(LOGTAG, "mContainer already has a parent in"
+ + " attachTabToContentView!");
+ parent.removeView(container);
+ }
+ mContentView.addView(container, COVER_SCREEN_PARAMS);
+ } else {
+ Log.w(LOGTAG, "mContainer is already attached to content in"
+ + " attachTabToContentView!");
+ }
+ mainView.setNextFocusUpId(R.id.url_focused);
+ mainView.setNextFocusDownId(R.id.url_focused);
+ mUiController.attachSubWindow(tab);
+ }
+
+ private void removeTabFromContentView(Tab tab) {
+ hideFakeTitleBar();
+ // Remove the container that contains the main WebView.
+ WebView mainView = tab.getWebView();
+ View container = tab.getViewContainer();
+ if (mainView == null) {
+ return;
+ }
+ // Remove the container from the content and then remove the
+ // WebView from the container. This will trigger a focus change
+ // needed by WebView.
+ mainView.setEmbeddedTitleBar(null);
+ FrameLayout wrapper =
+ (FrameLayout) container.findViewById(R.id.webview_wrapper);
+ wrapper.removeView(mainView);
+ mContentView.removeView(container);
+ mUiController.endActionMode();
+ mUiController.removeSubWindow(tab);
+ ErrorConsoleView errorConsole = tab.getErrorConsole(false);
+ if (errorConsole != null) {
+ mErrorConsoleContainer.removeView(errorConsole);
+ }
+ }
+
+ @Override
+ public void onSetWebView(Tab tab, WebView webView) {
+ View container = tab.getViewContainer();
+ if (container == null) {
+ // The tab consists of a container view, which contains the main
+ // WebView, as well as any other UI elements associated with the tab.
+ container = mActivity.getLayoutInflater().inflate(R.layout.tab,
+ null);
+ tab.setViewContainer(container);
+ }
+ if (tab.getWebView() != webView) {
+ // Just remove the old one.
+ FrameLayout wrapper =
+ (FrameLayout) container.findViewById(R.id.webview_wrapper);
+ wrapper.removeView(tab.getWebView());
+ }
+ }
+
+ /**
+ * create a sub window container and webview for the tab
+ * Note: this methods operates through side-effects for now
+ * it sets both the subView and subViewContainer for the given tab
+ * @param tab tab to create the sub window for
+ * @param subView webview to be set as a subwindow for the tab
+ */
+ @Override
+ public void createSubWindow(Tab tab, WebView subView) {
+ View subViewContainer = mActivity.getLayoutInflater().inflate(
+ R.layout.browser_subwindow, null);
+ ViewGroup inner = (ViewGroup) subViewContainer
+ .findViewById(R.id.inner_container);
+ inner.addView(subView, new LayoutParams(LayoutParams.MATCH_PARENT,
+ LayoutParams.MATCH_PARENT));
+ final ImageButton cancel = (ImageButton) subViewContainer
+ .findViewById(R.id.subwindow_close);
+ final WebView cancelSubView = subView;
+ cancel.setOnClickListener(new OnClickListener() {
+ public void onClick(View v) {
+ cancelSubView.getWebChromeClient().onCloseWindow(cancelSubView);
+ }
+ });
+ tab.setSubWebView(subView);
+ tab.setSubViewContainer(subViewContainer);
+ }
+
+ /**
+ * Remove the sub window from the content view.
+ */
+ @Override
+ public void removeSubWindow(View subviewContainer) {
+ mContentView.removeView(subviewContainer);
+ mUiController.endActionMode();
+ }
+
+ /**
+ * Attach the sub window to the content view.
+ */
+ @Override
+ public void attachSubWindow(View container) {
+ if (container.getParent() != null) {
+ // already attached, remove first
+ ((ViewGroup) container.getParent()).removeView(container);
+ }
+ mContentView.addView(container, COVER_SCREEN_PARAMS);
+ }
+
+ void showFakeTitleBar() {
+ if (!isFakeTitleBarShowing() && !isActivityPaused()) {
+ WebView mainView = mUiController.getCurrentWebView();
+ // if there is no current WebView, don't show the faked title bar;
+ if (mainView == null) {
+ return;
+ }
+ // Do not need to check for null, since the current tab will have
+ // at least a main WebView, or we would have returned above.
+ if (mUiController.isInCustomActionMode()) {
+ // Do not show the fake title bar, while a custom ActionMode
+ // (i.e. find or select) is showing.
+ return;
+ }
+ attachFakeTitleBar(mainView);
+ }
+ }
+
+ protected abstract void attachFakeTitleBar(WebView mainView);
+
+ protected abstract void hideFakeTitleBar();
+
+ protected abstract boolean isFakeTitleBarShowing();
+
+ protected abstract TitleBarBase getFakeTitleBar();
+
+ protected abstract TitleBarBase getEmbeddedTitleBar();
+
+ @Override
+ public void showVoiceTitleBar(String title) {
+ getEmbeddedTitleBar().setInVoiceMode(true);
+ getEmbeddedTitleBar().setDisplayTitle(title);
+ getFakeTitleBar().setInVoiceMode(true);
+ getFakeTitleBar().setDisplayTitle(title);
+ }
+
+ @Override
+ public void revertVoiceTitleBar(Tab tab) {
+ getEmbeddedTitleBar().setInVoiceMode(false);
+ String url = tab.getUrl();
+ getEmbeddedTitleBar().setDisplayTitle(url);
+ getFakeTitleBar().setInVoiceMode(false);
+ getFakeTitleBar().setDisplayTitle(url);
+ }
+
+ @Override
+ public void showComboView(boolean startWithHistory, Bundle extras) {
+ if (mComboView != null) {
+ return;
+ }
+ mComboView = new CombinedBookmarkHistoryView(mActivity,
+ mUiController,
+ startWithHistory ?
+ CombinedBookmarkHistoryView.FRAGMENT_ID_HISTORY
+ : CombinedBookmarkHistoryView.FRAGMENT_ID_BOOKMARKS,
+ extras);
+ FrameLayout wrapper =
+ (FrameLayout) mContentView.findViewById(R.id.webview_wrapper);
+ wrapper.setVisibility(View.GONE);
+ hideFakeTitleBar();
+ dismissIME();
+ if (mActiveTab != null) {
+ WebView web = mActiveTab.getWebView();
+ mActiveTab.putInBackground();
+ }
+ mContentView.addView(mComboView, COVER_SCREEN_PARAMS);
+ }
+
+ /**
+ * dismiss the ComboPage
+ */
+ @Override
+ public void hideComboView() {
+ if (mComboView != null) {
+ mContentView.removeView(mComboView);
+ FrameLayout wrapper =
+ (FrameLayout) mContentView.findViewById(R.id.webview_wrapper);
+ wrapper.setVisibility(View.VISIBLE);
+ mComboView = null;
+ }
+ if (mActiveTab != null) {
+ mActiveTab.putInForeground();
+ }
+ mActivity.invalidateOptionsMenu();
+ }
+
+ @Override
+ public void showCustomView(View view,
+ WebChromeClient.CustomViewCallback callback) {
+ // if a view already exists then immediately terminate the new one
+ if (mCustomView != null) {
+ callback.onCustomViewHidden();
+ return;
+ }
+
+ // Add the custom view to its container.
+ mCustomViewContainer.addView(view, COVER_SCREEN_GRAVITY_CENTER);
+ mCustomView = view;
+ mCustomViewCallback = callback;
+ // Hide the content view.
+ mContentView.setVisibility(View.GONE);
+ // Finally show the custom view container.
+ setStatusBarVisibility(false);
+ mCustomViewContainer.setVisibility(View.VISIBLE);
+ mCustomViewContainer.bringToFront();
+ }
+
+ @Override
+ public void onHideCustomView() {
+ if (mCustomView == null)
+ return;
+
+ // Hide the custom view.
+ mCustomView.setVisibility(View.GONE);
+ // Remove the custom view from its container.
+ mCustomViewContainer.removeView(mCustomView);
+ mCustomView = null;
+ mCustomViewContainer.setVisibility(View.GONE);
+ mCustomViewCallback.onCustomViewHidden();
+ // Show the content view.
+ setStatusBarVisibility(true);
+ mContentView.setVisibility(View.VISIBLE);
+ }
+
+ @Override
+ public boolean isCustomViewShowing() {
+ return mCustomView != null;
+ }
+
+ protected void dismissIME() {
+ if (mInputManager.isActive()) {
+ mInputManager.hideSoftInputFromWindow(mContentView.getWindowToken(),
+ 0);
+ }
+ }
+
+ @Override
+ public boolean showsWeb() {
+ return mCustomView == null
+ && mComboView == null;
+ }
+
+ // -------------------------------------------------------------------------
+
+ protected void updateNavigationState(Tab tab) {
+ }
+
+ /**
+ * Update the lock icon to correspond to our latest state.
+ */
+ protected void updateLockIconToLatest(Tab t) {
+ if (t != null && t.inForeground()) {
+ updateLockIconImage(t.getLockIconType());
+ }
+ }
+
+ /**
+ * Updates the lock-icon image in the title-bar.
+ */
+ private void updateLockIconImage(LockIcon lockIconType) {
+ Drawable d = null;
+ if (lockIconType == LockIcon.LOCK_ICON_SECURE) {
+ d = mSecLockIcon;
+ } else if (lockIconType == LockIcon.LOCK_ICON_MIXED) {
+ d = mMixLockIcon;
+ }
+ getEmbeddedTitleBar().setLock(d);
+ getFakeTitleBar().setLock(d);
+ }
+
+ protected void setUrlTitle(Tab tab) {
+ String url = tab.getUrl();
+ String title = tab.getTitle();
+ if (TextUtils.isEmpty(title)) {
+ title = url;
+ }
+ if (tab.isInVoiceSearchMode()) return;
+ if (tab.inForeground()) {
+ getEmbeddedTitleBar().setDisplayTitle(url);
+ getFakeTitleBar().setDisplayTitle(url);
+ }
+ }
+
+ // Set the favicon in the title bar.
+ protected void setFavicon(Tab tab) {
+ if (tab.inForeground()) {
+ Bitmap icon = tab.getFavicon();
+ getEmbeddedTitleBar().setFavicon(icon);
+ getFakeTitleBar().setFavicon(icon);
+ }
+ }
+
+ @Override
+ public void onActionModeFinished(boolean inLoad) {
+ if (inLoad) {
+ // the titlebar was removed when the CAB was shown
+ // if the page is loading, show it again
+ showFakeTitleBar();
+ }
+ }
+
+ // active tabs page
+
+ public void showActiveTabsPage() {
+ }
+
+ /**
+ * Remove the active tabs page.
+ */
+ public void removeActiveTabsPage() {
+ }
+
+ // menu handling callbacks
+
+ @Override
+ public void onOptionsMenuOpened() {
+ }
+
+ @Override
+ public void onExtendedMenuOpened() {
+ }
+
+ @Override
+ public void onOptionsMenuClosed(boolean inLoad) {
+ }
+
+ @Override
+ public void onExtendedMenuClosed(boolean inLoad) {
+ }
+
+ @Override
+ public void onContextMenuCreated(Menu menu) {
+ }
+
+ @Override
+ public void onContextMenuClosed(Menu menu, boolean inLoad) {
+ }
+
+ // error console
+
+ @Override
+ public void setShouldShowErrorConsole(Tab tab, boolean flag) {
+ ErrorConsoleView errorConsole = tab.getErrorConsole(true);
+ if (flag) {
+ // Setting the show state of the console will cause it's the layout
+ // to be inflated.
+ if (errorConsole.numberOfErrors() > 0) {
+ errorConsole.showConsole(ErrorConsoleView.SHOW_MINIMIZED);
+ } else {
+ errorConsole.showConsole(ErrorConsoleView.SHOW_NONE);
+ }
+ if (errorConsole.getParent() != null) {
+ mErrorConsoleContainer.removeView(errorConsole);
+ }
+ // Now we can add it to the main view.
+ mErrorConsoleContainer.addView(errorConsole,
+ new LinearLayout.LayoutParams(
+ ViewGroup.LayoutParams.MATCH_PARENT,
+ ViewGroup.LayoutParams.WRAP_CONTENT));
+ } else {
+ mErrorConsoleContainer.removeView(errorConsole);
+ }
+ }
+
+ private void setStatusBarVisibility(boolean visible) {
+ WindowManager.LayoutParams params = mActivity.getWindow().getAttributes();
+ params.systemUiVisibility = visible ? View.STATUS_BAR_VISIBLE : View.STATUS_BAR_HIDDEN;
+ mActivity.getWindow().setAttributes(params);
+ }
+
+ // -------------------------------------------------------------------------
+ // Helper function for WebChromeClient
+ // -------------------------------------------------------------------------
+
+ @Override
+ public Bitmap getDefaultVideoPoster() {
+ if (mDefaultVideoPoster == null) {
+ mDefaultVideoPoster = BitmapFactory.decodeResource(
+ mActivity.getResources(), R.drawable.default_video_poster);
+ }
+ return mDefaultVideoPoster;
+ }
+
+ @Override
+ public View getVideoLoadingProgressView() {
+ if (mVideoProgressView == null) {
+ LayoutInflater inflater = LayoutInflater.from(mActivity);
+ mVideoProgressView = inflater.inflate(
+ R.layout.video_loading_progress, null);
+ }
+ return mVideoProgressView;
+ }
+
+ @Override
+ public void showMaxTabsWarning() {
+ Toast warning = Toast.makeText(mActivity,
+ mActivity.getString(R.string.max_tabs_warning),
+ Toast.LENGTH_SHORT);
+ warning.show();
+ }
+
+}
diff --git a/src/com/android/browser/BookmarkItem.java b/src/com/android/browser/BookmarkItem.java
index fbb362e..4e60073 100644
--- a/src/com/android/browser/BookmarkItem.java
+++ b/src/com/android/browser/BookmarkItem.java
@@ -18,6 +18,7 @@
import android.content.Context;
import android.graphics.Bitmap;
+import android.graphics.drawable.Drawable;
import android.view.LayoutInflater;
import android.view.View;
import android.widget.ImageView;
@@ -94,6 +95,10 @@
}
}
+ void setFaviconBackground(Drawable d) {
+ mImageView.setBackgroundDrawable(d);
+ }
+
/**
* Set the new name for the bookmark item.
*
diff --git a/src/com/android/browser/BookmarkUtils.java b/src/com/android/browser/BookmarkUtils.java
new file mode 100644
index 0000000..cfb8e46
--- /dev/null
+++ b/src/com/android/browser/BookmarkUtils.java
@@ -0,0 +1,274 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.app.ActivityManager;
+import android.app.AlertDialog;
+import android.content.ContentUris;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.content.Intent;
+import android.content.SharedPreferences;
+import android.content.res.Resources;
+import android.graphics.Bitmap;
+import android.graphics.BitmapFactory;
+import android.graphics.Canvas;
+import android.graphics.Color;
+import android.graphics.Paint;
+import android.graphics.Path;
+import android.graphics.PorterDuff;
+import android.graphics.PorterDuffXfermode;
+import android.graphics.Rect;
+import android.graphics.RectF;
+import android.graphics.drawable.BitmapDrawable;
+import android.graphics.drawable.Drawable;
+import android.graphics.drawable.PaintDrawable;
+import android.net.Uri;
+import android.os.Message;
+import android.preference.PreferenceManager;
+import android.provider.Browser;
+import android.provider.BrowserContract;
+import android.util.DisplayMetrics;
+
+public class BookmarkUtils {
+ private final static String LOGTAG = "BookmarkUtils";
+
+ // XXX: There is no public string defining this intent so if Home changes the value, we
+ // have to update this string.
+ private static final String INSTALL_SHORTCUT = "com.android.launcher.action.INSTALL_SHORTCUT";
+
+ enum BookmarkIconType {
+ ICON_INSTALLABLE_WEB_APP, // Icon for an installable web app (launches WebAppRuntime).
+ ICON_HOME_SHORTCUT, // Icon for a shortcut on the home screen (launches Browser).
+ ICON_WIDGET,
+ }
+
+ /**
+ * Creates an icon to be associated with this bookmark. If available, the apple touch icon
+ * will be used, else we draw our own depending on the type of "bookmark" being created.
+ */
+ static Bitmap createIcon(Context context, Bitmap touchIcon, Bitmap favicon,
+ BookmarkIconType type) {
+ final ActivityManager am = (ActivityManager) context
+ .getSystemService(Context.ACTIVITY_SERVICE);
+ final int iconDimension = am.getLauncherLargeIconSize();
+ final int iconDensity = am.getLauncherLargeIconDensity();
+ return createIcon(context, touchIcon, favicon, type, iconDimension, iconDensity);
+ }
+
+ static Drawable createListFaviconBackground(Context context) {
+ PaintDrawable faviconBackground = new PaintDrawable();
+ Resources res = context.getResources();
+ int padding = res.getDimensionPixelSize(R.dimen.list_favicon_padding);
+ faviconBackground.setPadding(padding, padding, padding, padding);
+ faviconBackground.getPaint().setColor(context.getResources()
+ .getColor(R.color.bookmarkListFaviconBackground));
+ faviconBackground.setCornerRadius(
+ res.getDimension(R.dimen.list_favicon_corner_radius));
+ return faviconBackground;
+ }
+
+ private static Bitmap createIcon(Context context, Bitmap touchIcon,
+ Bitmap favicon, BookmarkIconType type, int iconDimension, int iconDensity) {
+ Bitmap bm = Bitmap.createBitmap(iconDimension, iconDimension, Bitmap.Config.ARGB_8888);
+ Canvas canvas = new Canvas(bm);
+ Rect iconBounds = new Rect(0, 0, bm.getWidth(), bm.getHeight());
+
+ // Use the apple-touch-icon if available
+ if (touchIcon != null) {
+ drawTouchIconToCanvas(touchIcon, canvas, iconBounds);
+ } else {
+ // No touch icon so create our own.
+ // Set the background based on the type of shortcut (either webapp or home shortcut).
+ Bitmap icon = getIconBackground(context, type, iconDensity);
+
+ if (icon != null) {
+ // Now draw the correct icon background into our new bitmap.
+ Paint p = new Paint(Paint.ANTI_ALIAS_FLAG | Paint.FILTER_BITMAP_FLAG);
+ canvas.drawBitmap(icon, null, iconBounds, p);
+ }
+
+ // If we have a favicon, overlay it in a nice rounded white box on top of the
+ // background.
+ if (favicon != null) {
+ drawFaviconToCanvas(context, favicon, canvas, iconBounds, type);
+ }
+ }
+ return bm;
+ }
+
+ /**
+ * Convenience method for creating an intent that will add a shortcut to the home screen.
+ */
+ static Intent createAddToHomeIntent(Context context, String url, String title,
+ Bitmap touchIcon, Bitmap favicon) {
+ Intent i = new Intent(INSTALL_SHORTCUT);
+ Intent shortcutIntent = new Intent(Intent.ACTION_VIEW, Uri.parse(url));
+ long urlHash = url.hashCode();
+ long uniqueId = (urlHash << 32) | shortcutIntent.hashCode();
+ shortcutIntent.putExtra(Browser.EXTRA_APPLICATION_ID, Long.toString(uniqueId));
+ i.putExtra(Intent.EXTRA_SHORTCUT_INTENT, shortcutIntent);
+ i.putExtra(Intent.EXTRA_SHORTCUT_NAME, title);
+ i.putExtra(Intent.EXTRA_SHORTCUT_ICON, createIcon(context, touchIcon, favicon,
+ BookmarkIconType.ICON_HOME_SHORTCUT));
+
+ // Do not allow duplicate items
+ i.putExtra("duplicate", false);
+ return i;
+ }
+
+ private static Bitmap getIconBackground(Context context, BookmarkIconType type, int density) {
+ if (type == BookmarkIconType.ICON_HOME_SHORTCUT) {
+ // Want to create a shortcut icon on the homescreen, so the icon
+ // background is the red bookmark.
+ Drawable drawable = context.getResources().getDrawableForDensity(
+ R.mipmap.ic_launcher_shortcut_browser_bookmark, density);
+ if (drawable instanceof BitmapDrawable) {
+ BitmapDrawable bd = (BitmapDrawable) drawable;
+ return bd.getBitmap();
+ }
+ } else if (type == BookmarkIconType.ICON_INSTALLABLE_WEB_APP) {
+ // Use the web browser icon as the background for the icon for an installable
+ // web app.
+ Drawable drawable = context.getResources().getDrawableForDensity(
+ R.mipmap.ic_launcher_browser, density);
+ if (drawable instanceof BitmapDrawable) {
+ BitmapDrawable bd = (BitmapDrawable) drawable;
+ return bd.getBitmap();
+ }
+ }
+ return null;
+ }
+
+ private static void drawTouchIconToCanvas(Bitmap touchIcon, Canvas canvas, Rect iconBounds) {
+ Rect src = new Rect(0, 0, touchIcon.getWidth(), touchIcon.getHeight());
+
+ // Paint used for scaling the bitmap and drawing the rounded rect.
+ Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
+ paint.setFilterBitmap(true);
+ canvas.drawBitmap(touchIcon, src, iconBounds, paint);
+
+ // Construct a path from a round rect. This will allow drawing with
+ // an inverse fill so we can punch a hole using the round rect.
+ Path path = new Path();
+ path.setFillType(Path.FillType.INVERSE_WINDING);
+ RectF rect = new RectF(iconBounds);
+ rect.inset(1, 1);
+ path.addRoundRect(rect, 8f, 8f, Path.Direction.CW);
+
+ // Reuse the paint and clear the outside of the rectangle.
+ paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.CLEAR));
+ canvas.drawPath(path, paint);
+ }
+
+ private static void drawFaviconToCanvas(Context context, Bitmap favicon,
+ Canvas canvas, Rect iconBounds, BookmarkIconType type) {
+ // Make a Paint for the white background rectangle and for
+ // filtering the favicon.
+ Paint p = new Paint(Paint.ANTI_ALIAS_FLAG | Paint.FILTER_BITMAP_FLAG);
+ p.setStyle(Paint.Style.FILL_AND_STROKE);
+ if (type == BookmarkIconType.ICON_WIDGET) {
+ p.setColor(context.getResources()
+ .getColor(R.color.bookmarkWidgetFaviconBackground));
+ } else {
+ p.setColor(Color.WHITE);
+ }
+
+ // Create a rectangle that is slightly wider than the favicon
+ int faviconDimension = context.getResources().getDimensionPixelSize(R.dimen.favicon_size);
+ int faviconPaddedRectDimension;
+ if (type == BookmarkIconType.ICON_WIDGET) {
+ faviconPaddedRectDimension = canvas.getWidth();
+ } else {
+ faviconPaddedRectDimension = context.getResources().getDimensionPixelSize(
+ R.dimen.favicon_padded_size);
+ }
+ float padding = (faviconPaddedRectDimension - faviconDimension) / 2;
+ final float x = iconBounds.exactCenterX() - (faviconPaddedRectDimension / 2);
+ float y = iconBounds.exactCenterY() - (faviconPaddedRectDimension / 2);
+ if (type != BookmarkIconType.ICON_WIDGET) {
+ // Note: Subtract from the y position since the box is
+ // slightly higher than center. Use padding since it is already
+ // device independent.
+ y -= padding;
+ }
+ RectF r = new RectF(x, y, x + faviconPaddedRectDimension, y + faviconPaddedRectDimension);
+ // Draw a white rounded rectangle behind the favicon
+ canvas.drawRoundRect(r, 3, 3, p);
+
+ // Draw the favicon in the same rectangle as the rounded
+ // rectangle but inset by the padding
+ // (results in a 16x16 favicon).
+ r.inset(padding, padding);
+ canvas.drawBitmap(favicon, null, r, null);
+ }
+
+ /* package */ static Uri getBookmarksUri(Context context) {
+ return addAccountInfo(context,
+ BrowserContract.Bookmarks.CONTENT_URI.buildUpon()).build();
+ }
+
+ public static Uri.Builder addAccountInfo(Context context, Uri.Builder ub) {
+ Uri uri = BrowserContract.Bookmarks.CONTENT_URI;
+ SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
+ String accountType = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE, null);
+ String accountName = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, null);
+ ub.appendQueryParameter(
+ BrowserContract.Bookmarks.PARAM_ACCOUNT_NAME,accountName);
+ ub.appendQueryParameter(
+ BrowserContract.Bookmarks.PARAM_ACCOUNT_TYPE, accountType);
+ return ub;
+ }
+
+ /**
+ * Show a confirmation dialog to remove a bookmark.
+ * @param id Id of the bookmark to remove
+ * @param title Title of the bookmark, to be displayed in the confirmation method.
+ * @param context Package Context for strings, dialog, ContentResolver
+ * @param msg Message to send if the bookmark is deleted.
+ */
+ static void displayRemoveBookmarkDialog( final long id, final String title,
+ final Context context, final Message msg) {
+
+ new AlertDialog.Builder(context)
+ .setTitle(R.string.delete_bookmark)
+ .setIcon(android.R.drawable.ic_dialog_alert)
+ .setMessage(context.getString(R.string.delete_bookmark_warning,
+ title))
+ .setPositiveButton(R.string.ok,
+ new DialogInterface.OnClickListener() {
+ @Override
+ public void onClick(DialogInterface dialog, int whichButton) {
+ if (msg != null) {
+ msg.sendToTarget();
+ }
+ Runnable runnable = new Runnable(){
+ @Override
+ public void run() {
+ Uri uri = ContentUris.withAppendedId(
+ BrowserContract.Bookmarks.CONTENT_URI,
+ id);
+ context.getContentResolver().delete(uri, null, null);
+ }
+ };
+ new Thread(runnable).start();
+ }
+ })
+ .setNegativeButton(R.string.cancel, null)
+ .show();
+ }
+}
diff --git a/src/com/android/browser/Bookmarks.java b/src/com/android/browser/Bookmarks.java
index 5ada9dc..beea489 100644
--- a/src/com/android/browser/Bookmarks.java
+++ b/src/com/android/browser/Bookmarks.java
@@ -20,16 +20,21 @@
import android.content.ContentUris;
import android.content.ContentValues;
import android.content.Context;
+import android.content.SharedPreferences;
import android.database.Cursor;
import android.graphics.Bitmap;
import android.net.Uri;
-import android.provider.Browser;
+import android.os.AsyncTask;
+import android.preference.PreferenceManager;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Combined;
+import android.provider.BrowserContract.Images;
+import android.text.TextUtils;
import android.util.Log;
import android.webkit.WebIconDatabase;
import android.widget.Toast;
import java.io.ByteArrayOutputStream;
-import java.util.Date;
/**
* This class is purely to have a common place for adding/deleting bookmarks.
@@ -53,89 +58,38 @@
* @param context Context of the calling Activity. This is used to make
* Toast confirming that the bookmark has been added. If the
* caller provides null, the Toast will not be shown.
- * @param cr The ContentResolver being used to add the bookmark to the db.
* @param url URL of the website to be bookmarked.
* @param name Provided name for the bookmark.
* @param thumbnail A thumbnail for the bookmark.
* @param retainIcon Whether to retain the page's icon in the icon database.
* This will usually be <code>true</code> except when bookmarks are
* added by a settings restore agent.
+ * @param parent ID of the parent folder.
*/
- /* package */ static void addBookmark(Context context,
- ContentResolver cr, String url, String name,
- Bitmap thumbnail, boolean retainIcon) {
+ /* package */ static void addBookmark(Context context, boolean showToast, String url,
+ String name, Bitmap thumbnail, boolean retainIcon, long parent) {
// Want to append to the beginning of the list
- long creationTime = new Date().getTime();
- ContentValues map = new ContentValues();
- Cursor cursor = null;
+ ContentValues values = new ContentValues();
try {
- cursor = Browser.getVisitedLike(cr, url);
- if (cursor.moveToFirst() && cursor.getInt(
- Browser.HISTORY_PROJECTION_BOOKMARK_INDEX) == 0) {
- // This means we have been to this site but not bookmarked
- // it, so convert the history item to a bookmark
- map.put(Browser.BookmarkColumns.CREATED, creationTime);
- map.put(Browser.BookmarkColumns.TITLE, name);
- map.put(Browser.BookmarkColumns.BOOKMARK, 1);
- map.put(Browser.BookmarkColumns.THUMBNAIL,
- bitmapToBytes(thumbnail));
- cr.update(Browser.BOOKMARKS_URI, map,
- "_id = " + cursor.getInt(0), null);
- } else {
- int count = cursor.getCount();
- boolean matchedTitle = false;
- for (int i = 0; i < count; i++) {
- // One or more bookmarks already exist for this site.
- // Check the names of each
- cursor.moveToPosition(i);
- if (cursor.getString(Browser.HISTORY_PROJECTION_TITLE_INDEX)
- .equals(name)) {
- // The old bookmark has the same name.
- // Update its creation time.
- map.put(Browser.BookmarkColumns.CREATED,
- creationTime);
- cr.update(Browser.BOOKMARKS_URI, map,
- "_id = " + cursor.getInt(0), null);
- matchedTitle = true;
- break;
- }
- }
- if (!matchedTitle) {
- // Adding a bookmark for a site the user has visited,
- // or a new bookmark (with a different name) for a site
- // the user has visited
- map.put(Browser.BookmarkColumns.TITLE, name);
- map.put(Browser.BookmarkColumns.URL, url);
- map.put(Browser.BookmarkColumns.CREATED, creationTime);
- map.put(Browser.BookmarkColumns.BOOKMARK, 1);
- map.put(Browser.BookmarkColumns.DATE, 0);
- map.put(Browser.BookmarkColumns.THUMBNAIL,
- bitmapToBytes(thumbnail));
- int visits = 0;
- if (count > 0) {
- // The user has already bookmarked, and possibly
- // visited this site. However, they are creating
- // a new bookmark with the same url but a different
- // name. The new bookmark should have the same
- // number of visits as the already created bookmark.
- visits = cursor.getInt(
- Browser.HISTORY_PROJECTION_VISITS_INDEX);
- }
- // Bookmark starts with 3 extra visits so that it will
- // bubble up in the most visited and goto search box
- map.put(Browser.BookmarkColumns.VISITS, visits + 3);
- cr.insert(Browser.BOOKMARKS_URI, map);
- }
- }
+ SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
+ String accountType = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE, null);
+ String accountName = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, null);
+ values.put(BrowserContract.Bookmarks.ACCOUNT_TYPE, accountType);
+ values.put(BrowserContract.Bookmarks.ACCOUNT_NAME, accountName);
+ values.put(BrowserContract.Bookmarks.TITLE, name);
+ values.put(BrowserContract.Bookmarks.URL, url);
+ values.put(BrowserContract.Bookmarks.IS_FOLDER, 0);
+ values.put(BrowserContract.Bookmarks.THUMBNAIL,
+ bitmapToBytes(thumbnail));
+ values.put(BrowserContract.Bookmarks.PARENT, parent);
+ context.getContentResolver().insert(BrowserContract.Bookmarks.CONTENT_URI, values);
} catch (IllegalStateException e) {
Log.e(LOGTAG, "addBookmark", e);
- } finally {
- if (cursor != null) cursor.close();
}
if (retainIcon) {
WebIconDatabase.getInstance().retainIconForPageUrl(url);
}
- if (context != null) {
+ if (showToast) {
Toast.makeText(context, R.string.added_to_bookmarks,
Toast.LENGTH_LONG).show();
}
@@ -146,8 +100,8 @@
* will remain in the database, but only as a history item, and not as a
* bookmarked site.
* @param context Context of the calling Activity. This is used to make
- * Toast confirming that the bookmark has been removed. If the
- * caller provides null, the Toast will not be shown.
+ * Toast confirming that the bookmark has been removed and to
+ * lookup the correct content uri. It must not be null.
* @param cr The ContentResolver being used to remove the bookmark.
* @param url URL of the website to be removed.
*/
@@ -155,37 +109,23 @@
ContentResolver cr, String url, String title) {
Cursor cursor = null;
try {
- cursor = cr.query(
- Browser.BOOKMARKS_URI,
- Browser.HISTORY_PROJECTION,
- "url = ? AND title = ?",
+ Uri uri = BookmarkUtils.getBookmarksUri(context);
+ cursor = cr.query(uri,
+ new String[] { BrowserContract.Bookmarks._ID },
+ BrowserContract.Bookmarks.URL + " = ? AND " +
+ BrowserContract.Bookmarks.TITLE + " = ?",
new String[] { url, title },
null);
- boolean first = cursor.moveToFirst();
- // Should be in the database no matter what
- if (!first) {
- throw new AssertionError("URL is not in the database! " + url
- + " " + title);
+
+ if (!cursor.moveToFirst()) {
+ return;
}
+
// Remove from bookmarks
WebIconDatabase.getInstance().releaseIconForPageUrl(url);
- Uri uri = ContentUris.withAppendedId(Browser.BOOKMARKS_URI,
- cursor.getInt(Browser.HISTORY_PROJECTION_ID_INDEX));
- int numVisits = cursor.getInt(
- Browser.HISTORY_PROJECTION_VISITS_INDEX);
- if (0 == numVisits) {
- cr.delete(uri, null, null);
- } else {
- // It is no longer a bookmark, but it is still a visited
- // site.
- ContentValues values = new ContentValues();
- values.put(Browser.BookmarkColumns.BOOKMARK, 0);
- try {
- cr.update(uri, values, null, null);
- } catch (IllegalStateException e) {
- Log.e("removeFromBookmarks", "no database!");
- }
- }
+ uri = ContentUris.withAppendedId(BrowserContract.Bookmarks.CONTENT_URI,
+ cursor.getLong(0));
+ cr.delete(uri, null, null);
if (context != null) {
Toast.makeText(context, R.string.removed_from_bookmarks,
Toast.LENGTH_LONG).show();
@@ -219,4 +159,86 @@
}
return false;
}
+
+ static final String QUERY_BOOKMARKS_WHERE =
+ Combined.URL + " == ? OR " +
+ Combined.URL + " == ? OR " +
+ Combined.URL + " LIKE ? || '%' OR " +
+ Combined.URL + " LIKE ? || '%'";
+
+ /* package */ static Cursor queryCombinedForUrl(ContentResolver cr,
+ String originalUrl, String url) {
+ if (cr == null || url == null) {
+ return null;
+ }
+
+ // If originalUrl is null, just set it to url.
+ if (originalUrl == null) {
+ originalUrl = url;
+ }
+
+ // Look for both the original url and the actual url. This takes in to
+ // account redirects.
+ String originalUrlNoQuery = removeQuery(originalUrl);
+ String urlNoQuery = removeQuery(url);
+ originalUrl = originalUrlNoQuery + '?';
+ url = urlNoQuery + '?';
+
+ // Use NoQuery to search for the base url (i.e. if the url is
+ // http://www.yahoo.com/?rs=1, search for http://www.yahoo.com)
+ // Use url to match the base url with other queries (i.e. if the url is
+ // http://www.google.com/m, search for
+ // http://www.google.com/m?some_query)
+ final String[] selArgs = new String[] { originalUrlNoQuery, urlNoQuery, originalUrl, url };
+ final String[] projection = new String[] { Combined.URL };
+ return cr.query(Combined.CONTENT_URI, projection, QUERY_BOOKMARKS_WHERE, selArgs, null);
+ }
+
+ // Strip the query from the given url.
+ static String removeQuery(String url) {
+ if (url == null) {
+ return null;
+ }
+ int query = url.indexOf('?');
+ String noQuery = url;
+ if (query != -1) {
+ noQuery = url.substring(0, query);
+ }
+ return noQuery;
+ }
+
+ /**
+ * Update the bookmark's favicon. This is a convenience method for updating
+ * a bookmark favicon for the originalUrl and url of the passed in WebView.
+ * @param cr The ContentResolver to use.
+ * @param originalUrl The original url before any redirects.
+ * @param url The current url.
+ * @param favicon The favicon bitmap to write to the db.
+ */
+ /* package */ static void updateFavicon(final ContentResolver cr,
+ final String originalUrl, final String url, final Bitmap favicon) {
+ new AsyncTask<Void, Void, Void>() {
+ @Override
+ protected Void doInBackground(Void... unused) {
+ final ByteArrayOutputStream os = new ByteArrayOutputStream();
+ favicon.compress(Bitmap.CompressFormat.PNG, 100, os);
+
+ // The Images update will insert if it doesn't exist
+ ContentValues values = new ContentValues();
+ values.put(Images.FAVICON, os.toByteArray());
+ updateImages(cr, originalUrl, values);
+ updateImages(cr, url, values);
+ return null;
+ }
+
+ private void updateImages(final ContentResolver cr,
+ final String url, ContentValues values) {
+ String iurl = removeQuery(url);
+ if (!TextUtils.isEmpty(iurl)) {
+ values.put(Images.URL, iurl);
+ cr.update(BrowserContract.Images.CONTENT_URI, values, null, null);
+ }
+ }
+ }.execute();
+ }
}
diff --git a/src/com/android/browser/BookmarksLoader.java b/src/com/android/browser/BookmarksLoader.java
new file mode 100644
index 0000000..7722392
--- /dev/null
+++ b/src/com/android/browser/BookmarksLoader.java
@@ -0,0 +1,71 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser;
+
+import android.content.Context;
+import android.content.CursorLoader;
+import android.net.Uri;
+import android.provider.BrowserContract.Bookmarks;
+import android.provider.BrowserContract.ChromeSyncColumns;
+
+public class BookmarksLoader extends CursorLoader {
+ public static final String ARG_ACCOUNT_TYPE = "acct_type";
+ public static final String ARG_ACCOUNT_NAME = "acct_name";
+
+ public static final int COLUMN_INDEX_ID = 0;
+ public static final int COLUMN_INDEX_URL = 1;
+ public static final int COLUMN_INDEX_TITLE = 2;
+ public static final int COLUMN_INDEX_FAVICON = 3;
+ public static final int COLUMN_INDEX_THUMBNAIL = 4;
+ public static final int COLUMN_INDEX_TOUCH_ICON = 5;
+ public static final int COLUMN_INDEX_IS_FOLDER = 6;
+ public static final int COLUMN_INDEX_PARENT = 8;
+ public static final int COLUMN_INDEX_SERVER_UNIQUE = 9;
+
+ public static final String[] PROJECTION = new String[] {
+ Bookmarks._ID, // 0
+ Bookmarks.URL, // 1
+ Bookmarks.TITLE, // 2
+ Bookmarks.FAVICON, // 3
+ Bookmarks.THUMBNAIL, // 4
+ Bookmarks.TOUCH_ICON, // 5
+ Bookmarks.IS_FOLDER, // 6
+ Bookmarks.POSITION, // 7
+ Bookmarks.PARENT, // 8
+ ChromeSyncColumns.SERVER_UNIQUE, // 9
+ };
+
+ private String mAccountType;
+ private String mAccountName;
+
+ public BookmarksLoader(Context context, String accountType, String accountName) {
+ super(context, addAccount(Bookmarks.CONTENT_URI_DEFAULT_FOLDER, accountType, accountName),
+ PROJECTION, null, null, null);
+ mAccountType = accountType;
+ mAccountName = accountName;
+ }
+
+ @Override
+ public void setUri(Uri uri) {
+ super.setUri(addAccount(uri, mAccountType, mAccountName));
+ }
+
+ static Uri addAccount(Uri uri, String accountType, String accountName) {
+ return uri.buildUpon().appendQueryParameter(Bookmarks.PARAM_ACCOUNT_TYPE, accountType).
+ appendQueryParameter(Bookmarks.PARAM_ACCOUNT_NAME, accountName).build();
+ }
+}
diff --git a/src/com/android/browser/BreadCrumbView.java b/src/com/android/browser/BreadCrumbView.java
new file mode 100644
index 0000000..9aaecd7
--- /dev/null
+++ b/src/com/android/browser/BreadCrumbView.java
@@ -0,0 +1,373 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.content.Context;
+import android.content.res.TypedArray;
+import android.graphics.drawable.Drawable;
+import android.text.TextUtils;
+import android.util.AttributeSet;
+import android.util.TypedValue;
+import android.view.Gravity;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.widget.ImageButton;
+import android.widget.ImageView;
+import android.widget.LinearLayout;
+import android.widget.TextView;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * Simple bread crumb view
+ * Use setController to receive callbacks from user interactions
+ * Use pushView, popView, clear, and getTopData to change/access the view stack
+ */
+public class BreadCrumbView extends LinearLayout implements OnClickListener {
+ private static final int DIVIDER_PADDING = 12; // dips
+
+ interface Controller {
+ public void onTop(int level, Object data);
+ }
+
+ private ImageButton mBackButton;
+ private Controller mController;
+ private List<Crumb> mCrumbs;
+ private boolean mUseBackButton;
+ private Drawable mSeparatorDrawable;
+ private float mDividerPadding;
+ private int mMaxVisible = -1;
+
+ /**
+ * @param context
+ * @param attrs
+ * @param defStyle
+ */
+ public BreadCrumbView(Context context, AttributeSet attrs, int defStyle) {
+ super(context, attrs, defStyle);
+ init(context);
+ }
+
+ /**
+ * @param context
+ * @param attrs
+ */
+ public BreadCrumbView(Context context, AttributeSet attrs) {
+ super(context, attrs);
+ init(context);
+ }
+
+ /**
+ * @param context
+ */
+ public BreadCrumbView(Context context) {
+ super(context);
+ init(context);
+ }
+
+ private void init(Context ctx) {
+ mUseBackButton = false;
+ mCrumbs = new ArrayList<Crumb>();
+ TypedArray a = ctx.obtainStyledAttributes(com.android.internal.R.styleable.Theme);
+ mSeparatorDrawable = a.getDrawable(com.android.internal.R.styleable.Theme_dividerVertical);
+ a.recycle();
+ mDividerPadding = DIVIDER_PADDING * ctx.getResources().getDisplayMetrics().density;
+ addBackButton();
+ }
+
+ public void setUseBackButton(boolean useflag) {
+ mUseBackButton = useflag;
+ updateVisible();
+ }
+
+ public void setController(Controller ctl) {
+ mController = ctl;
+ }
+
+ public int getMaxVisible() {
+ return mMaxVisible;
+ }
+
+ public void setMaxVisible(int max) {
+ mMaxVisible = max;
+ updateVisible();
+ }
+
+ public int getTopLevel() {
+ return mCrumbs.size();
+ }
+
+ public Object getTopData() {
+ Crumb c = getTopCrumb();
+ if (c != null) {
+ return c.data;
+ }
+ return null;
+ }
+
+ public int size() {
+ return mCrumbs.size();
+ }
+
+ public void clear() {
+ while (mCrumbs.size() > 1) {
+ pop(false);
+ }
+ pop(true);
+ }
+
+ public void notifyController() {
+ if (mController != null) {
+ if (mCrumbs.size() > 0) {
+ mController.onTop(mCrumbs.size(), getTopCrumb().data);
+ } else {
+ mController.onTop(0, null);
+ }
+ }
+ }
+
+ public View pushView(String name, Object data) {
+ return pushView(name, true, data);
+ }
+
+ public View pushView(String name, boolean canGoBack, Object data) {
+ Crumb crumb = new Crumb(name, canGoBack, data);
+ pushCrumb(crumb);
+ return crumb.crumbView;
+ }
+
+ public void pushView(View view, Object data) {
+ Crumb crumb = new Crumb(view, true, data);
+ pushCrumb(crumb);
+ }
+
+ public void popView() {
+ pop(true);
+ }
+
+ private void addBackButton() {
+ mBackButton = new ImageButton(mContext);
+ mBackButton.setImageResource(R.drawable.ic_back_hierarchy_holo_dark);
+ TypedValue outValue = new TypedValue();
+ getContext().getTheme().resolveAttribute(
+ android.R.attr.selectableItemBackground, outValue, true);
+ int resid = outValue.resourceId;
+ mBackButton.setBackgroundResource(resid);
+ mBackButton.setLayoutParams(new LayoutParams(LayoutParams.WRAP_CONTENT,
+ LayoutParams.MATCH_PARENT));
+ mBackButton.setOnClickListener(this);
+ mBackButton.setVisibility(View.GONE);
+ addView(mBackButton, 0);
+ }
+
+ private void pushCrumb(Crumb crumb) {
+ if (mCrumbs.size() > 0) {
+ addSeparator();
+ }
+ mCrumbs.add(crumb);
+ addView(crumb.crumbView);
+ updateVisible();
+ crumb.crumbView.setOnClickListener(this);
+ }
+
+ private void addSeparator() {
+ View sep = makeDividerView();
+ sep.setLayoutParams(makeDividerLayoutParams());
+ addView(sep);
+ }
+
+ private ImageView makeDividerView() {
+ ImageView result = new ImageView(mContext);
+ result.setImageDrawable(mSeparatorDrawable);
+ result.setScaleType(ImageView.ScaleType.FIT_XY);
+ return result;
+ }
+
+ private LayoutParams makeDividerLayoutParams() {
+ LayoutParams params = new LayoutParams(LayoutParams.WRAP_CONTENT,
+ LayoutParams.MATCH_PARENT);
+ params.topMargin = (int) mDividerPadding;
+ params.bottomMargin = (int) mDividerPadding;
+ return params;
+ }
+
+ private void pop(boolean notify) {
+ int n = mCrumbs.size();
+ if (n > 0) {
+ removeLastView();
+ if (!mUseBackButton || (n > 1)) {
+ // remove separator
+ removeLastView();
+ }
+ mCrumbs.remove(n - 1);
+ if (mUseBackButton) {
+ Crumb top = getTopCrumb();
+ if (top != null && top.canGoBack) {
+ mBackButton.setVisibility(View.VISIBLE);
+ } else {
+ mBackButton.setVisibility(View.GONE);
+ }
+ }
+ updateVisible();
+ if (notify) {
+ notifyController();
+ }
+ }
+ }
+
+ private void updateVisible() {
+ // start at index 1 (0 == back button)
+ int childIndex = 1;
+ if (mMaxVisible >= 0) {
+ int invisibleCrumbs = size() - mMaxVisible;
+ if (invisibleCrumbs > 0) {
+ int crumbIndex = 0;
+ while (crumbIndex < invisibleCrumbs) {
+ // Set the crumb to GONE.
+ getChildAt(childIndex).setVisibility(View.GONE);
+ childIndex++;
+ // Each crumb is followed by a separator (except the last
+ // one). Also make it GONE
+ if (getChildAt(childIndex) != null) {
+ getChildAt(childIndex).setVisibility(View.GONE);
+ }
+ childIndex++;
+ // Move to the next crumb.
+ crumbIndex++;
+ }
+ }
+ // Make sure the last two are visible.
+ int childCount = getChildCount();
+ while (childIndex < childCount) {
+ getChildAt(childIndex).setVisibility(View.VISIBLE);
+ childIndex++;
+ }
+ } else {
+ int count = getChildCount();
+ for (int i = childIndex; i < count ; i++) {
+ getChildAt(i).setVisibility(View.VISIBLE);
+ }
+ }
+ if (mUseBackButton) {
+ boolean canGoBack = getTopCrumb() != null ? getTopCrumb().canGoBack : false;
+ mBackButton.setVisibility(canGoBack ? View.VISIBLE : View.GONE);
+ } else {
+ mBackButton.setVisibility(View.GONE);
+ }
+ }
+
+ private void removeLastView() {
+ int ix = getChildCount();
+ if (ix > 0) {
+ removeViewAt(ix-1);
+ }
+ }
+
+ Crumb getTopCrumb() {
+ Crumb crumb = null;
+ if (mCrumbs.size() > 0) {
+ crumb = mCrumbs.get(mCrumbs.size() - 1);
+ }
+ return crumb;
+ }
+
+ @Override
+ public void onClick(View v) {
+ if (mBackButton == v) {
+ popView();
+ notifyController();
+ } else {
+ // pop until view matches crumb view
+ while (v != getTopCrumb().crumbView) {
+ pop(false);
+ }
+ notifyController();
+ }
+ }
+ @Override
+ public int getBaseline() {
+ int ix = getChildCount();
+ if (ix > 0) {
+ // If there is at least one crumb, the baseline will be its
+ // baseline.
+ return getChildAt(ix-1).getBaseline();
+ }
+ return super.getBaseline();
+ }
+
+ @Override
+ protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
+ super.onMeasure(widthMeasureSpec, heightMeasureSpec);
+ int height = mSeparatorDrawable.getIntrinsicHeight();
+ if (getMeasuredHeight() < height) {
+ // This should only be an issue if there are currently no separators
+ // showing; i.e. if there is one crumb and no back button.
+ int mode = View.MeasureSpec.getMode(heightMeasureSpec);
+ switch(mode) {
+ case View.MeasureSpec.AT_MOST:
+ if (View.MeasureSpec.getSize(heightMeasureSpec) < height) {
+ return;
+ }
+ break;
+ case View.MeasureSpec.EXACTLY:
+ return;
+ default:
+ break;
+ }
+ setMeasuredDimension(getMeasuredWidth(), height);
+ }
+ }
+
+ class Crumb {
+
+ public View crumbView;
+ public boolean canGoBack;
+ public Object data;
+
+ public Crumb(String title, boolean backEnabled, Object tag) {
+ init(makeCrumbView(title), backEnabled, tag);
+ }
+
+ public Crumb(View view, boolean backEnabled, Object tag) {
+ init(view, backEnabled, tag);
+ }
+
+ private void init(View view, boolean back, Object tag) {
+ canGoBack = back;
+ crumbView = view;
+ data = tag;
+ }
+
+ private TextView makeCrumbView(String name) {
+ TextView tv = new TextView(mContext);
+ tv.setTextAppearance(mContext, android.R.style.TextAppearance_Medium);
+ tv.setPadding(16, 0, 16, 0);
+ tv.setGravity(Gravity.CENTER_VERTICAL);
+ tv.setText(name);
+ tv.setLayoutParams(new LayoutParams(LayoutParams.WRAP_CONTENT,
+ LayoutParams.MATCH_PARENT));
+ tv.setMaxWidth(mContext.getResources().getInteger(
+ R.integer.max_width_crumb));
+ tv.setMaxLines(1);
+ tv.setEllipsize(TextUtils.TruncateAt.END);
+ return tv;
+ }
+
+ }
+
+}
diff --git a/src/com/android/browser/Browser.java b/src/com/android/browser/Browser.java
index 7822ec8..f49da5d 100644
--- a/src/com/android/browser/Browser.java
+++ b/src/com/android/browser/Browser.java
@@ -16,6 +16,7 @@
package com.android.browser;
+import android.os.FileUtils;
import android.util.Log;
import android.app.Application;
@@ -47,17 +48,22 @@
public Browser() {
}
+ @Override
public void onCreate() {
+ super.onCreate();
+
+ // Set the umask so that native code creates files with the correct
+ // permissions (0660)
+ FileUtils.setUMask(FileUtils.S_IRWXO);
if (LOGV_ENABLED)
Log.v(LOGTAG, "Browser.onCreate: this=" + this);
+
// Fix heap utilization for better heap size characteristics.
VMRuntime.getRuntime().setTargetHeapUtilization(
TARGET_HEAP_UTILIZATION);
// create CookieSyncManager with current Context
CookieSyncManager.createInstance(this);
- // remove all expired cookies
- CookieManager.getInstance().removeExpiredCookie();
- BrowserSettings.getInstance().loadFromDb(this);
+ BrowserSettings.getInstance().asyncLoadFromDb(this);
}
static Intent createBrowserViewIntent() {
diff --git a/src/com/android/browser/BrowserActivity.java b/src/com/android/browser/BrowserActivity.java
index 44ab307..899a7c2 100644
--- a/src/com/android/browser/BrowserActivity.java
+++ b/src/com/android/browser/BrowserActivity.java
@@ -16,155 +16,41 @@
package com.android.browser;
+import com.google.common.annotations.VisibleForTesting;
+
import android.app.Activity;
-import android.app.AlertDialog;
-import android.app.DownloadManager;
-import android.app.ProgressDialog;
-import android.app.SearchManager;
-import android.content.ActivityNotFoundException;
-import android.content.BroadcastReceiver;
-import android.content.ComponentName;
-import android.content.ContentProvider;
-import android.content.ContentProviderClient;
-import android.content.ContentResolver;
-import android.content.ContentUris;
-import android.content.ContentValues;
-import android.content.Context;
-import android.content.DialogInterface;
import android.content.Intent;
-import android.content.IntentFilter;
-import android.content.pm.PackageInfo;
-import android.content.pm.PackageManager;
-import android.content.pm.ResolveInfo;
import android.content.res.Configuration;
-import android.content.res.Resources;
-import android.database.Cursor;
-import android.database.DatabaseUtils;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
-import android.graphics.Canvas;
-import android.graphics.Picture;
import android.graphics.PixelFormat;
-import android.graphics.Rect;
-import android.graphics.drawable.Drawable;
-import android.net.ConnectivityManager;
-import android.net.NetworkInfo;
-import android.net.Uri;
-import android.net.WebAddress;
-import android.net.http.SslCertificate;
-import android.net.http.SslError;
-import android.os.AsyncTask;
import android.os.Bundle;
-import android.os.Debug;
-import android.os.Environment;
-import android.os.Handler;
-import android.os.Message;
-import android.os.PowerManager;
-import android.os.Process;
-import android.os.ServiceManager;
-import android.os.SystemClock;
-import android.provider.Browser;
-import android.provider.ContactsContract;
-import android.provider.ContactsContract.Intents.Insert;
-import android.provider.Downloads;
-import android.provider.MediaStore;
-import android.speech.RecognizerResultsIntent;
-import android.text.IClipboard;
-import android.text.TextUtils;
-import android.text.format.DateFormat;
-import android.util.AttributeSet;
import android.util.Log;
-import android.util.Patterns;
+import android.view.ActionMode;
import android.view.ContextMenu;
-import android.view.Gravity;
+import android.view.ContextMenu.ContextMenuInfo;
import android.view.KeyEvent;
-import android.view.LayoutInflater;
import android.view.Menu;
-import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
-import android.view.ViewGroup;
import android.view.Window;
import android.view.WindowManager;
-import android.view.ContextMenu.ContextMenuInfo;
-import android.view.MenuItem.OnMenuItemClickListener;
-import android.webkit.CookieManager;
-import android.webkit.CookieSyncManager;
-import android.webkit.DownloadListener;
-import android.webkit.HttpAuthHandler;
-import android.webkit.PluginManager;
-import android.webkit.SslErrorHandler;
-import android.webkit.URLUtil;
-import android.webkit.ValueCallback;
-import android.webkit.WebChromeClient;
-import android.webkit.WebHistoryItem;
-import android.webkit.WebIconDatabase;
-import android.webkit.WebView;
-import android.widget.EditText;
-import android.widget.FrameLayout;
-import android.widget.LinearLayout;
-import android.widget.TextView;
-import android.widget.Toast;
-import android.accounts.Account;
-import android.accounts.AccountManager;
-import android.accounts.AccountManagerFuture;
-import android.accounts.AuthenticatorException;
-import android.accounts.OperationCanceledException;
-import android.accounts.AccountManagerCallback;
+import android.view.accessibility.AccessibilityManager;
-import com.android.browser.search.SearchEngine;
-import com.android.common.Search;
-import com.android.common.speech.LoggingEvents;
+public class BrowserActivity extends Activity {
-import java.io.ByteArrayOutputStream;
-import java.io.File;
-import java.io.IOException;
-import java.io.InputStream;
-import java.net.MalformedURLException;
-import java.net.URI;
-import java.net.URISyntaxException;
-import java.net.URL;
-import java.net.URLEncoder;
-import java.text.ParseException;
-import java.util.Date;
-import java.util.HashMap;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
+ public static final String ACTION_SHOW_BOOKMARKS = "show_bookmarks";
+ public static final String ACTION_SHOW_BROWSER = "show_browser";
+ public static final String ACTION_RESTART = "--restart--";
+ private static final String EXTRA_STATE = "state";
-public class BrowserActivity extends Activity
- implements View.OnCreateContextMenuListener, DownloadListener {
+ private final static String LOGTAG = "browser";
- /* Define some aliases to make these debugging flags easier to refer to.
- * This file imports android.provider.Browser, so we can't just refer to "Browser.DEBUG".
- */
- private final static boolean DEBUG = com.android.browser.Browser.DEBUG;
- private final static boolean LOGV_ENABLED = com.android.browser.Browser.LOGV_ENABLED;
- private final static boolean LOGD_ENABLED = com.android.browser.Browser.LOGD_ENABLED;
+ private final static boolean LOGV_ENABLED =
+ com.android.browser.Browser.LOGV_ENABLED;
- private static class ClearThumbnails extends AsyncTask<File, Void, Void> {
- @Override
- public Void doInBackground(File... files) {
- if (files != null) {
- for (File f : files) {
- if (!f.delete()) {
- Log.e(LOGTAG, f.getPath() + " was not deleted");
- }
- }
- }
- return null;
- }
- }
-
- /**
- * This layout holds everything you see below the status bar, including the
- * error console, the custom view container, and the webviews.
- */
- private FrameLayout mBrowserFrameLayout;
+ private Controller mController;
+ private UI mUi;
@Override
public void onCreate(Bundle icicle) {
@@ -172,8 +58,23 @@
Log.v(LOGTAG, this + " onStart");
}
super.onCreate(icicle);
- // test the browser in OpenGL
- // requestWindowFeature(Window.FEATURE_OPENGL);
+
+ BrowserSettings settings = BrowserSettings.getInstance();
+
+ // We load the first set of BrowserSettings from the db asynchronously
+ // but if it has not completed at this point, we have no choice but
+ // to block waiting for them to finish loading. :(
+ settings.waitForLoadFromDbToComplete();
+
+ // render the browser in OpenGL
+ if (settings.isHardwareAccelerated()) {
+ // Set the flag in the activity's window
+ this.getWindow().setFlags(WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED,
+ WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED);
+ } else {
+ // Clear the flag in the activity's window
+ this.getWindow().setFlags(0, WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED);
+ }
// enable this to test the browser in 32bit
if (false) {
@@ -181,543 +82,56 @@
BitmapFactory.setDefaultConfig(Bitmap.Config.ARGB_8888);
}
- setDefaultKeyMode(DEFAULT_KEYS_SEARCH_LOCAL);
-
- mResolver = getContentResolver();
-
- // Keep a settings instance handy.
- mSettings = BrowserSettings.getInstance();
-
// If this was a web search request, pass it on to the default web
// search provider and finish this activity.
- if (handleWebSearchIntent(getIntent())) {
+ if (IntentHandler.handleWebSearchIntent(this, null, getIntent())) {
finish();
return;
}
- mSecLockIcon = Resources.getSystem().getDrawable(
- android.R.drawable.ic_secure);
- mMixLockIcon = Resources.getSystem().getDrawable(
- android.R.drawable.ic_partial_secure);
-
- FrameLayout frameLayout = (FrameLayout) getWindow().getDecorView()
- .findViewById(com.android.internal.R.id.content);
- mBrowserFrameLayout = (FrameLayout) LayoutInflater.from(this)
- .inflate(R.layout.custom_screen, null);
- mContentView = (FrameLayout) mBrowserFrameLayout.findViewById(
- R.id.main_content);
- mErrorConsoleContainer = (LinearLayout) mBrowserFrameLayout
- .findViewById(R.id.error_console);
- mCustomViewContainer = (FrameLayout) mBrowserFrameLayout
- .findViewById(R.id.fullscreen_custom_content);
- frameLayout.addView(mBrowserFrameLayout, COVER_SCREEN_PARAMS);
- mTitleBar = new TitleBar(this);
- // mTitleBar will be always shown in the fully loaded mode
- mTitleBar.setProgress(100);
- mFakeTitleBar = new TitleBar(this);
-
- // Create the tab control and our initial tab
- mTabControl = new TabControl(this);
-
- // Open the icon database and retain all the bookmark urls for favicons
- retainIconsOnStartup();
-
- mSettings.setTabControl(mTabControl);
-
- PowerManager pm = (PowerManager) getSystemService(Context.POWER_SERVICE);
- mWakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "Browser");
-
- // Find out if the network is currently up.
- ConnectivityManager cm = (ConnectivityManager) getSystemService(
- Context.CONNECTIVITY_SERVICE);
- NetworkInfo info = cm.getActiveNetworkInfo();
- if (info != null) {
- mIsNetworkUp = info.isAvailable();
+ if (((AccessibilityManager) getSystemService(ACCESSIBILITY_SERVICE))
+ .isEnabled()) {
+ setDefaultKeyMode(DEFAULT_KEYS_DISABLE);
}
- /* enables registration for changes in network status from
- http stack */
- mNetworkStateChangedFilter = new IntentFilter();
- mNetworkStateChangedFilter.addAction(
- ConnectivityManager.CONNECTIVITY_ACTION);
- mNetworkStateIntentReceiver = new BroadcastReceiver() {
- @Override
- public void onReceive(Context context, Intent intent) {
- if (intent.getAction().equals(
- ConnectivityManager.CONNECTIVITY_ACTION)) {
-
- NetworkInfo info = intent.getParcelableExtra(
- ConnectivityManager.EXTRA_NETWORK_INFO);
- String typeName = info.getTypeName();
- String subtypeName = info.getSubtypeName();
- sendNetworkType(typeName.toLowerCase(),
- (subtypeName != null ? subtypeName.toLowerCase() : ""));
-
- onNetworkToggle(info.isAvailable());
- }
- }
- };
-
- IntentFilter filter = new IntentFilter(Intent.ACTION_PACKAGE_ADDED);
- filter.addAction(Intent.ACTION_PACKAGE_REMOVED);
- filter.addDataScheme("package");
- mPackageInstallationReceiver = new BroadcastReceiver() {
- @Override
- public void onReceive(Context context, Intent intent) {
- final String action = intent.getAction();
- final String packageName = intent.getData()
- .getSchemeSpecificPart();
- final boolean replacing = intent.getBooleanExtra(
- Intent.EXTRA_REPLACING, false);
- if (Intent.ACTION_PACKAGE_REMOVED.equals(action) && replacing) {
- // if it is replacing, refreshPlugins() when adding
- return;
- }
-
- if (sGoogleApps.contains(packageName)) {
- BrowserActivity.this.packageChanged(packageName,
- Intent.ACTION_PACKAGE_ADDED.equals(action));
- }
-
- PackageManager pm = BrowserActivity.this.getPackageManager();
- PackageInfo pkgInfo = null;
- try {
- pkgInfo = pm.getPackageInfo(packageName,
- PackageManager.GET_PERMISSIONS);
- } catch (PackageManager.NameNotFoundException e) {
- return;
- }
- if (pkgInfo != null) {
- String permissions[] = pkgInfo.requestedPermissions;
- if (permissions == null) {
- return;
- }
- boolean permissionOk = false;
- for (String permit : permissions) {
- if (PluginManager.PLUGIN_PERMISSION.equals(permit)) {
- permissionOk = true;
- break;
- }
- }
- if (permissionOk) {
- PluginManager.getInstance(BrowserActivity.this)
- .refreshPlugins(
- Intent.ACTION_PACKAGE_ADDED
- .equals(action));
- }
- }
- }
- };
- registerReceiver(mPackageInstallationReceiver, filter);
-
- if (!mTabControl.restoreState(icicle)) {
- // clear up the thumbnail directory if we can't restore the state as
- // none of the files in the directory are referenced any more.
- new ClearThumbnails().execute(
- mTabControl.getThumbnailDir().listFiles());
- // there is no quit on Android. But if we can't restore the state,
- // we can treat it as a new Browser, remove the old session cookies.
- CookieManager.getInstance().removeSessionCookie();
- final Intent intent = getIntent();
- final Bundle extra = intent.getExtras();
- // Create an initial tab.
- // If the intent is ACTION_VIEW and data is not null, the Browser is
- // invoked to view the content by another application. In this case,
- // the tab will be close when exit.
- UrlData urlData = getUrlDataFromIntent(intent);
-
- String action = intent.getAction();
- final Tab t = mTabControl.createNewTab(
- (Intent.ACTION_VIEW.equals(action) &&
- intent.getData() != null)
- || RecognizerResultsIntent.ACTION_VOICE_SEARCH_RESULTS
- .equals(action),
- intent.getStringExtra(Browser.EXTRA_APPLICATION_ID), urlData.mUrl);
- mTabControl.setCurrentTab(t);
- attachTabToContentView(t);
- WebView webView = t.getWebView();
- if (extra != null) {
- int scale = extra.getInt(Browser.INITIAL_ZOOM_LEVEL, 0);
- if (scale > 0 && scale <= 1000) {
- webView.setInitialScale(scale);
- }
- }
-
- if (urlData.isEmpty()) {
- loadUrl(webView, mSettings.getHomePage());
- } else {
- loadUrlDataIn(t, urlData);
- }
+ mController = new Controller(this);
+ boolean xlarge = (getResources().getConfiguration().screenLayout
+ & Configuration.SCREENLAYOUT_SIZE_MASK)
+ == Configuration.SCREENLAYOUT_SIZE_XLARGE;
+ if (xlarge) {
+ mUi = new XLargeUi(this, mController);
} else {
- // TabControl.restoreState() will create a new tab even if
- // restoring the state fails.
- attachTabToContentView(mTabControl.getCurrentTab());
+ mUi = new PhoneUi(this, mController);
+ }
+ mController.setUi(mUi);
+ mController.setWebViewFactory((BaseUi) mUi);
+
+ Bundle state = getIntent().getBundleExtra(EXTRA_STATE);
+ if (state != null && icicle == null) {
+ icicle = state;
}
- // Delete old thumbnails to save space
- File dir = mTabControl.getThumbnailDir();
- if (dir.exists()) {
- for (String child : dir.list()) {
- File f = new File(dir, child);
- f.delete();
- }
- }
-
- // Read JavaScript flags if it exists.
- String jsFlags = mSettings.getJsFlags();
- if (jsFlags.trim().length() != 0) {
- mTabControl.getCurrentWebView().setJsFlags(jsFlags);
- }
- // Work out which packages are installed on the system.
- getInstalledPackages();
-
- // Start watching the default geolocation permissions
- mSystemAllowGeolocationOrigins
- = new SystemAllowGeolocationOrigins(getApplicationContext());
- mSystemAllowGeolocationOrigins.start();
+ mController.start(icicle, getIntent());
}
- /**
- * Feed the previously stored results strings to the BrowserProvider so that
- * the SearchDialog will show them instead of the standard searches.
- * @param result String to show on the editable line of the SearchDialog.
- */
- /* package */ void showVoiceSearchResults(String result) {
- ContentProviderClient client = mResolver.acquireContentProviderClient(
- Browser.BOOKMARKS_URI);
- ContentProvider prov = client.getLocalContentProvider();
- BrowserProvider bp = (BrowserProvider) prov;
- bp.setQueryResults(mTabControl.getCurrentTab().getVoiceSearchResults());
- client.release();
-
- Bundle bundle = createGoogleSearchSourceBundle(
- GOOGLE_SEARCH_SOURCE_SEARCHKEY);
- bundle.putBoolean(SearchManager.CONTEXT_IS_VOICE, true);
- startSearch(result, false, bundle, false);
+ @VisibleForTesting
+ Controller getController() {
+ return mController;
}
@Override
protected void onNewIntent(Intent intent) {
- Tab current = mTabControl.getCurrentTab();
- // When a tab is closed on exit, the current tab index is set to -1.
- // Reset before proceed as Browser requires the current tab to be set.
- if (current == null) {
- // Try to reset the tab in case the index was incorrect.
- current = mTabControl.getTab(0);
- if (current == null) {
- // No tabs at all so just ignore this intent.
- return;
- }
- mTabControl.setCurrentTab(current);
- attachTabToContentView(current);
- resetTitleAndIcon(current.getWebView());
- }
- final String action = intent.getAction();
- final int flags = intent.getFlags();
- if (Intent.ACTION_MAIN.equals(action) ||
- (flags & Intent.FLAG_ACTIVITY_LAUNCHED_FROM_HISTORY) != 0) {
- // just resume the browser
+ if (ACTION_RESTART.equals(intent.getAction())) {
+ Bundle outState = new Bundle();
+ mController.onSaveInstanceState(outState);
+ finish();
+ getApplicationContext().startActivity(
+ new Intent(getApplicationContext(), BrowserActivity.class)
+ .addFlags(Intent.FLAG_ACTIVITY_NEW_TASK)
+ .putExtra(EXTRA_STATE, outState));
return;
}
- // In case the SearchDialog is open.
- ((SearchManager) getSystemService(Context.SEARCH_SERVICE))
- .stopSearch();
- boolean activateVoiceSearch = RecognizerResultsIntent
- .ACTION_VOICE_SEARCH_RESULTS.equals(action);
- if (Intent.ACTION_VIEW.equals(action)
- || Intent.ACTION_SEARCH.equals(action)
- || MediaStore.INTENT_ACTION_MEDIA_SEARCH.equals(action)
- || Intent.ACTION_WEB_SEARCH.equals(action)
- || activateVoiceSearch) {
- if (current.isInVoiceSearchMode()) {
- String title = current.getVoiceDisplayTitle();
- if (title != null && title.equals(intent.getStringExtra(
- SearchManager.QUERY))) {
- // The user submitted the same search as the last voice
- // search, so do nothing.
- return;
- }
- if (Intent.ACTION_SEARCH.equals(action)
- && current.voiceSearchSourceIsGoogle()) {
- Intent logIntent = new Intent(
- LoggingEvents.ACTION_LOG_EVENT);
- logIntent.putExtra(LoggingEvents.EXTRA_EVENT,
- LoggingEvents.VoiceSearch.QUERY_UPDATED);
- logIntent.putExtra(
- LoggingEvents.VoiceSearch.EXTRA_QUERY_UPDATED_VALUE,
- intent.getDataString());
- sendBroadcast(logIntent);
- // Note, onPageStarted will revert the voice title bar
- // When http://b/issue?id=2379215 is fixed, we should update
- // the title bar here.
- }
- }
- // If this was a search request (e.g. search query directly typed into the address bar),
- // pass it on to the default web search provider.
- if (handleWebSearchIntent(intent)) {
- return;
- }
-
- UrlData urlData = getUrlDataFromIntent(intent);
- if (urlData.isEmpty()) {
- urlData = new UrlData(mSettings.getHomePage());
- }
-
- final String appId = intent
- .getStringExtra(Browser.EXTRA_APPLICATION_ID);
- if ((Intent.ACTION_VIEW.equals(action)
- // If a voice search has no appId, it means that it came
- // from the browser. In that case, reuse the current tab.
- || (activateVoiceSearch && appId != null))
- && !getPackageName().equals(appId)
- && (flags & Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT) != 0) {
- Tab appTab = mTabControl.getTabFromId(appId);
- if (appTab != null) {
- Log.i(LOGTAG, "Reusing tab for " + appId);
- // Dismiss the subwindow if applicable.
- dismissSubWindow(appTab);
- // Since we might kill the WebView, remove it from the
- // content view first.
- removeTabFromContentView(appTab);
- // Recreate the main WebView after destroying the old one.
- // If the WebView has the same original url and is on that
- // page, it can be reused.
- boolean needsLoad =
- mTabControl.recreateWebView(appTab, urlData);
-
- if (current != appTab) {
- switchToTab(mTabControl.getTabIndex(appTab));
- if (needsLoad) {
- loadUrlDataIn(appTab, urlData);
- }
- } else {
- // If the tab was the current tab, we have to attach
- // it to the view system again.
- attachTabToContentView(appTab);
- if (needsLoad) {
- loadUrlDataIn(appTab, urlData);
- }
- }
- return;
- } else {
- // No matching application tab, try to find a regular tab
- // with a matching url.
- appTab = mTabControl.findUnusedTabWithUrl(urlData.mUrl);
- if (appTab != null) {
- if (current != appTab) {
- switchToTab(mTabControl.getTabIndex(appTab));
- }
- // Otherwise, we are already viewing the correct tab.
- } else {
- // if FLAG_ACTIVITY_BROUGHT_TO_FRONT flag is on, the url
- // will be opened in a new tab unless we have reached
- // MAX_TABS. Then the url will be opened in the current
- // tab. If a new tab is created, it will have "true" for
- // exit on close.
- openTabAndShow(urlData, true, appId);
- }
- }
- } else {
- if (!urlData.isEmpty()
- && urlData.mUrl.startsWith("about:debug")) {
- if ("about:debug.dom".equals(urlData.mUrl)) {
- current.getWebView().dumpDomTree(false);
- } else if ("about:debug.dom.file".equals(urlData.mUrl)) {
- current.getWebView().dumpDomTree(true);
- } else if ("about:debug.render".equals(urlData.mUrl)) {
- current.getWebView().dumpRenderTree(false);
- } else if ("about:debug.render.file".equals(urlData.mUrl)) {
- current.getWebView().dumpRenderTree(true);
- } else if ("about:debug.display".equals(urlData.mUrl)) {
- current.getWebView().dumpDisplayTree();
- } else if (urlData.mUrl.startsWith("about:debug.drag")) {
- int index = urlData.mUrl.codePointAt(16) - '0';
- if (index <= 0 || index > 9) {
- current.getWebView().setDragTracker(null);
- } else {
- current.getWebView().setDragTracker(new MeshTracker(index));
- }
- } else {
- mSettings.toggleDebugSettings();
- }
- return;
- }
- // Get rid of the subwindow if it exists
- dismissSubWindow(current);
- // If the current Tab is being used as an application tab,
- // remove the association, since the new Intent means that it is
- // no longer associated with that application.
- current.setAppId(null);
- loadUrlDataIn(current, urlData);
- }
- }
- }
-
- /**
- * Launches the default web search activity with the query parameters if the given intent's data
- * are identified as plain search terms and not URLs/shortcuts.
- * @return true if the intent was handled and web search activity was launched, false if not.
- */
- private boolean handleWebSearchIntent(Intent intent) {
- if (intent == null) return false;
-
- String url = null;
- final String action = intent.getAction();
- if (RecognizerResultsIntent.ACTION_VOICE_SEARCH_RESULTS.equals(
- action)) {
- return false;
- }
- if (Intent.ACTION_VIEW.equals(action)) {
- Uri data = intent.getData();
- if (data != null) url = data.toString();
- } else if (Intent.ACTION_SEARCH.equals(action)
- || MediaStore.INTENT_ACTION_MEDIA_SEARCH.equals(action)
- || Intent.ACTION_WEB_SEARCH.equals(action)) {
- url = intent.getStringExtra(SearchManager.QUERY);
- }
- return handleWebSearchRequest(url, intent.getBundleExtra(SearchManager.APP_DATA),
- intent.getStringExtra(SearchManager.EXTRA_DATA_KEY));
- }
-
- /**
- * Launches the default web search activity with the query parameters if the given url string
- * was identified as plain search terms and not URL/shortcut.
- * @return true if the request was handled and web search activity was launched, false if not.
- */
- private boolean handleWebSearchRequest(String inUrl, Bundle appData, String extraData) {
- if (inUrl == null) return false;
-
- // In general, we shouldn't modify URL from Intent.
- // But currently, we get the user-typed URL from search box as well.
- String url = fixUrl(inUrl).trim();
-
- // URLs are handled by the regular flow of control, so
- // return early.
- if (Patterns.WEB_URL.matcher(url).matches()
- || ACCEPTED_URI_SCHEMA.matcher(url).matches()) {
- return false;
- }
-
- final ContentResolver cr = mResolver;
- final String newUrl = url;
- new AsyncTask<Void, Void, Void>() {
- protected Void doInBackground(Void... unused) {
- Browser.updateVisitedHistory(cr, newUrl, false);
- Browser.addSearchUrl(cr, newUrl);
- return null;
- }
- }.execute();
-
- SearchEngine searchEngine = mSettings.getSearchEngine();
- if (searchEngine == null) return false;
- searchEngine.startSearch(this, url, appData, extraData);
-
- return true;
- }
-
- private UrlData getUrlDataFromIntent(Intent intent) {
- String url = "";
- Map<String, String> headers = null;
- if (intent != null) {
- final String action = intent.getAction();
- if (Intent.ACTION_VIEW.equals(action)) {
- url = smartUrlFilter(intent.getData());
- if (url != null && url.startsWith("content:")) {
- /* Append mimetype so webview knows how to display */
- String mimeType = intent.resolveType(getContentResolver());
- if (mimeType != null) {
- url += "?" + mimeType;
- }
- }
- if (url != null && url.startsWith("http")) {
- final Bundle pairs = intent
- .getBundleExtra(Browser.EXTRA_HEADERS);
- if (pairs != null && !pairs.isEmpty()) {
- Iterator<String> iter = pairs.keySet().iterator();
- headers = new HashMap<String, String>();
- while (iter.hasNext()) {
- String key = iter.next();
- headers.put(key, pairs.getString(key));
- }
- }
- }
- } else if (Intent.ACTION_SEARCH.equals(action)
- || MediaStore.INTENT_ACTION_MEDIA_SEARCH.equals(action)
- || Intent.ACTION_WEB_SEARCH.equals(action)) {
- url = intent.getStringExtra(SearchManager.QUERY);
- if (url != null) {
- mLastEnteredUrl = url;
- // In general, we shouldn't modify URL from Intent.
- // But currently, we get the user-typed URL from search box as well.
- url = fixUrl(url);
- url = smartUrlFilter(url);
- final ContentResolver cr = mResolver;
- final String newUrl = url;
- new AsyncTask<Void, Void, Void>() {
- protected Void doInBackground(Void... unused) {
- Browser.updateVisitedHistory(cr, newUrl, false);
- return null;
- }
- }.execute();
- String searchSource = "&source=android-" + GOOGLE_SEARCH_SOURCE_SUGGEST + "&";
- if (url.contains(searchSource)) {
- String source = null;
- final Bundle appData = intent.getBundleExtra(SearchManager.APP_DATA);
- if (appData != null) {
- source = appData.getString(Search.SOURCE);
- }
- if (TextUtils.isEmpty(source)) {
- source = GOOGLE_SEARCH_SOURCE_UNKNOWN;
- }
- url = url.replace(searchSource, "&source=android-"+source+"&");
- }
- }
- }
- }
- return new UrlData(url, headers, intent);
- }
- /* package */ void showVoiceTitleBar(String title) {
- mTitleBar.setInVoiceMode(true);
- mFakeTitleBar.setInVoiceMode(true);
-
- mTitleBar.setDisplayTitle(title);
- mFakeTitleBar.setDisplayTitle(title);
- }
- /* package */ void revertVoiceTitleBar() {
- mTitleBar.setInVoiceMode(false);
- mFakeTitleBar.setInVoiceMode(false);
-
- mTitleBar.setDisplayTitle(mUrl);
- mFakeTitleBar.setDisplayTitle(mUrl);
- }
- /* package */ static String fixUrl(String inUrl) {
- // FIXME: Converting the url to lower case
- // duplicates functionality in smartUrlFilter().
- // However, changing all current callers of fixUrl to
- // call smartUrlFilter in addition may have unwanted
- // consequences, and is deferred for now.
- int colon = inUrl.indexOf(':');
- boolean allLower = true;
- for (int index = 0; index < colon; index++) {
- char ch = inUrl.charAt(index);
- if (!Character.isLetter(ch)) {
- break;
- }
- allLower &= Character.isLowerCase(ch);
- if (index == colon - 1 && !allLower) {
- inUrl = inUrl.substring(0, colon).toLowerCase()
- + inUrl.substring(colon);
- }
- }
- if (inUrl.startsWith("http://") || inUrl.startsWith("https://"))
- return inUrl;
- if (inUrl.startsWith("http:") ||
- inUrl.startsWith("https:")) {
- if (inUrl.startsWith("http:/") || inUrl.startsWith("https:/")) {
- inUrl = inUrl.replaceFirst("/", "//");
- } else inUrl = inUrl.replaceFirst(":", "://");
- }
- return inUrl;
+ mController.handleNewIntent(intent);
}
@Override
@@ -726,170 +140,28 @@
if (LOGV_ENABLED) {
Log.v(LOGTAG, "BrowserActivity.onResume: this=" + this);
}
-
- if (!mActivityInPause) {
- Log.e(LOGTAG, "BrowserActivity is already resumed.");
- return;
+ if (mController != null) {
+ mController.onResume();
}
-
- mTabControl.resumeCurrentTab();
- mActivityInPause = false;
- resumeWebViewTimers();
-
- if (mWakeLock.isHeld()) {
- mHandler.removeMessages(RELEASE_WAKELOCK);
- mWakeLock.release();
- }
-
- registerReceiver(mNetworkStateIntentReceiver,
- mNetworkStateChangedFilter);
- WebView.enablePlatformNotifications();
}
- /**
- * Since the actual title bar is embedded in the WebView, and removing it
- * would change its appearance, use a different TitleBar to show overlayed
- * at the top of the screen, when the menu is open or the page is loading.
- */
- private TitleBar mFakeTitleBar;
-
- /**
- * Keeps track of whether the options menu is open. This is important in
- * determining whether to show or hide the title bar overlay.
- */
- private boolean mOptionsMenuOpen;
-
- /**
- * Only meaningful when mOptionsMenuOpen is true. This variable keeps track
- * of whether the configuration has changed. The first onMenuOpened call
- * after a configuration change is simply a reopening of the same menu
- * (i.e. mIconView did not change).
- */
- private boolean mConfigChanged;
-
- /**
- * Whether or not the options menu is in its smaller, icon menu form. When
- * true, we want the title bar overlay to be up. When false, we do not.
- * Only meaningful if mOptionsMenuOpen is true.
- */
- private boolean mIconView;
-
@Override
public boolean onMenuOpened(int featureId, Menu menu) {
if (Window.FEATURE_OPTIONS_PANEL == featureId) {
- if (mOptionsMenuOpen) {
- if (mConfigChanged) {
- // We do not need to make any changes to the state of the
- // title bar, since the only thing that happened was a
- // change in orientation
- mConfigChanged = false;
- } else {
- if (mIconView) {
- // Switching the menu to expanded view, so hide the
- // title bar.
- hideFakeTitleBar();
- mIconView = false;
- } else {
- // Switching the menu back to icon view, so show the
- // title bar once again.
- showFakeTitleBar();
- mIconView = true;
- }
- }
- } else {
- // The options menu is closed, so open it, and show the title
- showFakeTitleBar();
- mOptionsMenuOpen = true;
- mConfigChanged = false;
- mIconView = true;
- }
+ mController.onMenuOpened(featureId, menu);
}
return true;
}
- private void showFakeTitleBar() {
- if (mFakeTitleBar.getParent() == null && mActiveTabsPage == null
- && !mActivityInPause) {
- WebView mainView = mTabControl.getCurrentWebView();
- // if there is no current WebView, don't show the faked title bar;
- if (mainView == null) {
- return;
- }
- // Do not need to check for null, since the current tab will have
- // at least a main WebView, or we would have returned above.
- if (dialogIsUp()) {
- // Do not show the fake title bar, which would cover up the
- // find or select dialog.
- return;
- }
-
- WindowManager manager
- = (WindowManager) getSystemService(Context.WINDOW_SERVICE);
-
- // Add the title bar to the window manager so it can receive touches
- // while the menu is up
- WindowManager.LayoutParams params
- = new WindowManager.LayoutParams(
- ViewGroup.LayoutParams.MATCH_PARENT,
- ViewGroup.LayoutParams.WRAP_CONTENT,
- WindowManager.LayoutParams.TYPE_APPLICATION,
- WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE,
- PixelFormat.TRANSLUCENT);
- params.gravity = Gravity.TOP;
- boolean atTop = mainView.getScrollY() == 0;
- params.windowAnimations = atTop ? 0 : R.style.TitleBar;
- manager.addView(mFakeTitleBar, params);
- }
- }
-
@Override
public void onOptionsMenuClosed(Menu menu) {
- mOptionsMenuOpen = false;
- if (!mInLoad) {
- hideFakeTitleBar();
- } else if (!mIconView) {
- // The page is currently loading, and we are in expanded mode, so
- // we were not showing the menu. Show it once again. It will be
- // removed when the page finishes.
- showFakeTitleBar();
- }
- }
-
- private void hideFakeTitleBar() {
- if (mFakeTitleBar.getParent() == null) return;
- WindowManager.LayoutParams params = (WindowManager.LayoutParams)
- mFakeTitleBar.getLayoutParams();
- WebView mainView = mTabControl.getCurrentWebView();
- // Although we decided whether or not to animate based on the current
- // scroll position, the scroll position may have changed since the
- // fake title bar was displayed. Make sure it has the appropriate
- // animation/lack thereof before removing.
- params.windowAnimations = mainView != null && mainView.getScrollY() == 0
- ? 0 : R.style.TitleBar;
- WindowManager manager
- = (WindowManager) getSystemService(Context.WINDOW_SERVICE);
- manager.updateViewLayout(mFakeTitleBar, params);
- manager.removeView(mFakeTitleBar);
- }
-
- /**
- * Special method for the fake title bar to call when displaying its context
- * menu, since it is in its own Window, and its parent does not show a
- * context menu.
- */
- /* package */ void showTitleBarContextMenu() {
- if (null == mTitleBar.getParent()) {
- return;
- }
- openContextMenu(mTitleBar);
+ mController.onOptionsMenuClosed(menu);
}
@Override
public void onContextMenuClosed(Menu menu) {
super.onContextMenuClosed(menu);
- if (mInLoad) {
- showFakeTitleBar();
- }
+ mController.onContextMenuClosed(menu);
}
/**
@@ -902,50 +174,15 @@
if (LOGV_ENABLED) {
Log.v(LOGTAG, "BrowserActivity.onSaveInstanceState: this=" + this);
}
- // the default implementation requires each view to have an id. As the
- // browser handles the state itself and it doesn't use id for the views,
- // don't call the default implementation. Otherwise it will trigger the
- // warning like this, "couldn't save which view has focus because the
- // focused view XXX has no id".
-
- // Save all the tabs
- mTabControl.saveState(outState);
+ mController.onSaveInstanceState(outState);
}
@Override
protected void onPause() {
+ if (mController != null) {
+ mController.onPause();
+ }
super.onPause();
-
- if (mActivityInPause) {
- Log.e(LOGTAG, "BrowserActivity is already paused.");
- return;
- }
-
- mTabControl.pauseCurrentTab();
- mActivityInPause = true;
- if (mTabControl.getCurrentIndex() >= 0 && !pauseWebViewTimers()) {
- mWakeLock.acquire();
- mHandler.sendMessageDelayed(mHandler
- .obtainMessage(RELEASE_WAKELOCK), WAKELOCK_TIMEOUT);
- }
-
- // FIXME: This removes the active tabs page and resets the menu to
- // MAIN_MENU. A better solution might be to do this work in onNewIntent
- // but then we would need to save it in onSaveInstanceState and restore
- // it in onCreate/onRestoreInstanceState
- if (mActiveTabsPage != null) {
- removeActiveTabPage(true);
- }
-
- cancelStopToast();
-
- // unregister network state listener
- unregisterReceiver(mNetworkStateIntentReceiver);
- WebView.disablePlatformNotifications();
-
- if (mCustomView != null) {
- mTabControl.getCurrentWebView().getWebChromeClient().onHideCustomView();
- }
}
@Override
@@ -954,3069 +191,85 @@
Log.v(LOGTAG, "BrowserActivity.onDestroy: this=" + this);
}
super.onDestroy();
-
- if (mUploadMessage != null) {
- mUploadMessage.onReceiveValue(null);
- mUploadMessage = null;
+ if (mController != null) {
+ mController.onDestroy();
}
-
- if (mTabControl == null) return;
-
- // Remove the fake title bar if it is there
- hideFakeTitleBar();
-
- // Remove the current tab and sub window
- Tab t = mTabControl.getCurrentTab();
- if (t != null) {
- dismissSubWindow(t);
- removeTabFromContentView(t);
- }
- // Destroy all the tabs
- mTabControl.destroy();
- WebIconDatabase.getInstance().close();
-
- unregisterReceiver(mPackageInstallationReceiver);
-
- // Stop watching the default geolocation permissions
- mSystemAllowGeolocationOrigins.stop();
- mSystemAllowGeolocationOrigins = null;
+ mUi = null;
+ mController = null;
}
@Override
public void onConfigurationChanged(Configuration newConfig) {
- mConfigChanged = true;
super.onConfigurationChanged(newConfig);
-
- if (mPageInfoDialog != null) {
- mPageInfoDialog.dismiss();
- showPageInfo(
- mPageInfoView,
- mPageInfoFromShowSSLCertificateOnError);
- }
- if (mSSLCertificateDialog != null) {
- mSSLCertificateDialog.dismiss();
- showSSLCertificate(
- mSSLCertificateView);
- }
- if (mSSLCertificateOnErrorDialog != null) {
- mSSLCertificateOnErrorDialog.dismiss();
- showSSLCertificateOnError(
- mSSLCertificateOnErrorView,
- mSSLCertificateOnErrorHandler,
- mSSLCertificateOnErrorError);
- }
- if (mHttpAuthenticationDialog != null) {
- String title = ((TextView) mHttpAuthenticationDialog
- .findViewById(com.android.internal.R.id.alertTitle)).getText()
- .toString();
- String name = ((TextView) mHttpAuthenticationDialog
- .findViewById(R.id.username_edit)).getText().toString();
- String password = ((TextView) mHttpAuthenticationDialog
- .findViewById(R.id.password_edit)).getText().toString();
- int focusId = mHttpAuthenticationDialog.getCurrentFocus()
- .getId();
- mHttpAuthenticationDialog.dismiss();
- showHttpAuthentication(mHttpAuthHandler, null, null, title,
- name, password, focusId);
- }
+ mController.onConfgurationChanged(newConfig);
}
@Override
public void onLowMemory() {
super.onLowMemory();
- mTabControl.freeMemory();
- }
-
- private void resumeWebViewTimers() {
- Tab tab = mTabControl.getCurrentTab();
- if (tab == null) return; // monkey can trigger this
- boolean inLoad = tab.inLoad();
- if ((!mActivityInPause && !inLoad) || (mActivityInPause && inLoad)) {
- CookieSyncManager.getInstance().startSync();
- WebView w = tab.getWebView();
- if (w != null) {
- w.resumeTimers();
- }
- }
- }
-
- private boolean pauseWebViewTimers() {
- Tab tab = mTabControl.getCurrentTab();
- boolean inLoad = tab.inLoad();
- if (mActivityInPause && !inLoad) {
- CookieSyncManager.getInstance().stopSync();
- WebView w = mTabControl.getCurrentWebView();
- if (w != null) {
- w.pauseTimers();
- }
- return true;
- } else {
- return false;
- }
- }
-
- // Open the icon database and retain all the icons for visited sites.
- private void retainIconsOnStartup() {
- final WebIconDatabase db = WebIconDatabase.getInstance();
- db.open(getDir("icons", 0).getPath());
- Cursor c = null;
- try {
- c = Browser.getAllBookmarks(mResolver);
- if (c.moveToFirst()) {
- int urlIndex = c.getColumnIndex(Browser.BookmarkColumns.URL);
- do {
- String url = c.getString(urlIndex);
- db.retainIconForPageUrl(url);
- } while (c.moveToNext());
- }
- } catch (IllegalStateException e) {
- Log.e(LOGTAG, "retainIconsOnStartup", e);
- } finally {
- if (c!= null) c.close();
- }
- }
-
- // Helper method for getting the top window.
- WebView getTopWindow() {
- return mTabControl.getCurrentTopWebView();
- }
-
- TabControl getTabControl() {
- return mTabControl;
+ mController.onLowMemory();
}
@Override
public boolean onCreateOptionsMenu(Menu menu) {
super.onCreateOptionsMenu(menu);
-
- MenuInflater inflater = getMenuInflater();
- inflater.inflate(R.menu.browser, menu);
- mMenu = menu;
- updateInLoadMenuItems();
- return true;
- }
-
- /**
- * As the menu can be open when loading state changes
- * we must manually update the state of the stop/reload menu
- * item
- */
- private void updateInLoadMenuItems() {
- if (mMenu == null) {
- return;
- }
- MenuItem src = mInLoad ?
- mMenu.findItem(R.id.stop_menu_id):
- mMenu.findItem(R.id.reload_menu_id);
- MenuItem dest = mMenu.findItem(R.id.stop_reload_menu_id);
- dest.setIcon(src.getIcon());
- dest.setTitle(src.getTitle());
- }
-
- @Override
- public boolean onContextItemSelected(MenuItem item) {
- // chording is not an issue with context menus, but we use the same
- // options selector, so set mCanChord to true so we can access them.
- mCanChord = true;
- int id = item.getItemId();
- boolean result = true;
- switch (id) {
- // For the context menu from the title bar
- case R.id.title_bar_copy_page_url:
- Tab currentTab = mTabControl.getCurrentTab();
- if (null == currentTab) {
- result = false;
- break;
- }
- WebView mainView = currentTab.getWebView();
- if (null == mainView) {
- result = false;
- break;
- }
- copy(mainView.getUrl());
- break;
- // -- Browser context menu
- case R.id.open_context_menu_id:
- case R.id.open_newtab_context_menu_id:
- case R.id.bookmark_context_menu_id:
- case R.id.save_link_context_menu_id:
- case R.id.share_link_context_menu_id:
- case R.id.copy_link_context_menu_id:
- final WebView webView = getTopWindow();
- if (null == webView) {
- result = false;
- break;
- }
- final HashMap hrefMap = new HashMap();
- hrefMap.put("webview", webView);
- final Message msg = mHandler.obtainMessage(
- FOCUS_NODE_HREF, id, 0, hrefMap);
- webView.requestFocusNodeHref(msg);
- break;
-
- default:
- // For other context menus
- result = onOptionsItemSelected(item);
- }
- mCanChord = false;
- return result;
- }
-
- private Bundle createGoogleSearchSourceBundle(String source) {
- Bundle bundle = new Bundle();
- bundle.putString(Search.SOURCE, source);
- return bundle;
- }
-
- /* package */ void editUrl() {
- if (mOptionsMenuOpen) closeOptionsMenu();
- String url = (getTopWindow() == null) ? null : getTopWindow().getUrl();
- startSearch(mSettings.getHomePage().equals(url) ? null : url, true,
- null, false);
- }
-
- /**
- * Overriding this to insert a local information bundle
- */
- @Override
- public void startSearch(String initialQuery, boolean selectInitialQuery,
- Bundle appSearchData, boolean globalSearch) {
- if (appSearchData == null) {
- appSearchData = createGoogleSearchSourceBundle(GOOGLE_SEARCH_SOURCE_TYPE);
- }
-
- SearchEngine searchEngine = mSettings.getSearchEngine();
- if (searchEngine != null && !searchEngine.supportsVoiceSearch()) {
- appSearchData.putBoolean(SearchManager.DISABLE_VOICE_SEARCH, true);
- }
-
- super.startSearch(initialQuery, selectInitialQuery, appSearchData, globalSearch);
- }
-
- /**
- * Switch tabs. Called by the TitleBarSet when sliding the title bar
- * results in changing tabs.
- * @param index Index of the tab to change to, as defined by
- * mTabControl.getTabIndex(Tab t).
- * @return boolean True if we successfully switched to a different tab. If
- * the indexth tab is null, or if that tab is the same as
- * the current one, return false.
- */
- /* package */ boolean switchToTab(int index) {
- Tab tab = mTabControl.getTab(index);
- Tab currentTab = mTabControl.getCurrentTab();
- if (tab == null || tab == currentTab) {
- return false;
- }
- if (currentTab != null) {
- // currentTab may be null if it was just removed. In that case,
- // we do not need to remove it
- removeTabFromContentView(currentTab);
- }
- mTabControl.setCurrentTab(tab);
- attachTabToContentView(tab);
- resetTitleIconAndProgress();
- updateLockIconToLatest();
- return true;
- }
-
- /* package */ Tab openTabToHomePage() {
- return openTabAndShow(mSettings.getHomePage(), false, null);
- }
-
- /* package */ void closeCurrentWindow() {
- final Tab current = mTabControl.getCurrentTab();
- if (mTabControl.getTabCount() == 1) {
- // This is the last tab. Open a new one, with the home
- // page and close the current one.
- openTabToHomePage();
- closeTab(current);
- return;
- }
- final Tab parent = current.getParentTab();
- int indexToShow = -1;
- if (parent != null) {
- indexToShow = mTabControl.getTabIndex(parent);
- } else {
- final int currentIndex = mTabControl.getCurrentIndex();
- // Try to move to the tab to the right
- indexToShow = currentIndex + 1;
- if (indexToShow > mTabControl.getTabCount() - 1) {
- // Try to move to the tab to the left
- indexToShow = currentIndex - 1;
- }
- }
- if (switchToTab(indexToShow)) {
- // Close window
- closeTab(current);
- }
- }
-
- private ActiveTabsPage mActiveTabsPage;
-
- /**
- * Remove the active tabs page.
- * @param needToAttach If true, the active tabs page did not attach a tab
- * to the content view, so we need to do that here.
- */
- /* package */ void removeActiveTabPage(boolean needToAttach) {
- mContentView.removeView(mActiveTabsPage);
- mActiveTabsPage = null;
- mMenuState = R.id.MAIN_MENU;
- if (needToAttach) {
- attachTabToContentView(mTabControl.getCurrentTab());
- }
- getTopWindow().requestFocus();
- }
-
- private WebView showDialog(WebDialog dialog) {
- Tab tab = mTabControl.getCurrentTab();
- if (tab.getSubWebView() == null) {
- // If the find or select is being performed on the main webview,
- // remove the embedded title bar.
- WebView mainView = tab.getWebView();
- if (mainView != null) {
- mainView.setEmbeddedTitleBar(null);
- }
- }
- hideFakeTitleBar();
- mMenuState = EMPTY_MENU;
- return tab.showDialog(dialog);
- }
-
- @Override
- public boolean onOptionsItemSelected(MenuItem item) {
- if (!mCanChord) {
- // The user has already fired a shortcut with this hold down of the
- // menu key.
- return false;
- }
- if (null == getTopWindow()) {
- return false;
- }
- if (mMenuIsDown) {
- // The shortcut action consumes the MENU. Even if it is still down,
- // it won't trigger the next shortcut action. In the case of the
- // shortcut action triggering a new activity, like Bookmarks, we
- // won't get onKeyUp for MENU. So it is important to reset it here.
- mMenuIsDown = false;
- }
- switch (item.getItemId()) {
- // -- Main menu
- case R.id.new_tab_menu_id:
- openTabToHomePage();
- break;
-
- case R.id.goto_menu_id:
- editUrl();
- break;
-
- case R.id.bookmarks_menu_id:
- bookmarksOrHistoryPicker(false);
- break;
-
- case R.id.active_tabs_menu_id:
- mActiveTabsPage = new ActiveTabsPage(this, mTabControl);
- removeTabFromContentView(mTabControl.getCurrentTab());
- hideFakeTitleBar();
- mContentView.addView(mActiveTabsPage, COVER_SCREEN_PARAMS);
- mActiveTabsPage.requestFocus();
- mMenuState = EMPTY_MENU;
- break;
-
- case R.id.add_bookmark_menu_id:
- Intent i = new Intent(BrowserActivity.this,
- AddBookmarkPage.class);
- WebView w = getTopWindow();
- i.putExtra("url", w.getUrl());
- i.putExtra("title", w.getTitle());
- i.putExtra("touch_icon_url", w.getTouchIconUrl());
- i.putExtra("thumbnail", createScreenshot(w));
- startActivity(i);
- break;
-
- case R.id.stop_reload_menu_id:
- if (mInLoad) {
- stopLoading();
- } else {
- getTopWindow().reload();
- }
- break;
-
- case R.id.back_menu_id:
- getTopWindow().goBack();
- break;
-
- case R.id.forward_menu_id:
- getTopWindow().goForward();
- break;
-
- case R.id.close_menu_id:
- // Close the subwindow if it exists.
- if (mTabControl.getCurrentSubWindow() != null) {
- dismissSubWindow(mTabControl.getCurrentTab());
- break;
- }
- closeCurrentWindow();
- break;
-
- case R.id.homepage_menu_id:
- Tab current = mTabControl.getCurrentTab();
- if (current != null) {
- dismissSubWindow(current);
- loadUrl(current.getWebView(), mSettings.getHomePage());
- }
- break;
-
- case R.id.preferences_menu_id:
- Intent intent = new Intent(this,
- BrowserPreferencesPage.class);
- intent.putExtra(BrowserPreferencesPage.CURRENT_PAGE,
- getTopWindow().getUrl());
- startActivityForResult(intent, PREFERENCES_PAGE);
- break;
-
- case R.id.find_menu_id:
- showFindDialog();
- break;
-
- case R.id.select_text_id:
- if (true) {
- Tab currentTab = mTabControl.getCurrentTab();
- if (currentTab != null) {
- currentTab.getWebView().setUpSelect();
- }
- } else {
- showSelectDialog();
- }
- break;
-
- case R.id.page_info_menu_id:
- showPageInfo(mTabControl.getCurrentTab(), false);
- break;
-
- case R.id.classic_history_menu_id:
- bookmarksOrHistoryPicker(true);
- break;
-
- case R.id.title_bar_share_page_url:
- case R.id.share_page_menu_id:
- Tab currentTab = mTabControl.getCurrentTab();
- if (null == currentTab) {
- mCanChord = false;
- return false;
- }
- currentTab.populatePickerData();
- sharePage(this, currentTab.getTitle(),
- currentTab.getUrl(), currentTab.getFavicon(),
- createScreenshot(currentTab.getWebView()));
- break;
-
- case R.id.dump_nav_menu_id:
- getTopWindow().debugDump();
- break;
-
- case R.id.dump_counters_menu_id:
- getTopWindow().dumpV8Counters();
- break;
-
- case R.id.zoom_in_menu_id:
- getTopWindow().zoomIn();
- break;
-
- case R.id.zoom_out_menu_id:
- getTopWindow().zoomOut();
- break;
-
- case R.id.view_downloads_menu_id:
- viewDownloads();
- break;
-
- case R.id.window_one_menu_id:
- case R.id.window_two_menu_id:
- case R.id.window_three_menu_id:
- case R.id.window_four_menu_id:
- case R.id.window_five_menu_id:
- case R.id.window_six_menu_id:
- case R.id.window_seven_menu_id:
- case R.id.window_eight_menu_id:
- {
- int menuid = item.getItemId();
- for (int id = 0; id < WINDOW_SHORTCUT_ID_ARRAY.length; id++) {
- if (WINDOW_SHORTCUT_ID_ARRAY[id] == menuid) {
- Tab desiredTab = mTabControl.getTab(id);
- if (desiredTab != null &&
- desiredTab != mTabControl.getCurrentTab()) {
- switchToTab(id);
- }
- break;
- }
- }
- }
- break;
-
- default:
- if (!super.onOptionsItemSelected(item)) {
- return false;
- }
- // Otherwise fall through.
- }
- mCanChord = false;
- return true;
- }
-
- private boolean dialogIsUp() {
- return null != mFindDialog && mFindDialog.isVisible() ||
- null != mSelectDialog && mSelectDialog.isVisible();
- }
-
- private boolean closeDialog(WebDialog dialog) {
- if (null == dialog || !dialog.isVisible()) return false;
- Tab currentTab = mTabControl.getCurrentTab();
- currentTab.closeDialog(dialog);
- dialog.dismiss();
- return true;
- }
-
- /*
- * Remove the find dialog or select dialog.
- */
- public void closeDialogs() {
- if (!(closeDialog(mFindDialog) || closeDialog(mSelectDialog))) return;
- // If the Find was being performed in the main WebView, replace the
- // embedded title bar.
- Tab currentTab = mTabControl.getCurrentTab();
- if (currentTab.getSubWebView() == null) {
- WebView mainView = currentTab.getWebView();
- if (mainView != null) {
- mainView.setEmbeddedTitleBar(mTitleBar);
- }
- }
- mMenuState = R.id.MAIN_MENU;
- if (mInLoad) {
- // The title bar was hidden, because otherwise it would cover up the
- // find or select dialog. Now that the dialog has been removed,
- // show the fake title bar once again.
- showFakeTitleBar();
- }
- }
-
- public void showFindDialog() {
- if (null == mFindDialog) {
- mFindDialog = new FindDialog(this);
- }
- showDialog(mFindDialog).setFindIsUp(true);
- }
-
- public void setFindDialogText(String text) {
- mFindDialog.setText(text);
- }
-
- public void showSelectDialog() {
- if (null == mSelectDialog) {
- mSelectDialog = new SelectDialog(this);
- }
- showDialog(mSelectDialog).setUpSelect();
- mSelectDialog.hideSoftInput();
+ return mController.onCreateOptionsMenu(menu);
}
@Override
public boolean onPrepareOptionsMenu(Menu menu) {
- // This happens when the user begins to hold down the menu key, so
- // allow them to chord to get a shortcut.
- mCanChord = true;
- // Note: setVisible will decide whether an item is visible; while
- // setEnabled() will decide whether an item is enabled, which also means
- // whether the matching shortcut key will function.
super.onPrepareOptionsMenu(menu);
- switch (mMenuState) {
- case EMPTY_MENU:
- if (mCurrentMenuState != mMenuState) {
- menu.setGroupVisible(R.id.MAIN_MENU, false);
- menu.setGroupEnabled(R.id.MAIN_MENU, false);
- menu.setGroupEnabled(R.id.MAIN_SHORTCUT_MENU, false);
- }
- break;
- default:
- if (mCurrentMenuState != mMenuState) {
- menu.setGroupVisible(R.id.MAIN_MENU, true);
- menu.setGroupEnabled(R.id.MAIN_MENU, true);
- menu.setGroupEnabled(R.id.MAIN_SHORTCUT_MENU, true);
- }
- final WebView w = getTopWindow();
- boolean canGoBack = false;
- boolean canGoForward = false;
- boolean isHome = false;
- if (w != null) {
- canGoBack = w.canGoBack();
- canGoForward = w.canGoForward();
- isHome = mSettings.getHomePage().equals(w.getUrl());
- }
- final MenuItem back = menu.findItem(R.id.back_menu_id);
- back.setEnabled(canGoBack);
+ return mController.onPrepareOptionsMenu(menu);
+ }
- final MenuItem home = menu.findItem(R.id.homepage_menu_id);
- home.setEnabled(!isHome);
-
- menu.findItem(R.id.forward_menu_id)
- .setEnabled(canGoForward);
-
- menu.findItem(R.id.new_tab_menu_id).setEnabled(
- mTabControl.canCreateNewTab());
-
- // decide whether to show the share link option
- PackageManager pm = getPackageManager();
- Intent send = new Intent(Intent.ACTION_SEND);
- send.setType("text/plain");
- ResolveInfo ri = pm.resolveActivity(send, PackageManager.MATCH_DEFAULT_ONLY);
- menu.findItem(R.id.share_page_menu_id).setVisible(ri != null);
-
- boolean isNavDump = mSettings.isNavDump();
- final MenuItem nav = menu.findItem(R.id.dump_nav_menu_id);
- nav.setVisible(isNavDump);
- nav.setEnabled(isNavDump);
-
- boolean showDebugSettings = mSettings.showDebugSettings();
- final MenuItem counter = menu.findItem(R.id.dump_counters_menu_id);
- counter.setVisible(showDebugSettings);
- counter.setEnabled(showDebugSettings);
-
- break;
+ @Override
+ public boolean onOptionsItemSelected(MenuItem item) {
+ if (!mController.onOptionsItemSelected(item)) {
+ return super.onOptionsItemSelected(item);
}
- mCurrentMenuState = mMenuState;
return true;
}
@Override
public void onCreateContextMenu(ContextMenu menu, View v,
ContextMenuInfo menuInfo) {
- if (v instanceof TitleBar) {
- return;
- }
- WebView webview = (WebView) v;
- WebView.HitTestResult result = webview.getHitTestResult();
- if (result == null) {
- return;
- }
-
- int type = result.getType();
- if (type == WebView.HitTestResult.UNKNOWN_TYPE) {
- Log.w(LOGTAG,
- "We should not show context menu when nothing is touched");
- return;
- }
- if (type == WebView.HitTestResult.EDIT_TEXT_TYPE) {
- // let TextView handles context menu
- return;
- }
-
- // Note, http://b/issue?id=1106666 is requesting that
- // an inflated menu can be used again. This is not available
- // yet, so inflate each time (yuk!)
- MenuInflater inflater = getMenuInflater();
- inflater.inflate(R.menu.browsercontext, menu);
-
- // Show the correct menu group
- String extra = result.getExtra();
- menu.setGroupVisible(R.id.PHONE_MENU,
- type == WebView.HitTestResult.PHONE_TYPE);
- menu.setGroupVisible(R.id.EMAIL_MENU,
- type == WebView.HitTestResult.EMAIL_TYPE);
- menu.setGroupVisible(R.id.GEO_MENU,
- type == WebView.HitTestResult.GEO_TYPE);
- menu.setGroupVisible(R.id.IMAGE_MENU,
- type == WebView.HitTestResult.IMAGE_TYPE
- || type == WebView.HitTestResult.SRC_IMAGE_ANCHOR_TYPE);
- menu.setGroupVisible(R.id.ANCHOR_MENU,
- type == WebView.HitTestResult.SRC_ANCHOR_TYPE
- || type == WebView.HitTestResult.SRC_IMAGE_ANCHOR_TYPE);
-
- // Setup custom handling depending on the type
- switch (type) {
- case WebView.HitTestResult.PHONE_TYPE:
- menu.setHeaderTitle(Uri.decode(extra));
- menu.findItem(R.id.dial_context_menu_id).setIntent(
- new Intent(Intent.ACTION_VIEW, Uri
- .parse(WebView.SCHEME_TEL + extra)));
- Intent addIntent = new Intent(Intent.ACTION_INSERT_OR_EDIT);
- addIntent.putExtra(Insert.PHONE, Uri.decode(extra));
- addIntent.setType(ContactsContract.Contacts.CONTENT_ITEM_TYPE);
- menu.findItem(R.id.add_contact_context_menu_id).setIntent(
- addIntent);
- menu.findItem(R.id.copy_phone_context_menu_id).setOnMenuItemClickListener(
- new Copy(extra));
- break;
-
- case WebView.HitTestResult.EMAIL_TYPE:
- menu.setHeaderTitle(extra);
- menu.findItem(R.id.email_context_menu_id).setIntent(
- new Intent(Intent.ACTION_VIEW, Uri
- .parse(WebView.SCHEME_MAILTO + extra)));
- menu.findItem(R.id.copy_mail_context_menu_id).setOnMenuItemClickListener(
- new Copy(extra));
- break;
-
- case WebView.HitTestResult.GEO_TYPE:
- menu.setHeaderTitle(extra);
- menu.findItem(R.id.map_context_menu_id).setIntent(
- new Intent(Intent.ACTION_VIEW, Uri
- .parse(WebView.SCHEME_GEO
- + URLEncoder.encode(extra))));
- menu.findItem(R.id.copy_geo_context_menu_id).setOnMenuItemClickListener(
- new Copy(extra));
- break;
-
- case WebView.HitTestResult.SRC_ANCHOR_TYPE:
- case WebView.HitTestResult.SRC_IMAGE_ANCHOR_TYPE:
- TextView titleView = (TextView) LayoutInflater.from(this)
- .inflate(android.R.layout.browser_link_context_header,
- null);
- titleView.setText(extra);
- menu.setHeaderView(titleView);
- // decide whether to show the open link in new tab option
- menu.findItem(R.id.open_newtab_context_menu_id).setVisible(
- mTabControl.canCreateNewTab());
- menu.findItem(R.id.bookmark_context_menu_id).setVisible(
- Bookmarks.urlHasAcceptableScheme(extra));
- PackageManager pm = getPackageManager();
- Intent send = new Intent(Intent.ACTION_SEND);
- send.setType("text/plain");
- ResolveInfo ri = pm.resolveActivity(send, PackageManager.MATCH_DEFAULT_ONLY);
- menu.findItem(R.id.share_link_context_menu_id).setVisible(ri != null);
- if (type == WebView.HitTestResult.SRC_ANCHOR_TYPE) {
- break;
- }
- // otherwise fall through to handle image part
- case WebView.HitTestResult.IMAGE_TYPE:
- if (type == WebView.HitTestResult.IMAGE_TYPE) {
- menu.setHeaderTitle(extra);
- }
- menu.findItem(R.id.view_image_context_menu_id).setIntent(
- new Intent(Intent.ACTION_VIEW, Uri.parse(extra)));
- menu.findItem(R.id.download_context_menu_id).
- setOnMenuItemClickListener(new Download(extra));
- menu.findItem(R.id.set_wallpaper_context_menu_id).
- setOnMenuItemClickListener(new SetAsWallpaper(extra));
- break;
-
- default:
- Log.w(LOGTAG, "We should not get here.");
- break;
- }
- hideFakeTitleBar();
+ mController.onCreateContextMenu(menu, v, menuInfo);
}
- // Attach the given tab to the content view.
- // this should only be called for the current tab.
- private void attachTabToContentView(Tab t) {
- // Attach the container that contains the main WebView and any other UI
- // associated with the tab.
- t.attachTabToContentView(mContentView);
-
- if (mShouldShowErrorConsole) {
- ErrorConsoleView errorConsole = t.getErrorConsole(true);
- if (errorConsole.numberOfErrors() == 0) {
- errorConsole.showConsole(ErrorConsoleView.SHOW_NONE);
- } else {
- errorConsole.showConsole(ErrorConsoleView.SHOW_MINIMIZED);
- }
-
- mErrorConsoleContainer.addView(errorConsole,
- new LinearLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,
- ViewGroup.LayoutParams.WRAP_CONTENT));
- }
-
- WebView view = t.getWebView();
- view.setEmbeddedTitleBar(mTitleBar);
- if (t.isInVoiceSearchMode()) {
- showVoiceTitleBar(t.getVoiceDisplayTitle());
- } else {
- revertVoiceTitleBar();
- }
- // Request focus on the top window.
- t.getTopWindow().requestFocus();
- }
-
- // Attach a sub window to the main WebView of the given tab.
- void attachSubWindow(Tab t) {
- t.attachSubWindow(mContentView);
- getTopWindow().requestFocus();
- }
-
- // Remove the given tab from the content view.
- private void removeTabFromContentView(Tab t) {
- // Remove the container that contains the main WebView.
- t.removeTabFromContentView(mContentView);
-
- ErrorConsoleView errorConsole = t.getErrorConsole(false);
- if (errorConsole != null) {
- mErrorConsoleContainer.removeView(errorConsole);
- }
-
- WebView view = t.getWebView();
- if (view != null) {
- view.setEmbeddedTitleBar(null);
- }
- }
-
- // Remove the sub window if it exists. Also called by TabControl when the
- // user clicks the 'X' to dismiss a sub window.
- /* package */ void dismissSubWindow(Tab t) {
- t.removeSubWindow(mContentView);
- // dismiss the subwindow. This will destroy the WebView.
- t.dismissSubWindow();
- getTopWindow().requestFocus();
- }
-
- // A wrapper function of {@link #openTabAndShow(UrlData, boolean, String)}
- // that accepts url as string.
- private Tab openTabAndShow(String url, boolean closeOnExit, String appId) {
- return openTabAndShow(new UrlData(url), closeOnExit, appId);
- }
-
- // This method does a ton of stuff. It will attempt to create a new tab
- // if we haven't reached MAX_TABS. Otherwise it uses the current tab. If
- // url isn't null, it will load the given url.
- /* package */Tab openTabAndShow(UrlData urlData, boolean closeOnExit,
- String appId) {
- final Tab currentTab = mTabControl.getCurrentTab();
- if (mTabControl.canCreateNewTab()) {
- final Tab tab = mTabControl.createNewTab(closeOnExit, appId,
- urlData.mUrl);
- WebView webview = tab.getWebView();
- // If the last tab was removed from the active tabs page, currentTab
- // will be null.
- if (currentTab != null) {
- removeTabFromContentView(currentTab);
- }
- // We must set the new tab as the current tab to reflect the old
- // animation behavior.
- mTabControl.setCurrentTab(tab);
- attachTabToContentView(tab);
- if (!urlData.isEmpty()) {
- loadUrlDataIn(tab, urlData);
- }
- return tab;
- } else {
- // Get rid of the subwindow if it exists
- dismissSubWindow(currentTab);
- if (!urlData.isEmpty()) {
- // Load the given url.
- loadUrlDataIn(currentTab, urlData);
- }
- return currentTab;
- }
- }
-
- private Tab openTab(String url) {
- if (mSettings.openInBackground()) {
- Tab t = mTabControl.createNewTab();
- if (t != null) {
- WebView view = t.getWebView();
- loadUrl(view, url);
- }
- return t;
- } else {
- return openTabAndShow(url, false, null);
- }
- }
-
- private class Copy implements OnMenuItemClickListener {
- private CharSequence mText;
-
- public boolean onMenuItemClick(MenuItem item) {
- copy(mText);
- return true;
- }
-
- public Copy(CharSequence toCopy) {
- mText = toCopy;
- }
- }
-
- private class Download implements OnMenuItemClickListener {
- private String mText;
-
- public boolean onMenuItemClick(MenuItem item) {
- onDownloadStartNoStream(mText, null, null, null, -1);
- return true;
- }
-
- public Download(String toDownload) {
- mText = toDownload;
- }
- }
-
- private class SetAsWallpaper extends Thread implements
- OnMenuItemClickListener, DialogInterface.OnCancelListener {
- private URL mUrl;
- private ProgressDialog mWallpaperProgress;
- private boolean mCanceled = false;
-
- public SetAsWallpaper(String url) {
- try {
- mUrl = new URL(url);
- } catch (MalformedURLException e) {
- mUrl = null;
- }
- }
-
- public void onCancel(DialogInterface dialog) {
- mCanceled = true;
- }
-
- public boolean onMenuItemClick(MenuItem item) {
- if (mUrl != null) {
- // The user may have tried to set a image with a large file size as their
- // background so it may take a few moments to perform the operation. Display
- // a progress spinner while it is working.
- mWallpaperProgress = new ProgressDialog(BrowserActivity.this);
- mWallpaperProgress.setIndeterminate(true);
- mWallpaperProgress.setMessage(getText(R.string.progress_dialog_setting_wallpaper));
- mWallpaperProgress.setCancelable(true);
- mWallpaperProgress.setOnCancelListener(this);
- mWallpaperProgress.show();
- start();
- }
- return true;
- }
-
- public void run() {
- Drawable oldWallpaper = BrowserActivity.this.getWallpaper();
- try {
- // TODO: This will cause the resource to be downloaded again, when we
- // should in most cases be able to grab it from the cache. To fix this
- // we should query WebCore to see if we can access a cached version and
- // instead open an input stream on that. This pattern could also be used
- // in the download manager where the same problem exists.
- InputStream inputstream = mUrl.openStream();
- if (inputstream != null) {
- setWallpaper(inputstream);
- }
- } catch (IOException e) {
- Log.e(LOGTAG, "Unable to set new wallpaper");
- // Act as though the user canceled the operation so we try to
- // restore the old wallpaper.
- mCanceled = true;
- }
-
- if (mCanceled) {
- // Restore the old wallpaper if the user cancelled whilst we were setting
- // the new wallpaper.
- int width = oldWallpaper.getIntrinsicWidth();
- int height = oldWallpaper.getIntrinsicHeight();
- Bitmap bm = Bitmap.createBitmap(width, height, Bitmap.Config.RGB_565);
- Canvas canvas = new Canvas(bm);
- oldWallpaper.setBounds(0, 0, width, height);
- oldWallpaper.draw(canvas);
- try {
- setWallpaper(bm);
- } catch (IOException e) {
- Log.e(LOGTAG, "Unable to restore old wallpaper.");
- }
- mCanceled = false;
- }
-
- if (mWallpaperProgress.isShowing()) {
- mWallpaperProgress.dismiss();
- }
- }
- }
-
- private void copy(CharSequence text) {
- try {
- IClipboard clip = IClipboard.Stub.asInterface(ServiceManager.getService("clipboard"));
- if (clip != null) {
- clip.setClipboardText(text);
- }
- } catch (android.os.RemoteException e) {
- Log.e(LOGTAG, "Copy failed", e);
- }
- }
-
- /**
- * Resets the browser title-view to whatever it must be
- * (for example, if we had a loading error)
- * When we have a new page, we call resetTitle, when we
- * have to reset the titlebar to whatever it used to be
- * (for example, if the user chose to stop loading), we
- * call resetTitleAndRevertLockIcon.
- */
- /* package */ void resetTitleAndRevertLockIcon() {
- mTabControl.getCurrentTab().revertLockIcon();
- updateLockIconToLatest();
- resetTitleIconAndProgress();
- }
-
- /**
- * Reset the title, favicon, and progress.
- */
- private void resetTitleIconAndProgress() {
- WebView current = mTabControl.getCurrentWebView();
- if (current == null) {
- return;
- }
- resetTitleAndIcon(current);
- int progress = current.getProgress();
- current.getWebChromeClient().onProgressChanged(current, progress);
- }
-
- // Reset the title and the icon based on the given item.
- private void resetTitleAndIcon(WebView view) {
- WebHistoryItem item = view.copyBackForwardList().getCurrentItem();
- if (item != null) {
- setUrlTitle(item.getUrl(), item.getTitle());
- setFavicon(item.getFavicon());
- } else {
- setUrlTitle(null, null);
- setFavicon(null);
- }
- }
-
- /**
- * Sets a title composed of the URL and the title string.
- * @param url The URL of the site being loaded.
- * @param title The title of the site being loaded.
- */
- void setUrlTitle(String url, String title) {
- mUrl = url;
- mTitle = title;
-
- // If we are in voice search mode, the title has already been set.
- if (mTabControl.getCurrentTab().isInVoiceSearchMode()) return;
- mTitleBar.setDisplayTitle(url);
- mFakeTitleBar.setDisplayTitle(url);
- }
-
- /**
- * @param url The URL to build a title version of the URL from.
- * @return The title version of the URL or null if fails.
- * The title version of the URL can be either the URL hostname,
- * or the hostname with an "https://" prefix (for secure URLs),
- * or an empty string if, for example, the URL in question is a
- * file:// URL with no hostname.
- */
- /* package */ static String buildTitleUrl(String url) {
- String titleUrl = null;
-
- if (url != null) {
- try {
- // parse the url string
- URL urlObj = new URL(url);
- if (urlObj != null) {
- titleUrl = "";
-
- String protocol = urlObj.getProtocol();
- String host = urlObj.getHost();
-
- if (host != null && 0 < host.length()) {
- titleUrl = host;
- if (protocol != null) {
- // if a secure site, add an "https://" prefix!
- if (protocol.equalsIgnoreCase("https")) {
- titleUrl = protocol + "://" + host;
- }
- }
- }
- }
- } catch (MalformedURLException e) {}
- }
-
- return titleUrl;
- }
-
- // Set the favicon in the title bar.
- void setFavicon(Bitmap icon) {
- mTitleBar.setFavicon(icon);
- mFakeTitleBar.setFavicon(icon);
- }
-
- /**
- * Close the tab, remove its associated title bar, and adjust mTabControl's
- * current tab to a valid value.
- */
- /* package */ void closeTab(Tab t) {
- int currentIndex = mTabControl.getCurrentIndex();
- int removeIndex = mTabControl.getTabIndex(t);
- mTabControl.removeTab(t);
- if (currentIndex >= removeIndex && currentIndex != 0) {
- currentIndex--;
- }
- mTabControl.setCurrentTab(mTabControl.getTab(currentIndex));
- resetTitleIconAndProgress();
- }
-
- /* package */ void goBackOnePageOrQuit() {
- Tab current = mTabControl.getCurrentTab();
- if (current == null) {
- /*
- * Instead of finishing the activity, simply push this to the back
- * of the stack and let ActivityManager to choose the foreground
- * activity. As BrowserActivity is singleTask, it will be always the
- * root of the task. So we can use either true or false for
- * moveTaskToBack().
- */
- moveTaskToBack(true);
- return;
- }
- WebView w = current.getWebView();
- if (w.canGoBack()) {
- w.goBack();
- } else {
- // Check to see if we are closing a window that was created by
- // another window. If so, we switch back to that window.
- Tab parent = current.getParentTab();
- if (parent != null) {
- switchToTab(mTabControl.getTabIndex(parent));
- // Now we close the other tab
- closeTab(current);
- } else {
- if (current.closeOnExit()) {
- // force the tab's inLoad() to be false as we are going to
- // either finish the activity or remove the tab. This will
- // ensure pauseWebViewTimers() taking action.
- mTabControl.getCurrentTab().clearInLoad();
- if (mTabControl.getTabCount() == 1) {
- finish();
- return;
- }
- // call pauseWebViewTimers() now, we won't be able to call
- // it in onPause() as the WebView won't be valid.
- // Temporarily change mActivityInPause to be true as
- // pauseWebViewTimers() will do nothing if mActivityInPause
- // is false.
- boolean savedState = mActivityInPause;
- if (savedState) {
- Log.e(LOGTAG, "BrowserActivity is already paused "
- + "while handing goBackOnePageOrQuit.");
- }
- mActivityInPause = true;
- pauseWebViewTimers();
- mActivityInPause = savedState;
- removeTabFromContentView(current);
- mTabControl.removeTab(current);
- }
- /*
- * Instead of finishing the activity, simply push this to the back
- * of the stack and let ActivityManager to choose the foreground
- * activity. As BrowserActivity is singleTask, it will be always the
- * root of the task. So we can use either true or false for
- * moveTaskToBack().
- */
- moveTaskToBack(true);
- }
- }
- }
-
- boolean isMenuDown() {
- return mMenuIsDown;
+ @Override
+ public boolean onContextItemSelected(MenuItem item) {
+ return mController.onContextItemSelected(item);
}
@Override
public boolean onKeyDown(int keyCode, KeyEvent event) {
- // Even if MENU is already held down, we need to call to super to open
- // the IME on long press.
- if (KeyEvent.KEYCODE_MENU == keyCode) {
- mMenuIsDown = true;
- return super.onKeyDown(keyCode, event);
- }
- // The default key mode is DEFAULT_KEYS_SEARCH_LOCAL. As the MENU is
- // still down, we don't want to trigger the search. Pretend to consume
- // the key and do nothing.
- if (mMenuIsDown) return true;
-
- switch(keyCode) {
- case KeyEvent.KEYCODE_SPACE:
- // WebView/WebTextView handle the keys in the KeyDown. As
- // the Activity's shortcut keys are only handled when WebView
- // doesn't, have to do it in onKeyDown instead of onKeyUp.
- if (event.isShiftPressed()) {
- getTopWindow().pageUp(false);
- } else {
- getTopWindow().pageDown(false);
- }
- return true;
- case KeyEvent.KEYCODE_BACK:
- if (event.getRepeatCount() == 0) {
- event.startTracking();
- return true;
- } else if (mCustomView == null && mActiveTabsPage == null
- && event.isLongPress()) {
- bookmarksOrHistoryPicker(true);
- return true;
- }
- break;
- }
- return super.onKeyDown(keyCode, event);
+ return mController.onKeyDown(keyCode, event) ||
+ super.onKeyDown(keyCode, event);
}
@Override
public boolean onKeyUp(int keyCode, KeyEvent event) {
- switch(keyCode) {
- case KeyEvent.KEYCODE_MENU:
- mMenuIsDown = false;
- break;
- case KeyEvent.KEYCODE_BACK:
- if (event.isTracking() && !event.isCanceled()) {
- if (mCustomView != null) {
- // if a custom view is showing, hide it
- mTabControl.getCurrentWebView().getWebChromeClient()
- .onHideCustomView();
- } else if (mActiveTabsPage != null) {
- // if tab page is showing, hide it
- removeActiveTabPage(true);
- } else {
- WebView subwindow = mTabControl.getCurrentSubWindow();
- if (subwindow != null) {
- if (subwindow.canGoBack()) {
- subwindow.goBack();
- } else {
- dismissSubWindow(mTabControl.getCurrentTab());
- }
- } else {
- goBackOnePageOrQuit();
- }
- }
- return true;
- }
- break;
- }
- return super.onKeyUp(keyCode, event);
+ return mController.onKeyUp(keyCode, event) ||
+ super.onKeyUp(keyCode, event);
}
- /* package */ void stopLoading() {
- mDidStopLoad = true;
- resetTitleAndRevertLockIcon();
- WebView w = getTopWindow();
- w.stopLoading();
- // FIXME: before refactor, it is using mWebViewClient. So I keep the
- // same logic here. But for subwindow case, should we call into the main
- // WebView's onPageFinished as we never call its onPageStarted and if
- // the page finishes itself, we don't call onPageFinished.
- mTabControl.getCurrentWebView().getWebViewClient().onPageFinished(w,
- w.getUrl());
-
- cancelStopToast();
- mStopToast = Toast
- .makeText(this, R.string.stopping, Toast.LENGTH_SHORT);
- mStopToast.show();
+ @Override
+ public void onActionModeStarted(ActionMode mode) {
+ super.onActionModeStarted(mode);
+ mController.onActionModeStarted(mode);
}
- boolean didUserStopLoading() {
- return mDidStopLoad;
- }
-
- private void cancelStopToast() {
- if (mStopToast != null) {
- mStopToast.cancel();
- mStopToast = null;
- }
- }
-
- // called by a UI or non-UI thread to post the message
- public void postMessage(int what, int arg1, int arg2, Object obj,
- long delayMillis) {
- mHandler.sendMessageDelayed(mHandler.obtainMessage(what, arg1, arg2,
- obj), delayMillis);
- }
-
- // called by a UI or non-UI thread to remove the message
- void removeMessages(int what, Object object) {
- mHandler.removeMessages(what, object);
- }
-
- // public message ids
- public final static int LOAD_URL = 1001;
- public final static int STOP_LOAD = 1002;
-
- // Message Ids
- private static final int FOCUS_NODE_HREF = 102;
- private static final int RELEASE_WAKELOCK = 107;
-
- static final int UPDATE_BOOKMARK_THUMBNAIL = 108;
-
- // Private handler for handling javascript and saving passwords
- private Handler mHandler = new Handler() {
-
- public void handleMessage(Message msg) {
- switch (msg.what) {
- case FOCUS_NODE_HREF:
- {
- String url = (String) msg.getData().get("url");
- String title = (String) msg.getData().get("title");
- if (url == null || url.length() == 0) {
- break;
- }
- HashMap focusNodeMap = (HashMap) msg.obj;
- WebView view = (WebView) focusNodeMap.get("webview");
- // Only apply the action if the top window did not change.
- if (getTopWindow() != view) {
- break;
- }
- switch (msg.arg1) {
- case R.id.open_context_menu_id:
- case R.id.view_image_context_menu_id:
- loadUrlFromContext(getTopWindow(), url);
- break;
- case R.id.open_newtab_context_menu_id:
- final Tab parent = mTabControl.getCurrentTab();
- final Tab newTab = openTab(url);
- if (newTab != parent) {
- parent.addChildTab(newTab);
- }
- break;
- case R.id.bookmark_context_menu_id:
- Intent intent = new Intent(BrowserActivity.this,
- AddBookmarkPage.class);
- intent.putExtra("url", url);
- intent.putExtra("title", title);
- startActivity(intent);
- break;
- case R.id.share_link_context_menu_id:
- // See if this site has been visited before
- StringBuilder sb = new StringBuilder(
- Browser.BookmarkColumns.URL + " = ");
- DatabaseUtils.appendEscapedSQLString(sb, url);
- Cursor c = null;
- try {
- c = mResolver.query(Browser.BOOKMARKS_URI,
- Browser.HISTORY_PROJECTION,
- sb.toString(),
- null,
- null);
- if (c.moveToFirst()) {
- // The site has been visited before, so grab the
- // info from the database.
- Bitmap favicon = null;
- Bitmap thumbnail = null;
- String linkTitle = c.getString(Browser.
- HISTORY_PROJECTION_TITLE_INDEX);
- byte[] data = c.getBlob(Browser.
- HISTORY_PROJECTION_FAVICON_INDEX);
- if (data != null) {
- favicon = BitmapFactory.decodeByteArray(
- data, 0, data.length);
- }
- data = c.getBlob(Browser.
- HISTORY_PROJECTION_THUMBNAIL_INDEX);
- if (data != null) {
- thumbnail = BitmapFactory.decodeByteArray(
- data, 0, data.length);
- }
- sharePage(BrowserActivity.this,
- linkTitle, url, favicon, thumbnail);
- } else {
- Browser.sendString(BrowserActivity.this, url,
- getString(
- R.string.choosertitle_sharevia));
- }
- } finally {
- if (c != null) c.close();
- }
- // close the cursor after its used
- if (c != null) {
- c.close();
- }
- break;
- case R.id.copy_link_context_menu_id:
- copy(url);
- break;
- case R.id.save_link_context_menu_id:
- case R.id.download_context_menu_id:
- onDownloadStartNoStream(url, null, null, null, -1);
- break;
- }
- break;
- }
-
- case LOAD_URL:
- loadUrlFromContext(getTopWindow(), (String) msg.obj);
- break;
-
- case STOP_LOAD:
- stopLoading();
- break;
-
- case RELEASE_WAKELOCK:
- if (mWakeLock.isHeld()) {
- mWakeLock.release();
- // if we reach here, Browser should be still in the
- // background loading after WAKELOCK_TIMEOUT (5-min).
- // To avoid burning the battery, stop loading.
- mTabControl.stopAllLoading();
- }
- break;
-
- case UPDATE_BOOKMARK_THUMBNAIL:
- WebView view = (WebView) msg.obj;
- if (view != null) {
- updateScreenshot(view);
- }
- break;
- }
- }
- };
-
- /**
- * Share a page, providing the title, url, favicon, and a screenshot. Uses
- * an {@link Intent} to launch the Activity chooser.
- * @param c Context used to launch a new Activity.
- * @param title Title of the page. Stored in the Intent with
- * {@link Intent#EXTRA_SUBJECT}
- * @param url URL of the page. Stored in the Intent with
- * {@link Intent#EXTRA_TEXT}
- * @param favicon Bitmap of the favicon for the page. Stored in the Intent
- * with {@link Browser#EXTRA_SHARE_FAVICON}
- * @param screenshot Bitmap of a screenshot of the page. Stored in the
- * Intent with {@link Browser#EXTRA_SHARE_SCREENSHOT}
- */
- public static final void sharePage(Context c, String title, String url,
- Bitmap favicon, Bitmap screenshot) {
- Intent send = new Intent(Intent.ACTION_SEND);
- send.setType("text/plain");
- send.putExtra(Intent.EXTRA_TEXT, url);
- send.putExtra(Intent.EXTRA_SUBJECT, title);
- send.putExtra(Browser.EXTRA_SHARE_FAVICON, favicon);
- send.putExtra(Browser.EXTRA_SHARE_SCREENSHOT, screenshot);
- try {
- c.startActivity(Intent.createChooser(send, c.getString(
- R.string.choosertitle_sharevia)));
- } catch(android.content.ActivityNotFoundException ex) {
- // if no app handles it, do nothing
- }
- }
-
- private void updateScreenshot(WebView view) {
- // If this is a bookmarked site, add a screenshot to the database.
- // FIXME: When should we update? Every time?
- // FIXME: Would like to make sure there is actually something to
- // draw, but the API for that (WebViewCore.pictureReady()) is not
- // currently accessible here.
-
- final Bitmap bm = createScreenshot(view);
- if (bm == null) {
- return;
- }
-
- final ContentResolver cr = getContentResolver();
- final String url = view.getUrl();
- final String originalUrl = view.getOriginalUrl();
-
- new AsyncTask<Void, Void, Void>() {
- @Override
- protected Void doInBackground(Void... unused) {
- Cursor c = null;
- try {
- c = BrowserBookmarksAdapter.queryBookmarksForUrl(
- cr, originalUrl, url, true);
- if (c != null) {
- if (c.moveToFirst()) {
- ContentValues values = new ContentValues();
- final ByteArrayOutputStream os
- = new ByteArrayOutputStream();
- bm.compress(Bitmap.CompressFormat.PNG, 100, os);
- values.put(Browser.BookmarkColumns.THUMBNAIL,
- os.toByteArray());
- do {
- cr.update(ContentUris.withAppendedId(
- Browser.BOOKMARKS_URI, c.getInt(0)),
- values, null, null);
- } while (c.moveToNext());
- }
- }
- } catch (IllegalStateException e) {
- // Ignore
- } finally {
- if (c != null) c.close();
- }
- return null;
- }
- }.execute();
- }
-
- /**
- * Values for the size of the thumbnail created when taking a screenshot.
- * Lazily initialized. Instead of using these directly, use
- * getDesiredThumbnailWidth() or getDesiredThumbnailHeight().
- */
- private static int THUMBNAIL_WIDTH = 0;
- private static int THUMBNAIL_HEIGHT = 0;
-
- /**
- * Return the desired width for thumbnail screenshots, which are stored in
- * the database, and used on the bookmarks screen.
- * @param context Context for finding out the density of the screen.
- * @return int desired width for thumbnail screenshot.
- */
- /* package */ static int getDesiredThumbnailWidth(Context context) {
- if (THUMBNAIL_WIDTH == 0) {
- float density = context.getResources().getDisplayMetrics().density;
- THUMBNAIL_WIDTH = (int) (90 * density);
- THUMBNAIL_HEIGHT = (int) (80 * density);
- }
- return THUMBNAIL_WIDTH;
- }
-
- /**
- * Return the desired height for thumbnail screenshots, which are stored in
- * the database, and used on the bookmarks screen.
- * @param context Context for finding out the density of the screen.
- * @return int desired height for thumbnail screenshot.
- */
- /* package */ static int getDesiredThumbnailHeight(Context context) {
- // To ensure that they are both initialized.
- getDesiredThumbnailWidth(context);
- return THUMBNAIL_HEIGHT;
- }
-
- private Bitmap createScreenshot(WebView view) {
- Picture thumbnail = view.capturePicture();
- if (thumbnail == null) {
- return null;
- }
- Bitmap bm = Bitmap.createBitmap(getDesiredThumbnailWidth(this),
- getDesiredThumbnailHeight(this), Bitmap.Config.RGB_565);
- Canvas canvas = new Canvas(bm);
- // May need to tweak these values to determine what is the
- // best scale factor
- int thumbnailWidth = thumbnail.getWidth();
- int thumbnailHeight = thumbnail.getHeight();
- float scaleFactorX = 1.0f;
- float scaleFactorY = 1.0f;
- if (thumbnailWidth > 0) {
- scaleFactorX = (float) getDesiredThumbnailWidth(this) /
- (float)thumbnailWidth;
- } else {
- return null;
- }
-
- if (view.getWidth() > view.getHeight() &&
- thumbnailHeight < view.getHeight() && thumbnailHeight > 0) {
- // If the device is in landscape and the page is shorter
- // than the height of the view, stretch the thumbnail to fill the
- // space.
- scaleFactorY = (float) getDesiredThumbnailHeight(this) /
- (float)thumbnailHeight;
- } else {
- // In the portrait case, this looks nice.
- scaleFactorY = scaleFactorX;
- }
-
- canvas.scale(scaleFactorX, scaleFactorY);
-
- thumbnail.draw(canvas);
- return bm;
- }
-
- // -------------------------------------------------------------------------
- // Helper function for WebViewClient.
- //-------------------------------------------------------------------------
-
- // Use in overrideUrlLoading
- /* package */ final static String SCHEME_WTAI = "wtai://wp/";
- /* package */ final static String SCHEME_WTAI_MC = "wtai://wp/mc;";
- /* package */ final static String SCHEME_WTAI_SD = "wtai://wp/sd;";
- /* package */ final static String SCHEME_WTAI_AP = "wtai://wp/ap;";
-
- // Keep this initial progress in sync with initialProgressValue (* 100)
- // in ProgressTracker.cpp
- private final static int INITIAL_PROGRESS = 10;
-
- void onPageStarted(WebView view, String url, Bitmap favicon) {
- // when BrowserActivity just starts, onPageStarted may be called before
- // onResume as it is triggered from onCreate. Call resumeWebViewTimers
- // to start the timer. As we won't switch tabs while an activity is in
- // pause state, we can ensure calling resume and pause in pair.
- if (mActivityInPause) resumeWebViewTimers();
-
- resetLockIcon(url);
- setUrlTitle(url, null);
- setFavicon(favicon);
- // Show some progress so that the user knows the page is beginning to
- // load
- onProgressChanged(view, INITIAL_PROGRESS);
- mDidStopLoad = false;
- if (!mIsNetworkUp) createAndShowNetworkDialog();
- closeDialogs();
- if (mSettings.isTracing()) {
- String host;
- try {
- WebAddress uri = new WebAddress(url);
- host = uri.mHost;
- } catch (android.net.ParseException ex) {
- host = "browser";
- }
- host = host.replace('.', '_');
- host += ".trace";
- mInTrace = true;
- Debug.startMethodTracing(host, 20 * 1024 * 1024);
- }
-
- // Performance probe
- if (false) {
- mStart = SystemClock.uptimeMillis();
- mProcessStart = Process.getElapsedCpuTime();
- long[] sysCpu = new long[7];
- if (Process.readProcFile("/proc/stat", SYSTEM_CPU_FORMAT, null,
- sysCpu, null)) {
- mUserStart = sysCpu[0] + sysCpu[1];
- mSystemStart = sysCpu[2];
- mIdleStart = sysCpu[3];
- mIrqStart = sysCpu[4] + sysCpu[5] + sysCpu[6];
- }
- mUiStart = SystemClock.currentThreadTimeMillis();
- }
- }
-
- void onPageFinished(WebView view, String url) {
- // Reset the title and icon in case we stopped a provisional load.
- resetTitleAndIcon(view);
- // Update the lock icon image only once we are done loading
- updateLockIconToLatest();
- // pause the WebView timer and release the wake lock if it is finished
- // while BrowserActivity is in pause state.
- if (mActivityInPause && pauseWebViewTimers()) {
- if (mWakeLock.isHeld()) {
- mHandler.removeMessages(RELEASE_WAKELOCK);
- mWakeLock.release();
- }
- }
-
- // Performance probe
- if (false) {
- long[] sysCpu = new long[7];
- if (Process.readProcFile("/proc/stat", SYSTEM_CPU_FORMAT, null,
- sysCpu, null)) {
- String uiInfo = "UI thread used "
- + (SystemClock.currentThreadTimeMillis() - mUiStart)
- + " ms";
- if (LOGD_ENABLED) {
- Log.d(LOGTAG, uiInfo);
- }
- //The string that gets written to the log
- String performanceString = "It took total "
- + (SystemClock.uptimeMillis() - mStart)
- + " ms clock time to load the page."
- + "\nbrowser process used "
- + (Process.getElapsedCpuTime() - mProcessStart)
- + " ms, user processes used "
- + (sysCpu[0] + sysCpu[1] - mUserStart) * 10
- + " ms, kernel used "
- + (sysCpu[2] - mSystemStart) * 10
- + " ms, idle took " + (sysCpu[3] - mIdleStart) * 10
- + " ms and irq took "
- + (sysCpu[4] + sysCpu[5] + sysCpu[6] - mIrqStart)
- * 10 + " ms, " + uiInfo;
- if (LOGD_ENABLED) {
- Log.d(LOGTAG, performanceString + "\nWebpage: " + url);
- }
- if (url != null) {
- // strip the url to maintain consistency
- String newUrl = new String(url);
- if (newUrl.startsWith("http://www.")) {
- newUrl = newUrl.substring(11);
- } else if (newUrl.startsWith("http://")) {
- newUrl = newUrl.substring(7);
- } else if (newUrl.startsWith("https://www.")) {
- newUrl = newUrl.substring(12);
- } else if (newUrl.startsWith("https://")) {
- newUrl = newUrl.substring(8);
- }
- if (LOGD_ENABLED) {
- Log.d(LOGTAG, newUrl + " loaded");
- }
- }
- }
- }
-
- if (mInTrace) {
- mInTrace = false;
- Debug.stopMethodTracing();
- }
- }
-
- boolean shouldOverrideUrlLoading(WebView view, String url) {
- if (url.startsWith(SCHEME_WTAI)) {
- // wtai://wp/mc;number
- // number=string(phone-number)
- if (url.startsWith(SCHEME_WTAI_MC)) {
- Intent intent = new Intent(Intent.ACTION_VIEW,
- Uri.parse(WebView.SCHEME_TEL +
- url.substring(SCHEME_WTAI_MC.length())));
- startActivity(intent);
- return true;
- }
- // wtai://wp/sd;dtmf
- // dtmf=string(dialstring)
- if (url.startsWith(SCHEME_WTAI_SD)) {
- // TODO: only send when there is active voice connection
- return false;
- }
- // wtai://wp/ap;number;name
- // number=string(phone-number)
- // name=string
- if (url.startsWith(SCHEME_WTAI_AP)) {
- // TODO
- return false;
- }
- }
-
- // The "about:" schemes are internal to the browser; don't want these to
- // be dispatched to other apps.
- if (url.startsWith("about:")) {
- return false;
- }
-
- Intent intent;
- // perform generic parsing of the URI to turn it into an Intent.
- try {
- intent = Intent.parseUri(url, Intent.URI_INTENT_SCHEME);
- } catch (URISyntaxException ex) {
- Log.w("Browser", "Bad URI " + url + ": " + ex.getMessage());
- return false;
- }
-
- // check whether the intent can be resolved. If not, we will see
- // whether we can download it from the Market.
- if (getPackageManager().resolveActivity(intent, 0) == null) {
- String packagename = intent.getPackage();
- if (packagename != null) {
- intent = new Intent(Intent.ACTION_VIEW, Uri
- .parse("market://search?q=pname:" + packagename));
- intent.addCategory(Intent.CATEGORY_BROWSABLE);
- startActivity(intent);
- return true;
- } else {
- return false;
- }
- }
-
- // sanitize the Intent, ensuring web pages can not bypass browser
- // security (only access to BROWSABLE activities).
- intent.addCategory(Intent.CATEGORY_BROWSABLE);
- intent.setComponent(null);
- try {
- if (startActivityIfNeeded(intent, -1)) {
- return true;
- }
- } catch (ActivityNotFoundException ex) {
- // ignore the error. If no application can handle the URL,
- // eg about:blank, assume the browser can handle it.
- }
-
- if (mMenuIsDown) {
- openTab(url);
- closeOptionsMenu();
- return true;
- }
- return false;
- }
-
- // -------------------------------------------------------------------------
- // Helper function for WebChromeClient
- // -------------------------------------------------------------------------
-
- void onProgressChanged(WebView view, int newProgress) {
- mFakeTitleBar.setProgress(newProgress);
-
- if (newProgress == 100) {
- // onProgressChanged() may continue to be called after the main
- // frame has finished loading, as any remaining sub frames continue
- // to load. We'll only get called once though with newProgress as
- // 100 when everything is loaded. (onPageFinished is called once
- // when the main frame completes loading regardless of the state of
- // any sub frames so calls to onProgressChanges may continue after
- // onPageFinished has executed)
- if (mInLoad) {
- mInLoad = false;
- updateInLoadMenuItems();
- // If the options menu is open, leave the title bar
- if (!mOptionsMenuOpen || !mIconView) {
- hideFakeTitleBar();
- }
- }
- } else {
- if (!mInLoad) {
- // onPageFinished may have already been called but a subframe is
- // still loading and updating the progress. Reset mInLoad and
- // update the menu items.
- mInLoad = true;
- updateInLoadMenuItems();
- }
- // When the page first begins to load, the Activity may still be
- // paused, in which case showFakeTitleBar will do nothing. Call
- // again as the page continues to load so that it will be shown.
- // (Calling it will the fake title bar is already showing will also
- // do nothing.
- if (!mOptionsMenuOpen || mIconView) {
- // This page has begun to load, so show the title bar
- showFakeTitleBar();
- }
- }
- }
-
- void onShowCustomView(View view, WebChromeClient.CustomViewCallback callback) {
- // if a view already exists then immediately terminate the new one
- if (mCustomView != null) {
- callback.onCustomViewHidden();
- return;
- }
-
- // Add the custom view to its container.
- mCustomViewContainer.addView(view, COVER_SCREEN_GRAVITY_CENTER);
- mCustomView = view;
- mCustomViewCallback = callback;
- // Save the menu state and set it to empty while the custom
- // view is showing.
- mOldMenuState = mMenuState;
- mMenuState = EMPTY_MENU;
- // Hide the content view.
- mContentView.setVisibility(View.GONE);
- // Finally show the custom view container.
- setStatusBarVisibility(false);
- mCustomViewContainer.setVisibility(View.VISIBLE);
- mCustomViewContainer.bringToFront();
- }
-
- void onHideCustomView() {
- if (mCustomView == null)
- return;
- // Hide the custom view.
- mCustomView.setVisibility(View.GONE);
- // Remove the custom view from its container.
- mCustomViewContainer.removeView(mCustomView);
- mCustomView = null;
- // Reset the old menu state.
- mMenuState = mOldMenuState;
- mOldMenuState = EMPTY_MENU;
- mCustomViewContainer.setVisibility(View.GONE);
- mCustomViewCallback.onCustomViewHidden();
- // Show the content view.
- setStatusBarVisibility(true);
- mContentView.setVisibility(View.VISIBLE);
- }
-
- Bitmap getDefaultVideoPoster() {
- if (mDefaultVideoPoster == null) {
- mDefaultVideoPoster = BitmapFactory.decodeResource(
- getResources(), R.drawable.default_video_poster);
- }
- return mDefaultVideoPoster;
- }
-
- View getVideoLoadingProgressView() {
- if (mVideoProgressView == null) {
- LayoutInflater inflater = LayoutInflater.from(BrowserActivity.this);
- mVideoProgressView = inflater.inflate(
- R.layout.video_loading_progress, null);
- }
- return mVideoProgressView;
- }
-
- /*
- * The Object used to inform the WebView of the file to upload.
- */
- private ValueCallback<Uri> mUploadMessage;
-
- void openFileChooser(ValueCallback<Uri> uploadMsg) {
- if (mUploadMessage != null) return;
- mUploadMessage = uploadMsg;
- Intent i = new Intent(Intent.ACTION_GET_CONTENT);
- i.addCategory(Intent.CATEGORY_OPENABLE);
- i.setType("*/*");
- BrowserActivity.this.startActivityForResult(Intent.createChooser(i,
- getString(R.string.choose_upload)), FILE_SELECTED);
- }
-
- // -------------------------------------------------------------------------
- // Implement functions for DownloadListener
- // -------------------------------------------------------------------------
-
- /**
- * Notify the host application a download should be done, or that
- * the data should be streamed if a streaming viewer is available.
- * @param url The full url to the content that should be downloaded
- * @param contentDisposition Content-disposition http header, if
- * present.
- * @param mimetype The mimetype of the content reported by the server
- * @param contentLength The file size reported by the server
- */
- public void onDownloadStart(String url, String userAgent,
- String contentDisposition, String mimetype, long contentLength) {
- // if we're dealing wih A/V content that's not explicitly marked
- // for download, check if it's streamable.
- if (contentDisposition == null
- || !contentDisposition.regionMatches(
- true, 0, "attachment", 0, 10)) {
- // query the package manager to see if there's a registered handler
- // that matches.
- Intent intent = new Intent(Intent.ACTION_VIEW);
- intent.setDataAndType(Uri.parse(url), mimetype);
- ResolveInfo info = getPackageManager().resolveActivity(intent,
- PackageManager.MATCH_DEFAULT_ONLY);
- if (info != null) {
- ComponentName myName = getComponentName();
- // If we resolved to ourselves, we don't want to attempt to
- // load the url only to try and download it again.
- if (!myName.getPackageName().equals(
- info.activityInfo.packageName)
- || !myName.getClassName().equals(
- info.activityInfo.name)) {
- // someone (other than us) knows how to handle this mime
- // type with this scheme, don't download.
- try {
- startActivity(intent);
- return;
- } catch (ActivityNotFoundException ex) {
- if (LOGD_ENABLED) {
- Log.d(LOGTAG, "activity not found for " + mimetype
- + " over " + Uri.parse(url).getScheme(),
- ex);
- }
- // Best behavior is to fall back to a download in this
- // case
- }
- }
- }
- }
- onDownloadStartNoStream(url, userAgent, contentDisposition, mimetype, contentLength);
- }
-
- // This is to work around the fact that java.net.URI throws Exceptions
- // instead of just encoding URL's properly
- // Helper method for onDownloadStartNoStream
- private static String encodePath(String path) {
- char[] chars = path.toCharArray();
-
- boolean needed = false;
- for (char c : chars) {
- if (c == '[' || c == ']') {
- needed = true;
- break;
- }
- }
- if (needed == false) {
- return path;
- }
-
- StringBuilder sb = new StringBuilder("");
- for (char c : chars) {
- if (c == '[' || c == ']') {
- sb.append('%');
- sb.append(Integer.toHexString(c));
- } else {
- sb.append(c);
- }
- }
-
- return sb.toString();
- }
-
- /**
- * Notify the host application a download should be done, even if there
- * is a streaming viewer available for thise type.
- * @param url The full url to the content that should be downloaded
- * @param contentDisposition Content-disposition http header, if
- * present.
- * @param mimetype The mimetype of the content reported by the server
- * @param contentLength The file size reported by the server
- */
- /*package */ void onDownloadStartNoStream(String url, String userAgent,
- String contentDisposition, String mimetype, long contentLength) {
-
- String filename = URLUtil.guessFileName(url,
- contentDisposition, mimetype);
-
- // Check to see if we have an SDCard
- String status = Environment.getExternalStorageState();
- if (!status.equals(Environment.MEDIA_MOUNTED)) {
- int title;
- String msg;
-
- // Check to see if the SDCard is busy, same as the music app
- if (status.equals(Environment.MEDIA_SHARED)) {
- msg = getString(R.string.download_sdcard_busy_dlg_msg);
- title = R.string.download_sdcard_busy_dlg_title;
- } else {
- msg = getString(R.string.download_no_sdcard_dlg_msg, filename);
- title = R.string.download_no_sdcard_dlg_title;
- }
-
- new AlertDialog.Builder(this)
- .setTitle(title)
- .setIcon(android.R.drawable.ic_dialog_alert)
- .setMessage(msg)
- .setPositiveButton(R.string.ok, null)
- .show();
- return;
- }
-
- // java.net.URI is a lot stricter than KURL so we have to encode some
- // extra characters. Fix for b 2538060 and b 1634719
- WebAddress webAddress;
- try {
- webAddress = new WebAddress(url);
- webAddress.mPath = encodePath(webAddress.mPath);
- } catch (Exception e) {
- // This only happens for very bad urls, we want to chatch the
- // exception here
- Log.e(LOGTAG, "Exception trying to parse url:" + url);
- return;
- }
-
- // XXX: Have to use the old url since the cookies were stored using the
- // old percent-encoded url.
- String cookies = CookieManager.getInstance().getCookie(url);
-
- ContentValues values = new ContentValues();
- values.put(Downloads.Impl.COLUMN_URI, webAddress.toString());
- values.put(Downloads.Impl.COLUMN_COOKIE_DATA, cookies);
- values.put(Downloads.Impl.COLUMN_USER_AGENT, userAgent);
- values.put(Downloads.Impl.COLUMN_NOTIFICATION_PACKAGE,
- getPackageName());
- values.put(Downloads.Impl.COLUMN_NOTIFICATION_CLASS,
- OpenDownloadReceiver.class.getCanonicalName());
- values.put(Downloads.Impl.COLUMN_VISIBILITY,
- Downloads.Impl.VISIBILITY_VISIBLE_NOTIFY_COMPLETED);
- values.put(Downloads.Impl.COLUMN_MIME_TYPE, mimetype);
- values.put(Downloads.Impl.COLUMN_FILE_NAME_HINT, filename);
- values.put(Downloads.Impl.COLUMN_DESCRIPTION, webAddress.mHost);
- if (contentLength > 0) {
- values.put(Downloads.Impl.COLUMN_TOTAL_BYTES, contentLength);
- }
- if (mimetype == null) {
- // We must have long pressed on a link or image to download it. We
- // are not sure of the mimetype in this case, so do a head request
- new FetchUrlMimeType(this).execute(values);
- } else {
- final Uri contentUri =
- getContentResolver().insert(Downloads.Impl.CONTENT_URI, values);
- }
- Toast.makeText(this, R.string.download_pending, Toast.LENGTH_SHORT)
- .show();
- }
-
- // -------------------------------------------------------------------------
-
- /**
- * Resets the lock icon. This method is called when we start a new load and
- * know the url to be loaded.
- */
- private void resetLockIcon(String url) {
- // Save the lock-icon state (we revert to it if the load gets cancelled)
- mTabControl.getCurrentTab().resetLockIcon(url);
- updateLockIconImage(LOCK_ICON_UNSECURE);
- }
-
- /**
- * Update the lock icon to correspond to our latest state.
- */
- private void updateLockIconToLatest() {
- updateLockIconImage(mTabControl.getCurrentTab().getLockIconType());
- }
-
- /**
- * Updates the lock-icon image in the title-bar.
- */
- private void updateLockIconImage(int lockIconType) {
- Drawable d = null;
- if (lockIconType == LOCK_ICON_SECURE) {
- d = mSecLockIcon;
- } else if (lockIconType == LOCK_ICON_MIXED) {
- d = mMixLockIcon;
- }
- mTitleBar.setLock(d);
- mFakeTitleBar.setLock(d);
- }
-
- /**
- * Displays a page-info dialog.
- * @param tab The tab to show info about
- * @param fromShowSSLCertificateOnError The flag that indicates whether
- * this dialog was opened from the SSL-certificate-on-error dialog or
- * not. This is important, since we need to know whether to return to
- * the parent dialog or simply dismiss.
- */
- private void showPageInfo(final Tab tab,
- final boolean fromShowSSLCertificateOnError) {
- final LayoutInflater factory = LayoutInflater
- .from(this);
-
- final View pageInfoView = factory.inflate(R.layout.page_info, null);
-
- final WebView view = tab.getWebView();
-
- String url = null;
- String title = null;
-
- if (view == null) {
- url = tab.getUrl();
- title = tab.getTitle();
- } else if (view == mTabControl.getCurrentWebView()) {
- // Use the cached title and url if this is the current WebView
- url = mUrl;
- title = mTitle;
- } else {
- url = view.getUrl();
- title = view.getTitle();
- }
-
- if (url == null) {
- url = "";
- }
- if (title == null) {
- title = "";
- }
-
- ((TextView) pageInfoView.findViewById(R.id.address)).setText(url);
- ((TextView) pageInfoView.findViewById(R.id.title)).setText(title);
-
- mPageInfoView = tab;
- mPageInfoFromShowSSLCertificateOnError = fromShowSSLCertificateOnError;
-
- AlertDialog.Builder alertDialogBuilder =
- new AlertDialog.Builder(this)
- .setTitle(R.string.page_info).setIcon(android.R.drawable.ic_dialog_info)
- .setView(pageInfoView)
- .setPositiveButton(
- R.string.ok,
- new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog,
- int whichButton) {
- mPageInfoDialog = null;
- mPageInfoView = null;
-
- // if we came here from the SSL error dialog
- if (fromShowSSLCertificateOnError) {
- // go back to the SSL error dialog
- showSSLCertificateOnError(
- mSSLCertificateOnErrorView,
- mSSLCertificateOnErrorHandler,
- mSSLCertificateOnErrorError);
- }
- }
- })
- .setOnCancelListener(
- new DialogInterface.OnCancelListener() {
- public void onCancel(DialogInterface dialog) {
- mPageInfoDialog = null;
- mPageInfoView = null;
-
- // if we came here from the SSL error dialog
- if (fromShowSSLCertificateOnError) {
- // go back to the SSL error dialog
- showSSLCertificateOnError(
- mSSLCertificateOnErrorView,
- mSSLCertificateOnErrorHandler,
- mSSLCertificateOnErrorError);
- }
- }
- });
-
- // if we have a main top-level page SSL certificate set or a certificate
- // error
- if (fromShowSSLCertificateOnError ||
- (view != null && view.getCertificate() != null)) {
- // add a 'View Certificate' button
- alertDialogBuilder.setNeutralButton(
- R.string.view_certificate,
- new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog,
- int whichButton) {
- mPageInfoDialog = null;
- mPageInfoView = null;
-
- // if we came here from the SSL error dialog
- if (fromShowSSLCertificateOnError) {
- // go back to the SSL error dialog
- showSSLCertificateOnError(
- mSSLCertificateOnErrorView,
- mSSLCertificateOnErrorHandler,
- mSSLCertificateOnErrorError);
- } else {
- // otherwise, display the top-most certificate from
- // the chain
- if (view.getCertificate() != null) {
- showSSLCertificate(tab);
- }
- }
- }
- });
- }
-
- mPageInfoDialog = alertDialogBuilder.show();
- }
-
- /**
- * Displays the main top-level page SSL certificate dialog
- * (accessible from the Page-Info dialog).
- * @param tab The tab to show certificate for.
- */
- private void showSSLCertificate(final Tab tab) {
- final View certificateView =
- inflateCertificateView(tab.getWebView().getCertificate());
- if (certificateView == null) {
- return;
- }
-
- LayoutInflater factory = LayoutInflater.from(this);
-
- final LinearLayout placeholder =
- (LinearLayout)certificateView.findViewById(R.id.placeholder);
-
- LinearLayout ll = (LinearLayout) factory.inflate(
- R.layout.ssl_success, placeholder);
- ((TextView)ll.findViewById(R.id.success))
- .setText(R.string.ssl_certificate_is_valid);
-
- mSSLCertificateView = tab;
- mSSLCertificateDialog =
- new AlertDialog.Builder(this)
- .setTitle(R.string.ssl_certificate).setIcon(
- R.drawable.ic_dialog_browser_certificate_secure)
- .setView(certificateView)
- .setPositiveButton(R.string.ok,
- new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog,
- int whichButton) {
- mSSLCertificateDialog = null;
- mSSLCertificateView = null;
-
- showPageInfo(tab, false);
- }
- })
- .setOnCancelListener(
- new DialogInterface.OnCancelListener() {
- public void onCancel(DialogInterface dialog) {
- mSSLCertificateDialog = null;
- mSSLCertificateView = null;
-
- showPageInfo(tab, false);
- }
- })
- .show();
- }
-
- /**
- * Displays the SSL error certificate dialog.
- * @param view The target web-view.
- * @param handler The SSL error handler responsible for cancelling the
- * connection that resulted in an SSL error or proceeding per user request.
- * @param error The SSL error object.
- */
- void showSSLCertificateOnError(
- final WebView view, final SslErrorHandler handler, final SslError error) {
-
- final View certificateView =
- inflateCertificateView(error.getCertificate());
- if (certificateView == null) {
- return;
- }
-
- LayoutInflater factory = LayoutInflater.from(this);
-
- final LinearLayout placeholder =
- (LinearLayout)certificateView.findViewById(R.id.placeholder);
-
- if (error.hasError(SslError.SSL_UNTRUSTED)) {
- LinearLayout ll = (LinearLayout)factory
- .inflate(R.layout.ssl_warning, placeholder);
- ((TextView)ll.findViewById(R.id.warning))
- .setText(R.string.ssl_untrusted);
- }
-
- if (error.hasError(SslError.SSL_IDMISMATCH)) {
- LinearLayout ll = (LinearLayout)factory
- .inflate(R.layout.ssl_warning, placeholder);
- ((TextView)ll.findViewById(R.id.warning))
- .setText(R.string.ssl_mismatch);
- }
-
- if (error.hasError(SslError.SSL_EXPIRED)) {
- LinearLayout ll = (LinearLayout)factory
- .inflate(R.layout.ssl_warning, placeholder);
- ((TextView)ll.findViewById(R.id.warning))
- .setText(R.string.ssl_expired);
- }
-
- if (error.hasError(SslError.SSL_NOTYETVALID)) {
- LinearLayout ll = (LinearLayout)factory
- .inflate(R.layout.ssl_warning, placeholder);
- ((TextView)ll.findViewById(R.id.warning))
- .setText(R.string.ssl_not_yet_valid);
- }
-
- mSSLCertificateOnErrorHandler = handler;
- mSSLCertificateOnErrorView = view;
- mSSLCertificateOnErrorError = error;
- mSSLCertificateOnErrorDialog =
- new AlertDialog.Builder(this)
- .setTitle(R.string.ssl_certificate).setIcon(
- R.drawable.ic_dialog_browser_certificate_partially_secure)
- .setView(certificateView)
- .setPositiveButton(R.string.ok,
- new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog,
- int whichButton) {
- mSSLCertificateOnErrorDialog = null;
- mSSLCertificateOnErrorView = null;
- mSSLCertificateOnErrorHandler = null;
- mSSLCertificateOnErrorError = null;
-
- view.getWebViewClient().onReceivedSslError(
- view, handler, error);
- }
- })
- .setNeutralButton(R.string.page_info_view,
- new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog,
- int whichButton) {
- mSSLCertificateOnErrorDialog = null;
-
- // do not clear the dialog state: we will
- // need to show the dialog again once the
- // user is done exploring the page-info details
-
- showPageInfo(mTabControl.getTabFromView(view),
- true);
- }
- })
- .setOnCancelListener(
- new DialogInterface.OnCancelListener() {
- public void onCancel(DialogInterface dialog) {
- mSSLCertificateOnErrorDialog = null;
- mSSLCertificateOnErrorView = null;
- mSSLCertificateOnErrorHandler = null;
- mSSLCertificateOnErrorError = null;
-
- view.getWebViewClient().onReceivedSslError(
- view, handler, error);
- }
- })
- .show();
- }
-
- /**
- * Inflates the SSL certificate view (helper method).
- * @param certificate The SSL certificate.
- * @return The resultant certificate view with issued-to, issued-by,
- * issued-on, expires-on, and possibly other fields set.
- * If the input certificate is null, returns null.
- */
- private View inflateCertificateView(SslCertificate certificate) {
- if (certificate == null) {
- return null;
- }
-
- LayoutInflater factory = LayoutInflater.from(this);
-
- View certificateView = factory.inflate(
- R.layout.ssl_certificate, null);
-
- // issued to:
- SslCertificate.DName issuedTo = certificate.getIssuedTo();
- if (issuedTo != null) {
- ((TextView) certificateView.findViewById(R.id.to_common))
- .setText(issuedTo.getCName());
- ((TextView) certificateView.findViewById(R.id.to_org))
- .setText(issuedTo.getOName());
- ((TextView) certificateView.findViewById(R.id.to_org_unit))
- .setText(issuedTo.getUName());
- }
-
- // issued by:
- SslCertificate.DName issuedBy = certificate.getIssuedBy();
- if (issuedBy != null) {
- ((TextView) certificateView.findViewById(R.id.by_common))
- .setText(issuedBy.getCName());
- ((TextView) certificateView.findViewById(R.id.by_org))
- .setText(issuedBy.getOName());
- ((TextView) certificateView.findViewById(R.id.by_org_unit))
- .setText(issuedBy.getUName());
- }
-
- // issued on:
- String issuedOn = formatCertificateDate(
- certificate.getValidNotBeforeDate());
- ((TextView) certificateView.findViewById(R.id.issued_on))
- .setText(issuedOn);
-
- // expires on:
- String expiresOn = formatCertificateDate(
- certificate.getValidNotAfterDate());
- ((TextView) certificateView.findViewById(R.id.expires_on))
- .setText(expiresOn);
-
- return certificateView;
- }
-
- /**
- * Formats the certificate date to a properly localized date string.
- * @return Properly localized version of the certificate date string and
- * the "" if it fails to localize.
- */
- private String formatCertificateDate(Date certificateDate) {
- if (certificateDate == null) {
- return "";
- }
- String formattedDate = DateFormat.getDateFormat(this).format(certificateDate);
- if (formattedDate == null) {
- return "";
- }
- return formattedDate;
- }
-
- /**
- * Displays an http-authentication dialog.
- */
- void showHttpAuthentication(final HttpAuthHandler handler,
- final String host, final String realm, final String title,
- final String name, final String password, int focusId) {
- LayoutInflater factory = LayoutInflater.from(this);
- final View v = factory
- .inflate(R.layout.http_authentication, null);
- if (name != null) {
- ((EditText) v.findViewById(R.id.username_edit)).setText(name);
- }
- if (password != null) {
- ((EditText) v.findViewById(R.id.password_edit)).setText(password);
- }
-
- String titleText = title;
- if (titleText == null) {
- titleText = getText(R.string.sign_in_to).toString().replace(
- "%s1", host).replace("%s2", realm);
- }
-
- mHttpAuthHandler = handler;
- AlertDialog dialog = new AlertDialog.Builder(this)
- .setTitle(titleText)
- .setIcon(android.R.drawable.ic_dialog_alert)
- .setView(v)
- .setPositiveButton(R.string.action,
- new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog,
- int whichButton) {
- String nm = ((EditText) v
- .findViewById(R.id.username_edit))
- .getText().toString();
- String pw = ((EditText) v
- .findViewById(R.id.password_edit))
- .getText().toString();
- BrowserActivity.this.setHttpAuthUsernamePassword
- (host, realm, nm, pw);
- handler.proceed(nm, pw);
- mHttpAuthenticationDialog = null;
- mHttpAuthHandler = null;
- }})
- .setNegativeButton(R.string.cancel,
- new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog,
- int whichButton) {
- handler.cancel();
- BrowserActivity.this.resetTitleAndRevertLockIcon();
- mHttpAuthenticationDialog = null;
- mHttpAuthHandler = null;
- }})
- .setOnCancelListener(new DialogInterface.OnCancelListener() {
- public void onCancel(DialogInterface dialog) {
- handler.cancel();
- BrowserActivity.this.resetTitleAndRevertLockIcon();
- mHttpAuthenticationDialog = null;
- mHttpAuthHandler = null;
- }})
- .create();
- // Make the IME appear when the dialog is displayed if applicable.
- dialog.getWindow().setSoftInputMode(
- WindowManager.LayoutParams.SOFT_INPUT_STATE_VISIBLE);
- dialog.show();
- if (focusId != 0) {
- dialog.findViewById(focusId).requestFocus();
- } else {
- v.findViewById(R.id.username_edit).requestFocus();
- }
- mHttpAuthenticationDialog = dialog;
- }
-
- public int getProgress() {
- WebView w = mTabControl.getCurrentWebView();
- if (w != null) {
- return w.getProgress();
- } else {
- return 100;
- }
- }
-
- /**
- * Set HTTP authentication password.
- *
- * @param host The host for the password
- * @param realm The realm for the password
- * @param username The username for the password. If it is null, it means
- * password can't be saved.
- * @param password The password
- */
- public void setHttpAuthUsernamePassword(String host, String realm,
- String username,
- String password) {
- WebView w = getTopWindow();
- if (w != null) {
- w.setHttpAuthUsernamePassword(host, realm, username, password);
- }
- }
-
- /**
- * connectivity manager says net has come or gone... inform the user
- * @param up true if net has come up, false if net has gone down
- */
- public void onNetworkToggle(boolean up) {
- if (up == mIsNetworkUp) {
- return;
- } else if (up) {
- mIsNetworkUp = true;
- if (mAlertDialog != null) {
- mAlertDialog.cancel();
- mAlertDialog = null;
- }
- } else {
- mIsNetworkUp = false;
- if (mInLoad) {
- createAndShowNetworkDialog();
- }
- }
- WebView w = mTabControl.getCurrentWebView();
- if (w != null) {
- w.setNetworkAvailable(up);
- }
- }
-
- boolean isNetworkUp() {
- return mIsNetworkUp;
- }
-
- // This method shows the network dialog alerting the user that the net is
- // down. It will only show the dialog if mAlertDialog is null.
- private void createAndShowNetworkDialog() {
- if (mAlertDialog == null) {
- mAlertDialog = new AlertDialog.Builder(this)
- .setTitle(R.string.loadSuspendedTitle)
- .setMessage(R.string.loadSuspended)
- .setPositiveButton(R.string.ok, null)
- .show();
- }
+ @Override
+ public void onActionModeFinished(ActionMode mode) {
+ super.onActionModeFinished(mode);
+ mController.onActionModeFinished(mode);
}
@Override
protected void onActivityResult(int requestCode, int resultCode,
- Intent intent) {
- if (getTopWindow() == null) return;
-
- switch (requestCode) {
- case COMBO_PAGE:
- if (resultCode == RESULT_OK && intent != null) {
- String data = intent.getAction();
- Bundle extras = intent.getExtras();
- if (extras != null && extras.getBoolean("new_window", false)) {
- openTab(data);
- } else {
- final Tab currentTab =
- mTabControl.getCurrentTab();
- dismissSubWindow(currentTab);
- if (data != null && data.length() != 0) {
- loadUrl(getTopWindow(), data);
- }
- }
- }
- // Deliberately fall through to PREFERENCES_PAGE, since the
- // same extra may be attached to the COMBO_PAGE
- case PREFERENCES_PAGE:
- if (resultCode == RESULT_OK && intent != null) {
- String action = intent.getStringExtra(Intent.EXTRA_TEXT);
- if (BrowserSettings.PREF_CLEAR_HISTORY.equals(action)) {
- mTabControl.removeParentChildRelationShips();
- }
- }
- break;
- // Choose a file from the file picker.
- case FILE_SELECTED:
- if (null == mUploadMessage) break;
- Uri result = intent == null || resultCode != RESULT_OK ? null
- : intent.getData();
- mUploadMessage.onReceiveValue(result);
- mUploadMessage = null;
- break;
- default:
- break;
- }
- getTopWindow().requestFocus();
- }
-
- /*
- * This method is called as a result of the user selecting the options
- * menu to see the download window. It shows the download window on top of
- * the current window.
- */
- private void viewDownloads() {
- Intent intent = new Intent(DownloadManager.ACTION_VIEW_DOWNLOADS);
- startActivity(intent);
- }
-
- /**
- * Open the Go page.
- * @param startWithHistory If true, open starting on the history tab.
- * Otherwise, start with the bookmarks tab.
- */
- /* package */ void bookmarksOrHistoryPicker(boolean startWithHistory) {
- WebView current = mTabControl.getCurrentWebView();
- if (current == null) {
- return;
- }
- Intent intent = new Intent(this,
- CombinedBookmarkHistoryActivity.class);
- String title = current.getTitle();
- String url = current.getUrl();
- Bitmap thumbnail = createScreenshot(current);
-
- // Just in case the user opens bookmarks before a page finishes loading
- // so the current history item, and therefore the page, is null.
- if (null == url) {
- url = mLastEnteredUrl;
- // This can happen.
- if (null == url) {
- url = mSettings.getHomePage();
- }
- }
- // In case the web page has not yet received its associated title.
- if (title == null) {
- title = url;
- }
- intent.putExtra("title", title);
- intent.putExtra("url", url);
- intent.putExtra("thumbnail", thumbnail);
- // Disable opening in a new window if we have maxed out the windows
- intent.putExtra("disable_new_window", !mTabControl.canCreateNewTab());
- intent.putExtra("touch_icon_url", current.getTouchIconUrl());
- if (startWithHistory) {
- intent.putExtra(CombinedBookmarkHistoryActivity.STARTING_TAB,
- CombinedBookmarkHistoryActivity.HISTORY_TAB);
- }
- startActivityForResult(intent, COMBO_PAGE);
- }
-
- // Called when loading from context menu or LOAD_URL message
- private void loadUrlFromContext(WebView view, String url) {
- // In case the user enters nothing.
- if (url != null && url.length() != 0 && view != null) {
- url = smartUrlFilter(url);
- if (!view.getWebViewClient().shouldOverrideUrlLoading(view, url)) {
- loadUrl(view, url);
- }
- }
- }
-
- /**
- * Load the URL into the given WebView and update the title bar
- * to reflect the new load. Call this instead of WebView.loadUrl
- * directly.
- * @param view The WebView used to load url.
- * @param url The URL to load.
- */
- private void loadUrl(WebView view, String url) {
- updateTitleBarForNewLoad(view, url);
- view.loadUrl(url);
- }
-
- /**
- * Load UrlData into a Tab and update the title bar to reflect the new
- * load. Call this instead of UrlData.loadIn directly.
- * @param t The Tab used to load.
- * @param data The UrlData being loaded.
- */
- private void loadUrlDataIn(Tab t, UrlData data) {
- updateTitleBarForNewLoad(t.getWebView(), data.mUrl);
- data.loadIn(t);
- }
-
- /**
- * If the WebView is the top window, update the title bar to reflect
- * loading the new URL. i.e. set its text, clear the favicon (which
- * will be set once the page begins loading), and set the progress to
- * INITIAL_PROGRESS to show that the page has begun to load. Called
- * by loadUrl and loadUrlDataIn.
- * @param view The WebView that is starting a load.
- * @param url The URL that is being loaded.
- */
- private void updateTitleBarForNewLoad(WebView view, String url) {
- if (view == getTopWindow()) {
- setUrlTitle(url, null);
- setFavicon(null);
- onProgressChanged(view, INITIAL_PROGRESS);
- }
- }
-
- private String smartUrlFilter(Uri inUri) {
- if (inUri != null) {
- return smartUrlFilter(inUri.toString());
- }
- return null;
- }
-
- protected static final Pattern ACCEPTED_URI_SCHEMA = Pattern.compile(
- "(?i)" + // switch on case insensitive matching
- "(" + // begin group for schema
- "(?:http|https|file):\\/\\/" +
- "|(?:inline|data|about|content|javascript):" +
- ")" +
- "(.*)" );
-
- /**
- * Attempts to determine whether user input is a URL or search
- * terms. Anything with a space is passed to search.
- *
- * Converts to lowercase any mistakenly uppercased schema (i.e.,
- * "Http://" converts to "http://"
- *
- * @return Original or modified URL
- *
- */
- String smartUrlFilter(String url) {
-
- String inUrl = url.trim();
- boolean hasSpace = inUrl.indexOf(' ') != -1;
-
- Matcher matcher = ACCEPTED_URI_SCHEMA.matcher(inUrl);
- if (matcher.matches()) {
- // force scheme to lowercase
- String scheme = matcher.group(1);
- String lcScheme = scheme.toLowerCase();
- if (!lcScheme.equals(scheme)) {
- inUrl = lcScheme + matcher.group(2);
- }
- if (hasSpace) {
- inUrl = inUrl.replace(" ", "%20");
- }
- return inUrl;
- }
- if (!hasSpace) {
- if (Patterns.WEB_URL.matcher(inUrl).matches()) {
- return URLUtil.guessUrl(inUrl);
- }
- }
-
- // FIXME: Is this the correct place to add to searches?
- // what if someone else calls this function?
-
- Browser.addSearchUrl(mResolver, inUrl);
- return URLUtil.composeSearchUrl(inUrl, QuickSearch_G, QUERY_PLACE_HOLDER);
- }
-
- /* package */ void setShouldShowErrorConsole(boolean flag) {
- if (flag == mShouldShowErrorConsole) {
- // Nothing to do.
- return;
- }
- Tab t = mTabControl.getCurrentTab();
- if (t == null) {
- // There is no current tab so we cannot toggle the error console
- return;
- }
-
- mShouldShowErrorConsole = flag;
-
- ErrorConsoleView errorConsole = t.getErrorConsole(true);
-
- if (flag) {
- // Setting the show state of the console will cause it's the layout to be inflated.
- if (errorConsole.numberOfErrors() > 0) {
- errorConsole.showConsole(ErrorConsoleView.SHOW_MINIMIZED);
- } else {
- errorConsole.showConsole(ErrorConsoleView.SHOW_NONE);
- }
-
- // Now we can add it to the main view.
- mErrorConsoleContainer.addView(errorConsole,
- new LinearLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT,
- ViewGroup.LayoutParams.WRAP_CONTENT));
- } else {
- mErrorConsoleContainer.removeView(errorConsole);
- }
-
- }
-
- boolean shouldShowErrorConsole() {
- return mShouldShowErrorConsole;
- }
-
- private void setStatusBarVisibility(boolean visible) {
- int flag = visible ? 0 : WindowManager.LayoutParams.FLAG_FULLSCREEN;
- getWindow().setFlags(flag, WindowManager.LayoutParams.FLAG_FULLSCREEN);
+ Intent intent) {
+ mController.onActivityResult(requestCode, resultCode, intent);
}
- private void sendNetworkType(String type, String subtype) {
- WebView w = mTabControl.getCurrentWebView();
- if (w != null) {
- w.setNetworkType(type, subtype);
- }
- }
-
- private void packageChanged(String packageName, boolean wasAdded) {
- WebView w = mTabControl.getCurrentWebView();
- if (w == null) {
- return;
- }
-
- if (wasAdded) {
- w.addPackageName(packageName);
- } else {
- w.removePackageName(packageName);
- }
- }
-
- private void addPackageNames(Set<String> packageNames) {
- WebView w = mTabControl.getCurrentWebView();
- if (w == null) {
- return;
- }
-
- w.addPackageNames(packageNames);
- }
-
- private void getInstalledPackages() {
- AsyncTask<Void, Void, Set<String> > task =
- new AsyncTask<Void, Void, Set<String> >() {
- protected Set<String> doInBackground(Void... unused) {
- Set<String> installedPackages = new HashSet<String>();
- PackageManager pm = BrowserActivity.this.getPackageManager();
- if (pm != null) {
- List<PackageInfo> packages = pm.getInstalledPackages(0);
- for (PackageInfo p : packages) {
- if (BrowserActivity.this.sGoogleApps.contains(p.packageName)) {
- installedPackages.add(p.packageName);
- }
- }
- }
-
- return installedPackages;
- }
-
- // Executes on the UI thread
- protected void onPostExecute(Set<String> installedPackages) {
- addPackageNames(installedPackages);
- }
- };
- task.execute();
- }
-
- final static int LOCK_ICON_UNSECURE = 0;
- final static int LOCK_ICON_SECURE = 1;
- final static int LOCK_ICON_MIXED = 2;
-
- private BrowserSettings mSettings;
- private TabControl mTabControl;
- private ContentResolver mResolver;
- private FrameLayout mContentView;
- private View mCustomView;
- private FrameLayout mCustomViewContainer;
- private WebChromeClient.CustomViewCallback mCustomViewCallback;
-
- // FIXME, temp address onPrepareMenu performance problem. When we move everything out of
- // view, we should rewrite this.
- private int mCurrentMenuState = 0;
- private int mMenuState = R.id.MAIN_MENU;
- private int mOldMenuState = EMPTY_MENU;
- private static final int EMPTY_MENU = -1;
- private Menu mMenu;
-
- private FindDialog mFindDialog;
- private SelectDialog mSelectDialog;
- // Used to prevent chording to result in firing two shortcuts immediately
- // one after another. Fixes bug 1211714.
- boolean mCanChord;
-
- private boolean mInLoad;
- private boolean mIsNetworkUp;
- private boolean mDidStopLoad;
-
- /* package */ boolean mActivityInPause = true;
-
- private boolean mMenuIsDown;
-
- private static boolean mInTrace;
-
- // Performance probe
- private static final int[] SYSTEM_CPU_FORMAT = new int[] {
- Process.PROC_SPACE_TERM | Process.PROC_COMBINE,
- Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG, // 1: user time
- Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG, // 2: nice time
- Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG, // 3: sys time
- Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG, // 4: idle time
- Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG, // 5: iowait time
- Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG, // 6: irq time
- Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG // 7: softirq time
- };
-
- private long mStart;
- private long mProcessStart;
- private long mUserStart;
- private long mSystemStart;
- private long mIdleStart;
- private long mIrqStart;
-
- private long mUiStart;
-
- private Drawable mMixLockIcon;
- private Drawable mSecLockIcon;
-
- /* hold a ref so we can auto-cancel if necessary */
- private AlertDialog mAlertDialog;
-
- // The up-to-date URL and title (these can be different from those stored
- // in WebView, since it takes some time for the information in WebView to
- // get updated)
- private String mUrl;
- private String mTitle;
-
- // As PageInfo has different style for landscape / portrait, we have
- // to re-open it when configuration changed
- private AlertDialog mPageInfoDialog;
- private Tab mPageInfoView;
- // If the Page-Info dialog is launched from the SSL-certificate-on-error
- // dialog, we should not just dismiss it, but should get back to the
- // SSL-certificate-on-error dialog. This flag is used to store this state
- private boolean mPageInfoFromShowSSLCertificateOnError;
-
- // as SSLCertificateOnError has different style for landscape / portrait,
- // we have to re-open it when configuration changed
- private AlertDialog mSSLCertificateOnErrorDialog;
- private WebView mSSLCertificateOnErrorView;
- private SslErrorHandler mSSLCertificateOnErrorHandler;
- private SslError mSSLCertificateOnErrorError;
-
- // as SSLCertificate has different style for landscape / portrait, we
- // have to re-open it when configuration changed
- private AlertDialog mSSLCertificateDialog;
- private Tab mSSLCertificateView;
-
- // as HttpAuthentication has different style for landscape / portrait, we
- // have to re-open it when configuration changed
- private AlertDialog mHttpAuthenticationDialog;
- private HttpAuthHandler mHttpAuthHandler;
-
- /*package*/ static final FrameLayout.LayoutParams COVER_SCREEN_PARAMS =
- new FrameLayout.LayoutParams(
- ViewGroup.LayoutParams.MATCH_PARENT,
- ViewGroup.LayoutParams.MATCH_PARENT);
- /*package*/ static final FrameLayout.LayoutParams COVER_SCREEN_GRAVITY_CENTER =
- new FrameLayout.LayoutParams(
- ViewGroup.LayoutParams.MATCH_PARENT,
- ViewGroup.LayoutParams.MATCH_PARENT,
- Gravity.CENTER);
- // Google search
- final static String QuickSearch_G = "http://www.google.com/m?q=%s";
-
- final static String QUERY_PLACE_HOLDER = "%s";
-
- // "source" parameter for Google search through search key
- final static String GOOGLE_SEARCH_SOURCE_SEARCHKEY = "browser-key";
- // "source" parameter for Google search through goto menu
- final static String GOOGLE_SEARCH_SOURCE_GOTO = "browser-goto";
- // "source" parameter for Google search through simplily type
- final static String GOOGLE_SEARCH_SOURCE_TYPE = "browser-type";
- // "source" parameter for Google search suggested by the browser
- final static String GOOGLE_SEARCH_SOURCE_SUGGEST = "browser-suggest";
- // "source" parameter for Google search from unknown source
- final static String GOOGLE_SEARCH_SOURCE_UNKNOWN = "unknown";
-
- private final static String LOGTAG = "browser";
-
- private String mLastEnteredUrl;
-
- private PowerManager.WakeLock mWakeLock;
- private final static int WAKELOCK_TIMEOUT = 5 * 60 * 1000; // 5 minutes
-
- private Toast mStopToast;
-
- private TitleBar mTitleBar;
-
- private LinearLayout mErrorConsoleContainer = null;
- private boolean mShouldShowErrorConsole = false;
-
- // As the ids are dynamically created, we can't guarantee that they will
- // be in sequence, so this static array maps ids to a window number.
- final static private int[] WINDOW_SHORTCUT_ID_ARRAY =
- { R.id.window_one_menu_id, R.id.window_two_menu_id, R.id.window_three_menu_id,
- R.id.window_four_menu_id, R.id.window_five_menu_id, R.id.window_six_menu_id,
- R.id.window_seven_menu_id, R.id.window_eight_menu_id };
-
- // monitor platform changes
- private IntentFilter mNetworkStateChangedFilter;
- private BroadcastReceiver mNetworkStateIntentReceiver;
-
- private BroadcastReceiver mPackageInstallationReceiver;
-
- private SystemAllowGeolocationOrigins mSystemAllowGeolocationOrigins;
-
- // activity requestCode
- final static int COMBO_PAGE = 1;
- final static int PREFERENCES_PAGE = 3;
- final static int FILE_SELECTED = 4;
-
- // the default <video> poster
- private Bitmap mDefaultVideoPoster;
- // the video progress view
- private View mVideoProgressView;
-
- // The Google packages we monitor for the navigator.isApplicationInstalled()
- // API. Add as needed.
- private static Set<String> sGoogleApps;
- static {
- sGoogleApps = new HashSet<String>();
- sGoogleApps.add("com.google.android.youtube");
- }
-
- /**
- * A UrlData class to abstract how the content will be set to WebView.
- * This base class uses loadUrl to show the content.
- */
- /* package */ static class UrlData {
- final String mUrl;
- final Map<String, String> mHeaders;
- final Intent mVoiceIntent;
-
- UrlData(String url) {
- this.mUrl = url;
- this.mHeaders = null;
- this.mVoiceIntent = null;
- }
-
- UrlData(String url, Map<String, String> headers, Intent intent) {
- this.mUrl = url;
- this.mHeaders = headers;
- if (RecognizerResultsIntent.ACTION_VOICE_SEARCH_RESULTS
- .equals(intent.getAction())) {
- this.mVoiceIntent = intent;
- } else {
- this.mVoiceIntent = null;
- }
- }
-
- boolean isEmpty() {
- return mVoiceIntent == null && (mUrl == null || mUrl.length() == 0);
- }
-
- /**
- * Load this UrlData into the given Tab. Use loadUrlDataIn to update
- * the title bar as well.
- */
- public void loadIn(Tab t) {
- if (mVoiceIntent != null) {
- t.activateVoiceSearchMode(mVoiceIntent);
- } else {
- t.getWebView().loadUrl(mUrl, mHeaders);
- }
- }
- };
-
- /* package */ static final UrlData EMPTY_URL_DATA = new UrlData(null);
}
diff --git a/src/com/android/browser/BrowserBackupAgent.java b/src/com/android/browser/BrowserBackupAgent.java
index c968ce5..2950474 100644
--- a/src/com/android/browser/BrowserBackupAgent.java
+++ b/src/com/android/browser/BrowserBackupAgent.java
@@ -16,24 +16,23 @@
package com.android.browser;
-import java.io.IOException;
-
import android.app.backup.BackupAgent;
import android.app.backup.BackupDataInput;
import android.app.backup.BackupDataOutput;
+import android.content.ContentValues;
import android.database.Cursor;
import android.os.ParcelFileDescriptor;
-import android.provider.Browser;
-import android.provider.Browser.BookmarkColumns;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Bookmarks;
import android.util.Log;
-import java.io.ByteArrayOutputStream;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.EOFException;
import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
+import java.io.IOException;
import java.util.ArrayList;
import java.util.zip.CRC32;
@@ -54,19 +53,8 @@
static final int BACKUP_AGENT_VERSION = 0;
/**
- * In order to determine whether the bookmark set has changed since the
- * last time we did a backup, we store the following bits of info in the
- * state file after a backup:
- *
- * 1. the size of the flattened bookmark file
- * 2. the CRC32 of that file
- * 3. the agent version number [relevant following an OTA]
- *
- * After we flatten the bookmarks file here in onBackup, we compare its
- * metrics with the values from the saved state. If they match, it means
- * the bookmarks didn't really change and we don't need to send the data.
- * (If they don't match, of course, then they've changed and we do indeed
- * send the new flattened file to be backed up.)
+ * This simply preserves the existing state as we now prefer Chrome Sync
+ * to handle bookmark backup.
*/
@Override
public void onBackup(ParcelFileDescriptor oldState, BackupDataOutput data,
@@ -84,33 +72,14 @@
savedVersion = in.readInt();
} catch (EOFException e) {
// It means we had no previous state; that's fine
+ return;
} finally {
if (in != null) {
in.close();
}
}
-
- // Build a flattened representation of the bookmarks table
- File tmpfile = File.createTempFile("bkp", null, getCacheDir());
- try {
- FileOutputStream outfstream = new FileOutputStream(tmpfile);
- long newCrc = buildBookmarkFile(outfstream);
- outfstream.close();
-
- // Any changes since the last backup?
- if ((savedVersion != BACKUP_AGENT_VERSION)
- || (newCrc != savedCrc)
- || (tmpfile.length() != savedFileSize)) {
- // Different checksum or different size, so we need to back it up
- copyFileToBackup(BOOKMARK_KEY, tmpfile, data);
- }
-
- // Record our backup state and we're done
- writeBackupState(tmpfile.length(), newCrc, newState);
- } finally {
- // Make sure to tidy up when we're done
- tmpfile.delete();
- }
+ // Write the existing state
+ writeBackupState(savedFileSize, savedCrc, newState);
}
/**
@@ -153,21 +122,19 @@
int N = bookmarks.size();
int nUnique = 0;
if (DEBUG) Log.v(TAG, "Restoring " + N + " bookmarks");
- String[] urlCol = new String[] { BookmarkColumns.URL };
+ String[] urlCol = new String[] { Bookmarks.URL };
for (int i = 0; i < N; i++) {
Bookmark mark = bookmarks.get(i);
// Does this URL exist in the bookmark table?
- Cursor cursor = getContentResolver().query(Browser.BOOKMARKS_URI,
- urlCol, BookmarkColumns.URL + " == '" + mark.url + "' AND " +
- BookmarkColumns.BOOKMARK + " == 1 ", null, null);
+ Cursor cursor = getContentResolver().query(
+ Bookmarks.CONTENT_URI, urlCol,
+ Bookmarks.URL + " == ?",
+ new String[] { mark.url }, null);
// if not, insert it
if (cursor.getCount() <= 0) {
if (DEBUG) Log.v(TAG, "Did not see url: " + mark.url);
- // Right now we do not reconstruct the db entry in its
- // entirety; we just add a new bookmark with the same data
- Bookmarks.addBookmark(null, getContentResolver(),
- mark.url, mark.title, null, false);
+ addBookmark(mark);
nUnique++;
} else {
if (DEBUG) Log.v(TAG, "Skipping extant url: " + mark.url);
@@ -195,6 +162,16 @@
}
}
+ void addBookmark(Bookmark mark) {
+ ContentValues values = new ContentValues();
+ values.put(Bookmarks.TITLE, mark.title);
+ values.put(Bookmarks.URL, mark.url);
+ values.put(Bookmarks.IS_FOLDER, 0);
+ values.put(Bookmarks.DATE_CREATED, mark.created);
+ values.put(Bookmarks.DATE_MODIFIED, mark.date);
+ getContentResolver().insert(Bookmarks.CONTENT_URI, values);
+ }
+
static class Bookmark {
public String url;
public int visits;
@@ -206,80 +183,6 @@
* Utility functions
*/
- // Flatten the bookmarks table into the given file, calculating its CRC in the process
- private long buildBookmarkFile(FileOutputStream outfstream) throws IOException {
- CRC32 crc = new CRC32();
- ByteArrayOutputStream bufstream = new ByteArrayOutputStream(512);
- DataOutputStream bout = new DataOutputStream(bufstream);
-
- Cursor cursor = getContentResolver().query(Browser.BOOKMARKS_URI,
- new String[] { BookmarkColumns.URL, BookmarkColumns.VISITS,
- BookmarkColumns.DATE, BookmarkColumns.CREATED,
- BookmarkColumns.TITLE },
- BookmarkColumns.BOOKMARK + " == 1 ", null, null);
-
- // The first thing in the file is the row count...
- int count = cursor.getCount();
- if (DEBUG) Log.v(TAG, "Backing up " + count + " bookmarks");
- bout.writeInt(count);
- byte[] record = bufstream.toByteArray();
- crc.update(record);
- outfstream.write(record);
-
- // ... followed by the data for each row
- for (int i = 0; i < count; i++) {
- cursor.moveToNext();
-
- String url = cursor.getString(0);
- int visits = cursor.getInt(1);
- long date = cursor.getLong(2);
- long created = cursor.getLong(3);
- String title = cursor.getString(4);
-
- // construct the flattened record in a byte array
- bufstream.reset();
- bout.writeUTF(url);
- bout.writeInt(visits);
- bout.writeLong(date);
- bout.writeLong(created);
- bout.writeUTF(title);
-
- // Update the CRC and write the record to the temp file
- record = bufstream.toByteArray();
- crc.update(record);
- outfstream.write(record);
-
- if (DEBUG) Log.v(TAG, " wrote url " + url);
- }
-
- cursor.close();
- return crc.getValue();
- }
-
- // Write the file to backup as a single record under the given key
- private void copyFileToBackup(String key, File file, BackupDataOutput data)
- throws IOException {
- final int CHUNK = 8192;
- byte[] buf = new byte[CHUNK];
-
- int toCopy = (int) file.length();
- data.writeEntityHeader(key, toCopy);
-
- FileInputStream in = new FileInputStream(file);
- try {
- int nRead;
- while (toCopy > 0) {
- nRead = in.read(buf, 0, CHUNK);
- data.writeEntityData(buf, nRead);
- toCopy -= nRead;
- }
- } finally {
- if (in != null) {
- in.close();
- }
- }
- }
-
// Read the given file from backup to a file, calculating a CRC32 along the way
private long copyBackupToFile(BackupDataInput data, File file, int toRead)
throws IOException {
diff --git a/src/com/android/browser/BrowserBookmarksAdapter.java b/src/com/android/browser/BrowserBookmarksAdapter.java
index 241b33b..9e71077 100644
--- a/src/com/android/browser/BrowserBookmarksAdapter.java
+++ b/src/com/android/browser/BrowserBookmarksAdapter.java
@@ -16,567 +16,116 @@
package com.android.browser;
-import android.content.ContentResolver;
-import android.content.ContentUris;
-import android.content.ContentValues;
-import android.database.ContentObserver;
+import android.content.Context;
import android.database.Cursor;
-import android.database.DataSetObserver;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
-import android.net.Uri;
-import android.os.AsyncTask;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.Looper;
-import android.provider.Browser;
-import android.provider.Browser.BookmarkColumns;
-import android.view.KeyEvent;
+import android.graphics.drawable.Drawable;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
-import android.webkit.WebIconDatabase;
-import android.webkit.WebView;
-import android.widget.BaseAdapter;
+import android.widget.CursorAdapter;
import android.widget.ImageView;
import android.widget.TextView;
-import java.io.ByteArrayOutputStream;
-
-class BrowserBookmarksAdapter extends BaseAdapter {
-
- private String mCurrentPage;
- private String mCurrentTitle;
- private Bitmap mCurrentThumbnail;
- private Cursor mCursor;
- private int mCount;
- private BrowserBookmarksPage mBookmarksPage;
- private ContentResolver mContentResolver;
- private boolean mDataValid;
- private BookmarkViewMode mViewMode;
- private boolean mMostVisited;
- private boolean mNeedsOffset;
- private int mExtraOffset;
+class BrowserBookmarksAdapter extends CursorAdapter {
+ LayoutInflater mInflater;
+ int mCurrentView;
+ Drawable mFaviconBackground;
/**
* Create a new BrowserBookmarksAdapter.
- * @param b BrowserBookmarksPage that instantiated this.
- * Necessary so it will adjust its focus
- * appropriately after a search.
*/
- public BrowserBookmarksAdapter(BrowserBookmarksPage b, String curPage,
- String curTitle, Bitmap curThumbnail, boolean createShortcut,
- boolean mostVisited) {
- mNeedsOffset = !(createShortcut || mostVisited);
- mMostVisited = mostVisited;
- mExtraOffset = mNeedsOffset ? 1 : 0;
- mBookmarksPage = b;
- mCurrentPage = b.getResources().getString(R.string.current_page)
- + curPage;
- mCurrentTitle = curTitle;
- mCurrentThumbnail = curThumbnail;
- mContentResolver = b.getContentResolver();
- mViewMode = BookmarkViewMode.LIST;
+ public BrowserBookmarksAdapter(Context context, int defaultView) {
+ // Make sure to tell the CursorAdapter to avoid the observer and auto-requery
+ // since the Loader will do that for us.
+ super(context, null, 0);
+ mInflater = LayoutInflater.from(context);
+ selectView(defaultView);
+ float density = context.getResources().getDisplayMetrics().density;
+ mFaviconBackground = BookmarkUtils.createListFaviconBackground(context);
+ }
- String whereClause;
- // FIXME: Should have a default sort order that the user selects.
- String orderBy = Browser.BookmarkColumns.VISITS + " DESC";
- if (mostVisited) {
- whereClause = Browser.BookmarkColumns.VISITS + " != 0";
+ @Override
+ public void bindView(View view, Context context, Cursor cursor) {
+ if (mCurrentView == BrowserBookmarksPage.VIEW_LIST) {
+ bindListView(view, context, cursor);
} else {
- whereClause = Browser.BookmarkColumns.BOOKMARK + " = 1";
- }
- mCursor = b.managedQuery(Browser.BOOKMARKS_URI,
- Browser.HISTORY_PROJECTION, whereClause, null, orderBy);
- mCursor.registerContentObserver(new ChangeObserver());
- mCursor.registerDataSetObserver(new MyDataSetObserver());
-
- mDataValid = true;
- notifyDataSetChanged();
-
- mCount = mCursor.getCount() + mExtraOffset;
- }
-
- /**
- * Return a hashmap with one row's Title, Url, and favicon.
- * @param position Position in the list.
- * @return Bundle Stores title, url of row position, favicon, and id
- * for the url. Return a blank map if position is out of
- * range.
- */
- public Bundle getRow(int position) {
- Bundle map = new Bundle();
- if (position < mExtraOffset || position >= mCount) {
- return map;
- }
- mCursor.moveToPosition(position- mExtraOffset);
- String url = mCursor.getString(Browser.HISTORY_PROJECTION_URL_INDEX);
- map.putString(Browser.BookmarkColumns.TITLE,
- mCursor.getString(Browser.HISTORY_PROJECTION_TITLE_INDEX));
- map.putString(Browser.BookmarkColumns.URL, url);
- byte[] data = mCursor.getBlob(Browser.HISTORY_PROJECTION_FAVICON_INDEX);
- if (data != null) {
- map.putParcelable(Browser.BookmarkColumns.FAVICON,
- BitmapFactory.decodeByteArray(data, 0, data.length));
- }
- map.putInt("id", mCursor.getInt(Browser.HISTORY_PROJECTION_ID_INDEX));
- return map;
- }
-
- /**
- * Update a row in the database with new information.
- * Requeries the database if the information has changed.
- * @param map Bundle storing id, title and url of new information
- */
- public void updateRow(Bundle map) {
-
- // Find the record
- int id = map.getInt("id");
- int position = -1;
- for (mCursor.moveToFirst(); !mCursor.isAfterLast(); mCursor.moveToNext()) {
- if (mCursor.getInt(Browser.HISTORY_PROJECTION_ID_INDEX) == id) {
- position = mCursor.getPosition();
- break;
- }
- }
- if (position < 0) {
- return;
- }
-
- mCursor.moveToPosition(position);
- ContentValues values = new ContentValues();
- String title = map.getString(Browser.BookmarkColumns.TITLE);
- if (!title.equals(mCursor
- .getString(Browser.HISTORY_PROJECTION_TITLE_INDEX))) {
- values.put(Browser.BookmarkColumns.TITLE, title);
- }
- String url = map.getString(Browser.BookmarkColumns.URL);
- if (!url.equals(mCursor.
- getString(Browser.HISTORY_PROJECTION_URL_INDEX))) {
- values.put(Browser.BookmarkColumns.URL, url);
- }
-
- if (map.getBoolean("invalidateThumbnail") == true) {
- values.put(Browser.BookmarkColumns.THUMBNAIL, new byte[0]);
- }
- if (values.size() > 0
- && mContentResolver.update(Browser.BOOKMARKS_URI, values,
- "_id = " + id, null) != -1) {
- refreshList();
+ bindGridView(view, context, cursor);
}
}
- /**
- * Delete a row from the database. Requeries the database.
- * Does nothing if the provided position is out of range.
- * @param position Position in the list.
- */
- public void deleteRow(int position) {
- if (position < mExtraOffset || position >= getCount()) {
- return;
- }
- mCursor.moveToPosition(position- mExtraOffset);
- String url = mCursor.getString(Browser.HISTORY_PROJECTION_URL_INDEX);
- String title = mCursor.getString(Browser.HISTORY_PROJECTION_TITLE_INDEX);
- Bookmarks.removeFromBookmarks(null, mContentResolver, url, title);
- refreshList();
- }
-
- /**
- * Delete all bookmarks from the db. Requeries the database.
- * All bookmarks with become visited URLs or if never visited
- * are removed
- */
- public void deleteAllRows() {
- StringBuilder deleteIds = null;
- StringBuilder convertIds = null;
-
- for (mCursor.moveToFirst(); !mCursor.isAfterLast(); mCursor.moveToNext()) {
- String url = mCursor.getString(Browser.HISTORY_PROJECTION_URL_INDEX);
- WebIconDatabase.getInstance().releaseIconForPageUrl(url);
- int id = mCursor.getInt(Browser.HISTORY_PROJECTION_ID_INDEX);
- int numVisits = mCursor.getInt(Browser.HISTORY_PROJECTION_VISITS_INDEX);
- if (0 == numVisits) {
- if (deleteIds == null) {
- deleteIds = new StringBuilder();
- deleteIds.append("( ");
- } else {
- deleteIds.append(" OR ( ");
- }
- deleteIds.append(BookmarkColumns._ID);
- deleteIds.append(" = ");
- deleteIds.append(id);
- deleteIds.append(" )");
- } else {
- // It is no longer a bookmark, but it is still a visited site.
- if (convertIds == null) {
- convertIds = new StringBuilder();
- convertIds.append("( ");
- } else {
- convertIds.append(" OR ( ");
- }
- convertIds.append(BookmarkColumns._ID);
- convertIds.append(" = ");
- convertIds.append(id);
- convertIds.append(" )");
- }
- }
-
- if (deleteIds != null) {
- mContentResolver.delete(Browser.BOOKMARKS_URI, deleteIds.toString(),
- null);
- }
- if (convertIds != null) {
- ContentValues values = new ContentValues();
- values.put(Browser.BookmarkColumns.BOOKMARK, 0);
- mContentResolver.update(Browser.BOOKMARKS_URI, values,
- convertIds.toString(), null);
- }
- refreshList();
- }
+ void bindGridView(View view, Context context, Cursor cursor) {
+ ImageView thumb = (ImageView) view.findViewById(R.id.thumb);
+ TextView tv = (TextView) view.findViewById(R.id.label);
- /**
- * Refresh list to recognize a change in the database.
- */
- public void refreshList() {
- mCursor.requery();
- mCount = mCursor.getCount() + mExtraOffset;
- notifyDataSetChanged();
- }
-
- /**
- * Update the bookmark's favicon. This is a convenience method for updating
- * a bookmark favicon for the originalUrl and url of the passed in WebView.
- * @param cr The ContentResolver to use.
- * @param originalUrl The original url before any redirects.
- * @param url The current url.
- * @param favicon The favicon bitmap to write to the db.
- */
- /* package */ static void updateBookmarkFavicon(final ContentResolver cr,
- final String originalUrl, final String url, final Bitmap favicon) {
- new AsyncTask<Void, Void, Void>() {
- protected Void doInBackground(Void... unused) {
- final Cursor c =
- queryBookmarksForUrl(cr, originalUrl, url, true);
- if (c == null) {
- return null;
- }
- if (c.moveToFirst()) {
- ContentValues values = new ContentValues();
- final ByteArrayOutputStream os =
- new ByteArrayOutputStream();
- favicon.compress(Bitmap.CompressFormat.PNG, 100, os);
- values.put(Browser.BookmarkColumns.FAVICON,
- os.toByteArray());
- do {
- cr.update(ContentUris.withAppendedId(
- Browser.BOOKMARKS_URI, c.getInt(0)),
- values, null, null);
- } while (c.moveToNext());
- }
- c.close();
- return null;
- }
- }.execute();
- }
-
- /* package */ static Cursor queryBookmarksForUrl(ContentResolver cr,
- String originalUrl, String url, boolean onlyBookmarks) {
- if (cr == null || url == null) {
- return null;
- }
-
- // If originalUrl is null, just set it to url.
- if (originalUrl == null) {
- originalUrl = url;
- }
-
- // Look for both the original url and the actual url. This takes in to
- // account redirects.
- String originalUrlNoQuery = removeQuery(originalUrl);
- String urlNoQuery = removeQuery(url);
- originalUrl = originalUrlNoQuery + '?';
- url = urlNoQuery + '?';
-
- // Use NoQuery to search for the base url (i.e. if the url is
- // http://www.yahoo.com/?rs=1, search for http://www.yahoo.com)
- // Use url to match the base url with other queries (i.e. if the url is
- // http://www.google.com/m, search for
- // http://www.google.com/m?some_query)
- final String[] selArgs = new String[] {
- originalUrlNoQuery, urlNoQuery, originalUrl, url };
- String where = BookmarkColumns.URL + " == ? OR "
- + BookmarkColumns.URL + " == ? OR "
- + BookmarkColumns.URL + " LIKE ? || '%' OR "
- + BookmarkColumns.URL + " LIKE ? || '%'";
- if (onlyBookmarks) {
- where = "(" + where + ") AND " + BookmarkColumns.BOOKMARK + " == 1";
- }
- final String[] projection =
- new String[] { Browser.BookmarkColumns._ID };
- return cr.query(Browser.BOOKMARKS_URI, projection, where, selArgs,
- null);
- }
-
- // Strip the query from the given url.
- private static String removeQuery(String url) {
- if (url == null) {
- return null;
- }
- int query = url.indexOf('?');
- String noQuery = url;
- if (query != -1) {
- noQuery = url.substring(0, query);
- }
- return noQuery;
- }
-
- /**
- * How many items should be displayed in the list.
- * @return Count of items.
- */
- public int getCount() {
- if (mDataValid) {
- return mCount;
+ tv.setText(cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE));
+ if (cursor.getInt(BookmarksLoader.COLUMN_INDEX_IS_FOLDER) != 0) {
+ // folder
+ thumb.setImageResource(R.drawable.thumb_bookmark_widget_folder_holo);
+ thumb.setBackgroundDrawable(null);
} else {
- return 0;
- }
- }
-
- public boolean areAllItemsEnabled() {
- return true;
- }
-
- public boolean isEnabled(int position) {
- return true;
- }
-
- /**
- * Get the data associated with the specified position in the list.
- * @param position Index of the item whose data we want.
- * @return The data at the specified position.
- */
- public Object getItem(int position) {
- return null;
- }
-
- /**
- * Get the row id associated with the specified position in the list.
- * @param position Index of the item whose row id we want.
- * @return The id of the item at the specified position.
- */
- public long getItemId(int position) {
- return position;
- }
-
- /* package */ void switchViewMode(BookmarkViewMode viewMode) {
- mViewMode = viewMode;
- }
-
- /* package */ void populateBookmarkItem(BookmarkItem b, int position) {
- mCursor.moveToPosition(position - mExtraOffset);
- String url = mCursor.getString(Browser.HISTORY_PROJECTION_URL_INDEX);
- b.setUrl(url);
- b.setName(mCursor.getString(Browser.HISTORY_PROJECTION_TITLE_INDEX));
- byte[] data = mCursor.getBlob(Browser.HISTORY_PROJECTION_FAVICON_INDEX);
- Bitmap bitmap = null;
- if (data == null) {
- bitmap = CombinedBookmarkHistoryActivity.getIconListenerSet()
- .getFavicon(url);
- } else {
- bitmap = BitmapFactory.decodeByteArray(data, 0, data.length);
- }
- b.setFavicon(bitmap);
- }
-
- /**
- * Get a View that displays the data at the specified position
- * in the list.
- * @param position Index of the item whose view we want.
- * @return A View corresponding to the data at the specified position.
- */
- public View getView(int position, View convertView, ViewGroup parent) {
- if (!mDataValid) {
- throw new IllegalStateException(
- "this should only be called when the cursor is valid");
- }
- if (position < 0 || position > mCount) {
- throw new AssertionError(
- "BrowserBookmarksAdapter tried to get a view out of range");
- }
- if (mViewMode == BookmarkViewMode.GRID) {
- if (convertView == null || convertView instanceof AddNewBookmark
- || convertView instanceof BookmarkItem) {
- LayoutInflater factory = LayoutInflater.from(mBookmarksPage);
- convertView
- = factory.inflate(R.layout.bookmark_thumbnail, null);
+ byte[] thumbData = cursor.getBlob(BookmarksLoader.COLUMN_INDEX_THUMBNAIL);
+ Bitmap thumbBitmap = null;
+ if (thumbData != null) {
+ thumbBitmap = BitmapFactory.decodeByteArray(thumbData, 0, thumbData.length);
}
- View holder = convertView.findViewById(R.id.holder);
- ImageView thumb = (ImageView) convertView.findViewById(R.id.thumb);
- TextView tv = (TextView) convertView.findViewById(R.id.label);
- if (0 == position && mNeedsOffset) {
- // This is to create a bookmark for the current page.
- holder.setVisibility(View.VISIBLE);
- tv.setText(mCurrentTitle);
-
- if (mCurrentThumbnail != null) {
- thumb.setImageBitmap(mCurrentThumbnail);
- } else {
- thumb.setImageResource(
- R.drawable.browser_thumbnail);
- }
- return convertView;
- }
- holder.setVisibility(View.GONE);
- mCursor.moveToPosition(position - mExtraOffset);
- tv.setText(mCursor.getString(
- Browser.HISTORY_PROJECTION_TITLE_INDEX));
- Bitmap thumbnail = getScreenshot(position);
- if (thumbnail == null) {
+ if (thumbBitmap == null) {
thumb.setImageResource(R.drawable.browser_thumbnail);
} else {
- thumb.setImageBitmap(thumbnail);
+ thumb.setImageBitmap(thumbBitmap);
+ }
+ thumb.setBackgroundResource(R.drawable.border_thumb_bookmarks_widget_holo);
+ }
+ }
+
+ void bindListView(View view, Context context, Cursor cursor) {
+ ImageView favicon = (ImageView) view.findViewById(R.id.favicon);
+ TextView tv = (TextView) view.findViewById(R.id.label);
+
+ tv.setText(cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE));
+ if (cursor.getInt(BookmarksLoader.COLUMN_INDEX_IS_FOLDER) != 0) {
+ // folder
+ favicon.setImageResource(R.drawable.ic_folder_holo_dark);
+ favicon.setBackgroundDrawable(null);
+ } else {
+ byte[] faviconData = cursor.getBlob(BookmarksLoader.COLUMN_INDEX_FAVICON);
+ Bitmap faviconBitmap = null;
+ if (faviconData != null) {
+ faviconBitmap = BitmapFactory.decodeByteArray(faviconData, 0, faviconData.length);
}
- return convertView;
-
- }
- if (position == 0 && mNeedsOffset) {
- AddNewBookmark b;
- if (convertView instanceof AddNewBookmark) {
- b = (AddNewBookmark) convertView;
+ if (faviconBitmap == null) {
+ favicon.setImageResource(R.drawable.app_web_browser_sm);
} else {
- b = new AddNewBookmark(mBookmarksPage);
+ favicon.setImageBitmap(faviconBitmap);
}
- b.setUrl(mCurrentPage);
- return b;
+ //favicon.setBackgroundResource(R.drawable.bookmark_list_favicon_bg);
+ // TODO: Switch to above instead of below once b/3353813 is fixed
+ favicon.setBackgroundDrawable(mFaviconBackground);
}
- if (mMostVisited) {
- if (convertView == null || !(convertView instanceof HistoryItem)) {
- convertView = new HistoryItem(mBookmarksPage);
- }
+ }
+
+ @Override
+ public View newView(Context context, Cursor cursor, ViewGroup parent) {
+ if (mCurrentView == BrowserBookmarksPage.VIEW_LIST) {
+ return mInflater.inflate(R.layout.bookmark_list, parent, false);
} else {
- if (convertView == null || !(convertView instanceof BookmarkItem)) {
- convertView = new BookmarkItem(mBookmarksPage);
- }
- }
- bind((BookmarkItem) convertView, position);
- if (mMostVisited) {
- ((HistoryItem) convertView).setIsBookmark(
- getIsBookmark(position));
- }
- return convertView;
- }
-
- /**
- * Return the title for this item in the list.
- */
- public String getTitle(int position) {
- return getString(Browser.HISTORY_PROJECTION_TITLE_INDEX, position);
- }
-
- /**
- * Return the Url for this item in the list.
- */
- public String getUrl(int position) {
- return getString(Browser.HISTORY_PROJECTION_URL_INDEX, position);
- }
-
- /**
- * Return the screenshot for this item in the list.
- */
- public Bitmap getScreenshot(int position) {
- return getBitmap(Browser.HISTORY_PROJECTION_THUMBNAIL_INDEX, position);
- }
-
- /**
- * Return the favicon for this item in the list.
- */
- public Bitmap getFavicon(int position) {
- return getBitmap(Browser.HISTORY_PROJECTION_FAVICON_INDEX, position);
- }
-
- public Bitmap getTouchIcon(int position) {
- return getBitmap(Browser.HISTORY_PROJECTION_TOUCH_ICON_INDEX, position);
- }
-
- private Bitmap getBitmap(int cursorIndex, int position) {
- if (position < mExtraOffset || position > mCount) {
- return null;
- }
- mCursor.moveToPosition(position - mExtraOffset);
- byte[] data = mCursor.getBlob(cursorIndex);
- if (data == null) {
- return null;
- }
- return BitmapFactory.decodeByteArray(data, 0, data.length);
- }
-
- /**
- * Return whether or not this item represents a bookmarked site.
- */
- public boolean getIsBookmark(int position) {
- if (position < mExtraOffset || position > mCount) {
- return false;
- }
- mCursor.moveToPosition(position - mExtraOffset);
- return (1 == mCursor.getInt(Browser.HISTORY_PROJECTION_BOOKMARK_INDEX));
- }
-
- /**
- * Private helper function to return the title or url.
- */
- private String getString(int cursorIndex, int position) {
- if (position < mExtraOffset || position > mCount) {
- return "";
- }
- mCursor.moveToPosition(position- mExtraOffset);
- return mCursor.getString(cursorIndex);
- }
-
- private void bind(BookmarkItem b, int position) {
- mCursor.moveToPosition(position- mExtraOffset);
-
- b.setName(mCursor.getString(Browser.HISTORY_PROJECTION_TITLE_INDEX));
- String url = mCursor.getString(Browser.HISTORY_PROJECTION_URL_INDEX);
- b.setUrl(url);
- byte[] data = mCursor.getBlob(Browser.HISTORY_PROJECTION_FAVICON_INDEX);
- if (data != null) {
- b.setFavicon(BitmapFactory.decodeByteArray(data, 0, data.length));
- } else {
- b.setFavicon(CombinedBookmarkHistoryActivity.getIconListenerSet()
- .getFavicon(url));
+ return mInflater.inflate(R.layout.bookmark_thumbnail, parent, false);
}
}
- private class ChangeObserver extends ContentObserver {
- public ChangeObserver() {
- super(new Handler(Looper.getMainLooper()));
+ public void selectView(int view) {
+ if (view != BrowserBookmarksPage.VIEW_LIST
+ && view != BrowserBookmarksPage.VIEW_THUMBNAILS) {
+ throw new IllegalArgumentException("Unknown view specified: " + view);
}
-
- @Override
- public boolean deliverSelfNotifications() {
- return true;
- }
-
- @Override
- public void onChange(boolean selfChange) {
- refreshList();
- }
+ mCurrentView = view;
}
-
- private class MyDataSetObserver extends DataSetObserver {
- @Override
- public void onChanged() {
- mDataValid = true;
- notifyDataSetChanged();
- }
- @Override
- public void onInvalidated() {
- mDataValid = false;
- notifyDataSetInvalidated();
- }
+ @Override
+ public Cursor getItem(int position) {
+ return (Cursor) super.getItem(position);
}
}
diff --git a/src/com/android/browser/BrowserBookmarksPage.java b/src/com/android/browser/BrowserBookmarksPage.java
index dd01009..7475237 100644
--- a/src/com/android/browser/BrowserBookmarksPage.java
+++ b/src/com/android/browser/BrowserBookmarksPage.java
@@ -16,91 +16,184 @@
package com.android.browser;
+import com.android.browser.BreadCrumbView.Crumb;
+
import android.app.Activity;
-import android.app.AlertDialog;
-import android.content.DialogInterface;
+import android.app.Fragment;
+import android.app.LoaderManager;
+import android.content.ClipData;
+import android.content.ClipboardManager;
+import android.content.ContentUris;
+import android.content.Context;
import android.content.Intent;
+import android.content.Loader;
import android.content.SharedPreferences;
import android.content.SharedPreferences.Editor;
+import android.content.SharedPreferences.OnSharedPreferenceChangeListener;
+import android.content.res.Configuration;
+import android.content.res.Resources;
+import android.database.Cursor;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
-import android.graphics.Canvas;
-import android.graphics.Color;
-import android.graphics.Paint;
-import android.graphics.Path;
-import android.graphics.PorterDuff;
-import android.graphics.PorterDuffXfermode;
-import android.graphics.Rect;
-import android.graphics.RectF;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.Bundle;
-import android.os.Handler;
-import android.os.Message;
-import android.os.ServiceManager;
-import android.provider.Browser;
-import android.text.IClipboard;
-import android.util.Log;
+import android.preference.PreferenceManager;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.ChromeSyncColumns;
import android.view.ContextMenu;
+import android.view.ContextMenu.ContextMenuInfo;
+import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
-import android.view.ContextMenu.ContextMenuInfo;
import android.webkit.WebIconDatabase.IconListener;
import android.widget.AdapterView;
+import android.widget.AdapterView.OnItemClickListener;
import android.widget.GridView;
import android.widget.ListView;
+import android.widget.PopupMenu.OnMenuItemClickListener;
import android.widget.Toast;
-/*package*/ enum BookmarkViewMode { NONE, GRID, LIST }
+interface BookmarksPageCallbacks {
+ // Return true if handled
+ boolean onBookmarkSelected(Cursor c, boolean isFolder);
+ // Return true if handled
+ boolean onOpenInNewWindow(Cursor c);
+ void onFolderChanged(int level, Uri uri);
+}
+
/**
* View showing the user's bookmarks in the browser.
*/
-public class BrowserBookmarksPage extends Activity implements
- View.OnCreateContextMenuListener {
+public class BrowserBookmarksPage extends Fragment implements View.OnCreateContextMenuListener,
+ LoaderManager.LoaderCallbacks<Cursor>, OnItemClickListener, IconListener,
+ BreadCrumbView.Controller, OnMenuItemClickListener, OnSharedPreferenceChangeListener {
- private BookmarkViewMode mViewMode = BookmarkViewMode.NONE;
- private GridView mGridPage;
- private ListView mVerticalList;
- private BrowserBookmarksAdapter mBookmarksAdapter;
- private static final int BOOKMARKS_SAVE = 1;
- private boolean mDisableNewWindow;
- private BookmarkItem mContextHeader;
- private AddNewBookmark mAddHeader;
- private boolean mCanceled = false;
- private boolean mCreateShortcut;
- private boolean mMostVisited;
- private View mEmptyView;
- private int mIconSize;
- // XXX: There is no public string defining this intent so if Home changes
- // the value, we have to update this string.
- private static final String INSTALL_SHORTCUT =
- "com.android.launcher.action.INSTALL_SHORTCUT";
+ static final String LOGTAG = "browser";
- private final static String LOGTAG = "browser";
- private final static String PREF_BOOKMARK_VIEW_MODE = "pref_bookmark_view_mode";
- private final static String PREF_MOST_VISITED_VIEW_MODE = "pref_most_visited_view_mode";
+ static final int LOADER_BOOKMARKS = 1;
+
+ static final String EXTRA_DISABLE_WINDOW = "disable_new_window";
+
+ static final String ACCOUNT_NAME_UNSYNCED = "Unsynced";
+
+ public static final String PREF_ACCOUNT_TYPE = "acct_type";
+ public static final String PREF_ACCOUNT_NAME = "acct_name";
+
+ static final int VIEW_THUMBNAILS = 1;
+ static final int VIEW_LIST = 2;
+ static final String PREF_SELECTED_VIEW = "bookmarks_view";
+
+ BookmarksPageCallbacks mCallbacks;
+ View mRoot;
+ GridView mGrid;
+ ListView mList;
+ BrowserBookmarksAdapter mAdapter;
+ boolean mDisableNewWindow;
+ boolean mCanceled = false;
+ boolean mEnableContextMenu = true;
+ boolean mShowRootFolder = false;
+ View mEmptyView;
+ int mCurrentView;
+ View mHeader;
+ ViewGroup mHeaderContainer;
+ BreadCrumbView mCrumbs;
+ int mCrumbVisibility = View.VISIBLE;
+ int mCrumbMaxVisible = -1;
+ boolean mCrumbBackButton = false;
+
+ static BrowserBookmarksPage newInstance(BookmarksPageCallbacks cb,
+ Bundle args, ViewGroup headerContainer) {
+ BrowserBookmarksPage bbp = new BrowserBookmarksPage();
+ bbp.mCallbacks = cb;
+ bbp.mHeaderContainer = headerContainer;
+ bbp.setArguments(args);
+ return bbp;
+ }
+
+ @Override
+ public Loader<Cursor> onCreateLoader(int id, Bundle args) {
+ switch (id) {
+ case LOADER_BOOKMARKS: {
+ SharedPreferences prefs = PreferenceManager
+ .getDefaultSharedPreferences(getActivity());
+ String accountType = prefs.getString(PREF_ACCOUNT_TYPE, null);
+ String accountName = prefs.getString(PREF_ACCOUNT_NAME, null);
+ BookmarksLoader bl = new BookmarksLoader(getActivity(),
+ accountType, accountName);
+ if (mCrumbs != null) {
+ Uri uri = (Uri) mCrumbs.getTopData();
+ if (uri != null) {
+ bl.setUri(uri);
+ }
+ }
+ return bl;
+ }
+ }
+ throw new UnsupportedOperationException("Unknown loader id " + id);
+ }
+
+ @Override
+ public void onLoadFinished(Loader<Cursor> loader, Cursor cursor) {
+ switch (loader.getId()) {
+ case LOADER_BOOKMARKS: {
+ // Set the visibility of the empty vs. content views
+ if (cursor == null || cursor.getCount() == 0) {
+ mEmptyView.setVisibility(View.VISIBLE);
+ mGrid.setVisibility(View.GONE);
+ mList.setVisibility(View.GONE);
+ } else {
+ mEmptyView.setVisibility(View.GONE);
+ setupBookmarkView();
+ }
+
+ // Give the new data to the adapter
+ mAdapter.changeCursor(cursor);
+ break;
+ }
+ }
+ }
+
+ @Override
+ public void onLoaderReset(Loader<Cursor> loader) {
+ onLoadFinished(loader, null);
+ }
+
+ long getFolderId() {
+ LoaderManager manager = getLoaderManager();
+ BookmarksLoader loader =
+ (BookmarksLoader) ((Loader<?>)manager.getLoader(LOADER_BOOKMARKS));
+
+ Uri uri = loader.getUri();
+ if (uri != null) {
+ try {
+ return ContentUris.parseId(uri);
+ } catch (NumberFormatException nfx) {
+ return -1;
+ }
+ }
+ return -1;
+ }
@Override
public boolean onContextItemSelected(MenuItem item) {
+ final Activity activity = getActivity();
// It is possible that the view has been canceled when we get to
// this point as back has a higher priority
if (mCanceled) {
- return true;
+ return false;
}
AdapterView.AdapterContextMenuInfo i =
(AdapterView.AdapterContextMenuInfo)item.getMenuInfo();
// If we have no menu info, we can't tell which item was selected.
if (i == null) {
- return true;
+ return false;
}
switch (item.getItemId()) {
- case R.id.new_context_menu_id:
- saveCurrentPage();
- break;
case R.id.open_context_menu_id:
loadUrl(i.position);
break;
@@ -108,652 +201,547 @@
editBookmark(i.position);
break;
case R.id.shortcut_context_menu_id:
- final Intent send = createShortcutIntent(i.position);
- send.setAction(INSTALL_SHORTCUT);
- sendBroadcast(send);
+ Cursor c = mAdapter.getItem(i.position);
+ activity.sendBroadcast(createShortcutIntent(getActivity(), c));
break;
case R.id.delete_context_menu_id:
- if (mMostVisited) {
- Browser.deleteFromHistory(getContentResolver(),
- getUrl(i.position));
- refreshList();
- } else {
- displayRemoveBookmarkDialog(i.position);
- }
+ displayRemoveBookmarkDialog(i.position);
break;
case R.id.new_window_context_menu_id:
openInNewWindow(i.position);
break;
- case R.id.share_link_context_menu_id:
- BrowserActivity.sharePage(BrowserBookmarksPage.this,
- mBookmarksAdapter.getTitle(i.position), getUrl(i.position),
- getFavicon(i.position),
- mBookmarksAdapter.getScreenshot(i.position));
+ case R.id.share_link_context_menu_id: {
+ Cursor cursor = mAdapter.getItem(i.position);
+ Controller.sharePage(activity,
+ cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE),
+ cursor.getString(BookmarksLoader.COLUMN_INDEX_URL),
+ getBitmap(cursor, BookmarksLoader.COLUMN_INDEX_FAVICON),
+ getBitmap(cursor, BookmarksLoader.COLUMN_INDEX_THUMBNAIL));
break;
+ }
case R.id.copy_url_context_menu_id:
copy(getUrl(i.position));
break;
- case R.id.homepage_context_menu_id:
- BrowserSettings.getInstance().setHomePage(this,
- getUrl(i.position));
- Toast.makeText(this, R.string.homepage_set,
- Toast.LENGTH_LONG).show();
+ case R.id.homepage_context_menu_id: {
+ BrowserSettings.getInstance().setHomePage(activity, getUrl(i.position));
+ Toast.makeText(activity, R.string.homepage_set, Toast.LENGTH_LONG).show();
break;
+ }
// Only for the Most visited page
- case R.id.save_to_bookmarks_menu_id:
- boolean isBookmark;
- String name;
- String url;
- if (mViewMode == BookmarkViewMode.GRID) {
- isBookmark = mBookmarksAdapter.getIsBookmark(i.position);
- name = mBookmarksAdapter.getTitle(i.position);
- url = mBookmarksAdapter.getUrl(i.position);
- } else {
- HistoryItem historyItem = ((HistoryItem) i.targetView);
- isBookmark = historyItem.isBookmark();
- name = historyItem.getName();
- url = historyItem.getUrl();
- }
+ case R.id.save_to_bookmarks_menu_id: {
+ Cursor cursor = mAdapter.getItem(i.position);
+ String name = cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE);
+ String url = cursor.getString(BookmarksLoader.COLUMN_INDEX_URL);
// If the site is bookmarked, the item becomes remove from
// bookmarks.
- if (isBookmark) {
- Bookmarks.removeFromBookmarks(this, getContentResolver(), url, name);
- } else {
- Browser.saveBookmark(this, name, url);
- }
+ Bookmarks.removeFromBookmarks(activity, activity.getContentResolver(), url, name);
break;
+ }
default:
return super.onContextItemSelected(item);
}
return true;
}
- @Override
- public void onCreateContextMenu(ContextMenu menu, View v,
- ContextMenuInfo menuInfo) {
- AdapterView.AdapterContextMenuInfo i =
- (AdapterView.AdapterContextMenuInfo) menuInfo;
-
- MenuInflater inflater = getMenuInflater();
- if (mMostVisited) {
- inflater.inflate(R.menu.historycontext, menu);
- } else {
- inflater.inflate(R.menu.bookmarkscontext, menu);
- }
-
- if (0 == i.position && !mMostVisited) {
- menu.setGroupVisible(R.id.CONTEXT_MENU, false);
- if (mAddHeader == null) {
- mAddHeader = new AddNewBookmark(BrowserBookmarksPage.this);
- } else if (mAddHeader.getParent() != null) {
- ((ViewGroup) mAddHeader.getParent()).
- removeView(mAddHeader);
- }
- mAddHeader.setUrl(getIntent().getStringExtra("url"));
- menu.setHeaderView(mAddHeader);
- return;
- }
- if (mMostVisited) {
- if ((mViewMode == BookmarkViewMode.LIST
- && ((HistoryItem) i.targetView).isBookmark())
- || mBookmarksAdapter.getIsBookmark(i.position)) {
- MenuItem item = menu.findItem(
- R.id.save_to_bookmarks_menu_id);
- item.setTitle(R.string.remove_from_bookmarks);
- }
- } else {
- // The historycontext menu has no ADD_MENU group.
- menu.setGroupVisible(R.id.ADD_MENU, false);
- }
- if (mDisableNewWindow) {
- menu.findItem(R.id.new_window_context_menu_id).setVisible(
- false);
- }
- if (mContextHeader == null) {
- mContextHeader = new BookmarkItem(BrowserBookmarksPage.this);
- } else if (mContextHeader.getParent() != null) {
- ((ViewGroup) mContextHeader.getParent()).
- removeView(mContextHeader);
- }
- if (mViewMode == BookmarkViewMode.GRID) {
- mBookmarksAdapter.populateBookmarkItem(mContextHeader,
- i.position);
- } else {
- BookmarkItem b = (BookmarkItem) i.targetView;
- b.copyTo(mContextHeader);
- }
- menu.setHeaderView(mContextHeader);
+ static Bitmap getBitmap(Cursor cursor, int columnIndex) {
+ byte[] data = cursor.getBlob(columnIndex);
+ if (data == null) {
+ return null;
}
+ return BitmapFactory.decodeByteArray(data, 0, data.length);
+ }
+
+ private MenuItem.OnMenuItemClickListener mContextItemClickListener =
+ new MenuItem.OnMenuItemClickListener() {
+ @Override
+ public boolean onMenuItemClick(MenuItem item) {
+ return onContextItemSelected(item);
+ }
+ };
+
+ @Override
+ public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
+ inflater.inflate(R.menu.bookmark, menu);
+ }
+
+ @Override
+ public void onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) {
+ AdapterView.AdapterContextMenuInfo info = (AdapterView.AdapterContextMenuInfo) menuInfo;
+ Cursor cursor = mAdapter.getItem(info.position);
+ if (!canEdit(cursor)) {
+ return;
+ }
+ boolean isFolder
+ = cursor.getInt(BookmarksLoader.COLUMN_INDEX_IS_FOLDER) != 0;
+
+ final Activity activity = getActivity();
+ MenuInflater inflater = activity.getMenuInflater();
+ inflater.inflate(R.menu.bookmarkscontext, menu);
+ if (isFolder) {
+ menu.setGroupVisible(R.id.FOLDER_CONTEXT_MENU, true);
+ } else {
+ menu.setGroupVisible(R.id.BOOKMARK_CONTEXT_MENU, true);
+ if (mDisableNewWindow) {
+ menu.findItem(R.id.new_window_context_menu_id).setVisible(false);
+ }
+ }
+ BookmarkItem header = new BookmarkItem(activity);
+ populateBookmarkItem(cursor, header, isFolder);
+ menu.setHeaderView(header);
+
+ int count = menu.size();
+ for (int i = 0; i < count; i++) {
+ menu.getItem(i).setOnMenuItemClickListener(mContextItemClickListener);
+ }
+ }
+
+ boolean canEdit(Cursor c) {
+ String unique = c.getString(BookmarksLoader.COLUMN_INDEX_SERVER_UNIQUE);
+ return !ChromeSyncColumns.FOLDER_NAME_OTHER_BOOKMARKS.equals(unique);
+ }
+
+ private void populateBookmarkItem(Cursor cursor, BookmarkItem item, boolean isFolder) {
+ item.setName(cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE));
+ if (isFolder) {
+ item.setUrl(null);
+ Bitmap bitmap =
+ BitmapFactory.decodeResource(getResources(), R.drawable.ic_folder_holo_dark);
+ item.setFavicon(bitmap);
+ new LookupBookmarkCount(getActivity(), item)
+ .execute(cursor.getLong(BookmarksLoader.COLUMN_INDEX_ID));
+ } else {
+ String url = cursor.getString(BookmarksLoader.COLUMN_INDEX_URL);
+ item.setUrl(url);
+ Bitmap bitmap = getBitmap(cursor, BookmarksLoader.COLUMN_INDEX_FAVICON);
+ if (bitmap == null) {
+ bitmap = CombinedBookmarkHistoryView.getIconListenerSet().getFavicon(url);
+ }
+ item.setFavicon(bitmap);
+ }
+ }
/**
* Create a new BrowserBookmarksPage.
*/
@Override
- protected void onCreate(Bundle icicle) {
+ public void onCreate(Bundle icicle) {
super.onCreate(icicle);
- // Grab the app icon size as a resource.
- mIconSize = getResources().getDimensionPixelSize(
- android.R.dimen.app_icon_size);
+ setHasOptionsMenu(true);
- Intent intent = getIntent();
- if (Intent.ACTION_CREATE_SHORTCUT.equals(intent.getAction())) {
- mCreateShortcut = true;
- }
- mDisableNewWindow = intent.getBooleanExtra("disable_new_window",
- false);
- mMostVisited = intent.getBooleanExtra("mostVisited", false);
-
- if (mCreateShortcut) {
- setTitle(R.string.browser_bookmarks_page_bookmarks_text);
- }
-
- setContentView(R.layout.empty_history);
- mEmptyView = findViewById(R.id.empty_view);
- mEmptyView.setVisibility(View.GONE);
-
- SharedPreferences p = getPreferences(MODE_PRIVATE);
-
- // See if the user has set a preference for the view mode of their
- // bookmarks. Otherwise default to grid mode.
- BookmarkViewMode preference = BookmarkViewMode.NONE;
- if (mMostVisited) {
- // For the most visited page, only use list mode.
- preference = BookmarkViewMode.LIST;
- } else {
- preference = BookmarkViewMode.values()[p.getInt(
- PREF_BOOKMARK_VIEW_MODE, BookmarkViewMode.GRID.ordinal())];
- }
- switchViewMode(preference);
-
- final boolean createShortcut = mCreateShortcut;
- final boolean mostVisited = mMostVisited;
- final String url = intent.getStringExtra("url");
- final String title = intent.getStringExtra("title");
- final Bitmap thumbnail =
- (Bitmap) intent.getParcelableExtra("thumbnail");
- new AsyncTask<Void, Void, Void>() {
- @Override
- protected Void doInBackground(Void... unused) {
- BrowserBookmarksAdapter adapter = new BrowserBookmarksAdapter(
- BrowserBookmarksPage.this,
- url,
- title,
- thumbnail,
- createShortcut,
- mostVisited);
- mHandler.obtainMessage(ADAPTER_CREATED, adapter).sendToTarget();
- return null;
- }
- }.execute();
+ Bundle args = getArguments();
+ mDisableNewWindow = args == null ? false : args.getBoolean(EXTRA_DISABLE_WINDOW, false);
}
@Override
- protected void onDestroy() {
- mHandler.removeCallbacksAndMessages(null);
- super.onDestroy();
+ public View onCreateView(LayoutInflater inflater, ViewGroup container,
+ Bundle savedInstanceState) {
+ Context context = getActivity();
+
+ mRoot = inflater.inflate(R.layout.bookmarks, container, false);
+ mEmptyView = mRoot.findViewById(android.R.id.empty);
+
+ mGrid = (GridView) mRoot.findViewById(R.id.grid);
+ mGrid.setOnItemClickListener(this);
+ mGrid.setColumnWidth(Controller.getDesiredThumbnailWidth(getActivity()));
+ mList = (ListView) mRoot.findViewById(R.id.list);
+ mList.setOnItemClickListener(this);
+ setEnableContextMenu(mEnableContextMenu);
+
+ // Prep the header
+ ViewGroup hc = mHeaderContainer;
+ if (hc == null) {
+ hc = (ViewGroup) mRoot.findViewById(R.id.header_container);
+ hc.setVisibility(View.VISIBLE);
+ }
+ mHeader = inflater.inflate(R.layout.bookmarks_header, hc, false);
+ hc.addView(mHeader);
+ mCrumbs = (BreadCrumbView) mHeader.findViewById(R.id.crumbs);
+ mCrumbs.setController(this);
+ mCrumbs.setUseBackButton(mCrumbBackButton);
+ mCrumbs.setMaxVisible(mCrumbMaxVisible);
+ mCrumbs.setVisibility(mCrumbVisibility);
+ String name = getString(R.string.bookmarks);
+ mCrumbs.pushView(name, false, BrowserContract.Bookmarks.CONTENT_URI_DEFAULT_FOLDER);
+ if (mCallbacks != null) {
+ mCallbacks.onFolderChanged(1, BrowserContract.Bookmarks.CONTENT_URI_DEFAULT_FOLDER);
+ }
+ // Start the loaders
+ LoaderManager lm = getLoaderManager();
+ SharedPreferences prefs = PreferenceManager
+ .getDefaultSharedPreferences(getActivity());
+ prefs.registerOnSharedPreferenceChangeListener(this);
+ mCurrentView =
+ prefs.getInt(PREF_SELECTED_VIEW, BrowserBookmarksPage.VIEW_THUMBNAILS);
+ mAdapter = new BrowserBookmarksAdapter(getActivity(), mCurrentView);
+ lm.restartLoader(LOADER_BOOKMARKS, null, this);
+
+ // Add our own listener in case there are favicons that have yet to be loaded.
+ CombinedBookmarkHistoryView.getIconListenerSet().addListener(this);
+
+ return mRoot;
}
- /**
- * Set the ContentView to be either the grid of thumbnails or the vertical
- * list.
- */
- private void switchViewMode(BookmarkViewMode viewMode) {
- if (mViewMode == viewMode) {
+ @Override
+ public void onDestroyView() {
+ super.onDestroyView();
+ SharedPreferences prefs = PreferenceManager
+ .getDefaultSharedPreferences(getActivity());
+ prefs.unregisterOnSharedPreferenceChangeListener(this);
+ if (mHeaderContainer != null) {
+ mHeaderContainer.removeView(mHeader);
+ }
+ mCrumbs.setController(null);
+ mCrumbs = null;
+ getLoaderManager().destroyLoader(LOADER_BOOKMARKS);
+ mAdapter = null;
+ CombinedBookmarkHistoryView.getIconListenerSet().removeListener(this);
+ }
+
+ @Override
+ public void onReceivedIcon(String url, Bitmap icon) {
+ // A new favicon has been loaded, so let anything attached to the adapter know about it
+ // so new icons will be loaded.
+ mAdapter.notifyDataSetChanged();
+ }
+
+ @Override
+ public void onItemClick(AdapterView<?> parent, View v, int position, long id) {
+ // It is possible that the view has been canceled when we get to
+ // this point as back has a higher priority
+ if (mCanceled) {
+ android.util.Log.e(LOGTAG, "item clicked when dismissing");
return;
}
- mViewMode = viewMode;
-
- // Update the preferences to make the new view mode sticky.
- Editor ed = getPreferences(MODE_PRIVATE).edit();
- if (mMostVisited) {
- ed.putInt(PREF_MOST_VISITED_VIEW_MODE, mViewMode.ordinal());
- } else {
- ed.putInt(PREF_BOOKMARK_VIEW_MODE, mViewMode.ordinal());
+ Cursor cursor = mAdapter.getItem(position);
+ boolean isFolder = cursor.getInt(BookmarksLoader.COLUMN_INDEX_IS_FOLDER) != 0;
+ if (mCallbacks != null &&
+ mCallbacks.onBookmarkSelected(cursor, isFolder)) {
+ return;
}
- ed.apply();
- if (mBookmarksAdapter != null) {
- mBookmarksAdapter.switchViewMode(viewMode);
- }
- if (mViewMode == BookmarkViewMode.GRID) {
- if (mGridPage == null) {
- mGridPage = new GridView(this);
- if (mBookmarksAdapter != null) {
- mGridPage.setAdapter(mBookmarksAdapter);
- }
- mGridPage.setOnItemClickListener(mListener);
- mGridPage.setNumColumns(GridView.AUTO_FIT);
- mGridPage.setColumnWidth(
- BrowserActivity.getDesiredThumbnailWidth(this));
- mGridPage.setFocusable(true);
- mGridPage.setFocusableInTouchMode(true);
- mGridPage.setSelector(android.R.drawable.gallery_thumb);
- float density = getResources().getDisplayMetrics().density;
- mGridPage.setVerticalSpacing((int) (14 * density));
- mGridPage.setHorizontalSpacing((int) (8 * density));
- mGridPage.setStretchMode(GridView.STRETCH_SPACING);
- mGridPage.setScrollBarStyle(View.SCROLLBARS_INSIDE_INSET);
- mGridPage.setDrawSelectorOnTop(true);
- if (mMostVisited) {
- mGridPage.setEmptyView(mEmptyView);
- }
- if (!mCreateShortcut) {
- mGridPage.setOnCreateContextMenuListener(this);
- }
+ if (isFolder) {
+ String title = cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE);
+ Uri uri = ContentUris.withAppendedId(
+ BrowserContract.Bookmarks.CONTENT_URI_DEFAULT_FOLDER, id);
+ if (mCrumbs != null) {
+ // update crumbs
+ mCrumbs.pushView(title, uri);
}
- addContentView(mGridPage, FULL_SCREEN_PARAMS);
- if (mVerticalList != null) {
- ViewGroup parent = (ViewGroup) mVerticalList.getParent();
- if (parent != null) {
- parent.removeView(mVerticalList);
- }
- }
- } else {
- if (null == mVerticalList) {
- ListView listView = new ListView(this);
- if (mBookmarksAdapter != null) {
- listView.setAdapter(mBookmarksAdapter);
- }
- listView.setDrawSelectorOnTop(false);
- listView.setVerticalScrollBarEnabled(true);
- listView.setOnItemClickListener(mListener);
- if (mMostVisited) {
- listView.setEmptyView(mEmptyView);
- }
- if (!mCreateShortcut) {
- listView.setOnCreateContextMenuListener(this);
- }
- mVerticalList = listView;
- }
- addContentView(mVerticalList, FULL_SCREEN_PARAMS);
- if (mGridPage != null) {
- ViewGroup parent = (ViewGroup) mGridPage.getParent();
- if (parent != null) {
- parent.removeView(mGridPage);
- }
- }
+ loadFolder(uri);
}
}
- private static final ViewGroup.LayoutParams FULL_SCREEN_PARAMS
- = new ViewGroup.LayoutParams(
- ViewGroup.LayoutParams.MATCH_PARENT,
- ViewGroup.LayoutParams.MATCH_PARENT);
-
- private static final int SAVE_CURRENT_PAGE = 1000;
- private static final int ADAPTER_CREATED = 1001;
- private final Handler mHandler = new Handler() {
- @Override
- public void handleMessage(Message msg) {
- switch (msg.what) {
- case SAVE_CURRENT_PAGE:
- saveCurrentPage();
- break;
- case ADAPTER_CREATED:
- mBookmarksAdapter = (BrowserBookmarksAdapter) msg.obj;
- mBookmarksAdapter.switchViewMode(mViewMode);
- if (mGridPage != null) {
- mGridPage.setAdapter(mBookmarksAdapter);
- }
- if (mVerticalList != null) {
- mVerticalList.setAdapter(mBookmarksAdapter);
- }
- // Add our own listener in case there are favicons that
- // have yet to be loaded.
- if (mMostVisited) {
- IconListener listener = new IconListener() {
- public void onReceivedIcon(String url,
- Bitmap icon) {
- if (mGridPage != null) {
- mGridPage.setAdapter(mBookmarksAdapter);
- }
- if (mVerticalList != null) {
- mVerticalList.setAdapter(mBookmarksAdapter);
- }
- }
- };
- CombinedBookmarkHistoryActivity.getIconListenerSet()
- .addListener(listener);
- }
- break;
- }
- }
- };
-
- private AdapterView.OnItemClickListener mListener = new AdapterView.OnItemClickListener() {
- public void onItemClick(AdapterView parent, View v, int position, long id) {
- // It is possible that the view has been canceled when we get to
- // this point as back has a higher priority
- if (mCanceled) {
- android.util.Log.e(LOGTAG, "item clicked when dismissing");
- return;
- }
- if (!mCreateShortcut) {
- if (0 == position && !mMostVisited) {
- // XXX: Work-around for a framework issue.
- mHandler.sendEmptyMessage(SAVE_CURRENT_PAGE);
- } else {
- loadUrl(position);
- }
- } else {
- final Intent intent = createShortcutIntent(position);
- setResultToParent(RESULT_OK, intent);
- finish();
- }
- }
- };
-
- private Intent createShortcutIntent(int position) {
- String url = getUrl(position);
- String title = getBookmarkTitle(position);
- Bitmap touchIcon = getTouchIcon(position);
-
- final Intent i = new Intent();
- final Intent shortcutIntent = new Intent(Intent.ACTION_VIEW,
- Uri.parse(url));
- long urlHash = url.hashCode();
- long uniqueId = (urlHash << 32) | shortcutIntent.hashCode();
- shortcutIntent.putExtra(Browser.EXTRA_APPLICATION_ID,
- Long.toString(uniqueId));
- i.putExtra(Intent.EXTRA_SHORTCUT_INTENT, shortcutIntent);
- i.putExtra(Intent.EXTRA_SHORTCUT_NAME, title);
- // Use the apple-touch-icon if available
- if (touchIcon != null) {
- // Make a copy so we can modify the pixels. We can't use
- // createScaledBitmap or copy since they will preserve the config
- // and lose the ability to add alpha.
- Bitmap bm = Bitmap.createBitmap(mIconSize, mIconSize,
- Bitmap.Config.ARGB_8888);
- Canvas canvas = new Canvas(bm);
- Rect src = new Rect(0, 0, touchIcon.getWidth(),
- touchIcon.getHeight());
- Rect dest = new Rect(0, 0, bm.getWidth(), bm.getHeight());
-
- // Paint used for scaling the bitmap and drawing the rounded rect.
- Paint paint = new Paint(Paint.ANTI_ALIAS_FLAG);
- paint.setFilterBitmap(true);
- canvas.drawBitmap(touchIcon, src, dest, paint);
-
- // Construct a path from a round rect. This will allow drawing with
- // an inverse fill so we can punch a hole using the round rect.
- Path path = new Path();
- path.setFillType(Path.FillType.INVERSE_WINDING);
- RectF rect = new RectF(0, 0, bm.getWidth(), bm.getHeight());
- rect.inset(1, 1);
- path.addRoundRect(rect, 8f, 8f, Path.Direction.CW);
-
- // Reuse the paint and clear the outside of the rectangle.
- paint.setXfermode(new PorterDuffXfermode(PorterDuff.Mode.CLEAR));
- canvas.drawPath(path, paint);
-
- i.putExtra(Intent.EXTRA_SHORTCUT_ICON, bm);
- } else {
- Bitmap favicon = getFavicon(position);
- if (favicon == null) {
- i.putExtra(Intent.EXTRA_SHORTCUT_ICON_RESOURCE,
- Intent.ShortcutIconResource.fromContext(
- BrowserBookmarksPage.this,
- R.drawable.ic_launcher_shortcut_browser_bookmark));
- } else {
- Bitmap icon = BitmapFactory.decodeResource(getResources(),
- R.drawable.ic_launcher_shortcut_browser_bookmark_icon);
-
- // Make a copy of the regular icon so we can modify the pixels.
- Bitmap copy = icon.copy(Bitmap.Config.ARGB_8888, true);
- Canvas canvas = new Canvas(copy);
-
- // Make a Paint for the white background rectangle and for
- // filtering the favicon.
- Paint p = new Paint(Paint.ANTI_ALIAS_FLAG
- | Paint.FILTER_BITMAP_FLAG);
- p.setStyle(Paint.Style.FILL_AND_STROKE);
- p.setColor(Color.WHITE);
-
- final float density =
- getResources().getDisplayMetrics().density;
- // Create a rectangle that is slightly wider than the favicon
- final float iconSize = 16 * density; // 16x16 favicon
- final float padding = 2 * density; // white padding around icon
- final float rectSize = iconSize + 2 * padding;
-
- final Rect iconBounds =
- new Rect(0, 0, icon.getWidth(), icon.getHeight());
- final float x = iconBounds.exactCenterX() - (rectSize / 2);
- // Note: Subtract 2 dip from the y position since the box is
- // slightly higher than center. Use padding since it is already
- // 2 * density.
- final float y = iconBounds.exactCenterY() - (rectSize / 2)
- - padding;
- RectF r = new RectF(x, y, x + rectSize, y + rectSize);
-
- // Draw a white rounded rectangle behind the favicon
- canvas.drawRoundRect(r, 2, 2, p);
-
- // Draw the favicon in the same rectangle as the rounded
- // rectangle but inset by the padding
- // (results in a 16x16 favicon).
- r.inset(padding, padding);
- canvas.drawBitmap(favicon, null, r, p);
- i.putExtra(Intent.EXTRA_SHORTCUT_ICON, copy);
- }
- }
- // Do not allow duplicate items
- i.putExtra("duplicate", false);
- return i;
- }
-
- private void saveCurrentPage() {
- Intent i = new Intent(BrowserBookmarksPage.this,
- AddBookmarkPage.class);
- i.putExtras(getIntent());
- startActivityForResult(i, BOOKMARKS_SAVE);
+ /* package */ static Intent createShortcutIntent(Context context, Cursor cursor) {
+ String url = cursor.getString(BookmarksLoader.COLUMN_INDEX_URL);
+ String title = cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE);
+ Bitmap touchIcon = getBitmap(cursor, BookmarksLoader.COLUMN_INDEX_TOUCH_ICON);
+ Bitmap favicon = getBitmap(cursor, BookmarksLoader.COLUMN_INDEX_FAVICON);
+ return BookmarkUtils.createAddToHomeIntent(context, url, title, touchIcon, favicon);
}
private void loadUrl(int position) {
- Intent intent = (new Intent()).setAction(getUrl(position));
- setResultToParent(RESULT_OK, intent);
- finish();
+ if (mCallbacks != null) {
+ mCallbacks.onBookmarkSelected(mAdapter.getItem(position), false);
+ }
}
- @Override
- public boolean onCreateOptionsMenu(Menu menu) {
- boolean result = super.onCreateOptionsMenu(menu);
- if (!mCreateShortcut && !mMostVisited) {
- MenuInflater inflater = getMenuInflater();
- inflater.inflate(R.menu.bookmarks, menu);
- return true;
+ private void openInNewWindow(int position) {
+ if (mCallbacks != null) {
+ Cursor c = mAdapter.getItem(position);
+ boolean isFolder = c.getInt(BookmarksLoader.COLUMN_INDEX_IS_FOLDER) == 1;
+ if (isFolder) {
+ long id = c.getLong(BookmarksLoader.COLUMN_INDEX_ID);
+ new OpenAllInTabsTask(id).execute();
+ } else {
+ mCallbacks.onOpenInNewWindow(c);
+ }
}
- return result;
}
- @Override
- public boolean onPrepareOptionsMenu(Menu menu) {
- boolean result = super.onPrepareOptionsMenu(menu);
- if (mCreateShortcut || mMostVisited || mBookmarksAdapter == null
- || mBookmarksAdapter.getCount() == 0) {
- // No need to show the menu if there are no items.
- return result;
+ class OpenAllInTabsTask extends AsyncTask<Void, Void, Cursor> {
+ long mFolderId;
+ public OpenAllInTabsTask(long id) {
+ mFolderId = id;
}
- MenuItem switchItem = menu.findItem(R.id.switch_mode_menu_id);
- int titleResId;
- int iconResId;
- if (mViewMode == BookmarkViewMode.GRID) {
- titleResId = R.string.switch_to_list;
- iconResId = R.drawable.ic_menu_list;
- } else {
- titleResId = R.string.switch_to_thumbnails;
- iconResId = R.drawable.ic_menu_thumbnail;
+
+ @Override
+ protected Cursor doInBackground(Void... params) {
+ Context c = getActivity();
+ if (c == null) return null;
+ return c.getContentResolver().query(BookmarkUtils.getBookmarksUri(c),
+ BookmarksLoader.PROJECTION, BrowserContract.Bookmarks.PARENT + "=?",
+ new String[] { Long.toString(mFolderId) }, null);
}
- switchItem.setTitle(titleResId);
- switchItem.setIcon(iconResId);
- return true;
+
+ @Override
+ protected void onPostExecute(Cursor result) {
+ if (mCallbacks != null) {
+ while (result.moveToNext()) {
+ mCallbacks.onOpenInNewWindow(result);
+ }
+ }
+ }
+
+ }
+
+ private void editBookmark(int position) {
+ Intent intent = new Intent(getActivity(), AddBookmarkPage.class);
+ Cursor cursor = mAdapter.getItem(position);
+ Bundle item = new Bundle();
+ item.putString(BrowserContract.Bookmarks.TITLE,
+ cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE));
+ item.putString(BrowserContract.Bookmarks.URL,
+ cursor.getString(BookmarksLoader.COLUMN_INDEX_URL));
+ byte[] data = cursor.getBlob(BookmarksLoader.COLUMN_INDEX_FAVICON);
+ if (data != null) {
+ item.putParcelable(BrowserContract.Bookmarks.FAVICON,
+ BitmapFactory.decodeByteArray(data, 0, data.length));
+ }
+ item.putLong(BrowserContract.Bookmarks._ID,
+ cursor.getLong(BookmarksLoader.COLUMN_INDEX_ID));
+ item.putLong(BrowserContract.Bookmarks.PARENT,
+ cursor.getLong(BookmarksLoader.COLUMN_INDEX_PARENT));
+ intent.putExtra(AddBookmarkPage.EXTRA_EDIT_BOOKMARK, item);
+ intent.putExtra(AddBookmarkPage.EXTRA_IS_FOLDER,
+ cursor.getInt(BookmarksLoader.COLUMN_INDEX_IS_FOLDER) == 1);
+ startActivity(intent);
+ }
+
+ private void displayRemoveBookmarkDialog(final int position) {
+ // Put up a dialog asking if the user really wants to
+ // delete the bookmark
+ Cursor cursor = mAdapter.getItem(position);
+ long id = cursor.getLong(BookmarksLoader.COLUMN_INDEX_ID);
+ String title = cursor.getString(BookmarksLoader.COLUMN_INDEX_TITLE);
+ Context context = getActivity();
+ BookmarkUtils.displayRemoveBookmarkDialog(id, title, context, null);
+ }
+
+ private String getUrl(int position) {
+ return getUrl(mAdapter.getItem(position));
+ }
+
+ /* package */ static String getUrl(Cursor c) {
+ return c.getString(BookmarksLoader.COLUMN_INDEX_URL);
+ }
+
+ private void copy(CharSequence text) {
+ ClipboardManager cm = (ClipboardManager) getActivity().getSystemService(
+ Context.CLIPBOARD_SERVICE);
+ cm.setPrimaryClip(ClipData.newRawUri(null, Uri.parse(text.toString())));
}
@Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
- case R.id.new_context_menu_id:
- saveCurrentPage();
- break;
+ case R.id.thumbnail_view:
+ selectView(VIEW_THUMBNAILS);
+ return true;
+ case R.id.list_view:
+ selectView(VIEW_LIST);
+ return true;
+ }
+ return super.onOptionsItemSelected(item);
+ }
- case R.id.switch_mode_menu_id:
- if (mViewMode == BookmarkViewMode.GRID) {
- switchViewMode(BookmarkViewMode.LIST);
+ @Override
+ public void onConfigurationChanged(Configuration newConfig) {
+ super.onConfigurationChanged(newConfig);
+ Resources res = getActivity().getResources();
+ int horizontalSpacing = (int) res.getDimension(R.dimen.combo_horizontalSpacing);
+ mGrid.setHorizontalSpacing(horizontalSpacing);
+ int paddingLeftRight = (int) res.getDimension(R.dimen.combo_paddingLeftRight);
+ int paddingTop = (int) res.getDimension(R.dimen.combo_paddingTop);
+ mRoot.setPadding(paddingLeftRight, paddingTop,
+ paddingLeftRight, 0);
+ }
+
+ @Override
+ public void onPrepareOptionsMenu(Menu menu) {
+ super.onPrepareOptionsMenu(menu);
+ menu.findItem(R.id.list_view).setVisible(mCurrentView != VIEW_LIST);
+ menu.findItem(R.id.thumbnail_view).setVisible(mCurrentView != VIEW_THUMBNAILS);
+ }
+
+ void selectView(int view) {
+ if (view == mCurrentView) {
+ return;
+ }
+ mCurrentView = view;
+ SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(getActivity());
+ Editor edit = prefs.edit();
+ edit.putInt(PREF_SELECTED_VIEW, mCurrentView);
+ edit.apply();
+ if (mEmptyView.getVisibility() == View.VISIBLE) {
+ return;
+ }
+ setupBookmarkView();
+ }
+
+ private void setupBookmarkView() {
+ mAdapter.selectView(mCurrentView);
+ switch (mCurrentView) {
+ case VIEW_THUMBNAILS:
+ mList.setAdapter(null);
+ mGrid.setAdapter(mAdapter);
+ mGrid.setVisibility(View.VISIBLE);
+ mList.setVisibility(View.GONE);
+ break;
+ case VIEW_LIST:
+ mGrid.setAdapter(null);
+ mList.setAdapter(mAdapter);
+ mGrid.setVisibility(View.GONE);
+ mList.setVisibility(View.VISIBLE);
+ break;
+ }
+ }
+
+ /**
+ * BreadCrumb controller callback
+ */
+ @Override
+ public void onTop(int level, Object data) {
+ Uri uri = (Uri) data;
+ if (uri == null) {
+ // top level
+ uri = BrowserContract.Bookmarks.CONTENT_URI_DEFAULT_FOLDER;
+ }
+ loadFolder(uri);
+ }
+
+ /**
+ * @param uri
+ */
+ private void loadFolder(Uri uri) {
+ LoaderManager manager = getLoaderManager();
+ BookmarksLoader loader =
+ (BookmarksLoader) ((Loader<?>) manager.getLoader(LOADER_BOOKMARKS));
+ loader.setUri(uri);
+ loader.forceLoad();
+ if (mCallbacks != null) {
+ mCallbacks.onFolderChanged(mCrumbs.getTopLevel(), uri);
+ }
+ }
+
+ @Override
+ public boolean onMenuItemClick(MenuItem item) {
+ switch (item.getItemId()) {
+ case R.id.list_view:
+ selectView(BrowserBookmarksPage.VIEW_LIST);
+ return true;
+ case R.id.thumbnail_view:
+ selectView(BrowserBookmarksPage.VIEW_THUMBNAILS);
+ return true;
+ }
+ return false;
+ }
+
+ public boolean onBackPressed() {
+ if (canGoBack()) {
+ mCrumbs.popView();
+ return true;
+ }
+ return false;
+ }
+
+ private boolean canGoBack() {
+ Crumb c = mCrumbs.getTopCrumb();
+ return c != null && c.canGoBack;
+ }
+
+ public void setCallbackListener(BookmarksPageCallbacks callbackListener) {
+ mCallbacks = callbackListener;
+ }
+
+ public void setEnableContextMenu(boolean enable) {
+ mEnableContextMenu = enable;
+ if (mGrid != null) {
+ if (mEnableContextMenu) {
+ registerForContextMenu(mGrid);
} else {
- switchViewMode(BookmarkViewMode.GRID);
+ unregisterForContextMenu(mGrid);
+ mGrid.setLongClickable(false);
}
- break;
-
- default:
- return super.onOptionsItemSelected(item);
}
- return true;
+ if (mList != null) {
+ if (mEnableContextMenu) {
+ registerForContextMenu(mList);
+ } else {
+ unregisterForContextMenu(mList);
+ mList.setLongClickable(false);
+ }
+ }
}
- private void openInNewWindow(int position) {
- Bundle b = new Bundle();
- b.putBoolean("new_window", true);
- setResultToParent(RESULT_OK,
- (new Intent()).setAction(getUrl(position)).putExtras(b));
+ private static class LookupBookmarkCount extends AsyncTask<Long, Void, Integer> {
+ Context mContext;
+ BookmarkItem mHeader;
- finish();
+ public LookupBookmarkCount(Context context, BookmarkItem header) {
+ mContext = context;
+ mHeader = header;
+ }
+
+ @Override
+ protected Integer doInBackground(Long... params) {
+ if (params.length != 1) {
+ throw new IllegalArgumentException("Missing folder id!");
+ }
+ Uri uri = BookmarkUtils.getBookmarksUri(mContext);
+ Cursor c = mContext.getContentResolver().query(uri,
+ null, BrowserContract.Bookmarks.PARENT + "=?",
+ new String[] {params[0].toString()}, null);
+ return c.getCount();
+ }
+
+ @Override
+ protected void onPostExecute(Integer result) {
+ if (result > 0) {
+ mHeader.setUrl(mContext.getString(R.string.contextheader_folder_bookmarkcount,
+ result));
+ } else if (result == 0) {
+ mHeader.setUrl(mContext.getString(R.string.contextheader_folder_empty));
+ }
+ }
}
+ public void setBreadCrumbVisibility(int visibility) {
+ mCrumbVisibility = visibility;
+ if (mCrumbs != null) {
+ mCrumbs.setVisibility(mCrumbVisibility);
+ }
+ }
- private void editBookmark(int position) {
- Intent intent = new Intent(BrowserBookmarksPage.this,
- AddBookmarkPage.class);
- intent.putExtra("bookmark", getRow(position));
- startActivityForResult(intent, BOOKMARKS_SAVE);
+ public void setBreadCrumbUseBackButton(boolean use) {
+ mCrumbBackButton = use;
+ if (mCrumbs != null) {
+ mCrumbs.setUseBackButton(mCrumbBackButton);
+ }
+ }
+
+ public void setBreadCrumbMaxVisible(int max) {
+ mCrumbMaxVisible = max;
+ if (mCrumbs != null) {
+ mCrumbs.setMaxVisible(mCrumbMaxVisible);
+ }
}
@Override
- protected void onActivityResult(int requestCode, int resultCode,
- Intent data) {
- switch(requestCode) {
- case BOOKMARKS_SAVE:
- if (resultCode == RESULT_OK) {
- Bundle extras;
- if (data != null && (extras = data.getExtras()) != null) {
- // If there are extras, then we need to save
- // the edited bookmark. This is done in updateRow()
- String title = extras.getString("title");
- String url = extras.getString("url");
- if (title != null && url != null) {
- mBookmarksAdapter.updateRow(extras);
- }
- } else {
- // extras == null then a new bookmark was added to
- // the database.
- refreshList();
- }
- }
- break;
- default:
- break;
- }
- }
-
- private void displayRemoveBookmarkDialog(int position) {
- // Put up a dialog asking if the user really wants to
- // delete the bookmark
- final int deletePos = position;
- new AlertDialog.Builder(this)
- .setTitle(R.string.delete_bookmark)
- .setIcon(android.R.drawable.ic_dialog_alert)
- .setMessage(getText(R.string.delete_bookmark_warning).toString().replace(
- "%s", getBookmarkTitle(deletePos)))
- .setPositiveButton(R.string.ok,
- new DialogInterface.OnClickListener() {
- public void onClick(DialogInterface dialog, int whichButton) {
- deleteBookmark(deletePos);
- }
- })
- .setNegativeButton(R.string.cancel, null)
- .show();
- }
-
- /**
- * Refresh the shown list after the database has changed.
- */
- private void refreshList() {
- if (mBookmarksAdapter == null) return;
- mBookmarksAdapter.refreshList();
- }
-
- /**
- * Return a hashmap representing the currently highlighted row.
- */
- public Bundle getRow(int position) {
- return mBookmarksAdapter == null ? null
- : mBookmarksAdapter.getRow(position);
- }
-
- /**
- * Return the url of the currently highlighted row.
- */
- public String getUrl(int position) {
- return mBookmarksAdapter == null ? null
- : mBookmarksAdapter.getUrl(position);
- }
-
- /**
- * Return the favicon of the currently highlighted row.
- */
- public Bitmap getFavicon(int position) {
- return mBookmarksAdapter == null ? null
- : mBookmarksAdapter.getFavicon(position);
- }
-
- private Bitmap getTouchIcon(int position) {
- return mBookmarksAdapter == null ? null
- : mBookmarksAdapter.getTouchIcon(position);
- }
-
- private void copy(CharSequence text) {
- try {
- IClipboard clip = IClipboard.Stub.asInterface(ServiceManager.getService("clipboard"));
- if (clip != null) {
- clip.setClipboardText(text);
+ public void onSharedPreferenceChanged(
+ SharedPreferences sharedPreferences, String key) {
+ if (PREF_ACCOUNT_NAME.equals(key) || PREF_ACCOUNT_TYPE.equals(key)) {
+ mCrumbs.setController(null);
+ mCrumbs.clear();
+ LoaderManager lm = getLoaderManager();
+ lm.restartLoader(LOADER_BOOKMARKS, null, this);
+ mCrumbs.setController(this);
+ String name = getString(R.string.bookmarks);
+ mCrumbs.pushView(name, false, BrowserContract.Bookmarks.CONTENT_URI_DEFAULT_FOLDER);
+ if (mCallbacks != null) {
+ mCallbacks.onFolderChanged(1, BrowserContract.Bookmarks.CONTENT_URI_DEFAULT_FOLDER);
}
- } catch (android.os.RemoteException e) {
- Log.e(LOGTAG, "Copy failed", e);
- }
- }
-
- public String getBookmarkTitle(int position) {
- return mBookmarksAdapter == null ? null
- : mBookmarksAdapter.getTitle(position);
- }
-
- /**
- * Delete the currently highlighted row.
- */
- public void deleteBookmark(int position) {
- if (mBookmarksAdapter == null) return;
- mBookmarksAdapter.deleteRow(position);
- }
-
- @Override
- public void onBackPressed() {
- setResultToParent(RESULT_CANCELED, null);
- mCanceled = true;
- super.onBackPressed();
- }
-
- // This Activity is generally a sub-Activity of
- // CombinedBookmarkHistoryActivity. In that situation, we need to pass our
- // result code up to our parent. However, if someone calls this Activity
- // directly, then this has no parent, and it needs to set it on itself.
- private void setResultToParent(int resultCode, Intent data) {
- Activity parent = getParent();
- if (parent == null) {
- setResult(resultCode, data);
- } else {
- ((CombinedBookmarkHistoryActivity) parent).setResultFromChild(
- resultCode, data);
}
}
}
diff --git a/src/com/android/browser/BrowserHistoryPage.java b/src/com/android/browser/BrowserHistoryPage.java
index 23080f8..44f358d 100644
--- a/src/com/android/browser/BrowserHistoryPage.java
+++ b/src/com/android/browser/BrowserHistoryPage.java
@@ -17,198 +17,344 @@
package com.android.browser;
import android.app.Activity;
-import android.app.ExpandableListActivity;
+import android.app.AlertDialog;
+import android.app.Dialog;
+import android.app.Fragment;
+import android.app.FragmentBreadCrumbs;
+import android.app.LoaderManager.LoaderCallbacks;
+import android.content.ClipboardManager;
+import android.content.ContentResolver;
import android.content.Context;
+import android.content.CursorLoader;
+import android.content.DialogInterface;
import android.content.Intent;
+import android.content.Loader;
+import android.content.SharedPreferences;
import android.content.pm.PackageManager;
import android.content.pm.ResolveInfo;
import android.database.Cursor;
+import android.database.DataSetObserver;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
+import android.graphics.drawable.Drawable;
+import android.net.Uri;
+import android.os.AsyncTask;
import android.os.Bundle;
-import android.os.ServiceManager;
+import android.preference.PreferenceManager;
import android.provider.Browser;
-import android.text.IClipboard;
-import android.util.Log;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Combined;
import android.view.ContextMenu;
+import android.view.ContextMenu.ContextMenuInfo;
+import android.view.LayoutInflater;
import android.view.Menu;
import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
import android.view.ViewGroup;
-import android.view.ViewGroup.LayoutParams;
-import android.view.ContextMenu.ContextMenuInfo;
import android.view.ViewStub;
import android.webkit.WebIconDatabase.IconListener;
-import android.widget.ExpandableListAdapter;
-import android.widget.ExpandableListView;
-import android.widget.ExpandableListView.ExpandableListContextMenuInfo;
+import android.widget.AbsListView;
+import android.widget.AdapterView;
+import android.widget.AdapterView.AdapterContextMenuInfo;
+import android.widget.AdapterView.OnItemClickListener;
+import android.widget.BaseAdapter;
+import android.widget.ListView;
+import android.widget.TextView;
import android.widget.Toast;
/**
* Activity for displaying the browser's history, divided into
* days of viewing.
*/
-public class BrowserHistoryPage extends ExpandableListActivity {
- private HistoryAdapter mAdapter;
- private boolean mDisableNewWindow;
- private HistoryItem mContextHeader;
+public class BrowserHistoryPage extends Fragment
+ implements LoaderCallbacks<Cursor> {
- private final static String LOGTAG = "browser";
+ static final int LOADER_HISTORY = 1;
+ static final int LOADER_MOST_VISITED = 2;
+
+ BookmarksHistoryCallbacks mCallbacks;
+ HistoryAdapter mAdapter;
+ HistoryChildWrapper mChildWrapper;
+ boolean mDisableNewWindow;
+ HistoryItem mContextHeader;
+ String mMostVisitsLimit;
+ ListView mGroupList, mChildList;
+ private ViewGroup mPrefsContainer;
+ private FragmentBreadCrumbs mFragmentBreadCrumbs;
// Implementation of WebIconDatabase.IconListener
- private class IconReceiver implements IconListener {
+ class IconReceiver implements IconListener {
+ @Override
public void onReceivedIcon(String url, Bitmap icon) {
- setListAdapter(mAdapter);
+ mAdapter.notifyDataSetChanged();
}
}
- // Instance of IconReceiver
- private final IconReceiver mIconReceiver = new IconReceiver();
- /**
- * Report back to the calling activity to load a site.
- * @param url Site to load.
- * @param newWindow True if the URL should be loaded in a new window
- */
- private void loadUrl(String url, boolean newWindow) {
- Intent intent = new Intent().setAction(url);
- if (newWindow) {
- Bundle b = new Bundle();
- b.putBoolean("new_window", true);
- intent.putExtras(b);
- }
- setResultToParent(RESULT_OK, intent);
- finish();
+ // Instance of IconReceiver
+ final IconReceiver mIconReceiver = new IconReceiver();
+ private View mRoot;
+
+ static interface HistoryQuery {
+ static final String[] PROJECTION = new String[] {
+ Combined._ID, // 0
+ Combined.DATE_LAST_VISITED, // 1
+ Combined.TITLE, // 2
+ Combined.URL, // 3
+ Combined.FAVICON, // 4
+ Combined.VISITS, // 5
+ Combined.IS_BOOKMARK, // 6
+ };
+
+ static final int INDEX_ID = 0;
+ static final int INDEX_DATE_LAST_VISITED = 1;
+ static final int INDEX_TITE = 2;
+ static final int INDEX_URL = 3;
+ static final int INDEX_FAVICON = 4;
+ static final int INDEX_VISITS = 5;
+ static final int INDEX_IS_BOOKMARK = 6;
}
-
+
private void copy(CharSequence text) {
- try {
- IClipboard clip = IClipboard.Stub.asInterface(ServiceManager.getService("clipboard"));
- if (clip != null) {
- clip.setClipboardText(text);
+ ClipboardManager cm = (ClipboardManager) getActivity().getSystemService(
+ Context.CLIPBOARD_SERVICE);
+ cm.setText(text);
+ }
+
+ static BrowserHistoryPage newInstance(BookmarksHistoryCallbacks cb, Bundle args) {
+ BrowserHistoryPage bhp = new BrowserHistoryPage();
+ bhp.mCallbacks = cb;
+ bhp.setArguments(args);
+ return bhp;
+ }
+
+ @Override
+ public Loader<Cursor> onCreateLoader(int id, Bundle args) {
+ SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(
+ getActivity());
+ String accountType = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE, null);
+ String accountName = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, null);
+ Uri.Builder combinedBuilder = Combined.CONTENT_URI.buildUpon();
+ combinedBuilder.appendQueryParameter(BrowserContract.Bookmarks.PARAM_ACCOUNT_TYPE, accountType);
+ combinedBuilder.appendQueryParameter(BrowserContract.Bookmarks.PARAM_ACCOUNT_NAME, accountName);
+
+ switch (id) {
+ case LOADER_HISTORY: {
+ String sort = Combined.DATE_LAST_VISITED + " DESC";
+ String where = Combined.VISITS + " > 0";
+ CursorLoader loader = new CursorLoader(getActivity(), combinedBuilder.build(),
+ HistoryQuery.PROJECTION, where, null, sort);
+ return loader;
}
- } catch (android.os.RemoteException e) {
- Log.e(LOGTAG, "Copy failed", e);
+
+ case LOADER_MOST_VISITED: {
+ Uri uri = combinedBuilder
+ .appendQueryParameter(BrowserContract.PARAM_LIMIT, mMostVisitsLimit)
+ .build();
+ String where = Combined.VISITS + " > 0";
+ CursorLoader loader = new CursorLoader(getActivity(), uri,
+ HistoryQuery.PROJECTION, where, null, Combined.VISITS + " DESC");
+ return loader;
+ }
+
+ default: {
+ throw new IllegalArgumentException();
+ }
+ }
+ }
+
+ void selectGroup(int position) {
+ mGroupItemClickListener.onItemClick(null,
+ mAdapter.getGroupView(position, false, null, null),
+ position, position);
+ }
+
+ void checkIfEmpty() {
+ if (mAdapter.mMostVisited != null && mAdapter.mHistoryCursor != null) {
+ // Both cursors have loaded - check to see if we have data
+ if (mAdapter.isEmpty()) {
+ mRoot.findViewById(R.id.history).setVisibility(View.GONE);
+ mRoot.findViewById(android.R.id.empty).setVisibility(View.VISIBLE);
+ } else {
+ mRoot.findViewById(R.id.history).setVisibility(View.VISIBLE);
+ mRoot.findViewById(android.R.id.empty).setVisibility(View.GONE);
+ }
}
}
@Override
- protected void onCreate(Bundle icicle) {
- super.onCreate(icicle);
- setTitle(R.string.browser_history);
-
- final String whereClause = Browser.BookmarkColumns.VISITS + " > 0"
- // In AddBookmarkPage, where we save new bookmarks, we add
- // three visits to newly created bookmarks, so that
- // bookmarks that have not been visited will show up in the
- // most visited, and higher in the goto search box.
- // However, this puts the site in the history, unless we
- // ignore sites with a DATE of 0, which the next line does.
- + " AND " + Browser.BookmarkColumns.DATE + " > 0";
- final String orderBy = Browser.BookmarkColumns.DATE + " DESC";
-
- Cursor cursor = managedQuery(
- Browser.BOOKMARKS_URI,
- Browser.HISTORY_PROJECTION,
- whereClause, null, orderBy);
-
- mAdapter = new HistoryAdapter(this, cursor,
- Browser.HISTORY_PROJECTION_DATE_INDEX);
- setListAdapter(mAdapter);
- final ExpandableListView list = getExpandableListView();
- list.setOnCreateContextMenuListener(this);
- View v = new ViewStub(this, R.layout.empty_history);
- addContentView(v, new LayoutParams(LayoutParams.MATCH_PARENT,
- LayoutParams.MATCH_PARENT));
- list.setEmptyView(v);
- // Do not post the runnable if there is nothing in the list.
- if (list.getExpandableListAdapter().getGroupCount() > 0) {
- list.post(new Runnable() {
- public void run() {
- // In case the history gets cleared before this event
- // happens.
- if (list.getExpandableListAdapter().getGroupCount() > 0) {
- list.expandGroup(0);
- }
+ public void onLoadFinished(Loader<Cursor> loader, Cursor data) {
+ switch (loader.getId()) {
+ case LOADER_HISTORY: {
+ mAdapter.changeCursor(data);
+ if (!mAdapter.isEmpty()
+ && mGroupList.getCheckedItemPosition() == ListView.INVALID_POSITION) {
+ selectGroup(0);
}
- });
+
+ checkIfEmpty();
+ break;
+ }
+
+ case LOADER_MOST_VISITED: {
+ mAdapter.changeMostVisitedCursor(data);
+
+ checkIfEmpty();
+ break;
+ }
+
+ default: {
+ throw new IllegalArgumentException();
+ }
}
- mDisableNewWindow = getIntent().getBooleanExtra("disable_new_window",
- false);
+ }
+
+ @Override
+ public void onLoaderReset(Loader<Cursor> loader) {
+ }
+
+ @Override
+ public void onCreate(Bundle icicle) {
+ super.onCreate(icicle);
+
+ setHasOptionsMenu(true);
+
+ Bundle args = getArguments();
+ mDisableNewWindow = args.getBoolean(BrowserBookmarksPage.EXTRA_DISABLE_WINDOW, false);
+ int mvlimit = getResources().getInteger(R.integer.most_visits_limit);
+ mMostVisitsLimit = Integer.toString(mvlimit);
+ }
+
+ @Override
+ public View onCreateView(LayoutInflater inflater, ViewGroup container,
+ Bundle savedInstanceState) {
+ mRoot = inflater.inflate(R.layout.history, container, false);
+ ViewStub stub = (ViewStub) mRoot.findViewById(R.id.pref_stub);
+ stub.setLayoutResource(com.android.internal.R.layout.preference_list_content);
+ stub.inflate();
+ mGroupList = (ListView) mRoot.findViewById(android.R.id.list);
+ mPrefsContainer = (ViewGroup) mRoot.findViewById(com.android.internal.R.id.prefs_frame);
+ mFragmentBreadCrumbs = (FragmentBreadCrumbs) mRoot.findViewById(android.R.id.title);
+ mFragmentBreadCrumbs.setMaxVisible(1);
+ mFragmentBreadCrumbs.setActivity(getActivity());
+ mPrefsContainer.setVisibility(View.VISIBLE);
+ mAdapter = new HistoryAdapter(getActivity());
+ mGroupList.setAdapter(new HistoryGroupWrapper(mAdapter));
+ mGroupList.setOnItemClickListener(mGroupItemClickListener);
+ mGroupList.setChoiceMode(AbsListView.CHOICE_MODE_SINGLE);
+ mChildWrapper = new HistoryChildWrapper(mAdapter);
+ mChildList = new ListView(getActivity());
+ mChildList.setAdapter(mChildWrapper);
+ mChildList.setOnItemClickListener(mChildItemClickListener);
+ registerForContextMenu(mChildList);
+ ViewGroup prefs = (ViewGroup) mRoot.findViewById(com.android.internal.R.id.prefs);
+ prefs.addView(mChildList);
+
+ // Start the loaders
+ getLoaderManager().restartLoader(LOADER_HISTORY, null, this);
+ getLoaderManager().restartLoader(LOADER_MOST_VISITED, null, this);
// Register to receive icons in case they haven't all been loaded.
- CombinedBookmarkHistoryActivity.getIconListenerSet()
- .addListener(mIconReceiver);
+ CombinedBookmarkHistoryView.getIconListenerSet().addListener(mIconReceiver);
+ return mRoot;
+ }
- Activity parent = getParent();
- if (null == parent
- || !(parent instanceof CombinedBookmarkHistoryActivity)) {
- throw new AssertionError("history page can only be viewed as a tab"
- + "in CombinedBookmarkHistoryActivity");
+ private OnItemClickListener mGroupItemClickListener = new OnItemClickListener() {
+ @Override
+ public void onItemClick(
+ AdapterView<?> parent, View view, int position, long id) {
+ CharSequence title = ((TextView) view).getText();
+ mFragmentBreadCrumbs.setTitle(title, title);
+ mChildWrapper.setSelectedGroup(position);
+ mGroupList.setItemChecked(position, true);
}
- // initialize the result to canceled, so that if the user just presses
- // back then it will have the correct result
- setResultToParent(RESULT_CANCELED, null);
- }
+ };
+
+ private OnItemClickListener mChildItemClickListener = new OnItemClickListener() {
+ @Override
+ public void onItemClick(
+ AdapterView<?> parent, View view, int position, long id) {
+ mCallbacks.onUrlSelected(((HistoryItem) view).getUrl(), false);
+ }
+ };
@Override
- protected void onDestroy() {
+ public void onDestroy() {
super.onDestroy();
- CombinedBookmarkHistoryActivity.getIconListenerSet()
- .removeListener(mIconReceiver);
+ CombinedBookmarkHistoryView.getIconListenerSet().removeListener(mIconReceiver);
+ getLoaderManager().destroyLoader(LOADER_HISTORY);
+ getLoaderManager().destroyLoader(LOADER_MOST_VISITED);
}
@Override
- public boolean onCreateOptionsMenu(Menu menu) {
- super.onCreateOptionsMenu(menu);
- MenuInflater inflater = getMenuInflater();
+ public void onCreateOptionsMenu(Menu menu, MenuInflater inflater) {
inflater.inflate(R.menu.history, menu);
- return true;
}
@Override
- public boolean onPrepareOptionsMenu(Menu menu) {
- menu.findItem(R.id.clear_history_menu_id).setVisible(Browser.canClearHistory(this.getContentResolver()));
- return true;
- }
-
- @Override
public boolean onOptionsItemSelected(MenuItem item) {
switch (item.getItemId()) {
case R.id.clear_history_menu_id:
- Browser.clearHistory(getContentResolver());
- // BrowserHistoryPage is always a child of
- // CombinedBookmarkHistoryActivity
- ((CombinedBookmarkHistoryActivity) getParent())
- .removeParentChildRelationShips();
- mAdapter.refreshData();
+ final ContentResolver resolver = getActivity().getContentResolver();
+ final ClearHistoryTask clear = new ClearHistoryTask(resolver, mCallbacks);
+ AlertDialog.Builder builder = new AlertDialog.Builder(getActivity())
+ .setTitle(R.string.clear)
+ .setMessage(R.string.pref_privacy_clear_history_dlg)
+ .setIcon(android.R.drawable.ic_dialog_alert)
+ .setNegativeButton(R.string.cancel, null)
+ .setPositiveButton(R.string.ok, new DialogInterface.OnClickListener() {
+ @Override
+ public void onClick(DialogInterface dialog, int which) {
+ if (which == DialogInterface.BUTTON_POSITIVE) {
+ clear.execute();
+ }
+ }
+ });
+ final Dialog dialog = builder.create();
+ dialog.show();
return true;
-
+
default:
break;
- }
+ }
return super.onOptionsItemSelected(item);
}
- @Override
- public void onCreateContextMenu(ContextMenu menu, View v,
- ContextMenuInfo menuInfo) {
- ExpandableListContextMenuInfo i =
- (ExpandableListContextMenuInfo) menuInfo;
- // Do not allow a context menu to come up from the group views.
- if (!(i.targetView instanceof HistoryItem)) {
- return;
+ static class ClearHistoryTask extends AsyncTask<Void, Void, Void> {
+ ContentResolver mResolver;
+ BookmarksHistoryCallbacks mCallbacks;
+
+ public ClearHistoryTask(ContentResolver resolver,
+ BookmarksHistoryCallbacks callbacks) {
+ mResolver = resolver;
+ mCallbacks = callbacks;
+ }
+ @Override
+ protected Void doInBackground(Void... params) {
+ Browser.clearHistory(mResolver);
+ return null;
}
+ @Override
+ protected void onPostExecute(Void result) {
+ mCallbacks.onRemoveParentChildRelationships();
+ }
+ }
+
+ @Override
+ public void onCreateContextMenu(ContextMenu menu, View v, ContextMenuInfo menuInfo) {
+ AdapterContextMenuInfo i = (AdapterContextMenuInfo) menuInfo;
+
// Inflate the menu
- MenuInflater inflater = getMenuInflater();
+ Activity parent = getActivity();
+ MenuInflater inflater = parent.getMenuInflater();
inflater.inflate(R.menu.historycontext, menu);
HistoryItem historyItem = (HistoryItem) i.targetView;
// Setup the header
if (mContextHeader == null) {
- mContextHeader = new HistoryItem(this);
+ mContextHeader = new HistoryItem(parent, false);
} else if (mContextHeader.getParent() != null) {
((ViewGroup) mContextHeader.getParent()).removeView(mContextHeader);
}
@@ -225,114 +371,293 @@
item.setTitle(R.string.remove_from_bookmarks);
}
// decide whether to show the share link option
- PackageManager pm = getPackageManager();
+ PackageManager pm = parent.getPackageManager();
Intent send = new Intent(Intent.ACTION_SEND);
send.setType("text/plain");
ResolveInfo ri = pm.resolveActivity(send, PackageManager.MATCH_DEFAULT_ONLY);
menu.findItem(R.id.share_link_context_menu_id).setVisible(ri != null);
-
+
super.onCreateContextMenu(menu, v, menuInfo);
}
-
+
@Override
public boolean onContextItemSelected(MenuItem item) {
- ExpandableListContextMenuInfo i =
- (ExpandableListContextMenuInfo) item.getMenuInfo();
+ AdapterContextMenuInfo i =
+ (AdapterContextMenuInfo) item.getMenuInfo();
+ if (i == null) {
+ return false;
+ }
HistoryItem historyItem = (HistoryItem) i.targetView;
String url = historyItem.getUrl();
String title = historyItem.getName();
+ Activity activity = getActivity();
switch (item.getItemId()) {
case R.id.open_context_menu_id:
- loadUrl(url, false);
+ mCallbacks.onUrlSelected(url, false);
return true;
case R.id.new_window_context_menu_id:
- loadUrl(url, true);
+ mCallbacks.onUrlSelected(url, true);
return true;
case R.id.save_to_bookmarks_menu_id:
if (historyItem.isBookmark()) {
- Bookmarks.removeFromBookmarks(this, getContentResolver(),
+ Bookmarks.removeFromBookmarks(activity, activity.getContentResolver(),
url, title);
} else {
- Browser.saveBookmark(this, title, url);
+ Browser.saveBookmark(activity, title, url);
}
return true;
case R.id.share_link_context_menu_id:
- Browser.sendString(this, url,
- getText(R.string.choosertitle_sharevia).toString());
+ Browser.sendString(activity, url,
+ activity.getText(R.string.choosertitle_sharevia).toString());
return true;
case R.id.copy_url_context_menu_id:
copy(url);
return true;
case R.id.delete_context_menu_id:
- Browser.deleteFromHistory(getContentResolver(), url);
- mAdapter.refreshData();
+ Browser.deleteFromHistory(activity.getContentResolver(), url);
return true;
case R.id.homepage_context_menu_id:
- BrowserSettings.getInstance().setHomePage(this, url);
- Toast.makeText(this, R.string.homepage_set,
- Toast.LENGTH_LONG).show();
+ BrowserSettings.getInstance().setHomePage(activity, url);
+ Toast.makeText(activity, R.string.homepage_set, Toast.LENGTH_LONG).show();
return true;
default:
break;
}
return super.onContextItemSelected(item);
}
-
- @Override
- public boolean onChildClick(ExpandableListView parent, View v,
- int groupPosition, int childPosition, long id) {
- if (v instanceof HistoryItem) {
- loadUrl(((HistoryItem) v).getUrl(), false);
- return true;
+
+ private static abstract class HistoryWrapper extends BaseAdapter {
+
+ protected HistoryAdapter mAdapter;
+ private DataSetObserver mObserver = new DataSetObserver() {
+ @Override
+ public void onChanged() {
+ super.onChanged();
+ notifyDataSetChanged();
+ }
+
+ @Override
+ public void onInvalidated() {
+ super.onInvalidated();
+ notifyDataSetInvalidated();
+ }
+ };
+
+ public HistoryWrapper(HistoryAdapter adapter) {
+ mAdapter = adapter;
+ mAdapter.registerDataSetObserver(mObserver);
}
- return false;
+
+ }
+ private static class HistoryGroupWrapper extends HistoryWrapper {
+
+ public HistoryGroupWrapper(HistoryAdapter adapter) {
+ super(adapter);
+ }
+
+ @Override
+ public int getCount() {
+ return mAdapter.getGroupCount();
+ }
+
+ @Override
+ public Object getItem(int position) {
+ return null;
+ }
+
+ @Override
+ public long getItemId(int position) {
+ return position;
+ }
+
+ @Override
+ public View getView(int position, View convertView, ViewGroup parent) {
+ return mAdapter.getGroupView(position, false, convertView, parent);
+ }
+
}
- // This Activity is always a sub-Activity of
- // CombinedBookmarkHistoryActivity. Therefore, we need to pass our
- // result code up to our parent.
- private void setResultToParent(int resultCode, Intent data) {
- ((CombinedBookmarkHistoryActivity) getParent()).setResultFromChild(
- resultCode, data);
+ private static class HistoryChildWrapper extends HistoryWrapper {
+
+ private int mSelectedGroup;
+
+ public HistoryChildWrapper(HistoryAdapter adapter) {
+ super(adapter);
+ }
+
+ void setSelectedGroup(int groupPosition) {
+ mSelectedGroup = groupPosition;
+ notifyDataSetChanged();
+ }
+
+ @Override
+ public int getCount() {
+ return mAdapter.getChildrenCount(mSelectedGroup);
+ }
+
+ @Override
+ public Object getItem(int position) {
+ return null;
+ }
+
+ @Override
+ public long getItemId(int position) {
+ return position;
+ }
+
+ @Override
+ public View getView(int position, View convertView, ViewGroup parent) {
+ return mAdapter.getChildView(mSelectedGroup, position,
+ false, convertView, parent);
+ }
+
}
private class HistoryAdapter extends DateSortedExpandableListAdapter {
- HistoryAdapter(Context context, Cursor cursor, int index) {
- super(context, cursor, index);
-
+
+ private Cursor mMostVisited, mHistoryCursor;
+ Drawable mFaviconBackground;
+
+ HistoryAdapter(Context context) {
+ super(context, HistoryQuery.INDEX_DATE_LAST_VISITED);
+ mFaviconBackground = BookmarkUtils.createListFaviconBackground(context);
}
+ @Override
+ public void changeCursor(Cursor cursor) {
+ mHistoryCursor = cursor;
+ super.changeCursor(cursor);
+ }
+
+ void changeMostVisitedCursor(Cursor cursor) {
+ if (mMostVisited == cursor) {
+ return;
+ }
+ if (mMostVisited != null) {
+ mMostVisited.unregisterDataSetObserver(mDataSetObserver);
+ mMostVisited.close();
+ }
+ mMostVisited = cursor;
+ if (mMostVisited != null) {
+ mMostVisited.registerDataSetObserver(mDataSetObserver);
+ }
+ notifyDataSetChanged();
+ }
+
+ @Override
+ public long getChildId(int groupPosition, int childPosition) {
+ if (moveCursorToChildPosition(groupPosition, childPosition)) {
+ Cursor cursor = getCursor(groupPosition);
+ return cursor.getLong(HistoryQuery.INDEX_ID);
+ }
+ return 0;
+ }
+
+ @Override
+ public int getGroupCount() {
+ return super.getGroupCount() + (!isMostVisitedEmpty() ? 1 : 0);
+ }
+
+ @Override
+ public int getChildrenCount(int groupPosition) {
+ if (groupPosition >= super.getGroupCount()) {
+ if (isMostVisitedEmpty()) {
+ return 0;
+ }
+ return mMostVisited.getCount();
+ }
+ return super.getChildrenCount(groupPosition);
+ }
+
+ @Override
+ public boolean isEmpty() {
+ if (!super.isEmpty()) {
+ return false;
+ }
+ return isMostVisitedEmpty();
+ }
+
+ private boolean isMostVisitedEmpty() {
+ return mMostVisited == null
+ || mMostVisited.isClosed()
+ || mMostVisited.getCount() == 0;
+ }
+
+ Cursor getCursor(int groupPosition) {
+ if (groupPosition >= super.getGroupCount()) {
+ return mMostVisited;
+ }
+ return mHistoryCursor;
+ }
+
+ @Override
+ public View getGroupView(int groupPosition, boolean isExpanded,
+ View convertView, ViewGroup parent) {
+ if (groupPosition >= super.getGroupCount()) {
+ if (mMostVisited == null || mMostVisited.isClosed()) {
+ throw new IllegalStateException("Data is not valid");
+ }
+ TextView item;
+ if (null == convertView || !(convertView instanceof TextView)) {
+ LayoutInflater factory = LayoutInflater.from(getContext());
+ item = (TextView) factory.inflate(R.layout.history_header, null);
+ } else {
+ item = (TextView) convertView;
+ }
+ item.setText(R.string.tab_most_visited);
+ return item;
+ }
+ return super.getGroupView(groupPosition, isExpanded, convertView, parent);
+ }
+
+ @Override
+ boolean moveCursorToChildPosition(
+ int groupPosition, int childPosition) {
+ if (groupPosition >= super.getGroupCount()) {
+ if (mMostVisited != null && !mMostVisited.isClosed()) {
+ mMostVisited.moveToPosition(childPosition);
+ return true;
+ }
+ return false;
+ }
+ return super.moveCursorToChildPosition(groupPosition, childPosition);
+ }
+
+ @Override
public View getChildView(int groupPosition, int childPosition, boolean isLastChild,
View convertView, ViewGroup parent) {
HistoryItem item;
if (null == convertView || !(convertView instanceof HistoryItem)) {
- item = new HistoryItem(BrowserHistoryPage.this);
+ item = new HistoryItem(getContext());
// Add padding on the left so it will be indented from the
// arrows on the group views.
item.setPadding(item.getPaddingLeft() + 10,
item.getPaddingTop(),
item.getPaddingRight(),
item.getPaddingBottom());
+ item.setFaviconBackground(mFaviconBackground);
} else {
item = (HistoryItem) convertView;
}
+
// Bail early if the Cursor is closed.
if (!moveCursorToChildPosition(groupPosition, childPosition)) {
return item;
}
- item.setName(getString(Browser.HISTORY_PROJECTION_TITLE_INDEX));
- String url = getString(Browser.HISTORY_PROJECTION_URL_INDEX);
+
+ Cursor cursor = getCursor(groupPosition);
+ item.setName(cursor.getString(HistoryQuery.INDEX_TITE));
+ String url = cursor.getString(HistoryQuery.INDEX_URL);
item.setUrl(url);
- byte[] data = getBlob(Browser.HISTORY_PROJECTION_FAVICON_INDEX);
+ byte[] data = cursor.getBlob(HistoryQuery.INDEX_FAVICON);
if (data != null) {
item.setFavicon(BitmapFactory.decodeByteArray(data, 0,
data.length));
} else {
- item.setFavicon(CombinedBookmarkHistoryActivity
+ item.setFavicon(CombinedBookmarkHistoryView
.getIconListenerSet().getFavicon(url));
}
- item.setIsBookmark(1 ==
- getInt(Browser.HISTORY_PROJECTION_BOOKMARK_INDEX));
+ item.setIsBookmark(cursor.getInt(HistoryQuery.INDEX_IS_BOOKMARK) == 1);
return item;
}
}
diff --git a/src/com/android/browser/BrowserHomepagePreference.java b/src/com/android/browser/BrowserHomepagePreference.java
index 4f18bd5..1e2697b 100644
--- a/src/com/android/browser/BrowserHomepagePreference.java
+++ b/src/com/android/browser/BrowserHomepagePreference.java
@@ -16,19 +16,17 @@
package com.android.browser;
-import android.app.AlertDialog;
import android.content.Context;
import android.os.Bundle;
import android.preference.EditTextPreference;
-import android.widget.Button;
-import android.widget.EditText;
-import android.widget.LinearLayout;
-import android.view.Gravity;
+import android.util.AttributeSet;
+import android.view.LayoutInflater;
import android.view.View;
+import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.view.Window;
import android.view.WindowManager;
-import android.util.AttributeSet;
+import android.widget.EditText;
public class BrowserHomepagePreference extends EditTextPreference {
private String mCurrentPage;
@@ -50,44 +48,43 @@
protected void onAddEditTextToDialogView(View dialogView,
EditText editText) {
super.onAddEditTextToDialogView(dialogView, editText);
+ editText.setSelectAllOnFocus(true);
// Now the EditText has a parent. Add a button to set to the current
// page.
- ViewGroup parent = (ViewGroup) editText.getParent();
- Button button = new Button(getContext());
- button.setText(R.string.pref_use_current);
- button.setOnClickListener(new View.OnClickListener() {
- public void onClick(View v) {
- getEditText().setText(mCurrentPage);
- }
- });
- if (parent instanceof LinearLayout) {
- ((LinearLayout) parent).setGravity(Gravity.CENTER_HORIZONTAL);
- }
- parent.addView(button, ViewGroup.LayoutParams.WRAP_CONTENT,
- ViewGroup.LayoutParams.WRAP_CONTENT);
+ createButtons((ViewGroup) editText.getParent());
}
+ void createButtons(ViewGroup parent) {
+ LayoutInflater inflater = (LayoutInflater) getContext()
+ .getSystemService(Context.LAYOUT_INFLATER_SERVICE);
+ View v = inflater.inflate(R.layout.pref_homepage_buttons, parent);
+ v.findViewById(R.id.use_current).setOnClickListener(mOnClick);
+ v.findViewById(R.id.use_default).setOnClickListener(mOnClick);
+ }
+
+ OnClickListener mOnClick = new OnClickListener() {
+ @Override
+ public void onClick(View v) {
+ switch (v.getId()) {
+ case R.id.use_current:
+ getEditText().setText(mCurrentPage);
+ break;
+ case R.id.use_default:
+ getEditText().setText(
+ BrowserSettings.getFactoryResetHomeUrl(getContext()));
+ break;
+ }
+ }
+ };
+
@Override
protected void onDialogClosed(boolean positiveResult) {
if (positiveResult) {
- String url = getEditText().getText().toString();
- if (url.length() > 0
- && !BrowserActivity.ACCEPTED_URI_SCHEMA.matcher(url)
- .matches()) {
- int colon = url.indexOf(':');
- int space = url.indexOf(' ');
- if (colon == -1 && space == -1) {
- // if no colon, no space, add "http://" to make it a url
- getEditText().setText("http://" + url);
- } else {
- // show an error dialog and change the positiveResult to
- // false so that the bad url will not override the old url
- new AlertDialog.Builder(this.getContext()).setMessage(
- R.string.bookmark_url_not_valid).setPositiveButton(
- R.string.ok, null).show();
- positiveResult = false;
- }
+ String url = getEditText().getText().toString().trim();
+ if (url.length() > 0) {
+ url = UrlUtils.smartUrlFilter(url);
}
+ getEditText().setText(url);
}
super.onDialogClosed(positiveResult);
}
@@ -97,7 +94,7 @@
* @param currentPage This String will replace the text in the EditText
* when the user clicks the "Use current page" button.
*/
- /* package */ void setCurrentPage(String currentPage) {
+ public void setCurrentPage(String currentPage) {
mCurrentPage = currentPage;
}
diff --git a/src/com/android/browser/BrowserPreferencesPage.java b/src/com/android/browser/BrowserPreferencesPage.java
index 9af66f1..dae838f 100644
--- a/src/com/android/browser/BrowserPreferencesPage.java
+++ b/src/com/android/browser/BrowserPreferencesPage.java
@@ -16,96 +16,44 @@
package com.android.browser;
-import android.content.Intent;
-import android.net.Uri;
+import com.android.browser.preferences.DebugPreferencesFragment;
+
+import android.app.ActionBar;
import android.os.Bundle;
-import android.preference.EditTextPreference;
-import android.preference.Preference;
import android.preference.PreferenceActivity;
-import android.preference.PreferenceScreen;
-import android.webkit.GeolocationPermissions;
-import android.webkit.ValueCallback;
-import android.webkit.WebStorage;
+import android.preference.PreferenceManager;
+import android.view.MenuItem;
-import java.util.Map;
-import java.util.Set;
+import java.util.List;
-public class BrowserPreferencesPage extends PreferenceActivity
- implements Preference.OnPreferenceChangeListener {
+public class BrowserPreferencesPage extends PreferenceActivity {
- private String LOGTAG = "BrowserPreferencesPage";
- /* package */ static final String CURRENT_PAGE = "currentPage";
+ public static final String CURRENT_PAGE = "currentPage";
@Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
+ public void onCreate(Bundle icicle) {
+ super.onCreate(icicle);
- // Load the XML preferences file
- addPreferencesFromResource(R.xml.browser_preferences);
-
- Preference e = findPreference(BrowserSettings.PREF_HOMEPAGE);
- e.setOnPreferenceChangeListener(this);
- e.setSummary(getPreferenceScreen().getSharedPreferences()
- .getString(BrowserSettings.PREF_HOMEPAGE, null));
- ((BrowserHomepagePreference) e).setCurrentPage(
- getIntent().getStringExtra(CURRENT_PAGE));
-
- e = findPreference(BrowserSettings.PREF_EXTRAS_RESET_DEFAULTS);
- e.setOnPreferenceChangeListener(this);
-
- e = findPreference(BrowserSettings.PREF_TEXT_SIZE);
- e.setOnPreferenceChangeListener(this);
- e.setSummary(getVisualTextSizeName(
- getPreferenceScreen().getSharedPreferences()
- .getString(BrowserSettings.PREF_TEXT_SIZE, null)) );
-
- e = findPreference(BrowserSettings.PREF_DEFAULT_ZOOM);
- e.setOnPreferenceChangeListener(this);
- e.setSummary(getVisualDefaultZoomName(
- getPreferenceScreen().getSharedPreferences()
- .getString(BrowserSettings.PREF_DEFAULT_ZOOM, null)) );
-
- e = findPreference(BrowserSettings.PREF_DEFAULT_TEXT_ENCODING);
- e.setOnPreferenceChangeListener(this);
-
- e = findPreference(BrowserSettings.PREF_CLEAR_HISTORY);
- e.setOnPreferenceChangeListener(this);
-
- if (BrowserSettings.getInstance().showDebugSettings()) {
- addPreferencesFromResource(R.xml.debug_preferences);
+ ActionBar actionBar = getActionBar();
+ if (actionBar != null) {
+ actionBar.setDisplayOptions(
+ ActionBar.DISPLAY_HOME_AS_UP, ActionBar.DISPLAY_HOME_AS_UP);
}
-
- PreferenceScreen websiteSettings = (PreferenceScreen)
- findPreference(BrowserSettings.PREF_WEBSITE_SETTINGS);
- Intent intent = new Intent(this, WebsiteSettingsActivity.class);
- websiteSettings.setIntent(intent);
}
- /*
- * We need to set the PreferenceScreen state in onResume(), as the number of
- * origins with active features (WebStorage, Geolocation etc) could have
- * changed after calling the WebsiteSettingsActivity.
+ /**
+ * Populate the activity with the top-level headers.
*/
@Override
- protected void onResume() {
- super.onResume();
- final PreferenceScreen websiteSettings = (PreferenceScreen)
- findPreference(BrowserSettings.PREF_WEBSITE_SETTINGS);
- websiteSettings.setEnabled(false);
- WebStorage.getInstance().getOrigins(new ValueCallback<Map>() {
- public void onReceiveValue(Map webStorageOrigins) {
- if ((webStorageOrigins != null) && !webStorageOrigins.isEmpty()) {
- websiteSettings.setEnabled(true);
- }
- }
- });
- GeolocationPermissions.getInstance().getOrigins(new ValueCallback<Set<String> >() {
- public void onReceiveValue(Set<String> geolocationOrigins) {
- if ((geolocationOrigins != null) && !geolocationOrigins.isEmpty()) {
- websiteSettings.setEnabled(true);
- }
- }
- });
+ public void onBuildHeaders(List<Header> target) {
+ loadHeadersFromResource(R.xml.preference_headers, target);
+
+ if (BrowserSettings.DEV_BUILD || BrowserSettings.getInstance().showDebugSettings()) {
+ Header debug = new Header();
+ debug.title = getText(R.string.pref_development_title);
+ debug.fragment = DebugPreferencesFragment.class.getName();
+ target.add(debug);
+ }
}
@Override
@@ -115,98 +63,21 @@
// sync the shared preferences back to BrowserSettings
BrowserSettings.getInstance().syncSharedPreferences(
getApplicationContext(),
- getPreferenceScreen().getSharedPreferences());
+ PreferenceManager.getDefaultSharedPreferences(this));
}
- public boolean onPreferenceChange(Preference pref, Object objValue) {
- if (pref.getKey().equals(BrowserSettings.PREF_EXTRAS_RESET_DEFAULTS)) {
- Boolean value = (Boolean) objValue;
- if (value.booleanValue() == true) {
- finish();
- }
- } else if (pref.getKey().equals(BrowserSettings.PREF_HOMEPAGE)) {
- String value = (String) objValue;
- boolean needUpdate = value.indexOf(' ') != -1;
- if (needUpdate) {
- value = value.trim().replace(" ", "%20");
- }
- if (value.length() != 0 && Uri.parse(value).getScheme() == null) {
- value = "http://" + value;
- needUpdate = true;
- }
- // Set the summary value.
- pref.setSummary(value);
- if (needUpdate) {
- // Update through the EditText control as it has a cached copy
- // of the string and it will handle persisting the value
- ((EditTextPreference) pref).setText(value);
-
- // as we update the value above, we need to return false
- // here so that setText() is not called by EditTextPref
- // with the old value.
- return false;
- } else {
+ @Override
+ public boolean onOptionsItemSelected(MenuItem item) {
+ switch (item.getItemId()) {
+ case android.R.id.home:
+ if (getFragmentManager().getBackStackEntryCount() > 0) {
+ getFragmentManager().popBackStack();
+ } else {
+ finish();
+ }
return true;
- }
- } else if (pref.getKey().equals(BrowserSettings.PREF_TEXT_SIZE)) {
- pref.setSummary(getVisualTextSizeName((String) objValue));
- return true;
- } else if (pref.getKey().equals(BrowserSettings.PREF_DEFAULT_ZOOM)) {
- pref.setSummary(getVisualDefaultZoomName((String) objValue));
- return true;
- } else if (pref.getKey().equals(
- BrowserSettings.PREF_DEFAULT_TEXT_ENCODING)) {
- pref.setSummary((String) objValue);
- return true;
- } else if (pref.getKey().equals(BrowserSettings.PREF_CLEAR_HISTORY)
- && ((Boolean) objValue).booleanValue() == true) {
- // Need to tell the browser to remove the parent/child relationship
- // between tabs
- setResult(RESULT_OK, (new Intent()).putExtra(Intent.EXTRA_TEXT,
- pref.getKey()));
- return true;
}
-
+
return false;
}
-
- private CharSequence getVisualTextSizeName(String enumName) {
- CharSequence[] visualNames = getResources().getTextArray(
- R.array.pref_text_size_choices);
- CharSequence[] enumNames = getResources().getTextArray(
- R.array.pref_text_size_values);
-
- // Sanity check
- if (visualNames.length != enumNames.length) {
- return "";
- }
-
- for (int i = 0; i < enumNames.length; i++) {
- if (enumNames[i].equals(enumName)) {
- return visualNames[i];
- }
- }
-
- return "";
- }
-
- private CharSequence getVisualDefaultZoomName(String enumName) {
- CharSequence[] visualNames = getResources().getTextArray(
- R.array.pref_default_zoom_choices);
- CharSequence[] enumNames = getResources().getTextArray(
- R.array.pref_default_zoom_values);
-
- // Sanity check
- if (visualNames.length != enumNames.length) {
- return "";
- }
-
- for (int i = 0; i < enumNames.length; i++) {
- if (enumNames[i].equals(enumName)) {
- return visualNames[i];
- }
- }
-
- return "";
- }
}
diff --git a/src/com/android/browser/BrowserProvider.java b/src/com/android/browser/BrowserProvider.java
index 72ec819..cba16a0 100644
--- a/src/com/android/browser/BrowserProvider.java
+++ b/src/com/android/browser/BrowserProvider.java
@@ -29,8 +29,10 @@
import android.content.SharedPreferences;
import android.content.SharedPreferences.Editor;
import android.content.UriMatcher;
+import android.content.res.Configuration;
import android.database.AbstractCursor;
import android.database.Cursor;
+import android.database.DatabaseUtils;
import android.database.sqlite.SQLiteDatabase;
import android.database.sqlite.SQLiteOpenHelper;
import android.net.Uri;
@@ -38,6 +40,7 @@
import android.preference.PreferenceManager;
import android.provider.Browser;
import android.provider.Browser.BookmarkColumns;
+import android.provider.Settings;
import android.speech.RecognizerResultsIntent;
import android.text.TextUtils;
import android.util.Log;
@@ -84,6 +87,17 @@
private static final int SUGGEST_COLUMN_QUERY_ID = 8;
private static final int SUGGEST_COLUMN_INTENT_EXTRA_DATA = 9;
+ // how many suggestions will be shown in dropdown
+ // 0..SHORT: filled by browser db
+ private static final int MAX_SUGGEST_SHORT_SMALL = 3;
+ // SHORT..LONG: filled by search suggestions
+ private static final int MAX_SUGGEST_LONG_SMALL = 6;
+
+ // large screen size shows more
+ private static final int MAX_SUGGEST_SHORT_LARGE = 6;
+ private static final int MAX_SUGGEST_LONG_LARGE = 9;
+
+
// shared suggestion columns
private static final String[] COLUMNS = new String[] {
"_id",
@@ -97,10 +111,6 @@
SearchManager.SUGGEST_COLUMN_QUERY,
SearchManager.SUGGEST_COLUMN_INTENT_EXTRA_DATA};
- private static final int MAX_SUGGESTION_SHORT_ENTRIES = 3;
- private static final int MAX_SUGGESTION_LONG_ENTRIES = 6;
- private static final String MAX_SUGGESTION_LONG_ENTRIES_STRING =
- Integer.valueOf(MAX_SUGGESTION_LONG_ENTRIES).toString();
// make sure that these match the index of TABLE_NAMES
private static final int URI_MATCH_BOOKMARKS = 0;
@@ -161,6 +171,9 @@
private BrowserSettings mSettings;
+ private int mMaxSuggestionShortSize;
+ private int mMaxSuggestionLongSize;
+
public BrowserProvider() {
}
@@ -365,6 +378,20 @@
@Override
public boolean onCreate() {
final Context context = getContext();
+ boolean xlargeScreenSize = (context.getResources().getConfiguration().screenLayout
+ & Configuration.SCREENLAYOUT_SIZE_MASK)
+ == Configuration.SCREENLAYOUT_SIZE_XLARGE;
+ boolean isPortrait = (context.getResources().getConfiguration().orientation
+ == Configuration.ORIENTATION_PORTRAIT);
+
+
+ if (xlargeScreenSize && isPortrait) {
+ mMaxSuggestionLongSize = MAX_SUGGEST_LONG_LARGE;
+ mMaxSuggestionShortSize = MAX_SUGGEST_SHORT_LARGE;
+ } else {
+ mMaxSuggestionLongSize = MAX_SUGGEST_LONG_SMALL;
+ mMaxSuggestionShortSize = MAX_SUGGEST_SHORT_SMALL;
+ }
mOpenHelper = new DatabaseHelper(context);
mBackupManager = new BackupManager(context);
// we added "picasa web album" into default bookmarks for version 19.
@@ -431,10 +458,10 @@
public MySuggestionCursor(Cursor hc, Cursor sc, String string) {
mHistoryCursor = hc;
mSuggestCursor = sc;
- mHistoryCount = hc.getCount();
+ mHistoryCount = hc != null ? hc.getCount() : 0;
mSuggestionCount = sc != null ? sc.getCount() : 0;
- if (mSuggestionCount > (MAX_SUGGESTION_LONG_ENTRIES - mHistoryCount)) {
- mSuggestionCount = MAX_SUGGESTION_LONG_ENTRIES - mHistoryCount;
+ if (mSuggestionCount > (mMaxSuggestionLongSize - mHistoryCount)) {
+ mSuggestionCount = mMaxSuggestionLongSize - mHistoryCount;
}
mString = string;
mIncludeWebSearch = string.length() > 0;
@@ -648,6 +675,7 @@
}
// TODO Temporary change, finalize after jq's changes go in
+ @Override
public void deactivate() {
if (mHistoryCursor != null) {
mHistoryCursor.deactivate();
@@ -658,12 +686,14 @@
super.deactivate();
}
+ @Override
public boolean requery() {
return (mHistoryCursor != null ? mHistoryCursor.requery() : false) |
(mSuggestCursor != null ? mSuggestCursor.requery() : false);
}
// TODO Temporary change, finalize after jq's changes go in
+ @Override
public void close() {
super.close();
if (mHistoryCursor != null) {
@@ -728,12 +758,15 @@
public ResultsCursor(ArrayList<String> results) {
mResults = results;
}
+ @Override
public int getCount() { return mResults.size(); }
+ @Override
public String[] getColumnNames() {
return RESULTS_COLUMNS;
}
+ @Override
public String getString(int column) {
switch (column) {
case RESULT_ACTION_ID:
@@ -755,30 +788,39 @@
return null;
}
}
+ @Override
public short getShort(int column) {
throw new UnsupportedOperationException();
}
+ @Override
public int getInt(int column) {
throw new UnsupportedOperationException();
}
+ @Override
public long getLong(int column) {
if ((mPos != -1) && column == 0) {
return mPos; // use row# as the _id
}
throw new UnsupportedOperationException();
}
+ @Override
public float getFloat(int column) {
throw new UnsupportedOperationException();
}
+ @Override
public double getDouble(int column) {
throw new UnsupportedOperationException();
}
+ @Override
public boolean isNull(int column) {
throw new UnsupportedOperationException();
}
}
+ /** Contains custom suggestions results set by the UI */
private ResultsCursor mResultsCursor;
+ /** Locks access to {@link #mResultsCursor} */
+ private Object mResultsCursorLock = new Object();
/**
* Provide a set of results to be returned to query, intended to be used
@@ -786,10 +828,12 @@
* @param results Strings to display in the dropdown from the SearchDialog
*/
/* package */ void setQueryResults(ArrayList<String> results) {
- if (results == null) {
- mResultsCursor = null;
- } else {
- mResultsCursor = new ResultsCursor(results);
+ synchronized (mResultsCursorLock) {
+ if (results == null) {
+ mResultsCursor = null;
+ } else {
+ mResultsCursor = new ResultsCursor(results);
+ }
}
}
@@ -801,57 +845,19 @@
if (match == -1) {
throw new IllegalArgumentException("Unknown URL");
}
- if (match == URI_MATCH_SUGGEST && mResultsCursor != null) {
- Cursor results = mResultsCursor;
- mResultsCursor = null;
- return results;
+
+ // If results for the suggestion are already ready just return them directly
+ synchronized (mResultsCursorLock) {
+ if (match == URI_MATCH_SUGGEST && mResultsCursor != null) {
+ Cursor results = mResultsCursor;
+ mResultsCursor = null;
+ return results;
+ }
}
- SQLiteDatabase db = mOpenHelper.getReadableDatabase();
if (match == URI_MATCH_SUGGEST || match == URI_MATCH_BOOKMARKS_SUGGEST) {
- String suggestSelection;
- String [] myArgs;
- if (selectionArgs[0] == null || selectionArgs[0].equals("")) {
- suggestSelection = null;
- myArgs = null;
- } else {
- String like = selectionArgs[0] + "%";
- if (selectionArgs[0].startsWith("http")
- || selectionArgs[0].startsWith("file")) {
- myArgs = new String[1];
- myArgs[0] = like;
- suggestSelection = selection;
- } else {
- SUGGEST_ARGS[0] = "http://" + like;
- SUGGEST_ARGS[1] = "http://www." + like;
- SUGGEST_ARGS[2] = "https://" + like;
- SUGGEST_ARGS[3] = "https://www." + like;
- // To match against titles.
- SUGGEST_ARGS[4] = like;
- myArgs = SUGGEST_ARGS;
- suggestSelection = SUGGEST_SELECTION;
- }
- }
-
- Cursor c = db.query(TABLE_NAMES[URI_MATCH_BOOKMARKS],
- SUGGEST_PROJECTION, suggestSelection, myArgs, null, null,
- ORDER_BY, MAX_SUGGESTION_LONG_ENTRIES_STRING);
-
- if (match == URI_MATCH_BOOKMARKS_SUGGEST
- || Patterns.WEB_URL.matcher(selectionArgs[0]).matches()) {
- return new MySuggestionCursor(c, null, "");
- } else {
- // get search suggestions if there is still space in the list
- if (myArgs != null && myArgs.length > 1
- && c.getCount() < (MAX_SUGGESTION_SHORT_ENTRIES - 1)) {
- SearchEngine searchEngine = mSettings.getSearchEngine();
- if (searchEngine != null && searchEngine.supportsSuggestions()) {
- Cursor sc = searchEngine.getSuggestions(getContext(), selectionArgs[0]);
- return new MySuggestionCursor(c, sc, selectionArgs[0]);
- }
- }
- return new MySuggestionCursor(c, null, selectionArgs[0]);
- }
+ // Handle suggestions
+ return doSuggestQuery(selection, selectionArgs, match == URI_MATCH_BOOKMARKS_SUGGEST);
}
String[] projection = null;
@@ -861,29 +867,62 @@
projection[projectionIn.length] = "_id AS _id";
}
- StringBuilder whereClause = new StringBuilder(256);
+ String whereClause = null;
if (match == URI_MATCH_BOOKMARKS_ID || match == URI_MATCH_SEARCHES_ID) {
- whereClause.append("(_id = ").append(url.getPathSegments().get(1))
- .append(")");
+ whereClause = "_id = " + url.getPathSegments().get(1);
}
- // Tack on the user's selection, if present
- if (selection != null && selection.length() > 0) {
- if (whereClause.length() > 0) {
- whereClause.append(" AND ");
- }
-
- whereClause.append('(');
- whereClause.append(selection);
- whereClause.append(')');
- }
- Cursor c = db.query(TABLE_NAMES[match % 10], projection,
- whereClause.toString(), selectionArgs, null, null, sortOrder,
- null);
+ Cursor c = mOpenHelper.getReadableDatabase().query(TABLE_NAMES[match % 10], projection,
+ DatabaseUtils.concatenateWhere(whereClause, selection), selectionArgs,
+ null, null, sortOrder, null);
c.setNotificationUri(getContext().getContentResolver(), url);
return c;
}
+ private Cursor doSuggestQuery(String selection, String[] selectionArgs, boolean bookmarksOnly) {
+ String suggestSelection;
+ String [] myArgs;
+ if (selectionArgs[0] == null || selectionArgs[0].equals("")) {
+ return new MySuggestionCursor(null, null, "");
+ } else {
+ String like = selectionArgs[0] + "%";
+ if (selectionArgs[0].startsWith("http")
+ || selectionArgs[0].startsWith("file")) {
+ myArgs = new String[1];
+ myArgs[0] = like;
+ suggestSelection = selection;
+ } else {
+ SUGGEST_ARGS[0] = "http://" + like;
+ SUGGEST_ARGS[1] = "http://www." + like;
+ SUGGEST_ARGS[2] = "https://" + like;
+ SUGGEST_ARGS[3] = "https://www." + like;
+ // To match against titles.
+ SUGGEST_ARGS[4] = like;
+ myArgs = SUGGEST_ARGS;
+ suggestSelection = SUGGEST_SELECTION;
+ }
+ }
+
+ Cursor c = mOpenHelper.getReadableDatabase().query(TABLE_NAMES[URI_MATCH_BOOKMARKS],
+ SUGGEST_PROJECTION, suggestSelection, myArgs, null, null,
+ ORDER_BY, Integer.toString(mMaxSuggestionLongSize));
+
+ if (bookmarksOnly || Patterns.WEB_URL.matcher(selectionArgs[0]).matches()) {
+ return new MySuggestionCursor(c, null, "");
+ } else {
+ // get search suggestions if there is still space in the list
+ if (myArgs != null && myArgs.length > 1
+ && c.getCount() < (MAX_SUGGEST_SHORT_SMALL - 1)) {
+ SearchEngine searchEngine = mSettings.getSearchEngine();
+ if (searchEngine != null && searchEngine.supportsSuggestions()) {
+ Cursor sc = searchEngine.getSuggestions(getContext(), selectionArgs[0]);
+ return new MySuggestionCursor(c, sc, selectionArgs[0]);
+ }
+ }
+ return new MySuggestionCursor(c, null, selectionArgs[0]);
+ }
+ }
+
@Override
public String getType(Uri url) {
int match = URI_MATCHER.match(url);
@@ -1089,4 +1128,10 @@
}
}
+ public static Cursor getBookmarksSuggestions(ContentResolver cr, String constraint) {
+ Uri uri = Uri.parse("content://browser/" + SearchManager.SUGGEST_URI_PATH_QUERY);
+ return cr.query(uri, SUGGEST_PROJECTION, SUGGEST_SELECTION,
+ new String[] { constraint }, ORDER_BY);
+ }
+
}
diff --git a/src/com/android/browser/BrowserSettings.java b/src/com/android/browser/BrowserSettings.java
index 3791eb0..faf0042 100644
--- a/src/com/android/browser/BrowserSettings.java
+++ b/src/com/android/browser/BrowserSettings.java
@@ -17,36 +17,33 @@
package com.android.browser;
+import com.android.browser.homepages.HomeProvider;
import com.android.browser.search.SearchEngine;
import com.android.browser.search.SearchEngines;
import android.app.ActivityManager;
-import android.content.ComponentName;
import android.content.ContentResolver;
import android.content.Context;
-import android.content.pm.ActivityInfo;
import android.content.SharedPreferences;
import android.content.SharedPreferences.Editor;
-import android.database.ContentObserver;
-import android.os.Handler;
-import android.preference.PreferenceActivity;
-import android.preference.PreferenceScreen;
-import android.provider.Settings;
+import android.content.SharedPreferences.OnSharedPreferenceChangeListener;
+import android.database.Cursor;
+import android.net.Uri;
+import android.os.AsyncTask;
+import android.os.Message;
+import android.preference.PreferenceManager;
+import android.provider.Browser;
import android.util.Log;
import android.webkit.CookieManager;
import android.webkit.GeolocationPermissions;
-import android.webkit.ValueCallback;
-import android.webkit.WebView;
-import android.webkit.WebViewDatabase;
import android.webkit.WebIconDatabase;
import android.webkit.WebSettings;
+import android.webkit.WebSettings.AutoFillProfile;
import android.webkit.WebStorage;
-import android.preference.PreferenceManager;
-import android.provider.Browser;
+import android.webkit.WebView;
+import android.webkit.WebViewDatabase;
import java.util.HashMap;
-import java.util.Map;
-import java.util.Set;
import java.util.Observable;
/*
@@ -62,8 +59,7 @@
* To remove an observer:
* s.deleteObserver(webView.getSettings());
*/
-class BrowserSettings extends Observable {
-
+public class BrowserSettings extends Observable implements OnSharedPreferenceChangeListener {
// Private variables for settings
// NOTE: these defaults need to be kept in sync with the XML
// until the performance of PreferenceManager.setDefaultValues()
@@ -76,12 +72,12 @@
private boolean showSecurityWarnings;
private boolean rememberPasswords;
private boolean saveFormData;
+ private boolean autoFillEnabled;
private boolean openInBackground;
private String defaultTextEncodingName;
private String homeUrl = "";
private SearchEngine searchEngine;
private boolean autoFitPage;
- private boolean landscapeOnly;
private boolean loadsPageInOverviewMode;
private boolean showDebugSettings;
// HTML5 API flags
@@ -96,6 +92,9 @@
private String databasePath; // default value set in loadFromDb()
private String geolocationDatabasePath; // default value set in loadFromDb()
private WebStorageSizeManager webStorageSizeManager;
+ // Autologin settings
+ private boolean autoLoginEnabled;
+ private String autoLoginAccount;
private String jsFlags = "";
@@ -109,14 +108,19 @@
private boolean tracing = false;
private boolean lightTouch = false;
private boolean navDump = false;
+ private boolean hardwareAccelerated = true;
+
+ // Lab settings
+ private boolean quickControls = false;
+ private boolean useMostVisitedHomepage = false;
// By default the error console is shown once the user navigates to about:debug.
// The setting can be then toggled from the settings menu.
private boolean showConsole = true;
// Private preconfigured values
- private static int minimumFontSize = 8;
- private static int minimumLogicalFontSize = 8;
+ private static int minimumFontSize = 1;
+ private static int minimumLogicalFontSize = 1;
private static int defaultFontSize = 16;
private static int defaultFixedFontSize = 13;
private static WebSettings.TextSize textSize =
@@ -125,6 +129,15 @@
WebSettings.ZoomDensity.MEDIUM;
private static int pageCacheCapacity;
+
+ private AutoFillProfile autoFillProfile;
+ // Default to zero. In the case no profile is set up, the initial
+ // value will come from the AutoFillSettingsFragment when the user
+ // creates a profile. Otherwise, we'll read the ID of the last used
+ // profile from the prefs db.
+ private int autoFillActiveProfileId;
+ private static final int NO_AUTOFILL_PROFILE_SET = 0;
+
// Preference keys that are used outside this class
public final static String PREF_CLEAR_CACHE = "privacy_clear_cache";
public final static String PREF_CLEAR_COOKIES = "privacy_clear_cookies";
@@ -145,6 +158,17 @@
"default_text_encoding";
public final static String PREF_CLEAR_GEOLOCATION_ACCESS =
"privacy_clear_geolocation_access";
+ public final static String PREF_AUTOFILL_ENABLED = "autofill_enabled";
+ public final static String PREF_AUTOFILL_PROFILE = "autofill_profile";
+ public final static String PREF_AUTOFILL_ACTIVE_PROFILE_ID = "autofill_active_profile_id";
+ public final static String PREF_HARDWARE_ACCEL = "enable_hardware_accel";
+ public final static String PREF_USER_AGENT = "user_agent";
+
+ public final static String PREF_QUICK_CONTROLS = "enable_quick_controls";
+ public final static String PREF_MOST_VISITED_HOMEPAGE = "use_most_visited_homepage";
+ public final static String PREF_AUTOLOGIN = "enable_autologin";
+ public final static String PREF_AUTOLOGIN_ACCOUNT = "autologin_account";
+ public final static String PREF_PLUGIN_STATE = "plugin_state";
private static final String DESKTOP_USERAGENT = "Mozilla/5.0 (Macintosh; " +
"U; Intel Mac OS X 10_6_3; en-us) AppleWebKit/533.16 (KHTML, " +
@@ -166,7 +190,14 @@
// a ListView
public final static int MAX_TEXTVIEW_LEN = 80;
- private TabControl mTabControl;
+ public static final String RLZ_PROVIDER = "com.google.android.partnersetup.rlzappprovider";
+
+ public static final Uri RLZ_PROVIDER_URI = Uri.parse("content://" + RLZ_PROVIDER + "/");
+
+ // Set to true to enable some of the about:debug options
+ public static final boolean DEV_BUILD = false;
+
+ private Controller mController;
// Single instance of the BrowserSettings for use in the Browser app.
private static BrowserSettings sSingleton;
@@ -176,6 +207,18 @@
private HashMap<WebSettings,Observer> mWebSettingsToObservers =
new HashMap<WebSettings,Observer>();
+ private boolean mLoadFromDbComplete;
+
+ public void waitForLoadFromDbToComplete() {
+ synchronized (sSingleton) {
+ while (!mLoadFromDbComplete) {
+ try {
+ sSingleton.wait();
+ } catch (InterruptedException e) { }
+ }
+ }
+ }
+
/*
* An observer wrapper for updating a WebSettings object with the new
* settings after a call to BrowserSettings.update().
@@ -221,6 +264,7 @@
s.setDefaultZoom(b.zoomDensity);
s.setLightTouchEnabled(b.lightTouch);
s.setSaveFormData(b.saveFormData);
+ s.setAutoFillEnabled(b.autoFillEnabled);
s.setSavePassword(b.rememberPasswords);
s.setLoadWithOverviewMode(b.loadsPageInOverviewMode);
s.setPageCacheCapacity(pageCacheCapacity);
@@ -229,6 +273,11 @@
s.setNeedInitialFocus(false);
// Browser supports multiple windows
s.setSupportMultipleWindows(true);
+ // enable smooth transition for better performance during panning or
+ // zooming
+ s.setEnableSmoothTransition(true);
+ // disable content url access
+ s.setAllowContentAccess(false);
// HTML5 API flags
s.setAppCacheEnabled(b.appCacheEnabled);
@@ -243,56 +292,123 @@
s.setDatabasePath(b.databasePath);
s.setGeolocationDatabasePath(b.geolocationDatabasePath);
+ // Active AutoFill profile data.
+ s.setAutoFillProfile(b.autoFillProfile);
+
b.updateTabControlSettings();
}
}
/**
- * Load settings from the browser app's database.
+ * Load settings from the browser app's database. It is performed in
+ * an AsyncTask as it involves plenty of slow disk IO.
* NOTE: Strings used for the preferences must match those specified
- * in the browser_preferences.xml
+ * in the various preference XML files.
* @param ctx A Context object used to query the browser's settings
* database. If the database exists, the saved settings will be
* stored in this BrowserSettings object. This will update all
* observers of this object.
*/
- public void loadFromDb(final Context ctx) {
- SharedPreferences p =
- PreferenceManager.getDefaultSharedPreferences(ctx);
- // Set the default value for the Application Caches path.
- appCachePath = ctx.getDir("appcache", 0).getPath();
- // Determine the maximum size of the application cache.
- webStorageSizeManager = new WebStorageSizeManager(
- ctx,
- new WebStorageSizeManager.StatFsDiskInfo(appCachePath),
- new WebStorageSizeManager.WebKitAppCacheInfo(appCachePath));
- appCacheMaxSize = webStorageSizeManager.getAppCacheMaxSize();
- // Set the default value for the Database path.
- databasePath = ctx.getDir("databases", 0).getPath();
- // Set the default value for the Geolocation database path.
- geolocationDatabasePath = ctx.getDir("geolocation", 0).getPath();
+ public void asyncLoadFromDb(final Context ctx) {
+ mLoadFromDbComplete = false;
+ // Run the initial settings load in an AsyncTask as it hits the
+ // disk multiple times through SharedPreferences and SQLite. We
+ // need to be certain though that this has completed before we start
+ // to load pages though, so in the worst case we will block waiting
+ // for it to finish in BrowserActivity.onCreate().
+ new LoadFromDbTask(ctx).execute();
+ }
- if (p.getString(PREF_HOMEPAGE, "") == "") {
- // No home page preferences is set, set it to default.
- setHomePage(ctx, getFactoryResetHomeUrl(ctx));
+ private class LoadFromDbTask extends AsyncTask<Void, Void, Void> {
+ private Context mContext;
+
+ public LoadFromDbTask(Context context) {
+ mContext = context;
}
- // the cost of one cached page is ~3M (measured using nytimes.com). For
- // low end devices, we only cache one page. For high end devices, we try
- // to cache more pages, currently choose 5.
- ActivityManager am = (ActivityManager) ctx
- .getSystemService(Context.ACTIVITY_SERVICE);
- if (am.getMemoryClass() > 16) {
- pageCacheCapacity = 5;
- } else {
- pageCacheCapacity = 1;
- }
+ protected Void doInBackground(Void... unused) {
+ SharedPreferences p =
+ PreferenceManager.getDefaultSharedPreferences(mContext);
+ // Set the default value for the Application Caches path.
+ appCachePath = mContext.getDir("appcache", 0).getPath();
+ // Determine the maximum size of the application cache.
+ webStorageSizeManager = new WebStorageSizeManager(
+ mContext,
+ new WebStorageSizeManager.StatFsDiskInfo(appCachePath),
+ new WebStorageSizeManager.WebKitAppCacheInfo(appCachePath));
+ appCacheMaxSize = webStorageSizeManager.getAppCacheMaxSize();
+ // Set the default value for the Database path.
+ databasePath = mContext.getDir("databases", 0).getPath();
+ // Set the default value for the Geolocation database path.
+ geolocationDatabasePath = mContext.getDir("geolocation", 0).getPath();
- // Load the defaults from the xml
- // This call is TOO SLOW, need to manually keep the defaults
- // in sync
- //PreferenceManager.setDefaultValues(ctx, R.xml.browser_preferences);
- syncSharedPreferences(ctx, p);
+ if (p.getString(PREF_HOMEPAGE, null) == null) {
+ // No home page preferences is set, set it to default.
+ setHomePage(mContext, getFactoryResetHomeUrl(mContext));
+ }
+
+ // the cost of one cached page is ~3M (measured using nytimes.com). For
+ // low end devices, we only cache one page. For high end devices, we try
+ // to cache more pages, currently choose 5.
+ ActivityManager am = (ActivityManager) mContext
+ .getSystemService(Context.ACTIVITY_SERVICE);
+ if (am.getMemoryClass() > 16) {
+ pageCacheCapacity = 5;
+ } else {
+ pageCacheCapacity = 1;
+ }
+
+ // Read the last active AutoFill profile id.
+ autoFillActiveProfileId = p.getInt(
+ PREF_AUTOFILL_ACTIVE_PROFILE_ID, autoFillActiveProfileId);
+
+ // Load the autofill profile data from the database. We use a database separate
+ // to the browser preference DB to make it easier to support multiple profiles
+ // and switching between them.
+ AutoFillProfileDatabase autoFillDb = AutoFillProfileDatabase.getInstance(mContext);
+ Cursor c = autoFillDb.getProfile(autoFillActiveProfileId);
+
+ if (c.getCount() > 0) {
+ c.moveToFirst();
+
+ String fullName = c.getString(c.getColumnIndex(
+ AutoFillProfileDatabase.Profiles.FULL_NAME));
+ String email = c.getString(c.getColumnIndex(
+ AutoFillProfileDatabase.Profiles.EMAIL_ADDRESS));
+ String company = c.getString(c.getColumnIndex(
+ AutoFillProfileDatabase.Profiles.COMPANY_NAME));
+ String addressLine1 = c.getString(c.getColumnIndex(
+ AutoFillProfileDatabase.Profiles.ADDRESS_LINE_1));
+ String addressLine2 = c.getString(c.getColumnIndex(
+ AutoFillProfileDatabase.Profiles.ADDRESS_LINE_2));
+ String city = c.getString(c.getColumnIndex(
+ AutoFillProfileDatabase.Profiles.CITY));
+ String state = c.getString(c.getColumnIndex(
+ AutoFillProfileDatabase.Profiles.STATE));
+ String zip = c.getString(c.getColumnIndex(
+ AutoFillProfileDatabase.Profiles.ZIP_CODE));
+ String country = c.getString(c.getColumnIndex(
+ AutoFillProfileDatabase.Profiles.COUNTRY));
+ String phone = c.getString(c.getColumnIndex(
+ AutoFillProfileDatabase.Profiles.PHONE_NUMBER));
+ autoFillProfile = new AutoFillProfile(autoFillActiveProfileId,
+ fullName, email, company, addressLine1, addressLine2, city,
+ state, zip, country, phone);
+ }
+ c.close();
+ autoFillDb.close();
+
+ // PreferenceManager.setDefaultValues is TOO SLOW, need to manually keep
+ // the defaults in sync
+ p.registerOnSharedPreferenceChangeListener(BrowserSettings.this);
+ syncSharedPreferences(mContext, p);
+
+ synchronized (sSingleton) {
+ mLoadFromDbComplete = true;
+ sSingleton.notify();
+ }
+ return null;
+ }
}
/* package */ void syncSharedPreferences(Context ctx, SharedPreferences p) {
@@ -307,8 +423,8 @@
// One or more tabs could have been in voice search mode.
// Clear it, since the new SearchEngine may not support
// it, or may handle it differently.
- for (int i = 0; i < mTabControl.getTabCount(); i++) {
- mTabControl.getTab(i).revertVoiceSearchMode();
+ for (int i = 0; i < mController.getTabControl().getTabCount(); i++) {
+ mController.getTabControl().getTab(i).revertVoiceSearchMode();
}
}
searchEngine.close();
@@ -322,7 +438,7 @@
javaScriptEnabled = p.getBoolean("enable_javascript",
javaScriptEnabled);
pluginState = WebSettings.PluginState.valueOf(
- p.getString("plugin_state", pluginState.name()));
+ p.getString(PREF_PLUGIN_STATE, pluginState.name()));
javaScriptCanOpenWindowsAutomatically = !p.getBoolean(
"block_popup_windows",
!javaScriptCanOpenWindowsAutomatically);
@@ -332,6 +448,7 @@
rememberPasswords);
saveFormData = p.getBoolean("save_formdata",
saveFormData);
+ autoFillEnabled = p.getBoolean("autofill_enabled", autoFillEnabled);
boolean accept_cookies = p.getBoolean("accept_cookies",
CookieManager.getInstance().acceptCookie());
CookieManager.getInstance().setAcceptCookie(accept_cookies);
@@ -343,11 +460,6 @@
autoFitPage = p.getBoolean("autofit_pages", autoFitPage);
loadsPageInOverviewMode = p.getBoolean("load_page",
loadsPageInOverviewMode);
- boolean landscapeOnlyTemp =
- p.getBoolean("landscape_only", landscapeOnly);
- if (landscapeOnlyTemp != landscapeOnly) {
- landscapeOnly = landscapeOnlyTemp;
- }
useWideViewPort = true; // use wide view port for either setting
if (autoFitPage) {
layoutAlgorithm = WebSettings.LayoutAlgorithm.NARROW_COLUMNS;
@@ -381,8 +493,17 @@
tracing = p.getBoolean("enable_tracing", tracing);
lightTouch = p.getBoolean("enable_light_touch", lightTouch);
navDump = p.getBoolean("enable_nav_dump", navDump);
- userAgent = Integer.parseInt(p.getString("user_agent", "0"));
}
+
+ quickControls = p.getBoolean(PREF_QUICK_CONTROLS, quickControls);
+ useMostVisitedHomepage = p.getBoolean(PREF_MOST_VISITED_HOMEPAGE, useMostVisitedHomepage);
+
+ // Only set these if this is a dev build or debug is enabled
+ if (DEV_BUILD || showDebugSettings()) {
+ userAgent = Integer.parseInt(p.getString(PREF_USER_AGENT, "0"));
+ hardwareAccelerated = p.getBoolean(PREF_HARDWARE_ACCEL, hardwareAccelerated);
+ }
+
// JS flags is loaded from DB even if showDebugSettings is false,
// so that it can be set once and be effective all the time.
jsFlags = p.getString("js_engine_flags", "");
@@ -401,10 +522,18 @@
geolocationEnabled = p.getBoolean("enable_geolocation", geolocationEnabled);
workersEnabled = p.getBoolean("enable_workers", workersEnabled);
+ // Autologin account settings. The account preference may be null until
+ // the user explicitly changes the account in the settings.
+ autoLoginEnabled = p.getBoolean(PREF_AUTOLOGIN, autoLoginEnabled);
+ autoLoginAccount = p.getString(PREF_AUTOLOGIN_ACCOUNT, autoLoginAccount);
+
update();
}
public String getHomePage() {
+ if (useMostVisitedHomepage) {
+ return HomeProvider.MOST_VISITED;
+ }
return homeUrl;
}
@@ -456,16 +585,90 @@
return navDump;
}
+ public boolean isHardwareAccelerated() {
+ return hardwareAccelerated;
+ }
+
+ public boolean useQuickControls() {
+ return quickControls;
+ }
+
+ public boolean useMostVisitedHomepage() {
+ return useMostVisitedHomepage;
+ }
+
public boolean showDebugSettings() {
return showDebugSettings;
}
- public void toggleDebugSettings() {
+ public void toggleDebugSettings(Context context) {
showDebugSettings = !showDebugSettings;
navDump = showDebugSettings;
+ syncSharedPreferences(context,
+ PreferenceManager.getDefaultSharedPreferences(context));
update();
}
+ public boolean isAutoLoginEnabled() {
+ return autoLoginEnabled;
+ }
+
+ public String getAutoLoginAccount(Context context) {
+ // Each time we attempt to get the account, we need to verify that the
+ // account is still valid.
+ return GoogleAccountLogin.validateAccount(context, autoLoginAccount);
+ }
+
+ public void setAutoLoginAccount(Context context, String name) {
+ Editor ed = PreferenceManager.
+ getDefaultSharedPreferences(context).edit();
+ ed.putString(PREF_AUTOLOGIN_ACCOUNT, name);
+ ed.apply();
+ autoLoginAccount = name;
+ }
+
+ public void setAutoLoginEnabled(Context context, boolean enable) {
+ Editor ed = PreferenceManager.
+ getDefaultSharedPreferences(context).edit();
+ ed.putBoolean(PREF_AUTOLOGIN, enable);
+ ed.apply();
+ autoLoginEnabled = enable;
+ }
+
+ public void setAutoFillProfile(Context ctx, AutoFillProfile profile, Message msg) {
+ if (profile != null) {
+ setActiveAutoFillProfileId(ctx, profile.getUniqueId());
+ // Update the AutoFill DB with the new profile.
+ new SaveProfileToDbTask(ctx, msg).execute(profile);
+ } else {
+ // Delete the current profile.
+ if (autoFillProfile != null) {
+ new DeleteProfileFromDbTask(ctx, msg).execute(autoFillProfile.getUniqueId());
+ setActiveAutoFillProfileId(ctx, NO_AUTOFILL_PROFILE_SET);
+ }
+ }
+ autoFillProfile = profile;
+ }
+
+ public AutoFillProfile getAutoFillProfile() {
+ return autoFillProfile;
+ }
+
+ private void setActiveAutoFillProfileId(Context context, int activeProfileId) {
+ autoFillActiveProfileId = activeProfileId;
+ Editor ed = PreferenceManager.
+ getDefaultSharedPreferences(context).edit();
+ ed.putInt(PREF_AUTOFILL_ACTIVE_PROFILE_ID, activeProfileId);
+ ed.apply();
+ }
+
+ /* package */ void disableAutoFill(Context ctx) {
+ autoFillEnabled = false;
+ Editor ed = PreferenceManager.getDefaultSharedPreferences(ctx).edit();
+ ed.putBoolean(PREF_AUTOFILL_ENABLED, false);
+ ed.apply();
+ }
+
/**
* Add a WebSettings object to the list of observers that will be updated
* when update() is called.
@@ -497,10 +700,10 @@
}
/*
- * Package level method for obtaining a single app instance of the
+ * Application level method for obtaining a single app instance of the
* BrowserSettings.
*/
- /*package*/ static BrowserSettings getInstance() {
+ public static BrowserSettings getInstance() {
if (sSingleton == null ) {
sSingleton = new BrowserSettings();
}
@@ -510,8 +713,8 @@
/*
* Package level method for associating the BrowserSettings with TabControl
*/
- /* package */void setTabControl(TabControl tabControl) {
- mTabControl = tabControl;
+ /* package */void setController(Controller ctrl) {
+ mController = ctrl;
updateTabControlSettings();
}
@@ -525,8 +728,8 @@
/*package*/ void clearCache(Context context) {
WebIconDatabase.getInstance().removeAllIcons();
- if (mTabControl != null) {
- WebView current = mTabControl.getCurrentWebView();
+ if (mController != null) {
+ WebView current = mController.getCurrentWebView();
if (current != null) {
current.clearCache(true);
}
@@ -545,8 +748,8 @@
/* package */ void clearFormData(Context context) {
WebViewDatabase.getInstance(context).clearFormData();
- if (mTabControl != null) {
- WebView currentTopView = mTabControl.getCurrentTopWebView();
+ if (mController!= null) {
+ WebView currentTopView = mController.getCurrentTopWebView();
if (currentTopView != null) {
currentTopView.clearFormData();
}
@@ -561,59 +764,33 @@
private void updateTabControlSettings() {
// Enable/disable the error console.
- mTabControl.getBrowserActivity().setShouldShowErrorConsole(
+ mController.setShouldShowErrorConsole(
showDebugSettings && showConsole);
- mTabControl.getBrowserActivity().setRequestedOrientation(
- landscapeOnly ? ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE
- : ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED);
- }
-
- private void maybeDisableWebsiteSettings(Context context) {
- PreferenceActivity activity = (PreferenceActivity) context;
- final PreferenceScreen screen = (PreferenceScreen)
- activity.findPreference(BrowserSettings.PREF_WEBSITE_SETTINGS);
- screen.setEnabled(false);
- WebStorage.getInstance().getOrigins(new ValueCallback<Map>() {
- public void onReceiveValue(Map webStorageOrigins) {
- if ((webStorageOrigins != null) && !webStorageOrigins.isEmpty()) {
- screen.setEnabled(true);
- }
- }
- });
-
- GeolocationPermissions.getInstance().getOrigins(new ValueCallback<Set<String> >() {
- public void onReceiveValue(Set<String> geolocationOrigins) {
- if ((geolocationOrigins != null) && !geolocationOrigins.isEmpty()) {
- screen.setEnabled(true);
- }
- }
- });
}
/*package*/ void clearDatabases(Context context) {
WebStorage.getInstance().deleteAllData();
- maybeDisableWebsiteSettings(context);
}
/*package*/ void clearLocationAccess(Context context) {
GeolocationPermissions.getInstance().clearAll();
- maybeDisableWebsiteSettings(context);
}
/*package*/ void resetDefaultPreferences(Context ctx) {
reset();
- SharedPreferences p =
- PreferenceManager.getDefaultSharedPreferences(ctx);
+ SharedPreferences p = PreferenceManager.getDefaultSharedPreferences(ctx);
p.edit().clear().apply();
- PreferenceManager.setDefaultValues(ctx, R.xml.browser_preferences,
- true);
+ PreferenceManager.setDefaultValues(ctx, R.xml.general_preferences, true);
+ PreferenceManager.setDefaultValues(ctx, R.xml.privacy_security_preferences, true);
+ PreferenceManager.setDefaultValues(ctx, R.xml.advanced_preferences, true);
// reset homeUrl
setHomePage(ctx, getFactoryResetHomeUrl(ctx));
// reset appcache max size
appCacheMaxSize = webStorageSizeManager.getAppCacheMaxSize();
+ setActiveAutoFillProfileId(ctx, NO_AUTOFILL_PROFILE_SET);
}
- private String getFactoryResetHomeUrl(Context context) {
+ /*package*/ static String getFactoryResetHomeUrl(Context context) {
String url = context.getResources().getString(R.string.homepage_base);
if (url.indexOf("{CID}") != -1) {
url = url.replace("{CID}",
@@ -639,9 +816,9 @@
showSecurityWarnings = true;
rememberPasswords = true;
saveFormData = true;
+ autoFillEnabled = true;
openInBackground = false;
autoFitPage = true;
- landscapeOnly = false;
loadsPageInOverviewMode = true;
showDebugSettings = false;
// HTML5 API flags
@@ -650,5 +827,72 @@
domStorageEnabled = true;
geolocationEnabled = true;
workersEnabled = true; // only affects V8. JSC does not have a similar setting
+ // Autologin default is true. The account will be populated when
+ // reading from the DB as that is when a context is available.
+ autoLoginEnabled = true;
+ }
+
+ private abstract class AutoFillProfileDbTask<T> extends AsyncTask<T, Void, Void> {
+ Context mContext;
+ AutoFillProfileDatabase mAutoFillProfileDb;
+ Message mCompleteMessage;
+
+ public AutoFillProfileDbTask(Context ctx, Message msg) {
+ mContext = ctx;
+ mCompleteMessage = msg;
+ }
+
+ protected void onPostExecute(Void result) {
+ if (mCompleteMessage != null) {
+ mCompleteMessage.sendToTarget();
+ }
+ mAutoFillProfileDb.close();
+ }
+
+ abstract protected Void doInBackground(T... values);
+ }
+
+
+ private class SaveProfileToDbTask extends AutoFillProfileDbTask<AutoFillProfile> {
+ public SaveProfileToDbTask(Context ctx, Message msg) {
+ super(ctx, msg);
+ }
+
+ protected Void doInBackground(AutoFillProfile... values) {
+ mAutoFillProfileDb = AutoFillProfileDatabase.getInstance(mContext);
+ assert autoFillActiveProfileId != NO_AUTOFILL_PROFILE_SET;
+ AutoFillProfile newProfile = values[0];
+ mAutoFillProfileDb.addOrUpdateProfile(autoFillActiveProfileId, newProfile);
+ return null;
+ }
+ }
+
+ private class DeleteProfileFromDbTask extends AutoFillProfileDbTask<Integer> {
+ public DeleteProfileFromDbTask(Context ctx, Message msg) {
+ super(ctx, msg);
+ }
+
+ protected Void doInBackground(Integer... values) {
+ mAutoFillProfileDb = AutoFillProfileDatabase.getInstance(mContext);
+ int id = values[0];
+ assert id > 0;
+ mAutoFillProfileDb.dropProfile(id);
+ return null;
+ }
+ }
+
+ @Override
+ public void onSharedPreferenceChanged(
+ SharedPreferences p, String key) {
+ if (PREF_HARDWARE_ACCEL.equals(key)) {
+ hardwareAccelerated = p.getBoolean(PREF_HARDWARE_ACCEL, hardwareAccelerated);
+ } else if (PREF_USER_AGENT.equals(key)) {
+ userAgent = Integer.parseInt(p.getString(PREF_USER_AGENT, "0"));
+ update();
+ } else if (PREF_QUICK_CONTROLS.equals(key)) {
+ quickControls = p.getBoolean(PREF_QUICK_CONTROLS, quickControls);
+ } else if (PREF_MOST_VISITED_HOMEPAGE.equals(key)) {
+ useMostVisitedHomepage = p.getBoolean(PREF_MOST_VISITED_HOMEPAGE, useMostVisitedHomepage);
+ }
}
}
diff --git a/src/com/android/browser/CombinedBookmarkHistoryActivity.java b/src/com/android/browser/CombinedBookmarkHistoryActivity.java
deleted file mode 100644
index 194956f..0000000
--- a/src/com/android/browser/CombinedBookmarkHistoryActivity.java
+++ /dev/null
@@ -1,192 +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.browser;
-
-import android.app.Activity;
-import android.app.TabActivity;
-import android.content.Intent;
-import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.os.AsyncTask;
-import android.os.Bundle;
-import android.provider.Browser;
-import android.webkit.WebIconDatabase;
-import android.webkit.WebIconDatabase.IconListener;
-import android.widget.TabHost;
-
-import java.util.HashMap;
-import java.util.Vector;
-
-public class CombinedBookmarkHistoryActivity extends TabActivity
- implements TabHost.OnTabChangeListener {
- /**
- * Used to inform BrowserActivity to remove the parent/child relationships
- * from all the tabs.
- */
- private String mExtraData;
- /**
- * Intent to be passed to calling Activity when finished. Keep a pointer to
- * it locally so mExtraData can be added.
- */
- private Intent mResultData;
- /**
- * Result code to pass back to calling Activity when finished.
- */
- private int mResultCode;
-
- /* package */ static String BOOKMARKS_TAB = "bookmark";
- /* package */ static String VISITED_TAB = "visited";
- /* package */ static String HISTORY_TAB = "history";
- /* package */ static String STARTING_TAB = "tab";
-
- static class IconListenerSet implements IconListener {
- // Used to store favicons as we get them from the database
- // FIXME: We use a different method to get the Favicons in
- // BrowserBookmarksAdapter. They should probably be unified.
- private HashMap<String, Bitmap> mUrlsToIcons;
- private Vector<IconListener> mListeners;
-
- public IconListenerSet() {
- mUrlsToIcons = new HashMap<String, Bitmap>();
- mListeners = new Vector<IconListener>();
- }
- public void onReceivedIcon(String url, Bitmap icon) {
- mUrlsToIcons.put(url, icon);
- for (IconListener listener : mListeners) {
- listener.onReceivedIcon(url, icon);
- }
- }
- public void addListener(IconListener listener) {
- mListeners.add(listener);
- }
- public void removeListener(IconListener listener) {
- mListeners.remove(listener);
- }
- public Bitmap getFavicon(String url) {
- return (Bitmap) mUrlsToIcons.get(url);
- }
- }
- private static IconListenerSet sIconListenerSet;
- static IconListenerSet getIconListenerSet() {
- if (null == sIconListenerSet) {
- sIconListenerSet = new IconListenerSet();
- }
- return sIconListenerSet;
- }
-
- @Override
- protected void onCreate(Bundle savedInstanceState) {
- super.onCreate(savedInstanceState);
- setContentView(R.layout.tabs);
-
- setDefaultKeyMode(DEFAULT_KEYS_SEARCH_LOCAL);
-
- getTabHost().setOnTabChangedListener(this);
-
- Bundle extras = getIntent().getExtras();
-
- Intent bookmarksIntent = new Intent(this, BrowserBookmarksPage.class);
- if (extras != null) {
- bookmarksIntent.putExtras(extras);
- }
- createTab(bookmarksIntent, R.string.tab_bookmarks,
- R.drawable.browser_bookmark_tab, BOOKMARKS_TAB);
-
- Intent visitedIntent = new Intent(this, BrowserBookmarksPage.class);
- // Need to copy extras so the bookmarks activity and this one will be
- // different
- Bundle visitedExtras = extras == null ? new Bundle() : new Bundle(extras);
- visitedExtras.putBoolean("mostVisited", true);
- visitedIntent.putExtras(visitedExtras);
- createTab(visitedIntent, R.string.tab_most_visited,
- R.drawable.browser_visited_tab, VISITED_TAB);
-
- Intent historyIntent = new Intent(this, BrowserHistoryPage.class);
- String defaultTab = null;
- if (extras != null) {
- historyIntent.putExtras(extras);
- defaultTab = extras.getString(STARTING_TAB);
- }
- createTab(historyIntent, R.string.tab_history,
- R.drawable.browser_history_tab, HISTORY_TAB);
-
- if (defaultTab != null) {
- getTabHost().setCurrentTab(2);
- }
-
- // XXX: Must do this before launching the AsyncTask to avoid a
- // potential crash if the icon database has not been created.
- WebIconDatabase.getInstance();
- // Do this every time we launch the activity in case a new favicon was
- // added to the webkit db.
- (new AsyncTask<Void, Void, Void>() {
- public Void doInBackground(Void... v) {
- Browser.requestAllIcons(getContentResolver(),
- Browser.BookmarkColumns.FAVICON + " is NULL",
- getIconListenerSet());
- return null;
- }
- }).execute();
- }
-
- private void createTab(Intent intent, int labelResId, int iconResId,
- String tab) {
- Resources resources = getResources();
- TabHost tabHost = getTabHost();
- tabHost.addTab(tabHost.newTabSpec(tab).setIndicator(
- resources.getText(labelResId), resources.getDrawable(iconResId))
- .setContent(intent));
- }
- // Copied from DialTacts Activity
- /** {@inheritDoc} */
- public void onTabChanged(String tabId) {
- Activity activity = getLocalActivityManager().getActivity(tabId);
- if (activity != null) {
- activity.onWindowFocusChanged(true);
- }
- }
-
- /**
- * Store extra data in the Intent to return to the calling Activity to tell
- * it to clear the parent/child relationships from all tabs.
- */
- /* package */ void removeParentChildRelationShips() {
- mExtraData = BrowserSettings.PREF_CLEAR_HISTORY;
- }
-
- /**
- * Custom setResult() method so that the Intent can have extra data attached
- * if necessary.
- * @param resultCode Uses same codes as Activity.setResult
- * @param data Intent returned to onActivityResult.
- */
- /* package */ void setResultFromChild(int resultCode, Intent data) {
- mResultCode = resultCode;
- mResultData = data;
- }
-
- @Override
- public void finish() {
- if (mExtraData != null) {
- mResultCode = RESULT_OK;
- if (mResultData == null) mResultData = new Intent();
- mResultData.putExtra(Intent.EXTRA_TEXT, mExtraData);
- }
- setResult(mResultCode, mResultData);
- super.finish();
- }
-}
diff --git a/src/com/android/browser/CombinedBookmarkHistoryView.java b/src/com/android/browser/CombinedBookmarkHistoryView.java
new file mode 100644
index 0000000..173abba
--- /dev/null
+++ b/src/com/android/browser/CombinedBookmarkHistoryView.java
@@ -0,0 +1,345 @@
+/*
+ * 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.browser;
+
+
+import android.app.ActionBar;
+import android.app.ActionBar.Tab;
+import android.app.ActionBar.TabListener;
+import android.app.Activity;
+import android.app.FragmentManager;
+import android.app.FragmentTransaction;
+import android.content.Intent;
+import android.content.res.Configuration;
+import android.content.res.Resources;
+import android.database.Cursor;
+import android.graphics.Bitmap;
+import android.net.Uri;
+import android.os.AsyncTask;
+import android.os.Bundle;
+import android.provider.Browser;
+import android.view.Gravity;
+import android.view.LayoutInflater;
+import android.view.Menu;
+import android.view.MenuItem;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.View.OnTouchListener;
+import android.view.ViewGroup;
+import android.webkit.WebIconDatabase;
+import android.webkit.WebIconDatabase.IconListener;
+import android.widget.FrameLayout;
+import android.widget.LinearLayout;
+
+import java.util.HashMap;
+import java.util.Vector;
+
+interface BookmarksHistoryCallbacks {
+ public void onUrlSelected(String url, boolean newWindow);
+ public void onRemoveParentChildRelationships();
+}
+
+public class CombinedBookmarkHistoryView extends LinearLayout
+ implements OnTouchListener, TabListener, OptionsMenuHandler {
+
+ final static String STARTING_FRAGMENT = "fragment";
+
+ final static int INVALID_ID = 0;
+ final static int FRAGMENT_ID_BOOKMARKS = 1;
+ final static int FRAGMENT_ID_HISTORY = 2;
+
+ private UiController mUiController;
+ private Activity mActivity;
+ private ActionBar mActionBar;
+
+ private Bundle mExtras;
+
+ int mCurrentFragment = INVALID_ID;
+
+ ActionBar.Tab mTabBookmarks;
+ ActionBar.Tab mTabHistory;
+ ViewGroup mBookmarksHeader;
+
+ BrowserBookmarksPage mBookmarks;
+ BrowserHistoryPage mHistory;
+
+ static class IconListenerSet implements IconListener {
+ // Used to store favicons as we get them from the database
+ // FIXME: We use a different method to get the Favicons in
+ // BrowserBookmarksAdapter. They should probably be unified.
+ private HashMap<String, Bitmap> mUrlsToIcons;
+ private Vector<IconListener> mListeners;
+
+ public IconListenerSet() {
+ mUrlsToIcons = new HashMap<String, Bitmap>();
+ mListeners = new Vector<IconListener>();
+ }
+ @Override
+ public void onReceivedIcon(String url, Bitmap icon) {
+ mUrlsToIcons.put(url, icon);
+ for (IconListener listener : mListeners) {
+ listener.onReceivedIcon(url, icon);
+ }
+ }
+ public void addListener(IconListener listener) {
+ mListeners.add(listener);
+ }
+ public void removeListener(IconListener listener) {
+ mListeners.remove(listener);
+ }
+ public Bitmap getFavicon(String url) {
+ return mUrlsToIcons.get(url);
+ }
+ }
+
+ private static IconListenerSet sIconListenerSet;
+ static IconListenerSet getIconListenerSet() {
+ if (null == sIconListenerSet) {
+ sIconListenerSet = new IconListenerSet();
+ }
+ return sIconListenerSet;
+ }
+
+ public CombinedBookmarkHistoryView(Activity activity, UiController controller,
+ int startingFragment, Bundle extras) {
+ super(activity);
+ mUiController = controller;
+ mActivity = activity;
+ mExtras = extras;
+ mActionBar = mActivity.getActionBar();
+
+ View v = LayoutInflater.from(activity).inflate(R.layout.bookmarks_history, this);
+ v.setOnTouchListener(this);
+ Resources res = activity.getResources();
+
+// setDefaultKeyMode(DEFAULT_KEYS_SEARCH_LOCAL);
+
+ mBookmarksHeader = new FrameLayout(mActivity);
+ mBookmarksHeader.setLayoutParams(new FrameLayout.LayoutParams(
+ FrameLayout.LayoutParams.WRAP_CONTENT,
+ FrameLayout.LayoutParams.MATCH_PARENT,
+ Gravity.CENTER_VERTICAL));
+
+ // Start up the default fragment
+ initFragments(mExtras);
+
+ // XXX: Must do this before launching the AsyncTask to avoid a
+ // potential crash if the icon database has not been created.
+ WebIconDatabase.getInstance();
+
+ // Do this every time the view is created in case a new favicon was
+ // added to the webkit db.
+ (new AsyncTask<Void, Void, Void>() {
+ @Override
+ public Void doInBackground(Void... v) {
+ Browser.requestAllIcons(mActivity.getContentResolver(),
+ Browser.BookmarkColumns.FAVICON + " is NULL", getIconListenerSet());
+ return null;
+ }
+ }).execute();
+
+ setupActionBar(startingFragment);
+ mUiController.registerOptionsMenuHandler(this);
+ }
+
+ void setupActionBar(int startingFragment) {
+ mActionBar.setDisplayOptions(ActionBar.DISPLAY_SHOW_HOME
+ | ActionBar.DISPLAY_USE_LOGO);
+ mActionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
+ mActionBar.removeAllTabs();
+ mTabBookmarks = mActionBar.newTab();
+ mTabBookmarks.setText(R.string.tab_bookmarks);
+ mTabBookmarks.setTabListener(this);
+ mActionBar.addTab(mTabBookmarks, FRAGMENT_ID_BOOKMARKS == startingFragment);
+ mTabHistory = mActionBar.newTab();
+ mTabHistory.setText(R.string.tab_history);
+ mTabHistory.setTabListener(this);
+ mActionBar.addTab(mTabHistory, FRAGMENT_ID_HISTORY == startingFragment);
+ mActionBar.setCustomView(mBookmarksHeader);
+
+ }
+
+ @Override
+ protected void onConfigurationChanged(Configuration newConfig) {
+ super.onConfigurationChanged(newConfig);
+ if (mCurrentFragment == FRAGMENT_ID_HISTORY) {
+ // Warning, ugly hack below
+ // This is done because history uses orientation-specific padding
+ FragmentManager fm = mActivity.getFragmentManager();
+ mHistory = BrowserHistoryPage.newInstance(mUiController, mHistory.getArguments());
+ fm.beginTransaction().replace(R.id.fragment, mHistory).commit();
+ }
+ }
+
+ private BookmarksPageCallbacks mBookmarkCallbackWrapper = new BookmarksPageCallbacks() {
+ @Override
+ public boolean onOpenInNewWindow(Cursor c) {
+ mUiController.onUrlSelected(BrowserBookmarksPage.getUrl(c), true);
+ return true;
+ }
+
+ @Override
+ public boolean onBookmarkSelected(Cursor c, boolean isFolder) {
+ if (isFolder) {
+ return false;
+ }
+ mUiController.onUrlSelected(BrowserBookmarksPage.getUrl(c), false);
+ return true;
+ }
+
+ @Override
+ public void onFolderChanged(int level, Uri uri) {
+ final int toggleFlags = ActionBar.DISPLAY_SHOW_CUSTOM
+ | ActionBar.DISPLAY_HOME_AS_UP;
+ // 1 is "bookmarks" root folder
+ if (level <= 1) {
+ mActionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS);
+ mActionBar.setDisplayOptions(0, toggleFlags);
+ } else {
+ mActionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD);
+ mActionBar.setDisplayOptions(toggleFlags, toggleFlags);
+ }
+ }
+ };
+
+ private void initFragments(Bundle extras) {
+ mBookmarks = BrowserBookmarksPage.newInstance(mBookmarkCallbackWrapper,
+ extras, mBookmarksHeader);
+ mBookmarks.setBreadCrumbMaxVisible(2);
+ mBookmarks.setBreadCrumbUseBackButton(false);
+ mHistory = BrowserHistoryPage.newInstance(mUiController, extras);
+ }
+
+ private void loadFragment(int id, FragmentTransaction ft) {
+ if (mCurrentFragment == id) return;
+
+ switch (id) {
+ case FRAGMENT_ID_BOOKMARKS:
+ ft.replace(R.id.fragment, mBookmarks);
+ break;
+ case FRAGMENT_ID_HISTORY:
+ ft.replace(R.id.fragment, mHistory);
+ break;
+ default:
+ throw new IllegalArgumentException();
+ }
+ mCurrentFragment = id;
+ }
+
+ @Override
+ protected void onDetachedFromWindow() {
+ super.onDetachedFromWindow();
+ if (mCurrentFragment != INVALID_ID) {
+ try {
+ FragmentManager fm = mActivity.getFragmentManager();
+ FragmentTransaction transaction = fm.beginTransaction();
+ if (mCurrentFragment == FRAGMENT_ID_BOOKMARKS) {
+ transaction.remove(mBookmarks);
+ } else if (mCurrentFragment == FRAGMENT_ID_HISTORY) {
+ transaction.remove(mHistory);
+ }
+ transaction.commit();
+ } catch (IllegalStateException ex) {
+ // This exception is thrown if the fragment isn't added
+ // This will happen if the activity is finishing, and the
+ // fragment was already removed before this view was detached
+ // Aka, success!
+ }
+ mCurrentFragment = INVALID_ID;
+ }
+ mUiController.unregisterOptionsMenuHandler(this);
+ }
+
+ /**
+ * callback for back key presses
+ */
+ boolean onBackPressed() {
+ if (mCurrentFragment == FRAGMENT_ID_BOOKMARKS) {
+ return mBookmarks.onBackPressed();
+ }
+ return false;
+ }
+
+ /**
+ * capture touch events to prevent them from going to the underlying
+ * WebView
+ */
+ @Override
+ public boolean onTouch(View v, MotionEvent event) {
+ return true;
+ }
+
+ @Override
+ public void onTabReselected(Tab tab, FragmentTransaction ft) {
+ // Ignore
+ }
+
+ @Override
+ public void onTabSelected(Tab tab, FragmentTransaction ft) {
+ if (tab == mTabBookmarks) {
+ loadFragment(FRAGMENT_ID_BOOKMARKS, ft);
+ } else if (tab == mTabHistory) {
+ loadFragment(FRAGMENT_ID_HISTORY, ft);
+ }
+ }
+
+ @Override
+ public void onTabUnselected(Tab tab, FragmentTransaction ft) {
+ // Ignore
+ }
+
+ @Override
+ public boolean onCreateOptionsMenu(Menu menu) {
+ // Handled by fragment
+ return false;
+ }
+
+ @Override
+ public boolean onPrepareOptionsMenu(Menu menu) {
+ // Handled by fragment
+ return false;
+ }
+
+ public boolean onOptionsItemSelected(MenuItem item) {
+ switch (item.getItemId()) {
+ case android.R.id.home:
+ mUiController.getUi().onBackKey();
+ return true;
+ case R.id.go_home:
+ BrowserSettings settings = BrowserSettings.getInstance();
+ mUiController.onUrlSelected(settings.getHomePage(), false);
+ return true;
+ case R.id.add_bookmark:
+ mUiController.bookmarkCurrentPage(mBookmarks.getFolderId());
+ return true;
+ case R.id.preferences_menu_id:
+ Intent intent = new Intent(mActivity, BrowserPreferencesPage.class);
+ intent.putExtra(BrowserPreferencesPage.CURRENT_PAGE,
+ mUiController.getCurrentTopWebView().getUrl());
+ mActivity.startActivityForResult(intent, Controller.PREFERENCES_PAGE);
+ return true;
+ }
+
+ switch (mCurrentFragment) {
+ case FRAGMENT_ID_BOOKMARKS:
+ return mBookmarks.onOptionsItemSelected(item);
+ case FRAGMENT_ID_HISTORY:
+ return mHistory.onOptionsItemSelected(item);
+ }
+ return false;
+ }
+}
diff --git a/src/com/android/browser/Controller.java b/src/com/android/browser/Controller.java
new file mode 100644
index 0000000..74a66b1
--- /dev/null
+++ b/src/com/android/browser/Controller.java
@@ -0,0 +1,2527 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.IntentHandler.UrlData;
+import com.android.browser.search.SearchEngine;
+import com.android.common.Search;
+
+import android.app.Activity;
+import android.app.DownloadManager;
+import android.app.SearchManager;
+import android.content.ClipboardManager;
+import android.content.ContentProvider;
+import android.content.ContentProviderClient;
+import android.content.ContentResolver;
+import android.content.ContentValues;
+import android.content.Context;
+import android.content.Intent;
+import android.content.pm.PackageManager;
+import android.content.pm.ResolveInfo;
+import android.content.res.Configuration;
+import android.database.ContentObserver;
+import android.database.Cursor;
+import android.database.sqlite.SQLiteDatabase;
+import android.graphics.Bitmap;
+import android.graphics.Canvas;
+import android.graphics.Picture;
+import android.net.Uri;
+import android.net.http.SslError;
+import android.os.AsyncTask;
+import android.os.Bundle;
+import android.os.Handler;
+import android.os.Message;
+import android.os.PowerManager;
+import android.os.PowerManager.WakeLock;
+import android.preference.PreferenceActivity;
+import android.provider.Browser;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Images;
+import android.provider.ContactsContract;
+import android.provider.ContactsContract.Intents.Insert;
+import android.speech.RecognizerIntent;
+import android.speech.RecognizerResultsIntent;
+import android.text.TextUtils;
+import android.util.Log;
+import android.util.Patterns;
+import android.view.ActionMode;
+import android.view.ContextMenu;
+import android.view.ContextMenu.ContextMenuInfo;
+import android.view.Gravity;
+import android.view.KeyEvent;
+import android.view.Menu;
+import android.view.MenuInflater;
+import android.view.MenuItem;
+import android.view.MenuItem.OnMenuItemClickListener;
+import android.view.View;
+import android.webkit.CookieManager;
+import android.webkit.CookieSyncManager;
+import android.webkit.HttpAuthHandler;
+import android.webkit.SslErrorHandler;
+import android.webkit.ValueCallback;
+import android.webkit.WebChromeClient;
+import android.webkit.WebIconDatabase;
+import android.webkit.WebSettings;
+import android.webkit.WebView;
+
+import java.io.ByteArrayOutputStream;
+import java.io.File;
+import java.net.URLEncoder;
+import java.util.Calendar;
+import java.util.HashMap;
+import java.util.List;
+
+/**
+ * Controller for browser
+ */
+public class Controller
+ implements WebViewController, UiController {
+
+ private static final String LOGTAG = "Controller";
+ private static final String SEND_APP_ID_EXTRA =
+ "android.speech.extras.SEND_APPLICATION_ID_EXTRA";
+
+
+ // public message ids
+ public final static int LOAD_URL = 1001;
+ public final static int STOP_LOAD = 1002;
+
+ // Message Ids
+ private static final int FOCUS_NODE_HREF = 102;
+ private static final int RELEASE_WAKELOCK = 107;
+
+ static final int UPDATE_BOOKMARK_THUMBNAIL = 108;
+
+ private static final int OPEN_BOOKMARKS = 201;
+
+ private static final int EMPTY_MENU = -1;
+
+ // activity requestCode
+ final static int PREFERENCES_PAGE = 3;
+ final static int FILE_SELECTED = 4;
+ final static int AUTOFILL_SETUP = 5;
+
+ private final static int WAKELOCK_TIMEOUT = 5 * 60 * 1000; // 5 minutes
+
+ // As the ids are dynamically created, we can't guarantee that they will
+ // be in sequence, so this static array maps ids to a window number.
+ final static private int[] WINDOW_SHORTCUT_ID_ARRAY =
+ { R.id.window_one_menu_id, R.id.window_two_menu_id,
+ R.id.window_three_menu_id, R.id.window_four_menu_id,
+ R.id.window_five_menu_id, R.id.window_six_menu_id,
+ R.id.window_seven_menu_id, R.id.window_eight_menu_id };
+
+ // "source" parameter for Google search through search key
+ final static String GOOGLE_SEARCH_SOURCE_SEARCHKEY = "browser-key";
+ // "source" parameter for Google search through simplily type
+ final static String GOOGLE_SEARCH_SOURCE_TYPE = "browser-type";
+
+ private Activity mActivity;
+ private UI mUi;
+ private TabControl mTabControl;
+ private BrowserSettings mSettings;
+ private WebViewFactory mFactory;
+ private OptionsMenuHandler mOptionsMenuHandler = null;
+
+ private WakeLock mWakeLock;
+
+ private UrlHandler mUrlHandler;
+ private UploadHandler mUploadHandler;
+ private IntentHandler mIntentHandler;
+ private PageDialogsHandler mPageDialogsHandler;
+ private NetworkStateHandler mNetworkHandler;
+
+ private Message mAutoFillSetupMessage;
+
+ private boolean mShouldShowErrorConsole;
+
+ private SystemAllowGeolocationOrigins mSystemAllowGeolocationOrigins;
+
+ // FIXME, temp address onPrepareMenu performance problem.
+ // When we move everything out of view, we should rewrite this.
+ private int mCurrentMenuState = 0;
+ private int mMenuState = R.id.MAIN_MENU;
+ private int mOldMenuState = EMPTY_MENU;
+ private Menu mCachedMenu;
+
+ // Used to prevent chording to result in firing two shortcuts immediately
+ // one after another. Fixes bug 1211714.
+ boolean mCanChord;
+ private boolean mMenuIsDown;
+
+ // For select and find, we keep track of the ActionMode so that
+ // finish() can be called as desired.
+ private ActionMode mActionMode;
+
+ /**
+ * Only meaningful when mOptionsMenuOpen is true. This variable keeps track
+ * of whether the configuration has changed. The first onMenuOpened call
+ * after a configuration change is simply a reopening of the same menu
+ * (i.e. mIconView did not change).
+ */
+ private boolean mConfigChanged;
+
+ /**
+ * Keeps track of whether the options menu is open. This is important in
+ * determining whether to show or hide the title bar overlay
+ */
+ private boolean mOptionsMenuOpen;
+
+ /**
+ * Whether or not the options menu is in its bigger, popup menu form. When
+ * true, we want the title bar overlay to be gone. When false, we do not.
+ * Only meaningful if mOptionsMenuOpen is true.
+ */
+ private boolean mExtendedMenuOpen;
+
+ private boolean mInLoad;
+
+ private boolean mActivityPaused = true;
+ private boolean mLoadStopped;
+
+ private Handler mHandler;
+ // Checks to see when the bookmarks database has changed, and updates the
+ // Tabs' notion of whether they represent bookmarked sites.
+ private ContentObserver mBookmarksObserver;
+ private DataController mDataController;
+
+ private static class ClearThumbnails extends AsyncTask<File, Void, Void> {
+ @Override
+ public Void doInBackground(File... files) {
+ if (files != null) {
+ for (File f : files) {
+ if (!f.delete()) {
+ Log.e(LOGTAG, f.getPath() + " was not deleted");
+ }
+ }
+ }
+ return null;
+ }
+ }
+
+ public Controller(Activity browser) {
+ mActivity = browser;
+ mSettings = BrowserSettings.getInstance();
+ mDataController = DataController.getInstance(mActivity);
+ mTabControl = new TabControl(this);
+ mSettings.setController(this);
+
+ mUrlHandler = new UrlHandler(this);
+ mIntentHandler = new IntentHandler(mActivity, this);
+ mPageDialogsHandler = new PageDialogsHandler(mActivity, this);
+
+ PowerManager pm = (PowerManager) mActivity
+ .getSystemService(Context.POWER_SERVICE);
+ mWakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "Browser");
+
+ startHandler();
+ mBookmarksObserver = new ContentObserver(mHandler) {
+ @Override
+ public void onChange(boolean selfChange) {
+ int size = mTabControl.getTabCount();
+ for (int i = 0; i < size; i++) {
+ mTabControl.getTab(i).updateBookmarkedStatus();
+ }
+ }
+
+ };
+ browser.getContentResolver().registerContentObserver(
+ BrowserContract.Bookmarks.CONTENT_URI, true, mBookmarksObserver);
+
+ mNetworkHandler = new NetworkStateHandler(mActivity, this);
+ // Start watching the default geolocation permissions
+ mSystemAllowGeolocationOrigins =
+ new SystemAllowGeolocationOrigins(mActivity.getApplicationContext());
+ mSystemAllowGeolocationOrigins.start();
+
+ retainIconsOnStartup();
+ }
+
+ void start(final Bundle icicle, final Intent intent) {
+ // Unless the last browser usage was within 24 hours, destroy any
+ // remaining incognito tabs.
+
+ Calendar lastActiveDate = icicle != null ?
+ (Calendar) icicle.getSerializable("lastActiveDate") : null;
+ Calendar today = Calendar.getInstance();
+ Calendar yesterday = Calendar.getInstance();
+ yesterday.add(Calendar.DATE, -1);
+
+ final boolean restoreIncognitoTabs = !(lastActiveDate == null
+ || lastActiveDate.before(yesterday)
+ || lastActiveDate.after(today));
+
+ // Find out if we will restore any state and remember the tab.
+ final int currentTab =
+ mTabControl.canRestoreState(icicle, restoreIncognitoTabs);
+
+ if (currentTab == -1) {
+ // Not able to restore so we go ahead and clear session cookies. We
+ // must do this before trying to login the user as we don't want to
+ // clear any session cookies set during login.
+ CookieManager.getInstance().removeSessionCookie();
+ }
+
+ GoogleAccountLogin.startLoginIfNeeded(mActivity, mSettings,
+ new Runnable() {
+ @Override public void run() {
+ start(icicle, intent, currentTab, restoreIncognitoTabs);
+ }
+ });
+ }
+
+ private void start(Bundle icicle, Intent intent, int currentTab,
+ boolean restoreIncognitoTabs) {
+ if (currentTab == -1) {
+ final Bundle extra = intent.getExtras();
+ // Create an initial tab.
+ // If the intent is ACTION_VIEW and data is not null, the Browser is
+ // invoked to view the content by another application. In this case,
+ // the tab will be close when exit.
+ UrlData urlData = mIntentHandler.getUrlDataFromIntent(intent);
+
+ String action = intent.getAction();
+ final Tab t = mTabControl.createNewTab(
+ (Intent.ACTION_VIEW.equals(action) &&
+ intent.getData() != null)
+ || RecognizerResultsIntent.ACTION_VOICE_SEARCH_RESULTS
+ .equals(action),
+ intent.getStringExtra(Browser.EXTRA_APPLICATION_ID),
+ urlData.mUrl, false);
+ addTab(t);
+ setActiveTab(t);
+ WebView webView = t.getWebView();
+ if (extra != null) {
+ int scale = extra.getInt(Browser.INITIAL_ZOOM_LEVEL, 0);
+ if (scale > 0 && scale <= 1000) {
+ webView.setInitialScale(scale);
+ }
+ }
+
+ if (urlData.isEmpty()) {
+ loadUrl(webView, mSettings.getHomePage());
+ } else {
+ loadUrlDataIn(t, urlData);
+ }
+ } else {
+ mTabControl.restoreState(icicle, currentTab, restoreIncognitoTabs,
+ mUi.needsRestoreAllTabs());
+ mUi.updateTabs(mTabControl.getTabs());
+ // TabControl.restoreState() will create a new tab even if
+ // restoring the state fails.
+ setActiveTab(mTabControl.getCurrentTab());
+ }
+ // clear up the thumbnail directory, which is no longer used;
+ // ideally this should only be run once after an upgrade from
+ // a previous version of the browser
+ new ClearThumbnails().execute(mTabControl.getThumbnailDir()
+ .listFiles());
+ // Read JavaScript flags if it exists.
+ String jsFlags = getSettings().getJsFlags();
+ if (jsFlags.trim().length() != 0) {
+ getCurrentWebView().setJsFlags(jsFlags);
+ }
+ if (BrowserActivity.ACTION_SHOW_BOOKMARKS.equals(intent.getAction())) {
+ bookmarksOrHistoryPicker(false);
+ }
+ }
+
+ void setWebViewFactory(WebViewFactory factory) {
+ mFactory = factory;
+ }
+
+ @Override
+ public WebViewFactory getWebViewFactory() {
+ return mFactory;
+ }
+
+ @Override
+ public void onSetWebView(Tab tab, WebView view) {
+ mUi.onSetWebView(tab, view);
+ }
+
+ @Override
+ public void createSubWindow(Tab tab) {
+ endActionMode();
+ WebView mainView = tab.getWebView();
+ WebView subView = mFactory.createWebView((mainView == null)
+ ? false
+ : mainView.isPrivateBrowsingEnabled());
+ mUi.createSubWindow(tab, subView);
+ }
+
+ @Override
+ public Activity getActivity() {
+ return mActivity;
+ }
+
+ void setUi(UI ui) {
+ mUi = ui;
+ }
+
+ BrowserSettings getSettings() {
+ return mSettings;
+ }
+
+ IntentHandler getIntentHandler() {
+ return mIntentHandler;
+ }
+
+ @Override
+ public UI getUi() {
+ return mUi;
+ }
+
+ int getMaxTabs() {
+ return mActivity.getResources().getInteger(R.integer.max_tabs);
+ }
+
+ @Override
+ public TabControl getTabControl() {
+ return mTabControl;
+ }
+
+ @Override
+ public List<Tab> getTabs() {
+ return mTabControl.getTabs();
+ }
+
+ // Open the icon database and retain all the icons for visited sites.
+ // This is done on a background thread so as not to stall startup.
+ private void retainIconsOnStartup() {
+ // WebIconDatabase needs to be retrieved on the UI thread so that if
+ // it has not been created successfully yet the Handler is started on the
+ // UI thread.
+ new RetainIconsOnStartupTask(WebIconDatabase.getInstance()).execute();
+ }
+
+ private class RetainIconsOnStartupTask extends AsyncTask<Void, Void, Void> {
+ private WebIconDatabase mDb;
+
+ public RetainIconsOnStartupTask(WebIconDatabase db) {
+ mDb = db;
+ }
+
+ @Override
+ protected Void doInBackground(Void... unused) {
+ mDb.open(mActivity.getDir("icons", 0).getPath());
+ Cursor c = null;
+ try {
+ c = Browser.getAllBookmarks(mActivity.getContentResolver());
+ if (c.moveToFirst()) {
+ int urlIndex = c.getColumnIndex(Browser.BookmarkColumns.URL);
+ do {
+ String url = c.getString(urlIndex);
+ mDb.retainIconForPageUrl(url);
+ } while (c.moveToNext());
+ }
+ } catch (IllegalStateException e) {
+ Log.e(LOGTAG, "retainIconsOnStartup", e);
+ } finally {
+ if (c != null) c.close();
+ }
+
+ return null;
+ }
+ }
+
+ private void startHandler() {
+ mHandler = new Handler() {
+
+ @Override
+ public void handleMessage(Message msg) {
+ switch (msg.what) {
+ case OPEN_BOOKMARKS:
+ bookmarksOrHistoryPicker(false);
+ break;
+ case FOCUS_NODE_HREF:
+ {
+ String url = (String) msg.getData().get("url");
+ String title = (String) msg.getData().get("title");
+ String src = (String) msg.getData().get("src");
+ if (url == "") url = src; // use image if no anchor
+ if (TextUtils.isEmpty(url)) {
+ break;
+ }
+ HashMap focusNodeMap = (HashMap) msg.obj;
+ WebView view = (WebView) focusNodeMap.get("webview");
+ // Only apply the action if the top window did not change.
+ if (getCurrentTopWebView() != view) {
+ break;
+ }
+ switch (msg.arg1) {
+ case R.id.open_context_menu_id:
+ loadUrlFromContext(getCurrentTopWebView(), url);
+ break;
+ case R.id.view_image_context_menu_id:
+ loadUrlFromContext(getCurrentTopWebView(), src);
+ break;
+ case R.id.open_newtab_context_menu_id:
+ final Tab parent = mTabControl.getCurrentTab();
+ final Tab newTab = openTab(parent, url, false);
+ if (newTab != null && newTab != parent) {
+ parent.addChildTab(newTab);
+ }
+ break;
+ case R.id.copy_link_context_menu_id:
+ copy(url);
+ break;
+ case R.id.save_link_context_menu_id:
+ case R.id.download_context_menu_id:
+ DownloadHandler.onDownloadStartNoStream(
+ mActivity, url, null, null, null);
+ break;
+ }
+ break;
+ }
+
+ case LOAD_URL:
+ loadUrlFromContext(getCurrentTopWebView(), (String) msg.obj);
+ break;
+
+ case STOP_LOAD:
+ stopLoading();
+ break;
+
+ case RELEASE_WAKELOCK:
+ if (mWakeLock.isHeld()) {
+ mWakeLock.release();
+ // if we reach here, Browser should be still in the
+ // background loading after WAKELOCK_TIMEOUT (5-min).
+ // To avoid burning the battery, stop loading.
+ mTabControl.stopAllLoading();
+ }
+ break;
+
+ case UPDATE_BOOKMARK_THUMBNAIL:
+ WebView view = (WebView) msg.obj;
+ if (view != null) {
+ updateScreenshot(view);
+ }
+ break;
+ }
+ }
+ };
+
+ }
+
+ @Override
+ public void shareCurrentPage() {
+ shareCurrentPage(mTabControl.getCurrentTab());
+ }
+
+ private void shareCurrentPage(Tab tab) {
+ if (tab != null) {
+ sharePage(mActivity, tab.getTitle(),
+ tab.getUrl(), tab.getFavicon(),
+ createScreenshot(tab.getWebView(),
+ getDesiredThumbnailWidth(mActivity),
+ getDesiredThumbnailHeight(mActivity)));
+ }
+ }
+
+ /**
+ * Share a page, providing the title, url, favicon, and a screenshot. Uses
+ * an {@link Intent} to launch the Activity chooser.
+ * @param c Context used to launch a new Activity.
+ * @param title Title of the page. Stored in the Intent with
+ * {@link Intent#EXTRA_SUBJECT}
+ * @param url URL of the page. Stored in the Intent with
+ * {@link Intent#EXTRA_TEXT}
+ * @param favicon Bitmap of the favicon for the page. Stored in the Intent
+ * with {@link Browser#EXTRA_SHARE_FAVICON}
+ * @param screenshot Bitmap of a screenshot of the page. Stored in the
+ * Intent with {@link Browser#EXTRA_SHARE_SCREENSHOT}
+ */
+ static final void sharePage(Context c, String title, String url,
+ Bitmap favicon, Bitmap screenshot) {
+ Intent send = new Intent(Intent.ACTION_SEND);
+ send.setType("text/plain");
+ send.putExtra(Intent.EXTRA_TEXT, url);
+ send.putExtra(Intent.EXTRA_SUBJECT, title);
+ send.putExtra(Browser.EXTRA_SHARE_FAVICON, favicon);
+ send.putExtra(Browser.EXTRA_SHARE_SCREENSHOT, screenshot);
+ try {
+ c.startActivity(Intent.createChooser(send, c.getString(
+ R.string.choosertitle_sharevia)));
+ } catch(android.content.ActivityNotFoundException ex) {
+ // if no app handles it, do nothing
+ }
+ }
+
+ private void copy(CharSequence text) {
+ ClipboardManager cm = (ClipboardManager) mActivity
+ .getSystemService(Context.CLIPBOARD_SERVICE);
+ cm.setText(text);
+ }
+
+ // lifecycle
+
+ protected void onConfgurationChanged(Configuration config) {
+ mConfigChanged = true;
+ if (mPageDialogsHandler != null) {
+ mPageDialogsHandler.onConfigurationChanged(config);
+ }
+ mUi.onConfigurationChanged(config);
+ }
+
+ @Override
+ public void handleNewIntent(Intent intent) {
+ mIntentHandler.onNewIntent(intent);
+ }
+
+ protected void onPause() {
+ if (mUi.isCustomViewShowing()) {
+ hideCustomView();
+ }
+ if (mActivityPaused) {
+ Log.e(LOGTAG, "BrowserActivity is already paused.");
+ return;
+ }
+ mActivityPaused = true;
+ Tab tab = mTabControl.getCurrentTab();
+ if (tab != null) {
+ tab.pause();
+ if (!pauseWebViewTimers(tab)) {
+ mWakeLock.acquire();
+ mHandler.sendMessageDelayed(mHandler
+ .obtainMessage(RELEASE_WAKELOCK), WAKELOCK_TIMEOUT);
+ }
+ }
+ mUi.onPause();
+ mNetworkHandler.onPause();
+
+ WebView.disablePlatformNotifications();
+ }
+
+ void onSaveInstanceState(Bundle outState) {
+ // the default implementation requires each view to have an id. As the
+ // browser handles the state itself and it doesn't use id for the views,
+ // don't call the default implementation. Otherwise it will trigger the
+ // warning like this, "couldn't save which view has focus because the
+ // focused view XXX has no id".
+
+ // Save all the tabs
+ mTabControl.saveState(outState);
+ // Save time so that we know how old incognito tabs (if any) are.
+ outState.putSerializable("lastActiveDate", Calendar.getInstance());
+ }
+
+ void onResume() {
+ if (!mActivityPaused) {
+ Log.e(LOGTAG, "BrowserActivity is already resumed.");
+ return;
+ }
+ mActivityPaused = false;
+ Tab current = mTabControl.getCurrentTab();
+ if (current != null) {
+ current.resume();
+ resumeWebViewTimers(current);
+ }
+ if (mWakeLock.isHeld()) {
+ mHandler.removeMessages(RELEASE_WAKELOCK);
+ mWakeLock.release();
+ }
+ mUi.onResume();
+ mNetworkHandler.onResume();
+ WebView.enablePlatformNotifications();
+ }
+
+ /**
+ * resume all WebView timers using the WebView instance of the given tab
+ * @param tab guaranteed non-null
+ */
+ private void resumeWebViewTimers(Tab tab) {
+ boolean inLoad = tab.inPageLoad();
+ if ((!mActivityPaused && !inLoad) || (mActivityPaused && inLoad)) {
+ CookieSyncManager.getInstance().startSync();
+ WebView w = tab.getWebView();
+ if (w != null) {
+ w.resumeTimers();
+ }
+ }
+ }
+
+ /**
+ * Pause all WebView timers using the WebView of the given tab
+ * @param tab
+ * @return true if the timers are paused or tab is null
+ */
+ private boolean pauseWebViewTimers(Tab tab) {
+ if (tab == null) {
+ return true;
+ } else if (!tab.inPageLoad()) {
+ CookieSyncManager.getInstance().stopSync();
+ WebView w = getCurrentWebView();
+ if (w != null) {
+ w.pauseTimers();
+ }
+ return true;
+ }
+ return false;
+ }
+
+ void onDestroy() {
+ if (mUploadHandler != null) {
+ mUploadHandler.onResult(Activity.RESULT_CANCELED, null);
+ mUploadHandler = null;
+ }
+ if (mTabControl == null) return;
+ mUi.onDestroy();
+ // Remove the current tab and sub window
+ Tab t = mTabControl.getCurrentTab();
+ if (t != null) {
+ dismissSubWindow(t);
+ removeTab(t);
+ }
+ mActivity.getContentResolver().unregisterContentObserver(mBookmarksObserver);
+ // Destroy all the tabs
+ mTabControl.destroy();
+ WebIconDatabase.getInstance().close();
+ // Stop watching the default geolocation permissions
+ mSystemAllowGeolocationOrigins.stop();
+ mSystemAllowGeolocationOrigins = null;
+ }
+
+ protected boolean isActivityPaused() {
+ return mActivityPaused;
+ }
+
+ protected void onLowMemory() {
+ mTabControl.freeMemory();
+ }
+
+ @Override
+ public boolean shouldShowErrorConsole() {
+ return mShouldShowErrorConsole;
+ }
+
+ protected void setShouldShowErrorConsole(boolean show) {
+ if (show == mShouldShowErrorConsole) {
+ // Nothing to do.
+ return;
+ }
+ mShouldShowErrorConsole = show;
+ Tab t = mTabControl.getCurrentTab();
+ if (t == null) {
+ // There is no current tab so we cannot toggle the error console
+ return;
+ }
+ mUi.setShouldShowErrorConsole(t, show);
+ }
+
+ @Override
+ public void stopLoading() {
+ mLoadStopped = true;
+ Tab tab = mTabControl.getCurrentTab();
+ WebView w = getCurrentTopWebView();
+ w.stopLoading();
+ mUi.onPageStopped(tab);
+ }
+
+ boolean didUserStopLoading() {
+ return mLoadStopped;
+ }
+
+ // WebViewController
+
+ @Override
+ public void onPageStarted(Tab tab, WebView view, Bitmap favicon) {
+
+ // We've started to load a new page. If there was a pending message
+ // to save a screenshot then we will now take the new page and save
+ // an incorrect screenshot. Therefore, remove any pending thumbnail
+ // messages from the queue.
+ mHandler.removeMessages(Controller.UPDATE_BOOKMARK_THUMBNAIL,
+ view);
+
+ // reset sync timer to avoid sync starts during loading a page
+ CookieSyncManager.getInstance().resetSync();
+
+ if (!mNetworkHandler.isNetworkUp()) {
+ view.setNetworkAvailable(false);
+ }
+
+ // when BrowserActivity just starts, onPageStarted may be called before
+ // onResume as it is triggered from onCreate. Call resumeWebViewTimers
+ // to start the timer. As we won't switch tabs while an activity is in
+ // pause state, we can ensure calling resume and pause in pair.
+ if (mActivityPaused) {
+ resumeWebViewTimers(tab);
+ }
+ mLoadStopped = false;
+ if (!mNetworkHandler.isNetworkUp()) {
+ mNetworkHandler.createAndShowNetworkDialog();
+ }
+ endActionMode();
+
+ mUi.onTabDataChanged(tab);
+
+ String url = tab.getUrl();
+ // update the bookmark database for favicon
+ maybeUpdateFavicon(tab, null, url, favicon);
+
+ Performance.tracePageStart(url);
+
+ // Performance probe
+ if (false) {
+ Performance.onPageStarted();
+ }
+
+ }
+
+ @Override
+ public void onPageFinished(Tab tab) {
+ mUi.onTabDataChanged(tab);
+ if (!tab.isPrivateBrowsingEnabled()
+ && !TextUtils.isEmpty(tab.getUrl())) {
+ if (tab.inForeground() && !didUserStopLoading()
+ || !tab.inForeground()) {
+ // Only update the bookmark screenshot if the user did not
+ // cancel the load early.
+ mHandler.sendMessageDelayed(mHandler.obtainMessage(
+ UPDATE_BOOKMARK_THUMBNAIL, 0, 0, tab.getWebView()),
+ 500);
+ }
+ }
+ // pause the WebView timer and release the wake lock if it is finished
+ // while BrowserActivity is in pause state.
+ if (mActivityPaused && pauseWebViewTimers(tab)) {
+ if (mWakeLock.isHeld()) {
+ mHandler.removeMessages(RELEASE_WAKELOCK);
+ mWakeLock.release();
+ }
+ }
+ // Performance probe
+ if (false) {
+ Performance.onPageFinished(tab.getUrl());
+ }
+
+ Performance.tracePageFinished();
+ }
+
+ @Override
+ public void onProgressChanged(Tab tab) {
+ int newProgress = tab.getLoadProgress();
+
+ if (newProgress == 100) {
+ CookieSyncManager.getInstance().sync();
+ // onProgressChanged() may continue to be called after the main
+ // frame has finished loading, as any remaining sub frames continue
+ // to load. We'll only get called once though with newProgress as
+ // 100 when everything is loaded. (onPageFinished is called once
+ // when the main frame completes loading regardless of the state of
+ // any sub frames so calls to onProgressChanges may continue after
+ // onPageFinished has executed)
+ if (mInLoad) {
+ mInLoad = false;
+ updateInLoadMenuItems(mCachedMenu);
+ }
+ } else {
+ if (!mInLoad) {
+ // onPageFinished may have already been called but a subframe is
+ // still loading and updating the progress. Reset mInLoad and
+ // update the menu items.
+ mInLoad = true;
+ updateInLoadMenuItems(mCachedMenu);
+ }
+ }
+ mUi.onProgressChanged(tab);
+ }
+
+ @Override
+ public void onUpdatedLockIcon(Tab tab) {
+ mUi.onTabDataChanged(tab);
+ }
+
+ @Override
+ public void onReceivedTitle(Tab tab, final String title) {
+ mUi.onTabDataChanged(tab);
+ final String pageUrl = tab.getUrl();
+ if (TextUtils.isEmpty(pageUrl) || pageUrl.length()
+ >= SQLiteDatabase.SQLITE_MAX_LIKE_PATTERN_LENGTH) {
+ return;
+ }
+ // Update the title in the history database if not in private browsing mode
+ if (!tab.isPrivateBrowsingEnabled()) {
+ mDataController.updateHistoryTitle(pageUrl, title);
+ }
+ }
+
+ @Override
+ public void onFavicon(Tab tab, WebView view, Bitmap icon) {
+ mUi.onTabDataChanged(tab);
+ maybeUpdateFavicon(tab, view.getOriginalUrl(), view.getUrl(), icon);
+ }
+
+ @Override
+ public boolean shouldOverrideUrlLoading(Tab tab, WebView view, String url) {
+ return mUrlHandler.shouldOverrideUrlLoading(tab, view, url);
+ }
+
+ @Override
+ public boolean shouldOverrideKeyEvent(KeyEvent event) {
+ if (mMenuIsDown) {
+ // only check shortcut key when MENU is held
+ return mActivity.getWindow().isShortcutKey(event.getKeyCode(),
+ event);
+ } else {
+ return false;
+ }
+ }
+
+ @Override
+ public void onUnhandledKeyEvent(KeyEvent event) {
+ if (!isActivityPaused()) {
+ if (event.getAction() == KeyEvent.ACTION_DOWN) {
+ mActivity.onKeyDown(event.getKeyCode(), event);
+ } else {
+ mActivity.onKeyUp(event.getKeyCode(), event);
+ }
+ }
+ }
+
+ @Override
+ public void doUpdateVisitedHistory(Tab tab, boolean isReload) {
+ // Don't save anything in private browsing mode
+ if (tab.isPrivateBrowsingEnabled()) return;
+ String url = tab.getUrl();
+
+ if (TextUtils.isEmpty(url)
+ || url.regionMatches(true, 0, "about:", 0, 6)) {
+ return;
+ }
+ mDataController.updateVisitedHistory(url);
+ WebIconDatabase.getInstance().retainIconForPageUrl(url);
+ }
+
+ @Override
+ public void getVisitedHistory(final ValueCallback<String[]> callback) {
+ AsyncTask<Void, Void, String[]> task =
+ new AsyncTask<Void, Void, String[]>() {
+ @Override
+ public String[] doInBackground(Void... unused) {
+ return Browser.getVisitedHistory(mActivity.getContentResolver());
+ }
+ @Override
+ public void onPostExecute(String[] result) {
+ callback.onReceiveValue(result);
+ }
+ };
+ task.execute();
+ }
+
+ @Override
+ public void onReceivedHttpAuthRequest(Tab tab, WebView view,
+ final HttpAuthHandler handler, final String host,
+ final String realm) {
+ String username = null;
+ String password = null;
+
+ boolean reuseHttpAuthUsernamePassword
+ = handler.useHttpAuthUsernamePassword();
+
+ if (reuseHttpAuthUsernamePassword && view != null) {
+ String[] credentials = view.getHttpAuthUsernamePassword(host, realm);
+ if (credentials != null && credentials.length == 2) {
+ username = credentials[0];
+ password = credentials[1];
+ }
+ }
+
+ if (username != null && password != null) {
+ handler.proceed(username, password);
+ } else {
+ if (tab.inForeground()) {
+ mPageDialogsHandler.showHttpAuthentication(tab, handler, host, realm);
+ } else {
+ handler.cancel();
+ }
+ }
+ }
+
+ @Override
+ public void onDownloadStart(Tab tab, String url, String userAgent,
+ String contentDisposition, String mimetype, long contentLength) {
+ DownloadHandler.onDownloadStart(mActivity, url, userAgent,
+ contentDisposition, mimetype);
+ if (tab.getWebView().copyBackForwardList().getSize() == 0) {
+ // This Tab was opened for the sole purpose of downloading a
+ // file. Remove it.
+ if (tab == mTabControl.getCurrentTab()) {
+ // In this case, the Tab is still on top.
+ goBackOnePageOrQuit();
+ } else {
+ // In this case, it is not.
+ closeTab(tab);
+ }
+ }
+ }
+
+ @Override
+ public Bitmap getDefaultVideoPoster() {
+ return mUi.getDefaultVideoPoster();
+ }
+
+ @Override
+ public View getVideoLoadingProgressView() {
+ return mUi.getVideoLoadingProgressView();
+ }
+
+ @Override
+ public void showSslCertificateOnError(WebView view, SslErrorHandler handler,
+ SslError error) {
+ mPageDialogsHandler.showSSLCertificateOnError(view, handler, error);
+ }
+
+ // helper method
+
+ /*
+ * Update the favorites icon if the private browsing isn't enabled and the
+ * icon is valid.
+ */
+ private void maybeUpdateFavicon(Tab tab, final String originalUrl,
+ final String url, Bitmap favicon) {
+ if (favicon == null) {
+ return;
+ }
+ if (!tab.isPrivateBrowsingEnabled()) {
+ Bookmarks.updateFavicon(mActivity
+ .getContentResolver(), originalUrl, url, favicon);
+ }
+ }
+
+ @Override
+ public void bookmarkedStatusHasChanged(Tab tab) {
+ // TODO: Switch to using onTabDataChanged after b/3262950 is fixed
+ mUi.bookmarkedStatusHasChanged(tab);
+ }
+
+ // end WebViewController
+
+ protected void pageUp() {
+ getCurrentTopWebView().pageUp(false);
+ }
+
+ protected void pageDown() {
+ getCurrentTopWebView().pageDown(false);
+ }
+
+ // callback from phone title bar
+ public void editUrl() {
+ if (mOptionsMenuOpen) mActivity.closeOptionsMenu();
+ String url = (getCurrentTopWebView() == null) ? null : getCurrentTopWebView().getUrl();
+ startSearch(mSettings.getHomePage().equals(url) ? null : url, true,
+ null, false);
+ }
+
+ public void startVoiceSearch() {
+ Intent intent = new Intent(RecognizerIntent.ACTION_WEB_SEARCH);
+ intent.putExtra(RecognizerIntent.EXTRA_LANGUAGE_MODEL,
+ RecognizerIntent.LANGUAGE_MODEL_WEB_SEARCH);
+ intent.putExtra(RecognizerIntent.EXTRA_CALLING_PACKAGE,
+ mActivity.getComponentName().flattenToString());
+ intent.putExtra(SEND_APP_ID_EXTRA, false);
+ intent.putExtra(RecognizerIntent.EXTRA_WEB_SEARCH_ONLY, true);
+ mActivity.startActivity(intent);
+ }
+
+ public void activateVoiceSearchMode(String title) {
+ mUi.showVoiceTitleBar(title);
+ }
+
+ public void revertVoiceSearchMode(Tab tab) {
+ mUi.revertVoiceTitleBar(tab);
+ }
+
+ public void showCustomView(Tab tab, View view,
+ WebChromeClient.CustomViewCallback callback) {
+ if (tab.inForeground()) {
+ if (mUi.isCustomViewShowing()) {
+ callback.onCustomViewHidden();
+ return;
+ }
+ mUi.showCustomView(view, callback);
+ // Save the menu state and set it to empty while the custom
+ // view is showing.
+ mOldMenuState = mMenuState;
+ mMenuState = EMPTY_MENU;
+ mActivity.invalidateOptionsMenu();
+ }
+ }
+
+ @Override
+ public void hideCustomView() {
+ if (mUi.isCustomViewShowing()) {
+ mUi.onHideCustomView();
+ // Reset the old menu state.
+ mMenuState = mOldMenuState;
+ mOldMenuState = EMPTY_MENU;
+ mActivity.invalidateOptionsMenu();
+ }
+ }
+
+ protected void onActivityResult(int requestCode, int resultCode,
+ Intent intent) {
+ if (getCurrentTopWebView() == null) return;
+ switch (requestCode) {
+ case PREFERENCES_PAGE:
+ if (resultCode == Activity.RESULT_OK && intent != null) {
+ String action = intent.getStringExtra(Intent.EXTRA_TEXT);
+ if (BrowserSettings.PREF_CLEAR_HISTORY.equals(action)) {
+ mTabControl.removeParentChildRelationShips();
+ }
+ }
+ break;
+ case FILE_SELECTED:
+ // Choose a file from the file picker.
+ if (null == mUploadHandler) break;
+ mUploadHandler.onResult(resultCode, intent);
+ mUploadHandler = null;
+ break;
+ case AUTOFILL_SETUP:
+ // Determine whether a profile was actually set up or not
+ // and if so, send the message back to the WebTextView to
+ // fill the form with the new profile.
+ if (getSettings().getAutoFillProfile() != null) {
+ mAutoFillSetupMessage.sendToTarget();
+ mAutoFillSetupMessage = null;
+ }
+ break;
+ default:
+ break;
+ }
+ getCurrentTopWebView().requestFocus();
+ }
+
+ /**
+ * Open the Go page.
+ * @param startWithHistory If true, open starting on the history tab.
+ * Otherwise, start with the bookmarks tab.
+ */
+ @Override
+ public void bookmarksOrHistoryPicker(boolean startWithHistory) {
+ if (mTabControl.getCurrentWebView() == null) {
+ return;
+ }
+ // clear action mode
+ if (isInCustomActionMode()) {
+ endActionMode();
+ }
+ Bundle extras = new Bundle();
+ // Disable opening in a new window if we have maxed out the windows
+ extras.putBoolean(BrowserBookmarksPage.EXTRA_DISABLE_WINDOW,
+ !mTabControl.canCreateNewTab());
+ mUi.showComboView(startWithHistory, extras);
+ }
+
+ // combo view callbacks
+
+ /**
+ * callback from ComboPage when clear history is requested
+ */
+ public void onRemoveParentChildRelationships() {
+ mTabControl.removeParentChildRelationShips();
+ }
+
+ /**
+ * callback from ComboPage when bookmark/history selection
+ */
+ @Override
+ public void onUrlSelected(String url, boolean newTab) {
+ removeComboView();
+ if (!TextUtils.isEmpty(url)) {
+ if (newTab) {
+ openTab(mTabControl.getCurrentTab(), url, false);
+ } else {
+ final Tab currentTab = mTabControl.getCurrentTab();
+ dismissSubWindow(currentTab);
+ loadUrl(getCurrentTopWebView(), url);
+ }
+ }
+ }
+
+ /**
+ * dismiss the ComboPage
+ */
+ @Override
+ public void removeComboView() {
+ mUi.hideComboView();
+ }
+
+ // active tabs page handling
+
+ protected void showActiveTabsPage() {
+ mMenuState = EMPTY_MENU;
+ mUi.showActiveTabsPage();
+ }
+
+ /**
+ * Remove the active tabs page.
+ * @param needToAttach If true, the active tabs page did not attach a tab
+ * to the content view, so we need to do that here.
+ */
+ @Override
+ public void removeActiveTabsPage(boolean needToAttach) {
+ mMenuState = R.id.MAIN_MENU;
+ mUi.removeActiveTabsPage();
+ if (needToAttach) {
+ setActiveTab(mTabControl.getCurrentTab());
+ }
+ getCurrentTopWebView().requestFocus();
+ }
+
+ // key handling
+ protected void onBackKey() {
+ if (!mUi.onBackKey()) {
+ WebView subwindow = mTabControl.getCurrentSubWindow();
+ if (subwindow != null) {
+ if (subwindow.canGoBack()) {
+ subwindow.goBack();
+ } else {
+ dismissSubWindow(mTabControl.getCurrentTab());
+ }
+ } else {
+ goBackOnePageOrQuit();
+ }
+ }
+ }
+
+ // menu handling and state
+ // TODO: maybe put into separate handler
+
+ protected boolean onCreateOptionsMenu(Menu menu) {
+ if (mOptionsMenuHandler != null) {
+ return mOptionsMenuHandler.onCreateOptionsMenu(menu);
+ }
+
+ if (mMenuState == EMPTY_MENU) {
+ return false;
+ }
+ MenuInflater inflater = mActivity.getMenuInflater();
+ inflater.inflate(R.menu.browser, menu);
+ updateInLoadMenuItems(menu);
+ // hold on to the menu reference here; it is used by the page callbacks
+ // to update the menu based on loading state
+ mCachedMenu = menu;
+ return true;
+ }
+
+ protected void onCreateContextMenu(ContextMenu menu, View v,
+ ContextMenuInfo menuInfo) {
+ if (v instanceof TitleBarBase) {
+ return;
+ }
+ if (!(v instanceof WebView)) {
+ return;
+ }
+ final WebView webview = (WebView) v;
+ WebView.HitTestResult result = webview.getHitTestResult();
+ if (result == null) {
+ return;
+ }
+
+ int type = result.getType();
+ if (type == WebView.HitTestResult.UNKNOWN_TYPE) {
+ Log.w(LOGTAG,
+ "We should not show context menu when nothing is touched");
+ return;
+ }
+ if (type == WebView.HitTestResult.EDIT_TEXT_TYPE) {
+ // let TextView handles context menu
+ return;
+ }
+
+ // Note, http://b/issue?id=1106666 is requesting that
+ // an inflated menu can be used again. This is not available
+ // yet, so inflate each time (yuk!)
+ MenuInflater inflater = mActivity.getMenuInflater();
+ inflater.inflate(R.menu.browsercontext, menu);
+
+ // Show the correct menu group
+ final String extra = result.getExtra();
+ menu.setGroupVisible(R.id.PHONE_MENU,
+ type == WebView.HitTestResult.PHONE_TYPE);
+ menu.setGroupVisible(R.id.EMAIL_MENU,
+ type == WebView.HitTestResult.EMAIL_TYPE);
+ menu.setGroupVisible(R.id.GEO_MENU,
+ type == WebView.HitTestResult.GEO_TYPE);
+ menu.setGroupVisible(R.id.IMAGE_MENU,
+ type == WebView.HitTestResult.IMAGE_TYPE
+ || type == WebView.HitTestResult.SRC_IMAGE_ANCHOR_TYPE);
+ menu.setGroupVisible(R.id.ANCHOR_MENU,
+ type == WebView.HitTestResult.SRC_ANCHOR_TYPE
+ || type == WebView.HitTestResult.SRC_IMAGE_ANCHOR_TYPE);
+ boolean hitText = type == WebView.HitTestResult.SRC_ANCHOR_TYPE
+ || type == WebView.HitTestResult.PHONE_TYPE
+ || type == WebView.HitTestResult.EMAIL_TYPE
+ || type == WebView.HitTestResult.GEO_TYPE;
+ menu.setGroupVisible(R.id.SELECT_TEXT_MENU, hitText);
+ if (hitText) {
+ menu.findItem(R.id.select_text_menu_id)
+ .setOnMenuItemClickListener(new SelectText(webview));
+ }
+ // Setup custom handling depending on the type
+ switch (type) {
+ case WebView.HitTestResult.PHONE_TYPE:
+ menu.setHeaderTitle(Uri.decode(extra));
+ menu.findItem(R.id.dial_context_menu_id).setIntent(
+ new Intent(Intent.ACTION_VIEW, Uri
+ .parse(WebView.SCHEME_TEL + extra)));
+ Intent addIntent = new Intent(Intent.ACTION_INSERT_OR_EDIT);
+ addIntent.putExtra(Insert.PHONE, Uri.decode(extra));
+ addIntent.setType(ContactsContract.Contacts.CONTENT_ITEM_TYPE);
+ menu.findItem(R.id.add_contact_context_menu_id).setIntent(
+ addIntent);
+ menu.findItem(R.id.copy_phone_context_menu_id)
+ .setOnMenuItemClickListener(
+ new Copy(extra));
+ break;
+
+ case WebView.HitTestResult.EMAIL_TYPE:
+ menu.setHeaderTitle(extra);
+ menu.findItem(R.id.email_context_menu_id).setIntent(
+ new Intent(Intent.ACTION_VIEW, Uri
+ .parse(WebView.SCHEME_MAILTO + extra)));
+ menu.findItem(R.id.copy_mail_context_menu_id)
+ .setOnMenuItemClickListener(
+ new Copy(extra));
+ break;
+
+ case WebView.HitTestResult.GEO_TYPE:
+ menu.setHeaderTitle(extra);
+ menu.findItem(R.id.map_context_menu_id).setIntent(
+ new Intent(Intent.ACTION_VIEW, Uri
+ .parse(WebView.SCHEME_GEO
+ + URLEncoder.encode(extra))));
+ menu.findItem(R.id.copy_geo_context_menu_id)
+ .setOnMenuItemClickListener(
+ new Copy(extra));
+ break;
+
+ case WebView.HitTestResult.SRC_ANCHOR_TYPE:
+ case WebView.HitTestResult.SRC_IMAGE_ANCHOR_TYPE:
+ menu.setHeaderTitle(extra);
+ // decide whether to show the open link in new tab option
+ boolean showNewTab = mTabControl.canCreateNewTab();
+ MenuItem newTabItem
+ = menu.findItem(R.id.open_newtab_context_menu_id);
+ newTabItem.setTitle(
+ BrowserSettings.getInstance().openInBackground()
+ ? R.string.contextmenu_openlink_newwindow_background
+ : R.string.contextmenu_openlink_newwindow);
+ newTabItem.setVisible(showNewTab);
+ if (showNewTab) {
+ if (WebView.HitTestResult.SRC_IMAGE_ANCHOR_TYPE == type) {
+ newTabItem.setOnMenuItemClickListener(
+ new MenuItem.OnMenuItemClickListener() {
+ @Override
+ public boolean onMenuItemClick(MenuItem item) {
+ final HashMap<String, WebView> hrefMap =
+ new HashMap<String, WebView>();
+ hrefMap.put("webview", webview);
+ final Message msg = mHandler.obtainMessage(
+ FOCUS_NODE_HREF,
+ R.id.open_newtab_context_menu_id,
+ 0, hrefMap);
+ webview.requestFocusNodeHref(msg);
+ return true;
+ }
+ });
+ } else {
+ newTabItem.setOnMenuItemClickListener(
+ new MenuItem.OnMenuItemClickListener() {
+ @Override
+ public boolean onMenuItemClick(MenuItem item) {
+ final Tab parent = mTabControl.getCurrentTab();
+ final Tab newTab = openTab(parent,
+ extra, false);
+ if (newTab != parent) {
+ parent.addChildTab(newTab);
+ }
+ return true;
+ }
+ });
+ }
+ }
+ if (type == WebView.HitTestResult.SRC_ANCHOR_TYPE) {
+ break;
+ }
+ // otherwise fall through to handle image part
+ case WebView.HitTestResult.IMAGE_TYPE:
+ if (type == WebView.HitTestResult.IMAGE_TYPE) {
+ menu.setHeaderTitle(extra);
+ }
+ menu.findItem(R.id.view_image_context_menu_id).setIntent(
+ new Intent(Intent.ACTION_VIEW, Uri.parse(extra)));
+ menu.findItem(R.id.download_context_menu_id).
+ setOnMenuItemClickListener(new Download(mActivity, extra));
+ menu.findItem(R.id.set_wallpaper_context_menu_id).
+ setOnMenuItemClickListener(new WallpaperHandler(mActivity,
+ extra));
+ break;
+
+ default:
+ Log.w(LOGTAG, "We should not get here.");
+ break;
+ }
+ //update the ui
+ mUi.onContextMenuCreated(menu);
+ }
+
+ /**
+ * As the menu can be open when loading state changes
+ * we must manually update the state of the stop/reload menu
+ * item
+ */
+ private void updateInLoadMenuItems(Menu menu) {
+ if (menu == null) {
+ return;
+ }
+ MenuItem dest = menu.findItem(R.id.stop_reload_menu_id);
+ MenuItem src = mInLoad ?
+ menu.findItem(R.id.stop_menu_id):
+ menu.findItem(R.id.reload_menu_id);
+ if (src != null) {
+ dest.setIcon(src.getIcon());
+ dest.setTitle(src.getTitle());
+ }
+ }
+
+ boolean onPrepareOptionsMenu(Menu menu) {
+ if (mOptionsMenuHandler != null) {
+ return mOptionsMenuHandler.onPrepareOptionsMenu(menu);
+ }
+ // This happens when the user begins to hold down the menu key, so
+ // allow them to chord to get a shortcut.
+ mCanChord = true;
+ // Note: setVisible will decide whether an item is visible; while
+ // setEnabled() will decide whether an item is enabled, which also means
+ // whether the matching shortcut key will function.
+ switch (mMenuState) {
+ case EMPTY_MENU:
+ if (mCurrentMenuState != mMenuState) {
+ menu.setGroupVisible(R.id.MAIN_MENU, false);
+ menu.setGroupEnabled(R.id.MAIN_MENU, false);
+ menu.setGroupEnabled(R.id.MAIN_SHORTCUT_MENU, false);
+ }
+ break;
+ default:
+ if (mCurrentMenuState != mMenuState) {
+ menu.setGroupVisible(R.id.MAIN_MENU, true);
+ menu.setGroupEnabled(R.id.MAIN_MENU, true);
+ menu.setGroupEnabled(R.id.MAIN_SHORTCUT_MENU, true);
+ }
+ final WebView w = getCurrentTopWebView();
+ boolean canGoBack = false;
+ boolean canGoForward = false;
+ boolean isHome = false;
+ if (w != null) {
+ canGoBack = w.canGoBack();
+ canGoForward = w.canGoForward();
+ isHome = mSettings.getHomePage().equals(w.getUrl());
+ }
+ final MenuItem back = menu.findItem(R.id.back_menu_id);
+ back.setEnabled(canGoBack);
+
+ final MenuItem home = menu.findItem(R.id.homepage_menu_id);
+ home.setEnabled(!isHome);
+
+ final MenuItem forward = menu.findItem(R.id.forward_menu_id);
+ forward.setEnabled(canGoForward);
+
+ // decide whether to show the share link option
+ PackageManager pm = mActivity.getPackageManager();
+ Intent send = new Intent(Intent.ACTION_SEND);
+ send.setType("text/plain");
+ ResolveInfo ri = pm.resolveActivity(send,
+ PackageManager.MATCH_DEFAULT_ONLY);
+ menu.findItem(R.id.share_page_menu_id).setVisible(ri != null);
+
+ boolean isNavDump = mSettings.isNavDump();
+ final MenuItem nav = menu.findItem(R.id.dump_nav_menu_id);
+ nav.setVisible(isNavDump);
+ nav.setEnabled(isNavDump);
+
+ boolean showDebugSettings = mSettings.showDebugSettings();
+ final MenuItem counter = menu.findItem(R.id.dump_counters_menu_id);
+ counter.setVisible(showDebugSettings);
+ counter.setEnabled(showDebugSettings);
+
+ final MenuItem newtab = menu.findItem(R.id.new_tab_menu_id);
+ newtab.setEnabled(getTabControl().canCreateNewTab());
+
+ break;
+ }
+ mCurrentMenuState = mMenuState;
+ return true;
+ }
+
+ public boolean onOptionsItemSelected(MenuItem item) {
+ if (mOptionsMenuHandler != null &&
+ mOptionsMenuHandler.onOptionsItemSelected(item)) {
+ return true;
+ }
+
+ if (item.getGroupId() != R.id.CONTEXT_MENU) {
+ // menu remains active, so ensure comboview is dismissed
+ // if main menu option is selected
+ removeComboView();
+ }
+ if (!mCanChord) {
+ // The user has already fired a shortcut with this hold down of the
+ // menu key.
+ return false;
+ }
+ if (null == getCurrentTopWebView()) {
+ return false;
+ }
+ if (mMenuIsDown) {
+ // The shortcut action consumes the MENU. Even if it is still down,
+ // it won't trigger the next shortcut action. In the case of the
+ // shortcut action triggering a new activity, like Bookmarks, we
+ // won't get onKeyUp for MENU. So it is important to reset it here.
+ mMenuIsDown = false;
+ }
+ switch (item.getItemId()) {
+ // -- Main menu
+ case R.id.new_tab_menu_id:
+ openTabToHomePage();
+ break;
+
+ case R.id.incognito_menu_id:
+ openIncognitoTab();
+ break;
+
+ case R.id.goto_menu_id:
+ editUrl();
+ break;
+
+ case R.id.bookmarks_menu_id:
+ bookmarksOrHistoryPicker(false);
+ break;
+
+ case R.id.active_tabs_menu_id:
+ showActiveTabsPage();
+ break;
+
+ case R.id.add_bookmark_menu_id:
+ bookmarkCurrentPage(AddBookmarkPage.DEFAULT_FOLDER_ID);
+ break;
+
+ case R.id.stop_reload_menu_id:
+ if (mInLoad) {
+ stopLoading();
+ } else {
+ getCurrentTopWebView().reload();
+ }
+ break;
+
+ case R.id.back_menu_id:
+ getCurrentTopWebView().goBack();
+ break;
+
+ case R.id.forward_menu_id:
+ getCurrentTopWebView().goForward();
+ break;
+
+ case R.id.close_menu_id:
+ // Close the subwindow if it exists.
+ if (mTabControl.getCurrentSubWindow() != null) {
+ dismissSubWindow(mTabControl.getCurrentTab());
+ break;
+ }
+ closeCurrentTab();
+ break;
+
+ case R.id.homepage_menu_id:
+ Tab current = mTabControl.getCurrentTab();
+ if (current != null) {
+ dismissSubWindow(current);
+ loadUrl(current.getWebView(), mSettings.getHomePage());
+ }
+ break;
+
+ case R.id.preferences_menu_id:
+ Intent intent = new Intent(mActivity, BrowserPreferencesPage.class);
+ intent.putExtra(BrowserPreferencesPage.CURRENT_PAGE,
+ getCurrentTopWebView().getUrl());
+ mActivity.startActivityForResult(intent, PREFERENCES_PAGE);
+ break;
+
+ case R.id.find_menu_id:
+ getCurrentTopWebView().showFindDialog(null, true);
+ break;
+
+ case R.id.page_info_menu_id:
+ mPageDialogsHandler.showPageInfo(mTabControl.getCurrentTab(),
+ false);
+ break;
+
+ case R.id.classic_history_menu_id:
+ bookmarksOrHistoryPicker(true);
+ break;
+
+ case R.id.title_bar_share_page_url:
+ case R.id.share_page_menu_id:
+ Tab currentTab = mTabControl.getCurrentTab();
+ if (null == currentTab) {
+ mCanChord = false;
+ return false;
+ }
+ shareCurrentPage(currentTab);
+ break;
+
+ case R.id.dump_nav_menu_id:
+ getCurrentTopWebView().debugDump();
+ break;
+
+ case R.id.dump_counters_menu_id:
+ getCurrentTopWebView().dumpV8Counters();
+ break;
+
+ case R.id.zoom_in_menu_id:
+ getCurrentTopWebView().zoomIn();
+ break;
+
+ case R.id.zoom_out_menu_id:
+ getCurrentTopWebView().zoomOut();
+ break;
+
+ case R.id.view_downloads_menu_id:
+ viewDownloads();
+ break;
+
+ case R.id.window_one_menu_id:
+ case R.id.window_two_menu_id:
+ case R.id.window_three_menu_id:
+ case R.id.window_four_menu_id:
+ case R.id.window_five_menu_id:
+ case R.id.window_six_menu_id:
+ case R.id.window_seven_menu_id:
+ case R.id.window_eight_menu_id:
+ {
+ int menuid = item.getItemId();
+ for (int id = 0; id < WINDOW_SHORTCUT_ID_ARRAY.length; id++) {
+ if (WINDOW_SHORTCUT_ID_ARRAY[id] == menuid) {
+ Tab desiredTab = mTabControl.getTab(id);
+ if (desiredTab != null &&
+ desiredTab != mTabControl.getCurrentTab()) {
+ switchToTab(id);
+ }
+ break;
+ }
+ }
+ }
+ break;
+
+ default:
+ return false;
+ }
+ mCanChord = false;
+ return true;
+ }
+
+ public boolean onContextItemSelected(MenuItem item) {
+ // Let the History and Bookmark fragments handle menus they created.
+ if (item.getGroupId() == R.id.CONTEXT_MENU) {
+ return false;
+ }
+
+ // chording is not an issue with context menus, but we use the same
+ // options selector, so set mCanChord to true so we can access them.
+ mCanChord = true;
+ int id = item.getItemId();
+ boolean result = true;
+ switch (id) {
+ // For the context menu from the title bar
+ case R.id.title_bar_copy_page_url:
+ Tab currentTab = mTabControl.getCurrentTab();
+ if (null == currentTab) {
+ result = false;
+ break;
+ }
+ WebView mainView = currentTab.getWebView();
+ if (null == mainView) {
+ result = false;
+ break;
+ }
+ copy(mainView.getUrl());
+ break;
+ // -- Browser context menu
+ case R.id.open_context_menu_id:
+ case R.id.save_link_context_menu_id:
+ case R.id.copy_link_context_menu_id:
+ final WebView webView = getCurrentTopWebView();
+ if (null == webView) {
+ result = false;
+ break;
+ }
+ final HashMap<String, WebView> hrefMap =
+ new HashMap<String, WebView>();
+ hrefMap.put("webview", webView);
+ final Message msg = mHandler.obtainMessage(
+ FOCUS_NODE_HREF, id, 0, hrefMap);
+ webView.requestFocusNodeHref(msg);
+ break;
+
+ default:
+ // For other context menus
+ result = onOptionsItemSelected(item);
+ }
+ mCanChord = false;
+ return result;
+ }
+
+ /**
+ * support programmatically opening the context menu
+ */
+ public void openContextMenu(View view) {
+ mActivity.openContextMenu(view);
+ }
+
+ /**
+ * programmatically open the options menu
+ */
+ public void openOptionsMenu() {
+ mActivity.openOptionsMenu();
+ }
+
+ public boolean onMenuOpened(int featureId, Menu menu) {
+ if (mOptionsMenuOpen) {
+ if (mConfigChanged) {
+ // We do not need to make any changes to the state of the
+ // title bar, since the only thing that happened was a
+ // change in orientation
+ mConfigChanged = false;
+ } else {
+ if (!mExtendedMenuOpen) {
+ mExtendedMenuOpen = true;
+ mUi.onExtendedMenuOpened();
+ } else {
+ // Switching the menu back to icon view, so show the
+ // title bar once again.
+ mExtendedMenuOpen = false;
+ mUi.onExtendedMenuClosed(mInLoad);
+ mUi.onOptionsMenuOpened();
+ }
+ }
+ } else {
+ // The options menu is closed, so open it, and show the title
+ mOptionsMenuOpen = true;
+ mConfigChanged = false;
+ mExtendedMenuOpen = false;
+ mUi.onOptionsMenuOpened();
+ }
+ return true;
+ }
+
+ public void onOptionsMenuClosed(Menu menu) {
+ mOptionsMenuOpen = false;
+ mUi.onOptionsMenuClosed(mInLoad);
+ }
+
+ public void onContextMenuClosed(Menu menu) {
+ mUi.onContextMenuClosed(menu, mInLoad);
+ }
+
+ // Helper method for getting the top window.
+ @Override
+ public WebView getCurrentTopWebView() {
+ return mTabControl.getCurrentTopWebView();
+ }
+
+ @Override
+ public WebView getCurrentWebView() {
+ return mTabControl.getCurrentWebView();
+ }
+
+ /*
+ * This method is called as a result of the user selecting the options
+ * menu to see the download window. It shows the download window on top of
+ * the current window.
+ */
+ void viewDownloads() {
+ Intent intent = new Intent(DownloadManager.ACTION_VIEW_DOWNLOADS);
+ mActivity.startActivity(intent);
+ }
+
+ // action mode
+
+ void onActionModeStarted(ActionMode mode) {
+ mUi.onActionModeStarted(mode);
+ mActionMode = mode;
+ }
+
+ /*
+ * True if a custom ActionMode (i.e. find or select) is in use.
+ */
+ @Override
+ public boolean isInCustomActionMode() {
+ return mActionMode != null;
+ }
+
+ /*
+ * End the current ActionMode.
+ */
+ @Override
+ public void endActionMode() {
+ if (mActionMode != null) {
+ mActionMode.finish();
+ }
+ }
+
+ /*
+ * Called by find and select when they are finished. Replace title bars
+ * as necessary.
+ */
+ public void onActionModeFinished(ActionMode mode) {
+ if (!isInCustomActionMode()) return;
+ mUi.onActionModeFinished(mInLoad);
+ mActionMode = null;
+ }
+
+ boolean isInLoad() {
+ return mInLoad;
+ }
+
+ // bookmark handling
+
+ /**
+ * add the current page as a bookmark to the given folder id
+ * @param folderId use -1 for the default folder
+ */
+ @Override
+ public void bookmarkCurrentPage(long folderId) {
+ Intent i = new Intent(mActivity,
+ AddBookmarkPage.class);
+ WebView w = getCurrentTopWebView();
+ i.putExtra(BrowserContract.Bookmarks.URL, w.getUrl());
+ i.putExtra(BrowserContract.Bookmarks.TITLE, w.getTitle());
+ String touchIconUrl = w.getTouchIconUrl();
+ if (touchIconUrl != null) {
+ i.putExtra(AddBookmarkPage.TOUCH_ICON_URL, touchIconUrl);
+ WebSettings settings = w.getSettings();
+ if (settings != null) {
+ i.putExtra(AddBookmarkPage.USER_AGENT,
+ settings.getUserAgentString());
+ }
+ }
+ i.putExtra(BrowserContract.Bookmarks.THUMBNAIL,
+ createScreenshot(w, getDesiredThumbnailWidth(mActivity),
+ getDesiredThumbnailHeight(mActivity)));
+ i.putExtra(BrowserContract.Bookmarks.FAVICON, w.getFavicon());
+ i.putExtra(BrowserContract.Bookmarks.PARENT,
+ folderId);
+ // Put the dialog at the upper right of the screen, covering the
+ // star on the title bar.
+ i.putExtra("gravity", Gravity.RIGHT | Gravity.TOP);
+ mActivity.startActivity(i);
+ }
+
+ // file chooser
+ public void openFileChooser(ValueCallback<Uri> uploadMsg, String acceptType) {
+ mUploadHandler = new UploadHandler(this);
+ mUploadHandler.openFileChooser(uploadMsg, acceptType);
+ }
+
+ // thumbnails
+
+ /**
+ * Return the desired width for thumbnail screenshots, which are stored in
+ * the database, and used on the bookmarks screen.
+ * @param context Context for finding out the density of the screen.
+ * @return desired width for thumbnail screenshot.
+ */
+ static int getDesiredThumbnailWidth(Context context) {
+ return context.getResources().getDimensionPixelOffset(
+ R.dimen.bookmarkThumbnailWidth);
+ }
+
+ /**
+ * Return the desired height for thumbnail screenshots, which are stored in
+ * the database, and used on the bookmarks screen.
+ * @param context Context for finding out the density of the screen.
+ * @return desired height for thumbnail screenshot.
+ */
+ static int getDesiredThumbnailHeight(Context context) {
+ return context.getResources().getDimensionPixelOffset(
+ R.dimen.bookmarkThumbnailHeight);
+ }
+
+ private static Bitmap createScreenshot(WebView view, int width, int height) {
+ // We render to a bitmap 2x the desired size so that we can then
+ // re-scale it with filtering since canvas.scale doesn't filter
+ // This helps reduce aliasing at the cost of being slightly blurry
+ final int filter_scale = 2;
+ Picture thumbnail = view.capturePicture();
+ if (thumbnail == null) {
+ return null;
+ }
+ width *= filter_scale;
+ height *= filter_scale;
+ Bitmap bm = Bitmap.createBitmap(width, height, Bitmap.Config.RGB_565);
+ Canvas canvas = new Canvas(bm);
+ // May need to tweak these values to determine what is the
+ // best scale factor
+ int thumbnailWidth = thumbnail.getWidth();
+ int thumbnailHeight = thumbnail.getHeight();
+ float scaleFactor = 1.0f;
+ if (thumbnailWidth > 0) {
+ scaleFactor = (float) width / (float)thumbnailWidth;
+ } else {
+ return null;
+ }
+
+ if (view.getWidth() > view.getHeight() &&
+ thumbnailHeight < view.getHeight() && thumbnailHeight > 0) {
+ // If the device is in landscape and the page is shorter
+ // than the height of the view, center the thumnail and crop the sides
+ scaleFactor = (float) height / (float)thumbnailHeight;
+ float wx = (thumbnailWidth * scaleFactor) - width;
+ canvas.translate((int) -(wx / 2), 0);
+ }
+
+ canvas.scale(scaleFactor, scaleFactor);
+
+ thumbnail.draw(canvas);
+ Bitmap ret = Bitmap.createScaledBitmap(bm, width / filter_scale,
+ height / filter_scale, true);
+ bm.recycle();
+ return ret;
+ }
+
+ private void updateScreenshot(WebView view) {
+ // If this is a bookmarked site, add a screenshot to the database.
+ // FIXME: When should we update? Every time?
+ // FIXME: Would like to make sure there is actually something to
+ // draw, but the API for that (WebViewCore.pictureReady()) is not
+ // currently accessible here.
+
+ final Bitmap bm = createScreenshot(view, getDesiredThumbnailWidth(mActivity),
+ getDesiredThumbnailHeight(mActivity));
+ if (bm == null) {
+ return;
+ }
+
+ final ContentResolver cr = mActivity.getContentResolver();
+ final String url = view.getUrl();
+ final String originalUrl = view.getOriginalUrl();
+
+ // Only update thumbnails for web urls (http(s)://), not for
+ // about:, javascript:, data:, etc...
+ if (url != null && Patterns.WEB_URL.matcher(url).matches()) {
+ new AsyncTask<Void, Void, Void>() {
+ @Override
+ protected Void doInBackground(Void... unused) {
+ Cursor cursor = null;
+ try {
+ // TODO: Clean this up
+ cursor = Bookmarks.queryCombinedForUrl(cr, originalUrl, url);
+ if (cursor != null && cursor.moveToFirst()) {
+ final ByteArrayOutputStream os =
+ new ByteArrayOutputStream();
+ bm.compress(Bitmap.CompressFormat.PNG, 100, os);
+
+ ContentValues values = new ContentValues();
+ values.put(Images.THUMBNAIL, os.toByteArray());
+ values.put(Images.URL, cursor.getString(0));
+
+ do {
+ cr.update(Images.CONTENT_URI, values, null, null);
+ } while (cursor.moveToNext());
+ }
+ } catch (IllegalStateException e) {
+ // Ignore
+ } finally {
+ if (cursor != null) cursor.close();
+ }
+ return null;
+ }
+ }.execute();
+ }
+ }
+
+ private class Copy implements OnMenuItemClickListener {
+ private CharSequence mText;
+
+ public boolean onMenuItemClick(MenuItem item) {
+ copy(mText);
+ return true;
+ }
+
+ public Copy(CharSequence toCopy) {
+ mText = toCopy;
+ }
+ }
+
+ private static class Download implements OnMenuItemClickListener {
+ private Activity mActivity;
+ private String mText;
+
+ public boolean onMenuItemClick(MenuItem item) {
+ DownloadHandler.onDownloadStartNoStream(mActivity, mText, null,
+ null, null);
+ return true;
+ }
+
+ public Download(Activity activity, String toDownload) {
+ mActivity = activity;
+ mText = toDownload;
+ }
+ }
+
+ private static class SelectText implements OnMenuItemClickListener {
+ private WebView mWebView;
+
+ public boolean onMenuItemClick(MenuItem item) {
+ if (mWebView != null) {
+ return mWebView.selectText();
+ }
+ return false;
+ }
+
+ public SelectText(WebView webView) {
+ mWebView = webView;
+ }
+
+ }
+
+ /********************** TODO: UI stuff *****************************/
+
+ // these methods have been copied, they still need to be cleaned up
+
+ /****************** tabs ***************************************************/
+
+ // basic tab interactions:
+
+ // it is assumed that tabcontrol already knows about the tab
+ protected void addTab(Tab tab) {
+ mUi.addTab(tab);
+ }
+
+ protected void removeTab(Tab tab) {
+ mUi.removeTab(tab);
+ mTabControl.removeTab(tab);
+ }
+
+ protected void setActiveTab(Tab tab) {
+ mTabControl.setCurrentTab(tab);
+ // the tab is guaranteed to have a webview after setCurrentTab
+ mUi.setActiveTab(tab);
+ }
+
+ protected void closeEmptyChildTab() {
+ Tab current = mTabControl.getCurrentTab();
+ if (current != null
+ && current.getWebView().copyBackForwardList().getSize() == 0) {
+ Tab parent = current.getParentTab();
+ if (parent != null) {
+ switchToTab(mTabControl.getTabIndex(parent));
+ closeTab(current);
+ }
+ }
+ }
+
+ protected void reuseTab(Tab appTab, String appId, UrlData urlData) {
+ // Dismiss the subwindow if applicable.
+ dismissSubWindow(appTab);
+ // Since we might kill the WebView, remove it from the
+ // content view first.
+ mUi.detachTab(appTab);
+ // Recreate the main WebView after destroying the old one.
+ mTabControl.recreateWebView(appTab);
+ // TODO: analyze why the remove and add are necessary
+ mUi.attachTab(appTab);
+ if (mTabControl.getCurrentTab() != appTab) {
+ switchToTab(mTabControl.getTabIndex(appTab));
+ loadUrlDataIn(appTab, urlData);
+ } else {
+ // If the tab was the current tab, we have to attach
+ // it to the view system again.
+ setActiveTab(appTab);
+ loadUrlDataIn(appTab, urlData);
+ }
+ }
+
+ // Remove the sub window if it exists. Also called by TabControl when the
+ // user clicks the 'X' to dismiss a sub window.
+ public void dismissSubWindow(Tab tab) {
+ removeSubWindow(tab);
+ // dismiss the subwindow. This will destroy the WebView.
+ tab.dismissSubWindow();
+ getCurrentTopWebView().requestFocus();
+ }
+
+ @Override
+ public void removeSubWindow(Tab t) {
+ if (t.getSubWebView() != null) {
+ mUi.removeSubWindow(t.getSubViewContainer());
+ }
+ }
+
+ @Override
+ public void attachSubWindow(Tab tab) {
+ if (tab.getSubWebView() != null) {
+ mUi.attachSubWindow(tab.getSubViewContainer());
+ getCurrentTopWebView().requestFocus();
+ }
+ }
+
+ @Override
+ public Tab openTabToHomePage() {
+ // check for max tabs
+ if (mTabControl.canCreateNewTab()) {
+ return openTabAndShow(null, new UrlData(mSettings.getHomePage()),
+ false, null);
+ } else {
+ mUi.showMaxTabsWarning();
+ return null;
+ }
+ }
+
+ protected Tab openTab(Tab parent, String url, boolean forceForeground) {
+ if (mSettings.openInBackground() && !forceForeground) {
+ Tab tab = mTabControl.createNewTab(false, null, null,
+ (parent != null) && parent.isPrivateBrowsingEnabled());
+ if (tab != null) {
+ addTab(tab);
+ WebView view = tab.getWebView();
+ loadUrl(view, url);
+ }
+ return tab;
+ } else {
+ return openTabAndShow(parent, new UrlData(url), false, null);
+ }
+ }
+
+
+ // This method does a ton of stuff. It will attempt to create a new tab
+ // if we haven't reached MAX_TABS. Otherwise it uses the current tab. If
+ // url isn't null, it will load the given url.
+ public Tab openTabAndShow(Tab parent, final UrlData urlData,
+ boolean closeOnExit, String appId) {
+ final Tab currentTab = mTabControl.getCurrentTab();
+ if (mTabControl.canCreateNewTab()) {
+ final Tab tab = mTabControl.createNewTab(closeOnExit, appId,
+ urlData.mUrl,
+ (parent != null) && parent.isPrivateBrowsingEnabled());
+ WebView webview = tab.getWebView();
+ // We must set the new tab as the current tab to reflect the old
+ // animation behavior.
+ addTab(tab);
+ setActiveTab(tab);
+
+ // Callback to load the url data.
+ final Runnable load = new Runnable() {
+ @Override public void run() {
+ if (!urlData.isEmpty()) {
+ loadUrlDataIn(tab, urlData);
+ }
+ }
+ };
+
+ GoogleAccountLogin.startLoginIfNeeded(mActivity, mSettings, load);
+ return tab;
+ } else {
+ // Get rid of the subwindow if it exists
+ dismissSubWindow(currentTab);
+ if (!urlData.isEmpty()) {
+ // Load the given url.
+ loadUrlDataIn(currentTab, urlData);
+ }
+ return currentTab;
+ }
+ }
+
+ @Override
+ public Tab openIncognitoTab() {
+ if (mTabControl.canCreateNewTab()) {
+ Tab currentTab = mTabControl.getCurrentTab();
+ Tab tab = mTabControl.createNewTab(false, null,
+ null, true);
+ addTab(tab);
+ setActiveTab(tab);
+ loadUrlDataIn(tab, new UrlData("browser:incognito"));
+ return tab;
+ } else {
+ mUi.showMaxTabsWarning();
+ return null;
+ }
+ }
+
+ /**
+ * @param index Index of the tab to change to, as defined by
+ * mTabControl.getTabIndex(Tab t).
+ * @return boolean True if we successfully switched to a different tab. If
+ * the indexth tab is null, or if that tab is the same as
+ * the current one, return false.
+ */
+ @Override
+ public boolean switchToTab(int index) {
+ // hide combo view if open
+ removeComboView();
+ Tab tab = mTabControl.getTab(index);
+ Tab currentTab = mTabControl.getCurrentTab();
+ if (tab == null || tab == currentTab) {
+ return false;
+ }
+ setActiveTab(tab);
+ return true;
+ }
+
+ @Override
+ public void closeCurrentTab() {
+ // hide combo view if open
+ removeComboView();
+ final Tab current = mTabControl.getCurrentTab();
+ if (mTabControl.getTabCount() == 1) {
+ mActivity.finish();
+ return;
+ }
+ final Tab parent = current.getParentTab();
+ int indexToShow = -1;
+ if (parent != null) {
+ indexToShow = mTabControl.getTabIndex(parent);
+ } else {
+ final int currentIndex = mTabControl.getCurrentIndex();
+ // Try to move to the tab to the right
+ indexToShow = currentIndex + 1;
+ if (indexToShow > mTabControl.getTabCount() - 1) {
+ // Try to move to the tab to the left
+ indexToShow = currentIndex - 1;
+ }
+ }
+ if (switchToTab(indexToShow)) {
+ // Close window
+ closeTab(current);
+ }
+ }
+
+ /**
+ * Close the tab, remove its associated title bar, and adjust mTabControl's
+ * current tab to a valid value.
+ */
+ @Override
+ public void closeTab(Tab tab) {
+ // hide combo view if open
+ removeComboView();
+ int currentIndex = mTabControl.getCurrentIndex();
+ int removeIndex = mTabControl.getTabIndex(tab);
+ Tab newtab = mTabControl.getTab(currentIndex);
+ setActiveTab(newtab);
+ removeTab(tab);
+ }
+
+ /**************** TODO: Url loading clean up *******************************/
+
+ // Called when loading from context menu or LOAD_URL message
+ protected void loadUrlFromContext(WebView view, String url) {
+ // In case the user enters nothing.
+ if (url != null && url.length() != 0 && view != null) {
+ url = UrlUtils.smartUrlFilter(url);
+ if (!view.getWebViewClient().shouldOverrideUrlLoading(view, url)) {
+ loadUrl(view, url);
+ }
+ }
+ }
+
+ /**
+ * Load the URL into the given WebView and update the title bar
+ * to reflect the new load. Call this instead of WebView.loadUrl
+ * directly.
+ * @param view The WebView used to load url.
+ * @param url The URL to load.
+ */
+ protected void loadUrl(WebView view, String url) {
+ view.loadUrl(url);
+ }
+
+ /**
+ * Load UrlData into a Tab and update the title bar to reflect the new
+ * load. Call this instead of UrlData.loadIn directly.
+ * @param t The Tab used to load.
+ * @param data The UrlData being loaded.
+ */
+ protected void loadUrlDataIn(Tab t, UrlData data) {
+ data.loadIn(t);
+ }
+
+ @Override
+ public void onUserCanceledSsl(Tab tab) {
+ WebView web = tab.getWebView();
+ // TODO: Figure out the "right" behavior
+ if (web.canGoBack()) {
+ web.goBack();
+ } else {
+ web.loadUrl(mSettings.getHomePage());
+ }
+ }
+
+ void goBackOnePageOrQuit() {
+ Tab current = mTabControl.getCurrentTab();
+ if (current == null) {
+ /*
+ * Instead of finishing the activity, simply push this to the back
+ * of the stack and let ActivityManager to choose the foreground
+ * activity. As BrowserActivity is singleTask, it will be always the
+ * root of the task. So we can use either true or false for
+ * moveTaskToBack().
+ */
+ mActivity.moveTaskToBack(true);
+ return;
+ }
+ WebView w = current.getWebView();
+ if (w.canGoBack()) {
+ w.goBack();
+ } else {
+ // Check to see if we are closing a window that was created by
+ // another window. If so, we switch back to that window.
+ Tab parent = current.getParentTab();
+ if (parent != null) {
+ switchToTab(mTabControl.getTabIndex(parent));
+ // Now we close the other tab
+ closeTab(current);
+ } else {
+ if (current.closeOnExit()) {
+ // force the tab's inLoad() to be false as we are going to
+ // either finish the activity or remove the tab. This will
+ // ensure pauseWebViewTimers() taking action.
+ current.clearInPageLoad();
+ if (mTabControl.getTabCount() == 1) {
+ mActivity.finish();
+ return;
+ }
+ if (mActivityPaused) {
+ Log.e(LOGTAG, "BrowserActivity is already paused "
+ + "while handing goBackOnePageOrQuit.");
+ }
+ pauseWebViewTimers(current);
+ removeTab(current);
+ }
+ /*
+ * Instead of finishing the activity, simply push this to the back
+ * of the stack and let ActivityManager to choose the foreground
+ * activity. As BrowserActivity is singleTask, it will be always the
+ * root of the task. So we can use either true or false for
+ * moveTaskToBack().
+ */
+ mActivity.moveTaskToBack(true);
+ }
+ }
+ }
+
+ /**
+ * Feed the previously stored results strings to the BrowserProvider so that
+ * the SearchDialog will show them instead of the standard searches.
+ * @param result String to show on the editable line of the SearchDialog.
+ */
+ @Override
+ public void showVoiceSearchResults(String result) {
+ ContentProviderClient client = mActivity.getContentResolver()
+ .acquireContentProviderClient(Browser.BOOKMARKS_URI);
+ ContentProvider prov = client.getLocalContentProvider();
+ BrowserProvider bp = (BrowserProvider) prov;
+ bp.setQueryResults(mTabControl.getCurrentTab().getVoiceSearchResults());
+ client.release();
+
+ Bundle bundle = createGoogleSearchSourceBundle(
+ GOOGLE_SEARCH_SOURCE_SEARCHKEY);
+ bundle.putBoolean(SearchManager.CONTEXT_IS_VOICE, true);
+ startSearch(result, false, bundle, false);
+ }
+
+ private void startSearch(String initialQuery, boolean selectInitialQuery,
+ Bundle appSearchData, boolean globalSearch) {
+ if (appSearchData == null) {
+ appSearchData = createGoogleSearchSourceBundle(
+ GOOGLE_SEARCH_SOURCE_TYPE);
+ }
+
+ SearchEngine searchEngine = mSettings.getSearchEngine();
+ if (searchEngine != null && !searchEngine.supportsVoiceSearch()) {
+ appSearchData.putBoolean(SearchManager.DISABLE_VOICE_SEARCH, true);
+ }
+ mActivity.startSearch(initialQuery, selectInitialQuery, appSearchData,
+ globalSearch);
+ }
+
+ private Bundle createGoogleSearchSourceBundle(String source) {
+ Bundle bundle = new Bundle();
+ bundle.putString(Search.SOURCE, source);
+ return bundle;
+ }
+
+ /**
+ * handle key events in browser
+ *
+ * @param keyCode
+ * @param event
+ * @return true if handled, false to pass to super
+ */
+ boolean onKeyDown(int keyCode, KeyEvent event) {
+ boolean noModifiers = event.hasNoModifiers();
+
+ // Even if MENU is already held down, we need to call to super to open
+ // the IME on long press.
+ if (!noModifiers && KeyEvent.KEYCODE_MENU == keyCode) {
+ mMenuIsDown = true;
+ return false;
+ }
+ // The default key mode is DEFAULT_KEYS_SEARCH_LOCAL. As the MENU is
+ // still down, we don't want to trigger the search. Pretend to consume
+ // the key and do nothing.
+ if (mMenuIsDown) return true;
+
+ WebView webView = getCurrentTopWebView();
+ if (webView == null) return false;
+
+ boolean ctrl = event.hasModifiers(KeyEvent.META_CTRL_ON);
+ boolean shift = event.hasModifiers(KeyEvent.META_SHIFT_ON);
+
+ switch(keyCode) {
+ case KeyEvent.KEYCODE_ESCAPE:
+ if (!noModifiers) break;
+ stopLoading();
+ return true;
+ case KeyEvent.KEYCODE_SPACE:
+ // WebView/WebTextView handle the keys in the KeyDown. As
+ // the Activity's shortcut keys are only handled when WebView
+ // doesn't, have to do it in onKeyDown instead of onKeyUp.
+ if (shift) {
+ pageUp();
+ } else if (noModifiers) {
+ pageDown();
+ }
+ return true;
+ case KeyEvent.KEYCODE_BACK:
+ if (!noModifiers) break;
+ if (event.getRepeatCount() == 0) {
+ event.startTracking();
+ return true;
+ } else if (mUi.showsWeb()
+ && event.isLongPress()) {
+ bookmarksOrHistoryPicker(true);
+ return true;
+ }
+ break;
+ case KeyEvent.KEYCODE_DPAD_LEFT:
+ if (ctrl) {
+ webView.goBack();
+ return true;
+ }
+ break;
+ case KeyEvent.KEYCODE_DPAD_RIGHT:
+ if (ctrl) {
+ webView.goForward();
+ return true;
+ }
+ break;
+ case KeyEvent.KEYCODE_A:
+ if (ctrl) {
+ webView.selectAll();
+ return true;
+ }
+ break;
+// case KeyEvent.KEYCODE_B: // menu
+ case KeyEvent.KEYCODE_C:
+ if (ctrl) {
+ webView.copySelection();
+ return true;
+ }
+ break;
+// case KeyEvent.KEYCODE_D: // menu
+// case KeyEvent.KEYCODE_E: // in Chrome: puts '?' in URL bar
+// case KeyEvent.KEYCODE_F: // menu
+// case KeyEvent.KEYCODE_G: // in Chrome: finds next match
+// case KeyEvent.KEYCODE_H: // menu
+// case KeyEvent.KEYCODE_I: // unused
+// case KeyEvent.KEYCODE_J: // menu
+// case KeyEvent.KEYCODE_K: // in Chrome: puts '?' in URL bar
+// case KeyEvent.KEYCODE_L: // menu
+// case KeyEvent.KEYCODE_M: // unused
+// case KeyEvent.KEYCODE_N: // in Chrome: new window
+// case KeyEvent.KEYCODE_O: // in Chrome: open file
+// case KeyEvent.KEYCODE_P: // in Chrome: print page
+// case KeyEvent.KEYCODE_Q: // unused
+// case KeyEvent.KEYCODE_R:
+// case KeyEvent.KEYCODE_S: // in Chrome: saves page
+ case KeyEvent.KEYCODE_T:
+ if (ctrl) {
+ if (event.isShiftPressed()) {
+ openIncognitoTab();
+ } else {
+ openTabToHomePage();
+ }
+ return true;
+ }
+ break;
+// case KeyEvent.KEYCODE_U: // in Chrome: opens source of page
+// case KeyEvent.KEYCODE_V: // text view intercepts to paste
+// case KeyEvent.KEYCODE_W: // menu
+// case KeyEvent.KEYCODE_X: // text view intercepts to cut
+// case KeyEvent.KEYCODE_Y: // unused
+// case KeyEvent.KEYCODE_Z: // unused
+ }
+ // if we get here, it is a regular key and webview is not null
+ return mUi.dispatchKey(keyCode, event);
+ }
+
+ boolean onKeyUp(int keyCode, KeyEvent event) {
+ if (!event.hasNoModifiers()) return false;
+ switch(keyCode) {
+ case KeyEvent.KEYCODE_MENU:
+ mMenuIsDown = false;
+ break;
+ case KeyEvent.KEYCODE_BACK:
+ if (event.isTracking() && !event.isCanceled()) {
+ onBackKey();
+ return true;
+ }
+ break;
+ }
+ return false;
+ }
+
+ public boolean isMenuDown() {
+ return mMenuIsDown;
+ }
+
+ public void setupAutoFill(Message message) {
+ // Open the settings activity at the AutoFill profile fragment so that
+ // the user can create a new profile. When they return, we will dispatch
+ // the message so that we can autofill the form using their new profile.
+ Intent intent = new Intent(mActivity, BrowserPreferencesPage.class);
+ intent.putExtra(PreferenceActivity.EXTRA_SHOW_FRAGMENT,
+ AutoFillSettingsFragment.class.getName());
+ mAutoFillSetupMessage = message;
+ mActivity.startActivityForResult(intent, AUTOFILL_SETUP);
+ }
+
+ @Override
+ public void registerOptionsMenuHandler(OptionsMenuHandler handler) {
+ mOptionsMenuHandler = handler;
+ }
+
+ @Override
+ public void unregisterOptionsMenuHandler(OptionsMenuHandler handler) {
+ if (mOptionsMenuHandler == handler) {
+ mOptionsMenuHandler = null;
+ }
+ }
+
+}
diff --git a/src/com/android/browser/DataController.java b/src/com/android/browser/DataController.java
new file mode 100644
index 0000000..a56fce8
--- /dev/null
+++ b/src/com/android/browser/DataController.java
@@ -0,0 +1,218 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+
+package com.android.browser;
+
+import android.content.ContentResolver;
+import android.content.ContentUris;
+import android.content.ContentValues;
+import android.content.Context;
+import android.database.Cursor;
+import android.database.sqlite.SQLiteException;
+import android.os.Handler;
+import android.os.Message;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.History;
+import android.util.Log;
+
+import java.util.concurrent.BlockingQueue;
+import java.util.concurrent.LinkedBlockingQueue;
+
+public class DataController {
+ private static final String LOGTAG = "DataController";
+ // Message IDs
+ private static final int HISTORY_UPDATE_VISITED = 100;
+ private static final int HISTORY_UPDATE_TITLE = 101;
+ public static final int QUERY_URL_IS_BOOKMARK = 200;
+ private static DataController sInstance;
+
+ private Context mContext;
+ private DataControllerHandler mDataHandler;
+ private Handler mCbHandler; // To respond on the UI thread
+
+ /* package */ static interface OnQueryUrlIsBookmark {
+ void onQueryUrlIsBookmark(String url, boolean isBookmark);
+ }
+ private static class CallbackContainer {
+ Object replyTo;
+ Object[] args;
+ }
+
+ private static class DCMessage {
+ int what;
+ Object obj;
+ Object replyTo;
+ DCMessage(int w, Object o) {
+ what = w;
+ obj = o;
+ }
+ }
+
+ /* package */ static DataController getInstance(Context c) {
+ if (sInstance == null) {
+ sInstance = new DataController(c);
+ }
+ return sInstance;
+ }
+
+ private DataController(Context c) {
+ mContext = c.getApplicationContext();
+ mDataHandler = new DataControllerHandler();
+ mDataHandler.setDaemon(true);
+ mDataHandler.start();
+ mCbHandler = new Handler() {
+ @Override
+ public void handleMessage(Message msg) {
+ CallbackContainer cc = (CallbackContainer) msg.obj;
+ switch (msg.what) {
+ case QUERY_URL_IS_BOOKMARK: {
+ OnQueryUrlIsBookmark cb = (OnQueryUrlIsBookmark) cc.replyTo;
+ String url = (String) cc.args[0];
+ boolean isBookmark = (Boolean) cc.args[1];
+ cb.onQueryUrlIsBookmark(url, isBookmark);
+ break;
+ }
+ }
+ }
+ };
+ }
+
+ public void updateVisitedHistory(String url) {
+ mDataHandler.sendMessage(HISTORY_UPDATE_VISITED, url);
+ }
+
+ public void updateHistoryTitle(String url, String title) {
+ mDataHandler.sendMessage(HISTORY_UPDATE_TITLE, new String[] { url, title });
+ }
+
+ public void queryBookmarkStatus(String url, OnQueryUrlIsBookmark replyTo) {
+ if (url == null || url.trim().length() == 0) {
+ // null or empty url is never a bookmark
+ replyTo.onQueryUrlIsBookmark(url, false);
+ return;
+ }
+ mDataHandler.sendMessage(QUERY_URL_IS_BOOKMARK, url.trim(), replyTo);
+ }
+
+ // The standard Handler and Message classes don't allow the queue manipulation
+ // we want (such as peeking). So we use our own queue.
+ class DataControllerHandler extends Thread {
+ private BlockingQueue<DCMessage> mMessageQueue
+ = new LinkedBlockingQueue<DCMessage>();
+
+ @Override
+ public void run() {
+ super.run();
+ while (true) {
+ try {
+ handleMessage(mMessageQueue.take());
+ } catch (InterruptedException ex) {
+ break;
+ }
+ }
+ }
+
+ void sendMessage(int what, Object obj) {
+ DCMessage m = new DCMessage(what, obj);
+ mMessageQueue.add(m);
+ }
+
+ void sendMessage(int what, Object obj, Object replyTo) {
+ DCMessage m = new DCMessage(what, obj);
+ m.replyTo = replyTo;
+ mMessageQueue.add(m);
+ }
+
+ private void handleMessage(DCMessage msg) {
+ switch (msg.what) {
+ case HISTORY_UPDATE_VISITED:
+ doUpdateVisitedHistory((String) msg.obj);
+ break;
+ case HISTORY_UPDATE_TITLE:
+ String[] args = (String[]) msg.obj;
+ doUpdateHistoryTitle(args[0], args[1]);
+ break;
+ case QUERY_URL_IS_BOOKMARK:
+ // TODO: Look for identical messages in the queue and remove them
+ // TODO: Also, look for partial matches and merge them (such as
+ // multiple callbacks querying the same URL)
+ doQueryBookmarkStatus((String) msg.obj, msg.replyTo);
+ break;
+ }
+ }
+
+ private void doUpdateVisitedHistory(String url) {
+ ContentResolver cr = mContext.getContentResolver();
+ Cursor c = null;
+ try {
+ c = cr.query(History.CONTENT_URI, new String[] { History._ID, History.VISITS },
+ History.URL + "=?", new String[] { url }, null);
+ if (c.moveToFirst()) {
+ ContentValues values = new ContentValues();
+ values.put(History.VISITS, c.getInt(1) + 1);
+ values.put(History.DATE_LAST_VISITED, System.currentTimeMillis());
+ cr.update(ContentUris.withAppendedId(History.CONTENT_URI, c.getLong(0)),
+ values, null, null);
+ } else {
+ android.provider.Browser.truncateHistory(cr);
+ ContentValues values = new ContentValues();
+ values.put(History.URL, url);
+ values.put(History.VISITS, 1);
+ values.put(History.DATE_LAST_VISITED, System.currentTimeMillis());
+ values.put(History.TITLE, url);
+ values.put(History.DATE_CREATED, 0);
+ values.put(History.USER_ENTERED, 0);
+ cr.insert(History.CONTENT_URI, values);
+ }
+ } finally {
+ if (c != null) c.close();
+ }
+ }
+
+ private void doQueryBookmarkStatus(String url, Object replyTo) {
+ ContentResolver cr = mContext.getContentResolver();
+ // Check to see if the site is bookmarked
+ Cursor cursor = null;
+ boolean isBookmark = false;
+ try {
+ cursor = mContext.getContentResolver().query(
+ BookmarkUtils.getBookmarksUri(mContext),
+ new String[] { BrowserContract.Bookmarks.URL },
+ BrowserContract.Bookmarks.URL + " == ?",
+ new String[] { url },
+ null);
+ isBookmark = cursor.moveToFirst();
+ } catch (SQLiteException e) {
+ Log.e(LOGTAG, "Error checking for bookmark: " + e);
+ } finally {
+ if (cursor != null) cursor.close();
+ }
+ CallbackContainer cc = new CallbackContainer();
+ cc.replyTo = replyTo;
+ cc.args = new Object[] { url, isBookmark };
+ mCbHandler.obtainMessage(QUERY_URL_IS_BOOKMARK, cc).sendToTarget();
+ }
+
+ private void doUpdateHistoryTitle(String url, String title) {
+ ContentResolver cr = mContext.getContentResolver();
+ ContentValues values = new ContentValues();
+ values.put(History.TITLE, title);
+ cr.update(History.CONTENT_URI, values, History.URL + "=?",
+ new String[] { url });
+ }
+ }
+}
diff --git a/src/com/android/browser/DateSortedExpandableListAdapter.java b/src/com/android/browser/DateSortedExpandableListAdapter.java
index 1d04493..a48efe6 100644
--- a/src/com/android/browser/DateSortedExpandableListAdapter.java
+++ b/src/com/android/browser/DateSortedExpandableListAdapter.java
@@ -17,65 +17,55 @@
package com.android.browser;
import android.content.Context;
-import android.database.ContentObserver;
import android.database.Cursor;
import android.database.DataSetObserver;
-import android.os.Handler;
-import android.provider.BaseColumns;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.webkit.DateSorter;
-import android.widget.ExpandableListAdapter;
+import android.widget.BaseExpandableListAdapter;
import android.widget.ExpandableListView;
import android.widget.TextView;
-import java.util.Vector;
-
/**
* ExpandableListAdapter which separates data into categories based on date.
* Used for History and Downloads.
*/
-public class DateSortedExpandableListAdapter implements ExpandableListAdapter {
+public class DateSortedExpandableListAdapter extends BaseExpandableListAdapter {
// Array for each of our bins. Each entry represents how many items are
// in that bin.
private int mItemMap[];
// This is our GroupCount. We will have at most DateSorter.DAY_COUNT
// bins, less if the user has no items in one or more bins.
private int mNumberOfBins;
- private Vector<DataSetObserver> mObservers;
private Cursor mCursor;
private DateSorter mDateSorter;
private int mDateIndex;
private int mIdIndex;
private Context mContext;
- private class ChangeObserver extends ContentObserver {
- public ChangeObserver() {
- super(new Handler());
+ boolean mDataValid;
+
+ DataSetObserver mDataSetObserver = new DataSetObserver() {
+ @Override
+ public void onChanged() {
+ mDataValid = true;
+ notifyDataSetChanged();
}
@Override
- public boolean deliverSelfNotifications() {
- return true;
+ public void onInvalidated() {
+ mDataValid = false;
+ notifyDataSetInvalidated();
}
-
- @Override
- public void onChange(boolean selfChange) {
- refreshData();
- }
- }
-
- public DateSortedExpandableListAdapter(Context context, Cursor cursor,
- int dateIndex) {
+ };
+
+ public DateSortedExpandableListAdapter(Context context, int dateIndex) {
mContext = context;
mDateSorter = new DateSorter(context);
- mObservers = new Vector<DataSetObserver>();
- mCursor = cursor;
- mIdIndex = cursor.getColumnIndexOrThrow(BaseColumns._ID);
- cursor.registerContentObserver(new ChangeObserver());
mDateIndex = dateIndex;
- buildMap();
+ mDataValid = false;
+ mIdIndex = -1;
}
/**
@@ -122,6 +112,7 @@
* @return corresponding byte array from the Cursor.
*/
/* package */ byte[] getBlob(int cursorIndex) {
+ if (!mDataValid) return null;
return mCursor.getBlob(cursorIndex);
}
@@ -138,6 +129,7 @@
* @return corresponding integer from the Cursor.
*/
/* package */ int getInt(int cursorIndex) {
+ if (!mDataValid) return 0;
return mCursor.getInt(cursorIndex);
}
@@ -146,6 +138,7 @@
* already been moved to the correct position.
*/
/* package */ long getLong(int cursorIndex) {
+ if (!mDataValid) return 0;
return mCursor.getLong(cursorIndex);
}
@@ -158,6 +151,7 @@
* @return corresponding String from the Cursor.
*/
/* package */ String getString(int cursorIndex) {
+ if (!mDataValid) return null;
return mCursor.getString(cursorIndex);
}
@@ -166,6 +160,7 @@
* @param childId ID of the child view in question.
* @return int Group position of the containing group.
/* package */ int groupFromChildId(long childId) {
+ if (!mDataValid) return -1;
int group = -1;
for (mCursor.moveToFirst(); !mCursor.isAfterLast();
mCursor.moveToNext()) {
@@ -173,11 +168,15 @@
int bin = mDateSorter.getIndex(getLong(mDateIndex));
// bin is the same as the group if the number of bins is the
// same as DateSorter
- if (mDateSorter.DAY_COUNT == mNumberOfBins) return bin;
+ if (DateSorter.DAY_COUNT == mNumberOfBins) {
+ return bin;
+ }
// There are some empty bins. Find the corresponding group.
group = 0;
for (int i = 0; i < bin; i++) {
- if (mItemMap[i] != 0) group++;
+ if (mItemMap[i] != 0) {
+ group++;
+ }
}
break;
}
@@ -193,6 +192,7 @@
* @return The corresponding bin that holds that group.
*/
private int groupPositionToBin(int groupPosition) {
+ if (!mDataValid) return -1;
if (groupPosition < 0 || groupPosition >= DateSorter.DAY_COUNT) {
throw new AssertionError("group position out of range");
}
@@ -241,7 +241,9 @@
*/
/* package */ boolean moveCursorToChildPosition(int groupPosition,
int childPosition) {
- if (mCursor.isClosed()) return false;
+ if (!mDataValid || mCursor.isClosed()) {
+ return false;
+ }
groupPosition = groupPositionToBin(groupPosition);
int index = childPosition;
for (int i = 0; i < groupPosition; i++) {
@@ -250,19 +252,34 @@
return mCursor.moveToPosition(index);
}
- /* package */ void refreshData() {
- if (mCursor.isClosed()) {
+ public void changeCursor(Cursor cursor) {
+ if (cursor == mCursor) {
return;
}
- mCursor.requery();
- buildMap();
- for (DataSetObserver o : mObservers) {
- o.onChanged();
+ if (mCursor != null) {
+ mCursor.unregisterDataSetObserver(mDataSetObserver);
+ mCursor.close();
+ }
+ mCursor = cursor;
+ if (cursor != null) {
+ cursor.registerDataSetObserver(mDataSetObserver);
+ mIdIndex = cursor.getColumnIndexOrThrow("_id");
+ mDataValid = true;
+ buildMap();
+ // notify the observers about the new cursor
+ notifyDataSetChanged();
+ } else {
+ mIdIndex = -1;
+ mDataValid = false;
+ // notify the observers about the lack of a data set
+ notifyDataSetInvalidated();
}
}
+ @Override
public View getGroupView(int groupPosition, boolean isExpanded,
View convertView, ViewGroup parent) {
+ if (!mDataValid) throw new IllegalStateException("Data is not valid");
TextView item;
if (null == convertView || !(convertView instanceof TextView)) {
LayoutInflater factory = LayoutInflater.from(mContext);
@@ -275,73 +292,87 @@
return item;
}
+ @Override
public View getChildView(int groupPosition, int childPosition,
boolean isLastChild, View convertView, ViewGroup parent) {
+ if (!mDataValid) throw new IllegalStateException("Data is not valid");
return null;
}
+ @Override
public boolean areAllItemsEnabled() {
return true;
}
+ @Override
public boolean isChildSelectable(int groupPosition, int childPosition) {
return true;
}
+ @Override
public int getGroupCount() {
+ if (!mDataValid) return 0;
return mNumberOfBins;
}
+ @Override
public int getChildrenCount(int groupPosition) {
+ if (!mDataValid) return 0;
return mItemMap[groupPositionToBin(groupPosition)];
}
+ @Override
public Object getGroup(int groupPosition) {
return null;
}
+ @Override
public Object getChild(int groupPosition, int childPosition) {
return null;
}
+ @Override
public long getGroupId(int groupPosition) {
+ if (!mDataValid) return 0;
return groupPosition;
}
+ @Override
public long getChildId(int groupPosition, int childPosition) {
+ if (!mDataValid) return 0;
if (moveCursorToChildPosition(groupPosition, childPosition)) {
return getLong(mIdIndex);
}
return 0;
}
+ @Override
public boolean hasStableIds() {
return true;
}
- public void registerDataSetObserver(DataSetObserver observer) {
- mObservers.add(observer);
- }
-
- public void unregisterDataSetObserver(DataSetObserver observer) {
- mObservers.remove(observer);
- }
-
+ @Override
public void onGroupExpanded(int groupPosition) {
}
+ @Override
public void onGroupCollapsed(int groupPosition) {
}
+ @Override
public long getCombinedChildId(long groupId, long childId) {
+ if (!mDataValid) return 0;
return childId;
}
+ @Override
public long getCombinedGroupId(long groupId) {
+ if (!mDataValid) return 0;
return groupId;
}
+ @Override
public boolean isEmpty() {
- return mCursor.isClosed() || mCursor.getCount() == 0;
+ return !mDataValid || mCursor == null || mCursor.isClosed() || mCursor.getCount() == 0;
}
}
diff --git a/src/com/android/browser/Dots.java b/src/com/android/browser/Dots.java
deleted file mode 100644
index eb8d493..0000000
--- a/src/com/android/browser/Dots.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.browser;
-
-import android.content.Context;
-import android.util.AttributeSet;
-import android.view.Gravity;
-import android.widget.ImageView;
-import android.widget.LinearLayout;
-
-import java.util.Map;
-
-/**
- * Displays a series of dots. The selected one is highlighted.
- * No animations yet. Nothing fancy.
- */
-class Dots extends LinearLayout {
-
- private static final int MAX_DOTS = 8;
- private int mSelected = -1;
-
- public Dots(Context context) {
- this(context, null);
- }
-
- public Dots(Context context, AttributeSet attrs) {
- super(context, attrs);
-
- setGravity(Gravity.CENTER);
- setPadding(0, 4, 0, 4);
-
- LayoutParams lp =
- new LayoutParams(LayoutParams.WRAP_CONTENT,
- LayoutParams.WRAP_CONTENT);
-
- for (int i = 0; i < MAX_DOTS; i++) {
- ImageView dotView = new ImageView(mContext);
- dotView.setImageResource(R.drawable.page_indicator_unselected2);
- addView(dotView, lp);
- }
- }
-
- /**
- * @param dotCount if less than 1 or greater than MAX_DOTS, Dots
- * disappears
- */
- public void setDotCount(int dotCount) {
- if (dotCount > 1 && dotCount <= MAX_DOTS) {
- setVisibility(VISIBLE);
- for (int i = 0; i < MAX_DOTS; i++) {
- getChildAt(i).setVisibility(i < dotCount? VISIBLE : GONE);
- }
- } else {
- setVisibility(GONE);
- }
- }
-
- public void setSelected(int index) {
- if (index < 0 || index >= MAX_DOTS) return;
-
- if (mSelected >= 0) {
- // Unselect old
- ((ImageView)getChildAt(mSelected)).setImageResource(
- R.drawable.page_indicator_unselected2);
- }
- ((ImageView)getChildAt(index)).setImageResource(R.drawable.page_indicator);
- mSelected = index;
- }
-}
diff --git a/src/com/android/browser/DownloadHandler.java b/src/com/android/browser/DownloadHandler.java
new file mode 100644
index 0000000..40278f4
--- /dev/null
+++ b/src/com/android/browser/DownloadHandler.java
@@ -0,0 +1,220 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.app.Activity;
+import android.app.AlertDialog;
+import android.app.DownloadManager;
+import android.content.ActivityNotFoundException;
+import android.content.ComponentName;
+import android.content.ContentValues;
+import android.content.Context;
+import android.content.Intent;
+import android.content.pm.PackageManager;
+import android.content.pm.ResolveInfo;
+import android.net.Uri;
+import android.net.WebAddress;
+import android.os.Environment;
+import android.text.TextUtils;
+import android.util.Log;
+import android.webkit.CookieManager;
+import android.webkit.URLUtil;
+import android.widget.Toast;
+
+/**
+ * Handle download requests
+ */
+public class DownloadHandler {
+
+ private static final boolean LOGD_ENABLED =
+ com.android.browser.Browser.LOGD_ENABLED;
+
+ private static final String LOGTAG = "DLHandler";
+
+ /**
+ * Notify the host application a download should be done, or that
+ * the data should be streamed if a streaming viewer is available.
+ * @param activity Activity requesting the download.
+ * @param url The full url to the content that should be downloaded
+ * @param userAgent User agent of the downloading application.
+ * @param contentDisposition Content-disposition http header, if present.
+ * @param mimetype The mimetype of the content reported by the server
+ */
+ public static void onDownloadStart(Activity activity, String url,
+ String userAgent, String contentDisposition, String mimetype) {
+ // if we're dealing wih A/V content that's not explicitly marked
+ // for download, check if it's streamable.
+ if (contentDisposition == null
+ || !contentDisposition.regionMatches(
+ true, 0, "attachment", 0, 10)) {
+ // query the package manager to see if there's a registered handler
+ // that matches.
+ Intent intent = new Intent(Intent.ACTION_VIEW);
+ intent.setDataAndType(Uri.parse(url), mimetype);
+ ResolveInfo info = activity.getPackageManager().resolveActivity(intent,
+ PackageManager.MATCH_DEFAULT_ONLY);
+ if (info != null) {
+ ComponentName myName = activity.getComponentName();
+ // If we resolved to ourselves, we don't want to attempt to
+ // load the url only to try and download it again.
+ if (!myName.getPackageName().equals(
+ info.activityInfo.packageName)
+ || !myName.getClassName().equals(
+ info.activityInfo.name)) {
+ // someone (other than us) knows how to handle this mime
+ // type with this scheme, don't download.
+ try {
+ activity.startActivity(intent);
+ return;
+ } catch (ActivityNotFoundException ex) {
+ if (LOGD_ENABLED) {
+ Log.d(LOGTAG, "activity not found for " + mimetype
+ + " over " + Uri.parse(url).getScheme(),
+ ex);
+ }
+ // Best behavior is to fall back to a download in this
+ // case
+ }
+ }
+ }
+ }
+ onDownloadStartNoStream(activity, url, userAgent, contentDisposition,
+ mimetype);
+ }
+
+ // This is to work around the fact that java.net.URI throws Exceptions
+ // instead of just encoding URL's properly
+ // Helper method for onDownloadStartNoStream
+ private static String encodePath(String path) {
+ char[] chars = path.toCharArray();
+
+ boolean needed = false;
+ for (char c : chars) {
+ if (c == '[' || c == ']') {
+ needed = true;
+ break;
+ }
+ }
+ if (needed == false) {
+ return path;
+ }
+
+ StringBuilder sb = new StringBuilder("");
+ for (char c : chars) {
+ if (c == '[' || c == ']') {
+ sb.append('%');
+ sb.append(Integer.toHexString(c));
+ } else {
+ sb.append(c);
+ }
+ }
+
+ return sb.toString();
+ }
+
+ /**
+ * Notify the host application a download should be done, even if there
+ * is a streaming viewer available for thise type.
+ * @param activity Activity requesting the download.
+ * @param url The full url to the content that should be downloaded
+ * @param userAgent User agent of the downloading application.
+ * @param contentDisposition Content-disposition http header, if present.
+ * @param mimetype The mimetype of the content reported by the server
+ */
+ /*package */ static void onDownloadStartNoStream(Activity activity,
+ String url, String userAgent, String contentDisposition,
+ String mimetype) {
+
+ String filename = URLUtil.guessFileName(url,
+ contentDisposition, mimetype);
+
+ // Check to see if we have an SDCard
+ String status = Environment.getExternalStorageState();
+ if (!status.equals(Environment.MEDIA_MOUNTED)) {
+ int title;
+ String msg;
+
+ // Check to see if the SDCard is busy, same as the music app
+ if (status.equals(Environment.MEDIA_SHARED)) {
+ msg = activity.getString(R.string.download_sdcard_busy_dlg_msg);
+ title = R.string.download_sdcard_busy_dlg_title;
+ } else {
+ msg = activity.getString(R.string.download_no_sdcard_dlg_msg, filename);
+ title = R.string.download_no_sdcard_dlg_title;
+ }
+
+ new AlertDialog.Builder(activity)
+ .setTitle(title)
+ .setIcon(android.R.drawable.ic_dialog_alert)
+ .setMessage(msg)
+ .setPositiveButton(R.string.ok, null)
+ .show();
+ return;
+ }
+
+ // java.net.URI is a lot stricter than KURL so we have to encode some
+ // extra characters. Fix for b 2538060 and b 1634719
+ WebAddress webAddress;
+ try {
+ webAddress = new WebAddress(url);
+ webAddress.setPath(encodePath(webAddress.getPath()));
+ } catch (Exception e) {
+ // This only happens for very bad urls, we want to chatch the
+ // exception here
+ Log.e(LOGTAG, "Exception trying to parse url:" + url);
+ return;
+ }
+
+ String addressString = webAddress.toString();
+ Uri uri = Uri.parse(addressString);
+ final DownloadManager.Request request = new DownloadManager.Request(uri);
+ request.setMimeType(mimetype);
+ // set downloaded file destination to /sdcard/Download.
+ // or, should it be set to one of several Environment.DIRECTORY* dirs depending on mimetype?
+ request.setDestinationInExternalPublicDir(Environment.DIRECTORY_DOWNLOADS, filename);
+ // let this downloaded file be scanned by MediaScanner - so that it can
+ // show up in Gallery app, for example.
+ request.allowScanningByMediaScanner();
+ request.setDescription(webAddress.getHost());
+ // XXX: Have to use the old url since the cookies were stored using the
+ // old percent-encoded url.
+ String cookies = CookieManager.getInstance().getCookie(url);
+ request.addRequestHeader("cookie", cookies);
+ request.setNotificationVisibility(
+ DownloadManager.Request.VISIBILITY_VISIBLE_NOTIFY_COMPLETED);
+ if (mimetype == null) {
+ if (TextUtils.isEmpty(addressString)) {
+ return;
+ }
+ // We must have long pressed on a link or image to download it. We
+ // are not sure of the mimetype in this case, so do a head request
+ new FetchUrlMimeType(activity, request, addressString, cookies,
+ userAgent).start();
+ } else {
+ final DownloadManager manager
+ = (DownloadManager) activity.getSystemService(Context.DOWNLOAD_SERVICE);
+ new Thread("Browser download") {
+ public void run() {
+ manager.enqueue(request);
+ }
+ }.start();
+ }
+ Toast.makeText(activity, R.string.download_pending, Toast.LENGTH_SHORT)
+ .show();
+ }
+
+}
diff --git a/src/com/android/browser/DownloadTouchIcon.java b/src/com/android/browser/DownloadTouchIcon.java
index e8a912c..768eab5 100644
--- a/src/com/android/browser/DownloadTouchIcon.java
+++ b/src/com/android/browser/DownloadTouchIcon.java
@@ -16,20 +16,6 @@
package com.android.browser;
-import android.content.ContentResolver;
-import android.content.ContentUris;
-import android.content.ContentValues;
-import android.content.Context;
-import android.database.Cursor;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.net.http.AndroidHttpClient;
-import android.net.Proxy;
-import android.os.AsyncTask;
-import android.provider.Browser;
-import android.webkit.WebView;
-
-
import org.apache.http.HttpEntity;
import org.apache.http.HttpHost;
import org.apache.http.HttpResponse;
@@ -37,6 +23,21 @@
import org.apache.http.client.params.HttpClientParams;
import org.apache.http.conn.params.ConnRouteParams;
+import android.content.ContentResolver;
+import android.content.ContentValues;
+import android.content.Context;
+import android.database.Cursor;
+import android.graphics.Bitmap;
+import android.graphics.BitmapFactory;
+import android.net.Proxy;
+import android.net.http.AndroidHttpClient;
+import android.os.AsyncTask;
+import android.os.Bundle;
+import android.os.Message;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Images;
+import android.webkit.WebView;
+
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
@@ -46,10 +47,17 @@
private Cursor mCursor;
private final String mOriginalUrl;
private final String mUrl;
- private final String mUserAgent;
+ private final String mUserAgent; // Sites may serve a different icon to different UAs
+ private Message mMessage;
+
private final Context mContext;
/* package */ Tab mTab;
+ /**
+ * Use this ctor to store the touch icon in the bookmarks database for
+ * the originalUrl so we take account of redirects. Used when the user
+ * bookmarks a page from outside the bookmarks activity.
+ */
public DownloadTouchIcon(Tab tab, Context ctx, ContentResolver cr, WebView view) {
mTab = tab;
mContext = ctx;
@@ -60,6 +68,13 @@
mUserAgent = view.getSettings().getUserAgentString();
}
+ /**
+ * Use this ctor to download the touch icon and update the bookmarks database
+ * entry for the given url. Used when the user creates a bookmark from
+ * within the bookmarks activity and there haven't been any redirects.
+ * TODO: Would be nice to set the user agent here so that there is no
+ * potential for the three different ctors here to return different icons.
+ */
public DownloadTouchIcon(Context ctx, ContentResolver cr, String url) {
mTab = null;
mContext = ctx;
@@ -69,15 +84,33 @@
mUserAgent = null;
}
+ /**
+ * Use this ctor to not store the touch icon in a database, rather add it to
+ * the passed Message's data bundle with the key
+ * {@link BrowserContract.Bookmarks#TOUCH_ICON} and then send the message.
+ */
+ public DownloadTouchIcon(Context context, Message msg, String userAgent) {
+ mMessage = msg;
+ mContext = context;
+ mContentResolver = null;
+ mOriginalUrl = null;
+ mUrl = null;
+ mUserAgent = userAgent;
+ }
+
@Override
public Void doInBackground(String... values) {
- mCursor = BrowserBookmarksAdapter.queryBookmarksForUrl(mContentResolver,
- mOriginalUrl, mUrl, true);
- if (mCursor != null && mCursor.getCount() > 0) {
- String url = values[0];
+ if (mContentResolver != null) {
+ mCursor = Bookmarks.queryCombinedForUrl(mContentResolver,
+ mOriginalUrl, mUrl);
+ }
- AndroidHttpClient client = AndroidHttpClient.newInstance(
- mUserAgent);
+ boolean inDatabase = mCursor != null && mCursor.getCount() > 0;
+
+ String url = values[0];
+
+ if (inDatabase || mMessage != null) {
+ AndroidHttpClient client = AndroidHttpClient.newInstance(mUserAgent);
HttpHost httpHost = Proxy.getPreferredHttpHost(mContext, url);
if (httpHost != null) {
ConnRouteParams.setDefaultProxy(client.getParams(), httpHost);
@@ -90,7 +123,6 @@
try {
HttpResponse response = client.execute(request);
-
if (response.getStatusLine().getStatusCode() == 200) {
HttpEntity entity = response.getEntity();
if (entity != null) {
@@ -98,7 +130,12 @@
if (content != null) {
Bitmap icon = BitmapFactory.decodeStream(
content, null, null);
- storeIcon(icon);
+ if (inDatabase) {
+ storeIcon(icon);
+ } else if (mMessage != null) {
+ Bundle b = mMessage.getData();
+ b.putParcelable(BrowserContract.Bookmarks.TOUCH_ICON, icon);
+ }
}
}
}
@@ -110,9 +147,15 @@
client.close();
}
}
+
if (mCursor != null) {
mCursor.close();
}
+
+ if (mMessage != null) {
+ mMessage.sendToTarget();
+ }
+
return null;
}
@@ -134,17 +177,16 @@
return;
}
- final ByteArrayOutputStream os = new ByteArrayOutputStream();
- icon.compress(Bitmap.CompressFormat.PNG, 100, os);
- ContentValues values = new ContentValues();
- values.put(Browser.BookmarkColumns.TOUCH_ICON,
- os.toByteArray());
-
if (mCursor.moveToFirst()) {
+ final ByteArrayOutputStream os = new ByteArrayOutputStream();
+ icon.compress(Bitmap.CompressFormat.PNG, 100, os);
+
+ ContentValues values = new ContentValues();
+ values.put(Images.TOUCH_ICON, os.toByteArray());
+ values.put(Images.URL, mCursor.getString(0));
+
do {
- mContentResolver.update(ContentUris.withAppendedId(
- Browser.BOOKMARKS_URI, mCursor.getInt(0)),
- values, null, null);
+ mContentResolver.update(Images.CONTENT_URI, values, null, null);
} while (mCursor.moveToNext());
}
}
diff --git a/src/com/android/browser/FetchUrlMimeType.java b/src/com/android/browser/FetchUrlMimeType.java
index 62d877e..85c588e 100644
--- a/src/com/android/browser/FetchUrlMimeType.java
+++ b/src/com/android/browser/FetchUrlMimeType.java
@@ -16,78 +16,68 @@
package com.android.browser;
-import android.content.ContentValues;
-import android.net.Proxy;
-import android.net.Uri;
-import android.net.http.AndroidHttpClient;
-
+import org.apache.http.Header;
import org.apache.http.HttpHost;
import org.apache.http.HttpResponse;
-import org.apache.http.Header;
import org.apache.http.client.methods.HttpHead;
import org.apache.http.conn.params.ConnRouteParams;
-import java.io.IOException;
-
-import android.os.AsyncTask;
-import android.provider.Downloads;
+import android.app.Activity;
+import android.app.DownloadManager;
+import android.content.Context;
+import android.net.Proxy;
+import android.net.http.AndroidHttpClient;
+import android.os.Environment;
import android.webkit.MimeTypeMap;
import android.webkit.URLUtil;
+import java.io.IOException;
+
/**
* This class is used to pull down the http headers of a given URL so that
* we can analyse the mimetype and make any correction needed before we give
- * the URL to the download manager. The ContentValues class holds the
- * content that would be provided to the download manager, so that on
- * completion of checking the mimetype, we can issue the download to
- * the download manager.
+ * the URL to the download manager.
* This operation is needed when the user long-clicks on a link or image and
* we don't know the mimetype. If the user just clicks on the link, we will
* do the same steps of correcting the mimetype down in
* android.os.webkit.LoadListener rather than handling it here.
*
*/
-class FetchUrlMimeType extends AsyncTask<ContentValues, String, ContentValues> {
+class FetchUrlMimeType extends Thread {
- BrowserActivity mActivity;
- ContentValues mValues;
+ private Activity mActivity;
+ private DownloadManager.Request mRequest;
+ private String mUri;
+ private String mCookies;
+ private String mUserAgent;
- public FetchUrlMimeType(BrowserActivity activity) {
+ public FetchUrlMimeType(Activity activity, DownloadManager.Request request,
+ String uri, String cookies, String userAgent) {
mActivity = activity;
+ mRequest = request;
+ mUri = uri;
+ mCookies = cookies;
+ mUserAgent = userAgent;
}
@Override
- public ContentValues doInBackground(ContentValues... values) {
- mValues = values[0];
-
- // Check to make sure we have a URI to download
- String uri = mValues.getAsString(Downloads.Impl.COLUMN_URI);
- if (uri == null || uri.length() == 0) {
- return null;
- }
-
+ public void run() {
// User agent is likely to be null, though the AndroidHttpClient
// seems ok with that.
- AndroidHttpClient client = AndroidHttpClient.newInstance(
- mValues.getAsString(Downloads.Impl.COLUMN_USER_AGENT));
- HttpHost httpHost = Proxy.getPreferredHttpHost(mActivity, uri);
+ AndroidHttpClient client = AndroidHttpClient.newInstance(mUserAgent);
+ HttpHost httpHost = Proxy.getPreferredHttpHost(mActivity, mUri);
if (httpHost != null) {
ConnRouteParams.setDefaultProxy(client.getParams(), httpHost);
}
- HttpHead request = new HttpHead(uri);
+ HttpHead request = new HttpHead(mUri);
- String cookie = mValues.getAsString(Downloads.Impl.COLUMN_COOKIE_DATA);
- if (cookie != null && cookie.length() > 0) {
- request.addHeader("Cookie", cookie);
- }
-
- String referer = mValues.getAsString(Downloads.Impl.COLUMN_REFERER);
- if (referer != null && referer.length() > 0) {
- request.addHeader("Referer", referer);
+ if (mCookies != null && mCookies.length() > 0) {
+ request.addHeader("Cookie", mCookies);
}
HttpResponse response;
- ContentValues result = new ContentValues();
+ String mimeType = null;
+ String contentDisposition = null;
try {
response = client.execute(request);
// We could get a redirect here, but if we do lets let
@@ -96,16 +86,15 @@
if (response.getStatusLine().getStatusCode() == 200) {
Header header = response.getFirstHeader("Content-Type");
if (header != null) {
- String mimeType = header.getValue();
+ mimeType = header.getValue();
final int semicolonIndex = mimeType.indexOf(';');
if (semicolonIndex != -1) {
mimeType = mimeType.substring(0, semicolonIndex);
}
- result.put("Content-Type", mimeType);
}
Header contentDispositionHeader = response.getFirstHeader("Content-Disposition");
if (contentDispositionHeader != null) {
- result.put("Content-Disposition", contentDispositionHeader.getValue());
+ contentDisposition = contentDispositionHeader.getValue();
}
}
} catch (IllegalArgumentException ex) {
@@ -116,32 +105,25 @@
client.close();
}
- return result;
- }
-
- @Override
- public void onPostExecute(ContentValues values) {
- final String mimeType = values.getAsString("Content-Type");
- final String contentDisposition = values.getAsString("Content-Disposition");
if (mimeType != null) {
- String url = mValues.getAsString(Downloads.Impl.COLUMN_URI);
if (mimeType.equalsIgnoreCase("text/plain") ||
mimeType.equalsIgnoreCase("application/octet-stream")) {
String newMimeType =
MimeTypeMap.getSingleton().getMimeTypeFromExtension(
- MimeTypeMap.getFileExtensionFromUrl(url));
+ MimeTypeMap.getFileExtensionFromUrl(mUri));
if (newMimeType != null) {
- mValues.put(Downloads.Impl.COLUMN_MIME_TYPE, newMimeType);
+ mRequest.setMimeType(newMimeType);
}
}
- String filename = URLUtil.guessFileName(url,
- contentDisposition, mimeType);
- mValues.put(Downloads.Impl.COLUMN_FILE_NAME_HINT, filename);
+ String filename = URLUtil.guessFileName(mUri, contentDisposition,
+ mimeType);
+ mRequest.setDestinationInExternalPublicDir(Environment.DIRECTORY_DOWNLOADS, filename);
}
// Start the download
- final Uri contentUri =
- mActivity.getContentResolver().insert(Downloads.Impl.CONTENT_URI, mValues);
+ DownloadManager manager = (DownloadManager) mActivity.getSystemService(
+ Context.DOWNLOAD_SERVICE);
+ manager.enqueue(mRequest);
}
}
diff --git a/src/com/android/browser/FindDialog.java b/src/com/android/browser/FindDialog.java
deleted file mode 100644
index 726138e..0000000
--- a/src/com/android/browser/FindDialog.java
+++ /dev/null
@@ -1,247 +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.browser;
-
-import android.content.Context;
-import android.text.Editable;
-import android.text.Selection;
-import android.text.Spannable;
-import android.text.TextWatcher;
-import android.view.Gravity;
-import android.view.KeyEvent;
-import android.view.LayoutInflater;
-import android.view.View;
-import android.view.ViewGroup;
-import android.view.animation.AnimationUtils;
-import android.view.inputmethod.InputMethodManager;
-import android.webkit.WebView;
-import android.widget.EditText;
-import android.widget.LinearLayout;
-import android.widget.TextView;
-
-/* package */ class FindDialog extends WebDialog implements TextWatcher {
- private TextView mMatches;
-
- // Views with which the user can interact.
- private EditText mEditText;
- private View mNextButton;
- private View mPrevButton;
- private View mMatchesView;
-
- // When the dialog is opened up with old text, enter needs to be pressed
- // (or the text needs to be changed) before WebView.findAll can be called.
- // Once it has been called, enter should move to the next match.
- private boolean mMatchesFound;
- private int mNumberOfMatches;
-
- private View.OnClickListener mFindListener = new View.OnClickListener() {
- public void onClick(View v) {
- findNext();
- }
- };
-
- private View.OnClickListener mFindPreviousListener =
- new View.OnClickListener() {
- public void onClick(View v) {
- if (mWebView == null) {
- throw new AssertionError("No WebView for FindDialog::onClick");
- }
- mWebView.findNext(false);
- updateMatchesString();
- hideSoftInput();
- }
- };
-
- private void disableButtons() {
- mPrevButton.setEnabled(false);
- mNextButton.setEnabled(false);
- mPrevButton.setFocusable(false);
- mNextButton.setFocusable(false);
- }
-
- /* package */ FindDialog(BrowserActivity context) {
- super(context);
-
- LayoutInflater factory = LayoutInflater.from(context);
- factory.inflate(R.layout.browser_find, this);
-
- addCancel();
- mEditText = (EditText) findViewById(R.id.edit);
-
- View button = findViewById(R.id.next);
- button.setOnClickListener(mFindListener);
- mNextButton = button;
-
- button = findViewById(R.id.previous);
- button.setOnClickListener(mFindPreviousListener);
- mPrevButton = button;
-
- mMatches = (TextView) findViewById(R.id.matches);
- mMatchesView = findViewById(R.id.matches_view);
- disableButtons();
-
- }
-
- /**
- * Called by BrowserActivity.closeDialog. Start the animation to hide
- * the dialog, inform the WebView that the dialog is being dismissed,
- * and hide the soft keyboard.
- */
- public void dismiss() {
- super.dismiss();
- mWebView.notifyFindDialogDismissed();
- hideSoftInput();
- }
-
- @Override
- public boolean dispatchKeyEventPreIme(KeyEvent event) {
- if (event.getKeyCode() == KeyEvent.KEYCODE_BACK) {
- KeyEvent.DispatcherState state = getKeyDispatcherState();
- if (state != null) {
- int action = event.getAction();
- if (KeyEvent.ACTION_DOWN == action
- && event.getRepeatCount() == 0) {
- state.startTracking(event, this);
- return true;
- } else if (KeyEvent.ACTION_UP == action
- && !event.isCanceled() && state.isTracking(event)) {
- mBrowserActivity.closeDialogs();
- return true;
- }
- }
- }
- return super.dispatchKeyEventPreIme(event);
- }
-
- @Override
- public boolean dispatchKeyEvent(KeyEvent event) {
- int keyCode = event.getKeyCode();
- if (event.getAction() == KeyEvent.ACTION_UP) {
- if (keyCode == KeyEvent.KEYCODE_ENTER
- && mEditText.hasFocus()) {
- if (mMatchesFound) {
- findNext();
- } else {
- findAll();
- // Set the selection to the end.
- Spannable span = (Spannable) mEditText.getText();
- Selection.setSelection(span, span.length());
- }
- return true;
- }
- }
- return super.dispatchKeyEvent(event);
- }
-
- private void findNext() {
- if (mWebView == null) {
- throw new AssertionError("No WebView for FindDialog::findNext");
- }
- mWebView.findNext(true);
- updateMatchesString();
- hideSoftInput();
- }
-
- public void show() {
- super.show();
- // In case the matches view is showing from a previous search
- mMatchesView.setVisibility(View.INVISIBLE);
- mMatchesFound = false;
- // This text is only here to ensure that mMatches has a height.
- mMatches.setText("0");
- mEditText.requestFocus();
- Spannable span = (Spannable) mEditText.getText();
- int length = span.length();
- Selection.setSelection(span, 0, length);
- span.setSpan(this, 0, length, Spannable.SPAN_INCLUSIVE_INCLUSIVE);
- disableButtons();
- InputMethodManager imm = (InputMethodManager)
- mBrowserActivity.getSystemService(Context.INPUT_METHOD_SERVICE);
- imm.showSoftInput(mEditText, 0);
- }
-
- // TextWatcher methods
- public void beforeTextChanged(CharSequence s,
- int start,
- int count,
- int after) {
- }
-
- public void onTextChanged(CharSequence s,
- int start,
- int before,
- int count) {
- findAll();
- }
-
- private void findAll() {
- if (mWebView == null) {
- throw new AssertionError(
- "No WebView for FindDialog::findAll");
- }
- CharSequence find = mEditText.getText();
- if (0 == find.length()) {
- disableButtons();
- mWebView.clearMatches();
- mMatchesView.setVisibility(View.INVISIBLE);
- } else {
- mMatchesView.setVisibility(View.VISIBLE);
- int found = mWebView.findAll(find.toString());
- mMatchesFound = true;
- setMatchesFound(found);
- if (found < 2) {
- disableButtons();
- if (found == 0) {
- // Cannot use getQuantityString, which ignores the "zero"
- // quantity.
- // FIXME: is this fix is beyond the scope
- // of adding touch selection to gingerbread?
- // mMatches.setText(mBrowserActivity.getResources().getString(
- // R.string.no_matches));
- }
- } else {
- mPrevButton.setFocusable(true);
- mNextButton.setFocusable(true);
- mPrevButton.setEnabled(true);
- mNextButton.setEnabled(true);
- }
- }
- }
-
- private void setMatchesFound(int found) {
- mNumberOfMatches = found;
- updateMatchesString();
- }
-
- public void setText(String text) {
- mEditText.setText(text);
- findAll();
- }
-
- private void updateMatchesString() {
- // Note: updateMatchesString is only called by methods that have already
- // checked mWebView for null.
- String template = mBrowserActivity.getResources().
- getQuantityString(R.plurals.matches_found, mNumberOfMatches,
- mWebView.findIndex() + 1, mNumberOfMatches);
-
- mMatches.setText(template);
- }
-
- public void afterTextChanged(Editable s) {
- }
-}
diff --git a/src/com/android/browser/GoogleAccountLogin.java b/src/com/android/browser/GoogleAccountLogin.java
new file mode 100644
index 0000000..eaf45ea
--- /dev/null
+++ b/src/com/android/browser/GoogleAccountLogin.java
@@ -0,0 +1,350 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import org.apache.http.Header;
+import org.apache.http.HeaderIterator;
+import org.apache.http.HttpEntity;
+import org.apache.http.HttpResponse;
+import org.apache.http.HttpStatus;
+import org.apache.http.client.methods.HttpPost;
+import org.apache.http.util.EntityUtils;
+
+import android.accounts.Account;
+import android.accounts.AccountManager;
+import android.accounts.AccountManagerCallback;
+import android.accounts.AccountManagerFuture;
+import android.app.Activity;
+import android.app.ProgressDialog;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.content.DialogInterface.OnCancelListener;
+import android.content.SharedPreferences.Editor;
+import android.net.http.AndroidHttpClient;
+import android.net.Uri;
+import android.os.Bundle;
+import android.os.Handler;
+import android.preference.PreferenceManager;
+import android.util.Log;
+import android.webkit.CookieManager;
+import android.webkit.WebView;
+import android.webkit.WebViewClient;
+
+import java.util.StringTokenizer;
+
+public class GoogleAccountLogin implements Runnable,
+ AccountManagerCallback<Bundle>, OnCancelListener {
+
+ private static final String LOGTAG = "BrowserLogin";
+
+ // Url for issuing the uber token.
+ private Uri ISSUE_AUTH_TOKEN_URL = Uri.parse(
+ "https://www.google.com/accounts/IssueAuthToken?service=gaia&Session=false");
+ // Url for signing into a particular service.
+ private static final Uri TOKEN_AUTH_URL = Uri.parse(
+ "https://www.google.com/accounts/TokenAuth");
+ // Google account type
+ private static final String GOOGLE = "com.google";
+ // Last auto login time
+ private static final String PREF_AUTOLOGIN_TIME = "last_autologin_time";
+ // A week in milliseconds (7*24*60*60*1000)
+ private static final long WEEK_IN_MILLIS = 604800000L;
+
+ private final Activity mActivity;
+ private final Account mAccount;
+ private final WebView mWebView;
+ // Does not matter if this is initialized in a non-ui thread.
+ // Dialog.dismiss() will post to the right handler.
+ private final Handler mHandler = new Handler();
+ private Runnable mRunnable;
+ private ProgressDialog mProgressDialog;
+
+ // SID and LSID retrieval process.
+ private String mSid;
+ private String mLsid;
+ private int mState; // {NONE(0), SID(1), LSID(2)}
+ private boolean mTokensInvalidated;
+
+ private GoogleAccountLogin(Activity activity, String name,
+ Runnable runnable) {
+ mActivity = activity;
+ mAccount = new Account(name, GOOGLE);
+ mWebView = new WebView(mActivity);
+ mRunnable = runnable;
+
+ mWebView.setWebViewClient(new WebViewClient() {
+ @Override
+ public boolean shouldOverrideUrlLoading(WebView view, String url) {
+ return false;
+ }
+ @Override
+ public void onPageFinished(WebView view, String url) {
+ saveLoginTime();
+ done();
+ }
+ });
+ }
+
+ private void saveLoginTime() {
+ Editor ed = PreferenceManager.
+ getDefaultSharedPreferences(mActivity).edit();
+ ed.putLong(PREF_AUTOLOGIN_TIME, System.currentTimeMillis());
+ ed.apply();
+ }
+
+ // Runnable
+ @Override
+ public void run() {
+ String url = ISSUE_AUTH_TOKEN_URL.buildUpon()
+ .appendQueryParameter("SID", mSid)
+ .appendQueryParameter("LSID", mLsid)
+ .build().toString();
+ // Check mRunnable to see if the request has been canceled. Otherwise
+ // we might access a destroyed WebView.
+ String ua = null;
+ synchronized (this) {
+ if (mRunnable == null) {
+ return;
+ }
+ ua = mWebView.getSettings().getUserAgentString();
+ }
+ // Intentionally not using Proxy.
+ AndroidHttpClient client = AndroidHttpClient.newInstance(ua);
+ HttpPost request = new HttpPost(url);
+
+ String result = null;
+ try {
+ HttpResponse response = client.execute(request);
+ int status = response.getStatusLine().getStatusCode();
+ if (status != HttpStatus.SC_OK) {
+ Log.d(LOGTAG, "LOGIN_FAIL: Bad status from auth url "
+ + status + ": "
+ + response.getStatusLine().getReasonPhrase());
+ // Invalidate the tokens once just in case the 403 was for other
+ // reasons.
+ if (status == HttpStatus.SC_FORBIDDEN && !mTokensInvalidated) {
+ Log.d(LOGTAG, "LOGIN_FAIL: Invalidating tokens...");
+ // Need to regenerate the auth tokens and try again.
+ invalidateTokens();
+ // XXX: Do not touch any more member variables from this
+ // thread as a second thread will handle the next login
+ // attempt.
+ return;
+ }
+ done();
+ return;
+ }
+ HttpEntity entity = response.getEntity();
+ if (entity == null) {
+ Log.d(LOGTAG, "LOGIN_FAIL: Null entity in response");
+ done();
+ return;
+ }
+ result = EntityUtils.toString(entity, "UTF-8");
+ } catch (Exception e) {
+ Log.d(LOGTAG, "LOGIN_FAIL: Exception acquiring uber token " + e);
+ request.abort();
+ done();
+ return;
+ } finally {
+ client.close();
+ }
+ final String newUrl = TOKEN_AUTH_URL.buildUpon()
+ .appendQueryParameter("source", "android-browser")
+ .appendQueryParameter("auth", result)
+ .appendQueryParameter("continue",
+ BrowserSettings.getFactoryResetHomeUrl(mActivity))
+ .build().toString();
+ mActivity.runOnUiThread(new Runnable() {
+ @Override public void run() {
+ // Check mRunnable in case the request has been canceled. This
+ // is most likely not necessary as run() is the only non-UI
+ // thread that calls done() but I am paranoid.
+ synchronized (GoogleAccountLogin.this) {
+ if (mRunnable == null) {
+ return;
+ }
+ mWebView.loadUrl(newUrl);
+ }
+ }
+ });
+ }
+
+ private void invalidateTokens() {
+ AccountManager am = AccountManager.get(mActivity);
+ am.invalidateAuthToken(GOOGLE, mSid);
+ am.invalidateAuthToken(GOOGLE, mLsid);
+ mTokensInvalidated = true;
+ mState = 1; // SID
+ am.getAuthToken(mAccount, "SID", null, mActivity, this, null);
+ }
+
+ // AccountManager callbacks.
+ @Override
+ public void run(AccountManagerFuture<Bundle> value) {
+ try {
+ String id = value.getResult().getString(
+ AccountManager.KEY_AUTHTOKEN);
+ switch (mState) {
+ default:
+ case 0:
+ throw new IllegalStateException(
+ "Impossible to get into this state");
+ case 1:
+ mSid = id;
+ mState = 2; // LSID
+ AccountManager.get(mActivity).getAuthToken(
+ mAccount, "LSID", null, mActivity, this, null);
+ break;
+ case 2:
+ mLsid = id;
+ new Thread(this).start();
+ break;
+ }
+ } catch (Exception e) {
+ Log.d(LOGTAG, "LOGIN_FAIL: Exception in state " + mState + " " + e);
+ // For all exceptions load the original signin page.
+ // TODO: toast login failed?
+ done();
+ }
+ }
+
+ // Start the login process if auto-login is enabled and the user is not
+ // already logged in.
+ public static void startLoginIfNeeded(Activity activity,
+ BrowserSettings settings, Runnable runnable) {
+ // Auto login not enabled?
+ if (!settings.isAutoLoginEnabled()) {
+ runnable.run();
+ return;
+ }
+
+ // No account found?
+ String account = settings.getAutoLoginAccount(activity);
+ if (account == null) {
+ runnable.run();
+ return;
+ }
+
+ // Already logged in?
+ if (isLoggedIn(activity)) {
+ runnable.run();
+ return;
+ }
+
+ GoogleAccountLogin login =
+ new GoogleAccountLogin(activity, account, runnable);
+ login.startLogin();
+ }
+
+ private void startLogin() {
+ mProgressDialog = ProgressDialog.show(mActivity,
+ mActivity.getString(R.string.pref_autologin_title),
+ mActivity.getString(R.string.pref_autologin_progress,
+ mAccount.name),
+ true /* indeterminate */,
+ true /* cancelable */,
+ this);
+ mState = 1; // SID
+ AccountManager.get(mActivity).getAuthToken(
+ mAccount, "SID", null, mActivity, this, null);
+ }
+
+ // Returns the account name passed in if the account exists, otherwise
+ // returns the default account.
+ public static String validateAccount(Context ctx, String name) {
+ Account[] accounts = getAccounts(ctx);
+ if (accounts.length == 0) {
+ return null;
+ }
+ if (name != null) {
+ // Make sure the account still exists.
+ for (Account a : accounts) {
+ if (a.name.equals(name)) {
+ return name;
+ }
+ }
+ }
+ // Return the first entry.
+ return accounts[0].name;
+ }
+
+ public static Account[] getAccounts(Context ctx) {
+ return AccountManager.get(ctx).getAccountsByType(GOOGLE);
+ }
+
+ // Checks for the presence of the SID cookie on google.com.
+ public static boolean isLoggedIn(Context ctx) {
+ // See if we last logged in less than a week ago.
+ long lastLogin = PreferenceManager.
+ getDefaultSharedPreferences(ctx).
+ getLong(PREF_AUTOLOGIN_TIME, -1);
+ if (lastLogin == -1) {
+ return false;
+ }
+ long diff = System.currentTimeMillis() - lastLogin;
+ if (diff > WEEK_IN_MILLIS) {
+ Log.d(LOGTAG, "Forcing login after " + diff + "ms");
+ return false;
+ }
+
+ // This will potentially block the UI thread but we have to have the
+ // most updated cookies.
+ // FIXME: Figure out how to avoid waiting to clear session cookies.
+ CookieManager.getInstance().waitForCookieOperationsToComplete();
+
+ // Use /a/ to grab hosted cookies as well as the base set of google.com
+ // cookies.
+ String cookies = CookieManager.getInstance().getCookie(
+ "http://www.google.com/a/");
+ if (cookies != null) {
+ StringTokenizer tokenizer = new StringTokenizer(cookies, ";");
+ while (tokenizer.hasMoreTokens()) {
+ String cookie = tokenizer.nextToken().trim();
+ if (cookie.startsWith("SID=") || cookie.startsWith("ASIDAP=")) {
+ return true;
+ }
+ }
+ }
+ return false;
+ }
+
+ // Used to indicate that the Browser should continue loading the main page.
+ // This can happen on success, error, or timeout.
+ private synchronized void done() {
+ if (mRunnable != null) {
+ Log.d(LOGTAG, "Finished login attempt for " + mAccount.name);
+ mActivity.runOnUiThread(mRunnable);
+
+ // Post a delayed message to dismiss the dialog in order to avoid a
+ // flash of the progress dialog.
+ mHandler.postDelayed(new Runnable() {
+ @Override public void run() {
+ mProgressDialog.dismiss();
+ }
+ }, 1000);
+
+ mRunnable = null;
+ mWebView.destroy();
+ }
+ }
+
+ // Called by the progress dialog on startup.
+ public void onCancel(DialogInterface unused) {
+ done();
+ }
+}
diff --git a/src/com/android/browser/HistoryItem.java b/src/com/android/browser/HistoryItem.java
index 72e1b19..8154be7 100644
--- a/src/com/android/browser/HistoryItem.java
+++ b/src/com/android/browser/HistoryItem.java
@@ -18,42 +18,36 @@
package com.android.browser;
import android.content.Context;
-import android.graphics.Bitmap;
import android.provider.Browser;
import android.view.View;
import android.widget.CompoundButton;
-import android.widget.ImageView;
-import android.widget.TextView;
+import android.widget.CompoundButton.OnCheckedChangeListener;
/**
* Layout representing a history item in the classic history viewer.
*/
-/* package */ class HistoryItem extends BookmarkItem {
+/* package */ class HistoryItem extends BookmarkItem
+ implements OnCheckedChangeListener {
private CompoundButton mStar; // Star for bookmarking
- private CompoundButton.OnCheckedChangeListener mListener;
/**
* Create a new HistoryItem.
* @param context Context for this HistoryItem.
*/
/* package */ HistoryItem(Context context) {
+ this(context, true);
+ }
+
+ /* package */ HistoryItem(Context context, boolean showStar) {
super(context);
mStar = (CompoundButton) findViewById(R.id.star);
- mStar.setVisibility(View.VISIBLE);
- mListener = new CompoundButton.OnCheckedChangeListener() {
- public void onCheckedChanged(CompoundButton buttonView,
- boolean isChecked) {
- if (isChecked) {
- Bookmarks.addBookmark(mContext,
- mContext.getContentResolver(), mUrl, getName(), null, true);
- LogTag.logBookmarkAdded(mUrl, "history");
- } else {
- Bookmarks.removeFromBookmarks(mContext,
- mContext.getContentResolver(), mUrl, getName());
- }
- }
- };
+ mStar.setOnCheckedChangeListener(this);
+ if (showStar) {
+ mStar.setVisibility(View.VISIBLE);
+ } else {
+ mStar.setVisibility(View.GONE);
+ }
}
/* package */ void copyTo(HistoryItem item) {
@@ -77,6 +71,20 @@
/* package */ void setIsBookmark(boolean isBookmark) {
mStar.setOnCheckedChangeListener(null);
mStar.setChecked(isBookmark);
- mStar.setOnCheckedChangeListener(mListener);
+ mStar.setOnCheckedChangeListener(this);
+ }
+
+ @Override
+ public void onCheckedChanged(CompoundButton buttonView,
+ boolean isChecked) {
+ if (isChecked) {
+ // Uncheck ourseves. When the bookmark is actually added,
+ // we will be notified
+ setIsBookmark(false);
+ Browser.saveBookmark(getContext(), getName(), mUrl);
+ } else {
+ Bookmarks.removeFromBookmarks(getContext(),
+ getContext().getContentResolver(), mUrl, getName());
+ }
}
}
diff --git a/src/com/android/browser/HttpAuthenticationDialog.java b/src/com/android/browser/HttpAuthenticationDialog.java
new file mode 100644
index 0000000..a9ba332
--- /dev/null
+++ b/src/com/android/browser/HttpAuthenticationDialog.java
@@ -0,0 +1,153 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.android.browser;
+
+import android.app.AlertDialog;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.WindowManager;
+import android.widget.TextView;
+
+/**
+ * HTTP authentication dialog.
+ */
+public class HttpAuthenticationDialog {
+
+ private final Context mContext;
+
+ private final String mHost;
+ private final String mRealm;
+
+ private AlertDialog mDialog;
+ private TextView mUsernameView;
+ private TextView mPasswordView;
+
+ private OkListener mOkListener;
+ private CancelListener mCancelListener;
+
+ /**
+ * Creates an HTTP authentication dialog.
+ */
+ public HttpAuthenticationDialog(Context context, String host, String realm) {
+ mContext = context;
+ mHost = host;
+ mRealm = realm;
+ createDialog();
+ }
+
+ private String getUsername() {
+ return mUsernameView.getText().toString();
+ }
+
+ private String getPassword() {
+ return mPasswordView.getText().toString();
+ }
+
+ /**
+ * Sets the listener that will be notified when the user submits the credentials.
+ */
+ public void setOkListener(OkListener okListener) {
+ mOkListener = okListener;
+ }
+
+ /**
+ * Sets the listener that will be notified when the user cancels the authentication
+ * dialog.
+ */
+ public void setCancelListener(CancelListener cancelListener) {
+ mCancelListener = cancelListener;
+ }
+
+ /**
+ * Shows the dialog.
+ */
+ public void show() {
+ mDialog.show();
+ mUsernameView.requestFocus();
+ }
+
+ /**
+ * Hides, recreates, and shows the dialog. This can be used to handle configuration changes.
+ */
+ public void reshow() {
+ String username = getUsername();
+ String password = getPassword();
+ int focusId = mDialog.getCurrentFocus().getId();
+ mDialog.dismiss();
+ createDialog();
+ mDialog.show();
+ if (username != null) {
+ mUsernameView.setText(username);
+ }
+ if (password != null) {
+ mPasswordView.setText(password);
+ }
+ if (focusId != 0) {
+ mDialog.findViewById(focusId).requestFocus();
+ } else {
+ mUsernameView.requestFocus();
+ }
+ }
+
+ private void createDialog() {
+ LayoutInflater factory = LayoutInflater.from(mContext);
+ View v = factory.inflate(R.layout.http_authentication, null);
+ mUsernameView = (TextView) v.findViewById(R.id.username_edit);
+ mPasswordView = (TextView) v.findViewById(R.id.password_edit);
+
+ String title = mContext.getText(R.string.sign_in_to).toString().replace(
+ "%s1", mHost).replace("%s2", mRealm);
+
+ mDialog = new AlertDialog.Builder(mContext)
+ .setTitle(title)
+ .setIcon(android.R.drawable.ic_dialog_alert)
+ .setView(v)
+ .setPositiveButton(R.string.action, new DialogInterface.OnClickListener() {
+ public void onClick(DialogInterface dialog, int whichButton) {
+ if (mOkListener != null) {
+ mOkListener.onOk(mHost, mRealm, getUsername(), getPassword());
+ }
+ }})
+ .setNegativeButton(R.string.cancel,new DialogInterface.OnClickListener() {
+ public void onClick(DialogInterface dialog, int whichButton) {
+ if (mCancelListener != null) mCancelListener.onCancel();
+ }})
+ .setOnCancelListener(new DialogInterface.OnCancelListener() {
+ public void onCancel(DialogInterface dialog) {
+ if (mCancelListener != null) mCancelListener.onCancel();
+ }})
+ .create();
+
+ // Make the IME appear when the dialog is displayed if applicable.
+ mDialog.getWindow().setSoftInputMode(WindowManager.LayoutParams.SOFT_INPUT_STATE_VISIBLE);
+ }
+
+ /**
+ * Interface for listeners that are notified when the user submits the credentials.
+ */
+ public interface OkListener {
+ void onOk(String host, String realm, String username, String password);
+ }
+
+ /**
+ * Interface for listeners that are notified when the user cancels the dialog.
+ */
+ public interface CancelListener {
+ void onCancel();
+ }
+}
diff --git a/src/com/android/browser/IntentHandler.java b/src/com/android/browser/IntentHandler.java
new file mode 100644
index 0000000..e17fdc5
--- /dev/null
+++ b/src/com/android/browser/IntentHandler.java
@@ -0,0 +1,359 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+
+package com.android.browser;
+
+import com.android.browser.search.SearchEngine;
+import com.android.common.Search;
+import com.android.common.speech.LoggingEvents;
+
+import android.app.Activity;
+import android.app.SearchManager;
+import android.content.ContentResolver;
+import android.content.Context;
+import android.content.Intent;
+import android.net.Uri;
+import android.os.AsyncTask;
+import android.os.Bundle;
+import android.provider.Browser;
+import android.provider.MediaStore;
+import android.speech.RecognizerResultsIntent;
+import android.text.TextUtils;
+import android.util.Patterns;
+
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.Map;
+
+/**
+ * Handle all browser related intents
+ */
+public class IntentHandler {
+
+ // "source" parameter for Google search suggested by the browser
+ final static String GOOGLE_SEARCH_SOURCE_SUGGEST = "browser-suggest";
+ // "source" parameter for Google search from unknown source
+ final static String GOOGLE_SEARCH_SOURCE_UNKNOWN = "unknown";
+
+ /* package */ static final UrlData EMPTY_URL_DATA = new UrlData(null);
+
+ private Activity mActivity;
+ private Controller mController;
+ private TabControl mTabControl;
+ private BrowserSettings mSettings;
+
+ public IntentHandler(Activity browser, Controller controller) {
+ mActivity = browser;
+ mController = controller;
+ mTabControl = mController.getTabControl();
+ mSettings = controller.getSettings();
+ }
+
+ void onNewIntent(Intent intent) {
+ Tab current = mTabControl.getCurrentTab();
+ // When a tab is closed on exit, the current tab index is set to -1.
+ // Reset before proceed as Browser requires the current tab to be set.
+ if (current == null) {
+ // Try to reset the tab in case the index was incorrect.
+ current = mTabControl.getTab(0);
+ if (current == null) {
+ // No tabs at all so just ignore this intent.
+ return;
+ }
+ mController.setActiveTab(current);
+ }
+ final String action = intent.getAction();
+ final int flags = intent.getFlags();
+ if (Intent.ACTION_MAIN.equals(action) ||
+ (flags & Intent.FLAG_ACTIVITY_LAUNCHED_FROM_HISTORY) != 0) {
+ // just resume the browser
+ return;
+ }
+ if (BrowserActivity.ACTION_SHOW_BOOKMARKS.equals(action)) {
+ mController.bookmarksOrHistoryPicker(false);
+ return;
+ }
+ mController.removeComboView();
+
+ // In case the SearchDialog is open.
+ ((SearchManager) mActivity.getSystemService(Context.SEARCH_SERVICE))
+ .stopSearch();
+ boolean activateVoiceSearch = RecognizerResultsIntent
+ .ACTION_VOICE_SEARCH_RESULTS.equals(action);
+ if (Intent.ACTION_VIEW.equals(action)
+ || Intent.ACTION_SEARCH.equals(action)
+ || MediaStore.INTENT_ACTION_MEDIA_SEARCH.equals(action)
+ || Intent.ACTION_WEB_SEARCH.equals(action)
+ || activateVoiceSearch) {
+ if (current.isInVoiceSearchMode()) {
+ String title = current.getVoiceDisplayTitle();
+ if (title != null && title.equals(intent.getStringExtra(
+ SearchManager.QUERY))) {
+ // The user submitted the same search as the last voice
+ // search, so do nothing.
+ return;
+ }
+ if (Intent.ACTION_SEARCH.equals(action)
+ && current.voiceSearchSourceIsGoogle()) {
+ Intent logIntent = new Intent(
+ LoggingEvents.ACTION_LOG_EVENT);
+ logIntent.putExtra(LoggingEvents.EXTRA_EVENT,
+ LoggingEvents.VoiceSearch.QUERY_UPDATED);
+ logIntent.putExtra(
+ LoggingEvents.VoiceSearch.EXTRA_QUERY_UPDATED_VALUE,
+ intent.getDataString());
+ mActivity.sendBroadcast(logIntent);
+ // Note, onPageStarted will revert the voice title bar
+ // When http://b/issue?id=2379215 is fixed, we should update
+ // the title bar here.
+ }
+ }
+ // If this was a search request (e.g. search query directly typed into the address bar),
+ // pass it on to the default web search provider.
+ if (handleWebSearchIntent(mActivity, mController, intent)) {
+ return;
+ }
+
+ UrlData urlData = getUrlDataFromIntent(intent);
+ if (urlData.isEmpty()) {
+ urlData = new UrlData(mSettings.getHomePage());
+ }
+
+ final String appId = intent
+ .getStringExtra(Browser.EXTRA_APPLICATION_ID);
+ if ((Intent.ACTION_VIEW.equals(action)
+ // If a voice search has no appId, it means that it came
+ // from the browser. In that case, reuse the current tab.
+ || (activateVoiceSearch && appId != null))
+ && !mActivity.getPackageName().equals(appId)
+ && (flags & Intent.FLAG_ACTIVITY_BROUGHT_TO_FRONT) != 0) {
+ Tab appTab = mTabControl.getTabFromId(appId);
+ if (appTab != null) {
+ mController.reuseTab(appTab, appId, urlData);
+ return;
+ } else {
+ // No matching application tab, try to find a regular tab
+ // with a matching url.
+ appTab = mTabControl.findUnusedTabWithUrl(urlData.mUrl);
+ if (appTab != null) {
+ if (current != appTab) {
+ mController.switchToTab(mTabControl.getTabIndex(appTab));
+ }
+ // Otherwise, we are already viewing the correct tab.
+ } else {
+ // if FLAG_ACTIVITY_BROUGHT_TO_FRONT flag is on, the url
+ // will be opened in a new tab unless we have reached
+ // MAX_TABS. Then the url will be opened in the current
+ // tab. If a new tab is created, it will have "true" for
+ // exit on close.
+ mController.openTabAndShow(null, urlData, true, appId);
+ }
+ }
+ } else {
+ if (!urlData.isEmpty()
+ && urlData.mUrl.startsWith("about:debug")) {
+ if ("about:debug.dom".equals(urlData.mUrl)) {
+ current.getWebView().dumpDomTree(false);
+ } else if ("about:debug.dom.file".equals(urlData.mUrl)) {
+ current.getWebView().dumpDomTree(true);
+ } else if ("about:debug.render".equals(urlData.mUrl)) {
+ current.getWebView().dumpRenderTree(false);
+ } else if ("about:debug.render.file".equals(urlData.mUrl)) {
+ current.getWebView().dumpRenderTree(true);
+ } else if ("about:debug.display".equals(urlData.mUrl)) {
+ current.getWebView().dumpDisplayTree();
+ } else if ("about:debug.nav".equals(urlData.mUrl)) {
+ current.getWebView().debugDump();
+ } else {
+ mSettings.toggleDebugSettings(mActivity);
+ }
+ return;
+ }
+ // Get rid of the subwindow if it exists
+ mController.dismissSubWindow(current);
+ // If the current Tab is being used as an application tab,
+ // remove the association, since the new Intent means that it is
+ // no longer associated with that application.
+ current.setAppId(null);
+ mController.loadUrlDataIn(current, urlData);
+ }
+ }
+ }
+
+ protected UrlData getUrlDataFromIntent(Intent intent) {
+ String url = "";
+ Map<String, String> headers = null;
+ if (intent != null
+ && (intent.getFlags() & Intent.FLAG_ACTIVITY_LAUNCHED_FROM_HISTORY) == 0) {
+ final String action = intent.getAction();
+ if (Intent.ACTION_VIEW.equals(action)) {
+ url = UrlUtils.smartUrlFilter(intent.getData());
+ if (url != null && url.startsWith("http")) {
+ final Bundle pairs = intent
+ .getBundleExtra(Browser.EXTRA_HEADERS);
+ if (pairs != null && !pairs.isEmpty()) {
+ Iterator<String> iter = pairs.keySet().iterator();
+ headers = new HashMap<String, String>();
+ while (iter.hasNext()) {
+ String key = iter.next();
+ headers.put(key, pairs.getString(key));
+ }
+ }
+ }
+ } else if (Intent.ACTION_SEARCH.equals(action)
+ || MediaStore.INTENT_ACTION_MEDIA_SEARCH.equals(action)
+ || Intent.ACTION_WEB_SEARCH.equals(action)) {
+ url = intent.getStringExtra(SearchManager.QUERY);
+ if (url != null) {
+ // In general, we shouldn't modify URL from Intent.
+ // But currently, we get the user-typed URL from search box as well.
+ url = UrlUtils.fixUrl(url);
+ url = UrlUtils.smartUrlFilter(url);
+ String searchSource = "&source=android-" + GOOGLE_SEARCH_SOURCE_SUGGEST + "&";
+ if (url.contains(searchSource)) {
+ String source = null;
+ final Bundle appData = intent.getBundleExtra(SearchManager.APP_DATA);
+ if (appData != null) {
+ source = appData.getString(Search.SOURCE);
+ }
+ if (TextUtils.isEmpty(source)) {
+ source = GOOGLE_SEARCH_SOURCE_UNKNOWN;
+ }
+ url = url.replace(searchSource, "&source=android-"+source+"&");
+ }
+ }
+ }
+ }
+ return new UrlData(url, headers, intent);
+ }
+
+ /**
+ * Launches the default web search activity with the query parameters if the given intent's data
+ * are identified as plain search terms and not URLs/shortcuts.
+ * @return true if the intent was handled and web search activity was launched, false if not.
+ */
+ static boolean handleWebSearchIntent(Activity activity,
+ Controller controller, Intent intent) {
+ if (intent == null) return false;
+
+ String url = null;
+ final String action = intent.getAction();
+ if (RecognizerResultsIntent.ACTION_VOICE_SEARCH_RESULTS.equals(
+ action)) {
+ return false;
+ }
+ if (Intent.ACTION_VIEW.equals(action)) {
+ Uri data = intent.getData();
+ if (data != null) url = data.toString();
+ } else if (Intent.ACTION_SEARCH.equals(action)
+ || MediaStore.INTENT_ACTION_MEDIA_SEARCH.equals(action)
+ || Intent.ACTION_WEB_SEARCH.equals(action)) {
+ url = intent.getStringExtra(SearchManager.QUERY);
+ }
+ return handleWebSearchRequest(activity, controller, url,
+ intent.getBundleExtra(SearchManager.APP_DATA),
+ intent.getStringExtra(SearchManager.EXTRA_DATA_KEY));
+ }
+
+ /**
+ * Launches the default web search activity with the query parameters if the given url string
+ * was identified as plain search terms and not URL/shortcut.
+ * @return true if the request was handled and web search activity was launched, false if not.
+ */
+ private static boolean handleWebSearchRequest(Activity activity,
+ Controller controller, String inUrl, Bundle appData,
+ String extraData) {
+ if (inUrl == null) return false;
+
+ // In general, we shouldn't modify URL from Intent.
+ // But currently, we get the user-typed URL from search box as well.
+ String url = UrlUtils.fixUrl(inUrl).trim();
+ if (TextUtils.isEmpty(url)) return false;
+
+ // URLs are handled by the regular flow of control, so
+ // return early.
+ if (Patterns.WEB_URL.matcher(url).matches()
+ || UrlUtils.ACCEPTED_URI_SCHEMA.matcher(url).matches()) {
+ return false;
+ }
+
+ final ContentResolver cr = activity.getContentResolver();
+ final String newUrl = url;
+ if (controller == null || controller.getTabControl() == null
+ || controller.getTabControl().getCurrentWebView() == null
+ || !controller.getTabControl().getCurrentWebView()
+ .isPrivateBrowsingEnabled()) {
+ new AsyncTask<Void, Void, Void>() {
+ @Override
+ protected Void doInBackground(Void... unused) {
+ Browser.addSearchUrl(cr, newUrl);
+ return null;
+ }
+ }.execute();
+ }
+
+ SearchEngine searchEngine = BrowserSettings.getInstance().getSearchEngine();
+ if (searchEngine == null) return false;
+ searchEngine.startSearch(activity, url, appData, extraData);
+
+ return true;
+ }
+
+ /**
+ * A UrlData class to abstract how the content will be set to WebView.
+ * This base class uses loadUrl to show the content.
+ */
+ static class UrlData {
+ final String mUrl;
+ final Map<String, String> mHeaders;
+ final Intent mVoiceIntent;
+
+ UrlData(String url) {
+ this.mUrl = url;
+ this.mHeaders = null;
+ this.mVoiceIntent = null;
+ }
+
+ UrlData(String url, Map<String, String> headers, Intent intent) {
+ this.mUrl = url;
+ this.mHeaders = headers;
+ if (RecognizerResultsIntent.ACTION_VOICE_SEARCH_RESULTS
+ .equals(intent.getAction())) {
+ this.mVoiceIntent = intent;
+ } else {
+ this.mVoiceIntent = null;
+ }
+ }
+
+ boolean isEmpty() {
+ return mVoiceIntent == null && (mUrl == null || mUrl.length() == 0);
+ }
+
+ /**
+ * Load this UrlData into the given Tab. Use loadUrlDataIn to update
+ * the title bar as well.
+ */
+ public void loadIn(Tab t) {
+ if (mVoiceIntent != null) {
+ t.activateVoiceSearchMode(mVoiceIntent);
+ } else {
+ t.getWebView().loadUrl(mUrl, mHeaders);
+ }
+ }
+ }
+
+}
diff --git a/src/com/android/browser/MeshTracker.java b/src/com/android/browser/MeshTracker.java
deleted file mode 100644
index c4b6332..0000000
--- a/src/com/android/browser/MeshTracker.java
+++ /dev/null
@@ -1,198 +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.browser;
-
-import android.graphics.Bitmap;
-import android.graphics.utils.BoundaryPatch;
-import android.graphics.Canvas;
-import android.graphics.Paint;
-import android.webkit.WebView;
-
-/*package*/ class MeshTracker extends WebView.DragTracker {
-
- private static class Mesh {
- private int mWhich;
- private int mRows;
- private int mCols;
- private BoundaryPatch mPatch = new BoundaryPatch();
- private float[] mCubics = new float[24];
- private float[] mOrig = new float[24];
- private float mStretchX, mStretchY;
-
- Mesh(int which, int rows, int cols) {
- mWhich = which;
- mRows = rows;
- mCols = cols;
- }
-
- private void rebuildPatch() {
- mPatch.setCubicBoundary(mCubics, 0, mRows, mCols);
- }
-
- private void setSize(float w, float h) {
- float[] pts = mCubics;
- float x1 = w*0.3333f;
- float y1 = h*0.3333f;
- float x2 = w*0.6667f;
- float y2 = h*0.6667f;
- pts[0*2+0] = 0; pts[0*2+1] = 0;
- pts[1*2+0] = x1; pts[1*2+1] = 0;
- pts[2*2+0] = x2; pts[2*2+1] = 0;
-
- pts[3*2+0] = w; pts[3*2+1] = 0;
- pts[4*2+0] = w; pts[4*2+1] = y1;
- pts[5*2+0] = w; pts[5*2+1] = y2;
-
- pts[6*2+0] = w; pts[6*2+1] = h;
- pts[7*2+0] = x2; pts[7*2+1] = h;
- pts[8*2+0] = x1; pts[8*2+1] = h;
-
- pts[9*2+0] = 0; pts[9*2+1] = h;
- pts[10*2+0] = 0; pts[10*2+1] = y2;
- pts[11*2+0] = 0; pts[11*2+1] = y1;
-
- System.arraycopy(pts, 0, mOrig, 0, 24);
-
- // recall our stretcher
- setStretch(mStretchX, mStretchY);
- }
-
- public void setBitmap(Bitmap bm) {
- mPatch.setTexture(bm);
- setSize(bm.getWidth(), bm.getHeight());
- }
-
- // first experimental behavior
- private void doit1(float dx, float dy) {
- final float scale = 0.75f; // temper how far we actually move
- dx *= scale;
- dy *= scale;
-
- int index;
- if (dx < 0) {
- index = 10;
- } else {
- index = 4;
- }
- mCubics[index*2 + 0] = mOrig[index*2 + 0] + dx;
- mCubics[index*2 + 2] = mOrig[index*2 + 2] + dx;
-
- if (dy < 0) {
- index = 1;
- } else {
- index = 7;
- }
- mCubics[index*2 + 1] = mOrig[index*2 + 1] + dy;
- mCubics[index*2 + 3] = mOrig[index*2 + 3] + dy;
- }
-
- private void doit2(float dx, float dy) {
- final float scale = 0.35f; // temper how far we actually move
- dx *= scale;
- dy *= scale;
- final float cornerScale = 0.25f;
-
- int index;
- if (dx < 0) {
- index = 4;
- } else {
- index = 10;
- }
- mCubics[index*2 + 0] = mOrig[index*2 + 0] + dx;
- mCubics[index*2 + 2] = mOrig[index*2 + 2] + dx;
- // corners
- index -= 1;
- mCubics[index*2 + 0] = mOrig[index*2 + 0] + dx * cornerScale;
- index = (index + 3) % 12; // next corner
- mCubics[index*2 + 0] = mOrig[index*2 + 0] + dx * cornerScale;
-
- if (dy < 0) {
- index = 7;
- } else {
- index = 1;
- }
- mCubics[index*2 + 1] = mOrig[index*2 + 1] + dy;
- mCubics[index*2 + 3] = mOrig[index*2 + 3] + dy;
- // corners
- index -= 1;
- mCubics[index*2 + 1] = mOrig[index*2 + 1] + dy * cornerScale;
- index = (index + 3) % 12; // next corner
- mCubics[index*2 + 1] = mOrig[index*2 + 1] + dy * cornerScale;
- }
-
- public void setStretch(float dx, float dy) {
- mStretchX = dx;
- mStretchY = dy;
- switch (mWhich) {
- case 1:
- doit1(dx, dy);
- break;
- case 2:
- doit2(dx, dy);
- break;
- }
- rebuildPatch();
- }
-
- public void draw(Canvas canvas) {
- mPatch.draw(canvas);
- }
- }
-
- private Mesh mMesh;
- private Bitmap mBitmap;
- private int mWhich;
- private Paint mBGPaint;
-
- public MeshTracker(int which) {
- mWhich = which;
- }
-
- public void setBGPaint(Paint paint) {
- mBGPaint = paint;
- }
-
- @Override public void onStartDrag(float x, float y) {
- mMesh = new Mesh(mWhich, 16, 16);
- }
-
- @Override public void onBitmapChange(Bitmap bm) {
- mBitmap = bm;
- mMesh.setBitmap(bm);
- }
-
- @Override public boolean onStretchChange(float sx, float sy) {
- mMesh.setStretch(-sx, -sy);
- return true;
- }
-
- @Override public void onStopDrag() {
- mMesh = null;
- }
-
- @Override public void onDraw(Canvas canvas) {
- if (mWhich == 2) {
- if (mBGPaint != null) {
- canvas.drawPaint(mBGPaint);
- } else {
- canvas.drawColor(0xFF000000);
- }
- }
- mMesh.draw(canvas);
- }
-}
-
diff --git a/src/com/android/browser/NetworkStateHandler.java b/src/com/android/browser/NetworkStateHandler.java
new file mode 100644
index 0000000..37f4a2f
--- /dev/null
+++ b/src/com/android/browser/NetworkStateHandler.java
@@ -0,0 +1,143 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.app.Activity;
+import android.app.AlertDialog;
+import android.content.BroadcastReceiver;
+import android.content.Context;
+import android.content.Intent;
+import android.content.IntentFilter;
+import android.net.ConnectivityManager;
+import android.net.NetworkInfo;
+import android.webkit.WebView;
+
+/**
+ * Handle network state changes
+ */
+public class NetworkStateHandler {
+
+ Activity mActivity;
+ Controller mController;
+
+ // monitor platform changes
+ private IntentFilter mNetworkStateChangedFilter;
+ private BroadcastReceiver mNetworkStateIntentReceiver;
+ private boolean mIsNetworkUp;
+
+ /* hold a ref so we can auto-cancel if necessary */
+ private AlertDialog mAlertDialog;
+
+ public NetworkStateHandler(Activity activity, Controller controller) {
+ mActivity = activity;
+ mController = controller;
+ // Find out if the network is currently up.
+ ConnectivityManager cm = (ConnectivityManager) mActivity
+ .getSystemService(Context.CONNECTIVITY_SERVICE);
+ NetworkInfo info = cm.getActiveNetworkInfo();
+ if (info != null) {
+ mIsNetworkUp = info.isAvailable();
+ }
+
+ /*
+ * enables registration for changes in network status from http stack
+ */
+ mNetworkStateChangedFilter = new IntentFilter();
+ mNetworkStateChangedFilter.addAction(
+ ConnectivityManager.CONNECTIVITY_ACTION);
+ mNetworkStateIntentReceiver = new BroadcastReceiver() {
+ @Override
+ public void onReceive(Context context, Intent intent) {
+ if (intent.getAction().equals(
+ ConnectivityManager.CONNECTIVITY_ACTION)) {
+
+ NetworkInfo info = intent.getParcelableExtra(
+ ConnectivityManager.EXTRA_NETWORK_INFO);
+ String typeName = info.getTypeName();
+ String subtypeName = info.getSubtypeName();
+ sendNetworkType(typeName.toLowerCase(),
+ (subtypeName != null ? subtypeName.toLowerCase() : ""));
+
+ boolean noConnection = intent.getBooleanExtra(
+ ConnectivityManager.EXTRA_NO_CONNECTIVITY, false);
+
+ onNetworkToggle(!noConnection);
+ }
+ }
+ };
+
+ }
+
+ void onPause() {
+ // unregister network state listener
+ mActivity.unregisterReceiver(mNetworkStateIntentReceiver);
+ }
+
+ void onResume() {
+ mActivity.registerReceiver(mNetworkStateIntentReceiver,
+ mNetworkStateChangedFilter);
+ }
+
+ /**
+ * connectivity manager says net has come or gone... inform the user
+ * @param up true if net has come up, false if net has gone down
+ */
+ void onNetworkToggle(boolean up) {
+ if (up == mIsNetworkUp) {
+ return;
+ } else if (up) {
+ mIsNetworkUp = true;
+ if (mAlertDialog != null) {
+ mAlertDialog.cancel();
+ mAlertDialog = null;
+ }
+ } else {
+ mIsNetworkUp = false;
+ if (mController.isInLoad()) {
+ createAndShowNetworkDialog();
+ }
+ }
+ WebView w = mController.getCurrentWebView();
+ if (w != null) {
+ w.setNetworkAvailable(up);
+ }
+ }
+
+ boolean isNetworkUp() {
+ return mIsNetworkUp;
+ }
+
+ // This method shows the network dialog alerting the user that the net is
+ // down. It will only show the dialog if mAlertDialog is null.
+ void createAndShowNetworkDialog() {
+ if (mAlertDialog == null) {
+ mAlertDialog = new AlertDialog.Builder(mActivity)
+ .setTitle(R.string.loadSuspendedTitle)
+ .setMessage(R.string.loadSuspended)
+ .setPositiveButton(R.string.ok, null)
+ .show();
+ }
+ }
+
+ private void sendNetworkType(String type, String subtype) {
+ WebView w = mController.getCurrentWebView();
+ if (w != null) {
+ w.setNetworkType(type, subtype);
+ }
+ }
+
+}
diff --git a/src/com/android/browser/OpenDownloadReceiver.java b/src/com/android/browser/OpenDownloadReceiver.java
index 99e5f41..4277ff4 100644
--- a/src/com/android/browser/OpenDownloadReceiver.java
+++ b/src/com/android/browser/OpenDownloadReceiver.java
@@ -19,15 +19,11 @@
import android.app.DownloadManager;
import android.content.ActivityNotFoundException;
import android.content.BroadcastReceiver;
-import android.content.ContentResolver;
import android.content.Context;
import android.content.Intent;
-import android.database.Cursor;
import android.net.Uri;
-import android.provider.Downloads;
-import android.widget.Toast;
-
-import java.io.File;
+import android.os.Handler;
+import android.os.HandlerThread;
/**
* This {@link BroadcastReceiver} handles clicks to notifications that
@@ -36,49 +32,63 @@
* a complete, successful download will open the file.
*/
public class OpenDownloadReceiver extends BroadcastReceiver {
- public void onReceive(Context context, Intent intent) {
- ContentResolver cr = context.getContentResolver();
- Uri data = intent.getData();
- Cursor cursor = null;
- try {
- cursor = cr.query(data,
- new String[] { Downloads.Impl._ID, Downloads.Impl._DATA,
- Downloads.Impl.COLUMN_MIME_TYPE, Downloads.COLUMN_STATUS },
- null, null, null);
- if (cursor.moveToFirst()) {
- String filename = cursor.getString(1);
- String mimetype = cursor.getString(2);
- String action = intent.getAction();
- if (Downloads.ACTION_NOTIFICATION_CLICKED.equals(action)) {
- int status = cursor.getInt(3);
- if (Downloads.isStatusCompleted(status)
- && Downloads.isStatusSuccess(status)) {
- Intent launchIntent = new Intent(Intent.ACTION_VIEW);
- Uri path = Uri.parse(filename);
- // If there is no scheme, then it must be a file
- if (path.getScheme() == null) {
- path = Uri.fromFile(new File(filename));
- }
- launchIntent.setDataAndType(path, mimetype);
- launchIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
- try {
- context.startActivity(launchIntent);
- } catch (ActivityNotFoundException ex) {
- Toast.makeText(context,
- R.string.download_no_application_title,
- Toast.LENGTH_LONG).show();
- }
- } else {
- // Open the downloads page
- Intent pageView = new Intent(
- DownloadManager.ACTION_VIEW_DOWNLOADS);
- pageView.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
- context.startActivity(pageView);
- }
- }
- }
- } finally {
- if (cursor != null) cursor.close();
+ private static Handler sAsyncHandler;
+ static {
+ HandlerThread thr = new HandlerThread("Open browser download async");
+ thr.start();
+ sAsyncHandler = new Handler(thr.getLooper());
+ }
+ @Override
+ public void onReceive(final Context context, Intent intent) {
+ String action = intent.getAction();
+ if (!DownloadManager.ACTION_NOTIFICATION_CLICKED.equals(action)) {
+ openDownloadsPage(context);
+ return;
}
+ long ids[] = intent.getLongArrayExtra(
+ DownloadManager.EXTRA_NOTIFICATION_CLICK_DOWNLOAD_IDS);
+ if (ids == null || ids.length == 0) {
+ openDownloadsPage(context);
+ return;
+ }
+ final long id = ids[0];
+ final PendingResult result = goAsync();
+ Runnable worker = new Runnable() {
+ @Override
+ public void run() {
+ onReceiveAsync(context, id);
+ result.finish();
+ }
+ };
+ sAsyncHandler.post(worker);
+ }
+
+ private void onReceiveAsync(Context context, long id) {
+ DownloadManager manager = (DownloadManager) context.getSystemService(
+ Context.DOWNLOAD_SERVICE);
+ Uri uri = manager.getUriForDownloadedFile(id);
+ if (uri == null) {
+ // Open the downloads page
+ openDownloadsPage(context);
+ } else {
+ Intent launchIntent = new Intent(Intent.ACTION_VIEW);
+ launchIntent.setDataAndType(uri, manager.getMimeTypeForDownloadedFile(id));
+ launchIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+ try {
+ context.startActivity(launchIntent);
+ } catch (ActivityNotFoundException e) {
+ openDownloadsPage(context);
+ }
+ }
+ }
+
+ /**
+ * Open the Activity which shows a list of all downloads.
+ * @param context
+ */
+ private void openDownloadsPage(Context context) {
+ Intent pageView = new Intent(DownloadManager.ACTION_VIEW_DOWNLOADS);
+ pageView.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
+ context.startActivity(pageView);
}
}
diff --git a/src/com/android/browser/OptionsMenuHandler.java b/src/com/android/browser/OptionsMenuHandler.java
new file mode 100644
index 0000000..d602c7d
--- /dev/null
+++ b/src/com/android/browser/OptionsMenuHandler.java
@@ -0,0 +1,27 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.view.Menu;
+import android.view.MenuItem;
+
+public interface OptionsMenuHandler {
+
+ boolean onCreateOptionsMenu(Menu menu);
+ boolean onPrepareOptionsMenu(Menu menu);
+ boolean onOptionsItemSelected(MenuItem item);
+}
diff --git a/src/com/android/browser/PageDialogsHandler.java b/src/com/android/browser/PageDialogsHandler.java
new file mode 100644
index 0000000..2dbddf3
--- /dev/null
+++ b/src/com/android/browser/PageDialogsHandler.java
@@ -0,0 +1,453 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.app.AlertDialog;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.content.res.Configuration;
+import android.net.http.SslCertificate;
+import android.net.http.SslError;
+import android.text.format.DateFormat;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.webkit.HttpAuthHandler;
+import android.webkit.SslErrorHandler;
+import android.webkit.WebView;
+import android.widget.LinearLayout;
+import android.widget.TextView;
+
+import java.util.Date;
+
+/**
+ * Displays page info
+ *
+ */
+public class PageDialogsHandler {
+
+ private Context mContext;
+ private Controller mController;
+ private boolean mPageInfoFromShowSSLCertificateOnError;
+ private Tab mPageInfoView;
+ private AlertDialog mPageInfoDialog;
+
+ // as SSLCertificateOnError has different style for landscape / portrait,
+ // we have to re-open it when configuration changed
+ private AlertDialog mSSLCertificateOnErrorDialog;
+ private WebView mSSLCertificateOnErrorView;
+ private SslErrorHandler mSSLCertificateOnErrorHandler;
+ private SslError mSSLCertificateOnErrorError;
+
+ // as SSLCertificate has different style for landscape / portrait, we
+ // have to re-open it when configuration changed
+ private AlertDialog mSSLCertificateDialog;
+ private Tab mSSLCertificateView;
+ private HttpAuthenticationDialog mHttpAuthenticationDialog;
+
+ public PageDialogsHandler(Context context, Controller controller) {
+ mContext = context;
+ mController = controller;
+ }
+
+ public void onConfigurationChanged(Configuration config) {
+ if (mPageInfoDialog != null) {
+ mPageInfoDialog.dismiss();
+ showPageInfo(mPageInfoView, mPageInfoFromShowSSLCertificateOnError);
+ }
+ if (mSSLCertificateDialog != null) {
+ mSSLCertificateDialog.dismiss();
+ showSSLCertificate(mSSLCertificateView);
+ }
+ if (mSSLCertificateOnErrorDialog != null) {
+ mSSLCertificateOnErrorDialog.dismiss();
+ showSSLCertificateOnError(mSSLCertificateOnErrorView, mSSLCertificateOnErrorHandler,
+ mSSLCertificateOnErrorError);
+ }
+ if (mHttpAuthenticationDialog != null) {
+ mHttpAuthenticationDialog.reshow();
+ }
+ }
+
+ /**
+ * Displays an http-authentication dialog.
+ */
+ void showHttpAuthentication(final Tab tab, final HttpAuthHandler handler, String host, String realm) {
+ mHttpAuthenticationDialog = new HttpAuthenticationDialog(mContext, host, realm);
+ mHttpAuthenticationDialog.setOkListener(new HttpAuthenticationDialog.OkListener() {
+ public void onOk(String host, String realm, String username, String password) {
+ setHttpAuthUsernamePassword(host, realm, username, password);
+ handler.proceed(username, password);
+ mHttpAuthenticationDialog = null;
+ }
+ });
+ mHttpAuthenticationDialog.setCancelListener(new HttpAuthenticationDialog.CancelListener() {
+ public void onCancel() {
+ handler.cancel();
+ mController.onUpdatedLockIcon(tab);
+ mHttpAuthenticationDialog = null;
+ }
+ });
+ mHttpAuthenticationDialog.show();
+ }
+
+ /**
+ * Set HTTP authentication password.
+ *
+ * @param host The host for the password
+ * @param realm The realm for the password
+ * @param username The username for the password. If it is null, it means
+ * password can't be saved.
+ * @param password The password
+ */
+ public void setHttpAuthUsernamePassword(String host, String realm,
+ String username,
+ String password) {
+ WebView w = mController.getCurrentTopWebView();
+ if (w != null) {
+ w.setHttpAuthUsernamePassword(host, realm, username, password);
+ }
+ }
+
+ /**
+ * Displays a page-info dialog.
+ * @param tab The tab to show info about
+ * @param fromShowSSLCertificateOnError The flag that indicates whether
+ * this dialog was opened from the SSL-certificate-on-error dialog or
+ * not. This is important, since we need to know whether to return to
+ * the parent dialog or simply dismiss.
+ */
+ void showPageInfo(final Tab tab,
+ final boolean fromShowSSLCertificateOnError) {
+ final LayoutInflater factory = LayoutInflater.from(mContext);
+
+ final View pageInfoView = factory.inflate(R.layout.page_info, null);
+
+ final WebView view = tab.getWebView();
+
+ String url = tab.getUrl();
+ String title = tab.getTitle();
+
+ if (url == null) {
+ url = "";
+ }
+ if (title == null) {
+ title = "";
+ }
+
+ ((TextView) pageInfoView.findViewById(R.id.address)).setText(url);
+ ((TextView) pageInfoView.findViewById(R.id.title)).setText(title);
+
+ mPageInfoView = tab;
+ mPageInfoFromShowSSLCertificateOnError = fromShowSSLCertificateOnError;
+
+ AlertDialog.Builder alertDialogBuilder =
+ new AlertDialog.Builder(mContext)
+ .setTitle(R.string.page_info)
+ .setIcon(android.R.drawable.ic_dialog_info)
+ .setView(pageInfoView)
+ .setPositiveButton(
+ R.string.ok,
+ new DialogInterface.OnClickListener() {
+ public void onClick(DialogInterface dialog,
+ int whichButton) {
+ mPageInfoDialog = null;
+ mPageInfoView = null;
+
+ // if we came here from the SSL error dialog
+ if (fromShowSSLCertificateOnError) {
+ // go back to the SSL error dialog
+ showSSLCertificateOnError(
+ mSSLCertificateOnErrorView,
+ mSSLCertificateOnErrorHandler,
+ mSSLCertificateOnErrorError);
+ }
+ }
+ })
+ .setOnCancelListener(
+ new DialogInterface.OnCancelListener() {
+ public void onCancel(DialogInterface dialog) {
+ mPageInfoDialog = null;
+ mPageInfoView = null;
+
+ // if we came here from the SSL error dialog
+ if (fromShowSSLCertificateOnError) {
+ // go back to the SSL error dialog
+ showSSLCertificateOnError(
+ mSSLCertificateOnErrorView,
+ mSSLCertificateOnErrorHandler,
+ mSSLCertificateOnErrorError);
+ }
+ }
+ });
+
+ // if we have a main top-level page SSL certificate set or a certificate
+ // error
+ if (fromShowSSLCertificateOnError ||
+ (view != null && view.getCertificate() != null)) {
+ // add a 'View Certificate' button
+ alertDialogBuilder.setNeutralButton(
+ R.string.view_certificate,
+ new DialogInterface.OnClickListener() {
+ public void onClick(DialogInterface dialog,
+ int whichButton) {
+ mPageInfoDialog = null;
+ mPageInfoView = null;
+
+ // if we came here from the SSL error dialog
+ if (fromShowSSLCertificateOnError) {
+ // go back to the SSL error dialog
+ showSSLCertificateOnError(
+ mSSLCertificateOnErrorView,
+ mSSLCertificateOnErrorHandler,
+ mSSLCertificateOnErrorError);
+ } else {
+ // otherwise, display the top-most certificate from
+ // the chain
+ if (view.getCertificate() != null) {
+ showSSLCertificate(tab);
+ }
+ }
+ }
+ });
+ }
+
+ mPageInfoDialog = alertDialogBuilder.show();
+ }
+
+ /**
+ * Displays the main top-level page SSL certificate dialog
+ * (accessible from the Page-Info dialog).
+ * @param tab The tab to show certificate for.
+ */
+ private void showSSLCertificate(final Tab tab) {
+ final View certificateView =
+ inflateCertificateView(tab.getWebView().getCertificate());
+ if (certificateView == null) {
+ return;
+ }
+
+ LayoutInflater factory = LayoutInflater.from(mContext);
+
+ final LinearLayout placeholder =
+ (LinearLayout)certificateView.findViewById(R.id.placeholder);
+
+ LinearLayout ll = (LinearLayout) factory.inflate(
+ R.layout.ssl_success, placeholder);
+ ((TextView)ll.findViewById(R.id.success))
+ .setText(R.string.ssl_certificate_is_valid);
+
+ mSSLCertificateView = tab;
+ mSSLCertificateDialog =
+ new AlertDialog.Builder(mContext)
+ .setTitle(R.string.ssl_certificate).setIcon(
+ R.drawable.ic_dialog_browser_certificate_secure)
+ .setView(certificateView)
+ .setPositiveButton(R.string.ok,
+ new DialogInterface.OnClickListener() {
+ public void onClick(DialogInterface dialog,
+ int whichButton) {
+ mSSLCertificateDialog = null;
+ mSSLCertificateView = null;
+
+ showPageInfo(tab, false);
+ }
+ })
+ .setOnCancelListener(
+ new DialogInterface.OnCancelListener() {
+ public void onCancel(DialogInterface dialog) {
+ mSSLCertificateDialog = null;
+ mSSLCertificateView = null;
+
+ showPageInfo(tab, false);
+ }
+ })
+ .show();
+ }
+
+ /**
+ * Displays the SSL error certificate dialog.
+ * @param view The target web-view.
+ * @param handler The SSL error handler responsible for cancelling the
+ * connection that resulted in an SSL error or proceeding per user request.
+ * @param error The SSL error object.
+ */
+ void showSSLCertificateOnError(
+ final WebView view, final SslErrorHandler handler,
+ final SslError error) {
+
+ final View certificateView =
+ inflateCertificateView(error.getCertificate());
+ if (certificateView == null) {
+ return;
+ }
+
+ LayoutInflater factory = LayoutInflater.from(mContext);
+
+ final LinearLayout placeholder =
+ (LinearLayout)certificateView.findViewById(R.id.placeholder);
+
+ if (error.hasError(SslError.SSL_UNTRUSTED)) {
+ LinearLayout ll = (LinearLayout)factory
+ .inflate(R.layout.ssl_warning, placeholder);
+ ((TextView)ll.findViewById(R.id.warning))
+ .setText(R.string.ssl_untrusted);
+ }
+
+ if (error.hasError(SslError.SSL_IDMISMATCH)) {
+ LinearLayout ll = (LinearLayout)factory
+ .inflate(R.layout.ssl_warning, placeholder);
+ ((TextView)ll.findViewById(R.id.warning))
+ .setText(R.string.ssl_mismatch);
+ }
+
+ if (error.hasError(SslError.SSL_EXPIRED)) {
+ LinearLayout ll = (LinearLayout)factory
+ .inflate(R.layout.ssl_warning, placeholder);
+ ((TextView)ll.findViewById(R.id.warning))
+ .setText(R.string.ssl_expired);
+ }
+
+ if (error.hasError(SslError.SSL_NOTYETVALID)) {
+ LinearLayout ll = (LinearLayout)factory
+ .inflate(R.layout.ssl_warning, placeholder);
+ ((TextView)ll.findViewById(R.id.warning))
+ .setText(R.string.ssl_not_yet_valid);
+ }
+
+ mSSLCertificateOnErrorHandler = handler;
+ mSSLCertificateOnErrorView = view;
+ mSSLCertificateOnErrorError = error;
+ mSSLCertificateOnErrorDialog =
+ new AlertDialog.Builder(mContext)
+ .setTitle(R.string.ssl_certificate).setIcon(
+ R.drawable.ic_dialog_browser_certificate_partially_secure)
+ .setView(certificateView)
+ .setPositiveButton(R.string.ok,
+ new DialogInterface.OnClickListener() {
+ public void onClick(DialogInterface dialog,
+ int whichButton) {
+ mSSLCertificateOnErrorDialog = null;
+ mSSLCertificateOnErrorView = null;
+ mSSLCertificateOnErrorHandler = null;
+ mSSLCertificateOnErrorError = null;
+
+ view.getWebViewClient().onReceivedSslError(
+ view, handler, error);
+ }
+ })
+ .setNeutralButton(R.string.page_info_view,
+ new DialogInterface.OnClickListener() {
+ public void onClick(DialogInterface dialog,
+ int whichButton) {
+ mSSLCertificateOnErrorDialog = null;
+
+ // do not clear the dialog state: we will
+ // need to show the dialog again once the
+ // user is done exploring the page-info details
+
+ showPageInfo(mController.getTabControl()
+ .getTabFromView(view),
+ true);
+ }
+ })
+ .setOnCancelListener(
+ new DialogInterface.OnCancelListener() {
+ public void onCancel(DialogInterface dialog) {
+ mSSLCertificateOnErrorDialog = null;
+ mSSLCertificateOnErrorView = null;
+ mSSLCertificateOnErrorHandler = null;
+ mSSLCertificateOnErrorError = null;
+
+ view.getWebViewClient().onReceivedSslError(
+ view, handler, error);
+ }
+ })
+ .show();
+ }
+
+ /**
+ * Inflates the SSL certificate view (helper method).
+ * @param certificate The SSL certificate.
+ * @return The resultant certificate view with issued-to, issued-by,
+ * issued-on, expires-on, and possibly other fields set.
+ * If the input certificate is null, returns null.
+ */
+ private View inflateCertificateView(SslCertificate certificate) {
+ if (certificate == null) {
+ return null;
+ }
+
+ LayoutInflater factory = LayoutInflater.from(mContext);
+
+ View certificateView = factory.inflate(
+ R.layout.ssl_certificate, null);
+
+ // issued to:
+ SslCertificate.DName issuedTo = certificate.getIssuedTo();
+ if (issuedTo != null) {
+ ((TextView) certificateView.findViewById(R.id.to_common))
+ .setText(issuedTo.getCName());
+ ((TextView) certificateView.findViewById(R.id.to_org))
+ .setText(issuedTo.getOName());
+ ((TextView) certificateView.findViewById(R.id.to_org_unit))
+ .setText(issuedTo.getUName());
+ }
+
+ // issued by:
+ SslCertificate.DName issuedBy = certificate.getIssuedBy();
+ if (issuedBy != null) {
+ ((TextView) certificateView.findViewById(R.id.by_common))
+ .setText(issuedBy.getCName());
+ ((TextView) certificateView.findViewById(R.id.by_org))
+ .setText(issuedBy.getOName());
+ ((TextView) certificateView.findViewById(R.id.by_org_unit))
+ .setText(issuedBy.getUName());
+ }
+
+ // issued on:
+ String issuedOn = formatCertificateDate(
+ certificate.getValidNotBeforeDate());
+ ((TextView) certificateView.findViewById(R.id.issued_on))
+ .setText(issuedOn);
+
+ // expires on:
+ String expiresOn = formatCertificateDate(
+ certificate.getValidNotAfterDate());
+ ((TextView) certificateView.findViewById(R.id.expires_on))
+ .setText(expiresOn);
+
+ return certificateView;
+ }
+
+ /**
+ * Formats the certificate date to a properly localized date string.
+ * @return Properly localized version of the certificate date string and
+ * the "" if it fails to localize.
+ */
+ private String formatCertificateDate(Date certificateDate) {
+ if (certificateDate == null) {
+ return "";
+ }
+ String formattedDate = DateFormat.getDateFormat(mContext)
+ .format(certificateDate);
+ if (formattedDate == null) {
+ return "";
+ }
+ return formattedDate;
+ }
+
+}
diff --git a/src/com/android/browser/PageProgressView.java b/src/com/android/browser/PageProgressView.java
new file mode 100644
index 0000000..f512cef
--- /dev/null
+++ b/src/com/android/browser/PageProgressView.java
@@ -0,0 +1,117 @@
+
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.android.browser;
+
+import android.content.Context;
+import android.graphics.Canvas;
+import android.graphics.Rect;
+import android.graphics.drawable.Drawable;
+import android.os.Handler;
+import android.os.Message;
+import android.util.AttributeSet;
+import android.widget.ImageView;
+
+/**
+ *
+ */
+public class PageProgressView extends ImageView {
+
+ public static final int MAX_PROGRESS = 10000;
+ private static final int MSG_UPDATE = 42;
+ private static final int STEPS = 10;
+ private static final int DELAY = 40;
+
+ private int mCurrentProgress;
+ private int mTargetProgress;
+ private int mIncrement;
+ private Rect mBounds;
+ private Handler mHandler;
+
+ /**
+ * @param context
+ * @param attrs
+ * @param defStyle
+ */
+ public PageProgressView(Context context, AttributeSet attrs, int defStyle) {
+ super(context, attrs, defStyle);
+ init(context);
+ }
+
+ /**
+ * @param context
+ * @param attrs
+ */
+ public PageProgressView(Context context, AttributeSet attrs) {
+ super(context, attrs);
+ init(context);
+ }
+
+ /**
+ * @param context
+ */
+ public PageProgressView(Context context) {
+ super(context);
+ init(context);
+ }
+
+ private void init(Context ctx) {
+ mBounds = new Rect(0,0,0,0);
+ mCurrentProgress = 0;
+ mTargetProgress = 0;
+ mHandler = new Handler() {
+
+ @Override
+ public void handleMessage(Message msg) {
+ if (msg.what == MSG_UPDATE) {
+ mCurrentProgress = Math.min(mTargetProgress,
+ mCurrentProgress + mIncrement);
+ mBounds.right = getWidth() * mCurrentProgress / MAX_PROGRESS;
+ invalidate();
+ if (mCurrentProgress < mTargetProgress) {
+ sendMessageDelayed(mHandler.obtainMessage(MSG_UPDATE), DELAY);
+ }
+ }
+ }
+
+ };
+ }
+
+ @Override
+ public void onLayout(boolean f, int l, int t, int r, int b) {
+ mBounds.left = 0;
+ mBounds.right = (r - l) * mCurrentProgress / MAX_PROGRESS;
+ mBounds.top = 0;
+ mBounds.bottom = b-t;
+ }
+
+ void setProgress(int progress) {
+ mCurrentProgress = mTargetProgress;
+ mTargetProgress = progress;
+ mIncrement = (mTargetProgress - mCurrentProgress) / STEPS;
+ mHandler.removeMessages(MSG_UPDATE);
+ mHandler.sendEmptyMessage(MSG_UPDATE);
+ }
+
+ @Override
+ public void onDraw(Canvas canvas) {
+// super.onDraw(canvas);
+ Drawable d = getDrawable();
+ d.setBounds(mBounds);
+ d.draw(canvas);
+ }
+
+}
diff --git a/src/com/android/browser/Performance.java b/src/com/android/browser/Performance.java
new file mode 100644
index 0000000..e9ddfa2
--- /dev/null
+++ b/src/com/android/browser/Performance.java
@@ -0,0 +1,133 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.net.WebAddress;
+import android.os.Debug;
+import android.os.Process;
+import android.os.SystemClock;
+import android.util.Log;
+
+/**
+ * Performance analysis
+ */
+public class Performance {
+
+ private static final String LOGTAG = "browser";
+
+ private final static boolean LOGD_ENABLED =
+ com.android.browser.Browser.LOGD_ENABLED;
+
+ private static boolean mInTrace;
+
+ // Performance probe
+ private static final int[] SYSTEM_CPU_FORMAT = new int[] {
+ Process.PROC_SPACE_TERM | Process.PROC_COMBINE,
+ Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG, // 1: user time
+ Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG, // 2: nice time
+ Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG, // 3: sys time
+ Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG, // 4: idle time
+ Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG, // 5: iowait time
+ Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG, // 6: irq time
+ Process.PROC_SPACE_TERM | Process.PROC_OUT_LONG // 7: softirq time
+ };
+
+ private static long mStart;
+ private static long mProcessStart;
+ private static long mUserStart;
+ private static long mSystemStart;
+ private static long mIdleStart;
+ private static long mIrqStart;
+
+ private static long mUiStart;
+
+ static void tracePageStart(String url) {
+ if (BrowserSettings.getInstance().isTracing()) {
+ String host;
+ try {
+ WebAddress uri = new WebAddress(url);
+ host = uri.getHost();
+ } catch (android.net.ParseException ex) {
+ host = "browser";
+ }
+ host = host.replace('.', '_');
+ host += ".trace";
+ mInTrace = true;
+ Debug.startMethodTracing(host, 20 * 1024 * 1024);
+ }
+ }
+
+ static void tracePageFinished() {
+ if (mInTrace) {
+ mInTrace = false;
+ Debug.stopMethodTracing();
+ }
+ }
+
+ static void onPageStarted() {
+ mStart = SystemClock.uptimeMillis();
+ mProcessStart = Process.getElapsedCpuTime();
+ long[] sysCpu = new long[7];
+ if (Process.readProcFile("/proc/stat", SYSTEM_CPU_FORMAT, null, sysCpu, null)) {
+ mUserStart = sysCpu[0] + sysCpu[1];
+ mSystemStart = sysCpu[2];
+ mIdleStart = sysCpu[3];
+ mIrqStart = sysCpu[4] + sysCpu[5] + sysCpu[6];
+ }
+ mUiStart = SystemClock.currentThreadTimeMillis();
+ }
+
+ static void onPageFinished(String url) {
+ long[] sysCpu = new long[7];
+ if (Process.readProcFile("/proc/stat", SYSTEM_CPU_FORMAT, null, sysCpu, null)) {
+ String uiInfo =
+ "UI thread used " + (SystemClock.currentThreadTimeMillis() - mUiStart) + " ms";
+ if (LOGD_ENABLED) {
+ Log.d(LOGTAG, uiInfo);
+ }
+ // The string that gets written to the log
+ String performanceString =
+ "It took total " + (SystemClock.uptimeMillis() - mStart)
+ + " ms clock time to load the page." + "\nbrowser process used "
+ + (Process.getElapsedCpuTime() - mProcessStart)
+ + " ms, user processes used " + (sysCpu[0] + sysCpu[1] - mUserStart)
+ * 10 + " ms, kernel used " + (sysCpu[2] - mSystemStart) * 10
+ + " ms, idle took " + (sysCpu[3] - mIdleStart) * 10
+ + " ms and irq took " + (sysCpu[4] + sysCpu[5] + sysCpu[6] - mIrqStart)
+ * 10 + " ms, " + uiInfo;
+ if (LOGD_ENABLED) {
+ Log.d(LOGTAG, performanceString + "\nWebpage: " + url);
+ }
+ if (url != null) {
+ // strip the url to maintain consistency
+ String newUrl = new String(url);
+ if (newUrl.startsWith("http://www.")) {
+ newUrl = newUrl.substring(11);
+ } else if (newUrl.startsWith("http://")) {
+ newUrl = newUrl.substring(7);
+ } else if (newUrl.startsWith("https://www.")) {
+ newUrl = newUrl.substring(12);
+ } else if (newUrl.startsWith("https://")) {
+ newUrl = newUrl.substring(8);
+ }
+ if (LOGD_ENABLED) {
+ Log.d(LOGTAG, newUrl + " loaded");
+ }
+ }
+ }
+ }
+}
diff --git a/src/com/android/browser/PhoneUi.java b/src/com/android/browser/PhoneUi.java
new file mode 100644
index 0000000..4119c29
--- /dev/null
+++ b/src/com/android/browser/PhoneUi.java
@@ -0,0 +1,278 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.app.Activity;
+import android.content.Context;
+import android.graphics.PixelFormat;
+import android.util.Log;
+import android.view.ActionMode;
+import android.view.Gravity;
+import android.view.KeyEvent;
+import android.view.Menu;
+import android.view.View;
+import android.view.ViewGroup;
+import android.view.WindowManager;
+import android.webkit.WebView;
+
+/**
+ * Ui for regular phone screen sizes
+ */
+public class PhoneUi extends BaseUi {
+
+ private static final String LOGTAG = "PhoneUi";
+
+ private TitleBar mTitleBar;
+ private TitleBar mFakeTitleBar;
+ private ActiveTabsPage mActiveTabsPage;
+
+ boolean mExtendedMenuOpen;
+ boolean mOptionsMenuOpen;
+
+ /**
+ * @param browser
+ * @param controller
+ */
+ public PhoneUi(Activity browser, UiController controller) {
+ super(browser, controller);
+ mTitleBar = new TitleBar(mActivity, mUiController);
+ // mTitleBar will be always be shown in the fully loaded mode on
+ // phone
+ mTitleBar.setProgress(100);
+ mFakeTitleBar = new TitleBar(mActivity, mUiController);
+
+ }
+
+ // webview factory
+
+ @Override
+ public WebView createWebView(boolean privateBrowsing) {
+ // Create a new WebView
+ WebView w = new WebView(mActivity, null,
+ android.R.attr.webViewStyle, privateBrowsing);
+ initWebViewSettings(w);
+ return w;
+ }
+
+ @Override
+ public WebView createSubWebView(boolean privateBrowsing) {
+ WebView web = createWebView(privateBrowsing);
+ return web;
+ }
+
+ // lifecycle
+
+ @Override
+ public void onPause() {
+ // FIXME: This removes the active tabs page and resets the menu to
+ // MAIN_MENU. A better solution might be to do this work in onNewIntent
+ // but then we would need to save it in onSaveInstanceState and restore
+ // it in onCreate/onRestoreInstanceState
+ if (mActiveTabsPage != null) {
+ mUiController.removeActiveTabsPage(true);
+ }
+ super.onPause();
+ }
+
+ @Override
+ public void onDestroy() {
+ hideFakeTitleBar();
+ }
+
+ @Override
+ public boolean onBackKey() {
+ if (mActiveTabsPage != null) {
+ // if tab page is showing, hide it
+ mUiController.removeActiveTabsPage(true);
+ return true;
+ }
+ return super.onBackKey();
+ }
+
+ @Override
+ public void onProgressChanged(Tab tab) {
+ if (tab.inForeground()) {
+ int progress = tab.getLoadProgress();
+ mFakeTitleBar.setProgress(progress);
+ if (progress == 100) {
+ if (!mOptionsMenuOpen || !mExtendedMenuOpen) {
+ hideFakeTitleBar();
+ }
+ } else {
+ if (!mOptionsMenuOpen || mExtendedMenuOpen) {
+ showFakeTitleBar();
+ }
+ }
+ }
+ }
+
+ @Override
+ public void setActiveTab(Tab tab) {
+ super.setActiveTab(tab);
+ WebView view = tab.getWebView();
+ // TabControl.setCurrentTab has been called before this,
+ // so the tab is guaranteed to have a webview
+ if (view == null) {
+ Log.e(LOGTAG, "active tab with no webview detected");
+ return;
+ }
+ view.setEmbeddedTitleBar(getEmbeddedTitleBar());
+ if (tab.isInVoiceSearchMode()) {
+ showVoiceTitleBar(tab.getVoiceDisplayTitle());
+ } else {
+ revertVoiceTitleBar(tab);
+ }
+ tab.getTopWindow().requestFocus();
+ }
+
+ @Override
+ protected void attachFakeTitleBar(WebView mainView) {
+ WindowManager manager = (WindowManager)
+ mActivity.getSystemService(Context.WINDOW_SERVICE);
+
+ // Add the title bar to the window manager so it can receive
+ // touches while the menu is up
+ WindowManager.LayoutParams params =
+ new WindowManager.LayoutParams(
+ ViewGroup.LayoutParams.MATCH_PARENT,
+ ViewGroup.LayoutParams.WRAP_CONTENT,
+ WindowManager.LayoutParams.TYPE_APPLICATION,
+ WindowManager.LayoutParams.FLAG_NOT_FOCUSABLE,
+ PixelFormat.TRANSLUCENT);
+ params.gravity = Gravity.TOP;
+ boolean atTop = mainView.getScrollY() == 0;
+ params.windowAnimations = atTop ? 0 : R.style.TitleBar;
+ manager.addView(mFakeTitleBar, params);
+ }
+
+ @Override
+ protected void hideFakeTitleBar() {
+ if (!isFakeTitleBarShowing()) return;
+ WindowManager.LayoutParams params =
+ (WindowManager.LayoutParams) mFakeTitleBar.getLayoutParams();
+ WebView mainView = mUiController.getCurrentWebView();
+ // Although we decided whether or not to animate based on the
+ // current
+ // scroll position, the scroll position may have changed since the
+ // fake title bar was displayed. Make sure it has the appropriate
+ // animation/lack thereof before removing.
+ params.windowAnimations =
+ mainView != null && mainView.getScrollY() == 0 ?
+ 0 : R.style.TitleBar;
+ WindowManager manager = (WindowManager) mActivity
+ .getSystemService(Context.WINDOW_SERVICE);
+ manager.updateViewLayout(mFakeTitleBar, params);
+ manager.removeView(mFakeTitleBar);
+ }
+
+ @Override
+ protected boolean isFakeTitleBarShowing() {
+ return (mFakeTitleBar.getParent() != null);
+ }
+
+ @Override
+ protected TitleBarBase getFakeTitleBar() {
+ return mFakeTitleBar;
+ }
+
+ @Override
+ protected TitleBarBase getEmbeddedTitleBar() {
+ return mTitleBar;
+ }
+
+ // active tabs page
+
+ @Override
+ public void showActiveTabsPage() {
+ mActiveTabsPage = new ActiveTabsPage(mActivity, mUiController);
+ mTitleBar.setVisibility(View.GONE);
+ hideFakeTitleBar();
+ mContentView.addView(mActiveTabsPage, COVER_SCREEN_PARAMS);
+ mActiveTabsPage.requestFocus();
+ }
+
+ /**
+ * Remove the active tabs page.
+ */
+ @Override
+ public void removeActiveTabsPage() {
+ mContentView.removeView(mActiveTabsPage);
+ mTitleBar.setVisibility(View.VISIBLE);
+ mActiveTabsPage = null;
+ }
+
+ @Override
+ public boolean showsWeb() {
+ return super.showsWeb() && mActiveTabsPage == null;
+ }
+
+ // menu handling callbacks
+
+ @Override
+ public void onOptionsMenuOpened() {
+ mOptionsMenuOpen = true;
+ // options menu opened, show fake title bar
+ showFakeTitleBar();
+ }
+
+ @Override
+ public void onExtendedMenuOpened() {
+ // Switching the menu to expanded view, so hide the
+ // title bar.
+ mExtendedMenuOpen = true;
+ hideFakeTitleBar();
+ }
+
+ @Override
+ public void onOptionsMenuClosed(boolean inLoad) {
+ mOptionsMenuOpen = false;
+ if (!inLoad) {
+ hideFakeTitleBar();
+ }
+ }
+
+ @Override
+ public void onExtendedMenuClosed(boolean inLoad) {
+ mExtendedMenuOpen = false;
+ showFakeTitleBar();
+ }
+
+ @Override
+ public void onContextMenuCreated(Menu menu) {
+ hideFakeTitleBar();
+ }
+
+ @Override
+ public void onContextMenuClosed(Menu menu, boolean inLoad) {
+ if (inLoad) {
+ showFakeTitleBar();
+ }
+ }
+
+ // action mode callbacks
+
+ @Override
+ public void onActionModeStarted(ActionMode mode) {
+ hideFakeTitleBar();
+ }
+
+ @Override
+ public boolean dispatchKey(int code, KeyEvent event) {
+ return false;
+ }
+
+}
diff --git a/src/com/android/browser/PieControl.java b/src/com/android/browser/PieControl.java
new file mode 100644
index 0000000..6326f2e
--- /dev/null
+++ b/src/com/android/browser/PieControl.java
@@ -0,0 +1,152 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.view.PieMenu;
+
+import android.app.Activity;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.view.ViewGroup.LayoutParams;
+import android.webkit.WebView;
+import android.widget.FrameLayout;
+import android.widget.ImageView;
+
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * controller for Quick Controls pie menu
+ */
+public class PieControl implements OnClickListener, PieMenu.PieController {
+
+ private Activity mActivity;
+ private UiController mUiController;
+ private XLargeUi mUi;
+ private PieMenu mPie;
+ private ImageView mBack;
+ private ImageView mForward;
+ private ImageView mRefresh;
+ private ImageView mUrl;
+ private ImageView mOptions;
+ private ImageView mBookmarks;
+ private ImageView mNewTab;
+ private ImageView mClose;
+
+ private Map<View,Tab> mTabItems;
+
+ boolean mNewTabMode = true;
+
+ public PieControl(Activity activity, UiController controller, XLargeUi ui) {
+ mActivity = activity;
+ mUiController = controller;
+ mUi = ui;
+ mTabItems = new HashMap<View, Tab>();
+ }
+
+ protected void attachToContainer(FrameLayout container) {
+ if (mPie == null) {
+ mPie = new PieMenu(mActivity);
+ LayoutParams lp = new LayoutParams(LayoutParams.MATCH_PARENT,
+ LayoutParams.MATCH_PARENT);
+ mPie.setLayoutParams(lp);
+ mForward = makeMenuView(R.drawable.ic_pie_forward);
+ mPie.addItem(mForward);
+ mRefresh = makeMenuView(R.drawable.ic_pie_refresh);
+ mPie.addItem(mRefresh);
+ mBack = makeMenuView(R.drawable.ic_pie_back);
+ mPie.addItem(mBack);
+ mUrl = makeMenuView(R.drawable.ic_pie_web);
+ mPie.addItem(mUrl);
+ mBookmarks = makeMenuView(R.drawable.ic_pie_bookmarks);
+ mPie.addItem(mBookmarks);
+ mNewTab = makeMenuView(R.drawable.ic_pie_new_tab);
+ mPie.addItem(mNewTab);
+ mOptions = makeMenuView(R.drawable.ic_pie_more);
+ mPie.addItem(mOptions);
+ setClickListener(mBack, mForward, mRefresh, mUrl, mOptions,
+ mBookmarks, mNewTab);
+ mPie.setController(this);
+ }
+ container.addView(mPie);
+ }
+
+ protected void removeFromContainer(FrameLayout container) {
+ container.removeView(mPie);
+ }
+
+ private ImageView makeMenuView(int image) {
+ ImageView item = new ImageView(mActivity);
+ item.setImageResource(image);
+ LayoutParams lp = new LayoutParams(48, 48);
+ item.setLayoutParams(lp);
+ return item;
+ }
+
+ private void setClickListener(View... views) {
+ for (View view : views) {
+ view.setOnClickListener(this);
+ }
+ }
+
+ protected void forceToTop(FrameLayout container) {
+ if (mPie.getParent() != null) {
+ container.removeView(mPie);
+ container.addView(mPie);
+ }
+ }
+
+ @Override
+ public void onClick(View v) {
+ mPie.show(false);
+ Tab tab = mUiController.getTabControl().getCurrentTab();
+ WebView web = tab.getWebView();
+ if (mBack == v) {
+ web.goBack();
+ } else if (mForward == v) {
+ web.goForward();
+ } else if (mRefresh == v) {
+ if (tab.inPageLoad()) {
+ web.stopLoading();
+ } else {
+ web.reload();
+ }
+ } else if (mUrl == v) {
+ mUi.showFakeTitleBarAndEdit();
+ } else if (mOptions == v) {
+ mActivity.openOptionsMenu();
+ } else if (mBookmarks == v) {
+ mUiController.bookmarksOrHistoryPicker(false);
+ } else if (mNewTab == v) {
+ mUiController.openTabToHomePage();
+ mUi.showFakeTitleBarAndEdit();
+ } else if (mClose == v) {
+ mUiController.closeCurrentTab();
+ } else {
+ Tab ntab = mTabItems.get(v);
+ if (ntab != null) {
+ mUiController.switchToTab(mUiController.getTabControl().getTabIndex(ntab));
+ }
+ }
+ }
+
+ @Override
+ public boolean onOpen() {
+ return true;
+ }
+
+}
diff --git a/src/com/android/browser/ScrollWebView.java b/src/com/android/browser/ScrollWebView.java
new file mode 100644
index 0000000..e2ef902
--- /dev/null
+++ b/src/com/android/browser/ScrollWebView.java
@@ -0,0 +1,129 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.content.Context;
+import android.util.AttributeSet;
+import android.view.View;
+import android.webkit.WebView;
+
+import java.util.Map;
+
+/**
+ * Manage WebView scroll events
+ */
+public class ScrollWebView extends WebView implements Runnable {
+
+ private ScrollListener mScrollListener;
+ private boolean mIsCancelled;
+ private boolean mBackgroundRemoved = false;
+
+ /**
+ * @param context
+ * @param attrs
+ * @param defStyle
+ * @param javascriptInterfaces
+ */
+ public ScrollWebView(Context context, AttributeSet attrs, int defStyle,
+ Map<String, Object> javascriptInterfaces, boolean privateBrowsing) {
+ super(context, attrs, defStyle, javascriptInterfaces, privateBrowsing);
+ }
+
+ /**
+ * @param context
+ * @param attrs
+ * @param defStyle
+ */
+ public ScrollWebView(Context context, AttributeSet attrs, int defStyle,
+ boolean privateBrowsing) {
+ super(context, attrs, defStyle, privateBrowsing);
+ }
+
+ /**
+ * @param context
+ * @param attrs
+ */
+ public ScrollWebView(Context context, AttributeSet attrs) {
+ super(context, attrs);
+ }
+
+ /**
+ * @param context
+ */
+ public ScrollWebView(Context context) {
+ super(context);
+ }
+
+ // scroll runnable implementation
+ public void run() {
+ if (!mIsCancelled && (mScrollListener != null)) {
+ mScrollListener.onScroll(getVisibleTitleHeight());
+ }
+ }
+
+ void hideEmbeddedTitleBar() {
+ scrollBy(0, getVisibleTitleHeight());
+ }
+
+ @Override
+ public void setEmbeddedTitleBar(final View title) {
+ super.setEmbeddedTitleBar(title);
+ if (title != null && mScrollListener != null) {
+ // allow the scroll listener to initialize its state
+ post(this);
+ }
+ }
+
+ @Override
+ public void stopScroll() {
+ mIsCancelled = true;
+ super.stopScroll();
+ }
+
+ @Override
+ protected void onScrollChanged(int l, final int t, int ol, int ot) {
+ super.onScrollChanged(l, t, ol, ot);
+ if (!mIsCancelled) {
+ post(this);
+ } else {
+ mIsCancelled = false;
+ }
+ }
+
+ void setScrollListener(ScrollListener l) {
+ mScrollListener = l;
+ }
+
+ // callback for scroll events
+
+ interface ScrollListener {
+ public void onScroll(int visibleTitleHeight);
+ }
+
+ @Override
+ protected void onDraw(android.graphics.Canvas c) {
+ super.onDraw(c);
+ if (!mBackgroundRemoved && getRootView().getBackground() != null) {
+ mBackgroundRemoved = true;
+ post(new Runnable() {
+ public void run() {
+ getRootView().setBackgroundDrawable(null);
+ }
+ });
+ }
+ }
+}
diff --git a/src/com/android/browser/SelectDialog.java b/src/com/android/browser/SelectDialog.java
deleted file mode 100644
index 461127a..0000000
--- a/src/com/android/browser/SelectDialog.java
+++ /dev/null
@@ -1,85 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.browser;
-
-import android.provider.Browser;
-import android.view.LayoutInflater;
-import android.view.View;
-
-/* package */ class SelectDialog extends WebDialog {
- private View mCopyButton;
- private View mSelectAllButton;
- private View mShareButton;
- private View mFindButton;
-
- SelectDialog(BrowserActivity context) {
- super(context);
- LayoutInflater factory = LayoutInflater.from(context);
- factory.inflate(R.layout.browser_select, this);
- addCancel();
-
- mCopyButton = findViewById(R.id.copy);
- mCopyButton.setOnClickListener(mCopyListener);
- mSelectAllButton = findViewById(R.id.select_all);
- mSelectAllButton.setOnClickListener(mSelectAllListener);
- mShareButton = findViewById(R.id.share);
- mShareButton.setOnClickListener(mShareListener);
- mFindButton = findViewById(R.id.find);
- mFindButton.setOnClickListener(mFindListener);
- }
-
- private View.OnClickListener mCopyListener = new View.OnClickListener() {
- public void onClick(View v) {
- mWebView.copySelection();
- mBrowserActivity.closeDialogs();
- }
- };
-
- private View.OnClickListener mSelectAllListener = new View.OnClickListener() {
- public void onClick(View v) {
- mWebView.selectAll();
- }
- };
-
- private View.OnClickListener mShareListener = new View.OnClickListener() {
- public void onClick(View v) {
- String selection = mWebView.getSelection();
- Browser.sendString(mBrowserActivity, selection);
- mBrowserActivity.closeDialogs();
- }
- };
-
- private View.OnClickListener mFindListener = new View.OnClickListener() {
- public void onClick(View v) {
- String selection = mWebView.getSelection();
- mBrowserActivity.closeDialogs();
- mBrowserActivity.showFindDialog();
- mBrowserActivity.setFindDialogText(selection);
- }
- };
-
- /**
- * Called by BrowserActivity.closeDialog. Start the animation to hide
- * the dialog, and inform the WebView that the dialog is being dismissed.
- */
- @Override
- public void dismiss() {
- super.dismiss();
- mWebView.notifySelectDialogDismissed();
- }
-
-}
diff --git a/src/com/android/browser/ShortcutActivity.java b/src/com/android/browser/ShortcutActivity.java
new file mode 100644
index 0000000..16a4cbe
--- /dev/null
+++ b/src/com/android/browser/ShortcutActivity.java
@@ -0,0 +1,87 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.app.Activity;
+import android.content.Intent;
+import android.database.Cursor;
+import android.net.Uri;
+import android.os.Bundle;
+import android.view.View;
+import android.view.View.OnClickListener;
+
+public class ShortcutActivity extends Activity
+ implements BookmarksPageCallbacks, OnClickListener {
+
+ private BrowserBookmarksPage mBookmarks;
+
+ @Override
+ protected void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+ // TODO: Is this needed?
+ setDefaultKeyMode(DEFAULT_KEYS_SEARCH_LOCAL);
+ setContentView(R.layout.pick_bookmark);
+ mBookmarks = (BrowserBookmarksPage) getFragmentManager()
+ .findFragmentById(R.id.bookmarks);
+ mBookmarks.setEnableContextMenu(false);
+ mBookmarks.setBreadCrumbMaxVisible(2);
+ mBookmarks.setBreadCrumbUseBackButton(true);
+ mBookmarks.setCallbackListener(this);
+ View cancel = findViewById(R.id.cancel);
+ if (cancel != null) {
+ cancel.setOnClickListener(this);
+ }
+ }
+
+ // BookmarksPageCallbacks
+
+ @Override
+ public boolean onBookmarkSelected(Cursor c, boolean isFolder) {
+ if (isFolder) {
+ return false;
+ }
+ Intent intent = BrowserBookmarksPage.createShortcutIntent(this, c);
+ setResult(RESULT_OK, intent);
+ finish();
+ return true;
+ }
+
+ @Override
+ public boolean onOpenInNewWindow(Cursor c) {
+ return false;
+ }
+
+ @Override
+ public void onBackPressed() {
+ if (!mBookmarks.onBackPressed()) {
+ super.onBackPressed();
+ }
+ }
+
+ @Override
+ public void onFolderChanged(int level, Uri uri) {
+ }
+
+ @Override
+ public void onClick(View v) {
+ switch (v.getId()) {
+ case R.id.cancel:
+ finish();
+ break;
+ }
+ }
+}
diff --git a/src/com/android/browser/SuggestionsAdapter.java b/src/com/android/browser/SuggestionsAdapter.java
new file mode 100644
index 0000000..6e55539
--- /dev/null
+++ b/src/com/android/browser/SuggestionsAdapter.java
@@ -0,0 +1,570 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.search.SearchEngine;
+
+import android.app.SearchManager;
+import android.content.Context;
+import android.database.Cursor;
+import android.net.Uri;
+import android.os.AsyncTask;
+import android.provider.BrowserContract;
+import android.text.TextUtils;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.view.ViewGroup;
+import android.widget.BaseAdapter;
+import android.widget.Filter;
+import android.widget.Filterable;
+import android.widget.ImageView;
+import android.widget.TextView;
+
+import java.util.ArrayList;
+import java.util.List;
+
+/**
+ * adapter to wrap multiple cursors for url/search completions
+ */
+public class SuggestionsAdapter extends BaseAdapter implements Filterable,
+ OnClickListener {
+
+ static final int TYPE_BOOKMARK = 0;
+ static final int TYPE_HISTORY = 1;
+ static final int TYPE_SUGGEST_URL = 2;
+ static final int TYPE_SEARCH = 3;
+ static final int TYPE_SUGGEST = 4;
+ static final int TYPE_VOICE_SEARCH = 5;
+
+ private static final String[] COMBINED_PROJECTION =
+ {BrowserContract.Combined._ID, BrowserContract.Combined.TITLE,
+ BrowserContract.Combined.URL, BrowserContract.Combined.IS_BOOKMARK};
+
+ private static final String COMBINED_SELECTION =
+ "(url LIKE ? OR url LIKE ? OR url LIKE ? OR url LIKE ? OR title LIKE ?)";
+
+ Context mContext;
+ Filter mFilter;
+ SuggestionResults mMixedResults;
+ List<SuggestItem> mSuggestResults, mFilterResults;
+ List<CursorSource> mSources;
+ boolean mLandscapeMode;
+ CompletionListener mListener;
+ int mLinesPortrait;
+ int mLinesLandscape;
+ Object mResultsLock = new Object();
+ List<String> mVoiceResults;
+ boolean mReverseResults;
+ boolean mIncognitoMode;
+
+ interface CompletionListener {
+
+ public void onSearch(String txt);
+
+ public void onSelect(String txt, int type, String extraData);
+
+ }
+
+ public SuggestionsAdapter(Context ctx, CompletionListener listener) {
+ mContext = ctx;
+ mListener = listener;
+ mLinesPortrait = mContext.getResources().
+ getInteger(R.integer.max_suggest_lines_portrait);
+ mLinesLandscape = mContext.getResources().
+ getInteger(R.integer.max_suggest_lines_landscape);
+ mFilter = new SuggestFilter();
+ addSource(new CombinedCursor());
+ }
+
+ void setVoiceResults(List<String> voiceResults) {
+ mVoiceResults = voiceResults;
+ notifyDataSetChanged();
+ }
+
+ public void setLandscapeMode(boolean mode) {
+ mLandscapeMode = mode;
+ notifyDataSetChanged();
+ }
+
+ public void addSource(CursorSource c) {
+ if (mSources == null) {
+ mSources = new ArrayList<CursorSource>(5);
+ }
+ mSources.add(c);
+ }
+
+ @Override
+ public void onClick(View v) {
+ SuggestItem item = (SuggestItem) ((View) v.getParent()).getTag();
+ if (R.id.icon2 == v.getId()) {
+ // replace input field text with suggestion text
+ mListener.onSearch(item.title);
+ } else {
+ mListener.onSelect(
+ (TextUtils.isEmpty(item.url)? item.title : item.url),
+ item.type, item.extra);
+ }
+ }
+
+ @Override
+ public Filter getFilter() {
+ return mFilter;
+ }
+
+ @Override
+ public int getCount() {
+ if (mVoiceResults != null) {
+ return mVoiceResults.size();
+ }
+ return (mMixedResults == null) ? 0 : mMixedResults.getLineCount();
+ }
+
+ @Override
+ public SuggestItem getItem(int position) {
+ if (mReverseResults) {
+ position = (getCount() - 1) - position;
+ }
+ if (mVoiceResults != null) {
+ SuggestItem item = new SuggestItem(mVoiceResults.get(position),
+ null, TYPE_VOICE_SEARCH);
+ item.extra = Integer.toString(position);
+ return item;
+ }
+ if (mMixedResults == null) {
+ return null;
+ }
+ return mMixedResults.items.get(position);
+ }
+
+ public void setReverseResults(boolean reverse) {
+ mReverseResults = reverse;
+ }
+
+ @Override
+ public long getItemId(int position) {
+ return position;
+ }
+
+ @Override
+ public View getView(int position, View convertView, ViewGroup parent) {
+ final LayoutInflater inflater = LayoutInflater.from(mContext);
+ View view = convertView;
+ if (view == null) {
+ view = inflater.inflate(R.layout.suggestion_item, parent, false);
+ }
+ bindView(view, getItem(position));
+ return view;
+ }
+
+ private void bindView(View view, SuggestItem item) {
+ // store item for click handling
+ view.setTag(item);
+ TextView tv1 = (TextView) view.findViewById(android.R.id.text1);
+ TextView tv2 = (TextView) view.findViewById(android.R.id.text2);
+ ImageView ic1 = (ImageView) view.findViewById(R.id.icon1);
+ View ic2 = view.findViewById(R.id.icon2);
+ View div = view.findViewById(R.id.divider);
+ tv1.setText(item.title);
+ if (TextUtils.isEmpty(item.url)) {
+ tv2.setVisibility(View.GONE);
+ } else {
+ tv2.setVisibility(View.VISIBLE);
+ tv2.setText(item.url);
+ }
+ int id = -1;
+ switch (item.type) {
+ case TYPE_SUGGEST:
+ case TYPE_SEARCH:
+ case TYPE_VOICE_SEARCH:
+ id = R.drawable.ic_search_category_suggest;
+ break;
+ case TYPE_BOOKMARK:
+ id = R.drawable.ic_search_category_bookmark;
+ break;
+ case TYPE_HISTORY:
+ id = R.drawable.ic_search_category_history;
+ break;
+ case TYPE_SUGGEST_URL:
+ id = R.drawable.ic_search_category_browser;
+ break;
+ default:
+ id = -1;
+ }
+ if (id != -1) {
+ ic1.setImageDrawable(mContext.getResources().getDrawable(id));
+ }
+ ic2.setVisibility(((TYPE_SUGGEST == item.type)
+ || (TYPE_SEARCH == item.type)
+ || (TYPE_VOICE_SEARCH == item.type))
+ ? View.VISIBLE : View.GONE);
+ div.setVisibility(ic2.getVisibility());
+ ic2.setOnClickListener(this);
+ view.findViewById(R.id.suggestion).setOnClickListener(this);
+ }
+
+ class SlowFilterTask extends AsyncTask<CharSequence, Void, List<SuggestItem>> {
+
+ @Override
+ protected List<SuggestItem> doInBackground(CharSequence... params) {
+ SuggestCursor cursor = new SuggestCursor();
+ cursor.runQuery(params[0]);
+ List<SuggestItem> results = new ArrayList<SuggestItem>();
+ int count = cursor.getCount();
+ for (int i = 0; i < count; i++) {
+ results.add(cursor.getItem());
+ cursor.moveToNext();
+ }
+ cursor.close();
+ return results;
+ }
+
+ @Override
+ protected void onPostExecute(List<SuggestItem> items) {
+ mSuggestResults = items;
+ mMixedResults = buildSuggestionResults();
+ notifyDataSetChanged();
+ }
+ }
+
+ SuggestionResults buildSuggestionResults() {
+ SuggestionResults mixed = new SuggestionResults();
+ List<SuggestItem> filter, suggest;
+ synchronized (mResultsLock) {
+ filter = mFilterResults;
+ suggest = mSuggestResults;
+ }
+ if (filter != null) {
+ for (SuggestItem item : filter) {
+ mixed.addResult(item);
+ }
+ }
+ if (suggest != null) {
+ for (SuggestItem item : suggest) {
+ mixed.addResult(item);
+ }
+ }
+ return mixed;
+ }
+
+ class SuggestFilter extends Filter {
+
+ @Override
+ public CharSequence convertResultToString(Object item) {
+ if (item == null) {
+ return "";
+ }
+ SuggestItem sitem = (SuggestItem) item;
+ if (sitem.title != null) {
+ return sitem.title;
+ } else {
+ return sitem.url;
+ }
+ }
+
+ void startSuggestionsAsync(final CharSequence constraint) {
+ if (!mIncognitoMode) {
+ new SlowFilterTask().execute(constraint);
+ }
+ }
+
+ @Override
+ protected FilterResults performFiltering(CharSequence constraint) {
+ FilterResults res = new FilterResults();
+ if (mVoiceResults == null) {
+ if (TextUtils.isEmpty(constraint)) {
+ res.count = 0;
+ res.values = null;
+ return res;
+ }
+ startSuggestionsAsync(constraint);
+ List<SuggestItem> filterResults = new ArrayList<SuggestItem>();
+ if (constraint != null) {
+ for (CursorSource sc : mSources) {
+ sc.runQuery(constraint);
+ }
+ mixResults(filterResults);
+ }
+ synchronized (mResultsLock) {
+ mFilterResults = filterResults;
+ }
+ SuggestionResults mixed = buildSuggestionResults();
+ res.count = mixed.getLineCount();
+ res.values = mixed;
+ } else {
+ res.count = mVoiceResults.size();
+ res.values = mVoiceResults;
+ }
+ return res;
+ }
+
+ void mixResults(List<SuggestItem> results) {
+ int maxLines = mLandscapeMode ? mLinesLandscape : mLinesPortrait;
+ maxLines = (int) Math.ceil(maxLines / 2.0);
+ for (int i = 0; i < mSources.size(); i++) {
+ CursorSource s = mSources.get(i);
+ int n = Math.min(s.getCount(), maxLines);
+ maxLines -= n;
+ boolean more = false;
+ for (int j = 0; j < n; j++) {
+ results.add(s.getItem());
+ more = s.moveToNext();
+ }
+ }
+ }
+
+ @Override
+ protected void publishResults(CharSequence constraint, FilterResults fresults) {
+ if (fresults.values instanceof SuggestionResults) {
+ mMixedResults = (SuggestionResults) fresults.values;
+ notifyDataSetChanged();
+ }
+ }
+
+ }
+
+ /**
+ * sorted list of results of a suggestion query
+ *
+ */
+ class SuggestionResults {
+
+ ArrayList<SuggestItem> items;
+ // count per type
+ int[] counts;
+
+ SuggestionResults() {
+ items = new ArrayList<SuggestItem>(24);
+ // n of types:
+ counts = new int[5];
+ }
+
+ int getTypeCount(int type) {
+ return counts[type];
+ }
+
+ void addResult(SuggestItem item) {
+ int ix = 0;
+ while ((ix < items.size()) && (item.type >= items.get(ix).type))
+ ix++;
+ items.add(ix, item);
+ counts[item.type]++;
+ }
+
+ int getLineCount() {
+ if (mLandscapeMode) {
+ return Math.min(mLinesLandscape, items.size());
+ } else {
+ return Math.min(mLinesPortrait, items.size());
+ }
+ }
+
+ @Override
+ public String toString() {
+ if (items == null) return null;
+ if (items.size() == 0) return "[]";
+ StringBuilder sb = new StringBuilder();
+ for (int i = 0; i < items.size(); i++) {
+ SuggestItem item = items.get(i);
+ sb.append(item.type + ": " + item.title);
+ if (i < items.size() - 1) {
+ sb.append(", ");
+ }
+ }
+ return sb.toString();
+ }
+ }
+
+ /**
+ * data object to hold suggestion values
+ */
+ class SuggestItem {
+ String title;
+ String url;
+ int type;
+ String extra;
+
+ public SuggestItem(String text, String u, int t) {
+ title = text;
+ url = u;
+ type = t;
+ }
+
+ }
+
+ abstract class CursorSource {
+
+ Cursor mCursor;
+
+ boolean moveToNext() {
+ return mCursor.moveToNext();
+ }
+
+ public abstract void runQuery(CharSequence constraint);
+
+ public abstract SuggestItem getItem();
+
+ public int getCount() {
+ return (mCursor != null) ? mCursor.getCount() : 0;
+ }
+
+ public void close() {
+ if (mCursor != null) {
+ mCursor.close();
+ }
+ }
+ }
+
+ /**
+ * combined bookmark & history source
+ */
+ class CombinedCursor extends CursorSource {
+
+ @Override
+ public SuggestItem getItem() {
+ if ((mCursor != null) && (!mCursor.isAfterLast())) {
+ String title = mCursor.getString(1);
+ String url = mCursor.getString(2);
+ boolean isBookmark = (mCursor.getInt(3) == 1);
+ return new SuggestItem(getTitle(title, url), getUrl(title, url),
+ isBookmark ? TYPE_BOOKMARK : TYPE_HISTORY);
+ }
+ return null;
+ }
+
+ @Override
+ public void runQuery(CharSequence constraint) {
+ // constraint != null
+ if (mCursor != null) {
+ mCursor.close();
+ }
+ String like = constraint + "%";
+ String[] args = null;
+ String selection = null;
+ if (like.startsWith("http") || like.startsWith("file")) {
+ args = new String[1];
+ args[0] = like;
+ selection = "url LIKE ?";
+ } else {
+ args = new String[5];
+ args[0] = "http://" + like;
+ args[1] = "http://www." + like;
+ args[2] = "https://" + like;
+ args[3] = "https://www." + like;
+ // To match against titles.
+ args[4] = like;
+ selection = COMBINED_SELECTION;
+ }
+ Uri.Builder ub = BrowserContract.Combined.CONTENT_URI.buildUpon();
+ ub.appendQueryParameter(BrowserContract.PARAM_LIMIT,
+ Integer.toString(Math.max(mLinesLandscape, mLinesPortrait)));
+ BookmarkUtils.addAccountInfo(mContext, ub);
+ mCursor =
+ mContext.getContentResolver().query(ub.build(), COMBINED_PROJECTION,
+ selection,
+ (constraint != null) ? args : null,
+ BrowserContract.Combined.IS_BOOKMARK + " DESC, " +
+ BrowserContract.Combined.VISITS + " DESC, " +
+ BrowserContract.Combined.DATE_LAST_VISITED + " DESC");
+ if (mCursor != null) {
+ mCursor.moveToFirst();
+ }
+ }
+
+ /**
+ * Provides the title (text line 1) for a browser suggestion, which should be the
+ * webpage title. If the webpage title is empty, returns the stripped url instead.
+ *
+ * @return the title string to use
+ */
+ private String getTitle(String title, String url) {
+ if (TextUtils.isEmpty(title) || TextUtils.getTrimmedLength(title) == 0) {
+ title = UrlUtils.stripUrl(url);
+ }
+ return title;
+ }
+
+ /**
+ * Provides the subtitle (text line 2) for a browser suggestion, which should be the
+ * webpage url. If the webpage title is empty, then the url should go in the title
+ * instead, and the subtitle should be empty, so this would return null.
+ *
+ * @return the subtitle string to use, or null if none
+ */
+ private String getUrl(String title, String url) {
+ if (TextUtils.isEmpty(title)
+ || TextUtils.getTrimmedLength(title) == 0
+ || title.equals(url)) {
+ return null;
+ } else {
+ return UrlUtils.stripUrl(url);
+ }
+ }
+ }
+
+ class SuggestCursor extends CursorSource {
+
+ @Override
+ public SuggestItem getItem() {
+ if (mCursor != null) {
+ String title = mCursor.getString(
+ mCursor.getColumnIndex(SearchManager.SUGGEST_COLUMN_TEXT_1));
+ String text2 = mCursor.getString(
+ mCursor.getColumnIndex(SearchManager.SUGGEST_COLUMN_TEXT_2));
+ String url = mCursor.getString(
+ mCursor.getColumnIndex(SearchManager.SUGGEST_COLUMN_TEXT_2_URL));
+ String uri = mCursor.getString(
+ mCursor.getColumnIndex(SearchManager.SUGGEST_COLUMN_INTENT_DATA));
+ int type = (TextUtils.isEmpty(url)) ? TYPE_SUGGEST : TYPE_SUGGEST_URL;
+ SuggestItem item = new SuggestItem(title, url, type);
+ item.extra = mCursor.getString(
+ mCursor.getColumnIndex(SearchManager.SUGGEST_COLUMN_INTENT_EXTRA_DATA));
+ return item;
+ }
+ return null;
+ }
+
+ @Override
+ public void runQuery(CharSequence constraint) {
+ if (mCursor != null) {
+ mCursor.close();
+ }
+ if (!TextUtils.isEmpty(constraint)) {
+ SearchEngine searchEngine = BrowserSettings.getInstance().getSearchEngine();
+ if (searchEngine != null && searchEngine.supportsSuggestions()) {
+ mCursor = searchEngine.getSuggestions(mContext, constraint.toString());
+ if (mCursor != null) {
+ mCursor.moveToFirst();
+ }
+ }
+ } else {
+ mCursor = null;
+ }
+ }
+
+ }
+
+ public void clearCache() {
+ mFilterResults = null;
+ mSuggestResults = null;
+ }
+
+ public void setIncognitoMode(boolean incognito) {
+ mIncognitoMode = incognito;
+ clearCache();
+ }
+}
diff --git a/src/com/android/browser/Tab.java b/src/com/android/browser/Tab.java
index 7019c8a..c4897f2 100644
--- a/src/com/android/browser/Tab.java
+++ b/src/com/android/browser/Tab.java
@@ -16,42 +16,31 @@
package com.android.browser;
-import java.io.File;
-import java.util.ArrayList;
-import java.util.HashMap;
-import java.util.Iterator;
-import java.util.LinkedList;
-import java.util.Map;
-import java.util.Vector;
+import com.android.browser.homepages.HomeProvider;
+import com.android.common.speech.LoggingEvents;
+import android.app.Activity;
import android.app.AlertDialog;
import android.app.SearchManager;
import android.content.ContentResolver;
-import android.content.ContentValues;
+import android.content.Context;
import android.content.DialogInterface;
import android.content.DialogInterface.OnCancelListener;
import android.content.Intent;
-import android.database.Cursor;
-import android.database.sqlite.SQLiteDatabase;
-import android.database.sqlite.SQLiteException;
import android.graphics.Bitmap;
+import android.graphics.BitmapFactory;
import android.net.Uri;
import android.net.http.SslError;
-import android.os.AsyncTask;
import android.os.Bundle;
import android.os.Message;
import android.os.SystemClock;
-import android.provider.Browser;
import android.speech.RecognizerResultsIntent;
import android.util.Log;
import android.view.KeyEvent;
import android.view.LayoutInflater;
import android.view.View;
-import android.view.ViewGroup;
import android.view.ViewStub;
-import android.view.View.OnClickListener;
import android.webkit.ConsoleMessage;
-import android.webkit.CookieSyncManager;
import android.webkit.DownloadListener;
import android.webkit.GeolocationPermissions;
import android.webkit.HttpAuthHandler;
@@ -62,21 +51,27 @@
import android.webkit.WebBackForwardListClient;
import android.webkit.WebChromeClient;
import android.webkit.WebHistoryItem;
-import android.webkit.WebIconDatabase;
+import android.webkit.WebResourceResponse;
import android.webkit.WebStorage;
import android.webkit.WebView;
import android.webkit.WebViewClient;
-import android.widget.FrameLayout;
-import android.widget.ImageButton;
+import android.widget.CheckBox;
import android.widget.LinearLayout;
import android.widget.TextView;
+import android.widget.Toast;
-import com.android.common.speech.LoggingEvents;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.LinkedList;
+import java.util.Map;
+import java.util.Vector;
/**
* Class for maintaining Tabs with a main WebView and a subwindow.
*/
class Tab {
+
// Log Tag
private static final String LOGTAG = "Tab";
// Special case the logtag for messages for the Console to make it easier to
@@ -84,10 +79,19 @@
// of the browser.
private static final String CONSOLE_LOGTAG = "browser";
+ public enum LockIcon {
+ LOCK_ICON_UNSECURE,
+ LOCK_ICON_SECURE,
+ LOCK_ICON_MIXED,
+ }
+
+ Activity mActivity;
+ private WebViewController mWebViewController;
+
// The Geolocation permissions prompt
private GeolocationPermissionsPrompt mGeolocationPermissionsPrompt;
// Main WebView wrapper
- private LinearLayout mContainer;
+ private View mContainer;
// Main WebView
private WebView mMainView;
// Subwindow container
@@ -98,8 +102,6 @@
// information needed to restore the WebView if the user goes back to the
// tab.
private Bundle mSavedState;
- // Data used when displaying the tab in the picker.
- private PickerData mPickerData;
// Parent Tab. This is the Tab that created this Tab, or null if the Tab was
// created by the UI
private Tab mParentTab;
@@ -110,8 +112,11 @@
private boolean mCloseOnExit;
// If true, the tab is in the foreground of the current activity.
private boolean mInForeground;
- // If true, the tab is in loading state.
- private boolean mInLoad;
+ // If true, the tab is in page loading state (after onPageStarted,
+ // before onPageFinsihed)
+ private boolean mInPageLoad;
+ // The last reported progress of the current page
+ private int mPageLoadProgress;
// The time the load started, used to find load page time
private long mLoadStartTime;
// Application identifier used to find tabs that another application wants
@@ -119,33 +124,63 @@
private String mAppId;
// Keep the original url around to avoid killing the old WebView if the url
// has not changed.
- private String mOriginalUrl;
// Error console for the tab
private ErrorConsoleView mErrorConsole;
- // the lock icon type and previous lock icon type for the tab
- private int mLockIconType;
- private int mPrevLockIconType;
- // Inflation service for making subwindows.
- private final LayoutInflater mInflateService;
- // The BrowserActivity which owners the Tab
- private final BrowserActivity mActivity;
// The listener that gets invoked when a download is started from the
// mMainView
private final DownloadListener mDownloadListener;
// Listener used to know when we move forward or back in the history list.
private final WebBackForwardListClient mWebBackForwardListClient;
+ private DataController mDataController;
// AsyncTask for downloading touch icons
DownloadTouchIcon mTouchIconLoader;
- // Extra saved information for displaying the tab in the picker.
- private static class PickerData {
- String mUrl;
- String mTitle;
- Bitmap mFavicon;
+ // All the state needed for a page
+ private static class PageState {
+ String mUrl;
+ String mTitle;
+ LockIcon mLockIcon;
+ Bitmap mFavicon;
+ Boolean mIsBookmarkedSite = false;
+
+ PageState(Context c, boolean incognito) {
+ if (incognito) {
+ mUrl = "browser:incognito";
+ mTitle = c.getString(R.string.new_incognito_tab);
+ } else {
+ mUrl = "";
+ mTitle = c.getString(R.string.new_tab);
+ }
+ mFavicon = BitmapFactory.decodeResource(
+ c.getResources(), R.drawable.app_web_browser_sm);
+ mLockIcon = LockIcon.LOCK_ICON_UNSECURE;
+ }
+
+ PageState(Context c, boolean incognito, String url, Bitmap favicon) {
+ mUrl = url;
+ mTitle = null;
+ if (URLUtil.isHttpsUrl(url)) {
+ mLockIcon = LockIcon.LOCK_ICON_SECURE;
+ } else {
+ mLockIcon = LockIcon.LOCK_ICON_UNSECURE;
+ }
+ if (favicon != null) {
+ mFavicon = favicon;
+ } else {
+ mFavicon = BitmapFactory.decodeResource(
+ c.getResources(), R.drawable.app_web_browser_sm);
+ }
+ }
}
+ // The current/loading page's state
+ private PageState mCurrentState;
+
// Used for saving and restoring each Tab
+ // TODO: Figure out who uses what and where
+ // Some of these aren't use in this class, and some are only used in
+ // restoring state but not saving it - FIX THIS
static final String WEBVIEW = "webview";
static final String NUMTABS = "numTabs";
static final String CURRTAB = "currentTab";
@@ -155,6 +190,7 @@
static final String PARENTTAB = "parentTab";
static final String APPID = "appid";
static final String ORIGINALURL = "originalUrl";
+ static final String INCOGNITO = "privateBrowsingEnabled";
// -------------------------------------------------------------------------
@@ -170,10 +206,11 @@
if (mVoiceSearchData != null) {
mVoiceSearchData = null;
if (mInForeground) {
- mActivity.revertVoiceTitleBar();
+ mWebViewController.revertVoiceSearchMode(this);
}
}
}
+
/**
* Return whether the tab is in voice search mode.
*/
@@ -271,7 +308,7 @@
mVoiceSearchData.mLastVoiceSearchTitle
= mVoiceSearchData.mVoiceSearchResults.get(index);
if (mInForeground) {
- mActivity.showVoiceTitleBar(mVoiceSearchData.mLastVoiceSearchTitle);
+ mWebViewController.activateVoiceSearchMode(mVoiceSearchData.mLastVoiceSearchTitle);
}
if (mVoiceSearchData.mVoiceSearchHtmls != null) {
// When index was found it was already ensured that it was valid
@@ -298,7 +335,7 @@
mVoiceSearchData.mLastVoiceSearchUrl
= mVoiceSearchData.mVoiceSearchUrls.get(index);
if (null == mVoiceSearchData.mLastVoiceSearchUrl) {
- mVoiceSearchData.mLastVoiceSearchUrl = mActivity.smartUrlFilter(
+ mVoiceSearchData.mLastVoiceSearchUrl = UrlUtils.smartUrlFilter(
mVoiceSearchData.mLastVoiceSearchTitle);
}
Map<String, String> headers = null;
@@ -391,7 +428,7 @@
mDescription = desc;
mError = error;
}
- };
+ }
private void processNextError() {
if (mQueuedErrors == null) {
@@ -458,7 +495,10 @@
private Message mResend;
@Override
public void onPageStarted(WebView view, String url, Bitmap favicon) {
- mInLoad = true;
+ mInPageLoad = true;
+ mPageLoadProgress = 0;
+ mCurrentState = new PageState(mActivity,
+ view.isPrivateBrowsingEnabled(), url, favicon);
mLoadStartTime = SystemClock.uptimeMillis();
if (mVoiceSearchData != null
&& !url.equals(mVoiceSearchData.mLastVoiceSearchUrl)) {
@@ -470,12 +510,6 @@
revertVoiceSearchMode();
}
- // We've started to load a new page. If there was a pending message
- // to save a screenshot then we will now take the new page and save
- // an incorrect screenshot. Therefore, remove any pending thumbnail
- // messages from the queue.
- mActivity.removeMessages(BrowserActivity.UPDATE_BOOKMARK_THUMBNAIL,
- view);
// If we start a touch icon load and then load a new page, we don't
// want to cancel the current touch icon loader. But, we do want to
@@ -488,49 +522,37 @@
// reset the error console
if (mErrorConsole != null) {
mErrorConsole.clearErrorMessages();
- if (mActivity.shouldShowErrorConsole()) {
+ if (mWebViewController.shouldShowErrorConsole()) {
mErrorConsole.showConsole(ErrorConsoleView.SHOW_NONE);
}
}
- // update the bookmark database for favicon
- if (favicon != null) {
- BrowserBookmarksAdapter.updateBookmarkFavicon(mActivity
- .getContentResolver(), null, url, favicon);
- }
-
- // reset sync timer to avoid sync starts during loading a page
- CookieSyncManager.getInstance().resetSync();
-
- if (!mActivity.isNetworkUp()) {
- view.setNetworkAvailable(false);
- }
-
// finally update the UI in the activity if it is in the foreground
- if (mInForeground) {
- mActivity.onPageStarted(view, url, favicon);
- }
+ mWebViewController.onPageStarted(Tab.this, view, favicon);
+
+ updateBookmarkedStatus();
}
@Override
public void onPageFinished(WebView view, String url) {
- LogTag.logPageFinishedLoading(
- url, SystemClock.uptimeMillis() - mLoadStartTime);
- mInLoad = false;
-
- if (mInForeground && !mActivity.didUserStopLoading()
- || !mInForeground) {
- // Only update the bookmark screenshot if the user did not
- // cancel the load early.
- mActivity.postMessage(
- BrowserActivity.UPDATE_BOOKMARK_THUMBNAIL, 0, 0, view,
- 500);
+ if (!isPrivateBrowsingEnabled()) {
+ LogTag.logPageFinishedLoading(
+ url, SystemClock.uptimeMillis() - mLoadStartTime);
}
-
- // finally update the UI in the activity if it is in the foreground
- if (mInForeground) {
- mActivity.onPageFinished(view, url);
+ mInPageLoad = false;
+ // Sync state (in case of stop/timeout)
+ mCurrentState.mUrl = view.getUrl();
+ if (mCurrentState.mUrl == null) {
+ mCurrentState.mUrl = url != null ? url : "";
}
+ mCurrentState.mTitle = view.getTitle();
+ mCurrentState.mFavicon = view.getFavicon();
+ if (!URLUtil.isHttpsUrl(mCurrentState.mUrl)) {
+ // In case we stop when loading an HTTPS page from an HTTP page
+ // but before a provisional load occurred
+ mCurrentState.mLockIcon = LockIcon.LOCK_ICON_UNSECURE;
+ }
+ mWebViewController.onPageFinished(Tab.this);
}
// return true if want to hijack the url to let another app to handle it
@@ -549,7 +571,8 @@
mActivity.sendBroadcast(logIntent);
}
if (mInForeground) {
- return mActivity.shouldOverrideUrlLoading(view, url);
+ return mWebViewController.shouldOverrideUrlLoading(Tab.this,
+ view, url);
} else {
return false;
}
@@ -566,11 +589,11 @@
if (url != null && url.length() > 0) {
// It is only if the page claims to be secure that we may have
// to update the lock:
- if (mLockIconType == BrowserActivity.LOCK_ICON_SECURE) {
+ if (mCurrentState.mLockIcon == LockIcon.LOCK_ICON_SECURE) {
// If NOT a 'safe' url, change the lock to mixed content!
if (!(URLUtil.isHttpsUrl(url) || URLUtil.isDataUrl(url)
|| URLUtil.isAboutUrl(url))) {
- mLockIconType = BrowserActivity.LOCK_ICON_MIXED;
+ mCurrentState.mLockIcon = LockIcon.LOCK_ICON_MIXED;
}
}
}
@@ -590,12 +613,11 @@
errorCode != WebViewClient.ERROR_FILE) {
queueError(errorCode, description);
}
- Log.e(LOGTAG, "onReceivedError " + errorCode + " " + failingUrl
- + " " + description);
- // We need to reset the title after an error if it is in foreground.
- if (mInForeground) {
- mActivity.resetTitleAndRevertLockIcon();
+ // Don't log URLs when in private browsing mode
+ if (!isPrivateBrowsingEnabled()) {
+ Log.e(LOGTAG, "onReceivedError " + errorCode + " " + failingUrl
+ + " " + description);
}
}
@@ -661,31 +683,7 @@
@Override
public void doUpdateVisitedHistory(WebView view, String url,
boolean isReload) {
- if (url.regionMatches(true, 0, "about:", 0, 6)) {
- return;
- }
- // remove "client" before updating it to the history so that it wont
- // show up in the auto-complete list.
- int index = url.indexOf("client=ms-");
- if (index > 0 && url.contains(".google.")) {
- int end = url.indexOf('&', index);
- if (end > 0) {
- url = url.substring(0, index)
- .concat(url.substring(end + 1));
- } else {
- // the url.charAt(index-1) should be either '?' or '&'
- url = url.substring(0, index-1);
- }
- }
- final ContentResolver cr = mActivity.getContentResolver();
- final String newUrl = url;
- new AsyncTask<Void, Void, Void>() {
- protected Void doInBackground(Void... unused) {
- Browser.updateVisitedHistory(cr, newUrl, true);
- return null;
- }
- }.execute();
- WebIconDatabase.getInstance().retainIconForPageUrl(url);
+ mWebViewController.doUpdateVisitedHistory(Tab.this, isReload);
}
/**
@@ -696,6 +694,7 @@
final SslErrorHandler handler, final SslError error) {
if (!mInForeground) {
handler.cancel();
+ setLockIconType(LockIcon.LOCK_ICON_UNSECURE);
return;
}
if (BrowserSettings.getInstance().showSecurityWarnings()) {
@@ -751,21 +750,21 @@
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog,
int whichButton) {
- mActivity.showSSLCertificateOnError(view,
+ mWebViewController.showSslCertificateOnError(view,
handler, error);
}
- }).setNegativeButton(R.string.cancel,
+ }).setNegativeButton(R.string.ssl_go_back,
new DialogInterface.OnClickListener() {
public void onClick(DialogInterface dialog,
int whichButton) {
- handler.cancel();
- mActivity.resetTitleAndRevertLockIcon();
+ dialog.cancel();
}
}).setOnCancelListener(
new DialogInterface.OnCancelListener() {
public void onCancel(DialogInterface dialog) {
handler.cancel();
- mActivity.resetTitleAndRevertLockIcon();
+ setLockIconType(LockIcon.LOCK_ICON_UNSECURE);
+ mWebViewController.onUserCanceledSsl(Tab.this);
}
}).show();
} else {
@@ -784,31 +783,15 @@
public void onReceivedHttpAuthRequest(WebView view,
final HttpAuthHandler handler, final String host,
final String realm) {
- String username = null;
- String password = null;
+ mWebViewController.onReceivedHttpAuthRequest(Tab.this, view, handler, host, realm);
+ }
- boolean reuseHttpAuthUsernamePassword = handler
- .useHttpAuthUsernamePassword();
-
- if (reuseHttpAuthUsernamePassword && view != null) {
- String[] credentials = view.getHttpAuthUsernamePassword(
- host, realm);
- if (credentials != null && credentials.length == 2) {
- username = credentials[0];
- password = credentials[1];
- }
- }
-
- if (username != null && password != null) {
- handler.proceed(username, password);
- } else {
- if (mInForeground) {
- mActivity.showHttpAuthentication(handler, host, realm,
- null, null, null, 0);
- } else {
- handler.cancel();
- }
- }
+ @Override
+ public WebResourceResponse shouldInterceptRequest(WebView view,
+ String url) {
+ WebResourceResponse res = HomeProvider.shouldInterceptRequest(
+ mActivity, url);
+ return res;
}
@Override
@@ -816,25 +799,15 @@
if (!mInForeground) {
return false;
}
- if (mActivity.isMenuDown()) {
- // only check shortcut key when MENU is held
- return mActivity.getWindow().isShortcutKey(event.getKeyCode(),
- event);
- } else {
- return false;
- }
+ return mWebViewController.shouldOverrideKeyEvent(event);
}
@Override
public void onUnhandledKeyEvent(WebView view, KeyEvent event) {
- if (!mInForeground || mActivity.mActivityInPause) {
+ if (!mInForeground) {
return;
}
- if (event.isDown()) {
- mActivity.onKeyDown(event.getKeyCode(), event);
- } else {
- mActivity.onKeyUp(event.getKeyCode(), event);
- }
+ mWebViewController.onUnhandledKeyEvent(event);
}
};
@@ -849,11 +822,12 @@
(WebView.WebViewTransport) msg.obj;
if (dialog) {
createSubWindow();
- mActivity.attachSubWindow(Tab.this);
+ mWebViewController.attachSubWindow(Tab.this);
transport.setWebView(mSubView);
} else {
- final Tab newTab = mActivity.openTabAndShow(
- BrowserActivity.EMPTY_URL_DATA, false, null);
+ final Tab newTab = mWebViewController.openTabAndShow(
+ Tab.this,
+ IntentHandler.EMPTY_URL_DATA, false, null);
if (newTab != Tab.this) {
Tab.this.addChildTab(newTab);
}
@@ -878,7 +852,7 @@
.setPositiveButton(R.string.ok, null)
.show();
return false;
- } else if (!mActivity.getTabControl().canCreateNewTab()) {
+ } else if (!mWebViewController.getTabControl().canCreateNewTab()) {
new AlertDialog.Builder(mActivity)
.setTitle(R.string.too_many_windows_dialog_title)
.setIcon(android.R.drawable.ic_dialog_alert)
@@ -930,7 +904,7 @@
@Override
public void onRequestFocus(WebView view) {
if (!mInForeground) {
- mActivity.switchToTab(mActivity.getTabControl().getTabIndex(
+ mWebViewController.switchToTab(mWebViewController.getTabControl().getTabIndex(
Tab.this));
}
}
@@ -940,94 +914,29 @@
if (mParentTab != null) {
// JavaScript can only close popup window.
if (mInForeground) {
- mActivity.switchToTab(mActivity.getTabControl()
+ mWebViewController.switchToTab(mWebViewController.getTabControl()
.getTabIndex(mParentTab));
}
- mActivity.closeTab(Tab.this);
+ mWebViewController.closeTab(Tab.this);
}
}
@Override
public void onProgressChanged(WebView view, int newProgress) {
- if (newProgress == 100) {
- // sync cookies and cache promptly here.
- CookieSyncManager.getInstance().sync();
- }
- if (mInForeground) {
- mActivity.onProgressChanged(view, newProgress);
- }
+ mPageLoadProgress = newProgress;
+ mWebViewController.onProgressChanged(Tab.this);
}
@Override
public void onReceivedTitle(WebView view, final String title) {
- final String pageUrl = view.getUrl();
- if (mInForeground) {
- // here, if url is null, we want to reset the title
- mActivity.setUrlTitle(pageUrl, title);
- }
- if (pageUrl == null || pageUrl.length()
- >= SQLiteDatabase.SQLITE_MAX_LIKE_PATTERN_LENGTH) {
- return;
- }
- new AsyncTask<Void, Void, Void>() {
- protected Void doInBackground(Void... unused) {
- // See if we can find the current url in our history
- // database and add the new title to it.
- String url = pageUrl;
- if (url.startsWith("http://www.")) {
- url = url.substring(11);
- } else if (url.startsWith("http://")) {
- url = url.substring(4);
- }
- // Escape wildcards for LIKE operator.
- url = url.replace("\\", "\\\\").replace("%", "\\%")
- .replace("_", "\\_");
- Cursor c = null;
- try {
- final ContentResolver cr
- = mActivity.getContentResolver();
- url = "%" + url;
- String [] selArgs = new String[] { url };
- String where = Browser.BookmarkColumns.URL
- + " LIKE ? ESCAPE '\\' AND "
- + Browser.BookmarkColumns.BOOKMARK + " = 0";
- c = cr.query(Browser.BOOKMARKS_URI, new String[]
- { Browser.BookmarkColumns._ID }, where, selArgs,
- null);
- if (c.moveToFirst()) {
- // Current implementation of database only has one
- // entry per url.
- ContentValues map = new ContentValues();
- map.put(Browser.BookmarkColumns.TITLE, title);
- String[] projection = new String[]
- { Integer.valueOf(c.getInt(0)).toString() };
- cr.update(Browser.BOOKMARKS_URI, map, "_id = ?",
- projection);
- }
- } catch (IllegalStateException e) {
- Log.e(LOGTAG, "Tab onReceived title", e);
- } catch (SQLiteException ex) {
- Log.e(LOGTAG,
- "onReceivedTitle() caught SQLiteException: ",
- ex);
- } finally {
- if (c != null) c.close();
- }
- return null;
- }
- }.execute();
+ mCurrentState.mTitle = title;
+ mWebViewController.onReceivedTitle(Tab.this, title);
}
@Override
public void onReceivedIcon(WebView view, Bitmap icon) {
- if (icon != null) {
- BrowserBookmarksAdapter.updateBookmarkFavicon(mActivity
- .getContentResolver(), view.getOriginalUrl(), view
- .getUrl(), icon);
- }
- if (mInForeground) {
- mActivity.setFavicon(icon);
- }
+ mCurrentState.mFavicon = icon;
+ mWebViewController.onFavicon(Tab.this, view, icon);
}
@Override
@@ -1042,30 +951,22 @@
}
// Have only one async task at a time.
if (mTouchIconLoader == null) {
- mTouchIconLoader = new DownloadTouchIcon(Tab.this, mActivity, cr, view);
+ mTouchIconLoader = new DownloadTouchIcon(Tab.this,
+ mActivity, cr, view);
mTouchIconLoader.execute(url);
}
}
@Override
- public void onSelectionDone(WebView view) {
- if (mInForeground) mActivity.closeDialogs();
- }
-
- @Override
- public void onSelectionStart(WebView view) {
- if (false && mInForeground) mActivity.showSelectDialog();
- }
-
- @Override
public void onShowCustomView(View view,
WebChromeClient.CustomViewCallback callback) {
- if (mInForeground) mActivity.onShowCustomView(view, callback);
+ if (mInForeground) mWebViewController.showCustomView(Tab.this, view,
+ callback);
}
@Override
public void onHideCustomView() {
- if (mInForeground) mActivity.onHideCustomView();
+ if (mInForeground) mWebViewController.hideCustomView();
}
/**
@@ -1144,12 +1045,16 @@
// call getErrorConsole(true) so it will create one if needed
ErrorConsoleView errorConsole = getErrorConsole(true);
errorConsole.addErrorMessage(consoleMessage);
- if (mActivity.shouldShowErrorConsole()
- && errorConsole.getShowState() != ErrorConsoleView.SHOW_MAXIMIZED) {
+ if (mWebViewController.shouldShowErrorConsole()
+ && errorConsole.getShowState() !=
+ ErrorConsoleView.SHOW_MAXIMIZED) {
errorConsole.showConsole(ErrorConsoleView.SHOW_MINIMIZED);
}
}
+ // Don't log console messages in private browsing mode
+ if (isPrivateBrowsingEnabled()) return true;
+
String message = "Console: " + consoleMessage.message() + " "
+ consoleMessage.sourceId() + ":"
+ consoleMessage.lineNumber();
@@ -1183,7 +1088,7 @@
@Override
public Bitmap getDefaultVideoPoster() {
if (mInForeground) {
- return mActivity.getDefaultVideoPoster();
+ return mWebViewController.getDefaultVideoPoster();
}
return null;
}
@@ -1196,15 +1101,15 @@
@Override
public View getVideoLoadingProgressView() {
if (mInForeground) {
- return mActivity.getVideoLoadingProgressView();
+ return mWebViewController.getVideoLoadingProgressView();
}
return null;
}
@Override
- public void openFileChooser(ValueCallback<Uri> uploadMsg) {
+ public void openFileChooser(ValueCallback<Uri> uploadMsg, String acceptType) {
if (mInForeground) {
- mActivity.openFileChooser(uploadMsg);
+ mWebViewController.openFileChooser(uploadMsg, acceptType);
} else {
uploadMsg.onReceiveValue(null);
}
@@ -1215,17 +1120,45 @@
*/
@Override
public void getVisitedHistory(final ValueCallback<String[]> callback) {
- AsyncTask<Void, Void, String[]> task = new AsyncTask<Void, Void, String[]>() {
- public String[] doInBackground(Void... unused) {
- return Browser.getVisitedHistory(mActivity
- .getContentResolver());
- }
- public void onPostExecute(String[] result) {
- callback.onReceiveValue(result);
- };
- };
- task.execute();
- };
+ mWebViewController.getVisitedHistory(callback);
+ }
+
+ @Override
+ public void setupAutoFill(Message message) {
+ // Prompt the user to set up their profile.
+ final Message msg = message;
+ AlertDialog.Builder builder = new AlertDialog.Builder(mActivity);
+ LayoutInflater inflater = (LayoutInflater) mActivity.getSystemService(
+ Context.LAYOUT_INFLATER_SERVICE);
+ final View layout = inflater.inflate(R.layout.setup_autofill_dialog, null);
+
+ builder.setView(layout)
+ .setPositiveButton(R.string.ok, new DialogInterface.OnClickListener() {
+ @Override
+ public void onClick(DialogInterface dialog, int id) {
+ CheckBox disableAutoFill = (CheckBox) layout.findViewById(
+ R.id.setup_autofill_dialog_disable_autofill);
+
+ if (disableAutoFill.isChecked()) {
+ // Disable autofill and show a toast with how to turn it on again.
+ BrowserSettings s = BrowserSettings.getInstance();
+ s.addObserver(mMainView.getSettings());
+ s.disableAutoFill(mActivity);
+ s.update();
+ Toast.makeText(mActivity,
+ R.string.autofill_setup_dialog_negative_toast,
+ Toast.LENGTH_LONG).show();
+ } else {
+ // Take user to the AutoFill profile editor. When they return,
+ // we will send the message that we pass here which will trigger
+ // the form to get filled out with their new profile.
+ mWebViewController.setupAutoFill(msg);
+ }
+ }
+ })
+ .setNegativeButton(R.string.cancel, null)
+ .show();
+ }
};
// -------------------------------------------------------------------------
@@ -1237,18 +1170,18 @@
private static class SubWindowClient extends WebViewClient {
// The main WebViewClient.
private final WebViewClient mClient;
- private final BrowserActivity mBrowserActivity;
+ private final WebViewController mController;
- SubWindowClient(WebViewClient client, BrowserActivity activity) {
+ SubWindowClient(WebViewClient client, WebViewController controller) {
mClient = client;
- mBrowserActivity = activity;
+ mController = controller;
}
@Override
public void onPageStarted(WebView view, String url, Bitmap favicon) {
// Unlike the others, do not call mClient's version, which would
// change the progress bar. However, we do want to remove the
// find or select dialog.
- mBrowserActivity.closeDialogs();
+ mController.endActionMode();
}
@Override
public void doUpdateVisitedHistory(WebView view, String url,
@@ -1316,48 +1249,33 @@
if (window != mSubView) {
Log.e(LOGTAG, "Can't close the window");
}
- mActivity.dismissSubWindow(Tab.this);
+ mWebViewController.dismissSubWindow(Tab.this);
}
}
// -------------------------------------------------------------------------
+ // TODO temporarily use activity here
+ // remove later
+
// Construct a new tab
- Tab(BrowserActivity activity, WebView w, boolean closeOnExit, String appId,
+ Tab(WebViewController wvcontroller, WebView w, boolean closeOnExit, String appId,
String url) {
- mActivity = activity;
+ mWebViewController = wvcontroller;
+ mActivity = mWebViewController.getActivity();
mCloseOnExit = closeOnExit;
mAppId = appId;
- mOriginalUrl = url;
- mLockIconType = BrowserActivity.LOCK_ICON_UNSECURE;
- mPrevLockIconType = BrowserActivity.LOCK_ICON_UNSECURE;
- mInLoad = false;
+ mDataController = DataController.getInstance(mActivity);
+ mCurrentState = new PageState(mActivity, w.isPrivateBrowsingEnabled());
+ mInPageLoad = false;
mInForeground = false;
- mInflateService = LayoutInflater.from(activity);
-
- // The tab consists of a container view, which contains the main
- // WebView, as well as any other UI elements associated with the tab.
- mContainer = (LinearLayout) mInflateService.inflate(R.layout.tab, null);
-
mDownloadListener = new DownloadListener() {
public void onDownloadStart(String url, String userAgent,
String contentDisposition, String mimetype,
long contentLength) {
- mActivity.onDownloadStart(url, userAgent, contentDisposition,
+ mWebViewController.onDownloadStart(Tab.this, url, userAgent, contentDisposition,
mimetype, contentLength);
- if (mMainView.copyBackForwardList().getSize() == 0) {
- // This Tab was opened for the sole purpose of downloading a
- // file. Remove it.
- if (mActivity.getTabControl().getCurrentWebView()
- == mMainView) {
- // In this case, the Tab is still on top.
- mActivity.goBackOnePageOrQuit();
- } else {
- // In this case, it is not.
- mActivity.closeTab(Tab.this);
- }
- }
}
};
mWebBackForwardListClient = new WebBackForwardListClient() {
@@ -1387,16 +1305,14 @@
if (mMainView == w) {
return;
}
+
// If the WebView is changing, the page will be reloaded, so any ongoing
// Geolocation permission requests are void.
if (mGeolocationPermissionsPrompt != null) {
mGeolocationPermissionsPrompt.hide();
}
- // Just remove the old one.
- FrameLayout wrapper =
- (FrameLayout) mContainer.findViewById(R.id.webview_wrapper);
- wrapper.removeView(mMainView);
+ mWebViewController.onSetWebView(this, w);
// set the new one
mMainView = w;
@@ -1449,17 +1365,9 @@
*/
boolean createSubWindow() {
if (mSubView == null) {
- mActivity.closeDialogs();
- mSubViewContainer = mInflateService.inflate(
- R.layout.browser_subwindow, null);
- mSubView = (WebView) mSubViewContainer.findViewById(R.id.webview);
- mSubView.setScrollBarStyle(View.SCROLLBARS_OUTSIDE_OVERLAY);
- // use trackball directly
- mSubView.setMapTrackballToArrowKeys(false);
- // Enable the built-in zoom
- mSubView.getSettings().setBuiltInZoomControls(true);
+ mWebViewController.createSubWindow(this);
mSubView.setWebViewClient(new SubWindowClient(mWebViewClient,
- mActivity));
+ mWebViewController));
mSubView.setWebChromeClient(new SubWindowChromeClient(
mWebChromeClient));
// Set a different DownloadListener for the mSubView, since it will
@@ -1468,25 +1376,16 @@
public void onDownloadStart(String url, String userAgent,
String contentDisposition, String mimetype,
long contentLength) {
- mActivity.onDownloadStart(url, userAgent,
+ mWebViewController.onDownloadStart(Tab.this, url, userAgent,
contentDisposition, mimetype, contentLength);
if (mSubView.copyBackForwardList().getSize() == 0) {
// This subwindow was opened for the sole purpose of
// downloading a file. Remove it.
- mActivity.dismissSubWindow(Tab.this);
+ mWebViewController.dismissSubWindow(Tab.this);
}
}
});
mSubView.setOnCreateContextMenuListener(mActivity);
- final BrowserSettings s = BrowserSettings.getInstance();
- s.addObserver(mSubView.getSettings()).update(s, null);
- final ImageButton cancel = (ImageButton) mSubViewContainer
- .findViewById(R.id.subwindow_close);
- cancel.setOnClickListener(new OnClickListener() {
- public void onClick(View v) {
- mSubView.getWebChromeClient().onCloseWindow(mSubView);
- }
- });
return true;
}
return false;
@@ -1497,7 +1396,7 @@
*/
void dismissSubWindow() {
if (mSubView != null) {
- mActivity.closeDialogs();
+ mWebViewController.endActionMode();
BrowserSettings.getInstance().deleteObserver(
mSubView.getSettings());
mSubView.destroy();
@@ -1506,84 +1405,6 @@
}
}
- /**
- * Attach the sub window to the content view.
- */
- void attachSubWindow(ViewGroup content) {
- if (mSubView != null) {
- content.addView(mSubViewContainer,
- BrowserActivity.COVER_SCREEN_PARAMS);
- }
- }
-
- /**
- * Remove the sub window from the content view.
- */
- void removeSubWindow(ViewGroup content) {
- if (mSubView != null) {
- content.removeView(mSubViewContainer);
- mActivity.closeDialogs();
- }
- }
-
- /**
- * This method attaches both the WebView and any sub window to the
- * given content view.
- */
- void attachTabToContentView(ViewGroup content) {
- if (mMainView == null) {
- return;
- }
-
- // Attach the WebView to the container and then attach the
- // container to the content view.
- FrameLayout wrapper =
- (FrameLayout) mContainer.findViewById(R.id.webview_wrapper);
- ViewGroup parent = (ViewGroup) mMainView.getParent();
- if (parent != wrapper) {
- if (parent != null) {
- Log.w(LOGTAG, "mMainView already has a parent in"
- + " attachTabToContentView!");
- parent.removeView(mMainView);
- }
- wrapper.addView(mMainView);
- } else {
- Log.w(LOGTAG, "mMainView is already attached to wrapper in"
- + " attachTabToContentView!");
- }
- parent = (ViewGroup) mContainer.getParent();
- if (parent != content) {
- if (parent != null) {
- Log.w(LOGTAG, "mContainer already has a parent in"
- + " attachTabToContentView!");
- parent.removeView(mContainer);
- }
- content.addView(mContainer, BrowserActivity.COVER_SCREEN_PARAMS);
- } else {
- Log.w(LOGTAG, "mContainer is already attached to content in"
- + " attachTabToContentView!");
- }
- attachSubWindow(content);
- }
-
- /**
- * Remove the WebView and any sub window from the given content view.
- */
- void removeTabFromContentView(ViewGroup content) {
- if (mMainView == null) {
- return;
- }
-
- // Remove the container from the content and then remove the
- // WebView from the container. This will trigger a focus change
- // needed by WebView.
- FrameLayout wrapper =
- (FrameLayout) mContainer.findViewById(R.id.webview_wrapper);
- wrapper.removeView(mMainView);
- content.removeView(mContainer);
- mActivity.closeDialogs();
- removeSubWindow(content);
- }
/**
* Set the parent tab of this tab.
@@ -1598,7 +1419,7 @@
if (parent == null) {
mSavedState.remove(PARENTTAB);
} else {
- mSavedState.putInt(PARENTTAB, mActivity.getTabControl()
+ mSavedState.putInt(PARENTTAB, mWebViewController.getTabControl()
.getTabIndex(parent));
}
}
@@ -1650,6 +1471,7 @@
if (mQueuedErrors != null && mQueuedErrors.size() > 0) {
showError(mQueuedErrors.getFirst());
}
+ mWebViewController.bookmarkedStatusHasChanged(this);
}
void putInBackground() {
@@ -1661,6 +1483,10 @@
}
}
+ boolean inForeground() {
+ return mInForeground;
+ }
+
/**
* Return the top window of this tab; either the subwindow if it is not
* null or the main window.
@@ -1683,6 +1509,27 @@
return mMainView;
}
+ void setViewContainer(View container) {
+ mContainer = container;
+ }
+
+ View getViewContainer() {
+ return mContainer;
+ }
+
+ /**
+ * Return whether private browsing is enabled for the main window of
+ * this tab.
+ * @return True if private browsing is enabled.
+ */
+ boolean isPrivateBrowsingEnabled() {
+ WebView webView = getWebView();
+ if (webView == null) {
+ return false;
+ }
+ return webView.isPrivateBrowsingEnabled();
+ }
+
/**
* Return the subwindow of this tab or null if there is no subwindow.
* @return The subwindow of this tab or null.
@@ -1691,6 +1538,18 @@
return mSubView;
}
+ void setSubWebView(WebView subView) {
+ mSubView = subView;
+ }
+
+ View getSubViewContainer() {
+ return mSubViewContainer;
+ }
+
+ void setSubViewContainer(View subViewContainer) {
+ mSubViewContainer = subViewContainer;
+ }
+
/**
* @return The geolocation permissions prompt for this tab.
*/
@@ -1720,55 +1579,29 @@
mAppId = id;
}
- /**
- * @return The original url associated with this Tab
- */
- String getOriginalUrl() {
- return mOriginalUrl;
- }
-
- /**
- * Set the original url associated with this tab
- */
- void setOriginalUrl(String url) {
- mOriginalUrl = url;
- }
-
- /**
- * Get the url of this tab. Valid after calling populatePickerData, but
- * before calling wipePickerData, or if the webview has been destroyed.
- * @return The WebView's url or null.
- */
String getUrl() {
- if (mPickerData != null) {
- return mPickerData.mUrl;
- }
- return null;
+ return UrlUtils.filteredUrl(mCurrentState.mUrl);
}
/**
- * Get the title of this tab. Valid after calling populatePickerData, but
- * before calling wipePickerData, or if the webview has been destroyed. If
- * the url has no title, use the url instead.
- * @return The WebView's title (or url) or null.
+ * Get the title of this tab.
*/
String getTitle() {
- if (mPickerData != null) {
- return mPickerData.mTitle;
+ if (mCurrentState.mTitle == null && mInPageLoad) {
+ return mActivity.getString(R.string.title_bar_loading);
}
- return null;
+ return mCurrentState.mTitle;
}
/**
- * Get the favicon of this tab. Valid after calling populatePickerData, but
- * before calling wipePickerData, or if the webview has been destroyed.
- * @return The WebView's favicon or null.
+ * Get the favicon of this tab.
*/
Bitmap getFavicon() {
- if (mPickerData != null) {
- return mPickerData.mFavicon;
- }
- return null;
+ return mCurrentState.mFavicon;
+ }
+
+ public boolean isBookmarkedSite() {
+ return mCurrentState.mIsBookmarkedSite;
}
/**
@@ -1805,91 +1638,42 @@
return mCloseOnExit;
}
- /**
- * Saves the current lock-icon state before resetting the lock icon. If we
- * have an error, we may need to roll back to the previous state.
- */
- void resetLockIcon(String url) {
- mPrevLockIconType = mLockIconType;
- mLockIconType = BrowserActivity.LOCK_ICON_UNSECURE;
- if (URLUtil.isHttpsUrl(url)) {
- mLockIconType = BrowserActivity.LOCK_ICON_SECURE;
- }
- }
-
- /**
- * Reverts the lock-icon state to the last saved state, for example, if we
- * had an error, and need to cancel the load.
- */
- void revertLockIcon() {
- mLockIconType = mPrevLockIconType;
+ private void setLockIconType(LockIcon icon) {
+ mCurrentState.mLockIcon = icon;
+ mWebViewController.onUpdatedLockIcon(this);
}
/**
* @return The tab's lock icon type.
*/
- int getLockIconType() {
- return mLockIconType;
+ LockIcon getLockIconType() {
+ return mCurrentState.mLockIcon;
+ }
+
+ int getLoadProgress() {
+ if (mInPageLoad) {
+ return mPageLoadProgress;
+ }
+ return 100;
}
/**
* @return TRUE if onPageStarted is called while onPageFinished is not
* called yet.
*/
- boolean inLoad() {
- return mInLoad;
+ boolean inPageLoad() {
+ return mInPageLoad;
}
// force mInLoad to be false. This should only be called before closing the
// tab to ensure BrowserActivity's pauseWebViewTimers() is called correctly.
- void clearInLoad() {
- mInLoad = false;
- }
-
- void populatePickerData() {
- if (mMainView == null) {
- populatePickerDataFromSavedState();
- return;
- }
-
- // FIXME: The only place we cared about subwindow was for
- // bookmarking (i.e. not when saving state). Was this deliberate?
- final WebBackForwardList list = mMainView.copyBackForwardList();
- final WebHistoryItem item = list != null ? list.getCurrentItem() : null;
- populatePickerData(item);
- }
-
- // Populate the picker data using the given history item and the current top
- // WebView.
- private void populatePickerData(WebHistoryItem item) {
- mPickerData = new PickerData();
- if (item != null) {
- mPickerData.mUrl = item.getUrl();
- mPickerData.mTitle = item.getTitle();
- mPickerData.mFavicon = item.getFavicon();
- if (mPickerData.mTitle == null) {
- mPickerData.mTitle = mPickerData.mUrl;
- }
- }
- }
-
- // Create the PickerData and populate it using the saved state of the tab.
- void populatePickerDataFromSavedState() {
- if (mSavedState == null) {
- return;
- }
- mPickerData = new PickerData();
- mPickerData.mUrl = mSavedState.getString(CURRURL);
- mPickerData.mTitle = mSavedState.getString(CURRTITLE);
- }
-
- void clearPickerData() {
- mPickerData = null;
+ void clearInPageLoad() {
+ mInPageLoad = false;
}
/**
- * Get the saved state bundle.
- * @return
+ * Get the cached saved state bundle.
+ * @return cached state bundle
*/
Bundle getSavedState() {
return mSavedState;
@@ -1917,24 +1701,16 @@
// Store some extra info for displaying the tab in the picker.
final WebHistoryItem item = list != null ? list.getCurrentItem() : null;
- populatePickerData(item);
- if (mPickerData.mUrl != null) {
- mSavedState.putString(CURRURL, mPickerData.mUrl);
- }
- if (mPickerData.mTitle != null) {
- mSavedState.putString(CURRTITLE, mPickerData.mTitle);
- }
+ mSavedState.putString(CURRURL, mCurrentState.mUrl);
+ mSavedState.putString(CURRTITLE, mCurrentState.mTitle);
mSavedState.putBoolean(CLOSEONEXIT, mCloseOnExit);
if (mAppId != null) {
mSavedState.putString(APPID, mAppId);
}
- if (mOriginalUrl != null) {
- mSavedState.putString(ORIGINALURL, mOriginalUrl);
- }
// Remember the parent tab so the relationship can be restored.
if (mParentTab != null) {
- mSavedState.putInt(PARENTTAB, mActivity.getTabControl().getTabIndex(
+ mSavedState.putInt(PARENTTAB, mWebViewController.getTabControl().getTabIndex(
mParentTab));
}
return true;
@@ -1950,10 +1726,8 @@
// Restore the internal state even if the WebView fails to restore.
// This will maintain the app id, original url and close-on-exit values.
mSavedState = null;
- mPickerData = null;
mCloseOnExit = b.getBoolean(CLOSEONEXIT);
mAppId = b.getString(APPID);
- mOriginalUrl = b.getString(ORIGINALURL);
final WebBackForwardList list = mMainView.restoreState(b);
if (list == null) {
@@ -1962,35 +1736,18 @@
return true;
}
- /*
- * Opens the find and select text dialogs. Called by BrowserActivity.
- */
- WebView showDialog(WebDialog dialog) {
- LinearLayout container;
- WebView view;
- if (mSubView != null) {
- view = mSubView;
- container = (LinearLayout) mSubViewContainer.findViewById(
- R.id.inner_container);
- } else {
- view = mMainView;
- container = mContainer;
- }
- dialog.show();
- container.addView(dialog, 0, new LinearLayout.LayoutParams(
- ViewGroup.LayoutParams.MATCH_PARENT,
- ViewGroup.LayoutParams.WRAP_CONTENT));
- dialog.setWebView(view);
- return view;
+ public void updateBookmarkedStatus() {
+ mDataController.queryBookmarkStatus(getUrl(), mIsBookmarkCallback);
}
- /*
- * Close the find or select dialog. Called by BrowserActivity.closeDialog.
- */
- void closeDialog(WebDialog dialog) {
- // The dialog may be attached to the subwindow. Ensure that the
- // correct parent has it removed.
- LinearLayout parent = (LinearLayout) dialog.getParent();
- if (parent != null) parent.removeView(dialog);
- }
+ private DataController.OnQueryUrlIsBookmark mIsBookmarkCallback
+ = new DataController.OnQueryUrlIsBookmark() {
+ @Override
+ public void onQueryUrlIsBookmark(String url, boolean isBookmark) {
+ if (mCurrentState.mUrl.equals(url)) {
+ mCurrentState.mIsBookmarkedSite = isBookmark;
+ mWebViewController.bookmarkedStatusHasChanged(Tab.this);
+ }
+ }
+ };
}
diff --git a/src/com/android/browser/TabBar.java b/src/com/android/browser/TabBar.java
new file mode 100644
index 0000000..d115f1a
--- /dev/null
+++ b/src/com/android/browser/TabBar.java
@@ -0,0 +1,645 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.ScrollWebView.ScrollListener;
+
+import android.animation.Animator;
+import android.animation.Animator.AnimatorListener;
+import android.animation.AnimatorSet;
+import android.animation.ObjectAnimator;
+import android.app.Activity;
+import android.content.Context;
+import android.content.res.Resources;
+import android.graphics.Bitmap;
+import android.graphics.BitmapShader;
+import android.graphics.Canvas;
+import android.graphics.Matrix;
+import android.graphics.Paint;
+import android.graphics.Path;
+import android.graphics.Shader;
+import android.graphics.drawable.BitmapDrawable;
+import android.graphics.drawable.Drawable;
+import android.graphics.drawable.LayerDrawable;
+import android.graphics.drawable.PaintDrawable;
+import android.view.ContextMenu;
+import android.view.Gravity;
+import android.view.LayoutInflater;
+import android.view.MenuInflater;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.webkit.WebView;
+import android.widget.ImageButton;
+import android.widget.ImageView;
+import android.widget.LinearLayout;
+import android.widget.TextView;
+
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+/**
+ * tabbed title bar for xlarge screen browser
+ */
+public class TabBar extends LinearLayout
+ implements ScrollListener, OnClickListener {
+
+ private static final int PROGRESS_MAX = 100;
+
+ private Activity mActivity;
+ private UiController mUiController;
+ private TabControl mTabControl;
+ private XLargeUi mUi;
+
+ private final int mTabWidthSelected;
+ private final int mTabWidthUnselected;
+
+ private TabScrollView mTabs;
+
+ private ImageButton mNewTab;
+ private int mButtonWidth;
+
+ private Map<Tab, TabView> mTabMap;
+
+ private int mVisibleTitleHeight;
+
+ private Drawable mGenericFavicon;
+
+ private int mCurrentTextureWidth = 0;
+ private int mCurrentTextureHeight = 0;
+
+ private Drawable mActiveDrawable;
+ private Drawable mInactiveDrawable;
+
+ private final Paint mActiveShaderPaint = new Paint();
+ private final Paint mInactiveShaderPaint = new Paint();
+ private final Matrix mActiveMatrix = new Matrix();
+ private final Matrix mInactiveMatrix = new Matrix();
+
+ private BitmapShader mActiveShader;
+ private BitmapShader mInactiveShader;
+
+ private int mTabOverlap;
+ private int mAddTabOverlap;
+ private int mTabSliceWidth;
+ private int mTabPadding;
+ private boolean mUseQuickControls;
+
+ public TabBar(Activity activity, UiController controller, XLargeUi ui) {
+ super(activity);
+ mActivity = activity;
+ mUiController = controller;
+ mTabControl = mUiController.getTabControl();
+ mUi = ui;
+ Resources res = activity.getResources();
+ mTabWidthSelected = (int) res.getDimension(R.dimen.tab_width_selected);
+ mTabWidthUnselected = (int) res.getDimension(R.dimen.tab_width_unselected);
+ mActiveDrawable = res.getDrawable(R.drawable.bg_urlbar);
+ mInactiveDrawable = res.getDrawable(R.drawable.browsertab_inactive);
+
+ mTabMap = new HashMap<Tab, TabView>();
+ Resources resources = activity.getResources();
+ LayoutInflater factory = LayoutInflater.from(activity);
+ factory.inflate(R.layout.tab_bar, this);
+ setPadding(0, (int) res.getDimension(R.dimen.tab_padding_top), 0, 0);
+ mTabs = (TabScrollView) findViewById(R.id.tabs);
+ mNewTab = (ImageButton) findViewById(R.id.newtab);
+ mNewTab.setOnClickListener(this);
+ mGenericFavicon = res.getDrawable(R.drawable.app_web_browser_sm);
+
+ updateTabs(mUiController.getTabs());
+
+ mVisibleTitleHeight = 1;
+ mButtonWidth = -1;
+ // tab dimensions
+ mTabOverlap = (int) res.getDimension(R.dimen.tab_overlap);
+ mAddTabOverlap = (int) res.getDimension(R.dimen.tab_addoverlap);
+ mTabSliceWidth = (int) res.getDimension(R.dimen.tab_slice);
+ mTabPadding = (int) res.getDimension(R.dimen.tab_padding);
+
+ mActiveShaderPaint.setStyle(Paint.Style.FILL);
+ mActiveShaderPaint.setAntiAlias(true);
+
+ mInactiveShaderPaint.setStyle(Paint.Style.FILL);
+ mInactiveShaderPaint.setAntiAlias(true);
+
+ }
+
+ void setUseQuickControls(boolean useQuickControls) {
+ mUseQuickControls = useQuickControls;
+ mNewTab.setVisibility(mUseQuickControls ? View.GONE
+ : View.VISIBLE);
+ }
+
+ int getTabCount() {
+ return mTabMap.size();
+ }
+
+ void updateTabs(List<Tab> tabs) {
+ mTabs.clearTabs();
+ mTabMap.clear();
+ for (Tab tab : tabs) {
+ TabView tv = buildTabView(tab);
+ mTabs.addTab(tv);
+ }
+ mTabs.setSelectedTab(mTabControl.getCurrentIndex());
+ }
+
+ @Override
+ protected void onMeasure(int hspec, int vspec) {
+ super.onMeasure(hspec, vspec);
+ int w = getMeasuredWidth();
+ // adjust for new tab overlap
+ if (!mUseQuickControls) {
+ w -= mAddTabOverlap;
+ }
+ setMeasuredDimension(w, getMeasuredHeight());
+ }
+
+ @Override
+ protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
+ // use paddingLeft and paddingTop
+ int pl = getPaddingLeft();
+ int pt = getPaddingTop();
+ int sw = mTabs.getMeasuredWidth();
+ int w = right - left - pl;
+ if (mUseQuickControls) {
+ mButtonWidth = 0;
+ } else {
+ mButtonWidth = mNewTab.getMeasuredWidth() - mAddTabOverlap;
+ if (w-sw < mButtonWidth) {
+ sw = w - mButtonWidth;
+ }
+ }
+ mTabs.layout(pl, pt, pl + sw, bottom - top);
+ // adjust for overlap
+ if (!mUseQuickControls) {
+ mNewTab.layout(pl + sw - mAddTabOverlap, pt,
+ pl + sw + mButtonWidth - mAddTabOverlap, bottom - top);
+ }
+ }
+
+ public void onClick(View view) {
+ if (mNewTab == view) {
+ mUiController.openTabToHomePage();
+ } else if (mTabs.getSelectedTab() == view) {
+ if (mUseQuickControls) {
+ if (mUi.isFakeTitleBarShowing() && !isLoading()) {
+ mUi.hideFakeTitleBar();
+ } else {
+ mUi.stopWebViewScrolling();
+ mUi.showFakeTitleBarAndEdit();
+ }
+ } else if (mUi.isFakeTitleBarShowing() && !isLoading()) {
+ mUi.hideFakeTitleBar();
+ } else {
+ showUrlBar();
+ }
+ } else {
+ int ix = mTabs.getChildIndex(view);
+ if (ix >= 0) {
+ mTabs.setSelectedTab(ix);
+ mUiController.switchToTab(ix);
+ }
+ }
+ }
+
+ private void showUrlBar() {
+ mUi.stopWebViewScrolling();
+ mUi.showFakeTitleBar();
+ }
+
+ void showTitleBarIndicator(boolean show) {
+ Tab tab = mTabControl.getCurrentTab();
+ if (tab != null) {
+ TabView tv = mTabMap.get(tab);
+ if (tv != null) {
+ tv.showIndicator(show);
+ }
+ }
+ }
+
+ boolean showsTitleBarIndicator() {
+ Tab tab = mTabControl.getCurrentTab();
+ if (tab != null) {
+ TabView tv = mTabMap.get(tab);
+ if (tv != null) {
+ return tv.showsIndicator();
+ }
+ }
+ return false;
+ }
+
+ // callback after fake titlebar is shown
+ void onShowTitleBar() {
+ showTitleBarIndicator(false);
+ }
+
+ // callback after fake titlebar is hidden
+ void onHideTitleBar() {
+ showTitleBarIndicator(mVisibleTitleHeight == 0);
+ Tab tab = mTabControl.getCurrentTab();
+ tab.getWebView().requestFocus();
+ }
+
+ // webview scroll listener
+
+ @Override
+ public void onScroll(int visibleTitleHeight) {
+ if (mUseQuickControls) return;
+ // isLoading is using the current tab, which initially might not be set yet
+ if (mTabControl.getCurrentTab() != null
+ && !isLoading()) {
+ if (visibleTitleHeight == 0) {
+ if (!showsTitleBarIndicator()) {
+ mUi.hideFakeTitleBar();
+ showTitleBarIndicator(true);
+ }
+ } else {
+ if (showsTitleBarIndicator()) {
+ showTitleBarIndicator(false);
+ }
+ }
+ }
+ mVisibleTitleHeight = visibleTitleHeight;
+ }
+
+ @Override
+ public void createContextMenu(ContextMenu menu) {
+ MenuInflater inflater = mActivity.getMenuInflater();
+ inflater.inflate(R.menu.title_context, menu);
+ mActivity.onCreateContextMenu(menu, this, null);
+ }
+
+ private TabView buildTabView(Tab tab) {
+ TabView tabview = new TabView(mActivity, tab);
+ mTabMap.put(tab, tabview);
+ tabview.setOnClickListener(this);
+ return tabview;
+ }
+
+ private static Bitmap getDrawableAsBitmap(Drawable drawable, int width, int height) {
+ Bitmap b = Bitmap.createBitmap(width, height, Bitmap.Config.ARGB_8888);
+ Canvas c = new Canvas(b);
+ drawable.setBounds(0, 0, width, height);
+ drawable.draw(c);
+ return b;
+ }
+
+ /**
+ * View used in the tab bar
+ */
+ class TabView extends LinearLayout implements OnClickListener {
+
+ Tab mTab;
+ View mTabContent;
+ TextView mTitle;
+ View mIndicator;
+ View mIncognito;
+ ImageView mIconView;
+ ImageView mLock;
+ ImageView mClose;
+ boolean mSelected;
+ boolean mInLoad;
+ Path mPath;
+ int[] mWindowPos;
+
+ /**
+ * @param context
+ */
+ public TabView(Context context, Tab tab) {
+ super(context);
+ setWillNotDraw(false);
+ mPath = new Path();
+ mWindowPos = new int[2];
+ mTab = tab;
+ setGravity(Gravity.CENTER_VERTICAL);
+ setOrientation(LinearLayout.HORIZONTAL);
+ setPadding(mTabOverlap, 0, mTabSliceWidth, 0);
+ LayoutInflater inflater = LayoutInflater.from(getContext());
+ mTabContent = inflater.inflate(R.layout.tab_title, this, true);
+ mTitle = (TextView) mTabContent.findViewById(R.id.title);
+ mIconView = (ImageView) mTabContent.findViewById(R.id.favicon);
+ mLock = (ImageView) mTabContent.findViewById(R.id.lock);
+ mClose = (ImageView) mTabContent.findViewById(R.id.close);
+ mClose.setOnClickListener(this);
+ mIncognito = mTabContent.findViewById(R.id.incognito);
+ mIndicator = mTabContent.findViewById(R.id.chevron);
+ mSelected = false;
+ mInLoad = false;
+ // update the status
+ updateFromTab();
+ }
+
+ void showIndicator(boolean show) {
+ if (mSelected) {
+ mIndicator.setVisibility(show ? View.VISIBLE : View.GONE);
+ LayoutParams lp = (LinearLayout.LayoutParams) getLayoutParams();
+ if (show) {
+ lp.width = mTabWidthSelected + mIndicator.getWidth();
+ } else {
+ lp.width = mTabWidthSelected;
+ }
+ lp.height = LayoutParams.MATCH_PARENT;
+ setLayoutParams(lp);
+ } else {
+ mIndicator.setVisibility(View.GONE);
+ }
+ }
+
+ boolean showsIndicator() {
+ return (mIndicator.getVisibility() == View.VISIBLE);
+ }
+
+ @Override
+ public void onClick(View v) {
+ if (v == mClose) {
+ closeTab();
+ }
+ }
+
+ private void updateFromTab() {
+ String displayTitle = mTab.getTitle();
+ if (displayTitle == null) {
+ displayTitle = mTab.getUrl();
+ }
+ setDisplayTitle(displayTitle);
+ setProgress(mTab.getLoadProgress());
+ if (mTab.getFavicon() != null) {
+ setFavicon(renderFavicon(mTab.getFavicon()));
+ }
+ if (mTab != null) {
+ mIncognito.setVisibility(
+ mTab.isPrivateBrowsingEnabled() ?
+ View.VISIBLE : View.GONE);
+ }
+ }
+
+ @Override
+ public void setActivated(boolean selected) {
+ mSelected = selected;
+ mClose.setVisibility(mSelected ? View.VISIBLE : View.GONE);
+ mIndicator.setVisibility(View.GONE);
+ mTitle.setTextAppearance(mActivity, mSelected ?
+ R.style.TabTitleSelected : R.style.TabTitleUnselected);
+ setHorizontalFadingEdgeEnabled(!mSelected);
+ super.setActivated(selected);
+ LayoutParams lp = (LinearLayout.LayoutParams) getLayoutParams();
+ lp.width = selected ? mTabWidthSelected : mTabWidthUnselected;
+ lp.height = LayoutParams.MATCH_PARENT;
+ setLayoutParams(lp);
+ }
+
+ void setDisplayTitle(String title) {
+ mTitle.setText(title);
+ }
+
+ void setFavicon(Drawable d) {
+ mIconView.setImageDrawable(d);
+ }
+
+ void setLock(Drawable d) {
+ if (null == d) {
+ mLock.setVisibility(View.GONE);
+ } else {
+ mLock.setImageDrawable(d);
+ mLock.setVisibility(View.VISIBLE);
+ }
+ }
+
+ void setProgress(int newProgress) {
+ if (newProgress >= PROGRESS_MAX) {
+ mInLoad = false;
+ } else {
+ if (!mInLoad && getWindowToken() != null) {
+ mInLoad = true;
+ }
+ }
+ }
+
+ private void closeTab() {
+ if (mTab == mTabControl.getCurrentTab()) {
+ mUiController.closeCurrentTab();
+ } else {
+ mUiController.closeTab(mTab);
+ }
+ }
+
+ @Override
+ protected void onLayout(boolean changed, int l, int t, int r, int b) {
+ super.onLayout(changed, l, t, r, b);
+ setTabPath(mPath, 0, 0, r - l, b - t);
+ }
+
+ @Override
+ protected void dispatchDraw(Canvas canvas) {
+ if (mCurrentTextureWidth != mUi.getContentWidth() ||
+ mCurrentTextureHeight != getHeight()) {
+ mCurrentTextureWidth = mUi.getContentWidth();
+ mCurrentTextureHeight = getHeight();
+
+ if (mCurrentTextureWidth > 0 && mCurrentTextureHeight > 0) {
+ Bitmap activeTexture = getDrawableAsBitmap(mActiveDrawable,
+ mCurrentTextureWidth, mCurrentTextureHeight);
+ Bitmap inactiveTexture = getDrawableAsBitmap(mInactiveDrawable,
+ mCurrentTextureWidth, mCurrentTextureHeight);
+
+ mActiveShader = new BitmapShader(activeTexture,
+ Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);
+ mActiveShaderPaint.setShader(mActiveShader);
+
+ mInactiveShader = new BitmapShader(inactiveTexture,
+ Shader.TileMode.CLAMP, Shader.TileMode.CLAMP);
+ mInactiveShaderPaint.setShader(mInactiveShader);
+ }
+ }
+
+ int state = canvas.save();
+ getLocationInWindow(mWindowPos);
+ Paint paint = mSelected ? mActiveShaderPaint : mInactiveShaderPaint;
+ drawClipped(canvas, paint, mPath, mWindowPos[0]);
+ canvas.restoreToCount(state);
+ super.dispatchDraw(canvas);
+ }
+
+ private void drawClipped(Canvas canvas, Paint paint, Path clipPath, int left) {
+ // TODO: We should change the matrix/shader only when needed
+ final Matrix matrix = mSelected ? mActiveMatrix : mInactiveMatrix;
+ matrix.setTranslate(-left, 0.0f);
+ (mSelected ? mActiveShader : mInactiveShader).setLocalMatrix(matrix);
+ canvas.drawPath(clipPath, paint);
+ }
+
+ private void setTabPath(Path path, int l, int t, int r, int b) {
+ path.reset();
+ path.moveTo(l, b);
+ path.lineTo(l, t);
+ path.lineTo(r - mTabSliceWidth, t);
+ path.lineTo(r, b);
+ path.close();
+ }
+
+ }
+
+ static Drawable createFaviconBackground(Context context) {
+ PaintDrawable faviconBackground = new PaintDrawable();
+ Resources res = context.getResources();
+ faviconBackground.getPaint().setColor(context.getResources()
+ .getColor(R.color.tabFaviconBackground));
+ faviconBackground.setCornerRadius(
+ res.getDimension(R.dimen.tab_favicon_corner_radius));
+ return faviconBackground;
+ }
+
+ private Drawable renderFavicon(Bitmap icon) {
+ Drawable[] array = new Drawable[2];
+ array[0] = createFaviconBackground(getContext());
+ if (icon == null) {
+ array[1] = mGenericFavicon;
+ } else {
+ array[1] = new BitmapDrawable(icon);
+ }
+ LayerDrawable d = new LayerDrawable(array);
+ d.setLayerInset(1, 2, 2, 2, 2);
+ return d;
+ }
+
+ private void animateTabOut(final Tab tab, final TabView tv) {
+ ObjectAnimator scalex = ObjectAnimator.ofFloat(tv, "scaleX", 1.0f, 0.0f);
+ ObjectAnimator scaley = ObjectAnimator.ofFloat(tv, "scaleY", 1.0f, 0.0f);
+ ObjectAnimator alpha = ObjectAnimator.ofFloat(tv, "alpha", 1.0f, 0.0f);
+ AnimatorSet animator = new AnimatorSet();
+ animator.playTogether(scalex, scaley, alpha);
+ animator.setDuration(150);
+ animator.addListener(new AnimatorListener() {
+
+ @Override
+ public void onAnimationCancel(Animator animation) {
+ }
+
+ @Override
+ public void onAnimationEnd(Animator animation) {
+ mTabs.removeTab(tv);
+ mTabMap.remove(tab);
+ mUi.onRemoveTabCompleted(tab);
+ }
+
+ @Override
+ public void onAnimationRepeat(Animator animation) {
+ }
+
+ @Override
+ public void onAnimationStart(Animator animation) {
+ }
+
+ });
+ animator.start();
+ }
+
+ private void animateTabIn(final Tab tab, final TabView tv) {
+ ObjectAnimator scalex = ObjectAnimator.ofFloat(tv, "scaleX", 0.0f, 1.0f);
+ scalex.setDuration(150);
+ scalex.addListener(new AnimatorListener() {
+
+ @Override
+ public void onAnimationCancel(Animator animation) {
+ }
+
+ @Override
+ public void onAnimationEnd(Animator animation) {
+ mUi.onAddTabCompleted(tab);
+ }
+
+ @Override
+ public void onAnimationRepeat(Animator animation) {
+ }
+
+ @Override
+ public void onAnimationStart(Animator animation) {
+ mTabs.addTab(tv);
+ }
+
+ });
+ scalex.start();
+ }
+
+ // TabChangeListener implementation
+
+ public void onSetActiveTab(Tab tab) {
+ mTabs.setSelectedTab(mTabControl.getTabIndex(tab));
+ TabView tv = mTabMap.get(tab);
+ if (tv != null) {
+ tv.setProgress(tv.mTab.getLoadProgress());
+ // update the scroll state
+ WebView webview = tab.getWebView();
+ if (webview != null) {
+ int h = webview.getVisibleTitleHeight();
+ mVisibleTitleHeight = h -1;
+ onScroll(h);
+ }
+ }
+ }
+
+ public void onFavicon(Tab tab, Bitmap favicon) {
+ TabView tv = mTabMap.get(tab);
+ if (tv != null) {
+ tv.setFavicon(renderFavicon(favicon));
+ }
+ }
+
+ public void onNewTab(Tab tab) {
+ TabView tv = buildTabView(tab);
+ animateTabIn(tab, tv);
+ }
+
+ public void onProgress(Tab tab, int progress) {
+ TabView tv = mTabMap.get(tab);
+ if (tv != null) {
+ tv.setProgress(progress);
+ }
+ }
+
+ public void onRemoveTab(Tab tab) {
+ TabView tv = mTabMap.get(tab);
+ if (tv != null) {
+ animateTabOut(tab, tv);
+ } else {
+ mTabMap.remove(tab);
+ }
+ }
+
+ public void onUrlAndTitle(Tab tab, String url, String title) {
+ TabView tv = mTabMap.get(tab);
+ if (tv != null) {
+ if (title != null) {
+ tv.setDisplayTitle(title);
+ } else if (url != null) {
+ tv.setDisplayTitle(UrlUtils.stripUrl(url));
+ }
+ }
+ }
+
+ private boolean isLoading() {
+ TabView tv = mTabMap.get(mTabControl.getCurrentTab());
+ if (tv != null) {
+ return tv.mInLoad;
+ } else {
+ return false;
+ }
+ }
+
+}
diff --git a/src/com/android/browser/TabControl.java b/src/com/android/browser/TabControl.java
index afd4ea8..af9928a 100644
--- a/src/com/android/browser/TabControl.java
+++ b/src/com/android/browser/TabControl.java
@@ -16,57 +16,51 @@
package com.android.browser;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.graphics.BitmapShader;
-import android.graphics.Paint;
-import android.graphics.Shader;
+import com.android.browser.IntentHandler.UrlData;
+
import android.os.Bundle;
import android.util.Log;
-import android.view.View;
import android.webkit.WebBackForwardList;
import android.webkit.WebView;
import java.io.File;
import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
import java.util.Vector;
class TabControl {
// Log Tag
private static final String LOGTAG = "TabControl";
// Maximum number of tabs.
- private static final int MAX_TABS = 8;
+ private int mMaxTabs;
// Private array of WebViews that are used as tabs.
- private ArrayList<Tab> mTabs = new ArrayList<Tab>(MAX_TABS);
+ private ArrayList<Tab> mTabs;
// Queue of most recently viewed tabs.
- private ArrayList<Tab> mTabQueue = new ArrayList<Tab>(MAX_TABS);
+ private ArrayList<Tab> mTabQueue;
// Current position in mTabs.
private int mCurrentTab = -1;
- // A private instance of BrowserActivity to interface with when adding and
- // switching between tabs.
- private final BrowserActivity mActivity;
- // Directory to store thumbnails for each WebView.
+ // the main browser controller
+ private final Controller mController;
+
private final File mThumbnailDir;
/**
- * Construct a new TabControl object that interfaces with the given
- * BrowserActivity instance.
- * @param activity A BrowserActivity instance that TabControl will interface
- * with.
+ * Construct a new TabControl object
*/
- TabControl(BrowserActivity activity) {
- mActivity = activity;
- mThumbnailDir = activity.getDir("thumbnails", 0);
+ TabControl(Controller controller) {
+ mController = controller;
+ mThumbnailDir = mController.getActivity()
+ .getDir("thumbnails", 0);
+ mMaxTabs = mController.getMaxTabs();
+ mTabs = new ArrayList<Tab>(mMaxTabs);
+ mTabQueue = new ArrayList<Tab>(mMaxTabs);
}
File getThumbnailDir() {
return mThumbnailDir;
}
- BrowserActivity getBrowserActivity() {
- return mActivity;
- }
-
/**
* Return the current tab's main WebView. This will always return the main
* WebView for a given tab and not a subwindow.
@@ -106,6 +100,13 @@
}
/**
+ * return the list of tabs
+ */
+ List<Tab> getTabs() {
+ return mTabs;
+ }
+
+ /**
* Return the tab at the specified index.
* @return The Tab for the specified index or null if the tab does not
* exist.
@@ -132,7 +133,7 @@
int getCurrentIndex() {
return mCurrentTab;
}
-
+
/**
* Given a Tab, find it's index
* @param Tab to find
@@ -146,7 +147,20 @@
}
boolean canCreateNewTab() {
- return MAX_TABS != mTabs.size();
+ return mMaxTabs != mTabs.size();
+ }
+
+ /**
+ * Returns true if there are any incognito tabs open.
+ * @return True when any incognito tabs are open, false otherwise.
+ */
+ boolean hasAnyOpenIncognitoTabs() {
+ for (Tab tab : mTabs) {
+ if (tab.getWebView() != null && tab.getWebView().isPrivateBrowsingEnabled()) {
+ return true;
+ }
+ }
+ return false;
}
/**
@@ -154,16 +168,17 @@
* @return The newly createTab or null if we have reached the maximum
* number of open tabs.
*/
- Tab createNewTab(boolean closeOnExit, String appId, String url) {
+ Tab createNewTab(boolean closeOnExit, String appId, String url,
+ boolean privateBrowsing) {
int size = mTabs.size();
// Return false if we have maxed out on tabs
- if (MAX_TABS == size) {
+ if (mMaxTabs == size) {
return null;
}
- final WebView w = createNewWebView();
+ final WebView w = createNewWebView(privateBrowsing);
// Create a new tab and add it to the tab list
- Tab t = new Tab(mActivity, w, closeOnExit, appId, url);
+ Tab t = new Tab(mController, w, closeOnExit, appId, url);
mTabs.add(t);
// Initially put the tab in the background.
t.putInBackground();
@@ -172,10 +187,10 @@
/**
* Create a new tab with default values for closeOnExit(false),
- * appId(null), and url(null).
+ * appId(null), url(null), and privateBrowsing(false).
*/
Tab createNewTab() {
- return createNewTab(false, null, null);
+ return createNewTab(false, null, null, false);
}
/**
@@ -272,64 +287,112 @@
}
/**
+ * Check if the state can be restored. If the state can be restored, the
+ * current tab index is returned. This can be passed to restoreState below
+ * in order to restore the correct tab. Otherwise, -1 is returned and the
+ * state cannot be restored.
+ */
+ int canRestoreState(Bundle inState, boolean restoreIncognitoTabs) {
+ final int numTabs = (inState == null)
+ ? - 1 : inState.getInt(Tab.NUMTABS, -1);
+ if (numTabs == -1) {
+ return -1;
+ }
+ final int oldCurrentTab = inState.getInt(Tab.CURRTAB, -1);
+
+ // Determine whether the saved current tab can be restored, and if not,
+ // which tab will take its place.
+ int currentTab = -1;
+ if (restoreIncognitoTabs ||
+ !inState.getBundle(Tab.WEBVIEW + oldCurrentTab)
+ .getBoolean(Tab.INCOGNITO)) {
+ currentTab = oldCurrentTab;
+ } else {
+ for (int i = 0; i < numTabs; i++) {
+ if (!inState.getBundle(Tab.WEBVIEW + i)
+ .getBoolean(Tab.INCOGNITO)) {
+ currentTab = i;
+ break;
+ }
+ }
+ }
+
+ return currentTab;
+ }
+
+ /**
* Restore the state of all the tabs.
+ * @param currentTab The tab index to restore.
* @param inState The saved state of all the tabs.
+ * @param restoreIncognitoTabs Restoring private browsing tabs
+ * @param restoreAll All webviews get restored, not just the current tab
+ * (this does not override handling of incognito tabs)
* @return True if there were previous tabs that were restored. False if
* there was no saved state or restoring the state failed.
*/
- boolean restoreState(Bundle inState) {
- final int numTabs = (inState == null)
- ? -1 : inState.getInt(Tab.NUMTABS, -1);
- if (numTabs == -1) {
- return false;
- } else {
- final int currentTab = inState.getInt(Tab.CURRTAB, -1);
- for (int i = 0; i < numTabs; i++) {
+ void restoreState(Bundle inState, int currentTab,
+ boolean restoreIncognitoTabs, boolean restoreAll) {
+ if (currentTab == -1) {
+ return;
+ }
+
+ // If currentTab is valid, numTabs must be present.
+ final int numTabs = inState.getInt(Tab.NUMTABS, -1);
+
+ // Map saved tab indices to new indices, in case any incognito tabs
+ // need to not be restored.
+ HashMap<Integer, Integer> originalTabIndices = new HashMap<Integer, Integer>();
+ originalTabIndices.put(-1, -1);
+ for (int i = 0; i < numTabs; i++) {
+ Bundle state = inState.getBundle(Tab.WEBVIEW + i);
+
+ if (!restoreIncognitoTabs && state != null && state.getBoolean(Tab.INCOGNITO)) {
+ originalTabIndices.put(i, -1);
+ } else if (i == currentTab || restoreAll) {
+ Tab t = createNewTab();
+ // Me must set the current tab before restoring the state
+ // so that all the client classes are set.
if (i == currentTab) {
- Tab t = createNewTab();
- // Me must set the current tab before restoring the state
- // so that all the client classes are set.
setCurrentTab(t);
- if (!t.restoreState(inState.getBundle(Tab.WEBVIEW + i))) {
- Log.w(LOGTAG, "Fail in restoreState, load home page.");
- t.getWebView().loadUrl(BrowserSettings.getInstance()
- .getHomePage());
- }
- } else {
- // Create a new tab and don't restore the state yet, add it
- // to the tab list
- Tab t = new Tab(mActivity, null, false, null, null);
- Bundle state = inState.getBundle(Tab.WEBVIEW + i);
- if (state != null) {
- t.setSavedState(state);
- t.populatePickerDataFromSavedState();
- // Need to maintain the app id and original url so we
- // can possibly reuse this tab.
- t.setAppId(state.getString(Tab.APPID));
- t.setOriginalUrl(state.getString(Tab.ORIGINALURL));
- }
- mTabs.add(t);
- // added the tab to the front as they are not current
- mTabQueue.add(0, t);
}
+ if (!t.restoreState(state)) {
+ Log.w(LOGTAG, "Fail in restoreState, load home page.");
+ t.getWebView().loadUrl(BrowserSettings.getInstance()
+ .getHomePage());
+ }
+ originalTabIndices.put(i, getTabCount() - 1);
+ } else {
+ // Create a new tab and don't restore the state yet, add it
+ // to the tab list
+ Tab t = new Tab(mController, null, false, null, null);
+ if (state != null) {
+ t.setSavedState(state);
+ // Need to maintain the app id and original url so we
+ // can possibly reuse this tab.
+ t.setAppId(state.getString(Tab.APPID));
+ }
+ mTabs.add(t);
+ // added the tab to the front as they are not current
+ mTabQueue.add(0, t);
+ originalTabIndices.put(i, getTabCount() - 1);
}
- // Rebuild the tree of tabs. Do this after all tabs have been
- // created/restored so that the parent tab exists.
- for (int i = 0; i < numTabs; i++) {
- final Bundle b = inState.getBundle(Tab.WEBVIEW + i);
- final Tab t = getTab(i);
- if (b != null && t != null) {
- final int parentIndex = b.getInt(Tab.PARENTTAB, -1);
- if (parentIndex != -1) {
- final Tab parent = getTab(parentIndex);
- if (parent != null) {
- parent.addChildTab(t);
- }
+ }
+
+ // Rebuild the tree of tabs. Do this after all tabs have been
+ // created/restored so that the parent tab exists.
+ for (int i = 0; i < numTabs; i++) {
+ final Bundle b = inState.getBundle(Tab.WEBVIEW + i);
+ final Tab t = getTab(i);
+ if (b != null && t != null) {
+ final Integer parentIndex = originalTabIndices.get(b.getInt(Tab.PARENTTAB, -1));
+ if (parentIndex != -1) {
+ final Tab parent = getTab(parentIndex);
+ if (parent != null) {
+ parent.addChildTab(t);
}
}
}
}
- return true;
}
/**
@@ -487,28 +550,11 @@
}
/**
- * Recreate the main WebView of the given tab. Returns true if the WebView
- * requires a load, whether it was due to the fact that it was deleted, or
- * it is because it was a voice search.
+ * Recreate the main WebView of the given tab.
*/
- boolean recreateWebView(Tab t, BrowserActivity.UrlData urlData) {
- final String url = urlData.mUrl;
+ void recreateWebView(Tab t) {
final WebView w = t.getWebView();
if (w != null) {
- if (url != null && url.equals(t.getOriginalUrl())
- // Treat a voice intent as though it is a different URL,
- // since it most likely is.
- && urlData.mVoiceIntent == null) {
- // The original url matches the current url. Just go back to the
- // first history item so we can load it faster than if we
- // rebuilt the WebView.
- final WebBackForwardList list = w.copyBackForwardList();
- if (list != null) {
- w.goBackOrForward(-list.getCurrentIndex());
- w.clearHistory(); // maintains the current page.
- return false;
- }
- }
t.destroy();
}
// Create a new WebView. If this tab is the current tab, we need to put
@@ -519,40 +565,22 @@
}
// Clear the saved state and picker data
t.setSavedState(null);
- t.clearPickerData();
- // Save the new url in order to avoid deleting the WebView.
- t.setOriginalUrl(url);
- return true;
}
/**
* Creates a new WebView and registers it with the global settings.
*/
private WebView createNewWebView() {
- // Create a new WebView
- WebView w = new WebView(mActivity);
- w.setScrollbarFadingEnabled(true);
- w.setScrollBarStyle(View.SCROLLBARS_OUTSIDE_OVERLAY);
- w.setMapTrackballToArrowKeys(false); // use trackball directly
- // Enable the built-in zoom
- w.getSettings().setBuiltInZoomControls(true);
- // Add this WebView to the settings observer list and update the
- // settings
- final BrowserSettings s = BrowserSettings.getInstance();
- s.addObserver(w.getSettings()).update(s, null);
+ return createNewWebView(false);
+ }
- // pick a default
- if (false) {
- MeshTracker mt = new MeshTracker(2);
- Paint paint = new Paint();
- Bitmap bm = BitmapFactory.decodeResource(mActivity.getResources(),
- R.drawable.pattern_carbon_fiber_dark);
- paint.setShader(new BitmapShader(bm, Shader.TileMode.REPEAT,
- Shader.TileMode.REPEAT));
- mt.setBGPaint(paint);
- w.setDragTracker(mt);
- }
- return w;
+ /**
+ * Creates a new WebView and registers it with the global settings.
+ * @param privateBrowsing When true, enables private browsing in the new
+ * WebView.
+ */
+ private WebView createNewWebView(boolean privateBrowsing) {
+ return mController.getWebViewFactory().createWebView(privateBrowsing);
}
/**
@@ -564,20 +592,6 @@
return setCurrentTab(newTab, false);
}
- void pauseCurrentTab() {
- Tab t = getCurrentTab();
- if (t != null) {
- t.pause();
- }
- }
-
- void resumeCurrentTab() {
- Tab t = getCurrentTab();
- if (t != null) {
- t.resume();
- }
- }
-
/**
* If force is true, this method skips the check for newTab == current.
*/
@@ -619,4 +633,5 @@
}
return true;
}
+
}
diff --git a/src/com/android/browser/TabScrollView.java b/src/com/android/browser/TabScrollView.java
new file mode 100644
index 0000000..d0648b7
--- /dev/null
+++ b/src/com/android/browser/TabScrollView.java
@@ -0,0 +1,250 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+
+package com.android.browser;
+
+import android.animation.ObjectAnimator;
+import android.content.Context;
+import android.util.AttributeSet;
+import android.view.View;
+import android.widget.HorizontalScrollView;
+import android.widget.LinearLayout;
+
+/**
+ * custom view for displaying tabs in the tabbed title bar
+ */
+public class TabScrollView extends HorizontalScrollView {
+
+ private LinearLayout mContentView;
+ private int mSelected;
+ private int mAnimationDuration;
+ private int mTabOverlap;
+
+ /**
+ * @param context
+ * @param attrs
+ * @param defStyle
+ */
+ public TabScrollView(Context context, AttributeSet attrs, int defStyle) {
+ super(context, attrs, defStyle);
+ init(context);
+ }
+
+ /**
+ * @param context
+ * @param attrs
+ */
+ public TabScrollView(Context context, AttributeSet attrs) {
+ super(context, attrs);
+ init(context);
+ }
+
+ /**
+ * @param context
+ */
+ public TabScrollView(Context context) {
+ super(context);
+ init(context);
+ }
+
+ private void init(Context ctx) {
+ mAnimationDuration = ctx.getResources().getInteger(
+ R.integer.tab_animation_duration);
+ mTabOverlap = (int) ctx.getResources().getDimension(R.dimen.tab_overlap);
+ setHorizontalScrollBarEnabled(false);
+ setOverScrollMode(OVER_SCROLL_NEVER);
+ mContentView = new TabLayout(ctx);
+ mContentView.setOrientation(LinearLayout.HORIZONTAL);
+ mContentView.setLayoutParams(
+ new LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.MATCH_PARENT));
+ mContentView.setPadding(
+ (int) ctx.getResources().getDimension(R.dimen.tab_first_padding_left),
+ 0, 0, 0);
+ addView(mContentView);
+ mSelected = -1;
+ // prevent ProGuard from removing the property methods
+ setScroll(getScroll());
+ }
+
+ @Override
+ protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
+ super.onLayout(changed, left, top, right, bottom);
+ ensureChildVisible(getSelectedTab());
+ }
+
+ void setSelectedTab(int position) {
+ View v = getSelectedTab();
+ if (v != null) {
+ v.setActivated(false);
+ }
+ mSelected = position;
+ v = getSelectedTab();
+ if (v != null) {
+ v.setActivated(true);
+ }
+ requestLayout();
+ }
+
+ int getChildIndex(View v) {
+ return mContentView.indexOfChild(v);
+ }
+
+ View getSelectedTab() {
+ if ((mSelected >= 0) && (mSelected < mContentView.getChildCount())) {
+ return mContentView.getChildAt(mSelected);
+ } else {
+ return null;
+ }
+ }
+
+ void clearTabs() {
+ mContentView.removeAllViews();
+ }
+
+ void addTab(View tab) {
+ mContentView.addView(tab);
+ tab.setActivated(false);
+ }
+
+ void removeTab(View tab) {
+ int ix = mContentView.indexOfChild(tab);
+ if (ix == mSelected) {
+ mSelected = -1;
+ } else if (ix < mSelected) {
+ mSelected--;
+ }
+ mContentView.removeView(tab);
+ }
+
+ private void ensureChildVisible(View child) {
+ if (child != null) {
+ int childl = child.getLeft();
+ int childr = childl + child.getWidth();
+ int viewl = getScrollX();
+ int viewr = viewl + getWidth();
+ if (childl < viewl) {
+ // need scrolling to left
+ animateScroll(childl);
+ } else if (childr > viewr) {
+ // need scrolling to right
+ animateScroll(childr - viewr + viewl);
+ }
+ }
+ }
+
+// TODO: These animations are broken and don't work correctly, removing for now
+// as animateOut is actually causing issues
+// private void animateIn(View tab) {
+// ObjectAnimator animator = ObjectAnimator.ofInt(tab, "TranslationX", 500, 0);
+// animator.setDuration(mAnimationDuration);
+// animator.start();
+// }
+//
+// private void animateOut(final View tab) {
+// ObjectAnimator animator = ObjectAnimator.ofInt(
+// tab, "TranslationX", 0, getScrollX() - tab.getRight());
+// animator.setDuration(mAnimationDuration);
+// animator.addListener(new AnimatorListenerAdapter() {
+// @Override
+// public void onAnimationEnd(Animator animation) {
+// mContentView.removeView(tab);
+// }
+// });
+// animator.setInterpolator(new AccelerateInterpolator());
+// animator.start();
+// }
+
+ private void animateScroll(int newscroll) {
+ ObjectAnimator animator = ObjectAnimator.ofInt(this, "scroll", getScrollX(), newscroll);
+ animator.setDuration(mAnimationDuration);
+ animator.start();
+ }
+
+ /**
+ * required for animation
+ */
+ public void setScroll(int newscroll) {
+ scrollTo(newscroll, getScrollY());
+ }
+
+ /**
+ * required for animation
+ */
+ public int getScroll() {
+ return getScrollX();
+ }
+
+ @Override
+ protected void onScrollChanged(int l, int t, int oldl, int oldt) {
+ super.onScrollChanged(l, t, oldl, oldt);
+
+ // TabViews base their drawing based on their absolute position within the
+ // window. When hardware accelerated, we need to recreate their display list
+ // when they scroll
+ if (isHardwareAccelerated()) {
+ int count = mContentView.getChildCount();
+ for (int i = 0; i < count; i++) {
+ mContentView.getChildAt(i).invalidate();
+ }
+ }
+ }
+
+ class TabLayout extends LinearLayout {
+
+ public TabLayout(Context context) {
+ super(context);
+ setChildrenDrawingOrderEnabled(true);
+ }
+
+ @Override
+ protected void onMeasure(int hspec, int vspec) {
+ super.onMeasure(hspec, vspec);
+ int w = getMeasuredWidth();
+ w -= Math.max(0, mContentView.getChildCount() - 1) * mTabOverlap;
+ setMeasuredDimension(w, getMeasuredHeight());
+ }
+
+ @Override
+ protected void onLayout(boolean changed, int left, int top, int right, int bottom) {
+ super.onLayout(changed, left, top, right, bottom);
+ if (getChildCount() > 1) {
+ int nextLeft = getChildAt(0).getRight() - mTabOverlap;
+ for (int i = 1; i < getChildCount(); i++) {
+ View tab = getChildAt(i);
+ int w = tab.getRight() - tab.getLeft();
+ tab.layout(nextLeft, tab.getTop(), nextLeft + w, tab.getBottom());
+ nextLeft += w - mTabOverlap;
+ }
+ }
+ }
+
+ @Override
+ protected int getChildDrawingOrder(int count, int i) {
+ int next = -1;
+ if ((i == (count - 1)) && (mSelected >= 0)) {
+ next = mSelected;
+ } else {
+ next = count - i - 1;
+ if (next <= mSelected) {
+ next--;
+ }
+ }
+ return next;
+ }
+
+ }
+
+}
diff --git a/src/com/android/browser/TitleBar.java b/src/com/android/browser/TitleBar.java
index dc4979b..bdef82e 100644
--- a/src/com/android/browser/TitleBar.java
+++ b/src/com/android/browser/TitleBar.java
@@ -16,19 +16,15 @@
package com.android.browser;
-import android.content.Context;
+import com.android.common.speech.LoggingEvents;
+
+import android.app.Activity;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.content.pm.ResolveInfo;
import android.content.res.Resources;
-import android.graphics.Bitmap;
-import android.graphics.Color;
-import android.graphics.Rect;
import android.graphics.drawable.Animatable;
-import android.graphics.drawable.BitmapDrawable;
import android.graphics.drawable.Drawable;
-import android.graphics.drawable.LayerDrawable;
-import android.graphics.drawable.PaintDrawable;
import android.os.Handler;
import android.os.Message;
import android.speech.RecognizerIntent;
@@ -45,50 +41,45 @@
import android.view.View;
import android.view.ViewConfiguration;
import android.widget.ImageView;
-import android.widget.LinearLayout;
import android.widget.ProgressBar;
import android.widget.TextView;
-import com.android.common.speech.LoggingEvents;
-
/**
* This class represents a title bar for a particular "tab" or "window" in the
* browser.
*/
-public class TitleBar extends LinearLayout {
- private TextView mTitle;
- private Drawable mCloseDrawable;
- private ImageView mRtButton;
- private Drawable mCircularProgress;
- private ProgressBar mHorizontalProgress;
- private ImageView mFavicon;
- private ImageView mLockIcon;
- private ImageView mStopButton;
- private Drawable mBookmarkDrawable;
- private Drawable mVoiceDrawable;
- private boolean mInLoad;
- private BrowserActivity mBrowserActivity;
- private Drawable mGenericFavicon;
- private int mIconDimension;
- private View mTitleBg;
- private MyHandler mHandler;
- private Intent mVoiceSearchIntent;
- private boolean mInVoiceMode;
- private Drawable mVoiceModeBackground;
- private Drawable mNormalBackground;
- private Drawable mLoadingBackground;
- private ImageSpan mArcsSpan;
- private int mLeftMargin;
- private int mRightMargin;
+public class TitleBar extends TitleBarBase {
+
+ private Activity mActivity;
+ private UiController mController;
+ private TextView mTitle;
+ private ImageView mRtButton;
+ private Drawable mCircularProgress;
+ private ProgressBar mHorizontalProgress;
+ private ImageView mStopButton;
+ private Drawable mBookmarkDrawable;
+ private Drawable mVoiceDrawable;
+ private boolean mInLoad;
+ private View mTitleBg;
+ private MyHandler mHandler;
+ private Intent mVoiceSearchIntent;
+ private boolean mInVoiceMode;
+ private Drawable mVoiceModeBackground;
+ private Drawable mNormalBackground;
+ private Drawable mLoadingBackground;
+ private ImageSpan mArcsSpan;
+ private int mLeftMargin;
+ private int mRightMargin;
private static int LONG_PRESS = 1;
- public TitleBar(BrowserActivity context) {
- super(context, null);
+ public TitleBar(Activity activity, UiController controller) {
+ super(activity);
mHandler = new MyHandler();
- LayoutInflater factory = LayoutInflater.from(context);
+ LayoutInflater factory = LayoutInflater.from(activity);
factory.inflate(R.layout.title_bar, this);
- mBrowserActivity = context;
+ mActivity = activity;
+ mController = controller;
mTitle = (TextView) findViewById(R.id.title);
mTitle.setCompoundDrawablePadding(5);
@@ -99,21 +90,19 @@
mStopButton = (ImageView) findViewById(R.id.stop);
mRtButton = (ImageView) findViewById(R.id.rt_btn);
- Resources resources = context.getResources();
- mCircularProgress = (Drawable) resources.getDrawable(
+ Resources resources = activity.getResources();
+ mCircularProgress = resources.getDrawable(
com.android.internal.R.drawable.search_spinner);
DisplayMetrics metrics = resources.getDisplayMetrics();
mLeftMargin = (int) TypedValue.applyDimension(
TypedValue.COMPLEX_UNIT_DIP, 8f, metrics);
mRightMargin = (int) TypedValue.applyDimension(
TypedValue.COMPLEX_UNIT_DIP, 6f, metrics);
- mIconDimension = (int) TypedValue.applyDimension(
+ int iconDimension = (int) TypedValue.applyDimension(
TypedValue.COMPLEX_UNIT_DIP, 20f, metrics);
- mCircularProgress.setBounds(0, 0, mIconDimension, mIconDimension);
+ mCircularProgress.setBounds(0, 0, iconDimension, iconDimension);
mHorizontalProgress = (ProgressBar) findViewById(
R.id.progress_horizontal);
- mGenericFavicon = context.getResources().getDrawable(
- R.drawable.app_web_browser_sm);
mVoiceSearchIntent = new Intent(RecognizerIntent.ACTION_WEB_SEARCH);
mVoiceSearchIntent.putExtra(RecognizerIntent.EXTRA_LANGUAGE_MODEL,
RecognizerIntent.LANGUAGE_MODEL_WEB_SEARCH);
@@ -121,8 +110,9 @@
// results intent - http://b/2546173
//
// TODO: Make a constant for this extra.
- mVoiceSearchIntent.putExtra("android.speech.extras.SEND_APPLICATION_ID_EXTRA", false);
- PackageManager pm = context.getPackageManager();
+ mVoiceSearchIntent.putExtra("android.speech.extras.SEND_APPLICATION_ID_EXTRA",
+ false);
+ PackageManager pm = activity.getPackageManager();
ResolveInfo ri = pm.resolveActivity(mVoiceSearchIntent,
PackageManager.MATCH_DEFAULT_ONLY);
if (ri == null) {
@@ -136,11 +126,12 @@
R.drawable.title_voice);
mNormalBackground = mTitleBg.getBackground();
mLoadingBackground = resources.getDrawable(R.drawable.title_loading);
- mArcsSpan = new ImageSpan(context, R.drawable.arcs,
+ mArcsSpan = new ImageSpan(activity, R.drawable.arcs,
ImageSpan.ALIGN_BASELINE);
}
private class MyHandler extends Handler {
+ @Override
public void handleMessage(Message msg) {
if (msg.what == LONG_PRESS) {
// Prevent the normal action from happening by setting the title
@@ -149,16 +140,20 @@
// Need to call a special method on BrowserActivity for when the
// fake title bar is up, because its ViewGroup does not show a
// context menu.
- mBrowserActivity.showTitleBarContextMenu();
+ // TODO:
+ // this test is not valid for all UIs; fix later
+ if (getParent() != null) {
+ mActivity.openContextMenu(TitleBar.this);
+ }
}
}
};
@Override
public void createContextMenu(ContextMenu menu) {
- MenuInflater inflater = mBrowserActivity.getMenuInflater();
+ MenuInflater inflater = mActivity.getMenuInflater();
inflater.inflate(R.menu.title_context, menu);
- mBrowserActivity.onCreateContextMenu(menu, this, null);
+ mActivity.onCreateContextMenu(menu, this, null);
}
@Override
@@ -179,7 +174,7 @@
}
break;
case MotionEvent.ACTION_MOVE:
- int slop = ViewConfiguration.get(mBrowserActivity)
+ int slop = ViewConfiguration.get(mActivity)
.getScaledTouchSlop();
if ((int) event.getY() > getHeight() + slop) {
// We only trigger the actions in ACTION_UP if one or the
@@ -207,36 +202,37 @@
case MotionEvent.ACTION_UP:
if (button.isPressed()) {
if (mInVoiceMode) {
- if (mBrowserActivity.getTabControl().getCurrentTab()
+ if (mController.getTabControl().getCurrentTab()
.voiceSearchSourceIsGoogle()) {
Intent i = new Intent(
LoggingEvents.ACTION_LOG_EVENT);
i.putExtra(LoggingEvents.EXTRA_EVENT,
LoggingEvents.VoiceSearch.RETRY);
- mBrowserActivity.sendBroadcast(i);
+ mActivity.sendBroadcast(i);
}
- mBrowserActivity.startActivity(mVoiceSearchIntent);
+ mActivity.startActivity(mVoiceSearchIntent);
} else if (mInLoad) {
- mBrowserActivity.stopLoading();
+ mController.stopLoading();
} else {
- mBrowserActivity.bookmarksOrHistoryPicker(false);
+ mController.bookmarkCurrentPage(
+ AddBookmarkPage.DEFAULT_FOLDER_ID);
}
button.setPressed(false);
} else if (mTitleBg.isPressed()) {
mHandler.removeMessages(LONG_PRESS);
if (mInVoiceMode) {
- if (mBrowserActivity.getTabControl().getCurrentTab()
+ if (mController.getTabControl().getCurrentTab()
.voiceSearchSourceIsGoogle()) {
Intent i = new Intent(
LoggingEvents.ACTION_LOG_EVENT);
i.putExtra(LoggingEvents.EXTRA_EVENT,
LoggingEvents.VoiceSearch.N_BEST_REVEAL);
- mBrowserActivity.sendBroadcast(i);
+ mActivity.sendBroadcast(i);
}
- mBrowserActivity.showVoiceSearchResults(
+ mController.showVoiceSearchResults(
mTitle.getText().toString().trim());
} else {
- mBrowserActivity.editUrl();
+ mController.editUrl();
}
mTitleBg.setPressed(false);
}
@@ -248,29 +244,11 @@
}
/**
- * Set a new Bitmap for the Favicon.
- */
- /* package */ void setFavicon(Bitmap icon) {
- Drawable[] array = new Drawable[3];
- array[0] = new PaintDrawable(Color.BLACK);
- PaintDrawable p = new PaintDrawable(Color.WHITE);
- array[1] = p;
- if (icon == null) {
- array[2] = mGenericFavicon;
- } else {
- array[2] = new BitmapDrawable(icon);
- }
- LayerDrawable d = new LayerDrawable(array);
- d.setLayerInset(1, 1, 1, 1, 1);
- d.setLayerInset(2, 2, 2, 2, 2);
- mFavicon.setImageDrawable(d);
- }
-
- /**
* Change the TitleBar to or from voice mode. If there is no package to
* handle voice search, the TitleBar cannot be set to voice mode.
*/
- /* package */ void setInVoiceMode(boolean inVoiceMode) {
+ @Override
+ void setInVoiceMode(boolean inVoiceMode) {
if (mInVoiceMode == inVoiceMode) return;
mInVoiceMode = inVoiceMode && mVoiceSearchIntent != null;
Drawable titleDrawable;
@@ -302,21 +280,10 @@
}
/**
- * Set the Drawable for the lock icon, or null to hide it.
- */
- /* package */ void setLock(Drawable d) {
- if (null == d) {
- mLockIcon.setVisibility(View.GONE);
- } else {
- mLockIcon.setImageDrawable(d);
- mLockIcon.setVisibility(View.VISIBLE);
- }
- }
-
- /**
* Update the progress, from 0 to 100.
*/
- /* package */ void setProgress(int newProgress) {
+ @Override
+ void setProgress(int newProgress) {
if (newProgress >= mHorizontalProgress.getMax()) {
mTitle.setCompoundDrawables(null, null, null, null);
((Animatable) mCircularProgress).stop();
@@ -353,12 +320,13 @@
/**
* Update the text displayed in the title bar.
- * @param title String to display. If null, the loading string will be
+ * @param title String to display. If null, the new tab string will be
* shown.
*/
- /* package */ void setDisplayTitle(String title) {
+ @Override
+ void setDisplayTitle(String title) {
if (title == null) {
- mTitle.setText(R.string.title_bar_loading);
+ mTitle.setText(R.string.new_tab);
} else {
if (mInVoiceMode) {
// Add two spaces. The second one will be replaced with an
@@ -374,11 +342,4 @@
}
}
}
-
- /* package */ void setToTabPicker() {
- mTitle.setText(R.string.tab_picker_title);
- setFavicon(null);
- setLock(null);
- mHorizontalProgress.setVisibility(View.GONE);
- }
}
diff --git a/src/com/android/browser/TitleBarBase.java b/src/com/android/browser/TitleBarBase.java
new file mode 100644
index 0000000..024f83c
--- /dev/null
+++ b/src/com/android/browser/TitleBarBase.java
@@ -0,0 +1,79 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.content.Context;
+import android.graphics.Bitmap;
+import android.graphics.Color;
+import android.graphics.drawable.BitmapDrawable;
+import android.graphics.drawable.Drawable;
+import android.graphics.drawable.LayerDrawable;
+import android.graphics.drawable.PaintDrawable;
+import android.view.View;
+import android.widget.ImageView;
+import android.widget.LinearLayout;
+
+/**
+ * Base class for a title bar used by the browser.
+ */
+public class TitleBarBase extends LinearLayout {
+ // These need to be set by the subclass.
+ protected ImageView mFavicon;
+ protected ImageView mLockIcon;
+
+ protected Drawable mGenericFavicon;
+
+ public TitleBarBase(Context context) {
+ super(context, null);
+ mGenericFavicon = context.getResources().getDrawable(
+ R.drawable.app_web_browser_sm);
+ }
+
+ /* package */ void setProgress(int newProgress) {}
+ /* package */ void setDisplayTitle(String title) {}
+
+ /* package */ void setLock(Drawable d) {
+ assert mLockIcon != null;
+ if (null == d) {
+ mLockIcon.setVisibility(View.GONE);
+ } else {
+ mLockIcon.setImageDrawable(d);
+ mLockIcon.setVisibility(View.VISIBLE);
+ }
+ }
+
+ /* package */ void setFavicon(Bitmap icon) {
+ assert mFavicon != null;
+ Drawable[] array = new Drawable[3];
+ array[0] = new PaintDrawable(Color.BLACK);
+ PaintDrawable p = new PaintDrawable(Color.WHITE);
+ array[1] = p;
+ if (icon == null) {
+ array[2] = mGenericFavicon;
+ } else {
+ array[2] = new BitmapDrawable(icon);
+ }
+ LayerDrawable d = new LayerDrawable(array);
+ d.setLayerInset(1, 1, 1, 1, 1);
+ d.setLayerInset(2, 2, 2, 2, 2);
+ mFavicon.setImageDrawable(d);
+ }
+
+ /* package */ void setInVoiceMode(boolean inVoiceMode) {}
+
+ /* package */ void setIncognitoMode(boolean incognito) {}
+}
diff --git a/src/com/android/browser/TitleBarXLarge.java b/src/com/android/browser/TitleBarXLarge.java
new file mode 100644
index 0000000..0dcece6
--- /dev/null
+++ b/src/com/android/browser/TitleBarXLarge.java
@@ -0,0 +1,460 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.UrlInputView.UrlInputListener;
+import com.android.browser.search.SearchEngine;
+
+import android.app.Activity;
+import android.app.SearchManager;
+import android.content.Context;
+import android.content.Intent;
+import android.content.res.Resources;
+import android.graphics.Bitmap;
+import android.graphics.drawable.Drawable;
+import android.os.Bundle;
+import android.speech.RecognizerResultsIntent;
+import android.text.Editable;
+import android.text.TextUtils;
+import android.text.TextWatcher;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.view.View.OnFocusChangeListener;
+import android.webkit.WebView;
+import android.widget.ImageButton;
+import android.widget.ImageView;
+
+import java.util.List;
+
+/**
+ * tabbed title bar for xlarge screen browser
+ */
+public class TitleBarXLarge extends TitleBarBase
+ implements UrlInputListener, OnClickListener, OnFocusChangeListener,
+ TextWatcher {
+
+ private static final int PROGRESS_MAX = 100;
+
+ private UiController mUiController;
+ private XLargeUi mUi;
+
+ private Drawable mStopDrawable;
+ private Drawable mReloadDrawable;
+
+ private View mContainer;
+ private ImageButton mBackButton;
+ private ImageButton mForwardButton;
+ private ImageView mStar;
+ private ImageView mWebIcon;
+ private View mSearchButton;
+ private View mUrlContainer;
+ private View mGoButton;
+ private ImageView mStopButton;
+ private View mAllButton;
+ private View mClearButton;
+ private View mVoiceSearch;
+ private View mVoiceSearchIndicator;
+ private PageProgressView mProgressView;
+ private UrlInputView mUrlInput;
+ private Drawable mFocusDrawable;
+ private Drawable mUnfocusDrawable;
+ private boolean mInVoiceMode;
+
+ private boolean mInLoad;
+ private boolean mEditable;
+ private boolean mUseQuickControls;
+
+ public TitleBarXLarge(Activity activity, UiController controller,
+ XLargeUi ui) {
+ super(activity);
+ mUiController = controller;
+ mUi = ui;
+ Resources resources = activity.getResources();
+ mStopDrawable = resources.getDrawable(R.drawable.ic_stop_holo_dark);
+ mReloadDrawable = resources.getDrawable(R.drawable.ic_refresh_holo_dark);
+ mFocusDrawable = resources.getDrawable(
+ R.drawable.textfield_active_holo_dark);
+ mUnfocusDrawable = resources.getDrawable(
+ R.drawable.textfield_default_holo_dark);
+ initLayout(activity);
+ mInVoiceMode = false;
+ }
+
+ private void initLayout(Context context) {
+ LayoutInflater factory = LayoutInflater.from(context);
+ factory.inflate(R.layout.url_bar, this);
+
+ mContainer = findViewById(R.id.taburlbar);
+ mUrlInput = (UrlInputView) findViewById(R.id.url_focused);
+ mAllButton = findViewById(R.id.all_btn);
+ // TODO: Change enabled states based on whether you can go
+ // back/forward. Probably should be done inside onPageStarted.
+ mBackButton = (ImageButton) findViewById(R.id.back);
+ mForwardButton = (ImageButton) findViewById(R.id.forward);
+ mWebIcon = (ImageView) findViewById(R.id.web_icon);
+ mStar = (ImageView) findViewById(R.id.star);
+ mStopButton = (ImageView) findViewById(R.id.stop);
+ mSearchButton = findViewById(R.id.search);
+ mLockIcon = (ImageView) findViewById(R.id.lock);
+ mGoButton = findViewById(R.id.go);
+ mClearButton = findViewById(R.id.clear);
+ mVoiceSearch = findViewById(R.id.voicesearch);
+ mProgressView = (PageProgressView) findViewById(R.id.progress);
+ mUrlContainer = findViewById(R.id.urlbar_focused);
+ mVoiceSearchIndicator = findViewById(R.id.voice_icon);
+ mBackButton.setOnClickListener(this);
+ mForwardButton.setOnClickListener(this);
+ mStar.setOnClickListener(this);
+ mAllButton.setOnClickListener(this);
+ mStopButton.setOnClickListener(this);
+ mSearchButton.setOnClickListener(this);
+ mGoButton.setOnClickListener(this);
+ mClearButton.setOnClickListener(this);
+ mVoiceSearch.setOnClickListener(this);
+ mUrlContainer.setOnClickListener(this);
+ mUrlInput.setUrlInputListener(this);
+ mUrlInput.setContainer(mUrlContainer);
+ mUrlInput.setController(mUiController);
+ mUrlInput.setOnFocusChangeListener(this);
+ mUrlInput.setSelectAllOnFocus(true);
+ mUrlInput.addTextChangedListener(this);
+ setEditMode(false);
+ }
+
+ void updateNavigationState(Tab tab) {
+ WebView web = tab.getWebView();
+ if (web != null) {
+ mBackButton.setImageResource(web.canGoBack()
+ ? R.drawable.ic_back_holo_dark
+ : R.drawable.ic_back_disabled_holo_dark);
+ mForwardButton.setImageResource(web.canGoForward()
+ ? R.drawable.ic_forward_holo_dark
+ : R.drawable.ic_forward_disabled_holo_dark);
+ }
+ }
+
+ public void setEditable(boolean editable) {
+ mEditable = editable;
+ mUrlInput.setFocusable(mEditable);
+ if (!mEditable) {
+ mUrlInput.setOnClickListener(this);
+ } else {
+ mUrlContainer.setOnClickListener(null);
+ }
+ }
+
+ void setUseQuickControls(boolean useQuickControls) {
+ mUseQuickControls = useQuickControls;
+ mUrlInput.setUseQuickControls(mUseQuickControls);
+ if (mUseQuickControls) {
+ mBackButton.setVisibility(View.GONE);
+ mForwardButton.setVisibility(View.GONE);
+ mStopButton.setVisibility(View.GONE);
+ mAllButton.setVisibility(View.GONE);
+ } else {
+ mBackButton.setVisibility(View.VISIBLE);
+ mForwardButton.setVisibility(View.VISIBLE);
+ mStopButton.setVisibility(View.VISIBLE);
+ mAllButton.setVisibility(View.VISIBLE);
+ }
+ }
+
+ void setShowProgressOnly(boolean progress) {
+ if (progress) {
+ mContainer.setVisibility(View.GONE);
+ } else {
+ mContainer.setVisibility(View.VISIBLE);
+ }
+ }
+
+ @Override
+ public void onFocusChange(View view, boolean hasFocus) {
+ if (!mEditable && hasFocus) {
+ mUi.editUrl(false);
+ } else {
+ if (hasFocus) {
+ setEditMode(hasFocus);
+ } else {
+ mUrlInput.stopEditing();
+ }
+ }
+ mUrlContainer.setBackgroundDrawable(hasFocus
+ ? mFocusDrawable : mUnfocusDrawable);
+ }
+
+ public void setCurrentUrlIsBookmark(boolean isBookmark) {
+ mStar.setActivated(isBookmark);
+ }
+
+ /**
+ * called from the Ui when the user wants to edit
+ * Note: only the fake titlebar will get this callback
+ * independent of which input field started the edit mode
+ * @param clearInput clear the input field
+ */
+ void onEditUrl(boolean clearInput) {
+ // editing takes preference of progress
+ mContainer.setVisibility(View.VISIBLE);
+ if (mUseQuickControls) {
+ mProgressView.setVisibility(View.GONE);
+ }
+ if (!mUrlInput.hasFocus()) {
+ mUrlInput.requestFocus();
+ }
+ if (clearInput) {
+ mUrlInput.setText("");
+ } else if (mInVoiceMode) {
+ mUrlInput.showDropDown();
+ }
+ }
+
+ boolean isEditingUrl() {
+ return mUrlInput.hasFocus();
+ }
+
+ @Override
+ public void onClick(View v) {
+ if (mUrlInput == v) {
+ mUi.editUrl(false);
+ } else if (mUrlContainer == v) {
+ if (!mUrlInput.hasFocus()) {
+ mUi.editUrl(false);
+ }
+ } else if (mBackButton == v) {
+ mUiController.getCurrentTopWebView().goBack();
+ } else if (mForwardButton == v) {
+ mUiController.getCurrentTopWebView().goForward();
+ } else if (mStar == v) {
+ mUiController.bookmarkCurrentPage(
+ AddBookmarkPage.DEFAULT_FOLDER_ID);
+ } else if (mAllButton == v) {
+ mUiController.bookmarksOrHistoryPicker(false);
+ } else if (mSearchButton == v) {
+ mUi.editUrl(true);
+ } else if (mStopButton == v) {
+ stopOrRefresh();
+ } else if (mGoButton == v) {
+ if (!TextUtils.isEmpty(mUrlInput.getText())) {
+ onAction(mUrlInput.getText().toString(), null,
+ UrlInputView.TYPED);
+ }
+ } else if (mClearButton == v) {
+ clearOrClose();
+ } else if (mVoiceSearch == v) {
+ mUiController.startVoiceSearch();
+ }
+ }
+
+ int getHeightWithoutProgress() {
+ return mContainer.getHeight();
+ }
+
+ @Override
+ void setFavicon(Bitmap icon) { }
+
+ private void clearOrClose() {
+ if (TextUtils.isEmpty(mUrlInput.getText())) {
+ // close
+ mUrlInput.stopEditing();
+ } else {
+ // clear
+ mUrlInput.setText("");
+ }
+ }
+
+ // UrlInputListener implementation
+
+ /**
+ * callback from suggestion dropdown
+ * user selected a suggestion
+ */
+ @Override
+ public void onAction(String text, String extra, String source) {
+ mUiController.getCurrentTopWebView().requestFocus();
+ mUi.hideFakeTitleBar();
+ Intent i = new Intent();
+ String action = null;
+ if (UrlInputView.VOICE.equals(source)) {
+ action = RecognizerResultsIntent.ACTION_VOICE_SEARCH_RESULTS;
+ source = null;
+ } else {
+ action = Intent.ACTION_SEARCH;
+ }
+ i.setAction(action);
+ i.putExtra(SearchManager.QUERY, text);
+ if (extra != null) {
+ i.putExtra(SearchManager.EXTRA_DATA_KEY, extra);
+ }
+ if (source != null) {
+ Bundle appData = new Bundle();
+ appData.putString(com.android.common.Search.SOURCE, source);
+ i.putExtra(SearchManager.APP_DATA, appData);
+ }
+ mUiController.handleNewIntent(i);
+ setDisplayTitle(text);
+ }
+
+ @Override
+ public void onDismiss() {
+ final Tab currentTab = mUi.getActiveTab();
+ mUi.hideFakeTitleBar();
+ post(new Runnable() {
+ public void run() {
+ TitleBarXLarge.this.clearFocus();
+ if ((currentTab != null) && !mInVoiceMode) {
+ setDisplayTitle(currentTab.getUrl());
+ }
+ }
+ });
+ }
+
+ /**
+ * callback from the suggestion dropdown
+ * copy text to input field and stay in edit mode
+ */
+ @Override
+ public void onEdit(String text) {
+ mUrlInput.setText(text, true);
+ if (text != null) {
+ mUrlInput.setSelection(text.length());
+ }
+ }
+
+ void setEditMode(boolean edit) {
+ if (edit) {
+ mUrlInput.setDropDownWidth(mUrlContainer.getWidth());
+ mUrlInput.setDropDownHorizontalOffset(-mUrlInput.getLeft());
+ mSearchButton.setVisibility(View.GONE);
+ mStar.setVisibility(View.GONE);
+ mClearButton.setVisibility(View.VISIBLE);
+ if (mInVoiceMode) {
+ mVoiceSearchIndicator.setVisibility(View.VISIBLE);
+ }
+ mWebIcon.setImageResource(R.drawable.ic_search_holo_dark);
+ updateSearchMode();
+ } else {
+ mGoButton.setVisibility(View.GONE);
+ mVoiceSearch.setVisibility(View.GONE);
+ mStar.setVisibility(View.VISIBLE);
+ mClearButton.setVisibility(View.GONE);
+ mVoiceSearchIndicator.setVisibility(View.GONE);
+ if (mUseQuickControls) {
+ mSearchButton.setVisibility(View.GONE);
+ } else {
+ mSearchButton.setVisibility(View.VISIBLE);
+ }
+ mWebIcon.setImageResource(R.drawable.ic_web_holo_dark);
+ }
+ }
+
+ private void stopOrRefresh() {
+ if (mInLoad) {
+ mUiController.stopLoading();
+ } else {
+ mUiController.getCurrentTopWebView().reload();
+ }
+ }
+
+ /**
+ * Update the progress, from 0 to 100.
+ */
+ @Override
+ void setProgress(int newProgress) {
+ boolean blockvisuals = mUseQuickControls && isEditingUrl();
+ if (newProgress >= PROGRESS_MAX) {
+ if (!blockvisuals) {
+ mProgressView.setProgress(PageProgressView.MAX_PROGRESS);
+ mProgressView.setVisibility(View.GONE);
+ mStopButton.setImageDrawable(mReloadDrawable);
+ }
+ mInLoad = false;
+ } else {
+ if (!mInLoad) {
+ if (!blockvisuals) {
+ mProgressView.setVisibility(View.VISIBLE);
+ mStopButton.setImageDrawable(mStopDrawable);
+ }
+ mInLoad = true;
+ }
+ mProgressView.setProgress(newProgress * PageProgressView.MAX_PROGRESS
+ / PROGRESS_MAX);
+ }
+ }
+
+ private void updateSearchMode() {
+ setSearchMode(TextUtils.isEmpty(mUrlInput.getText()));
+ }
+
+ private void setSearchMode(boolean voiceSearchEnabled) {
+ SearchEngine searchEngine = BrowserSettings.getInstance()
+ .getSearchEngine();
+ boolean showvoicebutton = voiceSearchEnabled &&
+ (searchEngine != null && searchEngine.supportsVoiceSearch());
+ mVoiceSearch.setVisibility(showvoicebutton ? View.VISIBLE :
+ View.GONE);
+ mGoButton.setVisibility(voiceSearchEnabled ? View.GONE :
+ View.VISIBLE);
+ }
+
+ @Override
+ /* package */ void setDisplayTitle(String title) {
+ if (!isEditingUrl()) {
+ mUrlInput.setText(title, false);
+ }
+ }
+
+ // UrlInput text watcher
+
+ @Override
+ public void afterTextChanged(Editable s) {
+ if (mUrlInput.hasFocus()) {
+ // check if input field is empty and adjust voice search state
+ updateSearchMode();
+ // clear voice mode when user types
+ setInVoiceMode(false, null);
+ }
+ }
+
+ @Override
+ public void beforeTextChanged(CharSequence s, int start, int count, int after) {
+ }
+
+ @Override
+ public void onTextChanged(CharSequence s, int start, int before, int count) {
+ }
+
+ // voicesearch
+
+ @Override
+ public void setInVoiceMode(boolean voicemode) {
+ setInVoiceMode(voicemode, null);
+ }
+
+ public void setInVoiceMode(boolean voicemode, List<String> voiceResults) {
+ mInVoiceMode = voicemode;
+ mUrlInput.setVoiceResults(voiceResults);
+ mVoiceSearchIndicator.setVisibility(mInVoiceMode
+ ? View.VISIBLE : View.GONE);
+ }
+
+ @Override
+ void setIncognitoMode(boolean incognito) {
+ mUrlInput.setIncognitoMode(incognito);
+ }
+
+}
diff --git a/src/com/android/browser/UI.java b/src/com/android/browser/UI.java
new file mode 100644
index 0000000..8de2b19
--- /dev/null
+++ b/src/com/android/browser/UI.java
@@ -0,0 +1,123 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.content.res.Configuration;
+import android.graphics.Bitmap;
+import android.os.Bundle;
+import android.view.ActionMode;
+import android.view.KeyEvent;
+import android.view.Menu;
+import android.view.View;
+import android.webkit.WebChromeClient.CustomViewCallback;
+import android.webkit.WebView;
+
+import java.util.List;
+
+/**
+ * UI interface definitions
+ */
+public interface UI {
+
+ public void onPause();
+
+ public void onResume();
+
+ public void onDestroy();
+
+ public void onConfigurationChanged(Configuration config);
+
+ public boolean onBackKey();
+
+ public boolean needsRestoreAllTabs();
+
+ public void addTab(Tab tab);
+
+ public void removeTab(Tab tab);
+
+ public void setActiveTab(Tab tab);
+
+ public void updateTabs(List<Tab> tabs);
+
+ public void detachTab(Tab tab);
+
+ public void attachTab(Tab tab);
+
+ public void onSetWebView(Tab tab, WebView view);
+
+ public void createSubWindow(Tab tab, WebView subWebView);
+
+ public void attachSubWindow(View subContainer);
+
+ public void removeSubWindow(View subContainer);
+
+ public void onTabDataChanged(Tab tab);
+
+ public void onPageStopped(Tab tab);
+
+ public void onProgressChanged(Tab tab);
+
+ public void showActiveTabsPage();
+
+ public void removeActiveTabsPage();
+
+ public void showComboView(boolean startWithHistory, Bundle extra);
+
+ public void hideComboView();
+
+ public void showCustomView(View view, CustomViewCallback callback);
+
+ public void onHideCustomView();
+
+ public boolean isCustomViewShowing();
+
+ public void showVoiceTitleBar(String title);
+
+ public void revertVoiceTitleBar(Tab tab);
+
+ public void onOptionsMenuOpened();
+
+ public void onExtendedMenuOpened();
+
+ public void onOptionsMenuClosed(boolean inLoad);
+
+ public void onExtendedMenuClosed(boolean inLoad);
+
+ public void onContextMenuCreated(Menu menu);
+
+ public void onContextMenuClosed(Menu menu, boolean inLoad);
+
+ public void onActionModeStarted(ActionMode mode);
+
+ public void onActionModeFinished(boolean inLoad);
+
+ public void setShouldShowErrorConsole(Tab tab, boolean show);
+
+ // returns if the web page is clear of any overlays (not including sub windows)
+ public boolean showsWeb();
+
+ Bitmap getDefaultVideoPoster();
+
+ View getVideoLoadingProgressView();
+
+ void bookmarkedStatusHasChanged(Tab tab);
+
+ void showMaxTabsWarning();
+
+ boolean dispatchKey(int code, KeyEvent event);
+
+}
diff --git a/src/com/android/browser/UiController.java b/src/com/android/browser/UiController.java
new file mode 100644
index 0000000..ae38cff
--- /dev/null
+++ b/src/com/android/browser/UiController.java
@@ -0,0 +1,85 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.content.Intent;
+import android.webkit.WebView;
+
+import java.util.List;
+
+
+/**
+ * UI aspect of the controller
+ */
+public interface UiController extends BookmarksHistoryCallbacks {
+
+ UI getUi();
+
+ WebView getCurrentWebView();
+
+ WebView getCurrentTopWebView();
+
+ TabControl getTabControl();
+
+ List<Tab> getTabs();
+
+ Tab openTabToHomePage();
+
+ Tab openIncognitoTab();
+
+ boolean switchToTab(int tabIndex);
+
+ void closeCurrentTab();
+
+ void closeTab(Tab tab);
+
+ void stopLoading();
+
+ void bookmarkCurrentPage(long folderId);
+
+ void bookmarksOrHistoryPicker(boolean openHistory);
+
+ void startVoiceSearch();
+
+ void showVoiceSearchResults(String title);
+
+ void editUrl();
+
+ void removeActiveTabsPage(boolean attach);
+
+ void handleNewIntent(Intent intent);
+
+ boolean shouldShowErrorConsole();
+
+ void removeComboView();
+
+ void hideCustomView();
+
+ void attachSubWindow(Tab tab);
+
+ void removeSubWindow(Tab tab);
+
+ boolean isInCustomActionMode();
+
+ void endActionMode();
+
+ void shareCurrentPage();
+
+ void registerOptionsMenuHandler(OptionsMenuHandler handler);
+
+ void unregisterOptionsMenuHandler(OptionsMenuHandler handler);
+}
diff --git a/src/com/android/browser/UploadHandler.java b/src/com/android/browser/UploadHandler.java
new file mode 100644
index 0000000..d9b387f
--- /dev/null
+++ b/src/com/android/browser/UploadHandler.java
@@ -0,0 +1,214 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.app.Activity;
+import android.content.Intent;
+import android.net.Uri;
+import android.os.Environment;
+import android.provider.MediaStore;
+import android.webkit.ValueCallback;
+
+import java.io.File;
+import java.util.Vector;
+
+/**
+ * Handle the file upload callbacks from WebView here
+ */
+public class UploadHandler {
+
+ /*
+ * The Object used to inform the WebView of the file to upload.
+ */
+ private ValueCallback<Uri> mUploadMessage;
+ private String mCameraFilePath;
+
+ private Controller mController;
+
+ public UploadHandler(Controller controller) {
+ mController = controller;
+ }
+
+ String getFilePath() {
+ return mCameraFilePath;
+ }
+
+ void onResult(int resultCode, Intent intent) {
+ Uri result = intent == null || resultCode != Activity.RESULT_OK ? null
+ : intent.getData();
+
+ // As we ask the camera to save the result of the user taking
+ // a picture, the camera application does not return anything other
+ // than RESULT_OK. So we need to check whether the file we expected
+ // was written to disk in the in the case that we
+ // did not get an intent returned but did get a RESULT_OK. If it was,
+ // we assume that this result has came back from the camera.
+ if (result == null && intent == null && resultCode == Activity.RESULT_OK) {
+ File cameraFile = new File(mCameraFilePath);
+ if (cameraFile.exists()) {
+ result = Uri.fromFile(cameraFile);
+ // Broadcast to the media scanner that we have a new photo
+ // so it will be added into the gallery for the user.
+ mController.getActivity().sendBroadcast(
+ new Intent(Intent.ACTION_MEDIA_SCANNER_SCAN_FILE, result));
+ }
+ }
+
+ mUploadMessage.onReceiveValue(result);
+ }
+
+ void openFileChooser(ValueCallback<Uri> uploadMsg, String acceptType) {
+
+ final String imageMimeType = "image/*";
+ final String videoMimeType = "video/*";
+ final String audioMimeType = "audio/*";
+ final String mediaSourceKey = "capture";
+ final String mediaSourceValueCamera = "camera";
+ final String mediaSourceValueFileSystem = "filesystem";
+ final String mediaSourceValueCamcorder = "camcorder";
+ final String mediaSourceValueMicrophone = "microphone";
+
+ // media source can be 'filesystem' or 'camera' or 'camcorder' or 'microphone'.
+ String mediaSource = "";
+
+ // We add the camera intent if there was no accept type (or '*/*' or 'image/*').
+ boolean addCameraIntent = true;
+ // We add the camcorder intent if there was no accept type (or '*/*' or 'video/*').
+ boolean addCamcorderIntent = true;
+
+ if (mUploadMessage != null) {
+ // Already a file picker operation in progress.
+ return;
+ }
+
+ mUploadMessage = uploadMsg;
+
+ // Parse the accept type.
+ String params[] = acceptType.split(";");
+ String mimeType = params[0];
+
+ for (String p : params) {
+ String[] keyValue = p.split("=");
+ if (keyValue.length == 2) {
+ // Process key=value parameters.
+ if (mediaSourceKey.equals(keyValue[0])) {
+ mediaSource = keyValue[1];
+ }
+ }
+ }
+
+ // This intent will display the standard OPENABLE file picker.
+ Intent i = new Intent(Intent.ACTION_GET_CONTENT);
+ i.addCategory(Intent.CATEGORY_OPENABLE);
+
+ // Create an intent to add to the standard file picker that will
+ // capture an image from the camera. We'll combine this intent with
+ // the standard OPENABLE picker unless the web developer specifically
+ // requested the camera or gallery be opened by passing a parameter
+ // in the accept type.
+ Intent cameraIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);
+ File externalDataDir = Environment.getExternalStoragePublicDirectory(
+ Environment.DIRECTORY_DCIM);
+ File cameraDataDir = new File(externalDataDir.getAbsolutePath() +
+ File.separator + "browser-photos");
+ cameraDataDir.mkdirs();
+ mCameraFilePath = cameraDataDir.getAbsolutePath() + File.separator +
+ System.currentTimeMillis() + ".jpg";
+ cameraIntent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(new File(mCameraFilePath)));
+
+ Intent camcorderIntent = new Intent(MediaStore.ACTION_VIDEO_CAPTURE);
+
+ Intent soundRecIntent = new Intent(MediaStore.Audio.Media.RECORD_SOUND_ACTION);
+
+ if (mimeType.equals(imageMimeType)) {
+ i.setType(imageMimeType);
+ addCamcorderIntent = false;
+ if (mediaSource.equals(mediaSourceValueCamera)) {
+ // Specified 'image/*' and requested the camera, so go ahead and launch the camera
+ // directly.
+ startActivity(cameraIntent);
+ return;
+ } else if (mediaSource.equals(mediaSourceValueFileSystem)) {
+ // Specified filesytem as the source, so don't want to consider the camera.
+ addCameraIntent = false;
+ }
+ } else if (mimeType.equals(videoMimeType)) {
+ i.setType(videoMimeType);
+ addCameraIntent = false;
+ // The camcorder saves it's own file and returns it to us in the intent, so
+ // we don't need to generate one here.
+ mCameraFilePath = null;
+
+ if (mediaSource.equals(mediaSourceValueCamcorder)) {
+ // Specified 'video/*' and requested the camcorder, so go ahead and launch the
+ // camcorder directly.
+ startActivity(camcorderIntent);
+ return;
+ } else if (mediaSource.equals(mediaSourceValueFileSystem)) {
+ // Specified filesystem as the source, so don't want to consider the camcorder.
+ addCamcorderIntent = false;
+ }
+ } else if (mimeType.equals(audioMimeType)) {
+ i.setType(audioMimeType);
+ addCameraIntent = false;
+ addCamcorderIntent = false;
+ if (mediaSource.equals(mediaSourceValueMicrophone)) {
+ // Specified 'audio/*' and requested microphone, so go ahead and launch the sound
+ // recorder.
+ startActivity(soundRecIntent);
+ return;
+ }
+ // On a default system, there is no single option to open an audio "gallery". Both the
+ // sound recorder and music browser respond to the OPENABLE/audio/* intent unlike the
+ // image/* and video/* OPENABLE intents where the image / video gallery are the only
+ // respondants (and so the user is not prompted by default).
+ } else {
+ i.setType("*/*");
+ }
+
+ // Combine the chooser and the extra choices (like camera or camcorder)
+ Intent chooser = new Intent(Intent.ACTION_CHOOSER);
+ chooser.putExtra(Intent.EXTRA_INTENT, i);
+
+ Vector<Intent> extraInitialIntents = new Vector<Intent>(0);
+
+ if (addCameraIntent) {
+ extraInitialIntents.add(cameraIntent);
+ }
+
+ if (addCamcorderIntent) {
+ extraInitialIntents.add(camcorderIntent);
+ }
+
+ if (extraInitialIntents.size() > 0) {
+ Intent[] extraIntents = new Intent[extraInitialIntents.size()];
+ chooser.putExtra(Intent.EXTRA_INITIAL_INTENTS,
+ extraInitialIntents.toArray(extraIntents));
+ }
+
+ chooser.putExtra(Intent.EXTRA_TITLE,
+ mController.getActivity().getResources()
+ .getString(R.string.choose_upload));
+ startActivity(chooser);
+ }
+
+ private void startActivity(Intent intent) {
+ mController.getActivity().startActivityForResult(intent,
+ Controller.FILE_SELECTED);
+ }
+
+}
diff --git a/src/com/android/browser/UrlHandler.java b/src/com/android/browser/UrlHandler.java
new file mode 100644
index 0000000..f1d1c4c
--- /dev/null
+++ b/src/com/android/browser/UrlHandler.java
@@ -0,0 +1,292 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.app.Activity;
+import android.content.ActivityNotFoundException;
+import android.content.Intent;
+import android.content.pm.PackageManager;
+import android.database.Cursor;
+import android.net.Uri;
+import android.os.AsyncTask;
+import android.os.Bundle;
+import android.util.Log;
+import android.webkit.WebView;
+
+import java.net.URISyntaxException;
+
+/**
+ *
+ */
+public class UrlHandler {
+
+ // Use in overrideUrlLoading
+ /* package */ final static String SCHEME_WTAI = "wtai://wp/";
+ /* package */ final static String SCHEME_WTAI_MC = "wtai://wp/mc;";
+ /* package */ final static String SCHEME_WTAI_SD = "wtai://wp/sd;";
+ /* package */ final static String SCHEME_WTAI_AP = "wtai://wp/ap;";
+
+ Controller mController;
+ Activity mActivity;
+
+ private Boolean mIsProviderPresent = null;
+ private Uri mRlzUri = null;
+
+ public UrlHandler(Controller controller) {
+ mController = controller;
+ mActivity = mController.getActivity();
+ }
+
+ boolean shouldOverrideUrlLoading(Tab tab, WebView view, String url) {
+ if (view.isPrivateBrowsingEnabled()) {
+ // Don't allow urls to leave the browser app when in
+ // private browsing mode
+ return false;
+ }
+
+ if (url.startsWith(SCHEME_WTAI)) {
+ // wtai://wp/mc;number
+ // number=string(phone-number)
+ if (url.startsWith(SCHEME_WTAI_MC)) {
+ Intent intent = new Intent(Intent.ACTION_VIEW,
+ Uri.parse(WebView.SCHEME_TEL +
+ url.substring(SCHEME_WTAI_MC.length())));
+ mActivity.startActivity(intent);
+ // before leaving BrowserActivity, close the empty child tab.
+ // If a new tab is created through JavaScript open to load this
+ // url, we would like to close it as we will load this url in a
+ // different Activity.
+ mController.closeEmptyChildTab();
+ return true;
+ }
+ // wtai://wp/sd;dtmf
+ // dtmf=string(dialstring)
+ if (url.startsWith(SCHEME_WTAI_SD)) {
+ // TODO: only send when there is active voice connection
+ return false;
+ }
+ // wtai://wp/ap;number;name
+ // number=string(phone-number)
+ // name=string
+ if (url.startsWith(SCHEME_WTAI_AP)) {
+ // TODO
+ return false;
+ }
+ }
+
+ // The "about:" schemes are internal to the browser; don't want these to
+ // be dispatched to other apps.
+ if (url.startsWith("about:")) {
+ return false;
+ }
+
+ // If this is a Google search, attempt to add an RLZ string
+ // (if one isn't already present).
+ if (rlzProviderPresent()) {
+ Uri siteUri = Uri.parse(url);
+ if (needsRlzString(siteUri)) {
+ // Need to look up the RLZ info from a database, so do it in an
+ // AsyncTask. Although we are not overriding the URL load synchronously,
+ // we guarantee that we will handle this URL load after the task executes,
+ // so it's safe to just return true to WebCore now to stop its own loading.
+ new RLZTask(tab, siteUri, view).execute();
+ return true;
+ }
+ }
+
+ if (startActivityForUrl(url)) {
+ return true;
+ }
+
+ if (handleMenuClick(tab, url)) {
+ return true;
+ }
+
+ return false;
+ }
+
+ boolean startActivityForUrl(String url) {
+ Intent intent;
+ // perform generic parsing of the URI to turn it into an Intent.
+ try {
+ intent = Intent.parseUri(url, Intent.URI_INTENT_SCHEME);
+ } catch (URISyntaxException ex) {
+ Log.w("Browser", "Bad URI " + url + ": " + ex.getMessage());
+ return false;
+ }
+
+ // check whether the intent can be resolved. If not, we will see
+ // whether we can download it from the Market.
+ if (mActivity.getPackageManager().resolveActivity(intent, 0) == null) {
+ String packagename = intent.getPackage();
+ if (packagename != null) {
+ intent = new Intent(Intent.ACTION_VIEW, Uri
+ .parse("market://search?q=pname:" + packagename));
+ intent.addCategory(Intent.CATEGORY_BROWSABLE);
+ mActivity.startActivity(intent);
+ // before leaving BrowserActivity, close the empty child tab.
+ // If a new tab is created through JavaScript open to load this
+ // url, we would like to close it as we will load this url in a
+ // different Activity.
+ mController.closeEmptyChildTab();
+ return true;
+ } else {
+ return false;
+ }
+ }
+
+ // sanitize the Intent, ensuring web pages can not bypass browser
+ // security (only access to BROWSABLE activities).
+ intent.addCategory(Intent.CATEGORY_BROWSABLE);
+ intent.setComponent(null);
+ try {
+ if (mActivity.startActivityIfNeeded(intent, -1)) {
+ // before leaving BrowserActivity, close the empty child tab.
+ // If a new tab is created through JavaScript open to load this
+ // url, we would like to close it as we will load this url in a
+ // different Activity.
+ mController.closeEmptyChildTab();
+ return true;
+ }
+ } catch (ActivityNotFoundException ex) {
+ // ignore the error. If no application can handle the URL,
+ // eg about:blank, assume the browser can handle it.
+ }
+
+ return false;
+ }
+
+ // In case a physical keyboard is attached, handle clicks with the menu key
+ // depressed by opening in a new tab
+ boolean handleMenuClick(Tab tab, String url) {
+ if (mController.isMenuDown()) {
+ mController.openTab(tab, url, false);
+ mActivity.closeOptionsMenu();
+ return true;
+ }
+
+ return false;
+ }
+
+ // TODO: Move this class into Tab, where it can be properly stopped upon
+ // closure of the tab
+ private class RLZTask extends AsyncTask<Void, Void, String> {
+ private Tab mTab;
+ private Uri mSiteUri;
+ private WebView mWebView;
+
+ public RLZTask(Tab tab, Uri uri, WebView webView) {
+ mTab = tab;
+ mSiteUri = uri;
+ mWebView = webView;
+ }
+
+ protected String doInBackground(Void... unused) {
+ String result = mSiteUri.toString();
+ Cursor cur = null;
+ try {
+ cur = mActivity.getContentResolver()
+ .query(getRlzUri(), null, null, null, null);
+ if (cur != null && cur.moveToFirst() && !cur.isNull(0)) {
+ result = mSiteUri.buildUpon()
+ .appendQueryParameter("rlz", cur.getString(0))
+ .build().toString();
+ }
+ } finally {
+ if (cur != null) {
+ cur.close();
+ }
+ }
+ return result;
+ }
+
+ protected void onPostExecute(String result) {
+ // Make sure the Tab was not closed while handling the task
+ if (mController.getTabControl().getTabIndex(mTab) != -1) {
+ // If the Activity Manager is not invoked, load the URL directly
+ if (!startActivityForUrl(result)) {
+ if (!handleMenuClick(mTab, result)) {
+ mController.loadUrl(mWebView, result);
+ }
+ }
+ }
+ }
+ }
+
+ // Determine whether the RLZ provider is present on the system.
+ private boolean rlzProviderPresent() {
+ if (mIsProviderPresent == null) {
+ PackageManager pm = mActivity.getPackageManager();
+ mIsProviderPresent = pm.resolveContentProvider(
+ BrowserSettings.RLZ_PROVIDER, 0) != null;
+ }
+ return mIsProviderPresent;
+ }
+
+ // Retrieve the RLZ access point string and cache the URI used to
+ // retrieve RLZ values.
+ private Uri getRlzUri() {
+ if (mRlzUri == null) {
+ String ap = mActivity.getResources()
+ .getString(R.string.rlz_access_point);
+ mRlzUri = Uri.withAppendedPath(BrowserSettings.RLZ_PROVIDER_URI, ap);
+ }
+ return mRlzUri;
+ }
+
+ // Determine if this URI appears to be for a Google search
+ // and does not have an RLZ parameter.
+ // Taken largely from Chrome source, src/chrome/browser/google_url_tracker.cc
+ private static boolean needsRlzString(Uri uri) {
+ String scheme = uri.getScheme();
+ if (("http".equals(scheme) || "https".equals(scheme)) &&
+ (uri.getQueryParameter("q") != null) &&
+ (uri.getQueryParameter("rlz") == null)) {
+ String host = uri.getHost();
+ if (host == null) {
+ return false;
+ }
+ String[] hostComponents = host.split("\\.");
+
+ if (hostComponents.length < 2) {
+ return false;
+ }
+ int googleComponent = hostComponents.length - 2;
+ String component = hostComponents[googleComponent];
+ if (!"google".equals(component)) {
+ if (hostComponents.length < 3 ||
+ (!"co".equals(component) && !"com".equals(component))) {
+ return false;
+ }
+ googleComponent = hostComponents.length - 3;
+ if (!"google".equals(hostComponents[googleComponent])) {
+ return false;
+ }
+ }
+
+ // Google corp network handling.
+ if (googleComponent > 0 && "corp".equals(
+ hostComponents[googleComponent - 1])) {
+ return false;
+ }
+
+ return true;
+ }
+ return false;
+ }
+
+}
diff --git a/src/com/android/browser/UrlInputView.java b/src/com/android/browser/UrlInputView.java
new file mode 100644
index 0000000..23e412d
--- /dev/null
+++ b/src/com/android/browser/UrlInputView.java
@@ -0,0 +1,266 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.SuggestionsAdapter.CompletionListener;
+import com.android.browser.SuggestionsAdapter.SuggestItem;
+import com.android.browser.search.SearchEngine;
+import com.android.browser.search.SearchEngineInfo;
+import com.android.browser.search.SearchEngines;
+
+import android.content.Context;
+import android.content.res.Configuration;
+import android.text.TextUtils;
+import android.util.AttributeSet;
+import android.util.Patterns;
+import android.view.KeyEvent;
+import android.view.View;
+import android.view.View.OnFocusChangeListener;
+import android.view.inputmethod.InputMethodManager;
+import android.widget.AdapterView;
+import android.widget.AdapterView.OnItemClickListener;
+import android.widget.AutoCompleteTextView;
+import android.widget.TextView;
+import android.widget.TextView.OnEditorActionListener;
+
+import java.util.List;
+
+/**
+ * url/search input view
+ * handling suggestions
+ */
+public class UrlInputView extends AutoCompleteTextView
+ implements OnFocusChangeListener, OnEditorActionListener,
+ CompletionListener, OnItemClickListener {
+
+
+ static final String TYPED = "browser-type";
+ static final String SUGGESTED = "browser-suggest";
+ static final String VOICE = "voice-search";
+
+ private UrlInputListener mListener;
+ private InputMethodManager mInputManager;
+ private SuggestionsAdapter mAdapter;
+ private OnFocusChangeListener mWrappedFocusListener;
+ private View mContainer;
+ private boolean mLandscape;
+ private boolean mInVoiceMode;
+ private boolean mIncognitoMode;
+ private int mVOffset;
+
+ public UrlInputView(Context context, AttributeSet attrs, int defStyle) {
+ super(context, attrs, defStyle);
+ init(context);
+ }
+
+ public UrlInputView(Context context, AttributeSet attrs) {
+ super(context, attrs);
+ init(context);
+ }
+
+ public UrlInputView(Context context) {
+ super(context);
+ init(context);
+ }
+
+ private void init(Context ctx) {
+ mInputManager = (InputMethodManager) ctx.getSystemService(Context.INPUT_METHOD_SERVICE);
+ setOnEditorActionListener(this);
+ super.setOnFocusChangeListener(this);
+ mAdapter = new SuggestionsAdapter(ctx, this);
+ setAdapter(mAdapter);
+ setSelectAllOnFocus(true);
+ onConfigurationChanged(ctx.getResources().getConfiguration());
+ setThreshold(1);
+ setOnItemClickListener(this);
+ mVOffset = 0;
+ }
+
+ void setController(UiController controller) {
+ UrlSelectionActionMode urlSelectionMode
+ = new UrlSelectionActionMode(controller);
+ setCustomSelectionActionModeCallback(urlSelectionMode);
+ }
+
+ void setUseQuickControls(boolean useQuickControls) {
+ mVOffset = (useQuickControls
+ ? (int) getResources().getDimension(R.dimen.dropdown_offset)
+ : 0);
+ mAdapter.setReverseResults(useQuickControls);
+ }
+
+ void setContainer(View container) {
+ mContainer = container;
+ }
+
+ void setVoiceResults(List<String> voiceResults) {
+ mAdapter.setVoiceResults(voiceResults);
+ mInVoiceMode = (voiceResults != null);
+ }
+
+ @Override
+ protected void onConfigurationChanged(Configuration config) {
+ super.onConfigurationChanged(config);
+ mLandscape = (config.orientation &
+ Configuration.ORIENTATION_LANDSCAPE) != 0;
+ mAdapter.setLandscapeMode(mLandscape);
+ if (isPopupShowing() && (getVisibility() == View.VISIBLE)) {
+ setupDropDown();
+ performFiltering(getText(), 0);
+ }
+ }
+
+ @Override
+ public void showDropDown() {
+ setupDropDown();
+ super.showDropDown();
+ }
+
+ @Override
+ public void dismissDropDown() {
+ super.dismissDropDown();
+ mAdapter.clearCache();
+ }
+
+ private void setupDropDown() {
+ int width = mContainer.getWidth();
+ if (width != getDropDownWidth()) {
+ setDropDownWidth(width);
+ }
+ if (getLeft() != -getDropDownHorizontalOffset()) {
+ setDropDownHorizontalOffset(-getLeft());
+ }
+ setDropDownVerticalOffset(mVOffset);
+ }
+
+ @Override
+ public void setOnFocusChangeListener(OnFocusChangeListener focusListener) {
+ mWrappedFocusListener = focusListener;
+ }
+
+ @Override
+ public boolean onEditorAction(TextView v, int actionId, KeyEvent event) {
+ finishInput(getText().toString(), null, TYPED);
+ return true;
+ }
+
+ @Override
+ public void onFocusChange(View v, boolean hasFocus) {
+ if (hasFocus) {
+ forceIme();
+ if (mInVoiceMode) {
+ performFiltering(getText().toString(), 0);
+ showDropDown();
+ }
+ }
+ if (mWrappedFocusListener != null) {
+ mWrappedFocusListener.onFocusChange(v, hasFocus);
+ }
+ }
+
+ void stopEditing() {
+ finishInput(null, null, null);
+ }
+
+ public void setUrlInputListener(UrlInputListener listener) {
+ mListener = listener;
+ }
+
+ public void forceIme() {
+ mInputManager.showSoftInput(this, 0);
+ }
+
+ private void finishInput(String url, String extra, String source) {
+ this.dismissDropDown();
+ mInputManager.hideSoftInputFromWindow(getWindowToken(), 0);
+ if (TextUtils.isEmpty(url)) {
+ mListener.onDismiss();
+ } else {
+ if (mIncognitoMode && isSearch(url)) {
+ // To prevent logging, intercept this request
+ // TODO: This is a quick hack, refactor this
+ SearchEngine searchEngine = BrowserSettings.getInstance()
+ .getSearchEngine();
+ if (searchEngine == null) return;
+ SearchEngineInfo engineInfo = SearchEngines
+ .getSearchEngineInfo(mContext, searchEngine.getName());
+ if (engineInfo == null) return;
+ url = engineInfo.getSearchUriForQuery(url);
+ // mLister.onAction can take it from here without logging
+ }
+ mListener.onAction(url, extra, source);
+ }
+ }
+
+ boolean isSearch(String inUrl) {
+ String url = UrlUtils.fixUrl(inUrl).trim();
+ if (TextUtils.isEmpty(url)) return false;
+
+ if (Patterns.WEB_URL.matcher(url).matches()
+ || UrlUtils.ACCEPTED_URI_SCHEMA.matcher(url).matches()) {
+ return false;
+ }
+ return true;
+ }
+
+ // Completion Listener
+
+ @Override
+ public void onSearch(String search) {
+ mListener.onEdit(search);
+ }
+
+ @Override
+ public void onSelect(String url, int type, String extra) {
+ finishInput(url, extra, (type == SuggestionsAdapter.TYPE_VOICE_SEARCH)
+ ? VOICE : SUGGESTED);
+ }
+
+ @Override
+ public boolean onKeyPreIme(int keyCode, KeyEvent evt) {
+ if (keyCode == KeyEvent.KEYCODE_BACK) {
+ // catch back key in order to do slightly more cleanup than usual
+ finishInput(null, null, null);
+ return true;
+ }
+ return super.onKeyPreIme(keyCode, evt);
+ }
+
+ @Override
+ public void onItemClick(
+ AdapterView<?> parent, View view, int position, long id) {
+ SuggestItem item = mAdapter.getItem(position);
+ onSelect((TextUtils.isEmpty(item.url) ? item.title : item.url),
+ item.type, item.extra);
+ }
+
+ interface UrlInputListener {
+
+ public void onDismiss();
+
+ public void onAction(String text, String extra, String source);
+
+ public void onEdit(String text);
+
+ }
+
+ public void setIncognitoMode(boolean incognito) {
+ mIncognitoMode = incognito;
+ mAdapter.setIncognitoMode(mIncognitoMode);
+ }
+
+}
diff --git a/src/com/android/browser/UrlSelectionActionMode.java b/src/com/android/browser/UrlSelectionActionMode.java
new file mode 100644
index 0000000..5636388
--- /dev/null
+++ b/src/com/android/browser/UrlSelectionActionMode.java
@@ -0,0 +1,61 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License"); you may not
+ * use this file except in compliance with the License. You may obtain a copy of
+ * the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
+ * WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
+ * License for the specific language governing permissions and limitations under
+ * the License.
+ */
+
+package com.android.browser;
+
+import android.view.ActionMode;
+import android.view.Menu;
+import android.view.MenuItem;
+
+public class UrlSelectionActionMode implements ActionMode.Callback {
+
+ private UiController mUiController;
+
+ public UrlSelectionActionMode(UiController controller) {
+ mUiController = controller;
+ }
+
+ // ActionMode.Callback implementation
+
+ @Override
+ public boolean onCreateActionMode(ActionMode mode, Menu menu) {
+ mode.getMenuInflater().inflate(R.menu.url_selection, menu);
+ return true;
+ }
+
+ @Override
+ public boolean onActionItemClicked(ActionMode mode, MenuItem item) {
+ switch (item.getItemId()) {
+ case R.id.share:
+ mUiController.shareCurrentPage();
+ mode.finish();
+ break;
+ default:
+ return false;
+ }
+ return true;
+ }
+
+ @Override
+ public void onDestroyActionMode(ActionMode mode) {
+ }
+
+ @Override
+ public boolean onPrepareActionMode(ActionMode mode, Menu menu) {
+ return true;
+ }
+
+}
diff --git a/src/com/android/browser/UrlUtils.java b/src/com/android/browser/UrlUtils.java
new file mode 100644
index 0000000..d6278ca
--- /dev/null
+++ b/src/com/android/browser/UrlUtils.java
@@ -0,0 +1,162 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.homepages.HomeProvider;
+
+import android.net.Uri;
+import android.util.Patterns;
+import android.webkit.URLUtil;
+
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+/**
+ * Utility methods for Url manipulation
+ */
+public class UrlUtils {
+
+ static final Pattern ACCEPTED_URI_SCHEMA = Pattern.compile(
+ "(?i)" + // switch on case insensitive matching
+ "(" + // begin group for schema
+ "(?:http|https|file):\\/\\/" +
+ "|(?:inline|data|about|javascript):" +
+ ")" +
+ "(.*)" );
+
+ // Google search
+ private final static String QUICKSEARCH_G = "http://www.google.com/m?q=%s";
+ private final static String QUERY_PLACE_HOLDER = "%s";
+
+ // Regular expression which matches http://, followed by some stuff, followed by
+ // optionally a trailing slash, all matched as separate groups.
+ private static final Pattern STRIP_URL_PATTERN = Pattern.compile("^(http://)(.*?)(/$)?");
+
+ private UrlUtils() { /* cannot be instantiated */ }
+
+ /**
+ * Strips the provided url of preceding "http://" and any trailing "/". Does not
+ * strip "https://". If the provided string cannot be stripped, the original string
+ * is returned.
+ *
+ * TODO: Put this in TextUtils to be used by other packages doing something similar.
+ *
+ * @param url a url to strip, like "http://www.google.com/"
+ * @return a stripped url like "www.google.com", or the original string if it could
+ * not be stripped
+ */
+ /* package */ static String stripUrl(String url) {
+ if (url == null) return null;
+ Matcher m = STRIP_URL_PATTERN.matcher(url);
+ if (m.matches() && m.groupCount() == 3) {
+ return m.group(2);
+ } else {
+ return url;
+ }
+ }
+
+ protected static String smartUrlFilter(Uri inUri) {
+ if (inUri != null) {
+ return smartUrlFilter(inUri.toString());
+ }
+ return null;
+ }
+
+ /**
+ * Attempts to determine whether user input is a URL or search
+ * terms. Anything with a space is passed to search.
+ *
+ * Converts to lowercase any mistakenly uppercased schema (i.e.,
+ * "Http://" converts to "http://"
+ *
+ * @return Original or modified URL
+ *
+ */
+ protected static String smartUrlFilter(String url) {
+
+ String inUrl = url.trim();
+ boolean hasSpace = inUrl.indexOf(' ') != -1;
+
+ Matcher matcher = ACCEPTED_URI_SCHEMA.matcher(inUrl);
+ if (matcher.matches()) {
+ // force scheme to lowercase
+ String scheme = matcher.group(1);
+ String lcScheme = scheme.toLowerCase();
+ if (!lcScheme.equals(scheme)) {
+ inUrl = lcScheme + matcher.group(2);
+ }
+ if (hasSpace) {
+ inUrl = inUrl.replace(" ", "%20");
+ }
+ return inUrl;
+ }
+ if (!hasSpace) {
+ if (Patterns.WEB_URL.matcher(inUrl).matches()) {
+ return URLUtil.guessUrl(inUrl);
+ }
+ }
+
+ // FIXME: Is this the correct place to add to searches?
+ // what if someone else calls this function?
+
+// Browser.addSearchUrl(mBrowser.getContentResolver(), inUrl);
+ return URLUtil.composeSearchUrl(inUrl, QUICKSEARCH_G, QUERY_PLACE_HOLDER);
+ }
+
+ /* package */ static String fixUrl(String inUrl) {
+ // FIXME: Converting the url to lower case
+ // duplicates functionality in smartUrlFilter().
+ // However, changing all current callers of fixUrl to
+ // call smartUrlFilter in addition may have unwanted
+ // consequences, and is deferred for now.
+ int colon = inUrl.indexOf(':');
+ boolean allLower = true;
+ for (int index = 0; index < colon; index++) {
+ char ch = inUrl.charAt(index);
+ if (!Character.isLetter(ch)) {
+ break;
+ }
+ allLower &= Character.isLowerCase(ch);
+ if (index == colon - 1 && !allLower) {
+ inUrl = inUrl.substring(0, colon).toLowerCase()
+ + inUrl.substring(colon);
+ }
+ }
+ if (inUrl.startsWith("http://") || inUrl.startsWith("https://"))
+ return inUrl;
+ if (inUrl.startsWith("http:") ||
+ inUrl.startsWith("https:")) {
+ if (inUrl.startsWith("http:/") || inUrl.startsWith("https:/")) {
+ inUrl = inUrl.replaceFirst("/", "//");
+ } else inUrl = inUrl.replaceFirst(":", "://");
+ }
+ return inUrl;
+ }
+
+ // Returns the filtered URL. Cannot return null, but can return an empty string
+ /* package */ static String filteredUrl(String inUrl) {
+ if (inUrl == null) {
+ return "";
+ }
+ if (inUrl.startsWith("content:")
+ || inUrl.startsWith("browser:")) {
+ return "";
+ }
+ return inUrl;
+ }
+
+}
diff --git a/src/com/android/browser/WallpaperHandler.java b/src/com/android/browser/WallpaperHandler.java
new file mode 100644
index 0000000..0c88a50
--- /dev/null
+++ b/src/com/android/browser/WallpaperHandler.java
@@ -0,0 +1,127 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.app.ProgressDialog;
+import android.app.WallpaperManager;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.graphics.Bitmap;
+import android.graphics.Canvas;
+import android.graphics.drawable.Drawable;
+import android.util.Log;
+import android.view.MenuItem;
+import android.view.MenuItem.OnMenuItemClickListener;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.net.MalformedURLException;
+import java.net.URL;
+
+/**
+ * Handle setWallpaper requests
+ *
+ */
+public class WallpaperHandler extends Thread
+ implements OnMenuItemClickListener, DialogInterface.OnCancelListener {
+
+
+ private static final String LOGTAG = "WallpaperHandler";
+
+ private Context mContext;
+ private URL mUrl;
+ private ProgressDialog mWallpaperProgress;
+ private boolean mCanceled = false;
+
+ public WallpaperHandler(Context context, String url) {
+ mContext = context;
+ try {
+ mUrl = new URL(url);
+ } catch (MalformedURLException e) {
+ mUrl = null;
+ }
+ }
+
+ @Override
+ public void onCancel(DialogInterface dialog) {
+ mCanceled = true;
+ }
+
+ @Override
+ public boolean onMenuItemClick(MenuItem item) {
+ if (mUrl != null) {
+ // The user may have tried to set a image with a large file size as
+ // their background so it may take a few moments to perform the
+ // operation.
+ // Display a progress spinner while it is working.
+ mWallpaperProgress = new ProgressDialog(mContext);
+ mWallpaperProgress.setIndeterminate(true);
+ mWallpaperProgress.setMessage(mContext.getResources()
+ .getText(R.string.progress_dialog_setting_wallpaper));
+ mWallpaperProgress.setCancelable(true);
+ mWallpaperProgress.setOnCancelListener(this);
+ mWallpaperProgress.show();
+ start();
+ }
+ return true;
+ }
+
+ @Override
+ public void run() {
+ Drawable oldWallpaper =
+ WallpaperManager.getInstance(mContext).getDrawable();
+ try {
+ // TODO: This will cause the resource to be downloaded again, when
+ // we should in most cases be able to grab it from the cache. To fix
+ // this we should query WebCore to see if we can access a cached
+ // version and instead open an input stream on that. This pattern
+ // could also be used in the download manager where the same problem
+ // exists.
+ InputStream inputstream = mUrl.openStream();
+ if (inputstream != null) {
+ WallpaperManager.getInstance(mContext).setStream(inputstream);
+ }
+ } catch (IOException e) {
+ Log.e(LOGTAG, "Unable to set new wallpaper");
+ // Act as though the user canceled the operation so we try to
+ // restore the old wallpaper.
+ mCanceled = true;
+ }
+
+ if (mCanceled) {
+ // Restore the old wallpaper if the user cancelled whilst we were
+ // setting
+ // the new wallpaper.
+ int width = oldWallpaper.getIntrinsicWidth();
+ int height = oldWallpaper.getIntrinsicHeight();
+ Bitmap bm = Bitmap.createBitmap(width, height, Bitmap.Config.RGB_565);
+ Canvas canvas = new Canvas(bm);
+ oldWallpaper.setBounds(0, 0, width, height);
+ oldWallpaper.draw(canvas);
+ try {
+ WallpaperManager.getInstance(mContext).setBitmap(bm);
+ } catch (IOException e) {
+ Log.e(LOGTAG, "Unable to restore old wallpaper.");
+ }
+ mCanceled = false;
+ }
+
+ if (mWallpaperProgress.isShowing()) {
+ mWallpaperProgress.dismiss();
+ }
+ }
+}
diff --git a/src/com/android/browser/WebDialog.java b/src/com/android/browser/WebDialog.java
deleted file mode 100644
index 9995e8f..0000000
--- a/src/com/android/browser/WebDialog.java
+++ /dev/null
@@ -1,79 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.browser;
-
-import android.content.Context;
-import android.view.View;
-import android.view.animation.AnimationUtils;
-import android.view.inputmethod.InputMethodManager;
-import android.webkit.WebView;
-import android.widget.LinearLayout;
-
-/* package */ class WebDialog extends LinearLayout {
- protected WebView mWebView;
- protected BrowserActivity mBrowserActivity;
- private boolean mIsVisible;
-
- /* package */ WebDialog(BrowserActivity context) {
- super(context);
- mBrowserActivity = context;
- }
-
- /* dialogs that have cancel buttons can optionally share code by including a
- * view with an id of 'done'.
- */
- protected void addCancel() {
- View button = findViewById(R.id.done);
- if (button != null) button.setOnClickListener(mCancelListener);
- }
-
- private View.OnClickListener mCancelListener = new View.OnClickListener() {
- public void onClick(View v) {
- mBrowserActivity.closeDialogs();
- }
- };
-
- protected void dismiss() {
- startAnimation(AnimationUtils.loadAnimation(mBrowserActivity,
- R.anim.dialog_exit));
- mIsVisible = false;
- }
-
- /*
- * Remove the soft keyboard from the screen.
- */
- protected void hideSoftInput() {
- InputMethodManager imm = (InputMethodManager)
- mBrowserActivity.getSystemService(Context.INPUT_METHOD_SERVICE);
- imm.hideSoftInputFromWindow(mWebView.getWindowToken(), 0);
- }
-
- protected boolean isVisible() {
- return mIsVisible;
- }
-
- /* package */ void setWebView(WebView webview) {
- mWebView = webview;
- }
-
- protected void show() {
- startAnimation(AnimationUtils.loadAnimation(mBrowserActivity,
- R.anim.dialog_enter));
- mIsVisible = true;
- }
-
-}
diff --git a/src/com/android/browser/WebStorageSizeManager.java b/src/com/android/browser/WebStorageSizeManager.java
index dcf2f8b..bd7f8e6 100644
--- a/src/com/android/browser/WebStorageSizeManager.java
+++ b/src/com/android/browser/WebStorageSizeManager.java
@@ -16,17 +16,19 @@
package com.android.browser;
+import com.android.browser.preferences.WebsiteSettingsFragment;
+
import android.app.Notification;
import android.app.NotificationManager;
import android.app.PendingIntent;
import android.content.Context;
import android.content.Intent;
import android.os.StatFs;
+import android.preference.PreferenceActivity;
import android.util.Log;
import android.webkit.WebStorage;
import java.io.File;
-import java.util.Set;
/**
@@ -82,7 +84,7 @@
* the user can free some of the Web storage space by deleting all the data used
* by an origin.
*/
-class WebStorageSizeManager {
+public class WebStorageSizeManager {
// Logging flags.
private final static boolean LOGV_ENABLED = com.android.browser.Browser.LOGV_ENABLED;
private final static boolean LOGD_ENABLED = com.android.browser.Browser.LOGD_ENABLED;
@@ -139,11 +141,11 @@
}
public long getFreeSpaceSizeBytes() {
- return mFs.getAvailableBlocks() * mFs.getBlockSize();
+ return (long)(mFs.getAvailableBlocks()) * mFs.getBlockSize();
}
public long getTotalSizeBytes() {
- return mFs.getBlockCount() * mFs.getBlockSize();
+ return (long)(mFs.getBlockCount()) * mFs.getBlockSize();
}
};
@@ -346,7 +348,7 @@
// Reset the notification time; we use this iff the user
// use clear all; we reset it to some time in the future instead
// of just setting it to -1, as the clear all method is asynchronous
- static void resetLastOutOfSpaceNotificationTime() {
+ public static void resetLastOutOfSpaceNotificationTime() {
mLastOutOfSpaceNotificationTime = System.currentTimeMillis() -
NOTIFICATION_INTERVAL + RESET_NOTIFICATION_INTERVAL;
}
@@ -403,7 +405,9 @@
CharSequence text = mContext.getString(
R.string.webstorage_outofspace_notification_text);
long when = System.currentTimeMillis();
- Intent intent = new Intent(mContext, WebsiteSettingsActivity.class);
+ Intent intent = new Intent(mContext, BrowserPreferencesPage.class);
+ intent.putExtra(PreferenceActivity.EXTRA_SHOW_FRAGMENT,
+ WebsiteSettingsFragment.class.getName());
PendingIntent contentIntent =
PendingIntent.getActivity(mContext, 0, intent, 0);
Notification notification = new Notification(icon, title, when);
diff --git a/src/com/android/browser/WebViewController.java b/src/com/android/browser/WebViewController.java
new file mode 100644
index 0000000..813b63b
--- /dev/null
+++ b/src/com/android/browser/WebViewController.java
@@ -0,0 +1,115 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.IntentHandler.UrlData;
+
+import android.app.Activity;
+import android.graphics.Bitmap;
+import android.net.Uri;
+import android.net.http.SslError;
+import android.os.Message;
+import android.view.KeyEvent;
+import android.view.View;
+import android.webkit.HttpAuthHandler;
+import android.webkit.SslErrorHandler;
+import android.webkit.ValueCallback;
+import android.webkit.WebChromeClient;
+import android.webkit.WebView;
+
+/**
+ * WebView aspect of the controller
+ */
+public interface WebViewController {
+
+ Activity getActivity();
+
+ TabControl getTabControl();
+
+ WebViewFactory getWebViewFactory();
+
+ void onSetWebView(Tab tab, WebView view);
+
+ void createSubWindow(Tab tab);
+
+ void onPageStarted(Tab tab, WebView view, Bitmap favicon);
+
+ void onPageFinished(Tab tab);
+
+ void onProgressChanged(Tab tab);
+
+ void onReceivedTitle(Tab tab, final String title);
+
+ void onFavicon(Tab tab, WebView view, Bitmap icon);
+
+ boolean shouldOverrideUrlLoading(Tab tab, WebView view, String url);
+
+ boolean shouldOverrideKeyEvent(KeyEvent event);
+
+ void onUnhandledKeyEvent(KeyEvent event);
+
+ void doUpdateVisitedHistory(Tab tab, boolean isReload);
+
+ void getVisitedHistory(final ValueCallback<String[]> callback);
+
+ void onReceivedHttpAuthRequest(Tab tab, WebView view, final HttpAuthHandler handler,
+ final String host, final String realm);
+
+ void onDownloadStart(Tab tab, String url, String useragent, String contentDisposition,
+ String mimeType, long contentLength);
+
+ void showCustomView(Tab tab, View view, WebChromeClient.CustomViewCallback callback);
+
+ void hideCustomView();
+
+ Bitmap getDefaultVideoPoster();
+
+ View getVideoLoadingProgressView();
+
+ void showSslCertificateOnError(WebView view, SslErrorHandler handler,
+ SslError error);
+
+ void onUserCanceledSsl(Tab tab);
+
+ void activateVoiceSearchMode(String title);
+
+ void revertVoiceSearchMode(Tab tab);
+
+ boolean shouldShowErrorConsole();
+
+ void onUpdatedLockIcon(Tab tab);
+
+ void openFileChooser(ValueCallback<Uri> uploadMsg, String acceptType);
+
+ void endActionMode();
+
+ void attachSubWindow(Tab tab);
+
+ void dismissSubWindow(Tab tab);
+
+ Tab openTabAndShow(Tab parent, UrlData urlData, boolean closeOnExit,
+ String appId);
+
+ boolean switchToTab(int tabindex);
+
+ void closeTab(Tab tab);
+
+ void setupAutoFill(Message message);
+
+ void bookmarkedStatusHasChanged(Tab tab);
+
+}
diff --git a/src/com/android/browser/WebViewFactory.java b/src/com/android/browser/WebViewFactory.java
new file mode 100644
index 0000000..1186e65
--- /dev/null
+++ b/src/com/android/browser/WebViewFactory.java
@@ -0,0 +1,30 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import android.webkit.WebView;
+
+/**
+ * Factory for WebViews
+ */
+public interface WebViewFactory {
+
+ public WebView createWebView(boolean privateBrowsing);
+
+ public WebView createSubWebView(boolean privateBrowsing);
+
+}
diff --git a/src/com/android/browser/XLargeUi.java b/src/com/android/browser/XLargeUi.java
new file mode 100644
index 0000000..562705b
--- /dev/null
+++ b/src/com/android/browser/XLargeUi.java
@@ -0,0 +1,429 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser;
+
+import com.android.browser.ScrollWebView.ScrollListener;
+
+import android.app.ActionBar;
+import android.app.Activity;
+import android.os.Bundle;
+import android.util.Log;
+import android.view.ActionMode;
+import android.view.Gravity;
+import android.view.KeyEvent;
+import android.view.View;
+import android.webkit.WebChromeClient.CustomViewCallback;
+import android.webkit.WebView;
+import android.widget.FrameLayout;
+import android.widget.FrameLayout.LayoutParams;
+
+import java.util.List;
+
+/**
+ * Ui for xlarge screen sizes
+ */
+public class XLargeUi extends BaseUi implements ScrollListener {
+
+ private static final String LOGTAG = "XLargeUi";
+
+ private ActionBar mActionBar;
+ private TabBar mTabBar;
+
+ private TitleBarXLarge mTitleBar;
+ private TitleBarXLarge mFakeTitleBar;
+
+ private boolean mUseQuickControls;
+ private PieControl mPieControl;
+
+ /**
+ * @param browser
+ * @param controller
+ */
+ public XLargeUi(Activity browser, UiController controller) {
+ super(browser, controller);
+ mTitleBar = new TitleBarXLarge(mActivity, mUiController, this);
+ mTitleBar.setProgress(100);
+ mTitleBar.setEditable(false);
+ mFakeTitleBar = new TitleBarXLarge(mActivity, mUiController, this);
+ mFakeTitleBar.setEditable(true);
+ mTabBar = new TabBar(mActivity, mUiController, this);
+ mActionBar = mActivity.getActionBar();
+ setupActionBar();
+ setUseQuickControls(BrowserSettings.getInstance().useQuickControls());
+ }
+
+ private void setupActionBar() {
+ mActionBar.setNavigationMode(ActionBar.NAVIGATION_MODE_STANDARD);
+ mActionBar.setDisplayOptions(ActionBar.DISPLAY_SHOW_CUSTOM);
+ mActionBar.setCustomView(mTabBar);
+ }
+
+ @Override
+ public void showComboView(boolean startWithHistory, Bundle extras) {
+ super.showComboView(startWithHistory, extras);
+ if (mUseQuickControls) {
+ mActionBar.show();
+ }
+ }
+
+ @Override
+ public void hideComboView() {
+ checkTabCount();
+ super.hideComboView();
+ // ComboView changes the action bar, set it back up to what we want
+ setupActionBar();
+ }
+
+ private void setUseQuickControls(boolean useQuickControls) {
+ mUseQuickControls = useQuickControls;
+ if (useQuickControls) {
+ checkTabCount();
+ mPieControl = new PieControl(mActivity, mUiController, this);
+ mPieControl.attachToContainer(mContentView);
+ setFakeTitleBarGravity(Gravity.BOTTOM);
+
+ // remove embedded title bar if present
+ WebView web = mTabControl.getCurrentWebView();
+ if ((web != null) && (web.getVisibleTitleHeight() > 0)) {
+ web.setEmbeddedTitleBar(null);
+ }
+ } else {
+ mActivity.getActionBar().show();
+ if (mPieControl != null) {
+ mPieControl.removeFromContainer(mContentView);
+ }
+ setFakeTitleBarGravity(Gravity.TOP);
+ // remove embedded title bar if present
+ WebView web = mTabControl.getCurrentWebView();
+ if ((web != null) && (web.getVisibleTitleHeight() == 0)) {
+ web.setEmbeddedTitleBar(mTitleBar);
+ }
+ }
+ mTabBar.setUseQuickControls(mUseQuickControls);
+ mFakeTitleBar.setUseQuickControls(mUseQuickControls);
+ }
+
+ private void checkTabCount() {
+ if (mUseQuickControls) {
+ int n = mTabBar.getTabCount();
+ if (n >= 2) {
+ mActivity.getActionBar().show();
+ } else if (n == 1) {
+ mActivity.getActionBar().hide();
+ }
+ }
+ }
+
+ @Override
+ public void onDestroy() {
+ hideFakeTitleBar();
+ }
+
+ // webview factory
+
+ @Override
+ public WebView createWebView(boolean privateBrowsing) {
+ // Create a new WebView
+ ScrollWebView w = new ScrollWebView(mActivity, null,
+ android.R.attr.webViewStyle, privateBrowsing);
+ initWebViewSettings(w);
+ w.setScrollListener(this);
+ w.getSettings().setDisplayZoomControls(false);
+ w.setExpandedTileBounds(true); // smoother scrolling
+ return w;
+ }
+
+ @Override
+ public WebView createSubWebView(boolean privateBrowsing) {
+ ScrollWebView web = (ScrollWebView) createWebView(privateBrowsing);
+ // no scroll listener for subview
+ web.setScrollListener(null);
+ return web;
+ }
+
+ @Override
+ public void onScroll(int visibleTitleHeight) {
+ mTabBar.onScroll(visibleTitleHeight);
+ }
+
+ void stopWebViewScrolling() {
+ ScrollWebView web = (ScrollWebView) mUiController.getCurrentWebView();
+ if (web != null) {
+ web.stopScroll();
+ }
+ }
+
+ // WebView callbacks
+
+ @Override
+ public void bookmarkedStatusHasChanged(Tab tab) {
+ if (tab.inForeground()) {
+ boolean isBookmark = tab.isBookmarkedSite();
+ mTitleBar.setCurrentUrlIsBookmark(isBookmark);
+ mFakeTitleBar.setCurrentUrlIsBookmark(isBookmark);
+ }
+ }
+
+ @Override
+ public void onProgressChanged(Tab tab) {
+ int progress = tab.getLoadProgress();
+ mTabBar.onProgress(tab, progress);
+ if (tab.inForeground()) {
+ mFakeTitleBar.setProgress(progress);
+ if (progress == 100) {
+ if (!mFakeTitleBar.isEditingUrl()) {
+ hideFakeTitleBar();
+ if (mUseQuickControls) {
+ mFakeTitleBar.setShowProgressOnly(false);
+ setFakeTitleBarGravity(Gravity.BOTTOM);
+ }
+ }
+ } else {
+ if (mUseQuickControls && !mFakeTitleBar.isEditingUrl()) {
+ mFakeTitleBar.setShowProgressOnly(true);
+ if (!isFakeTitleBarShowing()) {
+ setFakeTitleBarGravity(Gravity.TOP);
+ }
+ }
+ showFakeTitleBar();
+ }
+ }
+ }
+
+ @Override
+ public boolean needsRestoreAllTabs() {
+ return true;
+ }
+
+ @Override
+ public void addTab(Tab tab) {
+ mTabBar.onNewTab(tab);
+ }
+
+ protected void onAddTabCompleted(Tab tab) {
+ checkTabCount();
+ }
+
+ @Override
+ public void setActiveTab(Tab tab) {
+ super.setActiveTab(tab);
+ ScrollWebView view = (ScrollWebView) tab.getWebView();
+ // TabControl.setCurrentTab has been called before this,
+ // so the tab is guaranteed to have a webview
+ if (view == null) {
+ Log.e(LOGTAG, "active tab with no webview detected");
+ return;
+ }
+ // Request focus on the top window.
+ if (mUseQuickControls) {
+ mPieControl.forceToTop(mContentView);
+ view.setScrollListener(null);
+ mTabBar.showTitleBarIndicator(false);
+ } else {
+ view.setEmbeddedTitleBar(mTitleBar);
+ view.setScrollListener(this);
+ }
+ mTabBar.onSetActiveTab(tab);
+ if (tab.isInVoiceSearchMode()) {
+ showVoiceTitleBar(tab.getVoiceDisplayTitle());
+ } else {
+ revertVoiceTitleBar(tab);
+ }
+ updateLockIconToLatest(tab);
+ tab.getTopWindow().requestFocus();
+ }
+
+ @Override
+ public void updateTabs(List<Tab> tabs) {
+ mTabBar.updateTabs(tabs);
+ checkTabCount();
+ }
+
+ @Override
+ public void removeTab(Tab tab) {
+ super.removeTab(tab);
+ mTabBar.onRemoveTab(tab);
+ }
+
+ protected void onRemoveTabCompleted(Tab tab) {
+ checkTabCount();
+ }
+
+ int getContentWidth() {
+ if (mContentView != null) {
+ return mContentView.getWidth();
+ }
+ return 0;
+ }
+
+ void editUrl(boolean clearInput) {
+ if (mUiController.isInCustomActionMode()) {
+ mUiController.endActionMode();
+ }
+ showFakeTitleBar();
+ mFakeTitleBar.onEditUrl(clearInput);
+ }
+
+ void setFakeTitleBarGravity(int gravity) {
+ FrameLayout.LayoutParams lp = (FrameLayout.LayoutParams)
+ mFakeTitleBar.getLayoutParams();
+ if (lp == null) {
+ lp = new FrameLayout.LayoutParams(LayoutParams.MATCH_PARENT,
+ LayoutParams.WRAP_CONTENT);
+ }
+ lp.gravity = gravity;
+ mFakeTitleBar.setLayoutParams(lp);
+ }
+
+ void showFakeTitleBarAndEdit() {
+ mFakeTitleBar.setShowProgressOnly(false);
+ setFakeTitleBarGravity(Gravity.BOTTOM);
+ showFakeTitleBar();
+ mFakeTitleBar.onEditUrl(false);
+ }
+
+ @Override
+ protected void attachFakeTitleBar(WebView mainView) {
+ mContentView.addView(mFakeTitleBar);
+ mTabBar.onShowTitleBar();
+ }
+
+ @Override
+ protected void hideFakeTitleBar() {
+ if (isFakeTitleBarShowing()) {
+ mFakeTitleBar.setEditMode(false);
+ mTabBar.onHideTitleBar();
+ mContentView.removeView(mFakeTitleBar);
+ }
+ }
+
+ @Override
+ protected boolean isFakeTitleBarShowing() {
+ return (mFakeTitleBar.getParent() != null);
+ }
+
+ @Override
+ protected TitleBarBase getFakeTitleBar() {
+ return mFakeTitleBar;
+ }
+
+ @Override
+ protected TitleBarBase getEmbeddedTitleBar() {
+ return mTitleBar;
+ }
+
+ // action mode callbacks
+
+ @Override
+ public void onActionModeStarted(ActionMode mode) {
+ if (!mFakeTitleBar.isEditingUrl()) {
+ // hide the fake title bar when CAB is shown
+ hideFakeTitleBar();
+ }
+ }
+
+ @Override
+ public void onActionModeFinished(boolean inLoad) {
+ checkTabCount();
+ if (inLoad) {
+ // the titlebar was removed when the CAB was shown
+ // if the page is loading, show it again
+ mFakeTitleBar.setShowProgressOnly(true);
+ if (!isFakeTitleBarShowing()) {
+ setFakeTitleBarGravity(Gravity.TOP);
+ }
+ showFakeTitleBar();
+ }
+ }
+
+ @Override
+ protected void updateNavigationState(Tab tab) {
+ mTitleBar.updateNavigationState(tab);
+ mFakeTitleBar.updateNavigationState(tab);
+ }
+
+ @Override
+ public void setUrlTitle(Tab tab) {
+ super.setUrlTitle(tab);
+ mTabBar.onUrlAndTitle(tab, tab.getUrl(), tab.getTitle());
+ }
+
+ // Set the favicon in the title bar.
+ @Override
+ public void setFavicon(Tab tab) {
+ super.setFavicon(tab);
+ mTabBar.onFavicon(tab, tab.getFavicon());
+ }
+
+ @Override
+ public void showVoiceTitleBar(String title) {
+ List<String> vsresults = null;
+ if (getActiveTab() != null) {
+ vsresults = getActiveTab().getVoiceSearchResults();
+ }
+ mTitleBar.setInVoiceMode(true, null);
+ mTitleBar.setDisplayTitle(title);
+ mFakeTitleBar.setInVoiceMode(true, vsresults);
+ mFakeTitleBar.setDisplayTitle(title);
+ }
+
+ @Override
+ public void revertVoiceTitleBar(Tab tab) {
+ mTitleBar.setInVoiceMode(false, null);
+ String url = tab.getUrl();
+ mTitleBar.setDisplayTitle(url);
+ mFakeTitleBar.setInVoiceMode(false, null);
+ mFakeTitleBar.setDisplayTitle(url);
+ }
+
+ @Override
+ public void showCustomView(View view, CustomViewCallback callback) {
+ super.showCustomView(view, callback);
+ mActivity.getActionBar().hide();
+ }
+
+ @Override
+ public void onHideCustomView() {
+ super.onHideCustomView();
+ if (mUseQuickControls) {
+ checkTabCount();
+ } else {
+ mActivity.getActionBar().show();
+ }
+ }
+
+ @Override
+ public boolean dispatchKey(int code, KeyEvent event) {
+ WebView web = getActiveTab().getWebView();
+ switch (code) {
+ case KeyEvent.KEYCODE_TAB:
+ case KeyEvent.KEYCODE_DPAD_UP:
+ case KeyEvent.KEYCODE_DPAD_LEFT:
+ if ((web != null) && web.hasFocus()) {
+ editUrl(true);
+ return true;
+ }
+ }
+ boolean ctrl = event.hasModifiers(KeyEvent.META_CTRL_ON);
+ if (!ctrl && event.isPrintingKey() && !mFakeTitleBar.isEditingUrl()) {
+ editUrl(true);
+ return mContentView.dispatchKeyEvent(event);
+ }
+ return false;
+ }
+
+}
diff --git a/src/com/android/browser/addbookmark/FolderSpinner.java b/src/com/android/browser/addbookmark/FolderSpinner.java
new file mode 100644
index 0000000..dd85cda
--- /dev/null
+++ b/src/com/android/browser/addbookmark/FolderSpinner.java
@@ -0,0 +1,92 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser.addbookmark;
+
+import android.content.Context;
+import android.view.View;
+import android.util.AttributeSet;
+import android.widget.AdapterView;
+import android.widget.Spinner;
+
+/**
+ * Special Spinner class with its own callback for when the selection is set, which
+ * can be ignored by calling setSelectionIgnoringSelectionChange
+ */
+public class FolderSpinner extends Spinner
+ implements AdapterView.OnItemSelectedListener {
+ private OnSetSelectionListener mOnSetSelectionListener;
+ private boolean mFireSetSelection;
+
+ /**
+ * Callback for knowing when the selection has been manually set. Does not
+ * get called until the selected view has changed.
+ */
+ public interface OnSetSelectionListener {
+ public void onSetSelection(long id);
+ }
+
+ public FolderSpinner(Context context, AttributeSet attrs) {
+ super(context, attrs);
+ super.setOnItemSelectedListener(this);
+ }
+
+ @Override
+ public void setOnItemSelectedListener(AdapterView.OnItemSelectedListener l) {
+ // Disallow setting an OnItemSelectedListener, since it is used by us
+ // to fire onSetSelection.
+ throw new RuntimeException("Cannot set an OnItemSelectedListener on a FolderSpinner");
+ }
+
+ public void setOnSetSelectionListener(OnSetSelectionListener l) {
+ mOnSetSelectionListener = l;
+ }
+
+ /**
+ * Call setSelection, without firing the callback
+ * @param position New position to select.
+ */
+ public void setSelectionIgnoringSelectionChange(int position) {
+ super.setSelection(position);
+ }
+
+ @Override
+ public void setSelection(int position) {
+ mFireSetSelection = true;
+ int oldPosition = getSelectedItemPosition();
+ super.setSelection(position);
+ if (mOnSetSelectionListener != null) {
+ if (oldPosition == position) {
+ long id = getAdapter().getItemId(position);
+ // Normally this is not called because the item did not actually
+ // change, but in this case, we still want it to be called.
+ onItemSelected(this, null, position, id);
+ }
+ }
+ }
+
+ @Override
+ public void onItemSelected(AdapterView<?> parent, View view, int position, long id) {
+ if (mFireSetSelection) {
+ mOnSetSelectionListener.onSetSelection(id);
+ mFireSetSelection = false;
+ }
+ }
+
+ @Override
+ public void onNothingSelected(AdapterView<?> parent) {}
+}
+
diff --git a/src/com/android/browser/addbookmark/FolderSpinnerAdapter.java b/src/com/android/browser/addbookmark/FolderSpinnerAdapter.java
new file mode 100644
index 0000000..0712469
--- /dev/null
+++ b/src/com/android/browser/addbookmark/FolderSpinnerAdapter.java
@@ -0,0 +1,135 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser.addbookmark;
+
+import com.android.browser.R;
+
+import android.content.Context;
+import android.content.res.Resources;
+import android.database.DataSetObserver;
+import android.graphics.drawable.Drawable;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.Adapter;
+import android.widget.SpinnerAdapter;
+import android.widget.TextView;
+
+/**
+ * SpinnerAdapter used in the AddBookmarkPage to select where to save a
+ * bookmark/folder.
+ */
+public class FolderSpinnerAdapter implements SpinnerAdapter {
+ private boolean mIncludeHomeScreen;
+
+ public static final int HOME_SCREEN = 0;
+ public static final int ROOT_FOLDER = 1;
+ public static final int OTHER_FOLDER = 2;
+
+ public FolderSpinnerAdapter(boolean includeHomeScreen) {
+ mIncludeHomeScreen = includeHomeScreen;
+ }
+
+ @Override
+ public View getDropDownView(int position, View convertView, ViewGroup parent) {
+ int labelResource;
+ int drawableResource;
+ if (!mIncludeHomeScreen) {
+ position++;
+ }
+ switch (position) {
+ case HOME_SCREEN:
+ labelResource = R.string.add_to_homescreen_menu_option;
+ drawableResource = R.drawable.ic_home_holo_dark;
+ break;
+ case ROOT_FOLDER:
+ labelResource = R.string.add_to_bookmarks_menu_option;
+ drawableResource = R.drawable.ic_bookmarks_holo_dark;
+ break;
+ case OTHER_FOLDER:
+ labelResource = R.string.add_to_other_folder_menu_option;
+ drawableResource = R.drawable.ic_folder_holo_dark;
+ break;
+ default:
+ labelResource = 0;
+ drawableResource = 0;
+ // assert
+ break;
+ }
+ Context context = parent.getContext();
+ LayoutInflater factory = LayoutInflater.from(context);
+ TextView textView = (TextView) factory.inflate(R.layout.add_to_option, null);
+ textView.setText(labelResource);
+ Drawable drawable = context.getResources().getDrawable(drawableResource);
+ textView.setCompoundDrawablesWithIntrinsicBounds(drawable, null,
+ null, null);
+ return textView;
+ }
+
+ @Override
+ public void registerDataSetObserver(DataSetObserver observer) {
+ }
+
+ @Override
+ public void unregisterDataSetObserver(DataSetObserver observer) {
+ }
+
+ @Override
+ public int getCount() {
+ return mIncludeHomeScreen ? 3 : 2;
+ }
+
+ @Override
+ public Object getItem(int position) {
+ return null;
+ }
+
+ @Override
+ public long getItemId(int position) {
+ long id = position;
+ if (!mIncludeHomeScreen) {
+ id++;
+ }
+ return id;
+ }
+
+ @Override
+ public boolean hasStableIds() {
+ return true;
+ }
+
+ @Override
+ public View getView(int position, View convertView, ViewGroup parent) {
+ return getDropDownView(position, convertView, parent);
+ }
+
+ @Override
+ public int getItemViewType(int position) {
+ // Never want to recycle views
+ return Adapter.IGNORE_ITEM_VIEW_TYPE;
+ }
+
+ @Override
+ public int getViewTypeCount() {
+ return 1;
+ }
+
+ @Override
+ public boolean isEmpty() {
+ return false;
+ }
+}
diff --git a/src/com/android/browser/homepages/HomeProvider.java b/src/com/android/browser/homepages/HomeProvider.java
new file mode 100644
index 0000000..98fcfbe
--- /dev/null
+++ b/src/com/android/browser/homepages/HomeProvider.java
@@ -0,0 +1,102 @@
+
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.android.browser.homepages;
+
+import com.android.browser.BrowserSettings;
+
+import android.content.ContentProvider;
+import android.content.ContentValues;
+import android.content.Context;
+import android.content.res.AssetFileDescriptor;
+import android.database.Cursor;
+import android.net.Uri;
+import android.os.ParcelFileDescriptor;
+import android.util.Log;
+import android.webkit.WebResourceResponse;
+
+import java.io.IOException;
+import java.io.InputStream;
+
+public class HomeProvider extends ContentProvider {
+
+ private static final String TAG = "HomeProvider";
+ public static final String AUTHORITY = "com.android.browser.home";
+ public static final String MOST_VISITED = "content://" + AUTHORITY + "/";
+
+ @Override
+ public int delete(Uri uri, String selection, String[] selectionArgs) {
+ return 0;
+ }
+
+ @Override
+ public String getType(Uri uri) {
+ return null;
+ }
+
+ @Override
+ public Uri insert(Uri uri, ContentValues values) {
+ return null;
+ }
+
+ @Override
+ public boolean onCreate() {
+ return false;
+ }
+
+ @Override
+ public Cursor query(Uri uri, String[] projection, String selection,
+ String[] selectionArgs, String sortOrder) {
+ return null;
+ }
+
+ @Override
+ public int update(Uri uri, ContentValues values, String selection,
+ String[] selectionArgs) {
+ return 0;
+ }
+
+ @Override
+ public ParcelFileDescriptor openFile(Uri uri, String mode) {
+ try {
+ ParcelFileDescriptor[] pipes = ParcelFileDescriptor.createPipe();
+ final ParcelFileDescriptor write = pipes[1];
+ AssetFileDescriptor afd = new AssetFileDescriptor(write, 0, -1);
+ new RequestHandler(getContext(), uri, afd.createOutputStream()).start();
+ return pipes[0];
+ } catch (IOException e) {
+ Log.e(TAG, "Failed to handle request: " + uri, e);
+ return null;
+ }
+ }
+
+ public static WebResourceResponse shouldInterceptRequest(Context context,
+ String url) {
+ try {
+ boolean useMostVisited = BrowserSettings.getInstance().useMostVisitedHomepage();
+ if (useMostVisited && url.startsWith("content://")) {
+ Uri uri = Uri.parse(url);
+ if (AUTHORITY.equals(uri.getAuthority())) {
+ InputStream ins = context.getContentResolver()
+ .openInputStream(uri);
+ return new WebResourceResponse("text/html", "utf-8", ins);
+ }
+ }
+ } catch (Exception e) {}
+ return null;
+ }
+
+}
diff --git a/src/com/android/browser/homepages/RequestHandler.java b/src/com/android/browser/homepages/RequestHandler.java
new file mode 100644
index 0000000..a53fb52
--- /dev/null
+++ b/src/com/android/browser/homepages/RequestHandler.java
@@ -0,0 +1,145 @@
+
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.android.browser.homepages;
+
+import com.android.browser.R;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+import android.content.Context;
+import android.content.UriMatcher;
+import android.content.res.Resources;
+import android.database.Cursor;
+import android.net.Uri;
+import android.provider.Browser;
+import android.util.Base64;
+import android.util.Log;
+
+public class RequestHandler extends Thread {
+
+ private static final String TAG = "RequestHandler";
+ private static final int INDEX = 1;
+ private static final int RESOURCE = 2;
+ private static final UriMatcher sUriMatcher = new UriMatcher(UriMatcher.NO_MATCH);
+
+ Uri mUri;
+ Context mContext;
+ OutputStream mOutput;
+
+ static {
+ sUriMatcher.addURI(HomeProvider.AUTHORITY, "/", INDEX);
+ sUriMatcher.addURI(HomeProvider.AUTHORITY, "res/*/*", RESOURCE);
+ }
+
+ public RequestHandler(Context context, Uri uri, OutputStream out) {
+ mUri = uri;
+ mContext = context;
+ mOutput = out;
+ }
+
+ @Override
+ public void run() {
+ super.run();
+ try {
+ doHandleRequest();
+ } catch (Exception e) {
+ Log.e(TAG, "Failed to handle request: " + mUri, e);
+ } finally {
+ cleanup();
+ }
+ }
+
+ void doHandleRequest() throws IOException {
+ int match = sUriMatcher.match(mUri);
+ switch (match) {
+ case INDEX:
+ writeTemplatedIndex();
+ break;
+ case RESOURCE:
+ writeResource(getUriResourcePath());
+ break;
+ }
+ }
+
+ void writeTemplatedIndex() throws IOException {
+ Template t = Template.getCachedTemplate(mContext, R.raw.most_visited);
+ Cursor cursor = mContext.getContentResolver().query(Browser.BOOKMARKS_URI,
+ new String[] { "DISTINCT url", "title", "thumbnail" },
+ "(visits > 0 OR bookmark = 1) AND url NOT LIKE 'content:%' AND thumbnail IS NOT NULL", null, "visits DESC LIMIT 12");
+
+ t.assignLoop("most_visited", new Template.CursorListEntityWrapper(cursor) {
+ @Override
+ public void writeValue(OutputStream stream, String key) throws IOException {
+ Cursor cursor = getCursor();
+ if (key.equals("url")) {
+ stream.write(cursor.getString(0).getBytes());
+ } else if (key.equals("title")) {
+ stream.write(cursor.getString(1).getBytes());
+ } else if (key.equals("thumbnail")) {
+ stream.write("data:image/png;base64,".getBytes());
+ byte[] thumb = cursor.getBlob(2);
+ stream.write(Base64.encode(thumb, Base64.DEFAULT));
+ }
+ }
+ });
+ t.write(mOutput);
+ }
+
+ String getUriResourcePath() {
+ final Pattern pattern = Pattern.compile("/?res/([\\w/]+)");
+ Matcher m = pattern.matcher(mUri.getPath());
+ if (m.matches()) {
+ return m.group(1);
+ } else {
+ return mUri.getPath();
+ }
+ }
+
+ void writeResource(String fileName) throws IOException {
+ Resources res = mContext.getResources();
+ int id = res.getIdentifier(fileName, null, mContext.getPackageName());
+ if (id != 0) {
+ InputStream in = res.openRawResource(id);
+ byte[] buf = new byte[4096];
+ int read;
+ while ((read = in.read(buf)) > 0) {
+ mOutput.write(buf, 0, read);
+ }
+ }
+ }
+
+ void writeString(String str) throws IOException {
+ mOutput.write(str.getBytes());
+ }
+
+ void writeString(String str, int offset, int count) throws IOException {
+ mOutput.write(str.getBytes(), offset, count);
+ }
+
+ void cleanup() {
+ try {
+ mOutput.close();
+ } catch (Exception e) {
+ Log.e(TAG, "Failed to close pipe!", e);
+ }
+ }
+
+}
diff --git a/src/com/android/browser/homepages/Template.java b/src/com/android/browser/homepages/Template.java
new file mode 100644
index 0000000..c1a6b0e
--- /dev/null
+++ b/src/com/android/browser/homepages/Template.java
@@ -0,0 +1,279 @@
+
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.android.browser.homepages;
+
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+import android.content.Context;
+import android.content.res.Resources;
+import android.database.Cursor;
+import android.util.TypedValue;
+
+public class Template {
+
+ private static HashMap<Integer, Template> sCachedTemplates = new HashMap<Integer, Template>();
+
+ public static Template getCachedTemplate(Context context, int id) {
+ synchronized (sCachedTemplates) {
+ Template template = sCachedTemplates.get(id);
+ if (template == null) {
+ template = new Template(context, id);
+ sCachedTemplates.put(id, template);
+ }
+ // Return a copy so that we don't share data
+ return template.copy();
+ }
+ }
+
+ interface Entity {
+ void write(OutputStream stream, EntityData params) throws IOException;
+ }
+
+ interface EntityData {
+ void writeValue(OutputStream stream, String key) throws IOException;
+ ListEntityIterator getListIterator(String key);
+ }
+
+ interface ListEntityIterator extends EntityData {
+ void reset();
+ boolean moveToNext();
+ }
+
+ static class StringEntity implements Entity {
+
+ byte[] mValue;
+
+ public StringEntity(String value) {
+ mValue = value.getBytes();
+ }
+
+ @Override
+ public void write(OutputStream stream, EntityData params) throws IOException {
+ stream.write(mValue);
+ }
+
+ }
+
+ static class SimpleEntity implements Entity {
+
+ String mKey;
+
+ public SimpleEntity(String key) {
+ mKey = key;
+ }
+
+ @Override
+ public void write(OutputStream stream, EntityData params) throws IOException {
+ params.writeValue(stream, mKey);
+ }
+
+ }
+
+ static class ListEntity implements Entity {
+
+ String mKey;
+ Template mSubTemplate;
+
+ public ListEntity(Context context, String key, String subTemplate) {
+ mKey = key;
+ mSubTemplate = new Template(context, subTemplate);
+ }
+
+ @Override
+ public void write(OutputStream stream, EntityData params) throws IOException {
+ ListEntityIterator iter = params.getListIterator(mKey);
+ iter.reset();
+ while (iter.moveToNext()) {
+ mSubTemplate.write(stream, iter);
+ }
+ }
+
+ }
+
+ public abstract static class CursorListEntityWrapper implements ListEntityIterator {
+
+ private Cursor mCursor;
+
+ public CursorListEntityWrapper(Cursor cursor) {
+ mCursor = cursor;
+ }
+
+ @Override
+ public boolean moveToNext() {
+ return mCursor.moveToNext();
+ }
+
+ @Override
+ public void reset() {
+ mCursor.moveToPosition(-1);
+ }
+
+ @Override
+ public ListEntityIterator getListIterator(String key) {
+ return null;
+ }
+
+ public Cursor getCursor() {
+ return mCursor;
+ }
+
+ }
+
+ static class HashMapEntityData implements EntityData {
+
+ HashMap<String, Object> mData;
+
+ public HashMapEntityData(HashMap<String, Object> map) {
+ mData = map;
+ }
+
+ @Override
+ public ListEntityIterator getListIterator(String key) {
+ return (ListEntityIterator) mData.get(key);
+ }
+
+ @Override
+ public void writeValue(OutputStream stream, String key) throws IOException {
+ stream.write((byte[]) mData.get(key));
+ }
+
+ }
+
+ private List<Entity> mTemplate;
+ private HashMap<String, Object> mData = new HashMap<String, Object>();
+ private Template(Context context, int tid) {
+ this(context, readRaw(context, tid));
+ }
+
+ private Template(Context context, String template) {
+ mTemplate = new ArrayList<Entity>();
+ template = replaceConsts(context, template);
+ parseTemplate(context, template);
+ }
+
+ private Template(Template copy) {
+ mTemplate = copy.mTemplate;
+ }
+
+ Template copy() {
+ return new Template(this);
+ }
+
+ void parseTemplate(Context context, String template) {
+ final Pattern pattern = Pattern.compile("<%([=\\{])\\s*(\\w+)\\s*%>");
+ Matcher m = pattern.matcher(template);
+ int start = 0;
+ while (m.find()) {
+ String static_part = template.substring(start, m.start());
+ if (static_part.length() > 0) {
+ mTemplate.add(new StringEntity(static_part));
+ }
+ String type = m.group(1);
+ String name = m.group(2);
+ if (type.equals("=")) {
+ mTemplate.add(new SimpleEntity(name));
+ } else if (type.equals("{")) {
+ Pattern p = Pattern.compile("<%\\}\\s*" + Pattern.quote(name) + "\\s*%>");
+ Matcher end_m = p.matcher(template);
+ if (end_m.find(m.end())) {
+ start = m.end();
+ m.region(end_m.end(), template.length());
+ String subTemplate = template.substring(start, end_m.start());
+ mTemplate.add(new ListEntity(context, name, subTemplate));
+ start = end_m.end();
+ continue;
+ }
+ }
+ start = m.end();
+ }
+ String static_part = template.substring(start, template.length());
+ if (static_part.length() > 0) {
+ mTemplate.add(new StringEntity(static_part));
+ }
+ }
+
+ public void assign(String name, String value) {
+ mData.put(name, value.getBytes());
+ }
+
+ public void assignLoop(String name, ListEntityIterator iter) {
+ mData.put(name, iter);
+ }
+
+ public void write(OutputStream stream) throws IOException {
+ write(stream, new HashMapEntityData(mData));
+ }
+
+ public void write(OutputStream stream, EntityData data) throws IOException {
+ for (Entity ent : mTemplate) {
+ ent.write(stream, data);
+ }
+ }
+
+ private static String replaceConsts(Context context, String template) {
+ final Pattern pattern = Pattern.compile("<%@\\s*(\\w+/\\w+)\\s*%>");
+ final Resources res = context.getResources();
+ final String packageName = context.getPackageName();
+ Matcher m = pattern.matcher(template);
+ StringBuffer sb = new StringBuffer();
+ while (m.find()) {
+ String name = m.group(1);
+ if (name.startsWith("drawable/")) {
+ m.appendReplacement(sb, "res/" + name);
+ } else {
+ int id = res.getIdentifier(name, null, packageName);
+ if (id != 0) {
+ TypedValue value = new TypedValue();
+ res.getValue(id, value, true);
+ String replacement;
+ if (value.type == TypedValue.TYPE_DIMENSION) {
+ float dimen = res.getDimension(id);
+ int dimeni = (int) dimen;
+ if (dimeni == dimen)
+ replacement = Integer.toString(dimeni);
+ else
+ replacement = Float.toString(dimen);
+ } else {
+ replacement = value.coerceToString().toString();
+ }
+ m.appendReplacement(sb, replacement);
+ }
+ }
+ }
+ m.appendTail(sb);
+ return sb.toString();
+ }
+
+ private static String readRaw(Context context, int id) {
+ InputStream ins = context.getResources().openRawResource(id);
+ try {
+ byte[] buf = new byte[ins.available()];
+ ins.read(buf);
+ return new String(buf, "utf-8");
+ } catch (IOException ex) {
+ return "<html><body>Error</body></html>";
+ }
+ }
+
+}
diff --git a/src/com/android/browser/preferences/AdvancedPreferencesFragment.java b/src/com/android/browser/preferences/AdvancedPreferencesFragment.java
new file mode 100644
index 0000000..835778a
--- /dev/null
+++ b/src/com/android/browser/preferences/AdvancedPreferencesFragment.java
@@ -0,0 +1,175 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.preferences;
+
+import com.android.browser.BrowserSettings;
+import com.android.browser.R;
+
+import android.content.res.Resources;
+import android.os.Bundle;
+import android.preference.ListPreference;
+import android.preference.Preference;
+import android.preference.PreferenceFragment;
+import android.preference.PreferenceScreen;
+import android.util.Log;
+import android.webkit.GeolocationPermissions;
+import android.webkit.ValueCallback;
+import android.webkit.WebStorage;
+
+import java.util.Map;
+import java.util.Set;
+
+public class AdvancedPreferencesFragment extends PreferenceFragment
+ implements Preference.OnPreferenceChangeListener {
+
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+
+ // Load the XML preferences file
+ addPreferencesFromResource(R.xml.advanced_preferences);
+
+ PreferenceScreen websiteSettings = (PreferenceScreen) findPreference(
+ BrowserSettings.PREF_WEBSITE_SETTINGS);
+ websiteSettings.setFragment(WebsiteSettingsFragment.class.getName());
+
+ Preference e = findPreference(BrowserSettings.PREF_TEXT_SIZE);
+ e.setOnPreferenceChangeListener(this);
+ e.setSummary(getVisualTextSizeName(
+ getPreferenceScreen().getSharedPreferences()
+ .getString(BrowserSettings.PREF_TEXT_SIZE, null)) );
+
+ e = findPreference(BrowserSettings.PREF_DEFAULT_ZOOM);
+ e.setOnPreferenceChangeListener(this);
+ e.setSummary(getVisualDefaultZoomName(
+ getPreferenceScreen().getSharedPreferences()
+ .getString(BrowserSettings.PREF_DEFAULT_ZOOM, null)) );
+
+ e = findPreference(BrowserSettings.PREF_DEFAULT_TEXT_ENCODING);
+ e.setOnPreferenceChangeListener(this);
+
+ e = findPreference(BrowserSettings.PREF_PLUGIN_STATE);
+ e.setOnPreferenceChangeListener(this);
+ updatePluginSummary((ListPreference) e);
+ }
+
+ void updatePluginSummary(ListPreference e) {
+ e.setSummary(e.getEntry());
+ }
+
+ /*
+ * We need to set the PreferenceScreen state in onResume(), as the number of
+ * origins with active features (WebStorage, Geolocation etc) could have
+ * changed after calling the WebsiteSettingsActivity.
+ */
+ @Override
+ public void onResume() {
+ super.onResume();
+ final PreferenceScreen websiteSettings = (PreferenceScreen) findPreference(
+ BrowserSettings.PREF_WEBSITE_SETTINGS);
+ websiteSettings.setEnabled(false);
+ WebStorage.getInstance().getOrigins(new ValueCallback<Map>() {
+ @Override
+ public void onReceiveValue(Map webStorageOrigins) {
+ if ((webStorageOrigins != null) && !webStorageOrigins.isEmpty()) {
+ websiteSettings.setEnabled(true);
+ }
+ }
+ });
+ GeolocationPermissions.getInstance().getOrigins(new ValueCallback<Set<String> >() {
+ @Override
+ public void onReceiveValue(Set<String> geolocationOrigins) {
+ if ((geolocationOrigins != null) && !geolocationOrigins.isEmpty()) {
+ websiteSettings.setEnabled(true);
+ }
+ }
+ });
+ }
+
+ @Override
+ public boolean onPreferenceChange(Preference pref, Object objValue) {
+ if (getActivity() == null) {
+ // We aren't attached, so don't accept preferences changes from the
+ // invisible UI.
+ Log.w("PageContentPreferencesFragment", "onPreferenceChange called from detached fragment!");
+ return false;
+ }
+
+ if (pref.getKey().equals(BrowserSettings.PREF_TEXT_SIZE)) {
+ pref.setSummary(getVisualTextSizeName((String) objValue));
+ return true;
+ } else if (pref.getKey().equals(BrowserSettings.PREF_DEFAULT_ZOOM)) {
+ pref.setSummary(getVisualDefaultZoomName((String) objValue));
+ return true;
+ } else if (pref.getKey().equals(BrowserSettings.PREF_DEFAULT_TEXT_ENCODING)) {
+ pref.setSummary((String) objValue);
+ return true;
+ } else if (pref.getKey().equals(BrowserSettings.PREF_EXTRAS_RESET_DEFAULTS)) {
+ Boolean value = (Boolean) objValue;
+ if (value.booleanValue() == true) {
+ getActivity().finish();
+ return true;
+ }
+ } else if (pref.getKey().equals(BrowserSettings.PREF_PLUGIN_STATE)) {
+ ListPreference lp = (ListPreference) pref;
+ lp.setValue((String) objValue);
+ updatePluginSummary(lp);
+ return false;
+ }
+ return false;
+ }
+
+ private CharSequence getVisualTextSizeName(String enumName) {
+ Resources res = getActivity().getResources();
+ CharSequence[] visualNames = res.getTextArray(R.array.pref_text_size_choices);
+ CharSequence[] enumNames = res.getTextArray(R.array.pref_text_size_values);
+
+ // Sanity check
+ if (visualNames.length != enumNames.length) {
+ return "";
+ }
+
+ int length = enumNames.length;
+ for (int i = 0; i < length; i++) {
+ if (enumNames[i].equals(enumName)) {
+ return visualNames[i];
+ }
+ }
+
+ return "";
+ }
+
+ private CharSequence getVisualDefaultZoomName(String enumName) {
+ Resources res = getActivity().getResources();
+ CharSequence[] visualNames = res.getTextArray(R.array.pref_default_zoom_choices);
+ CharSequence[] enumNames = res.getTextArray(R.array.pref_default_zoom_values);
+
+ // Sanity check
+ if (visualNames.length != enumNames.length) {
+ return "";
+ }
+
+ int length = enumNames.length;
+ for (int i = 0; i < length; i++) {
+ if (enumNames[i].equals(enumName)) {
+ return visualNames[i];
+ }
+ }
+
+ return "";
+ }
+}
\ No newline at end of file
diff --git a/src/com/android/browser/preferences/DebugPreferencesFragment.java b/src/com/android/browser/preferences/DebugPreferencesFragment.java
new file mode 100644
index 0000000..0a82371
--- /dev/null
+++ b/src/com/android/browser/preferences/DebugPreferencesFragment.java
@@ -0,0 +1,61 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.preferences;
+
+import com.android.browser.BrowserActivity;
+import com.android.browser.BrowserSettings;
+import com.android.browser.Controller;
+import com.android.browser.R;
+
+import android.content.Context;
+import android.content.Intent;
+import android.os.AsyncTask;
+import android.os.Bundle;
+import android.preference.Preference;
+import android.preference.Preference.OnPreferenceChangeListener;
+import android.preference.PreferenceActivity.Header;
+import android.preference.PreferenceFragment;
+import android.preference.PreferenceManager.OnActivityResultListener;
+
+import java.io.IOException;
+import java.io.Serializable;
+
+public class DebugPreferencesFragment extends PreferenceFragment
+ implements OnPreferenceChangeListener {
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+
+ // Load the XML preferences file
+ addPreferencesFromResource(R.xml.debug_preferences);
+
+ if (BrowserSettings.getInstance().showDebugSettings()) {
+ addPreferencesFromResource(R.xml.hidden_debug_preferences);
+ }
+
+ Preference e = findPreference(BrowserSettings.PREF_HARDWARE_ACCEL);
+ e.setOnPreferenceChangeListener(this);
+ }
+
+ @Override
+ public boolean onPreferenceChange(Preference preference, Object newValue) {
+ // Attempt to restart
+ startActivity(new Intent(BrowserActivity.ACTION_RESTART, null,
+ getActivity(), BrowserActivity.class));
+ return true;
+ }
+}
diff --git a/src/com/android/browser/preferences/GeneralPreferencesFragment.java b/src/com/android/browser/preferences/GeneralPreferencesFragment.java
new file mode 100644
index 0000000..b6228dc
--- /dev/null
+++ b/src/com/android/browser/preferences/GeneralPreferencesFragment.java
@@ -0,0 +1,432 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.preferences;
+
+import com.android.browser.BrowserBookmarksPage;
+import com.android.browser.BrowserHomepagePreference;
+import com.android.browser.BrowserPreferencesPage;
+import com.android.browser.BrowserSettings;
+import com.android.browser.R;
+
+import android.accounts.Account;
+import android.accounts.AccountManager;
+import android.app.AlertDialog;
+import android.app.Dialog;
+import android.app.DialogFragment;
+import android.app.Fragment;
+import android.content.ContentProviderOperation;
+import android.content.ContentResolver;
+import android.content.ContentValues;
+import android.content.Context;
+import android.content.DialogInterface;
+import android.content.OperationApplicationException;
+import android.content.SharedPreferences;
+import android.content.SharedPreferences.OnSharedPreferenceChangeListener;
+import android.database.Cursor;
+import android.os.AsyncTask;
+import android.os.Bundle;
+import android.os.RemoteException;
+import android.preference.Preference;
+import android.preference.Preference.OnPreferenceClickListener;
+import android.preference.PreferenceFragment;
+import android.preference.PreferenceManager;
+import android.preference.PreferenceScreen;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Bookmarks;
+import android.provider.BrowserContract.ChromeSyncColumns;
+import android.util.Log;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.View.OnClickListener;
+import android.widget.Button;
+import android.widget.LinearLayout;
+
+import java.util.ArrayList;
+
+public class GeneralPreferencesFragment extends PreferenceFragment
+ implements OnPreferenceClickListener, Preference.OnPreferenceChangeListener {
+ static final String TAG = "PersonalPreferencesFragment";
+
+ static final String PREF_CHROME_SYNC = "sync_with_chrome";
+
+ Preference mChromeSync;
+ boolean mEnabled;
+ SharedPreferences mSharedPrefs;
+
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+
+ // Load the XML preferences file
+ addPreferencesFromResource(R.xml.general_preferences);
+
+ Preference e = findPreference(BrowserSettings.PREF_HOMEPAGE);
+ e.setOnPreferenceChangeListener(this);
+ e.setSummary(getPreferenceScreen().getSharedPreferences()
+ .getString(BrowserSettings.PREF_HOMEPAGE, null));
+ ((BrowserHomepagePreference) e).setCurrentPage(
+ getActivity().getIntent().getStringExtra(BrowserPreferencesPage.CURRENT_PAGE));
+ }
+
+ @Override
+ public boolean onPreferenceChange(Preference pref, Object objValue) {
+ if (getActivity() == null) {
+ // We aren't attached, so don't accept preferences changes from the
+ // invisible UI.
+ Log.w("PageContentPreferencesFragment", "onPreferenceChange called from detached fragment!");
+ return false;
+ }
+
+ if (pref.getKey().equals(BrowserSettings.PREF_HOMEPAGE)) {
+ pref.setSummary((String) objValue);
+ return true;
+ }
+
+ return false;
+ }
+
+ @Override
+ public void onResume() {
+ super.onResume();
+
+ // Setup the proper state for the sync with chrome item
+ mChromeSync = findPreference(PREF_CHROME_SYNC);
+ refreshUi();
+ mSharedPrefs = PreferenceManager.getDefaultSharedPreferences(getActivity());
+ mSharedPrefs.registerOnSharedPreferenceChangeListener(mListener);
+ }
+
+ @Override
+ public void onPause() {
+ super.onPause();
+
+ mSharedPrefs.unregisterOnSharedPreferenceChangeListener(mListener);
+ }
+
+ OnSharedPreferenceChangeListener mListener
+ = new OnSharedPreferenceChangeListener() {
+ @Override
+ public void onSharedPreferenceChanged(
+ SharedPreferences sharedPreferences, String key) {
+ if (BrowserBookmarksPage.PREF_ACCOUNT_NAME.equals(key)
+ || BrowserBookmarksPage.PREF_ACCOUNT_TYPE.equals(key)) {
+ refreshUi();
+ }
+ }
+
+ };
+
+ private class GetAccountsTask extends AsyncTask<Void, Void, String> {
+ private Context mContext;
+
+ GetAccountsTask(Context ctx) {
+ mContext = ctx;
+ }
+
+ @Override
+ protected String doInBackground(Void... unused) {
+ AccountManager am = (AccountManager) mContext.getSystemService(Context.ACCOUNT_SERVICE);
+ Account[] accounts = am.getAccountsByType("com.google");
+ if (accounts == null || accounts.length == 0) {
+ // No Google accounts setup, don't offer Chrome sync
+ if (mChromeSync != null) {
+ getPreferenceScreen().removePreference(mChromeSync);
+ }
+ } else {
+ // Google accounts are present.
+ SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(mContext);
+ Bundle args = mChromeSync.getExtras();
+ args.putParcelableArray("accounts", accounts);
+ mEnabled = BrowserContract.Settings.isSyncEnabled(mContext);
+ mChromeSync.setOnPreferenceClickListener(GeneralPreferencesFragment.this);
+
+ if (!mEnabled) {
+ // Setup a link to the enable wizard
+ return mContext.getResources().getString(
+ R.string.pref_personal_sync_with_chrome_summary);
+ } else {
+ // Chrome sync is enabled, setup a link to account switcher
+ String accountName = prefs.getString(
+ BrowserBookmarksPage.PREF_ACCOUNT_NAME, null);
+ args.putString("curAccount", accountName);
+ return accountName;
+ }
+ }
+
+ return null;
+ }
+
+ @Override
+ protected void onPostExecute(String summary) {
+ if (summary != null) {
+ mChromeSync.setSummary(summary);
+ }
+ }
+ }
+
+ void refreshUi() {
+ new GetAccountsTask(getActivity()).execute();
+
+ PreferenceScreen autoFillSettings =
+ (PreferenceScreen)findPreference(BrowserSettings.PREF_AUTOFILL_PROFILE);
+ autoFillSettings.setDependency(BrowserSettings.PREF_AUTOFILL_ENABLED);
+ }
+
+ @Override
+ public boolean onPreferenceClick(Preference preference) {
+ Fragment frag;
+ if (mEnabled) {
+ frag = new AccountChooserDialog();
+ } else {
+ frag = new ImportWizardDialog();
+ }
+ frag.setArguments(preference.getExtras());
+ getFragmentManager().beginTransaction()
+ .add(frag, null)
+ .commit();
+ return true;
+ }
+
+ public static class AccountChooserDialog extends DialogFragment
+ implements DialogInterface.OnClickListener {
+
+ AlertDialog mDialog;
+
+ @Override
+ public Dialog onCreateDialog(Bundle savedInstanceState) {
+ Bundle args = getArguments();
+ Account[] accounts = (Account[]) args.getParcelableArray("accounts");
+ String curAccount = args.getString("curAccount");
+ int length = accounts.length;
+ int curAccountOffset = 0;
+ CharSequence[] accountNames = new CharSequence[length];
+ for (int i = 0; i < length; i++) {
+ String name = accounts[i].name;
+ if (name.equals(curAccount)) {
+ curAccountOffset = i;
+ }
+ accountNames[i] = name;
+ }
+
+ mDialog = new AlertDialog.Builder(getActivity())
+ .setIcon(android.R.drawable.ic_dialog_alert)
+ .setTitle(R.string.account_chooser_dialog_title)
+ .setSingleChoiceItems(accountNames, curAccountOffset, this)
+ .create();
+ return mDialog;
+ }
+
+ @Override
+ public void onClick(DialogInterface dialog, int which) {
+ String accountName = mDialog.getListView().getAdapter().getItem(which).toString();
+ SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(getActivity());
+ prefs.edit().putString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, accountName).apply();
+ dismiss();
+ }
+ }
+
+ public static class ImportWizardDialog extends DialogFragment implements OnClickListener {
+ View mRemoveButton;
+ View mCancelButton;
+ String mDefaultAccount;
+
+ @Override
+ public Dialog onCreateDialog(Bundle savedInstanceState) {
+ Context context = getActivity();
+ Dialog dialog = new Dialog(context);
+ dialog.setTitle(R.string.import_bookmarks_dialog_title);
+ dialog.setContentView(R.layout.import_bookmarks_dialog);
+ mRemoveButton = dialog.findViewById(R.id.remove);
+ mRemoveButton.setOnClickListener(this);
+ mCancelButton = dialog.findViewById(R.id.cancel);
+ mCancelButton.setOnClickListener(this);
+
+ LayoutInflater inflater = dialog.getLayoutInflater();
+ LinearLayout accountList = (LinearLayout) dialog.findViewById(R.id.accountList);
+ Account[] accounts = (Account[]) getArguments().getParcelableArray("accounts");
+ mDefaultAccount = accounts[0].name;
+ int length = accounts.length;
+ for (int i = 0; i < length; i++) {
+ Button button = (Button) inflater.inflate(R.layout.import_bookmarks_dialog_button,
+ null);
+ button.setText(context.getString(R.string.import_bookmarks_dialog_import,
+ accounts[i].name));
+ button.setTag(accounts[i].name);
+ button.setOnClickListener(this);
+ accountList.addView(button);
+ }
+
+ return dialog;
+ }
+
+ @Override
+ public void onClick(View view) {
+ if (view == mCancelButton) {
+ dismiss();
+ return;
+ }
+
+ ContentResolver resolver = getActivity().getContentResolver();
+ SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(getActivity());
+ String accountName;
+ if (view == mRemoveButton) {
+ // The user chose to remove their old bookmarks, delete them now
+ resolver.delete(Bookmarks.CONTENT_URI,
+ Bookmarks.PARENT + "=1 AND " + Bookmarks.ACCOUNT_NAME + " IS NULL", null);
+ accountName = mDefaultAccount;
+ } else {
+ // The user chose to migrate their old bookmarks to the account they're syncing
+ accountName = view.getTag().toString();
+ migrateBookmarks(resolver, accountName);
+ }
+
+ // Record the fact that we turned on sync
+ BrowserContract.Settings.setSyncEnabled(getActivity(), true);
+ prefs.edit()
+ .putString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE, "com.google")
+ .putString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, accountName)
+ .apply();
+
+ // Enable bookmark sync on all accounts
+ Account[] accounts = (Account[]) getArguments().getParcelableArray("accounts");
+ for (Account account : accounts) {
+ if (ContentResolver.getIsSyncable(account, BrowserContract.AUTHORITY) == 0) {
+ // Account wasn't syncable, enable it
+ ContentResolver.setIsSyncable(account, BrowserContract.AUTHORITY, 1);
+ ContentResolver.setSyncAutomatically(account, BrowserContract.AUTHORITY, true);
+ }
+ }
+
+ dismiss();
+ }
+
+ /**
+ * Migrates bookmarks to the given account
+ */
+ void migrateBookmarks(ContentResolver resolver, String accountName) {
+ Cursor cursor = null;
+ try {
+ // Re-parent the bookmarks in the default root folder
+ cursor = resolver.query(Bookmarks.CONTENT_URI, new String[] { Bookmarks._ID },
+ Bookmarks.ACCOUNT_NAME + " =? AND " +
+ ChromeSyncColumns.SERVER_UNIQUE + " =?",
+ new String[] { accountName,
+ ChromeSyncColumns.FOLDER_NAME_BOOKMARKS_BAR },
+ null);
+ ContentValues values = new ContentValues();
+ if (cursor == null || !cursor.moveToFirst()) {
+ // The root folders don't exist for the account, create them now
+ ArrayList<ContentProviderOperation> ops =
+ new ArrayList<ContentProviderOperation>();
+
+ // Chrome sync root folder
+ values.clear();
+ values.put(ChromeSyncColumns.SERVER_UNIQUE, ChromeSyncColumns.FOLDER_NAME_ROOT);
+ values.put(Bookmarks.TITLE, "Google Chrome");
+ values.put(Bookmarks.POSITION, 0);
+ values.put(Bookmarks.IS_FOLDER, true);
+ values.put(Bookmarks.DIRTY, true);
+ ops.add(ContentProviderOperation.newInsert(
+ Bookmarks.CONTENT_URI.buildUpon().appendQueryParameter(
+ BrowserContract.CALLER_IS_SYNCADAPTER, "true").build())
+ .withValues(values)
+ .build());
+
+ // Bookmarks folder
+ values.clear();
+ values.put(ChromeSyncColumns.SERVER_UNIQUE,
+ ChromeSyncColumns.FOLDER_NAME_BOOKMARKS);
+ values.put(Bookmarks.TITLE, "Bookmarks");
+ values.put(Bookmarks.POSITION, 0);
+ values.put(Bookmarks.IS_FOLDER, true);
+ values.put(Bookmarks.DIRTY, true);
+ ops.add(ContentProviderOperation.newInsert(Bookmarks.CONTENT_URI)
+ .withValues(values)
+ .withValueBackReference(Bookmarks.PARENT, 0)
+ .build());
+
+ // Bookmarks Bar folder
+ values.clear();
+ values.put(ChromeSyncColumns.SERVER_UNIQUE,
+ ChromeSyncColumns.FOLDER_NAME_BOOKMARKS_BAR);
+ values.put(Bookmarks.TITLE, "Bookmarks Bar");
+ values.put(Bookmarks.POSITION, 0);
+ values.put(Bookmarks.IS_FOLDER, true);
+ values.put(Bookmarks.DIRTY, true);
+ ops.add(ContentProviderOperation.newInsert(Bookmarks.CONTENT_URI)
+ .withValues(values)
+ .withValueBackReference(Bookmarks.PARENT, 1)
+ .build());
+
+ // Other Bookmarks folder
+ values.clear();
+ values.put(ChromeSyncColumns.SERVER_UNIQUE,
+ ChromeSyncColumns.FOLDER_NAME_OTHER_BOOKMARKS);
+ values.put(Bookmarks.TITLE, "Other Bookmarks");
+ values.put(Bookmarks.POSITION, 1000);
+ values.put(Bookmarks.IS_FOLDER, true);
+ values.put(Bookmarks.DIRTY, true);
+ ops.add(ContentProviderOperation.newInsert(Bookmarks.CONTENT_URI)
+ .withValues(values)
+ .withValueBackReference(Bookmarks.PARENT, 1)
+ .build());
+
+ // Re-parent the existing bookmarks to the newly create bookmarks bar folder
+ ops.add(ContentProviderOperation.newUpdate(Bookmarks.CONTENT_URI)
+ .withValueBackReference(Bookmarks.PARENT, 2)
+ .withSelection(Bookmarks.PARENT + "=?",
+ new String[] { Integer.toString(1) })
+ .build());
+
+ // Mark all non-root folder items as belonging to the new account
+ values.clear();
+ values.put(Bookmarks.ACCOUNT_TYPE, "com.google");
+ values.put(Bookmarks.ACCOUNT_NAME, accountName);
+ ops.add(ContentProviderOperation.newUpdate(Bookmarks.CONTENT_URI)
+ .withValues(values)
+ .withSelection(Bookmarks.ACCOUNT_NAME + " IS NULL AND " +
+ Bookmarks._ID + "<>1", null)
+ .build());
+
+ try {
+ resolver.applyBatch(BrowserContract.AUTHORITY, ops);
+ } catch (RemoteException e) {
+ Log.e(TAG, "failed to create root folder for account " + accountName, e);
+ return;
+ } catch (OperationApplicationException e) {
+ Log.e(TAG, "failed to create root folder for account " + accountName, e);
+ return;
+ }
+ } else {
+ values.put(Bookmarks.PARENT, cursor.getLong(0));
+ resolver.update(Bookmarks.CONTENT_URI, values, Bookmarks.PARENT + "=?",
+ new String[] { Integer.toString(1) });
+
+ // Mark all bookmarks at all levels as part of the new account
+ values.clear();
+ values.put(Bookmarks.ACCOUNT_TYPE, "com.google");
+ values.put(Bookmarks.ACCOUNT_NAME, accountName);
+ resolver.update(Bookmarks.CONTENT_URI, values,
+ Bookmarks.ACCOUNT_NAME + " IS NULL AND " + Bookmarks._ID + "<>1",
+ null);
+ }
+ } finally {
+ if (cursor != null) cursor.close();
+ }
+ }
+ }
+}
diff --git a/src/com/android/browser/preferences/LabPreferencesFragment.java b/src/com/android/browser/preferences/LabPreferencesFragment.java
new file mode 100644
index 0000000..8a8546f
--- /dev/null
+++ b/src/com/android/browser/preferences/LabPreferencesFragment.java
@@ -0,0 +1,58 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.preferences;
+
+import com.android.browser.BrowserActivity;
+import com.android.browser.BrowserSettings;
+import com.android.browser.Controller;
+import com.android.browser.R;
+
+import android.content.Context;
+import android.content.Intent;
+import android.os.AsyncTask;
+import android.os.Bundle;
+import android.preference.Preference;
+import android.preference.Preference.OnPreferenceChangeListener;
+import android.preference.PreferenceActivity.Header;
+import android.preference.PreferenceFragment;
+import android.preference.PreferenceManager.OnActivityResultListener;
+
+import java.io.IOException;
+import java.io.Serializable;
+
+public class LabPreferencesFragment extends PreferenceFragment
+ implements OnPreferenceChangeListener {
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+
+ // Load the XML preferences file
+ addPreferencesFromResource(R.xml.lab_preferences);
+
+ Preference e = findPreference(BrowserSettings.PREF_QUICK_CONTROLS);
+ e.setOnPreferenceChangeListener(this);
+ }
+
+ @Override
+ public boolean onPreferenceChange(Preference preference, Object newValue) {
+ // Attempt to restart
+ startActivity(new Intent(BrowserActivity.ACTION_RESTART, null,
+ getActivity(), BrowserActivity.class));
+ return true;
+ }
+
+}
diff --git a/src/com/android/browser/preferences/PrivacySecurityPreferencesFragment.java b/src/com/android/browser/preferences/PrivacySecurityPreferencesFragment.java
new file mode 100644
index 0000000..409ddb7
--- /dev/null
+++ b/src/com/android/browser/preferences/PrivacySecurityPreferencesFragment.java
@@ -0,0 +1,120 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.preferences;
+
+import com.android.browser.BrowserSettings;
+import com.android.browser.GoogleAccountLogin;
+import com.android.browser.R;
+
+import android.accounts.Account;
+import android.app.Activity;
+import android.content.Intent;
+import android.os.Bundle;
+import android.preference.ListPreference;
+import android.preference.Preference;
+import android.preference.PreferenceFragment;
+
+public class PrivacySecurityPreferencesFragment extends PreferenceFragment
+ implements Preference.OnPreferenceChangeListener {
+
+ private BrowserSettings mSettings;
+
+ @Override
+ public void onCreate(Bundle savedInstanceState) {
+ super.onCreate(savedInstanceState);
+
+ mSettings = BrowserSettings.getInstance();
+
+ // Load the preferences from an XML resource
+ addPreferencesFromResource(R.xml.privacy_security_preferences);
+
+ Preference e = findPreference(BrowserSettings.PREF_CLEAR_HISTORY);
+ e.setOnPreferenceChangeListener(this);
+ }
+
+ @Override
+ public void onResume() {
+ super.onResume();
+ setupAutoLoginPreference();
+ }
+
+ void setupAutoLoginPreference() {
+ ListPreference autologinPref = (ListPreference) findPreference(
+ BrowserSettings.PREF_AUTOLOGIN_ACCOUNT);
+ autologinPref.setOnPreferenceChangeListener(this);
+ updateAutoLoginSummary(autologinPref);
+ Account[] accounts = GoogleAccountLogin.getAccounts(getActivity());
+ // +1 for disable
+ CharSequence[] names = new CharSequence[accounts.length + 1];
+ CharSequence[] values = new CharSequence[names.length];
+ int i = 0;
+ int defaultAccount = 0;
+ for (Account a : accounts) {
+ values[i] = names[i] = a.name;
+ i++;
+ }
+ names[i] = getResources().getString(R.string.pref_autologin_disable);
+ values[i] = "";
+ autologinPref.setEntries(names);
+ autologinPref.setEntryValues(values);
+ BrowserSettings bs = BrowserSettings.getInstance();
+ if (bs.isAutoLoginEnabled()) {
+ autologinPref.setValue(bs.getAutoLoginAccount(getActivity()));
+ } else {
+ autologinPref.setValue("");
+ }
+ }
+
+ private void updateAutoLoginSummary(Preference pref) {
+ if (!mSettings.isAutoLoginEnabled()) {
+ pref.setSummary(R.string.pref_autologin_disable);
+ } else {
+ String account = mSettings.getAutoLoginAccount(getActivity());
+ if (account == null) {
+ pref.setSummary(R.string.pref_autologin_no_account);
+ } else {
+ pref.setSummary(getString(R.string.pref_autologin_summary, account));
+ }
+ }
+ }
+
+ @Override
+ public boolean onPreferenceChange(Preference pref, Object objValue) {
+ if (pref.getKey().equals(BrowserSettings.PREF_CLEAR_HISTORY)
+ && ((Boolean) objValue).booleanValue() == true) {
+ // Need to tell the browser to remove the parent/child relationship
+ // between tabs
+ getActivity().setResult(Activity.RESULT_OK, (new Intent()).putExtra(Intent.EXTRA_TEXT,
+ pref.getKey()));
+ return true;
+ } else if (pref.getKey().equals(BrowserSettings.PREF_AUTOLOGIN_ACCOUNT)) {
+ String account = (String) objValue;
+ if (account.length() == 0) {
+ // Disable
+ mSettings.setAutoLoginEnabled(getActivity(), false);
+ } else {
+ mSettings.setAutoLoginEnabled(getActivity(), true);
+ }
+ mSettings.setAutoLoginAccount(getActivity(), account);
+ updateAutoLoginSummary(pref);
+ return true;
+ }
+
+ return false;
+ }
+
+}
diff --git a/src/com/android/browser/WebsiteSettingsActivity.java b/src/com/android/browser/preferences/WebsiteSettingsFragment.java
similarity index 71%
rename from src/com/android/browser/WebsiteSettingsActivity.java
rename to src/com/android/browser/preferences/WebsiteSettingsFragment.java
index 1e27092..6339d72 100644
--- a/src/com/android/browser/WebsiteSettingsActivity.java
+++ b/src/com/android/browser/preferences/WebsiteSettingsFragment.java
@@ -14,55 +14,62 @@
* limitations under the License.
*/
-package com.android.browser;
+package com.android.browser.preferences;
+
+import com.android.browser.R;
+import com.android.browser.WebStorageSizeManager;
import android.app.AlertDialog;
-import android.app.ListActivity;
+import android.app.FragmentTransaction;
+import android.app.ListFragment;
import android.content.Context;
import android.content.DialogInterface;
+import android.content.res.Resources;
import android.database.Cursor;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.net.Uri;
+import android.os.AsyncTask;
import android.os.Bundle;
-import android.provider.Browser;
+import android.preference.PreferenceActivity;
+import android.preference.PreferenceFragment;
+import android.provider.BrowserContract.Bookmarks;
import android.util.Log;
-import android.view.KeyEvent;
import android.view.LayoutInflater;
-import android.view.Menu;
-import android.view.MenuInflater;
import android.view.MenuItem;
import android.view.View;
+import android.view.View.OnClickListener;
import android.view.ViewGroup;
import android.webkit.GeolocationPermissions;
import android.webkit.ValueCallback;
-import android.webkit.WebIconDatabase;
import android.webkit.WebStorage;
-import android.widget.ArrayAdapter;
import android.widget.AdapterView;
import android.widget.AdapterView.OnItemClickListener;
+import android.widget.ArrayAdapter;
import android.widget.ImageView;
import android.widget.TextView;
+import java.io.Serializable;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Iterator;
import java.util.Map;
import java.util.Set;
-import java.util.Vector;
/**
* Manage the settings for an origin.
* We use it to keep track of the 'HTML5' settings, i.e. database (webstorage)
* and Geolocation.
*/
-public class WebsiteSettingsActivity extends ListActivity {
+public class WebsiteSettingsFragment extends ListFragment implements OnClickListener {
+ private static final String EXTRA_SITE = "site";
private String LOGTAG = "WebsiteSettingsActivity";
private static String sMBStored = null;
private SiteAdapter mAdapter = null;
+ private Site mSite = null;
- static class Site {
+ static class Site implements Serializable {
private String mOrigin;
private String mTitle;
private Bitmap mIcon;
@@ -168,6 +175,10 @@
private Site mCurrentSite;
public SiteAdapter(Context context, int rsc) {
+ this(context, rsc, null);
+ }
+
+ public SiteAdapter(Context context, int rsc, Site site) {
super(context, rsc);
mResource = rsc;
mInflater = (LayoutInflater)context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
@@ -180,10 +191,13 @@
mUsageHighIcon = BitmapFactory.decodeResource(getResources(),
R.drawable.ic_list_data_large);
mLocationAllowedIcon = BitmapFactory.decodeResource(getResources(),
- R.drawable.ic_list_gps_on);
+ R.drawable.ic_gps_on_holo_dark);
mLocationDisallowedIcon = BitmapFactory.decodeResource(getResources(),
- R.drawable.ic_list_gps_denied);
- askForOrigins();
+ R.drawable.ic_gps_denied_holo_dark);
+ mCurrentSite = site;
+ if (mCurrentSite == null) {
+ askForOrigins();
+ }
}
/**
@@ -242,67 +256,94 @@
public void populateIcons(Map<String, Site> sites) {
// Create a map from host to origin. This is used to add metadata
- // (title, icon) for this origin from the bookmarks DB.
- HashMap<String, Set<Site>> hosts = new HashMap<String, Set<Site>>();
- Set<Map.Entry<String, Site>> elements = sites.entrySet();
- Iterator<Map.Entry<String, Site>> originIter = elements.iterator();
- while (originIter.hasNext()) {
- Map.Entry<String, Site> entry = originIter.next();
- Site site = entry.getValue();
- String host = Uri.parse(entry.getKey()).getHost();
- Set<Site> hostSites = null;
- if (hosts.containsKey(host)) {
- hostSites = (Set<Site>)hosts.get(host);
- } else {
- hostSites = new HashSet<Site>();
- hosts.put(host, hostSites);
- }
- hostSites.add(site);
+ // (title, icon) for this origin from the bookmarks DB. We must do
+ // the DB access on a background thread.
+ new UpdateFromBookmarksDbTask(this.getContext(), sites).execute();
+ }
+
+ private class UpdateFromBookmarksDbTask extends AsyncTask<Void, Void, Void> {
+
+ private Context mContext;
+ private boolean mDataSetChanged;
+ private Map<String, Site> mSites;
+
+ public UpdateFromBookmarksDbTask(Context ctx, Map<String, Site> sites) {
+ mContext = ctx;
+ mSites = sites;
}
- // Check the bookmark DB. If we have data for a host used by any of
- // our origins, use it to set their title and favicon
- Cursor c = getContext().getContentResolver().query(Browser.BOOKMARKS_URI,
- new String[] { Browser.BookmarkColumns.URL, Browser.BookmarkColumns.TITLE,
- Browser.BookmarkColumns.FAVICON }, "bookmark = 1", null, null);
-
- if (c != null) {
- if (c.moveToFirst()) {
- int urlIndex = c.getColumnIndex(Browser.BookmarkColumns.URL);
- int titleIndex = c.getColumnIndex(Browser.BookmarkColumns.TITLE);
- int faviconIndex = c.getColumnIndex(Browser.BookmarkColumns.FAVICON);
- do {
- String url = c.getString(urlIndex);
- String host = Uri.parse(url).getHost();
- if (hosts.containsKey(host)) {
- String title = c.getString(titleIndex);
- Bitmap bmp = null;
- byte[] data = c.getBlob(faviconIndex);
- if (data != null) {
- bmp = BitmapFactory.decodeByteArray(data, 0, data.length);
- }
- Set matchingSites = (Set) hosts.get(host);
- Iterator<Site> sitesIter = matchingSites.iterator();
- while (sitesIter.hasNext()) {
- Site site = sitesIter.next();
- // We should only set the title if the bookmark is for the root
- // (i.e. www.google.com), as website settings act on the origin
- // as a whole rather than a single page under that origin. If the
- // user has bookmarked a page under the root but *not* the root,
- // then we risk displaying the title of that page which may or
- // may not have any relevance to the origin.
- if (url.equals(site.getOrigin()) ||
- (new String(site.getOrigin()+"/")).equals(url)) {
- site.setTitle(title);
- }
- if (bmp != null) {
- site.setIcon(bmp);
- }
- }
- }
- } while (c.moveToNext());
+ protected Void doInBackground(Void... unused) {
+ HashMap<String, Set<Site>> hosts = new HashMap<String, Set<Site>>();
+ Set<Map.Entry<String, Site>> elements = mSites.entrySet();
+ Iterator<Map.Entry<String, Site>> originIter = elements.iterator();
+ while (originIter.hasNext()) {
+ Map.Entry<String, Site> entry = originIter.next();
+ Site site = entry.getValue();
+ String host = Uri.parse(entry.getKey()).getHost();
+ Set<Site> hostSites = null;
+ if (hosts.containsKey(host)) {
+ hostSites = (Set<Site>)hosts.get(host);
+ } else {
+ hostSites = new HashSet<Site>();
+ hosts.put(host, hostSites);
+ }
+ hostSites.add(site);
}
- c.close();
+
+ // Check the bookmark DB. If we have data for a host used by any of
+ // our origins, use it to set their title and favicon
+ Cursor c = mContext.getContentResolver().query(Bookmarks.CONTENT_URI,
+ new String[] { Bookmarks.URL, Bookmarks.TITLE, Bookmarks.FAVICON },
+ Bookmarks.IS_FOLDER + " == 0", null, null);
+
+ if (c != null) {
+ if (c.moveToFirst()) {
+ int urlIndex = c.getColumnIndex(Bookmarks.URL);
+ int titleIndex = c.getColumnIndex(Bookmarks.TITLE);
+ int faviconIndex = c.getColumnIndex(Bookmarks.FAVICON);
+ do {
+ String url = c.getString(urlIndex);
+ String host = Uri.parse(url).getHost();
+ if (hosts.containsKey(host)) {
+ String title = c.getString(titleIndex);
+ Bitmap bmp = null;
+ byte[] data = c.getBlob(faviconIndex);
+ if (data != null) {
+ bmp = BitmapFactory.decodeByteArray(data, 0, data.length);
+ }
+ Set matchingSites = (Set) hosts.get(host);
+ Iterator<Site> sitesIter = matchingSites.iterator();
+ while (sitesIter.hasNext()) {
+ Site site = sitesIter.next();
+ // We should only set the title if the bookmark is for the root
+ // (i.e. www.google.com), as website settings act on the origin
+ // as a whole rather than a single page under that origin. If the
+ // user has bookmarked a page under the root but *not* the root,
+ // then we risk displaying the title of that page which may or
+ // may not have any relevance to the origin.
+ if (url.equals(site.getOrigin()) ||
+ (new String(site.getOrigin()+"/")).equals(url)) {
+ mDataSetChanged = true;
+ site.setTitle(title);
+ }
+
+ if (bmp != null) {
+ mDataSetChanged = true;
+ site.setIcon(bmp);
+ }
+ }
+ }
+ } while (c.moveToNext());
+ }
+ c.close();
+ }
+ return null;
+ }
+
+ protected void onPostExecute(Void unused) {
+ if (mDataSetChanged) {
+ notifyDataSetChanged();
+ }
}
}
@@ -381,6 +422,7 @@
}
}
+ @Override
public View getView(int position, View convertView, ViewGroup parent) {
View view;
final TextView title;
@@ -406,7 +448,6 @@
locationIcon.setVisibility(View.GONE);
if (mCurrentSite == null) {
- setTitle(getString(R.string.pref_extras_website_settings));
Site site = getItem(position);
title.setText(site.getPrettyTitle());
@@ -466,7 +507,6 @@
locationIcon.setVisibility(View.GONE);
usageIcon.setVisibility(View.GONE);
featureIcon.setVisibility(View.VISIBLE);
- setTitle(mCurrentSite.getPrettyTitle());
String origin = mCurrentSite.getOrigin();
switch (mCurrentSite.getFeatureByIndex(position)) {
case Site.FEATURE_WEB_STORAGE:
@@ -523,7 +563,7 @@
// origins list.
mCurrentSite.removeFeature(Site.FEATURE_WEB_STORAGE);
if (mCurrentSite.getFeatureCount() == 0) {
- mCurrentSite = null;
+ finish();
}
askForOrigins();
notifyDataSetChanged();
@@ -542,7 +582,7 @@
GeolocationPermissions.getInstance().clear(mCurrentSite.getOrigin());
mCurrentSite.removeFeature(Site.FEATURE_GEOLOCATION);
if (mCurrentSite.getFeatureCount() == 0) {
- mCurrentSite = null;
+ finish();
}
askForOrigins();
notifyDataSetChanged();
@@ -553,8 +593,14 @@
break;
}
} else {
- mCurrentSite = (Site) view.getTag();
- notifyDataSetChanged();
+ Site site = (Site) view.getTag();
+ PreferenceActivity activity = (PreferenceActivity) getActivity();
+ if (activity != null) {
+ Bundle args = new Bundle();
+ args.putSerializable(EXTRA_SITE, site);
+ activity.startPreferencePanel(WebsiteSettingsFragment.class.getName(), args, 0,
+ site.getPrettyTitle(), null, 0);
+ }
}
}
@@ -563,67 +609,64 @@
}
}
- /**
- * Intercepts the back key to immediately notify
- * NativeDialog that we are done.
- */
- public boolean dispatchKeyEvent(KeyEvent event) {
- if ((event.getKeyCode() == KeyEvent.KEYCODE_BACK)
- && (event.getAction() == KeyEvent.ACTION_DOWN)) {
- if ((mAdapter != null) && (mAdapter.backKeyPressed())){
- return true; // event consumed
- }
+ @Override
+ public View onCreateView(LayoutInflater inflater, ViewGroup container,
+ Bundle savedInstanceState) {
+ View view = inflater.inflate(R.layout.website_settings, container, false);
+ Bundle args = getArguments();
+ if (args != null) {
+ mSite = (Site) args.getSerializable(EXTRA_SITE);
}
- return super.dispatchKeyEvent(event);
+ if (mSite == null) {
+ View clear = view.findViewById(R.id.clear_all_button);
+ clear.setVisibility(View.VISIBLE);
+ clear.setOnClickListener(this);
+ }
+ return view;
}
@Override
- protected void onCreate(Bundle icicle) {
- super.onCreate(icicle);
+ public void onActivityCreated(Bundle savedInstanceState) {
+ super.onActivityCreated(savedInstanceState);
if (sMBStored == null) {
sMBStored = getString(R.string.webstorage_origin_summary_mb_stored);
}
- mAdapter = new SiteAdapter(this, R.layout.website_settings_row);
- setListAdapter(mAdapter);
+ mAdapter = new SiteAdapter(getActivity(), R.layout.website_settings_row);
+ if (mSite != null) {
+ mAdapter.mCurrentSite = mSite;
+ }
+ getListView().setAdapter(mAdapter);
getListView().setOnItemClickListener(mAdapter);
}
- @Override
- public boolean onCreateOptionsMenu(Menu menu) {
- MenuInflater inflater = getMenuInflater();
- inflater.inflate(R.menu.websitesettings, menu);
- return true;
- }
-
- @Override
- public boolean onPrepareOptionsMenu(Menu menu) {
- // If we are not on the sites list (rather on the page for a specific site) or
- // we aren't listing any sites hide the clear all button (and hence the menu).
- return mAdapter.currentSite() == null && mAdapter.getCount() > 0;
- }
-
- @Override
- public boolean onOptionsItemSelected(MenuItem item) {
- switch (item.getItemId()) {
- case R.id.website_settings_menu_clear_all:
- // Show the prompt to clear all origins of their data and geolocation permissions.
- new AlertDialog.Builder(this)
- .setTitle(R.string.website_settings_clear_all_dialog_title)
- .setMessage(R.string.website_settings_clear_all_dialog_message)
- .setPositiveButton(R.string.website_settings_clear_all_dialog_ok_button,
- new AlertDialog.OnClickListener() {
- public void onClick(DialogInterface dlg, int which) {
- WebStorage.getInstance().deleteAllData();
- GeolocationPermissions.getInstance().clearAll();
- WebStorageSizeManager.resetLastOutOfSpaceNotificationTime();
- mAdapter.askForOrigins();
- finish();
- }})
- .setNegativeButton(R.string.website_settings_clear_all_dialog_cancel_button, null)
- .setIcon(android.R.drawable.ic_dialog_alert)
- .show();
- return true;
+ private void finish() {
+ PreferenceActivity activity = (PreferenceActivity) getActivity();
+ if (activity != null) {
+ activity.finishPreferencePanel(this, 0, null);
}
- return false;
+ }
+
+ @Override
+ public void onClick(View v) {
+ switch (v.getId()) {
+ case R.id.clear_all_button:
+ // Show the prompt to clear all origins of their data and geolocation permissions.
+ new AlertDialog.Builder(getActivity())
+ .setTitle(R.string.website_settings_clear_all_dialog_title)
+ .setMessage(R.string.website_settings_clear_all_dialog_message)
+ .setPositiveButton(R.string.website_settings_clear_all_dialog_ok_button,
+ new AlertDialog.OnClickListener() {
+ public void onClick(DialogInterface dlg, int which) {
+ WebStorage.getInstance().deleteAllData();
+ GeolocationPermissions.getInstance().clearAll();
+ WebStorageSizeManager.resetLastOutOfSpaceNotificationTime();
+ mAdapter.askForOrigins();
+ finish();
+ }})
+ .setNegativeButton(R.string.website_settings_clear_all_dialog_cancel_button, null)
+ .setIcon(android.R.drawable.ic_dialog_alert)
+ .show();
+ break;
+ }
}
}
diff --git a/src/com/android/browser/provider/BrowserProvider2.java b/src/com/android/browser/provider/BrowserProvider2.java
new file mode 100644
index 0000000..a51635c
--- /dev/null
+++ b/src/com/android/browser/provider/BrowserProvider2.java
@@ -0,0 +1,1616 @@
+/*
+ * Copyright (C) 2010 he Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.browser.provider;
+
+import com.android.browser.BookmarkUtils;
+import com.android.browser.BrowserBookmarksPage;
+import com.android.browser.R;
+import com.android.common.content.SyncStateContentProviderHelper;
+
+import android.accounts.Account;
+import android.app.SearchManager;
+import android.content.ContentResolver;
+import android.content.ContentUris;
+import android.content.ContentValues;
+import android.content.Context;
+import android.content.Intent;
+import android.content.SharedPreferences;
+import android.content.UriMatcher;
+import android.content.res.Resources;
+import android.content.res.TypedArray;
+import android.database.AbstractCursor;
+import android.database.Cursor;
+import android.database.DatabaseUtils;
+import android.database.sqlite.SQLiteDatabase;
+import android.database.sqlite.SQLiteOpenHelper;
+import android.database.sqlite.SQLiteQueryBuilder;
+import android.net.Uri;
+import android.preference.PreferenceManager;
+import android.provider.BaseColumns;
+import android.provider.Browser;
+import android.provider.Browser.BookmarkColumns;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Accounts;
+import android.provider.BrowserContract.Bookmarks;
+import android.provider.BrowserContract.ChromeSyncColumns;
+import android.provider.BrowserContract.Combined;
+import android.provider.BrowserContract.History;
+import android.provider.BrowserContract.Images;
+import android.provider.BrowserContract.Searches;
+import android.provider.BrowserContract.Settings;
+import android.provider.BrowserContract.SyncState;
+import android.provider.ContactsContract.RawContacts;
+import android.provider.SyncStateContract;
+import android.text.TextUtils;
+
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.util.HashMap;
+
+public class BrowserProvider2 extends SQLiteContentProvider {
+
+ static final String LEGACY_AUTHORITY = "browser";
+ static final Uri LEGACY_AUTHORITY_URI = new Uri.Builder()
+ .authority(LEGACY_AUTHORITY).scheme("content").build();
+
+ static final String TABLE_BOOKMARKS = "bookmarks";
+ static final String TABLE_HISTORY = "history";
+ static final String TABLE_IMAGES = "images";
+ static final String TABLE_SEARCHES = "searches";
+ static final String TABLE_SYNC_STATE = "syncstate";
+ static final String TABLE_SETTINGS = "settings";
+
+ static final String TABLE_BOOKMARKS_JOIN_IMAGES = "bookmarks LEFT OUTER JOIN images " +
+ "ON bookmarks.url = images." + Images.URL;
+ static final String TABLE_HISTORY_JOIN_IMAGES = "history LEFT OUTER JOIN images " +
+ "ON history.url = images." + Images.URL;
+
+ static final String FORMAT_COMBINED_JOIN_SUBQUERY_JOIN_IMAGES =
+ "history LEFT OUTER JOIN (%s) bookmarks " +
+ "ON history.url = bookmarks.url LEFT OUTER JOIN images " +
+ "ON history.url = images.url_key";
+
+ static final String DEFAULT_SORT_HISTORY = History.DATE_LAST_VISITED + " DESC";
+
+ private static final String[] SUGGEST_PROJECTION = new String[] {
+ Bookmarks._ID,
+ Bookmarks.URL,
+ Bookmarks.TITLE};
+
+ private static final String SUGGEST_SELECTION =
+ "url LIKE ? OR url LIKE ? OR url LIKE ? OR url LIKE ?"
+ + " OR title LIKE ?";
+
+ private static final String IMAGE_PRUNE =
+ "url_key NOT IN (SELECT url FROM bookmarks " +
+ "WHERE url IS NOT NULL AND deleted == 0) AND url_key NOT IN " +
+ "(SELECT url FROM history WHERE url IS NOT NULL)";
+
+ static final int BOOKMARKS = 1000;
+ static final int BOOKMARKS_ID = 1001;
+ static final int BOOKMARKS_FOLDER = 1002;
+ static final int BOOKMARKS_FOLDER_ID = 1003;
+ static final int BOOKMARKS_SUGGESTIONS = 1004;
+
+ static final int HISTORY = 2000;
+ static final int HISTORY_ID = 2001;
+
+ static final int SEARCHES = 3000;
+ static final int SEARCHES_ID = 3001;
+
+ static final int SYNCSTATE = 4000;
+ static final int SYNCSTATE_ID = 4001;
+
+ static final int IMAGES = 5000;
+
+ static final int COMBINED = 6000;
+ static final int COMBINED_ID = 6001;
+
+ static final int ACCOUNTS = 7000;
+
+ static final int SETTINGS = 8000;
+
+ static final int LEGACY = 9000;
+ static final int LEGACY_ID = 9001;
+
+ public static final long FIXED_ID_ROOT = 1;
+
+ // Default sort order for unsync'd bookmarks
+ static final String DEFAULT_BOOKMARKS_SORT_ORDER =
+ Bookmarks.IS_FOLDER + " DESC, position ASC, _id ASC";
+
+ // Default sort order for sync'd bookmarks
+ static final String DEFAULT_BOOKMARKS_SORT_ORDER_SYNC = "position ASC, _id ASC";
+
+ static final UriMatcher URI_MATCHER = new UriMatcher(UriMatcher.NO_MATCH);
+
+ static final HashMap<String, String> ACCOUNTS_PROJECTION_MAP = new HashMap<String, String>();
+ static final HashMap<String, String> BOOKMARKS_PROJECTION_MAP = new HashMap<String, String>();
+ static final HashMap<String, String> OTHER_BOOKMARKS_PROJECTION_MAP =
+ new HashMap<String, String>();
+ static final HashMap<String, String> HISTORY_PROJECTION_MAP = new HashMap<String, String>();
+ static final HashMap<String, String> SYNC_STATE_PROJECTION_MAP = new HashMap<String, String>();
+ static final HashMap<String, String> IMAGES_PROJECTION_MAP = new HashMap<String, String>();
+ static final HashMap<String, String> COMBINED_HISTORY_PROJECTION_MAP = new HashMap<String, String>();
+ static final HashMap<String, String> COMBINED_BOOKMARK_PROJECTION_MAP = new HashMap<String, String>();
+ static final HashMap<String, String> SEARCHES_PROJECTION_MAP = new HashMap<String, String>();
+ static final HashMap<String, String> SETTINGS_PROJECTION_MAP = new HashMap<String, String>();
+
+ static {
+ final UriMatcher matcher = URI_MATCHER;
+ final String authority = BrowserContract.AUTHORITY;
+ matcher.addURI(authority, "accounts", ACCOUNTS);
+ matcher.addURI(authority, "bookmarks", BOOKMARKS);
+ matcher.addURI(authority, "bookmarks/#", BOOKMARKS_ID);
+ matcher.addURI(authority, "bookmarks/folder", BOOKMARKS_FOLDER);
+ matcher.addURI(authority, "bookmarks/folder/#", BOOKMARKS_FOLDER_ID);
+ matcher.addURI(authority,
+ SearchManager.SUGGEST_URI_PATH_QUERY,
+ BOOKMARKS_SUGGESTIONS);
+ matcher.addURI(authority,
+ "bookmarks/" + SearchManager.SUGGEST_URI_PATH_QUERY,
+ BOOKMARKS_SUGGESTIONS);
+ matcher.addURI(authority, "history", HISTORY);
+ matcher.addURI(authority, "history/#", HISTORY_ID);
+ matcher.addURI(authority, "searches", SEARCHES);
+ matcher.addURI(authority, "searches/#", SEARCHES_ID);
+ matcher.addURI(authority, "syncstate", SYNCSTATE);
+ matcher.addURI(authority, "syncstate/#", SYNCSTATE_ID);
+ matcher.addURI(authority, "images", IMAGES);
+ matcher.addURI(authority, "combined", COMBINED);
+ matcher.addURI(authority, "combined/#", COMBINED_ID);
+ matcher.addURI(authority, "settings", SETTINGS);
+
+ // Legacy
+ matcher.addURI(LEGACY_AUTHORITY, "searches", SEARCHES);
+ matcher.addURI(LEGACY_AUTHORITY, "searches/#", SEARCHES_ID);
+ matcher.addURI(LEGACY_AUTHORITY, "bookmarks", LEGACY);
+ matcher.addURI(LEGACY_AUTHORITY, "bookmarks/#", LEGACY_ID);
+ matcher.addURI(LEGACY_AUTHORITY,
+ SearchManager.SUGGEST_URI_PATH_QUERY,
+ BOOKMARKS_SUGGESTIONS);
+ matcher.addURI(LEGACY_AUTHORITY,
+ "bookmarks/" + SearchManager.SUGGEST_URI_PATH_QUERY,
+ BOOKMARKS_SUGGESTIONS);
+
+ // Projection maps
+ HashMap<String, String> map;
+
+ // Accounts
+ map = ACCOUNTS_PROJECTION_MAP;
+ map.put(Accounts.ACCOUNT_TYPE, Accounts.ACCOUNT_TYPE);
+ map.put(Accounts.ACCOUNT_NAME, Accounts.ACCOUNT_NAME);
+
+ // Bookmarks
+ map = BOOKMARKS_PROJECTION_MAP;
+ map.put(Bookmarks._ID, qualifyColumn(TABLE_BOOKMARKS, Bookmarks._ID));
+ map.put(Bookmarks.TITLE, Bookmarks.TITLE);
+ map.put(Bookmarks.URL, Bookmarks.URL);
+ map.put(Bookmarks.FAVICON, Bookmarks.FAVICON);
+ map.put(Bookmarks.THUMBNAIL, Bookmarks.THUMBNAIL);
+ map.put(Bookmarks.TOUCH_ICON, Bookmarks.TOUCH_ICON);
+ map.put(Bookmarks.IS_FOLDER, Bookmarks.IS_FOLDER);
+ map.put(Bookmarks.PARENT, Bookmarks.PARENT);
+ map.put(Bookmarks.POSITION, Bookmarks.POSITION);
+ map.put(Bookmarks.INSERT_AFTER, Bookmarks.INSERT_AFTER);
+ map.put(Bookmarks.IS_DELETED, Bookmarks.IS_DELETED);
+ map.put(Bookmarks.ACCOUNT_NAME, Bookmarks.ACCOUNT_NAME);
+ map.put(Bookmarks.ACCOUNT_TYPE, Bookmarks.ACCOUNT_TYPE);
+ map.put(Bookmarks.SOURCE_ID, Bookmarks.SOURCE_ID);
+ map.put(Bookmarks.VERSION, Bookmarks.VERSION);
+ map.put(Bookmarks.DATE_CREATED, Bookmarks.DATE_CREATED);
+ map.put(Bookmarks.DATE_MODIFIED, Bookmarks.DATE_MODIFIED);
+ map.put(Bookmarks.DIRTY, Bookmarks.DIRTY);
+ map.put(Bookmarks.SYNC1, Bookmarks.SYNC1);
+ map.put(Bookmarks.SYNC2, Bookmarks.SYNC2);
+ map.put(Bookmarks.SYNC3, Bookmarks.SYNC3);
+ map.put(Bookmarks.SYNC4, Bookmarks.SYNC4);
+ map.put(Bookmarks.SYNC5, Bookmarks.SYNC5);
+ map.put(Bookmarks.PARENT_SOURCE_ID, "(SELECT " + Bookmarks.SOURCE_ID +
+ " FROM " + TABLE_BOOKMARKS + " A WHERE " +
+ "A." + Bookmarks._ID + "=" + TABLE_BOOKMARKS + "." + Bookmarks.PARENT +
+ ") AS " + Bookmarks.PARENT_SOURCE_ID);
+ map.put(Bookmarks.INSERT_AFTER_SOURCE_ID, "(SELECT " + Bookmarks.SOURCE_ID +
+ " FROM " + TABLE_BOOKMARKS + " A WHERE " +
+ "A." + Bookmarks._ID + "=" + TABLE_BOOKMARKS + "." + Bookmarks.INSERT_AFTER +
+ ") AS " + Bookmarks.INSERT_AFTER_SOURCE_ID);
+
+ // Other bookmarks
+ OTHER_BOOKMARKS_PROJECTION_MAP.putAll(BOOKMARKS_PROJECTION_MAP);
+ OTHER_BOOKMARKS_PROJECTION_MAP.put(Bookmarks.POSITION,
+ Long.toString(Long.MAX_VALUE) + " AS " + Bookmarks.POSITION);
+
+ // History
+ map = HISTORY_PROJECTION_MAP;
+ map.put(History._ID, qualifyColumn(TABLE_HISTORY, History._ID));
+ map.put(History.TITLE, History.TITLE);
+ map.put(History.URL, History.URL);
+ map.put(History.FAVICON, History.FAVICON);
+ map.put(History.THUMBNAIL, History.THUMBNAIL);
+ map.put(History.TOUCH_ICON, History.TOUCH_ICON);
+ map.put(History.DATE_CREATED, History.DATE_CREATED);
+ map.put(History.DATE_LAST_VISITED, History.DATE_LAST_VISITED);
+ map.put(History.VISITS, History.VISITS);
+ map.put(History.USER_ENTERED, History.USER_ENTERED);
+
+ // Sync state
+ map = SYNC_STATE_PROJECTION_MAP;
+ map.put(SyncState._ID, SyncState._ID);
+ map.put(SyncState.ACCOUNT_NAME, SyncState.ACCOUNT_NAME);
+ map.put(SyncState.ACCOUNT_TYPE, SyncState.ACCOUNT_TYPE);
+ map.put(SyncState.DATA, SyncState.DATA);
+
+ // Images
+ map = IMAGES_PROJECTION_MAP;
+ map.put(Images.URL, Images.URL);
+ map.put(Images.FAVICON, Images.FAVICON);
+ map.put(Images.THUMBNAIL, Images.THUMBNAIL);
+ map.put(Images.TOUCH_ICON, Images.TOUCH_ICON);
+
+ // Combined history half
+ map = COMBINED_HISTORY_PROJECTION_MAP;
+ map.put(Combined._ID, bookmarkOrHistoryColumn(Combined._ID));
+ map.put(Combined.TITLE, bookmarkOrHistoryColumn(Combined.TITLE));
+ map.put(Combined.URL, qualifyColumn(TABLE_HISTORY, Combined.URL));
+ map.put(Combined.DATE_CREATED, qualifyColumn(TABLE_HISTORY, Combined.DATE_CREATED));
+ map.put(Combined.DATE_LAST_VISITED, Combined.DATE_LAST_VISITED);
+ map.put(Combined.IS_BOOKMARK, "CASE WHEN " +
+ TABLE_BOOKMARKS + "." + Bookmarks._ID +
+ " IS NOT NULL THEN 1 ELSE 0 END AS " + Combined.IS_BOOKMARK);
+ map.put(Combined.VISITS, Combined.VISITS);
+ map.put(Combined.FAVICON, Combined.FAVICON);
+ map.put(Combined.THUMBNAIL, Combined.THUMBNAIL);
+ map.put(Combined.TOUCH_ICON, Combined.TOUCH_ICON);
+ map.put(Combined.USER_ENTERED, "NULL AS " + Combined.USER_ENTERED);
+
+ // Combined bookmark half
+ map = COMBINED_BOOKMARK_PROJECTION_MAP;
+ map.put(Combined._ID, Combined._ID);
+ map.put(Combined.TITLE, Combined.TITLE);
+ map.put(Combined.URL, Combined.URL);
+ map.put(Combined.DATE_CREATED, Combined.DATE_CREATED);
+ map.put(Combined.DATE_LAST_VISITED, "NULL AS " + Combined.DATE_LAST_VISITED);
+ map.put(Combined.IS_BOOKMARK, "1 AS " + Combined.IS_BOOKMARK);
+ map.put(Combined.VISITS, "0 AS " + Combined.VISITS);
+ map.put(Combined.FAVICON, Combined.FAVICON);
+ map.put(Combined.THUMBNAIL, Combined.THUMBNAIL);
+ map.put(Combined.TOUCH_ICON, Combined.TOUCH_ICON);
+ map.put(Combined.USER_ENTERED, "NULL AS " + Combined.USER_ENTERED);
+
+ // Searches
+ map = SEARCHES_PROJECTION_MAP;
+ map.put(Searches._ID, Searches._ID);
+ map.put(Searches.SEARCH, Searches.SEARCH);
+ map.put(Searches.DATE, Searches.DATE);
+
+ // Settings
+ map = SETTINGS_PROJECTION_MAP;
+ map.put(Settings.KEY, Settings.KEY);
+ map.put(Settings.VALUE, Settings.VALUE);
+ }
+
+ static final String bookmarkOrHistoryColumn(String column) {
+ return "CASE WHEN bookmarks." + column + " IS NOT NULL THEN " +
+ "bookmarks." + column + " ELSE history." + column + " END AS " + column;
+ }
+
+ static final String qualifyColumn(String table, String column) {
+ return table + "." + column + " AS " + column;
+ }
+
+ DatabaseHelper mOpenHelper;
+ SyncStateContentProviderHelper mSyncHelper = new SyncStateContentProviderHelper();
+
+ final class DatabaseHelper extends SQLiteOpenHelper {
+ static final String DATABASE_NAME = "browser2.db";
+ static final int DATABASE_VERSION = 26;
+ public DatabaseHelper(Context context) {
+ super(context, DATABASE_NAME, null, DATABASE_VERSION);
+ }
+
+ @Override
+ public void onCreate(SQLiteDatabase db) {
+ db.execSQL("CREATE TABLE " + TABLE_BOOKMARKS + "(" +
+ Bookmarks._ID + " INTEGER PRIMARY KEY AUTOINCREMENT," +
+ Bookmarks.TITLE + " TEXT," +
+ Bookmarks.URL + " TEXT," +
+ Bookmarks.IS_FOLDER + " INTEGER NOT NULL DEFAULT 0," +
+ Bookmarks.PARENT + " INTEGER," +
+ Bookmarks.POSITION + " INTEGER NOT NULL," +
+ Bookmarks.INSERT_AFTER + " INTEGER," +
+ Bookmarks.IS_DELETED + " INTEGER NOT NULL DEFAULT 0," +
+ Bookmarks.ACCOUNT_NAME + " TEXT," +
+ Bookmarks.ACCOUNT_TYPE + " TEXT," +
+ Bookmarks.SOURCE_ID + " TEXT," +
+ Bookmarks.VERSION + " INTEGER NOT NULL DEFAULT 1," +
+ Bookmarks.DATE_CREATED + " INTEGER," +
+ Bookmarks.DATE_MODIFIED + " INTEGER," +
+ Bookmarks.DIRTY + " INTEGER NOT NULL DEFAULT 0," +
+ Bookmarks.SYNC1 + " TEXT," +
+ Bookmarks.SYNC2 + " TEXT," +
+ Bookmarks.SYNC3 + " TEXT," +
+ Bookmarks.SYNC4 + " TEXT," +
+ Bookmarks.SYNC5 + " TEXT" +
+ ");");
+
+ // TODO indices
+
+ db.execSQL("CREATE TABLE " + TABLE_HISTORY + "(" +
+ History._ID + " INTEGER PRIMARY KEY AUTOINCREMENT," +
+ History.TITLE + " TEXT," +
+ History.URL + " TEXT NOT NULL," +
+ History.DATE_CREATED + " INTEGER," +
+ History.DATE_LAST_VISITED + " INTEGER," +
+ History.VISITS + " INTEGER NOT NULL DEFAULT 0," +
+ History.USER_ENTERED + " INTEGER" +
+ ");");
+
+ db.execSQL("CREATE TABLE " + TABLE_IMAGES + " (" +
+ Images.URL + " TEXT UNIQUE NOT NULL," +
+ Images.FAVICON + " BLOB," +
+ Images.THUMBNAIL + " BLOB," +
+ Images.TOUCH_ICON + " BLOB" +
+ ");");
+ db.execSQL("CREATE INDEX imagesUrlIndex ON " + TABLE_IMAGES +
+ "(" + Images.URL + ")");
+
+ db.execSQL("CREATE TABLE " + TABLE_SEARCHES + " (" +
+ Searches._ID + " INTEGER PRIMARY KEY AUTOINCREMENT," +
+ Searches.SEARCH + " TEXT," +
+ Searches.DATE + " LONG" +
+ ");");
+
+ db.execSQL("CREATE TABLE " + TABLE_SETTINGS + " (" +
+ Settings.KEY + " TEXT PRIMARY KEY," +
+ Settings.VALUE + " TEXT NOT NULL" +
+ ");");
+
+ mSyncHelper.createDatabase(db);
+
+ createDefaultBookmarks(db);
+ }
+
+ @Override
+ public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
+ // TODO write upgrade logic
+ db.execSQL("DROP VIEW IF EXISTS combined");
+ if (oldVersion < 25) {
+ db.execSQL("DROP TABLE IF EXISTS " + TABLE_BOOKMARKS);
+ db.execSQL("DROP TABLE IF EXISTS " + TABLE_HISTORY);
+ db.execSQL("DROP TABLE IF EXISTS " + TABLE_SEARCHES);
+ db.execSQL("DROP TABLE IF EXISTS " + TABLE_IMAGES);
+ db.execSQL("DROP TABLE IF EXISTS " + TABLE_SETTINGS);
+ mSyncHelper.onAccountsChanged(db, new Account[] {}); // remove all sync info
+ onCreate(db);
+ }
+ }
+
+ @Override
+ public void onOpen(SQLiteDatabase db) {
+ db.enableWriteAheadLogging();
+ mSyncHelper.onDatabaseOpened(db);
+ }
+
+ private void createDefaultBookmarks(SQLiteDatabase db) {
+ ContentValues values = new ContentValues();
+ // TODO figure out how to deal with localization for the defaults
+
+ // Bookmarks folder
+ values.put(Bookmarks._ID, FIXED_ID_ROOT);
+ values.put(ChromeSyncColumns.SERVER_UNIQUE, ChromeSyncColumns.FOLDER_NAME_BOOKMARKS);
+ values.put(Bookmarks.TITLE, "Bookmarks");
+ values.putNull(Bookmarks.PARENT);
+ values.put(Bookmarks.POSITION, 0);
+ values.put(Bookmarks.IS_FOLDER, true);
+ values.put(Bookmarks.DIRTY, true);
+ db.insertOrThrow(TABLE_BOOKMARKS, null, values);
+
+ addDefaultBookmarks(db, FIXED_ID_ROOT);
+ }
+
+ private void addDefaultBookmarks(SQLiteDatabase db, long parentId) {
+ Resources res = getContext().getResources();
+ final CharSequence[] bookmarks = res.getTextArray(
+ R.array.bookmarks);
+ int size = bookmarks.length;
+ TypedArray preloads = res.obtainTypedArray(R.array.bookmark_preloads);
+ try {
+ String parent = Long.toString(parentId);
+ String now = Long.toString(System.currentTimeMillis());
+ for (int i = 0; i < size; i = i + 2) {
+ CharSequence bookmarkDestination = replaceSystemPropertyInString(getContext(),
+ bookmarks[i + 1]);
+ db.execSQL("INSERT INTO bookmarks (" +
+ Bookmarks.TITLE + ", " +
+ Bookmarks.URL + ", " +
+ Bookmarks.IS_FOLDER + "," +
+ Bookmarks.PARENT + "," +
+ Bookmarks.POSITION + "," +
+ Bookmarks.DATE_CREATED +
+ ") VALUES (" +
+ "'" + bookmarks[i] + "', " +
+ "'" + bookmarkDestination + "', " +
+ "0," +
+ parent + "," +
+ Integer.toString(i) + "," +
+ now +
+ ");");
+
+ int faviconId = preloads.getResourceId(i, 0);
+ int thumbId = preloads.getResourceId(i + 1, 0);
+ byte[] thumb = null, favicon = null;
+ try {
+ thumb = readRaw(res, thumbId);
+ } catch (IOException e) {
+ }
+ try {
+ favicon = readRaw(res, faviconId);
+ } catch (IOException e) {
+ }
+ if (thumb != null || favicon != null) {
+ ContentValues imageValues = new ContentValues();
+ imageValues.put(Images.URL, bookmarkDestination.toString());
+ if (favicon != null) {
+ imageValues.put(Images.FAVICON, favicon);
+ }
+ if (thumb != null) {
+ imageValues.put(Images.THUMBNAIL, thumb);
+ }
+ db.insert(TABLE_IMAGES, Images.FAVICON, imageValues);
+ }
+ }
+ } catch (ArrayIndexOutOfBoundsException e) {
+ }
+ }
+
+ private byte[] readRaw(Resources res, int id) throws IOException {
+ if (id == 0) {
+ return null;
+ }
+ InputStream is = res.openRawResource(id);
+ try {
+ ByteArrayOutputStream bos = new ByteArrayOutputStream();
+ byte[] buf = new byte[4096];
+ int read;
+ while ((read = is.read(buf)) > 0) {
+ bos.write(buf, 0, read);
+ }
+ bos.flush();
+ return bos.toByteArray();
+ } finally {
+ is.close();
+ }
+ }
+
+ // XXX: This is a major hack to remove our dependency on gsf constants and
+ // its content provider. http://b/issue?id=2425179
+ private String getClientId(ContentResolver cr) {
+ String ret = "android-google";
+ Cursor c = null;
+ try {
+ c = cr.query(Uri.parse("content://com.google.settings/partner"),
+ new String[] { "value" }, "name='client_id'", null, null);
+ if (c != null && c.moveToNext()) {
+ ret = c.getString(0);
+ }
+ } catch (RuntimeException ex) {
+ // fall through to return the default
+ } finally {
+ if (c != null) {
+ c.close();
+ }
+ }
+ return ret;
+ }
+
+ private CharSequence replaceSystemPropertyInString(Context context, CharSequence srcString) {
+ StringBuffer sb = new StringBuffer();
+ int lastCharLoc = 0;
+
+ final String client_id = getClientId(context.getContentResolver());
+
+ for (int i = 0; i < srcString.length(); ++i) {
+ char c = srcString.charAt(i);
+ if (c == '{') {
+ sb.append(srcString.subSequence(lastCharLoc, i));
+ lastCharLoc = i;
+ inner:
+ for (int j = i; j < srcString.length(); ++j) {
+ char k = srcString.charAt(j);
+ if (k == '}') {
+ String propertyKeyValue = srcString.subSequence(i + 1, j).toString();
+ if (propertyKeyValue.equals("CLIENT_ID")) {
+ sb.append(client_id);
+ } else {
+ sb.append("unknown");
+ }
+ lastCharLoc = j + 1;
+ i = j;
+ break inner;
+ }
+ }
+ }
+ }
+ if (srcString.length() - lastCharLoc > 0) {
+ // Put on the tail, if there is one
+ sb.append(srcString.subSequence(lastCharLoc, srcString.length()));
+ }
+ return sb;
+ }
+ }
+
+ @Override
+ public SQLiteOpenHelper getDatabaseHelper(Context context) {
+ synchronized (this) {
+ if (mOpenHelper == null) {
+ mOpenHelper = new DatabaseHelper(context);
+ }
+ return mOpenHelper;
+ }
+ }
+
+ @Override
+ public boolean isCallerSyncAdapter(Uri uri) {
+ return uri.getBooleanQueryParameter(BrowserContract.CALLER_IS_SYNCADAPTER, false);
+ }
+
+ @Override
+ public void notifyChange(boolean callerIsSyncAdapter) {
+ ContentResolver resolver = getContext().getContentResolver();
+ resolver.notifyChange(BrowserContract.AUTHORITY_URI, null, !callerIsSyncAdapter);
+ resolver.notifyChange(LEGACY_AUTHORITY_URI, null, !callerIsSyncAdapter);
+ }
+
+ @Override
+ public String getType(Uri uri) {
+ final int match = URI_MATCHER.match(uri);
+ switch (match) {
+ case LEGACY:
+ case BOOKMARKS:
+ return Bookmarks.CONTENT_TYPE;
+ case LEGACY_ID:
+ case BOOKMARKS_ID:
+ return Bookmarks.CONTENT_ITEM_TYPE;
+ case HISTORY:
+ return History.CONTENT_TYPE;
+ case HISTORY_ID:
+ return History.CONTENT_ITEM_TYPE;
+ case SEARCHES:
+ return Searches.CONTENT_TYPE;
+ case SEARCHES_ID:
+ return Searches.CONTENT_ITEM_TYPE;
+ }
+ return null;
+ }
+
+ boolean isNullAccount(String account) {
+ if (account == null) return true;
+ account = account.trim();
+ return account.length() == 0 || account.equals("null");
+ }
+
+ Object[] getSelectionWithAccounts(Uri uri, String selection, String[] selectionArgs) {
+ // Look for account info
+ String accountType = uri.getQueryParameter(Bookmarks.PARAM_ACCOUNT_TYPE);
+ String accountName = uri.getQueryParameter(Bookmarks.PARAM_ACCOUNT_NAME);
+ boolean hasAccounts = false;
+ if (accountType != null && accountName != null) {
+ if (!isNullAccount(accountType) && !isNullAccount(accountName)) {
+ selection = DatabaseUtils.concatenateWhere(selection,
+ Bookmarks.ACCOUNT_TYPE + "=? AND " + Bookmarks.ACCOUNT_NAME + "=? ");
+ selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+ new String[] { accountType, accountName });
+ hasAccounts = true;
+ } else {
+ selection = DatabaseUtils.concatenateWhere(selection,
+ Bookmarks.ACCOUNT_NAME + " IS NULL AND " +
+ Bookmarks.ACCOUNT_TYPE + " IS NULL");
+ }
+ }
+ return new Object[] { selection, selectionArgs, hasAccounts };
+ }
+
+ @Override
+ public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs,
+ String sortOrder) {
+ SQLiteDatabase db = mOpenHelper.getReadableDatabase();
+ final int match = URI_MATCHER.match(uri);
+ SQLiteQueryBuilder qb = new SQLiteQueryBuilder();
+ String limit = uri.getQueryParameter(BrowserContract.PARAM_LIMIT);
+ switch (match) {
+ case ACCOUNTS: {
+ qb.setTables(TABLE_BOOKMARKS);
+ qb.setProjectionMap(ACCOUNTS_PROJECTION_MAP);
+ qb.setDistinct(true);
+ qb.appendWhere(Bookmarks.ACCOUNT_NAME + " IS NOT NULL");
+ break;
+ }
+
+ case BOOKMARKS_FOLDER_ID:
+ case BOOKMARKS_ID:
+ case BOOKMARKS: {
+ // Only show deleted bookmarks if requested to do so
+ if (!uri.getBooleanQueryParameter(Bookmarks.QUERY_PARAMETER_SHOW_DELETED, false)) {
+ selection = DatabaseUtils.concatenateWhere(
+ Bookmarks.IS_DELETED + "=0", selection);
+ }
+
+ if (match == BOOKMARKS_ID) {
+ // Tack on the ID of the specific bookmark requested
+ selection = DatabaseUtils.concatenateWhere(selection,
+ TABLE_BOOKMARKS + "." + Bookmarks._ID + "=?");
+ selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+ new String[] { Long.toString(ContentUris.parseId(uri)) });
+ } else if (match == BOOKMARKS_FOLDER_ID) {
+ // Tack on the ID of the specific folder requested
+ selection = DatabaseUtils.concatenateWhere(selection,
+ TABLE_BOOKMARKS + "." + Bookmarks.PARENT + "=?");
+ selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+ new String[] { Long.toString(ContentUris.parseId(uri)) });
+ }
+
+ Object[] withAccount = getSelectionWithAccounts(uri, selection, selectionArgs);
+ selection = (String) withAccount[0];
+ selectionArgs = (String[]) withAccount[1];
+ boolean hasAccounts = (Boolean) withAccount[2];
+
+ // Set a default sort order if one isn't specified
+ if (TextUtils.isEmpty(sortOrder)) {
+ if (hasAccounts) {
+ sortOrder = DEFAULT_BOOKMARKS_SORT_ORDER_SYNC;
+ } else {
+ sortOrder = DEFAULT_BOOKMARKS_SORT_ORDER;
+ }
+ }
+
+ qb.setProjectionMap(BOOKMARKS_PROJECTION_MAP);
+ qb.setTables(TABLE_BOOKMARKS_JOIN_IMAGES);
+ break;
+ }
+
+ case BOOKMARKS_FOLDER: {
+ // Look for an account
+ boolean useAccount = false;
+ String accountType = uri.getQueryParameter(Bookmarks.PARAM_ACCOUNT_TYPE);
+ String accountName = uri.getQueryParameter(Bookmarks.PARAM_ACCOUNT_NAME);
+ if (!isNullAccount(accountType) && !isNullAccount(accountName)) {
+ useAccount = true;
+ }
+
+ qb.setTables(TABLE_BOOKMARKS_JOIN_IMAGES);
+ String[] args;
+ String query;
+ // Set a default sort order if one isn't specified
+ if (TextUtils.isEmpty(sortOrder)) {
+ if (useAccount) {
+ sortOrder = DEFAULT_BOOKMARKS_SORT_ORDER_SYNC;
+ } else {
+ sortOrder = DEFAULT_BOOKMARKS_SORT_ORDER;
+ }
+ }
+ if (!useAccount) {
+ qb.setProjectionMap(BOOKMARKS_PROJECTION_MAP);
+ String where = Bookmarks.PARENT + "=? AND " + Bookmarks.IS_DELETED + "=0";
+ where = DatabaseUtils.concatenateWhere(where, selection);
+ args = new String[] { Long.toString(FIXED_ID_ROOT) };
+ if (selectionArgs != null) {
+ args = DatabaseUtils.appendSelectionArgs(args, selectionArgs);
+ }
+ query = qb.buildQuery(projection, where, null, null, sortOrder, null);
+ } else {
+ qb.setProjectionMap(BOOKMARKS_PROJECTION_MAP);
+ String where = Bookmarks.ACCOUNT_TYPE + "=? AND " +
+ Bookmarks.ACCOUNT_NAME + "=? " +
+ "AND parent = " +
+ "(SELECT _id FROM " + TABLE_BOOKMARKS + " WHERE " +
+ ChromeSyncColumns.SERVER_UNIQUE + "=" +
+ "'" + ChromeSyncColumns.FOLDER_NAME_BOOKMARKS_BAR + "' " +
+ "AND account_type = ? AND account_name = ?) " +
+ "AND " + Bookmarks.IS_DELETED + "=0";
+ where = DatabaseUtils.concatenateWhere(where, selection);
+ String bookmarksBarQuery = qb.buildQuery(projection,
+ where, null, null, null, null);
+ args = new String[] {accountType, accountName,
+ accountType, accountName};
+ if (selectionArgs != null) {
+ args = DatabaseUtils.appendSelectionArgs(args, selectionArgs);
+ }
+
+ where = Bookmarks.ACCOUNT_TYPE + "=? AND " + Bookmarks.ACCOUNT_NAME + "=?" +
+ " AND " + ChromeSyncColumns.SERVER_UNIQUE + "=?";
+ where = DatabaseUtils.concatenateWhere(where, selection);
+ qb.setProjectionMap(OTHER_BOOKMARKS_PROJECTION_MAP);
+ String otherBookmarksQuery = qb.buildQuery(projection,
+ where, null, null, null, null);
+
+ query = qb.buildUnionQuery(
+ new String[] { bookmarksBarQuery, otherBookmarksQuery },
+ sortOrder, limit);
+
+ args = DatabaseUtils.appendSelectionArgs(args, new String[] {
+ accountType, accountName, ChromeSyncColumns.FOLDER_NAME_OTHER_BOOKMARKS,
+ });
+ if (selectionArgs != null) {
+ args = DatabaseUtils.appendSelectionArgs(args, selectionArgs);
+ }
+ }
+
+ Cursor cursor = db.rawQuery(query, args);
+ if (cursor != null) {
+ cursor.setNotificationUri(getContext().getContentResolver(),
+ BrowserContract.AUTHORITY_URI);
+ }
+ return cursor;
+ }
+
+ case BOOKMARKS_SUGGESTIONS: {
+ return doSuggestQuery(selection, selectionArgs, limit);
+ }
+
+ case HISTORY_ID: {
+ selection = DatabaseUtils.concatenateWhere(selection, TABLE_HISTORY + "._id=?");
+ selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+ new String[] { Long.toString(ContentUris.parseId(uri)) });
+ // fall through
+ }
+ case HISTORY: {
+ filterSearchClient(selectionArgs);
+ if (sortOrder == null) {
+ sortOrder = DEFAULT_SORT_HISTORY;
+ }
+ qb.setProjectionMap(HISTORY_PROJECTION_MAP);
+ qb.setTables(TABLE_HISTORY_JOIN_IMAGES);
+ break;
+ }
+
+ case SEARCHES_ID: {
+ selection = DatabaseUtils.concatenateWhere(selection, TABLE_SEARCHES + "._id=?");
+ selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+ new String[] { Long.toString(ContentUris.parseId(uri)) });
+ // fall through
+ }
+ case SEARCHES: {
+ qb.setTables(TABLE_SEARCHES);
+ qb.setProjectionMap(SEARCHES_PROJECTION_MAP);
+ break;
+ }
+
+ case SYNCSTATE: {
+ return mSyncHelper.query(db, projection, selection, selectionArgs, sortOrder);
+ }
+
+ case SYNCSTATE_ID: {
+ selection = appendAccountToSelection(uri, selection);
+ String selectionWithId =
+ (SyncStateContract.Columns._ID + "=" + ContentUris.parseId(uri) + " ")
+ + (selection == null ? "" : " AND (" + selection + ")");
+ return mSyncHelper.query(db, projection, selectionWithId, selectionArgs, sortOrder);
+ }
+
+ case IMAGES: {
+ qb.setTables(TABLE_IMAGES);
+ qb.setProjectionMap(IMAGES_PROJECTION_MAP);
+ break;
+ }
+
+ case LEGACY_ID:
+ case COMBINED_ID: {
+ selection = DatabaseUtils.concatenateWhere(
+ selection, Combined._ID + " = CAST(? AS INTEGER)");
+ selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+ new String[] { Long.toString(ContentUris.parseId(uri)) });
+ // fall through
+ }
+ case LEGACY:
+ case COMBINED: {
+ if ((match == LEGACY || match == LEGACY_ID)
+ && projection == null) {
+ projection = Browser.HISTORY_PROJECTION;
+ }
+ if (match == LEGACY) {
+ uri = BookmarkUtils.addAccountInfo(getContext(),
+ uri.buildUpon()).build();
+ }
+ String[] args = createCombinedQuery(uri, projection, qb);
+ if (selectionArgs == null) {
+ selectionArgs = args;
+ } else {
+ selectionArgs = DatabaseUtils.appendSelectionArgs(args, selectionArgs);
+ }
+ break;
+ }
+
+ case SETTINGS: {
+ qb.setTables(TABLE_SETTINGS);
+ qb.setProjectionMap(SETTINGS_PROJECTION_MAP);
+ break;
+ }
+
+ default: {
+ throw new UnsupportedOperationException("Unknown URL " + uri.toString());
+ }
+ }
+
+ Cursor cursor = qb.query(db, projection, selection, selectionArgs, null, null, sortOrder,
+ limit);
+ cursor.setNotificationUri(getContext().getContentResolver(), BrowserContract.AUTHORITY_URI);
+ return cursor;
+ }
+
+ private Cursor doSuggestQuery(String selection, String[] selectionArgs, String limit) {
+ if (selectionArgs[0] == null) {
+ return null;
+ } else {
+ String like = selectionArgs[0] + "%";
+ if (selectionArgs[0].startsWith("http")
+ || selectionArgs[0].startsWith("file")) {
+ selectionArgs[0] = like;
+ } else {
+ selectionArgs = new String[5];
+ selectionArgs[0] = "http://" + like;
+ selectionArgs[1] = "http://www." + like;
+ selectionArgs[2] = "https://" + like;
+ selectionArgs[3] = "https://www." + like;
+ // To match against titles.
+ selectionArgs[4] = like;
+ selection = SUGGEST_SELECTION;
+ }
+ }
+ selection = DatabaseUtils.concatenateWhere(selection,
+ Bookmarks.IS_DELETED + "=0 AND " + Bookmarks.IS_FOLDER + "=0");
+
+ SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(getContext());
+ String accountType = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE, null);
+ String accountName = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, null);
+ if (!TextUtils.isEmpty(accountName) && !TextUtils.isEmpty(accountType)) {
+ selection = DatabaseUtils.concatenateWhere(selection,
+ Bookmarks.ACCOUNT_TYPE + "=? AND " + Bookmarks.ACCOUNT_NAME + "=? ");
+ selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+ new String[] { accountType, accountName });
+ } else {
+ selection = DatabaseUtils.concatenateWhere(selection,
+ Bookmarks.ACCOUNT_TYPE + " IS NULL AND " +
+ Bookmarks.ACCOUNT_NAME + " IS NULL ");
+ }
+ Cursor c = mOpenHelper.getReadableDatabase().query(TABLE_BOOKMARKS,
+ SUGGEST_PROJECTION, selection, selectionArgs, null, null,
+ DEFAULT_BOOKMARKS_SORT_ORDER, null);
+
+ return new SuggestionsCursor(c);
+ }
+
+ private String[] createCombinedQuery(
+ Uri uri, String[] projection, SQLiteQueryBuilder qb) {
+ String[] args = null;
+ StringBuilder whereBuilder = new StringBuilder(128);
+ whereBuilder.append(Bookmarks.IS_DELETED);
+ whereBuilder.append(" = 0");
+ // Look for account info
+ Object[] withAccount = getSelectionWithAccounts(uri, null, null);
+ String selection = (String) withAccount[0];
+ String[] selectionArgs = (String[]) withAccount[1];
+ if (selection != null) {
+ whereBuilder.append(" AND " + selection);
+ if (selectionArgs != null) {
+ // We use the selection twice, hence we need to duplicate the args
+ args = new String[selectionArgs.length * 2];
+ System.arraycopy(selectionArgs, 0, args, 0, selectionArgs.length);
+ System.arraycopy(selectionArgs, 0, args, selectionArgs.length,
+ selectionArgs.length);
+ }
+ }
+ String where = whereBuilder.toString();
+ // Build the bookmark subquery for history union subquery
+ qb.setTables(TABLE_BOOKMARKS);
+ String subQuery = qb.buildQuery(null, where, null, null, null, null);
+ // Build the history union subquery
+ qb.setTables(String.format(FORMAT_COMBINED_JOIN_SUBQUERY_JOIN_IMAGES, subQuery));
+ qb.setProjectionMap(COMBINED_HISTORY_PROJECTION_MAP);
+ String historySubQuery = qb.buildQuery(null,
+ null, null, null, null, null);
+ // Build the bookmark union subquery
+ qb.setTables(TABLE_BOOKMARKS_JOIN_IMAGES);
+ qb.setProjectionMap(COMBINED_BOOKMARK_PROJECTION_MAP);
+ where += String.format(" AND %s NOT IN (SELECT %s FROM %s)",
+ Combined.URL, History.URL, TABLE_HISTORY);
+ String bookmarksSubQuery = qb.buildQuery(null, where,
+ null, null, null, null);
+ // Put it all together
+ String query = qb.buildUnionQuery(
+ new String[] {historySubQuery, bookmarksSubQuery},
+ null, null);
+ qb.setTables("(" + query + ")");
+ qb.setProjectionMap(null);
+ return args;
+ }
+
+ int deleteBookmarks(String selection, String[] selectionArgs,
+ boolean callerIsSyncAdapter) {
+ //TODO cascade deletes down from folders
+ final SQLiteDatabase db = mOpenHelper.getWritableDatabase();
+ if (callerIsSyncAdapter) {
+ return db.delete(TABLE_BOOKMARKS, selection, selectionArgs);
+ }
+ ContentValues values = new ContentValues();
+ values.put(Bookmarks.DATE_MODIFIED, System.currentTimeMillis());
+ values.put(Bookmarks.IS_DELETED, 1);
+ return updateBookmarksInTransaction(values, selection, selectionArgs,
+ callerIsSyncAdapter);
+ }
+
+ @Override
+ public int deleteInTransaction(Uri uri, String selection, String[] selectionArgs,
+ boolean callerIsSyncAdapter) {
+ final int match = URI_MATCHER.match(uri);
+ final SQLiteDatabase db = mOpenHelper.getWritableDatabase();
+ switch (match) {
+ case BOOKMARKS_ID: {
+ selection = DatabaseUtils.concatenateWhere(selection,
+ TABLE_BOOKMARKS + "._id=?");
+ selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+ new String[] { Long.toString(ContentUris.parseId(uri)) });
+ // fall through
+ }
+ case BOOKMARKS: {
+ // Look for account info
+ Object[] withAccount = getSelectionWithAccounts(uri, selection, selectionArgs);
+ selection = (String) withAccount[0];
+ selectionArgs = (String[]) withAccount[1];
+ int deleted = deleteBookmarks(selection, selectionArgs, callerIsSyncAdapter);
+ pruneImages();
+ return deleted;
+ }
+
+ case HISTORY_ID: {
+ selection = DatabaseUtils.concatenateWhere(selection, TABLE_HISTORY + "._id=?");
+ selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+ new String[] { Long.toString(ContentUris.parseId(uri)) });
+ // fall through
+ }
+ case HISTORY: {
+ filterSearchClient(selectionArgs);
+ int deleted = db.delete(TABLE_HISTORY, selection, selectionArgs);
+ pruneImages();
+ return deleted;
+ }
+
+ case SEARCHES_ID: {
+ selection = DatabaseUtils.concatenateWhere(selection, TABLE_SEARCHES + "._id=?");
+ selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+ new String[] { Long.toString(ContentUris.parseId(uri)) });
+ // fall through
+ }
+ case SEARCHES: {
+ return db.delete(TABLE_SEARCHES, selection, selectionArgs);
+ }
+
+ case SYNCSTATE: {
+ return mSyncHelper.delete(db, selection, selectionArgs);
+ }
+ case SYNCSTATE_ID: {
+ String selectionWithId =
+ (SyncStateContract.Columns._ID + "=" + ContentUris.parseId(uri) + " ")
+ + (selection == null ? "" : " AND (" + selection + ")");
+ return mSyncHelper.delete(db, selectionWithId, selectionArgs);
+ }
+ case LEGACY_ID: {
+ selection = DatabaseUtils.concatenateWhere(
+ selection, Combined._ID + " = CAST(? AS INTEGER)");
+ selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+ new String[] { Long.toString(ContentUris.parseId(uri)) });
+ // fall through
+ }
+ case LEGACY: {
+ String[] projection = new String[] { Combined._ID,
+ Combined.IS_BOOKMARK, Combined.URL };
+ SQLiteQueryBuilder qb = new SQLiteQueryBuilder();
+ uri = BookmarkUtils.addAccountInfo(getContext(), uri.buildUpon())
+ .build();
+ String[] args = createCombinedQuery(uri, projection, qb);
+ if (selectionArgs == null) {
+ selectionArgs = args;
+ } else {
+ selectionArgs = DatabaseUtils.appendSelectionArgs(
+ args, selectionArgs);
+ }
+ Cursor c = qb.query(db, projection, selection, selectionArgs,
+ null, null, null);
+ int deleted = 0;
+ while (c.moveToNext()) {
+ long id = c.getLong(0);
+ boolean isBookmark = c.getInt(1) != 0;
+ String url = c.getString(2);
+ if (isBookmark) {
+ deleted += deleteBookmarks(Bookmarks._ID + "=?",
+ new String[] { Long.toString(id) },
+ callerIsSyncAdapter);
+ db.delete(TABLE_HISTORY, History.URL + "=?",
+ new String[] { url });
+ } else {
+ deleted += db.delete(TABLE_HISTORY,
+ Bookmarks._ID + "=?",
+ new String[] { Long.toString(id) });
+ }
+ }
+ return deleted;
+ }
+ }
+ throw new UnsupportedOperationException("Unknown delete URI " + uri);
+ }
+
+ long queryDefaultFolderId(String accountName, String accountType) {
+ if (!TextUtils.isEmpty(accountName) && !TextUtils.isEmpty(accountType)) {
+ final SQLiteDatabase db = mOpenHelper.getReadableDatabase();
+ Cursor c = db.query(TABLE_BOOKMARKS, new String[] { Bookmarks._ID },
+ ChromeSyncColumns.SERVER_UNIQUE + " = ?" +
+ " AND account_type = ? AND account_name = ?",
+ new String[] { ChromeSyncColumns.FOLDER_NAME_BOOKMARKS_BAR,
+ accountType, accountName }, null, null, null);
+ if (c.moveToFirst()) {
+ return c.getLong(0);
+ }
+ }
+ return FIXED_ID_ROOT;
+ }
+
+ @Override
+ public Uri insertInTransaction(Uri uri, ContentValues values, boolean callerIsSyncAdapter) {
+ int match = URI_MATCHER.match(uri);
+ final SQLiteDatabase db = mOpenHelper.getWritableDatabase();
+ long id = -1;
+ if (match == LEGACY) {
+ // Intercept and route to the correct table
+ Integer bookmark = values.getAsInteger(BookmarkColumns.BOOKMARK);
+ values.remove(BookmarkColumns.BOOKMARK);
+ if (bookmark == null || bookmark == 0) {
+ match = HISTORY;
+ } else {
+ match = BOOKMARKS;
+ values.remove(BookmarkColumns.DATE);
+ values.remove(BookmarkColumns.VISITS);
+ values.remove(BookmarkColumns.USER_ENTERED);
+ SharedPreferences prefs = PreferenceManager
+ .getDefaultSharedPreferences(getContext());
+ String accountType = prefs.getString(
+ BrowserBookmarksPage.PREF_ACCOUNT_TYPE, null);
+ String accountName = prefs.getString(
+ BrowserBookmarksPage.PREF_ACCOUNT_NAME, null);
+ values.put(Bookmarks.ACCOUNT_TYPE, accountType);
+ values.put(Bookmarks.ACCOUNT_NAME, accountName);
+ values.put(Bookmarks.IS_FOLDER, 0);
+ }
+ }
+ switch (match) {
+ case BOOKMARKS: {
+ // Mark rows dirty if they're not coming from a sync adapter
+ if (!callerIsSyncAdapter) {
+ long now = System.currentTimeMillis();
+ values.put(Bookmarks.DATE_CREATED, now);
+ values.put(Bookmarks.DATE_MODIFIED, now);
+ values.put(Bookmarks.DIRTY, 1);
+
+ // If no parent is set default to the "Bookmarks Bar" folder
+ if (!values.containsKey(Bookmarks.PARENT)) {
+ String accountType = values
+ .getAsString(Bookmarks.ACCOUNT_TYPE);
+ String accountName = values
+ .getAsString(Bookmarks.ACCOUNT_NAME);
+ values.put(Bookmarks.PARENT,
+ queryDefaultFolderId(accountName, accountType));
+ }
+ }
+
+ // If no position is requested put the bookmark at the beginning of the list
+ if (!values.containsKey(Bookmarks.POSITION)) {
+ values.put(Bookmarks.POSITION, Long.toString(Long.MIN_VALUE));
+ }
+
+ // Extract out the image values so they can be inserted into the images table
+ String url = values.getAsString(Bookmarks.URL);
+ ContentValues imageValues = extractImageValues(values, url);
+ Boolean isFolder = values.getAsBoolean(Bookmarks.IS_FOLDER);
+ if ((isFolder == null || !isFolder)
+ && imageValues != null && !TextUtils.isEmpty(url)) {
+ int count = db.update(TABLE_IMAGES, imageValues, Images.URL + "=?",
+ new String[] { url });
+ if (count == 0) {
+ db.insertOrThrow(TABLE_IMAGES, Images.FAVICON, imageValues);
+ }
+ }
+
+ id = db.insertOrThrow(TABLE_BOOKMARKS, Bookmarks.DIRTY, values);
+ break;
+ }
+
+ case HISTORY: {
+ // If no created time is specified set it to now
+ if (!values.containsKey(History.DATE_CREATED)) {
+ values.put(History.DATE_CREATED, System.currentTimeMillis());
+ }
+ String url = values.getAsString(History.URL);
+ url = filterSearchClient(url);
+ values.put(History.URL, url);
+
+ // Extract out the image values so they can be inserted into the images table
+ ContentValues imageValues = extractImageValues(values,
+ values.getAsString(History.URL));
+ if (imageValues != null) {
+ db.insertOrThrow(TABLE_IMAGES, Images.FAVICON, imageValues);
+ }
+
+ id = db.insertOrThrow(TABLE_HISTORY, History.VISITS, values);
+ break;
+ }
+
+ case SEARCHES: {
+ id = insertSearchesInTransaction(db, values);
+ break;
+ }
+
+ case SYNCSTATE: {
+ id = mSyncHelper.insert(db, values);
+ break;
+ }
+
+ case SETTINGS: {
+ id = 0;
+ insertSettingsInTransaction(db, values);
+ break;
+ }
+
+ default: {
+ throw new UnsupportedOperationException("Unknown insert URI " + uri);
+ }
+ }
+
+ if (id >= 0) {
+ return ContentUris.withAppendedId(uri, id);
+ } else {
+ return null;
+ }
+ }
+
+ private void filterSearchClient(String[] selectionArgs) {
+ if (selectionArgs != null) {
+ for (int i = 0; i < selectionArgs.length; i++) {
+ selectionArgs[i] = filterSearchClient(selectionArgs[i]);
+ }
+ }
+ }
+
+ // Filters out the client=ms- param for search urls
+ private String filterSearchClient(String url) {
+ // remove "client" before updating it to the history so that it wont
+ // show up in the auto-complete list.
+ int index = url.indexOf("client=ms-");
+ if (index > 0 && url.contains(".google.")) {
+ int end = url.indexOf('&', index);
+ if (end > 0) {
+ url = url.substring(0, index)
+ .concat(url.substring(end + 1));
+ } else {
+ // the url.charAt(index-1) should be either '?' or '&'
+ url = url.substring(0, index-1);
+ }
+ }
+ return url;
+ }
+
+ /**
+ * Searches are unique, so perform an UPSERT manually since SQLite doesn't support them.
+ */
+ private long insertSearchesInTransaction(SQLiteDatabase db, ContentValues values) {
+ String search = values.getAsString(Searches.SEARCH);
+ if (TextUtils.isEmpty(search)) {
+ throw new IllegalArgumentException("Must include the SEARCH field");
+ }
+ Cursor cursor = null;
+ try {
+ cursor = db.query(TABLE_SEARCHES, new String[] { Searches._ID },
+ Searches.SEARCH + "=?", new String[] { search }, null, null, null);
+ if (cursor.moveToNext()) {
+ long id = cursor.getLong(0);
+ db.update(TABLE_SEARCHES, values, Searches._ID + "=?",
+ new String[] { Long.toString(id) });
+ return id;
+ } else {
+ return db.insertOrThrow(TABLE_SEARCHES, Searches.SEARCH, values);
+ }
+ } finally {
+ if (cursor != null) cursor.close();
+ }
+ }
+
+ /**
+ * Settings are unique, so perform an UPSERT manually since SQLite doesn't support them.
+ */
+ private long insertSettingsInTransaction(SQLiteDatabase db, ContentValues values) {
+ String key = values.getAsString(Settings.KEY);
+ if (TextUtils.isEmpty(key)) {
+ throw new IllegalArgumentException("Must include the KEY field");
+ }
+ String[] keyArray = new String[] { key };
+ Cursor cursor = null;
+ try {
+ cursor = db.query(TABLE_SETTINGS, new String[] { Settings.KEY },
+ Settings.KEY + "=?", keyArray, null, null, null);
+ if (cursor.moveToNext()) {
+ long id = cursor.getLong(0);
+ db.update(TABLE_SETTINGS, values, Settings.KEY + "=?", keyArray);
+ return id;
+ } else {
+ return db.insertOrThrow(TABLE_SETTINGS, Settings.VALUE, values);
+ }
+ } finally {
+ if (cursor != null) cursor.close();
+ }
+ }
+
+ @Override
+ public int updateInTransaction(Uri uri, ContentValues values, String selection,
+ String[] selectionArgs, boolean callerIsSyncAdapter) {
+ int match = URI_MATCHER.match(uri);
+ final SQLiteDatabase db = mOpenHelper.getWritableDatabase();
+ if (match == LEGACY || match == LEGACY_ID) {
+ // Intercept and route to the correct table
+ Integer bookmark = values.getAsInteger(BookmarkColumns.BOOKMARK);
+ values.remove(BookmarkColumns.BOOKMARK);
+ if (bookmark == null || bookmark == 0) {
+ if (match == LEGACY) {
+ match = HISTORY;
+ } else {
+ match = HISTORY_ID;
+ }
+ } else {
+ if (match == LEGACY) {
+ match = BOOKMARKS;
+ } else {
+ match = BOOKMARKS_ID;
+ }
+ values.remove(BookmarkColumns.DATE);
+ values.remove(BookmarkColumns.VISITS);
+ values.remove(BookmarkColumns.USER_ENTERED);
+ }
+ }
+ switch (match) {
+ case BOOKMARKS_ID: {
+ selection = DatabaseUtils.concatenateWhere(selection,
+ TABLE_BOOKMARKS + "._id=?");
+ selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+ new String[] { Long.toString(ContentUris.parseId(uri)) });
+ // fall through
+ }
+ case BOOKMARKS: {
+ Object[] withAccount = getSelectionWithAccounts(uri, selection, selectionArgs);
+ selection = (String) withAccount[0];
+ selectionArgs = (String[]) withAccount[1];
+ int updated = updateBookmarksInTransaction(values, selection, selectionArgs,
+ callerIsSyncAdapter);
+ pruneImages();
+ return updated;
+ }
+
+ case HISTORY_ID: {
+ selection = DatabaseUtils.concatenateWhere(selection, TABLE_HISTORY + "._id=?");
+ selectionArgs = DatabaseUtils.appendSelectionArgs(selectionArgs,
+ new String[] { Long.toString(ContentUris.parseId(uri)) });
+ // fall through
+ }
+ case HISTORY: {
+ int updated = updateHistoryInTransaction(values, selection, selectionArgs);
+ pruneImages();
+ return updated;
+ }
+
+ case SYNCSTATE: {
+ return mSyncHelper.update(mDb, values,
+ appendAccountToSelection(uri, selection), selectionArgs);
+ }
+
+ case SYNCSTATE_ID: {
+ selection = appendAccountToSelection(uri, selection);
+ String selectionWithId =
+ (SyncStateContract.Columns._ID + "=" + ContentUris.parseId(uri) + " ")
+ + (selection == null ? "" : " AND (" + selection + ")");
+ return mSyncHelper.update(mDb, values,
+ selectionWithId, selectionArgs);
+ }
+
+ case IMAGES: {
+ String url = values.getAsString(Images.URL);
+ if (TextUtils.isEmpty(url)) {
+ throw new IllegalArgumentException("Images.URL is required");
+ }
+ int count = db.update(TABLE_IMAGES, values, Images.URL + "=?",
+ new String[] { url });
+ if (count == 0) {
+ db.insertOrThrow(TABLE_IMAGES, Images.FAVICON, values);
+ count = 1;
+ }
+ return count;
+ }
+
+ case SEARCHES: {
+ return db.update(TABLE_SEARCHES, values, selection, selectionArgs);
+ }
+ }
+ throw new UnsupportedOperationException("Unknown update URI " + uri);
+ }
+
+ /**
+ * Does a query to find the matching bookmarks and updates each one with the provided values.
+ */
+ int updateBookmarksInTransaction(ContentValues values, String selection,
+ String[] selectionArgs, boolean callerIsSyncAdapter) {
+ int count = 0;
+ final SQLiteDatabase db = mOpenHelper.getWritableDatabase();
+ Cursor cursor = db.query(TABLE_BOOKMARKS,
+ new String[] { Bookmarks._ID, Bookmarks.VERSION, Bookmarks.URL },
+ selection, selectionArgs, null, null, null);
+ try {
+ String[] args = new String[1];
+ // Mark the bookmark dirty if the caller isn't a sync adapter
+ if (!callerIsSyncAdapter) {
+ values.put(Bookmarks.DATE_MODIFIED, System.currentTimeMillis());
+ values.put(Bookmarks.DIRTY, 1);
+ }
+
+ boolean updatingUrl = values.containsKey(Bookmarks.URL);
+ String url = null;
+ if (updatingUrl) {
+ url = values.getAsString(Bookmarks.URL);
+ }
+ ContentValues imageValues = extractImageValues(values, url);
+
+ while (cursor.moveToNext()) {
+ args[0] = cursor.getString(0);
+ if (!callerIsSyncAdapter) {
+ // increase the local version for non-sync changes
+ values.put(Bookmarks.VERSION, cursor.getLong(1) + 1);
+ }
+ count += db.update(TABLE_BOOKMARKS, values, "_id=?", args);
+
+ // Update the images over in their table
+ if (imageValues != null) {
+ if (!updatingUrl) {
+ url = cursor.getString(2);
+ imageValues.put(Images.URL, url);
+ }
+
+ if (!TextUtils.isEmpty(url)) {
+ args[0] = url;
+ if (db.update(TABLE_IMAGES, imageValues, Images.URL + "=?", args) == 0) {
+ db.insert(TABLE_IMAGES, Images.FAVICON, imageValues);
+ }
+ }
+ }
+ }
+ } finally {
+ if (cursor != null) cursor.close();
+ }
+ return count;
+ }
+
+ /**
+ * Does a query to find the matching bookmarks and updates each one with the provided values.
+ */
+ int updateHistoryInTransaction(ContentValues values, String selection, String[] selectionArgs) {
+ int count = 0;
+ final SQLiteDatabase db = mOpenHelper.getWritableDatabase();
+ filterSearchClient(selectionArgs);
+ Cursor cursor = query(History.CONTENT_URI,
+ new String[] { History._ID, History.URL },
+ selection, selectionArgs, null);
+ try {
+ String[] args = new String[1];
+
+ boolean updatingUrl = values.containsKey(History.URL);
+ String url = null;
+ if (updatingUrl) {
+ url = filterSearchClient(values.getAsString(History.URL));
+ values.put(History.URL, url);
+ }
+ ContentValues imageValues = extractImageValues(values, url);
+
+ while (cursor.moveToNext()) {
+ args[0] = cursor.getString(0);
+ count += db.update(TABLE_HISTORY, values, "_id=?", args);
+
+ // Update the images over in their table
+ if (imageValues != null) {
+ if (!updatingUrl) {
+ url = cursor.getString(1);
+ imageValues.put(Images.URL, url);
+ }
+ args[0] = url;
+ if (db.update(TABLE_IMAGES, imageValues, Images.URL + "=?", args) == 0) {
+ db.insert(TABLE_IMAGES, Images.FAVICON, imageValues);
+ }
+ }
+ }
+ } finally {
+ if (cursor != null) cursor.close();
+ }
+ return count;
+ }
+
+ String appendAccountToSelection(Uri uri, String selection) {
+ final String accountName = uri.getQueryParameter(RawContacts.ACCOUNT_NAME);
+ final String accountType = uri.getQueryParameter(RawContacts.ACCOUNT_TYPE);
+
+ final boolean partialUri = TextUtils.isEmpty(accountName) ^ TextUtils.isEmpty(accountType);
+ if (partialUri) {
+ // Throw when either account is incomplete
+ throw new IllegalArgumentException(
+ "Must specify both or neither of ACCOUNT_NAME and ACCOUNT_TYPE for " + uri);
+ }
+
+ // Accounts are valid by only checking one parameter, since we've
+ // already ruled out partial accounts.
+ final boolean validAccount = !TextUtils.isEmpty(accountName);
+ if (validAccount) {
+ StringBuilder selectionSb = new StringBuilder(RawContacts.ACCOUNT_NAME + "="
+ + DatabaseUtils.sqlEscapeString(accountName) + " AND "
+ + RawContacts.ACCOUNT_TYPE + "="
+ + DatabaseUtils.sqlEscapeString(accountType));
+ if (!TextUtils.isEmpty(selection)) {
+ selectionSb.append(" AND (");
+ selectionSb.append(selection);
+ selectionSb.append(')');
+ }
+ return selectionSb.toString();
+ } else {
+ return selection;
+ }
+ }
+
+ ContentValues extractImageValues(ContentValues values, String url) {
+ ContentValues imageValues = null;
+ // favicon
+ if (values.containsKey(Bookmarks.FAVICON)) {
+ imageValues = new ContentValues();
+ imageValues.put(Images.FAVICON, values.getAsByteArray(Bookmarks.FAVICON));
+ values.remove(Bookmarks.FAVICON);
+ }
+
+ // thumbnail
+ if (values.containsKey(Bookmarks.THUMBNAIL)) {
+ if (imageValues == null) {
+ imageValues = new ContentValues();
+ }
+ imageValues.put(Images.THUMBNAIL, values.getAsByteArray(Bookmarks.THUMBNAIL));
+ values.remove(Bookmarks.THUMBNAIL);
+ }
+
+ // touch icon
+ if (values.containsKey(Bookmarks.TOUCH_ICON)) {
+ if (imageValues == null) {
+ imageValues = new ContentValues();
+ }
+ imageValues.put(Images.TOUCH_ICON, values.getAsByteArray(Bookmarks.TOUCH_ICON));
+ values.remove(Bookmarks.TOUCH_ICON);
+ }
+
+ if (imageValues != null) {
+ imageValues.put(Images.URL, url);
+ }
+ return imageValues;
+ }
+
+ void pruneImages() {
+ final SQLiteDatabase db = mOpenHelper.getWritableDatabase();
+ db.delete(TABLE_IMAGES, IMAGE_PRUNE, null);
+ }
+
+ static class SuggestionsCursor extends AbstractCursor {
+ private static final int ID_INDEX = 0;
+ private static final int URL_INDEX = 1;
+ private static final int TITLE_INDEX = 2;
+ // shared suggestion array index, make sure to match COLUMNS
+ private static final int SUGGEST_COLUMN_INTENT_ACTION_ID = 1;
+ private static final int SUGGEST_COLUMN_INTENT_DATA_ID = 2;
+ private static final int SUGGEST_COLUMN_TEXT_1_ID = 3;
+ private static final int SUGGEST_COLUMN_TEXT_2_TEXT_ID = 4;
+ private static final int SUGGEST_COLUMN_TEXT_2_URL_ID = 5;
+ private static final int SUGGEST_COLUMN_ICON_1_ID = 6;
+
+ // shared suggestion columns
+ private static final String[] COLUMNS = new String[] {
+ BaseColumns._ID,
+ SearchManager.SUGGEST_COLUMN_INTENT_ACTION,
+ SearchManager.SUGGEST_COLUMN_INTENT_DATA,
+ SearchManager.SUGGEST_COLUMN_TEXT_1,
+ SearchManager.SUGGEST_COLUMN_TEXT_2,
+ SearchManager.SUGGEST_COLUMN_TEXT_2_URL,
+ SearchManager.SUGGEST_COLUMN_ICON_1};
+
+ private Cursor mSource;
+
+ public SuggestionsCursor(Cursor cursor) {
+ mSource = cursor;
+ }
+
+ @Override
+ public String[] getColumnNames() {
+ return COLUMNS;
+ }
+
+ @Override
+ public String getString(int columnIndex) {
+ switch (columnIndex) {
+ case ID_INDEX:
+ return mSource.getString(columnIndex);
+ case SUGGEST_COLUMN_INTENT_ACTION_ID:
+ return Intent.ACTION_VIEW;
+ case SUGGEST_COLUMN_INTENT_DATA_ID:
+ case SUGGEST_COLUMN_TEXT_2_TEXT_ID:
+ case SUGGEST_COLUMN_TEXT_2_URL_ID:
+ return mSource.getString(URL_INDEX);
+ case SUGGEST_COLUMN_TEXT_1_ID:
+ return mSource.getString(TITLE_INDEX);
+ case SUGGEST_COLUMN_ICON_1_ID:
+ return Integer.toString(R.drawable.ic_bookmark_off_holo_dark);
+ }
+ return null;
+ }
+
+ @Override
+ public int getCount() {
+ return mSource.getCount();
+ }
+
+ @Override
+ public double getDouble(int column) {
+ throw new UnsupportedOperationException();
+ }
+
+ @Override
+ public float getFloat(int column) {
+ throw new UnsupportedOperationException();
+ }
+
+ @Override
+ public int getInt(int column) {
+ throw new UnsupportedOperationException();
+ }
+
+ @Override
+ public long getLong(int column) {
+ switch (column) {
+ case ID_INDEX:
+ return mSource.getLong(ID_INDEX);
+ }
+ throw new UnsupportedOperationException();
+ }
+
+ @Override
+ public short getShort(int column) {
+ throw new UnsupportedOperationException();
+ }
+
+ @Override
+ public boolean isNull(int column) {
+ return mSource.isNull(column);
+ }
+
+ @Override
+ public boolean onMove(int oldPosition, int newPosition) {
+ return mSource.moveToPosition(newPosition);
+ }
+ }
+}
diff --git a/src/com/android/browser/provider/SQLiteContentProvider.java b/src/com/android/browser/provider/SQLiteContentProvider.java
new file mode 100644
index 0000000..a50894a
--- /dev/null
+++ b/src/com/android/browser/provider/SQLiteContentProvider.java
@@ -0,0 +1,276 @@
+/*
+ * 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.browser.provider;
+
+import android.content.ContentProvider;
+import android.content.ContentProviderOperation;
+import android.content.ContentProviderResult;
+import android.content.ContentValues;
+import android.content.Context;
+import android.content.OperationApplicationException;
+import android.database.sqlite.SQLiteDatabase;
+import android.database.sqlite.SQLiteOpenHelper;
+import android.database.sqlite.SQLiteTransactionListener;
+import android.net.Uri;
+
+import java.util.ArrayList;
+
+/**
+ * General purpose {@link ContentProvider} base class that uses SQLiteDatabase for storage.
+ */
+public abstract class SQLiteContentProvider extends ContentProvider
+ implements SQLiteTransactionListener {
+
+ private static final String TAG = "SQLiteContentProvider";
+
+ private SQLiteOpenHelper mOpenHelper;
+ private volatile boolean mNotifyChange;
+ protected SQLiteDatabase mDb;
+
+ private final ThreadLocal<Boolean> mApplyingBatch = new ThreadLocal<Boolean>();
+ private static final int SLEEP_AFTER_YIELD_DELAY = 4000;
+
+ /**
+ * Maximum number of operations allowed in a batch between yield points.
+ */
+ private static final int MAX_OPERATIONS_PER_YIELD_POINT = 500;
+
+ @Override
+ public boolean onCreate() {
+ Context context = getContext();
+ mOpenHelper = getDatabaseHelper(context);
+ return true;
+ }
+
+ /**
+ * Returns a {@link SQLiteOpenHelper} that can open the database.
+ */
+ public abstract SQLiteOpenHelper getDatabaseHelper(Context context);
+
+ /**
+ * The equivalent of the {@link #insert} method, but invoked within a transaction.
+ */
+ public abstract Uri insertInTransaction(Uri uri, ContentValues values,
+ boolean callerIsSyncAdapter);
+
+ /**
+ * The equivalent of the {@link #update} method, but invoked within a transaction.
+ */
+ public abstract int updateInTransaction(Uri uri, ContentValues values, String selection,
+ String[] selectionArgs, boolean callerIsSyncAdapter);
+
+ /**
+ * The equivalent of the {@link #delete} method, but invoked within a transaction.
+ */
+ public abstract int deleteInTransaction(Uri uri, String selection, String[] selectionArgs,
+ boolean callerIsSyncAdapter);
+
+ /**
+ * Called when the provider needs to notify the system of a change.
+ * @param callerIsSyncAdapter true if the caller that caused the change was a sync adapter.
+ */
+ public abstract void notifyChange(boolean callerIsSyncAdapter);
+
+ public boolean isCallerSyncAdapter(Uri uri) {
+ return false;
+ }
+
+ public SQLiteOpenHelper getDatabaseHelper() {
+ return mOpenHelper;
+ }
+
+ private boolean applyingBatch() {
+ return mApplyingBatch.get() != null && mApplyingBatch.get();
+ }
+
+ @Override
+ public Uri insert(Uri uri, ContentValues values) {
+ Uri result = null;
+ boolean callerIsSyncAdapter = isCallerSyncAdapter(uri);
+ boolean applyingBatch = applyingBatch();
+ if (!applyingBatch) {
+ mDb = mOpenHelper.getWritableDatabase();
+ mDb.beginTransactionWithListener(this);
+ try {
+ result = insertInTransaction(uri, values, callerIsSyncAdapter);
+ if (result != null) {
+ mNotifyChange = true;
+ }
+ mDb.setTransactionSuccessful();
+ } finally {
+ mDb.endTransaction();
+ }
+
+ onEndTransaction(callerIsSyncAdapter);
+ } else {
+ result = insertInTransaction(uri, values, callerIsSyncAdapter);
+ if (result != null) {
+ mNotifyChange = true;
+ }
+ }
+ return result;
+ }
+
+ @Override
+ public int bulkInsert(Uri uri, ContentValues[] values) {
+ int numValues = values.length;
+ boolean callerIsSyncAdapter = isCallerSyncAdapter(uri);
+ mDb = mOpenHelper.getWritableDatabase();
+ mDb.beginTransactionWithListener(this);
+ try {
+ for (int i = 0; i < numValues; i++) {
+ Uri result = insertInTransaction(uri, values[i], callerIsSyncAdapter);
+ if (result != null) {
+ mNotifyChange = true;
+ }
+ mDb.yieldIfContendedSafely();
+ }
+ mDb.setTransactionSuccessful();
+ } finally {
+ mDb.endTransaction();
+ }
+
+ onEndTransaction(callerIsSyncAdapter);
+ return numValues;
+ }
+
+ @Override
+ public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs) {
+ int count = 0;
+ boolean callerIsSyncAdapter = isCallerSyncAdapter(uri);
+ boolean applyingBatch = applyingBatch();
+ if (!applyingBatch) {
+ mDb = mOpenHelper.getWritableDatabase();
+ mDb.beginTransactionWithListener(this);
+ try {
+ count = updateInTransaction(uri, values, selection, selectionArgs,
+ callerIsSyncAdapter);
+ if (count > 0) {
+ mNotifyChange = true;
+ }
+ mDb.setTransactionSuccessful();
+ } finally {
+ mDb.endTransaction();
+ }
+
+ onEndTransaction(callerIsSyncAdapter);
+ } else {
+ count = updateInTransaction(uri, values, selection, selectionArgs, callerIsSyncAdapter);
+ if (count > 0) {
+ mNotifyChange = true;
+ }
+ }
+
+ return count;
+ }
+
+ @Override
+ public int delete(Uri uri, String selection, String[] selectionArgs) {
+ int count = 0;
+ boolean callerIsSyncAdapter = isCallerSyncAdapter(uri);
+ boolean applyingBatch = applyingBatch();
+ if (!applyingBatch) {
+ mDb = mOpenHelper.getWritableDatabase();
+ mDb.beginTransactionWithListener(this);
+ try {
+ count = deleteInTransaction(uri, selection, selectionArgs, callerIsSyncAdapter);
+ if (count > 0) {
+ mNotifyChange = true;
+ }
+ mDb.setTransactionSuccessful();
+ } finally {
+ mDb.endTransaction();
+ }
+
+ onEndTransaction(callerIsSyncAdapter);
+ } else {
+ count = deleteInTransaction(uri, selection, selectionArgs, callerIsSyncAdapter);
+ if (count > 0) {
+ mNotifyChange = true;
+ }
+ }
+ return count;
+ }
+
+ @Override
+ public ContentProviderResult[] applyBatch(ArrayList<ContentProviderOperation> operations)
+ throws OperationApplicationException {
+ int ypCount = 0;
+ int opCount = 0;
+ boolean callerIsSyncAdapter = false;
+ mDb = mOpenHelper.getWritableDatabase();
+ mDb.beginTransactionWithListener(this);
+ try {
+ mApplyingBatch.set(true);
+ final int numOperations = operations.size();
+ final ContentProviderResult[] results = new ContentProviderResult[numOperations];
+ for (int i = 0; i < numOperations; i++) {
+ if (++opCount >= MAX_OPERATIONS_PER_YIELD_POINT) {
+ throw new OperationApplicationException(
+ "Too many content provider operations between yield points. "
+ + "The maximum number of operations per yield point is "
+ + MAX_OPERATIONS_PER_YIELD_POINT, ypCount);
+ }
+ final ContentProviderOperation operation = operations.get(i);
+ if (!callerIsSyncAdapter && isCallerSyncAdapter(operation.getUri())) {
+ callerIsSyncAdapter = true;
+ }
+ if (i > 0 && operation.isYieldAllowed()) {
+ opCount = 0;
+ if (mDb.yieldIfContendedSafely(SLEEP_AFTER_YIELD_DELAY)) {
+ ypCount++;
+ }
+ }
+ results[i] = operation.apply(this, results, i);
+ }
+ mDb.setTransactionSuccessful();
+ return results;
+ } finally {
+ mApplyingBatch.set(false);
+ mDb.endTransaction();
+ onEndTransaction(callerIsSyncAdapter);
+ }
+ }
+
+ @Override
+ public void onBegin() {
+ onBeginTransaction();
+ }
+
+ @Override
+ public void onCommit() {
+ beforeTransactionCommit();
+ }
+
+ @Override
+ public void onRollback() {
+ // not used
+ }
+
+ protected void onBeginTransaction() {
+ }
+
+ protected void beforeTransactionCommit() {
+ }
+
+ protected void onEndTransaction(boolean callerIsSyncAdapter) {
+ if (mNotifyChange) {
+ mNotifyChange = false;
+ notifyChange(callerIsSyncAdapter);
+ }
+ }
+}
diff --git a/src/com/android/browser/search/.DefaultSearchEngine.java.swp b/src/com/android/browser/search/.DefaultSearchEngine.java.swp
new file mode 100644
index 0000000..441153c
--- /dev/null
+++ b/src/com/android/browser/search/.DefaultSearchEngine.java.swp
Binary files differ
diff --git a/src/com/android/browser/search/SearchEngines.java b/src/com/android/browser/search/SearchEngines.java
index 62690e7..a6ba3de 100644
--- a/src/com/android/browser/search/SearchEngines.java
+++ b/src/com/android/browser/search/SearchEngines.java
@@ -61,7 +61,7 @@
return new OpenSearchSearchEngine(context, searchEngineInfo);
}
- private static SearchEngineInfo getSearchEngineInfo(Context context, String name) {
+ public static SearchEngineInfo getSearchEngineInfo(Context context, String name) {
try {
return new SearchEngineInfo(context, name);
} catch (IllegalArgumentException exception) {
diff --git a/src/com/android/browser/view/PieMenu.java b/src/com/android/browser/view/PieMenu.java
new file mode 100644
index 0000000..5185adb
--- /dev/null
+++ b/src/com/android/browser/view/PieMenu.java
@@ -0,0 +1,484 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser.view;
+
+import com.android.browser.R;
+
+import android.content.Context;
+import android.content.res.Resources;
+import android.graphics.Canvas;
+import android.graphics.Paint;
+import android.graphics.Path;
+import android.graphics.Point;
+import android.graphics.PointF;
+import android.graphics.Rect;
+import android.graphics.RectF;
+import android.util.AttributeSet;
+import android.view.MotionEvent;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.FrameLayout;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+
+public class PieMenu extends FrameLayout {
+
+ private static final int RADIUS_GAP = 10;
+
+ public interface PieController {
+ /**
+ * called before menu opens to customize menu
+ * returns if pie state has been changed
+ */
+ public boolean onOpen();
+ }
+ private Point mCenter;
+ private int mRadius;
+ private int mRadiusInc;
+ private int mSlop;
+
+ private boolean mOpen;
+ private Paint mPaint;
+ private Paint mSelectedPaint;
+ private PieController mController;
+
+ private Map<View, List<View>> mMenu;
+ private List<View> mStack;
+
+ private boolean mDirty;
+
+ /**
+ * @param context
+ * @param attrs
+ * @param defStyle
+ */
+ public PieMenu(Context context, AttributeSet attrs, int defStyle) {
+ super(context, attrs, defStyle);
+ init(context);
+ }
+
+ /**
+ * @param context
+ * @param attrs
+ */
+ public PieMenu(Context context, AttributeSet attrs) {
+ super(context, attrs);
+ init(context);
+ }
+
+ /**
+ * @param context
+ */
+ public PieMenu(Context context) {
+ super(context);
+ init(context);
+ }
+
+ private void init(Context ctx) {
+ this.setTag(new MenuTag(0));
+ mStack = new ArrayList<View>();
+ mStack.add(this);
+ Resources res = ctx.getResources();
+ mRadius = (int) res.getDimension(R.dimen.qc_radius);
+ mRadiusInc = (int) res.getDimension(R.dimen.qc_radius_inc);
+ mSlop = (int) res.getDimension(R.dimen.qc_slop);
+ mPaint = new Paint();
+ mPaint.setAntiAlias(true);
+ mPaint.setColor(res.getColor(R.color.qc_slice_normal));
+ mSelectedPaint = new Paint();
+ mSelectedPaint.setAntiAlias(true);
+ mSelectedPaint.setColor(res.getColor(R.color.qc_slice_active));
+ mOpen = false;
+ mMenu = new HashMap<View, List<View>>();
+ setWillNotDraw(false);
+ setDrawingCacheEnabled(false);
+ mCenter = new Point(0,0);
+ mDirty = true;
+ }
+
+ public void setController(PieController ctl) {
+ mController = ctl;
+ }
+
+ public void setRadius(int r) {
+ mRadius = r;
+ requestLayout();
+ }
+
+ public void setRadiusIncrement(int ri) {
+ mRadiusInc = ri;
+ requestLayout();
+ }
+
+ /**
+ * add a menu item to another item as a submenu
+ * @param item
+ * @param parent
+ */
+ public void addItem(View item, View parent) {
+ List<View> subs = mMenu.get(parent);
+ if (subs == null) {
+ subs = new ArrayList<View>();
+ mMenu.put(parent, subs);
+ }
+ subs.add(item);
+ MenuTag tag = new MenuTag(((MenuTag) parent.getTag()).level + 1);
+ item.setTag(tag);
+ }
+
+ public void addItem(View view) {
+ // add the item to the pie itself
+ addItem(view, this);
+ }
+
+ public void removeItem(View view) {
+ List<View> subs = mMenu.get(view);
+ mMenu.remove(view);
+ for (View p : mMenu.keySet()) {
+ List<View> sl = mMenu.get(p);
+ if (sl != null) {
+ sl.remove(view);
+ }
+ }
+ }
+
+ public void clearItems(View parent) {
+ List<View> subs = mMenu.remove(parent);
+ if (subs != null) {
+ for (View sub: subs) {
+ clearItems(sub);
+ }
+ }
+ }
+
+ public void clearItems() {
+ mMenu.clear();
+ }
+
+
+ public void show(boolean show) {
+ mOpen = show;
+ if (mOpen) {
+ if (mController != null) {
+ boolean changed = mController.onOpen();
+ }
+ mDirty = true;
+ }
+ if (!show) {
+ // hide sub items
+ mStack.clear();
+ mStack.add(this);
+ }
+ invalidate();
+ }
+
+ private void setCenter(int x, int y) {
+ if (x < mSlop) {
+ mCenter.x = 0;
+ } else {
+ mCenter.x = getWidth();
+ }
+ mCenter.y = y;
+ }
+
+ private boolean onTheLeft() {
+ return mCenter.x < mSlop;
+ }
+
+ @Override
+ protected void onDraw(Canvas canvas) {
+ if (mOpen) {
+ int radius = mRadius;
+ // start in the center for 0 level menu
+ float anchor = (float) Math.PI / 2;
+ PointF angles = new PointF();
+ int state = canvas.save();
+ if (onTheLeft()) {
+ // left handed
+ canvas.scale(-1, 1);
+ }
+ for (View parent : mStack) {
+ List<View> subs = mMenu.get(parent);
+ if (subs != null) {
+ setGeometry(anchor, subs.size(), angles);
+ }
+ anchor = drawSlices(canvas, subs, radius, angles.x, angles.y);
+ radius += mRadiusInc + RADIUS_GAP;
+ }
+ canvas.restoreToCount(state);
+ mDirty = false;
+ }
+ }
+
+ /**
+ * draw the set of slices
+ * @param canvas
+ * @param items
+ * @param radius
+ * @param start
+ * @param sweep
+ * @return the angle of the selected slice
+ */
+ private float drawSlices(Canvas canvas, List<View> items, int radius,
+ float start, float sweep) {
+ float angle = start + sweep / 2;
+ // gap between slices in degrees
+ float gap = 1f;
+ float newanchor = 0f;
+ for (View item : items) {
+ if (mDirty) {
+ item.measure(item.getLayoutParams().width,
+ item.getLayoutParams().height);
+ int w = item.getMeasuredWidth();
+ int h = item.getMeasuredHeight();
+ int x = (int) (radius * Math.sin(angle));
+ int y = mCenter.y - (int) (radius * Math.cos(angle)) - h / 2;
+ if (onTheLeft()) {
+ x = mCenter.x + x - w / 2;
+ } else {
+ x = mCenter.x - x - w / 2;
+ }
+ item.layout(x, y, x + w, y + h);
+ }
+ float itemstart = angle - sweep / 2;
+ int inner = radius - mRadiusInc / 2;
+ int outer = radius + mRadiusInc / 2;
+ Path slice = makeSlice(getDegrees(itemstart) - gap,
+ getDegrees(itemstart + sweep) + gap,
+ outer, inner, mCenter);
+ MenuTag tag = (MenuTag) item.getTag();
+ tag.start = itemstart;
+ tag.sweep = sweep;
+ tag.inner = inner;
+ tag.outer = outer;
+
+ Paint p = item.isPressed() ? mSelectedPaint : mPaint;
+ canvas.drawPath(slice, p);
+ int state = canvas.save();
+ if (onTheLeft()) {
+ canvas.scale(-1, 1);
+ }
+ canvas.translate(item.getX(), item.getY());
+ item.draw(canvas);
+ canvas.restoreToCount(state);
+ if (mStack.contains(item)) {
+ // item is anchor for sub menu
+ newanchor = angle;
+ }
+ angle += sweep;
+ }
+ return newanchor;
+ }
+
+ /**
+ * converts a
+ * @param angle from 0..PI to Android degrees (clockwise starting at 3 o'clock)
+ * @return skia angle
+ */
+ private float getDegrees(double angle) {
+ return (float) (270 - 180 * angle / Math.PI);
+ }
+
+ private Path makeSlice(float startangle, float endangle, int outerradius,
+ int innerradius, Point center) {
+ RectF bb = new RectF(center.x - outerradius, center.y - outerradius,
+ center.x + outerradius, center.y + outerradius);
+ RectF bbi = new RectF(center.x - innerradius, center.y - innerradius,
+ center.x + innerradius, center.y + innerradius);
+ Path path = new Path();
+ path.arcTo(bb, startangle, endangle - startangle, true);
+ path.arcTo(bbi, endangle, startangle - endangle);
+ path.close();
+ return path;
+ }
+
+ /**
+ * all angles are 0 .. MATH.PI where 0 points up, and rotate counterclockwise
+ * set the startangle and slice sweep in result
+ * @param anchorangle : angle at which the menu is anchored
+ * @param nslices
+ * @param result : x : start, y : sweep
+ */
+ private void setGeometry(float anchorangle, int nslices, PointF result) {
+ float span = (float) Math.min(anchorangle, Math.PI - anchorangle);
+ float sweep = 2 * span / (nslices + 1);
+ result.x = anchorangle - span + sweep / 2;
+ result.y = sweep;
+ }
+
+ // touch handling for pie
+
+ View mCurrentView;
+ Rect mHitRect = new Rect();
+
+ @Override
+ public boolean onTouchEvent(MotionEvent evt) {
+ float x = evt.getX();
+ float y = evt.getY();
+ int action = evt.getActionMasked();
+ int edges = evt.getEdgeFlags();
+ if (MotionEvent.ACTION_DOWN == action) {
+ if ((x > getWidth() - mSlop) || (x < mSlop)) {
+ setCenter((int) x, (int) y);
+ show(true);
+ return true;
+ }
+ } else if (MotionEvent.ACTION_UP == action) {
+ if (mOpen) {
+ View v = mCurrentView;
+ deselect();
+ if (v != null) {
+ v.performClick();
+ }
+ show(false);
+ return true;
+ }
+ } else if (MotionEvent.ACTION_CANCEL == action) {
+ if (mOpen) {
+ show(false);
+ }
+ deselect();
+ return false;
+ } else if (MotionEvent.ACTION_MOVE == action) {
+ PointF polar = getPolar(x, y);
+ if (polar.y > mRadius + 2 * mRadiusInc) {
+ show(false);
+ deselect();
+ evt.setAction(MotionEvent.ACTION_DOWN);
+ if (getParent() != null) {
+ ((ViewGroup) getParent()).dispatchTouchEvent(evt);
+ }
+ return false;
+ }
+ View v = findView(polar);
+ if (mCurrentView != v) {
+ onEnter(v);
+ invalidate();
+ }
+ }
+ // always re-dispatch event
+ return false;
+ }
+
+ /**
+ * enter a slice for a view
+ * updates model only
+ * @param view
+ */
+ private void onEnter(View view) {
+ // deselect
+ if (mCurrentView != null) {
+ if (getLevel(mCurrentView) >= getLevel(view)) {
+ mCurrentView.setPressed(false);
+ }
+ }
+ if (view != null) {
+ // clear up stack
+ MenuTag tag = (MenuTag) view.getTag();
+ int i = mStack.size() - 1;
+ while (i > 0) {
+ View v = mStack.get(i);
+ if (((MenuTag) v.getTag()).level >= tag.level) {
+ v.setPressed(false);
+ mStack.remove(i);
+ } else {
+ break;
+ }
+ i--;
+ }
+ List<View> items = mMenu.get(view);
+ if (items != null) {
+ mStack.add(view);
+ mDirty = true;
+ }
+ view.setPressed(true);
+ }
+ mCurrentView = view;
+ }
+
+ private void deselect() {
+ if (mCurrentView != null) {
+ mCurrentView.setPressed(false);
+ }
+ mCurrentView = null;
+ }
+
+ private int getLevel(View v) {
+ if (v == null) return -1;
+ return ((MenuTag) v.getTag()).level;
+ }
+
+ private PointF getPolar(float x, float y) {
+ PointF res = new PointF();
+ // get angle and radius from x/y
+ res.x = (float) Math.PI / 2;
+ x = mCenter.x - x;
+ if (mCenter.x < mSlop) {
+ x = -x;
+ }
+ y = mCenter.y - y;
+ res.y = (float) Math.sqrt(x * x + y * y);
+ if (y > 0) {
+ res.x = (float) Math.asin(x / res.y);
+ } else if (y < 0) {
+ res.x = (float) (Math.PI - Math.asin(x / res.y ));
+ }
+ return res;
+ }
+
+ /**
+ *
+ * @param polar x: angle, y: dist
+ * @return
+ */
+ private View findView(PointF polar) {
+ // find the matching item:
+ for (View parent : mStack) {
+ List<View> subs = mMenu.get(parent);
+ if (subs != null) {
+ for (View item : subs) {
+ MenuTag tag = (MenuTag) item.getTag();
+ if ((tag.inner < polar.y)
+ && (tag.outer > polar.y)
+ && (tag.start < polar.x)
+ && (tag.start + tag.sweep > polar.x)) {
+ return item;
+ }
+ }
+ }
+ }
+ return null;
+ }
+
+ class MenuTag {
+
+ int level;
+ float start;
+ float sweep;
+ int inner;
+ int outer;
+
+ public MenuTag(int l) {
+ level = l;
+ }
+
+ }
+
+}
diff --git a/src/com/android/browser/widget/BookmarkThumbnailWidgetProvider.java b/src/com/android/browser/widget/BookmarkThumbnailWidgetProvider.java
new file mode 100644
index 0000000..b991abd
--- /dev/null
+++ b/src/com/android/browser/widget/BookmarkThumbnailWidgetProvider.java
@@ -0,0 +1,110 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser.widget;
+
+import com.android.browser.BrowserActivity;
+import com.android.browser.R;
+
+import android.app.PendingIntent;
+import android.appwidget.AppWidgetManager;
+import android.appwidget.AppWidgetProvider;
+import android.content.ComponentName;
+import android.content.Context;
+import android.content.Intent;
+import android.net.Uri;
+import android.widget.RemoteViews;
+
+/**
+ * Widget that shows a preview of the user's bookmarks.
+ */
+public class BookmarkThumbnailWidgetProvider extends AppWidgetProvider {
+ static final String ACTION_BOOKMARK_APPWIDGET_UPDATE =
+ "com.android.browser.BOOKMARK_APPWIDGET_UPDATE";
+
+ /**
+ * {@inheritDoc}
+ */
+ @Override
+ public void onReceive(Context context, Intent intent) {
+ // Handle bookmark-specific updates ourselves because they might be
+ // coming in without extras, which AppWidgetProvider then blocks.
+ final String action = intent.getAction();
+ if (ACTION_BOOKMARK_APPWIDGET_UPDATE.equals(action)) {
+ AppWidgetManager appWidgetManager = AppWidgetManager.getInstance(context);
+ performUpdate(context, appWidgetManager,
+ appWidgetManager.getAppWidgetIds(getComponentName(context)));
+ } else {
+ super.onReceive(context, intent);
+ }
+ }
+
+ @Override
+ public void onUpdate(Context context, AppWidgetManager mngr, int[] ids) {
+ performUpdate(context, mngr, ids);
+ }
+
+ @Override
+ public void onEnabled(Context context) {
+ // Start the backing service
+ context.startService(new Intent(context, BookmarkThumbnailWidgetService.class));
+ }
+
+ @Override
+ public void onDisabled(Context context) {
+ // Stop the backing service
+ context.stopService(new Intent(context, BookmarkThumbnailWidgetService.class));
+ }
+
+ @Override
+ public void onDeleted(Context context, int[] appWidgetIds) {
+ super.onDeleted(context, appWidgetIds);
+ context.startService(new Intent(BookmarkThumbnailWidgetService.ACTION_REMOVE_FACTORIES,
+ null, context, BookmarkThumbnailWidgetService.class)
+ .putExtra(AppWidgetManager.EXTRA_APPWIDGET_IDS, appWidgetIds));
+ }
+
+ private void performUpdate(Context context,
+ AppWidgetManager appWidgetManager, int[] appWidgetIds) {
+ PendingIntent launchBrowser = PendingIntent.getActivity(context, 0,
+ new Intent(BrowserActivity.ACTION_SHOW_BROWSER, null, context,
+ BrowserActivity.class),
+ PendingIntent.FLAG_UPDATE_CURRENT);
+ for (int appWidgetId : appWidgetIds) {
+ Intent updateIntent = new Intent(context, BookmarkThumbnailWidgetService.class);
+ updateIntent.putExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, appWidgetId);
+ updateIntent.setData(Uri.parse(updateIntent.toUri(Intent.URI_INTENT_SCHEME)));
+ RemoteViews views = new RemoteViews(context.getPackageName(),
+ R.layout.bookmarkthumbnailwidget);
+ views.setOnClickPendingIntent(R.id.app_shortcut, launchBrowser);
+ views.setRemoteAdapter(appWidgetId, R.id.bookmarks_list, updateIntent);
+ appWidgetManager.notifyAppWidgetViewDataChanged(appWidgetId, R.id.bookmarks_list);
+ Intent ic = new Intent(context, BookmarkThumbnailWidgetService.class);
+ views.setPendingIntentTemplate(R.id.bookmarks_list,
+ PendingIntent.getService(context, 0, ic,
+ PendingIntent.FLAG_UPDATE_CURRENT));
+ appWidgetManager.updateAppWidget(appWidgetId, views);
+ }
+ }
+
+ /**
+ * Build {@link ComponentName} describing this specific
+ * {@link AppWidgetProvider}
+ */
+ static ComponentName getComponentName(Context context) {
+ return new ComponentName(context, BookmarkThumbnailWidgetProvider.class);
+ }
+}
diff --git a/src/com/android/browser/widget/BookmarkThumbnailWidgetService.java b/src/com/android/browser/widget/BookmarkThumbnailWidgetService.java
new file mode 100644
index 0000000..e525159
--- /dev/null
+++ b/src/com/android/browser/widget/BookmarkThumbnailWidgetService.java
@@ -0,0 +1,491 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.browser.widget;
+
+import com.android.browser.BrowserActivity;
+import com.android.browser.BrowserBookmarksPage;
+import com.android.browser.R;
+
+import android.appwidget.AppWidgetManager;
+import android.content.ContentUris;
+import android.content.Context;
+import android.content.Intent;
+import android.content.SharedPreferences;
+import android.content.SharedPreferences.OnSharedPreferenceChangeListener;
+import android.database.ContentObserver;
+import android.database.Cursor;
+import android.graphics.Bitmap;
+import android.graphics.Bitmap.Config;
+import android.graphics.BitmapFactory;
+import android.graphics.BitmapFactory.Options;
+import android.net.Uri;
+import android.os.AsyncTask;
+import android.os.Handler;
+import android.preference.PreferenceManager;
+import android.provider.BrowserContract;
+import android.provider.BrowserContract.Bookmarks;
+import android.text.TextUtils;
+import android.util.Log;
+import android.widget.RemoteViews;
+import android.widget.RemoteViewsService;
+
+import java.util.ArrayList;
+import java.util.HashMap;
+import java.util.List;
+import java.util.Map;
+import java.util.Stack;
+
+public class BookmarkThumbnailWidgetService extends RemoteViewsService {
+
+ static final String TAG = "BookmarkThumbnailWidgetService";
+ static final boolean USE_FOLDERS = true;
+
+ static final String ACTION_REMOVE_FACTORIES
+ = "com.android.browser.widget.REMOVE_FACTORIES";
+ static final String ACTION_CHANGE_FOLDER
+ = "com.android.browser.widget.CHANGE_FOLDER";
+
+ private static final String[] PROJECTION = new String[] {
+ BrowserContract.Bookmarks._ID,
+ BrowserContract.Bookmarks.TITLE,
+ BrowserContract.Bookmarks.URL,
+ BrowserContract.Bookmarks.FAVICON,
+ BrowserContract.Bookmarks.IS_FOLDER,
+ BrowserContract.Bookmarks.TOUCH_ICON,
+ BrowserContract.Bookmarks.POSITION, /* needed for order by */
+ BrowserContract.Bookmarks.THUMBNAIL};
+ private static final int BOOKMARK_INDEX_ID = 0;
+ private static final int BOOKMARK_INDEX_TITLE = 1;
+ private static final int BOOKMARK_INDEX_URL = 2;
+ private static final int BOOKMARK_INDEX_FAVICON = 3;
+ private static final int BOOKMARK_INDEX_IS_FOLDER = 4;
+ private static final int BOOKMARK_INDEX_TOUCH_ICON = 5;
+ private static final int BOOKMARK_INDEX_THUMBNAIL = 7;
+
+ // The service will likely be destroyed at any time, so we need to keep references to the
+ // factories across services connections.
+ private static final Map<Integer, BookmarkFactory> mFactories =
+ new HashMap<Integer, BookmarkFactory>();
+ private Handler mUiHandler;
+ private BookmarksObserver mBookmarksObserver;
+
+ @Override
+ public void onCreate() {
+ super.onCreate();
+ mUiHandler = new Handler();
+ mBookmarksObserver = new BookmarksObserver(mUiHandler);
+ getContentResolver().registerContentObserver(
+ BrowserContract.Bookmarks.CONTENT_URI, true, mBookmarksObserver);
+ }
+
+ @Override
+ public int onStartCommand(Intent intent, int flags, int startId) {
+ String action = intent.getAction();
+ if (Intent.ACTION_VIEW.equals(action)) {
+ if (intent.getData() == null) {
+ startActivity(new Intent(BrowserActivity.ACTION_SHOW_BROWSER, null,
+ this, BrowserActivity.class)
+ .addFlags(Intent.FLAG_ACTIVITY_NEW_TASK));
+ } else {
+ Intent view = new Intent(intent);
+ view.setComponent(null);
+ startActivity(view);
+ }
+ } else if (ACTION_REMOVE_FACTORIES.equals(action)) {
+ int[] ids = intent.getIntArrayExtra(AppWidgetManager.EXTRA_APPWIDGET_IDS);
+ if (ids != null) {
+ for (int id : ids) {
+ BookmarkFactory bf = mFactories.remove(id);
+ if (bf != null) {
+ // Workaround a known framework bug
+ // onDestroy is currently never called
+ bf.onDestroy();
+ }
+ }
+ }
+ } else if (ACTION_CHANGE_FOLDER.equals(action)) {
+ int widgetId = intent.getIntExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, -1);
+ long folderId = intent.getLongExtra(Bookmarks._ID, -1);
+ BookmarkFactory fac = mFactories.get(widgetId);
+ if (fac != null && folderId >= 0) {
+ fac.changeFolder(folderId);
+ } else {
+ // This a workaround to the issue when the Browser process crashes, after which
+ // mFactories is not populated (due to onBind() not being called). Calling
+ // notifyDataSetChanged() will trigger a connection to be made.
+ AppWidgetManager.getInstance(getApplicationContext())
+ .notifyAppWidgetViewDataChanged(widgetId, R.id.bookmarks_list);
+ }
+ }
+ return START_STICKY;
+ }
+
+ @Override
+ public void onDestroy() {
+ super.onDestroy();
+ getContentResolver().unregisterContentObserver(mBookmarksObserver);
+ }
+
+ private class BookmarksObserver extends ContentObserver {
+ public BookmarksObserver(Handler handler) {
+ super(handler);
+ }
+
+ @Override
+ public void onChange(boolean selfChange) {
+ super.onChange(selfChange);
+
+ // Update all the bookmark widgets
+ if (mFactories != null) {
+ for (BookmarkFactory fac : mFactories.values()) {
+ fac.loadData();
+ }
+ }
+ }
+ }
+
+ @Override
+ public RemoteViewsFactory onGetViewFactory(Intent intent) {
+ int widgetId = intent.getIntExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, -1);
+ if (widgetId < 0) {
+ Log.w(TAG, "Missing EXTRA_APPWIDGET_ID!");
+ return null;
+ } else {
+ BookmarkFactory fac = mFactories.get(widgetId);
+ if (fac == null) {
+ fac = new BookmarkFactory(getApplicationContext(), widgetId);
+ }
+ mFactories.put(widgetId, fac);
+ return fac;
+ }
+ }
+
+ private static class Breadcrumb {
+ long mId;
+ String mTitle;
+ public Breadcrumb(long id, String title) {
+ mId = id;
+ mTitle = title;
+ }
+ }
+
+ static class BookmarkFactory implements RemoteViewsService.RemoteViewsFactory,
+ OnSharedPreferenceChangeListener {
+ private List<RenderResult> mBookmarks;
+ private Context mContext;
+ private int mWidgetId;
+ private String mAccountType;
+ private String mAccountName;
+ private Stack<Breadcrumb> mBreadcrumbs;
+ private LoadBookmarksTask mLoadTask;
+
+ public BookmarkFactory(Context context, int widgetId) {
+ mBreadcrumbs = new Stack<Breadcrumb>();
+ mContext = context;
+ mWidgetId = widgetId;
+ }
+
+ void changeFolder(long folderId) {
+ if (mBookmarks == null) return;
+
+ if (!mBreadcrumbs.empty() && mBreadcrumbs.peek().mId == folderId) {
+ mBreadcrumbs.pop();
+ loadData();
+ return;
+ }
+
+ for (RenderResult res : mBookmarks) {
+ if (res.mId == folderId) {
+ mBreadcrumbs.push(new Breadcrumb(res.mId, res.mTitle));
+ loadData();
+ break;
+ }
+ }
+ }
+
+ @Override
+ public int getCount() {
+ if (mBookmarks == null)
+ return 0;
+ return mBookmarks.size();
+ }
+
+ @Override
+ public long getItemId(int position) {
+ return position;
+ }
+
+ @Override
+ public RemoteViews getLoadingView() {
+ return null;
+ }
+
+ @Override
+ public RemoteViews getViewAt(int position) {
+ if (position < 0 || position >= getCount()) {
+ return null;
+ }
+
+ RenderResult res = mBookmarks.get(position);
+ Breadcrumb folder = mBreadcrumbs.empty() ? null : mBreadcrumbs.peek();
+
+ RemoteViews views = new RemoteViews(
+ mContext.getPackageName(), R.layout.bookmarkthumbnailwidget_item);
+ Intent fillin;
+ if (res.mIsFolder) {
+ long nfi = res.mId;
+ fillin = new Intent(ACTION_CHANGE_FOLDER, null,
+ mContext, BookmarkThumbnailWidgetService.class)
+ .putExtra(AppWidgetManager.EXTRA_APPWIDGET_ID, mWidgetId)
+ .putExtra(Bookmarks._ID, nfi);
+ } else {
+ fillin = new Intent(Intent.ACTION_VIEW)
+ .addCategory(Intent.CATEGORY_BROWSABLE);
+ if (!TextUtils.isEmpty(res.mUrl)) {
+ fillin.setData(Uri.parse(res.mUrl));
+ }
+ }
+ views.setOnClickFillInIntent(R.id.list_item, fillin);
+ // Set the title of the bookmark. Use the url as a backup.
+ String displayTitle = res.mTitle;
+ if (TextUtils.isEmpty(displayTitle)) {
+ // The browser always requires a title for bookmarks, but jic...
+ displayTitle = res.mUrl;
+ }
+ views.setTextViewText(R.id.label, displayTitle);
+ if (res.mIsFolder) {
+ if (folder != null && res.mId == folder.mId) {
+ views.setImageViewResource(R.id.thumb, R.drawable.thumb_bookmark_widget_folder_back_holo);
+ } else {
+ views.setImageViewResource(R.id.thumb, R.drawable.thumb_bookmark_widget_folder_holo);
+ }
+ views.setImageViewResource(R.id.favicon, R.drawable.ic_bookmark_widget_bookmark_holo_dark);
+ views.setDrawableParameters(R.id.thumb, true, 0, -1, null, -1);
+ } else {
+ views.setDrawableParameters(R.id.thumb, true, 255, -1, null, -1);
+ if (res.mThumbnail != null) {
+ views.setImageViewBitmap(R.id.thumb, res.mThumbnail);
+ } else {
+ views.setImageViewResource(R.id.thumb,
+ R.drawable.browser_thumbnail);
+ }
+ if (res.mIcon != null) {
+ views.setImageViewBitmap(R.id.favicon, res.mIcon);
+ } else {
+ views.setImageViewResource(R.id.favicon,
+ R.drawable.app_web_browser_sm);
+ }
+ }
+ return views;
+ }
+
+ @Override
+ public int getViewTypeCount() {
+ return 1;
+ }
+
+ @Override
+ public boolean hasStableIds() {
+ return false;
+ }
+
+ @Override
+ public void onCreate() {
+ SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(mContext);
+ mAccountType = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE, null);
+ mAccountName = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, null);
+ prefs.registerOnSharedPreferenceChangeListener(this);
+ loadData();
+ }
+
+ @Override
+ public void onDestroy() {
+ SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(mContext);
+ prefs.unregisterOnSharedPreferenceChangeListener(this);
+
+ // Workaround known framework bug
+ // This class currently leaks, so free as much memory as we can
+ recycleBitmaps();
+ mBookmarks.clear();
+ mBreadcrumbs.clear();
+ if (mLoadTask != null) {
+ mLoadTask.cancel(false);
+ mLoadTask = null;
+ }
+ }
+
+ @Override
+ public void onDataSetChanged() {
+ }
+
+ void loadData() {
+ if (mLoadTask != null) {
+ mLoadTask.cancel(false);
+ }
+ mLoadTask = new LoadBookmarksTask();
+ mLoadTask.execute();
+ }
+
+ class LoadBookmarksTask extends AsyncTask<Void, Void, List<RenderResult>> {
+ private Breadcrumb mFolder;
+
+ @Override
+ protected void onPreExecute() {
+ mFolder = mBreadcrumbs.empty() ? null : mBreadcrumbs.peek();
+ }
+
+ @Override
+ protected List<RenderResult> doInBackground(Void... params) {
+ return loadBookmarks(mFolder);
+ }
+
+ @Override
+ protected void onPostExecute(List<RenderResult> result) {
+ if (!isCancelled() && result != null) {
+ recycleBitmaps();
+ mBookmarks = result;
+ AppWidgetManager.getInstance(mContext)
+ .notifyAppWidgetViewDataChanged(mWidgetId, R.id.bookmarks_list);
+ }
+ }
+ }
+
+ List<RenderResult> loadBookmarks(Breadcrumb folder) {
+ String where = null;
+ Uri uri;
+ if (USE_FOLDERS) {
+ uri = BrowserContract.Bookmarks.CONTENT_URI_DEFAULT_FOLDER;
+ if (folder != null) {
+ uri = ContentUris.withAppendedId(uri, folder.mId);
+ }
+ } else {
+ uri = BrowserContract.Bookmarks.CONTENT_URI;
+ where = Bookmarks.IS_FOLDER + " == 0";
+ }
+ uri = uri.buildUpon()
+ .appendQueryParameter(Bookmarks.PARAM_ACCOUNT_TYPE, mAccountType)
+ .appendQueryParameter(Bookmarks.PARAM_ACCOUNT_NAME, mAccountName)
+ .build();
+ Cursor c = null;
+ try {
+ c = mContext.getContentResolver().query(uri, PROJECTION,
+ where, null, null);
+ if (c != null) {
+ ArrayList<RenderResult> bookmarks
+ = new ArrayList<RenderResult>(c.getCount() + 1);
+ if (folder != null) {
+ RenderResult res = new RenderResult(
+ folder.mId, folder.mTitle, null);
+ res.mIsFolder = true;
+ bookmarks.add(res);
+ }
+ while (c.moveToNext()) {
+ long id = c.getLong(BOOKMARK_INDEX_ID);
+ String title = c.getString(BOOKMARK_INDEX_TITLE);
+ String url = c.getString(BOOKMARK_INDEX_URL);
+ RenderResult res = new RenderResult(id, title, url);
+ res.mIsFolder = c.getInt(BOOKMARK_INDEX_IS_FOLDER) != 0;
+ if (!res.mIsFolder) {
+ // RemoteViews require a valid bitmap config
+ Options options = new Options();
+ options.inPreferredConfig = Config.ARGB_8888;
+ Bitmap thumbnail = null, favicon = null;
+ byte[] blob = c.getBlob(BOOKMARK_INDEX_THUMBNAIL);
+ if (blob != null && blob.length > 0) {
+ thumbnail = BitmapFactory.decodeByteArray(
+ blob, 0, blob.length, options);
+ }
+ blob = c.getBlob(BOOKMARK_INDEX_FAVICON);
+ if (blob != null && blob.length > 0) {
+ favicon = BitmapFactory.decodeByteArray(
+ blob, 0, blob.length, options);
+ }
+ res.mThumbnail = thumbnail;
+ res.mIcon = favicon;
+ }
+ bookmarks.add(res);
+ }
+ if (bookmarks.size() == 0) {
+ RenderResult res = new RenderResult(0, "", "");
+ Bitmap thumbnail = BitmapFactory.decodeResource(
+ mContext.getResources(),
+ R.drawable.thumbnail_bookmarks_widget_no_bookmark_holo);
+ Bitmap favicon = Bitmap.createBitmap(1, 1, Config.ALPHA_8);
+ res.mThumbnail = thumbnail;
+ res.mIcon = favicon;
+ for (int i = 0; i < 6; i++) {
+ bookmarks.add(res);
+ }
+ }
+ return bookmarks;
+ }
+ } catch (IllegalStateException e) {
+ Log.e(TAG, "update bookmark widget", e);
+ } finally {
+ if (c != null) {
+ c.close();
+ }
+ }
+ return null;
+ }
+
+ private void recycleBitmaps() {
+ // Do a bit of house cleaning for the system
+ if (mBookmarks != null) {
+ for (RenderResult res : mBookmarks) {
+ if (res.mThumbnail != null) {
+ res.mThumbnail.recycle();
+ res.mThumbnail = null;
+ }
+ }
+ }
+ }
+
+ @Override
+ public void onSharedPreferenceChanged(
+ SharedPreferences prefs, String key) {
+ if (BrowserBookmarksPage.PREF_ACCOUNT_TYPE.equals(key)) {
+ mAccountType = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_TYPE, null);
+ mBreadcrumbs.clear();
+ loadData();
+ }
+ if (BrowserBookmarksPage.PREF_ACCOUNT_NAME.equals(key)) {
+ mAccountName = prefs.getString(BrowserBookmarksPage.PREF_ACCOUNT_NAME, null);
+ mBreadcrumbs.clear();
+ loadData();
+ }
+ }
+ }
+
+ // Class containing the rendering information for a specific bookmark.
+ private static class RenderResult {
+ final String mTitle;
+ final String mUrl;
+ Bitmap mThumbnail;
+ Bitmap mIcon;
+ boolean mIsFolder;
+ long mId;
+
+ RenderResult(long id, String title, String url) {
+ mId = id;
+ mTitle = title;
+ mUrl = url;
+ }
+
+ }
+
+}
diff --git a/src/com/android/browser/widget/BookmarkWidgetProvider.java b/src/com/android/browser/widget/BookmarkWidgetProvider.java
deleted file mode 100644
index 62b48c0..0000000
--- a/src/com/android/browser/widget/BookmarkWidgetProvider.java
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.browser.widget;
-
-import android.app.PendingIntent;
-import android.appwidget.AppWidgetManager;
-import android.appwidget.AppWidgetProvider;
-import android.content.Context;
-import android.content.Intent;
-import android.util.Log;
-
-/**
- * Widget that shows a preview of the user's bookmarks.
- */
-public class BookmarkWidgetProvider extends AppWidgetProvider {
-
- static final String TAG = "BookmarkWidgetProvider";
-
- @Override
- public void onUpdate(Context context, AppWidgetManager mngr, int[] ids) {
- context.startService(new Intent(BookmarkWidgetService.UPDATE, null,
- context, BookmarkWidgetService.class));
- }
-
- @Override
- public void onEnabled(Context context) {
- context.startService(new Intent(context, BookmarkWidgetService.class));
- }
-
- @Override
- public void onDisabled(Context context) {
- context.stopService(new Intent(context, BookmarkWidgetService.class));
- }
-}
-
diff --git a/src/com/android/browser/widget/BookmarkWidgetService.java b/src/com/android/browser/widget/BookmarkWidgetService.java
deleted file mode 100644
index 1fd9163..0000000
--- a/src/com/android/browser/widget/BookmarkWidgetService.java
+++ /dev/null
@@ -1,385 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.browser.widget;
-
-import android.app.PendingIntent;
-import android.app.Service;
-import android.appwidget.AppWidgetManager;
-import android.content.ComponentName;
-import android.content.Context;
-import android.content.Intent;
-import android.content.ServiceConnection;
-import android.database.Cursor;
-import android.graphics.Bitmap;
-import android.graphics.BitmapFactory;
-import android.os.Handler;
-import android.os.IBinder;
-import android.os.Message;
-import android.os.ParcelFileDescriptor;
-import android.provider.Browser;
-import android.provider.Browser.BookmarkColumns;
-import android.service.urlrenderer.UrlRenderer;
-import android.service.urlrenderer.UrlRendererService;
-import android.util.Log;
-import android.view.View;
-import android.widget.RemoteViews;
-
-import com.android.browser.R;
-
-import java.io.InputStream;
-import java.io.IOException;
-import java.util.ArrayList;
-import java.util.HashMap;
-
-public class BookmarkWidgetService extends Service
- implements UrlRenderer.Callback {
-
- private static final String TAG = "BookmarkWidgetService";
-
- /** Force the bookmarks to be re-renderer. */
- public static final String UPDATE = "com.android.browser.widget.UPDATE";
-
- /** Change the widget to the next bookmark. */
- private static final String NEXT = "com.android.browser.widget.NEXT";
-
- /** Change the widget to the previous bookmark. */
- private static final String PREV = "com.android.browser.widget.PREV";
-
- /** Id of the current item displayed in the widget. */
- private static final String EXTRA_ID =
- "com.android.browser.widget.extra.ID";
-
- // XXX: Remove these magic numbers once the dimensions of the widget can be
- // queried.
- private static final int WIDTH = 306;
- private static final int HEIGHT = 386;
-
- // Limit the number of connection attempts.
- private static final int MAX_SERVICE_RETRY_COUNT = 5;
-
- // No id specified.
- private static final int NO_ID = -1;
-
- private static final int MSG_UPDATE = 0;
- private final Handler mHandler = new Handler() {
- @Override
- public void handleMessage(Message msg) {
- switch (msg.what) {
- case MSG_UPDATE:
- if (mRenderer != null) {
- queryCursorAndRender();
- } else {
- if (++mServiceRetryCount <= MAX_SERVICE_RETRY_COUNT) {
- // Service is not connected, try again in a second.
- mHandler.sendEmptyMessageDelayed(MSG_UPDATE, 1000);
- }
- }
- break;
- default:
- break;
- }
- }
- };
-
- private final ServiceConnection mConnection = new ServiceConnection() {
- public void onServiceConnected(ComponentName className,
- IBinder service) {
- mRenderer = new UrlRenderer(service);
- }
-
- public void onServiceDisconnected(ComponentName className) {
- mRenderer = null;
- }
- };
-
- // Id -> information map storing db ids and their result.
- private final HashMap<Integer, RenderResult> mIdsToResults =
- new HashMap<Integer, RenderResult>();
-
- // List of ids in order
- private final ArrayList<Integer> mIdList = new ArrayList<Integer>();
-
- // Map of urls to ids for when a url is complete.
- private final HashMap<String, Integer> mUrlsToIds =
- new HashMap<String, Integer>();
-
- // The current id used by the widget during an update.
- private int mCurrentId = NO_ID;
- // Class that contacts the service on the phone to render bookmarks.
- private UrlRenderer mRenderer;
- // Number of service retries. Stop trying to connect after
- // MAX_SERVICE_RETRY_COUNT
- private int mServiceRetryCount;
-
- @Override
- public void onCreate() {
- bindService(new Intent(UrlRendererService.SERVICE_INTERFACE),
- mConnection, Context.BIND_AUTO_CREATE);
- }
-
- @Override
- public void onDestroy() {
- unbindService(mConnection);
- }
-
- @Override
- public android.os.IBinder onBind(Intent intent) {
- return null;
- }
-
- @Override
- public int onStartCommand(Intent intent, int flags, int startId) {
- final String action = intent.getAction();
- if (UPDATE.equals(action)) {
- mHandler.sendEmptyMessage(MSG_UPDATE);
- } else if (PREV.equals(action) && mIdList.size() > 1) {
- int prev = getPreviousId(intent);
- if (prev == NO_ID) {
- Log.d(TAG, "Could not determine previous id");
- return START_NOT_STICKY;
- }
- RenderResult res = mIdsToResults.get(prev);
- if (res != null) {
- updateWidget(res);
- }
- } else if (NEXT.equals(action) && mIdList.size() > 1) {
- int next = getNextId(intent);
- if (next == NO_ID) {
- Log.d(TAG, "Could not determine next id");
- return START_NOT_STICKY;
- }
- RenderResult res = mIdsToResults.get(next);
- if (res != null) {
- updateWidget(res);
- }
- }
- return START_STICKY;
- }
-
- private int getPreviousId(Intent intent) {
- int listSize = mIdList.size();
- // If the list contains 1 or fewer entries, return NO_ID so that the
- // widget does not update.
- if (listSize <= 1) {
- return NO_ID;
- }
-
- int curr = intent.getIntExtra(EXTRA_ID, NO_ID);
- if (curr == NO_ID) {
- return NO_ID;
- }
-
- // Check if the current id is the beginning of the list so we can skip
- // iterating through.
- if (mIdList.get(0) == curr) {
- return mIdList.get(listSize - 1);
- }
-
- // Search for the current id and remember the previous id.
- int prev = NO_ID;
- for (int id : mIdList) {
- if (id == curr) {
- break;
- }
- prev = id;
- }
- return prev;
- }
-
- private int getNextId(Intent intent) {
- int listSize = mIdList.size();
- // If the list contains 1 or fewer entries, return NO_ID so that the
- // widget does not update.
- if (listSize <= 1) {
- return NO_ID;
- }
-
- int curr = intent.getIntExtra(EXTRA_ID, NO_ID);
- if (curr == NO_ID) {
- return NO_ID;
- }
-
- // Check if the current id is at the end of the list so we can skip
- // iterating through.
- if (mIdList.get(listSize - 1) == curr) {
- return mIdList.get(0);
- }
-
- // Iterate through the ids. i is set to the current index + 1.
- int i = 1;
- for (int id : mIdList) {
- if (id == curr) {
- break;
- }
- i++;
- }
- return mIdList.get(i);
- }
-
- private void updateWidget(RenderResult res) {
- RemoteViews views = new RemoteViews(getPackageName(),
- R.layout.bookmarkwidget);
-
- Intent prev = new Intent(PREV, null, this, BookmarkWidgetService.class);
- prev.putExtra(EXTRA_ID, res.mId);
- views.setOnClickPendingIntent(R.id.previous,
- PendingIntent.getService(this, 0, prev,
- PendingIntent.FLAG_CANCEL_CURRENT));
-
- Intent next = new Intent(NEXT, null, this, BookmarkWidgetService.class);
- next.putExtra(EXTRA_ID, res.mId);
- views.setOnClickPendingIntent(R.id.next,
- PendingIntent.getService(this, 0, next,
- PendingIntent.FLAG_CANCEL_CURRENT));
-
- // Set the title of the bookmark. Use the url as a backup.
- String displayTitle = res.mTitle;
- if (displayTitle == null) {
- displayTitle = res.mUrl;
- }
- views.setTextViewText(R.id.title, displayTitle);
-
- // Set the image or revert to the progress indicator.
- if (res.mBitmap != null) {
- views.setImageViewBitmap(R.id.image, res.mBitmap);
- views.setViewVisibility(R.id.image, View.VISIBLE);
- views.setViewVisibility(R.id.progress, View.GONE);
- } else {
- views.setViewVisibility(R.id.progress, View.VISIBLE);
- views.setViewVisibility(R.id.image, View.GONE);
- }
-
- // Update the current id.
- mCurrentId = res.mId;
-
- AppWidgetManager.getInstance(this).updateAppWidget(
- new ComponentName(this, BookmarkWidgetProvider.class),
- views);
- }
-
- // Default WHERE clause is all bookmarks.
- private static final String QUERY_WHERE =
- BookmarkColumns.BOOKMARK + " == 1";
- private static final String[] PROJECTION = new String[] {
- BookmarkColumns._ID, BookmarkColumns.TITLE, BookmarkColumns.URL };
-
- // Class containing the rendering information for a specific bookmark.
- private static class RenderResult {
- final int mId;
- final String mTitle;
- final String mUrl;
- Bitmap mBitmap;
-
- RenderResult(int id, String title, String url) {
- mId = id;
- mTitle = title;
- mUrl = url;
- }
- }
-
- private void queryCursorAndRender() {
- // Clear the ordered list of ids and the map of ids to bitmaps.
- mIdList.clear();
- mIdsToResults.clear();
-
- // Look up all the bookmarks
- Cursor c = getContentResolver().query(Browser.BOOKMARKS_URI, PROJECTION,
- QUERY_WHERE, null, null);
- if (c != null) {
- if (c.moveToFirst()) {
- ArrayList<String> urls = new ArrayList<String>(c.getCount());
- boolean sawCurrentId = false;
- do {
- int id = c.getInt(0);
- String title = c.getString(1);
- String url = c.getString(2);
-
- // Linear list of ids to obtain the previous and next.
- mIdList.add(id);
-
- // Map the url to its db id for lookup when complete.
- mUrlsToIds.put(url, id);
-
- // Is this the current id?
- if (mCurrentId == id) {
- sawCurrentId = true;
- }
-
- // Store the current information to at least display the
- // title.
- RenderResult res = new RenderResult(id, title, url);
- mIdsToResults.put(id, res);
-
- // Add the url to our list to render.
- urls.add(url);
- } while (c.moveToNext());
-
- // Request a rendering of the urls. XXX: Hard-coded dimensions
- // until the view's orientation and size can be determined. Or
- // in the future the image will be a picture that can be
- // scaled/zoomed arbitrarily.
- mRenderer.render(urls, WIDTH, HEIGHT, this);
-
- // Set the current id to the very first id if we did not see
- // the current id in the list (the bookmark could have been
- // deleted or this is the first update).
- if (!sawCurrentId) {
- mCurrentId = mIdList.get(0);
- }
- }
- c.close();
- }
- }
-
- // UrlRenderer.Callback implementation
- public void complete(String url, ParcelFileDescriptor result) {
- int id = mUrlsToIds.get(url);
- if (id == NO_ID) {
- Log.d(TAG, "No matching id found during completion of "
- + url);
- return;
- }
-
- RenderResult res = mIdsToResults.get(id);
- if (res == null) {
- Log.d(TAG, "No result found during completion of "
- + url);
- return;
- }
-
- // Set the result.
- if (result != null) {
- InputStream input =
- new ParcelFileDescriptor.AutoCloseInputStream(result);
- Bitmap orig = BitmapFactory.decodeStream(input, null, null);
- // XXX: Hard-coded scaled bitmap until I can query the image
- // dimensions.
- res.mBitmap = Bitmap.createScaledBitmap(orig, WIDTH, HEIGHT, true);
- try {
- input.close();
- } catch (IOException e) {
- // oh well...
- }
- }
-
- // If we are currently looking at the bookmark that just finished,
- // update the widget.
- if (mCurrentId == id) {
- updateWidget(res);
- }
- }
-}
diff --git a/tests/assets/popular_urls.txt b/tests/assets/popular_urls.txt
new file mode 100644
index 0000000..70d0997
--- /dev/null
+++ b/tests/assets/popular_urls.txt
@@ -0,0 +1,4 @@
+http://google.com
+http://nytimes.com
+http://slashdot.org
+
diff --git a/tests/src/com/android/browser/JNIBindingsTest.java b/tests/src/com/android/browser/JNIBindingsTest.java
index ba3c66a..94dc985 100644
--- a/tests/src/com/android/browser/JNIBindingsTest.java
+++ b/tests/src/com/android/browser/JNIBindingsTest.java
@@ -212,7 +212,8 @@
public boolean testJSPrimitivesToStringsInJava(String intParam, String nullParam,
String doubleParam, String booleanParam, String charParam,
String undefinedParam) {
- String expectedIntParam = "123";
+ // Since JS numbers are treated as doubles.
+ String expectedIntParam = "123.0";
String expectedDoubleParam = "456.789";
String expectedBooleanParam = "true";
String expectedCharParam = "d";
diff --git a/tests/src/com/android/browser/JNIBindingsTestApp.java b/tests/src/com/android/browser/JNIBindingsTestApp.java
index 4f083f6..f4efa2c 100644
--- a/tests/src/com/android/browser/JNIBindingsTestApp.java
+++ b/tests/src/com/android/browser/JNIBindingsTestApp.java
@@ -37,6 +37,9 @@
/**
* Adds a JavaScript interface to the webview and calls functions on it to verify variables
* are passed from JS to Java correctly.
+ * To run this test, execute:
+ * adb shell am instrument -w -e class com.android.browser.JNIBindingsTestApp#testJNIBindings \
+ * com.android.browser.tests/android.test.InstrumentationTestRunner
*/
public class JNIBindingsTestApp extends ActivityInstrumentationTestCase2<BrowserActivity> {
@@ -47,6 +50,7 @@
private static final int MSG_WEBKIT_DATA_READY = 101;
private BrowserActivity mActivity = null;
+ private Controller mController = null;
private Instrumentation mInst = null;
private boolean mTestDone = false;
@@ -89,7 +93,7 @@
}
}
};
- mWebView.documentAsText(mHandler.obtainMessage(MSG_WEBKIT_DATA_READY));
+ mWebView.documentAsText(mHandler.obtainMessage(MSG_WEBKIT_DATA_READY, 1, 0));
Looper.loop();
}
}
@@ -108,6 +112,7 @@
super.setUp();
mActivity = getActivity();
+ mController = mActivity.getController();
mInst = getInstrumentation();
mInst.waitForIdleSync();
@@ -144,7 +149,7 @@
* and wrapping the WebView's helper clients.
*/
void setUpBrowser() {
- Tab tab = mActivity.getTabControl().getCurrentTab();
+ Tab tab = mController.getTabControl().getCurrentTab();
WebView webView = tab.getWebView();
webView.addJavascriptInterface(new JNIBindingsTest(this), "JNIBindingsTest");
@@ -226,7 +231,7 @@
public void testJNIBindings() {
setUpBrowser();
- Tab tab = mActivity.getTabControl().getCurrentTab();
+ Tab tab = mController.getTabControl().getCurrentTab();
WebView webView = tab.getWebView();
webView.loadUrl("file://" + SDCARD_BINDINGS_TEST_HTML);
synchronized(this) {
diff --git a/tests/src/com/android/browser/PopularUrlsTest.java b/tests/src/com/android/browser/PopularUrlsTest.java
index 590542a..5e367be 100644
--- a/tests/src/com/android/browser/PopularUrlsTest.java
+++ b/tests/src/com/android/browser/PopularUrlsTest.java
@@ -22,6 +22,7 @@
import android.net.http.SslError;
import android.os.Environment;
import android.test.ActivityInstrumentationTestCase2;
+import android.text.TextUtils;
import android.util.Log;
import android.webkit.DownloadListener;
import android.webkit.HttpAuthHandler;
@@ -61,6 +62,7 @@
private final static int PAGE_LOAD_TIMEOUT = 120000; // 2 minutes
private BrowserActivity mActivity = null;
+ private Controller mController = null;
private Instrumentation mInst = null;
private CountDownLatch mLatch = new CountDownLatch(1);
private RunStatus mStatus;
@@ -77,6 +79,7 @@
Intent i = new Intent(Intent.ACTION_VIEW, Uri.parse("about:blank"));
setActivityIntent(i);
mActivity = getActivity();
+ mController = mActivity.getController();
mInst = getInstrumentation();
mInst.waitForIdleSync();
@@ -92,13 +95,12 @@
super.tearDown();
}
- static BufferedReader getInputStream() throws FileNotFoundException {
+ BufferedReader getInputStream() throws FileNotFoundException {
return getInputStream(sInputFile);
}
- static BufferedReader getInputStream(String inputFile) throws FileNotFoundException {
- String path = sExternalStorage + File.separator + inputFile;
- FileReader fileReader = new FileReader(path);
+ BufferedReader getInputStream(String inputFile) throws FileNotFoundException {
+ FileReader fileReader = new FileReader(new File(sExternalStorage, inputFile));
BufferedReader bufferedReader = new BufferedReader(fileReader);
return bufferedReader;
@@ -109,11 +111,7 @@
}
OutputStreamWriter getOutputStream(String outputFile) throws IOException {
- String path = sExternalStorage + File.separator + outputFile;
-
- File file = new File(path);
-
- return new FileWriter(file, mStatus.getIsRecovery());
+ return new FileWriter(new File(sExternalStorage, outputFile), mStatus.getIsRecovery());
}
/**
@@ -121,7 +119,16 @@
* and wrapping the WebView's helper clients.
*/
void setUpBrowser() {
- Tab tab = mActivity.getTabControl().getCurrentTab();
+ mInst.runOnMainSync(new Runnable() {
+ @Override
+ public void run() {
+ setupBrowserInternal();
+ }
+ });
+ }
+
+ void setupBrowserInternal() {
+ Tab tab = mController.getTabControl().getCurrentTab();
WebView webView = tab.getWebView();
webView.setWebChromeClient(new TestWebChromeClient(webView.getWebChromeClient()) {
@@ -230,6 +237,7 @@
*/
@Override
public void onPageFinished(WebView view, String url) {
+ super.onPageFinished(view, url);
if (!pageLoadFinishCalled) {
pageLoadFinishCalled = true;
if (pageProgressFull) {
@@ -280,7 +288,7 @@
// try to stop page load
mInst.runOnMainSync(new Runnable(){
public void run() {
- mActivity.getTabControl().getCurrentTab().getWebView().stopLoading();
+ mController.getTabControl().getCurrentTab().getWebView().stopLoading();
}
});
// try to wait for count down latch again
@@ -298,8 +306,8 @@
private String url;
private boolean isRecovery;
- private RunStatus(String file) throws IOException {
- mFile = new File(file);
+ private RunStatus(File file) throws IOException {
+ mFile = file;
FileReader input = null;
BufferedReader reader = null;
isRecovery = false;
@@ -340,7 +348,7 @@
}
public static RunStatus load(String file) throws IOException {
- return new RunStatus(sExternalStorage + File.separator + file);
+ return new RunStatus(new File(sExternalStorage, file));
}
public void write() throws IOException {
@@ -408,14 +416,16 @@
void loopUrls(BufferedReader input, OutputStreamWriter writer,
boolean clearCache, int loopCount)
throws IOException, InterruptedException {
- Tab tab = mActivity.getTabControl().getCurrentTab();
+ Tab tab = mController.getTabControl().getCurrentTab();
WebView webView = tab.getWebView();
List<String> pages = new LinkedList<String>();
String page;
while (null != (page = input.readLine())) {
- pages.add(page);
+ if (!TextUtils.isEmpty(page)) {
+ pages.add(page);
+ }
}
Iterator<String> iterator = pages.iterator();
diff --git a/tests/src/com/android/browser/TestWebChromeClient.java b/tests/src/com/android/browser/TestWebChromeClient.java
index d78eaed..53f8db3 100644
--- a/tests/src/com/android/browser/TestWebChromeClient.java
+++ b/tests/src/com/android/browser/TestWebChromeClient.java
@@ -195,7 +195,7 @@
/** {@inheritDoc} */
@Override
- public void openFileChooser(ValueCallback<Uri> uploadFile) {
- mWrappedClient.openFileChooser(uploadFile);
+ public void openFileChooser(ValueCallback<Uri> uploadFile, String acceptType) {
+ mWrappedClient.openFileChooser(uploadFile, acceptType);
}
}
diff --git a/tools/get_search_engines.py b/tools/get_search_engines.py
index cd73423..bd6e5f8 100755
--- a/tools/get_search_engines.py
+++ b/tools/get_search_engines.py
@@ -39,16 +39,15 @@
google_data = ["google", "Google", "google.com",
"http://www.google.com/favicon.ico",
- "http://www.google.com/m?hl={language}&ie={inputEncoding}&source=android-browser&q={searchTerms}",
+ "http://www.google.com/search?hl={language}&ie={inputEncoding}&source=android-browser&q={searchTerms}",
"UTF-8",
- "http://www.google.com/complete/search?hl={language}&json=true&q={searchTerms}"]
+ "http://www.google.com/complete/search?hl={language}&client=android&q={searchTerms}"]
class SearchEngineManager(object):
"""Manages list of search engines and creates locale specific lists.
The main method useful for the caller is generateListForLocale(), which
- creates a locale specific search_engines.xml file suitable for use by the
- Android WebSearchProvider implementation.
+ creates a locale specific donottranslate-search_engines.xml file.
"""
def __init__(self):
@@ -195,7 +194,7 @@
self.writeEngineList(os.path.join(self.resdir, 'values'), "default")
def generateListForLocale(self, locale):
- """Creates a new locale specific search_engines.xml file.
+ """Creates a new locale specific donottranslate-search_engines.xml file.
The new file contains search engines specific to that country. If required
this function updates all_search_engines.xml file with any new search
@@ -237,7 +236,7 @@
text.append(' </string-array>\n');
self.generateXmlFromTemplate(os.path.join(sys.path[0], 'search_engines.template.xml'),
- os.path.join(dir_path, 'search_engines.xml'),
+ os.path.join(dir_path, 'donottranslate-search_engines.xml'),
text)
def generateXmlFromTemplate(self, template_path, out_path, text):
@@ -265,4 +264,3 @@
for locale in locales:
manager.generateListForLocale(locale)
manager.writeAllEngines()
-