OSDN Git Service

TweetActPanelに対する設定値の設定・取得を LoadConfing/SaveConfig メソッドに移動
[opentween/open-tween.git] / OpenTween / Tween.cs
index 5d09936..eebdbc4 100644 (file)
@@ -53,8 +53,6 @@ namespace OpenTween
 {
     public partial class TweenMain : OTBaseForm
     {
-        private readonly HttpClient http;
-
         //各種設定
         private Size _mySize;           //画面サイズ
         private Point _myLoc;           //画面位置
@@ -201,7 +199,6 @@ namespace OpenTween
         private bool _waitLists = false;
         private BackgroundWorker[] _bw = new BackgroundWorker[20];
         private BackgroundWorker _bwFollower;
-        private InternetSecurityManager SecurityManager;
 
         private int UnreadCounter = -1;
         private int UnreadAtCounter = -1;
@@ -211,7 +208,6 @@ namespace OpenTween
 
         private bool _DoFavRetweetFlags = false;
         private bool osResumed = false;
-        private Dictionary<string, IMultimediaShareService> pictureService;
 
         //////////////////////////////////////////////////////////////////////////////////////////////////////////
         private string _postBrowserStatusText = "";
@@ -257,12 +253,8 @@ namespace OpenTween
         private class GetWorkerResult
         {
             public string retMsg = "";                     //処理結果詳細メッセージ。エラー時に値がセットされる
-            public int page;                      //取得対象ページ番号
-            public int endPage = 0;                   //取得終了ページ番号(継続可能ならインクリメントされて返る。pageと比較して継続判定)
             public MyCommon.WORKERTYPE type;                   //処理種別
-            public Dictionary<string, Image> imgs = null;                    //新規取得したアイコンイメージ
             public string tName = "";                  //Fav追加・削除時のタブ名
-            public List<long> ids = null;               //Fav追加・削除時のID
             public List<long> sIds = null;                  //Fav追加・削除成功分のID
             public bool newDM = false;
             public int addCount;
@@ -273,9 +265,7 @@ namespace OpenTween
         private class GetWorkerArg
         {
             public int page;                      //処理対象ページ番号
-            public int endPage;                   //処理終了ページ番号(起動時の読み込みページ数。通常時はpageと同じ値をセット)
             public MyCommon.WORKERTYPE type;                   //処理種別
-            public string url = "";            //URLをブラウザで開くときのアドレス
             public PostingStatus status = new PostingStatus();          //発言POST時の発言内容
             public List<long> ids;               //Fav追加・削除時のItemIndex
             public List<long> sIds;              //Fav追加・削除成功分のItemIndex
@@ -296,7 +286,7 @@ namespace OpenTween
             public long? inReplyToId = null;
             public string inReplyToName = null;
             public string imageService = "";      //画像投稿サービス名
-            public string imagePath = "";
+            public string[] imagePath = null;
             public PostingStatus()
             {
             }
@@ -317,54 +307,81 @@ namespace OpenTween
             }
         }
 
-        private void TweenMain_Disposed(object sender, EventArgs e)
-        {
-            //後始末
-            SettingDialog.Dispose();
-            SearchDialog.Dispose();
-            fltDialog.Dispose();
-            UrlDialog.Dispose();
-            if (NIconAt != null) NIconAt.Dispose();
-            if (NIconAtRed != null) NIconAtRed.Dispose();
-            if (NIconAtSmoke != null) NIconAtSmoke.Dispose();
-            if (NIconRefresh[0] != null) NIconRefresh[0].Dispose();
-            if (NIconRefresh[1] != null) NIconRefresh[1].Dispose();
-            if (NIconRefresh[2] != null) NIconRefresh[2].Dispose();
-            if (NIconRefresh[3] != null) NIconRefresh[3].Dispose();
-            if (TabIcon != null) TabIcon.Dispose();
-            if (MainIcon != null) MainIcon.Dispose();
-            if (ReplyIcon != null) ReplyIcon.Dispose();
-            if (ReplyIconBlink != null) ReplyIconBlink.Dispose();
-            _listViewImageList.Dispose();
-            _brsHighLight.Dispose();
-            if (_brsBackColorMine != null) _brsBackColorMine.Dispose();
-            if (_brsBackColorAt != null) _brsBackColorAt.Dispose();
-            if (_brsBackColorYou != null) _brsBackColorYou.Dispose();
-            if (_brsBackColorAtYou != null) _brsBackColorAtYou.Dispose();
-            if (_brsBackColorAtFromTarget != null) _brsBackColorAtFromTarget.Dispose();
-            if (_brsBackColorAtTo != null) _brsBackColorAtTo.Dispose();
-            if (_brsBackColorNone != null) _brsBackColorNone.Dispose();
-            if (_brsDeactiveSelection != null) _brsDeactiveSelection.Dispose();
-            //sf.Dispose();
-            sfTab.Dispose();
-            foreach (BackgroundWorker bw in _bw)
-            {
-                if (bw != null)
-                    bw.Dispose();
-            }
-            if (_bwFollower != null)
-            {
-                _bwFollower.Dispose();
-            }
-            this._apiGauge.Dispose();
-            if (IconCache != null)
-            {
-                this.IconCache.CancelAsync();
-                this.IconCache.Dispose();
+        private bool disposed = false;
+
+        /// <summary>
+        /// 使用中のリソースをすべてクリーンアップします。
+        /// </summary>
+        /// <param name="disposing">マネージ リソースが破棄される場合 true、破棄されない場合は false です。</param>
+        protected override void Dispose(bool disposing)
+        {
+            base.Dispose(disposing);
+
+            if (this.disposed)
+                return;
+
+            if (disposing)
+            {
+                if (this.components != null)
+                    this.components.Dispose();
+
+                //後始末
+                SettingDialog.Dispose();
+                SearchDialog.Dispose();
+                fltDialog.Dispose();
+                UrlDialog.Dispose();
+                if (NIconAt != null) NIconAt.Dispose();
+                if (NIconAtRed != null) NIconAtRed.Dispose();
+                if (NIconAtSmoke != null) NIconAtSmoke.Dispose();
+                if (NIconRefresh[0] != null) NIconRefresh[0].Dispose();
+                if (NIconRefresh[1] != null) NIconRefresh[1].Dispose();
+                if (NIconRefresh[2] != null) NIconRefresh[2].Dispose();
+                if (NIconRefresh[3] != null) NIconRefresh[3].Dispose();
+                if (TabIcon != null) TabIcon.Dispose();
+                if (MainIcon != null) MainIcon.Dispose();
+                if (ReplyIcon != null) ReplyIcon.Dispose();
+                if (ReplyIconBlink != null) ReplyIconBlink.Dispose();
+                _listViewImageList.Dispose();
+                _brsHighLight.Dispose();
+                if (_brsBackColorMine != null) _brsBackColorMine.Dispose();
+                if (_brsBackColorAt != null) _brsBackColorAt.Dispose();
+                if (_brsBackColorYou != null) _brsBackColorYou.Dispose();
+                if (_brsBackColorAtYou != null) _brsBackColorAtYou.Dispose();
+                if (_brsBackColorAtFromTarget != null) _brsBackColorAtFromTarget.Dispose();
+                if (_brsBackColorAtTo != null) _brsBackColorAtTo.Dispose();
+                if (_brsBackColorNone != null) _brsBackColorNone.Dispose();
+                if (_brsDeactiveSelection != null) _brsDeactiveSelection.Dispose();
+                //sf.Dispose();
+                sfTab.Dispose();
+                foreach (BackgroundWorker bw in _bw)
+                {
+                    if (bw != null)
+                        bw.Dispose();
+                }
+                if (_bwFollower != null)
+                {
+                    _bwFollower.Dispose();
+                }
+                this._apiGauge.Dispose();
+                if (IconCache != null)
+                {
+                    this.IconCache.CancelAsync();
+                    this.IconCache.Dispose();
+                }
+
+                if (this.thumbnailTokenSource != null)
+                    this.thumbnailTokenSource.Dispose();
+
+                this.itemCacheLock.Dispose();
+                this.tw.Dispose();
+                this._hookGlobalHotkey.Dispose();
             }
+
             // 終了時にRemoveHandlerしておかないとメモリリークする
             // http://msdn.microsoft.com/ja-jp/library/microsoft.win32.systemevents.powermodechanged.aspx
             Microsoft.Win32.SystemEvents.PowerModeChanged -= SystemEvents_PowerModeChanged;
+
+            this.disposed = true;
         }
 
         private void LoadIcon(ref Icon IconInstance, string FileName)
@@ -623,7 +640,7 @@ namespace OpenTween
 
             //Win32Api.SetProxy(HttpConnection.ProxyType.Specified, "127.0.0.1", 8080, "user", "pass")
 
-            SecurityManager = new InternetSecurityManager(PostBrowser);
+            new InternetSecurityManager(PostBrowser);
             this.PostBrowser.AllowWebBrowserDrop = false;  // COMException を回避するため、ActiveX の初期化が終わってから設定する
 
             MyCommon.TwitterApiInfo.AccessLimitUpdated += TwitterApiStatus_AccessLimitUpdated;
@@ -664,7 +681,7 @@ namespace OpenTween
 
             ThumbnailGenerator.InitializeGenerator();
 
-            var imgazyobizinet = ThumbnailGenerator.ImgAzyobuziNetInstance.Value;
+            var imgazyobizinet = ThumbnailGenerator.ImgAzyobuziNetInstance;
             imgazyobizinet.Enabled = this._cfgCommon.EnableImgAzyobuziNet;
             imgazyobizinet.DisabledInDM = this._cfgCommon.ImgAzyobuziNetDisabledInDM;
 
@@ -713,7 +730,30 @@ namespace OpenTween
             sfTab.Alignment = StringAlignment.Center;
             sfTab.LineAlignment = StringAlignment.Center;
 
+            //不正値チェック
+            if (!MyApplication.StartupOptions.ContainsKey("nolimit"))
+            {
+                if (this._cfgCommon.TimelinePeriod < 15 && this._cfgCommon.TimelinePeriod > 0)
+                    this._cfgCommon.TimelinePeriod = 15;
+
+                if (this._cfgCommon.ReplyPeriod < 15 && this._cfgCommon.ReplyPeriod > 0)
+                    this._cfgCommon.ReplyPeriod = 15;
+
+                if (this._cfgCommon.DMPeriod < 15 && this._cfgCommon.DMPeriod > 0)
+                    this._cfgCommon.DMPeriod = 15;
+
+                if (this._cfgCommon.PubSearchPeriod < 30 && this._cfgCommon.PubSearchPeriod > 0)
+                    this._cfgCommon.PubSearchPeriod = 30;
+
+                if (this._cfgCommon.UserTimelinePeriod < 15 && this._cfgCommon.UserTimelinePeriod > 0)
+                    this._cfgCommon.UserTimelinePeriod = 15;
+
+                if (this._cfgCommon.ListsPeriod < 15 && this._cfgCommon.ListsPeriod > 0)
+                    this._cfgCommon.ListsPeriod = 15;
+            }
+
             //設定画面への反映
+            this.SettingDialog.LoadConfig(this._cfgCommon, this._cfgLocal);
             HttpTwitter.TwitterUrl = _cfgCommon.TwitterUrl;
             SettingDialog.TwitterApiUrl = _cfgCommon.TwitterUrl;
 
@@ -723,39 +763,15 @@ namespace OpenTween
 
             SettingDialog.UserAccounts = _cfgCommon.UserAccounts;
 
-            SettingDialog.TimelinePeriodInt = _cfgCommon.TimelinePeriod;
-            SettingDialog.ReplyPeriodInt = _cfgCommon.ReplyPeriod;
-            SettingDialog.DMPeriodInt = _cfgCommon.DMPeriod;
-            SettingDialog.PubSearchPeriodInt = _cfgCommon.PubSearchPeriod;
-            SettingDialog.UserTimelinePeriodInt = _cfgCommon.UserTimelinePeriod;
-            SettingDialog.ListsPeriodInt = _cfgCommon.ListsPeriod;
-            //不正値チェック
-            if (!MyApplication.StartupOptions.ContainsKey("nolimit"))
-            {
-                if (SettingDialog.TimelinePeriodInt < 15 && SettingDialog.TimelinePeriodInt > 0) SettingDialog.TimelinePeriodInt = 15;
-                if (SettingDialog.ReplyPeriodInt < 15 && SettingDialog.ReplyPeriodInt > 0) SettingDialog.ReplyPeriodInt = 15;
-                if (SettingDialog.DMPeriodInt < 15 && SettingDialog.DMPeriodInt > 0) SettingDialog.DMPeriodInt = 15;
-                if (SettingDialog.PubSearchPeriodInt < 30 && SettingDialog.PubSearchPeriodInt > 0) SettingDialog.PubSearchPeriodInt = 30;
-                if (SettingDialog.UserTimelinePeriodInt < 15 && SettingDialog.UserTimelinePeriodInt > 0) SettingDialog.UserTimelinePeriodInt = 15;
-                if (SettingDialog.ListsPeriodInt < 15 && SettingDialog.ListsPeriodInt > 0) SettingDialog.ListsPeriodInt = 15;
-            }
-
-            //起動時読み込み分を既読にするか。trueなら既読として処理
-            SettingDialog.Readed = _cfgCommon.Read;
             //新着取得時のリストスクロールをするか。trueならスクロールしない
             ListLockMenuItem.Checked = _cfgCommon.ListLock;
             this.LockListFileMenuItem.Checked = _cfgCommon.ListLock;
-            SettingDialog.IconSz = _cfgCommon.IconSize;
-            //文末ステータス
-            SettingDialog.Status = _cfgLocal.StatusText;
             //未読管理。trueなら未読管理する
             SettingDialog.UnreadManage = _cfgCommon.UnreadManage;
             //サウンド再生(タブ別設定より優先)
             SettingDialog.PlaySound = _cfgCommon.PlaySound;
             PlaySoundMenuItem.Checked = SettingDialog.PlaySound;
             this.PlaySoundFileMenuItem.Checked = SettingDialog.PlaySound;
-            //片思い表示。trueなら片思い表示する
-            SettingDialog.OneWayLove = _cfgCommon.OneWayLove;
             //フォント&文字色&背景色
             SettingDialog.FontUnread = _fntUnread;
             SettingDialog.ColorUnread = _clUnread;
@@ -780,8 +796,6 @@ namespace OpenTween
             SettingDialog.FontInputFont = _fntInputFont;
 
             SettingDialog.NameBalloon = _cfgCommon.NameBalloon;
-            SettingDialog.PostCtrlEnter = _cfgCommon.PostCtrlEnter;
-            SettingDialog.PostShiftEnter = _cfgCommon.PostShiftEnter;
 
             SettingDialog.CountApi = _cfgCommon.CountApi;
             SettingDialog.CountApiReply = _cfgCommon.CountApiReply;
@@ -790,13 +804,10 @@ namespace OpenTween
 
             SettingDialog.BrowserPath = _cfgLocal.BrowserPath;
             SettingDialog.PostAndGet = _cfgCommon.PostAndGet;
-            SettingDialog.UseRecommendStatus = _cfgLocal.UseRecommendStatus;
             SettingDialog.DispUsername = _cfgCommon.DispUsername;
             SettingDialog.CloseToExit = _cfgCommon.CloseToExit;
             SettingDialog.MinimizeToTray = _cfgCommon.MinimizeToTray;
             SettingDialog.DispLatestPost = _cfgCommon.DispLatestPost;
-            SettingDialog.SortOrderLock = _cfgCommon.SortOrderLock;
-            SettingDialog.ViewTabBottom = _cfgCommon.ViewTabBottom;
             SettingDialog.TinyUrlResolve = _cfgCommon.TinyUrlResolve;
 
             SettingDialog.SelectedProxyType = _cfgLocal.ProxyType;
@@ -805,18 +816,13 @@ namespace OpenTween
             SettingDialog.ProxyUser = _cfgLocal.ProxyUser;
             SettingDialog.ProxyPassword = _cfgLocal.ProxyPassword;
 
-            SettingDialog.StartupVersion = _cfgCommon.StartupVersion;
-            SettingDialog.StartupFollowers = _cfgCommon.StartupFollowers;
             SettingDialog.RestrictFavCheck = _cfgCommon.RestrictFavCheck;
             SettingDialog.AlwaysTop = _cfgCommon.AlwaysTop;
             SettingDialog.UrlConvertAuto = false;
             //SettingDialog.UrlConvertAuto = _cfgCommon.UrlConvertAuto;
 
-            SettingDialog.UseUnreadStyle = _cfgCommon.UseUnreadStyle;
             SettingDialog.DefaultTimeOut = _cfgCommon.DefaultTimeOut;
-            SettingDialog.RetweetNoConfirm = _cfgCommon.RetweetNoConfirm;
             SettingDialog.PlaySound = _cfgCommon.PlaySound;
-            SettingDialog.DateTimeFormat = _cfgCommon.DateTimeFormat;
             SettingDialog.LimitBalloon = _cfgCommon.LimitBalloon;
             SettingDialog.EventNotifyEnabled = _cfgCommon.EventNotifyEnabled;
             SettingDialog.EventNotifyFlag = _cfgCommon.EventNotifyFlag;
@@ -834,15 +840,12 @@ namespace OpenTween
             SettingDialog.TabIconDisp = _cfgCommon.TabIconDisp;
             SettingDialog.ReplyIconState = _cfgCommon.ReplyIconState;
             SettingDialog.ReadOwnPost = _cfgCommon.ReadOwnPost;
-            SettingDialog.GetFav = _cfgCommon.GetFav;
             SettingDialog.ReadOldPosts = _cfgCommon.ReadOldPosts;
             SettingDialog.BitlyUser = _cfgCommon.BilyUser;
             SettingDialog.BitlyPwd = _cfgCommon.BitlyPwd;
-            SettingDialog.ShowGrid = _cfgCommon.ShowGrid;
             SettingDialog.Language = _cfgCommon.Language;
-            SettingDialog.UseAtIdSupplement = _cfgCommon.UseAtIdSupplement;
-            SettingDialog.UseHashSupplement = _cfgCommon.UseHashSupplement;
             SettingDialog.PreviewEnable = _cfgCommon.PreviewEnable;
+            SettingDialog.StatusAreaAtBottom = _cfgCommon.StatusAreaAtBottom;
             AtIdSupl = new AtIdSupplement(SettingAtIdList.Load().AtIdList, "@");
 
             SettingDialog.IsMonospace = _cfgCommon.IsMonospace;
@@ -853,22 +856,6 @@ namespace OpenTween
             //Regex statregex = new Regex("^0*");
             SettingDialog.RecommendStatusText = " [TWNv" + Regex.Replace(MyCommon.FileVersion.Replace(".", ""), "^0*", "") + "]";
 
-            //書式指定文字列エラーチェック
-            try
-            {
-                if (DateTime.Now.ToString(SettingDialog.DateTimeFormat).Length == 0)
-                {
-                    // このブロックは絶対に実行されないはず
-                    // 変換が成功した場合にLengthが0にならない
-                    SettingDialog.DateTimeFormat = "yyyy/MM/dd H:mm:ss";
-                }
-            }
-            catch (FormatException)
-            {
-                // FormatExceptionが発生したら初期値を設定 (=yyyy/MM/dd H:mm:ssとみなされる)
-                SettingDialog.DateTimeFormat = "yyyy/MM/dd H:mm:ss";
-            }
-
             SettingDialog.Nicoms = _cfgCommon.Nicoms;
             SettingDialog.HotkeyEnabled = _cfgCommon.HotkeyEnabled;
             SettingDialog.HotkeyMod = _cfgCommon.HotkeyModifier;
@@ -885,12 +872,9 @@ namespace OpenTween
             SettingDialog.UserTimelineCountApi = _cfgCommon.UserTimelineCountApi;
             SettingDialog.ListCountApi = _cfgCommon.ListCountApi;
 
-            SettingDialog.UserstreamStartup = _cfgCommon.UserstreamStartup;
-            SettingDialog.UserstreamPeriodInt = _cfgCommon.UserstreamPeriod;
             SettingDialog.OpenUserTimeline = _cfgCommon.OpenUserTimeline;
             SettingDialog.ListDoubleClickAction = _cfgCommon.ListDoubleClickAction;
             SettingDialog.UserAppointUrl = _cfgCommon.UserAppointUrl;
-            SettingDialog.HideDuplicatedRetweets = _cfgCommon.HideDuplicatedRetweets;
 
             SettingDialog.EnableImgAzyobuziNet = _cfgCommon.EnableImgAzyobuziNet;
             SettingDialog.ImgAzyobuziNetDisabledInDM = _cfgCommon.ImgAzyobuziNetDisabledInDM;
@@ -898,7 +882,6 @@ namespace OpenTween
             SettingDialog.MapThumbnailHeight = _cfgCommon.MapThumbnailHeight;
             SettingDialog.MapThumbnailWidth = _cfgCommon.MapThumbnailWidth;
             SettingDialog.MapThumbnailZoom = _cfgCommon.MapThumbnailZoom;
-            SettingDialog.IsListStatusesIncludeRts = _cfgCommon.IsListsIncludeRts;
             SettingDialog.TabMouseLock = _cfgCommon.TabMouseLock;
             SettingDialog.IsRemoveSameEvent = _cfgCommon.IsRemoveSameEvent;
             SettingDialog.IsNotifyUseGrowl = _cfgCommon.IsUseNotifyGrowl;
@@ -915,8 +898,10 @@ namespace OpenTween
 
             _initial = true;
 
+            Networking.Initialize();
+
             //アイコンリスト作成
-            this.IconCache = new ImageCache(this.http);
+            this.IconCache = new ImageCache();
 
             bool saveRequired = false;
             bool firstRun = false;
@@ -993,12 +978,10 @@ namespace OpenTween
             }
 
             //Twitter用通信クラス初期化
-            HttpConnection.InitializeConnection(SettingDialog.DefaultTimeOut,
-                                                SettingDialog.SelectedProxyType,
-                                                SettingDialog.ProxyAddress,
-                                                SettingDialog.ProxyPort,
-                                                SettingDialog.ProxyUser,
-                                                SettingDialog.ProxyPassword);
+            Networking.DefaultTimeout = TimeSpan.FromSeconds(this.SettingDialog.DefaultTimeOut);
+            Networking.SetWebProxy(this.SettingDialog.SelectedProxyType,
+                this.SettingDialog.ProxyAddress, this.SettingDialog.ProxyPort,
+                this.SettingDialog.ProxyUser, this.SettingDialog.ProxyPassword);
 
             tw.RestrictFavCheck = SettingDialog.RestrictFavCheck;
             tw.ReadOwnPost = SettingDialog.ReadOwnPost;
@@ -1012,11 +995,7 @@ namespace OpenTween
             AllrepliesToolStripMenuItem.Checked = tw.AllAtReply;
 
             //画像投稿サービス
-            this.CreatePictureServices();
-            SetImageServiceCombo();
-            ImageSelectionPanel.Enabled = false;
-
-            SelectImageServiceComboItem(_cfgCommon.UseImageServiceName, _cfgCommon.UseImageService);
+            ImageSelector.Initialize(tw, SettingDialog.TwitterConfiguration, _cfgCommon.UseImageServiceName, _cfgCommon.UseImageService);
 
             //ウィンドウ設定
             this.ClientSize = _cfgLocal.FormSize;
@@ -1066,6 +1045,9 @@ namespace OpenTween
             // NameLabel のフォントを OTBaseForm.GlobalFont に変更
             this.NameLabel.Font = this.ReplaceToGlobalFont(this.NameLabel.Font);
 
+            // 必要であれば、発言一覧と発言詳細部・入力欄の上下を入れ替える
+            SplitContainer1.IsPanelInverted = !SettingDialog.StatusAreaAtBottom;
+
             //全新着通知のチェック状態により、Reply&DMの新着通知有効無効切り替え(タブ別設定にするため削除予定)
             if (SettingDialog.UnreadManage == false)
             {
@@ -1123,9 +1105,7 @@ namespace OpenTween
             _statuses.SortMode = mode;
             ////////////////////////////////////////////////////////////////////////////////
 
-            ApplyListViewIconSize(SettingDialog.IconSz);
-
-            tw.TinyUrlResolve = SettingDialog.TinyUrlResolve;
+            ApplyListViewIconSize(this._cfgCommon.IconSize);
 
             StatusLabel.Text = Properties.Resources.Form1_LoadText1;       //画面右下の状態表示を変更
             StatusLabelUrl.Text = "";            //画面左下のリンク先URL表示部を初期化
@@ -1189,7 +1169,8 @@ namespace OpenTween
                 {
                     tab.TabType = MyCommon.TabUsageType.UserDefined;
                 }
-                if (!AddNewTab(tab.TabName, true, tab.TabType, tab.ListInfo)) throw new Exception(Properties.Resources.TweenMain_LoadText1);
+                if (!AddNewTab(tab.TabName, true, tab.TabType, tab.ListInfo))
+                    throw new TabException(Properties.Resources.TweenMain_LoadText1);
             }
 
             this.JumpReadOpMenuItem.ShortcutKeyDisplayString = "Space";
@@ -1276,20 +1257,6 @@ namespace OpenTween
             }
         }
 
-        private void CreatePictureServices()
-        {
-            if (this.pictureService != null) this.pictureService.Clear();
-            this.pictureService = null;
-            this.pictureService = new Dictionary<string, IMultimediaShareService> {
-                {"TwitPic", new TwitPic(tw)},
-                {"img.ly", new imgly(tw)},
-                {"yfrog", new yfrog(tw)},
-                {"Twitter", new TwitterPhoto(tw)},
-                {"ついっぷるフォト", new TwipplePhoto(tw)},
-                {"Imgur", new Imgur(tw)},
-            };
-        }
-
         private void ListTab_DrawItem(object sender, DrawItemEventArgs e)
         {
             string txt;
@@ -1325,6 +1292,7 @@ namespace OpenTween
         private void LoadConfig()
         {
             _cfgCommon = SettingCommon.Load();
+            SettingCommon.Instance = this._cfgCommon;
             if (_cfgCommon.UserAccounts == null || _cfgCommon.UserAccounts.Count == 0)
             {
                 _cfgCommon.UserAccounts = new List<UserAccount>();
@@ -1362,13 +1330,13 @@ namespace OpenTween
             }
         }
 
-        private void TimerInterval_Changed(object sender, AppendSettingDialog.IntervalChangedEventArgs e) //Handles SettingDialog.IntervalChanged
+        private void TimerInterval_Changed(object sender, IntervalChangedEventArgs e) //Handles SettingDialog.IntervalChanged
         {
             if (!TimerTimeline.Enabled) return;
             ResetTimers = e;
         }
 
-        private AppendSettingDialog.IntervalChangedEventArgs ResetTimers = new AppendSettingDialog.IntervalChangedEventArgs();
+        private IntervalChangedEventArgs ResetTimers = new IntervalChangedEventArgs();
 
         private static int homeCounter = 0;
         private static int mentionCounter = 0;
@@ -1392,45 +1360,45 @@ namespace OpenTween
             Interlocked.Increment(ref refreshFollowers);
 
             ////タイマー初期化
-            if (ResetTimers.Timeline || homeCounter <= 0 && SettingDialog.TimelinePeriodInt > 0)
+            if (ResetTimers.Timeline || homeCounter <= 0 && this._cfgCommon.TimelinePeriod > 0)
             {
-                Interlocked.Exchange(ref homeCounter, SettingDialog.TimelinePeriodInt);
-                if (!tw.IsUserstreamDataReceived && !ResetTimers.Timeline) GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, 0, "");
+                Interlocked.Exchange(ref homeCounter, this._cfgCommon.TimelinePeriod);
+                if (!tw.IsUserstreamDataReceived && !ResetTimers.Timeline) GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, "");
                 ResetTimers.Timeline = false;
             }
