From 83cf73a286bbcb0f71faf1503c7bf095ea791594 Mon Sep 17 00:00:00 2001 From: "Crom (Thibaut CHARLES)" Date: Tue, 18 Nov 2014 17:10:05 +0100 Subject: [PATCH 1/9] Fix light theme --- source/app.d | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/source/app.d b/source/app.d index 1ece442..99584bf 100644 --- a/source/app.d +++ b/source/app.d @@ -300,7 +300,7 @@ auto ref SetupColumn(TreeView tree, string sName, size_t index){ CellRendererText cr = new CellRendererText(); cr.setProperty("editable", true); if(index==0){ - cr.setProperty("background-rgba", cast(ulong)(new GdkRGBA(0.36, 0.13, 0.4, 1.0))); + cr.setProperty("background-rgba", cast(ulong)(new GdkRGBA(0.36, 0.13, 0.4, 0.5))); cr.setProperty("background-set", true); cr.addOnEdited((string path, string newval, CellRendererText crt){ From 736b14fc2d1a11f0b489ce901b6def8c83fabbd8 Mon Sep 17 00:00:00 2001 From: "Crom (Thibaut CHARLES)" Date: Wed, 19 Nov 2014 08:58:47 +0100 Subject: [PATCH 2/9] Column adding --- source/app.d | 51 +++++++++++++++++++++++++++++++++++++-------------- 1 file changed, 37 insertions(+), 14 deletions(-) diff --git a/source/app.d b/source/app.d index 99584bf..850d9e7 100644 --- a/source/app.d +++ b/source/app.d @@ -159,29 +159,52 @@ void main(string[] args) }); buttonNewCol.addOnClicked((Button){ - auto store = cast(ListStore)tree.getModel(); - int newColIndex = store.getNColumns(); + auto oldstore = cast(ListStore)tree.getModel(); + int newColIndex = oldstore.getNColumns(); GType[] types; - foreach(i ; 0..newColIndex+1) - types~= store.getColumnType(i); - store.setColumnTypes(types); + string[] titles; + foreach(i ; 0..newColIndex){ + if(i==0)types~= GType.INT; + else types~= GType.STRING; + titles~= tree.getColumn(0).getTitle; + tree.removeColumn(tree.getColumn(0)); + } + types~=GType.STRING; + titles~="new_col"; - writeln(types.length); + writeln(types); + auto store = new ListStore(types); + tree.setModel(store); - //auto col = SetupColumn(tree, "new_col", newColIndex); + //setup cols + foreach(i ; 0..newColIndex+1){ + tree.appendColumn(SetupColumn(tree, titles[i], i)); + } + //Fill them + TreeIter oldit = new TreeIter(); + TreeIter newit = new TreeIter(); + if(oldstore.getIterFirst(oldit)){ + do{ + store.append(newit); - //TreeIter it = new TreeIter(); - //if(store.getIterFirst(it)){ - // do{ - // store.setValue(it, newColIndex, "_"); - // }while(store.iterNext(it)); - //} + foreach(i ; 0..newColIndex+1){ + if(i Date: Wed, 19 Nov 2014 14:11:53 +0100 Subject: [PATCH 3/9] Fix: moved col containing old data --- source/app.d | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/source/app.d b/source/app.d index 850d9e7..e9d45e4 100644 --- a/source/app.d +++ b/source/app.d @@ -236,7 +236,8 @@ void Save(ref TreeView tree){ do{ file.write(store.getValueInt(it, 0)); foreach(i ; 1..store.getNColumns()){ - file.write("\t\"",store.getValueString(it, i),"\""); + int storecol = cast(int)(tree.getColumn(i).getData("colnumber")); + file.write("\t\"", store.getValueString(it, storecol), "\""); } file.write("\n"); }while(store.iterNext(it)); @@ -349,9 +350,11 @@ auto ref SetupColumn(TreeView tree, string sName, size_t index){ auto col = new TreeViewColumn(sName, cr, "text", cast(int)index); + col.setData("colnumber", cast(void*)cast(int)index); col.setResizable(true); col.setMinWidth(10); col.setClickable(true); + col.setReorderable(true); col.addOnClicked((TreeViewColumn col){ import gtk.Dialog; auto dlg = new Dialog("Rename column", window, GtkDialogFlags.MODAL, ["Cancel","Rename"], [ResponseType.CANCEL, ResponseType.OK]); From 61885f57aa0363e253a509a3928882db36f690bf Mon Sep 17 00:00:00 2001 From: "Crom (Thibaut CHARLES)" Date: Wed, 19 Nov 2014 14:47:35 +0100 Subject: [PATCH 4/9] Moving id is forbidden --- source/app.d | 20 ++++++++++++++++++-- 1 file changed, 18 insertions(+), 2 deletions(-) diff --git a/source/app.d b/source/app.d index e9d45e4..71c1118 100644 --- a/source/app.d +++ b/source/app.d @@ -101,6 +101,19 @@ void main(string[] args) tree.setProperty("tooltip-column", 0); tree.setProperty("reorderable", true); tree.setProperty("headers-clickable", true); + tree.addOnColumnsChanged((TreeView tree){ + auto store = cast(ListStore)tree.getModel(); + + if(store.getColumnType(GetColumnStoreIndex(tree, 0)) != GType.INT){ + writeln("Position 0 is forbidden"); + foreach(i ; 0..store.getNColumns()){ + if(store.getColumnType(GetColumnStoreIndex(tree, i))==GType.INT){ + tree.moveColumnAfter(tree.getColumn(i), null); + break; + } + } + } + }); //Configure button callbacks @@ -221,6 +234,10 @@ void main(string[] args) } +int GetColumnStoreIndex(TreeView tree, int colindex){ + return cast(int)(tree.getColumn(colindex).getData("colnumber")); +} + void Save(ref TreeView tree){ auto store = cast(ListStore)tree.getModel(); if(store !is null){ @@ -236,8 +253,7 @@ void Save(ref TreeView tree){ do{ file.write(store.getValueInt(it, 0)); foreach(i ; 1..store.getNColumns()){ - int storecol = cast(int)(tree.getColumn(i).getData("colnumber")); - file.write("\t\"", store.getValueString(it, storecol), "\""); + file.write("\t\"", store.getValueString(it, GetColumnStoreIndex(tree, i)), "\""); } file.write("\n"); }while(store.iterNext(it)); From 24a4fc950039d7351e350655aad2581e7daaa109 Mon Sep 17 00:00:00 2001 From: "Crom (Thibaut CHARLES)" Date: Wed, 19 Nov 2014 15:15:59 +0100 Subject: [PATCH 5/9] Fix: segfault on column add --- source/app.d | 22 +++++++++++++--------- 1 file changed, 13 insertions(+), 9 deletions(-) diff --git a/source/app.d b/source/app.d index 71c1118..43f99ff 100644 --- a/source/app.d +++ b/source/app.d @@ -104,10 +104,11 @@ void main(string[] args) tree.addOnColumnsChanged((TreeView tree){ auto store = cast(ListStore)tree.getModel(); - if(store.getColumnType(GetColumnStoreIndex(tree, 0)) != GType.INT){ - writeln("Position 0 is forbidden"); + int si = GetColumnStoreIndex(tree, 0); + if(si>=0 && store.getColumnType(si) != GType.INT){ foreach(i ; 0..store.getNColumns()){ - if(store.getColumnType(GetColumnStoreIndex(tree, i))==GType.INT){ + si = GetColumnStoreIndex(tree, i); + if(si>=0 && store.getColumnType(si)==GType.INT){ tree.moveColumnAfter(tree.getColumn(i), null); break; } @@ -192,11 +193,6 @@ void main(string[] args) auto store = new ListStore(types); tree.setModel(store); - //setup cols - foreach(i ; 0..newColIndex+1){ - tree.appendColumn(SetupColumn(tree, titles[i], i)); - } - //Fill them TreeIter oldit = new TreeIter(); TreeIter newit = new TreeIter(); @@ -217,6 +213,11 @@ void main(string[] args) }while(oldstore.iterNext(oldit)); } + //setup cols + foreach(i ; 0..newColIndex+1){ + tree.appendColumn(SetupColumn(tree, titles[i], i)); + } + oldstore.destroy(); }); @@ -235,7 +236,10 @@ void main(string[] args) } int GetColumnStoreIndex(TreeView tree, int colindex){ - return cast(int)(tree.getColumn(colindex).getData("colnumber")); + auto col = tree.getColumn(colindex); + if(col !is null) + return cast(int)(col.getData("colnumber")); + return -1; } void Save(ref TreeView tree){ From 53fe5511e097de17434ee7a4c8b9e80d6106b5da Mon Sep 17 00:00:00 2001 From: "Crom (Thibaut CHARLES)" Date: Wed, 19 Nov 2014 15:59:47 +0100 Subject: [PATCH 6/9] Save shortcut & notification animation --- source/app.d | 32 +++++++++++++++++++++++++++++++- 1 file changed, 31 insertions(+), 1 deletion(-) diff --git a/source/app.d b/source/app.d index 43f99ff..6e68886 100644 --- a/source/app.d +++ b/source/app.d @@ -18,6 +18,7 @@ import gtk.VBox; import gtk.Statusbar; import gtk.Button; import gtk.ScrolledWindow; +import gtk.AccelGroup; import gtk.HBox; @@ -30,6 +31,9 @@ void main(string[] args) //Window window = new MainWindow("2DA-Edit"); + auto accel = new AccelGroup(); + window.addAccelGroup(accel); + auto cont = new VBox(false, 0); window.add(cont); cont.setSizeRequest(300, 200); @@ -51,6 +55,8 @@ void main(string[] args) auto buttonNewCol = new Button("tab-new-symbolic", GtkIconSize.SMALL_TOOLBAR); } buttonSave.setTooltipText("Save"); + enum GDK_KEY_S = 0x053; + buttonSave.addAccelerator("clicked", accel, GDK_KEY_S, GdkModifierType.CONTROL_MASK, GtkAccelFlags.VISIBLE); buttonOpen.setTooltipText("Open 2DA"); buttonInsert.setTooltipText("Insert row after"); buttonDelete.setTooltipText("Delete row"); @@ -120,6 +126,31 @@ void main(string[] args) //Configure button callbacks buttonSave.addOnClicked((Button){ Save(tree); + + import core.thread; + new Thread({ + Thread.getThis.sleep(dur!"msecs"(100)); + + auto lbl = new Label(""); + lbl.setMarkup("File saved"); + statusbar.packEnd(lbl, false, false, 5); + + //Wow, much animation, very badass + lbl.setOpacity(0.0); + lbl.show(); + foreach(i ; 0..20){ + lbl.setOpacity(i/20.0); + Thread.getThis.sleep(dur!"msecs"(10)); + } + Thread.getThis.sleep(dur!"msecs"(1500)); + foreach(i ; 1..20){ + lbl.setOpacity(1.0-i/20.0); + Thread.getThis.sleep(dur!"msecs"(10)); + } + //Destroy + lbl.destroy(); + }).start(); + }); buttonOpen.addOnClicked((Button){ @@ -269,7 +300,6 @@ void Save(ref TreeView tree){ } else writeln("Nothing to save !"); - } string openedFile; From 33ccf7d8f0429c5b959fe274fac16e56d7e4e304 Mon Sep 17 00:00:00 2001 From: "Crom (Thibaut CHARLES)" Date: Wed, 19 Nov 2014 16:24:46 +0100 Subject: [PATCH 7/9] Generalized animated info --- source/app.d | 73 ++++++++++++++++++++++++++-------------------------- 1 file changed, 37 insertions(+), 36 deletions(-) diff --git a/source/app.d b/source/app.d index 6e68886..b69eac7 100644 --- a/source/app.d +++ b/source/app.d @@ -22,7 +22,8 @@ import gtk.AccelGroup; import gtk.HBox; -MainWindow window; +__gshared MainWindow window; +__gshared HBox statusbar; void main(string[] args) { @@ -87,7 +88,7 @@ void main(string[] args) } //Status bar - auto statusbar = new HBox(false, 0); + statusbar = new HBox(false, 0); cont.packEnd(statusbar, false, false, 5); statusbar.packStart(buttonRenumber, false, false, 5); statusbar.packStart(buttonInsert, false, false, 5); @@ -126,31 +127,6 @@ void main(string[] args) //Configure button callbacks buttonSave.addOnClicked((Button){ Save(tree); - - import core.thread; - new Thread({ - Thread.getThis.sleep(dur!"msecs"(100)); - - auto lbl = new Label(""); - lbl.setMarkup("File saved"); - statusbar.packEnd(lbl, false, false, 5); - - //Wow, much animation, very badass - lbl.setOpacity(0.0); - lbl.show(); - foreach(i ; 0..20){ - lbl.setOpacity(i/20.0); - Thread.getThis.sleep(dur!"msecs"(10)); - } - Thread.getThis.sleep(dur!"msecs"(1500)); - foreach(i ; 1..20){ - lbl.setOpacity(1.0-i/20.0); - Thread.getThis.sleep(dur!"msecs"(10)); - } - //Destroy - lbl.destroy(); - }).start(); - }); buttonOpen.addOnClicked((Button){ @@ -219,8 +195,6 @@ void main(string[] args) types~=GType.STRING; titles~="new_col"; - writeln(types); - auto store = new ListStore(types); tree.setModel(store); @@ -273,6 +247,32 @@ int GetColumnStoreIndex(TreeView tree, int colindex){ return -1; } +void SaySomething(string msg){ + import core.thread; + new Thread({ + Thread.getThis.sleep(dur!"msecs"(100)); + + auto lbl = new Label(""); + lbl.setMarkup(""~msg~""); + statusbar.packEnd(lbl, false, false, 5); + + //Wow, much animation, very badass + lbl.setOpacity(0.0); + lbl.show(); + foreach(i ; 0..20){ + lbl.setOpacity(i/20.0); + Thread.getThis.sleep(dur!"msecs"(10)); + } + Thread.getThis.sleep(dur!"msecs"(1500)); + foreach(i ; 1..20){ + lbl.setOpacity(1.0-i/20.0); + Thread.getThis.sleep(dur!"msecs"(10)); + } + //Destroy + lbl.destroy(); + }).start(); +} + void Save(ref TreeView tree){ auto store = cast(ListStore)tree.getModel(); if(store !is null){ @@ -292,14 +292,15 @@ void Save(ref TreeView tree){ } file.write("\n"); }while(store.iterNext(it)); - - file.flush(); - file.close(); - writeln("File written: ",openedFile); } + + file.flush(); + file.close(); + + SaySomething("Saved to "~openedFile); } else - writeln("Nothing to save !"); + SaySomething("Nothing to save !"); } string openedFile; @@ -384,7 +385,7 @@ auto ref SetupColumn(TreeView tree, string sName, size_t index){ store.setValue(t, cast(int)crt.getData("colnumber"), n); } catch(Exception e){ - writeln("Not a number"); + SaySomething("Not a number !"); } }); @@ -417,7 +418,7 @@ auto ref SetupColumn(TreeView tree, string sName, size_t index){ if(newname.countchars(" \t\n\r")==0) col.setTitle(newname); else - writeln("Unauthorized caracters in column name"); + SaySomething("Spaces are forbidden in column name"); } dlg.destroy(); From 04f9086315e427a2e33f4f1209c4e67d67a4a608 Mon Sep 17 00:00:00 2001 From: "Crom (Thibaut CHARLES)" Date: Wed, 19 Nov 2014 16:31:17 +0100 Subject: [PATCH 8/9] Forbid double quotes in values --- source/app.d | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/source/app.d b/source/app.d index b69eac7..1a263b9 100644 --- a/source/app.d +++ b/source/app.d @@ -393,7 +393,11 @@ auto ref SetupColumn(TreeView tree, string sName, size_t index){ else{ cr.addOnEdited((string path, string newval, CellRendererText crt){ TreeIter t = new TreeIter(tree.getModel(), path); - store.setValue(t, cast(int)crt.getData("colnumber"), newval); + if(newval.countchars("\"")!=0){ + SaySomething("Double quotes are forbidden !"); + } + else + store.setValue(t, cast(int)crt.getData("colnumber"), newval); }); } From 22f249b10a7d0a4fed7f81fe2b39e87cd98a5c3a Mon Sep 17 00:00:00 2001 From: "Crom (Thibaut CHARLES)" Date: Wed, 19 Nov 2014 16:52:06 +0100 Subject: [PATCH 9/9] Save as & global header --- source/app.d | 73 +++++++++++++++++++++++++++++++++++----------------- 1 file changed, 49 insertions(+), 24 deletions(-) diff --git a/source/app.d b/source/app.d index 1a263b9..1b78fa1 100644 --- a/source/app.d +++ b/source/app.d @@ -24,6 +24,7 @@ import gtk.HBox; __gshared MainWindow window; __gshared HBox statusbar; +__gshared Object header; void main(string[] args) { @@ -41,6 +42,7 @@ void main(string[] args) version(Windows){ auto buttonSave = new Button(StockID.SAVE, true); + auto buttonSaveAs = new Button(StockID.SAVE_AS, true); auto buttonOpen = new Button(StockID.OPEN, true); auto buttonInsert = new Button(StockID.JUMP_TO, true); auto buttonDelete = new Button(StockID.DELETE, true); @@ -49,6 +51,7 @@ void main(string[] args) } else{ auto buttonSave = new Button("document-save-symbolic", GtkIconSize.MENU); + auto buttonSaveAs = new Button("document-save-as-symbolic", GtkIconSize.MENU); auto buttonOpen = new Button("document-open-symbolic", GtkIconSize.MENU); auto buttonInsert = new Button("format-text-direction-ltr-symbolic", GtkIconSize.SMALL_TOOLBAR); auto buttonDelete = new Button("user-trash-symbolic", GtkIconSize.SMALL_TOOLBAR); @@ -56,35 +59,40 @@ void main(string[] args) auto buttonNewCol = new Button("tab-new-symbolic", GtkIconSize.SMALL_TOOLBAR); } buttonSave.setTooltipText("Save"); - enum GDK_KEY_S = 0x053; - buttonSave.addAccelerator("clicked", accel, GDK_KEY_S, GdkModifierType.CONTROL_MASK, GtkAccelFlags.VISIBLE); + buttonSaveAs.setTooltipText("Save as"); buttonOpen.setTooltipText("Open 2DA"); buttonInsert.setTooltipText("Insert row after"); buttonDelete.setTooltipText("Delete row"); buttonRenumber.setTooltipText("Renumber all rows"); buttonNewCol.setTooltipText("Add new column"); + enum GDK_KEY_S = 0x053; + buttonSave.addAccelerator("clicked", accel, GDK_KEY_S, GdkModifierType.CONTROL_MASK, GtkAccelFlags.VISIBLE); + buttonSaveAs.addAccelerator("clicked", accel, GDK_KEY_S, GdkModifierType.CONTROL_MASK|GdkModifierType.SHIFT_MASK, GtkAccelFlags.VISIBLE); + version(Windows){ //Menu bar import gtk.HBox; - auto cont2 = new HBox(false, 0); - cont.packStart(cont2, false, false, 0); + header = new HBox(false, 0); + cont.packStart(header, false, false, 0); - cont2.packStart(buttonOpen, false, false, 0); - cont2.packEnd(buttonSave, false, false, 0); + header.packStart(buttonOpen, false, false, 0); + header.packEnd(buttonSaveAs, false, false, 0); + header.packEnd(buttonSave, false, false, 0); } else{ //Header bar import gtk.HeaderBar; - auto header = new HeaderBar(); - window.setTitlebar(header); - header.setTitle("2DAEdit"); - header.setProperty("show-close-button", true); + header = new HeaderBar(); + window.setTitlebar(cast(HeaderBar)header); + (cast(HeaderBar)header).setTitle("2DAEdit"); + (cast(HeaderBar)header).setProperty("show-close-button", true); - header.packStart(buttonOpen); - header.packEnd(buttonSave); + (cast(HeaderBar)header).packStart(buttonOpen); + (cast(HeaderBar)header).packEnd(buttonSaveAs); + (cast(HeaderBar)header).packEnd(buttonSave); } //Status bar @@ -128,6 +136,18 @@ void main(string[] args) buttonSave.addOnClicked((Button){ Save(tree); }); + buttonSaveAs.addOnClicked((Button){ + import gtk.Dialog; + import gtk.FileChooserDialog; + + auto fc = new FileChooserDialog("Save 2DA as", window, FileChooserAction.SAVE); + auto res = fc.run(); + if(res==GtkResponseType.OK){ + string filename = fc.getFilename(); + Save(tree, filename); + } + fc.destroy(); + }); buttonOpen.addOnClicked((Button){ import gtk.Dialog; @@ -137,8 +157,7 @@ void main(string[] args) auto res = fc.run(); if(res==GtkResponseType.OK){ string filename = fc.getFilename(); - version(Windows) Open(filename, tree, cast(Object)window); - else Open(filename, tree, cast(Object)header); + Open(filename, tree); } fc.destroy(); }); @@ -230,8 +249,7 @@ void main(string[] args) //Open if exists if(args.length>=2 && exists(args[1])){ - version(Windows) Open(args[1], tree, cast(Object)window); - else Open(args[1], tree, cast(Object)header); + Open(args[1], tree); } window.showAll(); @@ -273,9 +291,13 @@ void SaySomething(string msg){ }).start(); } -void Save(ref TreeView tree){ +void Save(ref TreeView tree, string newpath=""){ auto store = cast(ListStore)tree.getModel(); if(store !is null){ + if(newpath!=""){ + openedFile = newpath; + SetTitle(openedFile); + } auto file = File(openedFile, "w"); @@ -303,18 +325,21 @@ void Save(ref TreeView tree){ SaySomething("Nothing to save !"); } +void SetTitle(string title){ + version(Windows) (cast(MainWindow)header).setTitle(title); + else{ + import gtk.HeaderBar; + (cast(HeaderBar)header).setSubtitle(title); + } +} + string openedFile; -void Open(string file, ref TreeView tree, Object header){ +void Open(string file, ref TreeView tree){ auto twoda = new TwoDA(file); openedFile = file; - - version(Windows) (cast(MainWindow)header).setTitle(file); - else{ - import gtk.HeaderBar; - (cast(HeaderBar)header).setSubtitle(file); - } + SetTitle(openedFile); //Delete old store auto oldstore = cast(ListStore)tree.getModel();