<commit_before>var _ = require('lodash'),
    Cursor = require('../cursor'),
    VariableScope = require('postman-collection').VariableScope,

    prepareLookupHash,
    extractSNR;

/**
 * Returns a hash of IDs and Names of items in an array
 *
 * @param {Array} items
 * @returns {Object}
 */
prepareLookupHash = function (items) {
    var hash = {
        ids: {},
        names: {},
        obj: {}
    };

    _.each(items, function (item, index) {
        if (item) {
            item.id && (hash.ids[item.id] = index);
            item.name && (hash.names[item.name] = index);
        }
    });

    return hash;
};

extractSNR = function (executions, previous) {
    var snr = previous || {};

    _.isArray(executions) && executions.forEach(function (execution) {
        _.has(_.get(execution, 'result.masked'), 'nextRequest') && (
            (snr.defined = true),
            (snr.value = execution.result.masked.nextRequest)
        );
    });

    return snr;
};

/**
 * Adds options
 * disableSNR:Boolean
 *
 * @type {Object}
 */
module.exports = {
    init: function (done) {
        var state = this.state;

        // in case the environment or global is sent as an array, assume it is the values object from our environment
        // format
        _.isArray(state.environment) &&
            (state.environment = _(state.environment).indexBy('key').mapValues('value').value());
        _.isArray(state.globals) && (state.globals = _(state.globals).indexBy('key').mapValues('value').value());

        // sanitise state object
        state.environment = new VariableScope(state.environment);
        state.globals = new VariableScope(state.globals);

        // ensure that the items and iteration data set is in place
        !_.isArray(state.items) && (state.items = []);
        !_.isArray(state.data) && (state.data = []);
        !_.isObject(state.data[0]) && (state.data[0] = {});

        // if the location in state is already normalised then go ahead and queue iteration, else normalise the
        // location
        state.cursor = Cursor.box(state.cursor, { // we pass bounds to ensure there is no stale state
            cycles: state.data.length,
            length: state.items.length
        });
        this.waterfall = state.cursor; // copy the location object to instance for quick access

        // queue the iteration command on start
        this.queue('waterfall', {
            coords: this.waterfall.current(),
            static: true,
            start: true
        });

        // clear the variable that is supposed to store item name and id lookup hash for easy setNextRequest
        this.snrHash = null; // we populate it in the first SNR call

        done();
    },

    triggers: ['beforeIteration', 'iteration'],

    process: {
        /**
         * This processor simply queues scripts and requests in a linear chain.
         *
         * @param {Object} payload
         * @param {Object} payload.coords
         * @param {Boolean} [payload.static=false]
         * @param {Function} next
         */
        waterfall: function (payload, next) {
            // we procure the coordinates that we have to pick item and data from. the data is
            var coords = payload.static ? payload.coords : this.waterfall.whatnext(payload.coords),
                item = this.state.items[coords.position],
                delay;

            // if there is nothing to process, we bail out from here, even before we enter the iteration cycle
            if (coords.empty) {
                return next();
            }

            if (payload.stopRunNow) {
                this.triggers.iteration(null, payload.coords);
                return next();
            }

            // if it is a beginning of a run, we need to raise events for iteration start
            if (payload.start) {
                this.triggers.beforeIteration(null, coords);
            }

            // if this is a new iteration, we close the previous one and start new
            if (coords.cr) {
                // getting the iteration delay here ensures that delay is only called between two iterations
                delay = _.get(this.options, 'delay.iteration', 0);

                this.triggers.iteration(null, payload.coords);
                this.triggers.beforeIteration(null, coords);
            }

            // if this is end of waterfall, it is an end of iteration and also end of run
            if (coords.eof) {
                this.triggers.iteration(null, coords);
                return next();
            }

            this.queueDelay(function () {
                this.queue('item', {
                    item: item,
                    coords: coords,
                    data: this.state.data[coords.iteration],
                    environment: this.state.environment,
                    globals: this.state.globals
                }, function (executionError, executions) {
                    var snr = {},
                        nextCoords,
                        seekingToStart,
                        stopRunNow,

                        stopOnFailure = this.options.stopOnFailure;

                    if (!executionError) {
                        // extract set next request
                        snr = extractSNR(executions.prerequest);
                        snr = extractSNR(executions.test, snr);
                    }

                    if (!this.options.disableSNR && snr.defined) {
                        // prepare the snr lookup hash if it is not already provided
                        // @todo - figure out a way to reset this post run complete
                        !this.snrHash && (this.snrHash = prepareLookupHash(this.state.items));

                        // if it is null, we do not proceed further and move on
                        // see if a request is found in the hash and then reset the coords position to the lookup
                        // value.
                        (snr.value !== null) && (snr.position =
                            this.snrHash[_.has(this.snrHash.ids, snr.value) ? 'ids' :
                                (_.has(this.snrHash.names, snr.value) ? 'names' : 'obj')][snr.value]);

                        snr.valid = _.isNumber(snr.position);
                    }

                    nextCoords = _.clone(coords);

                    if (snr.valid) {
                        // if the position was detected, we set the position to the one previous to the desired location
                        // this ensures that the next call to .whatnext() will return the desired position.
                        nextCoords.position = snr.position - 1;
                    }
                    else {
                        // if snr was requested, but not valid, we stop this iteration.
                        // stopping an iteration is equivalent to seeking the last position of the current
                        // iteration, so that the next call to .whatnext() will automatically move to the next
                        // iteration.
                        (snr.defined || executionError) && (nextCoords.position = nextCoords.length - 1);

                        // If we need to stop on a run, we set the stop flag to true.
                        (stopOnFailure && executionError) && (stopRunNow = true);
                    }

                    // @todo - do this in unhacky way
                    if (nextCoords.position === -1) {
                        nextCoords.position = 0;
                        seekingToStart = true;
                    }

                    this.waterfall.seek(nextCoords.position, nextCoords.iteration, function (err, chngd, coords) {
                        // this condition should never arise, so better throw error when this happens
                        if (err) {
                            throw err;
                        }

                        this.queue('waterfall', {
                            coords: coords,
                            static: seekingToStart,
                            stopRunNow: stopRunNow
                        });
                    }, this);
                });
            }.bind(this), {
                time: delay,
                source: 'iteration',
                cursor: coords
            }, next);
        }
    }
};
<commit_msg>Removed environment and globals legacy format detection and delegated it to VariableScope<commit_after>var _ = require('lodash'),
    Cursor = require('../cursor'),
    VariableScope = require('postman-collection').VariableScope,

    prepareLookupHash,
    extractSNR;

/**
 * Returns a hash of IDs and Names of items in an array
 *
 * @param {Array} items
 * @returns {Object}
 */
prepareLookupHash = function (items) {
    var hash = {
        ids: {},
        names: {},
        obj: {}
    };

    _.each(items, function (item, index) {
        if (item) {
            item.id && (hash.ids[item.id] = index);
            item.name && (hash.names[item.name] = index);
        }
    });

    return hash;
};

extractSNR = function (executions, previous) {
    var snr = previous || {};

    _.isArray(executions) && executions.forEach(function (execution) {
        _.has(_.get(execution, 'result.masked'), 'nextRequest') && (
            (snr.defined = true),
            (snr.value = execution.result.masked.nextRequest)
        );
    });

    return snr;
};

/**
 * Adds options
 * disableSNR:Boolean
 *
 * @type {Object}
 */
module.exports = {
    init: function (done) {
        var state = this.state;

        // ensure that the environment and globals are in VariableScope instance format
        state.environment = VariableScope.isVariableScope(state.environment) ? state.environment :
            new VariableScope(state.environment);
        state.globals = VariableScope.isVariableScope(state.globals) ? state.globals :
            new VariableScope(state.globals);

        // ensure that the items and iteration data set is in place
        !_.isArray(state.items) && (state.items = []);
        !_.isArray(state.data) && (state.data = []);
        !_.isObject(state.data[0]) && (state.data[0] = {});

        // if the location in state is already normalised then go ahead and queue iteration, else normalise the
        // location
        state.cursor = Cursor.box(state.cursor, { // we pass bounds to ensure there is no stale state
            cycles: state.data.length,
            length: state.items.length
        });
        this.waterfall = state.cursor; // copy the location object to instance for quick access

        // queue the iteration command on start
        this.queue('waterfall', {
            coords: this.waterfall.current(),
            static: true,
            start: true
        });

        // clear the variable that is supposed to store item name and id lookup hash for easy setNextRequest
        this.snrHash = null; // we populate it in the first SNR call

        done();
    },

    triggers: ['beforeIteration', 'iteration'],

    process: {
        /**
         * This processor simply queues scripts and requests in a linear chain.
         *
         * @param {Object} payload
         * @param {Object} payload.coords
         * @param {Boolean} [payload.static=false]
         * @param {Function} next
         */
        waterfall: function (payload, next) {
            // we procure the coordinates that we have to pick item and data from. the data is
            var coords = payload.static ? payload.coords : this.waterfall.whatnext(payload.coords),
                item = this.state.items[coords.position],
                delay;

            // if there is nothing to process, we bail out from here, even before we enter the iteration cycle
            if (coords.empty) {
                return next();
            }

            if (payload.stopRunNow) {
                this.triggers.iteration(null, payload.coords);
                return next();
            }

            // if it is a beginning of a run, we need to raise events for iteration start
            if (payload.start) {
                this.triggers.beforeIteration(null, coords);
            }

            // if this is a new iteration, we close the previous one and start new
            if (coords.cr) {
                // getting the iteration delay here ensures that delay is only called between two iterations
                delay = _.get(this.options, 'delay.iteration', 0);

                this.triggers.iteration(null, payload.coords);
                this.triggers.beforeIteration(null, coords);
            }

            // if this is end of waterfall, it is an end of iteration and also end of run
            if (coords.eof) {
                this.triggers.iteration(null, coords);
                return next();
            }

            this.queueDelay(function () {
                this.queue('item', {
                    item: item,
                    coords: coords,
                    data: this.state.data[coords.iteration],
                    environment: this.state.environment,
                    globals: this.state.globals
                }, function (executionError, executions) {
                    var snr = {},
                        nextCoords,
                        seekingToStart,
                        stopRunNow,

                        stopOnFailure = this.options.stopOnFailure;

                    if (!executionError) {
                        // extract set next request
                        snr = extractSNR(executions.prerequest);
                        snr = extractSNR(executions.test, snr);
                    }

                    if (!this.options.disableSNR && snr.defined) {
                        // prepare the snr lookup hash if it is not already provided
                        // @todo - figure out a way to reset this post run complete
                        !this.snrHash && (this.snrHash = prepareLookupHash(this.state.items));

                        // if it is null, we do not proceed further and move on
                        // see if a request is found in the hash and then reset the coords position to the lookup
                        // value.
                        (snr.value !== null) && (snr.position =
                            this.snrHash[_.has(this.snrHash.ids, snr.value) ? 'ids' :
                                (_.has(this.snrHash.names, snr.value) ? 'names' : 'obj')][snr.value]);

                        snr.valid = _.isNumber(snr.position);
                    }

                    nextCoords = _.clone(coords);

                    if (snr.valid) {
                        // if the position was detected, we set the position to the one previous to the desired location
                        // this ensures that the next call to .whatnext() will return the desired position.
                        nextCoords.position = snr.position - 1;
                    }
                    else {
                        // if snr was requested, but not valid, we stop this iteration.
                        // stopping an iteration is equivalent to seeking the last position of the current
                        // iteration, so that the next call to .whatnext() will automatically move to the next
                        // iteration.
                        (snr.defined || executionError) && (nextCoords.position = nextCoords.length - 1);

                        // If we need to stop on a run, we set the stop flag to true.
                        (stopOnFailure && executionError) && (stopRunNow = true);
                    }

                    // @todo - do this in unhacky way
                    if (nextCoords.position === -1) {
                        nextCoords.position = 0;
                        seekingToStart = true;
                    }

                    this.waterfall.seek(nextCoords.position, nextCoords.iteration, function (err, chngd, coords) {
                        // this condition should never arise, so better throw error when this happens
                        if (err) {
                            throw err;
                        }

                        this.queue('waterfall', {
                            coords: coords,
                            static: seekingToStart,
                            stopRunNow: stopRunNow
                        });
                    }, this);
                });
            }.bind(this), {
                time: delay,
                source: 'iteration',
                cursor: coords
            }, next);
        }
    }
};
<|endoftext|>