-            if (ResetTimers.Reply || mentionCounter <= 0 && SettingDialog.ReplyPeriodInt > 0)
+            if (ResetTimers.Reply || mentionCounter <= 0 && this._cfgCommon.ReplyPeriod > 0)
             {
-                Interlocked.Exchange(ref mentionCounter, SettingDialog.ReplyPeriodInt);
-                if (!tw.IsUserstreamDataReceived && !ResetTimers.Reply) GetTimeline(MyCommon.WORKERTYPE.Reply, 1, 0, "");
+                Interlocked.Exchange(ref mentionCounter, this._cfgCommon.ReplyPeriod);
+                if (!tw.IsUserstreamDataReceived && !ResetTimers.Reply) GetTimeline(MyCommon.WORKERTYPE.Reply, 1, "");
                 ResetTimers.Reply = false;
             }
-            if (ResetTimers.DirectMessage || dmCounter <= 0 && SettingDialog.DMPeriodInt > 0)
+            if (ResetTimers.DirectMessage || dmCounter <= 0 && this._cfgCommon.DMPeriod > 0)
             {
-                Interlocked.Exchange(ref dmCounter, SettingDialog.DMPeriodInt);
-                if (!tw.IsUserstreamDataReceived && !ResetTimers.DirectMessage) GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, 1, 0, "");
+                Interlocked.Exchange(ref dmCounter, this._cfgCommon.DMPeriod);
+                if (!tw.IsUserstreamDataReceived && !ResetTimers.DirectMessage) GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, 1, "");
                 ResetTimers.DirectMessage = false;
             }
-            if (ResetTimers.PublicSearch || pubSearchCounter <= 0 && SettingDialog.PubSearchPeriodInt > 0)
+            if (ResetTimers.PublicSearch || pubSearchCounter <= 0 && this._cfgCommon.PubSearchPeriod > 0)
             {
-                Interlocked.Exchange(ref pubSearchCounter, SettingDialog.PubSearchPeriodInt);
-                if (!ResetTimers.PublicSearch) GetTimeline(MyCommon.WORKERTYPE.PublicSearch, 1, 0, "");
+                Interlocked.Exchange(ref pubSearchCounter, this._cfgCommon.PubSearchPeriod);
+                if (!ResetTimers.PublicSearch) GetTimeline(MyCommon.WORKERTYPE.PublicSearch, 1, "");
                 ResetTimers.PublicSearch = false;
             }
-            if (ResetTimers.UserTimeline || userTimelineCounter <= 0 && SettingDialog.UserTimelinePeriodInt > 0)
+            if (ResetTimers.UserTimeline || userTimelineCounter <= 0 && this._cfgCommon.UserTimelinePeriod > 0)
             {
-                Interlocked.Exchange(ref userTimelineCounter, SettingDialog.UserTimelinePeriodInt);
-                if (!ResetTimers.UserTimeline) GetTimeline(MyCommon.WORKERTYPE.UserTimeline, 1, 0, "");
+                Interlocked.Exchange(ref userTimelineCounter, this._cfgCommon.UserTimelinePeriod);
+                if (!ResetTimers.UserTimeline) GetTimeline(MyCommon.WORKERTYPE.UserTimeline, 1, "");
                 ResetTimers.UserTimeline = false;
             }
-            if (ResetTimers.Lists || listsCounter <= 0 && SettingDialog.ListsPeriodInt > 0)
+            if (ResetTimers.Lists || listsCounter <= 0 && this._cfgCommon.ListsPeriod > 0)
             {
-                Interlocked.Exchange(ref listsCounter, SettingDialog.ListsPeriodInt);
-                if (!ResetTimers.Lists) GetTimeline(MyCommon.WORKERTYPE.List, 1, 0, "");
+                Interlocked.Exchange(ref listsCounter, this._cfgCommon.ListsPeriod);
+                if (!ResetTimers.Lists) GetTimeline(MyCommon.WORKERTYPE.List, 1, "");
                 ResetTimers.Lists = false;
             }
-            if (ResetTimers.UserStream || usCounter <= 0 && SettingDialog.UserstreamPeriodInt > 0)
+            if (ResetTimers.UserStream || usCounter <= 0 && this._cfgCommon.UserstreamPeriod > 0)
             {
-                Interlocked.Exchange(ref usCounter, SettingDialog.UserstreamPeriodInt);
+                Interlocked.Exchange(ref usCounter, this._cfgCommon.UserstreamPeriod);
                 if (this._isActiveUserstream) RefreshTimeline(true);
                 ResetTimers.UserStream = false;
             }
@@ -1438,9 +1406,8 @@ namespace OpenTween
             {
                 Interlocked.Exchange(ref refreshFollowers, 0);
                 doGetFollowersMenu();
-                GetTimeline(MyCommon.WORKERTYPE.NoRetweetIds, 0, 0, "");
-                GetTimeline(MyCommon.WORKERTYPE.Configuration, 0, 0, "");
-                if (InvokeRequired && !IsDisposed) this.Invoke(new MethodInvoker(this.TrimPostChain));
+                GetTimeline(MyCommon.WORKERTYPE.NoRetweetIds, 0, "");
+                GetTimeline(MyCommon.WORKERTYPE.Configuration, 0, "");
             }
             if (osResumed)
             {
@@ -1449,15 +1416,14 @@ namespace OpenTween
                 {
                     osResumed = false;
                     Interlocked.Exchange(ref ResumeWait, 0);
-                    GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, 0, "");
-                    GetTimeline(MyCommon.WORKERTYPE.Reply, 1, 0, "");
-                    GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, 1, 0, "");
-                    GetTimeline(MyCommon.WORKERTYPE.PublicSearch, 1, 0, "");
-                    GetTimeline(MyCommon.WORKERTYPE.UserTimeline, 1, 0, "");
-                    GetTimeline(MyCommon.WORKERTYPE.List, 1, 0, "");
+                    GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, "");
+                    GetTimeline(MyCommon.WORKERTYPE.Reply, 1, "");
+                    GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, 1, "");
+                    GetTimeline(MyCommon.WORKERTYPE.PublicSearch, 1, "");
+                    GetTimeline(MyCommon.WORKERTYPE.UserTimeline, 1, "");
+                    GetTimeline(MyCommon.WORKERTYPE.List, 1, "");
                     doGetFollowersMenu();
-                    GetTimeline(MyCommon.WORKERTYPE.Configuration, 0, 0, "");
-                    if (InvokeRequired && !IsDisposed) this.Invoke(new MethodInvoker(this.TrimPostChain));
+                    GetTimeline(MyCommon.WORKERTYPE.Configuration, 0, "");
                 }
             }
         }
@@ -1512,8 +1478,8 @@ namespace OpenTween
                                 //アイコン描画不具合あり?
                             }
                             this.SelectListItem(lst,
-                                                _statuses.IndexOf(tab.Text, selId[tab.Text]),
-                                                _statuses.IndexOf(tab.Text, focusedId[tab.Text]));
+                                                tabInfo.IndexOf(selId[tab.Text]),
+                                                tabInfo.IndexOf(focusedId[tab.Text]));
                         }
                     }
                     if (tabInfo.UnreadCount > 0)
