1 /* -*- c-basic-offset:2; tab-width:2; indent-tabs-mode:nil -*- */
2 
3 #include "mc_sb_view.h"
4 
5 #include <pobl/bl_str.h> /* strdup */
6 #include <pobl/bl_mem.h> /* free */
7 #include <pobl/bl_debug.h>
8 #include <pobl/bl_conf_io.h>
9 #include <glib.h>
10 #include <c_intl.h>
11 #include <pobl/bl_types.h>
12 #include <dirent.h>
13 
14 #include "mc_combo.h"
15 #include "mc_io.h"
16 
17 #ifndef XDATADIR
18 #define SB_DIR "/usr/local/share/mlterm/scrollbars"
19 #else
20 #define SB_DIR XDATADIR "/mlterm/scrollbars"
21 #endif
22 
23 #define MAX_SCROLLBARS 100
24 
25 #if 0
26 #define __DEBUG
27 #endif
28 
29 /* --- static variables --- */
30 
31 static char *new_sb_view_name = NULL;
32 static char *old_sb_view_name = NULL;
33 static int is_changed;
34 
35 /* --- static functions --- */
36 
sb_view_name_selected(GtkWidget * widget,gpointer data)37 static gint sb_view_name_selected(GtkWidget *widget, gpointer data) {
38   free(new_sb_view_name);
39   new_sb_view_name = gtk_editable_get_chars(GTK_EDITABLE(widget), 0, -1);
40 
41 #ifdef __DEBUG
42   bl_debug_printf(BL_DEBUG_TAG " %s sb_view_name is selected.\n", new_sb_view_name);
43 #endif
44 
45   return 1;
46 }
47 
has_rc_file(char * dirname,char * sbdirname)48 static int has_rc_file(char *dirname, char *sbdirname) {
49   DIR *d;
50   struct dirent *e;
51   char path[PATH_MAX];
52   int result = 0;
53 
54   snprintf(path, PATH_MAX, "%s/%s", dirname, sbdirname);
55   if (!(d = opendir(path))) return 0;
56 
57   while ((e = readdir(d))) {
58     if (strcmp("rc", e->d_name) == 0) {
59       result = 1;
60       break;
61     }
62   }
63 
64   closedir(d);
65 
66   return result;
67 }
68 
read_sb_names(char * dirname,char ** sbnames,int n)69 static int read_sb_names(char *dirname, char **sbnames, int n) {
70   int n0, j;
71   DIR *d;
72   struct dirent *e;
73 
74   d = opendir(dirname);
75   if (!d) return n;
76 
77   n0 = n;
78 
79   while (n < MAX_SCROLLBARS) {
80   ignore:
81     e = readdir(d);
82     if (!e) break;
83     if (e->d_name[0] == '.' || !has_rc_file(dirname, e->d_name)) continue;
84     sbnames[n] = strdup(e->d_name);
85     if (!sbnames[n]) break;
86     for (j = 0; j < n0; j++) {
87       if (!strcmp(sbnames[n], sbnames[j])) goto ignore;
88     }
89     n++;
90   }
91   closedir(d);
92   return n;
93 }
94 
95 /* --- global functions --- */
96 
mc_sb_view_config_widget_new(void)97 GtkWidget *mc_sb_view_config_widget_new(void) {
98   char *sb_view0[] = {"simple", "sample", "sample3", "athena", "motif", "mozmodern", "next"};
99   char *sb_view_names[MAX_SCROLLBARS];
100   char *userdir;
101   int n;
102   GtkWidget *combo;
103   GtkWidget *entry;
104 
105   for (n = 0; n < sizeof(sb_view0) / sizeof(sb_view0[0]); n++) {
106     sb_view_names[n] = sb_view0[n];
107   }
108 
109   userdir = bl_get_user_rc_path("mlterm/scrollbars");
110   if (userdir) {
111     n = read_sb_names(userdir, sb_view_names, n);
112     free(userdir);
113   }
114   n = read_sb_names(SB_DIR, sb_view_names, n);
115 
116   new_sb_view_name = strdup(old_sb_view_name = mc_get_str_value("scrollbar_view_name"));
117   is_changed = 0;
118 
119   combo = mc_combo_new(_("View"), sb_view_names, n, new_sb_view_name, 0, &entry);
120   g_signal_connect(entry, "changed", G_CALLBACK(sb_view_name_selected), NULL);
121 
122   return combo;
123 }
124 
mc_update_sb_view_name(void)125 void mc_update_sb_view_name(void) {
126   if (strcmp(new_sb_view_name, old_sb_view_name)) is_changed = 1;
127 
128   if (is_changed) {
129     mc_set_str_value("scrollbar_view_name", new_sb_view_name);
130     free(old_sb_view_name);
131     old_sb_view_name = strdup(new_sb_view_name);
132   }
133 }
134