Mercurial > dwindows
comparison gtk3/dw.c @ 1884:71780cf68aa2
More container and tree changes on all platforms regarding memory.
This should fix GTK3 memory leaks I wasn't previously aware of...
but it will cause all platforms to leak memory if strings returned
from dw_container_query_start(), dw_container_query_next() and
dw_tree_get_title() are not freed with dw_free() when using version 3.
author | bsmith@81767d24-ef19-dc11-ae90-00e081727c95 |
---|---|
date | Wed, 28 Aug 2013 23:47:40 +0000 |
parents | 653ccb517aa1 |
children | f7d408a47752 |
comparison
equal
deleted
inserted
replaced
1883:0fecaedb83fa | 1884:71780cf68aa2 |
---|---|
1380 } | 1380 } |
1381 } | 1381 } |
1382 return retval; | 1382 return retval; |
1383 } | 1383 } |
1384 | 1384 |
1385 #define _DW_DATA_TYPE_STRING 0 | |
1386 #define _DW_DATA_TYPE_POINTER 1 | |
1387 | |
1385 static gint _tree_context_event(GtkWidget *widget, GdkEventButton *event, gpointer data) | 1388 static gint _tree_context_event(GtkWidget *widget, GdkEventButton *event, gpointer data) |
1386 { | 1389 { |
1387 SignalHandler work = _get_signal_handler(data); | 1390 SignalHandler work = _get_signal_handler(data); |
1388 int retval = FALSE; | 1391 int retval = FALSE; |
1389 | 1392 |
1404 if(sel && gtk_tree_selection_get_mode(sel) != GTK_SELECTION_MULTIPLE && | 1407 if(sel && gtk_tree_selection_get_mode(sel) != GTK_SELECTION_MULTIPLE && |
1405 gtk_tree_selection_get_selected(sel, NULL, &iter)) | 1408 gtk_tree_selection_get_selected(sel, NULL, &iter)) |
1406 { | 1409 { |
1407 if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_TREE)) | 1410 if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_TREE)) |
1408 { | 1411 { |
1409 gtk_tree_model_get(store, &iter, 0, &text, 2, &itemdata, -1); | 1412 gtk_tree_model_get(store, &iter, _DW_DATA_TYPE_STRING, &text, 2, &itemdata, -1); |
1410 } | 1413 } |
1411 else | 1414 else |
1412 { | 1415 { |
1413 gtk_tree_model_get(store, &iter, 0, &text, -1); | 1416 gtk_tree_model_get(store, &iter, _DW_DATA_TYPE_STRING, &text, -1); |
1414 } | 1417 } |
1415 } | 1418 } |
1416 else | 1419 else |
1417 { | 1420 { |
1418 GtkTreePath *path; | 1421 GtkTreePath *path; |
1424 | 1427 |
1425 if(gtk_tree_model_get_iter(GTK_TREE_MODEL(store), &iter, path)) | 1428 if(gtk_tree_model_get_iter(GTK_TREE_MODEL(store), &iter, path)) |
1426 { | 1429 { |
1427 if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_TREE)) | 1430 if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_TREE)) |
1428 { | 1431 { |
1429 gtk_tree_model_get(store, &iter, 0, &text, 2, &itemdata, -1); | 1432 gtk_tree_model_get(store, &iter, _DW_DATA_TYPE_STRING, &text, 2, &itemdata, -1); |
1430 } | 1433 } |
1431 else | 1434 else |
1432 { | 1435 { |
1433 gtk_tree_model_get(store, &iter, 0, &text, -1); | 1436 gtk_tree_model_get(store, &iter, _DW_DATA_TYPE_STRING, &text, -1); |
1434 } | 1437 } |
1435 } | 1438 } |
1436 gtk_tree_path_free(path); | 1439 gtk_tree_path_free(path); |
1437 } | 1440 } |
1438 } | 1441 } |
1439 } | 1442 } |
1440 | 1443 |
1441 retval = contextfunc(work.window, text, event->x, event->y, work.data, itemdata); | 1444 retval = contextfunc(work.window, text, event->x, event->y, work.data, itemdata); |
1445 if(text) | |
1446 g_free(text); | |
1442 } | 1447 } |
1443 } | 1448 } |
1444 return retval; | 1449 return retval; |
1445 } | 1450 } |
1446 | 1451 |
1470 if(gtk_tree_selection_get_mode(sel) != GTK_SELECTION_MULTIPLE && | 1475 if(gtk_tree_selection_get_mode(sel) != GTK_SELECTION_MULTIPLE && |
1471 gtk_tree_selection_get_selected(sel, NULL, &iter)) | 1476 gtk_tree_selection_get_selected(sel, NULL, &iter)) |
1472 { | 1477 { |
1473 if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_TREE)) | 1478 if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_TREE)) |
1474 { | 1479 { |
1475 gtk_tree_model_get(store, &iter, 0, &text, 2, &itemdata, 3, &item, -1); | 1480 gtk_tree_model_get(store, &iter, _DW_DATA_TYPE_STRING, &text, 2, &itemdata, 3, &item, -1); |
1476 retval = treeselectfunc(work.window, (HTREEITEM)item, text, work.data, itemdata); | 1481 retval = treeselectfunc(work.window, (HTREEITEM)item, text, work.data, itemdata); |
1477 } | 1482 } |
1478 else if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_CONTAINER)) | 1483 else if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_CONTAINER)) |
1479 { | 1484 { |
1480 gtk_tree_model_get(store, &iter, 0, &text, 1, &itemdata, -1); | 1485 gtk_tree_model_get(store, &iter, _DW_DATA_TYPE_STRING, &text, _DW_DATA_TYPE_POINTER, &itemdata, -1); |
1481 retval = treeselectfunc(work.window, (HTREEITEM)item, text, work.data, itemdata); | 1486 retval = treeselectfunc(work.window, (HTREEITEM)item, text, work.data, itemdata); |
1482 } | 1487 } |
1483 else | 1488 else |
1484 { | 1489 { |
1485 GtkTreePath *path = gtk_tree_model_get_path(GTK_TREE_MODEL(store), &iter); | 1490 GtkTreePath *path = gtk_tree_model_get_path(GTK_TREE_MODEL(store), &iter); |
1509 | 1514 |
1510 if(gtk_tree_model_get_iter(GTK_TREE_MODEL(store), &iter, path)) | 1515 if(gtk_tree_model_get_iter(GTK_TREE_MODEL(store), &iter, path)) |
1511 { | 1516 { |
1512 if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_TREE)) | 1517 if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_TREE)) |
1513 { | 1518 { |
1514 gtk_tree_model_get(store, &iter, 0, &text, 2, &itemdata, 3, &item, -1); | 1519 gtk_tree_model_get(store, &iter, _DW_DATA_TYPE_STRING, &text, 2, &itemdata, 3, &item, -1); |
1515 retval = treeselectfunc(work.window, (HTREEITEM)item, text, work.data, itemdata); | 1520 retval = treeselectfunc(work.window, (HTREEITEM)item, text, work.data, itemdata); |
1516 } | 1521 } |
1517 else if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_CONTAINER)) | 1522 else if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_CONTAINER)) |
1518 { | 1523 { |
1519 gtk_tree_model_get(store, &iter, 0, &text, 1, &itemdata, -1); | 1524 gtk_tree_model_get(store, &iter, _DW_DATA_TYPE_STRING, &text, _DW_DATA_TYPE_POINTER, &itemdata, -1); |
1520 retval = treeselectfunc(work.window, (HTREEITEM)item, text, work.data, itemdata); | 1525 retval = treeselectfunc(work.window, (HTREEITEM)item, text, work.data, itemdata); |
1521 } | 1526 } |
1522 else | 1527 else |
1523 { | 1528 { |
1524 gint *indices = gtk_tree_path_get_indices(path); | 1529 gint *indices = gtk_tree_path_get_indices(path); |
1532 } | 1537 } |
1533 } | 1538 } |
1534 gtk_tree_path_free(path); | 1539 gtk_tree_path_free(path); |
1535 } | 1540 } |
1536 } | 1541 } |
1542 if(text) | |
1543 g_free(text); | |
1537 } | 1544 } |
1538 } | 1545 } |
1539 return retval; | 1546 return retval; |
1540 } | 1547 } |
1541 | 1548 |
1588 | 1595 |
1589 if(gtk_tree_model_get_iter(GTK_TREE_MODEL(store), &iter, path)) | 1596 if(gtk_tree_model_get_iter(GTK_TREE_MODEL(store), &iter, path)) |
1590 { | 1597 { |
1591 if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_CONTAINER)) | 1598 if(g_object_get_data(G_OBJECT(widget), "_dw_tree_type") == GINT_TO_POINTER(_DW_TREE_TYPE_CONTAINER)) |
1592 { | 1599 { |
1593 gtk_tree_model_get(store, &iter, 0, &text, 1, &data, -1); | 1600 gtk_tree_model_get(store, &iter, _DW_DATA_TYPE_STRING, &text, _DW_DATA_TYPE_POINTER, &data, -1); |
1594 retval = contextfunc(work.window, text, work.data, data); | 1601 retval = contextfunc(work.window, text, work.data, data); |
1602 if(text) | |
1603 g_free(text); | |
1595 } | 1604 } |
1596 } | 1605 } |
1597 gtk_tree_path_free(path); | 1606 gtk_tree_path_free(path); |
1598 } | 1607 } |
1599 } | 1608 } |
5258 DW_MUTEX_LOCK; | 5267 DW_MUTEX_LOCK; |
5259 tree = (GtkWidget *)g_object_get_data(G_OBJECT(handle), "_dw_user"); | 5268 tree = (GtkWidget *)g_object_get_data(G_OBJECT(handle), "_dw_user"); |
5260 | 5269 |
5261 if(tree && GTK_IS_TREE_VIEW(tree) && | 5270 if(tree && GTK_IS_TREE_VIEW(tree) && |
5262 (store = (GtkTreeModel *)gtk_tree_view_get_model(GTK_TREE_VIEW(tree)))) | 5271 (store = (GtkTreeModel *)gtk_tree_view_get_model(GTK_TREE_VIEW(tree)))) |
5263 gtk_tree_model_get(store, (GtkTreeIter *)item, 0, &text, -1); | 5272 gtk_tree_model_get(store, (GtkTreeIter *)item, _DW_DATA_TYPE_STRING, &text, -1); |
5273 if(text) | |
5274 { | |
5275 char *temp = text; | |
5276 text = strdup(temp); | |
5277 g_free(temp); | |
5278 } | |
5264 DW_MUTEX_UNLOCK; | 5279 DW_MUTEX_UNLOCK; |
5265 return text; | 5280 return text; |
5266 } | 5281 } |
5267 | 5282 |
5268 /* | 5283 /* |
6139 } | 6154 } |
6140 DW_MUTEX_UNLOCK; | 6155 DW_MUTEX_UNLOCK; |
6141 } | 6156 } |
6142 | 6157 |
6143 /* Internal version for both */ | 6158 /* Internal version for both */ |
6144 #define _DW_DATA_TYPE_STRING 0 | |
6145 #define _DW_DATA_TYPE_POINTER 1 | |
6146 | |
6147 void _dw_container_set_row_data(HWND handle, void *pointer, int row, int type, void *data) | 6159 void _dw_container_set_row_data(HWND handle, void *pointer, int row, int type, void *data) |
6148 { | 6160 { |
6149 GtkWidget *cont = handle; | 6161 GtkWidget *cont = handle; |
6150 GtkListStore *store = NULL; | 6162 GtkListStore *store = NULL; |
6151 int _locked_by_me = FALSE; | 6163 int _locked_by_me = FALSE; |
6391 { | 6403 { |
6392 GtkWidget *cont; | 6404 GtkWidget *cont; |
6393 GtkListStore *store = NULL; | 6405 GtkListStore *store = NULL; |
6394 char *retval = NULL; | 6406 char *retval = NULL; |
6395 int _locked_by_me = FALSE; | 6407 int _locked_by_me = FALSE; |
6408 int type = flags & DW_CR_RETDATA ? _DW_DATA_TYPE_POINTER : _DW_DATA_TYPE_STRING; | |
6396 | 6409 |
6397 DW_MUTEX_LOCK; | 6410 DW_MUTEX_LOCK; |
6398 cont = (GtkWidget *)g_object_get_data(G_OBJECT(handle), "_dw_user"); | 6411 cont = (GtkWidget *)g_object_get_data(G_OBJECT(handle), "_dw_user"); |
6399 | 6412 |
6400 /* Make sure it is the correct tree type */ | 6413 /* Make sure it is the correct tree type */ |
6420 { | 6433 { |
6421 GtkTreeIter iter; | 6434 GtkTreeIter iter; |
6422 | 6435 |
6423 if(gtk_tree_model_iter_nth_child(GTK_TREE_MODEL(store), &iter, NULL, indices[0])) | 6436 if(gtk_tree_model_iter_nth_child(GTK_TREE_MODEL(store), &iter, NULL, indices[0])) |
6424 { | 6437 { |
6425 gtk_tree_model_get(GTK_TREE_MODEL(store), &iter, 0, &retval, -1); | 6438 gtk_tree_model_get(GTK_TREE_MODEL(store), &iter, type, &retval, -1); |
6426 g_object_set_data(G_OBJECT(cont), "_dw_querypos", GINT_TO_POINTER(1)); | 6439 g_object_set_data(G_OBJECT(cont), "_dw_querypos", GINT_TO_POINTER(1)); |
6427 } | 6440 } |
6428 } | 6441 } |
6429 } | 6442 } |
6430 g_list_foreach(list, (GFunc) gtk_tree_path_free, NULL); | 6443 g_list_foreach(list, (GFunc) gtk_tree_path_free, NULL); |
6440 { | 6453 { |
6441 GtkTreeIter iter; | 6454 GtkTreeIter iter; |
6442 | 6455 |
6443 if(gtk_tree_model_get_iter(GTK_TREE_MODEL(store), &iter, path)) | 6456 if(gtk_tree_model_get_iter(GTK_TREE_MODEL(store), &iter, path)) |
6444 { | 6457 { |
6445 gtk_tree_model_get(GTK_TREE_MODEL(store), &iter, 0, &retval, -1); | 6458 gtk_tree_model_get(GTK_TREE_MODEL(store), &iter, type, &retval, -1); |
6446 } | 6459 } |
6447 gtk_tree_path_free(path); | 6460 gtk_tree_path_free(path); |
6448 } | 6461 } |
6449 } | 6462 } |
6450 else | 6463 else |
6451 { | 6464 { |
6452 GtkTreeIter iter; | 6465 GtkTreeIter iter; |
6453 | 6466 |
6454 if(gtk_tree_model_iter_nth_child(GTK_TREE_MODEL(store), &iter, NULL, 0)) | 6467 if(gtk_tree_model_iter_nth_child(GTK_TREE_MODEL(store), &iter, NULL, 0)) |
6455 { | 6468 { |
6456 gtk_tree_model_get(GTK_TREE_MODEL(store), &iter, 0, &retval, -1); | 6469 gtk_tree_model_get(GTK_TREE_MODEL(store), &iter, type, &retval, -1); |
6457 g_object_set_data(G_OBJECT(cont), "_dw_querypos", GINT_TO_POINTER(1)); | 6470 g_object_set_data(G_OBJECT(cont), "_dw_querypos", GINT_TO_POINTER(1)); |
6458 } | 6471 } |
6459 } | 6472 } |
6473 } | |
6474 /* If there is a title, duplicate it and free the temporary copy */ | |
6475 if(retval && type == _DW_DATA_TYPE_STRING) | |
6476 { | |
6477 char *temp = retval; | |
6478 retval = strdup(temp); | |
6479 g_free(temp); | |
6460 } | 6480 } |
6461 DW_MUTEX_UNLOCK; | 6481 DW_MUTEX_UNLOCK; |
6462 return retval; | 6482 return retval; |
6463 } | 6483 } |
6464 | 6484 |
6474 { | 6494 { |
6475 GtkWidget *cont; | 6495 GtkWidget *cont; |
6476 GtkListStore *store = NULL; | 6496 GtkListStore *store = NULL; |
6477 char *retval = NULL; | 6497 char *retval = NULL; |
6478 int _locked_by_me = FALSE; | 6498 int _locked_by_me = FALSE; |
6499 int type = flags & DW_CR_RETDATA ? _DW_DATA_TYPE_POINTER : _DW_DATA_TYPE_STRING; | |
6479 | 6500 |
6480 DW_MUTEX_LOCK; | 6501 DW_MUTEX_LOCK; |
6481 cont = (GtkWidget *)g_object_get_data(G_OBJECT(handle), "_dw_user"); | 6502 cont = (GtkWidget *)g_object_get_data(G_OBJECT(handle), "_dw_user"); |
6482 | 6503 |
6483 /* Make sure it is the correct tree type */ | 6504 /* Make sure it is the correct tree type */ |
6507 { | 6528 { |
6508 GtkTreeIter iter; | 6529 GtkTreeIter iter; |
6509 | 6530 |
6510 if(gtk_tree_model_iter_nth_child(GTK_TREE_MODEL(store), &iter, NULL, indices[0])) | 6531 if(gtk_tree_model_iter_nth_child(GTK_TREE_MODEL(store), &iter, NULL, indices[0])) |
6511 { | 6532 { |
6512 gtk_tree_model_get(GTK_TREE_MODEL(store), &iter, 0, &retval, -1); | 6533 gtk_tree_model_get(GTK_TREE_MODEL(store), &iter, type, &retval, -1); |
6513 g_object_set_data(G_OBJECT(cont), "_dw_querypos", GINT_TO_POINTER(pos+1)); | 6534 g_object_set_data(G_OBJECT(cont), "_dw_querypos", GINT_TO_POINTER(pos+1)); |
6514 } | 6535 } |
6515 } | 6536 } |
6516 } | 6537 } |
6517 g_list_foreach(list, (GFunc) gtk_tree_path_free, NULL); | 6538 g_list_foreach(list, (GFunc) gtk_tree_path_free, NULL); |
6529 { | 6550 { |
6530 GtkTreeIter iter; | 6551 GtkTreeIter iter; |
6531 | 6552 |
6532 if(pos < count && gtk_tree_model_iter_nth_child(GTK_TREE_MODEL(store), &iter, NULL, pos)) | 6553 if(pos < count && gtk_tree_model_iter_nth_child(GTK_TREE_MODEL(store), &iter, NULL, pos)) |
6533 { | 6554 { |
6534 gtk_tree_model_get(GTK_TREE_MODEL(store), &iter, 0, &retval, -1); | 6555 gtk_tree_model_get(GTK_TREE_MODEL(store), &iter, type, &retval, -1); |
6535 g_object_set_data(G_OBJECT(cont), "_dw_querypos", GINT_TO_POINTER(pos+1)); | 6556 g_object_set_data(G_OBJECT(cont), "_dw_querypos", GINT_TO_POINTER(pos+1)); |
6536 } | 6557 } |
6537 } | 6558 } |
6538 } | 6559 } |
6560 /* If there is a title, duplicate it and free the temporary copy */ | |
6561 if(retval && type == _DW_DATA_TYPE_STRING) | |
6562 { | |
6563 char *temp = retval; | |
6564 retval = strdup(temp); | |
6565 g_free(temp); | |
6566 } | |
6539 DW_MUTEX_UNLOCK; | 6567 DW_MUTEX_UNLOCK; |
6540 return retval; | 6568 return retval; |
6541 } | 6569 } |
6542 | 6570 |
6543 int _find_iter(GtkListStore *store, GtkTreeIter *iter, void *data, int textcomp) | 6571 int _find_iter(GtkListStore *store, GtkTreeIter *iter, void *data, int textcomp) |
6544 { | 6572 { |
6545 int z, rows = gtk_tree_model_iter_n_children(GTK_TREE_MODEL(store), NULL); | 6573 int z, rows = gtk_tree_model_iter_n_children(GTK_TREE_MODEL(store), NULL); |
6546 void *thisdata; | 6574 void *thisdata; |
6575 int retval = FALSE; | |
6547 | 6576 |
6548 for(z=0;z<rows;z++) | 6577 for(z=0;z<rows;z++) |
6549 { | 6578 { |
6550 if(gtk_tree_model_iter_nth_child(GTK_TREE_MODEL(store), iter, NULL, z)) | 6579 if(gtk_tree_model_iter_nth_child(GTK_TREE_MODEL(store), iter, NULL, z)) |
6551 { | 6580 { |
6552 /* Get either string from position 0 or pointer from position 1 */ | 6581 /* Get either string from position 0 or pointer from position 1 */ |
6553 gtk_tree_model_get(GTK_TREE_MODEL(store), iter, textcomp ? 0 : 1, &thisdata, -1); | 6582 gtk_tree_model_get(GTK_TREE_MODEL(store), iter, textcomp ? _DW_DATA_TYPE_STRING : _DW_DATA_TYPE_POINTER, &thisdata, -1); |
6554 if((textcomp && thisdata && strcmp((char *)thisdata, (char *)data) == 0) || (!textcomp && thisdata == data)) | 6583 if((textcomp && thisdata && strcmp((char *)thisdata, (char *)data) == 0) || (!textcomp && thisdata == data)) |
6555 { | 6584 { |
6556 return TRUE; | 6585 retval = TRUE; |
6586 z = rows; | |
6557 } | 6587 } |
6558 } | 6588 if(textcomp && thisdata) |
6559 } | 6589 g_free(thisdata); |
6560 return FALSE; | 6590 } |
6591 } | |
6592 return retval; | |
6561 } | 6593 } |
6562 | 6594 |
6563 void _dw_container_cursor(HWND handle, void *data, int textcomp) | 6595 void _dw_container_cursor(HWND handle, void *data, int textcomp) |
6564 { | 6596 { |
6565 GtkWidget *cont; | 6597 GtkWidget *cont; |
9988 /* Get the nth child at the top level */ | 10020 /* Get the nth child at the top level */ |
9989 if(gtk_tree_model_iter_nth_child(GTK_TREE_MODEL(store), &iter, NULL, index)) | 10021 if(gtk_tree_model_iter_nth_child(GTK_TREE_MODEL(store), &iter, NULL, index)) |
9990 { | 10022 { |
9991 /* Get the text */ | 10023 /* Get the text */ |
9992 gchar *text; | 10024 gchar *text; |
9993 gtk_tree_model_get(GTK_TREE_MODEL(store), &iter, 0, &text, -1); | 10025 gtk_tree_model_get(GTK_TREE_MODEL(store), &iter, _DW_DATA_TYPE_STRING, &text, -1); |
9994 strncpy(buffer, text, length); | 10026 if(text) |
10027 { | |
10028 strncpy(buffer, text, length); | |
10029 g_free(text); | |
10030 } | |
9995 DW_MUTEX_UNLOCK; | 10031 DW_MUTEX_UNLOCK; |
9996 return; | 10032 return; |
9997 } | 10033 } |
9998 } | 10034 } |
9999 } | 10035 } |