Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(3944)

Unified Diff: chrome/android/java/src/org/chromium/chrome/browser/preferences/privacy/ConfirmImportantSitesDialogFragment.java

Issue 1465363002: [Storage] Android - ManageSpace UI, Important Origins, and CBD Dialog (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Android Java Hookup Created 4 years, 10 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: chrome/android/java/src/org/chromium/chrome/browser/preferences/privacy/ConfirmImportantSitesDialogFragment.java
diff --git a/chrome/android/java/src/org/chromium/chrome/browser/preferences/privacy/ConfirmImportantSitesDialogFragment.java b/chrome/android/java/src/org/chromium/chrome/browser/preferences/privacy/ConfirmImportantSitesDialogFragment.java
new file mode 100644
index 0000000000000000000000000000000000000000..f6615b40be29e50febd815457b9cecc0249971bf
--- /dev/null
+++ b/chrome/android/java/src/org/chromium/chrome/browser/preferences/privacy/ConfirmImportantSitesDialogFragment.java
@@ -0,0 +1,222 @@
+// Copyright 2015 The Chromium Authors. All rights reserved.
Finnur 2016/03/03 14:15:43 Nit: 2016 (elsewhere too)
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+package org.chromium.chrome.browser.preferences.privacy;
+
+import android.app.Dialog;
+import android.app.DialogFragment;
+import android.app.ProgressDialog;
+import android.content.DialogInterface;
+import android.content.res.Resources;
+import android.graphics.Bitmap;
+import android.graphics.drawable.BitmapDrawable;
+import android.graphics.drawable.Drawable;
+import android.os.Bundle;
+import android.support.v7.app.AlertDialog;
+import android.text.TextUtils;
+import android.util.LruCache;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.AdapterView;
+import android.widget.AdapterView.OnItemClickListener;
+import android.widget.ArrayAdapter;
+import android.widget.CheckedTextView;
+
+import org.chromium.base.ApiCompatibilityUtils;
+import org.chromium.chrome.R;
+import org.chromium.chrome.browser.favicon.FaviconHelper;
+import org.chromium.chrome.browser.favicon.FaviconHelper.FaviconImageCallback;
+import org.chromium.chrome.browser.profiles.Profile;
+
+import java.util.HashSet;
+import java.util.List;
+import java.util.Set;
+
+/**
+ * Modal dialog with options for selection the type of browsing data
+ * to clear (history, cookies), triggered from a preference.
+ */
+public class ConfirmImportantSitesDialogFragment extends DialogFragment {
+ private class ClearBrowsingDataAdapter extends ArrayAdapter<String> {
+ OriginEntry[] mOrigins;
+ private final Drawable mDefaultFavicon;
+ private final int mFaviconSize;
+
+ private ClearBrowsingDataAdapter(OriginEntry[] origins, String[] names) {
+ super(getActivity(), R.layout.select_dialog_multichoice_material, names);
+ mOrigins = origins;
+ Resources resources = getActivity().getResources();
+ mFaviconSize = resources.getDimensionPixelSize(R.dimen.default_favicon_size);
+ mDefaultFavicon =
+ ApiCompatibilityUtils.getDrawable(resources, R.drawable.default_favicon);
+ }
+
+ @Override
+ public int getCount() {
+ return mOrigins.length;
+ }
+
+ @Override
+ public boolean hasStableIds() {
+ return true;
+ }
+
+ @Override
+ public View getView(int position, View convertView, ViewGroup parent) {
+ View childView = convertView;
+ if (childView == null) {
+ LayoutInflater inflater = LayoutInflater.from(getActivity());
+ childView = inflater.inflate(
+ R.layout.select_dialog_multichoice_material, parent, false);
+
+ ViewHolder viewHolder = new ViewHolder();
+ viewHolder.textView = (CheckedTextView) childView;
+ childView.setTag(viewHolder);
+ }
+ ViewHolder viewHolder = (ViewHolder) childView.getTag();
+ configureChildView(position, viewHolder);
+ return childView;
+ }
+
+ public void configureChildView(int position, ViewHolder viewHolder) {
+ OriginEntry option = mOrigins[position];
+ viewHolder.textView.setChecked(!mDeselectedURLs.contains(option.url));
+ viewHolder.textView.setText(TextUtils.isEmpty(option.name) ? option.url : option.name);
+ loadLocalFavicon(viewHolder, option.url);
+ }
+
+ public void onClick(int position) {
+ OriginEntry option = mOrigins[position];
+ if (mDeselectedURLs.contains(option.url)) {
+ mDeselectedURLs.remove(option.url);
+ } else {
+ mDeselectedURLs.add(option.url);
+ }
+ notifyDataSetChanged();
+ }
+
+ private void loadLocalFavicon(final ViewHolder viewHolder, final String url) {
+ Drawable image;
+ if (url == null) {
+ // URL is null for print jobs, for example.
+ image = mDefaultFavicon;
+ } else {
+ image = mFaviconCache.getLocalFaviconImage(url);
+ if (image == null) {
+ FaviconImageCallback imageCallback = new FaviconImageCallback() {
+ @Override
+ public void onFaviconAvailable(Bitmap bitmap, String iconUrl) {
+ if (this != viewHolder.imageCallback) return;
+ Drawable image = faviconDrawable(bitmap);
+ image = (image == null) ? mDefaultFavicon : image;
+ mFaviconCache.putLocalFaviconImage(url, image);
+ viewHolder.textView.setCheckMarkDrawable(image);
+ }
+ };
+ viewHolder.imageCallback = imageCallback;
+ mFaviconHelper.getLocalFaviconImageForURL(
+ mProfile, url, mFaviconSize, imageCallback);
+ image = mDefaultFavicon;
+ }
+ }
+ viewHolder.textView.setCheckMarkDrawable(image);
+ }
+
+ private Drawable faviconDrawable(Bitmap image) {
+ if (image == null) return null;
+ return new BitmapDrawable(getActivity().getResources(),
+ Bitmap.createScaledBitmap(image, mFaviconSize, mFaviconSize, true));
+ }
+ }
+
+ private static class FaviconCache {
+ private final LruCache<String, Drawable> mMemoryCache;
+
+ public FaviconCache(int size) {
+ mMemoryCache = new LruCache<String, Drawable>(size);
+ }
+
+ public Drawable getLocalFaviconImage(String url) {
+ return mMemoryCache.get(url);
+ }
+
+ public void putLocalFaviconImage(String url, Drawable image) {
+ mMemoryCache.put(url, image);
+ }
+ }
+
+ /** The tag used when showing the clear browsing fragment. */
+ public static final String FRAGMENT_TAG = "ConfirmImportantSitesDialogFragment";
+
+ /**
+ * ViewHolder class optimizes looking up table row fields. findViewById is only called once
+ * per row view initialization, and the references are cached here. Also stores a reference to
+ * the favicon image callback; so that we can make sure we load the correct favicon.
+ */
+ private static class ViewHolder {
+ public CheckedTextView textView;
+ public FaviconImageCallback imageCallback;
+ }
+
+ public static class OriginEntry {
+ public String url;
+ public String name;
+ }
+
+ private List<OriginEntry> mOriginList;
+ private Set<String> mDeselectedURLs;
+ private AlertDialog mDialog;
+ private ProgressDialog mProgressDialog;
+ private ClearBrowsingDataAdapter mAdapter;
+ private FaviconHelper mFaviconHelper;
+ private FaviconCache mFaviconCache;
+ private Profile mProfile;
+ private DialogInterface.OnClickListener mListener;
+
+ public ConfirmImportantSitesDialogFragment(Profile profile, List<OriginEntry> importantOrigins,
+ DialogInterface.OnClickListener listener) {
+ mProfile = profile;
+ mOriginList = importantOrigins;
+ mListener = listener;
+ mFaviconHelper = new FaviconHelper();
+ mDeselectedURLs = new HashSet<>();
+ mFaviconCache = new FaviconCache(5);
+ }
+
+ /**
+ * @return the set of URLs that were deselected by this dialog.
+ */
+ public Set<String> getDeselectedURLs() {
+ return mDeselectedURLs;
+ }
+
+ @Override
+ public Dialog onCreateDialog(Bundle savedInstanceState) {
+ OriginEntry[] origins = mOriginList.toArray(new OriginEntry[0]);
+ String[] originNames = new String[origins.length];
+ for (int i = 0; i < origins.length; i++) {
+ originNames[i] = origins[i].name;
+ }
+ mAdapter = new ClearBrowsingDataAdapter(origins, originNames);
+ final AlertDialog.Builder builder =
+ new AlertDialog.Builder(getActivity(), R.style.AlertDialogTheme)
+ .setTitle(R.string.clear_browsing_data_title)
+ .setPositiveButton(R.string.clear_data_delete, mListener)
+ .setNegativeButton(R.string.cancel, mListener)
+ .setAdapter(mAdapter, null);
+ // OnClickListener is registered manually.
+ mDialog = builder.create();
+ mDialog.getListView().setOnItemClickListener(new OnItemClickListener() {
+ @Override
+ public void onItemClick(AdapterView<?> parent, View v, int position, long id) {
+ // The present behaviour of AlertDialog is to dismiss after the onClick event.
+ // Hence we are manually overriding this outside the builder.
+ mAdapter.onClick(position);
+ }
+ });
+
+ return mDialog;
+ }
+}

Powered by Google App Engine
This is Rietveld 408576698