mirror of
https://github.com/KokaKiwi/BarInsta
synced 2024-11-14 18:57:30 +00:00
parent
53b0301385
commit
4d9494cbcf
@ -10,20 +10,21 @@ import androidx.recyclerview.widget.ListAdapter;
|
|||||||
import androidx.recyclerview.widget.RecyclerView;
|
import androidx.recyclerview.widget.RecyclerView;
|
||||||
|
|
||||||
import awais.instagrabber.databinding.ItemStoryBinding;
|
import awais.instagrabber.databinding.ItemStoryBinding;
|
||||||
import awais.instagrabber.models.StoryModel;
|
import awais.instagrabber.repositories.responses.stories.StoryMedia;
|
||||||
|
import awais.instagrabber.utils.ResponseBodyUtils;
|
||||||
|
|
||||||
public final class StoriesAdapter extends ListAdapter<StoryModel, StoriesAdapter.StoryViewHolder> {
|
public final class StoriesAdapter extends ListAdapter<StoryMedia, StoriesAdapter.StoryViewHolder> {
|
||||||
private final OnItemClickListener onItemClickListener;
|
private final OnItemClickListener onItemClickListener;
|
||||||
|
|
||||||
private static final DiffUtil.ItemCallback<StoryModel> diffCallback = new DiffUtil.ItemCallback<StoryModel>() {
|
private static final DiffUtil.ItemCallback<StoryMedia> diffCallback = new DiffUtil.ItemCallback<StoryMedia>() {
|
||||||
@Override
|
@Override
|
||||||
public boolean areItemsTheSame(@NonNull final StoryModel oldItem, @NonNull final StoryModel newItem) {
|
public boolean areItemsTheSame(@NonNull final StoryMedia oldItem, @NonNull final StoryMedia newItem) {
|
||||||
return oldItem.getStoryMediaId().equals(newItem.getStoryMediaId());
|
return oldItem.getId().equals(newItem.getId());
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean areContentsTheSame(@NonNull final StoryModel oldItem, @NonNull final StoryModel newItem) {
|
public boolean areContentsTheSame(@NonNull final StoryMedia oldItem, @NonNull final StoryMedia newItem) {
|
||||||
return oldItem.getStoryMediaId().equals(newItem.getStoryMediaId());
|
return oldItem.getId().equals(newItem.getId());
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -42,8 +43,8 @@ public final class StoriesAdapter extends ListAdapter<StoryModel, StoriesAdapter
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onBindViewHolder(@NonNull final StoryViewHolder holder, final int position) {
|
public void onBindViewHolder(@NonNull final StoryViewHolder holder, final int position) {
|
||||||
final StoryModel storyModel = getItem(position);
|
final StoryMedia storyMedia = getItem(position);
|
||||||
holder.bind(storyModel, position, onItemClickListener);
|
holder.bind(storyMedia, position, onItemClickListener);
|
||||||
}
|
}
|
||||||
|
|
||||||
public final static class StoryViewHolder extends RecyclerView.ViewHolder {
|
public final static class StoryViewHolder extends RecyclerView.ViewHolder {
|
||||||
@ -54,7 +55,7 @@ public final class StoriesAdapter extends ListAdapter<StoryModel, StoriesAdapter
|
|||||||
this.binding = binding;
|
this.binding = binding;
|
||||||
}
|
}
|
||||||
|
|
||||||
public void bind(final StoryModel model,
|
public void bind(final StoryMedia model,
|
||||||
final int position,
|
final int position,
|
||||||
final OnItemClickListener clickListener) {
|
final OnItemClickListener clickListener) {
|
||||||
if (model == null) return;
|
if (model == null) return;
|
||||||
@ -67,14 +68,11 @@ public final class StoriesAdapter extends ListAdapter<StoryModel, StoriesAdapter
|
|||||||
});
|
});
|
||||||
|
|
||||||
binding.selectedView.setVisibility(model.isCurrentSlide() ? View.VISIBLE : View.GONE);
|
binding.selectedView.setVisibility(model.isCurrentSlide() ? View.VISIBLE : View.GONE);
|
||||||
binding.icon.setImageURI(model.getStoryUrl());
|
binding.icon.setImageURI(ResponseBodyUtils.getThumbUrl(model));
|
||||||
// Glide.with(itemView).load(model.getStoryUrl())
|
|
||||||
// .apply(new RequestOptions().override(width, height))
|
|
||||||
// .into(holder.icon);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
public interface OnItemClickListener {
|
public interface OnItemClickListener {
|
||||||
void onItemClick(StoryModel storyModel, int position);
|
void onItemClick(StoryMedia storyModel, int position);
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -548,7 +548,7 @@ public class HashTagFragment extends Fragment implements SwipeRefreshLayout.OnRe
|
|||||||
// private void fetchStories() {
|
// private void fetchStories() {
|
||||||
// if (!isLoggedIn) return;
|
// if (!isLoggedIn) return;
|
||||||
// storiesFetching = true;
|
// storiesFetching = true;
|
||||||
// storiesRepository.getUserStory(
|
// storiesRepository.getStories(
|
||||||
// StoryViewerOptions.forHashtag(hashtagModel.getName()),
|
// StoryViewerOptions.forHashtag(hashtagModel.getName()),
|
||||||
// CoroutineUtilsKt.getContinuation((storyModels, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
// CoroutineUtilsKt.getContinuation((storyModels, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
||||||
// if (throwable != null) {
|
// if (throwable != null) {
|
||||||
|
@ -552,7 +552,7 @@ public class LocationFragment extends Fragment implements SwipeRefreshLayout.OnR
|
|||||||
// private void fetchStories() {
|
// private void fetchStories() {
|
||||||
// if (isLoggedIn) {
|
// if (isLoggedIn) {
|
||||||
// storiesFetching = true;
|
// storiesFetching = true;
|
||||||
// storiesRepository.getUserStory(
|
// storiesRepository.getStories(
|
||||||
// StoryViewerOptions.forLocation(locationId, locationModel.getName()),
|
// StoryViewerOptions.forLocation(locationId, locationModel.getName()),
|
||||||
// CoroutineUtilsKt.getContinuation((storyModels, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
// CoroutineUtilsKt.getContinuation((storyModels, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
||||||
// if (throwable != null) {
|
// if (throwable != null) {
|
||||||
|
@ -58,8 +58,10 @@ import com.google.android.exoplayer2.upstream.DefaultDataSourceFactory;
|
|||||||
|
|
||||||
import java.io.IOException;
|
import java.io.IOException;
|
||||||
import java.text.NumberFormat;
|
import java.text.NumberFormat;
|
||||||
|
import java.util.Arrays;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.regex.Matcher;
|
import java.util.regex.Matcher;
|
||||||
import java.util.regex.Pattern;
|
import java.util.regex.Pattern;
|
||||||
@ -72,23 +74,17 @@ import awais.instagrabber.databinding.FragmentStoryViewerBinding;
|
|||||||
import awais.instagrabber.fragments.main.ProfileFragmentDirections;
|
import awais.instagrabber.fragments.main.ProfileFragmentDirections;
|
||||||
import awais.instagrabber.fragments.settings.PreferenceKeys;
|
import awais.instagrabber.fragments.settings.PreferenceKeys;
|
||||||
import awais.instagrabber.interfaces.SwipeEvent;
|
import awais.instagrabber.interfaces.SwipeEvent;
|
||||||
import awais.instagrabber.models.StoryModel;
|
|
||||||
import awais.instagrabber.models.enums.MediaItemType;
|
import awais.instagrabber.models.enums.MediaItemType;
|
||||||
import awais.instagrabber.models.stickers.PollModel;
|
|
||||||
import awais.instagrabber.models.stickers.QuestionModel;
|
|
||||||
import awais.instagrabber.models.stickers.QuizModel;
|
|
||||||
import awais.instagrabber.models.stickers.SliderModel;
|
|
||||||
import awais.instagrabber.models.stickers.SwipeUpModel;
|
|
||||||
import awais.instagrabber.repositories.requests.StoryViewerOptions;
|
import awais.instagrabber.repositories.requests.StoryViewerOptions;
|
||||||
import awais.instagrabber.repositories.requests.StoryViewerOptions.Type;
|
import awais.instagrabber.repositories.requests.StoryViewerOptions.Type;
|
||||||
import awais.instagrabber.repositories.requests.directmessages.ThreadIdsOrUserIds;
|
import awais.instagrabber.repositories.requests.directmessages.ThreadIdsOrUserIds;
|
||||||
import awais.instagrabber.repositories.responses.stories.Broadcast;
|
import awais.instagrabber.repositories.responses.stories.*;
|
||||||
import awais.instagrabber.repositories.responses.stories.Story;
|
|
||||||
import awais.instagrabber.utils.AppExecutors;
|
import awais.instagrabber.utils.AppExecutors;
|
||||||
import awais.instagrabber.utils.Constants;
|
import awais.instagrabber.utils.Constants;
|
||||||
import awais.instagrabber.utils.CookieUtils;
|
import awais.instagrabber.utils.CookieUtils;
|
||||||
import awais.instagrabber.utils.CoroutineUtilsKt;
|
import awais.instagrabber.utils.CoroutineUtilsKt;
|
||||||
import awais.instagrabber.utils.DownloadUtils;
|
import awais.instagrabber.utils.DownloadUtils;
|
||||||
|
import awais.instagrabber.utils.ResponseBodyUtils;
|
||||||
import awais.instagrabber.utils.TextUtils;
|
import awais.instagrabber.utils.TextUtils;
|
||||||
import awais.instagrabber.utils.Utils;
|
import awais.instagrabber.utils.Utils;
|
||||||
import awais.instagrabber.viewmodels.ArchivesViewModel;
|
import awais.instagrabber.viewmodels.ArchivesViewModel;
|
||||||
@ -121,16 +117,16 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
private GestureDetectorCompat gestureDetector;
|
private GestureDetectorCompat gestureDetector;
|
||||||
private StoriesRepository storiesRepository;
|
private StoriesRepository storiesRepository;
|
||||||
private MediaRepository mediaRepository;
|
private MediaRepository mediaRepository;
|
||||||
private StoryModel currentStory;
|
private StoryMedia currentStory;
|
||||||
private Broadcast live;
|
private Broadcast live;
|
||||||
private int slidePos;
|
private int slidePos;
|
||||||
private int lastSlidePos;
|
private int lastSlidePos;
|
||||||
private String url;
|
private String url;
|
||||||
private PollModel poll;
|
private PollSticker poll;
|
||||||
private QuestionModel question;
|
private QuestionSticker question;
|
||||||
private String[] mentions;
|
private List<String> mentions = new ArrayList<String>();
|
||||||
private QuizModel quiz;
|
private QuizSticker quiz;
|
||||||
private SliderModel slider;
|
private SliderSticker slider;
|
||||||
private MenuItem menuDownload, menuDm, menuProfile;
|
private MenuItem menuDownload, menuDm, menuProfile;
|
||||||
private SimpleExoPlayer player;
|
private SimpleExoPlayer player;
|
||||||
// private boolean isHashtag;
|
// private boolean isHashtag;
|
||||||
@ -220,10 +216,10 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
csrfToken,
|
csrfToken,
|
||||||
userId,
|
userId,
|
||||||
deviceId,
|
deviceId,
|
||||||
ThreadIdsOrUserIds.Companion.ofOneUser(String.valueOf(currentStory.getUserId())),
|
ThreadIdsOrUserIds.Companion.ofOneUser(String.valueOf(currentStory.getUser().getPk())),
|
||||||
input.getText().toString(),
|
input.getText().toString(),
|
||||||
currentStory.getStoryMediaId(),
|
currentStory.getId(),
|
||||||
String.valueOf(currentStory.getUserId()),
|
String.valueOf(currentStory.getUser().getPk()),
|
||||||
CoroutineUtilsKt.getContinuation(
|
CoroutineUtilsKt.getContinuation(
|
||||||
(directThreadBroadcastResponse, throwable1) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
(directThreadBroadcastResponse, throwable1) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
||||||
if (throwable1 != null) {
|
if (throwable1 != null) {
|
||||||
@ -253,7 +249,7 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
if (itemId == R.id.action_profile) {
|
if (itemId == R.id.action_profile) {
|
||||||
openProfile("@" + currentStory.getUsername());
|
openProfile("@" + currentStory.getUser().getPk());
|
||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
@ -357,7 +353,7 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
final Context context = getContext();
|
final Context context = getContext();
|
||||||
if (context == null) return;
|
if (context == null) return;
|
||||||
swipeEvent = isRightSwipe -> {
|
swipeEvent = isRightSwipe -> {
|
||||||
final List<StoryModel> storyModels = storiesViewModel.getList().getValue();
|
final List<StoryMedia> storyModels = storiesViewModel.getList().getValue();
|
||||||
final int storiesLen = storyModels == null ? 0 : storyModels.size();
|
final int storiesLen = storyModels == null ? 0 : storyModels.size();
|
||||||
if (sticking) {
|
if (sticking) {
|
||||||
Toast.makeText(context, R.string.follower_wait_to_load, Toast.LENGTH_SHORT).show();
|
Toast.makeText(context, R.string.follower_wait_to_load, Toast.LENGTH_SHORT).show();
|
||||||
@ -373,12 +369,14 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
Toast.makeText(context, R.string.no_more_stories, Toast.LENGTH_SHORT).show();
|
Toast.makeText(context, R.string.no_more_stories, Toast.LENGTH_SHORT).show();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
removeStickers();
|
||||||
final Object feedStoryModel = isRightSwipe
|
final Object feedStoryModel = isRightSwipe
|
||||||
? finalModels.get(index - 1)
|
? finalModels.get(index - 1)
|
||||||
: finalModels.size() == index + 1 ? null : finalModels.get(index + 1);
|
: finalModels.size() == index + 1 ? null : finalModels.get(index + 1);
|
||||||
paginateStories(feedStoryModel, finalModels.get(index), context, isRightSwipe, currentFeedStoryIndex == finalModels.size() - 2);
|
paginateStories(feedStoryModel, finalModels.get(index), context, isRightSwipe, currentFeedStoryIndex == finalModels.size() - 2);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
removeStickers();
|
||||||
if (isRightSwipe) {
|
if (isRightSwipe) {
|
||||||
if (--slidePos <= 0) {
|
if (--slidePos <= 0) {
|
||||||
slidePos = 0;
|
slidePos = 0;
|
||||||
@ -471,35 +469,31 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
});
|
});
|
||||||
final View.OnClickListener storyActionListener = v -> {
|
final View.OnClickListener storyActionListener = v -> {
|
||||||
final Object tag = v.getTag();
|
final Object tag = v.getTag();
|
||||||
if (tag instanceof PollModel) {
|
if (tag instanceof PollSticker) {
|
||||||
poll = (PollModel) tag;
|
poll = (PollSticker) tag;
|
||||||
if (poll.getMyChoice() > -1) {
|
final List<Tally> tallies = poll.getTallies();
|
||||||
|
final String[] choices = tallies.stream()
|
||||||
|
.map(t -> (poll.getViewerVote() == tallies.indexOf(t) ? "√ " : "")
|
||||||
|
+ t.getText() + " (" + t.getCount() + ")" )
|
||||||
|
.toArray(String[]::new);
|
||||||
|
final ArrayAdapter adapter = new ArrayAdapter<>(context, android.R.layout.simple_list_item_1, choices);
|
||||||
|
if (poll.getViewerVote() > -1) {
|
||||||
new AlertDialog.Builder(context)
|
new AlertDialog.Builder(context)
|
||||||
.setTitle(R.string.voted_story_poll)
|
.setTitle(R.string.voted_story_poll)
|
||||||
.setAdapter(new ArrayAdapter<>(
|
.setAdapter(adapter, null)
|
||||||
context,
|
|
||||||
android.R.layout.simple_list_item_1,
|
|
||||||
new String[]{
|
|
||||||
(poll.getMyChoice() == 0 ? "√ " : "") + poll.getLeftChoice() + " (" + poll.getLeftCount() + ")",
|
|
||||||
(poll.getMyChoice() == 1 ? "√ " : "") + poll.getRightChoice() + " (" + poll.getRightCount() + ")"
|
|
||||||
}),
|
|
||||||
null)
|
|
||||||
.setPositiveButton(R.string.ok, null)
|
.setPositiveButton(R.string.ok, null)
|
||||||
.show();
|
.show();
|
||||||
} else {
|
} else {
|
||||||
new AlertDialog.Builder(context)
|
new AlertDialog.Builder(context)
|
||||||
.setTitle(poll.getQuestion())
|
.setTitle(poll.getQuestion())
|
||||||
.setAdapter(new ArrayAdapter<>(context, android.R.layout.simple_list_item_1, new String[]{
|
.setAdapter(adapter, (d, w) -> {
|
||||||
poll.getLeftChoice() + " (" + poll.getLeftCount() + ")",
|
|
||||||
poll.getRightChoice() + " (" + poll.getRightCount() + ")"
|
|
||||||
}), (d, w) -> {
|
|
||||||
sticking = true;
|
sticking = true;
|
||||||
storiesRepository.respondToPoll(
|
storiesRepository.respondToPoll(
|
||||||
csrfToken,
|
csrfToken,
|
||||||
userId,
|
userId,
|
||||||
deviceId,
|
deviceId,
|
||||||
currentStory.getStoryMediaId().split("_")[0],
|
currentStory.getId().split("_")[0],
|
||||||
poll.getId(),
|
poll.getPollId(),
|
||||||
w,
|
w,
|
||||||
CoroutineUtilsKt.getContinuation(
|
CoroutineUtilsKt.getContinuation(
|
||||||
(storyStickerResponse, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
(storyStickerResponse, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
||||||
@ -513,7 +507,7 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
}
|
}
|
||||||
sticking = false;
|
sticking = false;
|
||||||
try {
|
try {
|
||||||
poll.setMyChoice(w);
|
poll.setViewerVote(w);
|
||||||
Toast.makeText(context, R.string.votef_story_poll, Toast.LENGTH_SHORT).show();
|
Toast.makeText(context, R.string.votef_story_poll, Toast.LENGTH_SHORT).show();
|
||||||
} catch (Exception ignored) {}
|
} catch (Exception ignored) {}
|
||||||
}),
|
}),
|
||||||
@ -524,8 +518,8 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
.setPositiveButton(R.string.cancel, null)
|
.setPositiveButton(R.string.cancel, null)
|
||||||
.show();
|
.show();
|
||||||
}
|
}
|
||||||
} else if (tag instanceof QuestionModel) {
|
} else if (tag instanceof QuestionSticker) {
|
||||||
question = (QuestionModel) tag;
|
question = (QuestionSticker) tag;
|
||||||
final EditText input = new EditText(context);
|
final EditText input = new EditText(context);
|
||||||
input.setHint(R.string.answer_hint);
|
input.setHint(R.string.answer_hint);
|
||||||
final AlertDialog ad = new AlertDialog.Builder(context)
|
final AlertDialog ad = new AlertDialog.Builder(context)
|
||||||
@ -537,8 +531,8 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
csrfToken,
|
csrfToken,
|
||||||
userId,
|
userId,
|
||||||
deviceId,
|
deviceId,
|
||||||
currentStory.getStoryMediaId().split("_")[0],
|
currentStory.getId().split("_")[0],
|
||||||
question.getId(),
|
question.getQuestionId(),
|
||||||
input.getText().toString(),
|
input.getText().toString(),
|
||||||
CoroutineUtilsKt.getContinuation(
|
CoroutineUtilsKt.getContinuation(
|
||||||
(storyStickerResponse, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
(storyStickerResponse, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
||||||
@ -575,28 +569,31 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
public void afterTextChanged(final Editable s) {}
|
public void afterTextChanged(final Editable s) {}
|
||||||
});
|
});
|
||||||
} else if (tag instanceof String[]) {
|
} else if (tag instanceof String[]) {
|
||||||
mentions = (String[]) tag;
|
final String[] rawMentions = (String[]) tag;
|
||||||
|
mentions = new ArrayList<String>(Arrays.asList(rawMentions));
|
||||||
new AlertDialog.Builder(context)
|
new AlertDialog.Builder(context)
|
||||||
.setTitle(R.string.story_mentions)
|
.setTitle(R.string.story_mentions)
|
||||||
.setAdapter(new ArrayAdapter<>(context, android.R.layout.simple_list_item_1, mentions), (d, w) -> openProfile(mentions[w]))
|
.setAdapter(new ArrayAdapter<>(context, android.R.layout.simple_list_item_1, rawMentions), (d, w) -> openProfile(mentions.get(w)))
|
||||||
.setPositiveButton(R.string.cancel, null)
|
.setPositiveButton(R.string.cancel, null)
|
||||||
.show();
|
.show();
|
||||||
} else if (tag instanceof QuizModel) {
|
} else if (tag instanceof QuizSticker) {
|
||||||
String[] choices = new String[quiz.getChoices().length];
|
final List<Tally> tallies = quiz.getTallies();
|
||||||
for (int q = 0; q < choices.length; ++q) {
|
final String[] choices = tallies.stream().map(
|
||||||
choices[q] = (quiz.getMyChoice() == q ? "√ " : "") + quiz.getChoices()[q] + " (" + quiz.getCounts()[q] + ")";
|
t -> (quiz.getViewerAnswer() == tallies.indexOf(t) ? "√ " : "") +
|
||||||
}
|
(quiz.getCorrectAnswer() == tallies.indexOf(t) ? "*** " : "") +
|
||||||
|
t.getText() + " (" + t.getCount() + ")"
|
||||||
|
).toArray(String[]::new);
|
||||||
new AlertDialog.Builder(context)
|
new AlertDialog.Builder(context)
|
||||||
.setTitle(quiz.getMyChoice() > -1 ? getString(R.string.story_quizzed) : quiz.getQuestion())
|
.setTitle(quiz.getViewerAnswer() > -1 ? getString(R.string.story_quizzed) : quiz.getQuestion())
|
||||||
.setAdapter(new ArrayAdapter<>(context, android.R.layout.simple_list_item_1, choices), (d, w) -> {
|
.setAdapter(new ArrayAdapter<>(context, android.R.layout.simple_list_item_1, choices), (d, w) -> {
|
||||||
if (quiz.getMyChoice() == -1) {
|
if (quiz.getViewerAnswer() == -1) {
|
||||||
sticking = true;
|
sticking = true;
|
||||||
storiesRepository.respondToQuiz(
|
storiesRepository.respondToQuiz(
|
||||||
csrfToken,
|
csrfToken,
|
||||||
userId,
|
userId,
|
||||||
deviceId,
|
deviceId,
|
||||||
currentStory.getStoryMediaId().split("_")[0],
|
currentStory.getId().split("_")[0],
|
||||||
quiz.getId(),
|
quiz.getQuizId(),
|
||||||
w,
|
w,
|
||||||
CoroutineUtilsKt.getContinuation(
|
CoroutineUtilsKt.getContinuation(
|
||||||
(storyStickerResponse, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
(storyStickerResponse, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
||||||
@ -610,7 +607,7 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
}
|
}
|
||||||
sticking = false;
|
sticking = false;
|
||||||
try {
|
try {
|
||||||
quiz.setMyChoice(w);
|
quiz.setViewerAnswer(w);
|
||||||
Toast.makeText(context, R.string.answered_story, Toast.LENGTH_SHORT).show();
|
Toast.makeText(context, R.string.answered_story, Toast.LENGTH_SHORT).show();
|
||||||
} catch (Exception ignored) {}
|
} catch (Exception ignored) {}
|
||||||
}),
|
}),
|
||||||
@ -621,8 +618,8 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
})
|
})
|
||||||
.setPositiveButton(R.string.cancel, null)
|
.setPositiveButton(R.string.cancel, null)
|
||||||
.show();
|
.show();
|
||||||
} else if (tag instanceof SliderModel) {
|
} else if (tag instanceof SliderSticker) {
|
||||||
slider = (SliderModel) tag;
|
slider = (SliderSticker) tag;
|
||||||
NumberFormat percentage = NumberFormat.getPercentInstance();
|
NumberFormat percentage = NumberFormat.getPercentInstance();
|
||||||
percentage.setMaximumFractionDigits(2);
|
percentage.setMaximumFractionDigits(2);
|
||||||
LinearLayout sliderView = new LinearLayout(context);
|
LinearLayout sliderView = new LinearLayout(context);
|
||||||
@ -633,11 +630,11 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
TextView tv = new TextView(context);
|
TextView tv = new TextView(context);
|
||||||
tv.setGravity(Gravity.CENTER_HORIZONTAL);
|
tv.setGravity(Gravity.CENTER_HORIZONTAL);
|
||||||
final SeekBar input = new SeekBar(context);
|
final SeekBar input = new SeekBar(context);
|
||||||
double avg = slider.getAverage() * 100;
|
double avg = slider.getSliderVoteAverage() * 100;
|
||||||
input.setProgress((int) avg);
|
input.setProgress((int) avg);
|
||||||
sliderView.addView(input);
|
sliderView.addView(input);
|
||||||
sliderView.addView(tv);
|
sliderView.addView(tv);
|
||||||
if (slider.getMyChoice().isNaN() && slider.canVote()) {
|
if (slider.getViewerVote().isNaN() && slider.getViewerCanVote()) {
|
||||||
input.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
|
input.setOnSeekBarChangeListener(new SeekBar.OnSeekBarChangeListener() {
|
||||||
@Override
|
@Override
|
||||||
public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
|
public void onProgressChanged(SeekBar seekBar, int progress, boolean fromUser) {
|
||||||
@ -656,9 +653,9 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
new AlertDialog.Builder(context)
|
new AlertDialog.Builder(context)
|
||||||
.setTitle(TextUtils.isEmpty(slider.getQuestion()) ? slider.getEmoji() : slider.getQuestion())
|
.setTitle(TextUtils.isEmpty(slider.getQuestion()) ? slider.getEmoji() : slider.getQuestion())
|
||||||
.setMessage(getResources().getQuantityString(R.plurals.slider_info,
|
.setMessage(getResources().getQuantityString(R.plurals.slider_info,
|
||||||
slider.getVoteCount(),
|
slider.getSliderVoteCount(),
|
||||||
slider.getVoteCount(),
|
slider.getSliderVoteCount(),
|
||||||
percentage.format(slider.getAverage())))
|
percentage.format(slider.getSliderVoteAverage())))
|
||||||
.setView(sliderView)
|
.setView(sliderView)
|
||||||
.setPositiveButton(R.string.confirm, (d, w) -> {
|
.setPositiveButton(R.string.confirm, (d, w) -> {
|
||||||
sticking = true;
|
sticking = true;
|
||||||
@ -666,8 +663,8 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
csrfToken,
|
csrfToken,
|
||||||
userId,
|
userId,
|
||||||
deviceId,
|
deviceId,
|
||||||
currentStory.getStoryMediaId().split("_")[0],
|
currentStory.getId().split("_")[0],
|
||||||
slider.getId(),
|
slider.getSliderId(),
|
||||||
sliderValue,
|
sliderValue,
|
||||||
CoroutineUtilsKt.getContinuation(
|
CoroutineUtilsKt.getContinuation(
|
||||||
(storyStickerResponse, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
(storyStickerResponse, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
||||||
@ -681,7 +678,7 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
}
|
}
|
||||||
sticking = false;
|
sticking = false;
|
||||||
try {
|
try {
|
||||||
slider.setMyChoice(sliderValue);
|
slider.setViewerVote(sliderValue);
|
||||||
Toast.makeText(context, R.string.answered_story, Toast.LENGTH_SHORT).show();
|
Toast.makeText(context, R.string.answered_story, Toast.LENGTH_SHORT).show();
|
||||||
} catch (Exception ignored) {}
|
} catch (Exception ignored) {}
|
||||||
}), Dispatchers.getIO()
|
}), Dispatchers.getIO()
|
||||||
@ -692,13 +689,13 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
.show();
|
.show();
|
||||||
} else {
|
} else {
|
||||||
input.setEnabled(false);
|
input.setEnabled(false);
|
||||||
tv.setText(getString(R.string.slider_answer, percentage.format(slider.getMyChoice())));
|
tv.setText(getString(R.string.slider_answer, percentage.format(slider.getViewerVote())));
|
||||||
new AlertDialog.Builder(context)
|
new AlertDialog.Builder(context)
|
||||||
.setTitle(TextUtils.isEmpty(slider.getQuestion()) ? slider.getEmoji() : slider.getQuestion())
|
.setTitle(TextUtils.isEmpty(slider.getQuestion()) ? slider.getEmoji() : slider.getQuestion())
|
||||||
.setMessage(getResources().getQuantityString(R.plurals.slider_info,
|
.setMessage(getResources().getQuantityString(R.plurals.slider_info,
|
||||||
slider.getVoteCount(),
|
slider.getSliderVoteCount(),
|
||||||
slider.getVoteCount(),
|
slider.getSliderVoteCount(),
|
||||||
percentage.format(slider.getAverage())))
|
percentage.format(slider.getSliderVoteAverage())))
|
||||||
.setView(sliderView)
|
.setView(sliderView)
|
||||||
.setPositiveButton(R.string.ok, null)
|
.setPositiveButton(R.string.ok, null)
|
||||||
.show();
|
.show();
|
||||||
@ -746,11 +743,12 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
case FEED_STORY_POSITION: {
|
case FEED_STORY_POSITION: {
|
||||||
final FeedStoriesViewModel feedStoriesViewModel = (FeedStoriesViewModel) viewModel;
|
final FeedStoriesViewModel feedStoriesViewModel = (FeedStoriesViewModel) viewModel;
|
||||||
final List<Story> models = feedStoriesViewModel.getList().getValue();
|
final List<Story> models = feedStoriesViewModel.getList().getValue();
|
||||||
if (models == null || currentFeedStoryIndex >= models.size() || currentFeedStoryIndex < 0) return;
|
if (models == null || currentFeedStoryIndex >= models.size() || currentFeedStoryIndex < 0)
|
||||||
|
return;
|
||||||
final Story model = models.get(currentFeedStoryIndex);
|
final Story model = models.get(currentFeedStoryIndex);
|
||||||
currentStoryMediaId = model.getId();
|
currentStoryMediaId = String.valueOf(model.getUser().getPk());
|
||||||
currentStoryUsername = model.getUser().getUsername();
|
currentStoryUsername = model.getUser().getUsername();
|
||||||
fetchOptions = StoryViewerOptions.forUser(Long.parseLong(currentStoryMediaId), currentStoryUsername);
|
fetchOptions = StoryViewerOptions.forUser(model.getUser().getPk(), currentStoryUsername);
|
||||||
live = model.getBroadcast();
|
live = model.getBroadcast();
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
@ -767,11 +765,12 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
fetchOptions = StoryViewerOptions.forStoryArchive(model.getId());
|
fetchOptions = StoryViewerOptions.forStoryArchive(model.getId());
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
case USER: {
|
||||||
if (type == Type.USER) {
|
currentStoryMediaId = String.valueOf(options.getId());
|
||||||
currentStoryMediaId = String.valueOf(options.getId());
|
currentStoryUsername = options.getName();
|
||||||
currentStoryUsername = options.getName();
|
fetchOptions = StoryViewerOptions.forUser(options.getId(), currentStoryUsername);
|
||||||
fetchOptions = StoryViewerOptions.forUser(options.getId(), currentStoryUsername);
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
setTitle(type);
|
setTitle(type);
|
||||||
storiesViewModel.getList().setValue(Collections.emptyList());
|
storiesViewModel.getList().setValue(Collections.emptyList());
|
||||||
@ -804,9 +803,9 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
refreshLive();
|
refreshLive();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
final ServiceCallback<List<StoryModel>> storyCallback = new ServiceCallback<List<StoryModel>>() {
|
final ServiceCallback<List<StoryMedia>> storyCallback = new ServiceCallback<List<StoryMedia>>() {
|
||||||
@Override
|
@Override
|
||||||
public void onSuccess(final List<StoryModel> storyModels) {
|
public void onSuccess(final List<StoryMedia> storyModels) {
|
||||||
fetching = false;
|
fetching = false;
|
||||||
if (storyModels == null || storyModels.isEmpty()) {
|
if (storyModels == null || storyModels.isEmpty()) {
|
||||||
storiesViewModel.getList().setValue(Collections.emptyList());
|
storiesViewModel.getList().setValue(Collections.emptyList());
|
||||||
@ -826,11 +825,10 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void onFailure(final Throwable t) {
|
public void onFailure(final Throwable t) {
|
||||||
Toast.makeText(context, t.getMessage(), Toast.LENGTH_SHORT).show();
|
|
||||||
Log.e(TAG, "Error", t);
|
Log.e(TAG, "Error", t);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
storiesRepository.getUserStory(
|
storiesRepository.getStories(
|
||||||
fetchOptions,
|
fetchOptions,
|
||||||
CoroutineUtilsKt.getContinuation((storyModels, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
CoroutineUtilsKt.getContinuation((storyModels, throwable) -> AppExecutors.INSTANCE.getMainThread().execute(() -> {
|
||||||
if (throwable != null) {
|
if (throwable != null) {
|
||||||
@ -838,7 +836,7 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
//noinspection unchecked
|
//noinspection unchecked
|
||||||
storyCallback.onSuccess((List<StoryModel>) storyModels);
|
storyCallback.onSuccess((List<StoryMedia>) storyModels);
|
||||||
}), Dispatchers.getIO())
|
}), Dispatchers.getIO())
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
@ -887,9 +885,9 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
|
|
||||||
private synchronized void refreshStory() {
|
private synchronized void refreshStory() {
|
||||||
if (binding.storiesList.getVisibility() == View.VISIBLE) {
|
if (binding.storiesList.getVisibility() == View.VISIBLE) {
|
||||||
final List<StoryModel> storyModels = storiesViewModel.getList().getValue();
|
final List<StoryMedia> storyModels = storiesViewModel.getList().getValue();
|
||||||
if (storyModels != null && storyModels.size() > 0) {
|
if (storyModels != null && storyModels.size() > 0) {
|
||||||
StoryModel item = storyModels.get(lastSlidePos);
|
StoryMedia item = storyModels.get(lastSlidePos);
|
||||||
if (item != null) {
|
if (item != null) {
|
||||||
item.setCurrentSlide(false);
|
item.setCurrentSlide(false);
|
||||||
storiesAdapter.notifyItemChanged(lastSlidePos, item);
|
storiesAdapter.notifyItemChanged(lastSlidePos, item);
|
||||||
@ -903,59 +901,96 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
}
|
}
|
||||||
lastSlidePos = slidePos;
|
lastSlidePos = slidePos;
|
||||||
|
|
||||||
final MediaItemType itemType = currentStory.getItemType();
|
final MediaItemType itemType = currentStory.getMediaType();
|
||||||
|
|
||||||
url = itemType == MediaItemType.MEDIA_TYPE_IMAGE ? currentStory.getStoryUrl() : currentStory.getVideoUrl();
|
url = itemType == MediaItemType.MEDIA_TYPE_IMAGE
|
||||||
|
? ResponseBodyUtils.getImageUrl(currentStory)
|
||||||
|
: ResponseBodyUtils.getVideoUrl(currentStory);
|
||||||
|
|
||||||
final String shortCode = currentStory.getTappableShortCode();
|
if (currentStory.getStoryFeedMedia() != null) {
|
||||||
binding.viewStoryPost.setVisibility(shortCode != null ? View.VISIBLE : View.GONE);
|
final String shortCode = currentStory.getStoryFeedMedia().get(0).getMediaId();
|
||||||
binding.viewStoryPost.setTag(shortCode);
|
binding.viewStoryPost.setVisibility(View.VISIBLE);
|
||||||
|
binding.viewStoryPost.setTag(shortCode);
|
||||||
|
}
|
||||||
|
|
||||||
final String spotify = currentStory.getSpotify();
|
final StoryAppAttribution spotify = currentStory.getStoryAppAttribution();
|
||||||
binding.spotify.setVisibility(spotify != null ? View.VISIBLE : View.GONE);
|
if (spotify != null) {
|
||||||
binding.spotify.setTag(spotify);
|
binding.spotify.setVisibility(View.VISIBLE);
|
||||||
|
binding.spotify.setText(spotify.getName());
|
||||||
|
binding.spotify.setTag(spotify.getContentUrl().split("?")[0]);
|
||||||
|
}
|
||||||
|
|
||||||
poll = currentStory.getPoll();
|
if (currentStory.getStoryPolls() != null) {
|
||||||
binding.poll.setVisibility(poll != null ? View.VISIBLE : View.GONE);
|
poll = currentStory.getStoryPolls().get(0).getPollSticker();
|
||||||
binding.poll.setTag(poll);
|
binding.poll.setVisibility(View.VISIBLE);
|
||||||
|
binding.poll.setTag(poll);
|
||||||
|
}
|
||||||
|
|
||||||
question = currentStory.getQuestion();
|
if (currentStory.getStoryQuestions() != null) {
|
||||||
binding.answer.setVisibility((question != null) ? View.VISIBLE : View.GONE);
|
question = currentStory.getStoryQuestions().get(0).getQuestionSticker();
|
||||||
binding.answer.setTag(question);
|
binding.answer.setVisibility(View.VISIBLE);
|
||||||
|
binding.answer.setTag(question);
|
||||||
|
}
|
||||||
|
|
||||||
mentions = currentStory.getMentions();
|
mentions.clear();
|
||||||
binding.mention.setVisibility((mentions != null && mentions.length > 0) ? View.VISIBLE : View.GONE);
|
if (currentStory.getReelMentions() != null) {
|
||||||
binding.mention.setTag(mentions);
|
mentions.addAll(currentStory.getReelMentions().stream().map(
|
||||||
|
s -> s.getUser().getUsername()
|
||||||
|
).distinct().collect(Collectors.toList()));
|
||||||
|
}
|
||||||
|
if (currentStory.getStoryHashtags() != null) {
|
||||||
|
mentions.addAll(currentStory.getStoryHashtags().stream().map(
|
||||||
|
s -> s.getHashtag().getName()
|
||||||
|
).distinct().collect(Collectors.toList()));
|
||||||
|
}
|
||||||
|
if (currentStory.getStoryLocations() != null) {
|
||||||
|
mentions.addAll(currentStory.getStoryLocations().stream().map(
|
||||||
|
s -> s.getLocation().getShortName() + " (" + s.getLocation().getPk() + ")"
|
||||||
|
).distinct().collect(Collectors.toList()));
|
||||||
|
}
|
||||||
|
if (mentions.size() > 0) {
|
||||||
|
binding.mention.setVisibility(View.VISIBLE);
|
||||||
|
binding.mention.setTag(mentions.stream().toArray(String[]::new));
|
||||||
|
}
|
||||||
|
|
||||||
quiz = currentStory.getQuiz();
|
if (currentStory.getStoryQuizs() != null) {
|
||||||
binding.quiz.setVisibility(quiz != null ? View.VISIBLE : View.GONE);
|
quiz = currentStory.getStoryQuizs().get(0).getQuizSticker();
|
||||||
binding.quiz.setTag(quiz);
|
binding.quiz.setVisibility(View.VISIBLE);
|
||||||
|
binding.quiz.setTag(quiz);
|
||||||
|
}
|
||||||
|
|
||||||
slider = currentStory.getSlider();
|
if (currentStory.getStorySliders() != null) {
|
||||||
binding.slider.setVisibility(slider != null ? View.VISIBLE : View.GONE);
|
slider = currentStory.getStorySliders().get(0).getSliderSticker();
|
||||||
binding.slider.setTag(slider);
|
binding.slider.setVisibility(View.VISIBLE);
|
||||||
|
binding.slider.setTag(slider);
|
||||||
|
}
|
||||||
|
|
||||||
final SwipeUpModel swipeUp = currentStory.getSwipeUp();
|
if (currentStory.getStoryCta() != null) {
|
||||||
if (swipeUp != null) {
|
final StoryCta swipeUp = currentStory.getStoryCta().get(0).getLinks();
|
||||||
binding.swipeUp.setVisibility(View.VISIBLE);
|
binding.swipeUp.setVisibility(View.VISIBLE);
|
||||||
binding.swipeUp.setText(swipeUp.getText());
|
binding.swipeUp.setText(currentStory.getLinkText());
|
||||||
binding.swipeUp.setTag(swipeUp.getUrl());
|
final String swipeUpUrl = swipeUp.getWebUri();
|
||||||
} else binding.swipeUp.setVisibility(View.GONE);
|
final String actualLink = swipeUpUrl.startsWith("https://l.instagram.com/")
|
||||||
|
? Uri.parse(swipeUpUrl).getQueryParameter("u")
|
||||||
|
: null;
|
||||||
|
binding.swipeUp.setTag(actualLink == null && actualLink.startsWith("http")
|
||||||
|
? swipeUpUrl : actualLink);
|
||||||
|
}
|
||||||
|
|
||||||
releasePlayer();
|
releasePlayer();
|
||||||
final Type type = options.getType();
|
final Type type = options.getType();
|
||||||
if (type == Type.HASHTAG || type == Type.LOCATION) {
|
if (type == Type.HASHTAG || type == Type.LOCATION) {
|
||||||
final ActionBar actionBar = fragmentActivity.getSupportActionBar();
|
final ActionBar actionBar = fragmentActivity.getSupportActionBar();
|
||||||
if (actionBar != null) {
|
if (actionBar != null) {
|
||||||
actionBarTitle = currentStory.getUsername();
|
actionBarTitle = currentStory.getUser().getUsername();
|
||||||
actionBar.setTitle(currentStory.getUsername());
|
actionBar.setTitle(currentStory.getUser().getUsername());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if (itemType == MediaItemType.MEDIA_TYPE_VIDEO) setupVideo();
|
if (itemType == MediaItemType.MEDIA_TYPE_VIDEO) setupVideo();
|
||||||
else setupImage();
|
else setupImage();
|
||||||
|
|
||||||
final ActionBar actionBar = fragmentActivity.getSupportActionBar();
|
final ActionBar actionBar = fragmentActivity.getSupportActionBar();
|
||||||
actionBarSubtitle = TextUtils.epochSecondToString(currentStory.getTimestamp());
|
actionBarSubtitle = TextUtils.epochSecondToString(currentStory.getTakenAt());
|
||||||
if (actionBar != null) {
|
if (actionBar != null) {
|
||||||
try {
|
try {
|
||||||
actionBar.setSubtitle(actionBarSubtitle);
|
actionBar.setSubtitle(actionBarSubtitle);
|
||||||
@ -969,13 +1004,23 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
csrfToken,
|
csrfToken,
|
||||||
userId,
|
userId,
|
||||||
deviceId,
|
deviceId,
|
||||||
currentStory.getStoryMediaId(),
|
currentStory.getId(),
|
||||||
currentStory.getTimestamp(),
|
currentStory.getTakenAt(),
|
||||||
System.currentTimeMillis() / 1000,
|
System.currentTimeMillis() / 1000,
|
||||||
CoroutineUtilsKt.getContinuation((s, throwable) -> {}, Dispatchers.getIO())
|
CoroutineUtilsKt.getContinuation((s, throwable) -> {}, Dispatchers.getIO())
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private void removeStickers() {
|
||||||
|
binding.swipeUp.setVisibility(View.GONE);
|
||||||
|
binding.quiz.setVisibility(View.GONE);
|
||||||
|
binding.spotify.setVisibility(View.GONE);
|
||||||
|
binding.mention.setVisibility(View.GONE);
|
||||||
|
binding.viewStoryPost.setVisibility(View.GONE);
|
||||||
|
binding.answer.setVisibility(View.GONE);
|
||||||
|
binding.slider.setVisibility(View.GONE);
|
||||||
|
}
|
||||||
|
|
||||||
private void downloadStory() {
|
private void downloadStory() {
|
||||||
final Context context = getContext();
|
final Context context = getContext();
|
||||||
if (context == null) return;
|
if (context == null) return;
|
||||||
@ -1016,7 +1061,7 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
dmVisible = true;
|
dmVisible = true;
|
||||||
menuDm.setVisible(true);
|
menuDm.setVisible(true);
|
||||||
}
|
}
|
||||||
if (!TextUtils.isEmpty(currentStory.getUsername())) {
|
if (!TextUtils.isEmpty(currentStory.getUser().getUsername())) {
|
||||||
profileVisible = true;
|
profileVisible = true;
|
||||||
menuProfile.setVisible(true);
|
menuProfile.setVisible(true);
|
||||||
}
|
}
|
||||||
@ -1057,7 +1102,7 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
dmVisible = true;
|
dmVisible = true;
|
||||||
menuDm.setVisible(true);
|
menuDm.setVisible(true);
|
||||||
}
|
}
|
||||||
if (!TextUtils.isEmpty(currentStory.getUsername()) && menuProfile != null) {
|
if (!TextUtils.isEmpty(currentStory.getUser().getUsername()) && menuProfile != null) {
|
||||||
profileVisible = true;
|
profileVisible = true;
|
||||||
menuProfile.setVisible(true);
|
menuProfile.setVisible(true);
|
||||||
}
|
}
|
||||||
@ -1077,7 +1122,7 @@ public class StoryViewerFragment extends Fragment {
|
|||||||
dmVisible = true;
|
dmVisible = true;
|
||||||
menuDm.setVisible(true);
|
menuDm.setVisible(true);
|
||||||
}
|
}
|
||||||
if (!TextUtils.isEmpty(currentStory.getUsername()) && menuProfile != null) {
|
if (!TextUtils.isEmpty(currentStory.getUser().getUsername()) && menuProfile != null) {
|
||||||
profileVisible = true;
|
profileVisible = true;
|
||||||
menuProfile.setVisible(true);
|
menuProfile.setVisible(true);
|
||||||
}
|
}
|
||||||
|
@ -1,29 +0,0 @@
|
|||||||
package awais.instagrabber.models
|
|
||||||
|
|
||||||
import awais.instagrabber.models.enums.MediaItemType
|
|
||||||
import awais.instagrabber.models.stickers.*
|
|
||||||
import java.io.Serializable
|
|
||||||
|
|
||||||
data class StoryModel(
|
|
||||||
val storyMediaId: String? = null,
|
|
||||||
val storyUrl: String? = null,
|
|
||||||
var thumbnail: String? = null,
|
|
||||||
val itemType: MediaItemType? = null,
|
|
||||||
val timestamp: Long = 0,
|
|
||||||
val username: String? = null,
|
|
||||||
val userId: Long = 0,
|
|
||||||
val canReply: Boolean = false,
|
|
||||||
) : Serializable {
|
|
||||||
var videoUrl: String? = null
|
|
||||||
var tappableShortCode: String? = null
|
|
||||||
val tappableId: String? = null
|
|
||||||
var spotify: String? = null
|
|
||||||
var poll: PollModel? = null
|
|
||||||
var question: QuestionModel? = null
|
|
||||||
var slider: SliderModel? = null
|
|
||||||
var quiz: QuizModel? = null
|
|
||||||
var swipeUp: SwipeUpModel? = null
|
|
||||||
var mentions: Array<String>? = null
|
|
||||||
var position = 0
|
|
||||||
var isCurrentSlide = false
|
|
||||||
}
|
|
@ -1,52 +0,0 @@
|
|||||||
package awais.instagrabber.models.stickers;
|
|
||||||
|
|
||||||
import java.io.Serializable;
|
|
||||||
|
|
||||||
public final class PollModel implements Serializable {
|
|
||||||
private int leftcount, rightcount, mychoice;
|
|
||||||
private final String id, question, leftchoice, rightchoice;
|
|
||||||
|
|
||||||
public PollModel(final String id, final String question, final String leftchoice, final int leftcount,
|
|
||||||
final String rightchoice, final int rightcount, final int mychoice) {
|
|
||||||
this.id = id; // only the poll id
|
|
||||||
this.question = question;
|
|
||||||
this.leftchoice = leftchoice;
|
|
||||||
this.leftcount = leftcount;
|
|
||||||
this.rightchoice = rightchoice;
|
|
||||||
this.rightcount = rightcount;
|
|
||||||
this.mychoice = mychoice;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getId() {
|
|
||||||
return id;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getQuestion() {
|
|
||||||
return question;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getLeftChoice() {
|
|
||||||
return leftchoice;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getLeftCount() {
|
|
||||||
return leftcount;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getRightChoice() {
|
|
||||||
return rightchoice;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getRightCount() {
|
|
||||||
return rightcount;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getMyChoice() { return mychoice; }
|
|
||||||
|
|
||||||
public int setMyChoice(final int choice) {
|
|
||||||
this.mychoice = choice;
|
|
||||||
if (choice == 0) this.leftcount += 1;
|
|
||||||
else if (choice == 1) this.rightcount += 1;
|
|
||||||
return choice;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,20 +0,0 @@
|
|||||||
package awais.instagrabber.models.stickers;
|
|
||||||
|
|
||||||
import java.io.Serializable;
|
|
||||||
|
|
||||||
public final class QuestionModel implements Serializable {
|
|
||||||
private final String id, question;
|
|
||||||
|
|
||||||
public QuestionModel(final String id, final String question) {
|
|
||||||
this.id = id; // only the poll id
|
|
||||||
this.question = question;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getId() {
|
|
||||||
return id;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getQuestion() {
|
|
||||||
return question;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,37 +0,0 @@
|
|||||||
package awais.instagrabber.models.stickers;
|
|
||||||
|
|
||||||
import java.io.Serializable;
|
|
||||||
|
|
||||||
public final class QuizModel implements Serializable {
|
|
||||||
private final String id, question;
|
|
||||||
private final String[] choices;
|
|
||||||
private Long[] counts;
|
|
||||||
private int mychoice;
|
|
||||||
|
|
||||||
public QuizModel(final String id, final String question, final String[] choices, final Long[] counts, final int mychoice) {
|
|
||||||
this.id = id; // only the poll id
|
|
||||||
this.question = question;
|
|
||||||
this.choices = choices;
|
|
||||||
this.counts = counts;
|
|
||||||
this.mychoice = mychoice;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getId() {
|
|
||||||
return id;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getQuestion() {
|
|
||||||
return question;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String[] getChoices() { return choices;}
|
|
||||||
|
|
||||||
public Long[] getCounts() { return counts;}
|
|
||||||
|
|
||||||
public int getMyChoice() { return mychoice; }
|
|
||||||
|
|
||||||
public void setMyChoice(final int choice) {
|
|
||||||
this.mychoice = choice;
|
|
||||||
counts[choice] += 1L;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,53 +0,0 @@
|
|||||||
package awais.instagrabber.models.stickers;
|
|
||||||
|
|
||||||
import java.io.Serializable;
|
|
||||||
|
|
||||||
public final class SliderModel implements Serializable {
|
|
||||||
private final int voteCount;
|
|
||||||
private final Double average;
|
|
||||||
private Double myChoice;
|
|
||||||
private final boolean canVote;
|
|
||||||
private final String id, question, emoji;
|
|
||||||
|
|
||||||
public SliderModel(final String id, final String question, final String emoji, final boolean canVote,
|
|
||||||
final Double average, final int voteCount, final Double myChoice) {
|
|
||||||
this.id = id;
|
|
||||||
this.question = question;
|
|
||||||
this.emoji = emoji;
|
|
||||||
this.canVote = canVote;
|
|
||||||
this.average = average;
|
|
||||||
this.voteCount = voteCount;
|
|
||||||
this.myChoice = myChoice;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getId() {
|
|
||||||
return id;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getQuestion() {
|
|
||||||
return question;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getEmoji() {
|
|
||||||
return emoji;
|
|
||||||
}
|
|
||||||
|
|
||||||
public boolean canVote() {
|
|
||||||
return canVote;
|
|
||||||
}
|
|
||||||
|
|
||||||
public int getVoteCount() {
|
|
||||||
return voteCount;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Double getAverage() {
|
|
||||||
return average;
|
|
||||||
}
|
|
||||||
|
|
||||||
public Double getMyChoice() { return myChoice; }
|
|
||||||
|
|
||||||
public Double setMyChoice(final Double choice) {
|
|
||||||
this.myChoice = choice;
|
|
||||||
return choice;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,20 +0,0 @@
|
|||||||
package awais.instagrabber.models.stickers;
|
|
||||||
|
|
||||||
import java.io.Serializable;
|
|
||||||
|
|
||||||
public final class SwipeUpModel implements Serializable {
|
|
||||||
private final String url, text;
|
|
||||||
|
|
||||||
public SwipeUpModel(final String url, final String text) {
|
|
||||||
this.url = url;
|
|
||||||
this.text = text;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getUrl() {
|
|
||||||
return url;
|
|
||||||
}
|
|
||||||
|
|
||||||
public String getText() {
|
|
||||||
return text;
|
|
||||||
}
|
|
||||||
}
|
|
@ -1,14 +1,17 @@
|
|||||||
package awais.instagrabber.repositories
|
package awais.instagrabber.repositories
|
||||||
|
|
||||||
import awais.instagrabber.repositories.responses.stories.ArchiveResponse
|
import awais.instagrabber.repositories.responses.stories.ArchiveResponse
|
||||||
|
import awais.instagrabber.repositories.responses.stories.ReelsMediaResponse
|
||||||
|
import awais.instagrabber.repositories.responses.stories.ReelsResponse
|
||||||
import awais.instagrabber.repositories.responses.stories.ReelsTrayResponse
|
import awais.instagrabber.repositories.responses.stories.ReelsTrayResponse
|
||||||
|
import awais.instagrabber.repositories.responses.stories.StoryMediaResponse
|
||||||
import awais.instagrabber.repositories.responses.stories.StoryStickerResponse
|
import awais.instagrabber.repositories.responses.stories.StoryStickerResponse
|
||||||
import retrofit2.http.*
|
import retrofit2.http.*
|
||||||
|
|
||||||
interface StoriesService {
|
interface StoriesService {
|
||||||
// this one is the same as MediaRepository.fetch BUT you need to make sure it's a story
|
// this one is the same as MediaRepository.fetch BUT you need to make sure it's a story
|
||||||
@GET("/api/v1/media/{mediaId}/info/")
|
@GET("/api/v1/media/{mediaId}/info/")
|
||||||
suspend fun fetch(@Path("mediaId") mediaId: Long): String
|
suspend fun fetch(@Path("mediaId") mediaId: Long): StoryMediaResponse
|
||||||
|
|
||||||
@GET("/api/v1/feed/reels_tray/")
|
@GET("/api/v1/feed/reels_tray/")
|
||||||
suspend fun getFeedStories(): ReelsTrayResponse?
|
suspend fun getFeedStories(): ReelsTrayResponse?
|
||||||
@ -19,14 +22,20 @@ interface StoriesService {
|
|||||||
@GET("/api/v1/archive/reel/day_shells/")
|
@GET("/api/v1/archive/reel/day_shells/")
|
||||||
suspend fun fetchArchive(@QueryMap queryParams: Map<String, String>): ArchiveResponse?
|
suspend fun fetchArchive(@QueryMap queryParams: Map<String, String>): ArchiveResponse?
|
||||||
|
|
||||||
@GET
|
@GET("/api/v1/feed/reels_media/")
|
||||||
suspend fun getUserStory(@Url url: String): String
|
suspend fun getReelsMedia(@Query("user_ids") id: String): ReelsMediaResponse
|
||||||
|
|
||||||
|
@GET("/api/v1/{type}/{id}/story/")
|
||||||
|
suspend fun getStories(@Path("type") type: String, @Path("id") id: String): ReelsResponse
|
||||||
|
|
||||||
|
@GET("/api/v1/feed/user/{id}/story/")
|
||||||
|
suspend fun getUserStories(@Path("id") id: String): ReelsResponse
|
||||||
|
|
||||||
@FormUrlEncoded
|
@FormUrlEncoded
|
||||||
@POST("/api/v1/media/{storyId}/{stickerId}/{action}/")
|
@POST("/api/v1/media/{storyId}/{stickerId}/{action}/")
|
||||||
suspend fun respondToSticker(
|
suspend fun respondToSticker(
|
||||||
@Path("storyId") storyId: String,
|
@Path("storyId") storyId: String,
|
||||||
@Path("stickerId") stickerId: String,
|
@Path("stickerId") stickerId: Long,
|
||||||
@Path("action") action: String, // story_poll_vote, story_question_response, story_slider_vote, story_quiz_answer
|
@Path("action") action: String, // story_poll_vote, story_question_response, story_slider_vote, story_quiz_answer
|
||||||
@FieldMap form: Map<String, String>,
|
@FieldMap form: Map<String, String>,
|
||||||
): StoryStickerResponse
|
): StoryStickerResponse
|
||||||
|
@ -42,7 +42,7 @@ public class StoryViewerOptions implements Serializable {
|
|||||||
}
|
}
|
||||||
|
|
||||||
public static StoryViewerOptions forUser(final long id, final String name) {
|
public static StoryViewerOptions forUser(final long id, final String name) {
|
||||||
return new StoryViewerOptions(id, name,Type.USER);
|
return new StoryViewerOptions(id, name, Type.USER);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static StoryViewerOptions forHighlight(final String highlight) {
|
public static StoryViewerOptions forHighlight(final String highlight) {
|
||||||
|
@ -9,5 +9,5 @@ data class PollSticker(
|
|||||||
val pollId: Long?,
|
val pollId: Long?,
|
||||||
val question: String?,
|
val question: String?,
|
||||||
val tallies: List<Tally>?,
|
val tallies: List<Tally>?,
|
||||||
val viewerVote: Int?
|
var viewerVote: Int = -1
|
||||||
) : Serializable
|
) : Serializable
|
@ -9,6 +9,6 @@ data class QuizSticker(
|
|||||||
val quizId: Long?,
|
val quizId: Long?,
|
||||||
val question: String?,
|
val question: String?,
|
||||||
val tallies: List<Tally>?,
|
val tallies: List<Tally>?,
|
||||||
val viewerAnswer: Int?,
|
var viewerAnswer: Int? = -1,
|
||||||
val correctAnswer: Int?
|
val correctAnswer: Int?
|
||||||
) : Serializable
|
) : Serializable
|
@ -0,0 +1,8 @@
|
|||||||
|
package awais.instagrabber.repositories.responses.stories
|
||||||
|
|
||||||
|
import java.io.Serializable
|
||||||
|
|
||||||
|
data class ReelsMediaResponse(
|
||||||
|
val status: String?,
|
||||||
|
val reels: Map<String, Story?>?
|
||||||
|
) : Serializable
|
@ -4,6 +4,7 @@ import java.io.Serializable
|
|||||||
|
|
||||||
data class ReelsResponse(
|
data class ReelsResponse(
|
||||||
val status: String?,
|
val status: String?,
|
||||||
val reel: Story?,
|
val reel: Story?, // users
|
||||||
|
val story: Story?, // hashtag and locations (unused)
|
||||||
val broadcast: Broadcast?
|
val broadcast: Broadcast?
|
||||||
) : Serializable
|
) : Serializable
|
@ -10,7 +10,7 @@ data class SliderSticker(
|
|||||||
val question: String?,
|
val question: String?,
|
||||||
val emoji: String?,
|
val emoji: String?,
|
||||||
val viewerCanVote: Boolean?,
|
val viewerCanVote: Boolean?,
|
||||||
val viewerVote: Double?,
|
var viewerVote: Double?,
|
||||||
val sliderVoteAverage: Double?,
|
val sliderVoteAverage: Double?,
|
||||||
val sliderVoteCount: Int?,
|
val sliderVoteCount: Int?,
|
||||||
) : Serializable
|
) : Serializable
|
@ -41,6 +41,8 @@ data class StoryMedia(
|
|||||||
val storyAppAttribution: StoryAppAttribution? = null
|
val storyAppAttribution: StoryAppAttribution? = null
|
||||||
) : Serializable {
|
) : Serializable {
|
||||||
private var dateString: String? = null
|
private var dateString: String? = null
|
||||||
|
var position = 0
|
||||||
|
var isCurrentSlide = false
|
||||||
|
|
||||||
// TODO use extension once all usages are converted to kotlin
|
// TODO use extension once all usages are converted to kotlin
|
||||||
// val date: String by lazy {
|
// val date: String by lazy {
|
||||||
|
@ -0,0 +1,14 @@
|
|||||||
|
package awais.instagrabber.repositories.responses.stories
|
||||||
|
|
||||||
|
import awais.instagrabber.models.enums.MediaItemType
|
||||||
|
import awais.instagrabber.repositories.responses.ImageVersions2
|
||||||
|
import awais.instagrabber.repositories.responses.MediaCandidate
|
||||||
|
import awais.instagrabber.repositories.responses.User
|
||||||
|
import awais.instagrabber.utils.TextUtils
|
||||||
|
import java.io.Serializable
|
||||||
|
|
||||||
|
data class StoryMediaResponse(
|
||||||
|
val items: List<StoryMedia?>?, // length 1
|
||||||
|
val status: String?
|
||||||
|
// ignoring pagination properties
|
||||||
|
) : Serializable
|
@ -13,9 +13,9 @@ import androidx.documentfile.provider.DocumentFile
|
|||||||
import androidx.work.*
|
import androidx.work.*
|
||||||
import awais.instagrabber.R
|
import awais.instagrabber.R
|
||||||
import awais.instagrabber.fragments.settings.PreferenceKeys
|
import awais.instagrabber.fragments.settings.PreferenceKeys
|
||||||
import awais.instagrabber.models.StoryModel
|
|
||||||
import awais.instagrabber.models.enums.MediaItemType
|
import awais.instagrabber.models.enums.MediaItemType
|
||||||
import awais.instagrabber.repositories.responses.Media
|
import awais.instagrabber.repositories.responses.Media
|
||||||
|
import awais.instagrabber.repositories.responses.stories.StoryMedia
|
||||||
import awais.instagrabber.utils.TextUtils.isEmpty
|
import awais.instagrabber.utils.TextUtils.isEmpty
|
||||||
import awais.instagrabber.workers.DownloadWorker
|
import awais.instagrabber.workers.DownloadWorker
|
||||||
import com.google.gson.Gson
|
import com.google.gson.Gson
|
||||||
@ -392,18 +392,19 @@ object DownloadUtils {
|
|||||||
@JvmStatic
|
@JvmStatic
|
||||||
fun download(
|
fun download(
|
||||||
context: Context,
|
context: Context,
|
||||||
storyModel: StoryModel
|
storyModel: StoryMedia
|
||||||
) {
|
) {
|
||||||
val downloadDir = getDownloadDir(context, storyModel.username) ?: return
|
val downloadDir = getDownloadDir(context, storyModel.user?.username) ?: return
|
||||||
val url =
|
val url =
|
||||||
if (storyModel.itemType == MediaItemType.MEDIA_TYPE_VIDEO) storyModel.videoUrl else storyModel.storyUrl
|
if (storyModel.mediaType == MediaItemType.MEDIA_TYPE_VIDEO) ResponseBodyUtils.getVideoUrl(storyModel)
|
||||||
|
else ResponseBodyUtils.getImageUrl(storyModel)
|
||||||
val extension = getFileExtensionFromUrl(url)
|
val extension = getFileExtensionFromUrl(url)
|
||||||
val baseFileName = (storyModel.storyMediaId + "_"
|
val baseFileName = (storyModel.id + "_"
|
||||||
+ storyModel.timestamp + extension)
|
+ storyModel.takenAt + extension)
|
||||||
val usernamePrepend =
|
val usernamePrepend =
|
||||||
if (Utils.settingsHelper.getBoolean(PreferenceKeys.DOWNLOAD_PREPEND_USER_NAME)
|
if (Utils.settingsHelper.getBoolean(PreferenceKeys.DOWNLOAD_PREPEND_USER_NAME)
|
||||||
&& storyModel.username != null
|
&& storyModel.user?.username != null
|
||||||
) storyModel.username + "_" else ""
|
) storyModel.user.username + "_" else ""
|
||||||
val fileName = usernamePrepend + baseFileName
|
val fileName = usernamePrepend + baseFileName
|
||||||
var saveFile = downloadDir.findFile(fileName)
|
var saveFile = downloadDir.findFile(fileName)
|
||||||
if (saveFile == null) {
|
if (saveFile == null) {
|
||||||
|
@ -14,13 +14,7 @@ import java.util.Collections;
|
|||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
import awais.instagrabber.models.StoryModel;
|
|
||||||
import awais.instagrabber.models.enums.MediaItemType;
|
import awais.instagrabber.models.enums.MediaItemType;
|
||||||
import awais.instagrabber.models.stickers.PollModel;
|
|
||||||
import awais.instagrabber.models.stickers.QuestionModel;
|
|
||||||
import awais.instagrabber.models.stickers.QuizModel;
|
|
||||||
import awais.instagrabber.models.stickers.SliderModel;
|
|
||||||
import awais.instagrabber.models.stickers.SwipeUpModel;
|
|
||||||
import awais.instagrabber.repositories.responses.Caption;
|
import awais.instagrabber.repositories.responses.Caption;
|
||||||
import awais.instagrabber.repositories.responses.FriendshipStatus;
|
import awais.instagrabber.repositories.responses.FriendshipStatus;
|
||||||
import awais.instagrabber.repositories.responses.ImageVersions2;
|
import awais.instagrabber.repositories.responses.ImageVersions2;
|
||||||
@ -276,136 +270,6 @@ public final class ResponseBodyUtils {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static StoryModel parseStoryItem(final JSONObject data,
|
|
||||||
final boolean isLocOrHashtag,
|
|
||||||
final String username) throws JSONException {
|
|
||||||
final boolean isVideo = data.has("video_duration");
|
|
||||||
final StoryModel model = new StoryModel(data.getString("id"),
|
|
||||||
data.getJSONObject("image_versions2").getJSONArray("candidates").getJSONObject(0)
|
|
||||||
.getString("url"), null,
|
|
||||||
isVideo ? MediaItemType.MEDIA_TYPE_VIDEO : MediaItemType.MEDIA_TYPE_IMAGE,
|
|
||||||
data.optLong("taken_at", 0),
|
|
||||||
isLocOrHashtag ? data.getJSONObject("user").getString("username") : username,
|
|
||||||
data.getJSONObject("user").getLong("pk"),
|
|
||||||
data.optBoolean("can_reply"));
|
|
||||||
|
|
||||||
if (data.getJSONObject("image_versions2").getJSONArray("candidates").length() > 1) {
|
|
||||||
model.setThumbnail(data.getJSONObject("image_versions2").getJSONArray("candidates").getJSONObject(1)
|
|
||||||
.getString("url"));
|
|
||||||
}
|
|
||||||
|
|
||||||
final JSONArray videoResources = data.optJSONArray("video_versions");
|
|
||||||
if (isVideo && videoResources != null)
|
|
||||||
model.setVideoUrl(ResponseBodyUtils.getHighQualityPost(videoResources, true, true, false));
|
|
||||||
|
|
||||||
if (data.has("story_feed_media")) {
|
|
||||||
model.setTappableShortCode(data.getJSONArray("story_feed_media").getJSONObject(0).optString("media_id"));
|
|
||||||
}
|
|
||||||
|
|
||||||
// TODO: this may not be limited to spotify
|
|
||||||
if (!data.isNull("story_app_attribution"))
|
|
||||||
model.setSpotify(data.getJSONObject("story_app_attribution").optString("content_url").split("\\?")[0]);
|
|
||||||
|
|
||||||
if (data.has("story_polls")) {
|
|
||||||
final JSONArray storyPolls = data.optJSONArray("story_polls");
|
|
||||||
JSONObject tappableObject = null;
|
|
||||||
if (storyPolls != null) {
|
|
||||||
tappableObject = storyPolls.getJSONObject(0).optJSONObject("poll_sticker");
|
|
||||||
}
|
|
||||||
if (tappableObject != null) model.setPoll(new PollModel(
|
|
||||||
String.valueOf(tappableObject.getLong("poll_id")),
|
|
||||||
tappableObject.getString("question"),
|
|
||||||
tappableObject.getJSONArray("tallies").getJSONObject(0).getString("text"),
|
|
||||||
tappableObject.getJSONArray("tallies").getJSONObject(0).getInt("count"),
|
|
||||||
tappableObject.getJSONArray("tallies").getJSONObject(1).getString("text"),
|
|
||||||
tappableObject.getJSONArray("tallies").getJSONObject(1).getInt("count"),
|
|
||||||
tappableObject.optInt("viewer_vote", -1)
|
|
||||||
));
|
|
||||||
}
|
|
||||||
if (data.has("story_questions")) {
|
|
||||||
final JSONObject tappableObject = data.getJSONArray("story_questions").getJSONObject(0)
|
|
||||||
.optJSONObject("question_sticker");
|
|
||||||
if (tappableObject != null && !tappableObject.getString("question_type").equals("music"))
|
|
||||||
model.setQuestion(new QuestionModel(
|
|
||||||
String.valueOf(tappableObject.getLong("question_id")),
|
|
||||||
tappableObject.getString("question")
|
|
||||||
));
|
|
||||||
}
|
|
||||||
if (data.has("story_quizs")) {
|
|
||||||
JSONObject tappableObject = data.getJSONArray("story_quizs").getJSONObject(0).optJSONObject("quiz_sticker");
|
|
||||||
if (tappableObject != null) {
|
|
||||||
String[] choices = new String[tappableObject.getJSONArray("tallies").length()];
|
|
||||||
Long[] counts = new Long[choices.length];
|
|
||||||
for (int q = 0; q < choices.length; ++q) {
|
|
||||||
JSONObject tempchoice = tappableObject.getJSONArray("tallies").getJSONObject(q);
|
|
||||||
choices[q] = (q == tappableObject.getInt("correct_answer") ? "*** " : "")
|
|
||||||
+ tempchoice.getString("text");
|
|
||||||
counts[q] = tempchoice.getLong("count");
|
|
||||||
}
|
|
||||||
model.setQuiz(new QuizModel(
|
|
||||||
String.valueOf(tappableObject.getLong("quiz_id")),
|
|
||||||
tappableObject.getString("question"),
|
|
||||||
choices,
|
|
||||||
counts,
|
|
||||||
tappableObject.optInt("viewer_answer", -1)
|
|
||||||
));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (data.has("story_cta") && data.has("link_text")) {
|
|
||||||
JSONObject tappableObject = data.getJSONArray("story_cta").getJSONObject(0).getJSONArray("links").getJSONObject(0);
|
|
||||||
String swipeUpUrl = tappableObject.optString("webUri");
|
|
||||||
final String backupSwipeUpUrl = swipeUpUrl;
|
|
||||||
if (swipeUpUrl != null && swipeUpUrl.startsWith("https://l.instagram.com/")) {
|
|
||||||
swipeUpUrl = Uri.parse(swipeUpUrl).getQueryParameter("u");
|
|
||||||
}
|
|
||||||
if (swipeUpUrl != null && swipeUpUrl.startsWith("http"))
|
|
||||||
model.setSwipeUp(new SwipeUpModel(swipeUpUrl, data.getString("link_text")));
|
|
||||||
else if (backupSwipeUpUrl != null && backupSwipeUpUrl.startsWith("http"))
|
|
||||||
model.setSwipeUp(new SwipeUpModel(backupSwipeUpUrl, data.getString("link_text")));
|
|
||||||
}
|
|
||||||
if (data.has("story_sliders")) {
|
|
||||||
final JSONObject tappableObject = data.getJSONArray("story_sliders").getJSONObject(0)
|
|
||||||
.optJSONObject("slider_sticker");
|
|
||||||
if (tappableObject != null)
|
|
||||||
model.setSlider(new SliderModel(
|
|
||||||
String.valueOf(tappableObject.getLong("slider_id")),
|
|
||||||
tappableObject.getString("question"),
|
|
||||||
tappableObject.getString("emoji"),
|
|
||||||
tappableObject.getBoolean("viewer_can_vote"),
|
|
||||||
tappableObject.optDouble("slider_vote_average"),
|
|
||||||
tappableObject.getInt("slider_vote_count"),
|
|
||||||
tappableObject.optDouble("viewer_vote")
|
|
||||||
));
|
|
||||||
}
|
|
||||||
JSONArray hashtags = data.optJSONArray("story_hashtags");
|
|
||||||
JSONArray locations = data.optJSONArray("story_locations");
|
|
||||||
JSONArray atmarks = data.optJSONArray("reel_mentions");
|
|
||||||
String[] mentions = new String[(hashtags == null ? 0 : hashtags.length())
|
|
||||||
+ (atmarks == null ? 0 : atmarks.length())
|
|
||||||
+ (locations == null ? 0 : locations.length())];
|
|
||||||
if (hashtags != null) {
|
|
||||||
for (int h = 0; h < hashtags.length(); ++h) {
|
|
||||||
mentions[h] = "#" + hashtags.getJSONObject(h).getJSONObject("hashtag").getString("name");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (atmarks != null) {
|
|
||||||
for (int h = 0; h < atmarks.length(); ++h) {
|
|
||||||
mentions[h + (hashtags == null ? 0 : hashtags.length())] =
|
|
||||||
"@" + atmarks.getJSONObject(h).getJSONObject("user").getString("username");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (locations != null) {
|
|
||||||
for (int h = 0; h < locations.length(); ++h) {
|
|
||||||
mentions[h + (hashtags == null ? 0 : hashtags.length()) + (atmarks == null ? 0 : atmarks.length())] =
|
|
||||||
locations.getJSONObject(h).getJSONObject("location").getString("short_name")
|
|
||||||
+ " (" + locations.getJSONObject(h).getJSONObject("location").getLong("pk") + ")";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (mentions.length != 0) model.setMentions(mentions);
|
|
||||||
|
|
||||||
return model;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static String getThumbUrl(final Object media) {
|
public static String getThumbUrl(final Object media) {
|
||||||
return getImageCandidate(media, CandidateType.THUMBNAIL);
|
return getImageCandidate(media, CandidateType.THUMBNAIL);
|
||||||
}
|
}
|
||||||
@ -415,6 +279,7 @@ public final class ResponseBodyUtils {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private static String getImageCandidate(final Object rawMedia, final CandidateType type) {
|
private static String getImageCandidate(final Object rawMedia, final CandidateType type) {
|
||||||
|
if (rawMedia == null) return null;
|
||||||
final ImageVersions2 imageVersions2;
|
final ImageVersions2 imageVersions2;
|
||||||
final int originalWidth, originalHeight;
|
final int originalWidth, originalHeight;
|
||||||
if (rawMedia instanceof StoryMedia) {
|
if (rawMedia instanceof StoryMedia) {
|
||||||
@ -453,22 +318,34 @@ public final class ResponseBodyUtils {
|
|||||||
return getVideoCandidate(media, CandidateType.VIDEO_THUMBNAIL);
|
return getVideoCandidate(media, CandidateType.VIDEO_THUMBNAIL);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static String getVideoUrl(final Media media) {
|
public static String getVideoUrl(final Object media) {
|
||||||
return getVideoCandidate(media, CandidateType.DOWNLOAD);
|
return getVideoCandidate(media, CandidateType.DOWNLOAD);
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: merge with getImageCandidate when Kotlin
|
// TODO: merge with getImageCandidate when Kotlin
|
||||||
private static String getVideoCandidate(final Media media, final CandidateType type) {
|
private static String getVideoCandidate(final Object rawMedia, final CandidateType type) {
|
||||||
if (media == null) return null;
|
if (rawMedia == null) return null;
|
||||||
final List<MediaCandidate> candidates = media.getVideoVersions();
|
final List<MediaCandidate> candidates;
|
||||||
|
final int originalWidth, originalHeight;
|
||||||
|
if (rawMedia instanceof StoryMedia) {
|
||||||
|
candidates = ((StoryMedia) rawMedia).getVideoVersions();
|
||||||
|
originalWidth = ((StoryMedia) rawMedia).getOriginalWidth();
|
||||||
|
originalHeight = ((StoryMedia) rawMedia).getOriginalHeight();
|
||||||
|
}
|
||||||
|
else if (rawMedia instanceof Media) {
|
||||||
|
candidates = ((Media) rawMedia).getVideoVersions();
|
||||||
|
originalWidth = ((Media) rawMedia).getOriginalWidth();
|
||||||
|
originalHeight = ((Media) rawMedia).getOriginalHeight();
|
||||||
|
}
|
||||||
|
else return null;
|
||||||
if (candidates == null || candidates.isEmpty()) return null;
|
if (candidates == null || candidates.isEmpty()) return null;
|
||||||
final boolean isSquare = Integer.compare(media.getOriginalWidth(), media.getOriginalHeight()) == 0;
|
final boolean isSquare = Integer.compare(originalWidth, originalHeight) == 0;
|
||||||
final List<MediaCandidate> sortedCandidates = candidates.stream()
|
final List<MediaCandidate> sortedCandidates = candidates.stream()
|
||||||
.sorted((c1, c2) -> Integer.compare(c2.getWidth(), c1.getWidth()))
|
.sorted((c1, c2) -> Integer.compare(c2.getWidth(), c1.getWidth()))
|
||||||
.collect(Collectors.toList());
|
.collect(Collectors.toList());
|
||||||
final List<MediaCandidate> filteredCandidates = sortedCandidates.stream()
|
final List<MediaCandidate> filteredCandidates = sortedCandidates.stream()
|
||||||
.filter(c ->
|
.filter(c ->
|
||||||
c.getWidth() <= media.getOriginalWidth()
|
c.getWidth() <= originalWidth
|
||||||
&& c.getWidth() <= type.getValue()
|
&& c.getWidth() <= type.getValue()
|
||||||
&& (isSquare || Integer
|
&& (isSquare || Integer
|
||||||
.compare(c.getWidth(), c.getHeight()) != 0)
|
.compare(c.getWidth(), c.getHeight()) != 0)
|
||||||
@ -480,19 +357,6 @@ public final class ResponseBodyUtils {
|
|||||||
return candidate.getUrl();
|
return candidate.getUrl();
|
||||||
}
|
}
|
||||||
|
|
||||||
public static StoryModel parseBroadcastItem(final JSONObject data) throws JSONException {
|
|
||||||
final StoryModel model = new StoryModel(data.getString("id"),
|
|
||||||
data.getString("cover_frame_url"),
|
|
||||||
data.getString("cover_frame_url"),
|
|
||||||
MediaItemType.MEDIA_TYPE_LIVE,
|
|
||||||
data.optLong("published_time", 0),
|
|
||||||
data.getJSONObject("broadcast_owner").getString("username"),
|
|
||||||
data.getJSONObject("broadcast_owner").getLong("pk"),
|
|
||||||
false);
|
|
||||||
model.setVideoUrl(data.getString("dash_playback_url"));
|
|
||||||
return model;
|
|
||||||
}
|
|
||||||
|
|
||||||
private enum CandidateType {
|
private enum CandidateType {
|
||||||
VIDEO_THUMBNAIL(700),
|
VIDEO_THUMBNAIL(700),
|
||||||
THUMBNAIL(1000),
|
THUMBNAIL(1000),
|
||||||
|
@ -8,7 +8,6 @@ import awais.instagrabber.db.entities.Favorite
|
|||||||
import awais.instagrabber.db.repositories.FavoriteRepository
|
import awais.instagrabber.db.repositories.FavoriteRepository
|
||||||
import awais.instagrabber.managers.DirectMessagesManager
|
import awais.instagrabber.managers.DirectMessagesManager
|
||||||
import awais.instagrabber.models.Resource
|
import awais.instagrabber.models.Resource
|
||||||
import awais.instagrabber.models.StoryModel
|
|
||||||
import awais.instagrabber.models.enums.BroadcastItemType
|
import awais.instagrabber.models.enums.BroadcastItemType
|
||||||
import awais.instagrabber.models.enums.FavoriteType
|
import awais.instagrabber.models.enums.FavoriteType
|
||||||
import awais.instagrabber.repositories.requests.StoryViewerOptions
|
import awais.instagrabber.repositories.requests.StoryViewerOptions
|
||||||
@ -17,6 +16,7 @@ import awais.instagrabber.repositories.responses.User
|
|||||||
import awais.instagrabber.repositories.responses.UserProfileContextLink
|
import awais.instagrabber.repositories.responses.UserProfileContextLink
|
||||||
import awais.instagrabber.repositories.responses.directmessages.RankedRecipient
|
import awais.instagrabber.repositories.responses.directmessages.RankedRecipient
|
||||||
import awais.instagrabber.repositories.responses.stories.Story
|
import awais.instagrabber.repositories.responses.stories.Story
|
||||||
|
import awais.instagrabber.repositories.responses.stories.StoryMedia
|
||||||
import awais.instagrabber.utils.ControlledRunner
|
import awais.instagrabber.utils.ControlledRunner
|
||||||
import awais.instagrabber.utils.Event
|
import awais.instagrabber.utils.Event
|
||||||
import awais.instagrabber.utils.SingleRunner
|
import awais.instagrabber.utils.SingleRunner
|
||||||
@ -153,9 +153,9 @@ class ProfileFragmentViewModel(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private val storyFetchControlledRunner = ControlledRunner<List<StoryModel>?>()
|
private val storyFetchControlledRunner = ControlledRunner<List<StoryMedia>?>()
|
||||||
val userStories: LiveData<Resource<List<StoryModel>?>> = currentUserProfileActionLiveData.switchMap { currentUserAndProfilePair ->
|
val userStories: LiveData<Resource<List<StoryMedia>?>> = currentUserProfileActionLiveData.switchMap { currentUserAndProfilePair ->
|
||||||
liveData<Resource<List<StoryModel>?>>(context = viewModelScope.coroutineContext + ioDispatcher) {
|
liveData<Resource<List<StoryMedia>?>>(context = viewModelScope.coroutineContext + ioDispatcher) {
|
||||||
val (currentUserResource, profileResource, action) = currentUserAndProfilePair
|
val (currentUserResource, profileResource, action) = currentUserAndProfilePair
|
||||||
if (action != INIT && action != REFRESH) {
|
if (action != INIT && action != REFRESH) {
|
||||||
return@liveData
|
return@liveData
|
||||||
@ -231,7 +231,7 @@ class ProfileFragmentViewModel(
|
|||||||
return graphQLRepository.fetchUser(stateUsername)
|
return graphQLRepository.fetchUser(stateUsername)
|
||||||
}
|
}
|
||||||
|
|
||||||
private suspend fun fetchUserStory(fetchedUser: User): List<StoryModel> = storiesRepository.getUserStory(
|
private suspend fun fetchUserStory(fetchedUser: User): List<StoryMedia> = storiesRepository.getStories(
|
||||||
StoryViewerOptions.forUser(fetchedUser.pk, fetchedUser.fullName)
|
StoryViewerOptions.forUser(fetchedUser.pk, fetchedUser.fullName)
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -5,12 +5,12 @@ import androidx.lifecycle.ViewModel;
|
|||||||
|
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
|
|
||||||
import awais.instagrabber.models.StoryModel;
|
import awais.instagrabber.repositories.responses.stories.StoryMedia;
|
||||||
|
|
||||||
public class StoriesViewModel extends ViewModel {
|
public class StoriesViewModel extends ViewModel {
|
||||||
private MutableLiveData<List<StoryModel>> list;
|
private MutableLiveData<List<StoryMedia>> list;
|
||||||
|
|
||||||
public MutableLiveData<List<StoryModel>> getList() {
|
public MutableLiveData<List<StoryMedia>> getList() {
|
||||||
if (list == null) {
|
if (list == null) {
|
||||||
list = new MutableLiveData<>();
|
list = new MutableLiveData<>();
|
||||||
}
|
}
|
||||||
|
@ -1,26 +1,22 @@
|
|||||||
package awais.instagrabber.webservices
|
package awais.instagrabber.webservices
|
||||||
|
|
||||||
import awais.instagrabber.fragments.settings.PreferenceKeys
|
import awais.instagrabber.fragments.settings.PreferenceKeys
|
||||||
import awais.instagrabber.models.StoryModel
|
|
||||||
import awais.instagrabber.repositories.StoriesService
|
import awais.instagrabber.repositories.StoriesService
|
||||||
import awais.instagrabber.repositories.requests.StoryViewerOptions
|
import awais.instagrabber.repositories.requests.StoryViewerOptions
|
||||||
import awais.instagrabber.repositories.responses.stories.ArchiveResponse
|
import awais.instagrabber.repositories.responses.stories.ArchiveResponse
|
||||||
import awais.instagrabber.repositories.responses.stories.Story
|
import awais.instagrabber.repositories.responses.stories.Story
|
||||||
|
import awais.instagrabber.repositories.responses.stories.StoryMedia
|
||||||
import awais.instagrabber.repositories.responses.stories.StoryStickerResponse
|
import awais.instagrabber.repositories.responses.stories.StoryStickerResponse
|
||||||
import awais.instagrabber.utils.ResponseBodyUtils
|
|
||||||
import awais.instagrabber.utils.TextUtils.isEmpty
|
import awais.instagrabber.utils.TextUtils.isEmpty
|
||||||
import awais.instagrabber.utils.Utils
|
import awais.instagrabber.utils.Utils
|
||||||
import awais.instagrabber.webservices.RetrofitFactory.retrofit
|
import awais.instagrabber.webservices.RetrofitFactory.retrofit
|
||||||
import org.json.JSONArray
|
import java.util.UUID
|
||||||
import org.json.JSONObject
|
|
||||||
import java.util.*
|
|
||||||
|
|
||||||
open class StoriesRepository(private val service: StoriesService) {
|
open class StoriesRepository(private val service: StoriesService) {
|
||||||
|
|
||||||
suspend fun fetch(mediaId: Long): StoryModel {
|
suspend fun fetch(mediaId: Long): StoryMedia? {
|
||||||
val response = service.fetch(mediaId)
|
val response = service.fetch(mediaId)
|
||||||
val itemJson = JSONObject(response).getJSONArray("items").getJSONObject(0)
|
return response.items?.get(0)
|
||||||
return ResponseBodyUtils.parseStoryItem(itemJson, false, null)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
suspend fun getFeedStories(): List<Story> {
|
suspend fun getFeedStories(): List<Story> {
|
||||||
@ -70,31 +66,30 @@ open class StoriesRepository(private val service: StoriesService) {
|
|||||||
return service.fetchArchive(form)
|
return service.fetchArchive(form)
|
||||||
}
|
}
|
||||||
|
|
||||||
open suspend fun getUserStory(options: StoryViewerOptions): List<StoryModel> {
|
open suspend fun getStories(options: StoryViewerOptions): List<StoryMedia> {
|
||||||
val url = buildUrl(options) ?: return emptyList()
|
return when (options.type) {
|
||||||
val response = service.getUserStory(url)
|
StoryViewerOptions.Type.HIGHLIGHT,
|
||||||
val isLocOrHashtag = options.type == StoryViewerOptions.Type.LOCATION || options.type == StoryViewerOptions.Type.HASHTAG
|
StoryViewerOptions.Type.STORY_ARCHIVE
|
||||||
val isHighlight = options.type == StoryViewerOptions.Type.HIGHLIGHT || options.type == StoryViewerOptions.Type.STORY_ARCHIVE
|
-> {
|
||||||
var data: JSONObject? = JSONObject(response)
|
val response = service.getReelsMedia(options.name)
|
||||||
data = if (!isHighlight) {
|
val story: Story? = response.reels?.get(options.name)
|
||||||
data?.optJSONObject(if (isLocOrHashtag) "story" else "reel")
|
story?.items ?: emptyList()
|
||||||
} else {
|
|
||||||
data?.getJSONObject("reels")?.optJSONObject(options.name)
|
|
||||||
}
|
|
||||||
var username: String? = null
|
|
||||||
if (data != null && !isLocOrHashtag) {
|
|
||||||
username = data.getJSONObject("user").getString("username")
|
|
||||||
}
|
|
||||||
val media: JSONArray? = data?.optJSONArray("items")
|
|
||||||
return if (media?.length() ?: 0 > 0 && media?.optJSONObject(0) != null) {
|
|
||||||
val mediaLen = media.length()
|
|
||||||
val models: MutableList<StoryModel> = ArrayList()
|
|
||||||
for (i in 0 until mediaLen) {
|
|
||||||
data = media.getJSONObject(i)
|
|
||||||
models.add(ResponseBodyUtils.parseStoryItem(data, isLocOrHashtag, username))
|
|
||||||
}
|
}
|
||||||
models
|
StoryViewerOptions.Type.USER -> {
|
||||||
} else emptyList()
|
val response = service.getUserStories(options.id.toString())
|
||||||
|
response.reel?.items ?: emptyList()
|
||||||
|
}
|
||||||
|
// should not reach beyond this point
|
||||||
|
StoryViewerOptions.Type.LOCATION -> {
|
||||||
|
val response = service.getStories("locations", options.id.toString())
|
||||||
|
response.story?.items ?: emptyList()
|
||||||
|
}
|
||||||
|
StoryViewerOptions.Type.HASHTAG -> {
|
||||||
|
val response = service.getStories("tags", options.name)
|
||||||
|
response.story?.items ?: emptyList()
|
||||||
|
}
|
||||||
|
else -> emptyList()
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private suspend fun respondToSticker(
|
private suspend fun respondToSticker(
|
||||||
@ -102,7 +97,7 @@ open class StoriesRepository(private val service: StoriesService) {
|
|||||||
userId: Long,
|
userId: Long,
|
||||||
deviceUuid: String,
|
deviceUuid: String,
|
||||||
storyId: String,
|
storyId: String,
|
||||||
stickerId: String,
|
stickerId: Long,
|
||||||
action: String,
|
action: String,
|
||||||
arg1: String,
|
arg1: String,
|
||||||
arg2: String,
|
arg2: String,
|
||||||
@ -125,7 +120,7 @@ open class StoriesRepository(private val service: StoriesService) {
|
|||||||
userId: Long,
|
userId: Long,
|
||||||
deviceUuid: String,
|
deviceUuid: String,
|
||||||
storyId: String,
|
storyId: String,
|
||||||
stickerId: String,
|
stickerId: Long,
|
||||||
answer: String,
|
answer: String,
|
||||||
): StoryStickerResponse = respondToSticker(csrfToken, userId, deviceUuid, storyId, stickerId, "story_question_response", "response", answer)
|
): StoryStickerResponse = respondToSticker(csrfToken, userId, deviceUuid, storyId, stickerId, "story_question_response", "response", answer)
|
||||||
|
|
||||||
@ -134,7 +129,7 @@ open class StoriesRepository(private val service: StoriesService) {
|
|||||||
userId: Long,
|
userId: Long,
|
||||||
deviceUuid: String,
|
deviceUuid: String,
|
||||||
storyId: String,
|
storyId: String,
|
||||||
stickerId: String,
|
stickerId: Long,
|
||||||
answer: Int,
|
answer: Int,
|
||||||
): StoryStickerResponse {
|
): StoryStickerResponse {
|
||||||
return respondToSticker(csrfToken, userId, deviceUuid, storyId, stickerId, "story_quiz_answer", "answer", answer.toString())
|
return respondToSticker(csrfToken, userId, deviceUuid, storyId, stickerId, "story_quiz_answer", "answer", answer.toString())
|
||||||
@ -145,7 +140,7 @@ open class StoriesRepository(private val service: StoriesService) {
|
|||||||
userId: Long,
|
userId: Long,
|
||||||
deviceUuid: String,
|
deviceUuid: String,
|
||||||
storyId: String,
|
storyId: String,
|
||||||
stickerId: String,
|
stickerId: Long,
|
||||||
answer: Int,
|
answer: Int,
|
||||||
): StoryStickerResponse = respondToSticker(csrfToken, userId, deviceUuid, storyId, stickerId, "story_poll_vote", "vote", answer.toString())
|
): StoryStickerResponse = respondToSticker(csrfToken, userId, deviceUuid, storyId, stickerId, "story_poll_vote", "vote", answer.toString())
|
||||||
|
|
||||||
@ -154,7 +149,7 @@ open class StoriesRepository(private val service: StoriesService) {
|
|||||||
userId: Long,
|
userId: Long,
|
||||||
deviceUuid: String,
|
deviceUuid: String,
|
||||||
storyId: String,
|
storyId: String,
|
||||||
stickerId: String,
|
stickerId: Long,
|
||||||
answer: Double,
|
answer: Double,
|
||||||
): StoryStickerResponse = respondToSticker(csrfToken, userId, deviceUuid, storyId, stickerId, "story_slider_vote", "vote", answer.toString())
|
): StoryStickerResponse = respondToSticker(csrfToken, userId, deviceUuid, storyId, stickerId, "story_slider_vote", "vote", answer.toString())
|
||||||
|
|
||||||
@ -182,43 +177,6 @@ open class StoriesRepository(private val service: StoriesService) {
|
|||||||
return service.seen(queryMap, signedForm)
|
return service.seen(queryMap, signedForm)
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun buildUrl(options: StoryViewerOptions): String? {
|
|
||||||
val builder = StringBuilder()
|
|
||||||
builder.append("https://i.instagram.com/api/v1/")
|
|
||||||
val type = options.type
|
|
||||||
var id: String? = null
|
|
||||||
when (type) {
|
|
||||||
StoryViewerOptions.Type.HASHTAG -> {
|
|
||||||
builder.append("tags/")
|
|
||||||
id = options.name
|
|
||||||
}
|
|
||||||
StoryViewerOptions.Type.LOCATION -> {
|
|
||||||
builder.append("locations/")
|
|
||||||
id = options.id.toString()
|
|
||||||
}
|
|
||||||
StoryViewerOptions.Type.USER -> {
|
|
||||||
builder.append("feed/user/")
|
|
||||||
id = options.id.toString()
|
|
||||||
}
|
|
||||||
StoryViewerOptions.Type.HIGHLIGHT, StoryViewerOptions.Type.STORY_ARCHIVE -> {
|
|
||||||
builder.append("feed/reels_media/?user_ids=")
|
|
||||||
id = options.name
|
|
||||||
}
|
|
||||||
StoryViewerOptions.Type.STORY -> {
|
|
||||||
}
|
|
||||||
else -> {
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (id == null) {
|
|
||||||
return null
|
|
||||||
}
|
|
||||||
builder.append(id)
|
|
||||||
if (type != StoryViewerOptions.Type.HIGHLIGHT && type != StoryViewerOptions.Type.STORY_ARCHIVE) {
|
|
||||||
builder.append("/story/")
|
|
||||||
}
|
|
||||||
return builder.toString()
|
|
||||||
}
|
|
||||||
|
|
||||||
private fun sort(list: List<Story>): List<Story> {
|
private fun sort(list: List<Story>): List<Story> {
|
||||||
val listCopy = ArrayList(list)
|
val listCopy = ArrayList(list)
|
||||||
listCopy.sortWith { o1, o2 ->
|
listCopy.sortWith { o1, o2 ->
|
||||||
|
@ -10,12 +10,12 @@ import awais.instagrabber.db.entities.Favorite
|
|||||||
import awais.instagrabber.db.repositories.FavoriteRepository
|
import awais.instagrabber.db.repositories.FavoriteRepository
|
||||||
import awais.instagrabber.getOrAwaitValue
|
import awais.instagrabber.getOrAwaitValue
|
||||||
import awais.instagrabber.models.Resource
|
import awais.instagrabber.models.Resource
|
||||||
import awais.instagrabber.models.StoryModel
|
|
||||||
import awais.instagrabber.models.enums.FavoriteType
|
import awais.instagrabber.models.enums.FavoriteType
|
||||||
import awais.instagrabber.repositories.requests.StoryViewerOptions
|
import awais.instagrabber.repositories.requests.StoryViewerOptions
|
||||||
import awais.instagrabber.repositories.responses.FriendshipStatus
|
import awais.instagrabber.repositories.responses.FriendshipStatus
|
||||||
import awais.instagrabber.repositories.responses.User
|
import awais.instagrabber.repositories.responses.User
|
||||||
import awais.instagrabber.repositories.responses.stories.Story
|
import awais.instagrabber.repositories.responses.stories.Story
|
||||||
|
import awais.instagrabber.repositories.responses.stories.StoryMedia
|
||||||
import awais.instagrabber.webservices.*
|
import awais.instagrabber.webservices.*
|
||||||
import kotlinx.coroutines.ExperimentalCoroutinesApi
|
import kotlinx.coroutines.ExperimentalCoroutinesApi
|
||||||
import org.json.JSONException
|
import org.json.JSONException
|
||||||
@ -320,13 +320,13 @@ internal class ProfileFragmentViewModelTest {
|
|||||||
"username" to testPublicUser.username
|
"username" to testPublicUser.username
|
||||||
)
|
)
|
||||||
)
|
)
|
||||||
val testUserStories = listOf(StoryModel())
|
val testUserStories = listOf(StoryMedia())
|
||||||
val testUserHighlights = listOf(Story())
|
val testUserHighlights = listOf(Story())
|
||||||
val userRepository = object : UserRepository(UserServiceAdapter()) {
|
val userRepository = object : UserRepository(UserServiceAdapter()) {
|
||||||
override suspend fun getUsernameInfo(username: String): User = testPublicUser
|
override suspend fun getUsernameInfo(username: String): User = testPublicUser
|
||||||
}
|
}
|
||||||
val storiesRepository = object : StoriesRepository(StoriesServiceAdapter()) {
|
val storiesRepository = object : StoriesRepository(StoriesServiceAdapter()) {
|
||||||
override suspend fun getUserStory(options: StoryViewerOptions): List<StoryModel> = testUserStories
|
override suspend fun getStories(options: StoryViewerOptions): List<StoryMedia> = testUserStories
|
||||||
override suspend fun fetchHighlights(profileId: Long): List<Story> = testUserHighlights
|
override suspend fun fetchHighlights(profileId: Long): List<Story> = testUserHighlights
|
||||||
}
|
}
|
||||||
val viewModel = ProfileFragmentViewModel(
|
val viewModel = ProfileFragmentViewModel(
|
||||||
|
Loading…
Reference in New Issue
Block a user