evolution-3.6.4/widgets/table/e-table-subset-variable.c

No issues found

  1 /*
  2  * This program is free software; you can redistribute it and/or
  3  * modify it under the terms of the GNU Lesser General Public
  4  * License as published by the Free Software Foundation; either
  5  * version 2 of the License, or (at your option) version 3.
  6  *
  7  * This program is distributed in the hope that it will be useful,
  8  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  9  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 10  * Lesser General Public License for more details.
 11  *
 12  * You should have received a copy of the GNU Lesser General Public
 13  * License along with the program; if not, see <http://www.gnu.org/licenses/>
 14  *
 15  *
 16  * Authors:
 17  *		Chris Lahey <clahey@ximian.com>
 18  *
 19  * Copyright (C) 1999-2008 Novell, Inc. (www.novell.com)
 20  *
 21  */
 22 
 23 #ifdef HAVE_CONFIG_H
 24 #include <config.h>
 25 #endif
 26 
 27 #include <stdlib.h>
 28 #include <string.h>
 29 
 30 #include "e-util/e-util.h"
 31 
 32 #include "e-table-subset-variable.h"
 33 
 34 #define ETSSV_CLASS(e) (E_TABLE_SUBSET_VARIABLE_GET_CLASS (e))
 35 
 36 /* workaround for avoiding API breakage */
 37 #define etssv_get_type e_table_subset_variable_get_type
 38 G_DEFINE_TYPE (ETableSubsetVariable, etssv, E_TYPE_TABLE_SUBSET)
 39 
 40 #define INCREMENT_AMOUNT 10
 41 
 42 static void
 43 etssv_add (ETableSubsetVariable *etssv,
 44            gint row)
 45 {
 46 	ETableModel *etm = E_TABLE_MODEL (etssv);
 47 	ETableSubset *etss = E_TABLE_SUBSET (etssv);
 48 
 49 	e_table_model_pre_change (etm);
 50 
 51 	if (etss->n_map + 1 > etssv->n_vals_allocated) {
 52 		etssv->n_vals_allocated += INCREMENT_AMOUNT;
 53 		etss->map_table = g_realloc (
 54 			etss->map_table,
 55 			etssv->n_vals_allocated * sizeof (gint));
 56 	}
 57 
 58 	etss->map_table[etss->n_map++] = row;
 59 
 60 	e_table_model_row_inserted (etm, etss->n_map - 1);
 61 }
 62 
 63 static void
 64 etssv_add_array (ETableSubsetVariable *etssv,
 65                  const gint *array,
 66                  gint count)
 67 {
 68 	ETableModel *etm = E_TABLE_MODEL (etssv);
 69 	ETableSubset *etss = E_TABLE_SUBSET (etssv);
 70 	gint i;
 71 
 72 	e_table_model_pre_change (etm);
 73 
 74 	if (etss->n_map + count > etssv->n_vals_allocated) {
 75 		etssv->n_vals_allocated += MAX (INCREMENT_AMOUNT, count);
 76 		etss->map_table = g_realloc (
 77 			etss->map_table,
 78 			etssv->n_vals_allocated * sizeof (gint));
 79 	}
 80 	for (i = 0; i < count; i++)
 81 		etss->map_table[etss->n_map++] = array[i];
 82 
 83 	e_table_model_changed (etm);
 84 }
 85 
 86 static void
 87 etssv_add_all (ETableSubsetVariable *etssv)
 88 {
 89 	ETableModel *etm = E_TABLE_MODEL (etssv);
 90 	ETableSubset *etss = E_TABLE_SUBSET (etssv);
 91 	gint rows;
 92 	gint i;
 93 
 94 	e_table_model_pre_change (etm);
 95 
 96 	rows = e_table_model_row_count (etss->source);
 97 	if (etss->n_map + rows > etssv->n_vals_allocated) {
 98 		etssv->n_vals_allocated += MAX (INCREMENT_AMOUNT, rows);
 99 		etss->map_table = g_realloc (
100 			etss->map_table,
101 			etssv->n_vals_allocated * sizeof (gint));
102 	}
103 	for (i = 0; i < rows; i++)
104 		etss->map_table[etss->n_map++] = i;
105 
106 	e_table_model_changed (etm);
107 }
108 
109 static gboolean
110 etssv_remove (ETableSubsetVariable *etssv,
111               gint row)
112 {
113 	ETableModel *etm = E_TABLE_MODEL (etssv);
114 	ETableSubset *etss = E_TABLE_SUBSET (etssv);
115 	gint i;
116 
117 	for (i = 0; i < etss->n_map; i++) {
118 		if (etss->map_table[i] == row) {
119 			e_table_model_pre_change (etm);
120 			memmove (
121 				etss->map_table + i,
122 				etss->map_table + i + 1,
123 				(etss->n_map - i - 1) * sizeof (gint));
124 			etss->n_map--;
125 
126 			e_table_model_row_deleted (etm, i);
127 			return TRUE;
128 		}
129 	}
130 	return FALSE;
131 }
132 
133 static void
134 etssv_class_init (ETableSubsetVariableClass *class)
135 {
136 	class->add     = etssv_add;
137 	class->add_array = etssv_add_array;
138 	class->add_all = etssv_add_all;
139 	class->remove  = etssv_remove;
140 }
141 
142 static void
143 etssv_init (ETableSubsetVariable *etssv)
144 {
145 	/* nothing to do */
146 }
147 
148 ETableModel *
149 e_table_subset_variable_construct (ETableSubsetVariable *etssv,
150                                    ETableModel *source)
151 {
152 	if (e_table_subset_construct (E_TABLE_SUBSET (etssv), source, 1) == NULL)
153 		return NULL;
154 	E_TABLE_SUBSET (etssv)->n_map = 0;
155 
156 	return E_TABLE_MODEL (etssv);
157 }
158 
159 ETableModel *
160 e_table_subset_variable_new (ETableModel *source)
161 {
162 	ETableSubsetVariable *etssv = g_object_new (E_TYPE_TABLE_SUBSET_VARIABLE, NULL);
163 
164 	if (e_table_subset_variable_construct (etssv, source) == NULL) {
165 		g_object_unref (etssv);
166 		return NULL;
167 	}
168 
169 	return (ETableModel *) etssv;
170 }
171 
172 void
173 e_table_subset_variable_add (ETableSubsetVariable *etssv,
174                              gint row)
175 {
176 	g_return_if_fail (etssv != NULL);
177 	g_return_if_fail (E_IS_TABLE_SUBSET_VARIABLE (etssv));
178 
179 	if (ETSSV_CLASS (etssv)->add)
180 		ETSSV_CLASS (etssv)->add (etssv, row);
181 }
182 
183 void
184 e_table_subset_variable_add_array (ETableSubsetVariable *etssv,
185                                    const gint *array,
186                                    gint count)
187 {
188 	g_return_if_fail (etssv != NULL);
189 	g_return_if_fail (E_IS_TABLE_SUBSET_VARIABLE (etssv));
190 
191 	if (ETSSV_CLASS (etssv)->add_array)
192 		ETSSV_CLASS (etssv)->add_array (etssv, array, count);
193 }
194 
195 void
196 e_table_subset_variable_add_all (ETableSubsetVariable *etssv)
197 {
198 	g_return_if_fail (etssv != NULL);
199 	g_return_if_fail (E_IS_TABLE_SUBSET_VARIABLE (etssv));
200 
201 	if (ETSSV_CLASS (etssv)->add_all)
202 		ETSSV_CLASS (etssv)->add_all (etssv);
203 }
204 
205 gboolean
206 e_table_subset_variable_remove (ETableSubsetVariable *etssv,
207                                 gint row)
208 {
209 	g_return_val_if_fail (etssv != NULL, FALSE);
210 	g_return_val_if_fail (E_IS_TABLE_SUBSET_VARIABLE (etssv), FALSE);
211 
212 	if (ETSSV_CLASS (etssv)->remove)
213 		return ETSSV_CLASS (etssv)->remove (etssv, row);
214 	else
215 		return FALSE;
216 }
217 
218 void
219 e_table_subset_variable_clear (ETableSubsetVariable *etssv)
220 {
221 	ETableModel *etm = E_TABLE_MODEL (etssv);
222 	ETableSubset *etss = E_TABLE_SUBSET (etssv);
223 
224 	e_table_model_pre_change (etm);
225 	etss->n_map = 0;
226 	g_free (etss->map_table);
227 	etss->map_table = (gint *) g_new (guint, 1);
228 	etssv->n_vals_allocated = 1;
229 
230 	e_table_model_changed (etm);
231 }
232 
233 void
234 e_table_subset_variable_increment (ETableSubsetVariable *etssv,
235                                    gint position,
236                                    gint amount)
237 {
238 	gint i;
239 	ETableSubset *etss = E_TABLE_SUBSET (etssv);
240 	for (i = 0; i < etss->n_map; i++) {
241 		if (etss->map_table[i] >= position)
242 			etss->map_table[i] += amount;
243 	}
244 }
245 
246 void
247 e_table_subset_variable_decrement (ETableSubsetVariable *etssv,
248                                    gint position,
249                                    gint amount)
250 {
251 	gint i;
252 	ETableSubset *etss = E_TABLE_SUBSET (etssv);
253 	for (i = 0; i < etss->n_map; i++) {
254 		if (etss->map_table[i] >= position)
255 			etss->map_table[i] -= amount;
256 	}
257 }
258 
259 void
260 e_table_subset_variable_set_allocation (ETableSubsetVariable *etssv,
261                                         gint total)
262 {
263 	ETableSubset *etss = E_TABLE_SUBSET (etssv);
264 	if (total <= 0)
265 		total = 1;
266 	if (total > etss->n_map) {
267 		etss->map_table = g_realloc (etss->map_table, total * sizeof (gint));
268 	}
269 }