OSDN Git Service

1つのSsParserインスタンスで複数の処理が出来るように変更。
[winbottle/winbottle.git] / bottleclient / MainForm.pas
index b00fa73..68a94cc 100755 (executable)
@@ -12,14 +12,15 @@ uses
   Menus, StdCtrls, ComCtrls, BRegExp, BottleDef, BottleSstp,
   DirectSstp, IdBaseComponent, IdComponent, IdTCPConnection, IdTCPClient,
   IdSLPP20, SsParser, ImgList, AppEvnts, TaskTray, StdActns,
-  ActnList, MPlayer, MenuBar, ToolWin,
-  IniFiles, ExtCtrls, ShellAPI, Contnrs,
+  ActnList, MPlayer, MenuBar, ToolWin, SsPlayTime, heClasses, heFountain,
+  SakuraScriptFountain, HEditor,
+  IniFiles, ShellAPI, Contnrs,
   ConstEditor, Buttons, Clipbrd, HeadValue, Logs, MultipleChoiceEditor,
   IdException, HttpThread, IdHTTP, LogDownload,
   ScriptConsts, DateUtils, BottleChainRule, BottleChainEvent,
-  SakuraSeekerInstance, HEditor, HTSearch, heClasses, heFountain,
-  SakuraScriptFountain, SppList, SurfacePreview, XDOM_2_3_J3, SsPlayTime,
-  RegexUtils, StrReplace, StrReplaceDialog, ReplacePresetEditor;
+  SakuraSeekerInstance, HTSearch,
+  SppList, SurfacePreview, XDOM_2_3_J3,
+  RegexUtils, StrReplace, StrReplaceDialog, ReplacePresetEditor, ExtCtrls;
 
 type
   TSurfacePreviewType = (spHint, spEditor);
@@ -407,6 +408,7 @@ function Token(const Str: String; const Delimiter: char;
   const Index: integer): String;
 
 function StringReplaceEx(const Before: String; List: THeadValue): String;
+procedure OpenBrowser(const Url: String);
 
 implementation
 
@@ -433,6 +435,18 @@ begin
   end;
 end;
 
+// \83u\83\89\83E\83U\82ÅURL\82ð\8aJ\82­\8f\88\97\9d
+procedure OpenBrowser(const Url: String);
+begin
+  if Pref.BrowserExeName='' then
+    begin
+      ShellExecute(HWND(nil), 'open', PChar(Url), nil, nil, SW_SHOW);
+    end else
+    begin
+      ShellExecute(HWND(nil), 'open', PChar(Pref.BrowserExeName), PChar(Url), nil, SW_SHOW);
+    end;
+end;
+
 // \95\8e\9a\97ñ\82ð\92u\82«\8a·\82¦\82é\83\86\81[\83e\83B\83\8a\83e\83B\8aÖ\90\94
 function StringReplaceEx(const Before: String; List: THeadValue): String;
 var
@@ -466,6 +480,7 @@ begin
   end;
 end;
 
+
 {TfrmSender}
 
 procedure TfrmSender.actConfirmExecute(Sender: TObject);
@@ -663,7 +678,7 @@ begin
     actStart.Enabled := true;
     actStop.Enabled := true;
     actSend.Enabled := true;
-    frmLog.lvwLogChange(Self, nil, ctState);
+    frmLog.lvwLogClick(Self);
     mnGetNewId.Enabled := Pref.LUID = '';
     Screen.Cursor := crDefault;
   end;
@@ -710,6 +725,12 @@ begin
     Exit;
   end;
 
+  if Length(Talk) < Pref.MinScriptLength then
+  begin
+    MessageDlg('\8dÅ\8f¬\91\97\90M\83o\83C\83g\90\94\88È\89º\82Å\82·\81B', mtError, [mbOk], 0);
+    Exit;
+  end;
+
   if not Pref.NoConfirm then begin
     if not SendConfirmDialog(FNowChannel, cbxTargetGhost.Text) then Exit;
   end;
@@ -755,6 +776,13 @@ begin
     IdSlpp20.Host := Pref.ProxyAddress;
     IdSlpp20.Port := Pref.ProxyPort;
     IdSlpp20.ProxyMode := true;
