<commit_before>var fs = require('fs')
  , path = require('path')
  , lconfig = require("lconfig")
  , spawn = require('child_process').spawn
  , datastore
  , async = require('async')
  , lutil = require('lutil')
  , EventEmitter = require('events').EventEmitter
  ;

var synclets = {
    available:[],
    installed:{}
};

exports.eventEmitter = new EventEmitter();

exports.synclets = function() {
  return synclets;
};

/**
* Scans the Me directory for instaled synclets
*/
exports.findInstalled = function (callback) {
    if (!path.existsSync(lconfig.me)) fs.mkdirSync(lconfig.me, 0755);
    var dirs = fs.readdirSync(lconfig.me);
    for (var i = 0; i < dirs.length; i++) {
        var dir =  lconfig.me + "/" + dirs[i];
        try {
            if(!fs.statSync(dir).isDirectory()) continue;
            if(!path.existsSync(dir+'/me.json')) continue;
            var js = JSON.parse(fs.readFileSync(dir+'/me.json', 'utf-8'));
            if (js.synclets) {
                console.log("Loaded synclets for "+js.id);
                synclets.installed[js.id] = js;
                synclets.installed[js.id].status = "waiting";
                for (var j = 0; j < js.synclets.length; j++) {
                    scheduleRun(js, js.synclets[j]);
                }
            }
        } catch (E) {
            console.log("Me/"+dirs[i]+" does not appear to be a synclet (" +E+ ")");
        }
    }
}

exports.scanDirectory = function(dir) {
    datastore = require('./synclet/datastore');
    var files = fs.readdirSync(dir);
    for (var i = 0; i < files.length; i++) {
        var fullPath = dir + '/' + files[i];
        var stats = fs.statSync(fullPath);
        if(stats.isDirectory()) {
            exports.scanDirectory(fullPath);
            continue;
        }
        if (RegExp("\\.synclet$").test(fullPath)) {
            mapMetaData(fullPath);
        }
    }
    addUrls();
}

/**
* Install a synclet
*/
exports.install = function(metaData) {
    var serviceInfo;
    synclets.available.some(function(svcInfo) {
        if (svcInfo.srcdir == metaData.srcdir) {
            serviceInfo = {};
            for(var a in svcInfo){serviceInfo[a]=svcInfo[a];}
            serviceInfo.auth = metaData.auth;
            return true;
        }
        return false;
    });
    if (!serviceInfo) return serviceInfo;

    // local/internal name for the service on disk and whatnot, try to make it more friendly to devs/debugging
    if(serviceInfo.provider) {
        var inc = 0;
        if (path.existsSync(path.join(lconfig.lockerDir, lconfig.me, serviceInfo.provider))) {
            inc++;
            while (path.existsSync(path.join(lconfig.lockerDir, lconfig.me, serviceInfo.provider + '-' + inc))) inc++;
            serviceInfo.id = serviceInfo.provider + "-" + inc;
        } else {
            serviceInfo.id = serviceInfo.provider;
        }
    } else {
        throw "invalid synclet, has no provider";
    }
    synclets.installed[serviceInfo.id] = serviceInfo;
    fs.mkdirSync(path.join(lconfig.lockerDir, lconfig.me, serviceInfo.id),0755);
    fs.writeFileSync(path.join(lconfig.lockerDir, lconfig.me, serviceInfo.id, 'me.json'),JSON.stringify(serviceInfo, null, 4));
    for (var i = 0; i < serviceInfo.synclets.length; i++) {
        scheduleRun(serviceInfo, serviceInfo.synclets[i]);
    }
    return serviceInfo;
}

exports.isInstalled = function(serviceId) {
    return serviceId in synclets.installed;
}

exports.status = function(serviceId) {
    return synclets.installed[serviceId];
};

exports.syncNow = function(serviceId, callback) {
    if (!synclets.installed[serviceId]) return callback("no service like that installed");
    async.forEach(synclets.installed[serviceId].synclets, function(synclet, cb) { executeSynclet(synclets.installed[serviceId], synclet, cb); }, callback);
};

/**
* Add a timeout to run a synclet
*/
function scheduleRun(info, synclet) {
    // TODO if there is a .nextRun and it's past-due, run it now!
    synclet.nextRun = new Date(Date.now() + (parseInt(synclet.frequency) * 1000));
    setTimeout(function() {
        executeSynclet(info, synclet);
    }, parseInt(synclet.frequency) * 1000);
};

/**
* Executes a synclet
*/
function executeSynclet(info, synclet, callback) {
    if (synclet.status === 'running') {
        if (callback) {
            callback('already running');
        }
        return;
    }
    console.log("Synclet "+synclet.name+" starting for "+info.id);
    info.status = synclet.status = "running";
    if (!synclet.run) {
        run = ["node", lconfig.lockerDir + "/Common/node/synclet/client.js"];
    } else {
        run = ["node", path.join(lconfig.lockerDir, info.srcdir, synclet.run)];
    }

    var dataResponse = '';

    app = spawn(run.shift(), run, {cwd: path.join(lconfig.lockerDir, info.srcdir)});

    app.stderr.on('data', function (data) {
        var mod = console.outputModule;
        console.outputModule = info.title+" "+synclet.name;
        console.error(data.toString());
        console.outputModule = mod;
    });

    app.stdout.on('data',function (data) {
        dataResponse += data;
    });

    app.on('exit', function (code,signal) {
        var response;
        try {
            response = JSON.parse(dataResponse);
        } catch (E) {
            console.error(E);
            console.error(dataResponse);
            info.status = synclet.status = 'failed : ' + E;
            if (callback) callback(E);
            return;
        }
        console.log("Synclet "+synclet.name+" finished for "+info.id);
        info.status = synclet.status = 'processing data';
        tempInfo = JSON.parse(fs.readFileSync(path.join(lconfig.lockerDir, lconfig.me, info.id, 'me.json')));
        var deleteIDs = compareIDs(info.config, response.config);
        processResponse(deleteIDs, info, synclet, response, callback);
        info.config = lutil.extend(tempInfo.config, response.config);
        fs.writeFileSync(path.join(lconfig.lockerDir, lconfig.me, info.id, 'me.json'), JSON.stringify(info, null, 4));
        scheduleRun(info, synclet);
    });
    if (!info.config) info.config = {};

    info.syncletToRun = synclet;
    info.syncletToRun.workingDirectory = path.join(lconfig.lockerDir, lconfig.me, info.id);
    app.stdin.write(JSON.stringify(info)+"\n"); // Send them the process information
    delete info.syncletToRun;
};

function compareIDs (originalConfig, newConfig) {
    var resp = {};
    if (originalConfig.ids && newConfig.ids) {
        for (var i in newConfig.ids) {
            if (!originalConfig.ids[i]) break;
            var newSet = newConfig.ids[i];
            var oldSet = originalConfig.ids[i];
            seenIDs = {};
            resp[i] = [];
            for (var j = 0; j < newSet.length; j++) seenIDs[newSet[j]] = true;
            for (var j = 0; j < oldSet.length; j++) {
                if (!seenIDs[oldSet[j]]) resp[i].push(oldSet[j]);
            }
        }
    }
    return resp;
}
function processResponse(deleteIDs, info, synclet, response, callback) {
    datastore.init(function() {
        info.status = synclet.status = 'waiting';

        if (!callback) {
            callback = function() {};
        }
        var dataKeys = [];
        for (var i in response.data) {
            dataKeys.push(i);
        }
        for (var i in deleteIDs) {
            if (!dataKeys[i]) dataKeys.push(i);
        }
        async.forEach(dataKeys, function(key, cb) { processData(deleteIDs[key], info, key, response.data[key], cb); }, callback);
    });
};

function processData (deleteIDs, info, key, data, callback) {
    // console.error(deleteIDs);
    var collection = info.id + "_" + key;
    var eventType = key + "/" + info.provider;

    if (key.indexOf('/') !== -1) {
        collection = info.id + "_" + key.substring(key.indexOf('/') + 1);
        eventType = key.substring(0, key.indexOf('/')) + "/" + info.provider;
        key = key.substring(key.indexOf('/') + 1);
    }

    if (info.mongoId) {
        datastore.addCollection(key, info.id, info.mongoId);
    } else {
        datastore.addCollection(key, info.id, "id");
    }

    if (deleteIDs && deleteIDs.length > 0 && data) {
        addData(collection, data, info, eventType, function() {
            deleteData(collection, deleteIDs, info, eventType, callback);
        });
    } else if (data) {
        addData(collection, data, info, eventType, callback);
    } else if (deleteIDs && deleteIDs.length > 0) {
        deleteData(collection, deleteIDs, info, eventType, callback);
    } else {
        callback();
    }
}

function deleteData (collection, deleteIds, info, eventType, callback) {
    async.forEach(deleteIds, function(id, cb) {
        var newEvent = {obj : {source : eventType, type: 'delete', data : {}}};
        newEvent.obj.data[info.mongoId] = id;
        newEvent.fromService = "synclet/" + info.id;
        exports.eventEmitter.emit(eventType, newEvent);
        datastore.removeObject(collection, id, {timeStampe: Date.now()}, cb);
    }, callback);
}

function addData (collection, data, info, eventType, callback) {
    async.forEach(data, function(object, cb) {
        var newEvent = {obj : {source : collection, type: object.type, data: object.obj}};
        newEvent.fromService = "synclet/" + info.id;
        if (object.type === 'delete') {
            datastore.removeObject(collection, object.obj[info.mongoId], {timeStamp: object.timestamp}, cb);
            exports.eventEmitter.emit(eventType, newEvent);
        } else {
            datastore.addObject(collection, object.obj, {timeStamp: object.timestamp}, function(err, type) {
                if (type === 'same') return cb();
                newEvent.obj.type = type;
                exports.eventEmitter.emit(eventType, newEvent);
                cb();
            });
        }
    }, callback);
}
/**
* Map a meta data file JSON with a few more fields and make it available
*/
function mapMetaData(file) {
    var metaData = JSON.parse(fs.readFileSync(file, 'utf-8'));
    metaData.srcdir = path.dirname(file);
    synclets.available.push(metaData);
    return metaData;
}

function addUrls() {
    var apiKeys;
    var host = "http://" + lconfig.externalHost + ":" + lconfig.externalPort + "/";
    try {
        apiKeys = JSON.parse(fs.readFileSync(path.join(lconfig.lockerDir, lconfig.me, "apikeys.json"), 'ascii'));
    } catch(e) {
        return console.log('Error reading apikeys.json file - ' + e);
    }
    for (var i = 0; i < synclets.available.length; i++) {
        synclet = synclets.available[i];
        if (synclet.provider === 'facebook') {
            if (apiKeys.facebook) synclet.authurl = "https://graph.facebook.com/oauth/authorize?client_id=" + apiKeys.facebook.appKey + '&response_type=code&redirect_uri=' + host + "auth/facebook/auth&scope=email,offline_access,read_stream,user_photos,friends_photos,publish_stream,user_photo_video_tags";
        } else if (synclet.provider === 'twitter') {
            if (apiKeys.twitter) synclet.authurl = host + "auth/twitter/auth";
        } else if (synclet.provider === 'foursquare') {
            if (apiKeys.foursquare) synclet.authurl = "https://foursquare.com/oauth2/authenticate?client_id=" + apiKeys.foursquare.appKey + "&response_type=code&redirect_uri=" + host + "auth/foursquare/auth";
        } else if (synclet.provider === 'gcontacts') {
            if (apiKeys.gcontacts) synclet.authurl = "https://accounts.google.com/o/oauth2/auth?client_id=" + apiKeys.gcontacts.appKey + "&redirect_uri=" + host + "auth/gcontacts/auth&scope=https://www.google.com/m8/feeds/&response_type=code";
        } else if (synclet.provider === 'github') {
            if (apiKeys.github) synclet.authurl = "https://github.com/login/oauth/authorize?client_id=" + apiKeys.github.appKey + '&response_type=code&redirect_uri=' + host + 'auth/github/auth';
        }
    }
}<commit_msg>https for integral<commit_after>var fs = require('fs')
  , path = require('path')
  , lconfig = require("lconfig")
  , spawn = require('child_process').spawn
  , datastore
  , async = require('async')
  , lutil = require('lutil')
  , EventEmitter = require('events').EventEmitter
  ;