<commit_before>/*
 * raja browser client
 */
(function() {

window.raja = new Raja();

script('/socket.io/socket.io.js', function(err) {
	if (err) throw err;
	var proto = io.Manager.prototype;
	raja._on = proto.on;
	raja._emit = proto.emit;
	raja.off = proto.off;
	raja.listeners = proto.listeners;
	raja.ready();
});

function Raja() {
	this.delays = [];
	this.base = document.getElementById('raja-io').content;
}

Raja.prototype.updateLink = function(resource, mtime) {
	var link = $('head > link[rel="resource"][href="'+resource.url+'"]');
	if (!link) {
		link = document.createElement('link');
		link.rel = "resource";
		link.href = resource.url;
		var tn = document.createTextNode("\n");
		document.head.insertBefore(link, document.head.firstChild);
		document.head.insertBefore(tn, link);
	}
	if (mtime != null) {
		if (!resource.mtime || mtime > resource.mtime) {
			resource.mtime = mtime;
		}
		link.setAttribute("last-modified", resource.mtime);
	} else {
		console.warn("empty mtime", resource, mtime);
	}
};

Raja.prototype.delay = function(url, listener) {
	this.delays.push([url, listener]);
	return this;
};

Raja.prototype.ready = function() {
	this.resources = {};
	var links = document.head.querySelectorAll('link[rel="resource"]');
	for (var i=0; i < links.length; i++) {
		var link = links.item(i);
		this.resources[link.href] = {
			mtime: parseInt(link.getAttribute('last-modified')),
			url: link.href
		};
	}
	var list = this.delays;
	delete this.delays;
	for (var i=0; i < list.length; i++) {
		this.on(list[i][0], list[i][1]);
	}
};

Raja.prototype.emit = function(what) {
	var args = Array.prototype.slice.call(arguments, 0);
	try {
		this._emit.apply(this, args);
	} catch(e) {
		console.error(e);
	}
	if (what == "error" && this.listeners("error").length == 0) {
		args.shift();
		console.error.apply(console, args);
	}
};

Raja.prototype.on = function(url, listener) {
	if (!this.resources) {
		return this.delay(url, listener);
	}
	if (!this.io) this.setio();
	var self = this;
	if (url == "error") return this._on(url, listener);
	var plistener = function() {
		try {
			listener.apply(null, Array.prototype.slice.call(arguments));
		} catch(e) {
			self.emit('error', e);
		}
	};
	url = this.absolute(url);
	var murl = url.split('?').shift();
	this._on(murl, plistener);
	var resources = this.resources;
	var resource = resources[murl];
	if (!resource) resource = resources[murl] = {url: murl};
	if (resource.error) return;

	(function(next) {
		if (resource.data !== undefined) {
			// resource has been loaded once
			// this is wrong when murl != url
			listener(resource.data, {method:"get", url: url, mtime: resource.mtime});
			return next();
		} else if (resource.mtime !== undefined) {
			// resource merged, just join it
			return next();
		} else if (resource.queue) {
			// resource is currently loading
			resource.queue.push(listener);
			return;
		}
		// resource has not been loaded, is not loading. Proceed
		resource.queue = [listener];
		xhr(url, function(err, txt, mtime) {
			var obj = tryJSON(txt);
			if (err) {
				resource.error = err;
				return next(err);
			}
			resource.data = obj;
			var queue = resource.queue;
			for (var i=0; i < queue.length; i++) {
				try {
					queue[i](obj, {method:"get", url: url, mtime: mtime});
				} catch(e) {
					console.error(e);
				}
			}
			delete resource.queue;
			self.updateLink(resource, mtime);
			next();
		});
	})(function(err) {
		if (err) self.emit('error', err);
		if (!resource.live) {
			resource.live = true;
			self.io.emit('join', {room: murl, mtime: resource.mtime});
		}
	});
	return this;
};

Raja.prototype.setio = function() {
	this.io = io(this.base);
	var self = this;
	this.io.on('reconnect_failed', function(err) {
		if (err) self.emit('error', err);
	});
	var pageUrl = this.absolute('.');
	var pageResource = this.resources[pageUrl];
	if (!pageResource) pageResource = this.resources[pageUrl] = {url: pageUrl};
	this.io.emit('join', {
		room: pageUrl,
		mtime: pageResource.mtime
	});

	this.io.on('message', function(msg) {
		if (!msg.url) return;
		var data = msg.data;
		if (data) delete msg.data;
		var resource = self.resources[msg.url];
		var mtime = msg.mtime;
		if (!mtime) return;
		if (msg.url != pageUrl) {
			self.updateLink(pageResource, mtime);
			self.emit(msg.url, data, msg);
		} else if (pageResource.mtime && mtime > pageResource.mtime) {
			console.log("A dependency was modified, please reload", pageUrl);
		}
		if (resource) self.updateLink(resource, mtime);
	});
};

Raja.prototype.absolute = function(url) {
	if (/^https?/i.test(url)) return url;
	var path = document.location.pathname;
	if (url.indexOf('..') == 0) {
		path = path.split('/');
		path.pop();
		url = path.join('/') + url.substring(2);
	} else if (url.indexOf('.') == 0) {
		url = path + url.substring(1);
	}
	// regular interpretation of url
	if (!this._a) this._a = document.createElement('a');
	this._a.href = url;
	return this._a.href;
};

function xhr(url, cb) {
	var req = new XMLHttpRequest();
	req.open('GET', url, true);
	req.onreadystatechange = function (e) {
		if (req.readyState == 4) {
			if (req.status >= 200 && req.status < 300) {
				cb(null, req.responseText, tryDate(req.getResponseHeader("Last-Modified")));
			} else {
				cb(req.status, req.responseText);
			}
		}
	};
	req.send(null);
}

function script(url, cb) {
	var script = document.createElement("script");
	script.async = true;
	script.type = 'text/javascript';
	script.charset = 'utf-8';
	script.src = url;
	function done() {
		script.onload = null;
		script.onerror = null;
		if (script.parentNode) {
			script.parentNode.removeChild(script);
		}
		script = null;
	}
	script.onload = function() {
		done();
		cb();
	};
	script.onerror = function(e) {
		done();
		cb(e);
	};
	// Circumvent IE6 bugs with base elements
	document.head.insertBefore(script, document.head.firstChild);
}

function tryJSON(txt) {
	var obj;
	try {
		obj = JSON.parse(txt);
	} catch(e) {
		console.error(e.toString());
		return txt;
	}
	return obj;
}

function tryDate(txt) {
	if (!txt) return;
	var date = new Date(txt);
	var time = date.getTime();
	if (isNaN(time)) return;
	else return time;
}

function $(str) {
	return document.querySelector(str);
}

})();
<commit_msg>Expose xhr get function<commit_after>/*
 * raja browser client
 */
(function() {

window.raja = new Raja();

script('/socket.io/socket.io.js', function(err) {
	if (err) throw err;
	var proto = io.Manager.prototype;
	raja._on = proto.on;
	raja._emit = proto.emit;
	raja.off = proto.off;
	raja.listeners = proto.listeners;
	raja.ready();
});

function Raja() {
	this.delays = [];
	this.base = document.getElementById('raja-io').content;
}

Raja.prototype.updateLink = function(resource, mtime) {
	var link = $('head > link[rel="resource"][href="'+resource.url+'"]');
	if (!link) {
		link = document.createElement('link');
		link.rel = "resource";
		link.href = resource.url;
		var tn = document.createTextNode("\n");
		document.head.insertBefore(link, document.head.firstChild);
		document.head.insertBefore(tn, link);
	}
	if (mtime != null) {
		if (!resource.mtime || mtime > resource.mtime) {
			resource.mtime = mtime;
		}
		link.setAttribute("last-modified", resource.mtime);
	} else {
		console.warn("empty mtime", resource, mtime);
	}
};

Raja.prototype.delay = function(url, listener) {
	this.delays.push([url, listener]);
	return this;
};

Raja.prototype.ready = function() {
	this.resources = {};
	var links = document.head.querySelectorAll('link[rel="resource"]');
	for (var i=0; i < links.length; i++) {
		var link = links.item(i);
		this.resources[link.href] = {
			mtime: parseInt(link.getAttribute('last-modified')),
			url: link.href
		};
	}
	var list = this.delays;
	delete this.delays;
	for (var i=0; i < list.length; i++) {
		this.on(list[i][0], list[i][1]);
	}
};

Raja.prototype.emit = function(what) {
	var args = Array.prototype.slice.call(arguments, 0);
	try {
		this._emit.apply(this, args);
	} catch(e) {
		console.error(e);
	}
	if (what == "error" && this.listeners("error").length == 0) {
		args.shift();
		console.error.apply(console, args);
	}
};

Raja.prototype.on = function(url, listener) {
	if (!this.resources) {
		return this.delay(url, listener);
	}
	if (!this.io) this.setio();
	var self = this;
	if (url == "error") return this._on(url, listener);
	var plistener = function() {
		try {
			listener.apply(null, Array.prototype.slice.call(arguments));
		} catch(e) {
			self.emit('error', e);
		}
	};
	url = this.absolute(url);
	var murl = url.split('?').shift();
	this._on(murl, plistener);
	var resources = this.resources;
	var resource = resources[murl];
	if (!resource) resource = resources[murl] = {url: murl};
	if (resource.error) return;

	(function(next) {
		if (resource.data !== undefined) {
			// resource has been loaded once
			// this is wrong when murl != url
			listener(resource.data, {method:"get", url: url, mtime: resource.mtime});
			return next();
		} else if (resource.mtime !== undefined) {
			// resource merged, just join it
			return next();
		} else if (resource.queue) {
			// resource is currently loading
			resource.queue.push(listener);
			return;
		}
		// resource has not been loaded, is not loading. Proceed
		resource.queue = [listener];
		Raja.xhr(url, function(err, txt, mtime) {
			var obj = tryJSON(txt);
			if (err) {
				resource.error = err;
				return next(err);
			}
			resource.data = obj;
			var queue = resource.queue;
			for (var i=0; i < queue.length; i++) {
				try {
					queue[i](obj, {method:"get", url: url, mtime: mtime});
				} catch(e) {
					console.error(e);
				}
			}
			delete resource.queue;
			self.updateLink(resource, mtime);
			next();
		});
	})(function(err) {
		if (err) self.emit('error', err);
		if (!resource.live) {
			resource.live = true;
			self.io.emit('join', {room: murl, mtime: resource.mtime});
		}
	});
	return this;
};

Raja.prototype.setio = function() {
	this.io = io(this.base);
	var self = this;
	this.io.on('reconnect_failed', function(err) {
		if (err) self.emit('error', err);
	});
	var pageUrl = this.absolute('.');
	var pageResource = this.resources[pageUrl];
	if (!pageResource) pageResource = this.resources[pageUrl] = {url: pageUrl};
	this.io.emit('join', {
		room: pageUrl,
		mtime: pageResource.mtime
	});

	this.io.on('message', function(msg) {
		if (!msg.url) return;
		var data = msg.data;
		if (data) delete msg.data;
		var resource = self.resources[msg.url];
		var mtime = msg.mtime;
		if (!mtime) return;
		if (msg.url != pageUrl) {
			self.updateLink(pageResource, mtime);
			self.emit(msg.url, data, msg);
		} else if (pageResource.mtime && mtime > pageResource.mtime) {
			console.log("A dependency was modified, please reload", pageUrl);
		}
		if (resource) self.updateLink(resource, mtime);
	});
};

Raja.prototype.absolute = function(url) {
	if (/^https?/i.test(url)) return url;
	var path = document.location.pathname;
	if (url.indexOf('..') == 0) {
		path = path.split('/');
		path.pop();
		url = path.join('/') + url.substring(2);
	} else if (url.indexOf('.') == 0) {
		url = path + url.substring(1);
	}
	// regular interpretation of url
	if (!this._a) this._a = document.createElement('a');
	this._a.href = url;
	return this._a.href;
};

Raja.xhr = function(url, cb) {
	var req = new XMLHttpRequest();
	req.open('GET', url, true);
	req.onreadystatechange = function (e) {
		if (req.readyState == 4) {
			if (req.status >= 200 && req.status < 300) {
				cb(null, req.responseText, tryDate(req.getResponseHeader("Last-Modified")));
			} else {
				cb(req.status, req.responseText);
			}
		}
	};
	req.send(null);
	return req;
};

function script(url, cb) {
	var script = document.createElement("script");
	script.async = true;
	script.type = 'text/javascript';
	script.charset = 'utf-8';
	script.src = url;
	function done() {
		script.onload = null;
		script.onerror = null;
		if (script.parentNode) {
			script.parentNode.removeChild(script);
		}
		script = null;
	}
	script.onload = function() {
		done();
		cb();
	};
	script.onerror = function(e) {
		done();
		cb(e);
	};
	// Circumvent IE6 bugs with base elements
	document.head.insertBefore(script, document.head.firstChild);
}

function tryJSON(txt) {
	var obj;
	try {
		obj = JSON.parse(txt);
	} catch(e) {
		console.error(e.toString());
		return txt;
	}
	return obj;
}

function tryDate(txt) {
	if (!txt) return;
	var date = new Date(txt);
	var time = date.getTime();
	if (isNaN(time)) return;
	else return time;
}

function $(str) {
	return document.querySelector(str);
}

})();
<|endoftext|>


