sfu-natlang / lensingwikipedia

Lensing Wikipedia is an interface to visually browse through human history as represented in Wikipedia. This the source code that runs the website:
http://lensingwikipedia.cs.sfu.ca
Other
11 stars 4 forks source link

Selections interface refactoring #183

Closed theq629 closed 8 years ago

theq629 commented 9 years ago

In having the storyline make facet selections for #168, I've refactored the facet code around a new selections (in this case a set of selected entity values) interface, with a general implementation in utils.js. The interface allows directly changing which items are selected and watching for changes, separate from internal code or the constraints system. This system allows factoring out some of the common callback spaghetti code into functions which setup coordination between the selection and another interface. It may cost a few more total callbacks but I think can simplify the code a lot.

Since all the views require the user making some selection of objects, I'd like to change all the view code to use the same interface.

For example, the callback spaghetti in the facet setup() function is replaced with:

Utils.setupSelectionClearButton(clearElt, listBox.selection);
Utils.syncSelectionWithConstraints(selection, globalQuery, ownCnstrQuery, function (value) {
    // ... (code for making a single constraint)
});

and those functions isolate code for specific interactions, eg:

setupSelectionClearButton = function (buttonElt, selection) {
        selection.on('add', function (value) {
                buttonElt.removeAttr('disabled');
        });
        selection.on('remove-not-clear', function (value) {
                if (selection.isEmpty())
                        buttonElt.attr('disabled', 'disabled');
        });
        selection.on('clear', function() {
                buttonElt.attr('disabled', 'disabled');
        });

        buttonElt.click(function () {
                selection.clear();
        });
}

While having one view select something in another view is now trivial, eg for the storyline:

function onSelectEntityLine(entityLine) {
    var entity = vis.lookupEntity(entityLine.entityId);
    facetsByField[entity.field].facet.selection.toggle(entity.value);
}
anoopsarkar commented 9 years ago

I like it.

theq629 commented 8 years ago

Done, in the storylinesidekeyclean branch all views use the new interface for whatever their primary thing to select is, except for the comparison view which doesn't seem to have anything selectable (it does use the new interface internally now). For the storyline view, it uses it's own selection object for node selections and uses the facet and global per-field selections (#186) for entity selections.

The interface changed a bit, see selections.js.

This could potentially have introduced bugs since it touched many parts of the code. However, so far I've only found it to have eliminated a couple of minor bugs (consistency between visual selections and clear buttons or the constraints list).

theq629 commented 8 years ago

I think likely there is more we can do with this interface. For example, if there was a convenient way to make a selection that merges multiple selections objects, that could encapsulate the storyline view's interactions with the facet/per-field selections. I haven't come up with anything definite for that yet, though.