This patch adds a graphical method of selecting the permissions to apply to files. Index:rox-1.1.13-chmod/ROX-Filer/src/action.c *** rox-1.1.13/ROX-Filer/src/action.c Sat Feb 2 14:31:32 2002 --- rox-1.1.13-chmod/ROX-Filer/src/action.c Mon Feb 11 13:49:21 2002 *************** *** 95,100 **** --- 95,104 ---- /* Used by Find */ FilerWindow *preview; GtkWidget *results; + + /* Used by Permissions */ + GtkWidget *bits[3][3]; + GtkWidget *permpreview; }; /* These don't need to be in a structure because we fork() before *************** *** 927,933 **** gui_side->entry = NULL; gui_side->default_string = NULL; gui_side->entry_string_func = NULL; ! gui_side->window = gtk_window_new(GTK_WINDOW_DIALOG); #ifdef GTK2 gtk_window_set_type_hint(GTK_WINDOW(gui_side->window), --- 931,938 ---- gui_side->entry = NULL; gui_side->default_string = NULL; gui_side->entry_string_func = NULL; ! gui_side->permpreview = NULL; ! gui_side->window = gtk_window_new(GTK_WINDOW_DIALOG); #ifdef GTK2 gtk_window_set_type_hint(GTK_WINDOW(gui_side->window), *************** *** 2058,2069 **** gtk_widget_show_all(gui_side->window); } /* Change the permissions of the selected items */ void action_chmod(GList *paths) { GUIside *gui_side; ! GtkWidget *hbox, *label, *combo; static GList *presets = NULL; if (!paths) { --- 2063,2169 ---- gtk_widget_show_all(gui_side->window); } + #define check_bit(g, i, j, a, s) \ + do { char *let[]={"r","w","x"}; \ + gint state=GPOINTER_TO_INT(gtk_object_get_data(GTK_OBJECT(g->bits[i][j]), "state")); \ + if(state==1) strcat(a, let[i]); else if(state==2) strcat(s, let[i]); \ + } while(0); + + static void update_perm_preview(GUIside *gui_side) + { + char ua[4]=""; + char ga[4]=""; + char oa[4]=""; + char us[4]=""; + char gs[4]=""; + char os[4]=""; + char res[6*4+6*2+1]; + int i; + + for(i=0; i<3; i++) { + check_bit(gui_side, i, 0, ua, us); + check_bit(gui_side, i, 1, ga, gs); + check_bit(gui_side, i, 2, oa, os); + } + res[0]=0; + if(ua[0] || us[0]) { + strcat(res, "u"); + if(ua[0]) { + strcat(res, "+"); + strcat(res, ua); + } + if(us[0]) { + strcat(res, "-"); + strcat(res, us); + } + } + if(ga[0] || gs[0]) { + if(res[0]) + strcat(res, ","); + strcat(res, "g"); + if(ga[0]) { + strcat(res, "+"); + strcat(res, ga); + } + if(gs[0]) { + strcat(res, "-"); + strcat(res, gs); + } + } + if(oa[0] || os[0]) { + if(res[0]) + strcat(res, ","); + strcat(res, "o"); + if(oa[0]) { + strcat(res, "+"); + strcat(res, oa); + } + if(os[0]) { + strcat(res, "-"); + strcat(res, os); + } + } + + gtk_label_set_text(GTK_LABEL(gui_side->permpreview), res); + if(gui_side->permpreview->parent) + gtk_widget_set_sensitive(gui_side->permpreview->parent, + strlen(res)>0); + } + + static void chmod_bit_change(GtkWidget *widget, gpointer data) + { + gint state; + gchar *nlabel; + + state=GPOINTER_TO_INT(gtk_object_get_data(GTK_OBJECT(widget), "state")); + state=(state+1)%3; + gtk_object_set_data(GTK_OBJECT(widget), "state", GINT_TO_POINTER(state)); + switch(state) { + case 0: nlabel=" "; break; + case 1: nlabel="+"; break; + case 2: nlabel="-"; break; + default: nlabel=""; break; + } + gtk_object_set(GTK_OBJECT(widget), "label", nlabel, NULL); + update_perm_preview((GUIside *) data); + } + + static void chmod_bit_use(GtkWidget *widget, gpointer data) + { + GUIside *gui_side=(GUIside *) data; + gchar *perm; + + gtk_label_get(GTK_LABEL(gui_side->permpreview), &perm); + gtk_entry_set_text(GTK_ENTRY(gui_side->entry), perm); + } + /* Change the permissions of the selected items */ void action_chmod(GList *paths) { GUIside *gui_side; ! GtkWidget *hbox, *label, *combo, *table, *bit, *but, *align; static GList *presets = NULL; + int i, j; if (!paths) { *************** *** 2127,2133 **** --- 2227,2287 ---- gtk_signal_connect_object(GTK_OBJECT(gui_side->entry), "activate", GTK_SIGNAL_FUNC(gtk_button_clicked), GTK_OBJECT(gui_side->yes)); + + hbox = gtk_hbox_new(FALSE, 0); + gtk_box_pack_start(GTK_BOX(gui_side->vbox), hbox, FALSE, TRUE, 0); + label = gtk_label_new(_("Bits:")); + gtk_box_pack_start(GTK_BOX(hbox), label, FALSE, FALSE, 4); + table=gtk_table_new(4, 4, TRUE); + gtk_box_pack_start(GTK_BOX(hbox), table, FALSE, TRUE, 4); + gtk_table_attach(GTK_TABLE(table), gtk_label_new(_("u")), + 0, 1, 1, 2, + GTK_EXPAND, GTK_EXPAND, + 2, 2); + gtk_table_attach(GTK_TABLE(table), gtk_label_new(_("g")), + 0, 1, 2, 3, + GTK_EXPAND, GTK_EXPAND, + 2, 2); + gtk_table_attach(GTK_TABLE(table), gtk_label_new(_("o")), + 0, 1, 3, 4, + GTK_EXPAND, GTK_EXPAND, + 2, 2); + gtk_table_attach(GTK_TABLE(table), gtk_label_new(_("r")), + 1, 2, 0, 1, + GTK_EXPAND, GTK_EXPAND, + 2, 2); + gtk_table_attach(GTK_TABLE(table), gtk_label_new(_("w")), + 2, 3, 0, 1, + GTK_EXPAND, GTK_EXPAND, + 2, 2); + gtk_table_attach(GTK_TABLE(table), gtk_label_new(_("x")), + 3, 4, 0, 1, + GTK_EXPAND, GTK_EXPAND, + 2, 2); + label=gtk_label_new(""); + gui_side->permpreview=label; + for(i=0; i<3; i++) + for(j=0; j<3; j++) { + bit=gtk_button_new_with_label(" "); + gtk_table_attach(GTK_TABLE(table), bit, + i+1, i+2, j+1, j+2, + GTK_EXPAND, GTK_EXPAND, + 2, 2); + gtk_signal_connect(GTK_OBJECT(bit), "clicked", + GTK_SIGNAL_FUNC(chmod_bit_change), gui_side); + gtk_object_set_data(GTK_OBJECT(bit), "state", 0); + gui_side->bits[i][j]=bit; + } + align=gtk_alignment_new(0, .5, 1, 0); + gtk_box_pack_start(GTK_BOX(hbox), align, FALSE, FALSE, 4); + but=gtk_button_new(); + gtk_container_add(GTK_CONTAINER(but), gui_side->permpreview); + gtk_container_add(GTK_CONTAINER(align), but); + gtk_signal_connect(GTK_OBJECT(but), "clicked", + GTK_SIGNAL_FUNC(chmod_bit_use), gui_side); + gtk_widget_set_sensitive(but, FALSE); + number_of_windows++; gtk_widget_show_all(gui_side->window); }