<commit_before>import { NotFoundError } from './errors';
import Promise from 'es6-promise';
import map from 'lodash/map';
import forEach from 'lodash/forEach';
import isArray from 'lodash/isArray';
import isFunction from 'lodash/isFunction';
import isString from 'lodash/isString';
const idAttribute = process.env.KINVEY_ID_ATTRIBUTE || '_id';
const masterCollectionName = 'sqlite_master';
let dbCache = {};
let isSupported;

export default class WebSQL {
  constructor(name = 'kinvey', size = 5000) {
    this.name = name;
    this.size = size;
  }

  openDatabase() {
    let db = dbCache[this.name];

    if (!db) {
      db = global.openDatabase(this.name, 1, '', this.size);
      dbCache[this.name] = db;
    }

    return db;
  }

  openTransaction(collection, query, parameters, write = false) {
    const db = this.openDatabase();
    const escapedCollection = `"${collection}"`;
    const isMaster = collection === masterCollectionName;
    const isMulti = isArray(query);
    query = isMulti ? query : [[query, parameters]];

    const promise = new Promise((resolve, reject) => {
      const writeTxn = write || !isFunction(db.readTransaction);
      db[writeTxn ? 'transaction' : 'readTransaction']((tx) => {
        if (write && !isMaster) {
          tx.executeSql(`CREATE TABLE IF NOT EXISTS ${escapedCollection} ` +
            '(key BLOB PRIMARY KEY NOT NULL, value BLOB NOT NULL)');
        }

        let pending = query.length;
        const responses = [];

        if (pending === 0) {
          resolve(isMulti ? responses : responses.shift());
        } else {
          forEach(query, (parts) => {
            const sql = parts[0].replace('#{collection}', escapedCollection);

            tx.executeSql(sql, parts[1], (_, resultSet) => {
              const response = {
                rowCount: resultSet.rowsAffected,
                result: []
              };

              if (resultSet.rows.length) {
                for (let i = 0, len = resultSet.rows.length; i < len; i += 1) {
                  try {
                    const value = resultSet.rows.item(i).value;
                    const entity = isMaster ? value : JSON.parse(value);
                    response.result.push(entity);
                  } catch (error) {
                    // Catch the error
                  }
                }
              }

              responses.push(response);
              pending -= 1;

              if (pending === 0) {
                resolve(isMulti ? responses : responses.shift());
              }
            }, () => false); // Returning true to rollback, false to continue the transaction
          });
        }
      }, (error) => {
        error = isString(error) ? error : error.message;

        // Safari calls this function regardless if user permits more quota or not.
        // And there's no way for a developer to know user's reaction.
        if (error && error.code === SQLError.QUOTA_ERR) {
          // Start over the transaction again to check if user permitted or not.
          return this.openTransaction(collection, query, parameters, write);
        }

        if (error && error.indexOf('no such table') === -1) {
          return reject(new NotFoundError(`The ${collection} collection was not found on`
            + ` the ${this.name} WebSQL database.`));
        }

        const checkQuery = 'SELECT name AS value from #{collection} WHERE type = ? AND name = ?';
        const checkParameters = ['table', collection];

        return this.openTransaction(masterCollectionName, checkQuery, checkParameters).then((response) => {
          if (response.result.length === 0) {
            return reject(new NotFoundError(`The ${collection} collection was not found on`
              + ` the ${this.name} WebSQL database.`));
          }

          return reject(new Error(`Unable to open a transaction for the ${collection}`
            + ` collection on the ${this.name} WebSQL database.`));
        }).catch((error) => {
          reject(new Error(`Unable to open a transaction for the ${collection}`
            + ` collection on the ${this.name} WebSQL database.`, error));
        });
      });
    });

    return promise;
  }

  find(collection) {
    const sql = 'SELECT value FROM #{collection}';
    return this.openTransaction(collection, sql, [])
      .then(response => response.result);
  }

  findById(collection, id) {
    const sql = 'SELECT value FROM #{collection} WHERE key = ?';
    return this.openTransaction(collection, sql, [id])
      .then(response => response.result)
      .then((entities) => {
        if (entities.length === 0) {
          throw new NotFoundError(`An entity with _id = ${id} was not found in the ${collection}`
            + ` collection on the ${this.name} WebSQL database.`);
        }

        return entities[0];
      });
  }

  save(collection, entities) {
    const queries = [];
    let singular = false;

    if (!isArray(entities)) {
      singular = true;
      entities = [entities];
    }

    if (entities.length === 0) {
      return Promise.resolve(null);
    }

    entities = map(entities, (entity) => {
      queries.push([
        'REPLACE INTO #{collection} (key, value) VALUES (?, ?)',
        [entity[idAttribute], JSON.stringify(entity)]
      ]);

      return entity;
    });

    return this.openTransaction(collection, queries, null, true)
      .then(() => (singular ? entities[0] : entities));
  }

  removeById(collection, id) {
    const queries = [
      ['SELECT value FROM #{collection} WHERE key = ?', [id]],
      ['DELETE FROM #{collection} WHERE key = ?', [id]],
    ];
    return this.openTransaction(collection, queries, null, true)
      .then((response) => {
        const entities = response[0].result;
        let count = response[1].rowCount;
        count = count || entities.length;

        if (count === 0) {
          throw new NotFoundError(`An entity with _id = ${id} was not found in the ${collection}`
            + ` collection on the ${this.name} WebSQL database.`);
        }

        return entities[0];
      });
  }

  clear() {
    return this.openTransaction(
      masterCollectionName,
      'SELECT name AS value FROM #{collection} WHERE type = ?',
      ['table'],
      false
    )
      .then(response => response.result)
      .then((tables) => {
        // If there are no tables, return.
        if (tables.length === 0) {
          return null;
        }

        // Drop all tables. Filter tables first to avoid attempting to delete
        // system tables (which will fail).
        const queries = tables
          .filter(table => (/^[a-zA-Z0-9-]{1,128}/).test(table))
          .map(table => [`DROP TABLE IF EXISTS '${table}'`]);
        return this.openTransaction(masterCollectionName, queries, null, true);
      })
      .then(() => {
        dbCache = {};
        return null;
      });
  }

  static loadAdapter(name) {
    const db = new WebSQL(name);

    if (typeof isSupported !== 'undefined') {
      if (isSupported) {
        return Promise.resolve(db);
      }

      return Promise.resolve(undefined);
    }

    if (typeof global.openDatabase === 'undefined') {
      isSupported = false;
      return Promise.resolve(undefined);
    }

    return db.save('__testSupport', { _id: '1' })
      .then(() => {
        isSupported = true;
        return db;
      })
      .catch(() => {
        isSupported = false;
        return undefined;
      });
  }
}
<commit_msg>MLIBZ-1620 Check if SQLError is defined<commit_after>import { NotFoundError } from './errors';
import Promise from 'es6-promise';
import map from 'lodash/map';
import forEach from 'lodash/forEach';
import isArray from 'lodash/isArray';
import isFunction from 'lodash/isFunction';
import isString from 'lodash/isString';
const idAttribute = process.env.KINVEY_ID_ATTRIBUTE || '_id';
const masterCollectionName = 'sqlite_master';
let dbCache = {};
let isSupported;

export default class WebSQL {
  constructor(name = 'kinvey', size = 5000) {
    this.name = name;
    this.size = size;
  }

  openDatabase() {
    let db = dbCache[this.name];

    if (!db) {
      db = global.openDatabase(this.name, 1, '', this.size);
      dbCache[this.name] = db;
    }

    return db;
  }

  openTransaction(collection, query, parameters, write = false) {
    const db = this.openDatabase();
    const escapedCollection = `"${collection}"`;
    const isMaster = collection === masterCollectionName;
    const isMulti = isArray(query);
    query = isMulti ? query : [[query, parameters]];

    const promise = new Promise((resolve, reject) => {
      const writeTxn = write || !isFunction(db.readTransaction);
      db[writeTxn ? 'transaction' : 'readTransaction']((tx) => {
        if (write && !isMaster) {
          tx.executeSql(`CREATE TABLE IF NOT EXISTS ${escapedCollection} ` +
            '(key BLOB PRIMARY KEY NOT NULL, value BLOB NOT NULL)');
        }

        let pending = query.length;
        const responses = [];

        if (pending === 0) {
          resolve(isMulti ? responses : responses.shift());
        } else {
          forEach(query, (parts) => {
            const sql = parts[0].replace('#{collection}', escapedCollection);

            tx.executeSql(sql, parts[1], (_, resultSet) => {
              const response = {
                rowCount: resultSet.rowsAffected,
                result: []
              };

              if (resultSet.rows.length) {
                for (let i = 0, len = resultSet.rows.length; i < len; i += 1) {
                  try {
                    const value = resultSet.rows.item(i).value;
                    const entity = isMaster ? value : JSON.parse(value);
                    response.result.push(entity);
                  } catch (error) {
                    // Catch the error
                  }
                }
              }

              responses.push(response);
              pending -= 1;

              if (pending === 0) {
                resolve(isMulti ? responses : responses.shift());
              }
            });
          });
        }
      }, (error) => {
        error = isString(error) ? error : error.message;

        // Safari calls this function regardless if user permits more quota or not.
        // And there's no way for a developer to know user's reaction.
        if (error && typeof SQLError !== 'undefined' && error.code === SQLError.QUOTA_ERR) {
          // Start over the transaction again to check if user permitted or not.
          return this.openTransaction(collection, query, parameters, write);
        }

        if (error && error.indexOf('no such table') === -1) {
          return reject(new NotFoundError(`The ${collection} collection was not found on`
            + ` the ${this.name} WebSQL database.`));
        }

        const checkQuery = 'SELECT name AS value from #{collection} WHERE type = ? AND name = ?';
        const checkParameters = ['table', collection];

        return this.openTransaction(masterCollectionName, checkQuery, checkParameters).then((response) => {
          if (response.result.length === 0) {
            return reject(new NotFoundError(`The ${collection} collection was not found on`
              + ` the ${this.name} WebSQL database.`));
          }

          return reject(new Error(`Unable to open a transaction for the ${collection}`
            + ` collection on the ${this.name} WebSQL database.`));
        }).catch((error) => {
          reject(new Error(`Unable to open a transaction for the ${collection}`
            + ` collection on the ${this.name} WebSQL database.`, error));
        });
      });
    });

    return promise;
  }

