Commit ec25514c authored by galinap's avatar galinap Committed by Commit Bot

[Contextual Suggestions] Add offline icon when suggestion is downloaded

This CL adds an offline icon when the user downloads a suggestion from
the context menu. This is done by registering an OfflineModelObserver
in the SuggestionsCarouselAdapter.

Bug: 763390
Change-Id: I8cf9adf54706927b5f11628c7e330b42eb4f2e94
Reviewed-on: https://chromium-review.googlesource.com/660538Reviewed-by: default avatarNicolas Dossou-Gbété <dgn@chromium.org>
Commit-Queue: Galia Peycheva <galinap@google.com>
Cr-Commit-Position: refs/heads/master@{#501594}
parent ae366fd6
...@@ -66,6 +66,7 @@ public class ContextualSuggestionsCardViewHolder extends NewTabPageViewHolder { ...@@ -66,6 +66,7 @@ public class ContextualSuggestionsCardViewHolder extends NewTabPageViewHolder {
mSuggestion = suggestion; mSuggestion = suggestion;
mDisplayStyleObserver.attach(); mDisplayStyleObserver.attach();
mSuggestionsBinder.updateViewInformation(mSuggestion); mSuggestionsBinder.updateViewInformation(mSuggestion);
refreshOfflineBadgeVisibility();
} }
@Override @Override
...@@ -102,6 +103,11 @@ public class ContextualSuggestionsCardViewHolder extends NewTabPageViewHolder { ...@@ -102,6 +103,11 @@ public class ContextualSuggestionsCardViewHolder extends NewTabPageViewHolder {
itemView.setLayoutParams(params); itemView.setLayoutParams(params);
} }
public void refreshOfflineBadgeVisibility() {
boolean visible = mSuggestion.getOfflinePageOfflineId() != null;
mSuggestionsBinder.updateOfflineBadgeVisibility(visible);
}
private class InteractionsDelegate implements ContextMenuManager.Delegate, View.OnClickListener, private class InteractionsDelegate implements ContextMenuManager.Delegate, View.OnClickListener,
View.OnCreateContextMenuListener { View.OnCreateContextMenuListener {
private final ContextMenuManager mContextMenuManager; private final ContextMenuManager mContextMenuManager;
......
...@@ -116,14 +116,17 @@ public class SuggestionsBottomSheetContent implements BottomSheet.BottomSheetCon ...@@ -116,14 +116,17 @@ public class SuggestionsBottomSheetContent implements BottomSheet.BottomSheetCon
UiConfig uiConfig = new UiConfig(mRecyclerView); UiConfig uiConfig = new UiConfig(mRecyclerView);
mRecyclerView.init(uiConfig, mContextMenuManager); mRecyclerView.init(uiConfig, mContextMenuManager);
OfflinePageBridge offlinePageBridge = OfflinePageBridge.getForProfile(profile);
mSuggestionsCarousel = mSuggestionsCarousel =
ChromeFeatureList.isEnabled(ChromeFeatureList.CONTEXTUAL_SUGGESTIONS_CAROUSEL) ChromeFeatureList.isEnabled(ChromeFeatureList.CONTEXTUAL_SUGGESTIONS_CAROUSEL)
? new SuggestionsCarousel(uiConfig, mSuggestionsUiDelegate, mContextMenuManager) ? new SuggestionsCarousel(
uiConfig, mSuggestionsUiDelegate, mContextMenuManager, offlinePageBridge)
: null; : null;
final NewTabPageAdapter adapter = new NewTabPageAdapter(mSuggestionsUiDelegate, final NewTabPageAdapter adapter = new NewTabPageAdapter(mSuggestionsUiDelegate,
/* aboveTheFoldView = */ null, uiConfig, OfflinePageBridge.getForProfile(profile), /* aboveTheFoldView = */ null, uiConfig, offlinePageBridge, mContextMenuManager,
mContextMenuManager, mTileGroupDelegate, mSuggestionsCarousel); mTileGroupDelegate, mSuggestionsCarousel);
mBottomSheetObserver = new SuggestionsSheetVisibilityChangeObserver(this, activity) { mBottomSheetObserver = new SuggestionsSheetVisibilityChangeObserver(this, activity) {
@Override @Override
......
...@@ -23,6 +23,7 @@ import org.chromium.chrome.browser.ntp.cards.NewTabPageViewHolder; ...@@ -23,6 +23,7 @@ import org.chromium.chrome.browser.ntp.cards.NewTabPageViewHolder;
import org.chromium.chrome.browser.ntp.cards.NodeVisitor; import org.chromium.chrome.browser.ntp.cards.NodeVisitor;
import org.chromium.chrome.browser.ntp.cards.OptionalLeaf; import org.chromium.chrome.browser.ntp.cards.OptionalLeaf;
import org.chromium.chrome.browser.ntp.snippets.SnippetArticle; import org.chromium.chrome.browser.ntp.snippets.SnippetArticle;
import org.chromium.chrome.browser.offlinepages.OfflinePageBridge;
import org.chromium.chrome.browser.widget.displaystyle.UiConfig; import org.chromium.chrome.browser.widget.displaystyle.UiConfig;
import org.chromium.ui.widget.Toast; import org.chromium.ui.widget.Toast;
...@@ -51,8 +52,9 @@ public class SuggestionsCarousel extends OptionalLeaf implements ImpressionTrack ...@@ -51,8 +52,9 @@ public class SuggestionsCarousel extends OptionalLeaf implements ImpressionTrack
private boolean mWasScrolledSinceShown; private boolean mWasScrolledSinceShown;
public SuggestionsCarousel(UiConfig uiConfig, SuggestionsUiDelegate uiDelegate, public SuggestionsCarousel(UiConfig uiConfig, SuggestionsUiDelegate uiDelegate,
ContextMenuManager contextMenuManager) { ContextMenuManager contextMenuManager, OfflinePageBridge offlinePageBridge) {
mAdapter = new SuggestionsCarouselAdapter(uiConfig, uiDelegate, contextMenuManager); mAdapter = new SuggestionsCarouselAdapter(
uiConfig, uiDelegate, contextMenuManager, offlinePageBridge);
mUiDelegate = uiDelegate; mUiDelegate = uiDelegate;
// The impression tracker will record metrics only once per bottom sheet opened. // The impression tracker will record metrics only once per bottom sheet opened.
......
...@@ -4,11 +4,15 @@ ...@@ -4,11 +4,15 @@
package org.chromium.chrome.browser.suggestions; package org.chromium.chrome.browser.suggestions;
import android.support.annotation.Nullable;
import android.support.v7.widget.RecyclerView; import android.support.v7.widget.RecyclerView;
import android.view.ViewGroup; import android.view.ViewGroup;
import org.chromium.chrome.browser.ChromeFeatureList;
import org.chromium.chrome.browser.ntp.ContextMenuManager; import org.chromium.chrome.browser.ntp.ContextMenuManager;
import org.chromium.chrome.browser.ntp.snippets.SnippetArticle; import org.chromium.chrome.browser.ntp.snippets.SnippetArticle;
import org.chromium.chrome.browser.offlinepages.OfflinePageBridge;
import org.chromium.chrome.browser.offlinepages.OfflinePageItem;
import org.chromium.chrome.browser.widget.displaystyle.UiConfig; import org.chromium.chrome.browser.widget.displaystyle.UiConfig;
import java.util.ArrayList; import java.util.ArrayList;
...@@ -22,16 +26,33 @@ public class SuggestionsCarouselAdapter ...@@ -22,16 +26,33 @@ public class SuggestionsCarouselAdapter
extends RecyclerView.Adapter<ContextualSuggestionsCardViewHolder> { extends RecyclerView.Adapter<ContextualSuggestionsCardViewHolder> {
private final SuggestionsUiDelegate mUiDelegate; private final SuggestionsUiDelegate mUiDelegate;
private final UiConfig mUiConfig; private final UiConfig mUiConfig;
/** Manager for creating a context menu for a contextual suggestions card. */
private final ContextMenuManager mContextMenuManager; private final ContextMenuManager mContextMenuManager;
private final List<SnippetArticle> mSuggestions; /** The list of suggestions held in the carousel currently. */
private final List<SnippetArticle> mSuggestionsList;
/**
* Access point to offline related features. Will be {@code null} when the badges are disabled.
* @see ChromeFeatureList#NTP_OFFLINE_PAGES_FEATURE_NAME
*/
@Nullable
private final OfflineModelObserver mObserver;
public SuggestionsCarouselAdapter(UiConfig uiConfig, SuggestionsUiDelegate uiDelegate, public SuggestionsCarouselAdapter(UiConfig uiConfig, SuggestionsUiDelegate uiDelegate,
ContextMenuManager contextMenuManager) { ContextMenuManager contextMenuManager, OfflinePageBridge offlinePageBridge) {
mUiConfig = uiConfig;
mUiDelegate = uiDelegate; mUiDelegate = uiDelegate;
mUiConfig = uiConfig;
mContextMenuManager = contextMenuManager; mContextMenuManager = contextMenuManager;
mSuggestions = new ArrayList<>(); mSuggestionsList = new ArrayList<>();
if (ChromeFeatureList.isEnabled(ChromeFeatureList.NTP_OFFLINE_PAGES_FEATURE_NAME)) {
mObserver = new OfflineModelObserver(offlinePageBridge);
mUiDelegate.addDestructionObserver(mObserver);
} else {
mObserver = null;
}
} }
@Override @Override
...@@ -42,7 +63,7 @@ public class SuggestionsCarouselAdapter ...@@ -42,7 +63,7 @@ public class SuggestionsCarouselAdapter
@Override @Override
public void onBindViewHolder(ContextualSuggestionsCardViewHolder holder, int i) { public void onBindViewHolder(ContextualSuggestionsCardViewHolder holder, int i) {
holder.onBindViewHolder(mSuggestions.get(i)); holder.onBindViewHolder(mSuggestionsList.get(i));
} }
@Override @Override
...@@ -52,7 +73,7 @@ public class SuggestionsCarouselAdapter ...@@ -52,7 +73,7 @@ public class SuggestionsCarouselAdapter
@Override @Override
public int getItemCount() { public int getItemCount() {
return mSuggestions.size(); return mSuggestionsList.size();
} }
/** /**
...@@ -61,9 +82,46 @@ public class SuggestionsCarouselAdapter ...@@ -61,9 +82,46 @@ public class SuggestionsCarouselAdapter
* @param suggestions The new suggestions to be shown in the suggestions carousel. * @param suggestions The new suggestions to be shown in the suggestions carousel.
*/ */
public void setSuggestions(List<SnippetArticle> suggestions) { public void setSuggestions(List<SnippetArticle> suggestions) {
mSuggestions.clear(); mSuggestionsList.clear();
mSuggestions.addAll(suggestions); mSuggestionsList.addAll(suggestions);
if (mObserver != null) {
mObserver.updateOfflinableSuggestionsAvailability();
}
notifyDataSetChanged(); notifyDataSetChanged();
} }
private class OfflineModelObserver extends SuggestionsOfflineModelObserver<SnippetArticle> {
/**
* Constructor for an offline model observer. It registers itself with the bridge, but the
* unregistration will have to be done by the caller, either directly or by registering the
* created observer as {@link DestructionObserver}.
*
* @param bridge source of the offline state data.
*/
public OfflineModelObserver(OfflinePageBridge bridge) {
super(bridge);
}
@Override
public void onSuggestionOfflineIdChanged(SnippetArticle suggestion, OfflinePageItem item) {
Long newId = item == null ? null : item.getOfflineId();
int index = mSuggestionsList.indexOf(suggestion);
// The suggestions could have been removed / replaced in the meantime.
if (index == -1) return;
Long oldId = suggestion.getOfflinePageOfflineId();
suggestion.setOfflinePageOfflineId(newId);
if ((oldId == null) == (newId == null)) return;
notifyItemChanged(index);
}
@Override
public Iterable<SnippetArticle> getOfflinableSuggestions() {
return mSuggestionsList;
}
}
} }
\ No newline at end of file
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment