anastasis-gtk_rows.h (8236B)
1 /* 2 This file is part of anastasis-gtk. 3 Copyright (C) 2025 Anastasis SARL 4 5 Anastasis is free software; you can redistribute it and/or modify 6 it under the terms of the GNU General Public License as published 7 by the Free Software Foundation; either version 3, or (at your 8 option) any later version. 9 10 Anastasis is distributed in the hope that it will be useful, but 11 WITHOUT ANY WARRANTY; without even the implied warranty of 12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 13 General Public License for more details. 14 15 You should have received a copy of the GNU General Public License 16 along with Anastasis; see the file COPYING. If not, write to the 17 Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, 18 Boston, MA 02110-1301, USA. 19 */ 20 /** 21 * @file src/anastasis/anastasis-gtk_rows.h 22 * @brief Rows of the GtkColumnViews and the models holding them 23 * @author Christian Grothoff 24 */ 25 #ifndef ANASTASIS_GTK_ROWS_H 26 #define ANASTASIS_GTK_ROWS_H 27 28 #include <gtk/gtk.h> 29 #include <jansson.h> 30 31 32 /** 33 * One row of one of our lists. The values shown in the cells and the 34 * bookkeeping data that goes with them are kept as JSON, which is also 35 * what the reducer state we build the rows from is made of. 36 */ 37 #define AG_TYPE_ROW (AG_row_get_type ()) 38 39 G_DECLARE_FINAL_TYPE (AGRow, 40 AG_row, 41 AG, 42 ROW, 43 GObject); 44 45 46 /** 47 * Create a row with the given @a fields. 48 * 49 * @param fields the values of the row, ownership is taken 50 * @return the new row 51 */ 52 AGRow * 53 AG_row_new (json_t *fields); 54 55 56 /** 57 * Change the @a field of @a row to @a value. 58 * 59 * @param row the row to update 60 * @param field name of the field 61 * @param value new value, ownership is taken 62 */ 63 void 64 AG_row_set (AGRow *row, 65 const char *field, 66 json_t *value); 67 68 69 /** 70 * Obtain the string @a field of @a row. 71 * 72 * @param row the row to inspect 73 * @param field name of the field 74 * @return NULL if there is no such string field 75 */ 76 const char * 77 AG_row_string (AGRow *row, 78 const char *field); 79 80 81 /** 82 * Obtain the boolean @a field of @a row. 83 * 84 * @param row the row to inspect 85 * @param field name of the field 86 * @return false if there is no such field 87 */ 88 bool 89 AG_row_bool (AGRow *row, 90 const char *field); 91 92 93 /** 94 * Obtain the numeric @a field of @a row. 95 * 96 * @param row the row to inspect 97 * @param field name of the field 98 * @return 0 if there is no such field 99 */ 100 uint64_t 101 AG_row_uint (AGRow *row, 102 const char *field); 103 104 105 /** 106 * Obtain the @a field of @a row as JSON. 107 * 108 * @param row the row to inspect 109 * @param field name of the field 110 * @return NULL if there is no such field, otherwise 111 * a value borrowed from @a row 112 */ 113 json_t * 114 AG_row_json (AGRow *row, 115 const char *field); 116 117 118 /** 119 * Set the image @a row is to be rendered with. 120 * 121 * @param row the row to update 122 * @param image the image, ownership is taken; may be NULL 123 */ 124 void 125 AG_row_set_image (AGRow *row, 126 GdkPaintable *image); 127 128 129 /** 130 * Return the image @a row is rendered with. 131 * 132 * @param row the row to inspect 133 * @return NULL if @a row has no image 134 */ 135 GdkPaintable * 136 AG_row_image (AGRow *row); 137 138 139 /** 140 * Return the rows nested under @a row, creating the list on first use. 141 * Only rows of a tree ever have children. 142 * 143 * @param row the parent row 144 * @return the children of @a row, owned by @a row 145 */ 146 GListStore * 147 AG_row_children (AGRow *row); 148 149 150 /* ***************** the lists of rows ****************** */ 151 152 153 /** 154 * Return the list of rows called @a name in the main window. 155 * 156 * @param name name of the model in the UI file 157 * @return the model, NULL on error 158 */ 159 GListStore * 160 AG_list (const char *name); 161 162 163 /** 164 * Return the list of rows called @a name in the window @a builder built. 165 * 166 * @param builder builder of the window holding the list 167 * @param name name of the model in the UI file 168 * @return the model, NULL on error 169 */ 170 GListStore * 171 AG_list_of (GtkBuilder *builder, 172 const char *name); 173 174 175 /** 176 * Remove all rows from the list called @a name in the main window. 177 * 178 * @param name name of the model in the UI file 179 */ 180 void 181 AG_list_clear (const char *name); 182 183 184 /** 185 * Append a row with the given @a fields to @a list. 186 * 187 * @param list list to append to 188 * @param fields the values of the row, ownership is taken 189 * @return the new row, owned by @a list 190 */ 191 AGRow * 192 AG_list_append (GListStore *list, 193 json_t *fields); 194 195 196 /** 197 * Append @a row to @a list. Rows that have children must be filled 198 * before they are added, as only then does the list learn that they can 199 * be expanded. 200 * 201 * @param list list to append to 202 * @param row the row to append, ownership is taken 203 */ 204 void 205 AG_list_add_row (GListStore *list, 206 AGRow *row); 207 208 209 /** 210 * Append a row with the given @a fields to the list called @a name in 211 * the main window. 212 * 213 * @param name name of the model in the UI file 214 * @param fields the values of the row, ownership is taken 215 * @return the new row, owned by the list 216 */ 217 AGRow * 218 AG_list_add (const char *name, 219 json_t *fields); 220 221 222 /** 223 * Return the row @a item stands for. Rows of a tree are wrapped into a 224 * `GtkTreeListRow` by the model, this unwraps them. 225 * 226 * @param item item of a list model, may be NULL 227 * @return NULL if @a item is NULL 228 */ 229 AGRow * 230 AG_row_of (gpointer item); 231 232 233 /** 234 * Attach the row a cell shows to the @a widget rendering it, so that 235 * #AG_row_at() can find the row a click landed on. 236 * 237 * @param widget widget rendering the cell 238 * @param row the row being rendered, may be NULL 239 */ 240 void 241 AG_cell_set_row (GtkWidget *widget, 242 AGRow *row); 243 244 245 /** 246 * Return the row the cell rendered by @a widget shows. 247 * 248 * @param widget widget rendering a cell 249 * @return NULL if @a widget is not bound to a row 250 */ 251 AGRow * 252 AG_cell_get_row (GtkWidget *widget); 253 254 255 /* ******************* selections ********************* */ 256 257 258 /** 259 * Return the row that is selected in @a selection. 260 * 261 * @param selection the selection to inspect 262 * @return NULL if nothing is selected 263 */ 264 AGRow * 265 AG_selected (GtkSingleSelection *selection); 266 267 268 /** 269 * Return the row selected in the selection called @a name of the main 270 * window. 271 * 272 * @param name name of the selection in the UI file 273 * @return NULL if nothing is selected 274 */ 275 AGRow * 276 AG_selected_row (const char *name); 277 278 279 /** 280 * Select the row at @a position in the selection called @a name of the 281 * main window. 282 * 283 * @param name name of the selection in the UI file 284 * @param position index of the row to select 285 */ 286 void 287 AG_select_row (const char *name, 288 guint position); 289 290 291 /** 292 * Return the row shown at @a y in @a view. Used to find the row a 293 * context menu was opened on. 294 * 295 * @param view the column view that was clicked 296 * @param y vertical position of the click, in widget coordinates 297 * @return NULL if there is no row at @a y 298 */ 299 AGRow * 300 AG_row_at (GtkWidget *view, 301 double y); 302 303 304 /* ****************** sorting ******************* */ 305 306 307 /** 308 * How a column of a list is to be sorted. 309 */ 310 struct AG_SortSpec 311 { 312 /** 313 * Name of the `GtkColumnViewColumn` in the UI file. 314 */ 315 const char *column; 316 317 /** 318 * Field of the rows to compare. 319 */ 320 const char *field; 321 322 /** 323 * True to compare the field numerically instead of as text. 324 */ 325 bool numeric; 326 }; 327 328 329 /** 330 * Make the columns given in @a specs of the column view called @a view 331 * sort the rows of @a sort_model. Both objects are looked up in @a 332 * builder. 333 * 334 * @param builder builder of the window holding the list 335 * @param view name of the `GtkColumnView` in the UI file 336 * @param sort_model name of the `GtkSortListModel` feeding @a view 337 * @param specs the columns to make sortable, terminated by a NULL column 338 */ 339 void 340 AG_list_make_sortable (GtkBuilder *builder, 341 const char *view, 342 const char *sort_model, 343 const struct AG_SortSpec *specs); 344 345 346 /** 347 * Set up those models of the main window that cannot be described in 348 * the UI file. To be called once, after the main window was built. 349 */ 350 void 351 AG_lists_setup (void); 352 353 354 #endif