  find(collection) {
    const sql = 'SELECT value FROM #{collection}';
    return this.openTransaction(collection, sql, [])
      .then(response => response.result);
  }

  findById(collection, id) {
    const sql = 'SELECT value FROM #{collection} WHERE key = ?';
    return this.openTransaction(collection, sql, [id])
      .then(response => response.result)
      .then((entities) => {
        if (entities.length === 0) {
          throw new NotFoundError(`An entity with _id = ${id} was not found in the ${collection}`
            + ` collection on the ${this.name} WebSQL database.`);
        }

        return entities[0];
      });
  }

  save(collection, entities) {
    const queries = [];
    let singular = false;

    if (!isArray(entities)) {
      singular = true;
      entities = [entities];
    }

    if (entities.length === 0) {
      return Promise.resolve(null);
    }

    entities = map(entities, (entity) => {
      queries.push([
        'REPLACE INTO #{collection} (key, value) VALUES (?, ?)',
        [entity[idAttribute], JSON.stringify(entity)]
      ]);

      return entity;
    });

    return this.openTransaction(collection, queries, null, true)
      .then(() => (singular ? entities[0] : entities));
  }

  removeById(collection, id) {
    const queries = [
      ['SELECT value FROM #{collection} WHERE key = ?', [id]],
      ['DELETE FROM #{collection} WHERE key = ?', [id]],
    ];
    return this.openTransaction(collection, queries, null, true)
      .then((response) => {
        const entities = response[0].result;
        let count = response[1].rowCount;
        count = count || entities.length;

        if (count === 0) {
          throw new NotFoundError(`An entity with _id = ${id} was not found in the ${collection}`
            + ` collection on the ${this.name} WebSQL database.`);
        }

        return entities[0];
      });
  }

  clear() {
    return this.openTransaction(
      masterCollectionName,
      'SELECT name AS value FROM #{collection} WHERE type = ?',
      ['table'],
      false
    )
      .then(response => response.result)
      .then((tables) => {
        // If there are no tables, return.
        if (tables.length === 0) {
          return null;
        }

        // Drop all tables. Filter tables first to avoid attempting to delete
        // system tables (which will fail).
        const queries = tables
          .filter(table => (/^[a-zA-Z0-9-]{1,128}/).test(table))
          .map(table => [`DROP TABLE IF EXISTS '${table}'`]);
        return this.openTransaction(masterCollectionName, queries, null, true);
      })
      .then(() => {
        dbCache = {};
        return null;
      });
  }

  static loadAdapter(name) {
    const db = new WebSQL(name);

    if (typeof isSupported !== 'undefined') {
      if (isSupported) {
        return Promise.resolve(db);
      }

      return Promise.resolve(undefined);
    }

    if (typeof global.openDatabase === 'undefined') {
      isSupported = false;
      return Promise.resolve(undefined);
    }

    return db.save('__testSupport', { _id: '1' })
      .then(() => {
        isSupported = true;
        return db;
      })
      .catch(() => {
        isSupported = false;
        return undefined;
      });
  }
}
<|endoftext|>


<commit_before>/**
 * @author alteredq / http://alteredqualia.com/
 */

THREE.EffectComposer = function ( renderer, renderTarget ) {

	this.renderer = renderer;

	if ( renderTarget === undefined ) {

		var parameters = {
			minFilter: THREE.LinearFilter,
			magFilter: THREE.LinearFilter,
			format: THREE.RGBAFormat,
			stencilBuffer: false
		};

		var size = renderer.getSize( new THREE.Vector2() );
		this._pixelRatio = renderer.getPixelRatio();
		this._width = size.width;
		this._height = size.height;

		renderTarget = new THREE.WebGLRenderTarget( this._width * this._pixelRatio, this._height * this._pixelRatio, parameters );
		renderTarget.texture.name = 'EffectComposer.rt1';

	} else {

		this._pixelRatio = 1;
		this._width = renderTarget.width;
		this._height = renderTarget.height;

	}

	this.renderTarget1 = renderTarget;
	this.renderTarget2 = renderTarget.clone();
	this.renderTarget2.texture.name = 'EffectComposer.rt2';

	this.writeBuffer = this.renderTarget1;
	this.readBuffer = this.renderTarget2;

	this.renderToScreen = true;

	this.passes = [];

	// dependencies

	if ( THREE.CopyShader === undefined ) {

		console.error( 'THREE.EffectComposer relies on THREE.CopyShader' );

	}

	if ( THREE.ShaderPass === undefined ) {

		console.error( 'THREE.EffectComposer relies on THREE.ShaderPass' );

	}

	this.copyPass = new THREE.ShaderPass( THREE.CopyShader );

	this.clock = new THREE.Clock();

};

Object.assign( THREE.EffectComposer.prototype, {

	swapBuffers: function () {

		var tmp = this.readBuffer;
		this.readBuffer = this.writeBuffer;
		this.writeBuffer = tmp;

	},

	addPass: function ( pass ) {

		this.passes.push( pass );
		pass.setSize( this._width * this._pixelRatio, this._height * this._pixelRatio );

	},

	insertPass: function ( pass, index ) {

		this.passes.splice( index, 0, pass );

	},

	isLastEnabledPass: function ( passIndex ) {

		for ( var i = passIndex + 1; i < this.passes.length; i ++ ) {

			if ( this.passes[ i ].enabled ) {

				return false;

			}

		}

		return true;

	},

	render: function ( deltaTime ) {

		// deltaTime value is in seconds

		if ( deltaTime === undefined ) {

			deltaTime = this.clock.getDelta();

		}

		var currentRenderTarget = this.renderer.getRenderTarget();

		var maskActive = false;

		var pass, i, il = this.passes.length;

		for ( i = 0; i < il; i ++ ) {

			pass = this.passes[ i ];

			if ( pass.enabled === false ) continue;

			pass.renderToScreen = ( this.renderToScreen && this.isLastEnabledPass( i ) );
			pass.render( this.renderer, this.writeBuffer, this.readBuffer, deltaTime, maskActive );

			if ( pass.needsSwap ) {

				if ( maskActive ) {

					var context = this.renderer.getContext();
					var stencil = this.renderer.state.buffers.stencil;

					//context.stencilFunc( context.NOTEQUAL, 1, 0xffffffff );
					stencil.setFunc( context.NOTEQUAL, 1, 0xffffffff );

					this.copyPass.render( this.renderer, this.writeBuffer, this.readBuffer, deltaTime );

					//context.stencilFunc( context.EQUAL, 1, 0xffffffff );
					stencil.setFunc( context.EQUAL, 1, 0xffffffff );

				}

				this.swapBuffers();

			}

			if ( THREE.MaskPass !== undefined ) {

				if ( pass instanceof THREE.MaskPass ) {

					maskActive = true;

				} else if ( pass instanceof THREE.ClearMaskPass ) {

					maskActive = false;

				}

			}

		}

		this.renderer.setRenderTarget( currentRenderTarget );

	},

	reset: function ( renderTarget ) {

		if ( renderTarget === undefined ) {

			var size = this.renderer.getSize( new THREE.Vector2() );
			this._pixelRatio = this.renderer.getPixelRatio();
			this._width = size.width;
			this._height = size.height;

			renderTarget = this.renderTarget1.clone();
			renderTarget.setSize( this._width * this._pixelRatio, this._height * this._pixelRatio );

		}

		this.renderTarget1.dispose();
		this.renderTarget2.dispose();
		this.renderTarget1 = renderTarget;
		this.renderTarget2 = renderTarget.clone();

		this.writeBuffer = this.renderTarget1;
		this.readBuffer = this.renderTarget2;

	},

	setSize: function ( width, height ) {

		this._width = width;
		this._height = height;

		var effectiveWidth = this._width * this._pixelRatio;
		var effectiveHeight = this._height * this._pixelRatio;

		this.renderTarget1.setSize( effectiveWidth, effectiveHeight );
		this.renderTarget2.setSize( effectiveWidth, effectiveHeight );

		for ( var i = 0; i < this.passes.length; i ++ ) {

			this.passes[ i ].setSize( effectiveWidth, effectiveHeight );

		}

	},

	setPixelRatio: function ( pixelRatio ) {

		this._pixelRatio = pixelRatio;

		this.setSize( this._width, this._height );

	}

} );

THREE.Pass = function () {

	// if set to true, the pass is processed by the composer
	this.enabled = true;

	// if set to true, the pass indicates to swap read and write buffer after rendering
	this.needsSwap = true;

	// if set to true, the pass clears its buffer before rendering
	this.clear = false;

	// if set to true, the result of the pass is rendered to screen. This is set automatically by EffectComposer.
	this.renderToScreen = false;

};

Object.assign( THREE.Pass.prototype, {

	setSize: function ( /* width, height */ ) {},

	render: function ( /* renderer, writeBuffer, readBuffer, deltaTime, maskActive */ ) {

		console.error( 'THREE.Pass: .render() must be implemented in derived pass.' );

	}

} );

// Helper for passes that need to fill the viewport with a single quad.
THREE.Pass.FullScreenQuad = ( function () {

	var camera = new THREE.OrthographicCamera( - 1, 1, 1, - 1, 0, 1 );
	var geometry = new THREE.PlaneBufferGeometry( 2, 2 );

	var FullScreenQuad = function ( material ) {

		this._mesh = new THREE.Mesh( geometry, material );

	};

	Object.defineProperty( FullScreenQuad.prototype, 'material', {

		get: function () {

			return this._mesh.material;

		},

		set: function ( value ) {

			this._mesh.material = value;

		}

	} );

	Object.assign( FullScreenQuad.prototype, {

		render: function ( renderer ) {

			renderer.render( this._mesh, camera );

		}

	} );

	return FullScreenQuad;

} )();
<commit_msg>Updated libs<commit_after>/**
 * @author alteredq / http://alteredqualia.com/
 */

THREE.EffectComposer = function ( renderer, renderTarget ) {

	this.renderer = renderer;

	if ( renderTarget === undefined ) {

		var parameters = {
			minFilter: THREE.LinearFilter,
			magFilter: THREE.LinearFilter,
			format: THREE.RGBAFormat,
			stencilBuffer: false
		};

		var size = renderer.getSize( new THREE.Vector2() );
		this._pixelRatio = renderer.getPixelRatio();
		this._width = size.width;
		this._height = size.height;

		renderTarget = new THREE.WebGLRenderTarget( this._width * this._pixelRatio, this._height * this._pixelRatio, parameters );
		renderTarget.texture.name = 'EffectComposer.rt1';

	} else {

		this._pixelRatio = 1;
		this._width = renderTarget.width;
		this._height = renderTarget.height;

	}

	this.renderTarget1 = renderTarget;
	this.renderTarget2 = renderTarget.clone();
	this.renderTarget2.texture.name = 'EffectComposer.rt2';

	this.writeBuffer = this.renderTarget1;
	this.readBuffer = this.renderTarget2;

	this.renderToScreen = true;

	this.passes = [];

	// dependencies

	if ( THREE.CopyShader === undefined ) {

		console.error( 'THREE.EffectComposer relies on THREE.CopyShader' );

	}

	if ( THREE.ShaderPass === undefined ) {

		console.error( 'THREE.EffectComposer relies on THREE.ShaderPass' );

	}

	this.copyPass = new THREE.ShaderPass( THREE.CopyShader );

	this.clock = new THREE.Clock();

};

