OSDN Git Service

auto_populate_reply_metadataによって自動で付加されるメンションを抽出し、送信するtextパラメータから除去する
authorKimura Youichi <kim.upsilon@bucyou.net>
Sat, 24 Sep 2016 06:17:37 +0000 (15:17 +0900)
committerKimura Youichi <kim.upsilon@bucyou.net>
Sat, 11 Nov 2017 21:06:30 +0000 (06:06 +0900)
auto_populate_reply_metadata を true にした場合、下記のユーザーに対して自動で
先頭にメンションが付加される。

 * in_reply_to_status_id の宛先のツイートを投稿したユーザー
 * in_reply_to_status_id の宛先のツイートに含まれる全てのメンション先ユーザー

これらのユーザーに対するメンションは、text パラメータ内にメンションが既に
含まれていても重複して付与されてしまうため、事前に除去する必要がある。

一方で、投稿欄に入力されているメンションのみを忠実に付与させるため、ユーザーが
入力していないメンションが auto_populate_reply_metadata によって付与されて
しまう場合は exclude_reply_user_ids パラメータを使用して明示的に除外する。

OpenTween/Tween.cs

index a9388c4..f66deff 100644 (file)
@@ -987,7 +987,7 @@ namespace OpenTween
             StatusLabel.AutoToolTip = false;
             StatusLabel.ToolTipText = "";
             //文字カウンタ初期化
-            lblLen.Text = this.GetRestStatusCount(this.FormatStatusText("")).ToString();
+            lblLen.Text = this.GetRestStatusCount("").ToString();
 
             this.JumpReadOpMenuItem.ShortcutKeyDisplayString = "Space";
             CopySTOTMenuItem.ShortcutKeyDisplayString = "Ctrl+C";
@@ -2122,7 +2122,10 @@ namespace OpenTween
             StatusText.SelectionStart = StatusText.Text.Length;
             CheckReplyTo(StatusText.Text);
 
-            var statusText = this.FormatStatusText(this.StatusText.Text);
+            long[] autoPopulatedUserIds;
+
+            var statusText = this.RemoveAutoPopuratedMentions(this.StatusText.Text, out autoPopulatedUserIds);
+            statusText = this.FormatStatusText(statusText);
 
             if (this.GetRestStatusCount(statusText) < 0)
             {
@@ -2137,6 +2140,15 @@ namespace OpenTween
 
             status.inReplyToId = this.inReplyTo?.Item1;
             status.inReplyToName = this.inReplyTo?.Item2;
+
+            var replyToPost = this.inReplyTo != null ? this._statuses[this.inReplyTo.Item1] : null;
+            if (replyToPost != null)
+            {
+                // ReplyToList のうち autoPopulatedUserIds に含まれていないユーザー ID を抽出
+                status.excludeReplyUserIds = replyToPost.ReplyToList.Select(x => x.Item1).Except(autoPopulatedUserIds)
+                    .ToArray();
+            }
+
             if (ImageSelector.Visible)
             {
                 //画像投稿
@@ -4700,7 +4712,7 @@ namespace OpenTween
         private void StatusText_TextChanged(object sender, EventArgs e)
         {
             //文字数カウント
-            int pLen = this.GetRestStatusCount(this.FormatStatusText(this.StatusText.Text));
+            int pLen = this.GetRestStatusCount(this.StatusText.Text);
             lblLen.Text = pLen.ToString();
             if (pLen < 0)
             {
@@ -4720,6 +4732,36 @@ namespace OpenTween
         }
 
         /// <summary>
+        /// 投稿時に auto_populate_reply_metadata オプションによって自動で追加されるメンションを除去します
+        /// </summary>
+        private string RemoveAutoPopuratedMentions(string statusText, out long[] autoPopulatedUserIds)
+        {
+            List<long> _autoPopulatedUserIds = new List<long>();
+
+            var replyToPost = this.inReplyTo != null ? this._statuses[this.inReplyTo.Item1] : null;
+            if (replyToPost != null)
+            {
+                if (statusText.StartsWith($"@{replyToPost.ScreenName} ", StringComparison.Ordinal))
+                {
+                    statusText = statusText.Substring(replyToPost.ScreenName.Length + 2);
+
+                    foreach (var reply in replyToPost.ReplyToList)
+                    {
+                        if (statusText.StartsWith($"@{reply.Item2} ", StringComparison.Ordinal))
+                        {
+                            statusText = statusText.Substring(reply.Item2.Length + 2);
+                            _autoPopulatedUserIds.Add(reply.Item1);
+                        }
+                    }
+                }
+            }
+
+            autoPopulatedUserIds = _autoPopulatedUserIds.ToArray();
+
+            return statusText;
+        }
+
+        /// <summary>
         /// ツイート投稿前のフッター付与などの前処理を行います
         /// </summary>
         private string FormatStatusText(string statusText)
@@ -4818,7 +4860,11 @@ namespace OpenTween
         /// </summary>
         private int GetRestStatusCount(string statusText)
         {
-            //文字数カウント
+            long[] autoPopulatedUserIds;
+            statusText = this.RemoveAutoPopuratedMentions(statusText, out autoPopulatedUserIds);
+
+            statusText = this.FormatStatusText(statusText);
+
             var remainCount = this.tw.GetTextLengthRemain(statusText);
 
             var uploadService = this.GetSelectedImageService();