fedilab-Android-App/app/src/main/java/app/fedilab/android/client/Entities/Status.java

1903 lines
85 KiB
Java
Raw Normal View History

2017-05-05 16:36:04 +02:00
/* Copyright 2017 Thomas Schneider
*
2019-05-18 11:10:30 +02:00
* This file is a part of Fedilab
2017-05-05 16:36:04 +02:00
*
* This program is free software; you can redistribute it and/or modify it under the terms of the
* GNU General Public License as published by the Free Software Foundation; either version 3 of the
* License, or (at your option) any later version.
*
2019-05-18 11:10:30 +02:00
* Fedilab is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even
2017-05-05 16:36:04 +02:00
* the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General
* Public License for more details.
*
2019-05-18 11:10:30 +02:00
* You should have received a copy of the GNU General Public License along with Fedilab; if not,
2017-05-05 16:36:04 +02:00
* see <http://www.gnu.org/licenses>. */
2019-05-18 11:10:30 +02:00
package app.fedilab.android.client.Entities;
2017-05-05 16:36:04 +02:00
2018-01-11 07:32:19 +01:00
import android.app.Activity;
2019-11-28 18:42:16 +01:00
import android.content.ClipData;
import android.content.ClipboardManager;
2017-12-03 10:56:54 +01:00
import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
2017-12-03 10:56:54 +01:00
import android.graphics.Bitmap;
2019-07-25 15:50:29 +02:00
import android.graphics.drawable.Drawable;
2018-08-14 18:27:21 +02:00
import android.net.Uri;
2017-12-03 10:56:54 +01:00
import android.os.Build;
import android.os.Bundle;
2019-11-29 15:26:49 +01:00
import android.os.Handler;
2017-05-26 17:20:36 +02:00
import android.os.Parcel;
import android.os.Parcelable;
2017-12-03 10:56:54 +01:00
import android.text.Html;
import android.text.Spannable;
2017-10-20 19:58:46 +02:00
import android.text.SpannableString;
2019-07-12 10:20:55 +02:00
import android.text.SpannableStringBuilder;
2017-12-03 10:56:54 +01:00
import android.text.Spanned;
import android.text.TextPaint;
2019-01-16 13:58:05 +01:00
import android.text.TextUtils;
2017-12-03 10:56:54 +01:00
import android.text.style.ClickableSpan;
import android.text.style.ImageSpan;
2019-08-20 13:34:43 +02:00
import android.text.style.QuoteSpan;
import android.text.style.URLSpan;
import android.util.Patterns;
2017-12-03 10:56:54 +01:00
import android.view.View;
2019-11-28 18:42:16 +01:00
import android.widget.Toast;
2017-12-03 10:56:54 +01:00
2019-11-15 16:32:25 +01:00
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
2019-11-28 18:42:16 +01:00
import androidx.appcompat.app.AlertDialog;
import androidx.appcompat.widget.PopupMenu;
2019-11-15 16:32:25 +01:00
import androidx.core.content.ContextCompat;
import androidx.preference.PreferenceManager;
2017-12-03 10:56:54 +01:00
import com.bumptech.glide.Glide;
import com.bumptech.glide.load.DataSource;
import com.bumptech.glide.load.engine.GlideException;
import com.bumptech.glide.request.RequestListener;
2020-04-09 14:59:36 +02:00
import com.bumptech.glide.request.target.CustomTarget;
2017-12-03 10:56:54 +01:00
import com.bumptech.glide.request.target.Target;
import com.bumptech.glide.request.transition.Transition;
2020-04-08 12:42:15 +02:00
2020-04-25 19:20:42 +02:00
import java.lang.ref.WeakReference;
2019-07-12 17:23:31 +02:00
import java.net.URI;
import java.net.URISyntaxException;
import java.util.ArrayList;
2017-05-05 16:36:04 +02:00
import java.util.Date;
2018-09-15 12:43:36 +02:00
import java.util.HashMap;
import java.util.Iterator;
2017-05-05 16:36:04 +02:00
import java.util.List;
2018-09-15 12:43:36 +02:00
import java.util.Map;
2020-03-14 08:41:21 +01:00
import java.util.Objects;
2017-12-03 10:56:54 +01:00
import java.util.regex.Matcher;
2018-09-01 12:42:22 +02:00
import java.util.regex.Pattern;
2017-12-03 10:56:54 +01:00
2019-05-18 11:10:30 +02:00
import app.fedilab.android.R;
2019-11-28 18:48:18 +01:00
import app.fedilab.android.activities.BaseActivity;
2019-07-24 10:05:15 +02:00
import app.fedilab.android.activities.GroupActivity;
2019-05-18 11:10:30 +02:00
import app.fedilab.android.activities.HashTagActivity;
import app.fedilab.android.activities.MainActivity;
import app.fedilab.android.activities.PeertubeActivity;
import app.fedilab.android.activities.ShowAccountActivity;
import app.fedilab.android.asynctasks.RetrieveFeedsAsyncTask;
import app.fedilab.android.asynctasks.UpdateAccountInfoAsyncTask;
2019-11-29 15:26:49 +01:00
import app.fedilab.android.client.HttpsConnection;
2019-05-18 11:10:30 +02:00
import app.fedilab.android.helper.CrossActions;
2019-08-20 13:34:43 +02:00
import app.fedilab.android.helper.CustomQuoteSpan;
2019-05-18 11:10:30 +02:00
import app.fedilab.android.helper.Helper;
2019-11-28 18:42:16 +01:00
import app.fedilab.android.helper.LongClickableSpan;
2019-11-12 19:08:05 +01:00
import app.fedilab.android.helper.ThemeHelper;
2019-05-18 11:10:30 +02:00
import app.fedilab.android.interfaces.OnRetrieveEmojiInterface;
2019-11-28 18:42:16 +01:00
import es.dmoral.toasty.Toasty;
2017-05-05 16:36:04 +02:00
2019-08-18 17:17:47 +02:00
import static android.content.Context.MODE_PRIVATE;
import static app.fedilab.android.drawers.StatusListAdapter.COMPACT_STATUS;
import static app.fedilab.android.drawers.StatusListAdapter.CONSOLE_STATUS;
import static app.fedilab.android.drawers.StatusListAdapter.DISPLAYED_STATUS;
2020-04-08 17:42:28 +02:00
2018-09-01 15:59:16 +02:00
2017-05-05 16:36:04 +02:00
/**
* Created by Thomas on 23/04/2017.
2017-05-26 17:20:36 +02:00
* Manage Status (ie: toots)
2017-05-05 16:36:04 +02:00
*/
2020-03-14 08:41:21 +01:00
@SuppressWarnings({"WeakerAccess", "BooleanMethodIsAlwaysInverted", "unused"})
2019-09-06 17:55:14 +02:00
public class Status implements Parcelable {
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
public static final Creator<Status> CREATOR = new Creator<Status>() {
@Override
public Status createFromParcel(Parcel source) {
return new Status(source);
}
@Override
public Status[] newArray(int size) {
return new Status[size];
}
};
2017-05-05 16:36:04 +02:00
private String id;
private String uri;
private String url;
private Account account;
private String in_reply_to_id;
private String in_reply_to_account_id;
private Status reblog;
private Date created_at;
private int reblogs_count;
private int favourites_count;
2018-08-19 15:21:39 +02:00
private int replies_count;
2017-05-05 16:36:04 +02:00
private boolean reblogged;
private boolean favourited;
2018-02-15 07:55:24 +01:00
private boolean muted;
private boolean pinned;
2017-05-05 16:36:04 +02:00
private boolean sensitive;
private boolean bookmarked;
2017-05-05 16:36:04 +02:00
private String visibility;
private boolean attachmentShown = false;
2017-06-07 16:52:53 +02:00
private boolean spoilerShown = false;
private ArrayList<Attachment> media_attachments;
private Attachment art_attachment;
private List<Mention> mentions;
2017-10-20 06:57:53 +02:00
private List<Emojis> emojis;
private List<Reaction> reactions;
private List<Tag> tags;
private Application application;
2017-12-20 13:57:28 +01:00
private Card card;
private String language;
private boolean isTranslated = false;
2020-06-06 18:42:12 +02:00
private transient boolean isEmojiFound = false;
private transient boolean isPollEmojiFound = false;
private transient boolean isImageFound = false;
private transient boolean isEmojiTranslateFound = false;
private boolean isTranslationShown = false;
2017-09-08 18:30:49 +02:00
private boolean isNew = false;
private boolean isVisible = true;
private boolean fetchMore = false;
2017-12-03 14:17:57 +01:00
private String content, contentCW, contentTranslated;
2020-04-09 11:04:38 +02:00
private SpannableString contentSpan, contentSpanCW, contentSpanTranslated;
2020-06-06 18:42:12 +02:00
private transient RetrieveFeedsAsyncTask.Type type;
private int itemViewType;
2018-11-21 18:04:10 +01:00
private String conversationId;
2018-11-28 09:44:19 +01:00
private boolean isExpanded = false;
private int numberLines = -1;
2019-01-31 18:01:08 +01:00
private boolean showSpoiler = false;
2019-10-20 18:03:10 +02:00
private String quickReplyContent;
private String quickReplyPrivacy;
2019-10-31 09:58:05 +01:00
private boolean showBottomLine = false;
private boolean showTopLine = false;
2019-08-01 11:41:38 +02:00
private List<String> conversationProfilePicture;
2018-11-07 11:03:32 +01:00
private String webviewURL = null;
2017-05-05 16:36:04 +02:00
2018-12-03 19:19:36 +01:00
private boolean isBoostAnimated = false, isFavAnimated = false;
2019-01-19 19:41:55 +01:00
private String scheduled_at;
2019-01-26 20:01:11 +01:00
private String contentType;
2019-02-05 18:05:21 +01:00
private boolean isNotice = false;
2019-03-24 16:38:12 +01:00
private Poll poll = null;
2017-05-26 17:20:36 +02:00
2019-05-08 09:37:17 +02:00
private int media_height;
2019-05-12 11:39:25 +02:00
private boolean cached = false;
2019-05-22 18:08:43 +02:00
private boolean autoHiddenCW = false;
2019-06-10 18:33:54 +02:00
private boolean customFeaturesDisplayed = false;
2019-06-26 14:18:18 +02:00
private boolean shortReply = false;
2019-05-08 09:37:17 +02:00
private int warningFetched = -1;
private List<String> imageURL;
2019-08-18 17:17:47 +02:00
private int viewType;
private boolean isFocused = false;
2020-06-06 18:42:12 +02:00
private transient long db_id;
private transient boolean commentsFetched = false;
private transient List<Status> comments = new ArrayList<>();
2019-11-15 16:32:25 +01:00
public Status() {
2018-11-15 19:09:44 +01:00
}
2017-12-03 10:56:54 +01:00
2019-01-16 13:58:05 +01:00
protected Status(Parcel in) {
this.id = in.readString();
this.uri = in.readString();
this.url = in.readString();
this.account = in.readParcelable(Account.class.getClassLoader());
this.in_reply_to_id = in.readString();
this.in_reply_to_account_id = in.readString();
this.reblog = in.readParcelable(Status.class.getClassLoader());
long tmpCreated_at = in.readLong();
this.created_at = tmpCreated_at == -1 ? null : new Date(tmpCreated_at);
this.reblogs_count = in.readInt();
this.favourites_count = in.readInt();
this.replies_count = in.readInt();
this.reblogged = in.readByte() != 0;
this.favourited = in.readByte() != 0;
this.muted = in.readByte() != 0;
this.pinned = in.readByte() != 0;
this.sensitive = in.readByte() != 0;
this.bookmarked = in.readByte() != 0;
this.visibility = in.readString();
this.attachmentShown = in.readByte() != 0;
this.spoilerShown = in.readByte() != 0;
this.media_attachments = in.createTypedArrayList(Attachment.CREATOR);
this.art_attachment = in.readParcelable(Attachment.class.getClassLoader());
this.mentions = in.createTypedArrayList(Mention.CREATOR);
this.emojis = in.createTypedArrayList(Emojis.CREATOR);
this.reactions = in.createTypedArrayList(Reaction.CREATOR);
2019-01-16 13:58:05 +01:00
this.tags = in.createTypedArrayList(Tag.CREATOR);
this.application = in.readParcelable(Application.class.getClassLoader());
this.card = in.readParcelable(Card.class.getClassLoader());
this.language = in.readString();
this.isTranslated = in.readByte() != 0;
this.isTranslationShown = in.readByte() != 0;
this.isNew = in.readByte() != 0;
this.isVisible = in.readByte() != 0;
this.fetchMore = in.readByte() != 0;
this.content = in.readString();
this.contentCW = in.readString();
this.contentTranslated = in.readString();
this.contentSpan = (SpannableString) TextUtils.CHAR_SEQUENCE_CREATOR.createFromParcel(in);
this.contentSpanCW = (SpannableString) TextUtils.CHAR_SEQUENCE_CREATOR.createFromParcel(in);
this.contentSpanTranslated = (SpannableString) TextUtils.CHAR_SEQUENCE_CREATOR.createFromParcel(in);
int tmpType = in.readInt();
this.type = tmpType == -1 ? null : RetrieveFeedsAsyncTask.Type.values()[tmpType];
this.itemViewType = in.readInt();
this.conversationId = in.readString();
this.isExpanded = in.readByte() != 0;
this.numberLines = in.readInt();
2019-08-01 11:41:38 +02:00
this.conversationProfilePicture = in.createStringArrayList();
2019-01-16 13:58:05 +01:00
this.webviewURL = in.readString();
this.isBoostAnimated = in.readByte() != 0;
this.isFavAnimated = in.readByte() != 0;
2019-01-19 19:41:55 +01:00
this.scheduled_at = in.readString();
2019-01-26 20:01:11 +01:00
this.contentType = in.readString();
2019-01-31 18:01:08 +01:00
this.showSpoiler = in.readByte() != 0;
2019-02-05 18:05:21 +01:00
this.isNotice = in.readByte() != 0;
2019-03-24 16:38:12 +01:00
this.poll = in.readParcelable(Poll.class.getClassLoader());
2019-05-08 09:37:17 +02:00
this.media_height = in.readInt();
2019-05-12 11:39:25 +02:00
this.cached = in.readByte() != 0;
2019-05-22 18:08:43 +02:00
this.autoHiddenCW = in.readByte() != 0;
2019-06-10 18:33:54 +02:00
this.customFeaturesDisplayed = in.readByte() != 0;
2019-06-26 14:18:18 +02:00
this.shortReply = in.readByte() != 0;
this.warningFetched = in.readInt();
this.imageURL = in.createStringArrayList();
2019-08-18 17:17:47 +02:00
this.viewType = in.readInt();
this.isFocused = in.readByte() != 0;
2019-10-20 18:03:10 +02:00
this.quickReplyContent = in.readString();
this.quickReplyPrivacy = in.readString();
2019-10-31 09:58:05 +01:00
this.showBottomLine = in.readByte() != 0;
this.showTopLine = in.readByte() != 0;
2019-01-16 13:58:05 +01:00
}
2017-05-26 17:20:36 +02:00
2020-04-08 17:56:59 +02:00
2020-04-25 19:20:42 +02:00
public static void fillSpan(WeakReference<Context> contextWeakReference, Status status) {
Status.transform(contextWeakReference, status);
Status.makeEmojis(contextWeakReference, status);
Status.makeImage(contextWeakReference, status);
2020-04-08 17:56:59 +02:00
}
2020-04-25 19:20:42 +02:00
private static void transform(WeakReference<Context> contextWeakReference, Status status) {
Context context = contextWeakReference.get();
2020-03-14 08:41:21 +01:00
if (status == null)
2019-11-15 16:32:25 +01:00
return;
SpannableString spannableStringContent, spannableStringCW;
if ((status.getReblog() != null && status.getReblog().getContent() == null) || (status.getReblog() == null && status.getContent() == null))
return;
2017-05-26 17:20:36 +02:00
2019-11-15 16:32:25 +01:00
String content = status.getReblog() != null ? status.getReblog().getContent() : status.getContent();
Matcher matcher = Helper.youtubePattern.matcher(content);
SharedPreferences sharedpreferences = context.getSharedPreferences(Helper.APP_PREFS, Context.MODE_PRIVATE);
boolean invidious = sharedpreferences.getBoolean(Helper.SET_INVIDIOUS, false);
if (invidious) {
while (matcher.find()) {
final String youtubeId = matcher.group(3);
String invidiousHost = sharedpreferences.getString(Helper.SET_INVIDIOUS_HOST, Helper.DEFAULT_INVIDIOUS_HOST).toLowerCase();
2020-03-14 08:41:21 +01:00
if (matcher.group(2) != null && Objects.equals(matcher.group(2), "youtu.be")) {
2019-11-15 16:32:25 +01:00
content = content.replaceAll("https://" + Pattern.quote(matcher.group()), Matcher.quoteReplacement("https://" + invidiousHost + "/watch?v=" + youtubeId + "&local=true"));
content = content.replaceAll(">" + Pattern.quote(matcher.group()), Matcher.quoteReplacement(">" + invidiousHost + "/watch?v=" + youtubeId + "&local=true"));
} else {
content = content.replaceAll("https://" + Pattern.quote(matcher.group()), Matcher.quoteReplacement("https://" + invidiousHost + "/" + youtubeId + "&local=true"));
content = content.replaceAll(">" + Pattern.quote(matcher.group()), Matcher.quoteReplacement(">" + invidiousHost + "/" + youtubeId + "&local=true"));
}
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
}
}
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
matcher = Helper.nitterPattern.matcher(content);
boolean nitter = sharedpreferences.getBoolean(Helper.SET_NITTER, false);
if (nitter) {
while (matcher.find()) {
final String nitter_directory = matcher.group(2);
String nitterHost = sharedpreferences.getString(Helper.SET_NITTER_HOST, Helper.DEFAULT_NITTER_HOST).toLowerCase();
content = content.replaceAll("https://" + Pattern.quote(matcher.group()), Matcher.quoteReplacement("https://" + nitterHost + nitter_directory));
content = content.replaceAll(">" + Pattern.quote(matcher.group()), Matcher.quoteReplacement(">" + nitterHost + nitter_directory));
}
}
2017-05-05 16:36:04 +02:00
2020-05-16 11:32:09 +02:00
matcher = Helper.bibliogramPattern.matcher(content);
boolean bibliogram = sharedpreferences.getBoolean(Helper.SET_BIBLIOGRAM, false);
if (bibliogram) {
while (matcher.find()) {
final String bibliogram_directory = matcher.group(2);
String bibliogramHost = sharedpreferences.getString(Helper.SET_BIBLIOGRAM_HOST, Helper.DEFAULT_BIBLIOGRAM_HOST).toLowerCase();
content = content.replaceAll("https://" + Pattern.quote(matcher.group()), Matcher.quoteReplacement("https://" + bibliogramHost + bibliogram_directory));
content = content.replaceAll(">" + Pattern.quote(matcher.group()), Matcher.quoteReplacement(">" + bibliogramHost + bibliogram_directory));
}
}
2020-05-10 11:19:22 +02:00
matcher = Helper.ouichesPattern.matcher(content);
while (matcher.find()) {
2020-05-16 11:32:09 +02:00
Attachment attachment = new Attachment();
attachment.setType("audio");
String tag = matcher.group(1);
attachment.setId(tag);
if (tag == null) {
continue;
}
attachment.setRemote_url("http://ouich.es/mp3/" + tag + ".mp3");
attachment.setUrl("http://ouich.es/mp3/" + tag + ".mp3");
if (status.getMedia_attachments() == null) {
status.setMedia_attachments(new ArrayList<>());
}
boolean alreadyAdded = false;
for (Attachment at : status.getMedia_attachments()) {
if (tag.compareTo(at.getId()) == 0) {
alreadyAdded = true;
break;
}
}
if (!alreadyAdded) {
status.getMedia_attachments().add(attachment);
}
2020-05-10 11:19:22 +02:00
}
2020-03-14 08:41:21 +01:00
Pattern aLink = Pattern.compile("<a((?!href).)*href=\"([^\"]*)\"[^>]*(((?!</a).)*)</a>");
2019-11-15 16:32:25 +01:00
Matcher matcherALink = aLink.matcher(content);
int count = 0;
while (matcherALink.find()) {
String beforemodification;
String urlText = matcherALink.group(3);
2017-05-05 16:36:04 +02:00
2020-03-14 08:41:21 +01:00
assert urlText != null;
2019-11-15 16:32:25 +01:00
urlText = urlText.substring(1);
beforemodification = urlText;
if (!beforemodification.startsWith("http")) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N)
urlText = new SpannableString(Html.fromHtml(urlText, Html.FROM_HTML_MODE_LEGACY)).toString();
else
urlText = new SpannableString(Html.fromHtml(urlText)).toString();
if (urlText.startsWith("http")) {
urlText = urlText.replace("http://", "").replace("https://", "").replace("www.", "");
if (urlText.length() > 31) {
urlText = urlText.substring(0, 30);
urlText += "" + count;
count++;
}
} else if (urlText.startsWith("@")) {
urlText += "|" + count;
count++;
}
content = content.replaceFirst(Pattern.quote(beforemodification), Matcher.quoteReplacement(urlText));
}
}
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
Pattern imgPattern = Pattern.compile("<img [^>]*src=\"([^\"]+)\"[^>]*>");
matcher = imgPattern.matcher(content);
List<String> imgs = new ArrayList<>();
int i = 1;
while (matcher.find()) {
content = content.replaceAll(Pattern.quote(matcher.group()), "<br/>[media_" + i + "]<br/>");
imgs.add("[media_" + i + "]|" + matcher.group(1));
i++;
}
status.setImageURL(imgs);
2020-03-14 08:41:21 +01:00
content = content.replaceAll("(<\\s?p\\s?>)&gt;(((?!(</p>)|(<br)).){5,})(<\\s?/p\\s?><\\s?p\\s?>|<\\s?br\\s?/?>|<\\s?/p\\s?>$)", "<blockquote>$2</blockquote><p>");
content = content.replaceAll("^<\\s?p\\s?>(.*)<\\s?/p\\s?>$", "$1");
2019-11-15 16:32:25 +01:00
spannableStringContent = new SpannableString(content);
String spoilerText = "";
if (status.getReblog() != null && status.getReblog().getSpoiler_text() != null)
spoilerText = status.getReblog().getSpoiler_text();
else if (status.getSpoiler_text() != null)
spoilerText = status.getSpoiler_text();
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N)
spannableStringCW = new SpannableString(Html.fromHtml(spoilerText, Html.FROM_HTML_MODE_LEGACY));
else
spannableStringCW = new SpannableString(Html.fromHtml(spoilerText));
if (spannableStringContent.length() > 0)
status.setContentSpan(treatment(context, spannableStringContent, status));
if (spannableStringCW.length() > 0)
status.setContentSpanCW(spannableStringCW);
2020-03-14 08:41:21 +01:00
2017-05-05 16:36:04 +02:00
}
2019-11-15 16:32:25 +01:00
private static SpannableString treatment(final Context context, SpannableString spannableString, Status status) {
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
URLSpan[] urls = spannableString.getSpans(0, spannableString.length(), URLSpan.class);
for (URLSpan span : urls)
spannableString.removeSpan(span);
List<Mention> mentions = status.getReblog() != null ? status.getReblog().getMentions() : status.getMentions();
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
SharedPreferences sharedpreferences = context.getSharedPreferences(Helper.APP_PREFS, Context.MODE_PRIVATE);
int theme = sharedpreferences.getInt(Helper.SET_THEME, Helper.THEME_DARK);
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
Matcher matcher;
2020-03-14 08:41:21 +01:00
Pattern linkPattern = Pattern.compile("<a((?!href).)*href=\"([^\"]*)\"[^>]*(((?!</a).)*)</a>");
2019-11-15 16:32:25 +01:00
matcher = linkPattern.matcher(spannableString);
HashMap<String, String> targetedURL = new HashMap<>();
HashMap<String, Account> accountsMentionUnknown = new HashMap<>();
String liveInstance = Helper.getLiveInstance(context);
2020-06-06 14:04:31 +02:00
int i = 1;
2019-11-15 16:32:25 +01:00
while (matcher.find()) {
String key;
2019-11-15 16:32:25 +01:00
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N)
key = new SpannableString(Html.fromHtml(matcher.group(3), Html.FROM_HTML_MODE_LEGACY)).toString();
else
key = new SpannableString(Html.fromHtml(matcher.group(3))).toString();
key = key.substring(1);
2020-03-14 08:41:21 +01:00
if (!key.startsWith("#") && !key.startsWith("@") && !key.trim().equals("") && !Objects.requireNonNull(matcher.group(2)).contains("search?tag=") && !Objects.requireNonNull(matcher.group(2)).contains(liveInstance + "/users/")) {
2019-11-15 16:32:25 +01:00
String url;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
url = Html.fromHtml(matcher.group(2), Html.FROM_HTML_MODE_LEGACY).toString();
} else {
url = Html.fromHtml(matcher.group(2)).toString();
}
2020-06-06 14:04:31 +02:00
targetedURL.put(key + "|" + i, url);
i++;
2020-03-14 08:41:21 +01:00
} else if (key.startsWith("@") || Objects.requireNonNull(matcher.group(2)).contains(liveInstance + "/users/")) {
2019-11-15 16:32:25 +01:00
String acct;
String url;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
url = Html.fromHtml(matcher.group(2), Html.FROM_HTML_MODE_LEGACY).toString();
} else {
url = Html.fromHtml(matcher.group(2)).toString();
}
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
URI uri;
String instance = null;
try {
uri = new URI(url);
instance = uri.getHost();
} catch (URISyntaxException e) {
2020-03-08 10:29:06 +01:00
if (url.contains("|")) {
2020-01-18 18:23:09 +01:00
try {
uri = new URI(url.split("\\|")[0]);
instance = uri.getHost();
} catch (URISyntaxException ex) {
ex.printStackTrace();
}
}
2019-11-15 16:32:25 +01:00
}
if (key.startsWith("@"))
acct = key.substring(1).split("\\|")[0];
else
acct = key.split("\\|")[0];
Account account = new Account();
account.setAcct(acct);
account.setInstance(instance);
account.setUrl(url);
String accountId = null;
2020-03-08 10:29:06 +01:00
if (mentions != null) {
2019-12-08 18:26:38 +01:00
for (Mention mention : mentions) {
String[] accountMentionAcct = mention.getAcct().split("@");
//Different isntance
if (accountMentionAcct.length > 1) {
if (mention.getAcct().equals(account.getAcct() + "@" + account.getInstance())) {
accountId = mention.getId();
break;
}
} else {
if (mention.getAcct().equals(account.getAcct())) {
accountId = mention.getId();
break;
}
2019-11-15 16:32:25 +01:00
}
}
}
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
if (accountId != null) {
account.setId(accountId);
}
accountsMentionUnknown.put(key, account);
}
}
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
SpannableString spannableStringT;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N)
spannableStringT = new SpannableString(Html.fromHtml(spannableString.toString().replaceAll("[\\s]{2}", "&nbsp;&nbsp;"), Html.FROM_HTML_MODE_LEGACY));
else
spannableStringT = new SpannableString(Html.fromHtml(spannableString.toString().replaceAll("[\\s]{2}", "&nbsp;&nbsp;")));
replaceQuoteSpans(context, spannableStringT);
URLSpan[] spans = spannableStringT.getSpans(0, spannableStringT.length(), URLSpan.class);
for (URLSpan span : spans) {
spannableStringT.removeSpan(span);
}
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
int l_c = prefs.getInt("theme_link_color", -1);
if (l_c == -1) {
l_c = ThemeHelper.getAttColor(context, R.attr.linkColor);
}
final int link_color = l_c;
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
matcher = Helper.twitterPattern.matcher(spannableStringT);
while (matcher.find()) {
int matchStart = matcher.start(2);
int matchEnd = matcher.end();
final String twittername = matcher.group(2);
2020-06-06 16:43:45 +02:00
if (matchStart >= 0 && matchEnd <= spannableStringT.toString().length() && matchEnd >= matchStart)
2019-11-15 16:32:25 +01:00
spannableStringT.setSpan(new ClickableSpan() {
@Override
public void onClick(@NonNull View textView) {
Intent intent;
boolean nitter = sharedpreferences.getBoolean(Helper.SET_NITTER, false);
if (nitter) {
String nitterHost = sharedpreferences.getString(Helper.SET_NITTER_HOST, Helper.DEFAULT_NITTER_HOST).toLowerCase();
2020-03-14 08:41:21 +01:00
assert twittername != null;
2019-11-15 16:32:25 +01:00
String url = "https://" + nitterHost + "/" + twittername.substring(1).replace("@twitter.com", "");
Helper.openBrowser(context, url);
} else {
2020-03-14 08:41:21 +01:00
assert twittername != null;
2019-11-15 16:32:25 +01:00
intent = new Intent(Intent.ACTION_VIEW, Uri.parse("https://twitter.com/" + twittername.substring(1).replace("@twitter.com", "")));
context.startActivity(intent);
}
}
2020-04-08 12:42:15 +02:00
2019-11-15 16:32:25 +01:00
@Override
public void updateDrawState(@NonNull TextPaint ds) {
super.updateDrawState(ds);
ds.setUnderlineText(false);
ds.setColor(link_color);
}
}, matchStart, matchEnd, Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
}
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
if (accountsMentionUnknown.size() > 0) {
Iterator it = accountsMentionUnknown.entrySet().iterator();
while (it.hasNext()) {
Map.Entry pair = (Map.Entry) it.next();
String key = (String) pair.getKey();
Account account = (Account) pair.getValue();
String targetedAccount = "@" + account.getAcct();
if (spannableStringT.toString().toLowerCase().contains(targetedAccount.toLowerCase())) {
2017-05-05 16:36:04 +02:00
2019-11-15 16:32:25 +01:00
int startPosition = spannableStringT.toString().toLowerCase().indexOf(key.toLowerCase());
int endPosition = startPosition + key.length();
if (key.contains("|")) {
key = key.split("\\|")[0];
SpannableStringBuilder ssb = new SpannableStringBuilder();
ssb.append(spannableStringT, 0, spannableStringT.length());
if (ssb.length() >= endPosition) {
ssb.replace(startPosition, endPosition, key);
}
spannableStringT = SpannableString.valueOf(ssb);
endPosition = startPosition + key.length();
}
//Accounts can be mentioned several times so we have to loop
2020-06-06 16:43:45 +02:00
if (startPosition >= 0 && endPosition <= spannableStringT.toString().length() && endPosition >= startPosition)
2019-11-15 16:32:25 +01:00
spannableStringT.setSpan(new ClickableSpan() {
2020-04-08 12:42:15 +02:00
@Override
public void onClick(@NonNull View textView) {
if (account.getId() == null) {
CrossActions.doCrossProfile(context, account);
} else {
Intent intent = new Intent(context, ShowAccountActivity.class);
Bundle b = new Bundle();
b.putString("accountId", account.getId());
intent.putExtras(b);
context.startActivity(intent);
}
}
@Override
public void updateDrawState(@NonNull TextPaint ds) {
super.updateDrawState(ds);
ds.setUnderlineText(false);
ds.setColor(link_color);
}
},
2019-11-15 16:32:25 +01:00
startPosition, endPosition,
Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
}
it.remove();
}
}
if (targetedURL.size() > 0) {
Iterator it = targetedURL.entrySet().iterator();
2020-06-06 14:04:31 +02:00
int endPosition = 0;
2019-11-15 16:32:25 +01:00
while (it.hasNext()) {
Map.Entry pair = (Map.Entry) it.next();
2020-06-06 14:04:31 +02:00
String key = ((String) pair.getKey()).split("\\|")[0];
2019-11-15 16:32:25 +01:00
String url = (String) pair.getValue();
if (spannableStringT.toString().toLowerCase().contains(key.toLowerCase())) {
//Accounts can be mentioned several times so we have to loop
2020-06-06 14:04:31 +02:00
int startPosition = spannableStringT.toString().toLowerCase().indexOf(key.toLowerCase(), endPosition);
if (startPosition < 0) {
startPosition = 0;
}
endPosition = startPosition + key.length();
2019-11-15 16:32:25 +01:00
if (key.contains("") && !key.endsWith("")) {
key = key.split("")[0] + "";
SpannableStringBuilder ssb = new SpannableStringBuilder();
ssb.append(spannableStringT, 0, spannableStringT.length());
if (ssb.length() >= endPosition) {
ssb.replace(startPosition, endPosition, key);
}
spannableStringT = SpannableString.valueOf(ssb);
endPosition = startPosition + key.length();
}
if (endPosition <= spannableStringT.toString().length() && endPosition >= startPosition) {
2019-11-28 18:42:16 +01:00
spannableStringT.setSpan(new LongClickableSpan() {
2020-04-08 12:42:15 +02:00
@Override
public void onClick(@NonNull View textView) {
String finalUrl = url;
Pattern link = Pattern.compile("https?://([\\da-z.-]+\\.[a-z.]{2,10})/(@[\\w._-]*[0-9]*)(/[0-9]+)?$");
Matcher matcherLink = link.matcher(url);
if (matcherLink.find() && !url.contains("medium.com")) {
if (matcherLink.group(3) != null && Objects.requireNonNull(matcherLink.group(3)).length() > 0) { //It's a toot
CrossActions.doCrossConversation(context, finalUrl);
} else {//It's an account
Account account = new Account();
String acct = matcherLink.group(2);
if (acct != null) {
if (acct.startsWith("@"))
acct = acct.substring(1);
account.setAcct(acct);
account.setInstance(matcherLink.group(1));
CrossActions.doCrossProfile(context, account);
2020-03-08 10:29:06 +01:00
}
2020-04-08 12:42:15 +02:00
}
} else {
link = Pattern.compile("(https?://[\\da-z.-]+\\.[a-z.]{2,10})/videos/watch/(\\w{8}-\\w{4}-\\w{4}-\\w{4}-\\w{12})$");
matcherLink = link.matcher(url);
if (matcherLink.find()) { //Peertubee video
Intent intent = new Intent(context, PeertubeActivity.class);
Bundle b = new Bundle();
String url = matcherLink.group(1) + "/videos/watch/" + matcherLink.group(2);
b.putString("peertubeLinkToFetch", url);
b.putString("peertube_instance", Objects.requireNonNull(matcherLink.group(1)).replace("https://", "").replace("http://", ""));
b.putString("video_id", matcherLink.group(2));
intent.putExtras(b);
context.startActivity(intent);
} else {
if (!url.toLowerCase().startsWith("http://") && !url.toLowerCase().startsWith("https://"))
finalUrl = "http://" + url;
Helper.openBrowser(context, finalUrl);
}
2019-11-28 18:42:16 +01:00
2020-04-08 12:42:15 +02:00
}
}
2019-11-28 18:42:16 +01:00
2020-04-08 12:42:15 +02:00
@Override
public void onLongClick(@NonNull View textView) {
PopupMenu popup = new PopupMenu(context, textView);
popup.getMenuInflater()
.inflate(R.menu.links_popup, popup.getMenu());
int style;
if (theme == Helper.THEME_DARK) {
style = R.style.DialogDark;
} else if (theme == Helper.THEME_BLACK) {
style = R.style.DialogBlack;
} else {
style = R.style.Dialog;
2020-03-14 08:41:21 +01:00
}
2020-04-08 12:42:15 +02:00
popup.setOnMenuItemClickListener(item -> {
switch (item.getItemId()) {
case R.id.action_show_link:
AlertDialog.Builder builder = new AlertDialog.Builder(context, style);
builder.setMessage(url);
builder.setTitle(context.getString(R.string.display_full_link));
builder.setPositiveButton(R.string.close, (dialog, which) -> dialog.dismiss())
.show();
break;
case R.id.action_share_link:
Intent sendIntent = new Intent(Intent.ACTION_SEND);
sendIntent.putExtra(Intent.EXTRA_SUBJECT, context.getString(R.string.shared_via));
sendIntent.putExtra(Intent.EXTRA_TEXT, url);
sendIntent.setType("text/plain");
context.startActivity(Intent.createChooser(sendIntent, context.getString(R.string.share_with)));
break;
case R.id.action_open_other_app:
Intent intent = new Intent(Intent.ACTION_VIEW);
intent.setData(Uri.parse(url));
try {
context.startActivity(intent);
} catch (Exception e) {
Toasty.error(context, context.getString(R.string.toast_error), Toast.LENGTH_LONG).show();
}
break;
case R.id.action_copy_link:
ClipboardManager clipboard = (ClipboardManager) context.getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip = ClipData.newPlainText(Helper.CLIP_BOARD, url);
if (clipboard != null) {
clipboard.setPrimaryClip(clip);
Toasty.info(context, context.getString(R.string.clipboard_url), Toast.LENGTH_LONG).show();
}
break;
case R.id.action_unshorten:
Thread thread = new Thread() {
@Override
public void run() {
String response = new HttpsConnection(context, null).checkUrl(url);
Handler mainHandler = new Handler(context.getMainLooper());
Runnable myRunnable = () -> {
AlertDialog.Builder builder1 = new AlertDialog.Builder(context, style);
if (response != null) {
builder1.setMessage(context.getString(R.string.redirect_detected, url, response));
builder1.setNegativeButton(R.string.copy_link, (dialog, which) -> {
ClipboardManager clipboard1 = (ClipboardManager) context.getSystemService(Context.CLIPBOARD_SERVICE);
ClipData clip1 = ClipData.newPlainText(Helper.CLIP_BOARD, response);
if (clipboard1 != null) {
clipboard1.setPrimaryClip(clip1);
Toasty.info(context, context.getString(R.string.clipboard_url), Toast.LENGTH_LONG).show();
}
dialog.dismiss();
});
builder1.setNeutralButton(R.string.share_link, (dialog, which) -> {
Intent sendIntent1 = new Intent(Intent.ACTION_SEND);
sendIntent1.putExtra(Intent.EXTRA_SUBJECT, context.getString(R.string.shared_via));
sendIntent1.putExtra(Intent.EXTRA_TEXT, url);
sendIntent1.setType("text/plain");
context.startActivity(Intent.createChooser(sendIntent1, context.getString(R.string.share_with)));
dialog.dismiss();
});
} else {
builder1.setMessage(R.string.no_redirect);
}
builder1.setTitle(context.getString(R.string.check_redirect));
builder1.setPositiveButton(R.string.close, (dialog, which) -> dialog.dismiss())
.show();
};
mainHandler.post(myRunnable);
}
};
thread.start();
break;
}
return true;
});
popup.setOnDismissListener(menu -> BaseActivity.canShowActionMode = true);
popup.show();
textView.clearFocus();
BaseActivity.canShowActionMode = false;
}
@Override
public void updateDrawState(@NonNull TextPaint ds) {
super.updateDrawState(ds);
ds.setUnderlineText(false);
ds.setColor(link_color);
}
},
2020-03-08 10:29:06 +01:00
startPosition, endPosition,
Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
2019-11-15 16:32:25 +01:00
}
}
it.remove();
}
}
matcher = Helper.hashtagPattern.matcher(spannableStringT);
while (matcher.find()) {
int matchStart = matcher.start(1);
int matchEnd = matcher.end();
final String tag = spannableStringT.toString().substring(matchStart, matchEnd);
2020-06-06 16:43:45 +02:00
if (matchStart >= 0 && matchEnd <= spannableStringT.toString().length() && matchEnd >= matchStart)
2019-11-15 16:32:25 +01:00
spannableStringT.setSpan(new ClickableSpan() {
@Override
public void onClick(@NonNull View textView) {
if (MainActivity.social != UpdateAccountInfoAsyncTask.SOCIAL.FRIENDICA) {
Intent intent = new Intent(context, HashTagActivity.class);
Bundle b = new Bundle();
b.putString("tag", tag.substring(1));
intent.putExtras(b);
2020-06-06 16:43:45 +02:00
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
2019-11-15 16:32:25 +01:00
context.startActivity(intent);
}
}
2019-11-15 16:32:25 +01:00
@Override
public void updateDrawState(@NonNull TextPaint ds) {
super.updateDrawState(ds);
ds.setUnderlineText(false);
ds.setColor(link_color);
}
}, matchStart, matchEnd, Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
2019-11-15 16:32:25 +01:00
}
2019-11-15 16:32:25 +01:00
if (MainActivity.social == UpdateAccountInfoAsyncTask.SOCIAL.GNU) {
matcher = Helper.groupPattern.matcher(spannableStringT);
while (matcher.find()) {
int matchStart = matcher.start(1);
int matchEnd = matcher.end();
final String groupname = spannableStringT.toString().substring(matchStart, matchEnd);
2020-06-06 16:43:45 +02:00
if (matchStart >= 0 && matchEnd <= spannableStringT.toString().length() && matchEnd >= matchStart)
2019-11-15 16:32:25 +01:00
spannableStringT.setSpan(new ClickableSpan() {
@Override
public void onClick(@NonNull View textView) {
if (MainActivity.social != UpdateAccountInfoAsyncTask.SOCIAL.FRIENDICA) {
Intent intent = new Intent(context, GroupActivity.class);
Bundle b = new Bundle();
b.putString("groupname", groupname.substring(1));
intent.putExtras(b);
context.startActivity(intent);
}
}
2019-11-15 16:32:25 +01:00
@Override
public void updateDrawState(@NonNull TextPaint ds) {
super.updateDrawState(ds);
ds.setUnderlineText(false);
ds.setColor(link_color);
}
}, matchStart, matchEnd, Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
2019-11-15 16:32:25 +01:00
}
}
return spannableStringT;
}
2019-11-15 16:32:25 +01:00
public static void transformTranslation(Context context, Status status) {
2019-11-15 16:32:25 +01:00
SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(context);
int l_c = prefs.getInt("theme_link_color", -1);
if (l_c == -1) {
l_c = ThemeHelper.getAttColor(context, R.attr.linkColor);
}
final int link_color = l_c;
2020-04-16 16:01:13 +02:00
if ((context instanceof Activity && ((Activity) context).isFinishing()) || status == null)
2019-11-15 16:32:25 +01:00
return;
if ((status.getReblog() != null && status.getReblog().getContent() == null) || (status.getReblog() == null && status.getContent() == null))
return;
SpannableString spannableStringTranslated;
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N)
spannableStringTranslated = new SpannableString(Html.fromHtml(status.getContentTranslated(), Html.FROM_HTML_MODE_LEGACY));
else
spannableStringTranslated = new SpannableString(Html.fromHtml(status.getContentTranslated()));
2017-08-16 18:08:16 +02:00
2019-11-15 16:32:25 +01:00
status.setContentSpanTranslated(treatment(context, spannableStringTranslated, status));
2020-04-09 11:04:38 +02:00
2019-11-15 16:32:25 +01:00
SpannableString contentSpanTranslated = status.getContentSpanTranslated();
Matcher matcherALink = Patterns.WEB_URL.matcher(contentSpanTranslated.toString());
while (matcherALink.find()) {
int matchStart = matcherALink.start();
int matchEnd = matcherALink.end();
final String url = contentSpanTranslated.toString().substring(matcherALink.start(1), matcherALink.end(1));
2020-06-06 16:43:45 +02:00
if (matchStart >= 0 && matchEnd <= contentSpanTranslated.toString().length() && matchEnd >= matchStart)
2019-11-15 16:32:25 +01:00
contentSpanTranslated.setSpan(new ClickableSpan() {
2020-04-08 12:42:15 +02:00
@Override
public void onClick(@NonNull View textView) {
String finalUrl = url;
if (!url.toLowerCase().startsWith("http://") && !url.toLowerCase().startsWith("https://"))
finalUrl = "http://" + url;
Helper.openBrowser(context, finalUrl);
}
@Override
public void updateDrawState(@NonNull TextPaint ds) {
super.updateDrawState(ds);
ds.setUnderlineText(false);
ds.setColor(link_color);
}
},
2019-11-15 16:32:25 +01:00
matchStart, matchEnd,
Spanned.SPAN_INCLUSIVE_EXCLUSIVE);
2017-10-20 19:58:46 +02:00
2019-11-15 16:32:25 +01:00
}
status.setContentSpanTranslated(contentSpanTranslated);
}
2020-04-25 19:20:42 +02:00
private static void makeEmojis(final WeakReference<Context> contextWeakReference, Status status) {
Context context = contextWeakReference.get();
2020-04-16 16:01:13 +02:00
if (context instanceof Activity && ((Activity) context).isFinishing())
2018-01-11 07:32:19 +01:00
return;
2019-11-15 16:32:25 +01:00
if (status.getReblog() != null && status.getReblog().getEmojis() == null)
return;
if (status.getReblog() == null && status.getEmojis() == null)
return;
final List<Emojis> emojis = status.getReblog() != null ? status.getReblog().getEmojis() : status.getEmojis();
2019-08-01 11:41:38 +02:00
2019-11-15 16:32:25 +01:00
SpannableString contentSpan = status.getContentSpan();
SpannableString contentSpanCW = status.getContentSpanCW();
2019-09-11 17:25:02 +02:00
SharedPreferences sharedpreferences = context.getSharedPreferences(Helper.APP_PREFS, Context.MODE_PRIVATE);
2019-11-15 16:32:25 +01:00
boolean disableAnimatedEmoji = sharedpreferences.getBoolean(Helper.SET_DISABLE_ANIMATED_EMOJI, false);
2019-08-07 19:29:45 +02:00
2019-11-15 16:32:25 +01:00
if (emojis != null && emojis.size() > 0) {
final int[] i = {0};
for (final Emojis emoji : emojis) {
Glide.with(context)
.asDrawable()
2020-04-08 12:42:15 +02:00
.load(disableAnimatedEmoji ? emoji.getStatic_url() : emoji.getUrl())
.listener(new RequestListener<Drawable>() {
2019-11-15 16:32:25 +01:00
@Override
public boolean onResourceReady(Drawable resource, Object model, Target<Drawable> target, DataSource dataSource, boolean isFirstResource) {
2019-11-15 16:32:25 +01:00
return false;
}
2019-07-12 18:19:52 +02:00
2019-11-15 16:32:25 +01:00
@Override
public boolean onLoadFailed(@Nullable GlideException e, Object model, Target target, boolean isFirstResource) {
return false;
}
})
2020-04-09 14:59:36 +02:00
.into(new CustomTarget<Drawable>() {
2019-11-15 16:32:25 +01:00
@Override
public void onResourceReady(@NonNull Drawable resource, @Nullable Transition<? super Drawable> transition) {
2019-11-15 16:32:25 +01:00
final String targetedEmoji = ":" + emoji.getShortcode() + ":";
if (contentSpan != null && contentSpan.toString().contains(targetedEmoji)) {
//emojis can be used several times so we have to loop
for (int startPosition = -1; (startPosition = contentSpan.toString().indexOf(targetedEmoji, startPosition + 1)) != -1; startPosition++) {
final int endPosition = startPosition + targetedEmoji.length();
2020-04-24 14:41:44 +02:00
if (resource != null && endPosition <= contentSpan.toString().length() && endPosition >= startPosition) {
2019-11-15 16:32:25 +01:00
ImageSpan imageSpan;
2020-04-24 14:41:44 +02:00
try {
resource.setBounds(0, 0, (int) Helper.convertDpToPixel(20, context), (int) Helper.convertDpToPixel(20, context));
resource.setVisible(true, true);
imageSpan = new ImageSpan(resource);
contentSpan.setSpan(
imageSpan, startPosition,
endPosition, Spannable.SPAN_INCLUSIVE_EXCLUSIVE);
2020-04-24 14:44:47 +02:00
} catch (Exception ignored) {
}
2019-11-15 16:32:25 +01:00
}
}
}
if (contentSpanCW != null && contentSpanCW.toString().contains(targetedEmoji)) {
//emojis can be used several times so we have to loop
for (int startPosition = -1; (startPosition = contentSpanCW.toString().indexOf(targetedEmoji, startPosition + 1)) != -1; startPosition++) {
final int endPosition = startPosition + targetedEmoji.length();
if (endPosition <= contentSpanCW.toString().length() && endPosition >= startPosition) {
ImageSpan imageSpan;
resource.setBounds(0, 0, (int) Helper.convertDpToPixel(20, context), (int) Helper.convertDpToPixel(20, context));
resource.setVisible(true, true);
imageSpan = new ImageSpan(resource);
2019-11-15 16:32:25 +01:00
contentSpanCW.setSpan(
imageSpan, startPosition,
endPosition, Spannable.SPAN_INCLUSIVE_EXCLUSIVE);
}
}
}
}
2020-04-09 14:59:36 +02:00
@Override
public void onLoadCleared(@Nullable Drawable placeholder) {
}
2019-11-15 16:32:25 +01:00
});
2019-07-12 18:19:52 +02:00
2019-07-12 17:23:31 +02:00
}
}
2019-11-15 16:32:25 +01:00
}
2020-04-25 19:20:42 +02:00
public static void makeEmojiPoll(final WeakReference<Context> contextWeakReference, Poll poll) {
Context context = contextWeakReference.get();
2020-04-16 16:01:13 +02:00
if ((context instanceof Activity && ((Activity) context).isFinishing()) || poll == null || poll.getOptionsList() == null)
2019-11-15 16:32:25 +01:00
return;
2020-04-08 17:42:28 +02:00
final List<Emojis> emojis = poll.getEmojis();
2019-11-15 16:32:25 +01:00
SharedPreferences sharedpreferences = context.getSharedPreferences(Helper.APP_PREFS, Context.MODE_PRIVATE);
boolean disableAnimatedEmoji = sharedpreferences.getBoolean(Helper.SET_DISABLE_ANIMATED_EMOJI, false);
int inc = 0;
for (PollOptions pollOption : poll.getOptionsList()) {
inc++;
SpannableString titleSpan = new SpannableString(pollOption.getTitle());
if (emojis != null && emojis.size() > 0) {
final int[] i = {0};
for (final Emojis emoji : emojis) {
Glide.with(context)
.asDrawable()
2020-04-08 12:42:15 +02:00
.load(disableAnimatedEmoji ? emoji.getStatic_url() : emoji.getUrl())
.listener(new RequestListener<Drawable>() {
2019-11-15 16:32:25 +01:00
@Override
public boolean onResourceReady(Drawable resource, Object model, Target<Drawable> target, DataSource dataSource, boolean isFirstResource) {
2019-11-15 16:32:25 +01:00
return false;
}
2019-11-06 14:09:38 +01:00
2019-11-15 16:32:25 +01:00
@Override
public boolean onLoadFailed(@Nullable GlideException e, Object model, Target target, boolean isFirstResource) {
return false;
}
})
2020-04-09 14:59:36 +02:00
.into(new CustomTarget<Drawable>() {
2019-11-15 16:32:25 +01:00
@Override
public void onResourceReady(@NonNull Drawable resource, @Nullable Transition<? super Drawable> transition) {
2019-11-15 16:32:25 +01:00
final String targetedEmoji = ":" + emoji.getShortcode() + ":";
if (titleSpan.toString().contains(targetedEmoji)) {
//emojis can be used several times so we have to loop
for (int startPosition = -1; (startPosition = titleSpan.toString().indexOf(targetedEmoji, startPosition + 1)) != -1; startPosition++) {
final int endPosition = startPosition + targetedEmoji.length();
if (endPosition <= titleSpan.toString().length() && endPosition >= startPosition) {
ImageSpan imageSpan;
resource.setBounds(0, 0, (int) Helper.convertDpToPixel(20, context), (int) Helper.convertDpToPixel(20, context));
resource.setVisible(true, true);
imageSpan = new ImageSpan(resource);
2019-11-15 16:32:25 +01:00
titleSpan.setSpan(
imageSpan, startPosition,
endPosition, Spannable.SPAN_INCLUSIVE_EXCLUSIVE);
pollOption.setTitleSpan(titleSpan);
}
}
}
}
2020-04-09 14:59:36 +02:00
@Override
public void onLoadCleared(@Nullable Drawable placeholder) {
}
2019-11-15 16:32:25 +01:00
});
2019-09-06 17:55:14 +02:00
2019-11-15 16:32:25 +01:00
}
}
}
}
2019-07-12 17:23:31 +02:00
2020-04-25 19:20:42 +02:00
private static void makeImage(final WeakReference<Context> contextWeakReference, Status status) {
Context context = contextWeakReference.get();
2020-04-16 16:01:13 +02:00
if (context instanceof Activity && ((Activity) context).isFinishing())
2019-11-15 16:32:25 +01:00
return;
if (status.getAccount() == null)
return;
if (status.getImageURL() == null || status.getImageURL().size() == 0)
return;
2019-07-12 17:23:31 +02:00
2019-11-15 16:32:25 +01:00
SpannableString contentSpan = status.getContentSpan();
final int[] i = {0};
for (final String img : status.getImageURL()) {
final String name = img.split("\\|")[0];
final String imgURL = img.split("\\|")[1];
Glide.with(context)
.asBitmap()
.load(imgURL)
.listener(new RequestListener<Bitmap>() {
@Override
public boolean onResourceReady(Bitmap resource, Object model, Target<Bitmap> target, DataSource dataSource, boolean isFirstResource) {
return false;
2019-08-18 10:16:40 +02:00
}
2019-09-06 17:55:14 +02:00
2019-11-15 16:32:25 +01:00
@Override
public boolean onLoadFailed(@Nullable GlideException e, Object model, Target target, boolean isFirstResource) {
return false;
}
})
2020-04-09 14:59:36 +02:00
.into(new CustomTarget<Bitmap>() {
2019-11-15 16:32:25 +01:00
@Override
public void onResourceReady(@NonNull Bitmap resource, Transition<? super Bitmap> transition) {
int w = resource.getWidth();
int h = resource.getHeight();
if (w > 300) {
h = (h * 300) / w;
w = 300;
}
2020-03-14 08:41:21 +01:00
if (contentSpan != null && contentSpan.toString().contains(name)) {
2019-11-15 16:32:25 +01:00
//emojis can be used several times so we have to loop
2020-03-14 08:41:21 +01:00
for (int startPosition = -1; (startPosition = contentSpan.toString().indexOf(name, startPosition + 1)) != -1; startPosition++) {
final int endPosition = startPosition + name.length();
2019-11-15 16:32:25 +01:00
if (endPosition <= contentSpan.toString().length() && endPosition >= startPosition)
contentSpan.setSpan(
new ImageSpan(context,
Bitmap.createScaledBitmap(resource, (int) Helper.convertDpToPixel(w, context),
(int) Helper.convertDpToPixel(h, context), false)), startPosition,
endPosition, Spannable.SPAN_INCLUSIVE_EXCLUSIVE);
}
}
}
2020-04-09 14:59:36 +02:00
@Override
public void onLoadCleared(@Nullable Drawable placeholder) {
}
2019-11-15 16:32:25 +01:00
});
}
}
2020-04-08 17:42:28 +02:00
2019-11-15 16:32:25 +01:00
public static void makeEmojisTranslation(final Context context, final OnRetrieveEmojiInterface listener, Status status) {
2020-04-16 16:01:13 +02:00
if (context instanceof Activity && ((Activity) context).isFinishing())
2019-11-15 16:32:25 +01:00
return;
SpannableString spannableStringTranslated = null;
if (status.getContentTranslated() != null) {
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N)
spannableStringTranslated = new SpannableString(Html.fromHtml(status.getContentTranslated(), Html.FROM_HTML_MODE_LEGACY));
else
spannableStringTranslated = new SpannableString(Html.fromHtml(status.getContentTranslated()));
}
final List<Emojis> emojis = status.getReblog() != null ? status.getReblog().getEmojis() : status.getEmojis();
if (emojis != null && emojis.size() > 0) {
final int[] i = {0};
for (final Emojis emoji : emojis) {
final SpannableString finalSpannableStringTranslated = spannableStringTranslated;
Glide.with(context)
.asBitmap()
.load(emoji.getUrl())
.listener(new RequestListener<Bitmap>() {
@Override
public boolean onResourceReady(Bitmap resource, Object model, Target<Bitmap> target, DataSource dataSource, boolean isFirstResource) {
return false;
}
@Override
public boolean onLoadFailed(@Nullable GlideException e, Object model, Target target, boolean isFirstResource) {
i[0]++;
if (i[0] == (emojis.size())) {
if (finalSpannableStringTranslated != null)
status.setContentSpanTranslated(finalSpannableStringTranslated);
listener.onRetrieveEmoji(status, true);
}
return false;
}
})
2020-04-09 14:59:36 +02:00
.into(new CustomTarget<Bitmap>() {
2019-11-15 16:32:25 +01:00
@Override
public void onResourceReady(@NonNull Bitmap resource, Transition<? super Bitmap> transition) {
final String targetedEmoji = ":" + emoji.getShortcode() + ":";
if (finalSpannableStringTranslated != null && finalSpannableStringTranslated.toString().contains(targetedEmoji)) {
//emojis can be used several times so we have to loop
for (int startPosition = -1; (startPosition = finalSpannableStringTranslated.toString().indexOf(targetedEmoji, startPosition + 1)) != -1; startPosition++) {
final int endPosition = startPosition + targetedEmoji.length();
if (endPosition <= finalSpannableStringTranslated.toString().length() && endPosition >= startPosition)
finalSpannableStringTranslated.setSpan(
new ImageSpan(context,
Bitmap.createScaledBitmap(resource, (int) Helper.convertDpToPixel(20, context),
(int) Helper.convertDpToPixel(20, context), false)), startPosition,
endPosition, Spannable.SPAN_INCLUSIVE_EXCLUSIVE);
}
}
i[0]++;
if (i[0] == (emojis.size())) {
if (finalSpannableStringTranslated != null)
status.setContentSpanTranslated(finalSpannableStringTranslated);
status.setEmojiTranslateFound(true);
listener.onRetrieveEmoji(status, true);
}
}
2020-04-09 14:59:36 +02:00
@Override
public void onLoadCleared(@Nullable Drawable placeholder) {
}
2019-11-15 16:32:25 +01:00
});
2019-07-12 17:23:31 +02:00
}
}
2019-11-15 16:32:25 +01:00
}
private static void replaceQuoteSpans(Context context, Spannable spannable) {
QuoteSpan[] quoteSpans = spannable.getSpans(0, spannable.length(), QuoteSpan.class);
for (QuoteSpan quoteSpan : quoteSpans) {
int start = spannable.getSpanStart(quoteSpan);
int end = spannable.getSpanEnd(quoteSpan);
int flags = spannable.getSpanFlags(quoteSpan);
spannable.removeSpan(quoteSpan);
2019-12-02 18:49:55 +01:00
int colord = ContextCompat.getColor(context, R.color.cyanea_accent_reference);
2019-11-15 16:32:25 +01:00
spannable.setSpan(new CustomQuoteSpan(
ContextCompat.getColor(context, R.color.transparent),
colord,
10,
20),
start,
end,
flags);
}
}
@Override
public void writeToParcel(Parcel dest, int flags) {
dest.writeString(this.id);
dest.writeString(this.uri);
dest.writeString(this.url);
dest.writeParcelable(this.account, flags);
dest.writeString(this.in_reply_to_id);
dest.writeString(this.in_reply_to_account_id);
dest.writeParcelable(this.reblog, flags);
dest.writeLong(this.created_at != null ? this.created_at.getTime() : -1);
dest.writeInt(this.reblogs_count);
dest.writeInt(this.favourites_count);
dest.writeInt(this.replies_count);
dest.writeByte(this.reblogged ? (byte) 1 : (byte) 0);
dest.writeByte(this.favourited ? (byte) 1 : (byte) 0);
dest.writeByte(this.muted ? (byte) 1 : (byte) 0);
dest.writeByte(this.pinned ? (byte) 1 : (byte) 0);
dest.writeByte(this.sensitive ? (byte) 1 : (byte) 0);
dest.writeByte(this.bookmarked ? (byte) 1 : (byte) 0);
dest.writeString(this.visibility);
dest.writeByte(this.attachmentShown ? (byte) 1 : (byte) 0);
dest.writeByte(this.spoilerShown ? (byte) 1 : (byte) 0);
dest.writeTypedList(this.media_attachments);
dest.writeParcelable(this.art_attachment, flags);
dest.writeTypedList(this.mentions);
dest.writeTypedList(this.emojis);
dest.writeTypedList(this.reactions);
2019-11-15 16:32:25 +01:00
dest.writeTypedList(this.tags);
dest.writeParcelable(this.application, flags);
dest.writeParcelable(this.card, flags);
dest.writeString(this.language);
dest.writeByte(this.isTranslated ? (byte) 1 : (byte) 0);
dest.writeByte(this.isTranslationShown ? (byte) 1 : (byte) 0);
dest.writeByte(this.isNew ? (byte) 1 : (byte) 0);
dest.writeByte(this.isVisible ? (byte) 1 : (byte) 0);
dest.writeByte(this.fetchMore ? (byte) 1 : (byte) 0);
dest.writeString(this.content);
dest.writeString(this.contentCW);
dest.writeString(this.contentTranslated);
TextUtils.writeToParcel(this.contentSpan, dest, flags);
TextUtils.writeToParcel(this.contentSpanCW, dest, flags);
TextUtils.writeToParcel(this.contentSpanTranslated, dest, flags);
dest.writeInt(this.type == null ? -1 : this.type.ordinal());
dest.writeInt(this.itemViewType);
dest.writeString(this.conversationId);
dest.writeByte(this.isExpanded ? (byte) 1 : (byte) 0);
dest.writeInt(this.numberLines);
dest.writeStringList(this.conversationProfilePicture);
dest.writeString(this.webviewURL);
dest.writeByte(this.isBoostAnimated ? (byte) 1 : (byte) 0);
dest.writeByte(this.isFavAnimated ? (byte) 1 : (byte) 0);
dest.writeString(this.scheduled_at);
dest.writeString(this.contentType);
dest.writeByte(this.showSpoiler ? (byte) 1 : (byte) 0);
dest.writeByte(this.isNotice ? (byte) 1 : (byte) 0);
dest.writeParcelable(this.poll, flags);
dest.writeInt(this.media_height);
dest.writeByte(this.cached ? (byte) 1 : (byte) 0);
dest.writeByte(this.autoHiddenCW ? (byte) 1 : (byte) 0);
dest.writeByte(this.customFeaturesDisplayed ? (byte) 1 : (byte) 0);
dest.writeByte(this.shortReply ? (byte) 1 : (byte) 0);
dest.writeInt(this.warningFetched);
dest.writeStringList(this.imageURL);
dest.writeInt(this.viewType);
dest.writeByte(this.isFocused ? (byte) 1 : (byte) 0);
dest.writeString(this.quickReplyContent);
dest.writeString(this.quickReplyPrivacy);
dest.writeByte(this.showBottomLine ? (byte) 1 : (byte) 0);
dest.writeByte(this.showTopLine ? (byte) 1 : (byte) 0);
2019-09-06 17:55:14 +02:00
2019-11-15 16:32:25 +01:00
}
2019-09-06 17:55:14 +02:00
2019-11-15 16:32:25 +01:00
public String getId() {
return id;
}
2019-09-06 17:55:14 +02:00
2019-11-15 16:32:25 +01:00
public void setId(String id) {
this.id = id;
}
2019-09-06 17:55:14 +02:00
2019-11-15 16:32:25 +01:00
public String getUri() {
return uri;
}
2019-09-06 17:55:14 +02:00
2019-11-15 16:32:25 +01:00
public void setUri(String uri) {
this.uri = uri;
}
2019-07-12 17:23:31 +02:00
2019-11-15 16:32:25 +01:00
public String getUrl() {
return url;
}
2019-07-24 10:05:15 +02:00
2019-11-15 16:32:25 +01:00
public void setUrl(String url) {
this.url = url;
}
2019-09-06 17:55:14 +02:00
2019-11-15 16:32:25 +01:00
public Account getAccount() {
return account;
}
2019-07-24 10:05:15 +02:00
2019-11-15 16:32:25 +01:00
public void setAccount(Account account) {
this.account = account;
2019-07-12 17:23:31 +02:00
}
2019-11-15 16:32:25 +01:00
public String getIn_reply_to_id() {
return in_reply_to_id;
}
2017-12-03 11:14:52 +01:00
2019-11-15 16:32:25 +01:00
public void setIn_reply_to_id(String in_reply_to_id) {
this.in_reply_to_id = in_reply_to_id;
}
2019-11-06 14:09:38 +01:00
2019-11-15 16:32:25 +01:00
public String getIn_reply_to_account_id() {
return in_reply_to_account_id;
}
2017-12-03 10:56:54 +01:00
2019-11-15 16:32:25 +01:00
public void setIn_reply_to_account_id(String in_reply_to_account_id) {
this.in_reply_to_account_id = in_reply_to_account_id;
}
2019-11-06 14:09:38 +01:00
2019-11-15 16:32:25 +01:00
public String getContent() {
2020-06-06 18:42:12 +02:00
return content.replaceAll("\\p{C}", "?");
2019-11-15 16:32:25 +01:00
}
2019-11-06 14:09:38 +01:00
2019-11-30 08:53:37 +01:00
public void setContent(Context context, String content) {
2019-11-15 16:32:25 +01:00
//Remove UTM by default
2019-11-30 08:53:37 +01:00
this.content = Helper.remove_tracking_param(context, content);
2019-11-15 16:32:25 +01:00
}
2019-09-06 17:55:14 +02:00
2019-11-15 16:32:25 +01:00
public boolean isShortReply() {
return shortReply;
}
2019-11-15 16:32:25 +01:00
public void setShortReply(boolean shortReply) {
this.shortReply = shortReply;
2017-12-03 10:56:54 +01:00
}
2019-11-15 16:32:25 +01:00
public Status getReblog() {
return reblog;
}
2017-12-03 10:56:54 +01:00
2019-11-15 16:32:25 +01:00
public void setReblog(Status reblog) {
this.reblog = reblog;
}
2017-12-03 10:56:54 +01:00
2019-11-15 16:32:25 +01:00
public int getReblogs_count() {
return reblogs_count;
}
2018-08-17 16:22:26 +02:00
2019-11-15 16:32:25 +01:00
public void setReblogs_count(int reblogs_count) {
this.reblogs_count = reblogs_count;
}
2018-11-16 07:33:19 +01:00
2019-11-15 16:32:25 +01:00
public Date getCreated_at() {
return created_at;
}
2019-08-08 09:43:12 +02:00
2019-11-15 16:32:25 +01:00
public void setCreated_at(Date created_at) {
this.created_at = created_at;
}
2019-08-08 09:43:12 +02:00
2019-11-15 16:32:25 +01:00
public int getFavourites_count() {
return favourites_count;
}
public void setFavourites_count(int favourites_count) {
this.favourites_count = favourites_count;
}
2019-08-08 09:43:12 +02:00
2019-11-15 16:32:25 +01:00
public boolean isReblogged() {
return reblogged;
}
2019-07-25 17:20:04 +02:00
2019-11-15 16:32:25 +01:00
public void setReblogged(boolean reblogged) {
this.reblogged = reblogged;
}
2019-08-02 15:35:13 +02:00
2019-11-15 16:32:25 +01:00
public boolean isFavourited() {
return favourited;
}
2017-12-03 14:17:57 +01:00
2019-11-15 16:32:25 +01:00
public void setFavourited(boolean favourited) {
this.favourited = favourited;
2017-12-03 14:17:57 +01:00
}
2019-11-15 16:32:25 +01:00
public boolean isPinned() {
return pinned;
}
2017-12-03 14:17:57 +01:00
2019-11-15 16:32:25 +01:00
public void setPinned(boolean pinned) {
this.pinned = pinned;
}
2019-11-03 14:16:08 +01:00
2019-11-15 16:32:25 +01:00
public boolean isSensitive() {
return sensitive;
}
2019-11-03 14:16:08 +01:00
2019-11-15 16:32:25 +01:00
public void setSensitive(boolean sensitive) {
this.sensitive = sensitive;
}
2019-11-03 14:16:08 +01:00
2019-11-15 16:32:25 +01:00
public String getSpoiler_text() {
return contentCW;
}
2019-11-03 14:16:08 +01:00
2019-11-15 16:32:25 +01:00
public void setSpoiler_text(String spoiler_text) {
this.contentCW = spoiler_text;
}
public ArrayList<Attachment> getMedia_attachments() {
return media_attachments;
}
public void setMedia_attachments(ArrayList<Attachment> media_attachments) {
this.media_attachments = media_attachments;
}
public List<Mention> getMentions() {
return mentions;
}
public void setMentions(List<Mention> mentions) {
this.mentions = mentions;
}
2019-11-03 14:16:08 +01:00
2019-11-15 16:32:25 +01:00
public List<Tag> getTags() {
return tags;
}
public void setTags(List<Tag> tags) {
this.tags = tags;
}
public String getTagsString() {
//iterate through tags and create comma delimited string of tag names
2020-03-14 08:41:21 +01:00
StringBuilder tag_names = new StringBuilder();
2019-11-15 16:32:25 +01:00
for (Tag t : tags) {
2020-03-14 08:41:21 +01:00
if (tag_names.toString().equals("")) {
tag_names = new StringBuilder(t.getName());
2019-11-15 16:32:25 +01:00
} else {
2020-03-14 08:41:21 +01:00
tag_names.append(", ").append(t.getName());
2019-11-03 14:16:08 +01:00
}
}
2020-03-14 08:41:21 +01:00
return tag_names.toString();
2019-11-03 14:16:08 +01:00
}
2019-11-15 16:32:25 +01:00
public Application getApplication() {
return application;
}
2019-11-15 16:32:25 +01:00
public void setApplication(Application application) {
this.application = application;
}
2019-11-15 16:32:25 +01:00
public String getVisibility() {
return visibility;
}
2019-11-15 16:32:25 +01:00
public void setVisibility(String visibility) {
this.visibility = visibility;
}
2019-11-15 16:32:25 +01:00
public boolean isAttachmentShown() {
return attachmentShown;
}
2019-11-15 16:32:25 +01:00
public void setAttachmentShown(boolean attachmentShown) {
this.attachmentShown = attachmentShown;
}
2019-11-15 16:32:25 +01:00
public boolean isSpoilerShown() {
return spoilerShown;
}
2019-11-15 16:32:25 +01:00
public void setSpoilerShown(boolean spoilerShown) {
this.spoilerShown = spoilerShown;
}
2019-11-15 16:32:25 +01:00
public String getLanguage() {
return language;
}
2017-12-03 14:17:57 +01:00
2019-11-15 16:32:25 +01:00
public void setLanguage(String language) {
this.language = language;
}
2017-12-03 14:17:57 +01:00
2019-11-15 16:32:25 +01:00
public boolean isTranslated() {
return isTranslated;
}
2017-12-03 14:17:57 +01:00
2019-11-15 16:32:25 +01:00
public void setTranslated(boolean translated) {
isTranslated = translated;
}
2017-12-03 14:17:57 +01:00
2019-11-15 16:32:25 +01:00
public boolean isTranslationShown() {
return isTranslationShown;
}
2017-12-03 10:56:54 +01:00
2019-11-15 16:32:25 +01:00
public void setTranslationShown(boolean translationShown) {
isTranslationShown = translationShown;
2017-10-20 19:58:46 +02:00
}
2019-11-15 16:32:25 +01:00
public String getContentTranslated() {
return contentTranslated;
}
2017-12-03 10:56:54 +01:00
2019-11-15 16:32:25 +01:00
public void setContentTranslated(String content_translated) {
this.contentTranslated = content_translated;
}
public boolean isNew() {
return isNew;
}
public void setNew(boolean aNew) {
isNew = aNew;
}
public boolean isVisible() {
return isVisible;
}
public void setVisible(boolean visible) {
isVisible = visible;
}
public List<Emojis> getEmojis() {
return emojis;
}
public void setEmojis(List<Emojis> emojis) {
this.emojis = emojis;
}
public boolean isEmojiFound() {
return isEmojiFound;
}
public void setEmojiFound(boolean emojiFound) {
isEmojiFound = emojiFound;
}
public boolean isImageFound() {
return isImageFound;
2019-08-20 13:34:43 +02:00
}
2018-08-14 18:27:21 +02:00
2019-11-15 16:32:25 +01:00
public void setImageFound(boolean imageFound) {
isImageFound = imageFound;
}
2017-10-20 19:58:46 +02:00
2017-12-03 10:56:54 +01:00
public SpannableString getContentSpan() {
return contentSpan;
2017-10-20 19:58:46 +02:00
}
2017-12-03 10:56:54 +01:00
public void setContentSpan(SpannableString contentSpan) {
this.contentSpan = contentSpan;
}
public SpannableString getContentSpanCW() {
return contentSpanCW;
}
public void setContentSpanCW(SpannableString contentSpanCW) {
this.contentSpanCW = contentSpanCW;
}
public SpannableString getContentSpanTranslated() {
return contentSpanTranslated;
}
public void setContentSpanTranslated(SpannableString contentSpanTranslated) {
this.contentSpanTranslated = contentSpanTranslated;
}
2019-11-15 16:32:25 +01:00
2017-12-03 14:17:57 +01:00
public boolean isEmojiTranslateFound() {
return isEmojiTranslateFound;
}
public void setEmojiTranslateFound(boolean emojiTranslateFound) {
isEmojiTranslateFound = emojiTranslateFound;
}
public boolean isFetchMore() {
return fetchMore;
}
public void setFetchMore(boolean fetchMore) {
this.fetchMore = fetchMore;
}
2017-12-07 17:48:03 +01:00
@Override
public boolean equals(Object otherStatus) {
return otherStatus != null && (otherStatus == this || otherStatus instanceof Status && this.getId().equals(((Status) otherStatus).getId()));
}
2017-12-20 13:57:28 +01:00
public Card getCard() {
return card;
}
public void setCard(Card card) {
this.card = card;
}
2018-02-15 07:55:24 +01:00
public boolean isMuted() {
return muted;
}
public void setMuted(boolean muted) {
this.muted = muted;
}
public boolean isBookmarked() {
2019-11-15 16:32:25 +01:00
if (this.getReblog() != null && this.getReblog().isBookmarked()) {
2019-11-15 13:58:06 +01:00
bookmarked = true;
}
return bookmarked;
}
public void setBookmarked(boolean bookmarked) {
this.bookmarked = bookmarked;
}
2018-08-19 15:21:39 +02:00
public int getReplies_count() {
return replies_count;
}
public void setReplies_count(int replies_count) {
this.replies_count = replies_count;
}
public RetrieveFeedsAsyncTask.Type getType() {
return type;
}
public void setType(RetrieveFeedsAsyncTask.Type type) {
this.type = type;
}
2018-10-29 18:32:55 +01:00
2019-08-01 11:41:38 +02:00
public List<String> getConversationProfilePicture() {
return conversationProfilePicture;
2018-10-29 18:32:55 +01:00
}
2019-08-01 11:41:38 +02:00
public void setConversationProfilePicture(List<String> conversationProfilePicture) {
this.conversationProfilePicture = conversationProfilePicture;
2018-10-29 18:32:55 +01:00
}
2018-11-07 11:03:32 +01:00
public String getWebviewURL() {
return webviewURL;
}
public void setWebviewURL(String webviewURL) {
this.webviewURL = webviewURL;
}
public int getItemViewType() {
return itemViewType;
}
public void setItemViewType(int itemViewType) {
this.itemViewType = itemViewType;
}
2018-11-21 18:04:10 +01:00
public String getConversationId() {
return conversationId;
}
public void setConversationId(String conversationId) {
this.conversationId = conversationId;
}
2018-11-28 09:44:19 +01:00
public boolean isExpanded() {
return isExpanded;
}
public void setExpanded(boolean expanded) {
isExpanded = expanded;
}
public int getNumberLines() {
return numberLines;
}
public void setNumberLines(int numberLines) {
this.numberLines = numberLines;
}
2018-12-03 19:19:36 +01:00
public boolean isBoostAnimated() {
return isBoostAnimated;
}
public void setBoostAnimated(boolean boostAnimated) {
isBoostAnimated = boostAnimated;
}
public boolean isFavAnimated() {
return isFavAnimated;
}
public void setFavAnimated(boolean favAnimated) {
isFavAnimated = favAnimated;
}
public Attachment getArt_attachment() {
return art_attachment;
}
public void setArt_attachment(Attachment art_attachment) {
this.art_attachment = art_attachment;
}
2019-01-16 13:58:05 +01:00
@Override
public int describeContents() {
return 0;
}
2019-01-19 19:41:55 +01:00
public String getScheduled_at() {
return scheduled_at;
}
public void setScheduled_at(String scheduled_at) {
this.scheduled_at = scheduled_at;
}
2019-01-26 20:01:11 +01:00
public String getContentType() {
return contentType;
}
public void setContentType(String contentType) {
this.contentType = contentType;
}
2019-01-31 18:01:08 +01:00
public boolean isShowSpoiler() {
return showSpoiler;
}
public void setShowSpoiler(boolean showSpoiler) {
this.showSpoiler = showSpoiler;
}
2019-02-05 18:05:21 +01:00
public boolean isNotice() {
return isNotice;
}
public void setNotice(boolean notice) {
isNotice = notice;
}
2019-03-24 16:38:12 +01:00
public Poll getPoll() {
return poll;
}
public void setPoll(Poll poll) {
this.poll = poll;
}
2019-05-08 09:37:17 +02:00
public int getMedia_height() {
return media_height;
}
public void setMedia_height(int media_height) {
this.media_height = media_height;
}
2019-05-12 11:39:25 +02:00
public boolean iscached() {
return cached;
}
2019-05-12 11:39:25 +02:00
public void setcached(boolean cached) {
this.cached = cached;
}
2019-05-22 18:08:43 +02:00
public boolean isAutoHiddenCW() {
return autoHiddenCW;
}
public void setAutoHiddenCW(boolean autoHiddenCW) {
this.autoHiddenCW = autoHiddenCW;
}
2019-06-10 18:33:54 +02:00
public boolean isCustomFeaturesDisplayed() {
return customFeaturesDisplayed;
}
public void setCustomFeaturesDisplayed(boolean customFeaturesDisplayed) {
this.customFeaturesDisplayed = customFeaturesDisplayed;
}
public int getWarningFetched() {
return warningFetched;
}
public void setWarningFetched(int warningFetched) {
this.warningFetched = warningFetched;
}
public List<String> getImageURL() {
return imageURL;
}
public void setImageURL(List<String> imageURL) {
this.imageURL = imageURL;
}
2019-08-01 11:41:38 +02:00
2019-08-18 17:17:47 +02:00
public int getViewType() {
return viewType;
}
public void setViewType(Context context) {
SharedPreferences sharedpreferences = context.getSharedPreferences(Helper.APP_PREFS, MODE_PRIVATE);
boolean isCompactMode = sharedpreferences.getBoolean(Helper.SET_COMPACT_MODE, false);
boolean isConsoleMode = sharedpreferences.getBoolean(Helper.SET_CONSOLE_MODE, false);
2019-09-06 17:55:14 +02:00
if (isCompactMode)
this.viewType = COMPACT_STATUS;
else if (isConsoleMode)
this.viewType = CONSOLE_STATUS;
2019-08-18 18:05:50 +02:00
else
2019-09-06 17:55:14 +02:00
this.viewType = DISPLAYED_STATUS;
2019-08-18 18:05:50 +02:00
2019-08-18 17:17:47 +02:00
}
public boolean isFocused() {
return isFocused;
}
public void setFocused(boolean focused) {
isFocused = focused;
}
public long getDb_id() {
return db_id;
}
public void setDb_id(long db_id) {
this.db_id = db_id;
}
2019-09-27 18:52:42 +02:00
public boolean isCommentsFetched() {
return commentsFetched;
}
public void setCommentsFetched(boolean commentsFetched) {
this.commentsFetched = commentsFetched;
}
public List<Status> getComments() {
return comments;
}
public void setComments(List<Status> comments) {
this.comments = comments;
}
2019-10-20 18:03:10 +02:00
public String getQuickReplyContent() {
return quickReplyContent;
}
public void setQuickReplyContent(String quickReplyContent) {
this.quickReplyContent = quickReplyContent;
}
public String getQuickReplyPrivacy() {
return quickReplyPrivacy;
}
public void setQuickReplyPrivacy(String quickReplyPrivacy) {
this.quickReplyPrivacy = quickReplyPrivacy;
}
2019-10-31 09:58:05 +01:00
public boolean isShowBottomLine() {
return showBottomLine;
}
public void setShowBottomLine(boolean showBottomLine) {
this.showBottomLine = showBottomLine;
}
public boolean isShowTopLine() {
return showTopLine;
}
public void setShowTopLine(boolean showTopLine) {
this.showTopLine = showTopLine;
}
2019-11-03 14:16:08 +01:00
public boolean isPollEmojiFound() {
return isPollEmojiFound;
}
public void setPollEmojiFound(boolean pollEmojiFound) {
isPollEmojiFound = pollEmojiFound;
}
public List<Reaction> getReactions() {
return reactions;
}
public void setReactions(List<Reaction> reactions) {
this.reactions = reactions;
}
2020-03-14 08:41:21 +01:00
2017-05-05 16:36:04 +02:00
}