Suggest subreddits when searching.

This commit is contained in:
Alex Ning 2021-06-30 20:06:46 +08:00
parent b0f38f9db4
commit ef953a72f7
23 changed files with 177 additions and 39 deletions

View File

@ -28,6 +28,8 @@ import com.r0adkll.slidr.Slidr;
import org.greenrobot.eventbus.EventBus;
import org.greenrobot.eventbus.Subscribe;
import java.util.ArrayList;
import javax.inject.Inject;
import javax.inject.Named;
@ -37,12 +39,21 @@ import ml.docilealligator.infinityforreddit.Infinity;
import ml.docilealligator.infinityforreddit.R;
import ml.docilealligator.infinityforreddit.RedditDataRoomDatabase;
import ml.docilealligator.infinityforreddit.adapters.SearchActivityRecyclerViewAdapter;
import ml.docilealligator.infinityforreddit.adapters.SubredditAutocompleteRecyclerViewAdapter;
import ml.docilealligator.infinityforreddit.apis.RedditAPI;
import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
import ml.docilealligator.infinityforreddit.events.SwitchAccountEvent;
import ml.docilealligator.infinityforreddit.recentsearchquery.DeleteRecentSearchQuery;
import ml.docilealligator.infinityforreddit.recentsearchquery.RecentSearchQuery;
import ml.docilealligator.infinityforreddit.recentsearchquery.RecentSearchQueryViewModel;
import ml.docilealligator.infinityforreddit.subreddit.ParseSubredditData;
import ml.docilealligator.infinityforreddit.subreddit.SubredditData;
import ml.docilealligator.infinityforreddit.utils.APIUtils;
import ml.docilealligator.infinityforreddit.utils.SharedPreferencesUtils;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
import retrofit2.Retrofit;
public class SearchActivity extends BaseActivity {
@ -83,11 +94,12 @@ public class SearchActivity extends BaseActivity {
TextView subredditNameTextView;
@BindView(R.id.divider_search_activity)
View divider;
@BindView(R.id.recent_summary_text_view_search_activity)
TextView recentSummaryTextView;
@BindView(R.id.recycler_view_search_activity)
RecyclerView recyclerView;
@Inject
@Named("oauth")
Retrofit mOauthRetrofit;
@Inject
RedditDataRoomDatabase mRedditDataRoomDatabase;
@Inject
@Named("default")
@ -96,14 +108,20 @@ public class SearchActivity extends BaseActivity {
@Named("current_account")
SharedPreferences mCurrentAccountSharedPreferences;
@Inject
@Named("nsfw_and_spoiler")
SharedPreferences mNsfwAndSpoilerSharedPreferences;
@Inject
CustomThemeWrapper mCustomThemeWrapper;
private String mAccountName;
private String mAccessToken;
private String query;
private String subredditName;
private boolean subredditIsUser;
private boolean searchOnlySubreddits;
private boolean searchOnlyUsers;
private SearchActivityRecyclerViewAdapter adapter;
private SubredditAutocompleteRecyclerViewAdapter subredditAutocompleteRecyclerViewAdapter;
private Call<String> subredditAutocompleteCall;
RecentSearchQueryViewModel mRecentSearchQueryViewModel;
@Override
@ -159,6 +177,18 @@ public class SearchActivity extends BaseActivity {
}
});
mAccountName = mCurrentAccountSharedPreferences.getString(SharedPreferencesUtils.ACCOUNT_NAME, null);
mAccessToken = mCurrentAccountSharedPreferences.getString(SharedPreferencesUtils.ACCESS_TOKEN, null);
boolean nsfw = mNsfwAndSpoilerSharedPreferences.getBoolean((mAccountName == null ? "" : mAccountName) + SharedPreferencesUtils.NSFW_BASE, false);
subredditAutocompleteRecyclerViewAdapter = new SubredditAutocompleteRecyclerViewAdapter(this,
mCustomThemeWrapper, subredditData -> {
Intent intent = new Intent(SearchActivity.this, ViewSubredditDetailActivity.class);
intent.putExtra(ViewSubredditDetailActivity.EXTRA_SUBREDDIT_NAME_KEY, subredditData.getName());
startActivity(intent);
finish();
});
simpleSearchView.setOnQueryTextListener(new SimpleSearchView.OnQueryTextListener() {
@Override
public boolean onQueryTextSubmit(String query) {
@ -168,6 +198,38 @@ public class SearchActivity extends BaseActivity {
@Override
public boolean onQueryTextChange(String newText) {
if (!newText.isEmpty()) {
if (subredditAutocompleteCall != null) {
subredditAutocompleteCall.cancel();
}
subredditAutocompleteCall = mOauthRetrofit.create(RedditAPI.class).subredditAutocomplete(APIUtils.getOAuthHeader(mAccessToken),
newText, nsfw);
subredditAutocompleteCall.enqueue(new Callback<String>() {
@Override
public void onResponse(@NonNull Call<String> call, @NonNull Response<String> response) {
if (response.isSuccessful()) {
ParseSubredditData.parseSubredditListingData(response.body(), nsfw, new ParseSubredditData.ParseSubredditListingDataListener() {
@Override
public void onParseSubredditListingDataSuccess(ArrayList<SubredditData> subredditData, String after) {
subredditAutocompleteRecyclerViewAdapter.setSubreddits(subredditData);
recyclerView.setAdapter(subredditAutocompleteRecyclerViewAdapter);
}
@Override
public void onParseSubredditListingDataFail() {
}
});
}
}
@Override
public void onFailure(@NonNull Call<String> call, @NonNull Throwable t) {
}
});
return true;
}
return false;
}
@ -177,8 +239,6 @@ public class SearchActivity extends BaseActivity {
}
});
mAccountName = mCurrentAccountSharedPreferences.getString(SharedPreferencesUtils.ACCOUNT_NAME, null);
if (savedInstanceState != null) {
subredditName = savedInstanceState.getString(SUBREDDIT_NAME_STATE);
subredditIsUser = savedInstanceState.getBoolean(SUBREDDIT_IS_USER_STATE);
@ -238,10 +298,8 @@ public class SearchActivity extends BaseActivity {
mRecentSearchQueryViewModel.getAllRecentSearchQueries().observe(this, recentSearchQueries -> {
if (recentSearchQueries != null && !recentSearchQueries.isEmpty()) {
divider.setVisibility(View.VISIBLE);
recentSummaryTextView.setVisibility(View.VISIBLE);
} else {
divider.setVisibility(View.GONE);
recentSummaryTextView.setVisibility(View.GONE);
}
adapter.setRecentSearchQueries(recentSearchQueries);
});
@ -309,7 +367,6 @@ public class SearchActivity extends BaseActivity {
searchInTextView.setTextColor(colorAccent);
subredditNameTextView.setTextColor(mCustomThemeWrapper.getPrimaryTextColor());
divider.setBackgroundColor(mCustomThemeWrapper.getDividerColor());
recentSummaryTextView.setTextColor(colorAccent);
}
@Override

View File

@ -0,0 +1,103 @@
package ml.docilealligator.infinityforreddit.adapters;
import android.content.Context;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
import android.widget.ImageView;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.recyclerview.widget.RecyclerView;
import com.bumptech.glide.Glide;
import com.bumptech.glide.RequestManager;
import com.bumptech.glide.request.RequestOptions;
import com.google.android.material.checkbox.MaterialCheckBox;
import java.util.List;
import jp.wasabeef.glide.transformations.RoundedCornersTransformation;
import ml.docilealligator.infinityforreddit.R;
import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
import ml.docilealligator.infinityforreddit.subreddit.SubredditData;
import pl.droidsonroids.gif.GifImageView;
public class SubredditAutocompleteRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> {
private List<SubredditData> subreddits;
private RequestManager glide;
private CustomThemeWrapper customThemeWrapper;
private ItemOnClickListener itemOnClickListener;
public SubredditAutocompleteRecyclerViewAdapter(Context context, CustomThemeWrapper customThemeWrapper,
ItemOnClickListener itemOnClickListener) {
glide = Glide.with(context);
this.customThemeWrapper = customThemeWrapper;
this.itemOnClickListener = itemOnClickListener;
}
@NonNull
@Override
public RecyclerView.ViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) {
return new SubredditViewHolder(LayoutInflater.from(parent.getContext()).inflate(R.layout.item_subreddit_listing, parent, false));
}
@Override
public void onBindViewHolder(@NonNull RecyclerView.ViewHolder holder, int position) {
if (holder instanceof SubredditViewHolder) {
glide.load(subreddits.get(position).getIconUrl())
.apply(RequestOptions.bitmapTransform(new RoundedCornersTransformation(72, 0)))
.error(glide.load(R.drawable.subreddit_default_icon)
.apply(RequestOptions.bitmapTransform(new RoundedCornersTransformation(72, 0))))
.into(((SubredditViewHolder) holder).iconImageView);
((SubredditViewHolder) holder).subredditNameTextView.setText(subreddits.get(position).getName());
}
}
@Override
public int getItemCount() {
return subreddits == null ? 0 : subreddits.size();
}
@Override
public void onViewRecycled(@NonNull RecyclerView.ViewHolder holder) {
super.onViewRecycled(holder);
if (holder instanceof SubredditViewHolder) {
glide.clear(((SubredditViewHolder) holder).iconImageView);
}
}
public void setSubreddits(List<SubredditData> subreddits) {
this.subreddits = subreddits;
notifyDataSetChanged();
}
class SubredditViewHolder extends RecyclerView.ViewHolder {
GifImageView iconImageView;
TextView subredditNameTextView;
ImageView subscribeImageView;
MaterialCheckBox checkBox;
public SubredditViewHolder(@NonNull View itemView) {
super(itemView);
iconImageView = itemView.findViewById(R.id.subreddit_icon_gif_image_view_item_subreddit_listing);
subredditNameTextView = itemView.findViewById(R.id.subreddit_name_text_view_item_subreddit_listing);
subscribeImageView = itemView.findViewById(R.id.subscribe_image_view_item_subreddit_listing);
checkBox = itemView.findViewById(R.id.checkbox_item_subreddit_listing);
subscribeImageView.setVisibility(View.GONE);
checkBox.setVisibility(View.GONE);
subredditNameTextView.setTextColor(customThemeWrapper.getPrimaryTextColor());
itemView.setOnClickListener(view -> {
itemOnClickListener.onClick(subreddits.get(getBindingAdapterPosition()));
});
}
}
public interface ItemOnClickListener {
void onClick(SubredditData subredditData);
}
}

View File

@ -262,7 +262,7 @@ public class SubredditListingRecyclerViewAdapter extends PagedListAdapter<Subred
TextView subredditNameTextView;
@BindView(R.id.subscribe_image_view_item_subreddit_listing)
ImageView subscribeButton;
@BindView(R.id.checkbox__item_subreddit_listing)
@BindView(R.id.checkbox_item_subreddit_listing)
MaterialCheckBox checkBox;
DataViewHolder(View itemView) {

View File

@ -352,4 +352,8 @@ public interface RedditAPI {
@FormUrlEncoded
@POST("/api/quarantine_optin?raw_json=1")
Call<String> optInQuarantinedSubreddit(@HeaderMap Map<String, String> headers, @FieldMap Map<String, String> params);
@GET("/api/subreddit_autocomplete_v2?typeahead_active=true&include_profiles=false&raw_json=1")
Call<String> subredditAutocomplete(@HeaderMap Map<String ,String> headers, @Query("query") String query,
@Query("include_over_18") boolean nsfw);
}

View File

@ -13,12 +13,12 @@ import java.util.ArrayList;
import ml.docilealligator.infinityforreddit.utils.JSONUtils;
import ml.docilealligator.infinityforreddit.utils.Utils;
class ParseSubredditData {
static void parseSubredditData(String response, ParseSubredditDataListener parseSubredditDataListener) {
public class ParseSubredditData {
public static void parseSubredditData(String response, ParseSubredditDataListener parseSubredditDataListener) {
new ParseSubredditDataAsyncTask(response, parseSubredditDataListener).execute();
}
static void parseSubredditListingData(String response, boolean nsfw, ParseSubredditListingDataListener parseSubredditListingDataListener) {
public static void parseSubredditListingData(String response, boolean nsfw, ParseSubredditListingDataListener parseSubredditListingDataListener) {
new ParseSubredditListingDataAsyncTask(response, nsfw, parseSubredditListingDataListener).execute();
}
@ -70,7 +70,7 @@ class ParseSubredditData {
void onParseSubredditDataFail();
}
interface ParseSubredditListingDataListener {
public interface ParseSubredditListingDataListener {
void onParseSubredditListingDataSuccess(ArrayList<SubredditData> subredditData, String after);
void onParseSubredditListingDataFail();

View File

@ -91,15 +91,6 @@
android:layout_height="1dp"
android:visibility="gone" />
<TextView
android:id="@+id/recent_summary_text_view_search_activity"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="16dp"
android:text="@string/recent_searches"
android:fontFamily="?attr/font_family"
android:visibility="gone" />
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/recycler_view_search_activity"
android:layout_width="match_parent"

View File

@ -45,7 +45,7 @@
android:visibility="gone"/>
<com.google.android.material.checkbox.MaterialCheckBox
android:id="@+id/checkbox__item_subreddit_listing"
android:id="@+id/checkbox_item_subreddit_listing"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
app:layout_constraintEnd_toEndOf="parent"

View File

@ -871,7 +871,6 @@ Reiter könnten den Inhalt verlieren, wenn zu anderen gewechselt wird. Selbes Ve
<string name="give_award_error_message">"Code: %1$d/ Nachricht: %2$s"</string>
<string name="give_award_success">"Auszeichnung verliehen"</string>
<string name="give_award_failed">"Fehlgeschlagen"</string>
<string name="recent_searches">"Kürzliche Suchanfragen"</string>
<string name="warning">"Warnung"</string>
<string name="this_is_a_nsfw_subreddit">"Dieses ist ein NSFW-Subreddit"</string>
<string name="this_user_has_nsfw_content">"Dieser Nutzer hat NSFW-Inhalte"</string>

View File

@ -863,7 +863,6 @@ Videos de Reddit están en menor resolución"</string>
<string name="anonymous">"Anónimo"</string>
<string name="give_award_success">"Premio entregado"</string>
<string name="give_award_failed">"Falló"</string>
<string name="recent_searches">"Búsquedas recientes"</string>
<string name="warning">"Precaución"</string>
<string name="this_is_a_nsfw_subreddit">"Este es un Subreddit NSFW"</string>
<string name="this_user_has_nsfw_content">"Este usuario tiene contenido NSFW"</string>

View File

@ -918,7 +918,6 @@ Les onglets pourraient perdre tout leur contenu quand vous passez d'un onglet à
<string name="give_award_error_message">"Erreur: %2$s, code: %1$d/"</string>
<string name="give_award_success">"Succès ! "</string>
<string name="give_award_failed">"Échec de la récompense. "</string>
<string name="recent_searches">"Recherches récentes"</string>
<string name="warning">"Avertissement "</string>
<string name="this_is_a_nsfw_subreddit">"Cette Subreddit est PSPT (Pas Sécurisé Pour le Travail) "</string>
<string name="this_user_has_nsfw_content">"Cet utilisateur poste du contenu NSFW"</string>

View File

@ -901,7 +901,6 @@ https://play.google.com/store/apps/details?id=ml.docilealligator.infinityforredd
संदेश: %2$s"</string>
<string name="give_award_success">"पुरस्कार दे दिया गया "</string>
<string name="give_award_failed">"असफल "</string>
<string name="recent_searches">"हाल ही की खोजें "</string>
<string name="warning">"चेतावनी "</string>
<string name="this_is_a_nsfw_subreddit">"यह एक NSFW सबरैडिट है "</string>
<string name="this_user_has_nsfw_content">"इस यूजर के पास NSFW सामग्री है। "</string>

View File

@ -864,7 +864,6 @@ Reddit videi su niže rezolucije."</string>
Poruka: %2$s"</string>
<string name="give_award_success">"Nagrađeno"</string>
<string name="give_award_failed">"Nagrađivanje nije uspjelo"</string>
<string name="recent_searches">"Nedavne pretrage"</string>
<string name="warning">"Upozorenje"</string>
<string name="this_is_a_nsfw_subreddit">"Ovo je NSFW podreddit."</string>
<string name="this_user_has_nsfw_content">"Ovaj korisnik ima NSFW sadržaj"</string>

View File

@ -835,7 +835,6 @@ Videó autómatikus lejátszása le van tiltva."</string>
Üzenet %2$s"</string>
<string name="give_award_success">"Kitüntetés megadva"</string>
<string name="give_award_failed">"Nem sikerült"</string>
<string name="recent_searches">"Utóbbi keresések"</string>
<string name="warning">"Figyelem"</string>
<string name="this_is_a_nsfw_subreddit">"Ez egy NSFW subreddit."</string>
<string name="this_user_has_nsfw_content">"Ennek a felhasználónak van NSFW tartlama"</string>

View File

@ -865,7 +865,6 @@ La riproduzione automatica video è disabilitata"</string>
Messaggio: %2$s"</string>
<string name="give_award_success">"Premio conferito"</string>
<string name="give_award_failed">"Fallito"</string>
<string name="recent_searches">"Ricerche recenti"</string>
<string name="warning">"Avvertimento"</string>
<string name="this_is_a_nsfw_subreddit">"Questo è un subreddit marcato NSFW"</string>
<string name="this_user_has_nsfw_content">"Questo utente è marcato NSFW"</string>

View File

@ -912,7 +912,6 @@ https://play.google.com/store/apps/details?id=ml.docilealligator.infinityforredd
メッセージ: %2$s"</string>
<string name="give_award_success">"アワードを贈りました"</string>
<string name="give_award_failed">"失敗しました"</string>
<string name="recent_searches">"検索履歴"</string>
<string name="warning">"警告"</string>
<string name="this_is_a_nsfw_subreddit">"このSubredditはNSFWです"</string>
<string name="this_user_has_nsfw_content">"このユーザーはNSFWの投稿を含んでいます"</string>

View File

@ -838,7 +838,6 @@ Automatisch afspelen van video is uitgeschakeld."</string>
Bericht: %2$s"</string>
<string name="give_award_success">"Award gegeven"</string>
<string name="give_award_failed">"Mislukt"</string>
<string name="recent_searches">"Recente zoekopdrachten"</string>
<string name="warning">"Waarschuwing"</string>
<string name="this_is_a_nsfw_subreddit">"Dit is een NSFW subreddit."</string>
<string name="this_user_has_nsfw_content">"Deze gebruiker heeft NSFW inhoud"</string>

View File

@ -840,7 +840,6 @@ Autoodtwarzanie wideo jest wyłączone."</string>
Wiadomość: %2$s"</string>
<string name="give_award_success">"Nagroda przyznana"</string>
<string name="give_award_failed">"Niepowodzenie"</string>
<string name="recent_searches">"Ostatnie wyszukiwania"</string>
<string name="warning">"Ostrzeżenie "</string>
<string name="this_is_a_nsfw_subreddit">"To jest subreddit NSFW"</string>
<string name="this_user_has_nsfw_content">"Ten użytkownik posiada treści NSFW"</string>

View File

@ -841,7 +841,6 @@ Os vídeos do Reddit ficam em menor resolução."</string>
Mensagem: %2$s"</string>
<string name="give_award_success">"Prêmio concedido"</string>
<string name="give_award_failed">"Falhou"</string>
<string name="recent_searches">"Buscas recentes"</string>
<string name="warning">"Aviso"</string>
<string name="this_is_a_nsfw_subreddit">"Este é um subreddit NSFW."</string>
<string name="this_user_has_nsfw_content">"Este usuário tem conteúdo NSFW."</string>

View File

@ -833,7 +833,6 @@ Reddit видео - уменьшенное разрешение.
Сообщение: %2$s"</string>
<string name="give_award_success">"Награда выдана"</string>
<string name="give_award_failed">"Ошибка"</string>
<string name="recent_searches">"Недавние запросы"</string>
<string name="warning">"Предупреждение"</string>
<string name="this_is_a_nsfw_subreddit">"Это NSFW сабреддит"</string>
<string name="this_user_has_nsfw_content">"У пользователь есть NSFW контент"</string>

View File

@ -847,7 +847,6 @@ Sekmeler, diğerlerine geçtikten sonra tüm içeriği kaybedebilir. Bu, sayfay
Mesaj: %2$s"</string>
<string name="give_award_success">"Ödül verildi"</string>
<string name="give_award_failed">"İşlem Başarısız Oldu"</string>
<string name="recent_searches">"Son aramalar"</string>
<string name="warning">"Uyarı"</string>
<string name="this_is_a_nsfw_subreddit">"Bu bir NSFW subredditidir."</string>
<string name="this_user_has_nsfw_content">"Bu kullanıcının NSFW içeriği var"</string>

View File

@ -832,7 +832,6 @@ Tự động phát video bị tắt."</string>
Thông báo: %2$s"</string>
<string name="give_award_success">"Giải thưởng đã được cho"</string>
<string name="give_award_failed">"Thất bại"</string>
<string name="recent_searches">"Tìm kiếm gần đây"</string>
<string name="warning">"Cảnh báo"</string>
<string name="this_is_a_nsfw_subreddit">"Đây là một subreddit NSFW."</string>
<string name="this_user_has_nsfw_content">"Người dùng này có nội dung NSFW"</string>

View File

@ -892,7 +892,6 @@ https://play.google.com/store/apps/details?id=ml.docilealligator.infinityforredd
错误信息:%2$s"</string>
<string name="give_award_success">"奖励已赠送"</string>
<string name="give_award_failed">"失败"</string>
<string name="recent_searches">"最近搜索"</string>
<string name="warning">"警告"</string>
<string name="this_is_a_nsfw_subreddit">"这是一个 NSFW 版块。"</string>
<string name="this_user_has_nsfw_content">"该用户有 NSFW 内容"</string>

View File

@ -1002,8 +1002,6 @@
<string name="give_award_success">Award given</string>
<string name="give_award_failed">Failed</string>
<string name="recent_searches">Recent searches</string>
<string name="warning">Warning</string>
<string name="this_is_a_nsfw_subreddit">This is a NSFW subreddit.</string>
<string name="this_user_has_nsfw_content">This user has NSFW content</string>