update Docify

This commit is contained in:
lxsang 2020-11-20 20:05:29 +00:00
parent 0532d1fbeb
commit 685841635f
9 changed files with 1237 additions and 21 deletions

View File

@ -1 +1,249 @@
result("Hello from server side")
local arg = ...
ulib = require("ulib")
sqlite = modules.sqlite()
vfs = require("vfs")
local handle = {}
local docpath = nil
local dbpath = nil
local result = function(data)
return {
error = false,
result = data
}
end
local error = function(data)
return {
error = data,
result = false
}
end
local mkdirp =function(p)
if not vfs.exists(p) then
if not vfs.mkdir(p) then
return false, error("Unable to create directory: "..p)
end
end
return true, nil
end
handle.init = function(args)
local r, e = mkdirp(docpath)
if not r then return e end
r, e = mkdirp(docpath.."/unclassified")
if not r then return e end
r, e = mkdirp(docpath.."/cache")
if not r then return e end
local db = sqlite._getdb(vfs.ospath(dbpath))
if not db then
return error("Unable to initialized database "..dbpath)
end
local sql
-- check if table exists
if sqlite.hasTable(db, "categories") == 0 then
-- create the table
sql = [[
CREATE TABLE "categories" (
"id" INTEGER,
"name" TEXT NOT NULL,
PRIMARY KEY("id" AUTOINCREMENT)
);
]]
if sqlite.query(db, sql) ~= 1 then
sqlite.dbclose(db)
return error("Unable to create table categories")
end
-- insert unknown category
sql = [[
INSERT INTO categories("id","name") VALUES (0,'Uncategoried');
]]
if sqlite.query(db, sql) ~= 1 then
sqlite.dbclose(db)
return error("Unable to create default category")
end
end
if sqlite.hasTable(db, "owners") == 0 then
-- create the table
sql = [[
CREATE TABLE "owners" (
"id" INTEGER,
"name" TEXT NOT NULL,
PRIMARY KEY("id" AUTOINCREMENT)
);
]]
if sqlite.query(db, sql) ~= 1 then
sqlite.dbclose(db)
return error("Unable to create table owners")
end
-- insert unknown category
sql = [[
INSERT INTO owners("id","name") VALUES (0,'None');
]]
if sqlite.query(db, sql) ~= 1 then
sqlite.dbclose(db)
return error("Unable to create default None owner")
end
end
if sqlite.hasTable(db, "docs") == 0 then
-- create the table
sql = [[
CREATE TABLE "docs" (
"id" INTEGER,
"name" TEXT NOT NULL,
"ctime" INTEGER,
"day" INTEGER,
"month" INTEGER,
"year" INTEGER,
"cid" INTEGER DEFAULT 0,
"oid" INTEGER DEFAULT 0,
"file" TEXT NOT NULL,
"tags" TEXT,
"note" TEXT,
"mtime" INTEGER,
FOREIGN KEY("oid") REFERENCES "owners"("id") ON DELETE SET DEFAULT ON UPDATE NO ACTION,
FOREIGN KEY("cid") REFERENCES "categories"("id") ON DELETE SET DEFAULT ON UPDATE NO ACTION,
PRIMARY KEY("id" AUTOINCREMENT)
);
]]
if sqlite.query(db, sql) ~= 1 then
sqlite.dbclose(db)
return error("Unable to create table docs")
end
end
sqlite.dbclose(db)
return result("Docify initialized")
end
handle.fetch = function(table)
local db = sqlite._getdb(vfs.ospath(dbpath))
if not db then
return error("Unable to get database "..dbpath)
end
local r = sqlite.select(db, table, "*", "1=1")
sqlite.dbclose(db)
if r == nil then
return error("Unable to fetch data from "..table)
else
return result(r)
end
end
handle.insert = function(param)
local db = sqlite._getdb(vfs.ospath(dbpath))
if not db then
return error("Unable to get database "..dbpath)
end
local keys = {}
local values = {}
for k,v in pairs(param.data) do
if k ~= "id" then
table.insert(keys,k)
if type(v) == "number" then
table.insert(values, v)
elseif type(v) == "boolean" then
table.insert( values, v and 1 or 0 )
else
local t = "\""..v:gsub('"', '""').."\""
table.insert(values,t)
end
end
end
local sql = "INSERT INTO "..param.table.." ("..table.concat(keys,',')..') VALUES ('
sql = sql..table.concat(values,',')..');'
local r = sqlite.query(db, sql)
sqlite.dbclose(db)
if r == nil then
return error("Unable to insert data to "..param.table)
else
return result("Data inserted")
end
end
handle.preview = function(path)
-- convert -resize 300x500 noel.pdf[0] thumb.png
local name = std.sha1(path:gsub(docpath,""))..".png"
-- try to find the thumb
local tpath = docpath.."/cache/"..name
if not vfs.exists(tpath) then
-- regenerate thumb
local cmd = "convert -resize 200x500 "..vfs.ospath(path).."[0] "..vfs.ospath(tpath)
os.execute(cmd)
end
if vfs.exists(tpath) then
--local cmd = "rm "..vfs.ospath(tpath)
--os.execute(cmd)
return result("exist")
else
return error("do not exist")
end
end
handle.update = function(param)
if not param.data.id or param.data.id == 0 then
return error("Record id is 0 or not found")
end
local db = sqlite._getdb(vfs.ospath(dbpath))
if not db then
return error("Unable to get database "..dbpath)
end
local lst = {}
for k,v in pairs(param.data) do
if(type(v)== "number") then
table.insert(lst,k.."="..v)
elseif type(v) == "boolean" then
table.insert( lst, k.."="..(v and 1 or 0) )
else
table.insert(lst,k.."=\""..v:gsub('"', '""').."\"")
end
end
local sql = "UPDATE "..param.table.." SET "..table.concat(lst,",").." WHERE id="..param.data.id..";"
local r = sqlite.query(db, sql)
sqlite.dbclose(db)
if r == nil then
return error("Unable to update data to "..param.table)
else
return result("Data Updated")
end
end
handle.delete = function(param)
if param.id == 0 then
return error("Record with id = 0 cannot be deleted")
end
local db = sqlite._getdb(vfs.ospath(dbpath))
if not db then
return error("Unable to get database "..dbpath)
end
local sql = "DELETE FROM "..param.table.." WHERE id="..param.id..";"
local r = sqlite.query(db, sql)
sqlite.dbclose(db)
if r == nil then
return error("Unable to delete data from "..param.table)
else
return result("Data deleted")
end
end
if arg.action and handle[arg.action] then
-- check if the database exits
docpath = arg.docpath
dbpath = docpath.."/docify.db"
return handle[arg.action](arg.args)
else
return error("Invalid action parameter")
end