var synclets = {
    available:[],
    installed:{}
};

exports.eventEmitter = new EventEmitter();

exports.synclets = function() {
  return synclets;
};

/**
* Scans the Me directory for instaled synclets
*/
exports.findInstalled = function (callback) {
    if (!path.existsSync(lconfig.me)) fs.mkdirSync(lconfig.me, 0755);
    var dirs = fs.readdirSync(lconfig.me);
    for (var i = 0; i < dirs.length; i++) {
        var dir =  lconfig.me + "/" + dirs[i];
        try {
            if(!fs.statSync(dir).isDirectory()) continue;
            if(!path.existsSync(dir+'/me.json')) continue;
            var js = JSON.parse(fs.readFileSync(dir+'/me.json', 'utf-8'));
            if (js.synclets) {
                console.log("Loaded synclets for "+js.id);
                synclets.installed[js.id] = js;
                synclets.installed[js.id].status = "waiting";
                for (var j = 0; j < js.synclets.length; j++) {
                    scheduleRun(js, js.synclets[j]);
                }
            }
        } catch (E) {
            console.log("Me/"+dirs[i]+" does not appear to be a synclet (" +E+ ")");
        }
    }
}

exports.scanDirectory = function(dir) {
    datastore = require('./synclet/datastore');
    var files = fs.readdirSync(dir);
    for (var i = 0; i < files.length; i++) {
        var fullPath = dir + '/' + files[i];
        var stats = fs.statSync(fullPath);
        if(stats.isDirectory()) {
            exports.scanDirectory(fullPath);
            continue;
        }
        if (RegExp("\\.synclet$").test(fullPath)) {
            mapMetaData(fullPath);
        }
    }
    addUrls();
}

/**
* Install a synclet
*/
exports.install = function(metaData) {
    var serviceInfo;
    synclets.available.some(function(svcInfo) {
        if (svcInfo.srcdir == metaData.srcdir) {
            serviceInfo = {};
            for(var a in svcInfo){serviceInfo[a]=svcInfo[a];}
            serviceInfo.auth = metaData.auth;
            return true;
        }
        return false;
    });
    if (!serviceInfo) return serviceInfo;

    // local/internal name for the service on disk and whatnot, try to make it more friendly to devs/debugging
    if(serviceInfo.provider) {
        var inc = 0;
        if (path.existsSync(path.join(lconfig.lockerDir, lconfig.me, serviceInfo.provider))) {
            inc++;
            while (path.existsSync(path.join(lconfig.lockerDir, lconfig.me, serviceInfo.provider + '-' + inc))) inc++;
            serviceInfo.id = serviceInfo.provider + "-" + inc;
        } else {
            serviceInfo.id = serviceInfo.provider;
        }
    } else {
        throw "invalid synclet, has no provider";
    }
    synclets.installed[serviceInfo.id] = serviceInfo;
    fs.mkdirSync(path.join(lconfig.lockerDir, lconfig.me, serviceInfo.id),0755);
    fs.writeFileSync(path.join(lconfig.lockerDir, lconfig.me, serviceInfo.id, 'me.json'),JSON.stringify(serviceInfo, null, 4));
    for (var i = 0; i < serviceInfo.synclets.length; i++) {
        scheduleRun(serviceInfo, serviceInfo.synclets[i]);
    }
    return serviceInfo;
}

exports.isInstalled = function(serviceId) {
    return serviceId in synclets.installed;
}

exports.status = function(serviceId) {
    return synclets.installed[serviceId];
};

exports.syncNow = function(serviceId, callback) {
    if (!synclets.installed[serviceId]) return callback("no service like that installed");
    async.forEach(synclets.installed[serviceId].synclets, function(synclet, cb) { executeSynclet(synclets.installed[serviceId], synclet, cb); }, callback);
};

/**
* Add a timeout to run a synclet
*/
function scheduleRun(info, synclet) {
    // TODO if there is a .nextRun and it's past-due, run it now!
    synclet.nextRun = new Date(Date.now() + (parseInt(synclet.frequency) * 1000));
    setTimeout(function() {
        executeSynclet(info, synclet);
    }, parseInt(synclet.frequency) * 1000);
};

/**
* Executes a synclet
*/
function executeSynclet(info, synclet, callback) {
    if (synclet.status === 'running') {
        if (callback) {
            callback('already running');
        }
        return;
    }
    console.log("Synclet "+synclet.name+" starting for "+info.id);
    info.status = synclet.status = "running";
    if (!synclet.run) {
        run = ["node", lconfig.lockerDir + "/Common/node/synclet/client.js"];
    } else {
        run = ["node", path.join(lconfig.lockerDir, info.srcdir, synclet.run)];
    }

    var dataResponse = '';

    app = spawn(run.shift(), run, {cwd: path.join(lconfig.lockerDir, info.srcdir)});

    app.stderr.on('data', function (data) {
        var mod = console.outputModule;
        console.outputModule = info.title+" "+synclet.name;
        console.error(data.toString());
        console.outputModule = mod;
    });

    app.stdout.on('data',function (data) {
        dataResponse += data;
    });

    app.on('exit', function (code,signal) {
        var response;
        try {
            response = JSON.parse(dataResponse);
        } catch (E) {
            console.error(E);
            console.error(dataResponse);
            info.status = synclet.status = 'failed : ' + E;
            if (callback) callback(E);
            return;
        }
        console.log("Synclet "+synclet.name+" finished for "+info.id);
        info.status = synclet.status = 'processing data';
        tempInfo = JSON.parse(fs.readFileSync(path.join(lconfig.lockerDir, lconfig.me, info.id, 'me.json')));
        var deleteIDs = compareIDs(info.config, response.config);
        processResponse(deleteIDs, info, synclet, response, callback);
        info.config = lutil.extend(tempInfo.config, response.config);
        fs.writeFileSync(path.join(lconfig.lockerDir, lconfig.me, info.id, 'me.json'), JSON.stringify(info, null, 4));
        scheduleRun(info, synclet);
    });
    if (!info.config) info.config = {};

    info.syncletToRun = synclet;
    info.syncletToRun.workingDirectory = path.join(lconfig.lockerDir, lconfig.me, info.id);
    app.stdin.write(JSON.stringify(info)+"\n"); // Send them the process information
    delete info.syncletToRun;
};

function compareIDs (originalConfig, newConfig) {
    var resp = {};
    if (originalConfig.ids && newConfig.ids) {
        for (var i in newConfig.ids) {
            if (!originalConfig.ids[i]) break;
            var newSet = newConfig.ids[i];
            var oldSet = originalConfig.ids[i];
            seenIDs = {};
            resp[i] = [];
            for (var j = 0; j < newSet.length; j++) seenIDs[newSet[j]] = true;
            for (var j = 0; j < oldSet.length; j++) {
                if (!seenIDs[oldSet[j]]) resp[i].push(oldSet[j]);
            }
        }
    }
    return resp;
}
function processResponse(deleteIDs, info, synclet, response, callback) {
    datastore.init(function() {
        info.status = synclet.status = 'waiting';

        if (!callback) {
            callback = function() {};
        }
        var dataKeys = [];
        for (var i in response.data) {
            dataKeys.push(i);
        }
        for (var i in deleteIDs) {
            if (!dataKeys[i]) dataKeys.push(i);
        }
        async.forEach(dataKeys, function(key, cb) { processData(deleteIDs[key], info, key, response.data[key], cb); }, callback);
    });
};

function processData (deleteIDs, info, key, data, callback) {
    // console.error(deleteIDs);
    var collection = info.id + "_" + key;
    var eventType = key + "/" + info.provider;

    if (key.indexOf('/') !== -1) {
        collection = info.id + "_" + key.substring(key.indexOf('/') + 1);
        eventType = key.substring(0, key.indexOf('/')) + "/" + info.provider;
        key = key.substring(key.indexOf('/') + 1);
    }

    if (info.mongoId) {
        datastore.addCollection(key, info.id, info.mongoId);
    } else {
        datastore.addCollection(key, info.id, "id");
    }

    if (deleteIDs && deleteIDs.length > 0 && data) {
        addData(collection, data, info, eventType, function() {
            deleteData(collection, deleteIDs, info, eventType, callback);
        });
    } else if (data) {
        addData(collection, data, info, eventType, callback);
    } else if (deleteIDs && deleteIDs.length > 0) {
        deleteData(collection, deleteIDs, info, eventType, callback);
    } else {
        callback();
    }
}

function deleteData (collection, deleteIds, info, eventType, callback) {
    async.forEach(deleteIds, function(id, cb) {
        var newEvent = {obj : {source : eventType, type: 'delete', data : {}}};
        newEvent.obj.data[info.mongoId] = id;
        newEvent.fromService = "synclet/" + info.id;
        exports.eventEmitter.emit(eventType, newEvent);
        datastore.removeObject(collection, id, {timeStampe: Date.now()}, cb);
    }, callback);
}

function addData (collection, data, info, eventType, callback) {
    async.forEach(data, function(object, cb) {
        var newEvent = {obj : {source : collection, type: object.type, data: object.obj}};
        newEvent.fromService = "synclet/" + info.id;
        if (object.type === 'delete') {
            datastore.removeObject(collection, object.obj[info.mongoId], {timeStamp: object.timestamp}, cb);
            exports.eventEmitter.emit(eventType, newEvent);
        } else {
            datastore.addObject(collection, object.obj, {timeStamp: object.timestamp}, function(err, type) {
                if (type === 'same') return cb();
                newEvent.obj.type = type;
                exports.eventEmitter.emit(eventType, newEvent);
                cb();
            });
        }
    }, callback);
}
/**
* Map a meta data file JSON with a few more fields and make it available
*/
function mapMetaData(file) {
    var metaData = JSON.parse(fs.readFileSync(file, 'utf-8'));
    metaData.srcdir = path.dirname(file);
    synclets.available.push(metaData);
    return metaData;
}

function addUrls() {
    var apiKeys;
    var host;
    if (lconfig.externalSecure) {
        host = "https://";
    } else {
        host = "http://";
    }
    host += lconfig.externalHost + ":" + lconfig.externalPort + "/";
    try {
        apiKeys = JSON.parse(fs.readFileSync(path.join(lconfig.lockerDir, lconfig.me, "apikeys.json"), 'ascii'));
    } catch(e) {
        return console.log('Error reading apikeys.json file - ' + e);
    }
    for (var i = 0; i < synclets.available.length; i++) {
        synclet = synclets.available[i];
        if (synclet.provider === 'facebook') {
            if (apiKeys.facebook) synclet.authurl = "https://graph.facebook.com/oauth/authorize?client_id=" + apiKeys.facebook.appKey + '&response_type=code&redirect_uri=' + host + "auth/facebook/auth&scope=email,offline_access,read_stream,user_photos,friends_photos,publish_stream,user_photo_video_tags";
        } else if (synclet.provider === 'twitter') {
            if (apiKeys.twitter) synclet.authurl = host + "auth/twitter/auth";
        } else if (synclet.provider === 'foursquare') {
            if (apiKeys.foursquare) synclet.authurl = "https://foursquare.com/oauth2/authenticate?client_id=" + apiKeys.foursquare.appKey + "&response_type=code&redirect_uri=" + host + "auth/foursquare/auth";
        } else if (synclet.provider === 'gcontacts') {
            if (apiKeys.gcontacts) synclet.authurl = "https://accounts.google.com/o/oauth2/auth?client_id=" + apiKeys.gcontacts.appKey + "&redirect_uri=" + host + "auth/gcontacts/auth&scope=https://www.google.com/m8/feeds/&response_type=code";
        } else if (synclet.provider === 'github') {
            if (apiKeys.github) synclet.authurl = "https://github.com/login/oauth/authorize?client_id=" + apiKeys.github.appKey + '&response_type=code&redirect_uri=' + host + 'auth/github/auth';
        }
    }
}<|endoftext|>


<commit_before>var path = process.argv[2]
if (!path) {
   console.log("Please specify a path")
   return
}

require.main.__mainComponentPath = path
var result = require('maker')._o(module)(path)
if (result._init) {
    result._init(process.argv.slice(3))
}

console.log(result)

// yargs
// can print usage (we should gen)
// can give example (gen?)
// describe (can desribe opts)
// can require opts
// can set defaults
// can require num args
// can mark as boolean
// can alias
// long and short
// count -vvv
//

<commit_msg>renamed<commit_after><|endoftext|>


<commit_before>verb = "verb"
direction = "direction"
inverse_direction = "inv"
item = "item"
nil = "nil"
person = "person"
obj = "object"
abstract = "abstract"
here = "here"
words = {}

words.food = {type: abstract}
words.container = {type: abstract}
words.sittable = {type: abstract}
words.readable = {type: abstract}
words.movable = {type: abstract}

words.walk = {type:verb, eat : "to", method: "move"}
words.move = {type: verb, method: "move_obj", synonym: words.walk}
words.stumble = {type:verb, synonym: words.walk}
words.run = {type:verb, synonym: words.walk}
words.head = {type:verb, synonym: words.walk}
words.go = {type:verb, synonym: words.walk, method: "move"}
words.jump = {type:verb, method: "move"}

words.kill = {type:verb, method: "kill"}

words.examine = {type:verb, method : "examine"}
words.read = {type:verb, method: "read"}

words.help = {type: verb, method : "help"}
words.assist = {type:verb, synonym: words.help, method: "assist"}

words.stand = {type: verb, method: "stand", eat: "up"}
words.lie = {type: verb, method: "lie", eat: "down"}
words.sit = {type: verb, eat: "down", method: "sit"}

words.grab = {type:verb, method: "pickup"}
words.pick = {type: verb, eat: "up", synonym : words.grab}
words.take = {type: verb, synonym: words.grab}

words.open = {type: verb, method: "open"}
words.close = {type: verb, method: "close"}

words.brush = {type: verb, method : "brush"}

words.turn = {type: verb, eat: "on", method: "turn_lights"}

words.eat = {type: verb, method: "eat"}

words.east = {type:direction}
words.north = {type:direction}
words.south = {type:direction}
words.west = {type:direction}

words.up = {type:direction}
words.down = {type:direction}
words.away = {type: inverse_direction}

words.here = {type: here}
words.hall = {type: here}
words.room = {type: here}

words.from = {type: nil}
words.in = {type: nil}
words.on = {type: nil}

words.bed = {type: obj, is_a: words.sittable}
words.blackboard = {type: obj}
words.buttons = {type:obj, synonym: words.panel}
words.cabinet = {type: obj}
words.chair = {type: obj, is_a: words.sittable}
words.clock = {type: obj}
words.countertop = {type: obj}
words.dial = {type: obj}
words.desk = {type:obj}
words.drawer = {type:obj, is_a: words.container}
words.lights = {type: obj}
words.light = {type: obj, synonym: words.lights}
words.painting = {type: obj, is_a: words.movable}
words.panel = {type:obj}
words.porkchops = {type: obj, is_a: words.food}
words.rubbish = {type: obj}
words.safe = {type: obj, is_a: words.container}
words.sink = {type: obj}
words.stove = {type: obj}
words.table = {type: obj}
words.teeth = {type: obj}
words.telephone = {type:obj }
words.window = {type: obj}

words.coin = {type: item}
words.documents = {type: item}
words.knife = {type:item}
words.newspaper = {type:item, is_a: words.readable}
words.parachute = {type: item, is_a: words.container}
words.pen = {type:item}

words.toothbrush = {type: item, long_name : "dirty toothbrush"}
words.towel = {type : item}

words.key = {type: abstract}
words.copper = {type : item, eat: "key", long_name : "copper key", is_a : words.key}
words.small = {type: item, eat: "key", long_name: "small key", is_a: words.key}
words.master = {type: item, eat: "key", long_name: "master key", is_a: words.key} // no description

// Secretary
words.secretary = {type: person}

for (var key in words) {
  	if (words.hasOwnProperty(key)) {
  		words[key].text = key
  	}
}

function get_text (w)
{
	if(w.long_name)
		return w.long_name
	return w.text
}
// @requires: w is of type words.(...)
function get_article(w) {
	var item = get_text(w)
	var article = "a "
	if ("aeiou".indexOf(item[0]) >= 0) {
		article = "an "
	}
	return article
}
object_reaction = {}
object_reaction.toothbrush = {examine: ["",
		"It is probably mine."],
	 pickup: ["",
	 	 "Did I brush my teeth yesterday?
 Come to think of it, what day is it?"]}
object_reaction.teeth = {examine: ["",
		"I should clean them more often."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.clock = {examine: ["",
		"It tells  the time."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.towel = {examine: ["",
		"It's a towel."],
	 pickup: ["",
	 	 "I now have a towel"]}
object_reaction.copper = {examine: ["The label states it can be used to open the staff area on floor 14.",
		""],
	 pickup: ["",
	 	 "I found a copper key."]}
object_reaction.bed = {examine: ["",
		"It is a bed.
 It doesn't look very comfortable."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.window = {examine: ["You look out the window and see a city you don't recognize.",
		"The people look like ants from up here."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.porkchops = {examine: ["These are cooked porkchops.",
		"Did I... cook this?
It looks tasty."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.knife = {examine: ["It is a fairly large kitchen knife.",
		""],
	 pickup: ["You picked up a knife.",
	 	 "This knife feels familiar."]}
object_reaction.stove = {examine: ["It is a gas stove used for cooking.",
		"It is still warm..."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.countertop = {examine: ["It is a countertop used for cooking.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.panel = {examine: ["A panel with numbered buttons used to operate the elevator. Every button has a small keyhole next to it.",
		"Strange, the number 13 is missing..."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.dial = {examine: ["A dial with the numbers 1 to 14. It has a pointer that indicates which floor you are currently on.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.small = {examine: ["A small key with a label that reads: floors 12 - 14",
		""],
	 pickup: ["You obtained a small key",
	 	 ""]}
object_reaction.desk = {examine: ["It is a handcarved oaken desk that looks slightly worn. There is one unlocked drawer.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.drawer = {examine: ["A closed drawer.",
		"I can't see into a closed drawer."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.newspaper = {examine: ["It's a newspaper dated Friday the 27th of June 1969.",
		"At least I know the date now."],
	 pickup: ["You pick up the newspaper.",
	 	 ""],
	 read: ["Violent Serial Killer Miraculously Cured",
	 	 "At the Mercy Mental Hospital the notorious serial killer nicknamed 'The Arbitrator', is reported to have been cured after receiving extensive shock therapy. Currently still residing there, The Arbitrator is showing no signs of murderous intent according to Wolfram Switzer, head of Mercy Mental Hospital..."]}
object_reaction.chair = {examine: ["It's a chair. You can sit on it.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.table = {examine: ["It's a wooden table.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.rubbish = {examine: ["Useless pieces of paper and other trash.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.painting = {examine: ["It's a beautiful painting, realistically depicting lilacs in a vase. It is quite bleak however.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.safe = {examine: ["It's a locked safe.",
		"Unfortunately, nobody put the code on a post-it note."],
	 pickup: ["",
	 	 "Am I a hacker??"]}

<commit_msg>safe room<commit_after>verb = "verb"
direction = "direction"
inverse_direction = "inv"
item = "item"
nil = "nil"
person = "person"
obj = "object"
abstract = "abstract"
here = "here"
words = {}

words.food = {type: abstract}
words.container = {type: abstract}
words.sittable = {type: abstract}
words.readable = {type: abstract}
words.movable = {type: abstract}

words.walk = {type:verb, eat : "to", method: "move"}
words.move = {type: verb, method: "move_obj", synonym: words.walk}
words.stumble = {type:verb, synonym: words.walk}
words.run = {type:verb, synonym: words.walk}
words.head = {type:verb, synonym: words.walk}
words.go = {type:verb, synonym: words.walk, method: "move"}
words.jump = {type:verb, method: "move"}

words.kill = {type:verb, method: "kill"}

words.examine = {type:verb, method : "examine"}
words.read = {type:verb, method: "read"}

words.help = {type: verb, method : "help"}
words.assist = {type:verb, synonym: words.help, method: "assist"}

words.stand = {type: verb, method: "stand", eat: "up"}
words.lie = {type: verb, method: "lie", eat: "down"}
words.sit = {type: verb, eat: "down", method: "sit"}

words.grab = {type:verb, method: "pickup"}
words.pick = {type: verb, eat: "up", synonym : words.grab}
words.take = {type: verb, synonym: words.grab}

words.open = {type: verb, method: "open"}
words.close = {type: verb, method: "close"}

words.brush = {type: verb, method : "brush"}

words.turn = {type: verb, eat: "on", method: "turn_lights"}

words.eat = {type: verb, method: "eat"}

words.east = {type:direction}
words.north = {type:direction}
words.south = {type:direction}
words.west = {type:direction}

words.up = {type:direction}
words.down = {type:direction}
words.away = {type: inverse_direction}

words.here = {type: here}
words.hall = {type: here}
words.room = {type: here}

words.from = {type: nil}
words.in = {type: nil}
words.on = {type: nil}

words.bed = {type: obj, is_a: words.sittable}
words.blackboard = {type: obj}
words.buttons = {type:obj, synonym: words.panel}
words.cabinet = {type: obj}
words.chair = {type: obj, is_a: words.sittable}
words.clock = {type: obj}
words.countertop = {type: obj}
words.dial = {type: obj}
words.desk = {type:obj}
words.drawer = {type:obj, is_a: words.container}
words.lights = {type: obj}
words.light = {type: obj, synonym: words.lights}
words.painting = {type: obj, is_a: words.movable}
words.panel = {type:obj}
words.porkchops = {type: obj, is_a: words.food}
words.rubbish = {type: obj}
words.safe = {type: obj, is_a: words.container}
words.sink = {type: obj}
words.stove = {type: obj}
words.table = {type: obj}
words.teeth = {type: obj}
words.telephone = {type:obj }
words.window = {type: obj}

words.coin = {type: item}
words.documents = {type: item}
words.knife = {type:item}
words.newspaper = {type:item, is_a: words.readable}
words.parachute = {type: item, is_a: words.container}
words.pen = {type:item}

words.toothbrush = {type: item, long_name : "dirty toothbrush"}
words.towel = {type : item}

words.key = {type: abstract}
words.copper = {type : item, eat: "key", long_name : "copper key", is_a : words.key}
words.small = {type: item, eat: "key", long_name: "small key", is_a: words.key}
words.master = {type: item, eat: "key", long_name: "master key", is_a: words.key} // no description

// Secretary
words.secretary = {type: person}

for (var key in words) {
  	if (words.hasOwnProperty(key)) {
  		words[key].text = key
  	}
}

function get_text (w)
{
	if(w.long_name)
		return w.long_name
	return w.text
}
// @requires: w is of type words.(...)
function get_article(w) {
	var item = get_text(w)
	var article = "a "
	if ("aeiou".indexOf(item[0]) >= 0) {
		article = "an "
	}
	return article
}
object_reaction = {}
object_reaction.toothbrush = {examine: ["",
		"It is probably mine."],
	 pickup: ["",
	 	 "Did I brush my teeth yesterday?
 Come to think of it, what day is it?"]}
object_reaction.teeth = {examine: ["",
		"I should clean them more often."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.clock = {examine: ["",
		"It tells  the time."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.towel = {examine: ["",
		"It's a towel."],
	 pickup: ["",
	 	 "I now have a towel"]}
object_reaction.copper = {examine: ["The label states it can be used to open the staff area on floor 14.",
		""],
	 pickup: ["",
	 	 "I found a copper key."]}
object_reaction.bed = {examine: ["",
		"It is a bed.
 It doesn't look very comfortable."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.window = {examine: ["You look out the window and see a city you don't recognize.",
		"The people look like ants from up here."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.porkchops = {examine: ["These are cooked porkchops.",
		"Did I... cook this?
It looks tasty."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.knife = {examine: ["It is a fairly large kitchen knife.",
		""],
	 pickup: ["You picked up a knife.",
	 	 "This knife feels familiar."]}
object_reaction.stove = {examine: ["It is a gas stove used for cooking.",
		"It is still warm..."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.countertop = {examine: ["It is a countertop used for cooking.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.panel = {examine: ["A panel with numbered buttons used to operate the elevator. Every button has a small keyhole next to it.",
		"Strange, the number 13 is missing..."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.dial = {examine: ["A dial with the numbers 1 to 14. It has a pointer that indicates which floor you are currently on.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.small = {examine: ["A small key with a label that reads: floors 12 - 14",
		""],
	 pickup: ["You obtained a small key",
	 	 ""]}
object_reaction.desk = {examine: ["It is a handcarved oaken desk that looks slightly worn. There is one unlocked drawer.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.drawer = {examine: ["A closed drawer.",
		"I can't see into a closed drawer."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.newspaper = {examine: ["It's a newspaper dated Friday the 27th of June 1969.",
		"At least I know the date now."],
	 pickup: ["You pick up the newspaper.",
	 	 ""],
	 read: ["Violent Serial Killer Miraculously Cured",
	 	 "At the Mercy Mental Hospital the notorious serial killer nicknamed 'The Arbitrator', is reported to have been cured after receiving extensive shock therapy. Currently still residing there, The Arbitrator is showing no signs of murderous intent according to Wolfram Switzer, head of Mercy Mental Hospital..."]}
object_reaction.chair = {examine: ["It's a chair. You can sit on it.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.table = {examine: ["It's a wooden table.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.rubbish = {examine: ["Useless pieces of paper and other trash.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.painting = {examine: ["It's a beautiful painting, realistically depicting lilacs in a vase. It is quite bleak however.",
		""],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.safe = {examine: ["It's a locked safe.",
		"Unfortunately, nobody put the code on a post-it note."],
	 pickup: ["",
	 	 "Am I a hacker??"]}
object_reaction.parachute = {examine: ["Used to safely descend from a high altitude.",
		""],
	 pickup: ["You picked up the parachute.",
	 	 ""]}

<|endoftext|>


<commit_before>var Funnel = require('broccoli-funnel');
var Rollup = require('broccoli-rollup');
var JSHint = require('broccoli-jshint');
var TypeScript = require('broccoli-typescript-compiler').TypeScript;
var TSLint = require('broccoli-tslinter');
var MergeTrees = require('broccoli-merge-trees');
var concat = require('broccoli-concat');

module.exports = function(/* defaults */) {
  var srcJS = new Funnel('src', {
    include: ['**/*.js'],
    destDir: '/src'
  });

  var srcTS = new Funnel('src', {
    include: ['**/*.ts'],
    destDir: '/src'
  });

  var transpiledSrcTs = new TypeScript(srcTS, {
    tsconfig: {
      compilerOptions: {
        module: 'es6',
        moduleResolution: 'node',
        target: 'es5',
        newLine: 'LF',
        declaration: true,
        strictNullChecks: true,
        inlineSourceMap: true,
        inlineSources: true
      },
      include: ['**/*']
    }
  });

  var src = new MergeTrees([srcJS, transpiledSrcTs]);

  var es6 = new Funnel(src, {
    srcDir: '/src',
    destDir: '/es6'
  });

  var bundled = new Rollup(src, {
    rollup: {
      entry: 'src/index.js',

      sourceMap: true,
      dest: 'simple-html-tokenizer.js',
      format: 'umd',
      moduleName: 'HTML5Tokenizer'
    }
  });

  var tests = new Funnel('tests', {
    files: ['tokenizer-tests.js'],
    destDir: '/tests'
  });

  var srcJSHint = new JSHint(srcJS);
  var testsJSHint = new JSHint(tests);
  var srcTSLint = new TSLint(srcTS);

  var allTests = concat(new MergeTrees([tests, srcJSHint, testsJSHint, srcTSLint]), {
    outputFile: '/tests/tests.js',
    inputFiles: ['**/*.js', '**/*.ts'],
  });

  var testSupport = new Funnel('tests', {
    files: ['index.html'],
    destDir: '/tests'
  });

  var qunit = new Funnel('node_modules/qunitjs', {
    srcDir: 'qunit',
    files: ['qunit.js', 'qunit.css'],
    destDir: '/tests'
  });

  return new MergeTrees([bundled, es6, allTests, testSupport, qunit]);
};
<commit_msg>Clean up JS-specific steps in ember-cli-build.js<commit_after>var Funnel = require('broccoli-funnel');
var Rollup = require('broccoli-rollup');
var JSHint = require('broccoli-jshint');
var TypeScript = require('broccoli-typescript-compiler').TypeScript;
var TSLint = require('broccoli-tslinter');
var MergeTrees = require('broccoli-merge-trees');
var concat = require('broccoli-concat');

module.exports = function(/* defaults */) {
  var srcTS = new Funnel('src', {
    destDir: '/src'
  });

  var src = new TypeScript(srcTS, {
    tsconfig: {
      compilerOptions: {
        module: 'es6',
        moduleResolution: 'node',
        target: 'es5',
        newLine: 'LF',
        declaration: true,
        strictNullChecks: true,
        inlineSourceMap: true,
        inlineSources: true
      },
      include: ['**/*']
    }
  });

  var es6 = new Funnel(src, {
    srcDir: '/src',
    destDir: '/es6'
  });

  var bundled = new Rollup(src, {
    rollup: {
      entry: 'src/index.js',

      sourceMap: true,
      dest: 'simple-html-tokenizer.js',
      format: 'umd',
      moduleName: 'HTML5Tokenizer'
    }
  });

  var tests = new Funnel('tests', {
    files: ['tokenizer-tests.js'],
    destDir: '/tests'
  });

  var testsJSHint = new JSHint(tests);
  var srcTSLint = new TSLint(srcTS);

  var allTests = concat(new MergeTrees([tests, testsJSHint, srcTSLint]), {
    outputFile: '/tests/tests.js',
    inputFiles: ['**/*.js', '**/*.ts'],
  });

  var testSupport = new Funnel('tests', {
    files: ['index.html'],
    destDir: '/tests'
  });

  var qunit = new Funnel('node_modules/qunitjs', {
    srcDir: 'qunit',
    files: ['qunit.js', 'qunit.css'],
    destDir: '/tests'
  });

  return new MergeTrees([bundled, es6, allTests, testSupport, qunit]);
};
<|endoftext|>


<commit_before>"use strict";

Object.defineProperty(exports, "__esModule", {
    value: true
});
exports.buildContainer = buildContainer;
exports.findParentElement = findParentElement;
exports.renderAll = renderAll;
function buildContainer(value) {
    var str = typeof value === "string" ? value : value[0];
    var n = typeof value === "string" ? 0 : value[1];

    if (str.split("")[0] === ".") {
        return document.getElementsByClassName(str.slice(1))[n];
    }
    if (str.split("")[0] === "#") {
        return document.getElementById(str.slice(1));
    }
}

function findParentElement(lineNum, currentLine, elementsArray) {
    for (var i = lineNum - 1; i > 0; i -= 1) {
        if (elementsArray[i].indents < currentLine.indents) {
            currentLine.parent = elementsArray[i].element;
            break;
        }
    }
}

function renderAll(elementsArray, containerParent) {
    for (var lineNum = 0; lineNum < elementsArray.length; lineNum += 1) {
        var currentLine = elementsArray[lineNum];

        // Determine the parent line of the current one.
        currentLine.indents > 0 ? findParentElement(lineNum, currentLine, elementsArray) : currentLine.parent = containerParent;

        // Render current line inside it's parent
        currentLine.parent.insertBefore(currentLine.element, null);
    }
}<commit_msg>Delete handleRendering.js<commit_after><|endoftext|>


<commit_before>/*global
 define
 */
/*jslint
 browser: true,
 white: true
 */
define([], function () {
    'use strict';
    function createElement(name) {
        return document.createElement(name);
    }
    function appendRoot(child) {
        document.appendChild(child);
    }
    function append(parent, child) {
        return parent.appendChild(child);
    }
    function remove(parent, child) {
        return parent.removeChild(child);
    }
    function findById(id) {
        return document.getElementById(id);
    }
    function nodeForId(id) {
        return document.getElementById(id);
    }
    function qs(selector) {
        return document.querySelector(selector);
    }
    function qsa(selector) {
        var result = document.querySelectorAll(selector);
        if (result === null) {
            return [];
        }
        return Array.prototype.slice.call(result);
    }
    function setHtml(nodeOrSelector, content) {
        var node;
        if (typeof nodeOrSelector === 'string') {
            node = qs(nodeOrSelector);
            if (node === null) {
                throw new Error('No node found for selector "' + nodeOrSelector + '"');
            }
        } else {
            node = nodeOrSelector;
        }
        node.innerHTML = content;
        return node;
    }

    return {
        createElement: createElement,
        appendRoot: appendRoot,
        append: append,
        remove: remove,
        setHTML: setHtml,
        setHtml: setHtml,
        findById: findById,
        nodeForId: nodeForId,
        getById: findById,
        qs: qs,
        qsa: qsa
    };
});<commit_msg>qs and qsa can not take a node as first argument, otherwise defaults to document (previous behavior).<commit_after>/*global
 define
 */
/*jslint
 browser: true,
 white: true
 */
define([], function () {
    'use strict';
    function createElement(name) {
        return document.createElement(name);
    }
    function appendRoot(child) {
        document.appendChild(child);
    }
    function append(parent, child) {
        return parent.appendChild(child);
    }
    function remove(parent, child) {
        return parent.removeChild(child);
    }
    function findById(id) {
        return document.getElementById(id);
    }
    function nodeForId(id) {
        return document.getElementById(id);
    }
    function qs(node, selector) {
        if (selector === undefined) {
            selector = node;
            node = document;
        }
        return node.querySelector(selector);
    }
    function qsa(node, selector) {
        if (selector === undefined) {
            selector = node;
            node = document;
        }
        var result = node.querySelectorAll(selector);
        if (result === null) {
            return [];
        }
        return Array.prototype.slice.call(result);
    }
    function setHtml(nodeOrSelector, content) {
        var node;
        if (typeof nodeOrSelector === 'string') {
            node = qs(nodeOrSelector);
            if (node === null) {
                throw new Error('No node found for selector "' + nodeOrSelector + '"');
            }
        } else {
            node = nodeOrSelector;
        }
        node.innerHTML = content;
        return node;
    }

    return {
        createElement: createElement,
        appendRoot: appendRoot,
        append: append,
        remove: remove,
        setHTML: setHtml,
        setHtml: setHtml,
        findById: findById,
        nodeForId: nodeForId,
        getById: findById,
        qs: qs,
        qsa: qsa
    };
});<|endoftext|>


<commit_before>/* ***** BEGIN LICENSE BLOCK *****
 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
 *
 * The contents of this file are subject to the Mozilla Public License Version
 * 1.1 (the "License"); you may not use this file except in compliance with
 * the License. You may obtain a copy of the License at
 * http://www.mozilla.org/MPL/
 *
 * Software distributed under the License is distributed on an "AS IS" basis,
 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
 * for the specific language governing rights and limitations under the
 * License.
 *
 * The Original Code is infoRSS.
 *
 * The Initial Developer of the Original Code is
 *   Didier Ernotte <didier@ernotte.com>.
 * Portions created by the Initial Developer are Copyright (C) 2004
 * the Initial Developer. All Rights Reserved.
 *
 * Contributor(s):
 *   Didier Ernotte <didier@ernotte.com>.
 *
 * Alternatively, the contents of this file may be used under the terms of
 * either the GNU General Public License Version 2 or later (the "GPL"), or
 * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
 * in which case the provisions of the GPL or the LGPL are applicable instead
 * of those above. If you wish to allow use of your version of this file only
 * under the terms of either the GPL or the LGPL, and not to allow others to
 * use your version of this file under the terms of the MPL, indicate your
 * decision by deleting the provisions above and replace them with the notice
 * and other provisions required by the GPL or the LGPL. If you do not delete
 * the provisions above, a recipient may use your version of this file under
 * the terms of any one of the MPL, the GPL or the LGPL.
 *
 * ***** END LICENSE BLOCK ***** */
//------------------------------------------------------------------------------
// inforssMediator
// Author : Didier Ernotte 2005
// Inforss extension
//------------------------------------------------------------------------------
var inforss = inforss || {};
Components.utils.import("chrome://inforss/content/modules/inforss_Debug.jsm",
                        inforss);

//A LOT hacky. Hopefully this will be a module soon
/* eslint strict: "off" */

/* global inforssFeedManager */
/* global inforssHeadlineBar */
/* global inforssHeadlineDisplay */
/* global inforssXMLRepository */
/* global inforssClearPopupMenu */
/* global inforssAddNewFeed */

const ObserverService = Components.classes[
  "@mozilla.org/observer-service;1"].getService(
  Components.interfaces.nsIObserverService);

//FIXME get rid of all the 2 phase initialisation

//FIXME Not terribly happy about using the observer service for the addFeed
//window.
//It is not at all clear why this needs to use the observer service.
//There's only one client to each message.

/** This class contains the single feed manager, headline bar and headline
 * display objects, and allows them to communicate with one another.
 *
 * it also exists as a singleton used in inforss and the option window, which
 * last gets hold of it by poking around in the parent window properties.
 *
 * The observer method allows for the addfeed popup to communicate.
 */

function inforssMediator()
{
  this.feedManager = new inforssFeedManager(this);
  this.headlineBar = new inforssHeadlineBar(this);
  this.headlineDisplay = new inforssHeadlineDisplay(
    this,
    document.getElementById("inforss.newsbox1")
  );
  this._register();
  //fIXME why???
  this._reinit_after(1200);
  return this;
}

inforssMediator.prototype = {

  //----------------------------------------------------------------------------
  _init()
  {
    inforss.traceIn(this);
    try
    {
      this.feedManager.init();
      this.headlineDisplay.init();
    }
    catch (e)
    {
      inforss.debug(e, this);
    }
    inforss.traceOut(this);
  },

  //----------------------------------------------------------------------------
  //FIXME We need this because we need it but why on earth do we need it in the
  //first place?
  _reinit_after(timeout)
  {
    window.setTimeout(this._init.bind(this), timeout);
  },

  /** Registers with observer service */
  _register()
  {
    ObserverService.addObserver(this, "addNewFeed", false);
  },

  /** Deregisters from observer service on shutdown */
  deregister()
  {
    ObserverService.removeObserver(this, "addNewFeed");
  },

  /** API for observer service
   *
   * @param {nsISupports} subject - as defined in nsIObserverService
   * @param {string} topic - as defined in nsIObserverService
   * @param {wstring} data - as defined in nsIObserverService
   */
  observe(subject, topic, data)
  {
    try
    {
      switch (topic)
      {
        case "inforss.addNewFeed":
          inforssAddNewFeed({ inforssUrl: data });
          break;

        default:
          inforss.debug("Unknown mediator event", subject, topic, data);
      }
    }
    catch (e)
    {
      inforss.debug(e);
    }
  },

  /** Reload (seriously?)
   *
   * Deletes the supplied feeds and reinitialises headline bar and feed manager
   *
   * @param {array} deleted_feeds - array of feed urls to delete
   */
  reload(deleted_feeds = [])
  {
    for (let url of deleted_feeds)
    {
      this.deleteRss(url);
    }
    inforssClearPopupMenu();
    this._reinit_after(0);
  },

  /** Configuration was reset */
  configuration_reset()
  {
    this.feedManager.deleteAllRss();
    inforssClearPopupMenu();
    this._reinit_after(0);
  },

  /** Set a headline as viewed
   *
   * @param {string} title - title of headline
   * @param {string} link - url of headline
   */
  set_viewed(title, link)
  {
    this.headlineBar.setViewed(title, link);
  },

  /** Set a headline as banned
   *
   * @param {string} title - title of headline
   * @param {string} link - url of headline
   */
  set_banned(title, link)
  {
    this.headlineBar.setBanned(title, link);
  },

  /** Reload headline cache from disk */
  reload_headline_cache()
  {
    this.feedManager.reload_headline_cache();
  },

  /** Clear headline cache */
  clear_headline_cache()
  {
    this.feedManager.clear_headline_cache();
  },

  /** Purge old headlines from the headline cache */
  purge_headline_cache()
  {
    this.feedManager.purge_headline_cache();
  },

  //----------------------------------------------------------------------------
  updateBar(feed)
  {
    this.headlineBar.updateBar(feed);
  },

  //----------------------------------------------------------------------------
  updateDisplay(feed)
  {
    this.headlineDisplay.updateDisplay(feed);
  },

  //----------------------------------------------------------------------------
  refreshBar()
  {
    this.headlineBar.refreshBar();
  },

  //----------------------------------------------------------------------------
  setSelected(url)
  {
    var changed = false;
    try
    {
      var selectedInfo = this.feedManager.getSelectedInfo(false);
      if (selectedInfo == null || url != selectedInfo.getUrl())
      {
        this.feedManager.setSelected(url);
        changed = true;
      }
    }
    catch (e)
    {
      inforss.debug(e, this);
    }
    return changed;
  },

  //----------------------------------------------------------------------------
  addFeed(feedXML, menuItem)
  {
    this.feedManager.addFeed(feedXML, menuItem);
  },

  //----------------------------------------------------------------------------
  getSelectedInfo(findDefault)
  {
    return this.feedManager.getSelectedInfo(findDefault);
  },

  //----------------------------------------------------------------------------
  resetDisplay()
  {
    this.headlineDisplay.resetDisplay();
  },

  //----------------------------------------------------------------------------
  resetHeadlines()
  {
    this.headlineBar.resetHeadlines();
  },

  //----------------------------------------------------------------------------
  deleteRss(url)
  {
    try
    {
      this.feedManager.deleteRss(url);
    }
    catch (e)
    {
      inforss.debug(e, this);
    }
  },

  //----------------------------------------------------------------------------
  resizedWindow()
  {
    this.headlineDisplay.resizedWindow();
  },

  //----------------------------------------------------------------------------
  publishFeed(feed)
  {
    this.headlineBar.publishFeed(feed);
  },

  //----------------------------------------------------------------------------
  unpublishFeed(feed)
  {
    this.headlineBar.unpublishFeed(feed);
  },

  //----------------------------------------------------------------------------
  getLastDisplayedHeadline()
  {
    return this.headlineBar.getLastDisplayedHeadline();
  },

  //----------------------------------------------------------------------------
  removeDisplay(feed)
  {
    this.headlineDisplay.removeDisplay(feed);
  },

  //----------------------------------------------------------------------------
  updateMenuIcon(feed)
  {
    this.headlineDisplay.updateMenuIcon(feed);
  },

  //----------------------------------------------------------------------------
  clickRSS(event, link)
  {
    this.headlineDisplay.clickRSS(event, link);
  },

  //----------------------------------------------------------------------------
  locateFeed(url)
  {
    return this.feedManager.locateFeed(url);
  },

  //----------------------------------------------------------------------------
  setScroll(flag)
  {
    this.headlineDisplay.setScroll(flag);
  },

  //----------------------------------------------------------------------------
  checkStartScrolling()
  {
    this.headlineDisplay.checkStartScrolling();
  },

  //----------------------------------------------------------------------------
  setActiveTooltip()
  {
    this.headlineDisplay.setActiveTooltip();
  },

  //----------------------------------------------------------------------------
  resetActiveTooltip()
  {
    this.headlineDisplay.resetActiveTooltip();
  },

  //----------------------------------------------------------------------------
  isActiveTooltip()
  {
    return this.headlineDisplay.isActiveTooltip();
  },

  //----------------------------------------------------------------------------
  readAll()
  {
    if (inforss.confirm(inforss.get_string("readall")))
    {
      this.headlineBar.readAll();
    }
  },

  //----------------------------------------------------------------------------
  openTab(url)
  {
    inforss.traceIn(this);
    try
    {
      this.headlineDisplay.openTab(url);
    }
    catch (e)
    {
      inforss.debug(e, this);
    }
    inforss.traceOut(this);
  },

  //----------------------------------------------------------------------------
  viewAll()
  {
    if (inforss.confirm(inforss.get_string("viewall")))
    {
      this.headlineBar.viewAll();
    }
  },

  //----------------------------------------------------------------------------
  switchScroll()
  {
    this.headlineDisplay.switchScroll();
  },

  //----------------------------------------------------------------------------
  quickFilter()
  {
    this.headlineDisplay.quickFilter();
  },

  //----------------------------------------------------------------------------
  switchShuffle()
  {
    //FIXME This should be done as a function in headlineDisplay
    inforssXMLRepository.switchShuffle();
    this.headlineDisplay.updateCmdIcon();
  },

  //----------------------------------------------------------------------------
  switchPause()
  {
    this.headlineDisplay.switchPause();
  },

  //----------------------------------------------------------------------------
  switchDirection()
  {
    this.headlineDisplay.switchDirection();
  },

  //----------------------------------------------------------------------------
  goHome()
  {
    this.feedManager.goHome();
  },

  //----------------------------------------------------------------------------
  manualRefresh()
  {
    this.feedManager.manualRefresh();
  },

  //----------------------------------------------------------------------------
  manualSynchronize()
  {
    //FIXME What's this for then?
    //    this.feedManager.manualRefresh();
  },

  //----------------------------------------------------------------------------
  toggleHideOld()
  {
    inforssXMLRepository.hide_old_headlines =
      ! inforssXMLRepository.hide_old_headlines;
    inforssXMLRepository.save();
    this.headlineBar.refreshBar();
  },

  //----------------------------------------------------------------------------
  toggleHideViewed()
  {
    inforssXMLRepository.hide_viewed_headlines =
      ! inforssXMLRepository.hide_viewed_headlines;
    inforssXMLRepository.save();
    this.headlineBar.refreshBar();
  },

  //----------------------------------------------------------------------------
  handleMouseScroll(direction)
  {
    this.headlineDisplay.handleMouseScroll(direction);
  },

  //----------------------------------------------------------------------------
  //This is called from the 'next' and 'previous' buttons as
  //gInfoRssMediator.nextFeed(-1 (prev) or 1(next))
  nextFeed(direction)
  {
    this.feedManager.getNextGroupOrFeed(direction);
  },

};
<commit_msg>Small cleanup<commit_after>/* ***** BEGIN LICENSE BLOCK *****
 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
 *
 * The contents of this file are subject to the Mozilla Public License Version
 * 1.1 (the "License"); you may not use this file except in compliance with
 * the License. You may obtain a copy of the License at
 * http://www.mozilla.org/MPL/
 *
 * Software distributed under the License is distributed on an "AS IS" basis,
 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
 * for the specific language governing rights and limitations under the
 * License.
 *
 * The Original Code is infoRSS.
 *
 * The Initial Developer of the Original Code is
 *   Didier Ernotte <didier@ernotte.com>.
 * Portions created by the Initial Developer are Copyright (C) 2004
 * the Initial Developer. All Rights Reserved.
 *
 * Contributor(s):
 *   Didier Ernotte <didier@ernotte.com>.
 *
 * Alternatively, the contents of this file may be used under the terms of
 * either the GNU General Public License Version 2 or later (the "GPL"), or
 * the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
 * in which case the provisions of the GPL or the LGPL are applicable instead
 * of those above. If you wish to allow use of your version of this file only
 * under the terms of either the GPL or the LGPL, and not to allow others to
 * use your version of this file under the terms of the MPL, indicate your
 * decision by deleting the provisions above and replace them with the notice
 * and other provisions required by the GPL or the LGPL. If you do not delete
 * the provisions above, a recipient may use your version of this file under
 * the terms of any one of the MPL, the GPL or the LGPL.
 *
 * ***** END LICENSE BLOCK ***** */
//------------------------------------------------------------------------------
// inforssMediator
// Author : Didier Ernotte 2005
// Inforss extension
//------------------------------------------------------------------------------
var inforss = inforss || {};
Components.utils.import("chrome://inforss/content/modules/inforss_Debug.jsm",
                        inforss);

//A LOT hacky. Hopefully this will be a module soon
/* eslint strict: "off" */

/* global inforssFeedManager */
/* global inforssHeadlineBar */
/* global inforssHeadlineDisplay */
/* global inforssXMLRepository */
/* global inforssClearPopupMenu */
/* global inforssAddNewFeed */

const ObserverService = Components.classes[
  "@mozilla.org/observer-service;1"].getService(
  Components.interfaces.nsIObserverService);

//FIXME get rid of all the 2 phase initialisation

//FIXME Not terribly happy about using the observer service for the addFeed
//window.
//It is not at all clear why this needs to use the observer service.
//There's only one client to each message.

/** This class contains the single feed manager, headline bar and headline
 * display objects, and allows them to communicate with one another.
 *
 * it also exists as a singleton used in inforss and the option window, which
 * last gets hold of it by poking around in the parent window properties.
 *
 * The observer method allows for the addfeed popup to communicate.
 */

function inforssMediator()
{
  this.feedManager = new inforssFeedManager(this);
  this.headlineBar = new inforssHeadlineBar(this);
  this.headlineDisplay = new inforssHeadlineDisplay(
    this,
    document.getElementById("inforss.newsbox1")
  );
  this._register();
  //fIXME why???
  this._reinit_after(1200);
  return this;
}

inforssMediator.prototype = {

  //----------------------------------------------------------------------------
  _init()
  {
    inforss.traceIn(this);
    try
    {
      this.feedManager.init();
      this.headlineDisplay.init();
    }
    catch (e)
    {
      inforss.debug(e, this);
    }
    inforss.traceOut(this);
  },

  //----------------------------------------------------------------------------
  //FIXME We need this because we need it but why on earth do we need it in the
  //first place?
  _reinit_after(timeout)
  {
    window.setTimeout(this._init.bind(this), timeout);
  },

  /** Registers with observer service */
  _register()
  {
    ObserverService.addObserver(this, "addNewFeed", false);
  },

  /** Deregisters from observer service on shutdown */
  deregister()
  {
    ObserverService.removeObserver(this, "addNewFeed");
  },

  /** API for observer service
   *
   * @param {nsISupports} subject - as defined in nsIObserverService
   * @param {string} topic - as defined in nsIObserverService
   * @param {wstring} data - as defined in nsIObserverService
   */
  observe(subject, topic, data)
  {
    try
    {
      switch (topic)
      {
        case "inforss.addNewFeed":
          inforssAddNewFeed({ inforssUrl: data });
          break;

        default:
          inforss.debug("Unknown mediator event", subject, topic, data);
      }
    }
    catch (e)
    {
      inforss.debug(e);
    }
  },

  /** Reload (seriously?)
   *
   * Deletes the supplied feeds and reinitialises headline bar and feed manager
   *
   * @param {array} deleted_feeds - array of feed urls to delete
   */
  reload(deleted_feeds = [])
  {
    for (let url of deleted_feeds)
    {
      this.feedManager.deleteRss(url);
    }
    inforssClearPopupMenu();
    this._reinit_after(0);
  },

  /** Configuration was reset */
  configuration_reset()
  {
    this.feedManager.deleteAllRss();
    inforssClearPopupMenu();
    this._reinit_after(0);
  },

  /** Set a headline as viewed
   *
   * @param {string} title - title of headline
   * @param {string} link - url of headline
   */
  set_viewed(title, link)
  {
    this.headlineBar.setViewed(title, link);
  },

  /** Set a headline as banned
   *
   * @param {string} title - title of headline
   * @param {string} link - url of headline
   */
  set_banned(title, link)
  {
    this.headlineBar.setBanned(title, link);
  },

  /** Reload headline cache from disk */
  reload_headline_cache()
  {
    this.feedManager.reload_headline_cache();
  },

  /** Clear headline cache */
  clear_headline_cache()
  {
    this.feedManager.clear_headline_cache();
  },

  /** Purge old headlines from the headline cache */
  purge_headline_cache()
  {
    this.feedManager.purge_headline_cache();
  },

  //----------------------------------------------------------------------------
  updateBar(feed)
  {
    this.headlineBar.updateBar(feed);
  },

  //----------------------------------------------------------------------------
  updateDisplay(feed)
  {
    this.headlineDisplay.updateDisplay(feed);
  },

  //----------------------------------------------------------------------------
  refreshBar()
  {
    this.headlineBar.refreshBar();
  },

  //----------------------------------------------------------------------------
  setSelected(url)
  {
    var changed = false;
    try
    {
      var selectedInfo = this.feedManager.getSelectedInfo(false);
      if (selectedInfo == null || url != selectedInfo.getUrl())
      {
        this.feedManager.setSelected(url);
        changed = true;
      }
    }
    catch (e)
    {
      inforss.debug(e, this);
    }
    return changed;
  },

  //----------------------------------------------------------------------------
  addFeed(feedXML, menuItem)
  {
    this.feedManager.addFeed(feedXML, menuItem);
  },

  //----------------------------------------------------------------------------
  getSelectedInfo(findDefault)
  {
    return this.feedManager.getSelectedInfo(findDefault);
  },

  //----------------------------------------------------------------------------
  resetDisplay()
  {
    this.headlineDisplay.resetDisplay();
  },

  //----------------------------------------------------------------------------
  resetHeadlines()
  {
    this.headlineBar.resetHeadlines();
  },

  //----------------------------------------------------------------------------
  deleteRss(url)
  {
    this.feedManager.deleteRss(url);
  },

  //----------------------------------------------------------------------------
  resizedWindow()
  {
    this.headlineDisplay.resizedWindow();
  },

  //----------------------------------------------------------------------------
  publishFeed(feed)
  {
    this.headlineBar.publishFeed(feed);
  },

  //----------------------------------------------------------------------------
  unpublishFeed(feed)
  {
    this.headlineBar.unpublishFeed(feed);
  },

  //----------------------------------------------------------------------------
  getLastDisplayedHeadline()
  {
    return this.headlineBar.getLastDisplayedHeadline();
  },

  //----------------------------------------------------------------------------
  removeDisplay(feed)
  {
    this.headlineDisplay.removeDisplay(feed);
  },

  //----------------------------------------------------------------------------
  updateMenuIcon(feed)
  {
    this.headlineDisplay.updateMenuIcon(feed);
  },

  //----------------------------------------------------------------------------
  clickRSS(event, link)
  {
    this.headlineDisplay.clickRSS(event, link);
  },

  //----------------------------------------------------------------------------
  locateFeed(url)
  {
    return this.feedManager.locateFeed(url);
  },

  //----------------------------------------------------------------------------
  setScroll(flag)
  {
    this.headlineDisplay.setScroll(flag);
  },

  //----------------------------------------------------------------------------
  checkStartScrolling()
  {
    this.headlineDisplay.checkStartScrolling();
  },

  //----------------------------------------------------------------------------
  setActiveTooltip()
  {
    this.headlineDisplay.setActiveTooltip();
  },

  //----------------------------------------------------------------------------
  resetActiveTooltip()
  {
    this.headlineDisplay.resetActiveTooltip();
  },

  //----------------------------------------------------------------------------
  isActiveTooltip()
  {
    return this.headlineDisplay.isActiveTooltip();
  },

  //----------------------------------------------------------------------------
  readAll()
  {
    if (inforss.confirm(inforss.get_string("readall")))
    {
      this.headlineBar.readAll();
    }
  },

  //----------------------------------------------------------------------------
  openTab(url)
  {
    inforss.traceIn(this);
    try
    {
      this.headlineDisplay.openTab(url);
    }
    catch (e)
    {
      inforss.debug(e, this);
    }
    inforss.traceOut(this);
  },

  //----------------------------------------------------------------------------
  viewAll()
  {
    if (inforss.confirm(inforss.get_string("viewall")))
    {
      this.headlineBar.viewAll();
    }
  },

  //----------------------------------------------------------------------------
  switchScroll()
  {
    this.headlineDisplay.switchScroll();
  },

  //----------------------------------------------------------------------------
  quickFilter()
  {
    this.headlineDisplay.quickFilter();
  },

  //----------------------------------------------------------------------------
  switchShuffle()
  {
    //FIXME This should be done as a function in headlineDisplay
    inforssXMLRepository.switchShuffle();
    this.headlineDisplay.updateCmdIcon();
  },

  //----------------------------------------------------------------------------
  switchPause()
  {
    this.headlineDisplay.switchPause();
  },

  //----------------------------------------------------------------------------
  switchDirection()
  {
    this.headlineDisplay.switchDirection();
  },

  //----------------------------------------------------------------------------
  goHome()
  {
    this.feedManager.goHome();
  },

  //----------------------------------------------------------------------------
  manualRefresh()
  {
    this.feedManager.manualRefresh();
  },

  //----------------------------------------------------------------------------
  manualSynchronize()
  {
    //FIXME What's this for then?
    //    this.feedManager.manualRefresh();
  },

  //----------------------------------------------------------------------------
  toggleHideOld()
  {
    inforssXMLRepository.hide_old_headlines =
      ! inforssXMLRepository.hide_old_headlines;
    inforssXMLRepository.save();
    this.headlineBar.refreshBar();
  },

  //----------------------------------------------------------------------------
  toggleHideViewed()
  {
    inforssXMLRepository.hide_viewed_headlines =
      ! inforssXMLRepository.hide_viewed_headlines;
    inforssXMLRepository.save();
    this.headlineBar.refreshBar();
  },

  //----------------------------------------------------------------------------
  handleMouseScroll(direction)
  {
    this.headlineDisplay.handleMouseScroll(direction);
  },

  //----------------------------------------------------------------------------
  //This is called from the 'next' and 'previous' buttons as
  //gInfoRssMediator.nextFeed(-1 (prev) or 1(next))
  nextFeed(direction)
  {
    this.feedManager.getNextGroupOrFeed(direction);
  },

};
<|endoftext|>


<commit_before>if (!window.wps) {
  window.wps = {};
}
var wps = window.wps;

wps.client = function(options) {
  this.url_ = options.url;
  this.format_ = new OpenLayers.Format.WPSCapabilities();
  this.client_ = new OpenLayers.WPSClient({
    servers: {
      'wpsgui': this.url_
    }
  });
};

wps.client.prototype.getGroupedProcesses = function(callback) {
  var format = this.format_;
  $.ajax(this.url_ + '?service=WPS&request=GetCapabilities&version=1.0.0').
    then(function(response) {
      var info = format.read(response);
      var groups = {};
      for (var key in info.processOfferings) {
        var names = key.split(':');
        var group = names[0];
        if (!groups[group]) {
          groups[group] = [];
        }
        groups[group].push(names[1]);
      }
      callback.call(this, groups, info);
    });
};

wps.ui = function(options) {
  this.parentContainer_ = options.parentContainer;
  this.sideBar_ = options.sideBar;
  this.dropZone_ = options.dropZone;
  this.client_ = options.client;
  this.spaceWidth = options.spaceWidth || 5000;
  this.spaceHeight = options.spaceHeight || 5000;
  this.scaleFactor = options.scaleFactor || 1;
  this.nodeWidth = options.nodeWidth || 100;
  this.nodeHeight = options.nodeHeight || 30;
  this.nodes = [];
  this.createSearch();
  this.createCanvas();
  this.createDropTarget();
  this.createZoomToolbar();
};

wps.ui.prototype.zoomIn = function(evt) {
  var me = evt.data;
  if (me.scaleFactor < 2) {
    me.scaleFactor += 0.1;
    me.redraw();
  }
};

wps.ui.prototype.zoomOut = function(evt) {
  var me = evt.data;
  if (me.scaleFactor > 0.3) {
    me.scaleFactor -= 0.1;
    me.redraw();
  }
};

wps.ui.prototype.resetZoom = function(evt) {
  var me = evt.data;
  me.scaleFactor = 1;
  me.redraw();
};

wps.ui.prototype.createZoomToolbar = function() {
  $('#btn-zoom-out').click(this, this.zoomOut);
  $('#btn-zoom-zero').click(this, this.resetZoom);
  $('#btn-zoom-in').click(this, this.zoomIn);
};

wps.ui.prototype.createCanvas = function() {
  this.outer = d3.select("#chart").
    append("svg:svg").
    attr("width", this.spaceWidth).
    attr("height", this.spaceHeight).
    attr("pointer-events", "all").
    style("cursor","crosshair");
  this.vis = this.outer.
    append('svg:g').
    on("dblclick.zoom", null).
    append('svg:g');
  var outer_background = this.vis.append('svg:rect').
    attr('width', this.spaceWidth).
    attr('height', this.spaceHeight).
    attr('fill','#fff');
};

wps.ui.prototype.createDropTarget = function() {
  var me = this;
  this.dropZone_.droppable({
    accept:".palette_node",
    drop: function( event, ui ) {
      d3.event = event;
      var selected_tool = $(ui.draggable[0]).data('type');
      var process = me.client_.client_.getProcess('wpsgui', selected_tool, {callback: function(info) {
        window.console.log(info);
        var mousePos = d3.touches(this)[0]||d3.mouse(this);
        mousePos[1] += this.scrollTop;
        mousePos[0] += this.scrollLeft;
        mousePos[1] /= me.scaleFactor;
        mousePos[0] /= me.scaleFactor;
        /* TODO no workspaces as yet, so z is 0 */
        var nn = { id:(1+Math.random()*4294967295).toString(16),x: mousePos[0],y:mousePos[1],w:this.nodeWidth,z:0};
        nn.type = selected_tool;
        nn.inputs = info.dataInputs.length;
        nn.outputs = info.processOutputs.length;
        // TODO make dynamic
        nn._def = {
          category: "process",
          color: "rgb(231, 231, 74)",
          label: selected_tool
        };
        var i, ii, delta = 50, span = delta * info.dataInputs.length, deltaY = (span-delta)/2;
        for (i=0, ii=info.dataInputs.length; i<ii; ++i) {
          var input = { id:(1+Math.random()*4294967295).toString(16),x: mousePos[0]-200,y:mousePos[1]+deltaY,w:this.nodeWidth,z:0};
          deltaY -= delta;
          input.type = info.dataInputs[i].title;
          input._def = {
            category: "input",
            color: "rgb(255, 0, 0)",
            label: input.type
          };
          me.nodes.push(input);
        }
        for (i=0, ii=info.processOutputs.length; i<ii; ++i) {
          var output = { id:(1+Math.random()*4294967295).toString(16),x: mousePos[0]+200,y:mousePos[1],w:this.nodeWidth,z:0};
          output.type = info.processOutputs[i].title;
          output._def = {
            category: "output",
            color: "rgb(0, 255, 0)",
            label: output.type
          };
          me.nodes.push(output);
        }
        me.nodes.push(nn);
        me.redraw();
      }, scope: this});
    }
  });
};

wps.ui.prototype.redraw = function() {
  this.vis.attr("transform","scale(" + this.scaleFactor + ")");
  this.outer.attr("width", this.spaceWidth*this.scaleFactor).attr("height", this.spaceHeight*this.scaleFactor);
  var node = this.vis.selectAll(".nodegroup").data(this.nodes, function(d){ return d.id; });
  node.exit().remove();
  var nodeEnter = node.enter().insert("svg:g").attr("class", "node nodegroup");
  var me = this;
  nodeEnter.each(function(d,i) {
    var node = d3.select(this);
    node.attr("id",d.id);
    var l = d._def.label;
    l = (typeof l === "function" ? l.call(d) : l)||"";
    d.w = Math.max(me.nodeWidth,me.calculateTextWidth(l)+(d.inputs>0?7:0) );
    d.h = Math.max(me.nodeHeight,(d.outputs||0) * 15);
    if (d._def.button) {
      me.createButton(node);
    }
    me.createProcessRect(node);
    var text = me.createProcessText(node, d);
    me.createInputLink(node, d, text);
    node.each(function(d,i) {
      me.updateNode.call(this, d);
    });
  });
};

wps.ui.prototype.createInputLink = function(node, d, text) {
  if (d.inputs > 0) {
    text.attr("x",38);
    node.append("rect").attr("class","port port_input").attr("rx",3).attr("ry",3).attr("x",-5).attr("width",10).attr("height",10).
      attr("y", 10);
  }
};

wps.ui.prototype.calculateTextWidth = function(str) {
  var sp = document.createElement("span");
  sp.className = "node_label";
  sp.style.position = "absolute";
  sp.style.top = "-1000px";
  sp.innerHTML = (str||"").replace(/&/g,"&").replace(/</g,"<").replace(/>/g,">");
  document.body.appendChild(sp);
  var w = sp.offsetWidth;
  document.body.removeChild(sp);
  return 50+w;
};

wps.ui.prototype.updateNode = function(d) {
  // TODO decide when dirty
  d.dirty = true;
  if (d.dirty) {
    var thisNode = d3.select(this);
    thisNode.attr("transform", function(d) { return "translate(" + (d.x-d.w/2) + "," + (d.y-d.h/2) + ")"; });
    thisNode.selectAll(".node").
      attr("width",function(d){return d.w;}).
      attr("height",function(d){return d.h;}).
      classed("node_selected",function(d) { return d.selected; }).
      classed("node_highlighted",function(d) { return d.highlighted; });
      thisNode.selectAll('text.node_label').text(function(d,i){
        return d._def.label || "";
      }).
        attr('y', function(d){return (d.h/2)-1;}).
        attr('class',function(d){
          return 'node_label'+
            (d._def.align?' node_label_'+d._def.align:'')+
            (d._def.label?' '+(typeof d._def.labelStyle == "function" ? d._def.labelStyle.call(d):d._def.labelStyle):'');
        });
      var numOutputs = d.outputs;
      var y = (d.h/2)-((numOutputs-1)/2)*13;
      d.ports = d.ports || d3.range(numOutputs);
      d._ports = thisNode.selectAll(".port_output").data(d.ports);
      d._ports.enter().append("rect").attr("class","port port_output").attr("rx",3).attr("ry",3).attr("width",10).attr("height",10);
      d._ports.exit().remove();
      if (d._ports) {
        var numOutputs = d.outputs || 1;
        var y = (d.h/2)-((numOutputs-1)/2)*13;
        var x = d.w - 5;
        d._ports.each(function(d,i) {
          var port = d3.select(this);
          port.attr("y",(y+13*i)-5).attr("x",x);
        });
      }
      d.dirty = false;
    }
};

wps.ui.prototype.createProcessRect = function(node) {
  var mainRect = node.append("rect").
    attr("class", "node").
    classed("node_unknown",function(d) { return d.type == "unknown"; }).
    attr("rx", 6).
    attr("ry", 6).
    attr("fill",function(d) { return d._def.color;});
};

wps.ui.prototype.createProcessText = function(node, d) {
  var text = node.append('svg:text').attr('class','node_label').attr('x', 38).attr('dy', '.35em').attr('text-anchor','start');
  if (d._def.align) {
    text.attr('class','node_label node_label_'+d._def.align);
    text.attr('text-anchor','end');
  }
  return text;
};

wps.ui.prototype.createButton = function(node) {
  var nodeButtonGroup = node.append('svg:g').
    attr("transform",function(d) { return "translate("+((d._def.align == "right") ? 94 : -25)+",2)"; }).
    attr("class",function(d) { return "node_button "+((d._def.align == "right") ? "node_right_button" : "node_left_button"); });
  nodeButtonGroup.append('rect').
    attr("rx",8).
    attr("ry",8).
    attr("width",32).
    attr("height",this.nodeHeight-4).
    attr("fill","#eee");
  nodeButtonGroup.append('rect').
    attr("x",function(d) { return d._def.align == "right"? 10:5;}).
    attr("y",4).
    attr("rx",5).
    attr("ry",5).
    attr("width",16).
    attr("height",this.nodeHeight-12).
    attr("fill",function(d) { return d._def.color;}).
    attr("cursor","pointer");
};

wps.ui.prototype.createSearch = function() {
  var filterChange = function() {
    var val = $("#palette-search-input").val();
    if (val === "") {
      $("#palette-search-clear").hide();
    } else {
      $("#palette-search-clear").show();
    }
    var re = new RegExp(val, 'i');
    $(".palette_node").each(function(i,el) {
      if (val === "" || re.test(el.innerHTML)) {
        $(this).show();
      } else {
        $(this).hide();
      }
    });
  };
  $("#palette-search-clear").on("click",function(e) {
    e.preventDefault();
    $("#palette-search-input").val("");
    filterChange();
    $("#palette-search-input").focus();
  });
  $("#palette-search-input").val("");
  $("#palette-search-input").on("keyup",function() {
    filterChange();
  });
  $("#palette-search-input").on("focus",function() {
    $("body").one("mousedown",function() {
      $("#palette-search-input").blur();
    });
  });
};

wps.ui.prototype.createProcessCategory = function(group) {
  var category = $('

' +
    '' +
    group + '

');
  this.parentContainer_.append(category);
  var content = $('

');
  $(category).append(content);
  $(category).children('.palette-header').click(function(e) {
    $(this).next().slideToggle();
    $(this).children("i").toggleClass("expanded");
  });
  return content;
};

wps.ui.prototype.createProcess = function(offering) {
  var summary = offering['abstract'];
  var title = offering.title;
  var id = offering.identifier;
  var d = $('
' + id.split(':')[1] + '
');
  $(d).data('type', id);
  $(d).popover({
    title: title,
    placement:"right",
    trigger: "hover",
    delay: { show: 750, hide: 50 },
    html: true,
    container:'body',
    content: summary
  });
  var sidebar = this.sideBar_;
  $(d).click(summary, function(evt) {
    var help = '
' + evt.data + "
";
    sidebar.html(help);
  });
  $(d).draggable({
    helper: 'clone',
    appendTo: 'body',
    revert: true,
    revertDuration: 50
  });
  return d;
};

<commit_msg>have entry points on input and output boxes<commit_after>if (!window.wps) {
  window.wps = {};
}
var wps = window.wps;

wps.client = function(options) {
  this.url_ = options.url;
  this.format_ = new OpenLayers.Format.WPSCapabilities();
  this.client_ = new OpenLayers.WPSClient({
    servers: {
      'wpsgui': this.url_
    }
  });
};

wps.client.prototype.getGroupedProcesses = function(callback) {
  var format = this.format_;
  $.ajax(this.url_ + '?service=WPS&request=GetCapabilities&version=1.0.0').
    then(function(response) {
      var info = format.read(response);
      var groups = {};
      for (var key in info.processOfferings) {
        var names = key.split(':');
        var group = names[0];
        if (!groups[group]) {
          groups[group] = [];
        }
        groups[group].push(names[1]);
      }
      callback.call(this, groups, info);
    });
};

wps.ui = function(options) {
  this.parentContainer_ = options.parentContainer;
  this.sideBar_ = options.sideBar;
  this.dropZone_ = options.dropZone;
  this.client_ = options.client;
  this.spaceWidth = options.spaceWidth || 5000;
  this.spaceHeight = options.spaceHeight || 5000;
  this.scaleFactor = options.scaleFactor || 1;
  this.nodeWidth = options.nodeWidth || 100;
  this.nodeHeight = options.nodeHeight || 30;
  this.nodes = [];
  this.createSearch();
  this.createCanvas();
  this.createDropTarget();
  this.createZoomToolbar();
};

wps.ui.prototype.zoomIn = function(evt) {
  var me = evt.data;
  if (me.scaleFactor < 2) {
    me.scaleFactor += 0.1;
    me.redraw();
  }
};

wps.ui.prototype.zoomOut = function(evt) {
  var me = evt.data;
  if (me.scaleFactor > 0.3) {
    me.scaleFactor -= 0.1;
    me.redraw();
  }
};

wps.ui.prototype.resetZoom = function(evt) {
  var me = evt.data;
  me.scaleFactor = 1;
  me.redraw();
};

wps.ui.prototype.createZoomToolbar = function() {
  $('#btn-zoom-out').click(this, this.zoomOut);
  $('#btn-zoom-zero').click(this, this.resetZoom);
  $('#btn-zoom-in').click(this, this.zoomIn);
};

wps.ui.prototype.createCanvas = function() {
  this.outer = d3.select("#chart").
    append("svg:svg").
    attr("width", this.spaceWidth).
    attr("height", this.spaceHeight).
    attr("pointer-events", "all").
    style("cursor","crosshair");
  this.vis = this.outer.
    append('svg:g').
    on("dblclick.zoom", null).
    append('svg:g');
  var outer_background = this.vis.append('svg:rect').
    attr('width', this.spaceWidth).
    attr('height', this.spaceHeight).
    attr('fill','#fff');
};

wps.ui.prototype.createDropTarget = function() {
  var me = this;
  this.dropZone_.droppable({
    accept:".palette_node",
    drop: function( event, ui ) {
      d3.event = event;
      var selected_tool = $(ui.draggable[0]).data('type');
      var process = me.client_.client_.getProcess('wpsgui', selected_tool, {callback: function(info) {
        window.console.log(info);
        var mousePos = d3.touches(this)[0]||d3.mouse(this);
        mousePos[1] += this.scrollTop;
        mousePos[0] += this.scrollLeft;
        mousePos[1] /= me.scaleFactor;
        mousePos[0] /= me.scaleFactor;
        /* TODO no workspaces as yet, so z is 0 */
        var nn = { id:(1+Math.random()*4294967295).toString(16),x: mousePos[0],y:mousePos[1],w:this.nodeWidth,z:0};
        nn.type = selected_tool;
        nn.inputs = info.dataInputs.length;
        nn.outputs = info.processOutputs.length;
        // TODO make dynamic
        nn._def = {
          category: "process",
          color: "rgb(231, 231, 74)",
          label: selected_tool
        };
        var i, ii, delta = 50, span = delta * info.dataInputs.length, deltaY = (span-delta)/2;
        for (i=0, ii=info.dataInputs.length; i<ii; ++i) {
          var input = { id:(1+Math.random()*4294967295).toString(16),x: mousePos[0]-200,y:mousePos[1]+deltaY,w:this.nodeWidth,z:0};
          deltaY -= delta;
          input.type = info.dataInputs[i].title;
          input.outputs = 1;
          input._def = {
            category: "input",
            color: "rgb(255, 0, 0)",
            label: input.type
          };
          me.nodes.push(input);
        }
        for (i=0, ii=info.processOutputs.length; i<ii; ++i) {
          var output = { id:(1+Math.random()*4294967295).toString(16),x: mousePos[0]+200,y:mousePos[1],w:this.nodeWidth,z:0};
          output.type = info.processOutputs[i].title;
          output.inputs = 1;
          output._def = {
            category: "output",
            color: "rgb(0, 255, 0)",
            label: output.type
          };
          me.nodes.push(output);
        }
        me.nodes.push(nn);
        me.redraw();
      }, scope: this});
    }
  });
};

wps.ui.prototype.redraw = function() {
  this.vis.attr("transform","scale(" + this.scaleFactor + ")");
  this.outer.attr("width", this.spaceWidth*this.scaleFactor).attr("height", this.spaceHeight*this.scaleFactor);
  var node = this.vis.selectAll(".nodegroup").data(this.nodes, function(d){ return d.id; });
  node.exit().remove();
  var nodeEnter = node.enter().insert("svg:g").attr("class", "node nodegroup");
  var me = this;
  nodeEnter.each(function(d,i) {
    var node = d3.select(this);
    node.attr("id",d.id);
    var l = d._def.label;
    l = (typeof l === "function" ? l.call(d) : l)||"";
    d.w = Math.max(me.nodeWidth,me.calculateTextWidth(l)+(d.inputs>0?7:0) );
    d.h = Math.max(me.nodeHeight,(d.outputs||0) * 15);
    if (d._def.button) {
      me.createButton(node);
    }
    me.createProcessRect(node);
    var text = me.createProcessText(node, d);
    me.createInputLink(node, d, text);
    node.each(function(d,i) {
      me.updateNode.call(this, d);
    });
  });
};

wps.ui.prototype.createInputLink = function(node, d, text) {
  if (d.inputs > 0) {
    text.attr("x",38);
    node.append("rect").attr("class","port port_input").attr("rx",3).attr("ry",3).attr("x",-5).attr("width",10).attr("height",10).
      attr("y", 10);
  }
};

wps.ui.prototype.calculateTextWidth = function(str) {
  var sp = document.createElement("span");
  sp.className = "node_label";
  sp.style.position = "absolute";
  sp.style.top = "-1000px";
  sp.innerHTML = (str||"").replace(/&/g,"&").replace(/</g,"<").replace(/>/g,">");
  document.body.appendChild(sp);
  var w = sp.offsetWidth;
  document.body.removeChild(sp);
  return 50+w;
};

wps.ui.prototype.updateNode = function(d) {
  // TODO decide when dirty
  d.dirty = true;
  if (d.dirty) {
    var thisNode = d3.select(this);
    thisNode.attr("transform", function(d) { return "translate(" + (d.x-d.w/2) + "," + (d.y-d.h/2) + ")"; });
    thisNode.selectAll(".node").
      attr("width",function(d){return d.w;}).
      attr("height",function(d){return d.h;}).
      classed("node_selected",function(d) { return d.selected; }).
      classed("node_highlighted",function(d) { return d.highlighted; });
      thisNode.selectAll('text.node_label').text(function(d,i){
        return d._def.label || "";
      }).
        attr('y', function(d){return (d.h/2)-1;}).
        attr('class',function(d){
          return 'node_label'+
            (d._def.align?' node_label_'+d._def.align:'')+
            (d._def.label?' '+(typeof d._def.labelStyle == "function" ? d._def.labelStyle.call(d):d._def.labelStyle):'');
        });
      var numOutputs = d.outputs;
      var y = (d.h/2)-((numOutputs-1)/2)*13;
      d.ports = d.ports || d3.range(numOutputs);
      d._ports = thisNode.selectAll(".port_output").data(d.ports);
      d._ports.enter().append("rect").attr("class","port port_output").attr("rx",3).attr("ry",3).attr("width",10).attr("height",10);
      d._ports.exit().remove();
      if (d._ports) {
        var numOutputs = d.outputs || 1;
        var y = (d.h/2)-((numOutputs-1)/2)*13;
        var x = d.w - 5;
        d._ports.each(function(d,i) {
          var port = d3.select(this);
          port.attr("y",(y+13*i)-5).attr("x",x);
        });
      }
      d.dirty = false;
    }
};

wps.ui.prototype.createProcessRect = function(node) {
  var mainRect = node.append("rect").
    attr("class", "node").
    classed("node_unknown",function(d) { return d.type == "unknown"; }).
    attr("rx", 6).
    attr("ry", 6).
    attr("fill",function(d) { return d._def.color;});
};

wps.ui.prototype.createProcessText = function(node, d) {
  var text = node.append('svg:text').attr('class','node_label').attr('x', 38).attr('dy', '.35em').attr('text-anchor','start');
  if (d._def.align) {
    text.attr('class','node_label node_label_'+d._def.align);
    text.attr('text-anchor','end');
  }
  return text;
};

wps.ui.prototype.createButton = function(node) {
  var nodeButtonGroup = node.append('svg:g').
    attr("transform",function(d) { return "translate("+((d._def.align == "right") ? 94 : -25)+",2)"; }).
    attr("class",function(d) { return "node_button "+((d._def.align == "right") ? "node_right_button" : "node_left_button"); });
  nodeButtonGroup.append('rect').
    attr("rx",8).
    attr("ry",8).
    attr("width",32).
    attr("height",this.nodeHeight-4).
    attr("fill","#eee");
  nodeButtonGroup.append('rect').
    attr("x",function(d) { return d._def.align == "right"? 10:5;}).
    attr("y",4).
    attr("rx",5).
    attr("ry",5).
    attr("width",16).
    attr("height",this.nodeHeight-12).
    attr("fill",function(d) { return d._def.color;}).
    attr("cursor","pointer");
};

wps.ui.prototype.createSearch = function() {
  var filterChange = function() {
    var val = $("#palette-search-input").val();
    if (val === "") {
      $("#palette-search-clear").hide();
    } else {
      $("#palette-search-clear").show();
    }
    var re = new RegExp(val, 'i');
    $(".palette_node").each(function(i,el) {
      if (val === "" || re.test(el.innerHTML)) {
        $(this).show();
      } else {
        $(this).hide();
      }
    });
  };
  $("#palette-search-clear").on("click",function(e) {
    e.preventDefault();
    $("#palette-search-input").val("");
    filterChange();
    $("#palette-search-input").focus();
  });
  $("#palette-search-input").val("");
  $("#palette-search-input").on("keyup",function() {
    filterChange();
  });
  $("#palette-search-input").on("focus",function() {
    $("body").one("mousedown",function() {
      $("#palette-search-input").blur();
    });
  });
};

wps.ui.prototype.createProcessCategory = function(group) {
  var category = $('

' +
    '' +
    group + '

');
  this.parentContainer_.append(category);
  var content = $('

');
  $(category).append(content);
  $(category).children('.palette-header').click(function(e) {
    $(this).next().slideToggle();
    $(this).children("i").toggleClass("expanded");
  });
  return content;
};

wps.ui.prototype.createProcess = function(offering) {
  var summary = offering['abstract'];
  var title = offering.title;
  var id = offering.identifier;
  var d = $('
' + id.split(':')[1] + '
');
  $(d).data('type', id);
  $(d).popover({
    title: title,
    placement:"right",
    trigger: "hover",
    delay: { show: 750, hide: 50 },
    html: true,
    container:'body',
    content: summary
  });
  var sidebar = this.sideBar_;
  $(d).click(summary, function(evt) {
    var help = '
' + evt.data + "
";
    sidebar.html(help);
  });
  $(d).draggable({
    helper: 'clone',
    appendTo: 'body',
    revert: true,
    revertDuration: 50
  });
  return d;
};

<|endoftext|>