diff --git a/ui (gen4)/features/collections.js b/ui (gen4)/features/collections.js
index 68e8e3b5..e1a0653a 100755
--- a/ui (gen4)/features/collections.js
+++ b/ui (gen4)/features/collections.js
@@ -42,6 +42,7 @@ var widgets = require('features/ui-widgets')
// XXX handle tags here???
// ...keep them global or local to collection???
// global sounds better...
+// XXX undo...
var CollectionActions = actions.Actions({
// Format:
@@ -49,6 +50,8 @@ var CollectionActions = actions.Actions({
//
: {
// title: ,
// gid: ,
+ //
+ // // base collection format -- raw data...
// data: ,
// ...
// },
@@ -61,11 +64,36 @@ var CollectionActions = actions.Actions({
set collection(value){
this.loadCollection(value) },
- // XXX need a way to prevent multiple loads...
- // ...checking if .collection is set to collection is logical but
- // may prevent reloading of collections -- i.e. loading a collection
- // anew if it is already loaded...
- // XXX doc the protocol...
+ // Format:
+ // {
+ // : ,
+ // ...
+ // }
+ //
+ // NOTE: the 'data' handler is always first...
+ get collection_handlers(){
+ var handlers = this.__collection_handlers || {}
+
+ if(Object.keys(handlers).length == 0){
+ var that = this
+ handlers['data'] = null
+ this.actions.forEach(function(action){
+ var fmt = that.getActionAttr(action, 'collectionFormat')
+ if(fmt){
+ handlers[fmt] = action
+ }
+ })
+ }
+
+ return handlers
+ },
+
+ collectionDataLoader: ['- Collections/',
+ core.doc`Collection data loader`,
+ {collectionFormat: 'data'},
+ function(title, data){
+ return new Promise(function(resolve){ resolve(data.data) }) }],
+
loadCollection: ['- Collections/',
core.doc`Load collection...
@@ -75,28 +103,58 @@ var CollectionActions = actions.Actions({
this enables extending actions to handle the collection in
different ways.
- The extending action if compatible must:
- - construct data
- - load data via:
- this.crop(data)
- - when done call:
- this.collectionLoaded(collection)
+ Protocol:
+ - collection format handlers: .collection_handlers
+ - built from actions that define .collectionFormat attr to
+ contain the target format string.
+ - format is determined by matching it to a key in .collections[collection]
+ e.g. 'data' is applicable if .collections[collection].data is not null
+ - the format key's value is passed to the handler action
+ - the handler is expected to return a promise
+ - only the first matching handler is called
+ - the data handler is always first to get checked
- XXX would be good to have a way to check if loading was done
- within this .loadCollection(..) call...
+ For an example handler see:
+ .collectionDataLoader(..)
+
+
+ The .data handler is always first to enable caching, i.e. once some
+ non-data handler is done, it can set the .data which will be loaded
+ directly the next time.
+ To invalidate such a cache .data should simply be deleted.
`,
function(collection){
+ var that = this
if(collection == null
|| this.collections == null
|| !(collection in this.collections)){
return
}
- var data = this.collections[collection].data
+ var data = this.collections[collection]
+ var handlers = this.collection_handlers
- data
- && this.crop(data)
- && this.collectionLoaded(collection)
+ // XXX might be good to sort handlers...
+ // XXX
+
+ for(var format in handlers){
+ if(data[format]){
+ return this[handlers[format]](collection, data)
+ .then(function(data){
+ data
+ && that.crop.chainCall(that, function(){
+ // NOTE: the collection and .data may have different
+ // orders and/or sets of elements, this we need
+ // to sync, and do it BEFORE all the rendering
+ // happens...
+ that.data.updateImagePositions()
+ }, data)
+ // NOTE: we need this to sync the possible different
+ // states (order, ...) of the collection and .data...
+ && that.collectionLoaded(collection)
+ })
+ }
+ }
}],
collectionLoaded: ['- Collections/',
@@ -148,9 +206,14 @@ var CollectionActions = actions.Actions({
data: (empty ?
(new this.data.constructor())
: this.data
- .crop())
+ .clone()
+ .removeUnloadedGIDs())
.run(function(){
this.collection = collection
+ // NOTE: we are doing this manually after .removeUnloadedGIDs(..)
+ // as the later will mess-up the structures
+ // inherited from the main .data, namely tags...
+ this.tags = that.data.tags
}),
}
}],
@@ -166,7 +229,6 @@ var CollectionActions = actions.Actions({
.filter(function(c){
return !gid
|| that.collections[c].data.getImage(gid) })
- //|| that.collections[c].data.order.indexOf(gid) >= 0 })
}],
collect: ['- Collections/',
@@ -258,7 +320,7 @@ var CollectionActions = actions.Actions({
return
}
- // NOTE: we are not using .data.updateImagePositions(gids, 'hide')
+ /*/ NOTE: we are not using .data.updateImagePositions(gids, 'hide')
// here because it will remove the gids from everything
// while we need them removed only from ribbons...
var hideGIDs = function(){
@@ -270,15 +332,18 @@ var CollectionActions = actions.Actions({
})
})
}
+ //*/
if(this.collection == collection){
this.data
- .run(hideGIDs)
+ //.run(hideGIDs)
+ .removeGIDs(gids)
.removeEmptyRibbons()
}
this.collections[collection].data
- .run(hideGIDs)
+ //.run(hideGIDs)
+ .removeGIDs(gids)
.removeEmptyRibbons()
}],
@@ -329,12 +394,14 @@ var CollectionActions = actions.Actions({
}
} }],
clear: [function(){
- this.collectionUnloaded('*')
+ this.collection
+ && this.collectionUnloaded('*')
delete this.collections
delete this.location.collection
}],
})
+
// XXX manage format...
// XXX manage changes...
var Collection =
@@ -360,20 +427,26 @@ module.Collection = core.ImageGridFeatures.Feature({
function(){
var collection = this.collection
return function(){
- collection != this.data.collection
+ collection != null
+ && collection != this.data.collection
&& this.collectionUnloaded(collection) }
}],
['collectionLoaded',
function(){
+ console.log('COLLECTION: LOADED')
}],
['collectionUnloaded',
- function(collection){
+ function(_, collection){
var collection = this.location.collection = this.data.collection
// cleanup...
if(collection == null){
delete this.location.collection
}
+
+ console.log('COLLECTION: UNLOADED')
+
+ this.data.updateImagePositions()
}],
],
})
@@ -551,10 +624,27 @@ module.UICollection = core.ImageGridFeatures.Feature({
// - lazy load collections (load list, lazy-load data)
// - load directories as collections...
// - export collections to directories...
+// - collection history...
-// XXX lazy load collections...
var FileSystemCollectionActions = actions.Actions({
+ // Format:
+ // {
+ // path: ,
+ // ...
+ // }
+ collections: null,
+
+ collectionPathLoader: ['- Collections/',
+ {collectionFormat: 'path'},
+ function(data, loader){
+ // XXX
+ }],
+
+ loadPathCollections: ['- Collections/',
+ function(){
+ // XXX
+ }],
})
diff --git a/ui (gen4)/imagegrid/data.js b/ui (gen4)/imagegrid/data.js
index 63709c5a..0c097604 100755
--- a/ui (gen4)/imagegrid/data.js
+++ b/ui (gen4)/imagegrid/data.js
@@ -741,7 +741,8 @@ var DataPrototype = {
// invalid gid...
// XXX need a better way to report errors...
if(i == -1){
- return -1
+ //return -1
+ return undefined
}
}
@@ -1326,7 +1327,7 @@ var DataPrototype = {
})
// maintain focus...
- if(from.indexOf(this.current) >= 0){
+ if(from && from.indexOf(this.current) >= 0){
this.focusImage('r')
}