View File

@ -3,18 +3,18 @@
<div data-width="5"></div>
<afx-vbox data-width="150">
<afx-label class="header" iconclass = "fa fa-bars" text="__(Categories)" data-height="22"></afx-label>
<afx-tree-view data-id="catview"></afx-tree-view>
<afx-hbox data-height="30">
<div data-width="5"></div>
<afx-button data-width = "25" text = "" iconclass = "fa fa-plus-circle"></afx-button>
<afx-button data-width = "25" text = "" iconclass = "fa fa-minus-circle"></afx-button>
<afx-button data-width = "25" text = "" iconclass = "fa fa-pencil-square-o"></afx-button>
</afx-hbox>
<afx-list-view data-id="catview"></afx-list-view>
<div data-height="5"></div>
</afx-vbox>
<afx-resizer data-width="4"></afx-resizer>
<afx-vbox data-width = "300">
<afx-grid-view data-id="gridview"></afx-grid-view>
<afx-hbox data-height="30">
<div data-width="5"></div>
<afx-button data-id="bt-add-doc" data-width = "25" text = "" iconclass = "fa fa-plus-circle"></afx-button>
<afx-button data-width = "25" text = "" iconclass = "fa fa-minus-circle"></afx-button>
<afx-button data-width = "25" text = "" iconclass = "fa fa-pencil-square-o"></afx-button>
</afx-hbox>
</afx-vbox>
<afx-resizer data-width="4"></afx-resizer>
<afx-vbox></afx-vbox>

249
Docify/build/debug/api.lua Normal file
View File

