Skip to content

Commit

Permalink
Thumbnails used in NewPipe are small (list/grid) mode. This PR facili…
Browse files Browse the repository at this point in the history
…tates full width thumbnails and dubbed as card mode.
  • Loading branch information
mahendranv committed Jan 15, 2023
1 parent c47d1af commit 41e948d
Show file tree
Hide file tree
Showing 24 changed files with 608 additions and 69 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
import org.schabi.newpipe.fragments.BaseStateFragment;
import org.schabi.newpipe.fragments.OnScrollBelowItemsListener;
import org.schabi.newpipe.info_list.InfoListAdapter;
import org.schabi.newpipe.info_list.ItemViewMode;
import org.schabi.newpipe.info_list.dialog.InfoItemDialog;
import org.schabi.newpipe.util.NavigationHelper;
import org.schabi.newpipe.util.OnClickGesture;
Expand Down Expand Up @@ -91,11 +92,7 @@ public void onResume() {

if (updateFlags != 0) {
if ((updateFlags & LIST_MODE_UPDATE_FLAG) != 0) {
final boolean useGrid = isGridLayout();
itemsList.setLayoutManager(useGrid
? getGridLayoutManager() : getListLayoutManager());
infoListAdapter.setUseGridVariant(useGrid);
infoListAdapter.notifyDataSetChanged();
refreshItemViewMode();
}
updateFlags = 0;
}
Expand Down Expand Up @@ -221,15 +218,23 @@ protected RecyclerView.LayoutManager getGridLayoutManager() {
return lm;
}

/**
* Updates the item view mode based on user preference.
*/
private void refreshItemViewMode() {
final ItemViewMode itemViewMode = getItemViewMode();
itemsList.setLayoutManager((itemViewMode == ItemViewMode.GRID)
? getGridLayoutManager() : getListLayoutManager());
infoListAdapter.setItemViewMode(itemViewMode);
infoListAdapter.notifyDataSetChanged();
}

@Override
protected void initViews(final View rootView, final Bundle savedInstanceState) {
super.initViews(rootView, savedInstanceState);

final boolean useGrid = isGridLayout();
itemsList = rootView.findViewById(R.id.items_list);
itemsList.setLayoutManager(useGrid ? getGridLayoutManager() : getListLayoutManager());

infoListAdapter.setUseGridVariant(useGrid);
refreshItemViewMode();

final Supplier<View> listHeaderSupplier = getListHeaderSupplier();
if (listHeaderSupplier != null) {
Expand Down Expand Up @@ -474,7 +479,11 @@ public void onSharedPreferenceChanged(final SharedPreferences sharedPreferences,
}
}

protected boolean isGridLayout() {
return ThemeHelper.shouldUseGridLayout(activity);
/**
* Returns preferred item view mode.
* @return ItemViewMode
*/
protected ItemViewMode getItemViewMode() {
return ThemeHelper.getItemViewMode(requireContext());
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,7 @@
import org.schabi.newpipe.extractor.comments.CommentsInfo;
import org.schabi.newpipe.extractor.comments.CommentsInfoItem;
import org.schabi.newpipe.fragments.list.BaseListInfoFragment;
import org.schabi.newpipe.info_list.ItemViewMode;
import org.schabi.newpipe.ktx.ViewUtils;
import org.schabi.newpipe.util.ExtractorHelper;

Expand Down Expand Up @@ -106,7 +107,7 @@ public void onCreateOptionsMenu(@NonNull final Menu menu,
@NonNull final MenuInflater inflater) { }

@Override
protected boolean isGridLayout() {
return false;
protected ItemViewMode getItemViewMode() {
return ItemViewMode.LIST;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -132,6 +132,8 @@ protected Supplier<View> getListHeaderSupplier() {
protected void initViews(final View rootView, final Bundle savedInstanceState) {
super.initViews(rootView, savedInstanceState);

// Is mini variant still relevant?
// Only the remote playlist screen uses it now
infoListAdapter.setUseMiniVariant(true);
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
import org.schabi.newpipe.extractor.ListExtractor;
import org.schabi.newpipe.extractor.stream.StreamInfo;
import org.schabi.newpipe.fragments.list.BaseListInfoFragment;
import org.schabi.newpipe.info_list.ItemViewMode;
import org.schabi.newpipe.ktx.ViewUtils;
import org.schabi.newpipe.util.RelatedItemInfo;

Expand Down Expand Up @@ -167,7 +168,12 @@ public void onSharedPreferenceChanged(final SharedPreferences sharedPreferences,
}

@Override
protected boolean isGridLayout() {
return false;
protected ItemViewMode getItemViewMode() {
ItemViewMode mode = super.getItemViewMode();
// Only list mode is supported. Either List or card will be used.
if (mode != ItemViewMode.LIST && mode != ItemViewMode.CARD) {
mode = ItemViewMode.LIST;
}
return mode;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -23,9 +23,11 @@
import org.schabi.newpipe.info_list.holder.CommentsInfoItemHolder;
import org.schabi.newpipe.info_list.holder.CommentsMiniInfoItemHolder;
import org.schabi.newpipe.info_list.holder.InfoItemHolder;
import org.schabi.newpipe.info_list.holder.PlaylistCardInfoItemHolder;
import org.schabi.newpipe.info_list.holder.PlaylistGridInfoItemHolder;
import org.schabi.newpipe.info_list.holder.PlaylistInfoItemHolder;
import org.schabi.newpipe.info_list.holder.PlaylistMiniInfoItemHolder;
import org.schabi.newpipe.info_list.holder.StreamCardInfoItemHolder;
import org.schabi.newpipe.info_list.holder.StreamGridInfoItemHolder;
import org.schabi.newpipe.info_list.holder.StreamInfoItemHolder;
import org.schabi.newpipe.info_list.holder.StreamMiniInfoItemHolder;
Expand Down Expand Up @@ -67,12 +69,14 @@ public class InfoListAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolde
private static final int MINI_STREAM_HOLDER_TYPE = 0x100;
private static final int STREAM_HOLDER_TYPE = 0x101;
private static final int GRID_STREAM_HOLDER_TYPE = 0x102;
private static final int CARD_STREAM_HOLDER_TYPE = 0x103;
private static final int MINI_CHANNEL_HOLDER_TYPE = 0x200;
private static final int CHANNEL_HOLDER_TYPE = 0x201;
private static final int GRID_CHANNEL_HOLDER_TYPE = 0x202;
private static final int MINI_PLAYLIST_HOLDER_TYPE = 0x300;
private static final int PLAYLIST_HOLDER_TYPE = 0x301;
private static final int GRID_PLAYLIST_HOLDER_TYPE = 0x302;
private static final int CARD_PLAYLIST_HOLDER_TYPE = 0x303;
private static final int MINI_COMMENT_HOLDER_TYPE = 0x400;
private static final int COMMENT_HOLDER_TYPE = 0x401;

Expand All @@ -82,9 +86,10 @@ public class InfoListAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolde
private final HistoryRecordManager recordManager;

private boolean useMiniVariant = false;
private boolean useGridVariant = false;
private boolean showFooter = false;

private ItemViewMode itemMode = ItemViewMode.LIST;

private Supplier<View> headerSupplier = null;

public InfoListAdapter(final Context context) {
Expand Down Expand Up @@ -114,8 +119,8 @@ public void setUseMiniVariant(final boolean useMiniVariant) {
this.useMiniVariant = useMiniVariant;
}

public void setUseGridVariant(final boolean useGridVariant) {
this.useGridVariant = useGridVariant;
public void setItemViewMode(final ItemViewMode itemViewMode) {
this.itemMode = itemViewMode;
}

public void addInfoItemList(@Nullable final List<? extends InfoItem> data) {
Expand Down Expand Up @@ -234,14 +239,33 @@ public int getItemViewType(int position) {
final InfoItem item = infoItemList.get(position);
switch (item.getInfoType()) {
case STREAM:
return useGridVariant ? GRID_STREAM_HOLDER_TYPE : useMiniVariant
? MINI_STREAM_HOLDER_TYPE : STREAM_HOLDER_TYPE;
if (itemMode == ItemViewMode.CARD) {
return CARD_STREAM_HOLDER_TYPE;
} else if (itemMode == ItemViewMode.GRID) {
return GRID_STREAM_HOLDER_TYPE;
} else if (useMiniVariant) {
return MINI_STREAM_HOLDER_TYPE;
} else {
return STREAM_HOLDER_TYPE;
}
case CHANNEL:
return useGridVariant ? GRID_CHANNEL_HOLDER_TYPE : useMiniVariant
? MINI_CHANNEL_HOLDER_TYPE : CHANNEL_HOLDER_TYPE;
if (itemMode == ItemViewMode.GRID) {
return GRID_CHANNEL_HOLDER_TYPE;
} else if (useMiniVariant) {
return MINI_CHANNEL_HOLDER_TYPE;
} else {
return CHANNEL_HOLDER_TYPE;
}
case PLAYLIST:
return useGridVariant ? GRID_PLAYLIST_HOLDER_TYPE : useMiniVariant
? MINI_PLAYLIST_HOLDER_TYPE : PLAYLIST_HOLDER_TYPE;
if (itemMode == ItemViewMode.CARD) {
return CARD_PLAYLIST_HOLDER_TYPE;
} else if (itemMode == ItemViewMode.GRID) {
return GRID_PLAYLIST_HOLDER_TYPE;
} else if (useMiniVariant) {
return MINI_PLAYLIST_HOLDER_TYPE;
} else {
return PLAYLIST_HOLDER_TYPE;
}
case COMMENT:
return useMiniVariant ? MINI_COMMENT_HOLDER_TYPE : COMMENT_HOLDER_TYPE;
default:
Expand Down Expand Up @@ -274,6 +298,8 @@ public RecyclerView.ViewHolder onCreateViewHolder(@NonNull final ViewGroup paren
return new StreamInfoItemHolder(infoItemBuilder, parent);
case GRID_STREAM_HOLDER_TYPE:
return new StreamGridInfoItemHolder(infoItemBuilder, parent);
case CARD_STREAM_HOLDER_TYPE:
return new StreamCardInfoItemHolder(infoItemBuilder, parent);
case MINI_CHANNEL_HOLDER_TYPE:
return new ChannelMiniInfoItemHolder(infoItemBuilder, parent);
case CHANNEL_HOLDER_TYPE:
Expand All @@ -286,6 +312,8 @@ public RecyclerView.ViewHolder onCreateViewHolder(@NonNull final ViewGroup paren
return new PlaylistInfoItemHolder(infoItemBuilder, parent);
case GRID_PLAYLIST_HOLDER_TYPE:
return new PlaylistGridInfoItemHolder(infoItemBuilder, parent);
case CARD_PLAYLIST_HOLDER_TYPE:
return new PlaylistCardInfoItemHolder(infoItemBuilder, parent);
case MINI_COMMENT_HOLDER_TYPE:
return new CommentsMiniInfoItemHolder(infoItemBuilder, parent);
case COMMENT_HOLDER_TYPE:
Expand Down
23 changes: 23 additions & 0 deletions app/src/main/java/org/schabi/newpipe/info_list/ItemViewMode.java
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
package org.schabi.newpipe.info_list;

/**
* Item view mode for streams & playlist listing screens.
*/
public enum ItemViewMode {
/**
* Default mode.
*/
AUTO,
/**
* Full width list item with thumb on the left and two line title & uploader in right.
*/
LIST,
/**
* Grid mode places two cards per row.
*/
GRID,
/**
* A full width card in phone - portrait.
*/
CARD
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
package org.schabi.newpipe.info_list.holder;

import android.view.ViewGroup;

import org.schabi.newpipe.R;
import org.schabi.newpipe.info_list.InfoItemBuilder;

/**
* Playlist card layout.
*/
public class PlaylistCardInfoItemHolder extends PlaylistMiniInfoItemHolder {

public PlaylistCardInfoItemHolder(final InfoItemBuilder infoItemBuilder,
final ViewGroup parent) {
super(infoItemBuilder, R.layout.list_playlist_card_item, parent);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
package org.schabi.newpipe.info_list.holder;

import android.view.ViewGroup;

import org.schabi.newpipe.R;
import org.schabi.newpipe.info_list.InfoItemBuilder;

/**
* Card layout for stream.
*/
public class StreamCardInfoItemHolder extends StreamInfoItemHolder {

public StreamCardInfoItemHolder(final InfoItemBuilder infoItemBuilder, final ViewGroup parent) {
super(infoItemBuilder, R.layout.list_stream_card_item, parent);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -22,10 +22,11 @@
import org.schabi.newpipe.databinding.PignateFooterBinding;
import org.schabi.newpipe.fragments.BaseStateFragment;
import org.schabi.newpipe.fragments.list.ListViewContract;
import org.schabi.newpipe.info_list.ItemViewMode;

import static org.schabi.newpipe.ktx.ViewUtils.animate;
import static org.schabi.newpipe.ktx.ViewUtils.animateHideRecyclerViewAllowingScrolling;
import static org.schabi.newpipe.util.ThemeHelper.shouldUseGridLayout;
import static org.schabi.newpipe.util.ThemeHelper.getItemViewMode;

/**
* This fragment is design to be used with persistent data such as
Expand Down Expand Up @@ -77,16 +78,23 @@ public void onResume() {
super.onResume();
if (updateFlags != 0) {
if ((updateFlags & LIST_MODE_UPDATE_FLAG) != 0) {
final boolean useGrid = shouldUseGridLayout(requireContext());
itemsList.setLayoutManager(
useGrid ? getGridLayoutManager() : getListLayoutManager());
itemListAdapter.setUseGridVariant(useGrid);
itemListAdapter.notifyDataSetChanged();
refreshItemViewMode();
}
updateFlags = 0;
}
}

/**
* Updates the item view mode based on user preference.
*/
private void refreshItemViewMode() {
final ItemViewMode itemViewMode = getItemViewMode(requireContext());
itemsList.setLayoutManager((itemViewMode == ItemViewMode.GRID)
? getGridLayoutManager() : getListLayoutManager());
itemListAdapter.setItemViewMode(itemViewMode);
itemListAdapter.notifyDataSetChanged();
}

/*//////////////////////////////////////////////////////////////////////////
// Lifecycle - View
//////////////////////////////////////////////////////////////////////////*/
Expand Down Expand Up @@ -120,11 +128,9 @@ protected void initViews(final View rootView, final Bundle savedInstanceState) {

itemListAdapter = new LocalItemListAdapter(activity);

final boolean useGrid = shouldUseGridLayout(requireContext());
itemsList = rootView.findViewById(R.id.items_list);
itemsList.setLayoutManager(useGrid ? getGridLayoutManager() : getListLayoutManager());
refreshItemViewMode();

itemListAdapter.setUseGridVariant(useGrid);
headerRootBinding = getListHeader();
if (headerRootBinding != null) {
itemListAdapter.setHeader(headerRootBinding.getRoot());
Expand Down
Loading

0 comments on commit 41e948d

Please sign in to comment.