Object.assign( THREE.EffectComposer.prototype, {

	swapBuffers: function () {

		var tmp = this.readBuffer;
		this.readBuffer = this.writeBuffer;
		this.writeBuffer = tmp;

	},

	addPass: function ( pass ) {

		this.passes.push( pass );
		pass.setSize( this._width * this._pixelRatio, this._height * this._pixelRatio );

	},

	insertPass: function ( pass, index ) {

		this.passes.splice( index, 0, pass );

	},

	isLastEnabledPass: function ( passIndex ) {

		for ( var i = passIndex + 1; i < this.passes.length; i ++ ) {

			if ( this.passes[ i ].enabled ) {

				return false;

			}

		}

		return true;

	},

	render: function ( deltaTime ) {

		// deltaTime value is in seconds

		if ( deltaTime === undefined ) {

			deltaTime = this.clock.getDelta();

		}

		var currentRenderTarget = this.renderer.getRenderTarget();

		var maskActive = false;

		var pass, i, il = this.passes.length;

		for ( i = 0; i < il; i ++ ) {

			pass = this.passes[ i ];

			if ( pass.enabled === false ) continue;

			pass.renderToScreen = ( this.renderToScreen && this.isLastEnabledPass( i ) );
			pass.render( this.renderer, this.writeBuffer, this.readBuffer, deltaTime, maskActive );

			if ( pass.needsSwap ) {

				if ( maskActive ) {

					var context = this.renderer.getContext();
					var stencil = this.renderer.state.buffers.stencil;

					//context.stencilFunc( context.NOTEQUAL, 1, 0xffffffff );
					stencil.setFunc( context.NOTEQUAL, 1, 0xffffffff );

					this.copyPass.render( this.renderer, this.writeBuffer, this.readBuffer, deltaTime );

					//context.stencilFunc( context.EQUAL, 1, 0xffffffff );
					stencil.setFunc( context.EQUAL, 1, 0xffffffff );

				}

				this.swapBuffers();

			}

			if ( THREE.MaskPass !== undefined ) {

				if ( pass instanceof THREE.MaskPass ) {

					maskActive = true;

				} else if ( pass instanceof THREE.ClearMaskPass ) {

					maskActive = false;

				}

			}

		}

		this.renderer.setRenderTarget( currentRenderTarget );

	},

	reset: function ( renderTarget ) {

		if ( renderTarget === undefined ) {

			var size = this.renderer.getSize( new THREE.Vector2() );
			this._pixelRatio = this.renderer.getPixelRatio();
			this._width = size.width;
			this._height = size.height;

			renderTarget = this.renderTarget1.clone();
			renderTarget.setSize( this._width * this._pixelRatio, this._height * this._pixelRatio );

		}

		this.renderTarget1.dispose();
		this.renderTarget2.dispose();
		this.renderTarget1 = renderTarget;
		this.renderTarget2 = renderTarget.clone();

		this.writeBuffer = this.renderTarget1;
		this.readBuffer = this.renderTarget2;

	},

	setSize: function ( width, height ) {

		this._width = width;
		this._height = height;

		var effectiveWidth = this._width * this._pixelRatio;
		var effectiveHeight = this._height * this._pixelRatio;

		this.renderTarget1.setSize( effectiveWidth, effectiveHeight );
		this.renderTarget2.setSize( effectiveWidth, effectiveHeight );

		for ( var i = 0; i < this.passes.length; i ++ ) {

			this.passes[ i ].setSize( effectiveWidth, effectiveHeight );

		}

	},

	setPixelRatio: function ( pixelRatio ) {

		this._pixelRatio = pixelRatio;

		this.setSize( this._width, this._height );

	}

} );

THREE.Pass = function () {

	// if set to true, the pass is processed by the composer
	this.enabled = true;

	// if set to true, the pass indicates to swap read and write buffer after rendering
	this.needsSwap = true;

	// if set to true, the pass clears its buffer before rendering
	this.clear = false;

	// if set to true, the result of the pass is rendered to screen. This is set automatically by EffectComposer.
	this.renderToScreen = false;

};

Object.assign( THREE.Pass.prototype, {

	setSize: function ( /* width, height */ ) {},

	render: function ( /* renderer, writeBuffer, readBuffer, deltaTime, maskActive */ ) {

		console.error( 'THREE.Pass: .render() must be implemented in derived pass.' );

	}

} );

// Helper for passes that need to fill the viewport with a single quad.
THREE.Pass.FullScreenQuad = ( function () {

	var camera = new THREE.OrthographicCamera( - 1, 1, 1, - 1, 0, 1 );
	var geometry = new THREE.PlaneBufferGeometry( 2, 2 );

	var FullScreenQuad = function ( material ) {

		this._mesh = new THREE.Mesh( geometry, material );

	};

	Object.defineProperty( FullScreenQuad.prototype, 'material', {

		get: function () {

			return this._mesh.material;

		},

		set: function ( value ) {

			this._mesh.material = value;

		}

	} );

	Object.assign( FullScreenQuad.prototype, {

		dispose: function () {

			this._mesh.geometry.dispose();

		},

		render: function ( renderer ) {

			renderer.render( this._mesh, camera );

		}

	} );

	return FullScreenQuad;

} )();
<|endoftext|>


<commit_before>/*
 *
 * UI5Strap
 *
 * ScrollContainer Renderer
 *
 * Author: Jan Philipp Knöller
 *
 * Copyright (c) 2013 Jan Philipp Knöller
 *
 * http://pksoftware.de
 *
 * Get the latest version: https://github.com/pks5/ui5strap
 *
 * Released under Apache2 license: http://www.apache.org/licenses/LICENSE-2.0.txt
 *
 */

