mirror of
https://codeberg.org/Bazsalanszky/Infinity-For-Lemmy.git
synced 2024-11-10 20:57:25 +01:00
Start adding RPAN support.
This commit is contained in:
parent
09f05f3839
commit
bd0068eb6c
@ -32,7 +32,12 @@
|
||||
android:theme="@style/AppTheme"
|
||||
android:usesCleartextTraffic="true"
|
||||
tools:replace="android:label">
|
||||
<activity android:name=".activities.MotionTestActivity"
|
||||
<activity android:name=".activities.RPANActivity"
|
||||
android:label="@string/rpan_activity_label"
|
||||
android:parentActivityName=".activities.MainActivity"
|
||||
android:theme="@style/AppTheme.NoActionBar" />
|
||||
<activity
|
||||
android:name=".activities.MotionTestActivity"
|
||||
android:theme="@style/AppTheme.NoActionBar" />
|
||||
<activity
|
||||
android:name=".activities.LockScreenActivity"
|
||||
|
@ -31,6 +31,7 @@ import ml.docilealligator.infinityforreddit.activities.PostImageActivity;
|
||||
import ml.docilealligator.infinityforreddit.activities.PostLinkActivity;
|
||||
import ml.docilealligator.infinityforreddit.activities.PostTextActivity;
|
||||
import ml.docilealligator.infinityforreddit.activities.PostVideoActivity;
|
||||
import ml.docilealligator.infinityforreddit.activities.RPANActivity;
|
||||
import ml.docilealligator.infinityforreddit.activities.ReportActivity;
|
||||
import ml.docilealligator.infinityforreddit.activities.RulesActivity;
|
||||
import ml.docilealligator.infinityforreddit.activities.SearchActivity;
|
||||
@ -69,6 +70,7 @@ import ml.docilealligator.infinityforreddit.fragments.UserListingFragment;
|
||||
import ml.docilealligator.infinityforreddit.fragments.ViewImgurImageFragment;
|
||||
import ml.docilealligator.infinityforreddit.fragments.ViewImgurVideoFragment;
|
||||
import ml.docilealligator.infinityforreddit.fragments.ViewPostDetailFragment;
|
||||
import ml.docilealligator.infinityforreddit.fragments.ViewRPANBroadcastFragment;
|
||||
import ml.docilealligator.infinityforreddit.fragments.ViewRedditGalleryImageOrGifFragment;
|
||||
import ml.docilealligator.infinityforreddit.fragments.ViewRedditGalleryVideoFragment;
|
||||
import ml.docilealligator.infinityforreddit.services.DownloadMediaService;
|
||||
@ -269,4 +271,8 @@ public interface AppComponent {
|
||||
void inject(LockScreenActivity lockScreenActivity);
|
||||
|
||||
void inject(MaterialYouService materialYouService);
|
||||
|
||||
void inject(RPANActivity rpanActivity);
|
||||
|
||||
void inject(ViewRPANBroadcastFragment viewRPANBroadcastFragment);
|
||||
}
|
||||
|
@ -152,6 +152,17 @@ class AppModule {
|
||||
.build();
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Named("strapi")
|
||||
@Singleton
|
||||
Retrofit providestrapiRetrofit(OkHttpClient okHttpClient) {
|
||||
return new Retrofit.Builder()
|
||||
.baseUrl(APIUtils.STRAPI_BASE_URI)
|
||||
.client(okHttpClient)
|
||||
.addConverterFactory(ScalarsConverterFactory.create())
|
||||
.build();
|
||||
}
|
||||
|
||||
@Provides
|
||||
@Singleton
|
||||
OkHttpClient provideOkHttpClient(@Named("no_oauth") Retrofit retrofit, RedditDataRoomDatabase accountRoomDatabase,
|
||||
|
@ -0,0 +1,226 @@
|
||||
package ml.docilealligator.infinityforreddit;
|
||||
|
||||
import android.os.Parcel;
|
||||
import android.os.Parcelable;
|
||||
|
||||
public class RPANBroadcast implements Parcelable {
|
||||
|
||||
public int upvotes;
|
||||
public int downvotes;
|
||||
public int uniqueWatchers;
|
||||
public int continuousWatchers;
|
||||
public int totalContinuousWatchers;
|
||||
public boolean chatDisabled;
|
||||
public double broadcastTime;
|
||||
public double estimatedRemainingTime;
|
||||
|
||||
public RPANPost rpanPost;
|
||||
public RPANStream rpanStream;
|
||||
|
||||
public RPANBroadcast(int upvotes, int downvotes, int uniqueWatchers, int continuousWatchers,
|
||||
int totalContinuousWatchers, boolean chatDisabled, double broadcastTime,
|
||||
double estimatedRemainingTime, RPANPost rpanPost, RPANStream rpanStream) {
|
||||
this.upvotes = upvotes;
|
||||
this.downvotes = downvotes;
|
||||
this.uniqueWatchers = uniqueWatchers;
|
||||
this.continuousWatchers = continuousWatchers;
|
||||
this.totalContinuousWatchers = totalContinuousWatchers;
|
||||
this.chatDisabled = chatDisabled;
|
||||
this.broadcastTime = broadcastTime;
|
||||
this.estimatedRemainingTime = estimatedRemainingTime;
|
||||
this.rpanPost = rpanPost;
|
||||
this.rpanStream = rpanStream;
|
||||
}
|
||||
|
||||
protected RPANBroadcast(Parcel in) {
|
||||
upvotes = in.readInt();
|
||||
downvotes = in.readInt();
|
||||
uniqueWatchers = in.readInt();
|
||||
continuousWatchers = in.readInt();
|
||||
totalContinuousWatchers = in.readInt();
|
||||
chatDisabled = in.readByte() != 0;
|
||||
broadcastTime = in.readDouble();
|
||||
estimatedRemainingTime = in.readDouble();
|
||||
rpanPost = in.readParcelable(RPANPost.class.getClassLoader());
|
||||
rpanStream = in.readParcelable(RPANStream.class.getClassLoader());
|
||||
}
|
||||
|
||||
public static final Creator<RPANBroadcast> CREATOR = new Creator<RPANBroadcast>() {
|
||||
@Override
|
||||
public RPANBroadcast createFromParcel(Parcel in) {
|
||||
return new RPANBroadcast(in);
|
||||
}
|
||||
|
||||
@Override
|
||||
public RPANBroadcast[] newArray(int size) {
|
||||
return new RPANBroadcast[size];
|
||||
}
|
||||
};
|
||||
|
||||
@Override
|
||||
public int describeContents() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeToParcel(Parcel parcel, int i) {
|
||||
parcel.writeInt(upvotes);
|
||||
parcel.writeInt(downvotes);
|
||||
parcel.writeInt(uniqueWatchers);
|
||||
parcel.writeInt(continuousWatchers);
|
||||
parcel.writeInt(totalContinuousWatchers);
|
||||
parcel.writeByte((byte) (chatDisabled ? 1 : 0));
|
||||
parcel.writeDouble(broadcastTime);
|
||||
parcel.writeDouble(estimatedRemainingTime);
|
||||
parcel.writeParcelable(rpanPost, i);
|
||||
parcel.writeParcelable(rpanStream, i);
|
||||
}
|
||||
|
||||
public static class RPANPost implements Parcelable{
|
||||
public String title;
|
||||
public String subredditName;
|
||||
public String subredditIconUrl;
|
||||
public String username;
|
||||
public int postScore;
|
||||
public String voteState;
|
||||
public double upvoteRatio;
|
||||
public String postPermalink;
|
||||
public boolean isNsfw;
|
||||
public boolean isLocked;
|
||||
public boolean isArchived;
|
||||
public boolean isSpoiler;
|
||||
public String suggestedCommentSort;
|
||||
public String liveCommentsWebsocketUrl;
|
||||
|
||||
public RPANPost(String title, String subredditName, String subredditIconUrl, String username,
|
||||
int postScore, String voteState, double upvoteRatio, String postPermalink, String rpanUrl,
|
||||
boolean isNsfw, boolean isLocked, boolean isArchived, boolean isSpoiler,
|
||||
String suggestedCommentSort, String liveCommentsWebsocketUrl) {
|
||||
this.title = title;
|
||||
this.subredditName = subredditName;
|
||||
this.subredditIconUrl = subredditIconUrl;
|
||||
this.username = username;
|
||||
this.postScore = postScore;
|
||||
this.voteState = voteState;
|
||||
this.upvoteRatio = upvoteRatio;
|
||||
this.postPermalink = postPermalink;
|
||||
this.isNsfw = isNsfw;
|
||||
this.isLocked = isLocked;
|
||||
this.isArchived = isArchived;
|
||||
this.isSpoiler = isSpoiler;
|
||||
this.suggestedCommentSort = suggestedCommentSort;
|
||||
this.liveCommentsWebsocketUrl = liveCommentsWebsocketUrl;
|
||||
}
|
||||
|
||||
protected RPANPost(Parcel in) {
|
||||
title = in.readString();
|
||||
subredditName = in.readString();
|
||||
subredditIconUrl = in.readString();
|
||||
username = in.readString();
|
||||
postScore = in.readInt();
|
||||
voteState = in.readString();
|
||||
upvoteRatio = in.readDouble();
|
||||
postPermalink = in.readString();
|
||||
isNsfw = in.readByte() != 0;
|
||||
isLocked = in.readByte() != 0;
|
||||
isArchived = in.readByte() != 0;
|
||||
isSpoiler = in.readByte() != 0;
|
||||
suggestedCommentSort = in.readString();
|
||||
liveCommentsWebsocketUrl = in.readString();
|
||||
}
|
||||
|
||||
public static final Creator<RPANPost> CREATOR = new Creator<RPANPost>() {
|
||||
@Override
|
||||
public RPANPost createFromParcel(Parcel in) {
|
||||
return new RPANPost(in);
|
||||
}
|
||||
|
||||
@Override
|
||||
public RPANPost[] newArray(int size) {
|
||||
return new RPANPost[size];
|
||||
}
|
||||
};
|
||||
|
||||
@Override
|
||||
public int describeContents() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeToParcel(Parcel parcel, int i) {
|
||||
parcel.writeString(title);
|
||||
parcel.writeString(subredditName);
|
||||
parcel.writeString(subredditIconUrl);
|
||||
parcel.writeString(username);
|
||||
parcel.writeInt(postScore);
|
||||
parcel.writeString(voteState);
|
||||
parcel.writeDouble(upvoteRatio);
|
||||
parcel.writeString(postPermalink);
|
||||
parcel.writeByte((byte) (isNsfw ? 1 : 0));
|
||||
parcel.writeByte((byte) (isLocked ? 1 : 0));
|
||||
parcel.writeByte((byte) (isArchived ? 1 : 0));
|
||||
parcel.writeByte((byte) (isSpoiler ? 1 : 0));
|
||||
parcel.writeString(suggestedCommentSort);
|
||||
parcel.writeString(liveCommentsWebsocketUrl);
|
||||
}
|
||||
}
|
||||
|
||||
public static class RPANStream implements Parcelable {
|
||||
public String streamId;
|
||||
public String hlsUrl;
|
||||
public String thumbnail;
|
||||
public int width;
|
||||
public int height;
|
||||
public long publishAt;
|
||||
public String state;
|
||||
|
||||
public RPANStream(String streamId, String hlsUrl, String thumbnail, int width, int height, long publishAt,
|
||||
String state) {
|
||||
this.streamId = streamId;
|
||||
this.hlsUrl = hlsUrl;
|
||||
this.thumbnail = thumbnail;
|
||||
this.width = width;
|
||||
this.height = height;
|
||||
this.publishAt = publishAt;
|
||||
this.state = state;
|
||||
}
|
||||
|
||||
protected RPANStream(Parcel in) {
|
||||
streamId = in.readString();
|
||||
hlsUrl = in.readString();
|
||||
thumbnail = in.readString();
|
||||
width = in.readInt();
|
||||
height = in.readInt();
|
||||
publishAt = in.readLong();
|
||||
state = in.readString();
|
||||
}
|
||||
|
||||
public static final Creator<RPANStream> CREATOR = new Creator<RPANStream>() {
|
||||
@Override
|
||||
public RPANStream createFromParcel(Parcel in) {
|
||||
return new RPANStream(in);
|
||||
}
|
||||
|
||||
@Override
|
||||
public RPANStream[] newArray(int size) {
|
||||
return new RPANStream[size];
|
||||
}
|
||||
};
|
||||
|
||||
@Override
|
||||
public int describeContents() {
|
||||
return 0;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void writeToParcel(Parcel parcel, int i) {
|
||||
parcel.writeString(streamId);
|
||||
parcel.writeString(hlsUrl);
|
||||
parcel.writeString(thumbnail);
|
||||
parcel.writeInt(width);
|
||||
parcel.writeInt(height);
|
||||
parcel.writeLong(publishAt);
|
||||
parcel.writeString(state);
|
||||
}
|
||||
}
|
||||
}
|
@ -9,8 +9,6 @@ import android.graphics.Color;
|
||||
import android.os.Build;
|
||||
import android.os.Bundle;
|
||||
import android.os.Handler;
|
||||
import android.text.Editable;
|
||||
import android.text.TextWatcher;
|
||||
import android.view.Gravity;
|
||||
import android.view.KeyEvent;
|
||||
import android.view.Menu;
|
||||
@ -83,8 +81,6 @@ import ml.docilealligator.infinityforreddit.SortType;
|
||||
import ml.docilealligator.infinityforreddit.SortTypeSelectionCallback;
|
||||
import ml.docilealligator.infinityforreddit.account.AccountViewModel;
|
||||
import ml.docilealligator.infinityforreddit.adapters.NavigationDrawerRecyclerViewAdapter;
|
||||
import ml.docilealligator.infinityforreddit.adapters.SubredditAutocompleteRecyclerViewAdapter;
|
||||
import ml.docilealligator.infinityforreddit.apis.RedditAPI;
|
||||
import ml.docilealligator.infinityforreddit.asynctasks.InsertSubscribedThings;
|
||||
import ml.docilealligator.infinityforreddit.asynctasks.SwitchAccount;
|
||||
import ml.docilealligator.infinityforreddit.asynctasks.SwitchToAnonymousMode;
|
||||
@ -110,20 +106,16 @@ import ml.docilealligator.infinityforreddit.multireddit.MultiRedditViewModel;
|
||||
import ml.docilealligator.infinityforreddit.post.Post;
|
||||
import ml.docilealligator.infinityforreddit.post.PostDataSource;
|
||||
import ml.docilealligator.infinityforreddit.readpost.InsertReadPost;
|
||||
import ml.docilealligator.infinityforreddit.subreddit.ParseSubredditData;
|
||||
import ml.docilealligator.infinityforreddit.subreddit.SubredditData;
|
||||
import ml.docilealligator.infinityforreddit.subscribedsubreddit.SubscribedSubredditData;
|
||||
import ml.docilealligator.infinityforreddit.subscribedsubreddit.SubscribedSubredditViewModel;
|
||||
import ml.docilealligator.infinityforreddit.subscribeduser.SubscribedUserData;
|
||||
import ml.docilealligator.infinityforreddit.user.FetchUserData;
|
||||
import ml.docilealligator.infinityforreddit.user.UserData;
|
||||
import ml.docilealligator.infinityforreddit.utils.APIUtils;
|
||||
import ml.docilealligator.infinityforreddit.utils.CustomThemeSharedPreferencesUtils;
|
||||
import ml.docilealligator.infinityforreddit.utils.SharedPreferencesUtils;
|
||||
import ml.docilealligator.infinityforreddit.utils.Utils;
|
||||
import retrofit2.Call;
|
||||
import retrofit2.Callback;
|
||||
import retrofit2.Response;
|
||||
import retrofit2.Retrofit;
|
||||
|
||||
import static androidx.appcompat.app.AppCompatDelegate.MODE_NIGHT_NO;
|
||||
@ -1381,7 +1373,7 @@ public class MainActivity extends BaseActivity implements SortTypeSelectionCallb
|
||||
}
|
||||
|
||||
private void goToSubreddit() {
|
||||
View rootView = getLayoutInflater().inflate(R.layout.dialog_go_to_thing_edit_text, coordinatorLayout, false);
|
||||
/*View rootView = getLayoutInflater().inflate(R.layout.dialog_go_to_thing_edit_text, coordinatorLayout, false);
|
||||
TextInputEditText thingEditText = rootView.findViewById(R.id.text_input_edit_text_go_to_thing_edit_text);
|
||||
RecyclerView recyclerView = rootView.findViewById(R.id.recycler_view_go_to_thing_edit_text);
|
||||
InputMethodManager imm = (InputMethodManager) getSystemService(Context.INPUT_METHOD_SERVICE);
|
||||
@ -1475,7 +1467,9 @@ public class MainActivity extends BaseActivity implements SortTypeSelectionCallb
|
||||
imm.hideSoftInputFromWindow(thingEditText.getWindowToken(), 0);
|
||||
}
|
||||
})
|
||||
.show();
|
||||
.show();*/
|
||||
Intent intent = new Intent(this, RPANActivity.class);
|
||||
startActivity(intent);
|
||||
}
|
||||
|
||||
private void goToUser() {
|
||||
|
@ -0,0 +1,258 @@
|
||||
package ml.docilealligator.infinityforreddit.activities;
|
||||
|
||||
import android.content.SharedPreferences;
|
||||
import android.os.Build;
|
||||
import android.os.Bundle;
|
||||
import android.os.Handler;
|
||||
import android.view.View;
|
||||
import android.view.Window;
|
||||
import android.view.WindowManager;
|
||||
import android.widget.Toast;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.appcompat.widget.Toolbar;
|
||||
import androidx.coordinatorlayout.widget.CoordinatorLayout;
|
||||
import androidx.fragment.app.Fragment;
|
||||
import androidx.fragment.app.FragmentActivity;
|
||||
import androidx.viewpager2.adapter.FragmentStateAdapter;
|
||||
import androidx.viewpager2.widget.ViewPager2;
|
||||
|
||||
import com.google.android.material.appbar.AppBarLayout;
|
||||
|
||||
import org.json.JSONArray;
|
||||
import org.json.JSONException;
|
||||
import org.json.JSONObject;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.concurrent.Executor;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.inject.Named;
|
||||
|
||||
import butterknife.BindView;
|
||||
import butterknife.ButterKnife;
|
||||
import ml.docilealligator.infinityforreddit.Infinity;
|
||||
import ml.docilealligator.infinityforreddit.R;
|
||||
import ml.docilealligator.infinityforreddit.RPANBroadcast;
|
||||
import ml.docilealligator.infinityforreddit.apis.Strapi;
|
||||
import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
|
||||
import ml.docilealligator.infinityforreddit.fragments.ViewRPANBroadcastFragment;
|
||||
import ml.docilealligator.infinityforreddit.utils.APIUtils;
|
||||
import ml.docilealligator.infinityforreddit.utils.JSONUtils;
|
||||
import ml.docilealligator.infinityforreddit.utils.SharedPreferencesUtils;
|
||||
import retrofit2.Call;
|
||||
import retrofit2.Callback;
|
||||
import retrofit2.Response;
|
||||
import retrofit2.Retrofit;
|
||||
|
||||
public class RPANActivity extends BaseActivity {
|
||||
|
||||
@BindView(R.id.coordinator_layout_rpan_activity)
|
||||
CoordinatorLayout coordinatorLayout;
|
||||
@BindView(R.id.appbar_layout_rpan_activity)
|
||||
AppBarLayout appBarLayout;
|
||||
@BindView(R.id.toolbar_rpan_activity)
|
||||
Toolbar toolbar;
|
||||
@BindView(R.id.view_pager_2_rpan_activity)
|
||||
ViewPager2 viewPager2;
|
||||
@Inject
|
||||
@Named("strapi")
|
||||
Retrofit strapiRetrofit;
|
||||
@Inject
|
||||
@Named("default")
|
||||
SharedPreferences mSharedPreferences;
|
||||
@Inject
|
||||
@Named("current_account")
|
||||
SharedPreferences mCurrentAccountSharedPreferences;
|
||||
@Inject
|
||||
CustomThemeWrapper mCustomThemeWrapper;
|
||||
@Inject
|
||||
Executor mExecutor;
|
||||
private String mAccessToken;
|
||||
private String mAccountName;
|
||||
private ArrayList<RPANBroadcast> rpanBroadcasts;
|
||||
private String nextCursor;
|
||||
private SectionsPagerAdapter sectionsPagerAdapter;
|
||||
|
||||
@Override
|
||||
protected void onCreate(Bundle savedInstanceState) {
|
||||
((Infinity) getApplication()).getAppComponent().inject(this);
|
||||
|
||||
super.onCreate(savedInstanceState);
|
||||
setContentView(R.layout.activity_rpanactivity);
|
||||
|
||||
ButterKnife.bind(this);
|
||||
|
||||
applyCustomTheme();
|
||||
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
|
||||
Window window = getWindow();
|
||||
|
||||
if (isChangeStatusBarIconColor()) {
|
||||
addOnOffsetChangedListener(appBarLayout);
|
||||
}
|
||||
|
||||
if (isImmersiveInterface()) {
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
|
||||
coordinatorLayout.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);
|
||||
}
|
||||
adjustToolbar(toolbar);
|
||||
}
|
||||
}
|
||||
|
||||
setSupportActionBar(toolbar);
|
||||
getSupportActionBar().setDisplayHomeAsUpEnabled(true);
|
||||
|
||||
mAccessToken = mCurrentAccountSharedPreferences.getString(SharedPreferencesUtils.ACCESS_TOKEN, null);
|
||||
mAccountName = mCurrentAccountSharedPreferences.getString(SharedPreferencesUtils.ACCOUNT_NAME, null);
|
||||
|
||||
loadRPANVideos();
|
||||
}
|
||||
|
||||
private void loadRPANVideos() {
|
||||
strapiRetrofit.create(Strapi.class).getAllBroadcasts(APIUtils.getOAuthHeader(mAccessToken)).enqueue(new Callback<String>() {
|
||||
@Override
|
||||
public void onResponse(@NonNull Call<String> call, @NonNull Response<String> response) {
|
||||
if (response.isSuccessful()) {
|
||||
parseRPANBroadcasts(response.body());
|
||||
} else {
|
||||
Toast.makeText(RPANActivity.this,
|
||||
R.string.load_rpan_broadcasts_failed, Toast.LENGTH_SHORT).show();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onFailure(@NonNull Call<String> call, @NonNull Throwable t) {
|
||||
Toast.makeText(RPANActivity.this,
|
||||
R.string.load_rpan_broadcasts_failed, Toast.LENGTH_SHORT).show();
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void parseRPANBroadcasts(String response) {
|
||||
Handler handler = new Handler();
|
||||
mExecutor.execute(() -> {
|
||||
try {
|
||||
ArrayList<RPANBroadcast> rpanBroadcasts = new ArrayList<>();
|
||||
JSONObject responseObject = new JSONObject(response);
|
||||
String nextCursor = responseObject.getString(JSONUtils.NEXT_CURSOR_KEY);
|
||||
|
||||
JSONArray dataArray = responseObject.getJSONArray(JSONUtils.DATA_KEY);
|
||||
for (int i = 0; i < dataArray.length(); i++) {
|
||||
JSONObject singleData = dataArray.getJSONObject(i);
|
||||
JSONObject rpanPostObject = singleData.getJSONObject(JSONUtils.POST_KEY);
|
||||
RPANBroadcast.RPANPost rpanPost = new RPANBroadcast.RPANPost(
|
||||
rpanPostObject.getString(JSONUtils.TITLE_KEY),
|
||||
rpanPostObject.getJSONObject(JSONUtils.SUBREDDIT_KEY).getString(JSONUtils.NAME_KEY),
|
||||
rpanPostObject.getJSONObject(JSONUtils.SUBREDDIT_KEY).getJSONObject(JSONUtils.STYLES_KEY).getString(JSONUtils.ICON_KEY),
|
||||
rpanPostObject.getJSONObject(JSONUtils.AUTHOR_INFO_KEY).getString(JSONUtils.NAME_KEY),
|
||||
rpanPostObject.getInt(JSONUtils.SCORE_KEY),
|
||||
rpanPostObject.getString(JSONUtils.VOTE_STATE_KEY),
|
||||
rpanPostObject.getDouble(JSONUtils.UPVOTE_RATIO_CAMEL_CASE_KEY),
|
||||
rpanPostObject.getString(JSONUtils.PERMALINK_KEY),
|
||||
rpanPostObject.getJSONObject(JSONUtils.OUTBOUND_LINK_KEY).getString(JSONUtils.URL_KEY),
|
||||
rpanPostObject.getBoolean(JSONUtils.IS_NSFW_KEY),
|
||||
rpanPostObject.getBoolean(JSONUtils.IS_LOCKED_KEY),
|
||||
rpanPostObject.getBoolean(JSONUtils.IS_ARCHIVED_KEY),
|
||||
rpanPostObject.getBoolean(JSONUtils.IS_SPOILER),
|
||||
rpanPostObject.getString(JSONUtils.SUGGESTED_COMMENT_SORT_CAMEL_CASE_KEY),
|
||||
rpanPostObject.getString(JSONUtils.LIVE_COMMENTS_WEBSOCKET_KEY)
|
||||
);
|
||||
|
||||
JSONObject rpanStreamObject = singleData.getJSONObject(JSONUtils.STREAM_KEY);
|
||||
RPANBroadcast.RPANStream rpanStream = new RPANBroadcast.RPANStream(
|
||||
rpanStreamObject.getString(JSONUtils.STREAM_ID_KEY),
|
||||
rpanStreamObject.getString(JSONUtils.HLS_URL_KEY),
|
||||
rpanStreamObject.getString(JSONUtils.THUMBNAIL_KEY),
|
||||
rpanStreamObject.getInt(JSONUtils.WIDTH_KEY),
|
||||
rpanStreamObject.getInt(JSONUtils.HEIGHT_KEY),
|
||||
rpanStreamObject.getLong(JSONUtils.PUBLISH_AT_KEY),
|
||||
rpanStreamObject.getString(JSONUtils.STATE_KEY)
|
||||
);
|
||||
|
||||
rpanBroadcasts.add(new RPANBroadcast(
|
||||
singleData.getInt(JSONUtils.UPVOTES_KEY),
|
||||
singleData.getInt(JSONUtils.DOWNVOTES_KEY),
|
||||
singleData.getInt(JSONUtils.UNIQUE_WATCHERS_KEY),
|
||||
singleData.getInt(JSONUtils.CONTINUOUS_WATCHERS_KEY),
|
||||
singleData.getInt(JSONUtils.TOTAL_CONTINUOUS_WATCHERS_KEY),
|
||||
singleData.getBoolean(JSONUtils.CHAT_DISABLED_KEY),
|
||||
singleData.getDouble(JSONUtils.BROADCAST_TIME_KEY),
|
||||
singleData.getDouble(JSONUtils.ESTIMATED_REMAINING_TIME_KEY),
|
||||
rpanPost,
|
||||
rpanStream
|
||||
));
|
||||
}
|
||||
|
||||
handler.post(() -> {
|
||||
RPANActivity.this.rpanBroadcasts = rpanBroadcasts;
|
||||
RPANActivity.this.nextCursor = nextCursor;
|
||||
|
||||
initializeViewPager();
|
||||
});
|
||||
} catch (JSONException e) {
|
||||
e.printStackTrace();
|
||||
handler.post(() -> Toast.makeText(RPANActivity.this,
|
||||
R.string.parse_rpan_broadcasts_failed, Toast.LENGTH_SHORT).show());
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
private void initializeViewPager() {
|
||||
sectionsPagerAdapter = new SectionsPagerAdapter(this);
|
||||
viewPager2.setAdapter(sectionsPagerAdapter);
|
||||
viewPager2.setOffscreenPageLimit(3);
|
||||
viewPager2.setUserInputEnabled(!mSharedPreferences.getBoolean(SharedPreferencesUtils.DISABLE_SWIPING_BETWEEN_TABS, false));
|
||||
fixViewPager2Sensitivity(viewPager2);
|
||||
}
|
||||
|
||||
@Override
|
||||
protected SharedPreferences getDefaultSharedPreferences() {
|
||||
return mSharedPreferences;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected CustomThemeWrapper getCustomThemeWrapper() {
|
||||
return mCustomThemeWrapper;
|
||||
}
|
||||
|
||||
@Override
|
||||
protected void applyCustomTheme() {
|
||||
|
||||
}
|
||||
|
||||
private class SectionsPagerAdapter extends FragmentStateAdapter {
|
||||
|
||||
public SectionsPagerAdapter(FragmentActivity fa) {
|
||||
super(fa);
|
||||
}
|
||||
|
||||
@NonNull
|
||||
@Override
|
||||
public Fragment createFragment(int position) {
|
||||
ViewRPANBroadcastFragment fragment = new ViewRPANBroadcastFragment();
|
||||
Bundle bundle = new Bundle();
|
||||
bundle.putParcelable(ViewRPANBroadcastFragment.EXTRA_RPAN_BROADCAST, rpanBroadcasts.get(position));
|
||||
fragment.setArguments(bundle);
|
||||
return fragment;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
private Fragment getCurrentFragment() {
|
||||
if (viewPager2 == null || getSupportFragmentManager() == null) {
|
||||
return null;
|
||||
}
|
||||
return getSupportFragmentManager().findFragmentByTag("f" + viewPager2.getCurrentItem());
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getItemCount() {
|
||||
return rpanBroadcasts == null ? 0 : rpanBroadcasts.size();
|
||||
}
|
||||
}
|
||||
}
|
@ -0,0 +1,12 @@
|
||||
package ml.docilealligator.infinityforreddit.apis;
|
||||
|
||||
import java.util.Map;
|
||||
|
||||
import retrofit2.Call;
|
||||
import retrofit2.http.GET;
|
||||
import retrofit2.http.HeaderMap;
|
||||
|
||||
public interface Strapi {
|
||||
@GET("/broadcasts")
|
||||
Call<String> getAllBroadcasts(@HeaderMap Map<String ,String> headers);
|
||||
}
|
@ -0,0 +1,225 @@
|
||||
package ml.docilealligator.infinityforreddit.fragments;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.SharedPreferences;
|
||||
import android.net.Uri;
|
||||
import android.os.Bundle;
|
||||
import android.view.LayoutInflater;
|
||||
import android.view.View;
|
||||
import android.view.ViewGroup;
|
||||
import android.widget.ImageButton;
|
||||
import android.widget.ProgressBar;
|
||||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.appcompat.app.AppCompatActivity;
|
||||
import androidx.fragment.app.Fragment;
|
||||
|
||||
import com.google.android.exoplayer2.ExoPlaybackException;
|
||||
import com.google.android.exoplayer2.ExoPlayerFactory;
|
||||
import com.google.android.exoplayer2.Player;
|
||||
import com.google.android.exoplayer2.SimpleExoPlayer;
|
||||
import com.google.android.exoplayer2.source.BehindLiveWindowException;
|
||||
import com.google.android.exoplayer2.source.TrackGroupArray;
|
||||
import com.google.android.exoplayer2.source.hls.HlsMediaSource;
|
||||
import com.google.android.exoplayer2.trackselection.AdaptiveTrackSelection;
|
||||
import com.google.android.exoplayer2.trackselection.DefaultTrackSelector;
|
||||
import com.google.android.exoplayer2.trackselection.TrackSelection;
|
||||
import com.google.android.exoplayer2.trackselection.TrackSelectionArray;
|
||||
import com.google.android.exoplayer2.ui.PlayerView;
|
||||
import com.google.android.exoplayer2.ui.TrackSelectionDialogBuilder;
|
||||
import com.google.android.exoplayer2.upstream.DataSource;
|
||||
import com.google.android.exoplayer2.upstream.DefaultHttpDataSourceFactory;
|
||||
import com.google.android.exoplayer2.upstream.cache.SimpleCache;
|
||||
import com.google.android.exoplayer2.util.Util;
|
||||
|
||||
import javax.inject.Inject;
|
||||
import javax.inject.Named;
|
||||
|
||||
import butterknife.BindView;
|
||||
import butterknife.ButterKnife;
|
||||
import ml.docilealligator.infinityforreddit.Infinity;
|
||||
import ml.docilealligator.infinityforreddit.R;
|
||||
import ml.docilealligator.infinityforreddit.RPANBroadcast;
|
||||
import ml.docilealligator.infinityforreddit.customtheme.CustomThemeWrapper;
|
||||
import ml.docilealligator.infinityforreddit.utils.SharedPreferencesUtils;
|
||||
|
||||
public class ViewRPANBroadcastFragment extends Fragment {
|
||||
|
||||
public static final String EXTRA_RPAN_BROADCAST = "ERB";
|
||||
private static final String IS_MUTE_STATE = "IMS";
|
||||
|
||||
@BindView(R.id.player_view_view_rpan_broadcast_fragment)
|
||||
PlayerView playerView;
|
||||
@BindView(R.id.progress_bar_view_rpan_broadcast_fragment)
|
||||
ProgressBar progressBar;
|
||||
@BindView(R.id.mute_exo_playback_control_view)
|
||||
ImageButton muteButton;
|
||||
@BindView(R.id.hd_exo_playback_control_view)
|
||||
ImageButton hdButton;
|
||||
@Inject
|
||||
@Named("default")
|
||||
SharedPreferences mSharedPreferences;
|
||||
@Inject
|
||||
@Named("current_account")
|
||||
SharedPreferences mCurrentAccountSharedPreferences;
|
||||
@Inject
|
||||
CustomThemeWrapper mCustomThemeWrapper;
|
||||
@Inject
|
||||
SimpleCache mSimpleCache;
|
||||
private AppCompatActivity mActivity;
|
||||
private RPANBroadcast rpanBroadcast;
|
||||
private SimpleExoPlayer player;
|
||||
private DefaultTrackSelector trackSelector;
|
||||
private DataSource.Factory dataSourceFactory;
|
||||
|
||||
private boolean wasPlaying;
|
||||
private boolean isMute = false;
|
||||
private long resumePosition = -1;
|
||||
private boolean isDataSavingMode;
|
||||
|
||||
public ViewRPANBroadcastFragment() {
|
||||
// Required empty public constructor
|
||||
}
|
||||
|
||||
@Override
|
||||
public View onCreateView(LayoutInflater inflater, ViewGroup container,
|
||||
Bundle savedInstanceState) {
|
||||
// Inflate the layout for this fragment
|
||||
View rootView = inflater.inflate(R.layout.fragment_view_rpan_broadcast, container, false);
|
||||
|
||||
((Infinity) mActivity.getApplication()).getAppComponent().inject(this);
|
||||
|
||||
ButterKnife.bind(this, rootView);
|
||||
|
||||
rpanBroadcast = getArguments().getParcelable(EXTRA_RPAN_BROADCAST);
|
||||
|
||||
TrackSelection.Factory videoTrackSelectionFactory = new AdaptiveTrackSelection.Factory();
|
||||
trackSelector = new DefaultTrackSelector(videoTrackSelectionFactory);
|
||||
player = ExoPlayerFactory.newSimpleInstance(mActivity, trackSelector);
|
||||
playerView.setPlayer(player);
|
||||
|
||||
dataSourceFactory = new DefaultHttpDataSourceFactory(Util.getUserAgent(mActivity, "Infinity"));
|
||||
// Prepare the player with the source.
|
||||
player.prepare(new HlsMediaSource.Factory(dataSourceFactory).createMediaSource(Uri.parse(rpanBroadcast.rpanStream.hlsUrl)));
|
||||
player.setRepeatMode(Player.REPEAT_MODE_ALL);
|
||||
if (resumePosition > 0) {
|
||||
player.seekTo(resumePosition);
|
||||
}
|
||||
player.setPlayWhenReady(true);
|
||||
wasPlaying = true;
|
||||
|
||||
boolean muteVideo = mSharedPreferences.getBoolean(SharedPreferencesUtils.MUTE_VIDEO, false) ||
|
||||
(mSharedPreferences.getBoolean(SharedPreferencesUtils.MUTE_NSFW_VIDEO, false) && rpanBroadcast.rpanPost.isNsfw);
|
||||
|
||||
if (savedInstanceState != null) {
|
||||
isMute = savedInstanceState.getBoolean(IS_MUTE_STATE);
|
||||
if (isMute) {
|
||||
player.setVolume(0f);
|
||||
muteButton.setImageResource(R.drawable.ic_mute_24dp);
|
||||
} else {
|
||||
player.setVolume(1f);
|
||||
muteButton.setImageResource(R.drawable.ic_unmute_24dp);
|
||||
}
|
||||
} else if (muteVideo) {
|
||||
isMute = true;
|
||||
player.setVolume(0f);
|
||||
muteButton.setImageResource(R.drawable.ic_mute_24dp);
|
||||
} else {
|
||||
muteButton.setImageResource(R.drawable.ic_unmute_24dp);
|
||||
}
|
||||
|
||||
player.addListener(new Player.EventListener() {
|
||||
@Override
|
||||
public void onTracksChanged(TrackGroupArray trackGroups, TrackSelectionArray trackSelections) {
|
||||
if (!trackGroups.isEmpty()) {
|
||||
if (isDataSavingMode) {
|
||||
trackSelector.setParameters(
|
||||
trackSelector.buildUponParameters()
|
||||
.setMaxVideoSize(720, 720));
|
||||
}
|
||||
|
||||
hdButton.setVisibility(View.VISIBLE);
|
||||
hdButton.setOnClickListener(view -> {
|
||||
TrackSelectionDialogBuilder build = new TrackSelectionDialogBuilder(mActivity,
|
||||
getString(R.string.select_video_quality), trackSelector, 0);
|
||||
build.setShowDisableOption(true);
|
||||
build.setAllowAdaptiveSelections(false);
|
||||
build.build().show();
|
||||
});
|
||||
|
||||
for (int i = 0; i < trackGroups.length; i++) {
|
||||
String mimeType = trackGroups.get(i).getFormat(0).sampleMimeType;
|
||||
if (mimeType != null && mimeType.contains("audio")) {
|
||||
muteButton.setVisibility(View.VISIBLE);
|
||||
muteButton.setOnClickListener(view -> {
|
||||
if (isMute) {
|
||||
isMute = false;
|
||||
player.setVolume(1f);
|
||||
muteButton.setImageResource(R.drawable.ic_unmute_24dp);
|
||||
} else {
|
||||
isMute = true;
|
||||
player.setVolume(0f);
|
||||
muteButton.setImageResource(R.drawable.ic_mute_24dp);
|
||||
}
|
||||
});
|
||||
break;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
muteButton.setVisibility(View.GONE);
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
return rootView;
|
||||
}
|
||||
|
||||
private boolean isBehindLiveWindow(ExoPlaybackException e) {
|
||||
if (e.type != ExoPlaybackException.TYPE_SOURCE) {
|
||||
return false;
|
||||
}
|
||||
Throwable cause = e.getSourceException();
|
||||
while (cause != null) {
|
||||
if (cause instanceof BehindLiveWindowException) {
|
||||
return true;
|
||||
}
|
||||
cause = cause.getCause();
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onSaveInstanceState(@NonNull Bundle outState) {
|
||||
super.onSaveInstanceState(outState);
|
||||
outState.putBoolean(IS_MUTE_STATE, isMute);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onStart() {
|
||||
super.onStart();
|
||||
if (wasPlaying) {
|
||||
player.setPlayWhenReady(true);
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onStop() {
|
||||
super.onStop();
|
||||
wasPlaying = player.getPlayWhenReady();
|
||||
player.setPlayWhenReady(false);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onDestroy() {
|
||||
super.onDestroy();
|
||||
player.seekToDefaultPosition();
|
||||
player.stop(true);
|
||||
player.release();
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onAttach(@NonNull Context context) {
|
||||
super.onAttach(context);
|
||||
mActivity = (AppCompatActivity) context;
|
||||
}
|
||||
}
|
@ -22,6 +22,7 @@ public class APIUtils {
|
||||
public static final String REDGIFS_API_BASE_URI = "https://api.redgifs.com/v1/gfycats/";
|
||||
public static final String IMGUR_API_BASE_URI = "https://api.imgur.com/3/";
|
||||
public static final String PUSHSHIFT_API_BASE_URI = "https://api.pushshift.io/";
|
||||
public static final String STRAPI_BASE_URI = "https://strapi.reddit.com";
|
||||
|
||||
public static final String CLIENT_ID_KEY = "client_id";
|
||||
public static final String CLIENT_ID = "NOe2iKrPPzwscA";
|
||||
|
@ -135,4 +135,31 @@ public class JSONUtils {
|
||||
public static final String WEBM_URL_KEY = "webmUrl";
|
||||
public static final String UPVOTE_RATIO_KEY = "upvote_ratio";
|
||||
public static final String INBOX_COUNT_KEY = "inbox_count";
|
||||
public static final String NEXT_CURSOR_KEY = "next_cursor";
|
||||
public static final String POST_KEY = "post";
|
||||
public static final String STYLES_KEY = "styles";
|
||||
public static final String AUTHOR_INFO_KEY= "authorInfo";
|
||||
public static final String VOTE_STATE_KEY = "voteState";
|
||||
public static final String UPVOTE_RATIO_CAMEL_CASE_KEY = "upvoteRatio";
|
||||
public static final String OUTBOUND_LINK_KEY = "outboundLink";
|
||||
public static final String IS_NSFW_KEY = "isNsfw";
|
||||
public static final String IS_LOCKED_KEY = "isLocked";
|
||||
public static final String IS_ARCHIVED_KEY = "isArchived";
|
||||
public static final String IS_SPOILER = "isSpoiler";
|
||||
public static final String SUGGESTED_COMMENT_SORT_CAMEL_CASE_KEY = "suggestedCommentSort";
|
||||
public static final String LIVE_COMMENTS_WEBSOCKET_KEY = "liveCommentsWebsocket";
|
||||
public static final String ICON_KEY = "icon";
|
||||
public static final String STREAM_KEY = "stream";
|
||||
public static final String STREAM_ID_KEY = "stream_id";
|
||||
public static final String THUMBNAIL_KEY = "thumbnail";
|
||||
public static final String PUBLISH_AT_KEY = "publish_at";
|
||||
public static final String STATE_KEY = "state";
|
||||
public static final String UPVOTES_KEY = "upvotes";
|
||||
public static final String DOWNVOTES_KEY = "downvotes";
|
||||
public static final String UNIQUE_WATCHERS_KEY = "unique_watchers";
|
||||
public static final String CONTINUOUS_WATCHERS_KEY = "continuous_watchers";
|
||||
public static final String TOTAL_CONTINUOUS_WATCHERS_KEY = "total_continuous_watchers";
|
||||
public static final String CHAT_DISABLED_KEY = "chat_disabled";
|
||||
public static final String BROADCAST_TIME_KEY = "broadcast_time";
|
||||
public static final String ESTIMATED_REMAINING_TIME_KEY = "estimated_remaining_time";
|
||||
}
|
||||
|
33
app/src/main/res/layout/activity_rpanactivity.xml
Normal file
33
app/src/main/res/layout/activity_rpanactivity.xml
Normal file
@ -0,0 +1,33 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<androidx.coordinatorlayout.widget.CoordinatorLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
android:background="#000000"
|
||||
android:id="@+id/coordinator_layout_rpan_activity"
|
||||
tools:context=".activities.RPANActivity">
|
||||
|
||||
<com.google.android.material.appbar.AppBarLayout
|
||||
android:id="@+id/appbar_layout_rpan_activity"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:theme="@style/AppTheme.AppBarOverlay">
|
||||
|
||||
<androidx.appcompat.widget.Toolbar
|
||||
android:id="@+id/toolbar_rpan_activity"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="wrap_content"
|
||||
android:background="@android:color/transparent"
|
||||
android:minHeight="?attr/actionBarSize"
|
||||
app:popupTheme="@style/AppTheme.PopupOverlay"
|
||||
app:navigationIcon="?attr/homeAsUpIndicator" />
|
||||
|
||||
</com.google.android.material.appbar.AppBarLayout>
|
||||
|
||||
<androidx.viewpager2.widget.ViewPager2
|
||||
android:id="@+id/view_pager_2_rpan_activity"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent" />
|
||||
|
||||
</androidx.coordinatorlayout.widget.CoordinatorLayout>
|
22
app/src/main/res/layout/fragment_view_rpan_broadcast.xml
Normal file
22
app/src/main/res/layout/fragment_view_rpan_broadcast.xml
Normal file
@ -0,0 +1,22 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android"
|
||||
xmlns:tools="http://schemas.android.com/tools"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
xmlns:app="http://schemas.android.com/apk/res-auto"
|
||||
tools:context=".fragments.ViewRPANBroadcastFragment">
|
||||
|
||||
<com.google.android.exoplayer2.ui.PlayerView
|
||||
android:id="@+id/player_view_view_rpan_broadcast_fragment"
|
||||
android:layout_width="match_parent"
|
||||
android:layout_height="match_parent"
|
||||
app:controller_layout_id="@layout/exo_playback_control_view" />
|
||||
|
||||
<ProgressBar
|
||||
android:id="@+id/progress_bar_view_rpan_broadcast_fragment"
|
||||
android:layout_width="wrap_content"
|
||||
android:layout_height="wrap_content"
|
||||
android:layout_gravity="center"
|
||||
android:visibility="gone" />
|
||||
|
||||
</FrameLayout>
|
@ -39,6 +39,7 @@
|
||||
<string name="post_filter_preference_activity_label">Post Filter</string>
|
||||
<string name="search_users_result_activity_label">Users</string>
|
||||
<string name="multireddit_selection_activity_label">Select a Multireddit</string>
|
||||
<string name="rpan_activity_label">RPAN</string>
|
||||
|
||||
<string name="navigation_drawer_open">Open navigation drawer</string>
|
||||
<string name="navigation_drawer_close">Close navigation drawer</string>
|
||||
@ -1126,4 +1127,7 @@
|
||||
<string name="get_image_bitmap_failed">Unable to get the bitmap of the image</string>
|
||||
<string name="upload_image_failed">Unable to upload the image</string>
|
||||
|
||||
<string name="load_rpan_broadcasts_failed">Cannot load RPAN broadcasts</string>
|
||||
<string name="parse_rpan_broadcasts_failed">Cannot parse RPAN broadcasts</string>
|
||||
|
||||
</resources>
|
||||
|
Loading…
Reference in New Issue
Block a user