OSDN Git Service

Silence couple of warnings about unused variables
[radegast/radegast.git] / plugins / Radegast.Plugin.IRC / RelayConsole.cs
1 // 
2 // Radegast Metaverse Client
3 // Copyright (c) 2009-2013, Radegast Development Team
4 // All rights reserved.
5 // 
6 // Redistribution and use in source and binary forms, with or without
7 // modification, are permitted provided that the following conditions are met:
8 // 
9 //     * Redistributions of source code must retain the above copyright notice,
10 //       this list of conditions and the following disclaimer.
11 //     * Redistributions in binary form must reproduce the above copyright
12 //       notice, this list of conditions and the following disclaimer in the
13 //       documentation and/or other materials provided with the distribution.
14 //     * Neither the name of the application "Radegast", nor the names of its
15 //       contributors may be used to endorse or promote products derived from
16 //       this software without specific prior written permission.
17 // 
18 // THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
19 // AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
20 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
21 // DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
22 // FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
23 // DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
24 // SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
25 // CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
26 // OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
27 // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 //
29 // $Id$
30 //
31 using System;
32 using System.Collections.Generic;
33 using System.ComponentModel;
34 using System.Drawing;
35 using System.Data;
36 using System.Linq;
37 using System.Text;
38 using System.Text.RegularExpressions;
39 using System.Windows.Forms;
40 using System.Threading;
41 using Radegast;
42 using OpenMetaverse;
43 using Meebey.SmartIrc4net;
44
45 namespace Radegast.Plugin.IRC
46 {
47     public partial class RelayConsole : RadegastTabControl
48     {
49         public IrcClient irc;
50
51         TabsConsole TC { get { return instance.TabConsole; } }
52         RichTextBoxPrinter textPrinter;
53         private List<string> chatHistory = new List<string>();
54         private int chatPointer;
55         bool connecting = false;
56         UUID relayGroup;
57
58         public RelayConsole(RadegastInstance instance)
59             : base(instance)
60         {
61             InitializeComponent();
62             Disposed += new EventHandler(RelayConsole_Disposed);
63             textPrinter = new RichTextBoxPrinter(rtbChatText);
64
65             irc = new IrcClient();
66             irc.SendDelay = 200;
67             irc.AutoReconnect = true;
68             irc.CtcpVersion = Properties.Resources.RadegastTitle;
69             irc.Encoding = Encoding.UTF8;
70
71             TC.OnTabAdded += new TabsConsole.TabCallback(TC_OnTabAdded);
72             TC.OnTabRemoved += new TabsConsole.TabCallback(TC_OnTabRemoved);
73             irc.OnError += new ErrorEventHandler(irc_OnError);
74             irc.OnRawMessage += new IrcEventHandler(irc_OnRawMessage);
75             irc.OnChannelMessage += new IrcEventHandler(irc_OnChannelMessage);
76             irc.OnConnected += new EventHandler(irc_OnConnected);
77             irc.OnDisconnected += new EventHandler(irc_OnDisconnected);
78
79             client.Self.IM += new EventHandler<InstantMessageEventArgs>(Self_IM);
80
81             RefreshGroups();
82         }
83
84         void RelayConsole_Disposed(object sender, EventArgs e)
85         {
86             client.Self.IM -= new EventHandler<InstantMessageEventArgs>(Self_IM);
87
88             TC.OnTabAdded -= new TabsConsole.TabCallback(TC_OnTabAdded);
89             TC.OnTabRemoved -= new TabsConsole.TabCallback(TC_OnTabRemoved);
90
91             irc.OnError -= new ErrorEventHandler(irc_OnError);
92             irc.OnRawMessage -= new IrcEventHandler(irc_OnRawMessage);
93             irc.OnChannelMessage -= new IrcEventHandler(irc_OnChannelMessage);
94             irc.OnConnected -= new EventHandler(irc_OnConnected);
95             irc.OnDisconnected -= new EventHandler(irc_OnDisconnected);
96
97             if (irc.IsConnected)
98             {
99                 irc.AutoReconnect = false;
100                 irc.Disconnect();
101             }
102         }
103
104         void TC_OnTabRemoved(object sender, TabEventArgs e)
105         {
106             RefreshGroups();
107         }
108
109         void TC_OnTabAdded(object sender, TabEventArgs e)
110         {
111             if (e.Tab.Control is GroupIMTabWindow)
112                 RefreshGroups();
113         }
114
115         void RefreshGroups()
116         {
117             if (InvokeRequired)
118             {
119                 if (IsHandleCreated)
120                     BeginInvoke(new MethodInvoker(() => RefreshGroups()));
121                 return;
122             }
123
124             ddGroup.DropDownItems.Clear();
125
126             bool foundActive = false;
127
128             foreach (var tab in TC.Tabs)
129             {
130                 if (!(tab.Value.Control is GroupIMTabWindow)) continue;
131
132                 UUID session = new UUID(tab.Key);
133                 if (session == relayGroup)
134                     foundActive = true;
135
136                 ToolStripButton item = new ToolStripButton(instance.Groups[session].Name, null, groupSelect, session.ToString());
137                 ddGroup.DropDownItems.Add(item);
138             }
139
140             if (!foundActive)
141             {
142                 relayGroup = UUID.Zero;
143                 ddGroup.Text = "Groups (none)";
144             }
145
146         }
147
148         void groupSelect(object sender, EventArgs e)
149         {
150             if (sender is ToolStripButton)
151             {
152                 UUID session = new UUID(((ToolStripButton)sender).Name);
153                 relayGroup = session;
154                 ddGroup.Text = string.Format("Groups ({0})", instance.Groups[session].Name);
155             }
156         }
157
158         private void PrintMsg(string fromName, string message)
159         {
160             if (InvokeRequired)
161             {
162                 if (IsHandleCreated)
163                     BeginInvoke(new MethodInvoker(() => PrintMsg(fromName, message)));
164                 return;
165             }
166
167             DateTime timestamp = DateTime.Now;
168
169             if (message == null)
170                 message = string.Empty;
171
172             if (true)
173             {
174                 textPrinter.ForeColor = Color.Gray;
175                 textPrinter.PrintText(timestamp.ToString("[HH:mm] "));
176             }
177
178             textPrinter.ForeColor = Color.Black;
179
180             StringBuilder sb = new StringBuilder();
181
182             if (message.StartsWith("/me "))
183             {
184                 sb.Append(fromName);
185                 sb.Append(message.Substring(3));
186             }
187             else
188             {
189                 sb.Append(fromName);
190                 sb.Append(": ");
191                 sb.Append(message);
192             }
193
194             //instance.LogClientMessage(sessionName + ".txt", sb.ToString());
195             textPrinter.PrintTextLine(sb.ToString());
196             sb = null;
197         }
198
199         private void btnConnectPannel_Click(object sender, EventArgs e)
200         {
201             pnlConnectionSettings.Visible = true;
202         }
203
204         private void IrcThread(object param)
205         {
206             object[] args = (object[])param;
207             string server = (string)args[0];
208             int port = (int)args[1];
209             string nick = (string)args[2];
210             string chan = (string)args[3];
211
212             connecting = true;
213             PrintMsg("System", "Connecting...");
214
215             try
216             {
217                 irc.Connect(server, port);
218                 PrintMsg("System", "Logging in...");
219                 irc.Login(nick, "Radegast SL Relay", 0, nick);
220                 irc.RfcJoin(chan);
221                 connecting = false;
222             }
223             catch (Exception ex)
224             {
225                 PrintMsg("System", "An error has occured: " + ex.Message);
226             }
227
228             try
229             {
230                 irc.Listen();
231                 if (irc.IsConnected)
232                 {
233                     irc.AutoReconnect = false;
234                     irc.Disconnect();
235                 }
236             }
237             catch { }
238         }
239
240         private void btnConnect_Click(object sender, EventArgs e)
241         {
242             if (connecting)
243             {
244                 PrintMsg("System", "Already connecting");
245                 return;
246             }
247
248             if (irc.IsConnected)
249             {
250                 PrintMsg("System", "Already connected");
251                 return;
252             }
253
254
255             Thread IRCConnection = new Thread(new ParameterizedThreadStart(IrcThread));
256             IRCConnection.Name = "IRC Thread";
257             IRCConnection.IsBackground = true;
258             int port = 6667;
259             int.TryParse(txtPort.Text, out port);
260             IRCConnection.Start(new object[] { txtServer.Text, port, txtNick.Text, txtChan.Text });
261         }
262
263         void irc_OnRawMessage(object sender, IrcEventArgs e)
264         {
265             if (e.Data.Type == ReceiveType.Unknown || e.Data.Type == ReceiveType.ChannelMessage) return;
266             PrintMsg(e.Data.Nick, e.Data.Type + ": " + e.Data.Message);
267         }
268
269         void irc_OnError(object sender, ErrorEventArgs e)
270         {
271             PrintMsg("Error", e.ErrorMessage);
272         }
273
274         void irc_OnDisconnected(object sender, EventArgs e)
275         {
276             if (InvokeRequired)
277             {
278                 if (IsHandleCreated)
279                     Invoke(new MethodInvoker(() => irc_OnDisconnected(sender, e)));
280                 return;
281             }
282
283             lblConnected.Text = "not connected";
284             btnSend.Enabled = false;
285         }
286
287         void irc_OnConnected(object sender, EventArgs e)
288         {
289             if (InvokeRequired)
290             {
291                 if (IsHandleCreated)
292                     Invoke(new MethodInvoker(() => irc_OnConnected(sender, e)));
293                 return;
294             }
295             lblConnected.Text = "connected";
296             pnlConnectionSettings.Visible = false;
297             btnSend.Enabled = true;
298         }
299
300         void irc_OnChannelMessage(object sender, IrcEventArgs e)
301         {
302             ThreadPool.QueueUserWorkItem(sync =>
303                 {
304                     PrintMsg(e.Data.Nick, e.Data.Message);
305                     if (relayGroup != UUID.Zero)
306                     {
307                         client.Self.InstantMessageGroup(relayGroup, string.Format("(irc:{2}) {0}: {1}", e.Data.Nick, e.Data.Message, e.Data.Channel));
308                     }
309                 }
310             );
311         }
312
313         void Self_IM(object sender, InstantMessageEventArgs e)
314         {
315             if (e.IM.IMSessionID == relayGroup && irc.IsConnected && e.IM.FromAgentID != client.Self.AgentID)
316             {
317                 string[] lines = Regex.Split(e.IM.Message, "\n+");
318
319                 for (int l = 0; l < lines.Length; l++)
320                 {
321
322                     string[] words = lines[l].Split(' ');
323                     string outstr = string.Empty;
324
325                     for (int i = 0; i < words.Length; i++)
326                     {
327                         outstr += words[i] + " ";
328                         if (outstr.Length > 380)
329                         {
330                             PrintMsg(irc.Nickname, string.Format("{0}: {1}", e.IM.FromAgentName, outstr.Remove(outstr.Length - 1)));
331                             irc.SendMessage(SendType.Message, txtChan.Text, string.Format("{0}: {1}", e.IM.FromAgentName, outstr.Remove(outstr.Length - 1)));
332                             outstr = string.Empty;
333                         }
334                     }
335                     PrintMsg(irc.Nickname, string.Format("{0}: {1}", e.IM.FromAgentName, outstr.Remove(outstr.Length - 1)));
336                     irc.SendMessage(SendType.Message, txtChan.Text, string.Format("{0}: {1}", e.IM.FromAgentName, outstr.Remove(outstr.Length - 1)));
337                 }
338             }
339         }
340
341         private void btnDisconnect_Click(object sender, EventArgs e)
342         {
343             if (irc.IsConnected)
344             {
345                 irc.AutoReconnect = false;
346                 irc.Disconnect();
347             }
348         }
349
350         void SendMsg()
351         {
352             string msg = cbxInput.Text;
353             if (msg == string.Empty) return;
354
355             chatHistory.Add(cbxInput.Text);
356             chatPointer = chatHistory.Count;
357
358             cbxInput.Text = string.Empty;
359             if (irc.IsConnected)
360             {
361                 PrintMsg(irc.Nickname, msg);
362                 irc.SendMessage(SendType.Message, txtChan.Text, msg);
363             }
364         }
365
366         void ChatHistoryPrev()
367         {
368             if (chatPointer == 0) return;
369             chatPointer--;
370             if (chatHistory.Count > chatPointer)
371             {
372                 cbxInput.Text = chatHistory[chatPointer];
373                 cbxInput.SelectionStart = cbxInput.Text.Length;
374                 cbxInput.SelectionLength = 0;
375             }
376         }
377
378         void ChatHistoryNext()
379         {
380             if (chatPointer == chatHistory.Count) return;
381             chatPointer++;
382             if (chatPointer == chatHistory.Count)
383             {
384                 cbxInput.Text = string.Empty;
385                 return;
386             }
387             cbxInput.Text = chatHistory[chatPointer];
388             cbxInput.SelectionStart = cbxInput.Text.Length;
389             cbxInput.SelectionLength = 0;
390         }
391
392         private void cbxInput_KeyDown(object sender, KeyEventArgs e)
393         {
394             if (e.KeyCode == Keys.Up && e.Modifiers == Keys.Control)
395             {
396                 e.Handled = e.SuppressKeyPress = true;
397                 ChatHistoryPrev();
398                 return;
399             }
400
401             if (e.KeyCode == Keys.Down && e.Modifiers == Keys.Control)
402             {
403                 e.Handled = e.SuppressKeyPress = true;
404                 ChatHistoryNext();
405                 return;
406             }
407
408             if (e.KeyCode == Keys.Enter)
409             {
410                 e.Handled = e.SuppressKeyPress = true;
411                 SendMsg();
412             }
413         }
414
415         private void btnSend_Click(object sender, EventArgs e)
416         {
417             SendMsg();
418         }
419     }
420 }