working on collections...

Signed-off-by: Alex A. Naanou <alex.nanou@gmail.com>
This commit is contained in:
Alex A. Naanou 2017-08-16 05:41:49 +03:00
parent 1c9805f05c
commit 824ca10aef
6 changed files with 192 additions and 12 deletions

View File

@ -10,16 +10,19 @@
var actions = require('lib/actions') var actions = require('lib/actions')
var features = require('lib/features') var features = require('lib/features')
var browse = require('lib/widget/browse')
var core = require('features/core') var core = require('features/core')
var widgets = require('features/ui-widgets')
/*********************************************************************/ /*********************************************************************/
// XXX should collections be in the Crop menu????
// XXX things we need to do to collections: // XXX things we need to do to collections:
// - add images from current state // - add images from current state
// - remove images (from collection) // - remove images (from collection)
// - check what collections is image in...
var CollectionActions = actions.Actions({ var CollectionActions = actions.Actions({
collections: null, collections: null,
@ -42,8 +45,7 @@ var CollectionActions = actions.Actions({
// locations: // locations:
// - collection specific stuff (data) to collection path // - collection specific stuff (data) to collection path
// - global stuff (images, tags, ...) to base index... // - global stuff (images, tags, ...) to base index...
// XXX need to .reload() here... loadCollection: ['- Collections/',
loadCollection: ['-Collections/',
function(collection){ function(collection){
if(collection == null if(collection == null
|| this.collections == null || this.collections == null
@ -71,20 +73,23 @@ var CollectionActions = actions.Actions({
title: collection, title: collection,
// XXX we need to trim .order to only the current images??? // XXX we need to trim .order to only the current images???
data: this.data.clone(), data: this.data
.clone()
.removeUnloadedGids(),
} }
}], }],
inCollections: ['- Image/', inCollections: ['- Image/',
core.doc`Get list of collections containing item`, core.doc`Get list of collections containing item`,
function(gid){ function(gid){
var that = this var that = this
return Object.keys(this.collections || {}) return Object.keys(this.collections || {})
.filter(function(c){ .filter(function(c){
return that.collections[c].data.order.indexOf(gid) >= 0 }) return !gid
|| that.collections[c].data.order.indexOf(gid) >= 0 })
}], }],
toCollection: ['- Collections/',
collect: ['- Collections/',
core.doc`Add items to collection`, core.doc`Add items to collection`,
function(gids, collection){ function(gids, collection){
var that = this var that = this
@ -98,13 +103,21 @@ var CollectionActions = actions.Actions({
: [gid] }) : [gid] })
.reduce(function(a, b){ return a.concat(b) }, []) .reduce(function(a, b){ return a.concat(b) }, [])
console.log('>>>', gids) collection = collection || this.collection
// XXX add to collection... // XXX add to collection...
// XXX // XXX
}], }],
uncollect: ['- Collections/',
function(gids, collection){
// XXX
}],
removeCollection: ['- Collections/',
function(collection){
// XXX
delete this.collections[collection]
}],
}) })
var Collection = var Collection =
@ -117,6 +130,10 @@ module.Collection = core.ImageGridFeatures.Feature({
'base', 'base',
'crop', 'crop',
], ],
suggested: [
'ui-collections',
'fs-collections',
],
actions: CollectionActions, actions: CollectionActions,
@ -125,5 +142,143 @@ module.Collection = core.ImageGridFeatures.Feature({
//---------------------------------------------------------------------
// XXX show collections in image metadata...
var UICollectionActions = actions.Actions({
// XXX highlight current collections....
browseCollections: ['Collections/Collections...',
widgets.makeUIDialog(function(gid){
var that = this
gid = gid != null ? this.data.getImage(gid) : gid
var to_remove = []
return browse.makeLister(null,
function(path, make){
var dialog = this
//var collections = Object.keys(that.collections || {})
var collections = that.inCollections(gid || null)
make.EditableList(collections,
{
unique: true,
to_remove: to_remove,
itemopen: function(title){
that.loadCollection(title)
gid
&& that.focusImage(gid)
dialog.close()
},
normalize: function(title){
return title.trim() },
check: function(title){
return title.length > 0 },
itemadded: function(title){
that.saveCollection(title) },
})
})
.close(function(){
to_remove.forEach(function(title){
that.removeCollection(title)
})
})
})],
// XXX add kb handler???
// XXX highlight current collections....
// XXX this is very similar to .browseCollections(..), is this a problem???
browseImageCollections: ['Image/Collections...',
{dialogTitle: 'Image Collections...'},
widgets.makeUIDialog(function(gid){
var that = this
gid = this.data.getImage(gid)
var to_remove = []
return browse.makeLister(null,
function(path, make){
var dialog = this
var all = Object.keys(that.collections || {})
var collections = that.inCollections(gid || null)
// build the disabled list...
all.forEach(function(title){
collections.indexOf(title) < 0
&& to_remove.push(title)
})
all.length > 0 ?
make.EditableList(all,
{
new_item: false,
to_remove: to_remove,
itemopen: function(title){
that.loadCollection(title)
gid
&& that.focusImage(gid)
dialog.close()
},
})
: make.Empty()
})
.close(function(){
to_remove.forEach(function(title){
that.uncollect(gid, title)
})
})
})],
// XXX this is not used by metadata yet...
metadataSection: ['- Image/',
function(gid, make){
}],
})
var UICollection =
module.UICollection = core.ImageGridFeatures.Feature({
title: '',
doc: '',
tag: 'ui-collections',
depends: [
'ui',
'collections',
],
actions: UICollectionActions,
handlers: [],
})
//---------------------------------------------------------------------
// XXX
var FileSystemCollection =
module.FileSystemCollection = core.ImageGridFeatures.Feature({
title: '',
doc: '',
tag: 'fs-collections',
depends: [
'fs',
'collections',
],
handlers: [],
})
//---------------------------------------------------------------------
// XXX localstorage-collections (???)
/********************************************************************** /**********************************************************************
* vim:set ts=4 sw=4 : */ return module }) * vim:set ts=4 sw=4 : */ return module })