+    if Pref.ProxyNeedAuthentication then begin
+      IdSlpp20.ProxyUser := Pref.ProxyUser;
+      IdSlpp20.ProxyPass := Pref.ProxyPass;
+    end else begin
+      IdSlpp20.ProxyUser := '';
+      IdSlpp20.ProxyPass := '';
+    end;
   end else begin
     IdSlpp20.Host := Pref.BottleServer;
     IdSlpp20.Port := Pref.BottleServerPort;
@@ -797,7 +825,8 @@ begin
     try
       HeadValue := THeadValue.Create(Str);
     except
-      ShowMessage('SSTP Bottle\83T\81[\83o\82ª\89ð\90Í\82Å\82«\82È\82¢\83G\83\89\81[\82ð\95Ô\82µ\82Ü\82µ\82½\81B');
+      Beep;
+      frmMessageBox.ShowMessage('SSTP Bottle\83T\81[\83o\82ª\89ð\90Í\82Å\82«\82È\82¢\83G\83\89\81[\82ð\95Ô\82µ\82Ü\82µ\82½\81B');
       Exit;
     end;
     Command := HeadValue['Command'];
@@ -805,11 +834,11 @@ begin
     if ResStr = 'Err' then begin
       if HeadValue['ExtraMessage'] <> '' then begin
         Beep;