@ -0,0 +1,249 @@
local arg = ...
ulib = require("ulib")
sqlite = modules.sqlite()
vfs = require("vfs")
local handle = {}
local docpath = nil
local dbpath = nil
local result = function(data)
return {
error = false,
result = data
}
end
local error = function(data)
return {
error = data,
result = false
}
end
local mkdirp =function(p)
if not vfs.exists(p) then
if not vfs.mkdir(p) then
return false, error("Unable to create directory: "..p)
end
end
return true, nil
end
handle.init = function(args)
local r, e = mkdirp(docpath)
if not r then return e end
r, e = mkdirp(docpath.."/unclassified")
if not r then return e end
r, e = mkdirp(docpath.."/cache")
if not r then return e end
local db = sqlite._getdb(vfs.ospath(dbpath))
if not db then
return error("Unable to initialized database "..dbpath)
end
local sql
-- check if table exists
if sqlite.hasTable(db, "categories") == 0 then
-- create the table
sql = [[
CREATE TABLE "categories" (
"id" INTEGER,
"name" TEXT NOT NULL,
PRIMARY KEY("id" AUTOINCREMENT)
);
]]
if sqlite.query(db, sql) ~= 1 then
sqlite.dbclose(db)
return error("Unable to create table categories")
end
-- insert unknown category
sql = [[
INSERT INTO categories("id","name") VALUES (0,'Uncategoried');
]]
if sqlite.query(db, sql) ~= 1 then
sqlite.dbclose(db)
return error("Unable to create default category")
end
end
if sqlite.hasTable(db, "owners") == 0 then
-- create the table
sql = [[
CREATE TABLE "owners" (
"id" INTEGER,
"name" TEXT NOT NULL,
PRIMARY KEY("id" AUTOINCREMENT)
);
]]
if sqlite.query(db, sql) ~= 1 then
sqlite.dbclose(db)
return error("Unable to create table owners")
end
-- insert unknown category
sql = [[
INSERT INTO owners("id","name") VALUES (0,'None');
]]
if sqlite.query(db, sql) ~= 1 then
sqlite.dbclose(db)
return error("Unable to create default None owner")
end
end
if sqlite.hasTable(db, "docs") == 0 then
-- create the table
sql = [[
CREATE TABLE "docs" (
"id" INTEGER,
"name" TEXT NOT NULL,
"ctime" INTEGER,
"day" INTEGER,
"month" INTEGER,
"year" INTEGER,
"cid" INTEGER DEFAULT 0,
"oid" INTEGER DEFAULT 0,
"file" TEXT NOT NULL,
"tags" TEXT,
"note" TEXT,
"mtime" INTEGER,
FOREIGN KEY("oid") REFERENCES "owners"("id") ON DELETE SET DEFAULT ON UPDATE NO ACTION,
FOREIGN KEY("cid") REFERENCES "categories"("id") ON DELETE SET DEFAULT ON UPDATE NO ACTION,
PRIMARY KEY("id" AUTOINCREMENT)
);
]]
if sqlite.query(db, sql) ~= 1 then
sqlite.dbclose(db)
return error("Unable to create table docs")
end
end
sqlite.dbclose(db)
return result("Docify initialized")
end
handle.fetch = function(table)
local db = sqlite._getdb(vfs.ospath(dbpath))
if not db then
return error("Unable to get database "..dbpath)
end
local r = sqlite.select(db, table, "*", "1=1")
sqlite.dbclose(db)
if r == nil then
return error("Unable to fetch data from "..table)
else
return result(r)
end
end
handle.insert = function(param)
local db = sqlite._getdb(vfs.ospath(dbpath))
if not db then
return error("Unable to get database "..dbpath)
end
local keys = {}
local values = {}
for k,v in pairs(param.data) do
if k ~= "id" then
table.insert(keys,k)
if type(v) == "number" then
table.insert(values, v)
elseif type(v) == "boolean" then
table.insert( values, v and 1 or 0 )
else
local t = "\""..v:gsub('"', '""').."\""
table.insert(values,t)
end
end
end
local sql = "INSERT INTO "..param.table.." ("..table.concat(keys,',')..') VALUES ('
sql = sql..table.concat(values,',')..');'
local r = sqlite.query(db, sql)
sqlite.dbclose(db)
if r == nil then
return error("Unable to insert data to "..param.table)
else
return result("Data inserted")
end
end
handle.preview = function(path)
-- convert -resize 300x500 noel.pdf[0] thumb.png
local name = std.sha1(path:gsub(docpath,""))..".png"
-- try to find the thumb
local tpath = docpath.."/cache/"..name
if not vfs.exists(tpath) then
-- regenerate thumb
local cmd = "convert -resize 200x500 "..vfs.ospath(path).."[0] "..vfs.ospath(tpath)
os.execute(cmd)
end
if vfs.exists(tpath) then
local cmd = "rm "..vfs.ospath(tpath)
os.execute(cmd)
return result("exist")
else
return error("do not exist")
end
end
handle.update = function(param)
if not param.data.id or param.data.id == 0 then
return error("Record id is 0 or not found")
end
local db = sqlite._getdb(vfs.ospath(dbpath))
if not db then
return error("Unable to get database "..dbpath)
end
local lst = {}
for k,v in pairs(param.data) do
if(type(v)== "number") then
table.insert(lst,k.."="..v)
elseif type(v) == "boolean" then
table.insert( lst, k.."="..(v and 1 or 0) )
else
table.insert(lst,k.."=\""..v:gsub('"', '""').."\"")
end
end
local sql = "UPDATE "..param.table.." SET "..table.concat(lst,",").." WHERE id="..param.data.id..";"
local r = sqlite.query(db, sql)
sqlite.dbclose(db)
if r == nil then
return error("Unable to update data to "..param.table)
else
return result("Data Updated")
end
end
handle.delete = function(param)
if param.id == 0 then
return error("Record with id = 0 cannot be deleted")
end
local db = sqlite._getdb(vfs.ospath(dbpath))
if not db then
return error("Unable to get database "..dbpath)
end
local sql = "DELETE FROM "..param.table.." WHERE id="..param.id..";"
local r = sqlite.query(db, sql)
sqlite.dbclose(db)
if r == nil then
return error("Unable to delete data from "..param.table)
else
return result("Data deleted")
end
end
if arg.action and handle[arg.action] then
-- check if the database exits
docpath = arg.docpath
dbpath = docpath.."/docify.db"
return handle[arg.action](arg.args)
else
return error("Invalid action parameter")
end