@@ -1662,10 +1628,11 @@ namespace OpenTween
             if (MyCommon._endingFlag) return;
             foreach (TabPage tab in ListTab.TabPages)
             {
-                DetailsListView lst = (DetailsListView)tab.Tag;
+                var lst = (DetailsListView)tab.Tag;
+                var tabInfo = _statuses.Tabs[tab.Text];
                 if (lst.SelectedIndices.Count > 0 && lst.SelectedIndices.Count < 61)
                 {
-                    selId.Add(tab.Text, _statuses.GetId(tab.Text, lst.SelectedIndices));
+                    selId.Add(tab.Text, tabInfo.GetId(lst.SelectedIndices));
                 }
                 else
                 {
@@ -1674,9 +1641,9 @@ namespace OpenTween
 
                 var fIds = new long[2];  // 0 = focus, 1 = selection mark
                 var item = lst.FocusedItem;
-                fIds[0] = (item != null) ? _statuses.GetId(tab.Text, item.Index) : -2;
+                fIds[0] = (item != null) ? tabInfo.GetId(item.Index) : -2;
                 var mIdx = lst.SelectionMark;
-                fIds[1] = (mIdx > -1) ? _statuses.GetId(tab.Text, mIdx) : -2;
+                fIds[1] = (mIdx > -1) ? tabInfo.GetId(mIdx) : -2;
                 focusedId.Add(tab.Text, fIds);
             }
 
@@ -1718,7 +1685,7 @@ namespace OpenTween
                     !SettingDialog.LimitBalloon
                     )
                 ) &&
-                !Win32Api.IsScreenSaverRunning())
+                !NativeMethods.IsScreenSaverRunning())
             {
                 return true;
             }
@@ -1935,7 +1902,7 @@ namespace OpenTween
             //mentions新着時に画面ブリンク
             if (!_initial && SettingDialog.BlinkNewMentions && newMentions && Form.ActiveForm == null)
             {
-                Win32Api.FlashMyWindow(this.Handle, Win32Api.FlashSpecification.FlashTray, 3);
+                NativeMethods.FlashMyWindow(this.Handle, NativeMethods.FlashSpecification.FlashTray, 3);
             }
         }
 
@@ -1959,35 +1926,33 @@ namespace OpenTween
 
             if (SettingDialog.UnreadManage) _statuses.SetReadAllTab(true, _curTab.Text, _curItemIndex);
             //キャッシュの書き換え
-            ChangeCacheStyleRead(true, _curItemIndex, _curTab);   //既読へ(フォント、文字色)
+            ChangeCacheStyleRead(true, _curItemIndex);   //既読へ(フォント、文字色)
 
             ColorizeList();
             _colorize = true;
         }
 
-        private void ChangeCacheStyleRead(bool Read, int Index, TabPage Tab)
+        private void ChangeCacheStyleRead(bool Read, int Index)
         {
+            var tabInfo = _statuses.Tabs[_curTab.Text];
             //Read:true=既読 false=未読
             //未読管理していなかったら既読として扱う
-            if (!_statuses.Tabs[_curTab.Text].UnreadManage ||
+            if (!tabInfo.UnreadManage ||
                !SettingDialog.UnreadManage) Read = true;
 
             //対象の特定
             ListViewItem itm = null;
             PostClass post = null;
 
-            if (Tab.Equals(this._curTab))
-            {
-                this.TryGetListViewItemCache(Index, out itm, out post);
-            }
+            this.TryGetListViewItemCache(Index, out itm, out post);
 
             if (itm == null || post == null)
             {
-                itm = ((DetailsListView)Tab.Tag).Items[Index];
-                post = _statuses[Tab.Text, Index];
+                itm = ((DetailsListView)_curTab.Tag).Items[Index];
+                post = tabInfo[Index];
             }
 
-            ChangeItemStyleRead(Read, itm, post, ((DetailsListView)Tab.Tag));
+            ChangeItemStyleRead(Read, itm, post, ((DetailsListView)_curTab.Tag));
         }
 
         private void ChangeItemStyleRead(bool Read, ListViewItem Item, PostClass Post, DetailsListView DList)
@@ -2010,9 +1975,9 @@ namespace OpenTween
                 cl = _clFav;
             else if (Post.RetweetedId != null)
                 cl = _clRetweet;
-            else if (Post.IsOwl && (Post.IsDm || SettingDialog.OneWayLove))
+            else if (Post.IsOwl && (Post.IsDm || this._cfgCommon.OneWayLove))
                 cl = _clOWL;
-            else if (Read || !SettingDialog.UseUnreadStyle)
+            else if (Read || !this._cfgCommon.UseUnreadStyle)
                 cl = _clReaded;
             else
                 cl = _clUnread;
@@ -2020,13 +1985,13 @@ namespace OpenTween
             if (DList == null || Item.Index == -1)
             {
                 Item.ForeColor = cl;
-                if (SettingDialog.UseUnreadStyle)
+                if (this._cfgCommon.UseUnreadStyle)
                     Item.Font = fnt;
             }
             else
             {
                 DList.Update();
-                if (SettingDialog.UseUnreadStyle)
+                if (this._cfgCommon.UseUnreadStyle)
                     DList.ChangeItemFontAndColor(Item.Index, cl, fnt);
                 else
                     DList.ChangeItemForeColor(Item.Index, cl);
@@ -2125,7 +2090,7 @@ namespace OpenTween
         {
             if (StatusText.Text.Trim().Length == 0)
             {
-                if (!ImageSelectionPanel.Enabled)
+                if (!ImageSelector.Enabled)
                 {
                     DoRefresh();
                     return;
@@ -2169,7 +2134,6 @@ namespace OpenTween
             StatusText.SelectionStart = StatusText.Text.Length;
             GetWorkerArg args = new GetWorkerArg();
             args.page = 0;
-            args.endPage = 0;
             args.type = MyCommon.WORKERTYPE.PostMessage;
             CheckReplyTo(StatusText.Text);
 
@@ -2193,12 +2157,12 @@ namespace OpenTween
 
             bool isCutOff = false;
             bool isRemoveFooter = MyCommon.IsKeyDown(Keys.Shift);
-            if (StatusText.Multiline && !SettingDialog.PostCtrlEnter)
+            if (StatusText.Multiline && !this._cfgCommon.PostCtrlEnter)
             {
                 //複数行でEnter投稿の場合、Ctrlも押されていたらフッタ付加しない
                 isRemoveFooter = MyCommon.IsKeyDown(Keys.Control);
             }
-            if (SettingDialog.PostShiftEnter)
+            if (this._cfgCommon.PostShiftEnter)
             {
                 isRemoveFooter = MyCommon.IsKeyDown(Keys.Control);
             }
@@ -2255,12 +2219,12 @@ namespace OpenTween
                 }
                 if (!isRemoveFooter)
                 {
-                    if (SettingDialog.UseRecommendStatus)
+                    if (this._cfgLocal.UseRecommendStatus)
                         // 推奨ステータスを使用する
                         footer += SettingDialog.RecommendStatusText;
                     else
                         // テキストボックスに入力されている文字列を使用する
-                        footer += " " + SettingDialog.Status.Trim();
+                        footer += " " + this._cfgLocal.StatusText.Trim();
                 }
             }
             args.status.status = header + StatusText.Text + footer;
@@ -2305,10 +2269,10 @@ namespace OpenTween
 
             args.status.inReplyToId = _reply_to_id;
             args.status.inReplyToName = _reply_to_name;
-            if (ImageSelectionPanel.Visible)
+            if (ImageSelector.Visible)
             {
                 //画像投稿
-                if (!TryGetSelectedMedia(out args.status.imageService, out args.status.imagePath))
+                if (!ImageSelector.TryGetSelectedMedia(out args.status.imageService, out args.status.imagePath))
                     return;
             }
 
@@ -2403,7 +2367,7 @@ namespace OpenTween
             GetWorkerResult rslt = new GetWorkerResult();
 
             bool read = !SettingDialog.UnreadManage;
-            if (_initial && SettingDialog.UnreadManage) read = SettingDialog.Readed;
+            if (_initial && SettingDialog.UnreadManage) read = this._cfgCommon.Read;
 
             GetWorkerArg args = (GetWorkerArg)e.Argument;
 
@@ -2528,15 +2492,22 @@ namespace OpenTween
 
                 case MyCommon.WORKERTYPE.PostMessage:
                     bw.ReportProgress(200);
-                    if (string.IsNullOrEmpty(args.status.imagePath))
+                    if (args.status.imagePath == null || args.status.imagePath.Length == 0 || string.IsNullOrEmpty(args.status.imagePath[0]))
                     {
                         ret = tw.PostStatus(args.status.status, args.status.inReplyToId);
                     }
                     else
                     {
-                        ret = this.pictureService[args.status.imageService].Upload(ref args.status.imagePath,
-                                                                                   ref args.status.status,
-                                                                                   args.status.inReplyToId);
+                        var service = ImageSelector.GetService(args.status.imageService);
+                        try
+                        {
+                            service.PostStatusAsync(args.status.status, args.status.inReplyToId, args.status.imagePath)
+                                .Wait();
+                        }
+                        catch (AggregateException ex)
+                        {
+                            ret = ex.InnerException.Message;
+                        }
                     }
                     bw.ReportProgress(300);
                     rslt.status = args.status;
@@ -2723,14 +2694,6 @@ namespace OpenTween
             rslt.retMsg = ret;
             rslt.type = args.type;
             rslt.tName = args.tName;
-            if (args.type == MyCommon.WORKERTYPE.DirectMessegeRcv ||
-                args.type == MyCommon.WORKERTYPE.DirectMessegeSnt ||
-                args.type == MyCommon.WORKERTYPE.Reply ||
-                args.type == MyCommon.WORKERTYPE.Timeline ||
-                args.type == MyCommon.WORKERTYPE.Favorites)
-            {
-                rslt.page = args.page - 1;   //値が正しいか後でチェック。10ページ毎の継続確認
-            }
 
             e.Result = rslt;
         }
@@ -2926,7 +2889,7 @@ namespace OpenTween
                     _waitReply = false;
                     if (rslt.newDM && !_initial)
                     {
-                        GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, 1, 0, "");
+                        GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, 1, "");
                     }
                     break;
                 case MyCommon.WORKERTYPE.Favorites:
@@ -2966,7 +2929,7 @@ namespace OpenTween
                                                 {
                                                     post = _statuses[rslt.sIds[i]];
                                                 }
-                                                ChangeCacheStyleRead(post.IsRead, idx, _curTab);
+                                                ChangeCacheStyleRead(post.IsRead, idx);
                                             }
                                             if (idx == _curItemIndex) DispSelectedPost(true); //選択アイテム再表示
                                         }
@@ -3021,7 +2984,6 @@ namespace OpenTween
                         {
                             GetWorkerArg args = new GetWorkerArg();
                             args.page = 0;
-                            args.endPage = 0;
                             args.type = MyCommon.WORKERTYPE.PostMessage;
                             args.status = rslt.status;
                             RunAsync(args);
@@ -3035,7 +2997,7 @@ namespace OpenTween
                             }
                         }
                     }
-                    if (rslt.retMsg.Length == 0 && SettingDialog.PostAndGet)
+                    if (rslt.retMsg.Length == 0 && this._cfgCommon.PostAndGet)
                     {
                         if (_isActiveUserstream)
                         {
@@ -3043,7 +3005,7 @@ namespace OpenTween
                         }
                         else
                         {
-                            GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, 0, "");
+                            GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, "");
                         }
                     }
                     break;
@@ -3059,7 +3021,7 @@ namespace OpenTween
                                 _postTimestamps.RemoveAt(i);
                             }
                         }
-                        if (!_isActiveUserstream && SettingDialog.PostAndGet) GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, 0, "");
+                        if (!_isActiveUserstream && this._cfgCommon.PostAndGet) GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, "");
                     }
                     break;
                 case MyCommon.WORKERTYPE.Follower:
@@ -3073,7 +3035,10 @@ namespace OpenTween
                     //_waitFollower = false
                     if (SettingDialog.TwitterConfiguration.PhotoSizeLimit != 0)
                     {
-                        pictureService["Twitter"].Configuration("MaxUploadFilesize", SettingDialog.TwitterConfiguration.PhotoSizeLimit);
+                        foreach (var service in this.ImageSelector.GetServices())
+                        {
+                            service.UpdateTwitterConfiguration(this.SettingDialog.TwitterConfiguration);
+                        }
                     }
                     this.PurgeListViewItemCache();
                     if (_curList != null) _curList.Refresh();
@@ -3105,6 +3070,23 @@ namespace OpenTween
             }
         }
 
+        private async Task RefreshMuteUserIdsAsync()
+        {
+            this.StatusLabel.Text = Properties.Resources.UpdateMuteUserIds_Start;
+
+            try
+            {
+                await tw.RefreshMuteUserIdsAsync();
+            }
+            catch (WebApiException ex)
+            {
+                this.StatusLabel.Text = string.Format(Properties.Resources.UpdateMuteUserIds_Error, ex.Message);
+                return;
+            }
+
+            this.StatusLabel.Text = Properties.Resources.UpdateMuteUserIds_Finish;
+        }
+
         private void RemovePostFromFavTab(Int64[] ids)
         {
             string favTabName = _statuses.GetTabByType(MyCommon.TabUsageType.Favorites).TabName;
@@ -3173,14 +3155,13 @@ namespace OpenTween
 
         private static Dictionary<MyCommon.WORKERTYPE, DateTime> lastTime = new Dictionary<MyCommon.WORKERTYPE, DateTime>();
 
-        private void GetTimeline(MyCommon.WORKERTYPE WkType, int fromPage, int toPage, string tabName)
+        private void GetTimeline(MyCommon.WORKERTYPE WkType, int fromPage, string tabName)
         {
             if (!this.IsNetworkAvailable()) return;
 
             //非同期実行引数設定
             GetWorkerArg args = new GetWorkerArg();
             args.page = fromPage;
-            args.endPage = toPage;
             args.type = WkType;
             args.tName = tabName;
 
@@ -3393,7 +3374,7 @@ namespace OpenTween
 
         private void MyList_ColumnClick(object sender, ColumnClickEventArgs e)
         {
-            if (SettingDialog.SortOrderLock) return;
+            if (this._cfgCommon.SortOrderLock) return;
             IdComparerClass.ComparerMode mode = IdComparerClass.ComparerMode.Id;
             if (_iconCol)
             {
@@ -3740,7 +3721,7 @@ namespace OpenTween
                 }
                 foreach (int idx in _curList.SelectedIndices)
                 {
-                    ChangeCacheStyleRead(true, idx, _curTab);
+                    ChangeCacheStyleRead(true, idx);
                 }
                 ColorizeList();
             }
@@ -3770,7 +3751,7 @@ namespace OpenTween
                 }
                 foreach (int idx in _curList.SelectedIndices)
                 {
-                    ChangeCacheStyleRead(false, idx, _curTab);
+                    ChangeCacheStyleRead(false, idx);
                 }
                 ColorizeList();
             }
@@ -3799,13 +3780,13 @@ namespace OpenTween
                 switch (_statuses.Tabs[_curTab.Text].TabType)
                 {
                     case MyCommon.TabUsageType.Mentions:
-                        GetTimeline(MyCommon.WORKERTYPE.Reply, 1, 0, "");
+                        GetTimeline(MyCommon.WORKERTYPE.Reply, 1, "");
                         break;
                     case MyCommon.TabUsageType.DirectMessage:
-                        GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, 1, 0, "");
+                        GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, 1, "");
                         break;
                     case MyCommon.TabUsageType.Favorites:
-                        GetTimeline(MyCommon.WORKERTYPE.Favorites, 1, 0, "");
+                        GetTimeline(MyCommon.WORKERTYPE.Favorites, 1, "");
                         break;
                     //case MyCommon.TabUsageType.Profile:
                         //// TODO
@@ -3813,25 +3794,25 @@ namespace OpenTween
                         //// TODO
                         TabClass tb = _statuses.Tabs[_curTab.Text];
                         if (string.IsNullOrEmpty(tb.SearchWords)) return;
-                        GetTimeline(MyCommon.WORKERTYPE.PublicSearch, 1, 0, _curTab.Text);
+                        GetTimeline(MyCommon.WORKERTYPE.PublicSearch, 1, _curTab.Text);
                         break;
                     case MyCommon.TabUsageType.UserTimeline:
-                        GetTimeline(MyCommon.WORKERTYPE.UserTimeline, 1, 0, _curTab.Text);
+                        GetTimeline(MyCommon.WORKERTYPE.UserTimeline, 1, _curTab.Text);
                         break;
                     case MyCommon.TabUsageType.Lists:
                         //// TODO
                         TabClass tab = _statuses.Tabs[_curTab.Text];
                         if (tab.ListInfo == null || tab.ListInfo.Id == 0) return;
-                        GetTimeline(MyCommon.WORKERTYPE.List, 1, 0, _curTab.Text);
+                        GetTimeline(MyCommon.WORKERTYPE.List, 1, _curTab.Text);
                         break;
                     default:
