public static void UpdatePartyParticipants(Service service, string bubbleGroupAddress, Action <bool> finished = null) { var bubbleGroup = BubbleGroupManager.FindWithAddress(service, bubbleGroupAddress); if (bubbleGroup == null) { finished(false); } UpdatePartyParticipants(bubbleGroup, () => { try { BubbleGroupEvents.RaiseBubblesUpdated(bubbleGroup); } catch { // do nothing } if (finished != null) { finished(true); } }); }
public static List <VisualBubble> FindAll(Service service, string address) { var bubbleGroup = BubbleGroupManager.FindWithAddress(service, address); if (bubbleGroup == null) { return(new List <VisualBubble>()); } BubbleGroupFactory.LoadFullyIfNeeded(bubbleGroup); return(bubbleGroup.Bubbles.ToList()); }
public static BubbleGroup AddNewIfNotExist(VisualBubble bubble, bool updateUi = false) { var group = BubbleGroupManager.FindWithAddress(bubble.Service, bubble.Address); if (@group != null) { return(null); } return(AddNewInternal(bubble, updateUi)); }
public static bool UpdateQuotedMessageTitle(VisualBubble bubble, Action <string> onTitleUpdated) { var service = bubble.Service; if (!ServiceManager.IsRunning(service)) { return(false); } if (string.IsNullOrWhiteSpace(bubble.QuotedAddress)) { return(false); } try { service.GetQuotedMessageTitle(bubble, result => { var bubbleGroup = BubbleGroupManager.FindWithAddress(bubble.Service, bubble.Address); if (bubbleGroup != null) { var quotedTitles = bubbleGroup.QuotedTitles == null ? new List <DisaQuotedTitle>() : bubbleGroup.QuotedTitles.ToList(); var quotedTitle = quotedTitles.FirstOrDefault(x => bubbleGroup.Service.BubbleGroupComparer(x.Address, bubble.QuotedAddress)); if (quotedTitle == null) { quotedTitles.Add(new DisaQuotedTitle { Address = bubble.QuotedAddress, Title = result, }); } else { quotedTitle.Title = result; } bubbleGroup.QuotedTitles = quotedTitles.ToArray(); } onTitleUpdated(result); }); return(true); } catch (Exception e) { Utils.DebugPrint("Error getting quoted message title " + e); return(false); } }
public static void Update(Service service, string bubbleGroupAddress) { Utils.DebugPrint("Service: " + service.Information.ServiceName + " has called UpdateBubbleGroup with id: " + bubbleGroupAddress); var selectedGroup = BubbleGroupManager.FindWithAddress(service, bubbleGroupAddress); if (selectedGroup == null) { return; } Utils.DebugPrint("Updating " + selectedGroup.ID + " with name " + (selectedGroup.Title != null ? selectedGroup.Title : "[unknown]")); Update(selectedGroup); }
public static IEnumerable <VisualBubble> FindAllUnread(Service service, string address) { var bubbleGroup = BubbleGroupManager.FindWithAddress(service, address); if (bubbleGroup != null) { foreach (var bubble in bubbleGroup) { if (bubble.Direction == Bubble.BubbleDirection.Incoming && bubble.Time >= BubbleGroupSettingsManager.GetLastUnreadSetTime(bubbleGroup)) { yield return(bubble); } } } }
public static bool UpdateStatus(Service service, string bubbleGroupAddress, string bubbleId, Bubble.BubbleStatus status) { var group = BubbleGroupManager.FindWithAddress(service, bubbleGroupAddress); if (group == null) { return(false); } BubbleGroupFactory.LoadFullyIfNeeded(group); foreach (var bubble in @group.Bubbles) { if (bubble.ID == bubbleId) { UpdateStatus(bubble, status, @group); return(true); } } return(false); }
internal static void OnBubbleReceived(Bubble b) { var visualBubble = b as VisualBubble; if (visualBubble != null) { try { BubbleManager.Group(visualBubble); } catch (Exception ex) { Utils.DebugPrint("Problem in OnBubbleReceived (VisualBubble) from service " + visualBubble.Service.Information.ServiceName + ": " + ex.Message); } if (visualBubble.Direction == Bubble.BubbleDirection.Incoming && IsRunning(visualBubble.Service) && BubbleQueueManager.HasQueuedBubbles(b.Service.Information.ServiceName, true, true)) { Utils.DebugPrint("Sending queued bubbles as we're getting some received."); BubbleQueueManager.Send(new [] { b.Service.Information.ServiceName }); } } else if (b is AbstractBubble) { Utils.DebugPrint("We got an abstract bubble: " + b.GetType().Name + " Address: " + b.Address); BubbleGroup group = null; var deliveredBubble = b as DeliveredBubble; if (deliveredBubble != null) { @group = BubbleGroupManager.FindWithAddress(deliveredBubble.Service, deliveredBubble.Address); if (@group != null) { BubbleGroupFactory.LoadFullyIfNeeded(@group); var bubbles = @group.Bubbles; for (var i = bubbles.Count - 1; i >= 0; i--) { var bubble = bubbles[i]; if (bubble.ID != deliveredBubble.VisualBubbleID) { continue; } BubbleManager.UpdateStatus(bubble, Bubble.BubbleStatus.Delivered, @group); if (@group.Service.Information.DoesSupport(typeof(DeliveredBubbleReceipt))) { BubbleManager.Send(new DeliveredBubbleReceipt(Time.GetNowUnixTimestamp(), Bubble.BubbleDirection.Outgoing, @group.Service, bubble)); } break; } } } var readBubble = b as ReadBubble; if (readBubble != null) { @group = BubbleGroupManager.FindWithAddress(readBubble.Service, readBubble.Address); if (@group != null) { BubbleGroupFactory.LoadFullyIfNeeded(@group); if (@group.ReadTimes == null || [email protected]) { @group.ReadTimes = new [] { new DisaReadTime { ParticipantAddress = readBubble.ParticipantAddress, Time = readBubble.ReadTime } }; } else { var readTimes = @group.ReadTimes.ToList(); var duplicateReadTime = readTimes.FirstOrDefault(x => @group.Service.BubbleGroupComparer(x.ParticipantAddress, readBubble.ParticipantAddress)); if (duplicateReadTime != null) { readTimes.Remove(duplicateReadTime); } readTimes.Add(new DisaReadTime { ParticipantAddress = readBubble.ParticipantAddress, Time = readBubble.ReadTime }); @group.ReadTimes = readTimes.ToArray(); } } } var prescenceBubble = b as PresenceBubble; if (prescenceBubble != null) { @group = BubbleGroupManager.Find(bubbleGroup => !bubbleGroup.IsParty && bubbleGroup.Service == prescenceBubble.Service && prescenceBubble.Service.BubbleGroupComparer( bubbleGroup.Address, prescenceBubble.Address)); if (@group != null) { if ([email protected] && !prescenceBubble.Available) { var oldPresence = @group.PresenceType; @group.PresenceType = PresenceBubble.PresenceType.Unavailable; if (oldPresence != prescenceBubble.Presence) { BubbleGroupManager.UpdateLastOnline(@group); } } else { @group.PresenceType = prescenceBubble.Presence; @group.PresencePlatformType = prescenceBubble.Platform; } if (!prescenceBubble.Available) { @group.Typing = false; } } } var typingBubble = b as TypingBubble; if (typingBubble != null) { @group = BubbleGroupManager.Find(bubbleGroup => !bubbleGroup.IsParty && bubbleGroup.Service == typingBubble.Service && typingBubble.Service.BubbleGroupComparer( bubbleGroup.Address, typingBubble.Address)); if (@group != null) { if (@group.Presence) { @group.Typing = typingBubble.Typing; @group.TypingIsAudio = typingBubble.IsAudio; } else { @group.Typing = false; } } } try { if (@group != null) { BubbleGroupEvents.RaiseNewAbstractBubble(b as AbstractBubble, @group); } } catch (Exception ex) { Utils.DebugPrint("Problem in OnBubbleReceived (AbstractBubble) from service " + b.Service.Information.ServiceName + ": " + ex.Message); } } }
internal static BubbleGroup Group(VisualBubble vb, bool resend = false, bool insertAtBottom = false) { lock (BubbleGroupDatabase.OperationLock) { Utils.DebugPrint("Grouping an " + vb.Direction + " bubble on service " + vb.Service.Information.ServiceName); var theGroup = BubbleGroupManager.FindWithAddress(vb.Service, vb.Address); BubbleGroupFactory.LoadFullyIfNeeded(theGroup); var duplicate = false; var newGroup = false; if (theGroup == null) { Utils.DebugPrint(vb.Service.Information.ServiceName + " unable to find suitable group. Creating a new one."); theGroup = new BubbleGroup(vb, null, false); newGroup = true; Utils.DebugPrint("GUID of new group: " + theGroup.ID); vb.Service.NewBubbleGroupCreated(theGroup).ContinueWith(x => { // force the UI to refetch the photo theGroup.IsPhotoSetFromService = false; SendSubscribe(theGroup, true); BubbleGroupUpdater.Update(theGroup); }); BubbleGroupManager.BubbleGroupsAdd(theGroup); } else { if (resend) { if (vb.Status == Bubble.BubbleStatus.Failed) { UpdateStatus(vb, Bubble.BubbleStatus.Waiting, theGroup); } return(theGroup); } var visualBubbleServiceId = vb.Service as IVisualBubbleServiceId; if (visualBubbleServiceId != null && visualBubbleServiceId.DisctinctIncomingVisualBubbleIdServices()) { if (vb.IdService != null) { duplicate = theGroup.Bubbles.FirstOrDefault(x => x.GetType() == vb.GetType() && x.IdService == vb.IdService) != null; } if (!duplicate && vb.IdService2 != null) { duplicate = theGroup.Bubbles.FirstOrDefault(x => x.GetType() == vb.GetType() && x.IdService2 == vb.IdService2) != null; } } if (!duplicate) { Utils.DebugPrint(vb.Service.Information.ServiceName + " found a group. Adding."); if (insertAtBottom) { var lastBubble = theGroup.LastBubbleSafe(); if (lastBubble.Time > vb.Time) { vb.Time = lastBubble.Time; } } theGroup.InsertByTime(vb); } else { Utils.DebugPrint("Yuck. It's a duplicate bubble. No need to readd: " + vb.IdService + ", " + vb.IdService2); } } if (!duplicate) { Utils.DebugPrint("Inserting bubble into database group!"); try { if (newGroup) { BubbleGroupDatabase.AddBubble(theGroup, vb); } else { BubbleGroupDatabase.InsertBubbleByTime(theGroup, vb); } } catch (Exception ex) { Utils.DebugPrint("Bubble failed to be inserting/added into the group " + theGroup.ID + ": " + ex); } try { BubbleGroupEvents.RaiseBubbleInserted(vb, theGroup); } catch (Exception ex) { Utils.DebugPrint( "Error in notifying the interface that the bubble group has been updated (" + vb.Service.Information.ServiceName + "): " + ex.Message); } } return(theGroup); } }
internal static BubbleGroup Group(VisualBubble vb, bool resend = false, bool insertAtBottom = false) { lock (BubbleGroupDatabase.OperationLock) { Utils.DebugPrint("Grouping an " + vb.Direction + " bubble on service " + vb.Service.Information.ServiceName); var theGroup = BubbleGroupManager.FindWithAddress(vb.Service, vb.Address); BubbleGroupFactory.LoadFullyIfNeeded(theGroup); var duplicate = false; var newGroup = false; if (theGroup == null) { Utils.DebugPrint(vb.Service.Information.ServiceName + " unable to find suitable group. Creating a new one."); theGroup = new BubbleGroup(vb, null, false); newGroup = true; Utils.DebugPrint("GUID of new group: " + theGroup.ID); BubbleGroupSettingsManager.SetUnreadIndicatorGuid(theGroup, theGroup.LastBubbleSafe().ID, true); vb.Service.NewBubbleGroupCreated(theGroup).ContinueWith(x => { // force the UI to refetch the photo theGroup.IsPhotoSetFromService = false; SendSubscribe(theGroup, true); BubbleGroupUpdater.Update(theGroup); }); BubbleGroupManager.BubbleGroupsAdd(theGroup); } else { if (resend) { if (vb.Status == Bubble.BubbleStatus.Failed) { UpdateStatus(vb, Bubble.BubbleStatus.Waiting, theGroup); } return(theGroup); } var visualBubbleServiceId = vb.Service as IVisualBubbleServiceId; if (visualBubbleServiceId != null && visualBubbleServiceId.DisctinctIncomingVisualBubbleIdServices()) { if (vb.IdService != null) { duplicate = theGroup.Bubbles.FirstOrDefault(x => x.GetType() == vb.GetType() && x.IdService == vb.IdService) != null; } if (!duplicate && vb.IdService2 != null) { duplicate = theGroup.Bubbles.FirstOrDefault(x => x.GetType() == vb.GetType() && x.IdService2 == vb.IdService2) != null; } } if (!duplicate) { Utils.DebugPrint(vb.Service.Information.ServiceName + " found a group. Adding."); if (insertAtBottom) { var lastBubble = theGroup.LastBubbleSafe(); if (lastBubble.Time > vb.Time) { vb.Time = lastBubble.Time; } } theGroup.InsertByTime(vb); } else { Utils.DebugPrint("Yuck. It's a duplicate bubble. No need to readd: " + vb.IdService + ", " + vb.IdService2); } } try { if (theGroup.IsParty && !string.IsNullOrWhiteSpace(vb.ParticipantAddressNickname)) { var participantAddressNicknamesArray = theGroup.ParticipantNicknames; if (participantAddressNicknamesArray == null) { participantAddressNicknamesArray = new DisaParticipantNickname[0]; } var participantAddressNicknames = participantAddressNicknamesArray.ToList(); var changed = false; var adding = true; foreach (var participantAddressNickname in participantAddressNicknames) { if (theGroup.Service.BubbleGroupComparer(participantAddressNickname.Address, vb.ParticipantAddress)) { if (participantAddressNickname.Nickname != vb.ParticipantAddressNickname) { participantAddressNickname.Nickname = vb.ParticipantAddressNickname; changed = true; } adding = false; break; } } if (adding) { participantAddressNicknames.Add(new DisaParticipantNickname { Address = vb.ParticipantAddress, Nickname = vb.ParticipantAddressNickname, }); } if (changed || adding) { theGroup.ParticipantNicknames = participantAddressNicknames.ToArray(); } } } catch (Exception ex) { Utils.DebugPrint("Failed to insert/update participant nickname into cache: " + ex); } if (!duplicate) { Utils.DebugPrint("Inserting bubble into database group!"); try { if (newGroup) { BubbleGroupDatabase.AddBubble(theGroup, vb); } else { BubbleGroupDatabase.InsertBubbleByTime(theGroup, vb); } } catch (Exception ex) { Utils.DebugPrint("Bubble failed to be inserting/added into the group " + theGroup.ID + ": " + ex); } try { BubbleGroupEvents.RaiseBubbleInserted(vb, theGroup); } catch (Exception ex) { Utils.DebugPrint( "Error in notifying the interface that the bubble group has been updated (" + vb.Service.Information.ServiceName + "): " + ex.Message); } } return(theGroup); } }
internal static BubbleGroup Group(VisualBubble vb, bool resend = false, bool insertAtBottom = false) { lock (BubbleGroupDatabase.OperationLock) { Utils.DebugPrint("Grouping an " + vb.Direction + " bubble on service " + vb.Service.Information.ServiceName); AddUrlMarkupIfNeeded(vb); var theGroup = BubbleGroupManager.FindWithAddress(vb.Service, vb.Address); BubbleGroupFactory.LoadFullyIfNeeded(theGroup); var duplicate = false; var newGroup = false; if (theGroup == null) { Utils.DebugPrint(vb.Service.Information.ServiceName + " unable to find suitable group. Creating a new one."); theGroup = new BubbleGroup(vb, null, false); newGroup = true; Utils.DebugPrint("GUID of new group: " + theGroup.ID); BubbleGroupSettingsManager.SetUnreadIndicatorGuid(theGroup, theGroup.LastBubbleSafe().ID, true); vb.Service.NewBubbleGroupCreated(theGroup).ContinueWith(x => { // force the UI to refetch the photo theGroup.IsPhotoSetFromService = false; SendSubscribe(theGroup, true); BubbleGroupUpdater.Update(theGroup); }); BubbleGroupManager.BubbleGroupsAdd(theGroup); } else { if (resend) { if (vb.Status == Bubble.BubbleStatus.Failed) { UpdateStatus(vb, Bubble.BubbleStatus.Waiting, theGroup); } return(theGroup); } // Does the Service for this VisualBubble require that the VisualBubble's IdService and IdService2 // be distinct? var visualBubbleServiceId = vb.Service as IVisualBubbleServiceId; if (visualBubbleServiceId != null && visualBubbleServiceId.DisctinctIncomingVisualBubbleIdServices()) { // Ok, we need to be distinct, BUT do the VisualBubble Type's have to be distinct as well? var checkType = true; if (!DisaFrameworkMethods.Missing(vb.Service, DisaFrameworkMethods.IVisualBubbleServiceIdCheckType)) { checkType = visualBubbleServiceId.CheckType(); } // Ok, now does the Service have special additional logic it wants to use for the distinction comparison? // Example: For Telegram, we allow an ImageBubble immediately followed by a TextBubble to have the // same VisualBubble.IdService - as this represents an image with a caption in Telegram. if (DisaFrameworkMethods.Missing(vb.Service, DisaFrameworkMethods.IVisualBubbleServiceIdVisualBubbleIdComparer)) { // Normal distinction checks if (vb.IdService != null) { duplicate = theGroup.Bubbles.FirstOrDefault(x => (!checkType || x.GetType() == vb.GetType()) && x.IdService == vb.IdService) != null; } if (!duplicate && vb.IdService2 != null) { duplicate = theGroup.Bubbles.FirstOrDefault(x => (!checkType || x.GetType() == vb.GetType()) && x.IdService2 == vb.IdService2) != null; } } else { // Special additional Service defined distinction checks if (vb.IdService != null) { var duplicateBubble = theGroup.Bubbles.FirstOrDefault(x => (!checkType || x.GetType() == vb.GetType()) && x.IdService == vb.IdService); duplicate = duplicateBubble == null ? false : visualBubbleServiceId.VisualBubbleIdComparer(left: duplicateBubble, right: vb); } if (!duplicate && vb.IdService2 != null) { var duplicateBubble = theGroup.Bubbles.FirstOrDefault(x => (!checkType || x.GetType() == vb.GetType()) && x.IdService2 == vb.IdService2); duplicate = duplicateBubble == null ? false : visualBubbleServiceId.VisualBubbleIdComparer(duplicateBubble, vb); } } } if (!duplicate) { Utils.DebugPrint(vb.Service.Information.ServiceName + " found a group. Adding."); if (insertAtBottom) { var lastBubble = theGroup.LastBubbleSafe(); if (lastBubble.Time > vb.Time) { vb.Time = lastBubble.Time; } } theGroup.InsertByTime(vb); } else { Utils.DebugPrint("Yuck. It's a duplicate bubble. No need to readd: " + vb.IdService + ", " + vb.IdService2); } } try { if (theGroup.IsParty && !string.IsNullOrWhiteSpace(vb.ParticipantAddressNickname)) { var participantAddressNicknamesArray = theGroup.ParticipantNicknames; if (participantAddressNicknamesArray == null) { participantAddressNicknamesArray = new DisaParticipantNickname[0]; } var participantAddressNicknames = participantAddressNicknamesArray.ToList(); var changed = false; var adding = true; foreach (var participantAddressNickname in participantAddressNicknames) { if (theGroup.Service.BubbleGroupComparer(participantAddressNickname.Address, vb.ParticipantAddress)) { if (participantAddressNickname.Nickname != vb.ParticipantAddressNickname) { participantAddressNickname.Nickname = vb.ParticipantAddressNickname; changed = true; } adding = false; break; } } if (adding) { participantAddressNicknames.Add(new DisaParticipantNickname { Address = vb.ParticipantAddress, Nickname = vb.ParticipantAddressNickname, }); } if (changed || adding) { theGroup.ParticipantNicknames = participantAddressNicknames.ToArray(); } } } catch (Exception ex) { Utils.DebugPrint("Failed to insert/update participant nickname into cache: " + ex); } if (!duplicate) { Utils.DebugPrint("Inserting bubble into database group!"); try { if (newGroup) { BubbleGroupDatabase.AddBubble(theGroup, vb); } else { BubbleGroupDatabase.InsertBubbleByTime(theGroup, vb); } } catch (Exception ex) { Utils.DebugPrint("Bubble failed to be inserting/added into the group " + theGroup.ID + ": " + ex); } try { BubbleGroupEvents.RaiseBubbleInserted(vb, theGroup); } catch (Exception ex) { Utils.DebugPrint( "Error in notifying the interface that the bubble group has been updated (" + vb.Service.Information.ServiceName + "): " + ex.Message); } } return(theGroup); } }