View File

@ -1097,6 +1097,8 @@ var KeyboardUIActions = actions.Actions({
return dialog return dialog
})], })],
// XXX this does not handle the passed container protocol...
// .editKeyboardBindings('Drawer') is broken...
editKeyboardBindings: ['Interface/Keyboard bindings editor...', editKeyboardBindings: ['Interface/Keyboard bindings editor...',
core.doc`Keyboard bindings editor... core.doc`Keyboard bindings editor...

View File

@ -336,6 +336,7 @@ var MetadataUIActions = actions.Actions({
// //
// XXX should we replace 'mode' with nested set of metadata??? // XXX should we replace 'mode' with nested set of metadata???
// XXX make this support multiple images... // XXX make this support multiple images...
// XXX add support for .metadataSection(make) action to construct a section...
showMetadata: ['Image/Metadata...', showMetadata: ['Image/Metadata...',
widgets.makeUIDialog(function(image, mode){ widgets.makeUIDialog(function(image, mode){
//function(image, mode){ //function(image, mode){

View File

@ -1361,7 +1361,7 @@ var BrowseActionsActions = actions.Actions({
Object.keys(paths).forEach(function(key){ Object.keys(paths).forEach(function(key){
// handle mode flag... // handle mode flag...
var action = paths[key][0] var action = paths[key][0]
var mode = key.split(/^- /) var mode = key.split(/^-\s*/)
var path = mode.pop() var path = mode.pop()
mode = mode.length > 0 ? 'hidden' : null mode = mode.length > 0 ? 'hidden' : null

View File

@ -2552,6 +2552,15 @@ var DataPrototype = {
return this return this
}, },
// Remove unloaded gids...
//
// This removes:
// - images from .data that are not in any ribbon
removeUnloadedGids: function(){
this.order = this.getImages('loaded')
return this
},
/****************************************** JSON serialization ***/ /****************************************** JSON serialization ***/

View File

@ -569,6 +569,10 @@ function(data, options){
// // just use it for uniqueness testing... // // just use it for uniqueness testing...
// unique: <bool> | function(value){ ... }, // unique: <bool> | function(value){ ... },
// //
// // called when new item is added to list...
// //
// itemadded: function(value){ ... },
//
// // If true sort values... // // If true sort values...
// // If function will be used as cmp for sorting... // // If function will be used as cmp for sorting...
// sort: <bool> || function(a, b){ ... }, // sort: <bool> || function(a, b){ ... },
@ -589,7 +593,7 @@ function(data, options){
// // list length limit is reached... // // list length limit is reached...
// overflow: function(selected){ ... }, // overflow: function(selected){ ... },
// //
// // list if items to remove, if not given this will be maintained // // list of items to remove, if not given this will be maintained
// // internally // // internally
// to_remove: null | <list>, // to_remove: null | <list>,
// //
@ -938,6 +942,11 @@ function(list, options){
return return
} }
// check if item pre-existed...
var preexisted = lst.indexOf(options.unique instanceof Function ?
options.unique(txt)
: txt) >= 0
// add new value and sort list... // add new value and sort list...
lst.push(txt) lst.push(txt)
@ -950,6 +959,10 @@ function(list, options){
lst = lst.unique(options.unique) lst = lst.unique(options.unique)
} }
options.itemadded
&& !(options.unique && preexisted)
&& options.itemadded.call(dialog, txt)
// sort... // sort...
if(options.sort){ if(options.sort){
lst = lst lst = lst
@ -2018,7 +2031,7 @@ var BrowserPrototype = {
// //
// //
// Finalize the dialog (optional)... // Finalize the dialog (optional)...
// - Call make.done() can optionally be called after all the itmes // - Call make.done() can optionally be called after all the items
// are created. This will update the dialog to align the // are created. This will update the dialog to align the
// selected position. // selected position.
// This is useful for dialogs with async loading items. // This is useful for dialogs with async loading items.