-                        GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, 0, "");
+                        GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, "");
                         break;
                 }
             }
             else
             {
-                GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, 0, "");
+                GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, "");
             }
         }
 
@@ -3843,13 +3824,13 @@ namespace OpenTween
                 switch (_statuses.Tabs[_curTab.Text].TabType)
                 {
                     case MyCommon.TabUsageType.Mentions:
-                        GetTimeline(MyCommon.WORKERTYPE.Reply, -1, 0, "");
+                        GetTimeline(MyCommon.WORKERTYPE.Reply, -1, "");
                         break;
                     case MyCommon.TabUsageType.DirectMessage:
-                        GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, -1, 0, "");
+                        GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, -1, "");
                         break;
                     case MyCommon.TabUsageType.Favorites:
-                        GetTimeline(MyCommon.WORKERTYPE.Favorites, -1, 0, "");
+                        GetTimeline(MyCommon.WORKERTYPE.Favorites, -1, "");
                         break;
                     case MyCommon.TabUsageType.Profile:
                         //// TODO
@@ -3858,25 +3839,25 @@ namespace OpenTween
                         // TODO
                         TabClass tb = _statuses.Tabs[_curTab.Text];
                         if (string.IsNullOrEmpty(tb.SearchWords)) return;
-                        GetTimeline(MyCommon.WORKERTYPE.PublicSearch, -1, 0, _curTab.Text);
+                        GetTimeline(MyCommon.WORKERTYPE.PublicSearch, -1, _curTab.Text);
                         break;
                     case MyCommon.TabUsageType.UserTimeline:
-                        GetTimeline(MyCommon.WORKERTYPE.UserTimeline, -1, 0, _curTab.Text);
+                        GetTimeline(MyCommon.WORKERTYPE.UserTimeline, -1, _curTab.Text);
                         break;
                     case MyCommon.TabUsageType.Lists:
                         //// TODO
                         TabClass tab = _statuses.Tabs[_curTab.Text];
                         if (tab.ListInfo == null || tab.ListInfo.Id == 0) return;
-                        GetTimeline(MyCommon.WORKERTYPE.List, -1, 0, _curTab.Text);
+                        GetTimeline(MyCommon.WORKERTYPE.List, -1, _curTab.Text);
                         break;
                     default:
-                        GetTimeline(MyCommon.WORKERTYPE.Timeline, -1, 0, "");
+                        GetTimeline(MyCommon.WORKERTYPE.Timeline, -1, "");
                         break;
                 }
             }
             else
             {
-                GetTimeline(MyCommon.WORKERTYPE.Timeline, -1, 0, "");
+                GetTimeline(MyCommon.WORKERTYPE.Timeline, -1, "");
             }
         }
 
