diff options
Diffstat (limited to 'src/main/java/de/pixart/messenger')
15 files changed, 143 insertions, 54 deletions
diff --git a/src/main/java/de/pixart/messenger/entities/Contact.java b/src/main/java/de/pixart/messenger/entities/Contact.java index 38808a1d7..8079ff2db 100644 --- a/src/main/java/de/pixart/messenger/entities/Contact.java +++ b/src/main/java/de/pixart/messenger/entities/Contact.java @@ -536,8 +536,13 @@ public class Contact implements ListItem, Blockable { return this.mActive; } - public void setLastseen(long timestamp) { - this.mLastseen = Math.max(timestamp, mLastseen); + public boolean setLastseen(long timestamp) { + if (timestamp > this.mLastseen) { + this.mLastseen = timestamp; + return true; + } else { + return false; + } } public long getLastseen() { diff --git a/src/main/java/de/pixart/messenger/entities/Conversation.java b/src/main/java/de/pixart/messenger/entities/Conversation.java index e3e2f0bc5..ec59e2c07 100644 --- a/src/main/java/de/pixart/messenger/entities/Conversation.java +++ b/src/main/java/de/pixart/messenger/entities/Conversation.java @@ -497,6 +497,8 @@ public class Conversation extends AbstractEntity implements Blockable, Comparabl return getJid().getUnescapedLocalpart(); } } + } else if (isWithStranger()) { + return contactJid.toBareJid().toString(); } else { return this.getContact().getDisplayName(); } @@ -1059,7 +1061,7 @@ public class Conversation extends AbstractEntity implements Blockable, Comparabl public boolean isWithStranger() { return mode == MODE_SINGLE && !getJid().equals(account.getJid().toDomainJid()) - && !getContact().mutualPresenceSubscription() + && !getContact().showInRoster() && sentMessagesCount() == 0; } diff --git a/src/main/java/de/pixart/messenger/generator/AbstractGenerator.java b/src/main/java/de/pixart/messenger/generator/AbstractGenerator.java index 33ce81859..5800db73e 100644 --- a/src/main/java/de/pixart/messenger/generator/AbstractGenerator.java +++ b/src/main/java/de/pixart/messenger/generator/AbstractGenerator.java @@ -16,6 +16,7 @@ import de.pixart.messenger.Config; import de.pixart.messenger.R; import de.pixart.messenger.crypto.axolotl.AxolotlService; import de.pixart.messenger.services.XmppConnectionService; +import de.pixart.messenger.utils.Namespace; import de.pixart.messenger.utils.PhoneHelper; import de.pixart.messenger.xmpp.jingle.stanzas.Content; @@ -118,6 +119,9 @@ public abstract class AbstractGenerator { if (Config.supportOtr()) { features.addAll(Arrays.asList(OTR)); } + if (mXmppConnectionService.broadcastLastActivity()) { + features.add(Namespace.IDLE); + } Collections.sort(features); return features; } diff --git a/src/main/java/de/pixart/messenger/parser/MessageParser.java b/src/main/java/de/pixart/messenger/parser/MessageParser.java index baa3b4d79..6965dfed5 100644 --- a/src/main/java/de/pixart/messenger/parser/MessageParser.java +++ b/src/main/java/de/pixart/messenger/parser/MessageParser.java @@ -595,10 +595,14 @@ public class MessageParser extends AbstractParser implements OnMessagePacketRece if (message.trusted() && message.treatAsDownloadable() != Message.Decision.NEVER && manager.getAutoAcceptFileSize() > 0) { manager.createNewDownloadConnection(message); } else if (notify) { - if (query == null) { - mXmppConnectionService.getNotificationService().push(message); + if (query != null && query.isCatchup()) { + mXmppConnectionService.getNotificationService().pushFromBacklog(message); + } else if (account.getXmppConnection().isWaitingForSmCatchup()) { + account.getXmppConnection().incrementSmCatchupMessageCounter(); } else if (query.isCatchup()) { // mam catchup mXmppConnectionService.getNotificationService().pushFromBacklog(message); + } else { + mXmppConnectionService.getNotificationService().push(message); } } } else if (!packet.hasChild("body")) { //no body diff --git a/src/main/java/de/pixart/messenger/parser/PresenceParser.java b/src/main/java/de/pixart/messenger/parser/PresenceParser.java index 41dfa61e9..810a6dcc5 100644 --- a/src/main/java/de/pixart/messenger/parser/PresenceParser.java +++ b/src/main/java/de/pixart/messenger/parser/PresenceParser.java @@ -17,6 +17,7 @@ import de.pixart.messenger.entities.Presence; import de.pixart.messenger.generator.IqGenerator; import de.pixart.messenger.generator.PresenceGenerator; import de.pixart.messenger.services.XmppConnectionService; +import de.pixart.messenger.utils.Namespace; import de.pixart.messenger.xml.Element; import de.pixart.messenger.xmpp.OnPresencePacketReceived; import de.pixart.messenger.xmpp.jid.Jid; @@ -210,18 +211,19 @@ public class PresenceParser extends AbstractParser implements mXmppConnectionService.fetchCaps(account, from, presence); } - final Element idle = packet.findChild("idle", "urn:xmpp:idle:1"); + final Element idle = packet.findChild("idle", Namespace.IDLE); if (idle != null) { contact.flagInactive(); - String since = idle.getAttribute("since"); + final String since = idle.getAttribute("since"); try { contact.setLastseen(AbstractParser.parseTimestamp(since)); } catch (NullPointerException | ParseException e) { contact.setLastseen(System.currentTimeMillis()); } } else { - contact.flagActive(); - contact.setLastseen(AbstractParser.parseTimestamp(packet)); + if (contact.setLastseen(AbstractParser.parseTimestamp(packet))) { + contact.flagActive(); + } } PgpEngine pgp = mXmppConnectionService.getPgpEngine(); @@ -234,6 +236,9 @@ public class PresenceParser extends AbstractParser implements boolean online = sizeBefore < contact.getPresences().size(); mXmppConnectionService.onContactStatusChanged.onContactStatusChanged(contact, online); } else if (type.equals("unavailable")) { + if (contact.setLastseen(AbstractParser.parseTimestamp(packet))) { + contact.flagInactive(); + } if (from.isBareJid()) { contact.clearPresences(); } else { diff --git a/src/main/java/de/pixart/messenger/services/NotificationService.java b/src/main/java/de/pixart/messenger/services/NotificationService.java index a571c1816..accd2e933 100644 --- a/src/main/java/de/pixart/messenger/services/NotificationService.java +++ b/src/main/java/de/pixart/messenger/services/NotificationService.java @@ -22,9 +22,12 @@ import android.util.Log; import java.io.FileNotFoundException; import java.util.ArrayList; import java.util.Calendar; +import java.util.HashMap; +import java.util.Iterator; import java.util.LinkedHashMap; import java.util.List; import java.util.Map; +import java.util.concurrent.atomic.AtomicInteger; import java.util.regex.Matcher; import java.util.regex.Pattern; @@ -52,6 +55,8 @@ public class NotificationService { private boolean mIsInForeground; private long mLastNotification; + private final HashMap<Conversation, AtomicInteger> mBacklogMessageCounter = new HashMap<>(); + public NotificationService(final XmppConnectionService service) { this.mXmppConnectionService = service; } @@ -102,11 +107,21 @@ public class NotificationService { public void pushFromBacklog(final Message message) { if (notify(message)) { synchronized (notifications) { + getBacklogMessageCounter(message.getConversation()).incrementAndGet(); pushToStack(message); } } } + private AtomicInteger getBacklogMessageCounter(Conversation conversation) { + synchronized (mBacklogMessageCounter) { + if (!mBacklogMessageCounter.containsKey(conversation)) { + mBacklogMessageCounter.put(conversation, new AtomicInteger(0)); + } + return mBacklogMessageCounter.get(conversation); + } + } + public void pushFromDirectReply(final Message message) { synchronized (notifications) { pushToStack(message); @@ -120,16 +135,24 @@ public class NotificationService { if (account == null || !notify) { updateNotification(notify); } else { - boolean hasPendingMessages = false; - for (ArrayList<Message> messages : notifications.values()) { - if (messages.size() > 0 && messages.get(0).getConversation().getAccount() == account) { - hasPendingMessages = true; - break; - } + updateNotification(getBacklogMessageCount(account) > 0); + } + } + } + + private int getBacklogMessageCount(Account account) { + int count = 0; + synchronized (this.mBacklogMessageCounter) { + for (Iterator<Map.Entry<Conversation, AtomicInteger>> it = mBacklogMessageCounter.entrySet().iterator(); it.hasNext(); ) { + Map.Entry<Conversation, AtomicInteger> entry = it.next(); + if (entry.getKey().getAccount() == account) { + count += entry.getValue().get(); + it.remove(); } - updateNotification(hasPendingMessages); } } + Log.d(Config.LOGTAG,account.getJid().toBareJid()+": backlog message count="+count); + return count; } public void finishBacklog(boolean notify) { @@ -184,6 +207,9 @@ public class NotificationService { } public void clear(final Conversation conversation) { + synchronized (this.mBacklogMessageCounter) { + this.mBacklogMessageCounter.remove(conversation); + } synchronized (notifications) { markAsReadIfHasDirectReply(conversation); notifications.remove(conversation.getUuid()); diff --git a/src/main/java/de/pixart/messenger/services/XmppConnectionService.java b/src/main/java/de/pixart/messenger/services/XmppConnectionService.java index cd40442cd..936a4591f 100644 --- a/src/main/java/de/pixart/messenger/services/XmppConnectionService.java +++ b/src/main/java/de/pixart/messenger/services/XmppConnectionService.java @@ -3423,7 +3423,7 @@ public class XmppConnectionService extends Service { } public boolean broadcastLastActivity() { - return getPreferences().getBoolean("last_activity", true); + return getPreferences().getBoolean(SettingsActivity.BROADCAST_LAST_ACTIVITY, true); } public int unreadCount() { @@ -3697,7 +3697,7 @@ public class XmppConnectionService extends Service { } if (mLastActivity > 0 && includeIdleTimestamp) { long since = Math.min(mLastActivity, System.currentTimeMillis()); //don't send future dates - packet.addChild("idle", "urn:xmpp:idle:1").setAttribute("since", AbstractGenerator.getTimestamp(since)); + packet.addChild("idle", Namespace.IDLE).setAttribute("since", AbstractGenerator.getTimestamp(since)); } sendPresencePacket(account, packet); } diff --git a/src/main/java/de/pixart/messenger/ui/BlockContactDialog.java b/src/main/java/de/pixart/messenger/ui/BlockContactDialog.java index bf33c35d9..9cc0a4ddf 100644 --- a/src/main/java/de/pixart/messenger/ui/BlockContactDialog.java +++ b/src/main/java/de/pixart/messenger/ui/BlockContactDialog.java @@ -15,6 +15,7 @@ import android.widget.Toast; import de.pixart.messenger.R; import de.pixart.messenger.entities.Blockable; +import de.pixart.messenger.entities.Conversation; public final class BlockContactDialog { public static void show(final XmppActivity xmppActivity, @@ -37,7 +38,8 @@ public final class BlockContactDialog { value = blockable.getJid().toDomainJid().toString(); spannable = new SpannableString(xmppActivity.getString(isBlocked ? R.string.unblock_domain_text : R.string.block_domain_text, value)); } else { - builder.setTitle(isBlocked ? R.string.action_unblock_contact : R.string.action_block_contact); + int resBlockAction = blockable instanceof Conversation && ((Conversation) blockable).isWithStranger() ? R.string.block_stranger : R.string.action_block_contact; + builder.setTitle(isBlocked ? R.string.action_unblock_contact : resBlockAction); value = blockable.getJid().toBareJid().toString(); spannable = new SpannableString(xmppActivity.getString(isBlocked ? R.string.unblock_contact_text : R.string.block_contact_text, value)); } diff --git a/src/main/java/de/pixart/messenger/ui/ContactDetailsActivity.java b/src/main/java/de/pixart/messenger/ui/ContactDetailsActivity.java index 6270e4721..b0fd4cd79 100644 --- a/src/main/java/de/pixart/messenger/ui/ContactDetailsActivity.java +++ b/src/main/java/de/pixart/messenger/ui/ContactDetailsActivity.java @@ -49,6 +49,7 @@ import de.pixart.messenger.entities.ListItem; import de.pixart.messenger.services.XmppConnectionService.OnAccountUpdate; import de.pixart.messenger.services.XmppConnectionService.OnRosterUpdate; import de.pixart.messenger.utils.CryptoHelper; +import de.pixart.messenger.utils.Namespace; import de.pixart.messenger.utils.UIHelper; import de.pixart.messenger.utils.XmppUri; import de.pixart.messenger.xmpp.OnKeyStatusUpdated; @@ -516,7 +517,9 @@ public class ContactDetailsActivity extends OmemoActivity implements OnAccountUp lastseen.setVisibility(View.VISIBLE); lastseen.setText(R.string.contact_blocked); } else { - if (showLastSeen && contact.getLastseen() > 0) { + if (showLastSeen + && contact.getLastseen() > 0 + && contact.getPresences().allOrNonSupport(Namespace.IDLE)) { lastseen.setVisibility(View.VISIBLE); lastseen.setText(UIHelper.lastseen(getApplicationContext(), contact.isActive(), contact.getLastseen())); } else { diff --git a/src/main/java/de/pixart/messenger/ui/ConversationActivity.java b/src/main/java/de/pixart/messenger/ui/ConversationActivity.java index efffb1d32..784f2e3ce 100644 --- a/src/main/java/de/pixart/messenger/ui/ConversationActivity.java +++ b/src/main/java/de/pixart/messenger/ui/ConversationActivity.java @@ -2016,9 +2016,12 @@ public class ConversationActivity extends XmppActivity public void success(Message message) { message.setEncryption(Message.ENCRYPTION_DECRYPTED); xmppConnectionService.sendMessage(message); - if (mConversationFragment != null) { - mConversationFragment.messageSent(); - } + runOnUiThread(new Runnable() { + @Override + public void run() { + mConversationFragment.messageSent(); + } + }); } @Override @@ -2026,15 +2029,13 @@ public class ConversationActivity extends XmppActivity runOnUiThread(new Runnable() { @Override public void run() { + mConversationFragment.doneSendingPgpMessage(); Toast.makeText(ConversationActivity.this, R.string.unable_to_connect_to_keychain, Toast.LENGTH_SHORT ).show(); } }); - if (mConversationFragment != null) { - mConversationFragment.doneSendingPgpMessage(); - } } }); } diff --git a/src/main/java/de/pixart/messenger/ui/ConversationFragment.java b/src/main/java/de/pixart/messenger/ui/ConversationFragment.java index b52c94753..fc735785c 100644 --- a/src/main/java/de/pixart/messenger/ui/ConversationFragment.java +++ b/src/main/java/de/pixart/messenger/ui/ConversationFragment.java @@ -9,10 +9,8 @@ import android.content.Context; import android.content.DialogInterface; import android.content.Intent; import android.content.IntentSender.SendIntentException; -import android.content.SharedPreferences; import android.os.Bundle; import android.os.Handler; -import android.preference.PreferenceManager; import android.support.v13.view.inputmethod.InputConnectionCompat; import android.support.v13.view.inputmethod.InputContentInfoCompat; import android.text.Editable; @@ -36,6 +34,7 @@ import android.widget.AdapterView; import android.widget.AdapterView.AdapterContextMenuInfo; import android.widget.ImageButton; import android.widget.ListView; +import android.widget.PopupMenu; import android.widget.RelativeLayout; import android.widget.TextView; import android.widget.TextView.OnEditorActionListener; @@ -55,6 +54,7 @@ import java.util.concurrent.atomic.AtomicBoolean; import de.pixart.messenger.Config; import de.pixart.messenger.R; import de.pixart.messenger.entities.Account; +import de.pixart.messenger.entities.Blockable; import de.pixart.messenger.entities.Contact; import de.pixart.messenger.entities.Conversation; import de.pixart.messenger.entities.DownloadableFile; @@ -355,8 +355,8 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa case CANCEL: if (conversation != null) { if (conversation.setCorrectingMessage(null)) { - mEditMessage.getEditableText().clear(); - mEditMessage.getEditableText().append(conversation.getDraftMessage()); + mEditMessage.setText(""); + mEditMessage.append(conversation.getDraftMessage()); conversation.setDraftMessage(null); } else if (conversation.getMode() == Conversation.MODE_MULTI) { conversation.setNextCounterpart(null); @@ -848,8 +848,6 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa Transferable transferable = message.getTransferable(); if (transferable != null) { transferable.cancel(); - } else { - activity.xmppConnectionService.markMessage(message, Message.STATUS_SEND_FAILED); } } @@ -864,7 +862,7 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa if (conversation.setOutgoingChatState(Config.DEFAULT_CHATSTATE)) { activity.xmppConnectionService.sendChatState(conversation); } - this.mEditMessage.getEditableText().clear(); + this.mEditMessage.setText(""); this.conversation.setNextCounterpart(counterpart); updateChatMsgHint(); updateSendButton(); @@ -877,8 +875,8 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa this.conversation.setCorrectingMessage(message); final Editable editable = mEditMessage.getText(); this.conversation.setDraftMessage(editable.toString()); - this.mEditMessage.getEditableText().clear(); - this.mEditMessage.getEditableText().append(message.getBody()); + this.mEditMessage.setText(""); + this.mEditMessage.append(message.getBody()); } @@ -992,8 +990,30 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa private OnClickListener mBlockClickListener = new OnClickListener() { @Override - public void onClick(final View v) { - BlockContactDialog.show(activity, conversation); + public void onClick(final View view) { + final Jid jid = conversation.getJid(); + if (jid.isDomainJid()) { + BlockContactDialog.show(activity, conversation); + } else { + PopupMenu popupMenu = new PopupMenu(activity, view); + popupMenu.inflate(R.menu.block); + popupMenu.setOnMenuItemClickListener(new PopupMenu.OnMenuItemClickListener() { + @Override + public boolean onMenuItemClick(MenuItem menuItem) { + Blockable blockable; + switch (menuItem.getItemId()) { + case R.id.block_domain: + blockable = conversation.getAccount().getRoster().getContact(jid.toDomainJid()); + break; + default: + blockable = conversation; + } + BlockContactDialog.show(activity, blockable); + return true; + } + }); + popupMenu.show(); + } } }; @@ -1036,6 +1056,7 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa private void updateSnackBar(final Conversation conversation) { final Account account = conversation.getAccount(); + final XmppConnection connection = account.getXmppConnection(); final Contact contact = conversation.getContact(); final int mode = conversation.getMode(); if (account.getStatus() == Account.State.DISABLED) { @@ -1091,7 +1112,9 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa && (conversation.getOtrSession().getSessionStatus() == SessionStatus.ENCRYPTED) && (!conversation.isOtrFingerprintVerified())) { showSnackbar(R.string.unknown_otr_fingerprint, R.string.verify, clickToVerify); - } else if (conversation.countMessages() != 0 + } else if (connection != null + && connection.getFeatures().blocking() + && conversation.countMessages() != 0 && !conversation.isBlocked() && conversation.isWithStranger()) { showSnackbar(R.string.received_message_from_stranger, R.string.block, mBlockClickListener); @@ -1122,10 +1145,9 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa } protected void messageSent() { - Editable editable = mEditMessage.getEditableText(); - editable.clear(); + mEditMessage.setText(""); if (conversation.setCorrectingMessage(null)) { - editable.append(conversation.getDraftMessage()); + mEditMessage.append(conversation.getDraftMessage()); conversation.setDraftMessage(null); } updateChatMsgHint(); @@ -1519,7 +1541,7 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa @Override public void onTypingStarted() { - final boolean broadcastLastActivity = broadcastLastActivity(); + final boolean broadcastLastActivity = activity.xmppConnectionService.broadcastLastActivity(); Account.State status = conversation.getAccount().getStatus(); if (status == Account.State.ONLINE && conversation.setOutgoingChatState(ChatState.COMPOSING)) { activity.xmppConnectionService.sendChatState(conversation); @@ -1531,15 +1553,6 @@ public class ConversationFragment extends Fragment implements EditMessage.Keyboa updateSendButton(); } - public boolean broadcastLastActivity() { - return getPreferences().getBoolean("last_activity", true); - } - - public SharedPreferences getPreferences() { - return PreferenceManager - .getDefaultSharedPreferences(getActivity().getApplicationContext()); - } - @Override public void onTypingStopped() { Account.State status = conversation.getAccount().getStatus(); diff --git a/src/main/java/de/pixart/messenger/ui/SettingsActivity.java b/src/main/java/de/pixart/messenger/ui/SettingsActivity.java index 6624266f7..61cf0a4af 100644 --- a/src/main/java/de/pixart/messenger/ui/SettingsActivity.java +++ b/src/main/java/de/pixart/messenger/ui/SettingsActivity.java @@ -41,6 +41,7 @@ public class SettingsActivity extends XmppActivity implements public static final String MANUALLY_CHANGE_PRESENCE = "manually_change_presence"; public static final String BLIND_TRUST_BEFORE_VERIFICATION = "btbv"; public static final String AUTOMATIC_MESSAGE_DELETION = "automatic_message_deletion"; + public static final String BROADCAST_LAST_ACTIVITY = "last_activity"; public static final int REQUEST_WRITE_LOGS = 0xbf8701; private SettingsFragment mSettingsFragment; @@ -231,7 +232,7 @@ public class SettingsActivity extends XmppActivity implements "allow_message_correction", TREAT_VIBRATE_AS_SILENT, MANUALLY_CHANGE_PRESENCE, - "last_activity"); + BROADCAST_LAST_ACTIVITY); if (name.equals("resource")) { String resource = preferences.getString("resource", "mobile") .toLowerCase(Locale.US); diff --git a/src/main/java/de/pixart/messenger/utils/Namespace.java b/src/main/java/de/pixart/messenger/utils/Namespace.java index bc6d56752..a384712db 100644 --- a/src/main/java/de/pixart/messenger/utils/Namespace.java +++ b/src/main/java/de/pixart/messenger/utils/Namespace.java @@ -9,4 +9,5 @@ public final class Namespace { public static final String STANZA_IDS = "urn:xmpp:sid:0"; public static final String MAM = "urn:xmpp:mam:2"; public static final String MAM_LEGACY = "urn:xmpp:mam:0"; + public static final String IDLE = "urn:xmpp:idle:1"; } diff --git a/src/main/java/de/pixart/messenger/utils/UIHelper.java b/src/main/java/de/pixart/messenger/utils/UIHelper.java index 05d6c2706..68f9297e9 100644 --- a/src/main/java/de/pixart/messenger/utils/UIHelper.java +++ b/src/main/java/de/pixart/messenger/utils/UIHelper.java @@ -112,8 +112,9 @@ public class UIHelper { public static String lastseen(Context context, boolean active, long time) { long difference = (System.currentTimeMillis() - time) / 1000; - active = active && difference <= 300; - if (active || difference < 60) { + if (active) { + return context.getString(R.string.last_seen_now); + } else if (difference < 60) { return context.getString(R.string.last_seen_now); } else if (difference < 60 * 2) { return context.getString(R.string.last_seen_min); diff --git a/src/main/java/de/pixart/messenger/xmpp/XmppConnection.java b/src/main/java/de/pixart/messenger/xmpp/XmppConnection.java index 48d4c631a..9e9b6f752 100644 --- a/src/main/java/de/pixart/messenger/xmpp/XmppConnection.java +++ b/src/main/java/de/pixart/messenger/xmpp/XmppConnection.java @@ -122,6 +122,8 @@ public class XmppConnection implements Runnable { private long lastDiscoStarted = 0; private AtomicInteger mPendingServiceDiscoveries = new AtomicInteger(0); private AtomicBoolean mWaitForDisco = new AtomicBoolean(true); + private AtomicBoolean mWaitingForSmCatchup = new AtomicBoolean(false); + private AtomicInteger mSmCatchupMessageCounter = new AtomicInteger(0); private boolean mInteractive = false; private int attempt = 0; public static String errorMessage = null; @@ -249,9 +251,18 @@ public class XmppConnection implements Runnable { this.lastConnect = SystemClock.elapsedRealtime(); this.lastPingSent = SystemClock.elapsedRealtime(); this.lastDiscoStarted = Long.MAX_VALUE; + this.mWaitingForSmCatchup.set(false); this.changeStatus(Account.State.CONNECTING); } + public boolean isWaitingForSmCatchup() { + return mWaitingForSmCatchup.get(); + } + + public void incrementSmCatchupMessageCounter() { + this.mSmCatchupMessageCounter.incrementAndGet(); + } + protected void connect() { if (mXmppConnectionService.areMessagesInitialized()) { mXmppConnectionService.resetSendingToWaiting(account); @@ -601,6 +612,7 @@ public class XmppConnection implements Runnable { final RequestPacket r = new RequestPacket(smVersion); tagWriter.writeStanzaAsync(r); } else if (nextTag.isStart("resumed")) { + this.tagWriter.writeStanzaAsync(new RequestPacket(smVersion)); lastPacketReceived = SystemClock.elapsedRealtime(); final Element resumed = tagReader.readElement(nextTag); final String h = resumed.getAttribute("h"); @@ -644,6 +656,13 @@ public class XmppConnection implements Runnable { final AckPacket ack = new AckPacket(this.stanzasReceived, smVersion); tagWriter.writeStanzaAsync(ack); } else if (nextTag.isStart("a")) { + if (mWaitingForSmCatchup.compareAndSet(true, false)) { + int count = mSmCatchupMessageCounter.get(); + Log.d(Config.LOGTAG, account.getJid().toBareJid() + ": SM catchup complete (" + count + ")"); + if (count > 0) { + mXmppConnectionService.getNotificationService().finishBacklog(true, account); + } + } final Element ack = tagReader.readElement(nextTag); lastPacketReceived = SystemClock.elapsedRealtime(); try { @@ -869,6 +888,8 @@ public class XmppConnection implements Runnable { Log.d(Config.LOGTAG, account.getJid().toBareJid() + ": resuming after stanza #" + stanzasReceived); } final ResumePacket resume = new ResumePacket(this.streamId, stanzasReceived, smVersion); + this.mSmCatchupMessageCounter.set(0); + this.mWaitingForSmCatchup.set(true); this.tagWriter.writeStanzaAsync(resume); } else if (needsBinding) { if (this.streamFeatures.hasChild("bind")) { |