Merge branch 'master' into gallery-captions-feature

This commit is contained in:
scria1000 2021-11-27 17:10:50 +00:00 committed by GitHub
commit a399200be2
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
59 changed files with 1137 additions and 947 deletions

View File

@ -6,8 +6,8 @@ android {
applicationId "ml.docilealligator.infinityforreddit"
minSdkVersion 21
targetSdkVersion 30
versionCode 82
versionName "5.1.0-beta2"
versionCode 86
versionName "5.1.2"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
javaCompileOptions {
annotationProcessorOptions {
@ -154,6 +154,7 @@ dependencies {
implementation "io.noties.markwon:recycler-table:$markwonVersion"
implementation "io.noties.markwon:simple-ext:$markwonVersion"
implementation "io.noties.markwon:html:$markwonVersion"
implementation "io.noties.markwon:inline-parser:$markwonVersion"
implementation 'com.atlassian.commonmark:commonmark-ext-gfm-tables:0.14.0'
implementation 'me.saket:better-link-movement-method:2.2.0'

View File

@ -25,7 +25,7 @@
<uses-permission android:name="android.permission.WAKE_LOCK" />
<application
android:name=".Infinity"
android:name="ml.docilealligator.infinityforreddit.Infinity"
android:allowBackup="true"
android:icon="@mipmap/ic_launcher"
android:label="@string/application_name"
@ -34,6 +34,11 @@
android:theme="@style/AppTheme"
android:usesCleartextTraffic="true"
tools:replace="android:label">
<activity android:name=".activities.EditProfileActivity"
android:label="@string/edit_profile_activity_label"
android:parentActivityName=".activities.MainActivity"
android:theme="@style/AppTheme.Slidable"
android:windowSoftInputMode="adjustPan" />
<activity
android:name=".activities.WikiActivity"
android:label="@string/wiki_activity_label"
@ -393,11 +398,6 @@
android:parentActivityName=".activities.MainActivity"
android:theme="@style/AppTheme.SlidableWithTranslucentWindow" />
<activity android:name=".activities.EditProfileActivity"
android:parentActivityName=".activities.MainActivity"
android:theme="@style/AppTheme.SlidableWithTranslucentWindow"
android:windowSoftInputMode="adjustPan" />
<provider
android:name="androidx.core.content.FileProvider"
android:authorities="ml.docilealligator.infinityforreddit.provider"

View File

@ -43,6 +43,9 @@ public class Infinity extends Application implements LifecycleObserver {
private boolean canStartLockScreenActivity = false;
private boolean isSecureMode;
@Inject
@Named("default")
SharedPreferences mSharedPreferences;
@Inject
@Named("security")
SharedPreferences mSecuritySharedPreferences;
@ -127,7 +130,7 @@ public class Infinity extends Application implements LifecycleObserver {
new NetworkWifiStatusReceiver(() -> EventBus.getDefault().post(new ChangeNetworkStatusEvent(Utils.getConnectedNetwork(getApplicationContext()))));
registerReceiver(mNetworkWifiStatusReceiver, new IntentFilter(ConnectivityManager.CONNECTIVITY_ACTION));
registerReceiver(new WallpaperChangeReceiver(), new IntentFilter(Intent.ACTION_WALLPAPER_CHANGED));
registerReceiver(new WallpaperChangeReceiver(mSharedPreferences), new IntentFilter(Intent.ACTION_WALLPAPER_CHANGED));
}
@OnLifecycleEvent(Lifecycle.Event.ON_START)

View File

@ -0,0 +1,29 @@
package ml.docilealligator.infinityforreddit;
import com.bumptech.glide.load.resource.bitmap.DownsampleStrategy;
public class SaveMemoryCenterInisdeDownsampleStrategy extends DownsampleStrategy {
@Override
public float getScaleFactor(int sourceWidth, int sourceHeight, int requestedWidth, int requestedHeight) {
int originalSourceWidth = sourceWidth;
int originalSourceHeight = sourceHeight;
if (sourceWidth * sourceHeight > 5_000_000) {
int divisor = 2;
do {
sourceWidth /= divisor;
sourceHeight /= divisor;
} while (sourceWidth * sourceHeight > 5_000_000);
}
float widthPercentage = (float) requestedWidth / (float) sourceWidth;
float heightPercentage = (float) requestedHeight / (float) sourceHeight;
return Math.min((float) sourceWidth / (float) originalSourceWidth, (float) sourceHeight / (float) originalSourceHeight) * Math.min(1.f, Math.min(widthPercentage, heightPercentage));
}
@Override
public SampleSizeRounding getSampleSizeRounding(int sourceWidth, int sourceHeight, int requestedWidth, int requestedHeight) {
return SampleSizeRounding.MEMORY;
}
}

View File

@ -129,10 +129,10 @@ public abstract class BaseActivity extends AppCompatActivity {
}
}
boolean userDefinedChangeSatusBarIconColorInImmersiveInterface =
boolean userDefinedChangeStatusBarIconColorInImmersiveInterface =
customThemeWrapper.isChangeStatusBarIconColorAfterToolbarCollapsedInImmersiveInterface();
if (immersiveInterface && isImmersiveInterfaceApplicable) {
changeStatusBarIconColor = userDefinedChangeSatusBarIconColorInImmersiveInterface;
changeStatusBarIconColor = userDefinedChangeStatusBarIconColorInImmersiveInterface;
} else {
changeStatusBarIconColor = false;
}

View File

@ -51,6 +51,10 @@ import io.noties.markwon.MarkwonConfiguration;
import io.noties.markwon.core.MarkwonTheme;
import io.noties.markwon.ext.strikethrough.StrikethroughPlugin;
import io.noties.markwon.html.HtmlPlugin;
import io.noties.markwon.html.tag.SuperScriptHandler;
import io.noties.markwon.inlineparser.BangInlineProcessor;
import io.noties.markwon.inlineparser.HtmlInlineProcessor;
import io.noties.markwon.inlineparser.MarkwonInlineParserPlugin;
import io.noties.markwon.linkify.LinkifyPlugin;
import io.noties.markwon.recycler.MarkwonAdapter;
import io.noties.markwon.recycler.table.TableEntry;
@ -68,6 +72,7 @@ import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
import ml.docilealligator.infinityforreddit.customviews.LinearLayoutManagerBugFixed;
import ml.docilealligator.infinityforreddit.events.SwitchAccountEvent;
import ml.docilealligator.infinityforreddit.utils.SharedPreferencesUtils;
import ml.docilealligator.infinityforreddit.markdown.SuperscriptInlineProcessor;
import ml.docilealligator.infinityforreddit.utils.Utils;
import retrofit2.Retrofit;
@ -160,8 +165,21 @@ public class CommentActivity extends BaseActivity implements UploadImageEnabledA
int linkColor = mCustomThemeWrapper.getLinkColor();
Markwon markwon = Markwon.builder(this)
.usePlugin(HtmlPlugin.create())
.usePlugin(MarkwonInlineParserPlugin.create(plugin -> {
plugin.excludeInlineProcessor(HtmlInlineProcessor.class);
plugin.excludeInlineProcessor(BangInlineProcessor.class);
plugin.addInlineProcessor(new SuperscriptInlineProcessor());
}))
.usePlugin(HtmlPlugin.create(plugin -> {
plugin.excludeDefaults(true).addHandler(new SuperScriptHandler());
}))
.usePlugin(new AbstractMarkwonPlugin() {
@NonNull
@Override
public String processMarkdown(@NonNull String markdown) {
return super.processMarkdown(Utils.fixSuperScript(markdown));
}
@Override
public void configureConfiguration(@NonNull MarkwonConfiguration.Builder builder) {
builder.linkResolver((view, link) -> {
@ -201,8 +219,21 @@ public class CommentActivity extends BaseActivity implements UploadImageEnabledA
contentMarkdownRecyclerView.setVisibility(View.VISIBLE);
contentMarkdownRecyclerView.setNestedScrollingEnabled(false);
Markwon postBodyMarkwon = Markwon.builder(this)
.usePlugin(HtmlPlugin.create())
.usePlugin(MarkwonInlineParserPlugin.create(plugin -> {
plugin.excludeInlineProcessor(HtmlInlineProcessor.class);
plugin.excludeInlineProcessor(BangInlineProcessor.class);
plugin.addInlineProcessor(new SuperscriptInlineProcessor());
}))
.usePlugin(HtmlPlugin.create(plugin -> {
plugin.excludeDefaults(true).addHandler(new SuperScriptHandler());
}))
.usePlugin(new AbstractMarkwonPlugin() {
@NonNull
@Override
public String processMarkdown(@NonNull String markdown) {
return super.processMarkdown(Utils.fixSuperScript(markdown));
}
@Override
public void beforeSetText(@NonNull TextView textView, @NonNull Spanned markdown) {
textView.setTextColor(markdownColor);

View File

@ -2,6 +2,7 @@ package ml.docilealligator.infinityforreddit.activities;
import android.content.Intent;
import android.content.SharedPreferences;
import android.os.Build;
import android.os.Bundle;
import android.view.Gravity;
import android.view.Menu;
@ -17,7 +18,6 @@ import android.widget.Toast;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import androidx.appcompat.widget.Toolbar;
import androidx.coordinatorlayout.widget.CoordinatorLayout;
import androidx.core.content.ContextCompat;
import androidx.lifecycle.ViewModelProvider;
@ -26,6 +26,8 @@ import com.bumptech.glide.Glide;
import com.bumptech.glide.RequestManager;
import com.bumptech.glide.request.RequestOptions;
import com.google.android.material.appbar.AppBarLayout;
import com.google.android.material.appbar.CollapsingToolbarLayout;
import com.google.android.material.appbar.MaterialToolbar;
import com.google.android.material.dialog.MaterialAlertDialogBuilder;
import com.r0adkll.slidr.Slidr;
import com.r0adkll.slidr.model.SlidrInterface;
@ -50,6 +52,7 @@ import ml.docilealligator.infinityforreddit.services.EditProfileService;
import ml.docilealligator.infinityforreddit.user.UserViewModel;
import ml.docilealligator.infinityforreddit.utils.EditProfileUtils;
import ml.docilealligator.infinityforreddit.utils.SharedPreferencesUtils;
import pl.droidsonroids.gif.GifImageView;
import retrofit2.Retrofit;
public class EditProfileActivity extends BaseActivity {
@ -61,14 +64,16 @@ public class EditProfileActivity extends BaseActivity {
CoordinatorLayout root;
@BindView(R.id.content_view_edit_profile_activity)
LinearLayout content;
@BindView(R.id.collapsing_toolbar_layout_edit_profile_activity)
CollapsingToolbarLayout collapsingToolbarLayout;
@BindView(R.id.appbar_layout_view_edit_profile_activity)
AppBarLayout appBarLayout;
@BindView(R.id.toolbar_view_edit_profile_activity)
Toolbar toolbar;
MaterialToolbar toolbar;
@BindView(R.id.image_view_banner_edit_profile_activity)
ImageView bannerImageView;
GifImageView bannerImageView;
@BindView(R.id.image_view_avatar_edit_profile_activity)
ImageView avatarImageView;
GifImageView avatarImageView;
@BindView(R.id.image_view_change_banner_edit_profile_activity)
ImageView changeBanner;
@BindView(R.id.image_view_change_avatar_edit_profile_activity)
@ -92,20 +97,28 @@ public class EditProfileActivity extends BaseActivity {
@Inject
CustomThemeWrapper mCustomThemeWrapper;
//
private String mAccountName;
private String mAccessToken;
@Override
protected void onCreate(@Nullable Bundle savedInstanceState) {
((Infinity) getApplication()).getAppComponent().inject(this);
setTransparentStatusBarAfterToolbarCollapsed();
setImmersiveModeNotApplicable();
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_edit_profile);
ButterKnife.bind(this);
EventBus.getDefault().register(this);
applyCustomTheme();
adjustToolbar(toolbar);
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && isChangeStatusBarIconColor()) {
addOnOffsetChangedListener(appBarLayout);
}
setSupportActionBar(toolbar);
if (mSharedPreferences.getBoolean(SharedPreferencesUtils.SWIPE_RIGHT_TO_GO_BACK, true)) {
@ -130,22 +143,26 @@ public class EditProfileActivity extends BaseActivity {
new ViewModelProvider(this, userViewModelFactory).get(UserViewModel.class);
userViewModel.getUserLiveData().observe(this, userData -> {
if (userData == null) return;//
if (userData == null) {
return;
}
// BANNER
final String userBanner = userData.getBanner();
LayoutParams cBannerLp = (LayoutParams) changeBanner.getLayoutParams();
if (userBanner == null || userBanner.isEmpty()) {
changeBanner.setLongClickable(false);
changeBanner.setImageResource(R.drawable.ic_add_day_night_24dp);
changeBanner.setLayoutParams(new LayoutParams(cBannerLp.width, cBannerLp.height, Gravity.CENTER));
cBannerLp.gravity = Gravity.CENTER;
changeBanner.setLayoutParams(cBannerLp);
changeBanner.setOnLongClickListener(v -> false);
} else {
changeBanner.setLongClickable(true);
changeBanner.setImageResource(R.drawable.ic_outline_add_a_photo_day_night_24dp);
changeBanner.setLayoutParams(new LayoutParams(cBannerLp.width, cBannerLp.height, Gravity.END | Gravity.BOTTOM));
cBannerLp.gravity = Gravity.END | Gravity.BOTTOM;
changeBanner.setLayoutParams(cBannerLp);
glide.load(userBanner).into(bannerImageView);
changeBanner.setOnLongClickListener(view -> {
if (mAccessToken == null) return false;
if (mAccessToken == null) {
return false;
}
new MaterialAlertDialogBuilder(this, R.style.MaterialAlertDialogTheme)
.setTitle(R.string.remove_banner)
.setMessage(R.string.are_you_sure)
@ -182,15 +199,13 @@ public class EditProfileActivity extends BaseActivity {
LayoutParams cAvatarLp = (LayoutParams) changeAvatar.getLayoutParams();
if (userAvatar.contains("avatar_default_")) {
changeAvatar.setLongClickable(false);
changeAvatar.setImageResource(R.drawable.ic_add_day_night_24dp);
changeAvatar.setLayoutParams(new LayoutParams(cAvatarLp.width, cAvatarLp.height, Gravity.CENTER));
changeAvatar.setOnLongClickListener(v -> false);
} else {
changeAvatar.setLongClickable(true);
changeAvatar.setImageResource(R.drawable.ic_outline_add_a_photo_day_night_24dp);
changeAvatar.setLayoutParams(new LayoutParams(cAvatarLp.width, cAvatarLp.height, Gravity.END | Gravity.BOTTOM));
changeAvatar.setOnLongClickListener(view -> {
if (mAccessToken == null) return false;
if (mAccessToken == null) {
return false;
}
new MaterialAlertDialogBuilder(this, R.style.MaterialAlertDialogTheme)
.setTitle(R.string.remove_avatar)
.setMessage(R.string.are_you_sure)
@ -328,8 +343,9 @@ public class EditProfileActivity extends BaseActivity {
@Override
protected void applyCustomTheme() {
applyAppBarLayoutAndCollapsingToolbarLayoutAndToolbarTheme(appBarLayout, null, toolbar);
applyAppBarLayoutAndCollapsingToolbarLayoutAndToolbarTheme(appBarLayout, collapsingToolbarLayout, toolbar);
root.setBackgroundColor(mCustomThemeWrapper.getBackgroundColor());
changeColorTextView(content, mCustomThemeWrapper.getPrimaryTextColor());
}

View File

@ -33,7 +33,6 @@ import org.commonmark.ext.gfm.tables.TableBlock;
import org.greenrobot.eventbus.EventBus;
import org.greenrobot.eventbus.Subscribe;
import java.util.ArrayList;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
@ -48,6 +47,10 @@ import io.noties.markwon.MarkwonConfiguration;
import io.noties.markwon.core.MarkwonTheme;
import io.noties.markwon.ext.strikethrough.StrikethroughPlugin;
import io.noties.markwon.html.HtmlPlugin;
import io.noties.markwon.html.tag.SuperScriptHandler;
import io.noties.markwon.inlineparser.BangInlineProcessor;
import io.noties.markwon.inlineparser.HtmlInlineProcessor;
import io.noties.markwon.inlineparser.MarkwonInlineParserPlugin;
import io.noties.markwon.linkify.LinkifyPlugin;
import io.noties.markwon.recycler.MarkwonAdapter;
import io.noties.markwon.recycler.table.TableEntry;
@ -58,7 +61,11 @@ import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
import ml.docilealligator.infinityforreddit.customviews.LinearLayoutManagerBugFixed;
import ml.docilealligator.infinityforreddit.customviews.MarkwonLinearLayoutManager;
import ml.docilealligator.infinityforreddit.events.SwitchAccountEvent;
import ml.docilealligator.infinityforreddit.markdown.SpoilerParserPlugin;
import ml.docilealligator.infinityforreddit.markdown.SpoilerSpan;
import ml.docilealligator.infinityforreddit.utils.SharedPreferencesUtils;
import ml.docilealligator.infinityforreddit.markdown.SuperscriptInlineProcessor;
import ml.docilealligator.infinityforreddit.utils.Utils;
public class FullMarkdownActivity extends BaseActivity {
@ -131,67 +138,19 @@ public class FullMarkdownActivity extends BaseActivity {
int spoilerBackgroundColor = markdownColor | 0xFF000000;
int linkColor = mCustomThemeWrapper.getLinkColor();
Markwon markwon = Markwon.builder(this)
.usePlugin(HtmlPlugin.create())
.usePlugin(MarkwonInlineParserPlugin.create(plugin -> {
plugin.excludeInlineProcessor(HtmlInlineProcessor.class);
plugin.excludeInlineProcessor(BangInlineProcessor.class);
plugin.addInlineProcessor(new SuperscriptInlineProcessor());
}))
.usePlugin(HtmlPlugin.create(plugin -> {
plugin.excludeDefaults(true).addHandler(new SuperScriptHandler());
}))
.usePlugin(new AbstractMarkwonPlugin() {
@NonNull
@Override
public String processMarkdown(@NonNull String markdown) {
StringBuilder markdownStringBuilder = new StringBuilder(markdown);
Pattern spoilerPattern = Pattern.compile(">![\\S\\s]+?!<");
Matcher matcher = spoilerPattern.matcher(markdownStringBuilder);
ArrayList<Integer> matched = new ArrayList<>();
while (matcher.find()) {
matched.add(matcher.start());
}
for (int i = matched.size() - 1; i >= 0; i--) {
markdownStringBuilder.replace(matched.get(i), matched.get(i) + 1, "&gt;");
}
return super.processMarkdown(markdownStringBuilder.toString());
}
@Override
public void afterSetText(@NonNull TextView textView) {
textView.setHighlightColor(Color.TRANSPARENT);
SpannableStringBuilder markdownStringBuilder = new SpannableStringBuilder(textView.getText().toString());
Pattern spoilerPattern = Pattern.compile(">![\\S\\s]+?!<");
Matcher matcher = spoilerPattern.matcher(markdownStringBuilder);
int start = 0;
boolean find = false;
while (matcher.find(start)) {
if (markdownStringBuilder.length() < 4
|| matcher.start() < 0
|| matcher.end() > markdownStringBuilder.length()) {
break;
}
find = true;
markdownStringBuilder.delete(matcher.end() - 2, matcher.end());
markdownStringBuilder.delete(matcher.start(), matcher.start() + 2);
ClickableSpan clickableSpan = new ClickableSpan() {
private boolean isShowing = false;
@Override
public void updateDrawState(@NonNull TextPaint ds) {
if (isShowing) {
super.updateDrawState(ds);
ds.setColor(markdownColor);
} else {
ds.bgColor = spoilerBackgroundColor;
ds.setColor(markdownColor);
}
ds.setUnderlineText(false);
}
@Override
public void onClick(@NonNull View view) {
isShowing = !isShowing;
view.invalidate();
}
};
markdownStringBuilder.setSpan(clickableSpan, matcher.start(), matcher.end() - 4, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
start = matcher.end() - 4;
}
if (find) {
textView.setText(markdownStringBuilder);
}
return super.processMarkdown(Utils.fixSuperScript(markdown));
}
@Override
@ -215,6 +174,7 @@ public class FullMarkdownActivity extends BaseActivity {
builder.linkColor(linkColor);
}
})
.usePlugin(SpoilerParserPlugin.create(markdownColor, spoilerBackgroundColor))
.usePlugin(StrikethroughPlugin.create())
.usePlugin(LinkifyPlugin.create(Linkify.WEB_URLS))
.usePlugin(TableEntryPlugin.create(this))

View File

@ -38,7 +38,6 @@ import androidx.drawerlayout.widget.DrawerLayout;
import androidx.fragment.app.Fragment;
import androidx.fragment.app.FragmentActivity;
import androidx.fragment.app.FragmentManager;
import androidx.lifecycle.Observer;
import androidx.lifecycle.ViewModelProvider;
import androidx.recyclerview.widget.RecyclerView;
import androidx.viewpager2.adapter.FragmentStateAdapter;
@ -270,9 +269,6 @@ public class MainActivity extends BaseActivity implements SortTypeSelectionCallb
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
drawer.setFitsSystemWindows(false);
getWindow().setDecorFitsSystemWindows(false);
/*drawer.setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_STABLE |
View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN |
View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION);*/
} else {
window.setFlags(WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS, WindowManager.LayoutParams.FLAG_LAYOUT_NO_LIMITS);
}
@ -855,19 +851,6 @@ public class MainActivity extends BaseActivity implements SortTypeSelectionCallb
tabLayout.setTabMode(TabLayout.MODE_FIXED);
}
new TabLayoutMediator(tabLayout, viewPager2, (tab, position) -> {
if (mAccessToken == null) {
switch (position) {
case 0:
tab.setText(R.string.home);
break;
case 1:
tab.setText(R.string.popular);
break;
case 2:
tab.setText(R.string.all);
break;
}
} else {
switch (position) {
case 0:
tab.setText(mMainActivityTabsSharedPreferences.getString((mAccountName == null ? "" : mAccountName) + SharedPreferencesUtils.MAIN_PAGE_TAB_1_TITLE, getString(R.string.home)));
@ -901,7 +884,6 @@ public class MainActivity extends BaseActivity implements SortTypeSelectionCallb
- sectionsPagerAdapter.favoriteSubscribedSubreddits.size()).getName());
}
}
}
}).attach();
} else {
tabLayout.setVisibility(View.GONE);
@ -925,7 +907,7 @@ public class MainActivity extends BaseActivity implements SortTypeSelectionCallb
loadSubscriptions();
multiRedditViewModel = new ViewModelProvider(this, new MultiRedditViewModel.Factory(getApplication(),
mRedditDataRoomDatabase, mAccountName))
mRedditDataRoomDatabase, mAccountName == null ? "-" : mAccountName))
.get(MultiRedditViewModel.class);
multiRedditViewModel.getAllFavoriteMultiReddits().observe(this, multiReddits -> {
@ -934,17 +916,14 @@ public class MainActivity extends BaseActivity implements SortTypeSelectionCallb
}
});
multiRedditViewModel.getAllMultiReddits().observe(this, new Observer<List<MultiReddit>>() {
@Override
public void onChanged(List<MultiReddit> multiReddits) {
multiRedditViewModel.getAllMultiReddits().observe(this, multiReddits -> {
if (mShowMultiReddits && sectionsPagerAdapter != null) {
sectionsPagerAdapter.setMultiReddits(multiReddits);
}
}
});
subscribedSubredditViewModel = new ViewModelProvider(this,
new SubscribedSubredditViewModel.Factory(getApplication(), mRedditDataRoomDatabase, mAccountName))
new SubscribedSubredditViewModel.Factory(getApplication(), mRedditDataRoomDatabase, mAccountName == null ? "-" : mAccountName))
.get(SubscribedSubredditViewModel.class);
subscribedSubredditViewModel.getAllSubscribedSubreddits().observe(this,
subscribedSubredditData -> {
@ -1696,9 +1675,6 @@ public class MainActivity extends BaseActivity implements SortTypeSelectionCallb
@Override
public int getItemCount() {
if (mAccessToken == null) {
return 3;
}
return tabCount + favoriteMultiReddits.size() + multiReddits.size() +
favoriteSubscribedSubreddits.size() + subscribedSubreddits.size();
}

View File

@ -35,6 +35,7 @@ import com.bumptech.glide.request.RequestOptions;
import com.google.android.material.appbar.AppBarLayout;
import com.google.android.material.button.MaterialButton;
import com.google.android.material.dialog.MaterialAlertDialogBuilder;
import com.google.android.material.divider.MaterialDivider;
import com.google.android.material.snackbar.Snackbar;
import com.google.android.material.switchmaterial.SwitchMaterial;
import com.google.gson.Gson;
@ -110,27 +111,23 @@ public class PostGalleryActivity extends BaseActivity implements FlairBottomShee
@BindView(R.id.rules_button_post_gallery_activity)
MaterialButton rulesButton;
@BindView(R.id.divider_1_post_gallery_activity)
View divider1;
MaterialDivider divider1;
@BindView(R.id.flair_custom_text_view_post_gallery_activity)
CustomTextView flairTextView;
@BindView(R.id.spoiler_custom_text_view_post_gallery_activity)
CustomTextView spoilerTextView;
@BindView(R.id.nsfw_custom_text_view_post_gallery_activity)
CustomTextView nsfwTextView;
@BindView(R.id.divider_2_post_gallery_activity)
View divider2;
@BindView(R.id.receive_post_reply_notifications_linear_layout_post_gallery_activity)
LinearLayout receivePostReplyNotificationsLinearLayout;
@BindView(R.id.receive_post_reply_notifications_text_view_post_gallery_activity)
TextView receivePostReplyNotificationsTextView;
@BindView(R.id.receive_post_reply_notifications_switch_material_post_gallery_activity)
SwitchMaterial receivePostReplyNotificationsSwitchMaterial;
@BindView(R.id.divider_3_post_gallery_activity)
View divider3;
@BindView(R.id.divider_2_post_gallery_activity)
MaterialDivider divider2;
@BindView(R.id.post_title_edit_text_post_gallery_activity)
EditText titleEditText;
@BindView(R.id.divider_4_post_gallery_activity)
View divider4;
@BindView(R.id.images_recycler_view_post_gallery_activity)
RecyclerView imagesRecyclerView;
@Inject
@ -415,10 +412,8 @@ public class PostGalleryActivity extends BaseActivity implements FlairBottomShee
primaryTextColor = mCustomThemeWrapper.getPrimaryTextColor();
receivePostReplyNotificationsTextView.setTextColor(primaryTextColor);
int dividerColor = mCustomThemeWrapper.getDividerColor();
divider1.setBackgroundColor(dividerColor);
divider2.setBackgroundColor(dividerColor);
divider3.setBackgroundColor(dividerColor);
divider4.setBackgroundColor(dividerColor);
divider1.setDividerColor(dividerColor);
divider2.setDividerColor(dividerColor);
flairBackgroundColor = mCustomThemeWrapper.getFlairBackgroundColor();
flairTextColor = mCustomThemeWrapper.getFlairTextColor();
spoilerBackgroundColor = mCustomThemeWrapper.getSpoilerBackgroundColor();

View File

@ -32,6 +32,7 @@ import com.bumptech.glide.request.RequestOptions;
import com.google.android.material.appbar.AppBarLayout;
import com.google.android.material.button.MaterialButton;
import com.google.android.material.dialog.MaterialAlertDialogBuilder;
import com.google.android.material.divider.MaterialDivider;
import com.google.android.material.floatingactionbutton.FloatingActionButton;
import com.google.android.material.snackbar.Snackbar;
import com.google.android.material.switchmaterial.SwitchMaterial;
@ -97,27 +98,23 @@ public class PostImageActivity extends BaseActivity implements FlairBottomSheetF
@BindView(R.id.rules_button_post_image_activity)
MaterialButton rulesButton;
@BindView(R.id.divider_1_post_image_activity)
View divider1;
MaterialDivider divider1;
@BindView(R.id.flair_custom_text_view_post_image_activity)
CustomTextView flairTextView;
@BindView(R.id.spoiler_custom_text_view_post_image_activity)
CustomTextView spoilerTextView;
@BindView(R.id.nsfw_custom_text_view_post_image_activity)
CustomTextView nsfwTextView;
@BindView(R.id.divider_2_post_image_activity)
View divider2;
@BindView(R.id.receive_post_reply_notifications_linear_layout_post_image_activity)
LinearLayout receivePostReplyNotificationsLinearLayout;
@BindView(R.id.receive_post_reply_notifications_text_view_post_image_activity)
TextView receivePostReplyNotificationsTextView;
@BindView(R.id.receive_post_reply_notifications_switch_material_post_image_activity)
SwitchMaterial receivePostReplyNotificationsSwitchMaterial;
@BindView(R.id.divider_3_post_image_activity)
View divider3;
@BindView(R.id.divider_2_post_image_activity)
MaterialDivider divider2;
@BindView(R.id.post_title_edit_text_post_image_activity)
EditText titleEditText;
@BindView(R.id.divider_4_post_image_activity)
View divider4;
@BindView(R.id.select_image_constraint_layout_post_image_activity)
ConstraintLayout constraintLayout;
@BindView(R.id.capture_fab_post_image_activity)
@ -396,10 +393,8 @@ public class PostImageActivity extends BaseActivity implements FlairBottomSheetF
primaryTextColor = mCustomThemeWrapper.getPrimaryTextColor();
receivePostReplyNotificationsTextView.setTextColor(primaryTextColor);
int dividerColor = mCustomThemeWrapper.getDividerColor();
divider1.setBackgroundColor(dividerColor);
divider2.setBackgroundColor(dividerColor);
divider3.setBackgroundColor(dividerColor);
divider4.setBackgroundColor(dividerColor);
divider1.setDividerColor(dividerColor);
divider2.setDividerColor(dividerColor);
flairBackgroundColor = mCustomThemeWrapper.getFlairBackgroundColor();
flairTextColor = mCustomThemeWrapper.getFlairTextColor();
spoilerBackgroundColor = mCustomThemeWrapper.getSpoilerBackgroundColor();

View File

@ -26,6 +26,7 @@ import com.bumptech.glide.request.RequestOptions;
import com.google.android.material.appbar.AppBarLayout;
import com.google.android.material.button.MaterialButton;
import com.google.android.material.dialog.MaterialAlertDialogBuilder;
import com.google.android.material.divider.MaterialDivider;
import com.google.android.material.snackbar.Snackbar;
import com.google.android.material.switchmaterial.SwitchMaterial;
import com.libRG.CustomTextView;
@ -91,11 +92,9 @@ public class PostLinkActivity extends BaseActivity implements FlairBottomSheetFr
@BindView(R.id.rules_button_post_link_activity)
MaterialButton rulesButton;
@BindView(R.id.divider_1_post_link_activity)
View divider1;
MaterialDivider divider1;
@BindView(R.id.divider_2_post_link_activity)
View divider2;
@BindView(R.id.divider_4_post_link_activity)
View divider4;
MaterialDivider divider2;
@BindView(R.id.flair_custom_text_view_post_link_activity)
CustomTextView flairTextView;
@BindView(R.id.spoiler_custom_text_view_post_link_activity)
@ -108,8 +107,6 @@ public class PostLinkActivity extends BaseActivity implements FlairBottomSheetFr
TextView receivePostReplyNotificationsTextView;
@BindView(R.id.receive_post_reply_notifications_switch_material_post_link_activity)
SwitchMaterial receivePostReplyNotificationsSwitchMaterial;
@BindView(R.id.divider_3_post_link_activity)
View divider3;
@BindView(R.id.post_title_edit_text_post_link_activity)
EditText titleEditText;
@BindView(R.id.suggest_title_button_post_link_activity)
@ -370,10 +367,8 @@ public class PostLinkActivity extends BaseActivity implements FlairBottomSheetFr
primaryTextColor = mCustomThemeWrapper.getPrimaryTextColor();
receivePostReplyNotificationsTextView.setTextColor(primaryTextColor);
int dividerColor = mCustomThemeWrapper.getDividerColor();
divider1.setBackgroundColor(dividerColor);
divider2.setBackgroundColor(dividerColor);
divider3.setBackgroundColor(dividerColor);
divider4.setBackgroundColor(dividerColor);
divider1.setDividerColor(dividerColor);
divider2.setDividerColor(dividerColor);
flairBackgroundColor = mCustomThemeWrapper.getFlairBackgroundColor();
flairTextColor = mCustomThemeWrapper.getFlairTextColor();
spoilerBackgroundColor = mCustomThemeWrapper.getSpoilerBackgroundColor();

View File

@ -33,6 +33,7 @@ import com.bumptech.glide.request.RequestOptions;
import com.google.android.material.appbar.AppBarLayout;
import com.google.android.material.button.MaterialButton;
import com.google.android.material.dialog.MaterialAlertDialogBuilder;
import com.google.android.material.divider.MaterialDivider;
import com.google.android.material.snackbar.Snackbar;
import com.google.android.material.switchmaterial.SwitchMaterial;
import com.libRG.CustomTextView;
@ -107,27 +108,23 @@ public class PostTextActivity extends BaseActivity implements FlairBottomSheetFr
@BindView(R.id.rules_button_post_text_activity)
MaterialButton rulesButton;
@BindView(R.id.divider_1_post_text_activity)
View divider1;
MaterialDivider divider1;
@BindView(R.id.flair_custom_text_view_post_text_activity)
CustomTextView flairTextView;
@BindView(R.id.spoiler_custom_text_view_post_text_activity)
CustomTextView spoilerTextView;
@BindView(R.id.nsfw_custom_text_view_post_text_activity)
CustomTextView nsfwTextView;
@BindView(R.id.divider_2_post_text_activity)
View divider2;
@BindView(R.id.receive_post_reply_notifications_linear_layout_post_text_activity)
LinearLayout receivePostReplyNotificationsLinearLayout;
@BindView(R.id.receive_post_reply_notifications_text_view_post_text_activity)
TextView receivePostReplyNotificationsTextView;
@BindView(R.id.receive_post_reply_notifications_switch_material_post_text_activity)
SwitchMaterial receivePostReplyNotificationsSwitchMaterial;
@BindView(R.id.divider_3_post_text_activity)
View divider3;
@BindView(R.id.divider_2_post_text_activity)
MaterialDivider divider2;
@BindView(R.id.post_title_edit_text_post_text_activity)
EditText titleEditText;
@BindView(R.id.divider_4_post_text_activity)
View divider4;
@BindView(R.id.post_text_content_edit_text_post_text_activity)
EditText contentEditText;
@BindView(R.id.markdown_bottom_bar_recycler_view_post_text_activity)
@ -394,10 +391,8 @@ public class PostTextActivity extends BaseActivity implements FlairBottomSheetFr
primaryTextColor = mCustomThemeWrapper.getPrimaryTextColor();
receivePostReplyNotificationsTextView.setTextColor(primaryTextColor);
int dividerColor = mCustomThemeWrapper.getDividerColor();
divider1.setBackgroundColor(dividerColor);
divider2.setBackgroundColor(dividerColor);
divider3.setBackgroundColor(dividerColor);
divider4.setBackgroundColor(dividerColor);
divider1.setDividerColor(dividerColor);
divider2.setDividerColor(dividerColor);
flairBackgroundColor = mCustomThemeWrapper.getFlairBackgroundColor();
flairTextColor = mCustomThemeWrapper.getFlairTextColor();
spoilerBackgroundColor = mCustomThemeWrapper.getSpoilerBackgroundColor();

View File

@ -1,5 +1,6 @@
package ml.docilealligator.infinityforreddit.activities;
import android.content.ActivityNotFoundException;
import android.content.Intent;
import android.content.SharedPreferences;
import android.content.res.Resources;
@ -14,6 +15,7 @@ import android.view.View;
import android.widget.EditText;
import android.widget.LinearLayout;
import android.widget.TextView;
import android.widget.Toast;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
@ -36,6 +38,7 @@ import com.google.android.exoplayer2.util.Util;
import com.google.android.material.appbar.AppBarLayout;
import com.google.android.material.button.MaterialButton;
import com.google.android.material.dialog.MaterialAlertDialogBuilder;
import com.google.android.material.divider.MaterialDivider;
import com.google.android.material.floatingactionbutton.FloatingActionButton;
import com.google.android.material.snackbar.Snackbar;
import com.google.android.material.switchmaterial.SwitchMaterial;
@ -98,27 +101,23 @@ public class PostVideoActivity extends BaseActivity implements FlairBottomSheetF
@BindView(R.id.rules_button_post_video_activity)
MaterialButton rulesButton;
@BindView(R.id.divider_1_post_video_activity)
View divider1;
MaterialDivider divider1;
@BindView(R.id.flair_custom_text_view_post_video_activity)
CustomTextView flairTextView;
@BindView(R.id.spoiler_custom_text_view_post_video_activity)
CustomTextView spoilerTextView;
@BindView(R.id.nsfw_custom_text_view_post_video_activity)
CustomTextView nsfwTextView;
@BindView(R.id.divider_2_post_video_activity)
View divider2;
@BindView(R.id.receive_post_reply_notifications_linear_layout_post_video_activity)
LinearLayout receivePostReplyNotificationsLinearLayout;
@BindView(R.id.receive_post_reply_notifications_text_view_post_video_activity)
TextView receivePostReplyNotificationsTextView;
@BindView(R.id.receive_post_reply_notifications_switch_material_post_video_activity)
SwitchMaterial receivePostReplyNotificationsSwitchMaterial;
@BindView(R.id.divider_3_post_video_activity)
View divider3;
@BindView(R.id.divider_2_post_video_activity)
MaterialDivider divider2;
@BindView(R.id.post_title_edit_text_post_video_activity)
EditText titleEditText;
@BindView(R.id.divider_4_post_video_activity)
View divider4;
@BindView(R.id.select_video_constraint_layout_post_video_activity)
ConstraintLayout constraintLayout;
@BindView(R.id.capture_fab_post_video_activity)
@ -364,8 +363,10 @@ public class PostVideoActivity extends BaseActivity implements FlairBottomSheetF
captureFab.setOnClickListener(view -> {
Intent takeVideoIntent = new Intent(MediaStore.ACTION_VIDEO_CAPTURE);
if (takeVideoIntent.resolveActivity(getPackageManager()) != null) {
try {
startActivityForResult(takeVideoIntent, CAPTURE_VIDEO_REQUEST_CODE);
} catch (ActivityNotFoundException e) {
Toast.makeText(this, R.string.no_camera_available, Toast.LENGTH_SHORT).show();
}
});
@ -407,10 +408,8 @@ public class PostVideoActivity extends BaseActivity implements FlairBottomSheetF
primaryTextColor = mCustomThemeWrapper.getPrimaryTextColor();
receivePostReplyNotificationsTextView.setTextColor(primaryTextColor);
int dividerColor = mCustomThemeWrapper.getDividerColor();
divider1.setBackgroundColor(dividerColor);
divider2.setBackgroundColor(dividerColor);
divider3.setBackgroundColor(dividerColor);
divider4.setBackgroundColor(dividerColor);
divider1.setDividerColor(dividerColor);
divider2.setDividerColor(dividerColor);
flairBackgroundColor = mCustomThemeWrapper.getFlairBackgroundColor();
flairTextColor = mCustomThemeWrapper.getFlairTextColor();
spoilerBackgroundColor = mCustomThemeWrapper.getSpoilerBackgroundColor();

View File

@ -22,6 +22,7 @@ import androidx.recyclerview.widget.RecyclerView;
import androidx.swiperefreshlayout.widget.SwipeRefreshLayout;
import com.bumptech.glide.Glide;
import com.bumptech.glide.RequestManager;
import com.google.android.material.appbar.AppBarLayout;
import com.google.android.material.appbar.CollapsingToolbarLayout;
import com.r0adkll.slidr.Slidr;
@ -100,10 +101,10 @@ public class TrendingActivity extends BaseActivity {
@Inject
Executor mExecutor;
private String mAccessToken;
private String mAccountName;
private boolean isRefreshing = false;
private ArrayList<TrendingSearch> trendingSearches;
private TrendingSearchRecyclerViewAdapter adapter;
private RequestManager mGlide;
@Override
protected void onCreate(Bundle savedInstanceState) {
@ -151,7 +152,8 @@ public class TrendingActivity extends BaseActivity {
setToolbarGoToTop(toolbar);
mAccessToken = mCurrentAccountSharedPreferences.getString(SharedPreferencesUtils.ACCESS_TOKEN, null);
mAccountName = mCurrentAccountSharedPreferences.getString(SharedPreferencesUtils.ACCOUNT_NAME, null);
mGlide = Glide.with(this);
DisplayMetrics displayMetrics = new DisplayMetrics();
getWindowManager().getDefaultDisplay().getMetrics(displayMetrics);
@ -277,7 +279,7 @@ public class TrendingActivity extends BaseActivity {
private void showErrorView(int stringId) {
errorLinearLayout.setVisibility(View.VISIBLE);
Glide.with(this).load(R.drawable.error_image).into(errorImageView);
mGlide.load(R.drawable.error_image).into(errorImageView);
errorTextView.setText(stringId);
}

View File

@ -4,6 +4,7 @@ import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
import android.content.res.ColorStateList;
import android.graphics.PorterDuff;
import android.net.Uri;
import android.os.Build;
import android.os.Bundle;
@ -71,6 +72,9 @@ import io.noties.markwon.AbstractMarkwonPlugin;
import io.noties.markwon.Markwon;
import io.noties.markwon.MarkwonConfiguration;
import io.noties.markwon.core.MarkwonTheme;
import io.noties.markwon.inlineparser.BangInlineProcessor;
import io.noties.markwon.inlineparser.HtmlInlineProcessor;
import io.noties.markwon.inlineparser.MarkwonInlineParserPlugin;
import io.noties.markwon.linkify.LinkifyPlugin;
import io.noties.markwon.movement.MovementMethodPlugin;
import jp.wasabeef.glide.transformations.RoundedCornersTransformation;
@ -380,6 +384,10 @@ public class ViewSubredditDetailActivity extends BaseActivity implements SortTyp
Locale locale = getResources().getConfiguration().locale;
Markwon markwon = Markwon.builder(this)
.usePlugin(MarkwonInlineParserPlugin.create(plugin -> {
plugin.excludeInlineProcessor(HtmlInlineProcessor.class);
plugin.excludeInlineProcessor(BangInlineProcessor.class);
}))
.usePlugin(new AbstractMarkwonPlugin() {
@Override
public void configureConfiguration(@NonNull MarkwonConfiguration.Builder builder) {
@ -541,10 +549,10 @@ public class ViewSubredditDetailActivity extends BaseActivity implements SortTyp
descriptionTextView.setTextColor(primaryTextColor);
bottomNavigationView.setBackgroundTint(ColorStateList.valueOf(mCustomThemeWrapper.getBottomAppBarBackgroundColor()));
int bottomAppBarIconColor = mCustomThemeWrapper.getBottomAppBarIconColor();
option2BottomAppBar.setColorFilter(bottomAppBarIconColor, android.graphics.PorterDuff.Mode.SRC_IN);
option1BottomAppBar.setColorFilter(bottomAppBarIconColor, android.graphics.PorterDuff.Mode.SRC_IN);
option3BottomAppBar.setColorFilter(bottomAppBarIconColor, android.graphics.PorterDuff.Mode.SRC_IN);
option4BottomAppBar.setColorFilter(bottomAppBarIconColor, android.graphics.PorterDuff.Mode.SRC_IN);
option2BottomAppBar.setColorFilter(bottomAppBarIconColor, PorterDuff.Mode.SRC_IN);
option1BottomAppBar.setColorFilter(bottomAppBarIconColor, PorterDuff.Mode.SRC_IN);
option3BottomAppBar.setColorFilter(bottomAppBarIconColor, PorterDuff.Mode.SRC_IN);
option4BottomAppBar.setColorFilter(bottomAppBarIconColor, PorterDuff.Mode.SRC_IN);
applyTabLayoutTheme(tabLayout);
applyFABTheme(fab);
unsubscribedColor = mCustomThemeWrapper.getUnsubscribed();
@ -1137,12 +1145,17 @@ public class ViewSubredditDetailActivity extends BaseActivity implements SortTyp
Toast.makeText(this, R.string.no_app, Toast.LENGTH_SHORT).show();
}
return true;
} else if (itemId == R.id.action_go_to_wiki_activity ) {
} else if (itemId == R.id.action_go_to_wiki_view_subreddit_detail_activity) {
Intent wikiIntent = new Intent(this, WikiActivity.class);
wikiIntent.putExtra(WikiActivity.EXTRA_SUBREDDIT_NAME, subredditName);
wikiIntent.putExtra(WikiActivity.EXTRA_WIKI_PATH, "index");
startActivity(wikiIntent);
return true;
} else if (itemId == R.id.action_contact_mods_view_subreddit_detail_activity) {
Intent intent = new Intent(this, SendPrivateMessageActivity.class);
intent.putExtra(SendPrivateMessageActivity.EXTRA_RECIPIENT_USERNAME, "r/" + subredditName);
startActivity(intent);
return true;
}
return false;
}

View File

@ -5,6 +5,7 @@ import android.content.Intent;
import android.content.SharedPreferences;
import android.content.res.ColorStateList;
import android.content.res.Resources;
import android.graphics.PorterDuff;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.Build;
@ -73,6 +74,9 @@ import io.noties.markwon.AbstractMarkwonPlugin;
import io.noties.markwon.Markwon;
import io.noties.markwon.MarkwonConfiguration;
import io.noties.markwon.core.MarkwonTheme;
import io.noties.markwon.inlineparser.BangInlineProcessor;
import io.noties.markwon.inlineparser.HtmlInlineProcessor;
import io.noties.markwon.inlineparser.MarkwonInlineParserPlugin;
import io.noties.markwon.linkify.LinkifyPlugin;
import io.noties.markwon.movement.MovementMethodPlugin;
import jp.wasabeef.glide.transformations.RoundedCornersTransformation;
@ -376,6 +380,10 @@ public class ViewUserDetailActivity extends BaseActivity implements SortTypeSele
Locale locale = getResources().getConfiguration().locale;
Markwon markwon = Markwon.builder(this)
.usePlugin(MarkwonInlineParserPlugin.create(plugin -> {
plugin.excludeInlineProcessor(HtmlInlineProcessor.class);
plugin.excludeInlineProcessor(BangInlineProcessor.class);
}))
.usePlugin(new AbstractMarkwonPlugin() {
@Override
public void configureConfiguration(@NonNull MarkwonConfiguration.Builder builder) {
@ -635,10 +643,10 @@ public class ViewUserDetailActivity extends BaseActivity implements SortTypeSele
cakedayTextView.setTextColor(mCustomThemeWrapper.getPrimaryTextColor());
bottomNavigationView.setBackgroundTint(ColorStateList.valueOf(mCustomThemeWrapper.getBottomAppBarBackgroundColor()));
int bottomAppBarIconColor = mCustomThemeWrapper.getBottomAppBarIconColor();
option2BottomAppBar.setColorFilter(bottomAppBarIconColor, android.graphics.PorterDuff.Mode.SRC_IN);
option1BottomAppBar.setColorFilter(bottomAppBarIconColor, android.graphics.PorterDuff.Mode.SRC_IN);
option3BottomAppBar.setColorFilter(bottomAppBarIconColor, android.graphics.PorterDuff.Mode.SRC_IN);
option4BottomAppBar.setColorFilter(bottomAppBarIconColor, android.graphics.PorterDuff.Mode.SRC_IN);
option2BottomAppBar.setColorFilter(bottomAppBarIconColor, PorterDuff.Mode.SRC_IN);
option1BottomAppBar.setColorFilter(bottomAppBarIconColor, PorterDuff.Mode.SRC_IN);
option3BottomAppBar.setColorFilter(bottomAppBarIconColor, PorterDuff.Mode.SRC_IN);
option4BottomAppBar.setColorFilter(bottomAppBarIconColor, PorterDuff.Mode.SRC_IN);
applyFABTheme(fab);
descriptionTextView.setTextColor(mCustomThemeWrapper.getPrimaryTextColor());
subscribeUserChip.setTextColor(mCustomThemeWrapper.getChipTextColor());

View File

@ -1,6 +1,12 @@
package ml.docilealligator.infinityforreddit.activities;
import static androidx.appcompat.app.AppCompatDelegate.MODE_NIGHT_AUTO_BATTERY;
import static androidx.appcompat.app.AppCompatDelegate.MODE_NIGHT_FOLLOW_SYSTEM;
import static androidx.appcompat.app.AppCompatDelegate.MODE_NIGHT_NO;
import static androidx.appcompat.app.AppCompatDelegate.MODE_NIGHT_YES;
import android.Manifest;
import android.app.AlertDialog;
import android.content.Intent;
import android.content.SharedPreferences;
import android.content.pm.ActivityInfo;
@ -32,6 +38,7 @@ import android.widget.Toast;
import androidx.annotation.NonNull;
import androidx.appcompat.app.ActionBar;
import androidx.appcompat.app.AppCompatActivity;
import androidx.appcompat.app.AppCompatDelegate;
import androidx.coordinatorlayout.widget.CoordinatorLayout;
import androidx.core.app.ActivityCompat;
import androidx.core.content.ContextCompat;
@ -79,6 +86,7 @@ import ml.docilealligator.infinityforreddit.Infinity;
import ml.docilealligator.infinityforreddit.R;
import ml.docilealligator.infinityforreddit.apis.VReddIt;
import ml.docilealligator.infinityforreddit.bottomsheetfragments.PlaybackSpeedBottomSheetFragment;
import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
import ml.docilealligator.infinityforreddit.font.ContentFontFamily;
import ml.docilealligator.infinityforreddit.font.ContentFontStyle;
import ml.docilealligator.infinityforreddit.font.FontFamily;
@ -150,6 +158,8 @@ public class ViewVideoActivity extends AppCompatActivity {
TextView titleTextView;
@BindView(R.id.download_image_view_exo_playback_control_view)
ImageView downloadImageView;
@BindView(R.id.playback_speed_image_view_exo_playback_control_view)
ImageView playbackSpeedImageView;
@BindView(R.id.lockable_nested_scroll_view_view_video_activity)
LockableNestedScrollView nestedScrollView;
@ -194,6 +204,9 @@ public class ViewVideoActivity extends AppCompatActivity {
@Named("default")
SharedPreferences mSharedPreferences;
@Inject
CustomThemeWrapper mCustomThemeWrapper;
@Inject
Executor mExecutor;
@ -206,7 +219,37 @@ public class ViewVideoActivity extends AppCompatActivity {
((Infinity) getApplication()).getAppComponent().inject(this);
boolean systemDefault = Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q;
int systemThemeType = Integer.parseInt(mSharedPreferences.getString(SharedPreferencesUtils.THEME_KEY, "2"));
switch (systemThemeType) {
case 0:
AppCompatDelegate.setDefaultNightMode(MODE_NIGHT_NO);
getTheme().applyStyle(R.style.Theme_Normal, true);
break;
case 1:
AppCompatDelegate.setDefaultNightMode(MODE_NIGHT_YES);
if(mSharedPreferences.getBoolean(SharedPreferencesUtils.AMOLED_DARK_KEY, false)) {
getTheme().applyStyle(R.style.Theme_Normal_AmoledDark, true);
} else {
getTheme().applyStyle(R.style.Theme_Normal_NormalDark, true);
}
break;
case 2:
if (systemDefault) {
AppCompatDelegate.setDefaultNightMode(MODE_NIGHT_FOLLOW_SYSTEM);
} else {
AppCompatDelegate.setDefaultNightMode(MODE_NIGHT_AUTO_BATTERY);
}
if((getResources().getConfiguration().uiMode & Configuration.UI_MODE_NIGHT_MASK) == Configuration.UI_MODE_NIGHT_NO) {
getTheme().applyStyle(R.style.Theme_Normal, true);
} else {
if(mSharedPreferences.getBoolean(SharedPreferencesUtils.AMOLED_DARK_KEY, false)) {
getTheme().applyStyle(R.style.Theme_Normal_AmoledDark, true);
} else {
getTheme().applyStyle(R.style.Theme_Normal_NormalDark, true);
}
}
}
getTheme().applyStyle(FontStyle.valueOf(mSharedPreferences
.getString(SharedPreferencesUtils.FONT_SIZE_KEY, FontStyle.Normal.name())).getResId(), true);
@ -250,6 +293,14 @@ public class ViewVideoActivity extends AppCompatActivity {
isDownloading = true;
requestPermissionAndDownload();
});
playbackSpeedImageView.setOnClickListener(view -> {
PlaybackSpeedBottomSheetFragment playbackSpeedBottomSheetFragment = new PlaybackSpeedBottomSheetFragment();
Bundle bundle = new Bundle();
bundle.putInt(PlaybackSpeedBottomSheetFragment.EXTRA_PLAYBACK_SPEED, playbackSpeed);
playbackSpeedBottomSheetFragment.setArguments(bundle);
playbackSpeedBottomSheetFragment.show(getSupportFragmentManager(), playbackSpeedBottomSheetFragment.getTag());
});
} else {
ActionBar actionBar = getSupportActionBar();
Drawable upArrow = resources.getDrawable(R.drawable.ic_arrow_back_white_24dp);
@ -520,10 +571,13 @@ public class ViewVideoActivity extends AppCompatActivity {
hdButton.setVisibility(View.VISIBLE);
hdButton.setOnClickListener(view -> {
TrackSelectionDialogBuilder build = new TrackSelectionDialogBuilder(ViewVideoActivity.this, getString(R.string.select_video_quality), trackSelector, 0);
build.setShowDisableOption(true);
build.setAllowAdaptiveSelections(false);
build.build().show();
TrackSelectionDialogBuilder builder = new TrackSelectionDialogBuilder(ViewVideoActivity.this, getString(R.string.select_video_quality), trackSelector, 0);
builder.setShowDisableOption(true);
builder.setAllowAdaptiveSelections(false);
AlertDialog alertDialog = builder.build();
alertDialog.show();
alertDialog.getButton(AlertDialog.BUTTON_POSITIVE).setTextColor(mCustomThemeWrapper.getPrimaryTextColor());
alertDialog.getButton(AlertDialog.BUTTON_NEGATIVE).setTextColor(mCustomThemeWrapper.getPrimaryTextColor());
});
}

View File

@ -26,6 +26,7 @@ import androidx.recyclerview.widget.RecyclerView;
import androidx.swiperefreshlayout.widget.SwipeRefreshLayout;
import com.bumptech.glide.Glide;
import com.bumptech.glide.RequestManager;
import com.google.android.material.appbar.AppBarLayout;
import com.google.android.material.appbar.CollapsingToolbarLayout;
import com.r0adkll.slidr.Slidr;
@ -37,7 +38,6 @@ import org.greenrobot.eventbus.Subscribe;
import org.json.JSONException;
import org.json.JSONObject;
import java.util.ArrayList;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
@ -52,6 +52,10 @@ import io.noties.markwon.MarkwonConfiguration;
import io.noties.markwon.core.MarkwonTheme;
import io.noties.markwon.ext.strikethrough.StrikethroughPlugin;
import io.noties.markwon.html.HtmlPlugin;
import io.noties.markwon.html.tag.SuperScriptHandler;
import io.noties.markwon.inlineparser.BangInlineProcessor;
import io.noties.markwon.inlineparser.HtmlInlineProcessor;
import io.noties.markwon.inlineparser.MarkwonInlineParserPlugin;
import io.noties.markwon.linkify.LinkifyPlugin;
import io.noties.markwon.recycler.MarkwonAdapter;
import io.noties.markwon.recycler.table.TableEntry;
@ -63,8 +67,12 @@ import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
import ml.docilealligator.infinityforreddit.customviews.LinearLayoutManagerBugFixed;
import ml.docilealligator.infinityforreddit.customviews.MarkwonLinearLayoutManager;
import ml.docilealligator.infinityforreddit.events.SwitchAccountEvent;
import ml.docilealligator.infinityforreddit.markdown.SpoilerParserPlugin;
import ml.docilealligator.infinityforreddit.markdown.SpoilerSpan;
import ml.docilealligator.infinityforreddit.utils.JSONUtils;
import ml.docilealligator.infinityforreddit.utils.SharedPreferencesUtils;
import ml.docilealligator.infinityforreddit.markdown.SuperscriptInlineProcessor;
import ml.docilealligator.infinityforreddit.utils.Utils;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
@ -108,6 +116,7 @@ public class WikiActivity extends BaseActivity {
private Markwon markwon;
private MarkwonAdapter markwonAdapter;
private boolean isRefreshing = false;
private RequestManager mGlide;
@Override
protected void onCreate(Bundle savedInstanceState) {
@ -149,6 +158,8 @@ public class WikiActivity extends BaseActivity {
}
}
mGlide = Glide.with(this);
swipeRefreshLayout.setEnabled(mSharedPreferences.getBoolean(SharedPreferencesUtils.PULL_TO_REFRESH, true));
swipeRefreshLayout.setOnRefreshListener(this::loadWiki);
@ -156,67 +167,19 @@ public class WikiActivity extends BaseActivity {
int spoilerBackgroundColor = markdownColor | 0xFF000000;
int linkColor = mCustomThemeWrapper.getLinkColor();
markwon = Markwon.builder(this)
.usePlugin(HtmlPlugin.create())
.usePlugin(MarkwonInlineParserPlugin.create(plugin -> {
plugin.excludeInlineProcessor(HtmlInlineProcessor.class);
plugin.excludeInlineProcessor(BangInlineProcessor.class);
plugin.addInlineProcessor(new SuperscriptInlineProcessor());
}))
.usePlugin(HtmlPlugin.create(plugin -> {
plugin.excludeDefaults(true).addHandler(new SuperScriptHandler());
}))
.usePlugin(new AbstractMarkwonPlugin() {
@NonNull
@Override
public String processMarkdown(@NonNull String markdown) {
StringBuilder markdownStringBuilder = new StringBuilder(markdown);
Pattern spoilerPattern = Pattern.compile(">![\\S\\s]+?!<");
Matcher matcher = spoilerPattern.matcher(markdownStringBuilder);
ArrayList<Integer> matched = new ArrayList<>();
while (matcher.find()) {
matched.add(matcher.start());
}
for (int i = matched.size() - 1; i >= 0; i--) {
markdownStringBuilder.replace(matched.get(i), matched.get(i) + 1, "&gt;");
}
return super.processMarkdown(markdownStringBuilder.toString());
}
@Override
public void afterSetText(@NonNull TextView textView) {
textView.setHighlightColor(Color.TRANSPARENT);
SpannableStringBuilder markdownStringBuilder = new SpannableStringBuilder(textView.getText().toString());
Pattern spoilerPattern = Pattern.compile(">![\\S\\s]+?!<");
Matcher matcher = spoilerPattern.matcher(markdownStringBuilder);
int start = 0;
boolean find = false;
while (matcher.find(start)) {
if (markdownStringBuilder.length() < 4
|| matcher.start() < 0
|| matcher.end() > markdownStringBuilder.length()) {
break;
}
find = true;
markdownStringBuilder.delete(matcher.end() - 2, matcher.end());
markdownStringBuilder.delete(matcher.start(), matcher.start() + 2);
ClickableSpan clickableSpan = new ClickableSpan() {
private boolean isShowing = false;
@Override
public void updateDrawState(@NonNull TextPaint ds) {
if (isShowing) {
super.updateDrawState(ds);
ds.setColor(markdownColor);
} else {
ds.bgColor = spoilerBackgroundColor;
ds.setColor(markdownColor);
}
ds.setUnderlineText(false);
}
@Override
public void onClick(@NonNull View view) {
isShowing = !isShowing;
view.invalidate();
}
};
markdownStringBuilder.setSpan(clickableSpan, matcher.start(), matcher.end() - 4, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
start = matcher.end() - 4;
}
if (find) {
textView.setText(markdownStringBuilder);
}
return super.processMarkdown(Utils.fixSuperScript(markdown));
}
@Override
@ -239,6 +202,7 @@ public class WikiActivity extends BaseActivity {
builder.linkColor(linkColor);
}
})
.usePlugin(SpoilerParserPlugin.create(markdownColor, spoilerBackgroundColor))
.usePlugin(StrikethroughPlugin.create())
.usePlugin(LinkifyPlugin.create(Linkify.WEB_URLS))
.usePlugin(TableEntryPlugin.create(this))
@ -326,7 +290,7 @@ public class WikiActivity extends BaseActivity {
swipeRefreshLayout.setRefreshing(false);
mFetchWikiInfoLinearLayout.setVisibility(View.VISIBLE);
mFetchWikiInfoTextView.setText(stringResId);
Glide.with(this).load(R.drawable.error_image).into(mFetchWikiInfoImageView);
mGlide.load(R.drawable.error_image).into(mFetchWikiInfoImageView);
}
@Override

View File

@ -4,6 +4,7 @@ import android.content.Intent;
import android.content.SharedPreferences;
import android.content.res.ColorStateList;
import android.graphics.Color;
import android.graphics.PorterDuff;
import android.net.Uri;
import android.os.Bundle;
import android.text.SpannableStringBuilder;
@ -30,7 +31,6 @@ import androidx.recyclerview.widget.DiffUtil;
import androidx.recyclerview.widget.ItemTouchHelper;
import androidx.recyclerview.widget.RecyclerView;
import java.util.ArrayList;
import java.util.Locale;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
@ -43,6 +43,10 @@ import io.noties.markwon.MarkwonConfiguration;
import io.noties.markwon.core.MarkwonTheme;
import io.noties.markwon.ext.strikethrough.StrikethroughPlugin;
import io.noties.markwon.html.HtmlPlugin;
import io.noties.markwon.html.tag.SuperScriptHandler;
import io.noties.markwon.inlineparser.BangInlineProcessor;
import io.noties.markwon.inlineparser.HtmlInlineProcessor;
import io.noties.markwon.inlineparser.MarkwonInlineParserPlugin;
import io.noties.markwon.linkify.LinkifyPlugin;
import me.saket.bettermovementmethod.BetterLinkMovementMethod;
import ml.docilealligator.infinityforreddit.NetworkState;
@ -59,8 +63,11 @@ import ml.docilealligator.infinityforreddit.comment.Comment;
import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
import ml.docilealligator.infinityforreddit.customviews.CommentIndentationView;
import ml.docilealligator.infinityforreddit.customviews.SpoilerOnClickTextView;
import ml.docilealligator.infinityforreddit.markdown.SpoilerParserPlugin;
import ml.docilealligator.infinityforreddit.markdown.SpoilerSpan;
import ml.docilealligator.infinityforreddit.utils.APIUtils;
import ml.docilealligator.infinityforreddit.utils.SharedPreferencesUtils;
import ml.docilealligator.infinityforreddit.markdown.SuperscriptInlineProcessor;
import ml.docilealligator.infinityforreddit.utils.Utils;
import retrofit2.Retrofit;
@ -116,72 +123,19 @@ public class CommentsListingRecyclerViewAdapter extends PagedListAdapter<Comment
mCommentColor = customThemeWrapper.getCommentColor();
int commentSpoilerBackgroundColor = mCommentColor | 0xFF000000;
mMarkwon = Markwon.builder(mActivity)
.usePlugin(HtmlPlugin.create())
.usePlugin(MarkwonInlineParserPlugin.create(plugin -> {
plugin.excludeInlineProcessor(HtmlInlineProcessor.class);
plugin.excludeInlineProcessor(BangInlineProcessor.class);
plugin.addInlineProcessor(new SuperscriptInlineProcessor());
}))
.usePlugin(HtmlPlugin.create(plugin -> {
plugin.excludeDefaults(true).addHandler(new SuperScriptHandler());
}))
.usePlugin(new AbstractMarkwonPlugin() {
@NonNull
@Override
public String processMarkdown(@NonNull String markdown) {
StringBuilder markdownStringBuilder = new StringBuilder(markdown);
Pattern spoilerPattern = Pattern.compile(">![\\S\\s]+?!<");
Matcher matcher = spoilerPattern.matcher(markdownStringBuilder);
ArrayList<Integer> matched = new ArrayList<>();
while (matcher.find()) {
matched.add(matcher.start());
}
for (int i = matched.size() - 1; i >= 0; i--) {
markdownStringBuilder.replace(matched.get(i), matched.get(i) + 1, "&gt;");
}
return super.processMarkdown(markdownStringBuilder.toString());
}
@Override
public void afterSetText(@NonNull TextView textView) {
textView.setHighlightColor(Color.TRANSPARENT);
SpannableStringBuilder markdownStringBuilder = new SpannableStringBuilder(textView.getText().toString());
Pattern spoilerPattern = Pattern.compile(">![\\S\\s]+?!<");
Matcher matcher = spoilerPattern.matcher(markdownStringBuilder);
int start = 0;
boolean find = false;
while (matcher.find(start)) {
if (markdownStringBuilder.length() < 4
|| matcher.start() < 0
|| matcher.end() > markdownStringBuilder.length()) {
break;
}
find = true;
markdownStringBuilder.delete(matcher.end() - 2, matcher.end());
markdownStringBuilder.delete(matcher.start(), matcher.start() + 2);
int matcherStart = matcher.start();
int matcherEnd = matcher.end();
ClickableSpan clickableSpan = new ClickableSpan() {
private boolean isShowing = false;
@Override
public void updateDrawState(@NonNull TextPaint ds) {
if (isShowing) {
super.updateDrawState(ds);
ds.setColor(mCommentColor);
} else {
ds.bgColor = commentSpoilerBackgroundColor;
ds.setColor(mCommentColor);
}
ds.setUnderlineText(false);
}
@Override
public void onClick(@NonNull View view) {
if (textView instanceof SpoilerOnClickTextView) {
((SpoilerOnClickTextView) textView).setSpoilerOnClick(true);
}
isShowing = !isShowing;
view.invalidate();
}
};
markdownStringBuilder.setSpan(clickableSpan, matcherStart, matcherEnd - 4, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
start = matcherEnd - 4;
}
if (find) {
textView.setText(markdownStringBuilder);
}
return super.processMarkdown(Utils.fixSuperScript(markdown));
}
@Override
@ -200,6 +154,7 @@ public class CommentsListingRecyclerViewAdapter extends PagedListAdapter<Comment
}
})
.usePlugin(SpoilerParserPlugin.create(mCommentColor, commentSpoilerBackgroundColor))
.usePlugin(LinkifyPlugin.create(Linkify.WEB_URLS))
.usePlugin(StrikethroughPlugin.create())
.build();
@ -282,12 +237,12 @@ public class CommentsListingRecyclerViewAdapter extends PagedListAdapter<Comment
switch (comment.getVoteType()) {
case Comment.VOTE_TYPE_UPVOTE:
((CommentViewHolder) holder).upvoteButton
.setColorFilter(mUpvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
.setColorFilter(mUpvotedColor, PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).scoreTextView.setTextColor(mUpvotedColor);
break;
case Comment.VOTE_TYPE_DOWNVOTE:
((CommentViewHolder) holder).downvoteButton
.setColorFilter(mDownvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
.setColorFilter(mDownvotedColor, PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).scoreTextView.setTextColor(mDownvotedColor);
break;
}
@ -322,8 +277,8 @@ public class CommentsListingRecyclerViewAdapter extends PagedListAdapter<Comment
((CommentViewHolder) holder).authorFlairTextView.setVisibility(View.GONE);
((CommentViewHolder) holder).awardsTextView.setText("");
((CommentViewHolder) holder).awardsTextView.setVisibility(View.GONE);
((CommentViewHolder) holder).upvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).downvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).upvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).downvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).scoreTextView.setTextColor(mCommentIconAndInfoColor);
}
}
@ -470,13 +425,13 @@ public class CommentsListingRecyclerViewAdapter extends PagedListAdapter<Comment
commentTimeTextView.setTextColor(mSecondaryTextColor);
awardsTextView.setTextColor(mSecondaryTextColor);
commentMarkdownView.setTextColor(mCommentColor);
upvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
upvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mCommentIconAndInfoColor);
downvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
moreButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
expandButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
saveButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
replyButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
moreButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
expandButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
saveButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
replyButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
commentDivider.setBackgroundColor(mDividerColor);
authorTextView.setOnClickListener(view -> {
@ -566,20 +521,20 @@ public class CommentsListingRecyclerViewAdapter extends PagedListAdapter<Comment
int previousVoteType = comment.getVoteType();
String newVoteType;
downvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
if (previousVoteType != Comment.VOTE_TYPE_UPVOTE) {
//Not upvoted before
comment.setVoteType(Comment.VOTE_TYPE_UPVOTE);
newVoteType = APIUtils.DIR_UPVOTE;
upvoteButton
.setColorFilter(mUpvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
.setColorFilter(mUpvotedColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mUpvotedColor);
} else {
//Upvoted before
comment.setVoteType(Comment.VOTE_TYPE_NO_VOTE);
newVoteType = APIUtils.DIR_UNVOTE;
upvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
upvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mCommentIconAndInfoColor);
}
@ -593,19 +548,19 @@ public class CommentsListingRecyclerViewAdapter extends PagedListAdapter<Comment
if (newVoteType.equals(APIUtils.DIR_UPVOTE)) {
comment.setVoteType(Comment.VOTE_TYPE_UPVOTE);
if (currentPosition == position) {
upvoteButton.setColorFilter(mUpvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
upvoteButton.setColorFilter(mUpvotedColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mUpvotedColor);
}
} else {
comment.setVoteType(Comment.VOTE_TYPE_NO_VOTE);
if (currentPosition == position) {
upvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
upvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mCommentIconAndInfoColor);
}
}
if (currentPosition == position) {
downvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setText(Utils.getNVotes(mShowAbsoluteNumberOfVotes,
comment.getScore() + comment.getVoteType()));
}
@ -633,19 +588,19 @@ public class CommentsListingRecyclerViewAdapter extends PagedListAdapter<Comment
int previousVoteType = comment.getVoteType();
String newVoteType;
upvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
upvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
if (previousVoteType != Comment.VOTE_TYPE_DOWNVOTE) {
//Not downvoted before
comment.setVoteType(Comment.VOTE_TYPE_DOWNVOTE);
newVoteType = APIUtils.DIR_DOWNVOTE;
downvoteButton.setColorFilter(mDownvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mDownvotedColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mDownvotedColor);
} else {
//Downvoted before
comment.setVoteType(Comment.VOTE_TYPE_NO_VOTE);
newVoteType = APIUtils.DIR_UNVOTE;
downvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mCommentIconAndInfoColor);
}
@ -659,19 +614,19 @@ public class CommentsListingRecyclerViewAdapter extends PagedListAdapter<Comment
if (newVoteType.equals(APIUtils.DIR_DOWNVOTE)) {
comment.setVoteType(Comment.VOTE_TYPE_DOWNVOTE);
if (currentPosition == position) {
downvoteButton.setColorFilter(mDownvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mDownvotedColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mDownvotedColor);
}
} else {
comment.setVoteType(Comment.VOTE_TYPE_NO_VOTE);
if (currentPosition == position) {
downvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mCommentIconAndInfoColor);
}
}
if (currentPosition == position) {
upvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
upvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setText(Utils.getNVotes(mShowAbsoluteNumberOfVotes,
comment.getScore() + comment.getVoteType()));
}

View File

@ -4,14 +4,11 @@ import android.content.Intent;
import android.content.SharedPreferences;
import android.content.res.ColorStateList;
import android.graphics.Color;
import android.graphics.PorterDuff;
import android.graphics.drawable.Drawable;
import android.net.Uri;
import android.os.Bundle;
import android.os.Handler;
import android.text.SpannableStringBuilder;
import android.text.Spanned;
import android.text.TextPaint;
import android.text.style.ClickableSpan;
import android.text.util.Linkify;
import android.view.LayoutInflater;
import android.view.View;
@ -37,8 +34,6 @@ import com.lsjwzh.widget.materialloadingprogressbar.CircleProgressBar;
import java.util.ArrayList;
import java.util.Locale;
import java.util.concurrent.Executor;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import butterknife.BindView;
import butterknife.ButterKnife;
@ -48,6 +43,11 @@ import io.noties.markwon.MarkwonConfiguration;
import io.noties.markwon.core.MarkwonTheme;
import io.noties.markwon.ext.strikethrough.StrikethroughPlugin;
import io.noties.markwon.html.HtmlPlugin;
import io.noties.markwon.html.tag.SuperScriptHandler;
import io.noties.markwon.inlineparser.BackslashInlineProcessor;
import io.noties.markwon.inlineparser.BangInlineProcessor;
import io.noties.markwon.inlineparser.HtmlInlineProcessor;
import io.noties.markwon.inlineparser.MarkwonInlineParserPlugin;
import io.noties.markwon.linkify.LinkifyPlugin;
import io.noties.markwon.movement.MovementMethodPlugin;
import me.saket.bettermovementmethod.BetterLinkMovementMethod;
@ -66,6 +66,8 @@ import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
import ml.docilealligator.infinityforreddit.customviews.CommentIndentationView;
import ml.docilealligator.infinityforreddit.customviews.SpoilerOnClickTextView;
import ml.docilealligator.infinityforreddit.fragments.ViewPostDetailFragment;
import ml.docilealligator.infinityforreddit.markdown.SpoilerParserPlugin;
import ml.docilealligator.infinityforreddit.markdown.SuperscriptInlineProcessor;
import ml.docilealligator.infinityforreddit.post.Post;
import ml.docilealligator.infinityforreddit.utils.APIUtils;
import ml.docilealligator.infinityforreddit.utils.SharedPreferencesUtils;
@ -160,68 +162,19 @@ public class CommentsRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVi
int commentSpoilerBackgroundColor = mCommentTextColor | 0xFF000000;
int linkColor = customThemeWrapper.getLinkColor();
mCommentMarkwon = Markwon.builder(mActivity)
.usePlugin(HtmlPlugin.create())
.usePlugin(MarkwonInlineParserPlugin.create(plugin -> {
plugin.excludeInlineProcessor(HtmlInlineProcessor.class);
plugin.excludeInlineProcessor(BangInlineProcessor.class);
plugin.addInlineProcessor(new SuperscriptInlineProcessor());
}))
.usePlugin(HtmlPlugin.create(plugin -> {
plugin.excludeDefaults(true).addHandler(new SuperScriptHandler());
}))
.usePlugin(new AbstractMarkwonPlugin() {
@NonNull
@Override
public String processMarkdown(@NonNull String markdown) {
StringBuilder markdownStringBuilder = new StringBuilder(markdown);
Pattern spoilerPattern = Pattern.compile(">![\\S\\s]+?!<");
Matcher matcher = spoilerPattern.matcher(markdownStringBuilder);
ArrayList<Integer> matched = new ArrayList<>();
while (matcher.find()) {
matched.add(matcher.start());
}
for (int i = matched.size() - 1; i >= 0; i--) {
markdownStringBuilder.replace(matched.get(i), matched.get(i) + 1, "&gt;");
}
return super.processMarkdown(markdownStringBuilder.toString());
}
@Override
public void afterSetText(@NonNull TextView textView) {
SpannableStringBuilder markdownStringBuilder = new SpannableStringBuilder(textView.getText().toString());
Pattern spoilerPattern = Pattern.compile(">![\\S\\s]+?!<");
Matcher matcher = spoilerPattern.matcher(markdownStringBuilder);
int start = 0;
boolean find = false;
while (matcher.find(start)) {
if (markdownStringBuilder.length() < 4
|| matcher.start() < 0
|| matcher.end() > markdownStringBuilder.length()) {
break;
}
find = true;
markdownStringBuilder.delete(matcher.end() - 2, matcher.end());
markdownStringBuilder.delete(matcher.start(), matcher.start() + 2);
ClickableSpan clickableSpan = new ClickableSpan() {
private boolean isShowing = false;
@Override
public void updateDrawState(@NonNull TextPaint ds) {
if (isShowing) {
super.updateDrawState(ds);
} else {
ds.bgColor = commentSpoilerBackgroundColor;
}
ds.setColor(mCommentTextColor);
ds.setUnderlineText(false);
}
@Override
public void onClick(@NonNull View view) {
if (textView instanceof SpoilerOnClickTextView) {
((SpoilerOnClickTextView) textView).setSpoilerOnClick(true);
}
isShowing = !isShowing;
view.invalidate();
}
};
markdownStringBuilder.setSpan(clickableSpan, matcher.start(), matcher.end() - 4, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
start = matcher.end() - 4;
}
if (find) {
textView.setText(markdownStringBuilder);
}
return super.processMarkdown(Utils.fixSuperScript(markdown));
}
@Override
@ -240,6 +193,7 @@ public class CommentsRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVi
builder.linkColor(linkColor);
}
})
.usePlugin(SpoilerParserPlugin.create(mCommentTextColor, commentSpoilerBackgroundColor))
.usePlugin(StrikethroughPlugin.create())
.usePlugin(MovementMethodPlugin.create(BetterLinkMovementMethod.newInstance().setOnLinkLongClickListener((textView, url) -> {
if (!activity.isDestroyed() && !activity.isFinishing()) {
@ -486,13 +440,13 @@ public class CommentsRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVi
switch (comment.getVoteType()) {
case Comment.VOTE_TYPE_UPVOTE:
((CommentViewHolder) holder).upvoteButton
.setColorFilter(mUpvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
.setColorFilter(mUpvotedColor, PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).scoreTextView.setTextColor(mUpvotedColor);
((CommentViewHolder) holder).topScoreTextView.setTextColor(mUpvotedColor);
break;
case Comment.VOTE_TYPE_DOWNVOTE:
((CommentViewHolder) holder).downvoteButton
.setColorFilter(mDownvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
.setColorFilter(mDownvotedColor, PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).scoreTextView.setTextColor(mDownvotedColor);
((CommentViewHolder) holder).topScoreTextView.setTextColor(mDownvotedColor);
break;
@ -501,19 +455,19 @@ public class CommentsRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVi
if (mPost.isArchived()) {
((CommentViewHolder) holder).replyButton
.setColorFilter(mVoteAndReplyUnavailableVoteButtonColor,
android.graphics.PorterDuff.Mode.SRC_IN);
PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).upvoteButton
.setColorFilter(mVoteAndReplyUnavailableVoteButtonColor,
android.graphics.PorterDuff.Mode.SRC_IN);
PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).downvoteButton
.setColorFilter(mVoteAndReplyUnavailableVoteButtonColor,
android.graphics.PorterDuff.Mode.SRC_IN);
PorterDuff.Mode.SRC_IN);
}
if (mPost.isLocked()) {
((CommentViewHolder) holder).replyButton
.setColorFilter(mVoteAndReplyUnavailableVoteButtonColor,
android.graphics.PorterDuff.Mode.SRC_IN);
PorterDuff.Mode.SRC_IN);
}
if (comment.isSaved()) {
@ -1059,10 +1013,10 @@ public class CommentsRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVi
((CommentViewHolder) holder).awardsTextView.setText("");
((CommentViewHolder) holder).awardsTextView.setVisibility(View.GONE);
((CommentViewHolder) holder).expandButton.setVisibility(View.GONE);
((CommentViewHolder) holder).upvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).upvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).scoreTextView.setTextColor(mCommentIconAndInfoColor);
((CommentViewHolder) holder).downvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).replyButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).downvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
((CommentViewHolder) holder).replyButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
}
}
@ -1171,13 +1125,13 @@ public class CommentsRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVi
topScoreTextView.setTextColor(mSecondaryTextColor);
awardsTextView.setTextColor(mSecondaryTextColor);
commentDivider.setBackgroundColor(mDividerColor);
upvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
upvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mCommentIconAndInfoColor);
downvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
moreButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
expandButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
saveButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
replyButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
moreButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
expandButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
saveButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
replyButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
authorFlairTextView.setOnClickListener(view -> authorTextView.performClick());
@ -1254,20 +1208,20 @@ public class CommentsRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVi
int previousVoteType = comment.getVoteType();
String newVoteType;
downvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
if (previousVoteType != Comment.VOTE_TYPE_UPVOTE) {
//Not upvoted before
comment.setVoteType(Comment.VOTE_TYPE_UPVOTE);
newVoteType = APIUtils.DIR_UPVOTE;
upvoteButton.setColorFilter(mUpvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
upvoteButton.setColorFilter(mUpvotedColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mUpvotedColor);
topScoreTextView.setTextColor(mUpvotedColor);
} else {
//Upvoted before
comment.setVoteType(Comment.VOTE_TYPE_NO_VOTE);
newVoteType = APIUtils.DIR_UNVOTE;
upvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
upvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mCommentIconAndInfoColor);
topScoreTextView.setTextColor(mSecondaryTextColor);
}
@ -1286,21 +1240,21 @@ public class CommentsRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVi
if (newVoteType.equals(APIUtils.DIR_UPVOTE)) {
comment.setVoteType(Comment.VOTE_TYPE_UPVOTE);
if (currentPosition == position) {
upvoteButton.setColorFilter(mUpvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
upvoteButton.setColorFilter(mUpvotedColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mUpvotedColor);
topScoreTextView.setTextColor(mUpvotedColor);
}
} else {
comment.setVoteType(Comment.VOTE_TYPE_NO_VOTE);
if (currentPosition == position) {
upvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
upvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mCommentIconAndInfoColor);
topScoreTextView.setTextColor(mSecondaryTextColor);
}
}
if (currentPosition == position) {
downvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setText(Utils.getNVotes(mShowAbsoluteNumberOfVotes,
comment.getScore() + comment.getVoteType()));
topScoreTextView.setText(mActivity.getString(R.string.top_score,
@ -1332,20 +1286,20 @@ public class CommentsRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVi
int previousVoteType = comment.getVoteType();
String newVoteType;
upvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
upvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
if (previousVoteType != Comment.VOTE_TYPE_DOWNVOTE) {
//Not downvoted before
comment.setVoteType(Comment.VOTE_TYPE_DOWNVOTE);
newVoteType = APIUtils.DIR_DOWNVOTE;
downvoteButton.setColorFilter(mDownvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mDownvotedColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mDownvotedColor);
topScoreTextView.setTextColor(mDownvotedColor);
} else {
//Downvoted before
comment.setVoteType(Comment.VOTE_TYPE_NO_VOTE);
newVoteType = APIUtils.DIR_UNVOTE;
downvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mCommentIconAndInfoColor);
topScoreTextView.setTextColor(mSecondaryTextColor);
}
@ -1364,21 +1318,21 @@ public class CommentsRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerVi
if (newVoteType.equals(APIUtils.DIR_DOWNVOTE)) {
comment.setVoteType(Comment.VOTE_TYPE_DOWNVOTE);
if (currentPosition == position) {
downvoteButton.setColorFilter(mDownvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mDownvotedColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mDownvotedColor);
topScoreTextView.setTextColor(mDownvotedColor);
}
} else {
comment.setVoteType(Comment.VOTE_TYPE_NO_VOTE);
if (currentPosition == position) {
downvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
downvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setTextColor(mCommentIconAndInfoColor);
topScoreTextView.setTextColor(mSecondaryTextColor);
}
}
if (currentPosition == position) {
upvoteButton.setColorFilter(mCommentIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
upvoteButton.setColorFilter(mCommentIconAndInfoColor, PorterDuff.Mode.SRC_IN);
scoreTextView.setText(Utils.getNVotes(mShowAbsoluteNumberOfVotes,
comment.getScore() + comment.getVoteType()));
topScoreTextView.setText(mActivity.getString(R.string.top_score,

View File

@ -35,6 +35,10 @@ import io.noties.markwon.MarkwonConfiguration;
import io.noties.markwon.core.MarkwonTheme;
import io.noties.markwon.ext.strikethrough.StrikethroughPlugin;
import io.noties.markwon.html.HtmlPlugin;
import io.noties.markwon.html.tag.SuperScriptHandler;
import io.noties.markwon.inlineparser.BangInlineProcessor;
import io.noties.markwon.inlineparser.HtmlInlineProcessor;
import io.noties.markwon.inlineparser.MarkwonInlineParserPlugin;
import io.noties.markwon.linkify.LinkifyPlugin;
import ml.docilealligator.infinityforreddit.NetworkState;
import ml.docilealligator.infinityforreddit.R;
@ -42,9 +46,13 @@ import ml.docilealligator.infinityforreddit.activities.LinkResolverActivity;
import ml.docilealligator.infinityforreddit.activities.ViewPrivateMessagesActivity;
import ml.docilealligator.infinityforreddit.activities.ViewUserDetailActivity;
import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
import ml.docilealligator.infinityforreddit.markdown.SpoilerParserPlugin;
import ml.docilealligator.infinityforreddit.markdown.SpoilerSpan;
import ml.docilealligator.infinityforreddit.message.FetchMessage;
import ml.docilealligator.infinityforreddit.message.Message;
import ml.docilealligator.infinityforreddit.message.ReadMessage;
import ml.docilealligator.infinityforreddit.markdown.SuperscriptInlineProcessor;
import ml.docilealligator.infinityforreddit.utils.Utils;
import retrofit2.Retrofit;
public class MessageRecyclerViewAdapter extends PagedListAdapter<Message, RecyclerView.ViewHolder> {
@ -99,69 +107,19 @@ public class MessageRecyclerViewAdapter extends PagedListAdapter<Message, Recycl
mButtonTextColor = customThemeWrapper.getButtonTextColor();
mMarkwon = Markwon.builder(mContext)
.usePlugin(HtmlPlugin.create())
.usePlugin(MarkwonInlineParserPlugin.create(plugin -> {
plugin.excludeInlineProcessor(HtmlInlineProcessor.class);
plugin.excludeInlineProcessor(BangInlineProcessor.class);
plugin.addInlineProcessor(new SuperscriptInlineProcessor());
}))
.usePlugin(HtmlPlugin.create(plugin -> {
plugin.excludeDefaults(true).addHandler(new SuperScriptHandler());
}))
.usePlugin(new AbstractMarkwonPlugin() {
@NonNull
@Override
public String processMarkdown(@NonNull String markdown) {
StringBuilder markdownStringBuilder = new StringBuilder(markdown);
Pattern spoilerPattern = Pattern.compile(">![\\S\\s]+?!<");
Matcher matcher = spoilerPattern.matcher(markdownStringBuilder);
ArrayList<Integer> matched = new ArrayList<>();
while (matcher.find()) {
matched.add(matcher.start());
}
for (int i = matched.size() - 1; i >= 0; i--) {
markdownStringBuilder.replace(matched.get(i), matched.get(i) + 1, "&gt;");
}
return super.processMarkdown(markdownStringBuilder.toString());
}
@Override
public void afterSetText(@NonNull TextView textView) {
textView.setHighlightColor(Color.TRANSPARENT);
SpannableStringBuilder markdownStringBuilder = new SpannableStringBuilder(textView.getText().toString());
Pattern spoilerPattern = Pattern.compile(">![\\S\\s]+?!<");
Matcher matcher = spoilerPattern.matcher(markdownStringBuilder);
int start = 0;
boolean find = false;
while (matcher.find(start)) {
if (markdownStringBuilder.length() < 4
|| matcher.start() < 0
|| matcher.end() > markdownStringBuilder.length()) {
break;
}
find = true;
markdownStringBuilder.delete(matcher.end() - 2, matcher.end());
markdownStringBuilder.delete(matcher.start(), matcher.start() + 2);
int matcherStart = matcher.start();
int matcherEnd = matcher.end();
ClickableSpan clickableSpan = new ClickableSpan() {
private boolean isShowing = false;
@Override
public void updateDrawState(@NonNull TextPaint ds) {
if (isShowing) {
super.updateDrawState(ds);
ds.setColor(mSecondaryTextColor);
} else {
ds.bgColor = spoilerBackgroundColor;
ds.setColor(mSecondaryTextColor);
}
ds.setUnderlineText(false);
}
@Override
public void onClick(@NonNull View view) {
isShowing = !isShowing;
view.invalidate();
}
};
markdownStringBuilder.setSpan(clickableSpan, matcherStart, matcherEnd - 4, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
start = matcherEnd - 4;
}
if (find) {
textView.setText(markdownStringBuilder);
}
return super.processMarkdown(Utils.fixSuperScript(markdown));
}
@Override
@ -179,6 +137,7 @@ public class MessageRecyclerViewAdapter extends PagedListAdapter<Message, Recycl
builder.linkColor(customThemeWrapper.getLinkColor());
}
})
.usePlugin(SpoilerParserPlugin.create(mSecondaryTextColor, spoilerBackgroundColor))
.usePlugin(StrikethroughPlugin.create())
.usePlugin(LinkifyPlugin.create(Linkify.WEB_URLS))
.build();

View File

@ -74,6 +74,10 @@ import io.noties.markwon.MarkwonConfiguration;
import io.noties.markwon.core.MarkwonTheme;
import io.noties.markwon.ext.strikethrough.StrikethroughPlugin;
import io.noties.markwon.html.HtmlPlugin;
import io.noties.markwon.html.tag.SuperScriptHandler;
import io.noties.markwon.inlineparser.BangInlineProcessor;
import io.noties.markwon.inlineparser.HtmlInlineProcessor;
import io.noties.markwon.inlineparser.MarkwonInlineParserPlugin;
import io.noties.markwon.linkify.LinkifyPlugin;
import io.noties.markwon.movement.MovementMethodPlugin;
import io.noties.markwon.recycler.MarkwonAdapter;
@ -83,6 +87,7 @@ import jp.wasabeef.glide.transformations.BlurTransformation;
import jp.wasabeef.glide.transformations.RoundedCornersTransformation;
import me.saket.bettermovementmethod.BetterLinkMovementMethod;
import ml.docilealligator.infinityforreddit.FetchGfycatOrRedgifsVideoLinks;
import ml.docilealligator.infinityforreddit.SaveMemoryCenterInisdeDownsampleStrategy;
import ml.docilealligator.infinityforreddit.R;
import ml.docilealligator.infinityforreddit.RedditDataRoomDatabase;
import ml.docilealligator.infinityforreddit.SaveThing;
@ -106,10 +111,13 @@ import ml.docilealligator.infinityforreddit.customviews.AspectRatioGifImageView;
import ml.docilealligator.infinityforreddit.customviews.LinearLayoutManagerBugFixed;
import ml.docilealligator.infinityforreddit.customviews.MarkwonLinearLayoutManager;
import ml.docilealligator.infinityforreddit.fragments.ViewPostDetailFragment;
import ml.docilealligator.infinityforreddit.markdown.SpoilerParserPlugin;
import ml.docilealligator.infinityforreddit.markdown.SpoilerSpan;
import ml.docilealligator.infinityforreddit.post.Post;
import ml.docilealligator.infinityforreddit.post.PostPagingSource;
import ml.docilealligator.infinityforreddit.utils.APIUtils;
import ml.docilealligator.infinityforreddit.utils.SharedPreferencesUtils;
import ml.docilealligator.infinityforreddit.markdown.SuperscriptInlineProcessor;
import ml.docilealligator.infinityforreddit.utils.Utils;
import pl.droidsonroids.gif.GifImageView;
import retrofit2.Retrofit;
@ -134,7 +142,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
private RedditDataRoomDatabase mRedditDataRoomDatabase;
private RequestManager mGlide;
private Markwon mPostDetailMarkwon;
private int mImageViewWidth;
private final MarkwonAdapter mMarkwonAdapter;
private String mAccessToken;
private String mAccountName;
private Post mPost;
@ -204,7 +212,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
Executor executor, CustomThemeWrapper customThemeWrapper,
Retrofit retrofit, Retrofit oauthRetrofit, Retrofit gfycatRetrofit,
Retrofit redgifsRetrofit, RedditDataRoomDatabase redditDataRoomDatabase,
RequestManager glide, int imageViewWidth,
RequestManager glide,
boolean separatePostAndComments, String accessToken,
String accountName, Post post, Locale locale,
SharedPreferences sharedPreferences,
@ -226,68 +234,19 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
int postSpoilerBackgroundColor = markdownColor | 0xFF000000;
int linkColor = customThemeWrapper.getLinkColor();
mPostDetailMarkwon = Markwon.builder(mActivity)
.usePlugin(HtmlPlugin.create())
.usePlugin(MarkwonInlineParserPlugin.create(plugin -> {
plugin.excludeInlineProcessor(HtmlInlineProcessor.class);
plugin.excludeInlineProcessor(BangInlineProcessor.class);
plugin.addInlineProcessor(new SuperscriptInlineProcessor());
}))
.usePlugin(HtmlPlugin.create(plugin -> {
plugin.excludeDefaults(true).addHandler(new SuperScriptHandler());
}))
.usePlugin(new AbstractMarkwonPlugin() {
@NonNull
@Override
public String processMarkdown(@NonNull String markdown) {
StringBuilder markdownStringBuilder = new StringBuilder(markdown);
Pattern spoilerPattern = Pattern.compile(">![\\S\\s]+?!<");
Matcher matcher = spoilerPattern.matcher(markdownStringBuilder);
ArrayList<Integer> matched = new ArrayList<>();
while (matcher.find()) {
matched.add(matcher.start());
}
for (int i = matched.size() - 1; i >= 0; i--) {
markdownStringBuilder.replace(matched.get(i), matched.get(i) + 1, "&gt;");
}
return super.processMarkdown(markdownStringBuilder.toString());
}
@Override
public void afterSetText(@NonNull TextView textView) {
textView.setHighlightColor(Color.TRANSPARENT);
SpannableStringBuilder markdownStringBuilder = new SpannableStringBuilder(textView.getText().toString());
Pattern spoilerPattern = Pattern.compile(">![\\S\\s]+?!<");
Matcher matcher = spoilerPattern.matcher(markdownStringBuilder);
int start = 0;
boolean find = false;
while (matcher.find(start)) {
if (markdownStringBuilder.length() < 4
|| matcher.start() < 0
|| matcher.end() > markdownStringBuilder.length()) {
break;
}
find = true;
markdownStringBuilder.delete(matcher.end() - 2, matcher.end());
markdownStringBuilder.delete(matcher.start(), matcher.start() + 2);
ClickableSpan clickableSpan = new ClickableSpan() {
private boolean isShowing = false;
@Override
public void updateDrawState(@NonNull TextPaint ds) {
if (isShowing) {
super.updateDrawState(ds);
ds.setColor(markdownColor);
} else {
ds.bgColor = postSpoilerBackgroundColor;
ds.setColor(markdownColor);
}
ds.setUnderlineText(false);
}
@Override
public void onClick(@NonNull View view) {
isShowing = !isShowing;
view.invalidate();
}
};
markdownStringBuilder.setSpan(clickableSpan, matcher.start(), matcher.end() - 4, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
start = matcher.end() - 4;
}
if (find) {
textView.setText(markdownStringBuilder);
}
return super.processMarkdown(Utils.fixSuperScript(markdown));
}
@Override
@ -322,6 +281,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
builder.linkColor(linkColor);
}
})
.usePlugin(SpoilerParserPlugin.create(markdownColor, postSpoilerBackgroundColor))
.usePlugin(StrikethroughPlugin.create())
.usePlugin(MovementMethodPlugin.create(BetterLinkMovementMethod.linkify(Linkify.WEB_URLS, activity).setOnLinkLongClickListener((textView, url) -> {
if (activity != null && !activity.isDestroyed() && !activity.isFinishing()) {
@ -341,7 +301,6 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
.tableLayout(R.layout.adapter_table_block, R.id.table_layout)
.textLayoutIsRoot(R.layout.view_table_entry_cell)))
.build();
mImageViewWidth = imageViewWidth;
mSeparatePostAndComments = separatePostAndComments;
mLegacyAutoplayVideoControllerUI = sharedPreferences.getBoolean(SharedPreferencesUtils.LEGACY_AUTOPLAY_VIDEO_CONTROLLER_UI, false);
mAccessToken = accessToken;
@ -596,16 +555,16 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
((PostDetailBaseViewHolder) holder).mScoreTextView.setTextColor(mDownvotedColor);
break;
case 0:
((PostDetailBaseViewHolder) holder).mUpvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
((PostDetailBaseViewHolder) holder).mDownvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
((PostDetailBaseViewHolder) holder).mUpvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
((PostDetailBaseViewHolder) holder).mDownvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
((PostDetailBaseViewHolder) holder).mScoreTextView.setTextColor(mPostIconAndInfoColor);
}
if (mPost.isArchived()) {
((PostDetailBaseViewHolder) holder).mUpvoteButton
.setColorFilter(mVoteAndReplyUnavailableVoteButtonColor, android.graphics.PorterDuff.Mode.SRC_IN);
.setColorFilter(mVoteAndReplyUnavailableVoteButtonColor, PorterDuff.Mode.SRC_IN);
((PostDetailBaseViewHolder) holder).mDownvoteButton
.setColorFilter(mVoteAndReplyUnavailableVoteButtonColor, android.graphics.PorterDuff.Mode.SRC_IN);
.setColorFilter(mVoteAndReplyUnavailableVoteButtonColor, PorterDuff.Mode.SRC_IN);
}
if (mPost.isCrosspost()) {
@ -676,11 +635,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
Post.Preview preview = getSuitablePreview(mPost.getPreviews());
if (preview != null) {
((PostDetailVideoAutoplayViewHolder) holder).aspectRatioFrameLayout.setAspectRatio((float) preview.getPreviewWidth() / preview.getPreviewHeight());
if (mImageViewWidth > preview.getPreviewWidth()) {
mGlide.load(preview.getPreviewUrl()).override(preview.getPreviewWidth(), preview.getPreviewHeight()).into(((PostDetailVideoAutoplayViewHolder) holder).previewImageView);
} else {
mGlide.load(preview.getPreviewUrl()).into(((PostDetailVideoAutoplayViewHolder) holder).previewImageView);
}
mGlide.load(preview.getPreviewUrl()).centerInside().downsample(new SaveMemoryCenterInisdeDownsampleStrategy()).into(((PostDetailVideoAutoplayViewHolder) holder).previewImageView);
} else {
((PostDetailVideoAutoplayViewHolder) holder).aspectRatioFrameLayout.setAspectRatio(1);
}
@ -736,8 +691,6 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
int height = (int) (400 * mScale);
((PostDetailImageAndGifAutoplayViewHolder) holder).mImageView.setScaleType(ImageView.ScaleType.CENTER_CROP);
((PostDetailImageAndGifAutoplayViewHolder) holder).mImageView.getLayoutParams().height = height;
preview.setPreviewWidth(mImageViewWidth);
preview.setPreviewHeight(height);
} else {
((PostDetailImageAndGifAutoplayViewHolder) holder).mImageView.setRatio((float) preview.getPreviewHeight() / (float) preview.getPreviewWidth());
}
@ -873,30 +826,14 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
previewIndex = 0;
}
preview = previews.get(previewIndex);
if (preview.getPreviewWidth() * preview.getPreviewHeight() > 10_000_000) {
if (preview.getPreviewWidth() * preview.getPreviewHeight() > 5_000_000) {
for (int i = previews.size() - 1; i >= 1; i--) {
preview = previews.get(i);
if (mImageViewWidth >= preview.getPreviewWidth()) {
if (preview.getPreviewWidth() * preview.getPreviewHeight() <= 10_000_000) {
return preview;
}
} else {
int height = mImageViewWidth / preview.getPreviewWidth() * preview.getPreviewHeight();
if (mImageViewWidth * height <= 10_000_000) {
if (preview.getPreviewWidth() * preview.getPreviewHeight() <= 5_000_000) {
return preview;
}
}
}
}
if (preview.getPreviewWidth() * preview.getPreviewHeight() > 10_000_000) {
int divisor = 2;
do {
preview.setPreviewWidth(preview.getPreviewWidth() / divisor);
preview.setPreviewHeight(preview.getPreviewHeight() / divisor);
divisor *= 2;
} while (preview.getPreviewWidth() * preview.getPreviewHeight() > 10_000_000);
}
return preview;
}
@ -909,7 +846,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
boolean blurImage = (mPost.isNSFW() && mNeedBlurNsfw && !(mDoNotBlurNsfwInNsfwSubreddits && mFragment != null && mFragment.getIsNsfwSubreddit()) && !(mPost.getPostType() == Post.GIF_TYPE && mAutoplayNsfwVideos)) || (mPost.isSpoiler() && mNeedBlurSpoiler);
String url = mPost.getPostType() == Post.IMAGE_TYPE || blurImage ? preview.getPreviewUrl() : mPost.getUrl();
RequestBuilder<Drawable> imageRequestBuilder = mGlide.load(url)
.listener(new RequestListener<Drawable>() {
.listener(new RequestListener<>() {
@Override
public boolean onLoadFailed(@Nullable GlideException e, Object model, Target<Drawable> target, boolean isFirstResource) {
((PostDetailImageAndGifAutoplayViewHolder) holder).mLoadImageProgressBar.setVisibility(View.GONE);
@ -932,15 +869,11 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
if (blurImage) {
imageRequestBuilder.apply(RequestOptions.bitmapTransform(new BlurTransformation(50, 10))).into(((PostDetailImageAndGifAutoplayViewHolder) holder).mImageView);
} else {
if (mImageViewWidth > preview.getPreviewWidth()) {
imageRequestBuilder.override(preview.getPreviewWidth(), preview.getPreviewHeight()).into(((PostDetailImageAndGifAutoplayViewHolder) holder).mImageView);
} else {
imageRequestBuilder.into(((PostDetailImageAndGifAutoplayViewHolder) holder).mImageView);
}
imageRequestBuilder.centerInside().downsample(new SaveMemoryCenterInisdeDownsampleStrategy()).into(((PostDetailImageAndGifAutoplayViewHolder) holder).mImageView);
}
} else if (holder instanceof PostDetailVideoAndGifPreviewHolder) {
RequestBuilder<Drawable> imageRequestBuilder = mGlide.load(preview.getPreviewUrl())
.listener(new RequestListener<Drawable>() {
.listener(new RequestListener<>() {
@Override
public boolean onLoadFailed(@Nullable GlideException e, Object model, Target<Drawable> target, boolean isFirstResource) {
((PostDetailVideoAndGifPreviewHolder) holder).mLoadImageProgressBar.setVisibility(View.GONE);
@ -964,15 +897,11 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
imageRequestBuilder.apply(RequestOptions.bitmapTransform(new BlurTransformation(50, 10)))
.into(((PostDetailVideoAndGifPreviewHolder) holder).mImageView);
} else {
if (mImageViewWidth > preview.getPreviewWidth()) {
imageRequestBuilder.override(preview.getPreviewWidth(), preview.getPreviewHeight()).into(((PostDetailVideoAndGifPreviewHolder) holder).mImageView);
} else {
imageRequestBuilder.into(((PostDetailVideoAndGifPreviewHolder) holder).mImageView);
}
imageRequestBuilder.centerInside().downsample(new SaveMemoryCenterInisdeDownsampleStrategy()).into(((PostDetailVideoAndGifPreviewHolder) holder).mImageView);
}
} else if (holder instanceof PostDetailLinkViewHolder) {
RequestBuilder<Drawable> imageRequestBuilder = mGlide.load(preview.getPreviewUrl())
.listener(new RequestListener<Drawable>() {
.listener(new RequestListener<>() {
@Override
public boolean onLoadFailed(@Nullable GlideException e, Object model, Target<Drawable> target, boolean isFirstResource) {
((PostDetailLinkViewHolder) holder).mLoadImageProgressBar.setVisibility(View.GONE);
@ -996,15 +925,11 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
imageRequestBuilder.apply(RequestOptions.bitmapTransform(new BlurTransformation(50, 10)))
.into(((PostDetailLinkViewHolder) holder).mImageView);
} else {
if (mImageViewWidth > preview.getPreviewWidth()) {
imageRequestBuilder.override(preview.getPreviewWidth(), preview.getPreviewHeight()).into(((PostDetailLinkViewHolder) holder).mImageView);
} else {
imageRequestBuilder.into(((PostDetailLinkViewHolder) holder).mImageView);
}
imageRequestBuilder.centerInside().downsample(new SaveMemoryCenterInisdeDownsampleStrategy()).into(((PostDetailLinkViewHolder) holder).mImageView);
}
} else if (holder instanceof PostDetailGalleryViewHolder) {
RequestBuilder<Drawable> imageRequestBuilder = mGlide.load(preview.getPreviewUrl())
.listener(new RequestListener<Drawable>() {
.listener(new RequestListener<>() {
@Override
public boolean onLoadFailed(@Nullable GlideException e, Object model, Target<Drawable> target, boolean isFirstResource) {
((PostDetailGalleryViewHolder) holder).mLoadImageProgressBar.setVisibility(View.GONE);
@ -1027,11 +952,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
if ((mPost.isNSFW() && mNeedBlurNsfw && !(mDoNotBlurNsfwInNsfwSubreddits && mFragment != null && mFragment.getIsNsfwSubreddit()) && !(mPost.getPostType() == Post.GIF_TYPE && mAutoplayNsfwVideos)) || (mPost.isSpoiler() && mNeedBlurSpoiler)) {
imageRequestBuilder.apply(RequestOptions.bitmapTransform(new BlurTransformation(50, 10))).into(((PostDetailGalleryViewHolder) holder).mImageView);
} else {
if (mImageViewWidth > preview.getPreviewWidth()) {
imageRequestBuilder.override(preview.getPreviewWidth(), preview.getPreviewHeight()).into(((PostDetailGalleryViewHolder) holder).mImageView);
} else {
imageRequestBuilder.into(((PostDetailGalleryViewHolder) holder).mImageView);
}
imageRequestBuilder.centerInside().downsample(new SaveMemoryCenterInisdeDownsampleStrategy()).into(((PostDetailGalleryViewHolder) holder).mImageView);
}
}
}
@ -1087,9 +1008,9 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
@Override
public void onViewRecycled(@NonNull RecyclerView.ViewHolder holder) {
if (holder instanceof PostDetailBaseViewHolder) {
((PostDetailBaseViewHolder) holder).mUpvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
((PostDetailBaseViewHolder) holder).mUpvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
((PostDetailBaseViewHolder) holder).mScoreTextView.setTextColor(mPostIconAndInfoColor);
((PostDetailBaseViewHolder) holder).mDownvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
((PostDetailBaseViewHolder) holder).mDownvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
((PostDetailBaseViewHolder) holder).mFlairTextView.setVisibility(View.GONE);
((PostDetailBaseViewHolder) holder).mSpoilerTextView.setVisibility(View.GONE);
((PostDetailBaseViewHolder) holder).mNSFWTextView.setVisibility(View.GONE);
@ -1286,19 +1207,19 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
int previousVoteType = mPost.getVoteType();
String newVoteType;
mDownvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
mDownvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
if (previousVoteType != 1) {
//Not upvoted before
mPost.setVoteType(1);
newVoteType = APIUtils.DIR_UPVOTE;
mUpvoteButton.setColorFilter(mUpvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
mUpvoteButton.setColorFilter(mUpvotedColor, PorterDuff.Mode.SRC_IN);
mScoreTextView.setTextColor(mUpvotedColor);
} else {
//Upvoted before
mPost.setVoteType(0);
newVoteType = APIUtils.DIR_UNVOTE;
mUpvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
mUpvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
mScoreTextView.setTextColor(mPostIconAndInfoColor);
}
@ -1314,15 +1235,15 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
public void onVoteThingSuccess() {
if (newVoteType.equals(APIUtils.DIR_UPVOTE)) {
mPost.setVoteType(1);
mUpvoteButton.setColorFilter(mUpvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
mUpvoteButton.setColorFilter(mUpvotedColor, PorterDuff.Mode.SRC_IN);
mScoreTextView.setTextColor(mUpvotedColor);
} else {
mPost.setVoteType(0);
mUpvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
mUpvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
mScoreTextView.setTextColor(mPostIconAndInfoColor);
}
mDownvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
mDownvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
if (!mHideTheNumberOfVotes) {
mScoreTextView.setText(Utils.getNVotes(mShowAbsoluteNumberOfVotes,
mPost.getScore() + mPost.getVoteType()));
@ -1366,19 +1287,19 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
int previousVoteType = mPost.getVoteType();
String newVoteType;
mUpvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
mUpvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
if (previousVoteType != -1) {
//Not upvoted before
mPost.setVoteType(-1);
newVoteType = APIUtils.DIR_DOWNVOTE;
mDownvoteButton.setColorFilter(mDownvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
mDownvoteButton.setColorFilter(mDownvotedColor, PorterDuff.Mode.SRC_IN);
mScoreTextView.setTextColor(mDownvotedColor);
} else {
//Upvoted before
mPost.setVoteType(0);
newVoteType = APIUtils.DIR_UNVOTE;
mDownvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
mDownvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
mScoreTextView.setTextColor(mPostIconAndInfoColor);
}
@ -1394,15 +1315,15 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
public void onVoteThingSuccess() {
if (newVoteType.equals(APIUtils.DIR_DOWNVOTE)) {
mPost.setVoteType(-1);
mDownvoteButton.setColorFilter(mDownvotedColor, android.graphics.PorterDuff.Mode.SRC_IN);
mDownvoteButton.setColorFilter(mDownvotedColor, PorterDuff.Mode.SRC_IN);
mScoreTextView.setTextColor(mDownvotedColor);
} else {
mPost.setVoteType(0);
mDownvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
mDownvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
mScoreTextView.setTextColor(mPostIconAndInfoColor);
}
mUpvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
mUpvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
if (!mHideTheNumberOfVotes) {
mScoreTextView.setText(Utils.getNVotes(mShowAbsoluteNumberOfVotes,
mPost.getScore() + mPost.getVoteType()));
@ -1574,13 +1495,13 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
mUpvoteRatioTextView.setCompoundDrawablesWithIntrinsicBounds(
upvoteRatioDrawable, null, null, null);
mUpvoteRatioTextView.setTextColor(mSecondaryTextColor);
mUpvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
mUpvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
mScoreTextView.setTextColor(mPostIconAndInfoColor);
mDownvoteButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
mDownvoteButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
commentsCountTextView.setTextColor(mPostIconAndInfoColor);
commentsCountTextView.setCompoundDrawablesWithIntrinsicBounds(mCommentIcon, null, null, null);
mSaveButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
mShareButton.setColorFilter(mPostIconAndInfoColor, android.graphics.PorterDuff.Mode.SRC_IN);
mSaveButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
mShareButton.setColorFilter(mPostIconAndInfoColor, PorterDuff.Mode.SRC_IN);
}
}
@ -2223,7 +2144,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
mLinkTextView.setTextColor(mSecondaryTextColor);
mNoPreviewPostTypeImageView.setBackgroundColor(mNoPreviewPostTypeBackgroundColor);
mNoPreviewPostTypeImageView.setColorFilter(mNoPreviewPostTypeIconTint, android.graphics.PorterDuff.Mode.SRC_IN);
mNoPreviewPostTypeImageView.setColorFilter(mNoPreviewPostTypeIconTint, PorterDuff.Mode.SRC_IN);
mNoPreviewPostTypeImageView.setOnClickListener(view -> {
if (mPost != null) {
@ -2374,7 +2295,7 @@ public class PostDetailRecyclerViewAdapter extends RecyclerView.Adapter<Recycler
mLoadImageProgressBar.setIndeterminateTintList(ColorStateList.valueOf(mColorAccent));
mLoadImageErrorTextView.setTextColor(mPrimaryTextColor);
mNoPreviewPostTypeImageView.setBackgroundColor(mNoPreviewPostTypeBackgroundColor);
mNoPreviewPostTypeImageView.setColorFilter(mNoPreviewPostTypeIconTint, android.graphics.PorterDuff.Mode.SRC_IN);
mNoPreviewPostTypeImageView.setColorFilter(mNoPreviewPostTypeIconTint, PorterDuff.Mode.SRC_IN);
mImageView.setOnClickListener(view -> {
Intent intent = new Intent(mActivity, ViewRedditGalleryActivity.class);

View File

@ -69,6 +69,7 @@ import jp.wasabeef.glide.transformations.BlurTransformation;
import jp.wasabeef.glide.transformations.RoundedCornersTransformation;
import ml.docilealligator.infinityforreddit.FetchGfycatOrRedgifsVideoLinks;
import ml.docilealligator.infinityforreddit.MarkPostAsReadInterface;
import ml.docilealligator.infinityforreddit.SaveMemoryCenterInisdeDownsampleStrategy;
import ml.docilealligator.infinityforreddit.R;
import ml.docilealligator.infinityforreddit.SaveThing;
import ml.docilealligator.infinityforreddit.VoteThing;
@ -128,7 +129,6 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
private Retrofit mOauthRetrofit;
private Retrofit mGfycatRetrofit;
private Retrofit mRedgifsRetrofit;
private int mImageViewWidth;
private String mAccessToken;
private RequestManager mGlide;
private Locale mLocale;
@ -208,7 +208,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
public PostRecyclerViewAdapter(AppCompatActivity activity, PostFragment fragment, Executor executor, Retrofit oauthRetrofit,
Retrofit gfycatRetrofit, Retrofit redgifsRetrofit,
CustomThemeWrapper customThemeWrapper, Locale locale, int imageViewWidth,
CustomThemeWrapper customThemeWrapper, Locale locale,
String accessToken, String accountName, int postType, int postLayout, boolean displaySubredditName,
SharedPreferences sharedPreferences, SharedPreferences nsfwAndSpoilerSharedPreferences,
SharedPreferences postHistorySharedPreferences,
@ -222,7 +222,6 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
mOauthRetrofit = oauthRetrofit;
mGfycatRetrofit = gfycatRetrofit;
mRedgifsRetrofit = redgifsRetrofit;
mImageViewWidth = imageViewWidth;
mAccessToken = accessToken;
mPostType = postType;
mDisplaySubredditName = displaySubredditName;
@ -678,11 +677,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
Post.Preview preview = getSuitablePreview(post.getPreviews());
if (preview != null) {
((PostVideoAutoplayViewHolder) holder).aspectRatioFrameLayout.setAspectRatio((float) preview.getPreviewWidth() / preview.getPreviewHeight());
if (mImageViewWidth > preview.getPreviewWidth()) {
mGlide.load(preview.getPreviewUrl()).override(Target.SIZE_ORIGINAL).into(((PostVideoAutoplayViewHolder) holder).previewImageView);
} else {
mGlide.load(preview.getPreviewUrl()).into(((PostVideoAutoplayViewHolder) holder).previewImageView);
}
mGlide.load(preview.getPreviewUrl()).centerInside().downsample(new SaveMemoryCenterInisdeDownsampleStrategy()).into(((PostVideoAutoplayViewHolder) holder).previewImageView);
} else {
((PostVideoAutoplayViewHolder) holder).aspectRatioFrameLayout.setAspectRatio(1);
}
@ -776,8 +771,6 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
int height = (int) (400 * mScale);
((PostWithPreviewTypeViewHolder) holder).imageView.setScaleType(ImageView.ScaleType.CENTER_CROP);
((PostWithPreviewTypeViewHolder) holder).imageView.getLayoutParams().height = height;
preview.setPreviewWidth(mImageViewWidth);
preview.setPreviewHeight(height);
} else {
((PostWithPreviewTypeViewHolder) holder).imageView
.setRatio((float) preview.getPreviewHeight() / preview.getPreviewWidth());
@ -811,11 +804,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
Post.Preview preview = getSuitablePreview(post.getPreviews());
if (preview != null) {
((PostCard2VideoAutoplayViewHolder) holder).aspectRatioFrameLayout.setAspectRatio((float) preview.getPreviewWidth() / preview.getPreviewHeight());
if (mImageViewWidth > preview.getPreviewWidth()) {
mGlide.load(preview.getPreviewUrl()).override(Target.SIZE_ORIGINAL).into(((PostCard2VideoAutoplayViewHolder) holder).previewImageView);
} else {
mGlide.load(preview.getPreviewUrl()).into(((PostCard2VideoAutoplayViewHolder) holder).previewImageView);
}
mGlide.load(preview.getPreviewUrl()).centerInside().downsample(new SaveMemoryCenterInisdeDownsampleStrategy()).into(((PostCard2VideoAutoplayViewHolder) holder).previewImageView);
} else {
((PostCard2VideoAutoplayViewHolder) holder).aspectRatioFrameLayout.setAspectRatio(1);
}
@ -911,8 +900,6 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
int height = (int) (400 * mScale);
((PostCard2WithPreviewViewHolder) holder).imageView.setScaleType(ImageView.ScaleType.CENTER_CROP);
((PostCard2WithPreviewViewHolder) holder).imageView.getLayoutParams().height = height;
preview.setPreviewWidth(mImageViewWidth);
preview.setPreviewHeight(height);
} else {
((PostCard2WithPreviewViewHolder) holder).imageView
.setRatio((float) preview.getPreviewHeight() / preview.getPreviewWidth());
@ -1293,8 +1280,6 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
int height = (int) (400 * mScale);
((PostGalleryViewHolder) holder).imageView.setScaleType(ImageView.ScaleType.CENTER_CROP);
((PostGalleryViewHolder) holder).imageView.getLayoutParams().height = height;
preview.setPreviewWidth(mImageViewWidth);
preview.setPreviewHeight(height);
} else {
((PostGalleryViewHolder) holder).imageView
.setRatio((float) preview.getPreviewHeight() / preview.getPreviewWidth());
@ -1329,8 +1314,6 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
int height = (int) (400 * mScale);
((PostGalleryViewHolder) holder).imageView.setScaleType(ImageView.ScaleType.CENTER_CROP);
((PostGalleryViewHolder) holder).imageView.getLayoutParams().height = height;
preview.setPreviewWidth(mImageViewWidth);
preview.setPreviewHeight(height);
} else {
((PostGalleryViewHolder) holder).imageView
.setRatio((float) preview.getPreviewHeight() / preview.getPreviewWidth());
@ -1355,8 +1338,6 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
int height = (int) (400 * mScale);
((PostGalleryViewHolder) holder).imageView.setScaleType(ImageView.ScaleType.CENTER_CROP);
((PostGalleryViewHolder) holder).imageView.getLayoutParams().height = height;
preview.setPreviewWidth(mImageViewWidth);
preview.setPreviewHeight(height);
} else {
((PostGalleryViewHolder) holder).imageView
.setRatio((float) preview.getPreviewHeight() / preview.getPreviewWidth());
@ -1381,8 +1362,6 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
int height = (int) (400 * mScale);
((PostGalleryViewHolder) holder).imageView.setScaleType(ImageView.ScaleType.CENTER_CROP);
((PostGalleryViewHolder) holder).imageView.getLayoutParams().height = height;
preview.setPreviewWidth(mImageViewWidth);
preview.setPreviewHeight(height);
} else {
((PostGalleryViewHolder) holder).imageView
.setRatio((float) preview.getPreviewHeight() / preview.getPreviewWidth());
@ -1417,8 +1396,6 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
int height = (int) (400 * mScale);
((PostGalleryViewHolder) holder).imageView.setScaleType(ImageView.ScaleType.CENTER_CROP);
((PostGalleryViewHolder) holder).imageView.getLayoutParams().height = height;
preview.setPreviewWidth(mImageViewWidth);
preview.setPreviewHeight(height);
} else {
((PostGalleryViewHolder) holder).imageView
.setRatio((float) preview.getPreviewHeight() / preview.getPreviewWidth());
@ -1449,29 +1426,11 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
if (preview.getPreviewWidth() * preview.getPreviewHeight() > 5_000_000) {
for (int i = previews.size() - 1; i >= 1; i--) {
preview = previews.get(i);
if (mImageViewWidth >= preview.getPreviewWidth()) {
if (preview.getPreviewWidth() * preview.getPreviewHeight() <= 5_000_000) {
return preview;
}
} else {
int height = mImageViewWidth / preview.getPreviewWidth() * preview.getPreviewHeight();
if (mImageViewWidth * height <= 5_000_000) {
preview.setPreviewWidth(mImageViewWidth);
preview.setPreviewHeight(height);
return preview;
}
}
}
}
if (preview.getPreviewWidth() * preview.getPreviewHeight() > 5_000_000) {
int divisor = 2;
do {
preview.setPreviewWidth(preview.getPreviewWidth() / divisor);
preview.setPreviewHeight(preview.getPreviewHeight() / divisor);
divisor *= 2;
} while (preview.getPreviewWidth() * preview.getPreviewHeight() > 5_000_000);
}
return preview;
}
@ -1496,7 +1455,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
imageRequestBuilder.apply(RequestOptions.bitmapTransform(new BlurTransformation(50, 10)))
.into(((PostWithPreviewTypeViewHolder) holder).imageView);
} else {
imageRequestBuilder.override(preview.getPreviewWidth(), preview.getPreviewHeight()).centerInside().into(((PostWithPreviewTypeViewHolder) holder).imageView);
imageRequestBuilder.centerInside().downsample(new SaveMemoryCenterInisdeDownsampleStrategy()).into(((PostWithPreviewTypeViewHolder) holder).imageView);
}
}
} else if (holder instanceof PostCompactBaseViewHolder) {
@ -1536,11 +1495,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
imageRequestBuilder.apply(RequestOptions.bitmapTransform(new BlurTransformation(50, 10)))
.into(((PostGalleryViewHolder) holder).imageView);
} else {
if (mImageViewWidth > preview.getPreviewWidth()) {
imageRequestBuilder.override(preview.getPreviewWidth(), preview.getPreviewHeight()).into(((PostGalleryViewHolder) holder).imageView);
} else {
imageRequestBuilder.into(((PostGalleryViewHolder) holder).imageView);
}
imageRequestBuilder.centerInside().downsample(new SaveMemoryCenterInisdeDownsampleStrategy()).into(((PostGalleryViewHolder) holder).imageView);
}
}
} else if (holder instanceof PostCard2WithPreviewViewHolder) {
@ -1560,11 +1515,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
imageRequestBuilder.apply(RequestOptions.bitmapTransform(new BlurTransformation(50, 10)))
.into(((PostCard2WithPreviewViewHolder) holder).imageView);
} else {
if (mImageViewWidth > preview.getPreviewWidth()) {
imageRequestBuilder.override(preview.getPreviewWidth(), preview.getPreviewHeight()).into(((PostCard2WithPreviewViewHolder) holder).imageView);
} else {
imageRequestBuilder.into(((PostCard2WithPreviewViewHolder) holder).imageView);
}
imageRequestBuilder.centerInside().downsample(new SaveMemoryCenterInisdeDownsampleStrategy()).into(((PostCard2WithPreviewViewHolder) holder).imageView);
}
}
}
@ -1918,6 +1869,8 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
}
private void openViewPostDetailActivity(Post post, int position) {
if (canStartActivity) {
canStartActivity = false;
Intent intent = new Intent(mActivity, ViewPostDetailActivity.class);
intent.putExtra(ViewPostDetailActivity.EXTRA_POST_DATA, post);
intent.putExtra(ViewPostDetailActivity.EXTRA_POST_LIST_POSITION, position);
@ -1925,6 +1878,7 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
intent.putExtra(ViewPostDetailActivity.EXTRA_IS_NSFW_SUBREDDIT, mFragment.getIsNsfwSubreddit());
mActivity.startActivity(intent);
}
}
private void openMedia(Post post) {
if (canStartActivity) {
@ -2115,7 +2069,6 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
Post post = getItem(position);
if (post != null) {
markPostRead(post, true);
canStartActivity = false;
openViewPostDetailActivity(post, getBindingAdapterPosition());
}
@ -3162,8 +3115,6 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
Post post = getItem(position);
if (post != null && canStartActivity) {
markPostRead(post, true);
canStartActivity = false;
openViewPostDetailActivity(post, getBindingAdapterPosition());
}
});
@ -3752,7 +3703,6 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
Post post = getItem(position);
if (post != null) {
markPostRead(post, true);
canStartActivity = false;
if (post.getPostType() == Post.TEXT_TYPE || !mSharedPreferences.getBoolean(SharedPreferencesUtils.CLICK_TO_SHOW_MEDIA_IN_GALLERY_LAYOUT, false)) {
openViewPostDetailActivity(post, getBindingAdapterPosition());
@ -3769,7 +3719,6 @@ public class PostRecyclerViewAdapter extends PagingDataAdapter<Post, RecyclerVie
Post post = getItem(position);
if (post != null) {
markPostRead(post, true);
canStartActivity = false;
if (post.getPostType() == Post.TEXT_TYPE || mSharedPreferences.getBoolean(SharedPreferencesUtils.CLICK_TO_SHOW_MEDIA_IN_GALLERY_LAYOUT, false)) {
openViewPostDetailActivity(post, getBindingAdapterPosition());

View File

@ -28,6 +28,10 @@ import io.noties.markwon.MarkwonConfiguration;
import io.noties.markwon.core.MarkwonTheme;
import io.noties.markwon.ext.strikethrough.StrikethroughPlugin;
import io.noties.markwon.html.HtmlPlugin;
import io.noties.markwon.html.tag.SuperScriptHandler;
import io.noties.markwon.inlineparser.BangInlineProcessor;
import io.noties.markwon.inlineparser.HtmlInlineProcessor;
import io.noties.markwon.inlineparser.MarkwonInlineParserPlugin;
import io.noties.markwon.linkify.LinkifyPlugin;
import jp.wasabeef.glide.transformations.RoundedCornersTransformation;
import ml.docilealligator.infinityforreddit.R;
@ -37,6 +41,7 @@ import ml.docilealligator.infinityforreddit.activities.ViewUserDetailActivity;
import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
import ml.docilealligator.infinityforreddit.message.Message;
import ml.docilealligator.infinityforreddit.utils.SharedPreferencesUtils;
import ml.docilealligator.infinityforreddit.markdown.SuperscriptInlineProcessor;
import ml.docilealligator.infinityforreddit.utils.Utils;
public class PrivateMessagesDetailRecyclerViewAdapter extends RecyclerView.Adapter<RecyclerView.ViewHolder> {
@ -66,8 +71,21 @@ public class PrivateMessagesDetailRecyclerViewAdapter extends RecyclerView.Adapt
mLocale = locale;
mAccountName = accountName;
mMarkwon = Markwon.builder(viewPrivateMessagesActivity)
.usePlugin(HtmlPlugin.create())
.usePlugin(MarkwonInlineParserPlugin.create(plugin -> {
plugin.excludeInlineProcessor(HtmlInlineProcessor.class);
plugin.excludeInlineProcessor(BangInlineProcessor.class);
plugin.addInlineProcessor(new SuperscriptInlineProcessor());
}))
.usePlugin(HtmlPlugin.create(plugin -> {
plugin.excludeDefaults(true).addHandler(new SuperScriptHandler());
}))
.usePlugin(new AbstractMarkwonPlugin() {
@NonNull
@Override
public String processMarkdown(@NonNull String markdown) {
return super.processMarkdown(Utils.fixSuperScript(markdown));
}
@Override
public void configureConfiguration(@NonNull MarkwonConfiguration.Builder builder) {
builder.linkResolver((view, link) -> {

View File

@ -23,6 +23,10 @@ import io.noties.markwon.MarkwonConfiguration;
import io.noties.markwon.core.MarkwonTheme;
import io.noties.markwon.ext.strikethrough.StrikethroughPlugin;
import io.noties.markwon.html.HtmlPlugin;
import io.noties.markwon.html.tag.SuperScriptHandler;
import io.noties.markwon.inlineparser.BangInlineProcessor;
import io.noties.markwon.inlineparser.HtmlInlineProcessor;
import io.noties.markwon.inlineparser.MarkwonInlineParserPlugin;
import io.noties.markwon.linkify.LinkifyPlugin;
import io.noties.markwon.movement.MovementMethodPlugin;
import me.saket.bettermovementmethod.BetterLinkMovementMethod;
@ -31,6 +35,8 @@ import ml.docilealligator.infinityforreddit.Rule;
import ml.docilealligator.infinityforreddit.activities.LinkResolverActivity;
import ml.docilealligator.infinityforreddit.bottomsheetfragments.UrlMenuBottomSheetFragment;
import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
import ml.docilealligator.infinityforreddit.markdown.SuperscriptInlineProcessor;
import ml.docilealligator.infinityforreddit.utils.Utils;
public class RulesRecyclerViewAdapter extends RecyclerView.Adapter<RulesRecyclerViewAdapter.RuleViewHolder> {
private Markwon markwon;
@ -40,8 +46,21 @@ public class RulesRecyclerViewAdapter extends RecyclerView.Adapter<RulesRecycler
public RulesRecyclerViewAdapter(AppCompatActivity activity, CustomThemeWrapper customThemeWrapper) {
markwon = Markwon.builder(activity)
.usePlugin(HtmlPlugin.create())
.usePlugin(MarkwonInlineParserPlugin.create(plugin -> {
plugin.excludeInlineProcessor(HtmlInlineProcessor.class);
plugin.excludeInlineProcessor(BangInlineProcessor.class);
plugin.addInlineProcessor(new SuperscriptInlineProcessor());
}))
.usePlugin(HtmlPlugin.create(plugin -> {
plugin.excludeDefaults(true).addHandler(new SuperScriptHandler());
}))
.usePlugin(new AbstractMarkwonPlugin() {
@NonNull
@Override
public String processMarkdown(@NonNull String markdown) {
return super.processMarkdown(Utils.fixSuperScript(markdown));
}
@Override
public void configureConfiguration(@NonNull MarkwonConfiguration.Builder builder) {
builder.linkResolver((view, link) -> {

View File

@ -6,6 +6,7 @@ import android.content.ClipData;
import android.content.ClipboardManager;
import android.content.Context;
import android.os.Bundle;
import android.text.Html;
import android.view.LayoutInflater;
import android.view.View;
import android.view.ViewGroup;
@ -72,7 +73,7 @@ public class CopyTextBottomSheetFragment extends LandscapeExpandedRoundedBottomS
}
if (markdownText != null) {
markdownText = markdownText.replaceAll("<sup>", "^").replaceAll("</sup>", "");
//markdownText = markdownText.replaceAll("<sup>", "^").replaceAll("</sup>", "");
copyMarkdownTextView.setOnClickListener(view -> {
showCopyDialog(markdownText);
dismiss();

View File

@ -3,16 +3,25 @@ package ml.docilealligator.infinityforreddit.broadcastreceivers;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
import androidx.core.content.ContextCompat;
import ml.docilealligator.infinityforreddit.services.MaterialYouService;
import ml.docilealligator.infinityforreddit.utils.SharedPreferencesUtils;
public class WallpaperChangeReceiver extends BroadcastReceiver {
private SharedPreferences sharedPreferences;
public WallpaperChangeReceiver(SharedPreferences sharedPreferences) {
this.sharedPreferences = sharedPreferences;
}
@Override
public void onReceive(Context context, Intent intent) {
if (sharedPreferences.getBoolean(SharedPreferencesUtils.ENABLE_MATERIAL_YOU, false)) {
Intent materialYouIntent = new Intent(context, MaterialYouService.class);
ContextCompat.startForegroundService(context, materialYouIntent);
}
}
}

View File

@ -17,7 +17,6 @@ import android.os.Build;
import android.os.Bundle;
import android.os.CountDownTimer;
import android.os.Handler;
import android.util.DisplayMetrics;
import android.view.HapticFeedbackConstants;
import android.view.KeyEvent;
import android.view.LayoutInflater;
@ -338,10 +337,6 @@ public class PostFragment extends Fragment implements FragmentCommunicator {
}
}
DisplayMetrics displayMetrics = new DisplayMetrics();
activity.getWindowManager().getDefaultDisplay().getMetrics(displayMetrics);
int windowWidth = displayMetrics.widthPixels;
mGlide = Glide.with(activity);
lazyModeRunnable = new LazyModeRunnable() {
@ -452,7 +447,7 @@ public class PostFragment extends Fragment implements FragmentCommunicator {
mAdapter = new PostRecyclerViewAdapter(activity, this, mExecutor, mOauthRetrofit, mGfycatRetrofit,
mRedgifsRetrofit, mCustomThemeWrapper, locale,
windowWidth, accessToken, accountName, postType, postLayout, true,
accessToken, accountName, postType, postLayout, true,
mSharedPreferences, mNsfwAndSpoilerSharedPreferences, mPostHistorySharedPreferences,
mExoCreator, new PostRecyclerViewAdapter.Callback() {
@Override
@ -529,7 +524,7 @@ public class PostFragment extends Fragment implements FragmentCommunicator {
mAdapter = new PostRecyclerViewAdapter(activity, this, mExecutor, mOauthRetrofit, mGfycatRetrofit,
mRedgifsRetrofit, mCustomThemeWrapper, locale,
windowWidth, accessToken, accountName, postType, postLayout, displaySubredditName,
accessToken, accountName, postType, postLayout, displaySubredditName,
mSharedPreferences, mNsfwAndSpoilerSharedPreferences, mPostHistorySharedPreferences,
mExoCreator, new PostRecyclerViewAdapter.Callback() {
@Override
@ -600,7 +595,7 @@ public class PostFragment extends Fragment implements FragmentCommunicator {
mAdapter = new PostRecyclerViewAdapter(activity, this, mExecutor, mOauthRetrofit, mGfycatRetrofit,
mRedgifsRetrofit, mCustomThemeWrapper, locale,
windowWidth, accessToken, accountName, postType, postLayout, true,
accessToken, accountName, postType, postLayout, true,
mSharedPreferences, mNsfwAndSpoilerSharedPreferences, mPostHistorySharedPreferences,
mExoCreator, new PostRecyclerViewAdapter.Callback() {
@Override
@ -665,7 +660,7 @@ public class PostFragment extends Fragment implements FragmentCommunicator {
mAdapter = new PostRecyclerViewAdapter(activity, this, mExecutor, mOauthRetrofit, mGfycatRetrofit,
mRedgifsRetrofit, mCustomThemeWrapper, locale,
windowWidth, accessToken, accountName, postType, postLayout, true,
accessToken, accountName, postType, postLayout, true,
mSharedPreferences, mNsfwAndSpoilerSharedPreferences, mPostHistorySharedPreferences,
mExoCreator, new PostRecyclerViewAdapter.Callback() {
@Override
@ -726,7 +721,7 @@ public class PostFragment extends Fragment implements FragmentCommunicator {
mAdapter = new PostRecyclerViewAdapter(activity, this, mExecutor, mOauthRetrofit, mGfycatRetrofit,
mRedgifsRetrofit, mCustomThemeWrapper, locale,
windowWidth, accessToken, accountName, postType, postLayout, true,
accessToken, accountName, postType, postLayout, true,
mSharedPreferences, mNsfwAndSpoilerSharedPreferences, mPostHistorySharedPreferences,
mExoCreator, new PostRecyclerViewAdapter.Callback() {
@Override
@ -786,7 +781,7 @@ public class PostFragment extends Fragment implements FragmentCommunicator {
mAdapter = new PostRecyclerViewAdapter(activity, this, mExecutor, mOauthRetrofit, mGfycatRetrofit,
mRedgifsRetrofit, mCustomThemeWrapper, locale,
windowWidth, accessToken, accountName, postType, postLayout, true,
accessToken, accountName, postType, postLayout, true,
mSharedPreferences, mNsfwAndSpoilerSharedPreferences, mPostHistorySharedPreferences,
mExoCreator, new PostRecyclerViewAdapter.Callback() {
@Override
@ -840,7 +835,7 @@ public class PostFragment extends Fragment implements FragmentCommunicator {
mAdapter = new PostRecyclerViewAdapter(activity, this, mExecutor, mOauthRetrofit, mGfycatRetrofit,
mRedgifsRetrofit, mCustomThemeWrapper, locale,
windowWidth, accessToken, accountName, postType, postLayout, true,
accessToken, accountName, postType, postLayout, true,
mSharedPreferences, mNsfwAndSpoilerSharedPreferences, mPostHistorySharedPreferences,
mExoCreator, new PostRecyclerViewAdapter.Callback() {
@Override
@ -891,7 +886,6 @@ public class PostFragment extends Fragment implements FragmentCommunicator {
StaggeredGridLayoutManagerItemOffsetDecoration itemDecoration =
new StaggeredGridLayoutManagerItemOffsetDecoration(activity, R.dimen.staggeredLayoutManagerItemOffset, nColumns);
mPostRecyclerView.addItemDecoration(itemDecoration);
windowWidth /= 2;
}
if (recyclerViewPosition > 0) {

View File

@ -35,6 +35,10 @@ import io.noties.markwon.MarkwonConfiguration;
import io.noties.markwon.core.MarkwonTheme;
import io.noties.markwon.ext.strikethrough.StrikethroughPlugin;
import io.noties.markwon.html.HtmlPlugin;
import io.noties.markwon.html.tag.SuperScriptHandler;
import io.noties.markwon.inlineparser.BangInlineProcessor;
import io.noties.markwon.inlineparser.HtmlInlineProcessor;
import io.noties.markwon.inlineparser.MarkwonInlineParserPlugin;
import io.noties.markwon.linkify.LinkifyPlugin;
import io.noties.markwon.movement.MovementMethodPlugin;
import io.noties.markwon.recycler.MarkwonAdapter;
@ -54,6 +58,8 @@ import ml.docilealligator.infinityforreddit.customviews.LinearLayoutManagerBugFi
import ml.docilealligator.infinityforreddit.subreddit.FetchSubredditData;
import ml.docilealligator.infinityforreddit.subreddit.SubredditData;
import ml.docilealligator.infinityforreddit.subreddit.SubredditViewModel;
import ml.docilealligator.infinityforreddit.markdown.SuperscriptInlineProcessor;
import ml.docilealligator.infinityforreddit.utils.Utils;
import retrofit2.Retrofit;
public class SidebarFragment extends Fragment {
@ -104,8 +110,21 @@ public class SidebarFragment extends Fragment {
markdownColor = mCustomThemeWrapper.getPrimaryTextColor();
Markwon markwon = Markwon.builder(activity)
.usePlugin(HtmlPlugin.create())
.usePlugin(MarkwonInlineParserPlugin.create(plugin -> {
plugin.excludeInlineProcessor(HtmlInlineProcessor.class);
plugin.excludeInlineProcessor(BangInlineProcessor.class);
plugin.addInlineProcessor(new SuperscriptInlineProcessor());
}))
.usePlugin(HtmlPlugin.create(plugin -> {
plugin.excludeDefaults(true).addHandler(new SuperScriptHandler());
}))
.usePlugin(new AbstractMarkwonPlugin() {
@NonNull
@Override
public String processMarkdown(@NonNull String markdown) {
return super.processMarkdown(Utils.fixSuperScript(markdown));
}
@Override
public void beforeSetText(@NonNull TextView textView, @NonNull Spanned markdown) {
textView.setTextColor(markdownColor);

View File

@ -16,7 +16,6 @@ import android.graphics.drawable.ColorDrawable;
import android.graphics.drawable.Drawable;
import android.os.Bundle;
import android.os.Handler;
import android.util.DisplayMetrics;
import android.view.HapticFeedbackConstants;
import android.view.LayoutInflater;
import android.view.Menu;
@ -67,6 +66,7 @@ import butterknife.ButterKnife;
import im.ene.toro.exoplayer.ExoCreator;
import im.ene.toro.media.PlaybackInfo;
import im.ene.toro.media.VolumeInfo;
import im.ene.toro.widget.Container;
import ml.docilealligator.infinityforreddit.DeleteThing;
import ml.docilealligator.infinityforreddit.Flair;
import ml.docilealligator.infinityforreddit.FragmentCommunicator;
@ -224,7 +224,6 @@ public class ViewPostDetailFragment extends Fragment implements FragmentCommunic
private boolean mExpandChildren;
private boolean mSeparatePostAndComments = false;
private boolean mMarkPostsAsRead;
private int mWindowWidth;
private ConcatAdapter mConcatAdapter;
private PostDetailRecyclerViewAdapter mPostAdapter;
private CommentsRecyclerViewAdapter mCommentsAdapter;
@ -290,10 +289,6 @@ public class ViewPostDetailFragment extends Fragment implements FragmentCommunic
showToast = true;
}
DisplayMetrics displayMetrics = new DisplayMetrics();
activity.getWindowManager().getDefaultDisplay().getMetrics(displayMetrics);
mWindowWidth = displayMetrics.widthPixels;
mLockFab = mSharedPreferences.getBoolean(SharedPreferencesUtils.LOCK_JUMP_TO_NEXT_TOP_LEVEL_COMMENT_BUTTON, false);
mSwipeUpToHideFab = mSharedPreferences.getBoolean(SharedPreferencesUtils.SWIPE_UP_TO_HIDE_JUMP_TO_NEXT_TOP_LEVEL_COMMENT_BUTTON, false);
mExpandChildren = !mSharedPreferences.getBoolean(SharedPreferencesUtils.SHOW_TOP_LEVEL_COMMENTS_FIRST, false);
@ -550,7 +545,7 @@ public class ViewPostDetailFragment extends Fragment implements FragmentCommunic
mPostAdapter = new PostDetailRecyclerViewAdapter(activity,
this, mExecutor, mCustomThemeWrapper, mRetrofit, mOauthRetrofit, mGfycatRetrofit,
mRedgifsRetrofit, mRedditDataRoomDatabase, mGlide,
mWindowWidth, mSeparatePostAndComments, mAccessToken, mAccountName, mPost, mLocale,
mSeparatePostAndComments, mAccessToken, mAccountName, mPost, mLocale,
mSharedPreferences, mNsfwAndSpoilerSharedPreferences, mPostDetailsSharedPreferences,
mExoCreator, post -> EventBus.getDefault().post(new PostUpdateEventToPostList(mPost, postListPosition)));
mCommentsAdapter = new CommentsRecyclerViewAdapter(activity,
@ -1195,7 +1190,7 @@ public class ViewPostDetailFragment extends Fragment implements FragmentCommunic
mPostAdapter = new PostDetailRecyclerViewAdapter(activity,
ViewPostDetailFragment.this, mExecutor, mCustomThemeWrapper,
mRetrofit, mOauthRetrofit, mGfycatRetrofit, mRedgifsRetrofit,
mRedditDataRoomDatabase, mGlide, mWindowWidth, mSeparatePostAndComments,
mRedditDataRoomDatabase, mGlide, mSeparatePostAndComments,
mAccessToken, mAccountName, mPost, mLocale, mSharedPreferences,
mNsfwAndSpoilerSharedPreferences, mPostDetailsSharedPreferences,
mExoCreator,
@ -1736,28 +1731,32 @@ public class ViewPostDetailFragment extends Fragment implements FragmentCommunic
}
public void scrollToNextParentComment() {
int currentPosition = ((LinearLayoutManagerBugFixed) (mCommentsRecyclerView == null ? mRecyclerView : mCommentsRecyclerView).getLayoutManager()).findFirstVisibleItemPosition();
if (mCommentsAdapter != null) {
int nextParentPosition = mCommentsAdapter.getNextParentCommentPosition(mCommentsRecyclerView == null ? currentPosition - 1 : currentPosition);
RecyclerView chooseYourView = mCommentsRecyclerView == null ? mRecyclerView : mCommentsRecyclerView;
if (mCommentsAdapter != null && chooseYourView != null) {
int currentPosition = ((LinearLayoutManagerBugFixed) chooseYourView.getLayoutManager()).findFirstVisibleItemPosition();
//int nextParentPosition = mCommentsAdapter.getNextParentCommentPosition(mCommentsRecyclerView == null ? currentPosition - 1 : currentPosition);
int nextParentPosition = mCommentsAdapter.getNextParentCommentPosition(mCommentsRecyclerView == null && !isSingleCommentThreadMode ? currentPosition - 1 : currentPosition);
if (nextParentPosition < 0) {
return;
}
mSmoothScroller.setTargetPosition(mCommentsRecyclerView == null ? nextParentPosition + 1 : nextParentPosition);
mSmoothScroller.setTargetPosition(mCommentsRecyclerView == null && !isSingleCommentThreadMode ? nextParentPosition + 1 : nextParentPosition);
mIsSmoothScrolling = true;
(mCommentsRecyclerView == null ? mRecyclerView : mCommentsRecyclerView).getLayoutManager().startSmoothScroll(mSmoothScroller);
chooseYourView.getLayoutManager().startSmoothScroll(mSmoothScroller);
}
}
public void scrollToPreviousParentComment() {
int currentPosition = ((LinearLayoutManagerBugFixed) (mCommentsRecyclerView == null ? mRecyclerView : mCommentsRecyclerView).getLayoutManager()).findFirstVisibleItemPosition();
if (mCommentsAdapter != null) {
int previousParentPosition = mCommentsAdapter.getPreviousParentCommentPosition(mCommentsRecyclerView == null ? currentPosition - 1 : currentPosition);
RecyclerView chooseYourView = mCommentsRecyclerView == null ? mRecyclerView : mCommentsRecyclerView;
if (mCommentsAdapter != null && chooseYourView != null) {
int currentPosition = ((LinearLayoutManagerBugFixed) chooseYourView.getLayoutManager()).findFirstVisibleItemPosition();
//int previousParentPosition = mCommentsAdapter.getPreviousParentCommentPosition(mCommentsRecyclerView == null ? currentPosition - 1 : currentPosition);
int previousParentPosition = mCommentsAdapter.getPreviousParentCommentPosition(mCommentsRecyclerView == null && !isSingleCommentThreadMode ? currentPosition - 1 : currentPosition);
if (previousParentPosition < 0) {
return;
}
mSmoothScroller.setTargetPosition(mCommentsRecyclerView == null ? previousParentPosition + 1 : previousParentPosition);
mSmoothScroller.setTargetPosition(mCommentsRecyclerView == null && !isSingleCommentThreadMode ? previousParentPosition + 1 : previousParentPosition);
mIsSmoothScrolling = true;
(mCommentsRecyclerView == null ? mRecyclerView : mCommentsRecyclerView).getLayoutManager().startSmoothScroll(mSmoothScroller);
chooseYourView.getLayoutManager().startSmoothScroll(mSmoothScroller);
}
}

View File

@ -1,5 +1,6 @@
package ml.docilealligator.infinityforreddit.fragments;
import android.app.AlertDialog;
import android.content.Context;
import android.content.SharedPreferences;
import android.content.res.Configuration;
@ -207,11 +208,14 @@ public class ViewRPANBroadcastFragment extends Fragment {
hdButton.setVisibility(View.VISIBLE);
hdButton.setOnClickListener(view -> {
TrackSelectionDialogBuilder build = new TrackSelectionDialogBuilder(mActivity,
TrackSelectionDialogBuilder builder = new TrackSelectionDialogBuilder(mActivity,
getString(R.string.select_video_quality), trackSelector, 0);
build.setShowDisableOption(true);
build.setAllowAdaptiveSelections(false);
build.build().show();
builder.setShowDisableOption(true);
builder.setAllowAdaptiveSelections(false);
AlertDialog alertDialog = builder.build();
alertDialog.show();
alertDialog.getButton(AlertDialog.BUTTON_POSITIVE).setTextColor(mCustomThemeWrapper.getPrimaryTextColor());
alertDialog.getButton(AlertDialog.BUTTON_NEGATIVE).setTextColor(mCustomThemeWrapper.getPrimaryTextColor());
});
for (int i = 0; i < trackGroups.length; i++) {

View File

@ -492,7 +492,7 @@ public class ViewRedditGalleryImageOrGifFragment extends Fragment {
@Override
public void onDestroyView() {
super.onDestroyView();
BigImageViewer.imageLoader().cancelAll();
imageView.cancel();
SubsamplingScaleImageView subsamplingScaleImageView = imageView.getSSIV();
if (subsamplingScaleImageView != null) {
subsamplingScaleImageView.recycle();

View File

@ -0,0 +1,85 @@
package ml.docilealligator.infinityforreddit.markdown;
import org.commonmark.internal.util.Parsing;
import org.commonmark.node.Block;
import org.commonmark.node.BlockQuote;
import org.commonmark.parser.block.AbstractBlockParser;
import org.commonmark.parser.block.AbstractBlockParserFactory;
import org.commonmark.parser.block.BlockContinue;
import org.commonmark.parser.block.BlockStart;
import org.commonmark.parser.block.MatchedBlockParser;
import org.commonmark.parser.block.ParserState;
// Parse and consume a block quote except when it's a spoiler opening
public class BlockQuoteWithExceptionParser extends AbstractBlockParser {
private final BlockQuote block = new BlockQuote();
private static boolean isMarker(ParserState state, int index) {
CharSequence line = state.getLine();
return state.getIndent() < Parsing.CODE_BLOCK_INDENT && index < line.length() && line.charAt(index) == '>';
}
private static boolean isMarkerSpoiler(ParserState state, int index) {
CharSequence line = state.getLine();
int length = line.length();
try {
return state.getIndent() < Parsing.CODE_BLOCK_INDENT && index < length && line.charAt(index) == '>' && (index + 1) < length && line.charAt(index + 1) == '!';
} catch (IndexOutOfBoundsException e) {
e.printStackTrace();
return false;
}
}
@Override
public boolean isContainer() {
return true;
}
@Override
public boolean canContain(Block block) {
return true;
}
@Override
public BlockQuote getBlock() {
return block;
}
@Override
public BlockContinue tryContinue(ParserState state) {
int nextNonSpace = state.getNextNonSpaceIndex();
if (isMarker(state, nextNonSpace)) {
int newColumn = state.getColumn() + state.getIndent() + 1;
// optional following space or tab
if (Parsing.isSpaceOrTab(state.getLine(), nextNonSpace + 1)) {
newColumn++;
}
return BlockContinue.atColumn(newColumn);
} else {
return BlockContinue.none();
}
}
public static class Factory extends AbstractBlockParserFactory {
public BlockStart tryStart(ParserState state, MatchedBlockParser matchedBlockParser) {
int nextNonSpace = state.getNextNonSpaceIndex();
// Potential for a spoiler opening
// We don't check for spoiler closing, neither does Reddit
if (isMarkerSpoiler(state, nextNonSpace)) {
// It might be a spoiler, don't consume
return BlockStart.none();
}
// Not a spoiler then
else if (isMarker(state, nextNonSpace)) {
int newColumn = state.getColumn() + state.getIndent() + 1;
// optional following space or tab
if (Parsing.isSpaceOrTab(state.getLine(), nextNonSpace + 1)) {
newColumn++;
}
return BlockStart.of(new BlockQuoteWithExceptionParser()).atColumn(newColumn);
} else {
return BlockStart.none();
}
}
}
}

View File

@ -0,0 +1,202 @@
package ml.docilealligator.infinityforreddit.markdown;
import android.graphics.Color;
import android.text.SpannableStringBuilder;
import android.text.Spanned;
import android.widget.TextView;
import androidx.annotation.NonNull;
import org.commonmark.node.Block;
import org.commonmark.node.BlockQuote;
import org.commonmark.node.HtmlBlock;
import org.commonmark.node.HtmlInline;
import org.commonmark.parser.Parser;
import java.util.LinkedHashMap;
import java.util.Map;
import java.util.Set;
import java.util.Stack;
import io.noties.markwon.AbstractMarkwonPlugin;
import io.noties.markwon.core.CorePlugin;
import io.noties.markwon.core.spans.CodeBlockSpan;
import io.noties.markwon.core.spans.CodeSpan;
public class SpoilerParserPlugin extends AbstractMarkwonPlugin {
private final int textColor;
private final int backgroundColor;
SpoilerParserPlugin(int textColor, int backgroundColor) {
this.textColor = textColor;
this.backgroundColor = backgroundColor;
}
public static SpoilerParserPlugin create(@NonNull int textColor, @NonNull int backgroundColor) {
return new SpoilerParserPlugin(textColor, backgroundColor);
}
@Override
public void configureParser(@NonNull Parser.Builder builder) {
builder.customBlockParserFactory(new BlockQuoteWithExceptionParser.Factory());
Set<Class<? extends Block>> blocks = CorePlugin.enabledBlockTypes();
blocks.remove(HtmlBlock.class);
blocks.remove(HtmlInline.class);
blocks.remove(BlockQuote.class);
builder.enabledBlockTypes(blocks);
}
@Override
public void afterSetText(@NonNull TextView textView) {
textView.setHighlightColor(Color.TRANSPARENT);
if(textView.getText().length() < 5) {
return;
}
SpannableStringBuilder markdownStringBuilder = new SpannableStringBuilder(textView.getText());
LinkedHashMap<Integer, Integer> spoilers = parse(markdownStringBuilder);
if(spoilers.size() == 0) {
return;
}
int offset = 2;
for (Map.Entry<Integer, Integer> entry : spoilers.entrySet()) {
int spoilerStart = entry.getKey() - offset;
int spoilerEnd = entry.getValue() - offset;
// Try not to set a spoiler span if it's inside a CodeSpan
CodeSpan[] codeSpans = markdownStringBuilder.getSpans(spoilerStart, spoilerEnd, CodeSpan.class);
CodeBlockSpan[] codeBlockSpans = markdownStringBuilder.getSpans(spoilerStart, spoilerEnd, CodeBlockSpan.class);
if (codeSpans.length == 0 && codeBlockSpans.length == 0) {
markdownStringBuilder.delete(spoilerStart, spoilerStart + 2);
markdownStringBuilder.delete(spoilerEnd, spoilerEnd + 2);
SpoilerSpan spoilerSpan = new SpoilerSpan(textColor, backgroundColor);
markdownStringBuilder.setSpan(spoilerSpan, spoilerStart, spoilerEnd, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
offset += 4;
}
for (CodeSpan codeSpan : codeSpans) {
int spanBeginning = markdownStringBuilder.getSpanStart(codeSpan);
int spanEnd = markdownStringBuilder.getSpanEnd(codeSpan);
if (spoilerStart + 2 <= spanBeginning && spanEnd <= spoilerEnd + 2) {
markdownStringBuilder.delete(spoilerStart, spoilerStart + 2);
markdownStringBuilder.delete(spoilerEnd, spoilerEnd + 2);
SpoilerSpan spoilerSpan = new SpoilerSpan(textColor, backgroundColor);
markdownStringBuilder.setSpan(spoilerSpan, spoilerStart, spoilerEnd, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
offset += 4;
} else {
break;
}
}
for (CodeBlockSpan codeBlockSpan : codeBlockSpans) {
int spanBeginning = markdownStringBuilder.getSpanStart(codeBlockSpan);
int spanEnd = markdownStringBuilder.getSpanEnd(codeBlockSpan);
if (spoilerStart + 2 <= spanBeginning && spanEnd <= spoilerEnd + 2) {
markdownStringBuilder.delete(spoilerStart, spoilerStart + 2);
markdownStringBuilder.delete(spoilerEnd, spoilerEnd + 2);
SpoilerSpan spoilerSpan = new SpoilerSpan(textColor, backgroundColor);
markdownStringBuilder.setSpan(spoilerSpan, spoilerStart, spoilerEnd, Spanned.SPAN_EXCLUSIVE_EXCLUSIVE);
offset += 4;
} else {
break;
}
}
}
if(offset > 2) {
textView.setText(markdownStringBuilder);
}
}
// Very naive implementation, needs to be improved for efficiency and edge cases
// Don't allow more than one new line after every non-blank line
// Try not to care about recursing spoilers, we just want the outermost spoiler because
// spoiler revealing-hiding breaks with recursing spoilers
private LinkedHashMap<Integer, Integer> parse(SpannableStringBuilder markdown) {
final int MAX_NEW_LINE = 1;
var openSpoilerStack = new Stack<Integer>();
var closedSpoilerMap = new LinkedHashMap<Integer, Integer>();
int variable_max_depth = calculateBalance(0, markdown) + 1;
int new_lines = 0;
int depth = 0;
for (int i = 0; i < markdown.length(); i++) {
if (markdown.charAt(i) == '\u2000' || markdown.charAt(i) == '\t') {
continue;
} else if (markdown.charAt(i) == '>' && (i + 1) < markdown.length() && markdown.charAt(i + 1) == '!') {
openSpoilerStack.push(i + 1);
depth++;
} else if (openSpoilerStack.size() > 0
&& markdown.charAt(i) == '!' && (i + 1) < markdown.length()
&& markdown.charAt(i + 1) == '<') {
var pos = i + 1;
for (int j = 0; j < depth; j++) {
if (!openSpoilerStack.isEmpty()) pos = openSpoilerStack.peek();
if (pos + 1 <= i) {
if (!openSpoilerStack.isEmpty()) pos = openSpoilerStack.peek();
break;
} else {
if (!openSpoilerStack.isEmpty()) pos = openSpoilerStack.pop();
}
}
if (depth <= variable_max_depth && pos + 1 <= i) //Spoiler content cannot be zero or less length
{
openSpoilerStack.clear();
closedSpoilerMap.put(pos + 1, i);
}
depth--;
} else if (markdown.charAt(i) == '\n') {
new_lines++;
if (openSpoilerStack.size() >= 1 && new_lines > MAX_NEW_LINE) {
openSpoilerStack.clear();
new_lines = 0;
depth = 0;
variable_max_depth = calculateBalance(i, markdown) + 1;
}
} else {
new_lines = 0;
}
if (openSpoilerStack.size() >= 32) // No
{
openSpoilerStack.clear();
closedSpoilerMap.clear();
continue;
}
}
return closedSpoilerMap;
}
private int calculateBalance(int index, SpannableStringBuilder line) {
final int MAX_NEW_LINE = 1;
int new_lines = 0;
int opening = 0;
int closing = 0;
for (int i = index; i < line.length(); i++) {
if (line.charAt(i) == '\u0020' || line.charAt(i) == '\t') {
continue;
} else if (line.charAt(i) == '>'
&& (i + 1) < line.length()
&& line.charAt(i + 1) == '!') {
opening++;
} else if (line.charAt(i) == '!' && (i + 1) < line.length()
&& line.charAt(i + 1) == '<') {
closing++;
} else if (line.charAt(i) == '\n') {
new_lines++;
if (new_lines > MAX_NEW_LINE) {
break;
}
} else {
new_lines = 0;
continue;
}
}
return Math.abs(opening - closing);
}
}

View File

@ -0,0 +1,64 @@
package ml.docilealligator.infinityforreddit.markdown;
import android.text.Layout;
import android.text.Spannable;
import android.text.TextPaint;
import android.text.style.ClickableSpan;
import android.view.View;
import android.widget.TextView;
import androidx.annotation.NonNull;
import androidx.transition.AutoTransition;
import androidx.transition.TransitionManager;
import ml.docilealligator.infinityforreddit.customviews.SpoilerOnClickTextView;
public class SpoilerSpan extends ClickableSpan {
final int textColor;
final int backgroundColor;
private boolean isShowing = false;
public SpoilerSpan(@NonNull int textColor, @NonNull int backgroundColor) {
this.textColor = textColor;
this.backgroundColor = backgroundColor;
}
@Override
public void onClick(@NonNull View widget) {
if (!(widget instanceof TextView)) {
return;
}
final TextView textView = (TextView) widget;
final Spannable spannable = (Spannable) textView.getText();
final int end = spannable.getSpanEnd(this);
if (end < 0) {
return;
}
final Layout layout = textView.getLayout();
if (layout == null) {
return;
}
if (widget instanceof SpoilerOnClickTextView) {
((SpoilerOnClickTextView) textView).setSpoilerOnClick(true);
}
isShowing = !isShowing;
widget.invalidate();
}
@Override
public void updateDrawState(@NonNull TextPaint ds) {
if (isShowing) {
ds.bgColor = backgroundColor & 0x0D000000; //Slightly darker background color for revealed spoiler
super.updateDrawState(ds);
} else {
ds.bgColor = backgroundColor;
}
ds.setColor(textColor);
ds.setUnderlineText(false);
}
}

View File

@ -0,0 +1,32 @@
package ml.docilealligator.infinityforreddit.markdown;
import androidx.annotation.Nullable;
import org.commonmark.node.HtmlInline;
import org.commonmark.node.Node;
import java.util.regex.Pattern;
import io.noties.markwon.inlineparser.InlineProcessor;
public class SuperscriptInlineProcessor extends InlineProcessor {
private static final Pattern HTML_TAG = Pattern.compile("</?sup>", Pattern.CASE_INSENSITIVE);
@Override
public char specialCharacter() {
return '<';
}
@Nullable
@Override
protected Node parse() {
String m = match(HTML_TAG);
if (m != null) {
HtmlInline node = new HtmlInline();
node.setLiteral(m);
return node;
} else {
return null;
}
}
}

View File

@ -492,26 +492,26 @@ public class CustomizeMainPageTabsFragment extends Fragment {
tab3AddImageView.setOnClickListener(view -> selectName(2));
showMultiredditsSwitchMaterial.setChecked(mainActivityTabsSharedPreferences.getBoolean(accountName + SharedPreferencesUtils.MAIN_PAGE_SHOW_MULTIREDDITS, false));
showMultiredditsSwitchMaterial.setOnCheckedChangeListener((compoundButton, b) -> mainActivityTabsSharedPreferences.edit().putBoolean(accountName + SharedPreferencesUtils.MAIN_PAGE_SHOW_MULTIREDDITS, b).apply());
showMultiredditsSwitchMaterial.setChecked(mainActivityTabsSharedPreferences.getBoolean((accountName == null ? "" : accountName) + SharedPreferencesUtils.MAIN_PAGE_SHOW_MULTIREDDITS, false));
showMultiredditsSwitchMaterial.setOnCheckedChangeListener((compoundButton, b) -> mainActivityTabsSharedPreferences.edit().putBoolean((accountName == null ? "" : accountName) + SharedPreferencesUtils.MAIN_PAGE_SHOW_MULTIREDDITS, b).apply());
showMultiredditsLinearLayout.setOnClickListener(view -> {
showMultiredditsSwitchMaterial.performClick();
});
showFavoriteMultiredditsSwitchMaterial.setChecked(mainActivityTabsSharedPreferences.getBoolean(accountName + SharedPreferencesUtils.MAIN_PAGE_SHOW_FAVORITE_MULTIREDDITS, false));
showFavoriteMultiredditsSwitchMaterial.setOnCheckedChangeListener((compoundButton, b) -> mainActivityTabsSharedPreferences.edit().putBoolean(accountName + SharedPreferencesUtils.MAIN_PAGE_SHOW_FAVORITE_MULTIREDDITS, b).apply());
showFavoriteMultiredditsSwitchMaterial.setChecked(mainActivityTabsSharedPreferences.getBoolean((accountName == null ? "" : accountName) + SharedPreferencesUtils.MAIN_PAGE_SHOW_FAVORITE_MULTIREDDITS, false));
showFavoriteMultiredditsSwitchMaterial.setOnCheckedChangeListener((compoundButton, b) -> mainActivityTabsSharedPreferences.edit().putBoolean((accountName == null ? "" : accountName) + SharedPreferencesUtils.MAIN_PAGE_SHOW_FAVORITE_MULTIREDDITS, b).apply());
showFavoriteMultiredditsLinearLayout.setOnClickListener(view -> {
showFavoriteMultiredditsSwitchMaterial.performClick();
});
showSubscribedSubredditsSwitchMaterial.setChecked(mainActivityTabsSharedPreferences.getBoolean(accountName + SharedPreferencesUtils.MAIN_PAGE_SHOW_SUBSCRIBED_SUBREDDITS, false));
showSubscribedSubredditsSwitchMaterial.setOnCheckedChangeListener((compoundButton, b) -> mainActivityTabsSharedPreferences.edit().putBoolean(accountName + SharedPreferencesUtils.MAIN_PAGE_SHOW_SUBSCRIBED_SUBREDDITS, b).apply());
showSubscribedSubredditsSwitchMaterial.setChecked(mainActivityTabsSharedPreferences.getBoolean((accountName == null ? "" : accountName) + SharedPreferencesUtils.MAIN_PAGE_SHOW_SUBSCRIBED_SUBREDDITS, false));
showSubscribedSubredditsSwitchMaterial.setOnCheckedChangeListener((compoundButton, b) -> mainActivityTabsSharedPreferences.edit().putBoolean((accountName == null ? "" : accountName) + SharedPreferencesUtils.MAIN_PAGE_SHOW_SUBSCRIBED_SUBREDDITS, b).apply());
showSubscribedSubredditsLinearLayout.setOnClickListener(view -> {
showSubscribedSubredditsSwitchMaterial.performClick();
});
showFavoriteSubscribedSubredditsSwitchMaterial.setChecked(mainActivityTabsSharedPreferences.getBoolean(accountName + SharedPreferencesUtils.MAIN_PAGE_SHOW_FAVORITE_SUBSCRIBED_SUBREDDITS, false));
showFavoriteSubscribedSubredditsSwitchMaterial.setOnCheckedChangeListener((compoundButton, b) -> mainActivityTabsSharedPreferences.edit().putBoolean(accountName + SharedPreferencesUtils.MAIN_PAGE_SHOW_FAVORITE_SUBSCRIBED_SUBREDDITS, b).apply());
showFavoriteSubscribedSubredditsSwitchMaterial.setChecked(mainActivityTabsSharedPreferences.getBoolean((accountName == null ? "" : accountName) + SharedPreferencesUtils.MAIN_PAGE_SHOW_FAVORITE_SUBSCRIBED_SUBREDDITS, false));
showFavoriteSubscribedSubredditsSwitchMaterial.setOnCheckedChangeListener((compoundButton, b) -> mainActivityTabsSharedPreferences.edit().putBoolean((accountName == null ? "" : accountName) + SharedPreferencesUtils.MAIN_PAGE_SHOW_FAVORITE_SUBSCRIBED_SUBREDDITS, b).apply());
showFavoriteSubscribedSubredditsLinearLayout.setOnClickListener(view -> {
showFavoriteSubscribedSubredditsSwitchMaterial.performClick();
});

View File

@ -1,28 +1,30 @@
package ml.docilealligator.infinityforreddit.utils;
import android.graphics.Bitmap;
import androidx.annotation.NonNull;
import com.google.gson.Gson;
import ml.docilealligator.infinityforreddit.apis.RedditAPI;
import ml.docilealligator.infinityforreddit.subreddit.SubredditSettingData;
import okhttp3.MediaType;
import okhttp3.MultipartBody;
import okhttp3.RequestBody;
import org.json.JSONException;
import org.json.JSONObject;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
import retrofit2.Retrofit;
import java.io.ByteArrayOutputStream;
import java.util.HashMap;
import java.util.Map;
import ml.docilealligator.infinityforreddit.apis.RedditAPI;
import ml.docilealligator.infinityforreddit.subreddit.SubredditSettingData;
import okhttp3.MediaType;
import okhttp3.MultipartBody;
import okhttp3.RequestBody;
import retrofit2.Call;
import retrofit2.Callback;
import retrofit2.Response;
import retrofit2.Retrofit;
public final class EditProfileUtils {
public static void updateProfile(Retrofit oauthRetrofit,
String accessToken,
String accountName,

View File

@ -72,10 +72,13 @@ public class Utils {
.replaceAll("(^|^ *|\\n *)#####(?!($|\\s|#))", "$0 ")
.replaceAll("(^|^ *|\\n *)######(?!($|\\s|#))", "$0 "));
return fixSuperScript(regexed);
//return fixSuperScript(regexed);
// We don't want to fix super scripts here because we need the original markdown later for editing posts
return regexed.toString();
}
private static String fixSuperScript(StringBuilder regexed) {
public static String fixSuperScript(String regexedMarkdown) {
StringBuilder regexed = new StringBuilder(regexedMarkdown);
boolean hasBracket = false;
int nCarets = 0;
for (int i = 0; i < regexed.length(); i++) {

View File

@ -23,6 +23,7 @@
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1"
android:paddingBottom="144dp"
android:clipToPadding="false"
app:layoutManager=".customviews.LinearLayoutManagerBugFixed" />

View File

@ -23,6 +23,7 @@
android:layout_width="0dp"
android:layout_height="match_parent"
android:layout_weight="1"
android:paddingBottom="144dp"
android:clipToPadding="false"
app:layoutManager=".customviews.LinearLayoutManagerBugFixed" />

View File

@ -13,14 +13,23 @@
android:layout_height="wrap_content"
android:theme="@style/AppTheme.AppBarOverlay">
<androidx.appcompat.widget.Toolbar
<com.google.android.material.appbar.CollapsingToolbarLayout
android:id="@+id/collapsing_toolbar_layout_edit_profile_activity"
android:layout_width="match_parent"
android:layout_height="match_parent"
app:layout_scrollFlags="scroll|enterAlways"
app:titleEnabled="false"
app:toolbarId="@+id/toolbar_post_text_activity">
<com.google.android.material.appbar.MaterialToolbar
android:id="@+id/toolbar_view_edit_profile_activity"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:minHeight="?attr/actionBarSize"
app:navigationIcon="?attr/homeAsUpIndicator"
app:popupTheme="@style/AppTheme.PopupOverlay"
app:title="@string/action_edit_profile" />
app:popupTheme="@style/AppTheme.PopupOverlay" />
</com.google.android.material.appbar.CollapsingToolbarLayout>
</com.google.android.material.appbar.AppBarLayout>
@ -42,130 +51,121 @@
<FrameLayout
android:id="@+id/frame_layout_view_banner_edit_profile_activity"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="8dp">
android:layout_height="wrap_content">
<ImageView
<pl.droidsonroids.gif.GifImageView
android:id="@+id/image_view_banner_edit_profile_activity"
android:layout_width="match_parent"
android:layout_height="180dp"
android:contentDescription="@null"
android:scaleType="centerCrop"
tools:src="@tools:sample/backgrounds/scenic" />
<ImageView
android:id="@+id/image_view_change_banner_edit_profile_activity"
android:layout_width="32dp"
android:layout_height="32dp"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="end|bottom"
android:layout_margin="4dp"
android:layout_margin="8dp"
android:padding="8dp"
android:background="@drawable/ic_dot_outline"
android:contentDescription="@null"
android:padding="4dp"
app:srcCompat="@drawable/ic_outline_add_a_photo_day_night_24dp" />
</FrameLayout>
<FrameLayout
android:id="@+id/frame_layout_view_avatar_edit_profile_activity"
android:layout_width="74dp"
android:layout_height="74dp"
android:layout_marginStart="24dp"
android:layout_marginTop="143dp"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginStart="16dp"
android:layout_marginTop="144dp"
android:elevation="4dp">
<ImageView
<pl.droidsonroids.gif.GifImageView
android:id="@+id/image_view_avatar_edit_profile_activity"
android:layout_width="74dp"
android:layout_height="74dp"
android:contentDescription="@null"
android:layout_width="72dp"
android:layout_height="72dp"
tools:src="@tools:sample/avatars" />
<ImageView
android:id="@+id/image_view_change_avatar_edit_profile_activity"
android:layout_width="32dp"
android:layout_height="32dp"
android:layout_gravity="end|bottom"
android:layout_margin="4dp"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:padding="8dp"
android:background="@drawable/ic_dot_outline"
android:contentDescription="@null"
android:padding="4dp"
app:srcCompat="@drawable/ic_outline_add_a_photo_day_night_24dp" />
</FrameLayout>
</FrameLayout>
<View
android:layout_width="match_parent"
android:layout_height="1dp"
android:layout_margin="8dp"
android:background="?dividerVertical" />
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="8dp"
android:orientation="vertical"
android:padding="8dp">
android:orientation="vertical">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:fontFamily="?attr/font_family"
android:paddingTop="48dp"
android:paddingStart="16dp"
android:paddingEnd="16dp"
android:text="@string/display_name_text"
android:textSize="?attr/font_18" />
android:textSize="?attr/font_18"
android:fontFamily="?attr/font_family" />
<EditText
android:id="@+id/edit_text_display_name_edit_profile_activity"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:gravity="top"
android:padding="16dp"
android:background="#00000000"
android:textSize="?attr/font_16"
android:fontFamily="?attr/font_family"
android:hint="@string/display_name_hint"
android:importantForAutofill="no"
android:inputType="textCapSentences"
android:lines="1"
android:maxLength="30"
android:maxLines="1"
android:paddingStart="16dp"
android:paddingEnd="16dp"
android:paddingBottom="16dp" />
android:maxLength="30" />
<TextView
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:text="@string/display_name_description" />
android:paddingStart="16dp"
android:paddingEnd="16dp"
android:text="@string/display_name_description"
android:textSize="?attr/font_12"
android:fontFamily="?attr/font_family" />
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="8dp"
android:orientation="vertical"
android:padding="8dp">
android:orientation="vertical">
<TextView
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:fontFamily="?attr/font_family"
android:paddingTop="48dp"
android:paddingStart="16dp"
android:paddingEnd="16dp"
android:text="@string/about_you_text"
android:textSize="?attr/font_18" />
android:textSize="?attr/font_18"
android:fontFamily="?attr/font_family" />
<EditText
android:id="@+id/edit_text_about_you_edit_profile_activity"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="16dp"
android:gravity="top"
android:background="#00000000"
android:textSize="?attr/font_16"
android:fontFamily="?attr/font_family"
android:hint="@string/about_you_hint"
android:importantForAutofill="no"
android:inputType="textCapSentences|textMultiLine"
android:lines="4"
android:maxLength="200"
android:maxLines="4"
android:paddingStart="16dp"
android:paddingEnd="16dp"
android:paddingBottom="16dp" />
android:maxLength="200" />
</LinearLayout>

View File

@ -73,10 +73,10 @@
</RelativeLayout>
<View
<com.google.android.material.divider.MaterialDivider
android:id="@+id/divider_1_post_gallery_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
android:layout_height="wrap_content" />
<LinearLayout
android:layout_width="match_parent"
@ -127,17 +127,10 @@
</LinearLayout>
<View
android:id="@+id/divider_2_post_gallery_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
<LinearLayout
android:id="@+id/receive_post_reply_notifications_linear_layout_post_gallery_activity"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="8dp"
android:paddingBottom="8dp"
android:paddingStart="16dp"
android:paddingEnd="16dp"
android:clickable="true"
@ -164,10 +157,10 @@
</LinearLayout>
<View
android:id="@+id/divider_3_post_gallery_activity"
<com.google.android.material.divider.MaterialDivider
android:id="@+id/divider_2_post_gallery_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
android:layout_height="wrap_content" />
<EditText
android:id="@+id/post_title_edit_text_post_gallery_activity"
@ -182,11 +175,6 @@
android:textSize="?attr/title_font_18"
android:fontFamily="?attr/title_font_family" />
<View
android:id="@+id/divider_4_post_gallery_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
<androidx.recyclerview.widget.RecyclerView
android:id="@+id/images_recycler_view_post_gallery_activity"
android:layout_width="match_parent"

View File

@ -73,10 +73,10 @@
</RelativeLayout>
<View
<com.google.android.material.divider.MaterialDivider
android:id="@+id/divider_1_post_image_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
android:layout_height="wrap_content" />
<LinearLayout
android:layout_width="match_parent"
@ -127,17 +127,10 @@
</LinearLayout>
<View
android:id="@+id/divider_2_post_image_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
<LinearLayout
android:id="@+id/receive_post_reply_notifications_linear_layout_post_image_activity"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="8dp"
android:paddingBottom="8dp"
android:paddingStart="16dp"
android:paddingEnd="16dp"
android:clickable="true"
@ -164,10 +157,10 @@
</LinearLayout>
<View
android:id="@+id/divider_3_post_image_activity"
<com.google.android.material.divider.MaterialDivider
android:id="@+id/divider_2_post_image_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
android:layout_height="wrap_content" />
<EditText
android:id="@+id/post_title_edit_text_post_image_activity"
@ -182,11 +175,6 @@
android:textSize="?attr/title_font_18"
android:fontFamily="?attr/title_font_family" />
<View
android:id="@+id/divider_4_post_image_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
<androidx.constraintlayout.widget.ConstraintLayout
android:id="@+id/select_image_constraint_layout_post_image_activity"
android:layout_width="match_parent"

View File

@ -73,10 +73,10 @@
</RelativeLayout>
<View
<com.google.android.material.divider.MaterialDivider
android:id="@+id/divider_1_post_link_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
android:layout_height="wrap_content" />
<LinearLayout
android:layout_width="match_parent"
@ -127,17 +127,10 @@
</LinearLayout>
<View
android:id="@+id/divider_2_post_link_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
<LinearLayout
android:id="@+id/receive_post_reply_notifications_linear_layout_post_link_activity"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="8dp"
android:paddingBottom="8dp"
android:paddingStart="16dp"
android:paddingEnd="16dp"
android:clickable="true"
@ -164,10 +157,10 @@
</LinearLayout>
<View
android:id="@+id/divider_3_post_link_activity"
<com.google.android.material.divider.MaterialDivider
android:id="@+id/divider_2_post_link_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
android:layout_height="wrap_content" />
<LinearLayout
android:layout_width="match_parent"
@ -201,11 +194,6 @@
</LinearLayout>
<View
android:id="@+id/divider_4_post_link_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
<EditText
android:id="@+id/post_link_edit_text_post_link_activity"
android:layout_width="match_parent"

View File

@ -79,10 +79,10 @@
</RelativeLayout>
<View
<com.google.android.material.divider.MaterialDivider
android:id="@+id/divider_1_post_text_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
android:layout_height="wrap_content" />
<LinearLayout
android:layout_width="match_parent"
@ -130,17 +130,10 @@
</LinearLayout>
<View
android:id="@+id/divider_2_post_text_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
<LinearLayout
android:id="@+id/receive_post_reply_notifications_linear_layout_post_text_activity"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="8dp"
android:paddingBottom="8dp"
android:paddingStart="16dp"
android:paddingEnd="16dp"
android:clickable="true"
@ -167,10 +160,10 @@
</LinearLayout>
<View
android:id="@+id/divider_3_post_text_activity"
<com.google.android.material.divider.MaterialDivider
android:id="@+id/divider_2_post_text_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
android:layout_height="wrap_content" />
<EditText
android:id="@+id/post_title_edit_text_post_text_activity"
@ -184,11 +177,6 @@
android:textSize="?attr/title_font_18"
android:fontFamily="?attr/title_font_family" />
<View
android:id="@+id/divider_4_post_text_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
<EditText
android:id="@+id/post_text_content_edit_text_post_text_activity"
android:layout_width="match_parent"

View File

@ -73,10 +73,10 @@
</RelativeLayout>
<View
<com.google.android.material.divider.MaterialDivider
android:id="@+id/divider_1_post_video_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
android:layout_height="wrap_content" />
<LinearLayout
android:layout_width="match_parent"
@ -127,17 +127,10 @@
</LinearLayout>
<View
android:id="@+id/divider_2_post_video_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
<LinearLayout
android:id="@+id/receive_post_reply_notifications_linear_layout_post_video_activity"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:padding="8dp"
android:paddingBottom="8dp"
android:paddingStart="16dp"
android:paddingEnd="16dp"
android:clickable="true"
@ -164,10 +157,10 @@
</LinearLayout>
<View
android:id="@+id/divider_3_post_video_activity"
<com.google.android.material.divider.MaterialDivider
android:id="@+id/divider_2_post_video_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
android:layout_height="wrap_content" />
<EditText
android:id="@+id/post_title_edit_text_post_video_activity"
@ -182,11 +175,6 @@
android:textSize="?attr/title_font_18"
android:fontFamily="?attr/title_font_family" />
<View
android:id="@+id/divider_4_post_video_activity"
android:layout_width="match_parent"
android:layout_height="1dp" />
<androidx.constraintlayout.widget.ConstraintLayout
android:id="@+id/select_video_constraint_layout_post_video_activity"
android:layout_width="match_parent"
@ -197,25 +185,27 @@
android:id="@+id/capture_fab_post_video_activity"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="16dp"
android:src="@drawable/ic_outline_add_a_photo_24dp"
app:useCompatPadding="true"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toStartOf="@+id/select_from_library_fab_post_video_activity"
app:layout_constraintHorizontal_chainStyle="spread"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toTopOf="parent"
app:tint="@android:color/white" />
app:layout_constraintTop_toTopOf="parent" />
<com.google.android.material.floatingactionbutton.FloatingActionButton
android:id="@+id/select_from_library_fab_post_video_activity"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="16dp"
android:src="@drawable/ic_outline_select_photo_24dp"
app:useCompatPadding="true"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintHorizontal_chainStyle="spread"
app:layout_constraintStart_toEndOf="@+id/capture_fab_post_video_activity"
app:layout_constraintTop_toTopOf="parent"
app:tint="@android:color/white" />
app:layout_constraintTop_toTopOf="parent" />
</androidx.constraintlayout.widget.ConstraintLayout>

View File

@ -119,6 +119,14 @@
android:src="@drawable/ic_file_download_toolbar_white_24dp"
android:background="?attr/selectableItemBackgroundBorderless" />
<ImageView
android:id="@+id/playback_speed_image_view_exo_playback_control_view"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:padding="16dp"
android:src="@drawable/ic_playback_speed_toolbar_24dp"
android:background="?attr/selectableItemBackgroundBorderless" />
</LinearLayout>
</com.google.android.material.bottomappbar.BottomAppBar>

View File

@ -31,6 +31,7 @@
android:layout_width="match_parent"
android:layout_height="match_parent"
app:show_timeout="1500"
app:auto_show="false"
app:controller_layout_id="@layout/exo_autoplay_playback_control_view" />
<pl.droidsonroids.gif.GifImageView

View File

@ -31,6 +31,7 @@
android:layout_width="match_parent"
android:layout_height="match_parent"
app:show_timeout="1500"
app:auto_show="false"
app:controller_layout_id="@layout/exo_autoplay_playback_control_view_legacy" />
<pl.droidsonroids.gif.GifImageView

View File

@ -214,6 +214,7 @@
android:layout_width="match_parent"
android:layout_height="match_parent"
app:show_timeout="1500"
app:auto_show="false"
app:controller_layout_id="@layout/exo_autoplay_playback_control_view" />
<pl.droidsonroids.gif.GifImageView

View File

@ -214,6 +214,7 @@
android:layout_width="match_parent"
android:layout_height="match_parent"
app:show_timeout="1500"
app:auto_show="false"
app:controller_layout_id="@layout/exo_autoplay_playback_control_view_legacy" />
<pl.droidsonroids.gif.GifImageView

View File

@ -208,6 +208,7 @@
android:layout_width="match_parent"
android:layout_height="match_parent"
app:show_timeout="1500"
app:auto_show="false"
app:controller_layout_id="@layout/exo_autoplay_playback_control_view" />
<pl.droidsonroids.gif.GifImageView

View File

@ -208,6 +208,7 @@
android:layout_width="match_parent"
android:layout_height="match_parent"
app:show_timeout="1500"
app:auto_show="false"
app:controller_layout_id="@layout/exo_autoplay_playback_control_view_legacy" />
<pl.droidsonroids.gif.GifImageView

View File

@ -216,8 +216,7 @@
android:id="@+id/image_view_item_post_with_preview"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:adjustViewBounds="true"
android:scaleType="fitStart" />
android:adjustViewBounds="true" />
<ImageView
android:id="@+id/video_or_gif_indicator_image_view_item_post_with_preview"

View File

@ -6,6 +6,6 @@
android:id="@+id/action_save_edit_profile_activity"
android:orderInCategory="1"
android:title="@string/action_save"
android:icon="@drawable/ic_save_to_database_24dp"
android:icon="@drawable/ic_check_circle_toolbar_24dp"
app:showAsAction="ifRoom" />
</menu>

View File

@ -54,8 +54,14 @@
app:showAsAction="never" />
<item
android:id="@+id/action_go_to_wiki_activity"
android:id="@+id/action_go_to_wiki_view_subreddit_detail_activity"
android:orderInCategory="9"
android:title="@string/action_go_to_wiki"
app:showAsAction="never" />
<item
android:id="@+id/action_contact_mods_view_subreddit_detail_activity"
android:orderInCategory="10"
android:title="@string/action_contact_mods"
app:showAsAction="never" />
</menu>

View File

@ -43,6 +43,7 @@
<string name="post_gallery_activity_label">Gallery Post</string>
<string name="trending_activity_label">Trending</string>
<string name="wiki_activity_label">Wiki</string>
<string name="edit_profile_activity_label">Edit Profile</string>
<string name="navigation_drawer_open">Open navigation drawer</string>
<string name="navigation_drawer_close">Close navigation drawer</string>
@ -91,6 +92,7 @@
<string name="action_share_post_link">Share Post Link</string>
<string name="action_go_to_wiki">Go to Wiki</string>
<string name="action_playback_speed">Playback Speed</string>
<string name="action_contact_mods">Contact Mods</string>
<string name="parse_json_response_error">Error occurred when parsing the JSON response</string>
<string name="retrieve_token_error">Error Retrieving the token</string>
@ -1226,18 +1228,18 @@
<string name="remove_banner">Remove Banner</string>
<string name="display_name_text">Display Name</string>
<string name="display_name_hint">Show on your profile page</string>
<string name="display_name_description">This will be displayed to viewer of your profile page and does not change your username</string>
<string name="display_name_description">This will be displayed to viewers of your profile page and does not change your username.</string>
<string name="about_you_text">About You</string>
<string name="about_you_hint">A little description of your self</string>
<string name="message_remove_avatar_success">Success remove Avatar</string>
<string name="message_remove_avatar_failed_fmt">Failed remove Avatar %s</string>
<string name="message_remove_banner_success">Success remove Banner</string>
<string name="message_remove_banner_failed_fmt">Failed remove Banner %s</string>
<string name="message_change_avatar_success">Success changing Avatar</string>
<string name="message_change_avatar_failed_fmt">Failed changing Avatar %s</string>
<string name="message_change_banner_success">Success changing Banner</string>
<string name="message_change_banner_failed_fmt">Failed changing Banner %s</string>
<string name="message_save_profile_success">Success save profile</string>
<string name="message_save_profile_failed_fmt">Failed save profile %s</string>
<string name="about_you_hint">A little description of yourself</string>
<string name="message_remove_avatar_success">Remove avatar successfully</string>
<string name="message_remove_avatar_failed_fmt">Failed to remove avatar %s</string>
<string name="message_remove_banner_success">Remove banner successfully</string>
<string name="message_remove_banner_failed_fmt">Failed to remove banner %s</string>
<string name="message_change_avatar_success">Change avatar successfully</string>
<string name="message_change_avatar_failed_fmt">Failed to change avatar %s</string>
<string name="message_change_banner_success">Changing banner successfully</string>
<string name="message_change_banner_failed_fmt">Failed to change banner %s</string>
<string name="message_save_profile_success">Save profile successfully</string>
<string name="message_save_profile_failed_fmt">Failed to save profile %s</string>
</resources>