comparison src/gtkpounce.c @ 5032:cb700c07ee07

[gaim-migrate @ 5375] Rewrote the buddy pounce code. It's now core/UI split, and may allow for more advanced stuff later. Pounce actions are now a UI thing, and the backend logic for registering, unregistering, and activating pouncs is now in core. Also, the buddy pounce dialog was redesigned. Oh, and there are new pounce types. You can now choose from: * Sign on * Sign off * Away * Return from away * Idle * Return from idle * Buddy starts typing * Buddy stops typing Should work. I've been using it for some time. If you find a bug, though, let me know. committer: Tailor Script <tailor@pidgin.im>
author Christian Hammond <chipx86@chipx86.com>
date Sat, 05 Apr 2003 10:14:21 +0000
parents
children b3d9195777bb
comparison
equal deleted inserted replaced
5031:bc494c4a3991 5032:cb700c07ee07
1 /**
2 * @file gtkpounce.h GTK+ buddy pounce API
3 *
4 * gaim
5 *
6 * Copyright (C) 2003, Christian Hammond <chipx86@gnupdate.org>
7 *
8 * This program is free software; you can redistribute it and/or modify
9 * it under the terms of the GNU General Public License as published by
10 * the Free Software Foundation; either version 2 of the License, or
11 * (at your option) any later version.
12 *
13 * This program is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 * GNU General Public License for more details.
17 *
18 * You should have received a copy of the GNU General Public License
19 * along with this program; if not, write to the Free Software
20 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
21 *
22 */
23 #include "gaim.h"
24 #include "gtkpounce.h"
25 #include "gtklist.h"
26 #include "prpl.h"
27 #include "sound.h"
28
29 struct gaim_gtkpounce_dialog
30 {
31 /* Pounce data */
32 struct gaim_pounce *pounce;
33 struct gaim_account *account;
34
35 /* The window */
36 GtkWidget *window;
37
38 /* Pounce Who */
39 GtkWidget *account_menu;
40 GtkWidget *buddy_entry;
41
42 /* Pounce When */
43 GtkWidget *signon;
44 GtkWidget *signoff;
45 GtkWidget *away;
46 GtkWidget *away_return;
47 GtkWidget *idle;
48 GtkWidget *idle_return;
49 GtkWidget *typing;
50 GtkWidget *stop_typing;
51
52 /* Pounce Action */
53 GtkWidget *open_win;
54 GtkWidget *popup;
55 GtkWidget *send_msg;
56 GtkWidget *send_msg_entry;
57 GtkWidget *exec_cmd;
58 GtkWidget *exec_cmd_entry;
59 GtkWidget *play_sound;
60 GtkWidget *play_sound_entry;
61
62 GtkWidget *save_pounce;
63 };
64
65 /**************************************************************************
66 * Callbacks
67 **************************************************************************/
68 static gint
69 delete_win_cb(GtkWidget *w, GdkEventAny *e,
70 struct gaim_gtkpounce_dialog *dialog)
71 {
72 gtk_widget_destroy(dialog->window);
73 g_free(dialog);
74
75 return TRUE;
76 }
77
78 static void
79 cancel_cb(GtkWidget *w, struct gaim_gtkpounce_dialog *dialog)
80 {
81 delete_win_cb(NULL, NULL, dialog);
82 }
83
84
85 static void
86 save_pounce_cb(GtkWidget *w, struct gaim_gtkpounce_dialog *dialog)
87 {
88 const char *name;
89 const char *message, *command, *sound;
90 struct gaim_buddy_list *blist;
91 struct gaim_gtk_buddy_list *gtkblist;
92 GaimPounceEvent events = GAIM_POUNCE_NONE;
93 GaimGtkPounceAction actions = GAIM_GTKPOUNCE_NONE;
94 gboolean save;
95
96 name = gtk_entry_get_text(GTK_ENTRY(dialog->buddy_entry));
97
98 if (*name == '\0') {
99 do_error_dialog(_("Please enter a buddy to pounce."), NULL, GAIM_ERROR);
100 return;
101 }
102
103 /* Events */
104 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->signon)))
105 events |= GAIM_POUNCE_SIGNON;
106
107 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->signoff)))
108 events |= GAIM_POUNCE_SIGNOFF;
109
110 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->away)))
111 events |= GAIM_POUNCE_AWAY;
112
113 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->away_return)))
114 events |= GAIM_POUNCE_AWAY_RETURN;
115
116 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->idle)))
117 events |= GAIM_POUNCE_IDLE;
118
119 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->idle_return)))
120 events |= GAIM_POUNCE_IDLE_RETURN;
121
122 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->typing)))
123 events |= GAIM_POUNCE_TYPING;
124
125 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->stop_typing)))
126 events |= GAIM_POUNCE_TYPING_STOPPED;
127
128
129 /* Actions */
130 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->open_win)))
131 actions |= GAIM_GTKPOUNCE_OPEN_WIN;
132
133 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->popup)))
134 actions |= GAIM_GTKPOUNCE_POPUP;
135
136 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->send_msg)))
137 actions |= GAIM_GTKPOUNCE_SEND_MSG;
138
139 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->exec_cmd)))
140 actions |= GAIM_GTKPOUNCE_EXEC_CMD;
141
142 if (gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->play_sound)))
143 actions |= GAIM_GTKPOUNCE_PLAY_SOUND;
144
145 save = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(dialog->save_pounce));
146
147 /* Data fields */
148 message = gtk_entry_get_text(GTK_ENTRY(dialog->send_msg_entry));
149 command = gtk_entry_get_text(GTK_ENTRY(dialog->exec_cmd_entry));
150 sound = gtk_entry_get_text(GTK_ENTRY(dialog->play_sound_entry));
151
152 if (*message == '\0') message = NULL;
153 if (*command == '\0') command = NULL;
154 if (*sound == '\0') sound = NULL;
155
156 if (dialog->pounce == NULL)
157 {
158 gaim_gtkpounce_new(dialog->account, name, events, actions,
159 message, command, sound, save);
160 }
161 else
162 {
163 struct gaim_gtkpounce_data *pounce_data;
164
165 gaim_pounce_set_events(dialog->pounce, events);
166 gaim_pounce_set_pouncer(dialog->pounce, dialog->account);
167 gaim_pounce_set_pouncee(dialog->pounce, name);
168
169 pounce_data = GAIM_GTKPOUNCE(dialog->pounce);
170
171 if (pounce_data->message != NULL) g_free(pounce_data->message);
172 if (pounce_data->command != NULL) g_free(pounce_data->command);
173 if (pounce_data->sound != NULL) g_free(pounce_data->sound);
174
175 pounce_data->message = (message == NULL ? NULL : g_strdup(message));
176 pounce_data->command = (command == NULL ? NULL : g_strdup(command));
177 pounce_data->sound = (sound == NULL ? NULL : g_strdup(sound));
178
179 pounce_data->actions = actions;
180 pounce_data->save = save;
181 }
182
183 delete_win_cb(NULL, NULL, dialog);
184
185 /* Rebuild the pounce menu */
186 blist = gaim_get_blist();
187
188 if (GAIM_IS_GTK_BLIST(blist))
189 {
190 gtkblist = GAIM_GTK_BLIST(blist);
191
192 gaim_gtkpounce_menu_build(gtkblist->bpmenu);
193 }
194
195 save_prefs();
196 }
197
198 static GtkWidget *
199 pounce_choose_cb(GtkWidget *item, struct gaim_gtkpounce_dialog *dialog)
200 {
201 dialog->account = g_object_get_data(G_OBJECT(item), "user_data");
202 }
203
204 static GtkWidget *
205 pounce_user_menu(struct gaim_gtkpounce_dialog *dialog)
206 {
207 struct gaim_account *account;
208 struct prpl *prpl;
209 GtkWidget *opt_menu;
210 GtkWidget *menu;
211 GtkWidget *item;
212 GSList *l;
213 char buf[2048];
214 int count, place;
215
216 opt_menu = gtk_option_menu_new();
217 menu = gtk_menu_new();
218
219 for (l = gaim_accounts, count = 0; l != NULL; l = l->next, count++) {
220 account = (struct gaim_account *)l->data;
221
222 prpl = (struct prpl *)find_prpl(account->protocol);
223
224 g_snprintf(buf, sizeof(buf), "%s (%s)", account->username,
225 (prpl && prpl->name) ? prpl->name : _("Unknown"));
226
227 item = gtk_menu_item_new_with_label(buf);
228 g_object_set_data(G_OBJECT(item), "user_data", account);
229
230 g_signal_connect(G_OBJECT(item), "activate",
231 G_CALLBACK(pounce_choose_cb), dialog);
232
233 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
234 gtk_widget_show(item);
235
236 if (dialog->account == account) {
237 gtk_menu_item_activate(GTK_MENU_ITEM(item));
238 place = count;
239 }
240 }
241
242 gtk_option_menu_set_menu(GTK_OPTION_MENU(opt_menu), menu);
243 gtk_option_menu_set_history(GTK_OPTION_MENU(opt_menu), place);
244
245 return opt_menu;
246 }
247
248 static void
249 pounce_cb(struct gaim_pounce *pounce, GaimPounceEvent events, void *data)
250 {
251 struct gaim_conversation *conv;
252 struct gaim_account *account;
253 struct gaim_gtkpounce_data *pounce_data;
254 const char *pouncee;
255
256 pounce_data = (struct gaim_gtkpounce_data *)data;
257 pouncee = gaim_pounce_get_pouncee(pounce);
258 account = gaim_pounce_get_pouncer(pounce);
259
260 if (pounce_data->actions & GAIM_GTKPOUNCE_OPEN_WIN) {
261 conv = gaim_find_conversation(pouncee);
262
263 if (conv == NULL)
264 conv = gaim_conversation_new(GAIM_CONV_IM, account, pouncee);
265 }
266
267 if (pounce_data->actions & GAIM_GTKPOUNCE_POPUP) {
268 char tmp[1024];
269
270 g_snprintf(tmp, sizeof(tmp),
271 (events & GAIM_POUNCE_TYPING) ? _("%s has started typing to you") :
272 (events & GAIM_POUNCE_SIGNON) ? _("%s has signed on") :
273 (events & GAIM_POUNCE_IDLE_RETURN) ? _("%s has returned from being idle") :
274 (events & GAIM_POUNCE_AWAY_RETURN) ? _("%s has returned from being away") :
275 (events & GAIM_POUNCE_TYPING_STOPPED) ? _("%s has stopped typing to you") :
276 (events & GAIM_POUNCE_SIGNOFF) ? _("%s has signed off") :
277 (events & GAIM_POUNCE_IDLE) ? _("%s has become idle") :
278 (events & GAIM_POUNCE_AWAY) ? _("%s has gone away.") :
279 _("Unknown pounce event. Please report this!"),
280 pouncee);
281
282 do_error_dialog(tmp, NULL, GAIM_INFO);
283 }
284
285 if (pounce_data->actions & GAIM_GTKPOUNCE_SEND_MSG &&
286 *pounce_data->message != '\0') {
287
288 conv = gaim_find_conversation(pouncee);
289
290 if (conv == NULL)
291 conv = gaim_conversation_new(GAIM_CONV_IM, account, pouncee);
292
293 gaim_conversation_write(conv, NULL, pounce_data->message, -1,
294 WFLAG_SEND, time(NULL));
295
296 serv_send_im(account->gc, (char *)pouncee, pounce_data->message, -1, 0);
297 }
298
299 if (pounce_data->actions & GAIM_GTKPOUNCE_EXEC_CMD &&
300 *pounce_data->command != '\0') {
301 #ifndef _WIN32
302 int pid = fork();
303
304 if (pid == 0) {
305 char *args[4];
306
307 args[0] = "sh";
308 args[1] = "-c";
309 args[2] = pounce_data->command;
310 args[3] = NULL;
311
312 execvp(args[0], args);
313
314 _exit(0);
315 }
316 #endif /* _WIN32 */
317 }
318
319 if (pounce_data->actions & GAIM_GTKPOUNCE_PLAY_SOUND) {
320 if (*pounce_data->sound != '\0')
321 gaim_sound_play_file(pounce_data->sound);
322 else
323 gaim_sound_play_event(GAIM_SOUND_POUNCE_DEFAULT);
324 }
325
326 if (!pounce_data->save)
327 gaim_pounce_destroy(pounce);
328 }
329
330 static void
331 free_pounce(void *data)
332 {
333 struct gaim_gtkpounce_data *pounce_data;
334 struct gaim_buddy_list *blist;
335 struct gaim_gtk_buddy_list *gtkblist;
336
337 pounce_data = (struct gaim_gtkpounce_data *)data;
338
339 if (pounce_data->message != NULL) g_free(pounce_data->message);
340 if (pounce_data->command != NULL) g_free(pounce_data->command);
341 if (pounce_data->sound != NULL) g_free(pounce_data->sound);
342
343 g_free(data);
344
345 /* Rebuild the pounce menu */
346 blist = gaim_get_blist();
347
348 if (GAIM_IS_GTK_BLIST(blist))
349 {
350 gtkblist = GAIM_GTK_BLIST(blist);
351
352 gaim_gtkpounce_menu_build(gtkblist->bpmenu);
353 }
354
355 save_prefs();
356 }
357
358 struct gaim_pounce *
359 gaim_gtkpounce_new(struct gaim_account *pouncer, const char *pouncee,
360 GaimPounceEvent events, GaimGtkPounceAction actions,
361 const char *message, const char *command,
362 const char *sound, gboolean save)
363 {
364 struct gaim_gtkpounce_data *data;
365
366 data = g_new0(struct gaim_gtkpounce_data, 1);
367
368 data->actions = actions;
369
370 if (message != NULL) data->message = g_strdup(message);
371 if (command != NULL) data->command = g_strdup(command);
372 if (sound != NULL) data->sound = g_strdup(sound);
373
374 data->save = save;
375
376 return gaim_pounce_new(pouncer, pouncee, events, pounce_cb, data,
377 free_pounce);
378 }
379
380 void
381 gaim_gtkpounce_dialog_show(struct buddy *buddy,
382 struct gaim_pounce *cur_pounce)
383 {
384 struct gaim_gtkpounce_dialog *dialog;
385 GtkWidget *window;
386 GtkWidget *label;
387 GtkWidget *bbox;
388 GtkWidget *vbox1, *vbox2;
389 GtkWidget *hbox;
390 GtkWidget *button;
391 GtkWidget *frame;
392 GtkWidget *table;
393 GtkWidget *optmenu;
394 GtkWidget *sep;
395 GtkSizeGroup *sg;
396
397 dialog = g_new0(struct gaim_gtkpounce_dialog, 1);
398
399 if (cur_pounce != NULL) {
400 dialog->pounce = cur_pounce;
401 dialog->account = gaim_pounce_get_pouncer(cur_pounce);
402 }
403 else if (buddy != NULL) {
404 dialog->pounce = NULL;
405 dialog->account = buddy->account;
406 }
407 else {
408 dialog->pounce = NULL;
409 dialog->account = gaim_accounts->data;
410 }
411
412 sg = gtk_size_group_new(GTK_SIZE_GROUP_HORIZONTAL);
413
414 /* Create the window. */
415 dialog->window = window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
416 gtk_window_set_type_hint(GTK_WINDOW(window), GDK_WINDOW_TYPE_HINT_DIALOG);
417 gtk_window_set_role(GTK_WINDOW(window), "buddy_pounce");
418 gtk_window_set_resizable(GTK_WINDOW(window), FALSE);
419 gtk_window_set_title(GTK_WINDOW(window),
420 (cur_pounce == NULL
421 ? _("New Buddy Pounce") : _("Edit Buddy Pounce")));
422
423 gtk_container_set_border_width(GTK_CONTAINER(window), 12);
424 gtk_widget_realize(window);
425
426 g_signal_connect(G_OBJECT(window), "delete_event",
427 G_CALLBACK(delete_win_cb), dialog);
428
429 /* Create the parent vbox for everything. */
430 vbox1 = gtk_vbox_new(FALSE, 12);
431 gtk_container_add(GTK_CONTAINER(window), vbox1);
432 gtk_widget_show(vbox1);
433
434 /* Create the vbox that will contain all the prefs stuff. */
435 vbox2 = gtk_vbox_new(FALSE, 18);
436 gtk_box_pack_start(GTK_BOX(vbox1), vbox2, TRUE, TRUE, 0);
437
438 /* Create the "Pounce Who" frame. */
439 frame = make_frame(vbox2, _("Pounce Who"));
440
441 /* Account: */
442 hbox = gtk_hbox_new(FALSE, 6);
443 gtk_box_pack_start(GTK_BOX(frame), hbox, FALSE, FALSE, 0);
444 gtk_widget_show(hbox);
445
446 label = gtk_label_new_with_mnemonic(_("_Account:"));
447 gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
448 gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0);
449 gtk_widget_show(label);
450 gtk_size_group_add_widget(sg, label);
451
452 dialog->account_menu = pounce_user_menu(dialog);
453 gtk_box_pack_start(GTK_BOX(hbox), dialog->account_menu, FALSE, FALSE, 0);
454 gtk_widget_show(dialog->account_menu);
455
456 /* Buddy: */
457 hbox = gtk_hbox_new(FALSE, 6);
458 gtk_box_pack_start(GTK_BOX(frame), hbox, FALSE, FALSE, 0);
459 gtk_widget_show(hbox);
460
461 label = gtk_label_new_with_mnemonic(_("_Buddy Name:"));
462 gtk_misc_set_alignment(GTK_MISC(label), 0, 0.5);
463 gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 0);
464 gtk_widget_show(label);
465 gtk_size_group_add_widget(sg, label);
466
467 dialog->buddy_entry = gtk_entry_new();
468 gtk_box_pack_start(GTK_BOX(hbox), dialog->buddy_entry, TRUE, TRUE, 0);
469 gtk_widget_show(dialog->buddy_entry);
470
471 if (cur_pounce != NULL) {
472 gtk_entry_set_text(GTK_ENTRY(dialog->buddy_entry),
473 gaim_pounce_get_pouncee(cur_pounce));
474 }
475 else if (buddy != NULL) {
476 gtk_entry_set_text(GTK_ENTRY(dialog->buddy_entry), buddy->name);
477 }
478
479 /* Create the "Pounce When" frame. */
480 frame = make_frame(vbox2, _("Pounce When"));
481
482 table = gtk_table_new(2, 4, FALSE);
483 gtk_container_add(GTK_CONTAINER(frame), table);
484 gtk_table_set_col_spacings(GTK_TABLE(table), 12);
485 gtk_widget_show(table);
486
487 dialog->signon =
488 gtk_check_button_new_with_label(_("Sign on"));
489 dialog->signoff =
490 gtk_check_button_new_with_label(_("Sign off"));
491 dialog->away =
492 gtk_check_button_new_with_label(_("Away"));
493 dialog->away_return =
494 gtk_check_button_new_with_label(_("Return from away"));
495 dialog->idle =
496 gtk_check_button_new_with_label(_("Idle"));
497 dialog->idle_return =
498 gtk_check_button_new_with_label(_("Return from idle"));
499 dialog->typing =
500 gtk_check_button_new_with_label(_("Buddy starts typing"));
501 dialog->stop_typing =
502 gtk_check_button_new_with_label(_("Buddy stops typing"));
503
504 gtk_table_attach(GTK_TABLE(table), dialog->signon, 0, 1, 0, 1,
505 GTK_FILL, 0, 0, 0);
506 gtk_table_attach(GTK_TABLE(table), dialog->signoff, 1, 2, 0, 1,
507 GTK_FILL, 0, 0, 0);
508 gtk_table_attach(GTK_TABLE(table), dialog->away, 0, 1, 1, 2,
509 GTK_FILL, 0, 0, 0);
510 gtk_table_attach(GTK_TABLE(table), dialog->away_return, 1, 2, 1, 2,
511 GTK_FILL, 0, 0, 0);
512 gtk_table_attach(GTK_TABLE(table), dialog->idle, 0, 1, 2, 3,
513 GTK_FILL, 0, 0, 0);
514 gtk_table_attach(GTK_TABLE(table), dialog->idle_return, 1, 2, 2, 3,
515 GTK_FILL, 0, 0, 0);
516 gtk_table_attach(GTK_TABLE(table), dialog->typing, 0, 1, 3, 4,
517 GTK_FILL, 0, 0, 0);
518 gtk_table_attach(GTK_TABLE(table), dialog->stop_typing, 1, 2, 3, 4,
519 GTK_FILL, 0, 0, 0);
520
521 gtk_widget_show(dialog->signon);
522 gtk_widget_show(dialog->signoff);
523 gtk_widget_show(dialog->away);
524 gtk_widget_show(dialog->away_return);
525 gtk_widget_show(dialog->idle);
526 gtk_widget_show(dialog->idle_return);
527 gtk_widget_show(dialog->typing);
528 gtk_widget_show(dialog->stop_typing);
529
530 /* Create the "Pounce Action" frame. */
531 frame = make_frame(vbox2, _("Pounce Action"));
532
533 table = gtk_table_new(2, 5, FALSE);
534 gtk_container_add(GTK_CONTAINER(frame), table);
535 gtk_table_set_col_spacings(GTK_TABLE(table), 12);
536 gtk_widget_show(table);
537
538 dialog->open_win = gtk_check_button_new_with_label(_("Open an IM window"));
539 dialog->popup = gtk_check_button_new_with_label(_("Popup notification"));
540 dialog->send_msg = gtk_check_button_new_with_label(_("Send a message"));
541 dialog->exec_cmd = gtk_check_button_new_with_label(_("Execute a command"));
542 dialog->play_sound = gtk_check_button_new_with_label(_("Play a Sound"));
543
544 dialog->send_msg_entry = gtk_entry_new();
545 dialog->exec_cmd_entry = gtk_entry_new();
546 dialog->play_sound_entry = gtk_entry_new();
547
548 gtk_widget_set_sensitive(dialog->send_msg_entry, FALSE);
549 gtk_widget_set_sensitive(dialog->exec_cmd_entry, FALSE);
550 gtk_widget_set_sensitive(dialog->play_sound_entry, FALSE);
551
552 gtk_table_attach(GTK_TABLE(table), dialog->open_win, 0, 1, 0, 1,
553 GTK_FILL, 0, 0, 0);
554 gtk_table_attach(GTK_TABLE(table), dialog->popup, 0, 1, 1, 2,
555 GTK_FILL, 0, 0, 0);
556 gtk_table_attach(GTK_TABLE(table), dialog->send_msg, 0, 1, 2, 3,
557 GTK_FILL, 0, 0, 0);
558 gtk_table_attach(GTK_TABLE(table), dialog->send_msg_entry, 1, 2, 2, 3,
559 GTK_FILL, 0, 0, 0);
560 gtk_table_attach(GTK_TABLE(table), dialog->exec_cmd, 0, 1, 3, 4,
561 GTK_FILL, 0, 0, 0);
562 gtk_table_attach(GTK_TABLE(table), dialog->exec_cmd_entry, 1, 2, 3, 4,
563 GTK_FILL, 0, 0, 0);
564 gtk_table_attach(GTK_TABLE(table), dialog->play_sound, 0, 1, 4, 5,
565 GTK_FILL, 0, 0, 0);
566 gtk_table_attach(GTK_TABLE(table), dialog->play_sound_entry, 1, 2, 4, 5,
567 GTK_FILL, 0, 0, 0);
568
569 gtk_widget_show(dialog->open_win);
570 gtk_widget_show(dialog->popup);
571 gtk_widget_show(dialog->send_msg);
572 gtk_widget_show(dialog->send_msg_entry);
573 gtk_widget_show(dialog->exec_cmd);
574 gtk_widget_show(dialog->exec_cmd_entry);
575 gtk_widget_show(dialog->play_sound);
576 gtk_widget_show(dialog->play_sound_entry);
577
578 g_signal_connect(G_OBJECT(dialog->send_msg), "clicked",
579 G_CALLBACK(gaim_gtk_toggle_sensitive),
580 dialog->send_msg_entry);
581 g_signal_connect(G_OBJECT(dialog->exec_cmd), "clicked",
582 G_CALLBACK(gaim_gtk_toggle_sensitive),
583 dialog->exec_cmd_entry);
584 g_signal_connect(G_OBJECT(dialog->play_sound), "clicked",
585 G_CALLBACK(gaim_gtk_toggle_sensitive),
586 dialog->play_sound_entry);
587
588 g_signal_connect(G_OBJECT(dialog->send_msg_entry), "activate",
589 G_CALLBACK(save_pounce_cb), dialog);
590 g_signal_connect(G_OBJECT(dialog->exec_cmd_entry), "activate",
591 G_CALLBACK(save_pounce_cb), dialog);
592 g_signal_connect(G_OBJECT(dialog->play_sound_entry), "activate",
593 G_CALLBACK(save_pounce_cb), dialog);
594
595 /* Now the last part, where we have the Save checkbox */
596 dialog->save_pounce = gtk_check_button_new_with_mnemonic(
597 _("_Save this pounce after activation"));
598
599 gtk_box_pack_start(GTK_BOX(vbox2), dialog->save_pounce, FALSE, FALSE, 0);
600
601 /* Separator... */
602 sep = gtk_hseparator_new();
603 gtk_box_pack_start(GTK_BOX(vbox1), sep, FALSE, FALSE, 0);
604 gtk_widget_show(sep);
605
606 /* Now the button box! */
607 bbox = gtk_hbutton_box_new();
608 gtk_box_set_spacing(GTK_BOX(bbox), 6);
609 gtk_button_box_set_layout(GTK_BUTTON_BOX(bbox), GTK_BUTTONBOX_END);
610 gtk_box_pack_end(GTK_BOX(vbox1), bbox, FALSE, FALSE, 0);
611 gtk_widget_show(bbox);
612
613 /* Cancel button */
614 button = gtk_button_new_from_stock(GTK_STOCK_CANCEL);
615 gtk_box_pack_start(GTK_BOX(bbox), button, FALSE, FALSE, 0);
616 gtk_widget_show(button);
617
618 g_signal_connect(G_OBJECT(button), "clicked",
619 G_CALLBACK(cancel_cb), dialog);
620
621 /* OK button */
622 button = gtk_button_new_from_stock(GTK_STOCK_OK);
623 gtk_box_pack_start(GTK_BOX(bbox), button, FALSE, FALSE, 0);
624 gtk_widget_show(button);
625
626 g_signal_connect(G_OBJECT(button), "clicked",
627 G_CALLBACK(save_pounce_cb), dialog);
628
629 /* Set the values of stuff. */
630 if (cur_pounce != NULL) {
631 GaimPounceEvent events;
632 GaimGtkPounceAction actions;
633 struct gaim_gtkpounce_data *pounce_data;
634
635 pounce_data = GAIM_GTKPOUNCE(cur_pounce);
636 events = gaim_pounce_get_events(cur_pounce);
637 actions = pounce_data->actions;
638
639 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->signon),
640 (events & GAIM_POUNCE_SIGNON));
641 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->signoff),
642 (events & GAIM_POUNCE_SIGNOFF));
643 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->away),
644 (events & GAIM_POUNCE_AWAY));
645 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->away_return),
646 (events & GAIM_POUNCE_AWAY_RETURN));
647 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->idle),
648 (events & GAIM_POUNCE_IDLE));
649 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->idle_return),
650 (events & GAIM_POUNCE_IDLE_RETURN));
651 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->typing),
652 (events & GAIM_POUNCE_TYPING));
653 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->stop_typing),
654 (events & GAIM_POUNCE_TYPING_STOPPED));
655
656 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->open_win),
657 (actions & GAIM_GTKPOUNCE_OPEN_WIN));
658 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->popup),
659 (actions & GAIM_GTKPOUNCE_POPUP));
660 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->send_msg),
661 (actions & GAIM_GTKPOUNCE_SEND_MSG));
662 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->exec_cmd),
663 (actions & GAIM_GTKPOUNCE_EXEC_CMD));
664 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->play_sound),
665 (actions & GAIM_GTKPOUNCE_PLAY_SOUND));
666
667 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->save_pounce),
668 pounce_data->save);
669
670 gtk_entry_set_text(GTK_ENTRY(dialog->send_msg_entry),
671 pounce_data->message);
672 gtk_entry_set_text(GTK_ENTRY(dialog->exec_cmd_entry),
673 pounce_data->command);
674 gtk_entry_set_text(GTK_ENTRY(dialog->play_sound_entry),
675 pounce_data->sound);
676 }
677 else {
678 /* Set some defaults */
679 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->send_msg), TRUE);
680 gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(dialog->signon), TRUE);
681 }
682
683 gtk_widget_show_all(vbox2);
684 gtk_widget_show(window);
685 }
686
687 static void
688 new_pounce_cb(GtkWidget *w, struct buddy *b)
689 {
690 gaim_gtkpounce_dialog_show(b, NULL);
691 }
692
693 static void
694 edit_pounce_cb(GtkWidget *w, struct gaim_pounce *pounce)
695 {
696 struct buddy *buddy;
697
698 buddy = gaim_find_buddy(gaim_pounce_get_pouncer(pounce),
699 gaim_pounce_get_pouncee(pounce));
700
701 gaim_gtkpounce_dialog_show(buddy, pounce);
702 }
703
704 void
705 gaim_gtkpounce_menu_build(GtkWidget *menu)
706 {
707 GtkWidget *remmenu, *submenu, *item;
708 GList *l;
709 GList *bp;
710 struct gaim_pounce *pounce;
711 const char *buddy;
712
713 for (l = gtk_container_get_children(GTK_CONTAINER(menu));
714 l != NULL;
715 l = l->next) {
716
717 gtk_widget_destroy(GTK_WIDGET(l->data));
718 }
719
720 /* "New Buddy Pounce" */
721 item = gtk_menu_item_new_with_label(_("New Buddy Pounce"));
722 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
723 gtk_widget_show(item);
724 g_signal_connect(G_OBJECT(item), "activate",
725 G_CALLBACK(new_pounce_cb), NULL);
726
727 /* "Remove Buddy Pounce" */
728 item = gtk_menu_item_new_with_label(_("Remove Buddy Pounce"));
729 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
730
731 /* "Remove Buddy Pounce" menu */
732 remmenu = gtk_menu_new();
733
734 for (bp = gaim_get_pounces(); bp != NULL; bp = bp->next) {
735 pounce = (struct gaim_pounce *)bp->data;
736 buddy = gaim_pounce_get_pouncee(pounce);
737
738 item = gtk_menu_item_new_with_label(buddy);
739 gtk_menu_shell_append(GTK_MENU_SHELL(remmenu), item);
740 gtk_widget_show(item);
741
742 g_signal_connect(G_OBJECT(item), "activate",
743 G_CALLBACK(edit_pounce_cb), pounce);
744 }
745
746 gtk_menu_item_set_submenu(GTK_MENU_ITEM(item), remmenu);
747 gtk_widget_show(remmenu);
748 gtk_widget_show(item);
749
750 /* Separator */
751 item = gtk_separator_menu_item_new();
752 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
753 gtk_widget_show(item);
754
755 /* Pounces */
756 for (bp = gaim_get_pounces(); bp != NULL; bp = bp->next) {
757 struct gaim_gtkpounce_data *pounce_data;
758
759 pounce = (struct gaim_pounce *)bp->data;
760 buddy = gaim_pounce_get_pouncee(pounce);
761
762 pounce_data = GAIM_GTKPOUNCE(pounce);
763
764 item = gtk_menu_item_new_with_label(buddy);
765 gtk_menu_shell_append(GTK_MENU_SHELL(menu), item);
766 gtk_widget_show(item);
767
768 g_signal_connect(G_OBJECT(item), "activate",
769 G_CALLBACK(edit_pounce_cb), pounce);
770 }
771 }
772