"Fossies" - the Fresh Open Source Software Archive

Member "jpilot-2_0_1/install_gui.c" (3 Apr 2021, 16768 Bytes) of package /linux/privat/jpilot-2_0_1.tar.gz:


As a special service "Fossies" has tried to format the requested source page into HTML format using (guessed) C and C++ source code syntax highlighting (style: standard) with prefixed line numbers and code folding option. Alternatively you can here view or download the uninterpreted source code file. For more information about "install_gui.c" see the Fossies "Dox" file reference documentation and the latest Fossies "Diffs" side-by-side code changes report: 1.8.2_vs_2_0_1.

    1 /*******************************************************************************
    2  * install_gui.c
    3  * A module of J-Pilot http://jpilot.org
    4  *
    5  * Copyright (C) 1999-2014 by Judd Montgomery
    6  *
    7  * This program is free software; you can redistribute it and/or modify
    8  * it under the terms of the GNU General Public License as published by
    9  * the Free Software Foundation; version 2 of the License.
   10  *
   11  * This program is distributed in the hope that it will be useful,
   12  * but WITHOUT ANY WARRANTY; without even the implied warranty of
   13  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
   14  * GNU General Public License for more details.
   15  *
   16  * You should have received a copy of the GNU General Public License
   17  * along with this program; if not, write to the Free Software
   18  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
   19  ******************************************************************************/
   20 
   21 /********************************* Includes ***********************************/
   22 #include "config.h"
   23 #include <gtk/gtk.h>
   24 #include <string.h>
   25 #include <stdlib.h>
   26 #include <sys/types.h>
   27 #include <sys/stat.h>
   28 #include <unistd.h>
   29 
   30 #include "i18n.h"
   31 #include "utils.h"
   32 #include "prefs.h"
   33 #include "log.h"
   34 
   35 /********************************* Constants **********************************/
   36 #define INST_SDCARD_COLUMN 0
   37 #define INST_FNAME_COLUMN  1
   38 
   39 /******************************* Global vars **********************************/
   40 static GtkWidget *treeView;
   41 static GtkListStore *listStore;
   42 static int row_selected;
   43 static int column_selected;
   44 enum {
   45     INSTALL_SDCARD_COLUMN_ENUM = 0,
   46     INSTALL_FNAME_COLUMN_ENUM,
   47     INSTALL_DATA_COLUMN_ENUM,
   48     INSTALL_BACKGROUND_COLOR_ENUM,
   49     INSTALL_BACKGROUND_COLOR_ENABLED_ENUM,
   50     INSTALL_NUM_COLS
   51 };
   52 
   53 /****************************** Prototypes ************************************/
   54 static int install_update_listStore(void);
   55 /****************************** Main Code *************************************/
   56 static int install_remove_line(int deleted_line_num) {
   57     FILE *in;
   58     FILE *out;
   59     char line[1002];
   60     char *Pc;
   61     int r, line_count;
   62 
   63     in = jp_open_home_file(EPN".install", "r");
   64     if (!in) {
   65         jp_logf(JP_LOG_DEBUG, "failed opening install_file\n");
   66         return EXIT_FAILURE;
   67     }
   68 
   69     out = jp_open_home_file(EPN".install.tmp", "w");
   70     if (!out) {
   71         fclose(in);
   72         jp_logf(JP_LOG_DEBUG, "failed opening install_file.tmp\n");
   73         return EXIT_FAILURE;
   74     }
   75 
   76     /* Delete line by copying file and skipping over line to delete */
   77     for (line_count = 0; !feof(in); line_count++) {
   78         line[0] = '\0';
   79         Pc = fgets(line, 1000, in);
   80         if (!Pc) {
   81             break;
   82         }
   83         if (line_count == deleted_line_num) {
   84             continue;
   85         }
   86         r = fprintf(out, "%s", line);
   87         if (r == EOF) {
   88             break;
   89         }
   90     }
   91     fclose(in);
   92     fclose(out);
   93 
   94     rename_file(EPN".install.tmp", EPN".install");
   95 
   96     return EXIT_SUCCESS;
   97 }
   98 
   99 int install_append_line(const char *line) {
  100     FILE *out;
  101     int r;
  102 
  103     out = jp_open_home_file(EPN".install", "a");
  104     if (!out) {
  105         return EXIT_FAILURE;
  106     }
  107 
  108     r = fprintf(out, "%s\n", line);
  109     if (r == EOF) {
  110         fclose(out);
  111         return EXIT_FAILURE;
  112     }
  113     fclose(out);
  114 
  115     return EXIT_SUCCESS;
  116 }
  117 
  118 static int install_modify_line(int modified_line_num, const char *modified_line) {
  119     FILE *in;
  120     FILE *out;
  121     char line[1002];
  122     char *Pc;
  123     int r, line_count;
  124 
  125     in = jp_open_home_file(EPN".install", "r");
  126     if (!in) {
  127         jp_logf(JP_LOG_DEBUG, "failed opening install_file\n");
  128         return EXIT_FAILURE;
  129     }
  130 
  131     out = jp_open_home_file(EPN".install.tmp", "w");
  132     if (!out) {
  133         fclose(in);
  134         jp_logf(JP_LOG_DEBUG, "failed opening install_file.tmp\n");
  135         return EXIT_FAILURE;
  136     }
  137 
  138     /* Delete line by copying file and skipping over line to delete */
  139     for (line_count = 0; !feof(in); line_count++) {
  140         line[0] = '\0';
  141         Pc = fgets(line, 1000, in);
  142         if (!Pc) {
  143             break;
  144         }
  145         if (line_count == modified_line_num) {
  146             r = fprintf(out, "%s\n", modified_line);
  147         } else {
  148             r = fprintf(out, "%s", line);
  149         }
  150         if (r == EOF) {
  151             break;
  152         }
  153     }
  154     fclose(in);
  155     fclose(out);
  156 
  157     rename_file(EPN".install.tmp", EPN".install");
  158 
  159     return EXIT_SUCCESS;
  160 }
  161 
  162 static gboolean cb_destroy(GtkWidget *widget) {
  163     gtk_widget_destroy(GTK_WIDGET(widget));
  164     return TRUE;
  165 }
  166 
  167 /* Save working directory for future installs */
  168 /* FIXME: find out why this is no longer used */
  169 #if 0
  170 static void cb_quit(GtkWidget *widget, gpointer data) {
  171     const gchar *sel;
  172     char dir[MAX_PREF_LEN + 2];
  173     struct stat statb;
  174     int i;
  175 
  176     jp_logf(JP_LOG_DEBUG, "Quit\n");
  177 
  178     sel = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(widget));
  179 
  180     g_strlcpy(dir, sel, MAX_PREF_LEN);
  181 
  182     if (stat(sel, &statb)) {
  183         jp_logf(JP_LOG_WARN, "File selected was not stat-able\n");
  184     }
  185 
  186     if (S_ISDIR(statb.st_mode)) {
  187         /* For directory, add '/' indicator to path */
  188         i = strlen(dir);
  189         dir[i] = '/', dir[i + 1] = '\0';
  190     } else {
  191         /* Otherwise, strip off filename to find actual directory */
  192         for (i = strlen(dir); i >= 0; i--) {
  193             if (dir[i] == '/') {
  194                 dir[i + 1] = '\0';
  195                 break;
  196             }
  197         }
  198     }
  199 
  200     set_pref(PREF_INSTALL_PATH, 0, dir, TRUE);
  201 
  202     gtk_widget_destroy(GTK_WIDGET(widget));
  203 }
  204 #endif
  205 
  206 static void cb_add(GtkWidget *widget, gpointer data) {
  207 
  208 
  209     const char *sel;
  210     struct stat statb;
  211 
  212     jp_logf(JP_LOG_DEBUG, "install: cb_add\n");
  213     sel = gtk_file_chooser_get_filename(GTK_FILE_CHOOSER(widget));
  214     jp_logf(JP_LOG_DEBUG, "file selected [%s]\n", sel);
  215 
  216     /* Check to see if its a regular file */
  217     if (stat(sel, &statb)) {
  218         jp_logf(JP_LOG_DEBUG, "File selected was not stat-able\n");
  219         return;
  220     }
  221     if (!S_ISREG(statb.st_mode)) {
  222         jp_logf(JP_LOG_DEBUG, "File selected was not a regular file\n");
  223         return;
  224     }
  225 
  226     install_append_line(sel);
  227     install_update_listStore();
  228 }
  229 
  230 static void cb_remove(GtkWidget *widget, gpointer data) {
  231     if (row_selected < 0) {
  232         return;
  233     }
  234     jp_logf(JP_LOG_DEBUG, "Remove line %d\n", row_selected);
  235     install_remove_line(row_selected);
  236     install_update_listStore();
  237 }
  238 
  239 gboolean
  240 selectInstallRecordByRow (GtkTreeModel *model,
  241                    GtkTreePath  *path,
  242                    GtkTreeIter  *iter,
  243                    gpointer data) {
  244     int * i = gtk_tree_path_get_indices ( path ) ;
  245     if(i[0] == row_selected){
  246         GtkTreeSelection * selection = NULL;
  247         selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(treeView));
  248         gtk_tree_selection_select_path(selection, path);
  249         gtk_tree_view_scroll_to_cell(GTK_TREE_VIEW(treeView), path,  INSTALL_SDCARD_COLUMN_ENUM,FALSE, 1.0, 0.0);
  250         return TRUE;
  251     }
  252 
  253     return FALSE;
  254 }
  255 static int install_update_listStore(void) {
  256     GtkTreeIter iter;
  257     GdkPixbuf *sdCardColumnDisplay;
  258     FILE *in;
  259     char line[1002];
  260     char *Pc;
  261     char *new_line[3];
  262 
  263     int last_row_selected;
  264     int count;
  265     int len;
  266     int sdcard_install;
  267 
  268     new_line[0] = "";
  269     new_line[1] = line;
  270     new_line[2] = NULL;
  271 
  272     last_row_selected = row_selected;
  273 
  274     in = jp_open_home_file(EPN".install", "r");
  275     if (!in) {
  276         return EXIT_FAILURE;
  277     }
  278 
  279 
  280     gtk_list_store_clear(listStore);
  281     for (count = 0; !feof(in); count++) {
  282         line[0] = '\0';
  283         sdCardColumnDisplay = NULL;
  284         Pc = fgets(line, 1000, in);
  285         if (!Pc) {
  286             break;
  287         }
  288 
  289         /* Strip newline characters from end of string */
  290         len = strlen(line);
  291         if ((line[len - 1] == '\n') || (line[len - 1] == '\r')) line[len - 1] = '\0';
  292         if ((line[len - 2] == '\n') || (line[len - 2] == '\r')) line[len - 2] = '\0';
  293 
  294         sdcard_install = (line[0] == '\001');
  295         /* Strip char indicating SDCARD install from start of string */
  296         if (sdcard_install) {
  297             new_line[1] = &line[1];
  298         } else {
  299             new_line[1] = &line[0];
  300         }
  301 
  302 
  303 
  304         /* Add SDCARD icon for files to be installed on SDCARD */
  305         if (sdcard_install) {
  306           get_pixbufs(PIXMAP_SDCARD, &sdCardColumnDisplay);
  307 
  308         }
  309         gtk_list_store_append(listStore, &iter);
  310         gtk_list_store_set(listStore, &iter,
  311                            INSTALL_SDCARD_COLUMN_ENUM, sdCardColumnDisplay,
  312                            INSTALL_FNAME_COLUMN_ENUM, new_line[1],
  313                            -1);
  314     }
  315     fclose(in);
  316 
  317 
  318     if (last_row_selected > count - 1) {
  319         last_row_selected = count - 1;
  320     }
  321 
  322     if (last_row_selected >= 0) {
  323         row_selected = last_row_selected;
  324         gtk_tree_model_foreach(GTK_TREE_MODEL(listStore), selectInstallRecordByRow, NULL);
  325     }
  326     return EXIT_SUCCESS;
  327 }
  328 void
  329 columnClicked (GtkTreeView       *tree_view,
  330                GtkTreePath       *path,
  331                GtkTreeViewColumn *column,
  332                gpointer           user_data){
  333     GtkTreeIter iter;
  334 
  335     column_selected = gtk_tree_view_column_get_sort_column_id(column);
  336     char fname[1000];
  337     char *gtk_str;
  338     if (gtk_tree_model_get_iter(GTK_TREE_MODEL(listStore), &iter, path)) {
  339         int *i = gtk_tree_path_get_indices(path);
  340         GdkPixbuf *sdCardColumnDisplay = NULL;
  341         if (column_selected == INSTALL_SDCARD_COLUMN_ENUM) {
  342             /* Toggle display of SDCARD pixmap */
  343             gtk_tree_model_get(GTK_TREE_MODEL(listStore),&iter,INSTALL_SDCARD_COLUMN_ENUM,&sdCardColumnDisplay,
  344                                INSTALL_FNAME_COLUMN_ENUM,&gtk_str,-1);
  345             if (sdCardColumnDisplay == NULL) {
  346                 fname[0] = '\001';
  347                 g_strlcpy(&fname[1], gtk_str, sizeof(fname) - 1);
  348                 install_modify_line(i[0], fname);
  349 
  350             } else {
  351                 g_strlcpy(&fname[0], gtk_str, sizeof(fname));
  352                 install_modify_line(i[0], fname);
  353             }
  354              install_update_listStore();
  355         }
  356     }
  357 }
  358 static gboolean handleInstallRowSelection(GtkTreeSelection *selection,
  359                                           GtkTreeModel *model,
  360                                           GtkTreePath *path,
  361                                           gboolean path_currently_selected,
  362                                           gpointer userdata) {
  363    GtkTreeIter iter;
  364 
  365     if ((gtk_tree_model_get_iter(model, &iter, path)) && (!path_currently_selected)) {
  366         int *i = gtk_tree_path_get_indices(path);
  367         row_selected = i[0];
  368     }
  369 
  370     return TRUE;
  371 }
  372 
  373 
  374 void intializeInstallTreeView(GtkWidget *pixbufwid, GdkPixbuf **pixbuf) {
  375     listStore = gtk_list_store_new(INSTALL_NUM_COLS, GDK_TYPE_PIXBUF, G_TYPE_STRING, G_TYPE_POINTER,
  376                                    GDK_TYPE_RGBA, G_TYPE_BOOLEAN);
  377     treeView = gtk_tree_view_new_with_model(GTK_TREE_MODEL(listStore));
  378     GtkCellRenderer *sdRenderer = gtk_cell_renderer_pixbuf_new();
  379     GtkTreeViewColumn *sdColumn = gtk_tree_view_column_new_with_attributes("",
  380                                                                            sdRenderer,
  381                                                                            "pixbuf", INSTALL_SDCARD_COLUMN_ENUM,
  382                                                                            "cell-background-rgba",
  383                                                                            INSTALL_BACKGROUND_COLOR_ENUM,
  384                                                                            "cell-background-set",
  385                                                                            INSTALL_BACKGROUND_COLOR_ENABLED_ENUM,
  386                                                                            NULL);
  387     gtk_tree_view_column_set_sort_column_id(sdColumn,INSTALL_SDCARD_COLUMN_ENUM);
  388     GtkCellRenderer *fileNameRenderer = gtk_cell_renderer_text_new();
  389     GtkTreeViewColumn *fileNameColumn = gtk_tree_view_column_new_with_attributes("Files to install",
  390                                                                                  fileNameRenderer,
  391                                                                                  "text", INSTALL_FNAME_COLUMN_ENUM,
  392                                                                                  "cell-background-rgba",
  393                                                                                  INSTALL_BACKGROUND_COLOR_ENUM,
  394                                                                                  "cell-background-set",
  395                                                                                  INSTALL_BACKGROUND_COLOR_ENABLED_ENUM,
  396                                                                                  NULL);
  397     gtk_tree_view_column_set_sort_column_id(fileNameColumn,INSTALL_FNAME_COLUMN_ENUM);
  398 
  399     gtk_tree_view_column_set_clickable(sdColumn, gtk_false());
  400     gtk_tree_view_column_set_clickable(fileNameColumn, gtk_false());
  401     gtk_tree_view_column_set_sizing(sdColumn, GTK_TREE_VIEW_COLUMN_AUTOSIZE);
  402     gtk_widget_set_size_request(GTK_WIDGET(treeView), 0, 166);
  403     gtk_tree_selection_set_mode(gtk_tree_view_get_selection(GTK_TREE_VIEW(treeView)),
  404                                 GTK_SELECTION_BROWSE);
  405 
  406     gtk_tree_view_insert_column(GTK_TREE_VIEW (treeView), sdColumn, INSTALL_SDCARD_COLUMN_ENUM);
  407     gtk_tree_view_insert_column(GTK_TREE_VIEW (treeView), fileNameColumn, INSTALL_FNAME_COLUMN_ENUM);
  408     get_pixbufs(PIXMAP_SDCARD, pixbuf);
  409 
  410     pixbufwid = gtk_image_new_from_pixbuf((*pixbuf));
  411     gtk_widget_show(GTK_WIDGET(pixbufwid));
  412     gtk_tree_view_column_set_widget(sdColumn, pixbufwid);
  413     gtk_tree_view_column_set_alignment(sdColumn, GTK_JUSTIFY_CENTER);
  414     GtkTreeSelection *treeSelection = gtk_tree_view_get_selection(GTK_TREE_VIEW(treeView));
  415     column_selected = -1;
  416     gtk_tree_selection_set_select_function(treeSelection, handleInstallRowSelection, NULL, NULL);
  417     gtk_widget_set_events(treeView, GDK_BUTTON1_MOTION_MASK);
  418     g_signal_connect (G_OBJECT(treeView), "motion_notify_event",
  419                       G_CALLBACK(motion_notify_event), NULL);
  420     g_signal_connect (G_OBJECT(treeView), "button-press-event",
  421                       G_CALLBACK(button_pressed_for_motion), NULL);
  422     g_signal_connect (G_OBJECT(treeView), "button-release-event",
  423                       G_CALLBACK(button_released_for_motion), NULL);
  424     gtk_tree_view_set_activate_on_single_click(GTK_TREE_VIEW(treeView), TRUE);
  425     g_signal_connect (treeView, "row-activated", G_CALLBACK(columnClicked), NULL);
  426 }
  427 
  428 int install_gui(GtkWidget *main_window, int w, int h, int x, int y) {
  429     GtkWidget *pixbufwid;
  430     GdkPixbuf *pixbuf;
  431     char temp_str[256];
  432     const char *svalue;
  433     GtkWidget *fileChooserWidget;
  434 
  435 
  436     row_selected = 0;
  437     pixbufwid = NULL;
  438     intializeInstallTreeView(pixbufwid, &pixbuf);
  439     install_update_listStore();
  440     g_snprintf(temp_str, sizeof(temp_str), "%s %s", PN, _("Install"));
  441     fileChooserWidget = gtk_file_chooser_dialog_new(_("Install"), GTK_WINDOW(main_window), GTK_FILE_CHOOSER_ACTION_OPEN,
  442                                                     "_Add", GTK_RESPONSE_ACCEPT,"_Delete", GTK_RESPONSE_DELETE_EVENT,
  443                                                     "Close",GTK_RESPONSE_CLOSE,
  444                                                     NULL);
  445     get_pref(PREF_INSTALL_PATH, NULL, &svalue);
  446     if (svalue && svalue[0]) {
  447         gtk_file_chooser_set_current_folder(GTK_FILE_CHOOSER(fileChooserWidget), svalue);
  448     }
  449     GtkBox *extraWidget = GTK_BOX(gtk_box_new(GTK_ORIENTATION_HORIZONTAL, 0));
  450     gtk_box_pack_start(extraWidget,treeView,TRUE,TRUE,0);
  451     gtk_widget_show_all(GTK_WIDGET(extraWidget));
  452     gtk_file_chooser_set_extra_widget(GTK_FILE_CHOOSER(fileChooserWidget), GTK_WIDGET(extraWidget));
  453     g_signal_connect(G_OBJECT(fileChooserWidget), "destroy",
  454                        G_CALLBACK(cb_destroy), fileChooserWidget);
  455     int dialogResponse = gtk_dialog_run(GTK_DIALOG(fileChooserWidget));
  456     do {
  457      if(dialogResponse == GTK_RESPONSE_DELETE_EVENT){
  458          //remove from list
  459          cb_remove(fileChooserWidget,fileChooserWidget);
  460      } else if(dialogResponse == GTK_RESPONSE_ACCEPT){
  461          // add to list.
  462          cb_add(fileChooserWidget,fileChooserWidget);
  463      } else {
  464          // handle close and destroy widget.
  465          cb_destroy(fileChooserWidget);
  466      }
  467      if(dialogResponse != GTK_RESPONSE_CLOSE){
  468         dialogResponse = gtk_dialog_run(GTK_DIALOG (fileChooserWidget));
  469      }
  470     } while (dialogResponse != GTK_RESPONSE_CLOSE);
  471 
  472     gtk_widget_destroy(GTK_WIDGET(fileChooserWidget));
  473 
  474     // gtk_main();
  475 
  476     return EXIT_SUCCESS;
  477 }