conference.c 7.01 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24
/***************************************************************************
 *            gtk/conference.c
 *
 *  Mon Sep 12, 2011
 *  Copyright  2011  Belledonne Communications
 *  Author: Simon Morlat
 *  Email simon dot morlat at linphone dot org
 ****************************************************************************/

/*
 *  This program is free software; you can redistribute it and/or modify
 *  it under the terms of the GNU General Public License as published by
 *  the Free Software Foundation; either version 2 of the License, or
 *  (at your option) any later version.
 *
 *  This program is distributed in the hope that it will be useful,
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 *  GNU General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License
 *  along with this program; if not, write to the Free Software
 *  Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
 */
25

26 27
#include "linphone.h"

28 29
#define PADDING_PIXELS 4

30 31 32 33 34
/*
 * conferencee_box = a vbox where participants are added or removed
 * conf_frame = the conference tab
 */

35 36
static GtkWidget *create_conference_label(void){
	GtkWidget *box=gtk_hbox_new(FALSE,0);
37
	gtk_box_pack_start(GTK_BOX(box),gtk_image_new_from_icon_name("linphone-conference-start",GTK_ICON_SIZE_MENU),FALSE,FALSE,0);
38 39 40 41 42 43 44
	gtk_box_pack_end(GTK_BOX(box),gtk_label_new(_("Conference")),TRUE,FALSE,0);
	gtk_widget_show_all(box);
	return box;
}

static void init_local_participant(GtkWidget *participant){
	GtkWidget *sound_meter;
45
	GtkWidget *button=linphone_gtk_get_widget(participant,"conference_control");
46 47
	gtk_label_set_markup(GTK_LABEL(linphone_gtk_get_widget(participant,"callee_name_label")),_("Me"));
	sound_meter=linphone_gtk_get_widget(participant,"sound_indicator");
48 49 50
	linphone_gtk_enable_mute_button(GTK_BUTTON(button),TRUE);
	g_signal_connect(G_OBJECT(button),"clicked",(GCallback)linphone_gtk_mute_clicked,NULL);
	gtk_widget_show(button);
51 52 53
	linphone_gtk_init_audio_meter(sound_meter, (get_volume_t) linphone_core_get_conference_local_input_volume, linphone_gtk_get_core());
}

54 55
static GtkWidget *get_conferencee_box(GtkWidget *mw){
	GtkWidget *box=(GtkWidget*)g_object_get_data(G_OBJECT(mw),"conferencee_box");
56 57 58 59 60
	return box;
}

static GtkWidget *find_conferencee_from_call(LinphoneCall *call){
	GtkWidget *mw=linphone_gtk_get_main_window();
61
	GtkWidget *conferencee_box=get_conferencee_box(mw);
62 63
	GList *elem;
	GtkWidget *ret=NULL;
64

65
	if (conferencee_box==NULL) return NULL;
66

67
	if (call!=NULL){
68
		GList *l=gtk_container_get_children(GTK_CONTAINER(conferencee_box));
69 70 71 72 73 74
		for(elem=l;elem!=NULL;elem=elem->next){
			GtkWidget *frame=(GtkWidget*)elem->data;
			if (call==g_object_get_data(G_OBJECT(frame),"call")){
				ret=frame;
				break;
			}
75
		}
76
		g_list_free(l);
77
	}
78
	//g_message("find_conferencee_from_call(): found widget %p for call %p",ret,call);
79 80 81
	return ret;
}

82
static GtkWidget * create_conference_panel(void){
83
	GtkWidget *mw=linphone_gtk_get_main_window();
84
	GtkWidget *conf_frame=linphone_gtk_create_widget("conf_frame");
85 86
	GtkWidget *conf_box=linphone_gtk_get_widget(conf_frame,"conf_box");
	GtkWidget *button_conf=linphone_gtk_get_widget(conf_frame,"terminate_conf");
87
	GtkWidget *image=gtk_image_new_from_icon_name("linphone-stop-call", GTK_ICON_SIZE_BUTTON);
88
	GtkWidget *box;
89
	GtkWidget *viewswitch=linphone_gtk_get_widget(mw,"viewswitch");
90
	GtkWidget *participant;
91
	GtkWidget *record = linphone_gtk_get_widget(conf_frame, "conf_record_button");
92

93
	gtk_button_set_image(GTK_BUTTON(record), gtk_image_new_from_icon_name("linphone-record", GTK_ICON_SIZE_BUTTON));
94 95 96
	gtk_button_set_image(GTK_BUTTON(button_conf),image);
	g_signal_connect_swapped(G_OBJECT(button_conf),"clicked",(GCallback)linphone_gtk_terminate_call,NULL);
	g_object_set_data(G_OBJECT(mw),"conf_frame",(gpointer)conf_frame);
97

98
	box=gtk_vbox_new(FALSE,0);
99
	participant=linphone_gtk_create_widget("callee_frame");
100 101 102 103 104 105 106
	gtk_widget_show(participant);
	gtk_box_set_homogeneous(GTK_BOX(box),TRUE);
	init_local_participant(participant);
	gtk_box_pack_start(GTK_BOX(box),participant,FALSE,FALSE,PADDING_PIXELS);
	gtk_widget_show(box);
	g_object_set_data(G_OBJECT(mw),"conferencee_box",box);
	gtk_box_pack_start(GTK_BOX(conf_box),box,FALSE,FALSE,PADDING_PIXELS);
107

108 109 110 111 112 113 114
	gtk_notebook_append_page(GTK_NOTEBOOK(viewswitch),conf_frame,
				create_conference_label());
	return conf_frame;
}