-        ShowMessage('SSTP Bottle\83T\81[\83o\82ª\8e\9f\82Ì\83G\83\89\81[\82ð\95Ô\82µ\82Ü\82µ\82½:'#13#10 +
+        frmMessageBox.ShowMessage('SSTP Bottle\83T\81[\83o\82ª\8e\9f\82Ì\83G\83\89\81[\82ð\95Ô\82µ\82Ü\82µ\82½:'#13#10 +
                      HeadValue['ExtraMessage']);
       end else begin
         Beep;
-        ShowMessage('SSTP Bottle\83T\81[\83o\82ª\89½\82ç\82©\82Ì\83G\83\89\81[\82ð\95Ô\82µ\82Ü\82µ\82½\81B');
+        frmMessageBox.ShowMessage('SSTP Bottle\83T\81[\83o\82ª\89½\82ç\82©\82Ì\83G\83\89\81[\82ð\95Ô\82µ\82Ü\82µ\82½\81B'#13#10 + '\81i\83R\83}\83\93\83h\81u' + Command + '\81v\82ð\8f\88\97\9d\92\86\81j');
       end;
     end;
     if (Command = 'sendBroadcast') and (ResStr = 'OK') then begin
@@ -882,7 +911,7 @@ begin
     if (Command = 'setChannels') then begin
       if ResStr <> 'OK' then begin
         Beep;
-        ShowMessage('\83`\83\83\83\93\83l\83\8b\90Ý\92è\82É\8e¸\94s\82µ\82Ü\82µ\82½\81B\82à\82¤\88ê\93x\93o\98^\82µ\82È\82¨\82µ\82Ä\82­\82¾\82³\82¢');
+        frmMessageBox.ShowMessage('\83`\83\83\83\93\83l\83\8b\90Ý\92è\82É\8e¸\94s\82µ\82Ü\82µ\82½\81B\82à\82¤\88ê\93x\93o\98^\82µ\82È\82¨\82µ\82Ä\82­\82¾\82³\82¢');
         ShowHintLabel('\83`\83\83\83\93\83l\83\8b\90Ý\92è\82É\8e¸\94s\82µ\82Ü\82µ\82½', WarningColor);
       end;
     end;
@@ -911,11 +940,8 @@ end;
 procedure TfrmSender.actStopExecute(Sender: TObject);
 begin
   // \8b­\90§\8dÄ\90Ú\91±\82ð\8ds\82¤
-  IdSlpp20.OnDisconnect := nil;
-  if IdSlpp20.Connected then IdSlpp20.Disconnect;
-  FAutoAddAfterGetChannel := true;
-  BeginConnect;
-  IdSlpp20.OnDisconnect := Slpp20Disconnect;
+  FBeginConnectFailCount := 0; // \8e©\93®\8dÄ\90Ú\91±\83J\83E\83\93\83^\83\8a\83Z\83b\83g
+  RetryBeginConnect;
 end;
 
 procedure TfrmSender.FormShow(Sender: TObject);
@@ -924,24 +950,32 @@ begin
   //LUID\82ª\8eæ\93¾\82³\82ê\82Ä\82¢\82ê\82Î\91\81\91¬\93o\98^\81B\82»\82¤\82Å\82È\82¯\82ê\82ÎLUID\8eæ\93¾\81B
   if Pref.LUID <> '' then BeginConnect
   else mnGetNewIdClick(Self);
+
   FAutoAddAfterGetChannel := Pref.AutoStart;
   FBooted := true;
+
   frmLog.Show;
   frmSurfacePreview.Show;
   Self.Show;
+
+  //\83G\83f\83B\83^\83v\83\8c\83r\83\85\81[\82ª\91O\89ñ\95\\8e¦\8fó\91Ô\82È\82ç\82±\82±\82Å\95\\8e¦\82·\82é
+  if Pref.ShowEditorPreviewWindow then actEditorPreviewExecute(Sender);
+
   SakuraSeeker.BeginDetect;
   SakuraSeekerDetectResultChanged(self);
-  if SakuraSeeker.Count = 0 then
+  if (SakuraSeeker.Count = 0) and not Pref.NoWarnOfEmptyFMO then
     frmMessageBox.ShowMessage('\83S\81[\83X\83g(SSTP\83T\81[\83o)\82ª1\82Â\82à\8bN\93®\82µ\82Ä\82¢\82Ü\82¹\82ñ\81B'#13#10 +
       'SSTP Bottle\82ð\97\98\97p\82·\82é\82½\82ß\82É\82Í\81A\83S\81[\83X\83g\82ð\93¯\8e\9e\82É\8bN\93®\82µ\82Ä\82­\82¾\82³\82¢\81B'#13#10 +
       '\8fÚ\8d×\82Í\83w\83\8b\83v\82ð\82²\97\97\89º\82³\82¢\81B');
 end;
 
 procedure TfrmSender.actAboutClick(Sender: TObject);
-var Str: String;
+var
+  Str: String;
 begin
   Str := VersionString + #13#10 + BottleDisclaimer + #13#10#13#10;
-  Str := Str + Format('Compiler Version: %f', [CompilerVersion]);
+  Str := Str + Format('Compiler Version: %f', [CompilerVersion]) + #13#10;
+  Str := Str + 'Indy Version: ' + IdSLPP20.Version;
   frmMessageBox.ShowMessage(Str);
 end;
 
@@ -1122,10 +1156,21 @@ begin
   BuildMenu(mnPopConst, Simple);
   BuildMenu(mnPopUpConst.Items, Simple);
   BuildMenu(ConstBarMenu.Items, Simple);
-  //ConstMenuBar.Menu := nil;
-  ConstMenuBar.AutoSize := false;
-  ConstMenuBar.Width := 1000;
+
+  {$IFDEF CONDITIONALEXPRESSIONS}
+    {$IF Declared(CompilerVersion)}
+      {$IF CompilerVersion < 15.0} // Delphi6\88È\89º\82È\82ç
+        // \83\81\83j\83\85\81[\82ð\88ê\93x\8fÁ\82·
+        // \82È\82º\82©2\89ñ\96Ú\88È\8d~\82Ì\95\\8e¦\82ª\82¨\82©\82µ\82­\82È\82é\96â\91è\82Ì\8fC\90³
+        // ported from YasagureClient
+        ConstMenuBar.AutoSize := false;
+        ConstMenuBar.Menu := nil;
+      {$IFEND}
+    {$IFEND}
+  {$ENDIF}
+  
   ConstMenuBar.Menu := ConstBarMenu;
+  ConstMenuBar.Width := 1000;
   ConstMenuBar.AutoSize := true;
 end;
 
@@ -1241,7 +1286,8 @@ begin
                 Url[UrlCount] := SsParser.GetParam(SsParser[i], UrlCount*2+2);
                 UrlName[UrlCount] := SsParser.GetParam(SsParser[i], UrlCount*2+3);
                 if UrlName[UrlCount] = '' then UrlName[UrlCount] := Url[UrlCount];
-                if Pos('http://', Url[UrlCount]) > 0 then Inc(UrlCount);
+                //https\82È\82Ç\82ª\92Ç\89Á\82³\82ê\82é\8e\9e\91Î\8dô\81c\81c://\82ð\8c\9f\8dõ\82·\82ê\82Î\82½\82Ô\82ñ\91å\8fä\95v
+                if Pos('://', Url[UrlCount]) > 0 then Inc(UrlCount);
               end;
             end;
             if UrlCount > 0 then UrlCancel := SsParser.GetParam(SsParser[i], 1);
@@ -1252,7 +1298,8 @@ begin
             Url[0] := SsParser.GetParam(SsParser[i], 1);
             UrlName[0] := '\8ds\82­\81@\81@\81@\81@\81@\81@';
             UrlCancel  := '\8ds\82©\82È\82¢\81@\81@\81@\81@';
-            if Pos('http://', Url[0]) > 0 then begin
+            //https\82È\82Ç\82ª\92Ç\89Á\82³\82ê\82é\8e\9e\91Î\8dô\81c\81c://\82ð\8c\9f\8dõ\82·\82ê\82Î\82½\82Ô\82ñ\91å\8fä\95v
+            if Pos('://', Url[0]) > 0 then begin
               UrlCount := 1;
               if not QuickSection then
                 Script := Script + '\_q' + Url[0] + '\_q'
@@ -1337,6 +1384,11 @@ begin
         Result := '"' + SsParser[i] + '"'#13#10 +
                   '\82Í\81ASSTP Bottle\82Å\94F\82ß\82ç\82ê\82È\82¢\82©\81A\94F\8e¯\82Å\82«\82È\82¢\83^\83O\82Å\82·\81B';
         Exit;
+      end else if SsParser.MarkUpType[i] = mtStr then begin
+        if Pos(#9,SsParser[i]) > 0 then begin
+          Result := '\83^\83u\95\8e\9a\82Í\81ASSTP Bottle\82Å\8eg\97p\82Å\82«\82Ü\82¹\82ñ\81B';
+          Exit;
+        end;
       end;
     end;
     if (SsParser[0] <> '\t') and Pref.WarnYenTNotExist then begin
@@ -1362,17 +1414,8 @@ begin
 end;
 
 procedure TfrmSender.mnGoToHPClick(Sender: TObject);
-var
-  Command: string;
 begin
-  if Pref.BrowserExeName='' then
-    begin
-      ShellExecute(Handle, 'open', PChar(Pref.HomePage), nil, nil, SW_SHOW);
-    end else
-    begin
-      Command := Pref.BrowserExeName+' '+Pref.HomePage;
-      WinExec(PChar(Command), SW_SHOW);
-    end;
+  OpenBrowser(Pref.HomePage);
 end;
 
 procedure TfrmSender.ShowHintLabel(const Mes: String; Col: TColor);
@@ -1420,15 +1463,24 @@ begin
         //\83\81\83b\83Z\81[\83W\8eó\90M
         DispatchBottle(EventType, HeadValue);
       end;
+
       etMemberCount: begin
+        //\91\8d\8eQ\89Á\8eÒ\90\94
         StatusBar.Panels[PanelMembers].Text := HeadValue['Num'] + '\90l'
       end;
+
       etChannelCount: begin
+        //\83`\83\83\83\93\83l\83\8b\95Ê\8eQ\89Á\8eÒ\90\94
         try
-          ChannelList.Channel[HeadValue['Channel']].Members := StrToInt(HeadValue['Num']);
+          if HeadValue['Channel'] <> '' then begin
+            if ChannelList.Channel[HeadValue['Channel']] <> nil then begin
+              ChannelList.Channel[HeadValue['Channel']].Members := StrToInt(HeadValue['Num']);
+            end;
+          end;
         except
         end;
       end;
+
       etConnectOk: begin
         ShowHintLabel('SSTP Bottle\83T\81[\83o\82Æ\92Ê\90M\8am\97§\81B');
         Added := true;
@@ -1436,34 +1488,50 @@ begin
         //\83`\83\83\83\93\83l\83\8b\8e©\93®\93o\98^
         if not Connecting then
           PostCommand(['Command: getChannels']);
-        SakuraSeeker.BeginDetect;
+        try
+          SakuraSeeker.BeginDetect;
+        except
+          on E: Exception do ShowHintLabel(E.Message,WarningColor);
+        end;
       end;
+
       etChannelList: begin
         UpdateJoinChannelList(HeadValue);
         // \8dÅ\8cã\82É\8eQ\89Á\82µ\82Ä\82¢\82½\83`\83\83\83\93\83l\83\8b\82ð\8bL\98^\82·\82é
         if JoinChannelsBackup = nil then JoinChannelsBackup := TStringList.Create;
         JoinChannelsBackup.Assign(JoinChannels);
       end;
+
       etCloseChannel: begin
-        with JoinChannels do
-          if IndexOf(HeadValue['Channel']) >= 0 then
-            Delete(IndexOf(HeadValue['Channel']));
-        with tabChannel do begin
-          if Tabs.IndexOf(HeadValue['Channel']) >= 0 then
-            Tabs.Delete(Tabs.IndexOf(HeadValue['Channel']));
-          if Tabs.Count > 0 then TabIndex := 0 else TabIndex := -1;
-          tabChannelChange(self);
+        //\83`\83\83\83\93\83l\83\8b\94p\8e~
+        if HeadValue['Channel'] <> '' then begin
+          with JoinChannels do
+            if IndexOf(HeadValue['Channel']) >= 0 then
+              Delete(IndexOf(HeadValue['Channel']));
+          with tabChannel do begin
+            if Tabs.IndexOf(HeadValue['Channel']) >= 0 then
+              Tabs.Delete(Tabs.IndexOf(HeadValue['Channel']));
+            if Tabs.Count > 0 then TabIndex := 0 else TabIndex := -1;
+            tabChannelChange(self);
+          end;
+          ShowHintLabel(HeadValue['Channel'] + '\83`\83\83\83\93\83l\83\8b\82Í\94p\8e~\82³\82ê\82Ü\82µ\82½',
+                        WarningColor);
+          frmLog.AddCurrentSystemLog('SYSTEM', HeadValue['Channel'] + '\83`\83\83\83\93\83l\83\8b\82Í\94p\8e~\82³\82ê\82Ü\82µ\82½');
+          frmMessageBox.ShowMessage(HeadValue['Channel'] + '\83`\83\83\83\93\83l\83\8b\82Í\94p\8e~\82³\82ê\82Ü\82µ\82½');
         end;
-        ShowHintLabel(HeadValue['Channel'] + '\83`\83\83\83\93\83l\83\8b\82Í\94p\8e~\82³\82ê\82Ü\82µ\82½',
-                      WarningColor);
-        frmLog.AddCurrentSystemLog('SYSTEM', HeadValue['Channel'] + '\83`\83\83\83\93\83l\83\8b\82Í\94p\8e~\82³\82ê\82Ü\82µ\82½');
-        frmMessageBox.ShowMessage(HeadValue['Channel'] + '\83`\83\83\83\93\83l\83\8b\82Í\94p\8e~\82³\82ê\82Ü\82µ\82½');
       end;
+
       etForceBroadcastInformation: begin
-        if HeadValue['Type'] = 'Vote' then begin
-          frmLog.VoteLog(HeadValue['MID'], StrToIntDef(HeadValue['Num'], 0));
-        end else if HeadValue['Type'] = 'Agree' then begin
-          frmLog.AgreeLog(HeadValue['MID'], StrToIntDef(HeadValue['Num'], 0));
+        //\93\8a\95[\81^\93¯\88Ó\81^\82»\82Ì\91¼\83u\83\8d\81[\83h\83L\83\83\83X\83g\8fî\95ñ
+        if HeadValue['MID'] <> '' then begin
+          try //Num\82ª\90\94\92l\82Å\82È\82©\82Á\82½\82Æ\82«\91Î\8dô
+            if HeadValue['Type'] = 'Vote' then begin
+              frmLog.VoteLog(HeadValue['MID'], StrToIntDef(HeadValue['Num'], 0));
+            end else if HeadValue['Type'] = 'Agree' then begin
+              frmLog.AgreeLog(HeadValue['MID'], StrToIntDef(HeadValue['Num'], 0));
+            end;
+          except
+          end;
         end;
       end;
     end;
@@ -1622,8 +1690,9 @@ begin
     Tabs.Clear;
     for i := 0 to JoinChannels.Count-1 do begin
       //\8eó\90M\90ê\97p\83`\83\83\83\93\83l\83\8b\82Í\95\\8e¦\82µ\82È\82¢
-      if not ChannelList.Channel[JoinChannels[i]].NoPost then
-        Tabs.Add(JoinChannels[i]);
+      if ChannelList.Channel[JoinChannels[i]] <> nil then
+        if not ChannelList.Channel[JoinChannels[i]].NoPost then
+          Tabs.Add(JoinChannels[i]);
     end;
     Tabs.EndUpdate;
     // \8c³\82©\82ç\83`\83\83\83\93\83l\83\8b\82É\8eQ\89Á\82µ\82Ä\82¢\82½\8fê\8d\87\82Í
@@ -1698,10 +1767,11 @@ var Opt: TSstpSendOptions;
     CueItem: TLogItem;
     ReplaceHash: THeadValue; 
 begin
+  Channel := Dat['Channel'];
+
   Opt := [];
   if Pref.NoTranslate then Opt := Opt + [soNoTranslate];
   if Pref.NoDescript  then Opt := Opt + [soNoDescript];
-  Channel := Dat['Channel'];
   case EventType of
     etScript: Sender := Channel;
     etForceBroadcast: Sender := '\81y\82¨\92m\82ç\82¹\81z';
@@ -1890,6 +1960,10 @@ begin
     if Pref.UseHttpProxy then begin
       FHttp.ProxyServer := Pref.ProxyAddress;
       FHttp.ProxyPort   := Pref.ProxyPort;
+      if Pref.ProxyNeedAuthentication then begin
+        FHttp.ProxyUser := Pref.ProxyUser;
+        FHttp.ProxyPass := Pref.ProxyPass;
+      end;
     end;
     FHttp.OnSuccess := HttpSuccess;
     FHttp.OnConnectionFailed := HttpFailure;
@@ -1906,8 +1980,8 @@ end;
 procedure TfrmSender.actVoteMessageExecute(Sender: TObject);
 var Log: TLogItem;
 begin
-  if frmLog.lvwLog.Selected = nil then Exit;
-  Log := frmLog.SelectedBottleLog[frmLog.lvwLog.Selected.Index] as TLogItem;
+  if frmLog.lvwLog.ItemIndex < 0 then Exit;
+  Log := frmLog.SelectedBottleLog[frmLog.lvwLog.ItemIndex] as TLogItem;
   if Log = nil then Exit;
   if Log.LogType <> ltBottle then Exit;
   PostCommand([
@@ -1922,8 +1996,8 @@ end;
 procedure TfrmSender.actAgreeMessageExecute(Sender: TObject);
 var Log: TLogItem;
 begin
-  if frmLog.lvwLog.Selected = nil then Exit;
-  Log := frmLog.SelectedBottleLog[frmLog.lvwLog.Selected.Index] as TLogItem;
+  if frmLog.lvwLog.ItemIndex < 0 then Exit;
+  Log := frmLog.SelectedBottleLog[frmLog.lvwLog.ItemIndex] as TLogItem;
   if Log = nil then Exit;
   if Log.LogType <> ltBottle then Exit;
   PostCommand([
@@ -1997,17 +2071,8 @@ begin
 end;
 
 procedure TfrmSender.mnGotoVoteClick(Sender: TObject);
-var
-  Command: string;
 begin
-  if Pref.BrowserExeName='' then
-    begin
-      ShellExecute(Handle, 'open', PChar(Pref.VotePage), nil, nil, SW_SHOW);
-    end else
-    begin
-      Command := Pref.BrowserExeName+' '+Pref.VotePage;
-      WinExec(PChar(Command), SW_SHOW);
-    end;
+  OpenBrowser(Pref.VotePage);
 end;
 
 procedure TfrmSender.tabChannelMouseMove(Sender: TObject;
@@ -2023,17 +2088,8 @@ begin
 end;
 
 procedure TfrmSender.mnGoToHelpClick(Sender: TObject);
-var
-  Command: string;
 begin
-  if Pref.BrowserExeName='' then
-    begin
-      ShellExecute(Handle, 'open', PChar(Pref.HelpPage), nil, nil, SW_SHOW);
-    end else
-    begin
-      Command := Pref.BrowserExeName+' '+Pref.HelpPage;
-      WinExec(PChar(Command), SW_SHOW);
-    end;
+  OpenBrowser(Pref.HelpPage);
 end;
 
 procedure TfrmSender.tabChannelMouseDown(Sender: TObject;
@@ -2210,7 +2266,7 @@ begin
   SysUtils.Beep;
   Beep;
   ShowHintLabel('SSTP Bottle\83T\81[\83o\82Æ\82Ì\90Ú\91±\82É\8e¸\94s\82µ\82Ü\82µ\82½', WarningColor);
-  ShowMessage('SSTP Bottle\83T\81[\83o\82Æ\82Ì\90Ú\91±\82É\8e¸\94s\82µ\82Ü\82µ\82½'#13#10 +
+  frmMessageBox.ShowMessage('SSTP Bottle\83T\81[\83o\82Æ\82Ì\90Ú\91±\82É\8e¸\94s\82µ\82Ü\82µ\82½'#13#10 +
     (Sender as THTTPDownloadThread).LastErrorMessage);
   Connecting := false;
 end;
@@ -2280,8 +2336,11 @@ procedure TfrmSender.RetryBeginConnect;
 begin
   if FBeginConnectFailCount < 3 then begin
     // \90Ø\92f\82³\82ê\82Ä\82¢\82ê\82Î\8dÄ\90Ú\91±
+    IdSlpp20.OnDisconnect := nil;
+    if IdSlpp20.Connected then IdSlpp20.Disconnect;
     FAutoAddAfterGetChannel := true;
     BeginConnect;
+    IdSlpp20.OnDisconnect := Slpp20Disconnect;
   end else if FBeginConnectFailCount = 3 then begin
     frmLog.AddCurrentSystemLog('SYSTEM', '\8dÄ\90Ú\91±\8e©\93®\83\8a\83g\83\89\83C\82ð\92\86\8e~\82µ\82Ü\82·');
     frmMessageBox.ShowMessage(
@@ -2535,12 +2594,12 @@ begin
   end;
   FBottleSstp.Clear;
   frmLog.AllBottleOpened;
-  if frmLog.lvwLog.Selected = nil then Exit;
+  if frmLog.lvwLog.ItemIndex < 0 then Exit;
   Log := frmLog.SelectedBottleLog;
   if Log = nil then Exit;
   FBottleSSTP.OnResendCountChange := nil;
   errCount := 0;
-  for i := frmLog.lvwLog.Selected.Index downto 0 do begin
+  for i := frmLog.lvwLog.ItemIndex downto 0 do begin
     if (Log[i] as TLogItem).LogType <> ltBottle then Continue;
     InsertItem := TLogItem.Create(Log[i] as TLogItem);
     try
@@ -2594,17 +2653,21 @@ begin
 end;
 
 procedure TfrmSender.FormResize(Sender: TObject);
-var w: integer;
+var w, SelS, SelL: integer;
 begin
   // \83G\83f\83B\83^\81[\95\94\95ª\82Ì\83\8f\81[\83h\83\89\83b\83v\95\9d\82ð\92²\90®\82·\82é
   if memScript.ColWidth <> 0 then
   begin
     with memScript do
     begin
+      SelS := SelStart;
+      SelL := SelLength;
       w := Width - LeftMargin - ColWidth div 2;
       if ScrollBars in [ssVertical, ssBoth] then
         w := w - GetSystemMetrics(SM_CYVSCROLL);
       WrapOption.WrapByte := w div ColWidth;
+      SelStart  := SelS;
+      SelLength := SelL;
     end;
   end;
 end;
@@ -2780,8 +2843,10 @@ begin
   else
   begin
     Application.CreateForm(TfrmEditorTalkShow, frmEditorTalkShow);
+    frmEditorTalkShow.TalkShowFrame.SetPreviewFont(memScript.Font);
     frmEditorTalkShow.Show;
   end;
+  Pref.ShowEditorPreviewWindow := True;
   EditorPreview;
 end;
 
@@ -2909,8 +2974,8 @@ end;
 procedure TfrmSender.actSendToEditorExecute(Sender: TObject);
 var Log: TLogItem;
 begin
-  if frmLog.lvwLog.Selected = nil then Exit;
-  Log := frmLog.SelectedBottleLog[frmLog.lvwLog.Selected.Index] as TLogItem;
+  if frmLog.lvwLog.ItemIndex < 0 then Exit;
+  Log := frmLog.SelectedBottleLog[frmLog.lvwLog.ItemIndex] as TLogItem;
   if Log = nil then Exit;
   CopyFromLogToEditor(Log);
 end;
@@ -2976,11 +3041,11 @@ begin
   // \83\8d\83O\83E\83B\83\93\83h\83E\82Ì\8cÂ\95Ê\83\8d\83O\82ð\8dí\8f\9c\82·\82é
   if frmLog.SelectedBottleLog = nil then
     Exit;
-  if frmLog.lvwLog.Selected = nil then
+  if frmLog.lvwLog.ItemIndex = -1 then
     Exit;
-  frmLog.SelectedBottleLog.Delete(frmLog.lvwLog.Selected.Index);
+  frmLog.SelectedBottleLog.Delete(frmLog.lvwLog.ItemIndex);
   frmLog.UpdateWindow;
-  frmLog.lvwLogChange(Self, nil, ctState);
+  frmLog.lvwLogClick(Self);
 end;
 
 procedure TfrmSender.ClearEditor;
@@ -3218,11 +3283,11 @@ begin
   begin
     Beep;
     if Pref.UseHttpProxy then
-      ShowMessage('HTTP Proxy\82ð\92Ê\82\82ÄSSTP Bottle\83T\81[\83o\82É\90Ú\91±\82Å\82«\82Ü\82¹\82ñ\82Å\82µ\82½\81B'#13#10 +
+      frmMessageBox.ShowMessage('HTTP Proxy\82ð\92Ê\82\82ÄSSTP Bottle\83T\81[\83o\82É\90Ú\91±\82Å\82«\82Ü\82¹\82ñ\82Å\82µ\82½\81B'#13#10 +
                   '\83l\83b\83g\83\8f\81[\83N\82Ì\8fó\91Ô\81EProxy\82Ì\8fó\91Ô\82ð\8am\94F\82µ\82Ä\82­\82¾\82³\82¢\81B'#13#10 +
                   '\82 \82é\82¢\82Í\83T\81[\83o\82ª\83_\83E\83\93\82µ\82Ä\82¢\82é\89Â\94\\90«\82ª\82 \82è\82Ü\82·\81B')
     else
-      ShowMessage('SSTP Bottle\83T\81[\83o\82É\90Ú\91±\82Å\82«\82Ü\82¹\82ñ\82Å\82µ\82½\81B'#13#10 +
+      frmMessageBox.ShowMessage('SSTP Bottle\83T\81[\83o\82É\90Ú\91±\82Å\82«\82Ü\82¹\82ñ\82Å\82µ\82½\81B'#13#10 +
                   '\83l\83b\83g\83\8f\81[\83N\82É\8cq\82ª\82Á\82Ä\82¢\82é\82©\8am\94F\82µ\82Ä\82­\82¾\82³\82¢\81B'#13#10 +
                   '\82 \82é\82¢\82Í\83T\81[\83o\82ª\83_\83E\83\93\82µ\82Ä\82¢\82é\89Â\94\\90«\82ª\82 \82è\82Ü\82·\81B');
   end;