@@ -3884,7 +3865,6 @@ namespace OpenTween
         {
             DialogResult result;
             string uid = tw.Username.ToLower();
-            var oldIconSz = SettingDialog.IconSz;
 
             try
             {
@@ -3899,7 +3879,10 @@ namespace OpenTween
             {
                 lock (_syncObject)
                 {
-                    tw.TinyUrlResolve = SettingDialog.TinyUrlResolve;
+                    var oldIconSz = this._cfgCommon.IconSize;
+
+                    this.SettingDialog.SaveConfig(this._cfgCommon, this._cfgLocal);
+
                     tw.RestrictFavCheck = SettingDialog.RestrictFavCheck;
                     tw.ReadOwnPost = SettingDialog.ReadOwnPost;
                     ShortUrl.Instance.DisableExpanding = !SettingDialog.TinyUrlResolve;
@@ -3907,13 +3890,12 @@ namespace OpenTween
                     ShortUrl.Instance.BitlyKey = SettingDialog.BitlyPwd;
                     HttpTwitter.TwitterUrl = _cfgCommon.TwitterUrl;
 
-                    HttpConnection.InitializeConnection(SettingDialog.DefaultTimeOut,
-                                                        SettingDialog.SelectedProxyType,
-                                                        SettingDialog.ProxyAddress,
-                                                        SettingDialog.ProxyPort,
-                                                        SettingDialog.ProxyUser,
-                                                        SettingDialog.ProxyPassword);
-                    this.CreatePictureServices();
+                    Networking.DefaultTimeout = TimeSpan.FromSeconds(this.SettingDialog.DefaultTimeOut);
+                    Networking.SetWebProxy(this.SettingDialog.SelectedProxyType,
+                        this.SettingDialog.ProxyAddress, this.SettingDialog.ProxyPort,
+                        this.SettingDialog.ProxyUser, this.SettingDialog.ProxyPassword);
+
+                    ImageSelector.Reset(tw, SettingDialog.TwitterConfiguration);
 
                     try
                     {
@@ -3968,7 +3950,9 @@ namespace OpenTween
                     // タブの表示位置の決定
                     SetTabAlignment();
 
-                    var imgazyobizinet = ThumbnailGenerator.ImgAzyobuziNetInstance.Value;
+                    SplitContainer1.IsPanelInverted = !SettingDialog.StatusAreaAtBottom;
+
+                    var imgazyobizinet = ThumbnailGenerator.ImgAzyobuziNetInstance;
                     imgazyobizinet.Enabled = this.SettingDialog.EnableImgAzyobuziNet;
                     imgazyobizinet.DisabledInDM = this.SettingDialog.ImgAzyobuziNetDisabledInDM;
 
@@ -4067,8 +4051,8 @@ namespace OpenTween
                     {
                         var oldIconCol = _iconCol;
 
-                        if (SettingDialog.IconSz != oldIconSz)
-                            ApplyListViewIconSize(SettingDialog.IconSz);
+                        if (this._cfgCommon.IconSize != oldIconSz)
+                            ApplyListViewIconSize(this._cfgCommon.IconSize);
 
                         foreach (TabPage tp in ListTab.TabPages)
                         {
@@ -4076,7 +4060,7 @@ namespace OpenTween
 
                             using (ControlTransaction.Update(lst))
                             {
-                                lst.GridLines = SettingDialog.ShowGrid;
+                                lst.GridLines = this._cfgCommon.ShowGrid;
                                 lst.Font = _fntReaded;
                                 lst.BackColor = _clListBackcolor;
 
@@ -4114,7 +4098,6 @@ namespace OpenTween
 
                     if (uid != tw.Username) this.doGetFollowersMenu();
 
-                    SetImageServiceCombo();
                     if (SettingDialog.IsNotifyUseGrowl) gh.RegisterGrowl();
                     try
                     {
@@ -4137,7 +4120,28 @@ namespace OpenTween
         /// </summary>
         private void SetTabAlignment()
         {
-            ListTab.Alignment = (SettingDialog.ViewTabBottom ? TabAlignment.Bottom : TabAlignment.Top);
+            var newAlignment = this._cfgCommon.ViewTabBottom ? TabAlignment.Bottom : TabAlignment.Top;
+            if (ListTab.Alignment == newAlignment) return;
+
+            //現在の選択状態を退避
+            Dictionary<string, long[]> selId = new Dictionary<string, long[]>();
+            Dictionary<string, long[]> focusedId = new Dictionary<string, long[]>();
+            SaveSelectedStatus(selId, focusedId);
+
+            ListTab.Alignment = newAlignment;
+
+            //選択状態を復帰
+            foreach (TabPage tab in ListTab.TabPages)
+            {
+                DetailsListView lst = (DetailsListView)tab.Tag;
+                TabClass tabInfo = _statuses.Tabs[tab.Text];
+                using (ControlTransaction.Update(lst))
+                {
+                    this.SelectListItem(lst,
+                                        tabInfo.IndexOf(selId[tab.Text]),
+                                        tabInfo.IndexOf(focusedId[tab.Text]));
+                }
+            }
         }
 
         private void ApplyListViewIconSize(MyCommon.IconSizes iconSz)
@@ -4353,7 +4357,7 @@ namespace OpenTween
             SaveConfigsTabs();
             //検索実行
 
-            GetTimeline(MyCommon.WORKERTYPE.UserTimeline, 1, 0, tabName);
+            GetTimeline(MyCommon.WORKERTYPE.UserTimeline, 1, tabName);
         }
 
         public bool AddNewTab(string tabName, bool startup, MyCommon.TabUsageType tabType, ListElement listInfo = null)
@@ -4532,7 +4536,7 @@ namespace OpenTween
                 _listCustom.Font = _fntReaded;
                 _listCustom.BackColor = _clListBackcolor;
 
-                _listCustom.GridLines = SettingDialog.ShowGrid;
+                _listCustom.GridLines = this._cfgCommon.ShowGrid;
                 _listCustom.AllowDrop = true;
 
                 _listCustom.SmallImageList = _listViewImageList;
@@ -4813,7 +4817,7 @@ namespace OpenTween
         {
             if (e.KeyChar == '@')
             {
-                if (!SettingDialog.UseAtIdSupplement) return;
+                if (!this._cfgCommon.UseAtIdSupplement) return;
                 //@マーク
                 int cnt = AtIdSupl.ItemCount;
                 ShowSuplDialog(StatusText, AtIdSupl);
@@ -4822,7 +4826,7 @@ namespace OpenTween
             }
             else if (e.KeyChar == '#')
             {
-                if (!SettingDialog.UseHashSupplement) return;
+                if (!this._cfgCommon.UseHashSupplement) return;
                 ShowSuplDialog(StatusText, HashSupl);
                 e.Handled = true;
             }
@@ -4947,14 +4951,14 @@ namespace OpenTween
 
             int pLen = 140 - statusText.Length;
             if (this.NotifyIcon1 == null || !this.NotifyIcon1.Visible) return pLen;
-            if ((isAuto && !MyCommon.IsKeyDown(Keys.Control) && SettingDialog.PostShiftEnter) ||
-                (isAuto && !MyCommon.IsKeyDown(Keys.Shift) && !SettingDialog.PostShiftEnter) ||
+            if ((isAuto && !MyCommon.IsKeyDown(Keys.Control) && this._cfgCommon.PostShiftEnter) ||
+                (isAuto && !MyCommon.IsKeyDown(Keys.Shift) && !this._cfgCommon.PostShiftEnter) ||
                 (!isAuto && isAddFooter))
             {
-                if (SettingDialog.UseRecommendStatus)
+                if (this._cfgLocal.UseRecommendStatus)
                     pLen -= SettingDialog.RecommendStatusText.Length;
-                else if (SettingDialog.Status.Length > 0)
-                    pLen -= SettingDialog.Status.Length + 1;
+                else if (this._cfgLocal.StatusText.Length > 0)
+                    pLen -= this._cfgLocal.StatusText.Length + 1;
             }
             if (!string.IsNullOrEmpty(HashMgr.UseHash))
             {
@@ -5013,7 +5017,7 @@ namespace OpenTween
                 //    pLen += m.Result("${url}").Length - SettingDialog.TwitterConfiguration.ShortUrlLength;
                 //}
             }
-            if (ImageSelectionPanel.Visible && ImageSelectedPicture.Tag != null && !string.IsNullOrEmpty(this.ImageService))
+            if (ImageSelector.Visible && !string.IsNullOrEmpty(ImageSelector.ServiceName))
             {
                 pLen -= SettingDialog.TwitterConfiguration.CharactersReservedPerMedia;
             }
@@ -5078,12 +5082,14 @@ namespace OpenTween
             this.itemCacheLock.EnterWriteLock();
             try
             {
+                var tabInfo = _statuses.Tabs[_curTab.Text];
+
                 //キャッシュ要求(要求範囲±30を作成)
                 StartIndex -= 30;
                 if (StartIndex < 0) StartIndex = 0;
                 EndIndex += 30;
-                if (EndIndex >= _statuses.Tabs[_curTab.Text].AllCount) EndIndex = _statuses.Tabs[_curTab.Text].AllCount - 1;
-                _postCache = _statuses[_curTab.Text, StartIndex, EndIndex]; //配列で取得
+                if (EndIndex >= tabInfo.AllCount) EndIndex = tabInfo.AllCount - 1;
+                _postCache = tabInfo[StartIndex, EndIndex]; //配列で取得
                 _itemCacheIndex = StartIndex;
 
                 _itemCache = new ListViewItem[0] {};
@@ -5152,7 +5158,7 @@ namespace OpenTween
                 string[] sitem= {"",
                                  Post.Nickname,
                                  Post.IsDeleted ? "(DELETED)" : Post.TextSingleLine,
-                                 Post.CreatedAt.ToString(SettingDialog.DateTimeFormat),
+                                 Post.CreatedAt.ToString(this._cfgCommon.DateTimeFormat),
                                  Post.ScreenName,
                                  "",
                                  mk.ToString(),
@@ -5164,14 +5170,14 @@ namespace OpenTween
                 string[] sitem = {"",
                                   Post.Nickname,
                                   Post.IsDeleted ? "(DELETED)" : Post.TextSingleLine,
-                                  Post.CreatedAt.ToString(SettingDialog.DateTimeFormat),
+                                  Post.CreatedAt.ToString(this._cfgCommon.DateTimeFormat),
                                   Post.ScreenName + Environment.NewLine + "(RT:" + Post.RetweetedBy + ")",
                                   "",
                                   mk.ToString(),
                                   Post.Source};
                 itm = new ImageListViewItem(sitem, this.IconCache, Post.ImageUrl);
             }
-            itm.StateImageIndex = Post.StateIndex;
+            itm.StateIndex = Post.StateIndex;
 
             bool read = Post.IsRead;
             //未読管理していなかったら既読として扱う
@@ -5235,10 +5241,10 @@ namespace OpenTween
         {
             if (e.State == 0) return;
             e.DrawDefault = false;
+
+            SolidBrush brs2 = null;
             if (!e.Item.Selected)     //e.ItemStateでうまく判定できない???
             {
-                SolidBrush brs2 = null;
-
                 if (e.Item.BackColor == _clSelf)
                     brs2 = _brsBackColorMine;
                 else if (e.Item.BackColor == _clAtSelf)
@@ -5253,18 +5259,17 @@ namespace OpenTween
                     brs2 = _brsBackColorAtTo;
                 else
                     brs2 = _brsBackColorNone;
-
-                e.Graphics.FillRectangle(brs2, e.Bounds);
             }
             else
             {
                 //選択中の行
                 if (((Control)sender).Focused)
-                    e.Graphics.FillRectangle(_brsHighLight, e.Bounds);
+                    brs2 = _brsHighLight;
                 else
-                    e.Graphics.FillRectangle(_brsDeactiveSelection, e.Bounds);
+                    brs2 = _brsDeactiveSelection;
             }
-            if ((e.State & ListViewItemStates.Focused) == ListViewItemStates.Focused) e.DrawFocusRectangle();
+            e.Graphics.FillRectangle(brs2, e.Bounds);
+            e.DrawFocusRectangle();
             this.DrawListViewItemIcon(e);
         }
 
@@ -5277,18 +5282,19 @@ namespace OpenTween
                 //アイコン以外の列
                 RectangleF rct = e.Bounds;
                 rct.Width = e.Header.Width;
+                int fontHeight = e.Item.Font.Height;
                 if (_iconCol)
                 {
-                    rct.Y += e.Item.Font.Height;
-                    rct.Height -= e.Item.Font.Height;
+                    rct.Y += fontHeight;
+                    rct.Height -= fontHeight;
                 }
 
                 int heightDiff;
-                int drawLineCount = Math.Max(1, Math.DivRem((int)rct.Height, e.Item.Font.Height, out heightDiff));
+                int drawLineCount = Math.Max(1, Math.DivRem((int)rct.Height, fontHeight, out heightDiff));
 
-                //if (heightDiff > e.Item.Font.Height * 0.7)
+                //if (heightDiff > fontHeight * 0.7)
                 //{
-                //    rct.Height += e.Item.Font.Height;
+                //    rct.Height += fontHeight;
                 //    drawLineCount += 1;
                 //}
 
@@ -5296,13 +5302,13 @@ namespace OpenTween
                 if (!_iconCol && drawLineCount <= 1)
                 {
                     //rct.Inflate(0, heightDiff / -2);
-                    //rct.Height += e.Item.Font.Height / 2;
+                    //rct.Height += fontHeight / 2;
                 }
-                else if (heightDiff < e.Item.Font.Height * 0.7)
+                else if (heightDiff < fontHeight * 0.7)
                 {
                     //最終行が70%以上欠けていたら、最終行は表示しない
-                    //rct.Height = (float)((e.Item.Font.Height * drawLineCount) + (e.Item.Font.Height / 2));
-                    rct.Height = (e.Item.Font.Height * drawLineCount) - 1;
+                    //rct.Height = (float)((fontHeight * drawLineCount) + (fontHeight / 2));
+                    rct.Height = (fontHeight * drawLineCount) - 1;
                 }
                 else
                 {
@@ -5311,8 +5317,8 @@ namespace OpenTween
 
                 //if (!_iconCol && drawLineCount > 1)
                 //{
-                //    rct.Y += e.Item.Font.Height * 0.2;
-                //    if (heightDiff >= e.Item.Font.Height * 0.8) rct.Height -= e.Item.Font.Height * 0.2;
+                //    rct.Y += fontHeight * 0.2;
+                //    if (heightDiff >= fontHeight * 0.8) rct.Height -= fontHeight * 0.2;
                 //}
 
                 if (rct.Width > 0)
@@ -5323,9 +5329,9 @@ namespace OpenTween
 
                     if (_iconCol)
                     {
-                        RectangleF rctB = e.Bounds;
+                        Rectangle rctB = e.Bounds;
                         rctB.Width = e.Header.Width;
-                        rctB.Height = e.Item.Font.Height;
+                        rctB.Height = fontHeight;
 
                         using (Font fnt = new Font(e.Item.Font, FontStyle.Bold))
                         {
@@ -5341,7 +5347,7 @@ namespace OpenTween
                             TextRenderer.DrawText(e.Graphics,
                                                     e.Item.SubItems[4].Text + " / " + e.Item.SubItems[1].Text + " (" + e.Item.SubItems[3].Text + ") " + e.Item.SubItems[5].Text + e.Item.SubItems[6].Text + " [" + e.Item.SubItems[7].Text + "]",
                                                     fnt,
-                                                    Rectangle.Round(rctB),
+                                                    rctB,
                                                     color,
                                                     TextFormatFlags.SingleLine |
                                                     TextFormatFlags.EndEllipsis |
@@ -5381,16 +5387,22 @@ namespace OpenTween
 
         private void DrawListViewItemIcon(DrawListViewItemEventArgs e)
         {
+            if (_iconSz == 0) return;
+
             ImageListViewItem item = (ImageListViewItem)e.Item;
 
             //e.Bounds.Leftが常に0を指すから自前で計算
             Rectangle itemRect = item.Bounds;
-            itemRect.Width = e.Item.ListView.Columns[0].Width;
+            var col0 = e.Item.ListView.Columns[0];
+            itemRect.Width = col0.Width;
 
-            foreach (ColumnHeader clm in e.Item.ListView.Columns)
+            if (col0.DisplayIndex > 0)
             {
-                if (clm.DisplayIndex < e.Item.ListView.Columns[0].DisplayIndex)
-                    itemRect.X += clm.Width;
+                foreach (ColumnHeader clm in e.Item.ListView.Columns)
+                {
+                    if (clm.DisplayIndex < col0.DisplayIndex)
+                        itemRect.X += clm.Width;
+                }
             }
 
             // ディスプレイの DPI 設定を考慮したアイコンサイズ
@@ -5398,42 +5410,40 @@ namespace OpenTween
             var realStateSize = new SizeF(16 * this.currentScaleFactor.Width, 16 * this.currentScaleFactor.Height).ToSize();
 
             Rectangle iconRect;
-            Rectangle stateRect;
-            if (item.Image != null)
+            var img = item.Image;
+            if (img != null)
             {
                 iconRect = Rectangle.Intersect(new Rectangle(e.Item.GetBounds(ItemBoundsPortion.Icon).Location, realIconSize), itemRect);
                 iconRect.Offset(0, Math.Max(0, (itemRect.Height - realIconSize.Height) / 2));
-                stateRect = Rectangle.Intersect(new Rectangle(new Point(iconRect.X + realIconSize.Width + 2, iconRect.Y), realStateSize), itemRect);
+
+                if (iconRect.Width > 0)
+                {
+                    e.Graphics.FillRectangle(Brushes.White, iconRect);
+                    e.Graphics.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.High;
+                    try
+                    {
+                        e.Graphics.DrawImage(img.Image, iconRect);
+                    }
+                    catch (ArgumentException)
+                    {
+                        item.RefreshImageAsync();
+                    }
+                }
             }
             else
             {
                 iconRect = Rectangle.Intersect(new Rectangle(e.Item.GetBounds(ItemBoundsPortion.Icon).Location, new Size(1, 1)), itemRect);
                 //iconRect.Offset(0, Math.Max(0, (itemRect.Height - realIconSize.Height) / 2));
-                stateRect = Rectangle.Intersect(new Rectangle(new Point(iconRect.X + realIconSize.Width + 2, iconRect.Y), realStateSize), itemRect);
-            }
-
-            var img = item.Image;
-            if (img != null && iconRect.Width > 0)
-            {
-                e.Graphics.FillRectangle(Brushes.White, iconRect);
-                e.Graphics.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.High;
-                try
-                {
-                    e.Graphics.DrawImage(img.Image, iconRect);
-                }
-                catch (ArgumentException)
-                {
-                    item.RefreshImageAsync();
-                }
             }
 
-            if (item.StateImageIndex > -1)
+            if (item.StateIndex > -1)
             {
+                Rectangle stateRect = Rectangle.Intersect(new Rectangle(new Point(iconRect.X + realIconSize.Width + 2, iconRect.Y), realStateSize), itemRect);
                 if (stateRect.Width > 0)
                 {
                     //e.Graphics.FillRectangle(Brushes.White, stateRect);
                     //e.Graphics.InterpolationMode = Drawing2D.InterpolationMode.High;
-                    e.Graphics.DrawImage(this.PostStateImageList.Images[item.StateImageIndex], stateRect);
+                    e.Graphics.DrawImage(this.PostStateImageList.Images[item.StateIndex], stateRect);
                 }
             }
         }
@@ -5754,7 +5764,7 @@ namespace OpenTween
             int idx = -1;
             DetailsListView lst = null;
 
-            if (ImageSelectionPanel.Enabled)
+            if (ImageSelector.Enabled)
                 return;
 
             //現在タブから最終タブまで探索
@@ -5874,12 +5884,10 @@ namespace OpenTween
         /// </summary>
         public async Task<VersionInfo> GetVersionInfoAsync()
         {
-            var http = MyCommon.CreateHttpClient();
-
             var versionInfoUrl = new Uri(ApplicationSettings.VersionInfoUrl + "?" +
                 DateTime.Now.ToString("yyMMddHHmmss") + Environment.TickCount);
 
-            var responseText = await http.GetStringAsync(versionInfoUrl)
+            var responseText = await Networking.Http.GetStringAsync(versionInfoUrl)
                 .ConfigureAwait(false);
 
             // 改行2つで前後パートを分割(前半がバージョン番号など、後半が詳細テキスト)
@@ -6004,7 +6012,7 @@ namespace OpenTween
             DispSelectedPost(false);
         }
 
-        private static PostClass displaypost = new PostClass();
+        private PostClass displayPost = new PostClass();
 
         /// <summary>
         /// サムネイルの表示処理を表すタスク
@@ -6021,10 +6029,12 @@ namespace OpenTween
             if (_curList.SelectedIndices.Count == 0 || _curPost == null)
                 return;
 
-            if (!forceupdate && _curPost.Equals(displaypost))
+            var oldDisplayPost = this.displayPost;
+            this.displayPost = this._curPost;
+
+            if (!forceupdate && this._curPost.Equals(oldDisplayPost))
                 return;
 
-            displaypost = _curPost;
             if (displayItem != null)
             {
                 displayItem.ImageDownloaded -= this.DisplayItemImage_Downloaded;
@@ -6033,134 +6043,125 @@ namespace OpenTween
             displayItem = (ImageListViewItem)_curList.Items[_curList.SelectedIndices[0]];
             displayItem.ImageDownloaded += this.DisplayItemImage_Downloaded;
 
-            string dTxt = createDetailHtml(_curPost.IsDeleted ? "(DELETED)" : _curPost.Text);
-            if (_curPost.IsDm)
-            {
-                SourceLinkLabel.Tag = null;
-                SourceLinkLabel.Text = "";
-            }
-            else
+            using (ControlTransaction.Update(this.TableLayoutPanel1))
             {
-                Match mc = Regex.Match(_curPost.SourceHtml, "<a href=\"(?<sourceurl>.+?)\"");
-                if (mc.Success)
+                var sourceText = "";
+                string sourceUrl = null;
+                if (!_curPost.IsDm)
                 {
-                    string src = mc.Groups["sourceurl"].Value;
-                    SourceLinkLabel.Tag = mc.Groups["sourceurl"].Value;
-                    mc = Regex.Match(src, "^https?://");
-                    if (!mc.Success)
+                    var mc = Regex.Match(_curPost.SourceHtml, "<a href=\"(?<sourceurl>.+?)\"");
+                    if (mc.Success)
                     {
-                        src = src.Insert(0, "https://twitter.com");
+                        var src = mc.Groups["sourceurl"].Value;
+                        if (Regex.IsMatch(src, "^https?://"))
+                            sourceUrl = src;
+                        else
+                            sourceUrl = "https://twitter.com/" + src;
                     }
-                    SourceLinkLabel.Tag = src;
-                }
-                else
-                {
-                    SourceLinkLabel.Tag = null;
+
+                    if (_curPost.Source != null)
+                        sourceText = _curPost.Source;
                 }
-                if (string.IsNullOrEmpty(_curPost.Source))
+                SourceLinkLabel.Text = sourceText;
+                SourceLinkLabel.Tag = sourceUrl;
+                SourceLinkLabel.TabStop = false; // Text を更新すると勝手に true にされる
+
+                string nameText;
+                if (_curPost.IsDm)
                 {
-                    SourceLinkLabel.Text = "";
-                    //SourceLinkLabel.Visible = false;
+                    if (_curPost.IsOwl)
+                        nameText = "DM FROM <- ";
+                    else
+                        nameText = "DM TO -> ";
                 }
                 else
                 {
-                    SourceLinkLabel.Text = _curPost.Source;
-                    //SourceLinkLabel.Visible = true;
+                    nameText = "";
                 }
-            }
-            SourceLinkLabel.TabStop = false;
+                nameText += _curPost.ScreenName + "/" + _curPost.Nickname;
+                if (_curPost.RetweetedId != null)
+                    nameText += " (RT:" + _curPost.RetweetedBy + ")";
 
-            if (_statuses.Tabs[_curTab.Text].TabType == MyCommon.TabUsageType.DirectMessage && !_curPost.IsOwl)
-            {
-                NameLabel.Text = "DM TO -> ";
-            }
-            else if (_statuses.Tabs[_curTab.Text].TabType == MyCommon.TabUsageType.DirectMessage)
-            {
-                NameLabel.Text = "DM FROM <- ";
-            }
-            else
-            {
-                NameLabel.Text = "";
-            }
-            NameLabel.Text += _curPost.ScreenName + "/" + _curPost.Nickname;
-            NameLabel.Tag = _curPost.ScreenName;
-            if (!string.IsNullOrEmpty(_curPost.RetweetedBy))
-            {
-                NameLabel.Text += " (RT:" + _curPost.RetweetedBy + ")";
-            }
+                NameLabel.Text = nameText;
+                NameLabel.Tag = _curPost.ScreenName;
 
-            this.ClearUserPicture();
+                var nameForeColor = SystemColors.ControlText;
+                if (_curPost.IsOwl && (this._cfgCommon.OneWayLove || _curPost.IsDm))
+                    nameForeColor = this._clOWL;
+                if (_curPost.RetweetedId != null)
+                    nameForeColor = this._clRetweet;
+                if (_curPost.IsFav)
+                    nameForeColor = this._clFav;
+                NameLabel.ForeColor = nameForeColor;
 
-            if (!string.IsNullOrEmpty(_curPost.ImageUrl))
-            {
-                var image = IconCache.TryGetFromCache(_curPost.ImageUrl);
-                try
+                this.ClearUserPicture();
+
+                if (!string.IsNullOrEmpty(_curPost.ImageUrl))
                 {
-                    UserPicture.Image = image != null ? image.Clone() : null;
+                    var image = IconCache.TryGetFromCache(_curPost.ImageUrl);
+                    try
+                    {
+                        UserPicture.Image = image != null ? image.Clone() : null;
+                    }
+                    catch (Exception)
+                    {
+                        UserPicture.ShowErrorImage();
+                    }
                 }
-                catch (Exception)
+
+                DateTimeLabel.Text = _curPost.CreatedAt.ToString();
+
+                if (DumpPostClassToolStripMenuItem.Checked)
                 {
-                    UserPicture.ShowErrorImage();
-                }
-            }
+                    StringBuilder sb = new StringBuilder(512);
 
-            NameLabel.ForeColor = System.Drawing.SystemColors.ControlText;
-            DateTimeLabel.Text = _curPost.CreatedAt.ToString();
-            if (_curPost.IsOwl && (SettingDialog.OneWayLove || _statuses.Tabs[_curTab.Text].TabType == MyCommon.TabUsageType.DirectMessage)) NameLabel.ForeColor = _clOWL;
-            if (_curPost.RetweetedId != null) NameLabel.ForeColor = _clRetweet;
-            if (_curPost.IsFav) NameLabel.ForeColor = _clFav;
-
-            if (DumpPostClassToolStripMenuItem.Checked)
-            {
-                StringBuilder sb = new StringBuilder(512);
-
-                sb.Append("-----Start PostClass Dump<br>");
-                sb.AppendFormat("TextFromApi           : {0}<br>", _curPost.TextFromApi);
-                sb.AppendFormat("(PlainText)    : <xmp>{0}</xmp><br>", _curPost.TextFromApi);
-                sb.AppendFormat("StatusId             : {0}<br>", _curPost.StatusId.ToString());
-                //sb.AppendFormat("ImageIndex     : {0}<br>", _curPost.ImageIndex.ToString());
-                sb.AppendFormat("ImageUrl       : {0}<br>", _curPost.ImageUrl);
-                sb.AppendFormat("InReplyToStatusId    : {0}<br>", _curPost.InReplyToStatusId.ToString());
-                sb.AppendFormat("InReplyToUser  : {0}<br>", _curPost.InReplyToUser);
-                sb.AppendFormat("IsDM           : {0}<br>", _curPost.IsDm.ToString());
-                sb.AppendFormat("IsFav          : {0}<br>", _curPost.IsFav.ToString());
-                sb.AppendFormat("IsMark         : {0}<br>", _curPost.IsMark.ToString());
-                sb.AppendFormat("IsMe           : {0}<br>", _curPost.IsMe.ToString());
-                sb.AppendFormat("IsOwl          : {0}<br>", _curPost.IsOwl.ToString());
-                sb.AppendFormat("IsProtect      : {0}<br>", _curPost.IsProtect.ToString());
-                sb.AppendFormat("IsRead         : {0}<br>", _curPost.IsRead.ToString());
-                sb.AppendFormat("IsReply        : {0}<br>", _curPost.IsReply.ToString());
-            
-                foreach (string nm in _curPost.ReplyToList)
-                {
-                    sb.AppendFormat("ReplyToList    : {0}<br>", nm);
-                }
-
-                sb.AppendFormat("ScreenName           : {0}<br>", _curPost.ScreenName);
-                sb.AppendFormat("NickName       : {0}<br>", _curPost.Nickname);
-                sb.AppendFormat("Text   : {0}<br>", _curPost.Text);
-                sb.AppendFormat("(PlainText)    : <xmp>{0}</xmp><br>", _curPost.Text);
-                sb.AppendFormat("CreatedAt          : {0}<br>", _curPost.CreatedAt.ToString());
-                sb.AppendFormat("Source         : {0}<br>", _curPost.Source);
-                sb.AppendFormat("UserId            : {0}<br>", _curPost.UserId);
-                sb.AppendFormat("FilterHit      : {0}<br>", _curPost.FilterHit);
-                sb.AppendFormat("RetweetedBy    : {0}<br>", _curPost.RetweetedBy);
-                sb.AppendFormat("RetweetedId    : {0}<br>", _curPost.RetweetedId);
-                sb.AppendFormat("SearchTabName  : {0}<br>", _curPost.RelTabName);
-                sb.Append("-----End PostClass Dump<br>");
-
-                PostBrowser.Visible = false;
-                PostBrowser.DocumentText = detailHtmlFormatHeader + sb.ToString() + detailHtmlFormatFooter;
-                PostBrowser.Visible = true;
-            }
-            else
-            {
-                try
+                    sb.Append("-----Start PostClass Dump<br>");
+                    sb.AppendFormat("TextFromApi           : {0}<br>", _curPost.TextFromApi);
+                    sb.AppendFormat("(PlainText)    : <xmp>{0}</xmp><br>", _curPost.TextFromApi);
+                    sb.AppendFormat("StatusId             : {0}<br>", _curPost.StatusId.ToString());
+                    //sb.AppendFormat("ImageIndex     : {0}<br>", _curPost.ImageIndex.ToString());
+                    sb.AppendFormat("ImageUrl       : {0}<br>", _curPost.ImageUrl);
+                    sb.AppendFormat("InReplyToStatusId    : {0}<br>", _curPost.InReplyToStatusId.ToString());
+                    sb.AppendFormat("InReplyToUser  : {0}<br>", _curPost.InReplyToUser);
+                    sb.AppendFormat("IsDM           : {0}<br>", _curPost.IsDm.ToString());
+                    sb.AppendFormat("IsFav          : {0}<br>", _curPost.IsFav.ToString());
+                    sb.AppendFormat("IsMark         : {0}<br>", _curPost.IsMark.ToString());
+                    sb.AppendFormat("IsMe           : {0}<br>", _curPost.IsMe.ToString());
+                    sb.AppendFormat("IsOwl          : {0}<br>", _curPost.IsOwl.ToString());
+                    sb.AppendFormat("IsProtect      : {0}<br>", _curPost.IsProtect.ToString());
+                    sb.AppendFormat("IsRead         : {0}<br>", _curPost.IsRead.ToString());
+                    sb.AppendFormat("IsReply        : {0}<br>", _curPost.IsReply.ToString());
+
+                    foreach (string nm in _curPost.ReplyToList)
+                    {
+                        sb.AppendFormat("ReplyToList    : {0}<br>", nm);
+                    }
+
+                    sb.AppendFormat("ScreenName           : {0}<br>", _curPost.ScreenName);
+                    sb.AppendFormat("NickName       : {0}<br>", _curPost.Nickname);
+                    sb.AppendFormat("Text   : {0}<br>", _curPost.Text);
+                    sb.AppendFormat("(PlainText)    : <xmp>{0}</xmp><br>", _curPost.Text);
+                    sb.AppendFormat("CreatedAt          : {0}<br>", _curPost.CreatedAt.ToString());
+                    sb.AppendFormat("Source         : {0}<br>", _curPost.Source);
+                    sb.AppendFormat("UserId            : {0}<br>", _curPost.UserId);
+                    sb.AppendFormat("FilterHit      : {0}<br>", _curPost.FilterHit);
+                    sb.AppendFormat("RetweetedBy    : {0}<br>", _curPost.RetweetedBy);
+                    sb.AppendFormat("RetweetedId    : {0}<br>", _curPost.RetweetedId);
+                    sb.AppendFormat("SearchTabName  : {0}<br>", _curPost.RelTabName);
+                    sb.Append("-----End PostClass Dump<br>");
+
+                    PostBrowser.DocumentText = detailHtmlFormatHeader + sb.ToString() + detailHtmlFormatFooter;
+                }
+                else
                 {
-                    if (PostBrowser.DocumentText != dTxt)
+                    // 同じIDのツイートであれば WebBrowser とサムネイルの更新を行わない
+                    // (同一ツイートの RT は文面が同じであるため同様に更新しない)
+                    if (_curPost.StatusId != oldDisplayPost.StatusId)
                     {
-                        PostBrowser.Visible = false;
-                        PostBrowser.DocumentText = dTxt;
+                        this.PostBrowser.DocumentText =
+                            this.createDetailHtml(_curPost.IsDeleted ? "(DELETED)" : _curPost.Text);
+
+                        this.PostBrowser.Document.Window.ScrollTo(0, 0);
 
                         this.SplitContainer3.Panel2Collapsed = true;
 
@@ -6169,8 +6170,11 @@ namespace OpenTween
                             if (this.thumbnailTokenSource != null)
                             {
                                 var oldTokenSource = this.thumbnailTokenSource;
-                                oldTokenSource.Cancel();
-                                this.thumbnailTask.ContinueWith(_ => oldTokenSource.Dispose());
+
+                                var cancelTask = Task.Run(() => oldTokenSource.Cancel());
+
+                                Task.WhenAll(this.thumbnailTask, cancelTask)
+                                    .ContinueWith(_ => oldTokenSource.Dispose(), TaskScheduler.Default);
                             }
 
                             this.thumbnailTokenSource = new CancellationTokenSource();
@@ -6180,18 +6184,6 @@ namespace OpenTween
                         }
                     }
                 }
-                catch (System.Runtime.InteropServices.COMException)
-                {
-                    //原因不明
-                }
-                catch (UriFormatException)
-                {
-                    PostBrowser.DocumentText = dTxt;
-                }
-                finally
-                {
-                    PostBrowser.Visible = true;
-                }
             }
         }
 
@@ -6320,10 +6312,10 @@ namespace OpenTween
                             DoRefresh();
                             return true;
                         case Keys.F6:
-                            GetTimeline(MyCommon.WORKERTYPE.Reply, 1, 0, "");
+                            GetTimeline(MyCommon.WORKERTYPE.Reply, 1, "");
                             return true;
                         case Keys.F7:
-                            GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, 1, 0, "");
+                            GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, 1, "");
                             return true;
                     }
                     if (Focused != FocusedControl.StatusText)
@@ -6619,10 +6611,10 @@ namespace OpenTween
                             DoRefreshMore();
                             return true;
                         case Keys.F6:
-                            GetTimeline(MyCommon.WORKERTYPE.Reply, -1, 0, "");
+                            GetTimeline(MyCommon.WORKERTYPE.Reply, -1, "");
                             return true;
                         case Keys.F7:
-                            GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, -1, 0, "");
+                            GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, -1, "");
                             return true;
                     }
                     //フォーカスStatusText以外
@@ -7534,35 +7526,78 @@ namespace OpenTween
 
         private void GoBackSelectPostChain()
         {
-            try
+            if (this.selectPostChains.Count > 1)
             {
-                this.selectPostChains.Pop();
-                Tuple<TabPage, PostClass> tabPostPair = this.selectPostChains.Pop();
-                if (!this.ListTab.TabPages.Contains(tabPostPair.Item1)) return;
-                this.ListTab.SelectedTab = tabPostPair.Item1;
-                if (tabPostPair.Item2 != null && this._statuses.Tabs[this._curTab.Text].IndexOf(tabPostPair.Item2.StatusId) > -1)
+                var idx = -1;
+                TabPage tp = null;
+
+                do
                 {
-                    this.SelectListItem(this._curList, this._statuses.Tabs[this._curTab.Text].IndexOf(tabPostPair.Item2.StatusId));
-                    this._curList.EnsureVisible(this._statuses.Tabs[this._curTab.Text].IndexOf(tabPostPair.Item2.StatusId));
+                    try
+                    {
+                        this.selectPostChains.Pop();
+                        var tabPostPair = this.selectPostChains.Peek();
+
+                        if (!this.ListTab.TabPages.Contains(tabPostPair.Item1)) continue;  //該当タブが存在しないので無視
+
+                        if (tabPostPair.Item2 != null)
+                        {
+                            idx = this._statuses.Tabs[tabPostPair.Item1.Text].IndexOf(tabPostPair.Item2.StatusId);
+                            if (idx == -1) continue;  //該当ポストが存在しないので無視
+                        }
+
+                        tp = tabPostPair.Item1;
+
+                        this.selectPostChains.Pop();
+                    }
+                    catch (InvalidOperationException)
+                    {
+                    }
+
+                    break;
                 }
-            }
-            catch (InvalidOperationException)
-            {
+                while (this.selectPostChains.Count > 1);
+
+                if (tp == null)
+                {
+                    //状態がおかしいので処理を中断
+                    //履歴が残り1つであればクリアしておく
+                    if (this.selectPostChains.Count == 1)
+                        this.selectPostChains.Clear();
+                    return;
+                }
+
+                DetailsListView lst = (DetailsListView)tp.Tag;
+                this.ListTab.SelectedTab = tp;
+                if (idx > -1)
+                {
+                    SelectListItem(lst, idx);
+                    lst.EnsureVisible(idx);
+                }
+                lst.Focus();
             }
         }
 
         private void PushSelectPostChain()
         {
-            if (this.selectPostChains.Count == 0 || (this.selectPostChains.Peek().Item1.Text != this._curTab.Text || this._curPost != this.selectPostChains.Peek().Item2))
+            int count = this.selectPostChains.Count;
+            if (count > 0)
             {
-                this.selectPostChains.Push(Tuple.Create(this._curTab, _curPost));
+                var p = this.selectPostChains.Peek();
+                if (p.Item1 == this._curTab)
+                {
+                    if (p.Item2 == this._curPost) return;  //最新の履歴と同一
+                    if (p.Item2 == null) this.selectPostChains.Pop();  //置き換えるため削除
+                }
             }
+            if (count >= 2500) TrimPostChain();
+            this.selectPostChains.Push(Tuple.Create(this._curTab, this._curPost));
         }
 
         private void TrimPostChain()
         {
-            if (this.selectPostChains.Count < 2000) return;
-            Stack<Tuple<TabPage, PostClass>> p = new Stack<Tuple<TabPage, PostClass>>();
+            if (this.selectPostChains.Count <= 2000) return;
+            var p = new Stack<Tuple<TabPage, PostClass>>(2000);
             for (int i = 0; i < 2000; i++)
             {
                 p.Push(this.selectPostChains.Pop());
@@ -7667,7 +7702,7 @@ namespace OpenTween
 
         private void SaveConfigsAtId()
         {
-            if (_ignoreConfigSave || !SettingDialog.UseAtIdSupplement && AtIdSupl == null) return;
+            if (_ignoreConfigSave || !this._cfgCommon.UseAtIdSupplement && AtIdSupl == null) return;
 
             _modifySettingAtId = false;
             SettingAtIdList cfgAtId = new SettingAtIdList(AtIdSupl.GetItemList());
@@ -7687,42 +7722,21 @@ namespace OpenTween
                 _cfgCommon.Token = tw.AccessToken;
                 _cfgCommon.TokenSecret = tw.AccessTokenSecret;
                 _cfgCommon.UserAccounts = SettingDialog.UserAccounts;
-                _cfgCommon.UserstreamStartup = SettingDialog.UserstreamStartup;
-                _cfgCommon.UserstreamPeriod = SettingDialog.UserstreamPeriodInt;
-                _cfgCommon.TimelinePeriod = SettingDialog.TimelinePeriodInt;
-                _cfgCommon.ReplyPeriod = SettingDialog.ReplyPeriodInt;
-                _cfgCommon.DMPeriod = SettingDialog.DMPeriodInt;
-                _cfgCommon.PubSearchPeriod = SettingDialog.PubSearchPeriodInt;
-                _cfgCommon.ListsPeriod = SettingDialog.ListsPeriodInt;
-                _cfgCommon.UserTimelinePeriod = SettingDialog.UserTimelinePeriodInt;
-                _cfgCommon.Read = SettingDialog.Readed;
-                _cfgCommon.IconSize = SettingDialog.IconSz;
                 _cfgCommon.UnreadManage = SettingDialog.UnreadManage;
                 _cfgCommon.PlaySound = SettingDialog.PlaySound;
-                _cfgCommon.OneWayLove = SettingDialog.OneWayLove;
 
                 _cfgCommon.NameBalloon = SettingDialog.NameBalloon;
-                _cfgCommon.PostCtrlEnter = SettingDialog.PostCtrlEnter;
-                _cfgCommon.PostShiftEnter = SettingDialog.PostShiftEnter;
                 _cfgCommon.CountApi = SettingDialog.CountApi;
                 _cfgCommon.CountApiReply = SettingDialog.CountApiReply;
-                _cfgCommon.PostAndGet = SettingDialog.PostAndGet;
                 _cfgCommon.DispUsername = SettingDialog.DispUsername;
                 _cfgCommon.MinimizeToTray = SettingDialog.MinimizeToTray;
                 _cfgCommon.CloseToExit = SettingDialog.CloseToExit;
                 _cfgCommon.DispLatestPost = SettingDialog.DispLatestPost;
-                _cfgCommon.SortOrderLock = SettingDialog.SortOrderLock;
-                _cfgCommon.ViewTabBottom = SettingDialog.ViewTabBottom;
                 _cfgCommon.TinyUrlResolve = SettingDialog.TinyUrlResolve;
-                _cfgCommon.StartupVersion = SettingDialog.StartupVersion;
-                _cfgCommon.StartupFollowers = SettingDialog.StartupFollowers;
                 _cfgCommon.RestrictFavCheck = SettingDialog.RestrictFavCheck;
                 _cfgCommon.AlwaysTop = SettingDialog.AlwaysTop;
                 _cfgCommon.UrlConvertAuto = SettingDialog.UrlConvertAuto;
-                _cfgCommon.UseUnreadStyle = SettingDialog.UseUnreadStyle;
-                _cfgCommon.DateTimeFormat = SettingDialog.DateTimeFormat;
                 _cfgCommon.DefaultTimeOut = SettingDialog.DefaultTimeOut;
-                _cfgCommon.RetweetNoConfirm = SettingDialog.RetweetNoConfirm;
                 _cfgCommon.LimitBalloon = SettingDialog.LimitBalloon;
                 _cfgCommon.EventNotifyEnabled = SettingDialog.EventNotifyEnabled;
                 _cfgCommon.EventNotifyFlag = SettingDialog.EventNotifyFlag;
@@ -7735,7 +7749,6 @@ namespace OpenTween
                 _cfgCommon.TabIconDisp = SettingDialog.TabIconDisp;
                 _cfgCommon.ReplyIconState = SettingDialog.ReplyIconState;
                 _cfgCommon.ReadOwnPost = SettingDialog.ReadOwnPost;
-                _cfgCommon.GetFav = SettingDialog.GetFav;
                 _cfgCommon.IsMonospace = SettingDialog.IsMonospace;
                 if (IdeographicSpaceToSpaceToolStripMenuItem != null &&
                    IdeographicSpaceToSpaceToolStripMenuItem.IsDisposed == false)
@@ -7745,10 +7758,8 @@ namespace OpenTween
                 _cfgCommon.ReadOldPosts = SettingDialog.ReadOldPosts;
                 _cfgCommon.BilyUser = SettingDialog.BitlyUser;
                 _cfgCommon.BitlyPwd = SettingDialog.BitlyPwd;
-                _cfgCommon.ShowGrid = SettingDialog.ShowGrid;
-                _cfgCommon.UseAtIdSupplement = SettingDialog.UseAtIdSupplement;
-                _cfgCommon.UseHashSupplement = SettingDialog.UseHashSupplement;
                 _cfgCommon.PreviewEnable = SettingDialog.PreviewEnable;
+                _cfgCommon.StatusAreaAtBottom = SettingDialog.StatusAreaAtBottom;
                 _cfgCommon.Language = SettingDialog.Language;
 
                 _cfgCommon.SortOrder = (int)_statuses.SortOrder;
@@ -7805,18 +7816,16 @@ namespace OpenTween
                 _cfgCommon.AllAtReply = tw.AllAtReply;
                 _cfgCommon.OpenUserTimeline = SettingDialog.OpenUserTimeline;
                 _cfgCommon.ListCountApi = SettingDialog.ListCountApi;
-                _cfgCommon.UseImageService = ImageServiceCombo.SelectedIndex;
-                _cfgCommon.UseImageServiceName = this.ImageService;
+                _cfgCommon.UseImageService = ImageSelector.ServiceIndex;
+                _cfgCommon.UseImageServiceName = ImageSelector.ServiceName;
                 _cfgCommon.ListDoubleClickAction = SettingDialog.ListDoubleClickAction;
                 _cfgCommon.UserAppointUrl = SettingDialog.UserAppointUrl;
-                _cfgCommon.HideDuplicatedRetweets = SettingDialog.HideDuplicatedRetweets;
                 _cfgCommon.EnableImgAzyobuziNet = SettingDialog.EnableImgAzyobuziNet;
                 _cfgCommon.ImgAzyobuziNetDisabledInDM = SettingDialog.ImgAzyobuziNetDisabledInDM;
                 _cfgCommon.MapThumbnailProvider = SettingDialog.MapThumbnailProvider;
                 _cfgCommon.MapThumbnailHeight = SettingDialog.MapThumbnailHeight;
                 _cfgCommon.MapThumbnailWidth = SettingDialog.MapThumbnailWidth;
                 _cfgCommon.MapThumbnailZoom = SettingDialog.MapThumbnailZoom;
-                _cfgCommon.IsListsIncludeRts = SettingDialog.IsListStatusesIncludeRts;
                 _cfgCommon.TabMouseLock = SettingDialog.TabMouseLock;
                 _cfgCommon.IsRemoveSameEvent = SettingDialog.IsRemoveSameEvent;
                 _cfgCommon.IsUseNotifyGrowl = SettingDialog.IsNotifyUseGrowl;
@@ -7837,7 +7846,6 @@ namespace OpenTween
                 _cfgLocal.PreviewDistance = _mySpDis3;
                 _cfgLocal.StatusMultiline = StatusText.Multiline;
                 _cfgLocal.StatusTextHeight = _mySpDis2;
-                _cfgLocal.StatusText = SettingDialog.Status;
 
                 _cfgLocal.FontUnread = _fntUnread;
                 _cfgLocal.ColorUnread = _clUnread;
@@ -7862,7 +7870,6 @@ namespace OpenTween
                 _cfgLocal.FontInputFont = _fntInputFont;
 
                 _cfgLocal.BrowserPath = SettingDialog.BrowserPath;
-                _cfgLocal.UseRecommendStatus = SettingDialog.UseRecommendStatus;
                 _cfgLocal.ProxyType = SettingDialog.SelectedProxyType;
                 _cfgLocal.ProxyAddress = SettingDialog.ProxyAddress;
                 _cfgLocal.ProxyPort = SettingDialog.ProxyPort;
@@ -7918,7 +7925,7 @@ namespace OpenTween
                 }
                 catch (WebApiException ex)
                 {
-                    var message = ex.InnerException.Message;
+                    var message = ex.Message;
                     MessageBox.Show(this, string.Format(Properties.Resources.OpenURL_LoadFailed, message),
                         Properties.Resources.OpenURL_Caption, MessageBoxButtons.OK, MessageBoxIcon.Error);
                     return;
@@ -8818,7 +8825,7 @@ namespace OpenTween
                     {
                         ListTab.SelectedIndex = ListTab.TabPages.Count - 1;
                         ListTabSelect(ListTab.TabPages[ListTab.TabPages.Count - 1]);
-                        GetTimeline(MyCommon.WORKERTYPE.List, 1, 0, tabName);
+                        GetTimeline(MyCommon.WORKERTYPE.List, 1, tabName);
                     }
                 }
             }
@@ -8865,7 +8872,7 @@ namespace OpenTween
                     bool _NewLine = false;
                     bool _Post = false;
 
-                    if (SettingDialog.PostCtrlEnter) //Ctrl+Enter投稿時
+                    if (this._cfgCommon.PostCtrlEnter) //Ctrl+Enter投稿時
                     {
                         if (StatusText.Multiline)
                         {
@@ -8879,7 +8886,7 @@ namespace OpenTween
                         }
 
                     }
-                    else if (SettingDialog.PostShiftEnter) //SHift+Enter投稿時
+                    else if (this._cfgCommon.PostShiftEnter) //SHift+Enter投稿時
                     {
                         if (StatusText.Multiline)
                         {
@@ -9356,13 +9363,13 @@ namespace OpenTween
             UnreadAtCounter = urat;
 
             slbl.AppendFormat(Properties.Resources.SetStatusLabelText1, tur, tal, ur, al, urat, _postTimestamps.Count, _favTimestamps.Count, _tlCount);
-            if (SettingDialog.TimelinePeriodInt == 0)
+            if (this._cfgCommon.TimelinePeriod == 0)
             {
                 slbl.Append(Properties.Resources.SetStatusLabelText2);
             }
             else
             {
-                slbl.Append(SettingDialog.TimelinePeriodInt.ToString() + Properties.Resources.SetStatusLabelText3);
+                slbl.Append(this._cfgCommon.TimelinePeriod + Properties.Resources.SetStatusLabelText3);
             }
             return slbl.ToString();
         }
@@ -9454,7 +9461,7 @@ namespace OpenTween
             // 本当にリプライ先指定すべきかどうかの判定
             m = Regex.Matches(StatusText, "(^|[ -/:-@[-^`{-~])(?<id>@[a-zA-Z0-9_]+)");
 
-            if (SettingDialog.UseAtIdSupplement)
+            if (this._cfgCommon.UseAtIdSupplement)
             {
                 int bCnt = AtIdSupl.ItemCount;
                 foreach (Match mid in m)
@@ -9721,25 +9728,16 @@ namespace OpenTween
         {
             if (this._curPost == null) return;
 
-            var imageUrl = this._curPost.ImageUrl;
-            try
+            await this.UserPicture.SetImageFromTask(async () =>
             {
-                var image = await this.IconCache.DownloadImageAsync(imageUrl, force: true);
+                var imageUrl = this._curPost.ImageUrl;
 
-                this.ClearUserPicture();
-                this.UserPicture.Image = image.Clone();
-            }
-            catch (Exception)
-            {
-                this.UserPicture.ShowErrorImage();
-                try
-                {
-                    throw;
-                }
-                catch (HttpRequestException) { }
-                catch (InvalidImageException) { }
-                catch (TaskCanceledException) { }
-            }
+                var image = await this.IconCache.DownloadImageAsync(imageUrl, force: true)
+                    .ConfigureAwait(false);
+
+                return await image.CloneAsync()
+                    .ConfigureAwait(false);
+            });
         }
 
         private void SaveOriginalSizeIconPictureToolStripMenuItem_Click(object sender, EventArgs e)
@@ -9928,6 +9926,15 @@ namespace OpenTween
                             var resultUri = await ShortUrl.Instance.ShortenUrlAsync(Converter_Type, srcUri);
                             result = resultUri.ToString();
                         }
+                        catch (HttpRequestException e)
+                        {
+                            // 例外のメッセージが「Response status code does not indicate success: 500 (Internal Server Error).」
+                            // のように長いので「:」が含まれていればそれ以降のみを抽出する
+                            var message = e.Message.Split(new[] { ':' }, count: 2).Last();
+
+                            this.StatusLabel.Text = Converter_Type + ":" + message;
+                            continue;
+                        }
                         catch (WebApiException e)
                         {
                             this.StatusLabel.Text = Converter_Type + ":" + e.Message;
@@ -10742,7 +10749,7 @@ namespace OpenTween
             MenuItemUserStream.Enabled = true;
             StopToolStripMenuItem.Text = "&Start";
             StopToolStripMenuItem.Enabled = true;
-            if (SettingDialog.UserstreamStartup) tw.StartUserStream();
+            if (this._cfgCommon.UserstreamStartup) tw.StartUserStream();
         }
 
         private async void TweenMain_Shown(object sender, EventArgs e)
@@ -10760,31 +10767,32 @@ namespace OpenTween
 
             if (this.IsNetworkAvailable())
             {
-                GetTimeline(MyCommon.WORKERTYPE.BlockIds, 0, 0, "");
-                GetTimeline(MyCommon.WORKERTYPE.NoRetweetIds, 0, 0, "");
-                if (SettingDialog.StartupFollowers)
+                this.RefreshMuteUserIdsAsync();
+                GetTimeline(MyCommon.WORKERTYPE.BlockIds, 0, "");
+                GetTimeline(MyCommon.WORKERTYPE.NoRetweetIds, 0, "");
+                if (this._cfgCommon.StartupFollowers)
                 {
-                    GetTimeline(MyCommon.WORKERTYPE.Follower, 0, 0, "");
+                    GetTimeline(MyCommon.WORKERTYPE.Follower, 0, "");
                 }
-                GetTimeline(MyCommon.WORKERTYPE.Configuration, 0, 0, "");
+                GetTimeline(MyCommon.WORKERTYPE.Configuration, 0, "");
                 StartUserStream();
                 _waitTimeline = true;
-                GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, 1, "");
+                GetTimeline(MyCommon.WORKERTYPE.Timeline, 1, "");
                 _waitReply = true;
-                GetTimeline(MyCommon.WORKERTYPE.Reply, 1, 1, "");
+                GetTimeline(MyCommon.WORKERTYPE.Reply, 1, "");
                 _waitDm = true;
-                GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, 1, 1, "");
-                if (SettingDialog.GetFav)
+                GetTimeline(MyCommon.WORKERTYPE.DirectMessegeRcv, 1, "");
+                if (this._cfgCommon.GetFav)
                 {
                     _waitFav = true;
-                    GetTimeline(MyCommon.WORKERTYPE.Favorites, 1, 1, "");
+                    GetTimeline(MyCommon.WORKERTYPE.Favorites, 1, "");
                 }
                 _waitPubSearch = true;
-                GetTimeline(MyCommon.WORKERTYPE.PublicSearch, 1, 0, "");  //tabname="":全タブ
+                GetTimeline(MyCommon.WORKERTYPE.PublicSearch, 1, "");  //tabname="":全タブ
                 _waitUserTimeline = true;
-                GetTimeline(MyCommon.WORKERTYPE.UserTimeline, 1, 0, "");  //tabname="":全タブ
+                GetTimeline(MyCommon.WORKERTYPE.UserTimeline, 1, "");  //tabname="":全タブ
                 _waitLists = true;
-                GetTimeline(MyCommon.WORKERTYPE.List, 1, 0, "");  //tabname="":全タブ
+                GetTimeline(MyCommon.WORKERTYPE.List, 1, "");  //tabname="":全タブ
 
                 var i = 0;
                 while (this.IsInitialRead())
@@ -10803,7 +10811,7 @@ namespace OpenTween
                 if (ApplicationSettings.VersionInfoUrl != null)
                 {
                     //バージョンチェック(引数:起動時チェックの場合はtrue・・・チェック結果のメッセージを表示しない)
-                    if (SettingDialog.StartupVersion)
+                    if (this._cfgCommon.StartupVersion)
                         await this.CheckNewVersion(true);
                 }
                 else
@@ -10815,16 +10823,16 @@ namespace OpenTween
                 }
 
                 // 取得失敗の場合は再試行する
-                if (!tw.GetFollowersSuccess && SettingDialog.StartupFollowers)
-                    GetTimeline(MyCommon.WORKERTYPE.Follower, 0, 0, "");
+                if (!tw.GetFollowersSuccess && this._cfgCommon.StartupFollowers)
+                    GetTimeline(MyCommon.WORKERTYPE.Follower, 0, "");
 
                 // 取得失敗の場合は再試行する
                 if (!tw.GetNoRetweetSuccess)
-                    GetTimeline(MyCommon.WORKERTYPE.NoRetweetIds, 0, 0, "");
+                    GetTimeline(MyCommon.WORKERTYPE.NoRetweetIds, 0, "");
 
                 // 取得失敗の場合は再試行する
                 if (SettingDialog.TwitterConfiguration.PhotoSizeLimit == 0)
-                    GetTimeline(MyCommon.WORKERTYPE.Configuration, 0, 0, "");
+                    GetTimeline(MyCommon.WORKERTYPE.Configuration, 0, "");
 
                 // 権限チェック read/write権限(xAuthで取得したトークン)の場合は再認証を促す
                 if (MyCommon.TwitterApiInfo.AccessLevel == TwitterApiAccessLevel.ReadWrite)
@@ -10847,7 +10855,7 @@ namespace OpenTween
 
         private void doGetFollowersMenu()
         {
-            GetTimeline(MyCommon.WORKERTYPE.Follower, 1, 0, "");
+            GetTimeline(MyCommon.WORKERTYPE.Follower, 1, "");
             DispSelectedPost(true);
         }
 
@@ -10923,7 +10931,7 @@ namespace OpenTween
                         _DoFavRetweetFlags = false;
                         return;
                     }
-                    if (!SettingDialog.RetweetNoConfirm)
+                    if (!this._cfgCommon.RetweetNoConfirm)
                     {
                         string Questiontext = Properties.Resources.RetweetQuestion1;
                         if (_DoFavRetweetFlags) Questiontext = Properties.Resources.FavoritesRetweetQuestionText2;
@@ -11225,7 +11233,6 @@ namespace OpenTween
                 public string id = "";
                 public bool isFollowing = false;
                 public bool isFollowed = false;
-                public bool isError = false;
                 public FriendshipInfo(string id)
                 {
                     this.id = id;
@@ -11244,7 +11251,6 @@ namespace OpenTween
                 if (!string.IsNullOrEmpty(rt))
                 {
                     if (string.IsNullOrEmpty(result)) result = rt;
-                    fInfo.isError = true;
                 }
             }
             e.Result = result;
@@ -11507,7 +11513,6 @@ namespace OpenTween
             TabClass tb = _statuses.Tabs[tbName];
             ComboBox cmb = (ComboBox)pnl.Controls["comboSearch"];
             ComboBox cmbLang = (ComboBox)pnl.Controls["comboLang"];
-            ComboBox cmbusline = (ComboBox)pnl.Controls["comboUserline"];
             cmb.Text = cmb.Text.Trim();
             // 検索式演算子 OR についてのみ大文字しか認識しないので強制的に大文字とする
             bool Quote = false;
@@ -11559,7 +11564,7 @@ namespace OpenTween
                 SaveConfigsTabs();   //検索条件の保存
             }
 
-            GetTimeline(MyCommon.WORKERTYPE.PublicSearch, 1, 0, tbName);
+            GetTimeline(MyCommon.WORKERTYPE.PublicSearch, 1, tbName);
             ((DetailsListView)ListTab.SelectedTab.Tag).Focus();
         }
 
@@ -11749,7 +11754,7 @@ namespace OpenTween
             Match m = Regex.Match(this._postBrowserStatusText, @"^https?://twitter.com/search\?q=%23(?<hash>.+)$");
             if (m.Success)
             {
-                HashMgr.SetPermanentHash("#" + m.Result("${hash}"));
+                HashMgr.SetPermanentHash("#" + Uri.UnescapeDataString(m.Result("${hash}")));
                 HashStripSplitButton.Text = HashMgr.UseHash;
                 HashToggleMenuItem.Checked = true;
                 HashToggleToolStripMenuItem.Checked = true;
@@ -12015,7 +12020,7 @@ namespace OpenTween
         {
             public Twitter tw;
             public string id;
-            public TwitterDataModel.User user;
+            public TwitterUser user;
         }
 
         private void GetUserInfo_DoWork(object sender, DoWorkEventArgs e)
@@ -12026,7 +12031,7 @@ namespace OpenTween
 
         private void doShowUserStatus(string id, bool ShowInputDialog)
         {
-            TwitterDataModel.User user = null;
+            TwitterUser user = null;
             GetUserInfoArgs args = new GetUserInfoArgs();
             if (ShowInputDialog)
             {
@@ -12081,15 +12086,18 @@ namespace OpenTween
             }
         }
 
-        private void doShowUserStatus(TwitterDataModel.User user)
+        private async void doShowUserStatus(TwitterUser user)
         {
-            using (ShowUserInfo userinfo = new ShowUserInfo())
+            using (var userDialog = new UserInfoDialog(this, this.tw))
             {
-                userinfo.Owner = this;
-                userinfo.User = user;
-                userinfo.ShowDialog(this);
+                var showUserTask = userDialog.ShowUserAsync(user);
+                userDialog.ShowDialog(this);
+
                 this.Activate();
                 this.BringToFront();
+
+                // ユーザー情報の表示が完了するまで userDialog を破棄しない
+                await showUserTask;
             }
         }
 
@@ -12219,7 +12227,6 @@ namespace OpenTween
         private HookGlobalHotkey _hookGlobalHotkey;
         public TweenMain()
         {
-            this.http = MyCommon.CreateHttpClient();
             _hookGlobalHotkey = new HookGlobalHotkey(this);
 
             // この呼び出しは、Windows フォーム デザイナで必要です。
@@ -12233,12 +12240,16 @@ namespace OpenTween
             this.gh.NotifyClicked += GrowlHelper_Callback;
 
             // メイリオフォント指定時にタブの最小幅が広くなる問題の対策
-            this.ListTab.HandleCreated += (s, e) => Win32Api.SetMinTabWidth((TabControl)s, 40);
+            this.ListTab.HandleCreated += (s, e) => NativeMethods.SetMinTabWidth((TabControl)s, 40);
 
             this._apiGauge = new ToolStripAPIGauge();
             this._apiGauge.BorderSides = ToolStripStatusLabelBorderSides.Right;
             this.StatusStrip1.Items.Insert(2, this._apiGauge);
 
+            this.ImageSelector.Visible = false;
+            this.ImageSelector.Enabled = false;
+            this.ImageSelector.FilePickDialog = OpenFileDialog1;
+
             this.ReplaceAppName();
         }
 
@@ -12295,60 +12306,19 @@ namespace OpenTween
 #region "画像投稿"
         private void ImageSelectMenuItem_Click(object sender, EventArgs e)
         {
-            if (ImageSelectionPanel.Visible)
-            {
-                CloseImageSelectionPanel();
-            }
+            if (ImageSelector.Visible)
+                ImageSelector.EndSelection();
             else
-            {
-                OpenImageSelectionPanel();
-                ImageFromSelectedFile(true);
-                ImagefilePathText.Focus();
-            }
-        }
-
-        private void OpenImageSelectionPanel()
-        {
-            ImageSelectionPanel.Visible = true;
-            ImageSelectionPanel.Enabled = true;
-            TimelinePanel.Visible = false;
-            TimelinePanel.Enabled = false;
-        }
-
-        private void CloseImageSelectionPanel()
-        {
-            ImagefilePathText.CausesValidation = false;
-            TimelinePanel.Visible = true;
-            TimelinePanel.Enabled = true;
-            ImageSelectionPanel.Visible = false;
-            ImageSelectionPanel.Enabled = false;
-            ((DetailsListView)ListTab.SelectedTab.Tag).Focus();
-            ClearImageSelectedPicture(false);
-            ImagefilePathText.CausesValidation = true;
+                ImageSelector.BeginSelection();
         }
 
         private void SelectMedia_DragEnter(DragEventArgs e)
         {
-            string filename = ((string[])e.Data.GetData(DataFormats.FileDrop, false))[0];
-            FileInfo fl = new FileInfo(filename);
-            string ext = fl.Extension;
-
-            if (!string.IsNullOrEmpty(this.ImageService) &&
-                this.pictureService[this.ImageService].CheckValidFilesize(ext, fl.Length))
+            if (ImageSelector.HasUploadableService(((string[])e.Data.GetData(DataFormats.FileDrop, false))[0], true))
             {
                 e.Effect = DragDropEffects.Copy;
                 return;
             }
-            foreach (string svc in ImageServiceCombo.Items)
-            {
-                if (!string.IsNullOrEmpty(svc) &&
-                    this.pictureService[svc].CheckValidFilesize(ext, fl.Length))
-                {
-                    //ImageServiceCombo.SelectedItem = svc;
-                    e.Effect = DragDropEffects.Copy;
-                    return;
-                }
-            }
             e.Effect = DragDropEffects.None;
         }
 
@@ -12361,308 +12331,46 @@ namespace OpenTween
         {
             this.Activate();
             this.BringToFront();
-            OpenImageSelectionPanel();
-            ImagefilePathText.Text = ((string[])e.Data.GetData(DataFormats.FileDrop, false))[0];
-            ImageFromSelectedFile(false);
+            ImageSelector.BeginSelection(((string[])e.Data.GetData(DataFormats.FileDrop, false))[0]);
             StatusText.Focus();
         }
 
-        private void FilePickButton_Click(object sender, EventArgs e)
+        private void ImageSelector_BeginSelecting(object sender, EventArgs e)
         {
-            if (string.IsNullOrEmpty(this.ImageService)) return;
-            OpenFileDialog1.Filter = this.pictureService[this.ImageService].GetFileOpenDialogFilter();
-            OpenFileDialog1.Title = Properties.Resources.PickPictureDialog1;
-            OpenFileDialog1.FileName = "";
-
-            try
-            {
-                this.AllowDrop = false;
-                if (OpenFileDialog1.ShowDialog() == DialogResult.Cancel) return;
-            }
-            finally
-            {
-                this.AllowDrop = true;
-            }
-
-            ImagefilePathText.Text = OpenFileDialog1.FileName;
-            ImageFromSelectedFile(false);
-        }
-
-        private void ImagefilePathText_Validating(object sender, CancelEventArgs e)
-        {
-            if (ImageCancelButton.Focused)
-            {
-                ImagefilePathText.CausesValidation = false;
-                return;
-            }
-
-            ImageFromSelectedFile(false);
-        }
-
-        private void ImageFromSelectedFile(bool suppressMsgBox)
-        {
-            try
-            {
-                ClearImageSelectedPicture(true);
-
-                ImagefilePathText.Text = ImagefilePathText.Text.Trim();
-                if (string.IsNullOrEmpty(ImagefilePathText.Text) || string.IsNullOrEmpty(this.ImageService))
-                {
-                    ImagefilePathText.Text = "";
-                    return;
-                }
-
-                FileInfo fl = new FileInfo(ImagefilePathText.Text);
-                string ext = fl.Extension;
-                var imageService = this.pictureService[this.ImageService];
-
-                if (!imageService.CheckValidExtension(ext))
-                {
-                    //画像以外の形式
-                    ImagefilePathText.Text = "";
-                    if (!suppressMsgBox)
-                    {
-                        MessageBox.Show(
-                            string.Format(Properties.Resources.PostPictureWarn3, this.ImageService, MakeAvailableServiceText(ext, fl.Length), ext),
-                            Properties.Resources.PostPictureWarn4,
-                            MessageBoxButtons.OK,
-                            MessageBoxIcon.Warning);
-                    }
-                    return;
-                }
-
-                if (!imageService.CheckValidFilesize(ext, fl.Length))
-                {
-                    // ファイルサイズが大きすぎる
-                    ImagefilePathText.Text = "";
-                    if (!suppressMsgBox)
-                    {
-                        MessageBox.Show(
-                            string.Format(Properties.Resources.PostPictureWarn5, this.ImageService, MakeAvailableServiceText(ext, fl.Length)),
-                            Properties.Resources.PostPictureWarn4,
-                            MessageBoxButtons.OK,
-                            MessageBoxIcon.Warning);
-                    }
-                    return;
-                }
-
-                switch (imageService.GetFileType(ext))
-                {
-                    case MyCommon.UploadFileType.Invalid:
-                        ImagefilePathText.Text = "";
-                        break;
-                    case MyCommon.UploadFileType.Picture:
-                        Image img = null;
-                        using (FileStream fs = new FileStream(ImagefilePathText.Text, FileMode.Open, FileAccess.Read))
-                        {
-                            img = Image.FromStream(fs);
-                        }
-                        ImageSelectedPicture.Image = (new HttpVarious()).CheckValidImage(
-                                    img,
-                                    img.Width,
-                                    img.Height);
-                        ImageSelectedPicture.Tag = MyCommon.UploadFileType.Picture;
-                        break;
-                    case MyCommon.UploadFileType.MultiMedia:
-                        ImageSelectedPicture.Image = Properties.Resources.MultiMediaImage;
-                        ImageSelectedPicture.Tag = MyCommon.UploadFileType.MultiMedia;
-                        break;
-                    default:
-                        ImagefilePathText.Text = "";
-                        break;
-                }
-            }
-            catch (FileNotFoundException)
-            {
-                ClearImageSelectedPicture(true);
-                ImagefilePathText.Text = "";
-                if (!suppressMsgBox) MessageBox.Show("File not found.");
-            }
-            catch (Exception)
-            {
-                ClearImageSelectedPicture(true);
-                ImagefilePathText.Text = "";
-                if (!suppressMsgBox) MessageBox.Show("The type of this file is not image.");
-            }
-        }
-
-        private string MakeAvailableServiceText(string ext, long fileSize)
-        {
-            StringBuilder sb = new StringBuilder();
-
-            foreach (string svc in ImageServiceCombo.Items)
-            {
-                if (!string.IsNullOrEmpty(svc) &&
-                    this.pictureService[svc].CheckValidFilesize(ext, fileSize))
-                {
-                    if (sb.Length > 0) sb.Append(", ");
-                    sb.Append(svc);
-                }
-            }
-            if (sb.Length == 0)
-                return Properties.Resources.PostPictureWarn6;
-
-            return sb.ToString();
-        }
-
-        private void ClearImageSelectedPicture(bool invalidate)
-        {
-            Image oldImage = null;
-            if (this.ImageSelectedPicture.Image != null)
-            {
-                if (this.ImageSelectedPicture.Image != ImageSelectedPicture.InitialImage &&
-                    this.ImageSelectedPicture.Image != Properties.Resources.MultiMediaImage)
-                {
-                    oldImage = this.ImageSelectedPicture.Image;
-                }
-            }
-            if (invalidate)
-            {
-                this.ImageSelectedPicture.Image = ImageSelectedPicture.InitialImage;
-                this.ImageSelectedPicture.Tag = MyCommon.UploadFileType.Invalid;
-            }
-            else
-            {
-                this.ImageSelectedPicture.Image = null;
-                this.ImageSelectedPicture.Tag = null;
-            }
-            if (oldImage != null) oldImage.Dispose();
-        }
-
-        private void ImageCancelButton_Click(object sender, EventArgs e)
-        {
-            CloseImageSelectionPanel();
-        }
-
-        private void ImageSelection_KeyDown(object sender, KeyEventArgs e)
-        {
-            if (e.KeyCode == Keys.Escape)
-            {
-                CloseImageSelectionPanel();
-            }
-        }
-
-        private void ImageSelection_KeyPress(object sender, KeyPressEventArgs e)
-        {
-            if (Convert.ToInt32(e.KeyChar) == 0x1B)
-            {
-                ImagefilePathText.CausesValidation = false;
-                e.Handled = true;
-            }
-        }
-
-        private void ImageSelection_PreviewKeyDown(object sender, PreviewKeyDownEventArgs e)
-        {
-            if (e.KeyCode == Keys.Escape)
-            {
-                ImagefilePathText.CausesValidation = false;
-            }
+            TimelinePanel.Visible = false;
+            TimelinePanel.Enabled = false;
         }
 
-        private bool TryGetSelectedMedia(out string imageService, out string imagePath)
+        private void ImageSelector_EndSelecting(object sender, EventArgs e)
         {
-            if (ImageSelectedPicture.Image != ImageSelectedPicture.InitialImage &&
-                ImageServiceCombo.SelectedIndex > -1 &&
-                !string.IsNullOrEmpty(ImagefilePathText.Text))
-            {
-                if (MessageBox.Show(string.Format(Properties.Resources.PostPictureConfirm1, this.ImageService),
-                                   Properties.Resources.PostPictureConfirm2,
-                                   MessageBoxButtons.OKCancel,
-                                   MessageBoxIcon.Question,
-                                   MessageBoxDefaultButton.Button1)
-                               == DialogResult.OK)
-                {
-                    imageService = ImageServiceCombo.Text;
-                    imagePath = ImagefilePathText.Text;
-                    CloseImageSelectionPanel();
-                    ImagefilePathText.Text = "";
-                    return true;
-                }
-            }
-            else
-            {
-                MessageBox.Show(Properties.Resources.PostPictureWarn1, Properties.Resources.PostPictureWarn2);
-            }
-
-            CloseImageSelectionPanel();
-            imageService = null;
-            imagePath = null;
-            return false;
+            TimelinePanel.Visible = true;
+            TimelinePanel.Enabled = true;
+            ((DetailsListView)ListTab.SelectedTab.Tag).Focus();
         }
 
-        private void SetImageServiceCombo()
+        private void ImageSelector_FilePickDialogOpening(object sender, EventArgs e)
         {
-            string svc = "";
-            if (ImageServiceCombo.SelectedIndex > -1) svc = ImageServiceCombo.SelectedItem.ToString();
-            ImageServiceCombo.Items.Clear();
-            
-            // Add service names to combobox
-            foreach (var key in pictureService.Keys)
-            {
-                ImageServiceCombo.Items.Add(key);
-            }
-
-            SelectImageServiceComboItem(svc);
+            this.AllowDrop = false;
         }
 
-        private void SelectImageServiceComboItem(string svc, int? index = null)
+        private void ImageSelector_FilePickDialogClosed(object sender, EventArgs e)
         {
-            int idx;
-            if (string.IsNullOrEmpty(svc))
-            {
-                idx = index ?? 0;
-            }
-            else
-            {
-                idx = ImageServiceCombo.Items.IndexOf(svc);
-                if (idx == -1) idx = index ?? 0;
-            }
-
-            try
-            {
-                ImageServiceCombo.SelectedIndex = idx;
-            }
-            catch (ArgumentOutOfRangeException)
-            {
-                ImageServiceCombo.SelectedIndex = 0;
-            }
-        }
-
-        private string ImageService
-        {
-            get { return ImageServiceCombo.SelectedItem.ToString(); }
+            this.AllowDrop = true;
         }
 
-        private void ImageServiceCombo_SelectedIndexChanged(object sender, EventArgs e)
+        private void ImageSelector_SelectedServiceChanged(object sender, EventArgs e)
         {
-            if (ImageSelectedPicture.Tag != null && !string.IsNullOrEmpty(this.ImageService))
+            if (ImageSelector.Visible)
             {
-                try
-                {
-                    FileInfo fi = new FileInfo(ImagefilePathText.Text.Trim());
-                    string ext = fi.Extension;
-                    var imageService = this.pictureService[this.ImageService];
-                    if (!imageService.CheckValidFilesize(ext, fi.Length))
-                    {
-                        ClearImageSelectedPicture(true);
-                        ImagefilePathText.Text = "";
-                    }
-                }
-                catch (Exception)
-                {
-                    ClearImageSelectedPicture(true);
-                    ImagefilePathText.Text = "";
-                }
                 _modifySettingCommon = true;
                 SaveConfigsAll(true);
-                if (this.ImageService == "Twitter")
-                {
+
+                if (ImageSelector.ServiceName.Equals("Twitter"))
                     this.StatusText_TextChanged(null, null);
-                }
             }
         }
 
-        private void ImageSelectionPanel_VisibleChanged(object sender, EventArgs e)
+        private void ImageSelector_VisibleChanged(object sender, EventArgs e)
         {
             this.StatusText_TextChanged(null, null);
         }
@@ -12801,7 +12509,7 @@ namespace OpenTween
                 }
             }
 
-            this.GetTimeline(MyCommon.WORKERTYPE.Related, 1, 1, tabName);
+            this.GetTimeline(MyCommon.WORKERTYPE.Related, 1, tabName);
         }
 
         private void CacheInfoMenuItem_Click(object sender, EventArgs e)
@@ -12822,7 +12530,7 @@ namespace OpenTween
 #region "Userstream"
         private bool _isActiveUserstream = false;
 
-        private void tw_PostDeleted(long id)
+        private void tw_PostDeleted(object sender, PostDeletedEventArgs e)
         {
             try
             {
@@ -12830,12 +12538,12 @@ namespace OpenTween
                 {
                     Invoke((Action) (() =>
                            {
-                               _statuses.RemovePostReserve(id);
-                               if (_curTab != null && _statuses.Tabs[_curTab.Text].Contains(id))
+                               _statuses.RemovePostReserve(e.StatusId);
+                               if (_curTab != null && _statuses.Tabs[_curTab.Text].Contains(e.StatusId))
                                {
                                    this.PurgeListViewItemCache();
                                    ((DetailsListView)_curTab.Tag).Update();
-                                   if (_curPost != null && _curPost.StatusId == id) DispSelectedPost(true);
+                                   if (_curPost != null && _curPost.StatusId == e.StatusId) DispSelectedPost(true);
                                }
                            }));
                     return;
@@ -12851,7 +12559,7 @@ namespace OpenTween
             }
         }
 
-        private void tw_NewPostFromStream()
+        private void tw_NewPostFromStream(object sender, EventArgs e)
         {
             if (SettingDialog.ReadOldPosts)
             {
@@ -12891,7 +12599,7 @@ namespace OpenTween
                 //before = Now;
             }
 
-            if (SettingDialog.UserstreamPeriodInt > 0) return;
+            if (this._cfgCommon.UserstreamPeriod > 0) return;
 
             try
             {
@@ -12911,14 +12619,14 @@ namespace OpenTween
             }
         }
 
-        private void tw_UserStreamStarted()
+        private void tw_UserStreamStarted(object sender, EventArgs e)
         {
             this._isActiveUserstream = true;
             try
             {
                 if (InvokeRequired && !IsDisposed)
                 {
-                    Invoke(new MethodInvoker(tw_UserStreamStarted));
+                    Invoke((Action)(() => this.tw_UserStreamStarted(sender, e)));
                     return;
                 }
             }
@@ -12939,14 +12647,14 @@ namespace OpenTween
             StatusLabel.Text = "UserStream Started.";
         }
 
-        private void tw_UserStreamStopped()
+        private void tw_UserStreamStopped(object sender, EventArgs e)
         {
             this._isActiveUserstream = false;
             try
             {
                 if (InvokeRequired && !IsDisposed)
                 {
-                    Invoke(new MethodInvoker(tw_UserStreamStopped));
+                    Invoke((Action)(() => this.tw_UserStreamStopped(sender, e)));
                     return;
                 }
             }
@@ -12967,13 +12675,13 @@ namespace OpenTween
             StatusLabel.Text = "UserStream Stopped.";
         }
 
-        private void tw_UserStreamEventArrived(Twitter.FormattedEvent ev)
+        private void tw_UserStreamEventArrived(object sender, UserStreamEventReceivedEventArgs e)
         {
             try
             {
                 if (InvokeRequired && !IsDisposed)
                 {
-                    Invoke(new Action<Twitter.FormattedEvent>(tw_UserStreamEventArrived), ev);
+                    Invoke((Action)(() => this.tw_UserStreamEventArrived(sender, e)));
                     return;
                 }
             }
@@ -12985,6 +12693,7 @@ namespace OpenTween
             {
                 return;
             }
+            var ev = e.EventData;
             StatusLabel.Text = "Event: " + ev.Event;
             //if (ev.Event == "favorite")
             //{
@@ -13200,14 +12909,14 @@ namespace OpenTween
             if (string.IsNullOrEmpty(str))
                 return;
 
-            var bing = new Bing(this.http);
+            var bing = new Bing();
             try
             {
                 var translatedText = await bing.TranslateAsync(str,
                     langFrom: null,
                     langTo: this.SettingDialog.TranslateLanguage);
 
-                this.PostBrowser.DocumentText = translatedText;
+                this.PostBrowser.DocumentText = this.createDetailHtml(translatedText);
             }
             catch (HttpRequestException e)
             {
@@ -13459,13 +13168,13 @@ namespace OpenTween
 
         private void ContextMenuColumnHeader_Opening(object sender, CancelEventArgs e)
         {
-            this.IconSizeNoneToolStripMenuItem.Checked = SettingDialog.IconSz == MyCommon.IconSizes.IconNone;
-            this.IconSize16ToolStripMenuItem.Checked = SettingDialog.IconSz == MyCommon.IconSizes.Icon16;
-            this.IconSize24ToolStripMenuItem.Checked = SettingDialog.IconSz == MyCommon.IconSizes.Icon24;
-            this.IconSize48ToolStripMenuItem.Checked = SettingDialog.IconSz == MyCommon.IconSizes.Icon48;
-            this.IconSize48_2ToolStripMenuItem.Checked = SettingDialog.IconSz == MyCommon.IconSizes.Icon48_2;
+            this.IconSizeNoneToolStripMenuItem.Checked = this._cfgCommon.IconSize == MyCommon.IconSizes.IconNone;
+            this.IconSize16ToolStripMenuItem.Checked = this._cfgCommon.IconSize == MyCommon.IconSizes.Icon16;
+            this.IconSize24ToolStripMenuItem.Checked = this._cfgCommon.IconSize == MyCommon.IconSizes.Icon24;
+            this.IconSize48ToolStripMenuItem.Checked = this._cfgCommon.IconSize == MyCommon.IconSizes.Icon48;
+            this.IconSize48_2ToolStripMenuItem.Checked = this._cfgCommon.IconSize == MyCommon.IconSizes.Icon48_2;
 
-            this.LockListSortOrderToolStripMenuItem.Checked = SettingDialog.SortOrderLock;
+            this.LockListSortOrderToolStripMenuItem.Checked = this._cfgCommon.SortOrderLock;
         }
 
         private void IconSizeNoneToolStripMenuItem_Click(object sender, EventArgs e)
@@ -13495,11 +13204,11 @@ namespace OpenTween
 
         private void ChangeListViewIconSize(MyCommon.IconSizes iconSize)
         {
-            if (SettingDialog.IconSz == iconSize) return;
+            if (this._cfgCommon.IconSize == iconSize) return;
 
             var oldIconCol = _iconCol;
 
-            SettingDialog.IconSz = iconSize;
+            this._cfgCommon.IconSize = iconSize;
             ApplyListViewIconSize(iconSize);
 
             if (_iconCol != oldIconCol)
@@ -13518,9 +13227,9 @@ namespace OpenTween
         private void LockListSortToolStripMenuItem_Click(object sender, EventArgs e)
         {
             var state = this.LockListSortOrderToolStripMenuItem.Checked;
-            if (SettingDialog.SortOrderLock == state) return;
+            if (this._cfgCommon.SortOrderLock == state) return;
 
-            SettingDialog.SortOrderLock = state;
+            this._cfgCommon.SortOrderLock = state;
 
             _modifySettingCommon = true;
         }