libpurple/example/nullclient.c

changeset 15673
7f2c84ae63b0
child 15755
ab33ab6b08ae
equal deleted inserted replaced
15672:4153831eb8af 15673:7f2c84ae63b0
1 /*
2 * pidgin
3 *
4 * Pidgin is the legal property of its developers, whose names are too numerous
5 * to list here. Please refer to the COPYRIGHT file distributed with this
6 * source distribution.
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 "account.h"
24 #include "conversation.h"
25 #include "core.h"
26 #include "debug.h"
27 #include "eventloop.h"
28 #include "ft.h"
29 #include "log.h"
30 #include "notify.h"
31 #include "prefix.h"
32 #include "prefs.h"
33 #include "prpl.h"
34 #include "pounce.h"
35 #include "savedstatuses.h"
36 #include "sound.h"
37 #include "status.h"
38 #include "util.h"
39 #include "whiteboard.h"
40
41 #include <glib.h>
42
43 #include <string.h>
44 #include <unistd.h>
45
46 #include "defines.h"
47
48 /**
49 * The following eventloop functions are used in both pidgin and gaim-text. If your
50 * application uses glib mainloop, you can safely use this verbatim.
51 */
52 #define GAIM_GLIB_READ_COND (G_IO_IN | G_IO_HUP | G_IO_ERR)
53 #define GAIM_GLIB_WRITE_COND (G_IO_OUT | G_IO_HUP | G_IO_ERR | G_IO_NVAL)
54
55 typedef struct _GaimGLibIOClosure {
56 GaimInputFunction function;
57 guint result;
58 gpointer data;
59 } GaimGLibIOClosure;
60
61 static void gaim_glib_io_destroy(gpointer data)
62 {
63 g_free(data);
64 }
65
66 static gboolean gaim_glib_io_invoke(GIOChannel *source, GIOCondition condition, gpointer data)
67 {
68 GaimGLibIOClosure *closure = data;
69 GaimInputCondition gaim_cond = 0;
70
71 if (condition & GAIM_GLIB_READ_COND)
72 gaim_cond |= GAIM_INPUT_READ;
73 if (condition & GAIM_GLIB_WRITE_COND)
74 gaim_cond |= GAIM_INPUT_WRITE;
75
76 closure->function(closure->data, g_io_channel_unix_get_fd(source),
77 gaim_cond);
78
79 return TRUE;
80 }
81
82 static guint glib_input_add(gint fd, GaimInputCondition condition, GaimInputFunction function,
83 gpointer data)
84 {
85 GaimGLibIOClosure *closure = g_new0(GaimGLibIOClosure, 1);
86 GIOChannel *channel;
87 GIOCondition cond = 0;
88
89 closure->function = function;
90 closure->data = data;
91
92 if (condition & GAIM_INPUT_READ)
93 cond |= GAIM_GLIB_READ_COND;
94 if (condition & GAIM_INPUT_WRITE)
95 cond |= GAIM_GLIB_WRITE_COND;
96
97 channel = g_io_channel_unix_new(fd);
98 closure->result = g_io_add_watch_full(channel, G_PRIORITY_DEFAULT, cond,
99 gaim_glib_io_invoke, closure, gaim_glib_io_destroy);
100
101 g_io_channel_unref(channel);
102 return closure->result;
103 }
104
105 static GaimEventLoopUiOps glib_eventloops =
106 {
107 g_timeout_add,
108 g_source_remove,
109 glib_input_add,
110 g_source_remove
111 };
112 /*** End of the eventloop functions. ***/
113
114 /*** Conversation uiops ***/
115 static void
116 null_write_conv(GaimConversation *conv, const char *who, const char *alias,
117 const char *message, GaimMessageFlags flags, time_t mtime)
118 {
119 const char *name;
120 if (alias && *alias)
121 name = alias;
122 else if (who && *who)
123 name = who;
124 else
125 name = NULL;
126
127 printf("(%s) %s %s: %s\n", gaim_conversation_get_name(conv),
128 gaim_utf8_strftime("(%H:%M:%S)", localtime(&mtime)),
129 name, message);
130 }
131
132 static GaimConversationUiOps null_conv_uiops =
133 {
134 .write_conv = null_write_conv
135 };
136
137 static void
138 null_ui_init()
139 {
140 /**
141 * This should initialize the UI components for all the modules. Here we
142 * just initialize the UI for conversations.
143 */
144 gaim_conversations_set_ui_ops(&null_conv_uiops);
145 }
146
147 static GaimCoreUiOps null_core_uiops =
148 {
149 NULL,
150 NULL,
151 null_ui_init,
152 NULL
153 };
154
155 static void
156 init_libpurple()
157 {
158 /* Set a custom user directory (optional) */
159 gaim_util_set_user_dir(CUSTOM_USER_DIRECTORY);
160
161 /* We do not want any debugging for now to keep the noise to a minimum. */
162 gaim_debug_set_enabled(FALSE);
163
164 /* Set the core-uiops, which is used to
165 * - initialize the ui specific preferences.
166 * - initialize the debug ui.
167 * - initialize the ui components for all the modules.
168 * - uninitialize the ui components for all the modules when the core terminates.
169 */
170 gaim_core_set_ui_ops(&null_core_uiops);
171
172 /* Set the uiops for the eventloop. If your client is glib-based, you can safely
173 * copy this verbatim. */
174 gaim_eventloop_set_ui_ops(&glib_eventloops);
175
176 /* Set path to search for plugins. The core (libpurple) takes care of loading the
177 * core-plugins, which includes the protocol-plugins. So it is not essential to add
178 * any path here, but it might be desired, especially for ui-specific plugins. */
179 gaim_plugins_add_search_path(CUSTOM_PLUGIN_PATH);
180
181 /* Now that all the essential stuff has been set, let's try to init the core. It's
182 * necessary to provide a non-NULL name for the current ui to the core. This name
183 * is used by stuff that depends on this ui, for example the ui-specific plugins. */
184 if (!gaim_core_init(UI_ID)) {
185 /* Initializing the core failed. Terminate. */
186 fprintf(stderr,
187 "libpurple initialization failed. Dumping core.\n"
188 "Please report this!\n");
189 abort();
190 }
191
192 /* Create and load the buddylist. */
193 gaim_set_blist(gaim_blist_new());
194 gaim_blist_load();
195
196 /* Load the preferences. */
197 gaim_prefs_load();
198
199 /* Load the desired plugins. The client should save the list of loaded plugins in
200 * the preferences using gaim_plugins_save_loaded(PLUGIN_SAVE_PREF) */
201 gaim_plugins_load_saved(PLUGIN_SAVE_PREF);
202
203 /* Load the pounces. */
204 gaim_pounces_load();
205 }
206
207 static void
208 signed_on(GaimConnection *gc, gpointer null)
209 {
210 GaimAccount *account = gaim_connection_get_account(gc);
211 printf("Account connected: %s %s\n", account->username, account->protocol_id);
212 }
213
214 static void
215 connect_to_signals_for_demonstration_purposes_only()
216 {
217 static int handle;
218 gaim_signal_connect(gaim_connections_get_handle(), "signed-on", &handle,
219 GAIM_CALLBACK(signed_on), NULL);
220 }
221
222 int main()
223 {
224 GList *iter;
225 int i, num;
226 GList *names = NULL;
227 const char *prpl;
228 char name[128];
229 char *password;
230 GMainLoop *loop = g_main_loop_new(NULL, FALSE);
231 GaimAccount *account;
232 GaimSavedStatus *status;
233
234 init_libpurple();
235
236 printf("libpurple initialized.\n");
237
238 iter = gaim_plugins_get_protocols();
239 for (i = 0; iter; iter = iter->next) {
240 GaimPlugin *plugin = iter->data;
241 GaimPluginInfo *info = plugin->info;
242 if (info && info->name) {
243 printf("\t%d: %s\n", i++, info->name);
244 names = g_list_append(names, info->id);
245 }
246 }
247 printf("Select the protocol [0-%d]: ", i-1);
248 fgets(name, sizeof(name), stdin);
249 sscanf(name, "%d", &num);
250 prpl = g_list_nth_data(names, num);
251
252 printf("Username: ");
253 fgets(name, sizeof(name), stdin);
254 name[strlen(name) - 1] = 0; /* strip the \n at the end */
255
256 /* Create the account */
257 account = gaim_account_new(name, prpl);
258
259 /* Get the password for the account */
260 password = getpass("Password: ");
261 gaim_account_set_password(account, password);
262
263 /* It's necessary to enable the account first. */
264 gaim_account_set_enabled(account, UI_ID, TRUE);
265
266 /* Now, to connect the account(s), create a status and activate it. */
267 status = gaim_savedstatus_new(NULL, GAIM_STATUS_AVAILABLE);
268 gaim_savedstatus_activate(status);
269
270 connect_to_signals_for_demonstration_purposes_only();
271
272 g_main_loop_run(loop);
273
274 return 0;
275 }
276

mercurial