void linphone_gtk_set_in_conference(LinphoneCall *call){
	GtkWidget *mw=linphone_gtk_get_main_window();
115
	GtkWidget *conf_frame=(GtkWidget *)g_object_get_data(G_OBJECT(mw),"conf_frame");
116
	GtkWidget *viewswitch=linphone_gtk_get_widget(mw,"viewswitch");
117 118
	GtkWidget *participant;

119
	if(conf_frame==NULL){
120
		conf_frame=create_conference_panel();
121
	}
122 123
	participant=find_conferencee_from_call(call);

124
	if (participant==NULL){
125 126
		/*create and add it */
		GtkWidget *conferencee_box=get_conferencee_box(mw);
127
		GtkWidget *sound_meter;
128
		const LinphoneAddress *addr=linphone_call_get_remote_address(call);
129
		gchar *markup;
130

131
		participant=linphone_gtk_create_widget("callee_frame");
132
		gtk_widget_show(participant);
133 134 135 136 137 138 139 140 141 142
		if (linphone_address_get_display_name(addr)!=NULL){
			markup=g_strdup_printf("<b>%s</b>",linphone_address_get_display_name(addr));
		}else{
			char *tmp=linphone_address_as_string_uri_only(addr);
			markup=g_strdup_printf("%s",tmp);
			ms_free(tmp);
		}
		gtk_label_set_markup(GTK_LABEL(linphone_gtk_get_widget(participant,"callee_name_label")),markup);
		g_free(markup);
		sound_meter=linphone_gtk_get_widget(participant,"sound_indicator");
143 144
		linphone_gtk_init_audio_meter(sound_meter, (get_volume_t) linphone_call_get_play_volume, call);
		gtk_box_pack_start(GTK_BOX(conferencee_box),participant,FALSE,FALSE,PADDING_PIXELS);
145 146
		g_object_set_data_full(G_OBJECT(participant),"call",linphone_call_ref(call),(GDestroyNotify)linphone_call_unref);
		gtk_notebook_set_current_page(GTK_NOTEBOOK(viewswitch),
147
		gtk_notebook_page_num(GTK_NOTEBOOK(viewswitch),conf_frame));
148 149 150 151
	}
}

void linphone_gtk_terminate_conference_participant(LinphoneCall *call){
152
	GtkWidget *frame=find_conferencee_from_call(call);
153 154 155 156 157 158
	if (frame){
		gtk_widget_set_sensitive(frame,FALSE);
	}
}

void linphone_gtk_unset_from_conference(LinphoneCall *call){
159
	GtkWidget *frame=find_conferencee_from_call(call);
160

161
	if (frame){
162 163 164 165
		GtkWidget *mw=linphone_gtk_get_main_window();
		GtkWidget *conf_frame=(GtkWidget *)g_object_get_data(G_OBJECT(mw),"conf_frame");
		GtkWidget *conferencee_box=g_object_get_data(G_OBJECT(mw),"conferencee_box");
		GList *children;
166

167
		g_message("Removing a participant from conference");
168
		gtk_widget_destroy(frame);
169 170 171 172 173 174 175 176 177
		children=gtk_container_get_children(GTK_CONTAINER(conferencee_box));
		if (g_list_length(children)==1){ /* only local participant */
			/*the conference is terminated */
			g_message("The conference is terminated");
			g_object_set_data(G_OBJECT(mw),"conferencee_box",NULL);
			gtk_widget_destroy(conf_frame);
			g_object_set_data(G_OBJECT(mw),"conf_frame",NULL);
		}
		g_list_free(children);
178 179
	}
}
180

181 182 183
bool_t linphone_gtk_call_is_in_conference_view(LinphoneCall *call) {
	return (find_conferencee_from_call(call) != NULL);
}