(function(){

	jQuery.sap.declare("de_pksoftware.ui5strap.ex.ScrollContainerRenderer");

	de_pksoftware.ui5strap.ex.ScrollContainerRenderer = {};

	de_pksoftware.ui5strap.ex.ScrollContainerRenderer.render = function(rm, oControl) {
		var content = oControl.getContent();

		//TODO: implement as classes (first, we need a ui5strap stylesheet)
		var elStyle = 'width:100%; height:100%;';

		elStyle += 'overflow-x:' + (oControl.getHorizontal() ? 'auto' : 'hidden') + ';';
		elStyle += 'overflow-y:' + (oControl.getVertical() ? 'auto' : 'hidden') + ';';

		rm.write("
");

		for(var i = 0; i < content.length; i++){
			rm.renderControl(content[i]);
		}

		rm.write("
");

	};

}());<commit_msg>ios scrolling<commit_after>/*
 *
 * UI5Strap
 *
 * ScrollContainer Renderer
 *
 * Author: Jan Philipp Knöller
 *
 * Copyright (c) 2013 Jan Philipp Knöller
 *
 * http://pksoftware.de
 *
 * Get the latest version: https://github.com/pks5/ui5strap
 *
 * Released under Apache2 license: http://www.apache.org/licenses/LICENSE-2.0.txt
 *
 */

(function(){

	jQuery.sap.declare("de_pksoftware.ui5strap.ex.ScrollContainerRenderer");

	de_pksoftware.ui5strap.ex.ScrollContainerRenderer = {};

	de_pksoftware.ui5strap.ex.ScrollContainerRenderer.render = function(rm, oControl) {
		var content = oControl.getContent();

		//TODO: implement as classes (first, we need a ui5strap stylesheet)
		var elStyle = 'width:100%; height:100%;-webkit-overflow-scrolling: touch;';

		elStyle += 'overflow-x:' + (oControl.getHorizontal() ? 'scroll' : 'hidden') + ';';
		elStyle += 'overflow-y:' + (oControl.getVertical() ? 'scroll' : 'hidden') + ';';

		rm.write("
");

		for(var i = 0; i < content.length; i++){
			rm.renderControl(content[i]);
		}

		rm.write("
");

	};

}());<|endoftext|>


<commit_before>/*jshint browser: true, devel: true, camelcase: true, curly: true, eqeqeq: true, undef: true, unused: true, strict: true */
/*global $:false */

$(document).ready(function() {

		'use strict';

	;( function ( win, doc, lS )
	{

		var MIN_TO_WORK = 30,
			APP_TITLE = 'Time Tracker',

			myAudio = new Audio("alert.mp3"),
			worked = 0,
			minToWork,
			nextCycle,
			startTime,
			startHour,
			startMin,
			cycle,
			count = 0;

		var init = function()
		{
			if (lS.cycle)
			{
				cycle = lS.cycle;
				minToWork = cycle;
			}
			else
			{
				minToWork = MIN_TO_WORK;
				cycle = minToWork;
				nextCycle = cycle;
			}

			$("#timer span").countdown({
				until: 0,
				format: "MS",
				compact: true,
				onExpiry: openAlert,
				onTick: updateTitle,
			});

			// Get stuff from lS
			if (typeof (Storage) !== undefined)
			{
				var i = 0;
				while (i < lS.length)
				{
					if (lS.key(i) === "htt_count" || lS.key(i).indexOf("htt_task") === -1) { continue; }
					$("#done").prepend( lS.getItem( lS.key(i) ) );
				}
				// check if the user is new
				if (lS.count)
				{
					$(".count").text(lS.count);
					count = lS.count;
					$("body").addClass("list");
				}
				else
				{
					$("body").addClass("new");
				}
			}

			// Tinycon.setOptions({
			// 	width: 7,
			// 	height: 9,
			// 	font: '10px arial',
			// 	colour: '#ffffff',
			// 	background: '#549A2F',
			// 	fallback: true
			// });

			updateTitle(APP_TITLE);
		};

		var openAlert = function()
		{
			myAudio.play();
			$("body").removeClass("working").addClass("log");
			$("#new").prop("checked", true);
			$("#what").focus();
		};

		var logTime = function()
		{
			$("body").removeClass("working").addClass("log");
			$("#new").prop("checked", true);
			$("#what").focus();
		};

		var cancelTimer = function(where)
		{
			$("body").removeClass("working").addClass(where);
		};

		var updateTitle = function(title)
		{
			if (!!title[5])
			{
				doc.title = title[5]+":"+title[6]+" - "+APP_TITLE;
				Tinycon.setBubble(title[5]);
			}
			else if (!!title)
			{
				doc.title = title;
				Tinycon.setBubble();
			}
			else
			{
				doc.title = APP_TITLE;
				Tinycon.setBubble();
			}
		};

		// set the cycle length
		$(".set-cycle").on("click", function()
		{
			$("body").addClass("settings-open");
			$("#cycle").val(lS.cycle);
			return false;
		});

		// set the next cycle length
		$(".set-next").on("click", function()
		{
			$("body").addClass("settings-open");
			$("#nextCycle").val(lS.nextCycle);
			return false;
		});

		// only allow numbers to be input into the fields
		$("#cycle").on("input", function()
		{
			this.value = this.value.replace(/[^0-9]/g, "");
			cycle = $(this).val();
		});

		$("#nextCycle").on("input", function()
		{
			this.value = this.value.replace(/[^0-9]/g, "");
			nextCycle = $(this).val();
		});

		// do magic when the cycle length form is submitted
		$("#cycle-form").submit(function()
		{
			if($("#cycle").val() === "")
			{
				$("#cycle").val(MIN_TO_WORK);
				lS.setItem("htt_cycle", MIN_TO_WORK);
				lS.setItem("htt_nextCycle", MIN_TO_WORK);
			}
			else
			{
				lS.setItem("htt_cycle", cycle);
				lS.setItem("htt_nextCycle", cycle);
			}
			minToWork = lS.cycle;
			$("body").removeClass("settings-open");
			return false;
		});

		// magic when the next cycle length form is submitted
		$("#next-form").submit(function()
		{
			lS.setItem("htt_nextCycle", nextCycle);
			nextCycle = lS.nextCycle;
			$("body").removeClass("settings-open");
			return false;
		});

		// close dropdown when clicked anywhere but inside
		$("#settings .overlay").on("click", function()
		{
			$("body").removeClass("settings-open");
			$("#cycle").val(lS.cycle);
			$("#nextCycle").val(lS.nextCycle);
		});

		// start the timer
		$(".btn-start").on("click", function()
		{
			startTime = new Date();
			startHour = ("0" + startTime.getHours()).slice(-2);
			startMin = ("0" + startTime.getMinutes()).slice(-2);
			$("body").removeClass().addClass("working");
			$("#timer span").countdown("option", {
				until: +cycle*60,
				onExpiry: openAlert
			});
			$("#actions span").hide();
			$("#reset").show();
			return false;
		});

		// user decides he's done
		$("#end").on("click", function()
		{
			worked = $("#timer span").countdown("getTimes");
			$("#timer span").countdown("option", {until: 0, onExpiry: logTime});
			updateTitle(APP_TITLE);
			return false;
		});

		// check that there are previous tasks already done
		$("#cancel").on("click", function()
		{
			if (lS.count)
			{
				$("#timer span").countdown("option", {until: 0, onExpiry: null});
				cancelTimer("list");
			}
			else
			{
				$("#timer span").countdown("option", {until: 0, onExpiry: null});
				cancelTimer("new");
			}
			return false;
		});

		// do some magic when form is submitted
		$("#logActivity").submit(function()
		{
			var task = $("#what").val(),
				d = new Date(),
				hour = ("0" + d.getHours()).slice(-2),
				min = ("0" + d.getMinutes()).slice(-2),
				timeWorked;

			count++;
			lS.count = count;

			myAudio.currentTime = 0;
			myAudio.pause();
			if (typeof worked[5] !== "number")
			{
				timeWorked = 0;
			}
			else
			{
				timeWorked = worked[5];
			}

			var text = '
' +
					'
' + startHour + ':' + startMin + ' - ' + hour + ':' + min + '
' +
					'
' + task + '' + (cycle - timeWorked) + ' minutes
' +
				'
';
			// if these differ, get them to be the same
			if (nextCycle !== cycle)
			{
				cycle = lS.nextCycle;
				lS.setItem("htt_cycle", lS.nextCycle);
			}

			// add lS keys
			lS.setItem("htt_task" + ("0" + count).slice(-2), text);

			// add new task to the top of the list
			$("#done").prepend(text);

			if ($("#new").is(":checked"))
			{
				$("#timer span").countdown("option", {until: +cycle*60});
				$("body").removeClass("log").addClass("working");
			}
			else
			{
				$("body").removeClass("log").addClass("list");
			}

			startTime = new Date();
			startHour = ("0" + startTime.getHours()).slice(-2);
			startMin = ("0" + startTime.getMinutes()).slice(-2);

			return false;
		});

		// TODO: .delete to be CSS based
		$("#done").on("mouseenter", "li[data-task]", function()
		{
			$(this).find("p").prepend("×");
			$(this).find(".delete").on("click", function() {
				var deleteThis = $(this).parent().parent().attr("data-task");
				$(this).parent().parent().remove();
				lS.removeItem(deleteThis);
			});
		});

		$("#done").on("mouseleave", "li", function()
		{
			$(this).find("span.delete").remove();
		});

		//ask user to confirm clearage
		$("#reset").on("click", function()
		{
			$(this).hide();
			$(this).siblings("span").show();
			return false;
		});

		// Get rid of tasks and count on lS
		var clearAllCycles = function()
		{
			var i = 0;
			while (i < lS.length)
			{
				if (lS.key(i) === "htt_nextCycle" || lS.key(i) === "htt_cycle") { continue; }
				lS.removeItem( lS.key(i) );
			}
			count = 0;
			$("#done").html("");
			$("body").removeClass().addClass("new");
			$(".count").text(count);
			$(this).parent().hide();
			$(this).parent().siblings("#reset").show();
			return false;
		};
		$("#actions .confirm").on("click", clearAllCycles());

		// Cancel clearage of lS
		var cancelCycle = function()
		{
			$(this).parent().hide();
			$(this).parent().siblings("#reset").show();
			return false;
		};
		$("#actions .cancel").on("click", cancelCycle());

		// Loop alert if browser tab is not active
		$(win).blur(function(){
			myAudio.addEventListener("ended", function()
			{
				this.currentTime = 0;
				this.play();
				(doc.title === APP_TITLE) ? updateTitle('▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉') : updateTitle(APP_TITLE);
			}, false);
		});

		//stop alert when browser tab is active
		$(win).focus(function(){
			myAudio.addEventListener("ended", function()
			{
				this.currentTime = 0;
				this.pause();
				updateTitle(APP_TITLE);
			}, false);
			myAudio.pause();
			myAudio.currentTime = 0;
		});

		init();

	} ( window, document, localStorage ) );

}); // doc.ready
<commit_msg>fixed bug with missing localStorage prexifes<commit_after>/*jshint browser: true, devel: true, camelcase: true, curly: true, eqeqeq: true, undef: true, unused: true, strict: true */
/*global $:false */

$(document).ready(function() {

		'use strict';

	;( function ( win, doc, lS )
	{

		var MIN_TO_WORK = 30,
			APP_TITLE = 'Time Tracker',

			myAudio = new Audio("alert.mp3"),
			worked = 0,
			minToWork,
			nextCycle,
			startTime,
			startHour,
			startMin,
			cycle,
			count = 0;

		var init = function()
		{
			if (lS.htt_cycle)
			{
				cycle = lS.htt_cycle;
				minToWork = cycle;
			}
			else
			{
				minToWork = MIN_TO_WORK;
				cycle = minToWork;
				nextCycle = cycle;
			}

			$("#timer span").countdown({
				until: 0,
				format: "MS",
				compact: true,
				onExpiry: openAlert,
				onTick: updateTitle,
			});

			// Get stuff from lS
			if (typeof (Storage) !== undefined)
			{
				var i = 0;
				while (i < lS.length)
				{
					if (lS.key(i) === "htt_count" || lS.key(i).indexOf("htt_task") === -1) { continue; }
					$("#done").prepend( lS.getItem( lS.key(i) ) );
				}
				// check if the user is new
				if (lS.htt_count)
				{
					$(".count").text(lS.htt_count);
					count = lS.htt_count;
					$("body").addClass("list");
				}
				else
				{
					$("body").addClass("new");
				}
			}

			// Tinycon.setOptions({
			// 	width: 7,
			// 	height: 9,
			// 	font: '10px arial',
			// 	colour: '#ffffff',
			// 	background: '#549A2F',
			// 	fallback: true
			// });

			updateTitle(APP_TITLE);
		};

		var openAlert = function()
		{
			myAudio.play();
			$("body").removeClass("working").addClass("log");
			$("#new").prop("checked", true);
			$("#what").focus();
		};

		var logTime = function()
		{
			$("body").removeClass("working").addClass("log");
			$("#new").prop("checked", true);
			$("#what").focus();
		};

		var cancelTimer = function(where)
		{
			$("body").removeClass("working").addClass(where);
		};

		var updateTitle = function(title)
		{
			if (!!title[5])
			{
				doc.title = title[5]+":"+title[6]+" - "+APP_TITLE;
				Tinycon.setBubble(title[5]);
			}
			else if (!!title)
			{
				doc.title = title;
				Tinycon.setBubble();
			}
			else
			{
				doc.title = APP_TITLE;
				Tinycon.setBubble();
			}
		};

		// set the cycle length
		$(".set-cycle").on("click", function()
		{
			$("body").addClass("settings-open");
			$("#cycle").val(lS.htt_cycle);
			return false;
		});

		// set the next cycle length
		$(".set-next").on("click", function()
		{
			$("body").addClass("settings-open");
			$("#nextCycle").val(lS.htt_nextCycle);
			return false;
		});

		// only allow numbers to be input into the fields
		$("#cycle").on("input", function()
		{
			this.value = this.value.replace(/[^0-9]/g, "");
			cycle = $(this).val();
		});

		$("#nextCycle").on("input", function()
		{
			this.value = this.value.replace(/[^0-9]/g, "");
			nextCycle = $(this).val();
		});

		// do magic when the cycle length form is submitted
		$("#cycle-form").submit(function()
		{
			if($("#cycle").val() === "")
			{
				$("#cycle").val(MIN_TO_WORK);
				lS.setItem("htt_cycle", MIN_TO_WORK);
				lS.setItem("htt_nextCycle", MIN_TO_WORK);
			}
			else
			{
				lS.setItem("htt_cycle", cycle);
				lS.setItem("htt_nextCycle", cycle);
			}
			minToWork = lS.htt_cycle;
			$("body").removeClass("settings-open");
			return false;
		});

		// magic when the next cycle length form is submitted
		$("#next-form").submit(function()
		{
			lS.setItem("htt_nextCycle", nextCycle);
			nextCycle = lS.htt_nextCycle;
			$("body").removeClass("settings-open");
			return false;
		});

		// close dropdown when clicked anywhere but inside
		$("#settings .overlay").on("click", function()
		{
			$("body").removeClass("settings-open");
			$("#cycle").val(lS.htt_cycle);
			$("#nextCycle").val(lS.htt_nextCycle);
		});

		// start the timer
		$(".btn-start").on("click", function()
		{
			startTime = new Date();
			startHour = ("0" + startTime.getHours()).slice(-2);
			startMin = ("0" + startTime.getMinutes()).slice(-2);
			$("body").removeClass().addClass("working");
			$("#timer span").countdown("option", {
				until: +cycle*60,
				onExpiry: openAlert
			});
			$("#actions span").hide();
			$("#reset").show();
			return false;
		});

		// user decides he's done
		$("#end").on("click", function()
		{
			worked = $("#timer span").countdown("getTimes");
			$("#timer span").countdown("option", {until: 0, onExpiry: logTime});
			updateTitle(APP_TITLE);
			return false;
		});

		// check that there are previous tasks already done
		$("#cancel").on("click", function()
		{
			if (lS.htt_count)
			{
				$("#timer span").countdown("option", {until: 0, onExpiry: null});
				cancelTimer("list");
			}
			else
			{
				$("#timer span").countdown("option", {until: 0, onExpiry: null});
				cancelTimer("new");
			}
			return false;
		});

		// do some magic when form is submitted
		$("#logActivity").submit(function()
		{
			var task = $("#what").val(),
				d = new Date(),
				hour = ("0" + d.getHours()).slice(-2),
				min = ("0" + d.getMinutes()).slice(-2),
				timeWorked;

			count++;
			lS.htt_count = count;

			myAudio.currentTime = 0;
			myAudio.pause();
			if (typeof worked[5] !== "number")
			{
				timeWorked = 0;
			}
			else
			{
				timeWorked = worked[5];
			}

			var text = '
' +
					'
' + startHour + ':' + startMin + ' - ' + hour + ':' + min + '
' +
					'
' + task + '' + (cycle - timeWorked) + ' minutes
' +
				'
';
			// if these differ, get them to be the same
			if (nextCycle !== cycle)
			{
				cycle = lS.htt_nextCycle;
				lS.setItem("htt_cycle", lS.htt_nextCycle);
			}

			// add lS keys
			lS.setItem("htt_task" + ("0" + count).slice(-2), text);

			// add new task to the top of the list
			$("#done").prepend(text);

			if ($("#new").is(":checked"))
			{
				$("#timer span").countdown("option", {until: +cycle*60});
				$("body").removeClass("log").addClass("working");
			}
			else
			{
				$("body").removeClass("log").addClass("list");
			}

			startTime = new Date();
			startHour = ("0" + startTime.getHours()).slice(-2);
			startMin = ("0" + startTime.getMinutes()).slice(-2);

			return false;
		});

		// TODO: .delete to be CSS based
		$("#done").on("mouseenter", "li[data-task]", function()
		{
			$(this).find("p").prepend("×");
			$(this).find(".delete").on("click", function() {
				var deleteThis = $(this).parent().parent().attr("data-task");
				$(this).parent().parent().remove();
				lS.removeItem(deleteThis);
			});
		});

		$("#done").on("mouseleave", "li", function()
		{
			$(this).find("span.delete").remove();
		});

		//ask user to confirm clearage
		$("#reset").on("click", function()
		{
			$(this).hide();
			$(this).siblings("span").show();
			return false;
		});

		// Get rid of tasks and count on lS
		var clearAllCycles = function()
		{
			var i = 0;
			while (i < lS.length)
			{
				if (lS.key(i) === "htt_nextCycle" || lS.key(i) === "htt_cycle") { continue; }
				lS.removeItem( lS.key(i) );
			}
			count = 0;
			$("#done").html("");
			$("body").removeClass().addClass("new");
			$(".count").text(count);
			$(this).parent().hide();
			$(this).parent().siblings("#reset").show();
			return false;
		};
		$("#actions .confirm").on("click", clearAllCycles());

		// Cancel clearage of lS
		var cancelCycle = function()
		{
			$(this).parent().hide();
			$(this).parent().siblings("#reset").show();
			return false;
		};
		$("#actions .cancel").on("click", cancelCycle());

		// Loop alert if browser tab is not active
		$(win).blur(function(){
			myAudio.addEventListener("ended", function()
			{
				this.currentTime = 0;
				this.play();
				(doc.title === APP_TITLE) ? updateTitle('▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉▉') : updateTitle(APP_TITLE);
			}, false);
		});

		//stop alert when browser tab is active
		$(win).focus(function(){
			myAudio.addEventListener("ended", function()
			{
				this.currentTime = 0;
				this.pause();
				updateTitle(APP_TITLE);
			}, false);
			myAudio.pause();
			myAudio.currentTime = 0;
		});

		init();

	} ( window, document, localStorage ) );

}); // doc.ready
<|endoftext|>


<commit_before>'use strict';

angular.module('myapp')
    .controller('KeyController',['$scope','CalculateService',function($scope,CalculateService){

        $scope.keys = [1,2,3,4,5,6,7,8,9,0,'+','-','*','/','=','C'];
        $scope.output = '';

        $scope.press = function(key){
            $scope.output = calculate(key);
        }

        function calculate(key){
         if(typeof key == 'number'){
             if(typeof $scope.output != "number"){
                return key;
             }else{
                 return $scope.output*10+key;
             }
         }else{
             if(typeof key != '' && key != 'C' && key != '='){
                CalculateService.value1 = $scope.output;
                CalculateService.operator = key;
                return key;

             }

             if( key == '='){

                 return CalculateService.doCalculate($scope.output);
             }

             if(key == 'C'){
                 return '';
             }

         }
        }

    }])<commit_msg>keypad changes<commit_after>'use strict';

angular.module('myapp')
    .controller('KeyController',['$scope','CalculateService',function($scope,CalculateService){

        $scope.keys = [1,2,3,"+",4,5,6,"-",7,8,9,"*","C",0,'=','/'];
        $scope.output = '';

        $scope.press = function(key){
            $scope.output = calculate(key);
        }

        function calculate(key){
         if(typeof key == 'number'){
             if(typeof $scope.output != "number"){
                return key;
             }else{
                 return $scope.output*10+key;
             }
         }else{
             if(typeof key != '' && key != 'C' && key != '='){
                CalculateService.value1 = $scope.output;
                CalculateService.operator = key;
                return key;

             }

             if( key == '='){

                 return CalculateService.doCalculate($scope.output);
             }

             if(key == 'C'){
                 return '';
             }

         }
        }

    }])
<|endoftext|>


<commit_before>angular
  .module('app', ['ui.router', 'ngResource', 'templates'])
  .config(function($stateProvider, $urlRouterProvider) {
    $stateProvider
      .state('projects', {
        templateUrl: 'navbar/navbar.html',
        controller: 'ProjectsController as ctrl'
      })
      .state('projects.index', {
        url: '/',
        templateUrl: 'projects/index.html',
        controller: 'ProjectsController as ctrl'
      })
      .state('projects.new', {
        url: 'projects/new',
        templateUrl: 'projects/new.html',
        controller: 'ProjectsController as ctrl'
      })
      .state('projects.show', {
        url: 'projects/:id',
        templateUrl: 'projects/show.html',
        controller: 'ProjectsController as ctrl'
      })
      .state('projects.edit', {
        url: 'projects/:id/edit',
        templateUrl: 'projects/edit.html',
        controller: 'ProjectsController as ctrl'
      });
    $urlRouterProvider.otherwise('/');
});<commit_msg>Added '/' before the nested projects urls<commit_after>angular
  .module('app', ['ui.router', 'ngResource', 'templates'])
  .config(function($stateProvider, $urlRouterProvider) {
    $stateProvider
      .state('projects', {
        templateUrl: 'navbar/navbar.html',
        controller: 'ProjectsController as ctrl'
      })
      .state('projects.index', {
        url: '/',
        templateUrl: 'projects/index.html',
        controller: 'ProjectsController as ctrl'
      })
      .state('projects.new', {
        url: '/projects/new',
        templateUrl: 'projects/new.html',
        controller: 'ProjectsController as ctrl'
      })
      .state('projects.show', {
        url: '/projects/:id',
        templateUrl: 'projects/show.html',
        controller: 'ProjectsController as ctrl'
      })
      .state('projects.edit', {
        url: '/projects/:id/edit',
        templateUrl: 'projects/edit.html',
        controller: 'ProjectsController as ctrl'
      });
    $urlRouterProvider.otherwise('/');
});<|endoftext|>


<commit_before>var format = require('../../utils/format');
var Timer = require('../../stats/timer');
var debug = require('debug')('windshaft:renderer:pg_mvt');
var SubstitutionTokens = require('../../utils/substitution_tokens');
var geojsonUtils = require('../../utils/geojson_utils');

/// CLASS: pg_mvt Renderer
//
/// A renderer for a given MapConfig layer
///
function Renderer(layers, sql, attrs, options) {
    options = options || {};

    this.sql = sql;
    this.attrs = attrs;
    this.layers = layers;

    this.tile_size = options.tileSize || 256;
    this.tile_max_geosize = options.maxGeosize || 40075017; // earth circumference in webmercator 3857
    this.buffer_size = options.bufferSize || 0;
    this.mvt_extent = options.mvt_extent || 4096;
}

module.exports = Renderer;

Renderer.prototype = {
    /// API: renders a tile with the Renderer configuration
    /// @param x tile x coordinate
    /// @param y tile y coordinate
    /// @param z tile zoom
    /// callback: will be called when done using nodejs protocol (err, data)
    getTile: function (z, x, y, callback) {
        var query = 'SELECT (';
        this.layers.forEach((layer, i) => {
            layer.id = layer.id || `layer${i}`;
            if (i >= 1) {
                query += ' || ';
            }
            query += `coalesce((\
                select st_asmvt(geom, '${layer.id}') FROM\
                (SELECT ST_AsMVTGeom(the_geom_webmercator, CDB_XYZ_Extent(${x},${y},${z}), ${this.mvt_extent}, 0, true) FROM (${layer.options.sql}) AS cdbq where the_geom_webmercator && CDB_XYZ_Extent(${x},${y},${z}) ) as geom where geom is not null\
                ), '')`;
        });
        query += ') AS st_asmvt';

        var timer = new Timer();
        timer.start('query');
        this.sql(query, function (err, data) {
            timer.end('query');
            if (err) {
                debug("Error running pg_mvt query " + query + ": " + err);
                if (err.message) {
                    err.message = "PgMvtRenderer: " + err.message;
                }
                callback(err);
            } else {
                callback(null, data.rows[0].st_asmvt, { 'Content-Type': 'application/x-protobuf' }, timer.getTimes());
            }
        });
    }
};
<commit_msg>Fix to append non-geo yet needed columns to the SQL query<commit_after>var format = require('../../utils/format');
var Timer = require('../../stats/timer');
var debug = require('debug')('windshaft:renderer:pg_mvt');
var SubstitutionTokens = require('../../utils/substitution_tokens');
var geojsonUtils = require('../../utils/geojson_utils');

/// CLASS: pg_mvt Renderer
//
/// A renderer for a given MapConfig layer
///
function Renderer(layers, sql, attrs, options) {
    options = options || {};

    this.sql = sql;
    this.attrs = attrs;
    this.layers = layers;

    this.tile_size = options.tileSize || 256;
    this.tile_max_geosize = options.maxGeosize || 40075017; // earth circumference in webmercator 3857
    this.buffer_size = options.bufferSize || 0;
    this.mvt_extent = options.mvt_extent || 4096;
}

module.exports = Renderer;

Renderer.prototype = {
    /// API: renders a tile with the Renderer configuration
    /// @param x tile x coordinate
    /// @param y tile y coordinate
    /// @param z tile zoom
    /// callback: will be called when done using nodejs protocol (err, data)
    getTile: function (z, x, y, callback) {
        var query = 'SELECT (';
        this.layers.forEach((layer, i) => {
            layer.id = layer.id || `layer${i}`;
            if (i >= 1) {
                query += ' || ';
            }
            var nonGeoColumns = geojsonUtils.getGeojsonProperties(layer.options).join(',');
            if (nonGeoColumns !== '') {
                nonGeoColumns += ',';
            }
            query += `coalesce((\
                select st_asmvt(geom, '${layer.id}') FROM\
                (SELECT ${nonGeoColumns} ST_AsMVTGeom(the_geom_webmercator, CDB_XYZ_Extent(${x},${y},${z}), ${this.mvt_extent}, 0, true) FROM (${layer.options.sql}) AS cdbq where the_geom_webmercator && CDB_XYZ_Extent(${x},${y},${z}) ) as geom where geom is not null\
                ), '')`;
        });
        query += ') AS st_asmvt';

        var timer = new Timer();
        timer.start('query');
        this.sql(query, function (err, data) {
            timer.end('query');
            if (err) {
                debug("Error running pg_mvt query " + query + ": " + err);
                if (err.message) {
                    err.message = "PgMvtRenderer: " + err.message;
                }
                callback(err);
            } else {
                callback(null, data.rows[0].st_asmvt, { 'Content-Type': 'application/x-protobuf' }, timer.getTimes());
            }
        });
    }
};
<|endoftext|>


<commit_before>//= require jquery
//= require jquery_ujs
//= require material-design-lite/material
//= require moment/moment
//= require moment/locale/zh-tw.js
//= require markdown/lib/markdown
//= require_tree ./templates
//= require cable

componentHandler.registerUpgradedCallback('MaterialLayout', function(e){
  var $form = document.querySelector('.submit-form')
  var $textArea = $form.querySelector('textarea')
  var $main = document.getElementById('main')

  $form.addEventListener('submit', handleSubmit.bind(this))
  $textArea.addEventListener('input', handleInput.bind(this))
  $textArea.addEventListener('keypress', handleKeyPress.bind(this))

  setInterval(updateTime, 5)

  function handleSubmit(e){
    e.preventDefault()
    sendMessage()
  }

  function handleInput(e) {
    var lines = e.target.value.split(/\r\n|\r|\n/).length
    if(lines > 10) lines = 10
    e.target.rows = lines
  }

  function handleKeyPress(e) {
    if(e.key == 'Enter' && !e.shiftKey){
      e.preventDefault()
      sendMessage()
    }
  }

  function sendMessage(){
    var trimed = $textArea.value.trim()
    if(trimed.length == 0) return
    App.chat.send({ content: trimed })
    $textArea.value = ''
  }

  function updateTime(){
    for (var time of document.querySelectorAll('[data-time]')) {
      time.childNodes[0].nodeValue = moment(time.dataset.time).fromNow()
    }
  }
})
<commit_msg>prevent CPU burst<commit_after>//= require jquery
//= require jquery_ujs
//= require material-design-lite/material
//= require moment/moment
//= require moment/locale/zh-tw.js
//= require markdown/lib/markdown
//= require_tree ./templates
//= require cable

componentHandler.registerUpgradedCallback('MaterialLayout', function(e){
  var $form = document.querySelector('.submit-form')
  var $textArea = $form.querySelector('textarea')
  var $main = document.getElementById('main')

  $form.addEventListener('submit', handleSubmit.bind(this))
  $textArea.addEventListener('input', handleInput.bind(this))
  $textArea.addEventListener('keypress', handleKeyPress.bind(this))

  setInterval(updateTime, 5000)

  function handleSubmit(e){
    e.preventDefault()
    sendMessage()
  }

  function handleInput(e) {
    var lines = e.target.value.split(/\r\n|\r|\n/).length
    if(lines > 10) lines = 10
    e.target.rows = lines
  }

  function handleKeyPress(e) {
    if(e.key == 'Enter' && !e.shiftKey){
      e.preventDefault()
      sendMessage()
    }
  }

  function sendMessage(){
    var trimed = $textArea.value.trim()
    if(trimed.length == 0) return
    App.chat.send({ content: trimed })
    $textArea.value = ''
  }

  function updateTime(){
    for (var time of document.querySelectorAll('[data-time]')) {
      time.childNodes[0].nodeValue = moment(time.dataset.time).fromNow()
    }
  }
})
<|endoftext|>


<commit_before>/**
 * JS supplement to the Sked PHP calendar library.
 *
 * @see https://github.com/CampusUnion/Sked
 */
(function($) {

    $(document).ready(function(){

        // Pluralize intervals (days, weeks, etc.) based on frequency
        $('.sked-form select[name="frequency"], .sked-form select[name="lead_time_num"]').change(function(){
            var bPlural = $(this).val() !== '1';
            var fnPluralString = function(){
                var strText = $(this).text();
                if (bPlural && strText !== '-' && !strText.match('s$'))
                    $(this).text(strText + 's');
                else if (!bPlural && strText.match('s$'))
                    $(this).text(strText.slice(0, -1));
            };
            $(this).siblings('select').children('option').each(fnPluralString);
        }).change();

        // Only show weekdays for weekly & monthly intervals
        $('.sked-form select[name="interval"]').change(function(){
            var bHide = ($(this).val() === '1' || $(this).val() === '');
            $('[name="weekdays[]"]').prop('disabled', bHide)
                .parents('.sked-input-wrapper')[bHide ? 'hide' : 'show']();
        }).change();

    });

})(jQuery);

// Tell dependency loaders we're here.
window.skedJsLoaded = true;
<commit_msg>Toggle recurring-event fields<commit_after>/**
 * JS supplement to the Sked PHP calendar library.
 *
 * @see https://github.com/CampusUnion/Sked
 */
(function($) {

    $(document).ready(function(){

        // Pluralize intervals (days, weeks, etc.) based on frequency
        $('.sked-form select[name="frequency"], .sked-form select[name="lead_time_num"]').change(function(){
            var bPlural = $(this).val() !== '1';
            var fnPluralString = function(){
                var strText = $(this).text();
                if (bPlural && strText !== '-' && !strText.match('s$'))
                    $(this).text(strText + 's');
                else if (!bPlural && strText.match('s$'))
                    $(this).text(strText.slice(0, -1));
            };
            $(this).siblings('select').children('option').each(fnPluralString);
        }).change();

        // Only show weekdays for weekly & monthly intervals
        $('.sked-form select[name="interval"]').change(function(){
            var bHide = ($(this).val() === '1' || $(this).val() === '');
            $('[name="weekdays[]"]').prop('disabled', bHide)
                .parents('.sked-input-wrapper')[bHide ? 'hide' : 'show']();
        }).change();

        // Toggle recurring-event fields based on
        $('.sked-form input[name="repeats"]').change(function(){
            if ($(this).is(':checked'))
                $('.sked-input-recurring').show();
            else
                $('.sked-input-recurring').hide();
        }).change();

    });

})(jQuery);

// Tell dependency loaders we're here.
window.skedJsLoaded = true;
<|endoftext|>


<commit_before>// This is a manifest file that'll be compiled into application.js, which will include all the files
// listed below.
//
// Any JavaScript/Coffee file within this directory, lib/assets/javascripts, vendor/assets/javascripts,
// or vendor/assets/javascripts of plugins, if any, can be referenced here using a relative path.
//
// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
// the compiled file.
//
// WARNING: THE FIRST BLANK LINE MARKS THE END OF WHAT'S TO BE PROCESSED, ANY BLANK LINE SHOULD
// GO AFTER THE REQUIRES BELOW.
//
//= require jquery
//= require jquery_ujs
//= require bootstrap-sprockets
//= require typeahead.min
//= require coderwall
//= require jquery.timeago
//= require jquery.datetimepicker
//= require emojione
//= require lodash
//= require gmaps/google
//= require_tree .
//= stub maps
//
<commit_msg>Don’t stub out the maps.js file for now<commit_after>// This is a manifest file that'll be compiled into application.js, which will include all the files
// listed below.
//
// Any JavaScript/Coffee file within this directory, lib/assets/javascripts, vendor/assets/javascripts,
// or vendor/assets/javascripts of plugins, if any, can be referenced here using a relative path.
//
// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
// the compiled file.
//
// WARNING: THE FIRST BLANK LINE MARKS THE END OF WHAT'S TO BE PROCESSED, ANY BLANK LINE SHOULD
// GO AFTER THE REQUIRES BELOW.
//
//= require jquery
//= require jquery_ujs
//= require bootstrap-sprockets
//= require typeahead.min
//= require coderwall
//= require jquery.timeago
//= require jquery.datetimepicker
//= require emojione
//= require lodash
//= require gmaps/google
//= require_tree .
<|endoftext|>


<commit_before>// This is a manifest file that'll be compiled into application.js, which will include all the files
// listed below.
//
// Any JavaScript/Coffee file within this directory, lib/assets/javascripts, vendor/assets/javascripts,
// or vendor/assets/javascripts of plugins, if any, can be referenced here using a relative path.
//
// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
// compiled file.
//
// Read Sprockets README (https://github.com/sstephenson/sprockets#sprockets-directives) for details
// about supported directives.
//

//= require jquery
//= require jquery_ujs
//= require foundation
//= require abracadabra
//= require datatables
//= require dataTables.foundation
//= require ace-builds/src/ace
//= require ace-builds/src/ext-beautify
//= require ace-builds/src/mode-csharp
//= require turbolinks
//= require_tree .

$(function(){
  $(document).foundation();
  $.abracadabra();
  $('table').dataTable({
    'language': {
      'url': '//cdn.datatables.net/plug-ins/9dcbecd42ad/i18n/Spanish.json'
    }
  });
  var editor;
  var beautify = require('ace/ext/beautify');
  $('.editor').each(function( index ) {
    editor = ace.edit(this);
    editor.getSession().setMode('ace/mode/csharp');
    beautify.beautify(editor.getSession());
    editor.setReadOnly(true);
  });
});
<commit_msg>no more beautify<commit_after>// This is a manifest file that'll be compiled into application.js, which will include all the files
// listed below.
//
// Any JavaScript/Coffee file within this directory, lib/assets/javascripts, vendor/assets/javascripts,
// or vendor/assets/javascripts of plugins, if any, can be referenced here using a relative path.
//
// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
// compiled file.
//
// Read Sprockets README (https://github.com/sstephenson/sprockets#sprockets-directives) for details
// about supported directives.
//

//= require jquery
//= require jquery_ujs
//= require foundation
//= require abracadabra
//= require datatables
//= require dataTables.foundation
//= require ace-builds/src/ace
//= require ace-builds/src/mode-csharp
//= require turbolinks
//= require_tree .

$(function(){
  $(document).foundation();
  $.abracadabra();
  $('table').dataTable({
    'language': {
      'url': '//cdn.datatables.net/plug-ins/9dcbecd42ad/i18n/Spanish.json'
    }
  });
  var editor;
  $('.editor').each(function( index ) {
    editor = ace.edit(this);
    editor.getSession().setMode('ace/mode/csharp');
    editor.setReadOnly(false);
  });
});
<|endoftext|>


<commit_before>// This is a manifest file that'll be compiled into application.js, which will include all the files
// listed below.
//
// Any JavaScript/Coffee file within this directory, lib/assets/javascripts, vendor/assets/javascripts,
// or vendor/assets/javascripts of plugins, if any, can be referenced here using a relative path.
//
// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
// compiled file.
//
// Read Sprockets README (https://github.com/sstephenson/sprockets#sprockets-directives) for details
// about supported directives.
//
//= require jquery
//= require jquery_ujs
//= require turbolinks
//= require_tree ./global
<commit_msg>changed stuff<commit_after>// This is a manifest file that'll be compiled into application.js, which will include all the files
// listed below.
//
// Any JavaScript/Coffee file within this directory, lib/assets/javascripts, vendor/assets/javascripts,
// or vendor/assets/javascripts of plugins, if any, can be referenced here using a relative path.
//
// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
// compiled file.
//
// Read Sprockets README (https://github.com/sstephenson/sprockets#sprockets-directives) for details
// about supported directives.
//
//= require jquery
//= require jquery_ujs
//= require turbolinks
//= require_tree .<|endoftext|>


<commit_before>//= require jquery
//= require bootstrap-sprockets
//= require chartkick
<commit_msg>removed chartkick<commit_after>//= require jquery
//= require bootstrap-sprockets
<|endoftext|>


<commit_before>// This is a manifest file that'll be compiled into application.js, which will include all the files
// listed below.
//
// Any JavaScript/Coffee file within this directory, lib/assets/javascripts, vendor/assets/javascripts,
// or vendor/assets/javascripts of plugins, if any, can be referenced here using a relative path.
//
// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
// compiled file.
//
// Read Sprockets README (https://github.com/sstephenson/sprockets#sprockets-directives) for details
// about supported directives.
//
//= require jquery
//= require jquery_ujs
//= require chatlogs
//= require bootstrap
//= require turbolinks
//= require sidebar
<commit_msg>heroku work<commit_after>// This is a manifest file that'll be compiled into application.js, which will include all the files
// listed below.
//
// Any JavaScript/Coffee file within this directory, lib/assets/javascripts, vendor/assets/javascripts,
// or vendor/assets/javascripts of plugins, if any, can be referenced here using a relative path.
//
// It's not advisable to add code directly here, but if you do, it'll appear at the bottom of the
// compiled file.
//
// Read Sprockets README (https://github.com/sstephenson/sprockets#sprockets-directives) for details
// about supported directives.
//
//= require jquery
//= require jquery_ujs
//= require bootstrap
//= require turbolinks
<|endoftext|>