View File

@ -1,5 +1,5 @@
afx-app-window[data-id = "Docify"] .header .label-text
{
font-weight: bold !important;
font-weight: bold;
}

View File

@ -1,12 +1,456 @@
(function() {
var Docify;
var DocDialog, Docify, FilePreviewDialog, OwnerDialog;
OwnerDialog = class OwnerDialog extends this.OS.GUI.BasicDialog {
constructor() {
super("OwnerDialog", OwnerDialog.scheme);
}
main() {
super.main();
this.oview = this.find("ownview");
this.oview.buttons = [
{
text: "",
iconclass: "fa fa-plus-circle",
onbtclick: (e) => {
return this.openDialog("PromptDialog",
{
title: __("Owner"),
label: __("Name")
}).then((d) => {
return this.parent.exec("insert",
{
table: "owners",
data: {
name: d
}
}).then((r) => {
if (r.error) {
return this.error(r.error);
}
return this.owner_refresh();
}).catch((e) => {
return this.error(__("Unable to insert owner: {0}",
e.toString()),
e);
});
}).catch((e) => {
return this.error(e.toString(),
e);
});
}
},
{
text: "",
iconclass: "fa fa-minus-circle",
onbtclick: (e) => {
var item;
item = this.oview.selectedItem;
if (!item) {
return;
}
return this.ask({
text: __("Do you realy want to delete: `{0}`",
item.data.text)
}).then((d) => {
if (!d) {
return;
}
return this.parent.exec("delete",
{
table: "owners",
id: parseInt(item.data.id)
}).then((d) => {
if (d.error) {
return this.error(d.error);
}
return this.owner_refresh();
}).catch((e) => {
return this.error(__("Unable delete category: {0}",
e.toString()),
e);
});
});
}
},
{
text: "",
iconclass: "fa fa-pencil-square-o",
onbtclick: (e) => {
var item;
item = this.oview.selectedItem;
if (!item) {
return;
}
return this.openDialog("PromptDialog",
{
title: __("Owner"),
label: __("Name"),
value: item.data.name
}).then((d) => {
return this.parent.exec("update",
{
table: "owners",
data: {
id: parseInt(item.data.id),
name: d
}
}).then((r) => {
if (r.error) {
return this.error(r.error);
}
return this.owner_refresh();
}).catch((e) => {
return this.error(__("Unable to update owner: {0}",
e.toString()),
e);
});
}).catch((e) => {
return this.error(e.toString());
});
}
}
];
return this.owner_refresh();
}
owner_refresh() {
return this.parent.exec("fetch", "owners").then((d) => {
var i, len, ref, v;
ref = d.result;
for (i = 0, len = ref.length; i < len; i++) {
v = ref[i];
v.text = v.name;
}
return this.oview.data = d.result;
}).catch((err) => {
return this.error(__("Unable to fetch owners: {0}", err.toString()), e);
});
}
};
OwnerDialog.scheme = `<afx-app-window width='200' height='300'>
<afx-vbox>
<afx-list-view data-id="ownview"></afx-list-view>
</afx-vbox>
</afx-app-window>`;
DocDialog = class DocDialog extends this.OS.GUI.BasicDialog {
constructor() {
super("DocDialog", DocDialog.scheme);
}
main() {
super.main();
return this.find("file-list").buttons = [
{
text: "",
iconclass: "fa fa-plus-circle",
onbtclick: (e) => {}
},
{
text: "",
iconclass: "fa fa-minus-circle",
onbtclick: (e) => {}
}
];
}
};
DocDialog.scheme = `<afx-app-window width='500' height='300'>
<afx-hbox>
<afx-vbox data-width="300">
<afx-hbox data-height="22">
<afx-label text = "__(title)" data-width="50"></afx-label>
<input type="text"></input>
</afx-hbox>
<afx-hbox data-height="22">
<afx-label text = "__(Day)" data-width="50"></afx-label>
<afx-list-view dropdown="true"></afx-list-view>
<afx-label text = "__(Month)"data-width="50" ></afx-label>
<afx-list-view dropdown="true"></afx-list-view>
<afx-label text = "__(Year)"data-width="50" ></afx-label>
<afx-list-view dropdown="true"></afx-list-view>
</afx-hbox>
<afx-label text = "__(Files)" data-height="22"></afx-label>
<afx-list-view data-id="file-list"></afx-list-view>
<afx-label text = "__(Note)" data-height="22"></afx-label>
<textarea></textarea>
<afx-hbox data-height = "27">
<afx-label text = "__(Tags)" data-width="50"></afx-label>
<input type="text"></input>
</afx-hbox>
</afx-vbox>
<afx-vbox>
<div></div>
<afx-button text="__(Save)" iconclass="" data-height="30" ></afx-button>
</afx-vbox>
</afx-hbox>
</afx-app-window>`;
FilePreviewDialog = class FilePreviewDialog extends this.OS.GUI.BasicDialog {
constructor() {
super("FilePreviewDialog", FilePreviewDialog.scheme);
}
main() {
super.main();
this.flist = this.find("file-list");
this.flist.onlistselect = (e) => {
// console.log e.data.item.data
return this.parent.exec("preview", e.data.item.data.path).then((d) => {
return console.log(d);
}).catch((e) => {
return this.error(e.toString(), e);
});
};
return this.refresh();
}
refresh() {
return `${this.parent.setting.docpath}/unclassified`.asFileHandle().read().then((d) => {
var i, len, ref, v;
if (d.error) {
return this.parent.error(d.error);
}
ref = d.result;
for (i = 0, len = ref.length; i < len; i++) {
v = ref[i];
v.text = v.filename;
}
return this.flist.data = d.result;
}).catch((e) => {
return this.error(__("Unable to fetch unclassified file list: {0}", e.toString()), e);
});
}
};
FilePreviewDialog.scheme = `<afx-app-window width='500' height='300'>
<afx-hbox>
<afx-vbox data-width="200">
<afx-label text = "__(Files)" data-height="22"></afx-label>
<afx-list-view data-id="file-list"></afx-list-view>
</afx-vbox>
<afx-vbox>
<div></div>
<afx-button text="__(Ok)" iconclass="" data-height="30" ></afx-button>
</afx-vbox>
</afx-hbox>
</afx-app-window>`;
Docify = class Docify extends this.OS.application.BaseApplication {
constructor(args) {
super("Docify", args);
}
main() {}
main() {
this.catview = this.find("catview");
this.catview.buttons = [
{
text: "",
iconclass: "fa fa-plus-circle",
onbtclick: (e) => {
return this.openDialog("PromptDialog",
{
title: __("Category"),
label: __("Name")
}).then((d) => {
return this.exec("insert",
{
table: "categories",
data: {
name: d
}
}).then((r) => {
if (r.error) {
return this.error(r.error);
}
return this.cat_refresh();
}).catch((e) => {
return this.error(__("Unable to insert category: {0}",
e.toString()));
});
}).catch((e) => {
return this.error(e.toString());
});
}
},
{
text: "",
iconclass: "fa fa-minus-circle",
onbtclick: (e) => {
var item;
item = this.catview.selectedItem;
if (!item) {
return;
}
return this.ask({
text: __("Do you realy want to delete: `{0}`",
item.data.text)
}).then((d) => {
if (!d) {
return;
}
return this.exec("delete",
{
table: "categories",
id: parseInt(item.data.id)
}).then((d) => {
if (d.error) {
return this.error(d.error);
}
return this.cat_refresh();
}).catch((e) => {
return this.error(__("Unable delete category: {0}",
e.toString()));
});
});
}
},
{
text: "",
iconclass: "fa fa-pencil-square-o",
onbtclick: (e) => {
var item;
item = this.catview.selectedItem;
if (!item) {
return;
}
return this.openDialog("PromptDialog",
{
title: __("Category"),
label: __("Name"),
value: item.data.name
}).then((d) => {
return this.exec("update",
{
table: "categories",
data: {
id: parseInt(item.data.id),
name: d
}
}).then((r) => {
if (r.error) {
return this.error(r.error);
}
return this.cat_refresh();
}).catch((e) => {
return this.error(__("Unable to update category: {0}",
e.toString()));
});
}).catch((e) => {
return this.error(e.toString());
});
}
}
];
this.find("bt-add-doc").onbtclick = (e) => {
return this.openDialog(new DocDialog());
};
return this.initialize();
}
cat_refresh() {
return this.exec("fetch", "categories").then((d) => {
var i, len, ref, v;
ref = d.result;
for (i = 0, len = ref.length; i < len; i++) {
v = ref[i];
v.text = v.name;
}
return this.catview.data = d.result;
}).catch((err) => {
return this.error(__("Unable to fetch categories: {0}", err.toString()));
});
}
initialize() {
// Check if we have configured docpath
if (this.setting.docpath) {
// check data base
return this.initdb();
} else {
// ask user to choose a docpath
return this.openDialog("FileDialog", {
title: __("Please select a doc path"),
mimes: ['dir']
}).then((d) => {
this.setting.docpath = d.file.path;
this._api.setting();
return this.initdb();
}).catch((msg) => {
return this.error(msg.toString(), msg);
});
}
}
exec(action, args) {
var cmd;
cmd = {
path: `${this.path()}/api.lua`,
parameters: {
action: action,
docpath: this.setting.docpath,
args: args
}
};
return this.call(cmd);
}
initdb() {
if (!this.setting.docpath) {
return this.error(__("No configured docpath"));
}
// fetch the categories from the database
return this.exec("init").then((d) => {
if (d.error) {
return this.error(d.error);
}
this.notify(d.result);
// load categories
return this.cat_refresh();
}).catch((e) => {
return this.error(__("Unable to init database: {0}", e.toString()));
});
}
menu() {
return [
{
text: "__(View)",
nodes: [
{
text: "__(Owners)",
id: "owners",
shortcut: "A-O"
},
{
text: "__(Preview)",
id: "preview",
shortcut: "A-P"
}
],
onchildselect: (e) => {
return this.fileMenuHandle(e.data.item.data.id);
}
}
];
}
fileMenuHandle(id) {
switch (id) {
case "owners":
return this.openDialog(new OwnerDialog(), {
title: __("Owners")
});
case "preview":
return this.openDialog(new FilePreviewDialog());
}
}
};

View File

@ -3,18 +3,18 @@
<div data-width="5"></div>
<afx-vbox data-width="150">
<afx-label class="header" iconclass = "fa fa-bars" text="__(Categories)" data-height="22"></afx-label>
<afx-tree-view data-id="catview"></afx-tree-view>
<afx-hbox data-height="30">
<div data-width="5"></div>
<afx-button data-width = "25" text = "" iconclass = "fa fa-plus-circle"></afx-button>
<afx-button data-width = "25" text = "" iconclass = "fa fa-minus-circle"></afx-button>
<afx-button data-width = "25" text = "" iconclass = "fa fa-pencil-square-o"></afx-button>
</afx-hbox>
<afx-list-view data-id="catview"></afx-list-view>
<div data-height="5"></div>
</afx-vbox>
<afx-resizer data-width="4"></afx-resizer>
<afx-vbox data-width = "300">
<afx-grid-view data-id="gridview"></afx-grid-view>
<afx-hbox data-height="30">
<div data-width="5"></div>
<afx-button data-id="bt-add-doc" data-width = "25" text = "" iconclass = "fa fa-plus-circle"></afx-button>
<afx-button data-width = "25" text = "" iconclass = "fa fa-minus-circle"></afx-button>
<afx-button data-width = "25" text = "" iconclass = "fa fa-pencil-square-o"></afx-button>
</afx-hbox>
</afx-vbox>
<afx-resizer data-width="4"></afx-resizer>
<afx-vbox></afx-vbox>

View File

@ -0,0 +1,161 @@
class OwnerDialog extends this.OS.GUI.BasicDialog
constructor: () ->
super "OwnerDialog", OwnerDialog.scheme
main: () ->
super.main()
@oview = @find("ownview")
@oview.buttons = [
{
text: "",
iconclass: "fa fa-plus-circle",
onbtclick: (e) =>
@openDialog("PromptDialog", { title: __("Owner"), label: __("Name")})
.then (d) =>
@parent.exec("insert", { table: "owners", data: { name: d } })
.then (r) =>
return @error r.error if r.error
@owner_refresh()
.catch (e) => @error __("Unable to insert owner: {0}", e.toString()),e
.catch (e) => @error e.toString(),e
},
{
text: "",
iconclass: "fa fa-minus-circle",
onbtclick: (e) =>
item = @oview.selectedItem
return unless item
@ask({ text:__("Do you realy want to delete: `{0}`", item.data.text)})
.then (d) =>
return unless d
@parent.exec("delete", {table:"owners", id: parseInt(item.data.id)})
.then (d) =>
return @error d.error if d.error
@owner_refresh()
.catch (e) =>
@error __("Unable delete category: {0}", e.toString()), e
},
{
text: "",
iconclass: "fa fa-pencil-square-o",
onbtclick: (e) =>
item = @oview.selectedItem
return unless item
@openDialog("PromptDialog", { title: __("Owner"), label: __("Name"), value: item.data.name })
.then (d) =>
@parent.exec("update", { table: "owners", data: { id: parseInt(item.data.id), name: d } })
.then (r) =>
return @error r.error if r.error
@owner_refresh()
.catch (e) => @error __("Unable to update owner: {0}", e.toString()), e
.catch (e) => @error e.toString()
}
]
@owner_refresh()
owner_refresh: () ->
@parent.exec("fetch", "owners")
.then (d) =>
v.text = v.name for v in d.result
@oview.data = d.result
.catch (err) => @error __("Unable to fetch owners: {0}", err.toString()), e
OwnerDialog.scheme = """
<afx-app-window width='200' height='300'>
<afx-vbox>
<afx-list-view data-id="ownview"></afx-list-view>
</afx-vbox>
</afx-app-window>
"""
class DocDialog extends this.OS.GUI.BasicDialog
constructor: () ->
super "DocDialog", DocDialog.scheme
main: () ->
super.main()
@find("file-list").buttons = [
{
text: "",
iconclass: "fa fa-plus-circle",
onbtclick: (e) =>
},
{
text: "",
iconclass: "fa fa-minus-circle",
onbtclick: (e) =>
}
]
DocDialog.scheme = """
<afx-app-window width='500' height='300'>
<afx-hbox>
<afx-vbox data-width="300">
<afx-hbox data-height="22">
<afx-label text = "__(title)" data-width="50"></afx-label>
<input type="text"></input>
</afx-hbox>
<afx-hbox data-height="22">
<afx-label text = "__(Day)" data-width="50"></afx-label>
<afx-list-view dropdown="true"></afx-list-view>
<afx-label text = "__(Month)"data-width="50" ></afx-label>
<afx-list-view dropdown="true"></afx-list-view>
<afx-label text = "__(Year)"data-width="50" ></afx-label>
<afx-list-view dropdown="true"></afx-list-view>
</afx-hbox>
<afx-label text = "__(Files)" data-height="22"></afx-label>
<afx-list-view data-id="file-list"></afx-list-view>
<afx-label text = "__(Note)" data-height="22"></afx-label>
<textarea></textarea>
<afx-hbox data-height = "27">
<afx-label text = "__(Tags)" data-width="50"></afx-label>
<input type="text"></input>
</afx-hbox>
</afx-vbox>
<afx-vbox>
<div></div>
<afx-button text="__(Save)" iconclass="" data-height="30" ></afx-button>
</afx-vbox>
</afx-hbox>
</afx-app-window>
"""
class FilePreviewDialog extends this.OS.GUI.BasicDialog
constructor: () ->
super "FilePreviewDialog", FilePreviewDialog.scheme
main: () ->
super.main()
@flist = @find("file-list")
@flist.onlistselect = (e) =>
# console.log e.data.item.data
@parent.exec("preview", e.data.item.data.path)
.then (d) =>
console.log d
.catch (e) =>
@error e.toString(), e
@refresh()
refresh: () ->
"#{@parent.setting.docpath}/unclassified".asFileHandle().read()
.then (d) =>
return @parent.error d.error if d.error
v.text = v.filename for v in d.result
@flist.data = d.result
.catch (e) =>
@error __("Unable to fetch unclassified file list: {0}", e.toString()), e
FilePreviewDialog.scheme = """
<afx-app-window width='500' height='300'>
<afx-hbox>
<afx-vbox data-width="200">
<afx-label text = "__(Files)" data-height="22"></afx-label>
<afx-list-view data-id="file-list"></afx-list-view>
</afx-vbox>
<afx-vbox>
<div></div>
<afx-button text="__(Ok)" iconclass="" data-height="30" ></afx-button>
</afx-vbox>
</afx-hbox>
</afx-app-window>
"""

View File

@ -3,5 +3,119 @@ class Docify extends this.OS.application.BaseApplication
super "Docify", args
main: () ->
@catview = @find "catview"
@catview.buttons = [
{
text: "",
iconclass: "fa fa-plus-circle",
onbtclick: (e) =>
@openDialog("PromptDialog", { title: __("Category"), label: __("Name")})
.then (d) =>
@exec("insert", { table: "categories", data: { name: d } })
.then (r) =>
return @error r.error if r.error
@cat_refresh()
.catch (e) => @error __("Unable to insert category: {0}", e.toString())
.catch (e) => @error e.toString()
},
{
text: "",
iconclass: "fa fa-minus-circle",
onbtclick: (e) =>
item = @catview.selectedItem
return unless item
@ask({ text:__("Do you realy want to delete: `{0}`", item.data.text)})
.then (d) =>
return unless d
@exec("delete", {table:"categories", id: parseInt(item.data.id)})
.then (d) =>
return @error d.error if d.error
@cat_refresh()
.catch (e) =>
@error __("Unable delete category: {0}", e.toString())
},
{
text: "",
iconclass: "fa fa-pencil-square-o",
onbtclick: (e) =>
item = @catview.selectedItem
return unless item
@openDialog("PromptDialog", { title: __("Category"), label: __("Name"), value: item.data.name })
.then (d) =>
@exec("update", { table: "categories", data: { id: parseInt(item.data.id), name: d } })
.then (r) =>
return @error r.error if r.error
@cat_refresh()
.catch (e) => @error __("Unable to update category: {0}", e.toString())
.catch (e) => @error e.toString()
}
]
@find("bt-add-doc").onbtclick = (e) =>
@openDialog new DocDialog
@initialize()
cat_refresh: () ->
@exec("fetch", "categories")
.then (d) =>
v.text = v.name for v in d.result
@catview.data = d.result
.catch (err) => @error __("Unable to fetch categories: {0}", err.toString())
initialize: () ->
# Check if we have configured docpath
if @setting.docpath
# check data base
@initdb()
else
# ask user to choose a docpath
@openDialog "FileDialog", { title:__("Please select a doc path"), mimes: ['dir'] }
.then (d) =>
@setting.docpath = d.file.path
@_api.setting()
@initdb()
.catch (msg) => @error msg.toString(), msg
exec: (action, args) ->
cmd =
path: "#{@path()}/api.lua",
parameters:
action: action,
docpath: @setting.docpath,
args: args
return @call(cmd)
initdb: () ->
return @error __("No configured docpath") unless @setting.docpath
# fetch the categories from the database
@exec("init")
.then (d) =>
return @error d.error if d.error
@notify d.result
# load categories
@cat_refresh()
.catch (e) =>
@error __("Unable to init database: {0}", e.toString())
menu: () ->
[
{
text: "__(View)",
nodes: [
{ text: "__(Owners)", id:"owners", shortcut: "A-O"},
{ text: "__(Preview)", id:"preview", shortcut: "A-P"}
],
onchildselect: (e) => @fileMenuHandle e.data.item.data.id
}
]
fileMenuHandle:(id) ->
switch id
when "owners"
@openDialog new OwnerDialog(), { title: __("Owners")}
when "preview"
@openDialog new FilePreviewDialog()
this.OS.register "Docify", Docify

View File

@ -3,6 +3,6 @@
"root": "home://workspace/antosdk-apps/Docify",
"css": ["css/main.css"],
"javascripts": [],
"coffees": ["coffees/main.coffee"],
"coffees": ["coffees/dialogs.coffee", "coffees/main.coffee"],
"copies": ["assets/scheme.html", "api/api.lua", "package.json", "README.md"]
}