Code

6aff31ccaf335d39948a6dc7d21f4b747db4f844
[inkscape.git] / src / jabber_whiteboard / pedrogui.cpp
1 /*
2  * Simple demo GUI for the Pedro mini-XMPP client.
3  *
4  * Authors:
5  *   Bob Jamison
6  *
7  * Copyright (C) 2005 Bob Jamison
8  *
9  *  This library is free software; you can redistribute it and/or
10  *  modify it under the terms of the GNU Lesser General Public
11  *  License as published by the Free Software Foundation; either
12  *  version 2.1 of the License, or (at your option) any later version.
13  *
14  *  This library is distributed in the hope that it will be useful,
15  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
16  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
17  *  Lesser General Public License for more details.
18  *
19  *  You should have received a copy of the GNU Lesser General Public
20  *  License along with this library; if not, write to the Free Software
21  *  Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
22  */
24 #include "jabber_whiteboard/pedrogui.h"
25 #include "jabber_whiteboard/session-manager.h"
28 #include <stdarg.h>
30 namespace Pedro
31 {
35 //#########################################################################
36 //# I C O N S
37 //#########################################################################
39 static const guint8 icon_available[] =
40 { ""
41   /* Pixbuf magic (0x47646b50) */
42   "GdkP"
43   /* length: header (24) + pixel_data (672) */
44   "\0\0\2\270"
45   /* pixdata_type (0x1010002) */
46   "\1\1\0\2"
47   /* rowstride (48) */
48   "\0\0\0""0"
49   /* width (12) */
50   "\0\0\0\14"
51   /* height (14) */
52   "\0\0\0\16"
53   /* pixel_data: */
54   "\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377333"
55   "\377333\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
56   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377"
57   "\0\377\377\377\0\377\377\377\0\377333\377\377\377\377\0\377\377\377\0"
58   "\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377"
59   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\37733"
60   "3\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377"
61   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
62   "\377\377\0\377\377\377\0\377333\377\377\377\377\0\377\377\377\0\377\377"
63   "\377\0""333\377\377\377\0\377\377\377\0\377\0\0\0\377\377\377\0\377\0"
64   "\0\0\377\377\377\0\377\377\377\0\377333\377\377\377\377\0\377\377\377"
65   "\0\377\377\377\0""333\377\377\377\0\377\377\377\0\377\0\0\0\377\377\377"
66   "\0\377\0\0\0\377\377\377\0\377\377\377\0\377333\377\377\377\377\0\377"
67   "\377\377\0\377\377\377\0""333\377\377\377\0\377\377\377\0\377\377\377"
68   "\0\377\0\0\0\377\377\377\0\377\377\377\0\377\377\377\0\377333\377\377"
69   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377"
70   "\0\377\377\377\0\377\0\0\0\377\377\377\0\377\377\377\0\377333\377\377"
71   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""3"
72   "33\377\377\377\0\377\377\377\0\377\0\0\0\377\377\377\0\377\377\377\0"
73   "\377333\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
74   "\377\377\0\377\377\377\0""333\377\377\377\0\377\377\377\0\377\377\377"
75   "\0\377333\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0"
76   "\377\377\377\0\377\377\377\0\377\377\377\0LLL\377\0\0\0\377\0\0\0\377"
77   "\0\0\0\377LLL\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377"
78   "\0\377\377\377\0\377\377\377\0\377\377\377\0LLL\377\0\0\0\377\0\0\0\377"
79   "\0\0\0\377LLL\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377"
80   "\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\0\0\0\377"
81   "\0\0\0\377\0\0\0\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
82   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
83   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
84   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0"};
87 static const guint8 icon_away[] =
88 { ""
89   /* Pixbuf magic (0x47646b50) */
90   "GdkP"
91   /* length: header (24) + pixel_data (672) */
92   "\0\0\2\270"
93   /* pixdata_type (0x1010002) */
94   "\1\1\0\2"
95   /* rowstride (48) */
96   "\0\0\0""0"
97   /* width (12) */
98   "\0\0\0\14"
99   /* height (14) */
100   "\0\0\0\16"
101   /* pixel_data: */
102   "\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377"
103   "\0""333\377333\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
104   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
105   "\377\0""333\377\377\377\0\377\377\377\0\377333\377\377\377\377\0\377"
106   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
107   "\377\377\0""333\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377"
108   "\0\377333\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0"
109   "\377\377\377\0\377\0\0\377\377\0\0\377\377\0\0\377\377\0\0\377\377\0"
110   "\0\377\377\0\0\377\377\0\0\377\377\0\0\377\377\377\377\0\377\377\377"
111   "\0\377\377\377\0\377\0\0\377\377\377\377\377\377\377\377\377\377\377"
112   "\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377"
113   "\377\377\377\377\377\377\0\0\377\377\377\377\0\377\0\0\377\377\377\377"
114   "\377\0\0\0\377\377\377\377\377\377\377\377\377\0\0\0\377\377\377\377"
115   "\377\0\0\0\377\0\0\0\377\377\377\377\377\377\377\377\377\377\0\0\377"
116   "\377\0\0\377\377\377\377\377\0\0\0\377\0\0\0\377\377\377\377\377\0\0"
117   "\0\377\0\0\0\377\377\377\377\377\377\377\377\377\0\0\0\377\377\377\377"
118   "\377\377\0\0\377\377\0\0\377\377\377\377\377\0\0\0\377\377\377\377\377"
119   "\0\0\0\377\0\0\0\377\0\0\0\377\0\0\0\377\0\0\0\377\0\0\0\377\377\377"
120   "\377\377\377\0\0\377\377\0\0\377\377\377\377\377\0\0\0\377\377\377\377"
121   "\377\377\377\377\377\0\0\0\377\0\0\0\377\377\377\377\377\377\377\377"
122   "\377\0\0\0\377\377\377\377\377\377\0\0\377\377\377\377\0\377\0\0\377"
123   "\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377"
124   "\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377\0\0"
125   "\377\377\377\377\0\377\377\377\0\377\377\377\0\377\0\0\377\377\0\0\377"
126   "\377\0\0\377\377\0\0\377\377\0\0\377\377\0\0\377\377\0\0\377\377\0\0"
127   "\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
128   "\377\0\377\377\377\0LLL\377333\377\0\0\0\377\0\0\0\377LLL\377\377\377"
129   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
130   "\377\0\377\377\377\0\377\377\377\0""333\377333\377333\377\377\377\377"
131   "\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377"
132   "\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377"
133   "\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377"
134   "\0"};
137 static const guint8 icon_chat[] =
138 { ""
139   /* Pixbuf magic (0x47646b50) */
140   "GdkP"
141   /* length: header (24) + pixel_data (672) */
142   "\0\0\2\270"
143   /* pixdata_type (0x1010002) */
144   "\1\1\0\2"
145   /* rowstride (48) */
146   "\0\0\0""0"
147   /* width (12) */
148   "\0\0\0\14"
149   /* height (14) */
150   "\0\0\0\16"
151   /* pixel_data: */
152   "\377\377\377\0\377\377\377\0\377\377\377\0""333\377333\377333\377\377"
153   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
154   "\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377\0\377\377\377"
155   "\0\377\377\377\0\377333\377\377\377\377\0\377\377\377\0\377\377\377\0"
156   "\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377\0\377\377"
157   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377333\377\377\377\377"
158   "\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377\0\377\377"
159   "\377\0\377fff\377\377\377\0\377fff\377\377\377\0\377\377\377\0\37733"
160   "3\377\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377\0\377"
161   "fff\377\377\377\0\377fff\377\377\377\0\377fff\377\377\377\0\377333\377"
162   "\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377\0\377fff"
163   "\377\377\377\0\377\377\377\0\377\377\377\0\377\0\0\0\377\0\0\0\377\0"
164   "\0\0\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""33"
165   "3\377\377\377\0\377fff\377\377\377\0\377\0\0\0\377\377\377\0\377\377"
166   "\377\0\377\377\377\0\377\0\0\0\377\377\377\377\0\377\377\377\0\377\377"
167   "\377\0""333\377\377\377\0\377fff\377\0\0\0\377\377\377\0\377\377\377"
168   "\0\377\377\377\0\377\377\377\0\377\377\377\0\377\0\0\0\377\377\377\377"
169   "\0\377\377\377\0\377\377\377\0""333\377\0\0\0\377\377\377\0\377\377\377"
170   "\0\377\0\0\0\377\377\377\0\377\0\0\0\377\377\377\0\377\377\377\0\377"
171   "\0\0\0\377\377\377\377\0\377\377\377\0""333\377\0\0\0\377\377\377\0\377"
172   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
173   "\377\377\0\377\0\0\0\377\377\377\377\0\377\377\377\0LLL\377\0\0\0\377"
174   "\377\377\0\377\377\377\0\377\0\0\0\377\377\377\0\377\0\0\0\377\377\377"
175   "\0\377\377\377\0\377\0\0\0\377\377\377\377\0\377\377\377\0LLL\377333"
176   "\377\0\0\0\377\377\377\0\377\377\377\0\377\0\0\0\377\377\377\0\377\377"
177   "\377\0\377\0\0\0\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
178   "\377\0""333\377333\377\0\0\0\377\377\377\0\377\377\377\0\377\377\377"
179   "\0\377\0\0\0\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377"
180   "\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\0\0\0\377"
181   "\0\0\0\377\0\0\0\377\377\377\377\0\377\377\377\0\377\377\377\0"};
184 static const guint8 icon_dnd[] =
185 { ""
186   /* Pixbuf magic (0x47646b50) */
187   "GdkP"
188   /* length: header (24) + pixel_data (672) */
189   "\0\0\2\270"
190   /* pixdata_type (0x1010002) */
191   "\1\1\0\2"
192   /* rowstride (48) */
193   "\0\0\0""0"
194   /* width (12) */
195   "\0\0\0\14"
196   /* height (14) */
197   "\0\0\0\16"
198   /* pixel_data: */
199   "\377\377\377\0\377\377\377\0\377\377\377\0""333\377333\377333\377\377"
200   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
201   "\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377\0\377\377\377"
202   "\0\377\377\377\0\377333\377\377\377\377\0\377\377\377\0\377\377\377\0"
203   "\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377\0\377\377"
204   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377333\377\377\377\377"
205   "\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377\0\377\377"
206   "\377\0\377fff\377\377\377\0\377fff\377\377\377\0\377\377\377\0\37733"
207   "3\377\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377\0\377"
208   "fff\377\377\377\0\377fff\377\377\377\0\377fff\377\377\377\0\377333\377"
209   "\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377\0\377fff"
210   "\377\377\377\0\377\377\377\0\377\377\377\0\377\177\0\0\377\177\0\0\377"
211   "\177\0\0\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0"
212   "333\377\377\377\0\377fff\377\377\377\0\377\177\0\0\377\377\0\0\377\377"
213   "\0\0\377\377\0\0\377\177\0\0\377\377\377\377\0\377\377\377\0\377\377"
214   "\377\0""333\377\377\377\0\377fff\377\177\0\0\377\377\377\377\377fff\377"
215   "\377\0\0\377fff\377\377\377\377\377\177\0\0\377\377\377\377\0\377\377"
216   "\377\0\377\377\377\0""333\377\177\0\0\377\377\0\0\377fff\377\377\377"
217   "\377\377fff\377\377\377\377\377fff\377\377\0\0\377\177\0\0\377\377\377"
218   "\377\0\377\377\377\0""333\377\177\0\0\377\377\0\0\377\377\0\0\377fff"
219   "\377\377\377\377\377fff\377\377\0\0\377\377\0\0\377\177\0\0\377\377\377"
220   "\377\0\377\377\377\0LLL\377\177\0\0\377\377\0\0\377fff\377\377\377\377"
221   "\377fff\377\377\377\377\377fff\377\377\0\0\377\177\0\0\377\377\377\377"
222   "\0\377\377\377\0LLL\377333\377\177\0\0\377\377\377\377\377fff\377\377"
223   "\0\0\377fff\377\377\377\377\377\177\0\0\377\377\377\377\0\377\377\377"
224   "\0\377\377\377\0\377\377\377\0""333\377333\377\177\0\0\377\377\0\0\377"
225   "\377\0\0\377\377\0\0\377\177\0\0\377\377\377\377\0\377\377\377\0\377"
226   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
227   "\377\377\0\177\0\0\377\177\0\0\377\177\0\0\377\377\377\377\0\377\377"
228   "\377\0\377\377\377\0"};
231 static const guint8 icon_error[] =
232 { ""
233   /* Pixbuf magic (0x47646b50) */
234   "GdkP"
235   /* length: header (24) + pixel_data (672) */
236   "\0\0\2\270"
237   /* pixdata_type (0x1010002) */
238   "\1\1\0\2"
239   /* rowstride (48) */
240   "\0\0\0""0"
241   /* width (12) */
242   "\0\0\0\14"
243   /* height (14) */
244   "\0\0\0\16"
245   /* pixel_data: */
246   "\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377"
247   "\0""333\377333\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
248   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377"
249   "\377\377\377\0\0\0\0\377\350\350\350\377333\377\377\377\377\0\377\377"
250   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377"
251   "\350\350\350\377fff\377\0\0\0\377\350\350\350\377\350\350\350\377333"
252   "\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377"
253   "\350\350\350\377\350\350\350\377\350\350\350\377\0\0\0\377\350\350\350"
254   "\377\350\350\350\377\350\350\350\377333\377\377\377\377\0\377\377\377"
255   "\0\377\377\377\0""333\377\350\350\350\377\350\350\350\377\0\0\0\377\0"
256   "\0\0\377fff\377\350\350\350\377\350\350\350\377333\377\377\377\377\0"
257   "\377\377\377\0\377\377\377\0""333\377\350\350\350\377\350\350\350\377"
258   "\0\0\0\377\350\350\350\377\0\0\0\377\0\0\0\377\0\0\0\377333\377\377\377"
259   "\377\0\377\377\377\0\377\377\377\0""333\377\350\350\350\377\0\0\0\377"
260   "\350\350\350\377\0\0\0\377\350\350\350\377\350\350\350\377\350\350\350"
261   "\377333\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""3"
262   "33\377\350\350\350\377\0\0\0\377\0\0\0\377\0\0\0\377\350\350\350\377"
263   "fff\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
264   "\377\0""333\377\0\0\0\377\350\350\350\377\350\350\350\377\350\350\350"
265   "\377\0\0\0\377333\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
266   "\377\0\377\377\377\0\377\377\377\0""333\377\350\350\350\377\350\350\350"
267   "\377\350\350\350\377333\377\377\377\377\0\377\377\377\0\377\377\377\0"
268   "\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0LLL\377\0\0\0"
269   "\377\0\0\0\377\0\0\0\377LLL\377\377\377\377\0\377\377\377\0\377\377\377"
270   "\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0LLL\377\0\0"
271   "\0\377\0\0\0\377\0\0\0\377LLL\377\377\377\377\0\377\377\377\0\377\377"
272   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
273   "\377\0\0\0\0\377\0\0\0\377\0\0\0\377\377\377\377\0\377\377\377\0\377"
274   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
275   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
276   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0"};
279 static const guint8 icon_offline[] =
280 { ""
281   /* Pixbuf magic (0x47646b50) */
282   "GdkP"
283   /* length: header (24) + pixel_data (672) */
284   "\0\0\2\270"
285   /* pixdata_type (0x1010002) */
286   "\1\1\0\2"
287   /* rowstride (48) */
288   "\0\0\0""0"
289   /* width (12) */
290   "\0\0\0\14"
291   /* height (14) */
292   "\0\0\0\16"
293   /* pixel_data: */
294   "\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377333"
295   "\377333\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
296   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377"
297   "\377\377\377\377\377\377\377\377\377\377333\377\377\377\377\0\377\377"
298   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377"
299   "\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377"
300   "\377\377\377333\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
301   "\377\0""333\377\377\377\377\377\377\377\377\377\377\377\377\377\377\377"
302   "\377\377\377\377\377\377\377\377\377\377\377\377\377\377333\377\377\377"
303   "\377\0\377\377\377\0\377\377\377\0""333\377\377\377\377\377\377\377\377"
304   "\377\0\0\0\377\377\377\377\377\0\0\0\377\377\377\377\377\377\377\377"
305   "\377333\377\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377"
306   "\377\377\377\377\377\377\0\0\0\377\377\377\377\377\0\0\0\377\377\377"
307   "\377\377\377\377\377\377333\377\377\377\377\0\377\377\377\0\377\377\377"
308   "\0""333\377\377\377\377\377\377\377\377\377\377\377\377\377\0\0\0\377"
309   "\377\377\377\377\377\377\377\377\377\377\377\377333\377\377\377\377\0"
310   "\377\377\377\0\377\377\377\0\377\377\377\0""333\377\377\377\377\377\377"
311   "\377\377\377\0\0\0\377\377\377\377\377\377\377\377\377333\377\377\377"
312   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377"
313   "\377\377\377\377\377\377\377\377\0\0\0\377\377\377\377\377\377\377\377"
314   "\377333\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
315   "\377\377\0\377\377\377\0""333\377\377\377\377\377\377\377\377\377\377"
316   "\377\377\377333\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
317   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0LLL\377\0\0\0\377\0\0"
318   "\0\377\0\0\0\377LLL\377\377\377\377\0\377\377\377\0\377\377\377\0\377"
319   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0LLL\377\0\0\0\377"
320   "\0\0\0\377\0\0\0\377LLL\377\377\377\377\0\377\377\377\0\377\377\377\0"
321   "\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377"
322   "\0\0\0\0\377\0\0\0\377\0\0\0\377\377\377\377\0\377\377\377\0\377\377"
323   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
324   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
325   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0"};
328 static const guint8 icon_xa[] =
329 { ""
330   /* Pixbuf magic (0x47646b50) */
331   "GdkP"
332   /* length: header (24) + pixel_data (672) */
333   "\0\0\2\270"
334   /* pixdata_type (0x1010002) */
335   "\1\1\0\2"
336   /* rowstride (48) */
337   "\0\0\0""0"
338   /* width (12) */
339   "\0\0\0\14"
340   /* height (14) */
341   "\0\0\0\16"
342   /* pixel_data: */
343   "\377\377\377\0\377\377\377\0\377\377\377\0\377\0\0\377333\377333\377"
344   "333\377\377\0\0\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
345   "\377\0\377\377\377\0\377\377\377\0\377\0\0\377333\377\377\377\0\377\377"
346   "\377\0\377\377\377\0\377333\377\377\0\0\377\377\377\377\0\377\377\377"
347   "\0\377\377\377\0\377\377\377\0\377\377\377\0\377\0\0\377\377\377\0\377"
348   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\0\0\377"
349   "\177\0\0\377\177\0\0\377\377\377\377\0\377\377\377\0""333\377\377\0\0"
350   "\377\377\377\0\377fff\377\377\377\0\377\177\0\0\377\177\0\0\377\377\0"
351   "\0\377\377\377\377\377\177\0\0\377\377\377\377\0\377\377\377\0""333\377"
352   "\377\0\0\377\177\0\0\377\177\0\0\377\177\0\0\377\377\377\377\377\377"
353   "\377\377\377\377\377\377\377\0\0\0\377\0\0\0\377\177\0\0\377\177\0\0"
354   "\377\177\0\0\377\377\0\0\377\377\377\377\377\377\377\377\377\377\377"
355   "\377\377\262\262\262\377\377\377\377\377\0\0\0\377\0\0\0\377\377\377"
356   "\377\377\177\0\0\377\177\0\0\377\377\377\377\377\262\262\262\377\0\0"
357   "\0\377\262\262\262\377\0\0\0\377\377\377\377\377\0\0\0\377\377\377\377"
358   "\377\262\262\262\377\0\0\0\377\177\0\0\377\177\0\0\377\377\377\377\377"
359   "\0\0\0\377\377\377\377\377\0\0\0\377\0\0\0\377\377\377\377\377\0\0\0"
360   "\377\0\0\0\377\377\377\377\377\0\0\0\377\177\0\0\377\177\0\0\377\377"
361   "\377\377\377\0\0\0\377\377\377\377\377\0\0\0\377\377\377\377\377\0\0"
362   "\0\377\0\0\0\377\377\377\377\377\377\377\377\377\377\377\377\377\177"
363   "\0\0\377\377\377\377\0\177\0\0\377\262\262\262\377\0\0\0\377\262\262"
364   "\262\377\377\377\377\377\377\377\377\377\377\377\377\377\177\0\0\377"
365   "\177\0\0\377\177\0\0\377\377\377\377\0\377\377\377\0\177\0\0\377\377"
366   "\377\377\377\377\377\377\377\177\0\0\377\177\0\0\377\177\0\0\377\177"
367   "\0\0\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
368   "\377\377\0\177\0\0\377\177\0\0\377\177\0\0\377333\377\0\0\0\377\0\0\0"
369   "\377LLL\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377"
370   "\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0""333\377333\377"
371   "333\377\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
372   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
373   "\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377\377\0\377\377"
374   "\377\0\377\377\377\0\377\377\377\0"};
377 //#########################################################################
378 //# R O S T E R
379 //#########################################################################
382 void Roster::doubleClickCallback(const Gtk::TreeModel::Path &path,
383                    Gtk::TreeViewColumn *col)
385     Glib::RefPtr<Gtk::TreeModel> model = rosterView.get_model();
386     Glib::RefPtr<Gtk::TreeSelection> sel = rosterView.get_selection();
387     Gtk::TreeModel::iterator iter = sel->get_selected();
388     DOMString nick = iter->get_value(rosterColumns.userColumn);
389     //printf("Double clicked:%s\n", nick.c_str());
390     if (parent)
391         parent->doChat(nick);
395 void Roster::chatCallback()
397     Glib::RefPtr<Gtk::TreeModel> model = rosterView.get_model();
398     Glib::RefPtr<Gtk::TreeSelection> sel = rosterView.get_selection();
399     Gtk::TreeModel::iterator iter = sel->get_selected();
400     DOMString nick = iter->get_value(rosterColumns.userColumn);
401     //printf("Chat with:%s\n", nick.c_str());
402     if (parent)
403         parent->doChat(nick);
406 void Roster::sendFileCallback()
408     Glib::RefPtr<Gtk::TreeModel> model = rosterView.get_model();
409     Glib::RefPtr<Gtk::TreeSelection> sel = rosterView.get_selection();
410     Gtk::TreeModel::iterator iter = sel->get_selected();
411     DOMString nick = iter->get_value(rosterColumns.userColumn);
412     //printf("Send file to:%s\n", nick.c_str());
413     if (parent)
414         parent->doSendFile(nick);
417 void Roster::shareCallback()
419     Glib::RefPtr<Gtk::TreeModel> model = rosterView.get_model();
420     Glib::RefPtr<Gtk::TreeSelection> sel = rosterView.get_selection();
421     Gtk::TreeModel::iterator iter = sel->get_selected();
422     DOMString nick = iter->get_value(rosterColumns.userColumn);
423     //printf("share to:%s\n", nick.c_str());
424     if (parent)
425         parent->doShare(nick);
428 bool Roster::buttonPressCallback(GdkEventButton* event)
430     if( (event->type == GDK_BUTTON_PRESS) && (event->button == 3) )
431         {
432         Gtk::Widget *wid = uiManager->get_widget("/PopupMenu");
433         Gtk::Menu *popupMenu = dynamic_cast<Gtk::Menu*>(wid);
434         popupMenu->popup(event->button, event->time);
435         return true;
436         }
437     else
438         return false;
441 bool Roster::doSetup()
443     set_size_request(200,200);
445     pixbuf_available = Gdk::Pixbuf::create_from_inline(
446                       sizeof(icon_available), icon_available, false);
447     pixbuf_away     = Gdk::Pixbuf::create_from_inline(
448                       sizeof(icon_away), icon_away, false);
449     pixbuf_chat     = Gdk::Pixbuf::create_from_inline(
450                       sizeof(icon_chat), icon_chat, false);
451     pixbuf_dnd      = Gdk::Pixbuf::create_from_inline(
452                       sizeof(icon_dnd), icon_dnd, false);
453     pixbuf_error    = Gdk::Pixbuf::create_from_inline(
454                       sizeof(icon_error), icon_error, false);
455     pixbuf_offline  = Gdk::Pixbuf::create_from_inline(
456                       sizeof(icon_offline), icon_offline, false);
457     pixbuf_xa       = Gdk::Pixbuf::create_from_inline(
458                       sizeof(icon_xa), icon_xa, false);
460     rosterView.setParent(this);
461     treeStore = Gtk::TreeStore::create(rosterColumns);
462     rosterView.set_model(treeStore);
464     Gtk::CellRendererText *rend0 = new Gtk::CellRendererText();
465     //rend0->property_background() = "gray";
466     //rend0->property_foreground() = "black";
467     rosterView.append_column("Group", *rend0);
468     Gtk::TreeViewColumn *col0 = rosterView.get_column(0);
469     col0->add_attribute(*rend0, "text", 0);
471     Gtk::CellRendererPixbuf *rend1 = new Gtk::CellRendererPixbuf();
472     rosterView.append_column("Status", *rend1);
473     Gtk::TreeViewColumn *col1 = rosterView.get_column(1);
474     col1->add_attribute(*rend1, "pixbuf", 1);
476     Gtk::CellRendererText *rend2 = new Gtk::CellRendererText();
477     rosterView.append_column("Item", *rend2);
478     Gtk::TreeViewColumn *col2 = rosterView.get_column(2);
479     col2->add_attribute(*rend2, "text", 2);
481     Gtk::CellRendererText *rend3 = new Gtk::CellRendererText();
482     rosterView.append_column("Name", *rend3);
483     Gtk::TreeViewColumn *col3 = rosterView.get_column(3);
484     col3->add_attribute(*rend3, "text", 3);
486     Gtk::CellRendererText *rend4 = new Gtk::CellRendererText();
487     rosterView.append_column("Subscription", *rend4);
488     Gtk::TreeViewColumn *col4 = rosterView.get_column(4);
489     col4->add_attribute(*rend4, "text", 4);
491     rosterView.signal_row_activated().connect(
492         sigc::mem_fun(*this, &Roster::doubleClickCallback) );
494     add(rosterView);
495     set_policy(Gtk::POLICY_ALWAYS, Gtk::POLICY_ALWAYS);
497     //##### POPUP MENU
498     Glib::RefPtr<Gtk::ActionGroup> actionGroup = Gtk::ActionGroup::create();
500     actionGroup->add( Gtk::Action::create("UserMenu", "_User Menu") );
502     actionGroup->add( Gtk::Action::create("Chat",
503                                   Gtk::Stock::CONNECT, "Chat"),
504     sigc::mem_fun(*this, &Roster::chatCallback) );
505     actionGroup->add( Gtk::Action::create("SendFile",
506                                   Gtk::Stock::CONNECT, "Send file"),
507     sigc::mem_fun(*this, &Roster::sendFileCallback) );
508     actionGroup->add( Gtk::Action::create("Share",
509                                   Gtk::Stock::CONNECT, "Share whiteboard"),
510     sigc::mem_fun(*this, &Roster::shareCallback) );
513     uiManager = Gtk::UIManager::create();
515     uiManager->insert_action_group(actionGroup, 0);
517     Glib::ustring ui_info =
518         "<ui>"
519         "  <popup name='PopupMenu'>"
520         "    <menuitem action='Chat'/>"
521         "    <menuitem action='SendFile'/>"
522         "    <menuitem action='Share'/>"
523         "  </popup>"
524         "</ui>";
526     uiManager->add_ui_from_string(ui_info);
529     show_all_children();
531     return true;
535 /**
536  * Clear the roster
537  */
538 void Roster::clear()
540     treeStore->clear();
543 /**
544  * Regenerate the roster
545  */
546 void Roster::refresh()
548    if (!parent)
549         return;
550     treeStore->clear();
551     std::vector<XmppUser> items = parent->client.getRoster();
553     //## Add in tree fashion
554     DOMString lastGroup = "";
555     Gtk::TreeModel::Row row = *(treeStore->append());
556     row[rosterColumns.groupColumn] = "";
557     for (unsigned int i=0 ; i<items.size() ; i++)
558         {
559         XmppUser user = items[i];
560         if (user.group != lastGroup)
561             {
562             if (lastGroup.size()>0)
563                 row = *(treeStore->append());
564             row[rosterColumns.groupColumn] = user.group;
565             lastGroup = user.group;
566             }
567         Glib::RefPtr<Gdk::Pixbuf> pb = pixbuf_offline;
568         if (user.show == "available")
569             pb = pixbuf_available;
570         else if (user.show == "away")
571             pb = pixbuf_away;
572         else if (user.show == "chat")
573             pb = pixbuf_chat;
574         else if (user.show == "dnd")
575             pb = pixbuf_dnd;
576         else if (user.show == "xa")
577             pb = pixbuf_xa;
578         else
579             {
580             //printf("Unknown show for %s:'%s'\n", user.c_str(), show.c_str());
581             }
582         Gtk::TreeModel::Row childRow = *(treeStore->append(row.children()));
583         childRow[rosterColumns.statusColumn] = pb;
584         childRow[rosterColumns.userColumn]   = user.jid;
585         childRow[rosterColumns.nameColumn]   = user.nick;
586         childRow[rosterColumns.subColumn]    = user.subscription;
587         }
588     rosterView.expand_all();
591 //#########################################################################
592 //# M E S S A G E    L I S T
593 //#########################################################################
595 bool MessageList::doSetup()
597     set_size_request(400,200);
599     messageListBuffer = Gtk::TextBuffer::create();
600     messageList.set_buffer(messageListBuffer);
601     messageList.set_editable(false);
602     messageList.set_wrap_mode(Gtk::WRAP_WORD_CHAR);
604     Glib::RefPtr<Gtk::TextBuffer::TagTable> table =
605         messageListBuffer->get_tag_table();
606     Glib::RefPtr<Gtk::TextBuffer::Tag> color0 =
607         Gtk::TextBuffer::Tag::create("color0");
608     color0->property_foreground() = "DarkGreen";
609     color0->property_weight()     = Pango::WEIGHT_BOLD;
610     table->add(color0);
611     Glib::RefPtr<Gtk::TextBuffer::Tag> color1 =
612         Gtk::TextBuffer::Tag::create("color1");
613     color1->property_foreground() = "chocolate4";
614     color1->property_weight()     = Pango::WEIGHT_BOLD;
615     table->add(color1);
616     Glib::RefPtr<Gtk::TextBuffer::Tag> color2 =
617         Gtk::TextBuffer::Tag::create("color2");
618     color2->property_foreground() = "red4";
619     color2->property_weight()     = Pango::WEIGHT_BOLD;
620     table->add(color2);
621     Glib::RefPtr<Gtk::TextBuffer::Tag> color3 =
622         Gtk::TextBuffer::Tag::create("color3");
623     color3->property_foreground() = "MidnightBlue";
624     color3->property_weight()     = Pango::WEIGHT_BOLD;
625     table->add(color3);
626     Glib::RefPtr<Gtk::TextBuffer::Tag> color4 =
627         Gtk::TextBuffer::Tag::create("color4");
628     color4->property_foreground() = "turquoise4";
629     color4->property_weight()     = Pango::WEIGHT_BOLD;
630     table->add(color4);
631     Glib::RefPtr<Gtk::TextBuffer::Tag> color5 =
632         Gtk::TextBuffer::Tag::create("color5");
633     color5->property_foreground() = "OliveDrab";
634     color5->property_weight()     = Pango::WEIGHT_BOLD;
635     table->add(color5);
636     Glib::RefPtr<Gtk::TextBuffer::Tag> color6 =
637         Gtk::TextBuffer::Tag::create("color6");
638     color6->property_foreground() = "purple4";
639     color6->property_weight()     = Pango::WEIGHT_BOLD;
640     table->add(color6);
641     Glib::RefPtr<Gtk::TextBuffer::Tag> color7 =
642         Gtk::TextBuffer::Tag::create("color7");
643     color7->property_foreground() = "VioletRed4";
644     color7->property_weight()     = Pango::WEIGHT_BOLD;
645     table->add(color7);
647     add(messageList);
648     set_policy(Gtk::POLICY_ALWAYS, Gtk::POLICY_ALWAYS);
651     show_all_children();
653     return true;
656 /**
657  * Clear all messages from the list
658  */
659 void MessageList::clear()
661     messageListBuffer->erase(messageListBuffer->begin(),
662                              messageListBuffer->end());
666 /**
667  * Post a message to the list
668  */
669 void MessageList::postMessage(const DOMString &from, const DOMString &msg)
671     DOMString out = "<";
672     out.append(from);
673     out.append("> ");
675     int val = 0;
676     for (unsigned int i=0 ; i<from.size() ; i++)
677        val += from[i];
678     val = val % 8;
680     char buf[16];
681     sprintf(buf, "color%d", val);
682     DOMString tagName = buf;
684     messageListBuffer->insert_with_tag(
685             messageListBuffer->end(), out, tagName);
686     messageListBuffer->insert(messageListBuffer->end(), msg);
687     messageListBuffer->insert(messageListBuffer->end(), "\n");
688     //Gtk::Adjustment *adj = get_vadjustment();
689     //adj->set_value(adj->get_upper()-adj->get_page_size());
690     Glib::RefPtr<Gtk::TextBuffer::Mark> mark =
691         messageListBuffer->create_mark("temp", messageListBuffer->end());
692     messageList.scroll_mark_onscreen(mark);
693     messageListBuffer->delete_mark(mark);
698 //#########################################################################
699 //# U S E R     L I S T
700 //#########################################################################
701 void UserList::doubleClickCallback(const Gtk::TreeModel::Path &path,
702                    Gtk::TreeViewColumn *col)
704     Glib::RefPtr<Gtk::TreeModel> model = userList.get_model();
705     Glib::RefPtr<Gtk::TreeSelection> sel = userList.get_selection();
706     Gtk::TreeModel::iterator iter = sel->get_selected();
707     DOMString nick = iter->get_value(userListColumns.userColumn);
708     //printf("Double clicked:%s\n", nick.c_str());
709     if (parent)
710         parent->doChat(nick);
714 void UserList::chatCallback()
716     Glib::RefPtr<Gtk::TreeModel> model = userList.get_model();
717     Glib::RefPtr<Gtk::TreeSelection> sel = userList.get_selection();
718     Gtk::TreeModel::iterator iter = sel->get_selected();
719     DOMString nick = iter->get_value(userListColumns.userColumn);
720     //printf("Chat with:%s\n", nick.c_str());
721     if (parent)
722         parent->doChat(nick);
725 void UserList::sendFileCallback()
727     Glib::RefPtr<Gtk::TreeModel> model = userList.get_model();
728     Glib::RefPtr<Gtk::TreeSelection> sel = userList.get_selection();
729     Gtk::TreeModel::iterator iter = sel->get_selected();
730     DOMString nick = iter->get_value(userListColumns.userColumn);
731     //printf("Send file to:%s\n", nick.c_str());
732     if (parent)
733         parent->doSendFile(nick);
736 void UserList::shareCallback()
738     Glib::RefPtr<Gtk::TreeModel> model = userList.get_model();
739     Glib::RefPtr<Gtk::TreeSelection> sel = userList.get_selection();
740     Gtk::TreeModel::iterator iter = sel->get_selected();
741     DOMString nick = iter->get_value(userListColumns.userColumn);
742     //printf("Send file to:%s\n", nick.c_str());
743     if (parent)
744         parent->doShare(nick);
747 bool UserList::buttonPressCallback(GdkEventButton* event)
749     if( (event->type == GDK_BUTTON_PRESS) && (event->button == 3) )
750         {
751         Gtk::Widget *wid = uiManager->get_widget("/PopupMenu");
752         Gtk::Menu *popupMenu = dynamic_cast<Gtk::Menu*>(wid);
753         popupMenu->popup(event->button, event->time);
754         return true;
755         }
756     else
757         return false;
760 bool UserList::doSetup()
762     set_size_request(200,200);
764     setParent(NULL);
766     pixbuf_available = Gdk::Pixbuf::create_from_inline(
767                       sizeof(icon_available), icon_available, false);
768     pixbuf_away     = Gdk::Pixbuf::create_from_inline(
769                       sizeof(icon_away), icon_away, false);
770     pixbuf_chat     = Gdk::Pixbuf::create_from_inline(
771                       sizeof(icon_chat), icon_chat, false);
772     pixbuf_dnd      = Gdk::Pixbuf::create_from_inline(
773                       sizeof(icon_dnd), icon_dnd, false);
774     pixbuf_error    = Gdk::Pixbuf::create_from_inline(
775                       sizeof(icon_error), icon_error, false);
776     pixbuf_offline  = Gdk::Pixbuf::create_from_inline(
777                       sizeof(icon_offline), icon_offline, false);
778     pixbuf_xa       = Gdk::Pixbuf::create_from_inline(
779                       sizeof(icon_xa), icon_xa, false);
781     userList.setParent(this);
782     userListStore = Gtk::ListStore::create(userListColumns);
783     userList.set_model(userListStore);
785     Gtk::CellRendererPixbuf *rend0 = new Gtk::CellRendererPixbuf();
786     userList.append_column("Status", *rend0);
787     Gtk::TreeViewColumn *col0 = userList.get_column(0);
788     col0->add_attribute(*rend0, "pixbuf", 0);
790     Gtk::CellRendererText *rend1 = new Gtk::CellRendererText();
791     //rend1->property_background() = "gray";
792     //rend1->property_foreground() = "black";
793     userList.append_column("User", *rend1);
794     Gtk::TreeViewColumn *col1 = userList.get_column(1);
795     col1->add_attribute(*rend1, "text", 1);
797     userList.set_headers_visible(false);
799     userList.signal_row_activated().connect(
800         sigc::mem_fun(*this, &UserList::doubleClickCallback) );
802     add(userList);
803     set_policy(Gtk::POLICY_ALWAYS, Gtk::POLICY_ALWAYS);
805     //##### POPUP MENU
806     Glib::RefPtr<Gtk::ActionGroup> actionGroup = Gtk::ActionGroup::create();
808     actionGroup->add( Gtk::Action::create("UserMenu", "_User Menu") );
810     actionGroup->add( Gtk::Action::create("Chat",
811                                   Gtk::Stock::CONNECT, "Chat"),
812     sigc::mem_fun(*this, &UserList::chatCallback) );
813     actionGroup->add( Gtk::Action::create("SendFile",
814                                   Gtk::Stock::CONNECT, "Send file"),
815     sigc::mem_fun(*this, &UserList::sendFileCallback) );
816     actionGroup->add( Gtk::Action::create("Share",
817                                   Gtk::Stock::CONNECT, "Share whiteboard"),
818     sigc::mem_fun(*this, &UserList::shareCallback) );
821     uiManager = Gtk::UIManager::create();
823     uiManager->insert_action_group(actionGroup, 0);
825     Glib::ustring ui_info =
826         "<ui>"
827         "  <popup name='PopupMenu'>"
828         "    <menuitem action='Chat'/>"
829         "    <menuitem action='SendFile'/>"
830         "    <menuitem action='Share'/>"
831         "  </popup>"
832         "</ui>";
834     uiManager->add_ui_from_string(ui_info);
836     show_all_children();
838     return true;
841 /**
842  * Clear all messages from the list
843  */
844 void UserList::clear()
846     userListStore->clear();
850 /**
851  * Add a user to the list
852  */
853 void UserList::addUser(const DOMString &user, const DOMString &show)
855     Glib::RefPtr<Gdk::Pixbuf> pb = pixbuf_offline;
856     if (show == "available")
857         pb = pixbuf_available;
858     else if (show == "away")
859         pb = pixbuf_away;
860     else if (show == "chat")
861         pb = pixbuf_chat;
862     else if (show == "dnd")
863         pb = pixbuf_dnd;
864     else if (show == "xa")
865         pb = pixbuf_xa;
866     else
867         {
868         //printf("Unknown show for %s:'%s'\n", user.c_str(), show.c_str());
869         }
870     Gtk::TreeModel::Row row = *(userListStore->append());
871     row[userListColumns.userColumn]   = user;
872     row[userListColumns.statusColumn] = pb;
878 //#########################################################################
879 //# C H A T    W I N D O W
880 //#########################################################################
881 ChatWindow::ChatWindow(PedroGui &par, const DOMString jidArg)
882                         : parent(par)
884     jid = jidArg;
885     doSetup();
888 ChatWindow::~ChatWindow()
892 void ChatWindow::leaveCallback()
894     hide();
895     parent.chatDelete(jid);
899 void ChatWindow::hideCallback()
901     hide();
902     parent.chatDelete(jid);
905 void ChatWindow::shareCallback()
907 //    hide();
908     parent.doShare(this->jid);
911 void ChatWindow::textEnterCallback()
913     DOMString str = inputTxt.get_text();
914     if (str.size() > 0)
915         parent.client.message(jid, str);
916     inputTxt.set_text("");
917     messageList.postMessage(parent.client.getJid(), str);
920 bool ChatWindow::doSetup()
922     DOMString title = "Private Chat - ";
923     title.append(jid);
924     set_title(title);
926     set_size_request(500,300);
928     signal_hide().connect(
929            sigc::mem_fun(*this, &ChatWindow::hideCallback) );
931     Glib::RefPtr<Gtk::ActionGroup> actionGroup = Gtk::ActionGroup::create();
932     actionGroup->add( Gtk::Action::create("MenuFile", "_File") );
933     actionGroup->add( Gtk::Action::create("Leave",  Gtk::Stock::CANCEL),
934         sigc::mem_fun(*this, &ChatWindow::leaveCallback) );
935     actionGroup->add( Gtk::Action::create("Share",  Gtk::Stock::CONNECT,
936         "Share whiteboard"), sigc::mem_fun(*this, &ChatWindow::shareCallback) );
939     Glib::RefPtr<Gtk::UIManager> uiManager = Gtk::UIManager::create();
941     uiManager->insert_action_group(actionGroup, 0);
942     add_accel_group(uiManager->get_accel_group());
944     Glib::ustring ui_info =
945         "<ui>"
946         "  <menubar name='MenuBar'>"
947         "    <menu action='MenuFile'>"
948         "      <menuitem action='Leave'/>"
949         "      <menuitem action='Share'/>"
950         "    </menu>"
951         "  </menubar>"
952         "</ui>";
954     add(vbox);
956     uiManager->add_ui_from_string(ui_info);
957     Gtk::Widget* pMenuBar = uiManager->get_widget("/MenuBar");
958     vbox.pack_start(*pMenuBar, Gtk::PACK_SHRINK);
960     vbox.pack_end(vPaned);
962     vPaned.add1(messageList);
963     vPaned.add2(inputTxt);
965     inputTxt.signal_activate().connect(
966            sigc::mem_fun(*this, &ChatWindow::textEnterCallback) );
968     show_all_children();
970     return true;
973 bool ChatWindow::postMessage(const DOMString &data)
975     messageList.postMessage(jid, data);
976     return true;
979 //#########################################################################
980 //# G R O U P    C H A T    W I N D O W
981 //#########################################################################
983 GroupChatWindow::GroupChatWindow(PedroGui &par,
984                                  const DOMString &groupJidArg,
985                                  const DOMString &nickArg)
986                                : parent(par)
988     groupJid = groupJidArg;
989     nick     = nickArg;
990     doSetup();
993 GroupChatWindow::~GroupChatWindow()
998 void GroupChatWindow::leaveCallback()
1000     parent.client.groupChatLeave(groupJid, nick);
1001     hide();
1002     parent.groupChatDelete(groupJid, nick);
1005 void GroupChatWindow::hideCallback()
1007     parent.client.groupChatLeave(groupJid, nick);
1008     hide();
1009     parent.groupChatDelete(groupJid, nick);
1012 void GroupChatWindow::textEnterCallback()
1014     DOMString str = inputTxt.get_text();
1015     if (str.size() > 0)
1016         parent.client.groupChatMessage(groupJid, str);
1017     inputTxt.set_text("");
1020 void GroupChatWindow::shareCallback()
1022     parent.doGroupShare(groupJid);
1025 bool GroupChatWindow::doSetup()
1027     DOMString title = "Group Chat - ";
1028     title.append(groupJid);
1029     set_title(title);
1031     userList.setParent(this);
1033     set_size_request(500,300);
1035     signal_hide().connect(
1036            sigc::mem_fun(*this, &GroupChatWindow::hideCallback) );
1038     Glib::RefPtr<Gtk::ActionGroup> actionGroup = Gtk::ActionGroup::create();
1039     actionGroup->add( Gtk::Action::create("MenuFile", "_File") );
1040     actionGroup->add( Gtk::Action::create("Leave",  Gtk::Stock::CANCEL),
1041         sigc::mem_fun(*this, &GroupChatWindow::leaveCallback) );
1042     actionGroup->add( Gtk::Action::create("Share",  Gtk::Stock::CONNECT, "Share whiteboard"),
1043         sigc::mem_fun(*this, &GroupChatWindow::shareCallback) );
1046     Glib::RefPtr<Gtk::UIManager> uiManager = Gtk::UIManager::create();
1048     uiManager->insert_action_group(actionGroup, 0);
1049     add_accel_group(uiManager->get_accel_group());
1051     Glib::ustring ui_info =
1052         "<ui>"
1053         "  <menubar name='MenuBar'>"
1054         "    <menu action='MenuFile'>"
1055         "      <menuitem action='Leave'/>"
1056         "      <menuitem action='Share'/>"
1057         "    </menu>"
1058         "  </menubar>"
1059         "</ui>";
1061     add(vbox);
1062     uiManager->add_ui_from_string(ui_info);
1063     Gtk::Widget* pMenuBar = uiManager->get_widget("/MenuBar");
1064     vbox.pack_start(*pMenuBar, Gtk::PACK_SHRINK);
1066     vbox.pack_end(vPaned);
1068     vPaned.add1(hPaned);
1069     vPaned.add2(inputTxt);
1070     inputTxt.signal_activate().connect(
1071            sigc::mem_fun(*this, &GroupChatWindow::textEnterCallback) );
1074     hPaned.add1(messageList);
1075     hPaned.add2(userList);
1078     show_all_children();
1081     return true;
1084 bool GroupChatWindow::receiveMessage(const DOMString &from,
1085                                      const DOMString &data)
1087     messageList.postMessage(from, data);
1088     return true;
1091 bool GroupChatWindow::receivePresence(const DOMString &fromNick,
1092                                       bool presence,
1093                                       const DOMString &show,
1094                                       const DOMString &status)
1097     DOMString presStr = "";
1098     presStr.append(fromNick);
1099     if (!presence)
1100         presStr.append(" left the group");
1101     else
1102         {
1103         if (show.size()<1)
1104             presStr.append(" joined the group");
1105         else
1106             {
1107             presStr.append(" : ");
1108             presStr.append(show);
1109             }
1110         }
1112     if (presStr != "xa")
1113         messageList.postMessage("*", presStr);
1115     userList.clear();
1116     std::vector<XmppUser> memberList =
1117          parent.client.groupChatGetUserList(groupJid);
1118     for (unsigned int i=0 ; i<memberList.size() ; i++)
1119         {
1120         XmppUser user = memberList[i];
1121         userList.addUser(user.nick, user.show);
1122         }
1123     return true;
1127 void GroupChatWindow::doChat(const DOMString &nick)
1129     printf("##Chat with %s\n", nick.c_str());
1130     DOMString fullJid = groupJid;
1131     fullJid.append("/");
1132     fullJid.append(nick);
1133     parent.doChat(fullJid);
1136 void GroupChatWindow::doSendFile(const DOMString &nick)
1138     printf("##Send file to %s\n", nick.c_str());
1139     DOMString fullJid = groupJid;
1140     fullJid.append("/");
1141     fullJid.append(nick);
1142     parent.doSendFile(fullJid);
1146 void GroupChatWindow::doShare(const DOMString &nick)
1148     printf("##Share inkboard with %s\n", nick.c_str());
1149     DOMString fullJid = groupJid;
1150     fullJid.append("/");
1151     fullJid.append(nick);
1152     parent.doShare(fullJid);
1157 //#########################################################################
1158 //# C O N F I G    D I A L O G
1159 //#########################################################################
1162 void ConfigDialog::okCallback()
1164     Glib::ustring pass     = passField.get_text();
1165     Glib::ustring newpass  = newField.get_text();
1166     Glib::ustring confpass = confField.get_text();
1167     if ((pass.size()     < 5 || pass.size()    > 12 ) ||
1168         (newpass.size()  < 5 || newpass.size() > 12 ) ||
1169         (confpass.size() < 5 || confpass.size()> 12 ))
1170         {
1171         Gtk::MessageDialog dlg(*this, "Password must be 5 to 12 characters",
1172             false, Gtk::MESSAGE_ERROR, Gtk::BUTTONS_OK, true);
1173         dlg.run();
1174         }
1175     else if (newpass != confpass)
1176         {
1177         Gtk::MessageDialog dlg(*this, "New password and confirmation do not match",
1178             false, Gtk::MESSAGE_ERROR, Gtk::BUTTONS_OK, true);
1179         dlg.run();
1180         }
1181     else
1182         {
1183         //response(Gtk::RESPONSE_OK);
1184         hide();
1185         }
1188 void ConfigDialog::cancelCallback()
1190     //response(Gtk::RESPONSE_CANCEL);
1191     hide();
1194 void ConfigDialog::on_response(int response_id)
1196     if (response_id == Gtk::RESPONSE_OK)
1197         okCallback();
1198     else
1199         cancelCallback();
1202 bool ConfigDialog::doSetup()
1204     set_title("Change Password");
1205     set_size_request(300,200);
1207     Glib::RefPtr<Gtk::ActionGroup> actionGroup = Gtk::ActionGroup::create();
1208     actionGroup->add( Gtk::Action::create("MenuFile", "_File") );
1209     actionGroup->add( Gtk::Action::create("Change", Gtk::Stock::OK, "Change Password"),
1210         sigc::mem_fun(*this, &ConfigDialog::okCallback) );
1211     actionGroup->add( Gtk::Action::create("Cancel",  Gtk::Stock::CANCEL, "Cancel"),
1212          sigc::mem_fun(*this, &ConfigDialog::cancelCallback) );
1215     Glib::RefPtr<Gtk::UIManager> uiManager = Gtk::UIManager::create();
1217     uiManager->insert_action_group(actionGroup, 0);
1218     add_accel_group(uiManager->get_accel_group());
1220     Glib::ustring ui_info =
1221         "<ui>"
1222         "  <menubar name='MenuBar'>"
1223         "    <menu action='MenuFile'>"
1224         "      <menuitem action='Change'/>"
1225         "      <separator/>"
1226         "      <menuitem action='Cancel'/>"
1227         "    </menu>"
1228         "  </menubar>"
1229         "</ui>";
1231     uiManager->add_ui_from_string(ui_info);
1232     Gtk::Widget* pMenuBar = uiManager->get_widget("/MenuBar");
1233     get_vbox()->pack_start(*pMenuBar, Gtk::PACK_SHRINK);
1235     table.resize(3, 2);
1236     get_vbox()->pack_start(table);
1238     passLabel.set_text("Current Password");
1239     table.attach(passLabel, 0, 1, 0, 1);
1240     passField.set_visibility(false);
1241     passField.set_text(parent.client.getPassword());
1242     table.attach(passField, 1, 2, 0, 1);
1244     newLabel.set_text("New Password");
1245     table.attach(newLabel, 0, 1, 1, 2);
1246     newField.set_visibility(false);
1247     table.attach(newField, 1, 2, 1, 2);
1249     confLabel.set_text("Confirm New Password");
1250     table.attach(confLabel, 0, 1, 2, 3);
1251     confField.set_visibility(false);
1252     confField.signal_activate().connect(
1253            sigc::mem_fun(*this, &ConfigDialog::okCallback) );
1254     table.attach(confField, 1, 2, 2, 3);
1256     add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
1257     add_button(Gtk::Stock::OK,     Gtk::RESPONSE_OK);
1259     show_all_children();
1261     return true;
1264 //#########################################################################
1265 //# P A S S W O R D      D I A L O G
1266 //#########################################################################
1269 void PasswordDialog::okCallback()
1271     Glib::ustring pass     = passField.get_text();
1272     Glib::ustring newpass  = newField.get_text();
1273     Glib::ustring confpass = confField.get_text();
1274     if ((pass.size()     < 5 || pass.size()    > 12 ) ||
1275         (newpass.size()  < 5 || newpass.size() > 12 ) ||
1276         (confpass.size() < 5 || confpass.size()> 12 ))
1277         {
1278         Gtk::MessageDialog dlg(*this, "Password must be 5 to 12 characters",
1279             false, Gtk::MESSAGE_ERROR, Gtk::BUTTONS_OK, true);
1280         dlg.run();
1281         }
1282     else if (newpass != confpass)
1283         {
1284         Gtk::MessageDialog dlg(*this, "New password and confirmation do not match",
1285             false, Gtk::MESSAGE_ERROR, Gtk::BUTTONS_OK, true);
1286         dlg.run();
1287         }
1288     else
1289         {
1290         //response(Gtk::RESPONSE_OK);
1291         hide();
1292         }
1295 void PasswordDialog::cancelCallback()
1297     //response(Gtk::RESPONSE_CANCEL);
1298     hide();
1301 void PasswordDialog::on_response(int response_id)
1303     if (response_id == Gtk::RESPONSE_OK)
1304         okCallback();
1305     else
1306         cancelCallback();
1309 bool PasswordDialog::doSetup()
1311     set_title("Change Password");
1312     set_size_request(300,200);
1314     Glib::RefPtr<Gtk::ActionGroup> actionGroup = Gtk::ActionGroup::create();
1315     actionGroup->add( Gtk::Action::create("MenuFile", "_File") );
1316     actionGroup->add( Gtk::Action::create("Change", Gtk::Stock::OK, "Change Password"),
1317         sigc::mem_fun(*this, &PasswordDialog::okCallback) );
1318     actionGroup->add( Gtk::Action::create("Cancel",  Gtk::Stock::CANCEL, "Cancel"),
1319         sigc::mem_fun(*this, &PasswordDialog::cancelCallback) );
1322     Glib::RefPtr<Gtk::UIManager> uiManager = Gtk::UIManager::create();
1324     uiManager->insert_action_group(actionGroup, 0);
1325     add_accel_group(uiManager->get_accel_group());
1327     Glib::ustring ui_info =
1328         "<ui>"
1329         "  <menubar name='MenuBar'>"
1330         "    <menu action='MenuFile'>"
1331         "      <menuitem action='Change'/>"
1332         "      <separator/>"
1333         "      <menuitem action='Cancel'/>"
1334         "    </menu>"
1335         "  </menubar>"
1336         "</ui>";
1338     uiManager->add_ui_from_string(ui_info);
1339     Gtk::Widget* pMenuBar = uiManager->get_widget("/MenuBar");
1340     get_vbox()->pack_start(*pMenuBar, Gtk::PACK_SHRINK);
1342     table.resize(3, 2);
1343     get_vbox()->pack_start(table);
1345     passLabel.set_text("Current Password");
1346     table.attach(passLabel, 0, 1, 0, 1);
1347     passField.set_visibility(false);
1348     passField.set_text(parent.client.getPassword());
1349     table.attach(passField, 1, 2, 0, 1);
1351     newLabel.set_text("New Password");
1352     table.attach(newLabel, 0, 1, 1, 2);
1353     newField.set_visibility(false);
1354     table.attach(newField, 1, 2, 1, 2);
1356     confLabel.set_text("Confirm New Password");
1357     table.attach(confLabel, 0, 1, 2, 3);
1358     confField.set_visibility(false);
1359     confField.signal_activate().connect(
1360            sigc::mem_fun(*this, &PasswordDialog::okCallback) );
1361     table.attach(confField, 1, 2, 2, 3);
1363     add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
1364     add_button(Gtk::Stock::OK,     Gtk::RESPONSE_OK);
1366     show_all_children();
1368     return true;
1371 //#########################################################################
1372 //# C H A T    D I A L O G
1373 //#########################################################################
1376 void ChatDialog::okCallback()
1378     response(Gtk::RESPONSE_OK);
1379     hide();
1382 void ChatDialog::cancelCallback()
1384     response(Gtk::RESPONSE_CANCEL);
1385     hide();
1389 bool ChatDialog::doSetup()
1391     set_title("Chat with User");
1392     set_size_request(300,200);
1394     Glib::RefPtr<Gtk::ActionGroup> actionGroup = Gtk::ActionGroup::create();
1395     actionGroup->add( Gtk::Action::create("MenuFile", "_File") );
1396     actionGroup->add( Gtk::Action::create("Chat", Gtk::Stock::CONNECT, "Chat"),
1397     sigc::mem_fun(*this, &ChatDialog::okCallback) );
1398     actionGroup->add( Gtk::Action::create("Cancel",  Gtk::Stock::CANCEL, "Cancel"),
1399     sigc::mem_fun(*this, &ChatDialog::cancelCallback) );
1402     Glib::RefPtr<Gtk::UIManager> uiManager = Gtk::UIManager::create();
1404     uiManager->insert_action_group(actionGroup, 0);
1405     add_accel_group(uiManager->get_accel_group());
1407     Glib::ustring ui_info =
1408         "<ui>"
1409         "  <menubar name='MenuBar'>"
1410         "    <menu action='MenuFile'>"
1411         "      <menuitem action='Chat'/>"
1412         "      <separator/>"
1413         "      <menuitem action='Cancel'/>"
1414         "    </menu>"
1415         "  </menubar>"
1416         "</ui>";
1418     uiManager->add_ui_from_string(ui_info);
1419     Gtk::Widget* pMenuBar = uiManager->get_widget("/MenuBar");
1420     get_vbox()->pack_start(*pMenuBar, Gtk::PACK_SHRINK);
1422     table.resize(2, 2);
1423     get_vbox()->pack_start(table);
1425     userLabel.set_text("User");
1426     table.attach(userLabel, 0, 1, 0, 1);
1427     //userField.set_text("");
1428     table.attach(userField, 1, 2, 0, 1);
1430     //userField.set_text("");
1431     table.attach(textField, 0, 2, 1, 2);
1433     add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
1434     add_button(Gtk::Stock::OPEN,   Gtk::RESPONSE_OK);
1436     show_all_children();
1438     return true;
1441 //#########################################################################
1442 //# G R O U P    C H A T   D I A L O G
1443 //#########################################################################
1446 void GroupChatDialog::okCallback()
1448     response(Gtk::RESPONSE_OK);
1449     hide();
1452 void GroupChatDialog::cancelCallback()
1454     response(Gtk::RESPONSE_CANCEL);
1455     hide();
1459 bool GroupChatDialog::doSetup()
1461     set_title("Join Group Chat");
1462     set_size_request(300,200);
1464     Glib::RefPtr<Gtk::ActionGroup> actionGroup = Gtk::ActionGroup::create();
1465     actionGroup->add( Gtk::Action::create("MenuFile", "_File") );
1466     actionGroup->add( Gtk::Action::create("Join", Gtk::Stock::CONNECT, "Join Group"),
1467     sigc::mem_fun(*this, &GroupChatDialog::okCallback) );
1468     actionGroup->add( Gtk::Action::create("Cancel",  Gtk::Stock::CANCEL, "Cancel"),
1469     sigc::mem_fun(*this, &GroupChatDialog::cancelCallback) );
1472     Glib::RefPtr<Gtk::UIManager> uiManager = Gtk::UIManager::create();
1474     uiManager->insert_action_group(actionGroup, 0);
1475     add_accel_group(uiManager->get_accel_group());
1477     Glib::ustring ui_info =
1478         "<ui>"
1479         "  <menubar name='MenuBar'>"
1480         "    <menu action='MenuFile'>"
1481         "      <menuitem action='Join'/>"
1482         "      <separator/>"
1483         "      <menuitem action='Cancel'/>"
1484         "    </menu>"
1485         "  </menubar>"
1486         "</ui>";
1488     uiManager->add_ui_from_string(ui_info);
1489     Gtk::Widget* pMenuBar = uiManager->get_widget("/MenuBar");
1490     get_vbox()->pack_start(*pMenuBar, Gtk::PACK_SHRINK);
1492     table.resize(4, 2);
1493     get_vbox()->pack_start(table);
1495     groupLabel.set_text("Group");
1496     table.attach(groupLabel, 0, 1, 0, 1);
1497     groupField.set_text(parent.config.getMucGroup());
1498     table.attach(groupField, 1, 2, 0, 1);
1500     hostLabel.set_text("Host");
1501     table.attach(hostLabel, 0, 1, 1, 2);
1502     hostField.set_text(parent.config.getMucHost());
1503     table.attach(hostField, 1, 2, 1, 2);
1505     nickLabel.set_text("Alt Name");
1506     table.attach(nickLabel, 0, 1, 2, 3);
1507     nickField.set_text(parent.config.getMucNick());
1508     table.attach(nickField, 1, 2, 2, 3);
1510     passLabel.set_text("Password");
1511     table.attach(passLabel, 0, 1, 3, 4);
1512     passField.set_visibility(false);
1513     passField.set_text(parent.config.getMucPassword());
1514     table.attach(passField, 1, 2, 3, 4);
1517     add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
1518     add_button(Gtk::Stock::OPEN,   Gtk::RESPONSE_OK);
1520     show_all_children();
1522     return true;
1528 //#########################################################################
1529 //# C O N N E C T    D I A L O G
1530 //#########################################################################
1533 void ConnectDialog::okCallback()
1535     response(Gtk::RESPONSE_OK);
1536     hide();
1539 void ConnectDialog::saveCallback()
1541     Gtk::Entry txtField;
1542     Gtk::Dialog dlg("Account name", *this, true, true);
1543     dlg.get_vbox()->pack_start(txtField);
1544     txtField.signal_activate().connect(
1545            sigc::bind(sigc::mem_fun(dlg, &Gtk::Dialog::response),
1546               Gtk::RESPONSE_OK  ));
1547     dlg.add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
1548     dlg.add_button(Gtk::Stock::OK,     Gtk::RESPONSE_OK);
1549     dlg.show_all_children();
1550     int ret = dlg.run();
1551     if (ret != Gtk::RESPONSE_OK)
1552         return;
1554     Glib::ustring name = txtField.get_text();
1555     if (name.size() < 1)
1556         {
1557         parent.error("Account name too short");
1558         return;
1559         }
1561     if (parent.config.accountExists(name))
1562         {
1563         parent.config.accountRemove(name);          
1564         }
1566     XmppAccount account;
1567     account.setName(name);
1568     account.setHost(getHost());
1569     account.setPort(getPort());
1570     account.setUsername(getUser());
1571     account.setPassword(getPass());
1572     parent.config.accountAdd(account);
1574     refresh();
1576     parent.configSave();
1579 void ConnectDialog::cancelCallback()
1581     response(Gtk::RESPONSE_CANCEL);
1582     hide();
1586 void ConnectDialog::doubleClickCallback(
1587                    const Gtk::TreeModel::Path &path,
1588                    Gtk::TreeViewColumn *col)
1590     Glib::RefPtr<Gtk::TreeModel> model = accountView.get_model();
1591     Glib::RefPtr<Gtk::TreeSelection> sel = accountView.get_selection();
1592     Gtk::TreeModel::iterator iter = sel->get_selected();
1593     DOMString name = iter->get_value(accountColumns.nameColumn);
1594     //printf("Double clicked:%s\n", name.c_str());
1595     XmppAccount account;
1596     if (!parent.config.accountFind(name, account))
1597         return;
1598     setHost(account.getHost()); 
1599     setPort(account.getPort()); 
1600     setUser(account.getUsername()); 
1601     setPass(account.getPassword()); 
1603     response(Gtk::RESPONSE_OK);
1604     hide();
1607 void ConnectDialog::selectedCallback()
1609     Glib::RefPtr<Gtk::TreeModel> model = accountView.get_model();
1610     Glib::RefPtr<Gtk::TreeSelection> sel = accountView.get_selection();
1611     Gtk::TreeModel::iterator iter = sel->get_selected();
1612     DOMString name = iter->get_value(accountColumns.nameColumn);
1613     //printf("Single clicked:%s\n", name.c_str());
1614     XmppAccount account;
1615     if (!parent.config.accountFind(name, account))
1616         return;
1617     setHost(account.getHost()); 
1618     setPort(account.getPort()); 
1619     setUser(account.getUsername()); 
1620     setPass(account.getPassword()); 
1623 void ConnectDialog::deleteCallback()
1625     Glib::RefPtr<Gtk::TreeModel> model = accountView.get_model();
1626     Glib::RefPtr<Gtk::TreeSelection> sel = accountView.get_selection();
1627     Gtk::TreeModel::iterator iter = sel->get_selected();
1628     DOMString name = iter->get_value(accountColumns.nameColumn);
1630     parent.config.accountRemove(name);
1631     refresh();
1632     parent.configSave();
1633     
1638 void ConnectDialog::buttonPressCallback(GdkEventButton* event)
1640     if( (event->type == GDK_BUTTON_PRESS) && (event->button == 3) )
1641         {
1642         Gtk::Widget *wid = accountUiManager->get_widget("/PopupMenu");
1643         Gtk::Menu *popupMenu = dynamic_cast<Gtk::Menu*>(wid);
1644         popupMenu->popup(event->button, event->time);
1645         }
1649 bool ConnectDialog::doSetup()
1651     set_title("Connect");
1652     set_size_request(300,400);
1654     Glib::RefPtr<Gtk::ActionGroup> actionGroup = Gtk::ActionGroup::create();
1655     actionGroup->add( Gtk::Action::create("MenuFile", "_File") );
1656     actionGroup->add( Gtk::Action::create("Connect",
1657         Gtk::Stock::CONNECT, "Connect"),
1658         sigc::mem_fun(*this, &ConnectDialog::okCallback) );
1659     actionGroup->add( Gtk::Action::create("Save",
1660         Gtk::Stock::CONNECT, "Save as account"),
1661         sigc::mem_fun(*this, &ConnectDialog::saveCallback) );
1662     actionGroup->add( Gtk::Action::create("Cancel",
1663         Gtk::Stock::CANCEL, "Cancel"),
1664         sigc::mem_fun(*this, &ConnectDialog::cancelCallback) );
1667     Glib::RefPtr<Gtk::UIManager> uiManager = Gtk::UIManager::create();
1669     uiManager->insert_action_group(actionGroup, 0);
1670     add_accel_group(uiManager->get_accel_group());
1672     Glib::ustring ui_info =
1673         "<ui>"
1674         "  <menubar name='MenuBar'>"
1675         "    <menu action='MenuFile'>"
1676         "      <menuitem action='Connect'/>"
1677         "      <separator/>"
1678         "      <menuitem action='Save'/>"
1679         "      <separator/>"
1680         "      <menuitem action='Cancel'/>"
1681         "    </menu>"
1682         "  </menubar>"
1683         "</ui>";
1685     uiManager->add_ui_from_string(ui_info);
1686     Gtk::Widget* pMenuBar = uiManager->get_widget("/MenuBar");
1687     get_vbox()->pack_start(*pMenuBar, Gtk::PACK_SHRINK);
1689     table.resize(6, 2);
1690     get_vbox()->pack_start(table);
1692     parent.client.setHost("broadway.dynalias.com");
1693     parent.client.setPort(5222);
1694     parent.client.setUsername("");
1695     parent.client.setPassword("");
1696     parent.client.setResource("pedroXmpp");
1698     hostLabel.set_text("Host");
1699     table.attach(hostLabel, 0, 1, 0, 1);
1700     hostField.set_text(parent.client.getHost());
1701     table.attach(hostField, 1, 2, 0, 1);
1703     portLabel.set_text("Port");
1704     table.attach(portLabel, 0, 1, 1, 2);
1705     portSpinner.set_digits(0);
1706     portSpinner.set_range(1, 65000);
1707     portSpinner.set_value(parent.client.getPort());
1708     table.attach(portSpinner, 1, 2, 1, 2);
1710     userLabel.set_text("Username");
1711     table.attach(userLabel, 0, 1, 2, 3);
1712     userField.set_text(parent.client.getUsername());
1713     table.attach(userField, 1, 2, 2, 3);
1715     passLabel.set_text("Password");
1716     table.attach(passLabel, 0, 1, 3, 4);
1717     passField.set_visibility(false);
1718     passField.set_text(parent.client.getPassword());
1719     passField.signal_activate().connect(
1720            sigc::mem_fun(*this, &ConnectDialog::okCallback) );
1721     table.attach(passField, 1, 2, 3, 4);
1723     resourceLabel.set_text("Resource");
1724     table.attach(resourceLabel, 0, 1, 4, 5);
1725     resourceField.set_text(parent.client.getResource());
1726     table.attach(resourceField, 1, 2, 4, 5);
1728     registerLabel.set_text("Register");
1729     table.attach(registerLabel, 0, 1, 5, 6);
1730     registerButton.set_active(false);
1731     table.attach(registerButton, 1, 2, 5, 6);
1733     add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
1734     add_button(Gtk::Stock::OPEN,   Gtk::RESPONSE_OK);
1737     //######################
1738     //# ACCOUNT LIST
1739     //######################
1742     accountListStore = Gtk::ListStore::create(accountColumns);
1743     accountView.set_model(accountListStore);
1745     accountView.signal_row_activated().connect(
1746         sigc::mem_fun(*this, &ConnectDialog::doubleClickCallback) );
1748     accountView.get_selection()->signal_changed().connect(
1749         sigc::mem_fun(*this, &ConnectDialog::selectedCallback) );
1751     accountView.append_column("Account", accountColumns.nameColumn);
1752     accountView.append_column("Host",    accountColumns.hostColumn);
1754     //accountView.signal_row_activated().connect(
1755     //    sigc::mem_fun(*this, &AccountDialog::connectCallback) );
1757     accountScroll.add(accountView);
1758     accountScroll.set_policy(Gtk::POLICY_ALWAYS, Gtk::POLICY_ALWAYS);
1760     get_vbox()->pack_start(accountScroll);
1762     //##### POPUP MENU
1763     accountView.signal_button_press_event().connect_notify(
1764         sigc::mem_fun(*this, &ConnectDialog::buttonPressCallback) );
1766     Glib::RefPtr<Gtk::ActionGroup> accountActionGroup =
1767                 Gtk::ActionGroup::create();
1769     accountActionGroup->add( Gtk::Action::create("PopupMenu", "_Account") );
1771     accountActionGroup->add( Gtk::Action::create("Delete",
1772                                   Gtk::Stock::DELETE, "Delete"),
1773         sigc::mem_fun(*this, &ConnectDialog::deleteCallback) );
1776     accountUiManager = Gtk::UIManager::create();
1778     accountUiManager->insert_action_group(accountActionGroup, 0);
1780     Glib::ustring account_ui_info =
1781         "<ui>"
1782         "  <popup name='PopupMenu'>"
1783         "    <menuitem action='Delete'/>"
1784         "  </popup>"
1785         "</ui>";
1787     accountUiManager->add_ui_from_string(account_ui_info);
1788     //Gtk::Widget* accountMenuBar = uiManager->get_widget("/PopupMenu");
1789     //get_vbox()->pack_start(*accountMenuBar, Gtk::PACK_SHRINK);
1791     refresh();
1793     show_all_children();
1795     return true;
1799 /**
1800  * Regenerate the account list
1801  */
1802 void ConnectDialog::refresh()
1804     accountListStore->clear();
1806     std::vector<XmppAccount> accounts = parent.config.getAccounts();
1807     for (unsigned int i=0 ; i<accounts.size() ; i++)
1808         {
1809         XmppAccount account = accounts[i];
1810         Gtk::TreeModel::Row row = *(accountListStore->append());
1811         row[accountColumns.nameColumn] = account.getName();
1812         row[accountColumns.hostColumn] = account.getHost();
1813         }
1814     accountView.expand_all();
1819 //#########################################################################
1820 //# F I L E    S E N D    D I A L O G
1821 //#########################################################################
1824 void FileSendDialog::okCallback()
1826     response(Gtk::RESPONSE_OK);
1827     hide();
1830 void FileSendDialog::cancelCallback()
1832     response(Gtk::RESPONSE_CANCEL);
1833     hide();
1837 void FileSendDialog::buttonCallback()
1839     Gtk::FileChooserDialog dlg("Select a file to send",
1840                       Gtk::FILE_CHOOSER_ACTION_OPEN);
1841     dlg.add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
1842     dlg.add_button(Gtk::Stock::OPEN,   Gtk::RESPONSE_OK);
1843     int ret = dlg.run();
1844     if (ret == Gtk::RESPONSE_OK || ret == Gtk::RESPONSE_ACCEPT)
1845         {
1846         fileName = dlg.get_filename();
1847         fileNameField.set_text(fileName);
1848         }
1851 bool FileSendDialog::doSetup()
1853     set_title("Send file to user");
1854     set_size_request(400,150);
1856     Glib::RefPtr<Gtk::ActionGroup> actionGroup = Gtk::ActionGroup::create();
1857     actionGroup->add( Gtk::Action::create("MenuFile", "_File") );
1858     actionGroup->add( Gtk::Action::create("Send", Gtk::Stock::NETWORK, "Send File"),
1859         sigc::mem_fun(*this, &FileSendDialog::okCallback) );
1860     actionGroup->add( Gtk::Action::create("Cancel",  Gtk::Stock::CANCEL, "Cancel"),
1861         sigc::mem_fun(*this, &FileSendDialog::cancelCallback) );
1864     Glib::RefPtr<Gtk::UIManager> uiManager = Gtk::UIManager::create();
1866     uiManager->insert_action_group(actionGroup, 0);
1867     add_accel_group(uiManager->get_accel_group());
1869     Glib::ustring ui_info =
1870         "<ui>"
1871         "  <menubar name='MenuBar'>"
1872         "    <menu action='MenuFile'>"
1873         "      <menuitem action='Send'/>"
1874         "      <separator/>"
1875         "      <menuitem action='Cancel'/>"
1876         "    </menu>"
1877         "  </menubar>"
1878         "</ui>";
1880     uiManager->add_ui_from_string(ui_info);
1881     Gtk::Widget* pMenuBar = uiManager->get_widget("/MenuBar");
1882     get_vbox()->pack_start(*pMenuBar, Gtk::PACK_SHRINK);
1884     table.resize(2, 2);
1885     get_vbox()->pack_start(table);
1887     jidLabel.set_text("User ID");
1888     table.attach(jidLabel, 0, 1, 0, 1);
1889     jidField.set_text("inkscape");
1890     table.attach(jidField, 1, 2, 0, 1);
1892     selectFileButton.set_label("Select");
1893     selectFileButton.signal_clicked().connect(
1894            sigc::mem_fun(*this, &FileSendDialog::buttonCallback) );
1895     table.attach(selectFileButton, 0, 1, 1, 2);
1897     fileName = "";
1898     fileNameField.set_text("No file selected");
1899     fileNameField.set_editable(false);
1900     table.attach(fileNameField, 1, 2, 1, 2);
1902     add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
1903     add_button(Gtk::Stock::OPEN,   Gtk::RESPONSE_OK);
1905     show_all_children();
1907     return true;
1911 //#########################################################################
1912 //# F I L E    R E C E I V E   D I A L O G
1913 //#########################################################################
1916 void FileReceiveDialog::okCallback()
1918     response(Gtk::RESPONSE_OK);
1919     hide();
1922 void FileReceiveDialog::cancelCallback()
1924     response(Gtk::RESPONSE_CANCEL);
1925     hide();
1928 void FileReceiveDialog::buttonCallback()
1930     Gtk::FileChooserDialog dlg("Select a file to save",
1931                       Gtk::FILE_CHOOSER_ACTION_SAVE);
1932     dlg.add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
1933     dlg.add_button(Gtk::Stock::OPEN,   Gtk::RESPONSE_OK);
1934     int ret = dlg.run();
1935     if (ret == Gtk::RESPONSE_OK || ret == Gtk::RESPONSE_ACCEPT)
1936         {
1937         fileName = dlg.get_filename();
1938         fileNameField.set_text(fileName);
1939         }
1943 bool FileReceiveDialog::doSetup()
1945     set_title("File being sent by user");
1946     set_size_request(450,250);
1948     Glib::RefPtr<Gtk::ActionGroup> actionGroup = Gtk::ActionGroup::create();
1949     actionGroup->add( Gtk::Action::create("MenuFile", "_File") );
1950     actionGroup->add( Gtk::Action::create("Send", Gtk::Stock::NETWORK, "Send File"),
1951         sigc::mem_fun(*this, &FileReceiveDialog::okCallback) );
1952     actionGroup->add( Gtk::Action::create("Cancel",  Gtk::Stock::CANCEL, "Cancel"),
1953         sigc::mem_fun(*this, &FileReceiveDialog::cancelCallback) );
1956     Glib::RefPtr<Gtk::UIManager> uiManager = Gtk::UIManager::create();
1958     uiManager->insert_action_group(actionGroup, 0);
1959     add_accel_group(uiManager->get_accel_group());
1961     Glib::ustring ui_info =
1962         "<ui>"
1963         "  <menubar name='MenuBar'>"
1964         "    <menu action='MenuFile'>"
1965         "      <menuitem action='Send'/>"
1966         "      <separator/>"
1967         "      <menuitem action='Cancel'/>"
1968         "    </menu>"
1969         "  </menubar>"
1970         "</ui>";
1972     uiManager->add_ui_from_string(ui_info);
1973     Gtk::Widget* pMenuBar = uiManager->get_widget("/MenuBar");
1974     get_vbox()->pack_start(*pMenuBar, Gtk::PACK_SHRINK);
1976     table.resize(6, 2);
1977     get_vbox()->pack_start(table);
1979     jidLabel.set_text("User ID");
1980     table.attach(jidLabel, 0, 1, 0, 1);
1981     jidField.set_text(jid);
1982     jidField.set_editable(false);
1983     table.attach(jidField, 1, 2, 0, 1);
1985     offeredLabel.set_text("File Offered");
1986     table.attach(offeredLabel, 0, 1, 1, 2);
1987     offeredField.set_text(offeredName);
1988     offeredField.set_editable(false);
1989     table.attach(offeredField, 1, 2, 1, 2);
1991     descLabel.set_text("Description");
1992     table.attach(descLabel, 0, 1, 2, 3);
1993     descField.set_text(desc);
1994     descField.set_editable(false);
1995     table.attach(descField, 1, 2, 2, 3);
1997     char buf[32];
1998     snprintf(buf, 31, "%ld", fileSize);
1999     sizeLabel.set_text("Size");
2000     table.attach(sizeLabel, 0, 1, 3, 4);
2001     sizeField.set_text(buf);
2002     sizeField.set_editable(false);
2003     table.attach(sizeField, 1, 2, 3, 4);
2005     hashLabel.set_text("MD5 Hash");
2006     table.attach(hashLabel, 0, 1, 4, 5);
2007     hashField.set_text(hash);
2008     hashField.set_editable(false);
2009     table.attach(hashField, 1, 2, 4, 5);
2011     selectFileButton.set_label("Select");
2012     selectFileButton.signal_clicked().connect(
2013            sigc::mem_fun(*this, &FileReceiveDialog::buttonCallback) );
2014     table.attach(selectFileButton, 0, 1, 5, 6);
2016     fileName = "";
2017     fileNameField.set_text("No file selected");
2018     fileNameField.set_editable(false);
2019     table.attach(fileNameField, 1, 2, 5, 6);
2022     add_button(Gtk::Stock::CANCEL, Gtk::RESPONSE_CANCEL);
2023     add_button(Gtk::Stock::OPEN,   Gtk::RESPONSE_OK);
2025     show_all_children();
2027     return true;
2031 //#########################################################################
2032 //# M A I N    W I N D O W
2033 //#########################################################################
2035 PedroGui::PedroGui()
2037     doSetup();
2040 PedroGui::~PedroGui()
2042     chatDeleteAll();
2043     groupChatDeleteAll();
2047 void PedroGui::error(const char *fmt, ...)
2049     va_list args;
2050     va_start(args, fmt);
2051     vsnprintf(writeBuf, writeBufLen, fmt, args);
2052     va_end(args) ;
2054     Gtk::MessageDialog dlg(writeBuf,
2055                            false,
2056                            Gtk::MESSAGE_ERROR,
2057                            Gtk::BUTTONS_OK,
2058                            true);
2059     dlg.run();
2062 void PedroGui::status(const char *fmt, ...)
2064     va_list args;
2065     va_start(args, fmt);
2066     vsnprintf(writeBuf, writeBufLen, fmt, args);
2067     va_end(args) ;
2068     messageList.postMessage("STATUS", writeBuf);
2071 //################################
2072 //# CHAT WINDOW MANAGEMENT
2073 //################################
2074 bool PedroGui::chatCreate(const DOMString &userJid)
2076     std::vector<ChatWindow *>::iterator iter;
2077     for (iter=chats.begin() ; iter != chats.end() ; iter++)
2078         {
2079         if (userJid == (*iter)->getJid())
2080             return false;
2081         }
2082     ChatWindow *chat = new ChatWindow(*this, userJid);
2083     chat->show();
2084     chats.push_back(chat);
2085     return true;
2088 bool PedroGui::chatDelete(const DOMString &userJid)
2090     std::vector<ChatWindow *>::iterator iter;
2091     for (iter=chats.begin() ; iter != chats.end() ; )
2092         {
2093         if (userJid == (*iter)->getJid())
2094             {
2095             delete(*iter);
2096             iter = chats.erase(iter);
2097             }
2098         else
2099             iter++;
2100         }
2101     return true;
2104 bool PedroGui::chatDeleteAll()
2106     std::vector<ChatWindow *>::iterator iter;
2107     for (iter=chats.begin() ; iter != chats.end() ; )
2108         {
2109         delete(*iter);
2110         iter = chats.erase(iter);
2111         }
2112     return true;
2115 bool PedroGui::chatMessage(const DOMString &from, const DOMString &data)
2117     std::vector<ChatWindow *>::iterator iter;
2118     for (iter=chats.begin() ; iter != chats.end() ; iter++)
2119         {
2120         if (from == (*iter)->getJid())
2121             {
2122             (*iter)->postMessage(data);
2123             return true;
2124             }
2125         }
2126     ChatWindow *chat = new ChatWindow(*this, from);
2127     chat->show();
2128     chats.push_back(chat);
2129     chat->postMessage(data);
2130     return true;
2134 //################################
2135 //# GROUP CHAT WINDOW MANAGEMENT
2136 //################################
2138 bool PedroGui::groupChatCreate(const DOMString &groupJid, const DOMString &nick)
2140     std::vector<GroupChatWindow *>::iterator iter;
2141     for (iter=groupChats.begin() ; iter != groupChats.end() ; iter++)
2142         {
2143         if (groupJid == (*iter)->getGroupJid())
2144             return false;
2145         }
2146     GroupChatWindow *chat = new GroupChatWindow(*this, groupJid, nick);
2147     chat->show();
2148     groupChats.push_back(chat);
2149     return true;
2153 bool PedroGui::groupChatDelete(const DOMString &groupJid, const DOMString &nick)
2155     std::vector<GroupChatWindow *>::iterator iter;
2156     for (iter=groupChats.begin() ; iter != groupChats.end() ;)
2157         {
2158         if (groupJid == (*iter)->getGroupJid() &&
2159             nick     == (*iter)->getNick())
2160             {
2161             delete(*iter);
2162             iter = groupChats.erase(iter);
2163             }
2164         else
2165             iter++;
2166         }
2167     return true;
2171 bool PedroGui::groupChatDeleteAll()
2173     std::vector<GroupChatWindow *>::iterator iter;
2174     for (iter=groupChats.begin() ; iter != groupChats.end() ; )
2175         {
2176         delete(*iter);
2177         iter = groupChats.erase(iter);
2178         }
2179     return true;
2183 bool PedroGui::groupChatMessage(const DOMString &groupJid,
2184               const DOMString &from, const DOMString &data)
2186     std::vector<GroupChatWindow *>::iterator iter;
2187     for (iter=groupChats.begin() ; iter != groupChats.end() ; iter++)
2188         {
2189         if (groupJid == (*iter)->getGroupJid())
2190             {
2191             (*iter)->receiveMessage(from, data);
2192             }
2193         }
2194     return true;
2197 bool PedroGui::groupChatPresence(const DOMString &groupJid,
2198                       const DOMString &nick, bool presence,
2199                       const DOMString &show,
2200                       const DOMString &status)
2202     std::vector<GroupChatWindow *>::iterator iter;
2203     for (iter=groupChats.begin() ; iter != groupChats.end() ; iter++)
2204         {
2205         if (groupJid == (*iter)->getGroupJid())
2206             {
2207             (*iter)->receivePresence(nick, presence, show, status);
2208             }
2209         }
2210     return true;
2213 //################################
2214 //# EVENTS
2215 //################################
2217 /**
2218  *
2219  */
2220 void PedroGui::padlockEnable()
2222     padlockIcon.set(Gtk::Stock::DIALOG_AUTHENTICATION,
2223                Gtk::ICON_SIZE_MENU);
2226 /**
2227  *
2228  */
2229 void PedroGui::padlockDisable()
2231     padlockIcon.clear();
2235 /**
2236  *
2237  */
2238 void PedroGui::handleConnectEvent()
2240      status("##### CONNECTED");
2241      actionEnable("Connect",    false);
2242      actionEnable("Chat",       true);
2243      actionEnable("GroupChat",  true);
2244      actionEnable("Disconnect", true);
2245      actionEnable("RegPass",    true);
2246      actionEnable("RegCancel",  true);
2247      DOMString title = "Pedro - ";
2248      title.append(client.getJid());
2249      set_title(title);
2253 /**
2254  *
2255  */
2256 void PedroGui::handleDisconnectEvent()
2258      status("##### DISCONNECTED");
2259      actionEnable("Connect",    true);
2260      actionEnable("Chat",       false);
2261      actionEnable("GroupChat",  false);
2262      actionEnable("Disconnect", false);
2263      actionEnable("RegPass",    false);
2264      actionEnable("RegCancel",  false);
2265      padlockDisable();
2266      DOMString title = "Pedro";
2267      set_title(title);
2268      chatDeleteAll();
2269      groupChatDeleteAll();
2270      roster.clear();
2274 /**
2275  *
2276  */
2277 void PedroGui::doEvent(const XmppEvent &event)
2280     int typ = event.getType();
2281     switch (typ)
2282         {
2283         case XmppEvent::EVENT_STATUS:
2284             {
2285             //printf("##### STATUS: %s\n", event.getData().c_str());
2286             status(event.getData().c_str());
2287             break;
2288             }
2289         case XmppEvent::EVENT_ERROR:
2290             {
2291             //printf("##### ERROR: %s\n", event.getData().c_str());
2292             error(event.getData().c_str());
2293             padlockDisable();
2294             break;
2295             }
2296         case XmppEvent::EVENT_SSL_STARTED:
2297             {
2298             padlockEnable();
2299             break;
2300             }
2301         case XmppEvent::EVENT_CONNECTED:
2302             {
2303             handleConnectEvent();
2304             break;
2305             }
2306         case XmppEvent::EVENT_DISCONNECTED:
2307             {
2308             handleDisconnectEvent();
2309             break;
2310             }
2311         case XmppEvent::EVENT_MESSAGE:
2312             {
2313             status("##### MESSAGE: %s\n", event.getFrom().c_str());
2314             chatMessage(event.getFrom(), event.getData());
2315             break;
2316             }
2317         case XmppEvent::EVENT_PRESENCE:
2318             {
2319             status("##### PRESENCE: %s\n", event.getFrom().c_str());
2320             roster.refresh();
2321             break;
2322             }
2323         case XmppEvent::EVENT_ROSTER:
2324             {
2325             status("##### ROSTER\n");
2326             roster.refresh();
2327             break;
2328             }
2329         case XmppEvent::EVENT_MUC_JOIN:
2330             {
2331             status("##### GROUP JOINED: %s\n", event.getGroup().c_str());
2332             break;
2333             }
2334         case XmppEvent::EVENT_MUC_MESSAGE:
2335             {
2336             //printf("##### MUC_MESSAGE: %s\n", event.getGroup().c_str());
2337             groupChatMessage(event.getGroup(),
2338                     event.getFrom(), event.getData());
2339             break;
2340             }
2341         case XmppEvent::EVENT_MUC_PRESENCE:
2342             {
2343             //printf("##### MUC_USER LIST: %s\n", event.getFrom().c_str());
2344             groupChatPresence(event.getGroup(),
2345                               event.getFrom(),
2346                               event.getPresence(),
2347                               event.getShow(),
2348                               event.getStatus());
2349             break;
2350             }
2351         case XmppEvent::EVENT_MUC_LEAVE:
2352             {
2353             status("##### GROUP LEFT: %s\n", event.getGroup().c_str());
2354             groupChatDelete(event.getGroup(), event.getFrom());
2355             break;
2356             }
2357         case XmppEvent::EVENT_FILE_RECEIVE:
2358             {
2359             status("##### FILE RECEIVE: %s\n", event.getFileName().c_str());
2360             doReceiveFile(event.getFrom(), event.getIqId(), event.getStreamId(),
2361                        event.getFileName(), event.getFileDesc(),
2362                        event.getFileSize(), event.getFileHash());
2363             break;
2364             }
2365         case XmppEvent::EVENT_REGISTRATION_NEW:
2366             {
2367             status("##### REGISTERED: %s at %s\n",
2368                        event.getTo().c_str(), event.getFrom().c_str());
2369             break;
2370             }
2371         case XmppEvent::EVENT_REGISTRATION_CHANGE_PASS:
2372             {
2373             status("##### PASSWORD CHANGED: %s at %s\n",
2374                        event.getTo().c_str(), event.getFrom().c_str());
2375             break;
2376             }
2377         case XmppEvent::EVENT_REGISTRATION_CANCEL:
2378             {
2379             //client.disconnect();
2380             status("##### REGISTERATION CANCELLED: %s at %s\n",
2381                        event.getTo().c_str(), event.getFrom().c_str());
2382             break;
2383             }
2384         default:
2385             {
2386             printf("unknown event type: %d\n", typ);
2387             break;
2388             }
2389         }
2393 /**
2394  *
2395  */
2396 bool PedroGui::checkEventQueue()
2398     while (client.eventQueueAvailable() > 0)
2399         {
2400         XmppEvent evt = client.eventQueuePop();
2401         doEvent(evt);
2402         }
2404     while( Gtk::Main::events_pending() )
2405         Gtk::Main::iteration();
2407     return true;
2411 //##################
2412 //# COMMANDS
2413 //##################
2414 void PedroGui::doChat(const DOMString &jid)
2416     if (jid.size()>0)
2417         {
2418         chatCreate(jid);
2419         return;
2420         }
2422     FileSendDialog dlg(*this);
2423     int ret = dlg.run();
2424     if (ret == Gtk::RESPONSE_OK)
2425         {
2426         chatCreate(dlg.getJid());
2427         }
2431 void PedroGui::doSendFile(const DOMString &jid)
2433     FileSendDialog dlg(*this);
2434     if (jid.size()>0)
2435         dlg.setJid(jid);
2436     int ret = dlg.run();
2437     if (ret == Gtk::RESPONSE_OK)
2438         {
2439         DOMString fileName = dlg.getFileName();
2440         printf("fileName:%s\n", fileName.c_str());
2441         DOMString offeredName = "";
2442         DOMString desc = "";
2443         client.fileSendBackground(jid, offeredName, fileName, desc);
2444         }
2448 void PedroGui::doReceiveFile(
2449                       const DOMString &jid,
2450                       const DOMString &iqId,
2451                       const DOMString &streamId,
2452                       const DOMString &offeredName,
2453                       const DOMString &desc,
2454                       long  size,
2455                       const DOMString &hash
2456                       )
2459     FileReceiveDialog dlg(*this, jid, iqId, streamId,
2460                           offeredName, desc, size, hash);
2461     int ret = dlg.run();
2462     if (ret == Gtk::RESPONSE_OK)
2463         {
2464         DOMString fileName = dlg.getFileName();
2465         printf("fileName:%s\n", fileName.c_str());
2466         client.fileReceiveBackground(jid, iqId, streamId, fileName, size, hash);
2467         }
2471 void PedroGui::doShare(const DOMString &jid)
2473     Inkscape::Whiteboard::SessionManager& sm = Inkscape::Whiteboard::SessionManager::instance();
2474     sm.doShare(jid, Inkscape::Whiteboard::INKBOARD_PRIVATE);
2476 //  Inkscape::Whiteboard::SessionManager::instance().createInkboardDesktop(jid, Inkscape::Whiteboard::INKBOARD_PRIVATE);
2479 void PedroGui::doGroupShare(const DOMString &groupJid)
2481     Inkscape::Whiteboard::SessionManager& sm = Inkscape::Whiteboard::SessionManager::instance();
2482     sm.doShare(groupJid, Inkscape::Whiteboard::INKBOARD_MUC);
2484 //  Inkscape::Whiteboard::SessionManager::instance().createInkboardDesktop(groupJid, Inkscape::Whiteboard::INKBOARD_MUC);
2487 //##################
2488 //# CALLBACKS
2489 //##################
2490 void PedroGui::connectCallback()
2492     ConnectDialog dialog(*this);
2493     int result = dialog.run();
2494     dialog.hide();
2495     if (result == Gtk::RESPONSE_OK)
2496         {
2497         client.setHost(dialog.getHost());
2498         client.setPort(dialog.getPort());
2499         client.setUsername(dialog.getUser());
2500         client.setPassword(dialog.getPass());
2501         client.setResource(dialog.getResource());
2502         client.setDoRegister(dialog.getRegister());
2503         client.connect();
2504         }
2509 void PedroGui::chatCallback()
2511     ChatDialog dialog(*this);
2512     int result = dialog.run();
2513     dialog.hide();
2514     if (result == Gtk::RESPONSE_OK)
2515         {
2516         client.message(dialog.getUser(), dialog.getText());
2517         }
2522 void PedroGui::groupChatCallback()
2524     GroupChatDialog dialog(*this);
2525     int result = dialog.run();
2526     dialog.hide();
2527     if (result != Gtk::RESPONSE_OK)
2528         return;
2529     DOMString groupJid = dialog.getGroup();
2530     groupJid.append("@");
2531     groupJid.append(dialog.getHost());
2532     if (client.groupChatExists(groupJid))
2533         {
2534         error("Group chat %s already exists", groupJid.c_str());
2535         return;
2536         }
2537     groupChatCreate(groupJid, dialog.getNick());
2538     client.groupChatJoin(groupJid, dialog.getNick(), dialog.getPass() );
2539     config.setMucGroup(dialog.getGroup());
2540     config.setMucHost(dialog.getHost());
2541     config.setMucNick(dialog.getNick());
2542     config.setMucPassword(dialog.getPass());
2543  
2544     configSave();
2548 void PedroGui::disconnectCallback()
2550     client.disconnect();
2554 void PedroGui::quitCallback()
2556     Gtk::Main::quit();
2560 void PedroGui::fontCallback()
2562     Gtk::FontSelectionDialog dlg;
2563     int ret = dlg.run();
2564     if (ret == Gtk::RESPONSE_OK)
2565         {
2566         Glib::ustring fontName = dlg.get_font_name();
2567         Pango::FontDescription fontDesc(fontName);
2568         modify_font(fontDesc);
2569         }
2572 void PedroGui::colorCallback()
2574     Gtk::ColorSelectionDialog dlg;
2575     int ret = dlg.run();
2576     if (ret == Gtk::RESPONSE_OK)
2577         {
2578         Gdk::Color col = dlg.get_colorsel()->get_current_color();
2579         modify_bg(Gtk::STATE_NORMAL, col);
2580         }
2583 void PedroGui::regPassCallback()
2585     PasswordDialog dlg(*this);
2586     int ret = dlg.run();
2587     if (ret == Gtk::RESPONSE_OK)
2588         {
2589         DOMString newpass = dlg.getNewPass();
2590         client.inBandRegistrationChangePassword(newpass);
2591         }
2595 void PedroGui::regCancelCallback()
2597     Gtk::MessageDialog dlg(*this, "Do you want to cancel your registration on the server?",
2598         false, Gtk::MESSAGE_QUESTION, Gtk::BUTTONS_YES_NO, true);
2599     int ret = dlg.run();
2600     if (ret == Gtk::RESPONSE_YES)
2601         {
2602         client.inBandRegistrationCancel();
2603         }
2608 void PedroGui::sendFileCallback()
2610     doSendFile("");
2615 void PedroGui::aboutCallback()
2617     Gtk::AboutDialog dlg;
2618     std::vector<Glib::ustring>authors;
2619     authors.push_back("Bob Jamison");
2620     dlg.set_authors(authors);
2621     DOMString comments = "A simple XMPP gui client  ";
2622     comments.append("Based on the Pedro XMPP client");
2623     dlg.set_comments(comments);
2624     dlg.set_version("1.0");
2625     dlg.run();
2630 void PedroGui::actionEnable(const DOMString &name, bool val)
2632     DOMString path = "/ui/MenuBar/";
2633     path.append(name);
2634     Glib::RefPtr<Gtk::Action> action = uiManager->get_action(path);
2635     if (!action)
2636         {
2637         path = "/ui/MenuBar/MenuFile/";
2638         path.append(name);
2639         action = uiManager->get_action(path);
2640         }
2641     if (!action)
2642         {
2643         path = "/ui/MenuBar/MenuEdit/";
2644         path.append(name);
2645         action = uiManager->get_action(path);
2646         }
2647     if (!action)
2648         {
2649         path = "/ui/MenuBar/MenuRegister/";
2650         path.append(name);
2651         action = uiManager->get_action(path);
2652         }
2653     if (!action)
2654         {
2655         path = "/ui/MenuBar/MenuTransfer/";
2656         path.append(name);
2657         action = uiManager->get_action(path);
2658         }
2659     if (!action)
2660         {
2661         path = "/ui/MenuBar/MenuHelp/";
2662         path.append(name);
2663         action = uiManager->get_action(path);
2664         }
2665     if (!action)
2666         return;
2667     action->set_sensitive(val);
2671 bool PedroGui::configLoad()
2673     if (!config.readFile("pedro.ini"))
2674         return false;
2675     return true;
2679 bool PedroGui::configSave()
2681     if (!config.writeFile("pedro.ini"))
2682         return false;
2683     return true;
2689 bool PedroGui::doSetup()
2691     configLoad();
2693     set_title("Pedro XMPP Client");
2694     set_size_request(500, 300);
2695     add(mainBox);
2697     Glib::RefPtr<Gtk::ActionGroup> actionGroup = Gtk::ActionGroup::create();
2699     //### FILE MENU
2700     actionGroup->add( Gtk::Action::create("MenuFile", "_File") );
2702     actionGroup->add( Gtk::Action::create("Connect",
2703                                   Gtk::Stock::CONNECT, "Connect"),
2704     sigc::mem_fun(*this, &PedroGui::connectCallback) );
2706     actionGroup->add( Gtk::Action::create("Chat",
2707                                   Gtk::Stock::CONNECT, "Chat"),
2708     sigc::mem_fun(*this, &PedroGui::chatCallback) );
2710     actionGroup->add( Gtk::Action::create("GroupChat",
2711                                   Gtk::Stock::CONNECT, "Group Chat"),
2712     sigc::mem_fun(*this, &PedroGui::groupChatCallback) );
2714     actionGroup->add( Gtk::Action::create("Disconnect",
2715                                   Gtk::Stock::DISCONNECT, "Disconnect"),
2716     sigc::mem_fun(*this, &PedroGui::disconnectCallback) );
2718     actionGroup->add( Gtk::Action::create("Quit", Gtk::Stock::QUIT),
2719     sigc::mem_fun(*this, &PedroGui::quitCallback) );
2721     //### EDIT MENU
2722     actionGroup->add( Gtk::Action::create("MenuEdit", "_Edit") );
2723     actionGroup->add( Gtk::Action::create("SelectFont",
2724                                   Gtk::Stock::SELECT_FONT, "Select Font"),
2725     sigc::mem_fun(*this, &PedroGui::fontCallback) );
2726     actionGroup->add( Gtk::Action::create("SelectColor",
2727                                   Gtk::Stock::SELECT_COLOR, "Select Color"),
2728     sigc::mem_fun(*this, &PedroGui::colorCallback) );
2730     //### REGISTER MENU
2731     actionGroup->add( Gtk::Action::create("MenuRegister", "_Registration") );
2732     actionGroup->add( Gtk::Action::create("RegPass",
2733                                   Gtk::Stock::DIALOG_AUTHENTICATION, "Change Password"),
2734     sigc::mem_fun(*this, &PedroGui::regPassCallback) );
2735     actionGroup->add( Gtk::Action::create("RegCancel",
2736                                   Gtk::Stock::CANCEL, "Cancel Registration"),
2737     sigc::mem_fun(*this, &PedroGui::regCancelCallback) );
2739     //### TRANSFER MENU
2740     actionGroup->add( Gtk::Action::create("MenuTransfer", "_Transfer") );
2741     actionGroup->add( Gtk::Action::create("SendFile",
2742                                   Gtk::Stock::NETWORK, "Send File"),
2743     sigc::mem_fun(*this, &PedroGui::sendFileCallback) );
2745     //### HELP MENU
2746     actionGroup->add( Gtk::Action::create("MenuHelp", "_Help") );
2747     actionGroup->add( Gtk::Action::create("About",
2748                                   Gtk::Stock::ABOUT, "About Pedro"),
2749     sigc::mem_fun(*this, &PedroGui::aboutCallback) );
2751     uiManager = Gtk::UIManager::create();
2753     uiManager->insert_action_group(actionGroup, 0);
2754     add_accel_group(uiManager->get_accel_group());
2756     Glib::ustring ui_info =
2757         "<ui>"
2758         "  <menubar name='MenuBar'>"
2759         "    <menu action='MenuFile'>"
2760         "      <menuitem action='Connect'/>"
2761         "      <separator/>"
2762         "      <menuitem action='Chat'/>"
2763         "      <menuitem action='GroupChat'/>"
2764         "      <separator/>"
2765         "      <menuitem action='Disconnect'/>"
2766         "      <menuitem action='Quit'/>"
2767         "    </menu>"
2768         "    <menu action='MenuEdit'>"
2769         "      <menuitem action='SelectFont'/>"
2770         "      <menuitem action='SelectColor'/>"
2771         "    </menu>"
2772         "    <menu action='MenuRegister'>"
2773         "      <menuitem action='RegPass'/>"
2774         "      <menuitem action='RegCancel'/>"
2775         "    </menu>"
2776         "    <menu action='MenuTransfer'>"
2777         "      <menuitem action='SendFile'/>"
2778         "    </menu>"
2779         "    <menu action='MenuHelp'>"
2780         "      <menuitem action='About'/>"
2781         "    </menu>"
2782         "  </menubar>"
2783         "</ui>";
2785     uiManager->add_ui_from_string(ui_info);
2786     Gtk::Widget* pMenuBar = uiManager->get_widget("/MenuBar");
2787     menuBarBox.pack_start(*pMenuBar, Gtk::PACK_SHRINK);
2789     padlockDisable();
2790     menuBarBox.pack_end(padlockIcon, Gtk::PACK_SHRINK);
2792     mainBox.pack_start(menuBarBox, Gtk::PACK_SHRINK);
2794     actionEnable("Connect",    true);
2795     actionEnable("Chat",       false);
2796     actionEnable("GroupChat",  false);
2797     actionEnable("Disconnect", false);
2798     actionEnable("RegPass",    false);
2799     actionEnable("RegCancel",  false);
2801     mainBox.pack_start(vPaned);
2802     vPaned.add1(roster);
2803     vPaned.add2(messageList);
2804     roster.setParent(this);
2806     show_all_children();
2808     //# Start a timer to check the queue every nn milliseconds
2809     Glib::signal_timeout().connect(
2810            sigc::mem_fun(*this, &PedroGui::checkEventQueue), 20 );
2812     //client.addXmppEventListener(*this);
2813     client.eventQueueEnable(true);
2815     return true;
2819 } // namespace Pedro
2823 //########################################################################
2824 //# E N D    O F     F I L E
2825 //########################################################################