<commit_before>/**
 * Created by Lukas on 15.01.2016.
 */
var app = angular.module('loggify', ['ngMaterial']);

app.config(
    function($mdThemingProvider) {
        $mdThemingProvider.theme('default')
            .primaryPalette('deep-purple')
            .accentPalette('cyan')
            .dark();
    }
);

app.controller('AppController', function($http, $location, $window, $mdToast, $log) {
    var vm = this;
    vm.uploader = true;
    vm.file = {
        index: [],
        content: []
    };
    var url = $location.absUrl();
    if(url.indexOf('?log=')!=-1){
        $log.info('External log detected');
        var log = url.substr(url.indexOf('?log=')+5);
        $http.get('http://bochen415.info/loggify.php?url='+log).then(function (res) {
            readFile(res.data);
        });
    }

    $http.get('./resources/indicators.json').then(function (res) {
        $log.debug(res);
    });

    $window.Dropzone.options.upload = {
        accept: function (file, done) {
            console.log(file);
            if(file.name.indexOf('.log')!= -1){
                var reader = new FileReader;
                reader.readAsText(file);
                reader.onload = function () {
                    readFile(reader.result);
                }
            } else {
                $mdToast.showSimple("File isn't a logfile");
                done("File isn't a logfile");
            }
        }
    };

    function readFile (text) {
        vm.uploader = false;
        var file = angular.copy(text);
        var lines;
        lines = _.split(file, /\n/);
        var launcherline = lines[lines.length-2];
        vm.launcherBuild = launcherline.substr(launcherline.indexOf('[')+2, launcherline.indexOf(']')-2);
        var sortedLines = {
            0: []
        };
        var launch = 0;
        var crashFlag = false;
        var causeFlag = false;
        var javaFlag = false;
        lines.forEach(function (line) {
            var saveLine = {
                text: line
            };
            if(line.indexOf('Forge Mod Loader version')!= -1 && line.indexOf('loading')!= -1){
                launch++;
                sortedLines[launch] = [];
            }
            sortedLines[launch].push(saveLine);
        });
        var lineNum = 1;
        sortedLines[launch].forEach(function (lineObject) {
            lineObject.text = lineNum+" "+lineObject.text;
            var line = lineObject.text;
            if(javaFlag){
                lineObject.mark = 1;
                javaFlag = false;
                vm.javaError[1] = line;
            }
            if(line.indexOf('OS:')!= -1){
                vm.os = line.substr(line.indexOf('OS:')+4);
            }
            if(line.indexOf('Xmx')!= -1){
                vm.ram = line.substr(line.indexOf('Xmx')+3,5);
                vm.ramC = line.substr(line.indexOf('Xmx')+3,4);
            }
            if(line.indexOf('modpacks')!= -1){
                var packPath = line.substr(line.indexOf('modpacks')+9);
                console.log(packPath);
                vm.pack = packPath.substr(0, packPath.indexOf('\\'));
            }
            if(line.indexOf('jre')!= -1){
                var jrePath = line.substr(line.indexOf('jre'));
                vm.jre = jrePath.substr(0, jrePath.indexOf('\\'));
            }
            if(line.indexOf('---- Minecraft Crash Report ----')!= -1){
                crashFlag = true;
            }
            if(line.indexOf('Error occurred')!= -1){
                lineObject.mark = 1;
                javaFlag = true;
                vm.javaError = [];
                vm.javaError[0] = line;
            }
            if(line.indexOf('[java.lang.Throwable$WrappedPrintStream:println:-1]: java.lang.NoSuchMethodError: com.google.common.io.CharSource.readLines(Lcom/google/common/io/LineProcessor;)Ljava/lang/Object;')!= -1){
                vm.crack = true;
                lineObject.mark = 2;
            }
            if(line.indexOf('Caused by:')!= -1){
                causeFlag = true;
                lineObject.mark = 1;
                vm.cause = line;
            }
            if(line.indexOf('Program Files (x86)')!= -1){
                vm.falseJava = true;
            }
            if(line.indexOf('...')!= -1){
                causeFlag = false;
            }
            if(line.indexOf('at')!= -1 && causeFlag){
                lineObject.mark = 1;
            }
            if(line.indexOf('Starting download of')!= -1 || line.indexOf('Expected MD5:')!= -1){
                lineObject.mark = 3;
            }
            if(line.indexOf('[WARNING]')!= -1){
                lineObject.mark = 4;
            }
            if(line.indexOf('org.lwjgl.LWJGLException: Pixel format not accelerated')!= -1 ){
                vm.notAcc = true;
            }
            if(line.indexOf('[STDOUT]')!= -1 && crashFlag){
                lineObject.mark = 1;
            }
            lineNum++;
        });
        console.log(lines);
        console.log(vm.launcherBuild);
        console.log(sortedLines);
        vm.launches = launch;
        vm.latest = sortedLines[launch];
        vm.loaded = true;
        var url = 'http://api.technicpack.net/modpack/'+vm.pack+'?build=99';
        $http.get('http://bochen415.info/loggify.php?url='+url).then(function (res) {
            vm.packInfo = res.data;
            if(vm.packInfo.solder){
                $http.get('http://bochen415.info/loggify.php?url='+vm.packInfo.solder+'modpack/'+vm.packInfo.name).then(function (res) {
                    vm.packInfo.solderD = res.data;
                });
            }
        })
    }
});<commit_msg>Checking for external logs<commit_after>/**
 * Created by Lukas on 15.01.2016.
 */
var app = angular.module('loggify', ['ngMaterial']);

app.config(
    function($mdThemingProvider) {
        $mdThemingProvider.theme('default')
            .primaryPalette('deep-purple')
            .accentPalette('cyan')
            .dark();
    }
);

app.controller('AppController', function($http, $location, $window, $mdToast, $log) {
    var vm = this;
    vm.uploader = true;
    vm.file = {
        index: [],
        content: []
    };
    checkForExternalLog();

    $http.get('./resources/indicators.json').then(function (res) {
        $log.debug(res);
    });

    $window.Dropzone.options.upload = {
        accept: function (file, done) {
            console.log(file);
            if(file.name.indexOf('.log')!= -1){
                var reader = new FileReader;
                reader.readAsText(file);
                reader.onload = function () {
                    readFile(reader.result);
                }
            } else {
                $mdToast.showSimple("File isn't a logfile");
                done("File isn't a logfile");
            }
        }
    };

    function checkForExternalLog(){
        var url = $location.absUrl();
        if(url.indexOf('?log=')!=-1){
            $log.info('External log detected');
            var log = url.substr(url.indexOf('?log=')+5);
            $http.get('http://bochen415.info/loggify.php?url='+log).then(function (res) {
                readFile(res.data);
            });
        }
    }

    function readFile (text) {
        vm.uploader = false;
        var file = angular.copy(text);
        var lines;
        lines = _.split(file, /\n/);
        var launcherline = lines[lines.length-2];
        vm.launcherBuild = launcherline.substr(launcherline.indexOf('[')+2, launcherline.indexOf(']')-2);
        var sortedLines = {
            0: []
        };
        var launch = 0;
        var crashFlag = false;
        var causeFlag = false;
        var javaFlag = false;
        lines.forEach(function (line) {
            var saveLine = {
                text: line
            };
            if(line.indexOf('Forge Mod Loader version')!= -1 && line.indexOf('loading')!= -1){
                launch++;
                sortedLines[launch] = [];
            }
            sortedLines[launch].push(saveLine);
        });
        var lineNum = 1;
        sortedLines[launch].forEach(function (lineObject) {
            lineObject.text = lineNum+" "+lineObject.text;
            var line = lineObject.text;
            if(javaFlag){
                lineObject.mark = 1;
                javaFlag = false;
                vm.javaError[1] = line;
            }
            if(line.indexOf('OS:')!= -1){
                vm.os = line.substr(line.indexOf('OS:')+4);
            }
            if(line.indexOf('Xmx')!= -1){
                vm.ram = line.substr(line.indexOf('Xmx')+3,5);
                vm.ramC = line.substr(line.indexOf('Xmx')+3,4);
            }
            if(line.indexOf('modpacks')!= -1){
                var packPath = line.substr(line.indexOf('modpacks')+9);
                console.log(packPath);
                vm.pack = packPath.substr(0, packPath.indexOf('\\'));
            }
            if(line.indexOf('jre')!= -1){
                var jrePath = line.substr(line.indexOf('jre'));
                vm.jre = jrePath.substr(0, jrePath.indexOf('\\'));
            }
            if(line.indexOf('---- Minecraft Crash Report ----')!= -1){
                crashFlag = true;
            }
            if(line.indexOf('Error occurred')!= -1){
                lineObject.mark = 1;
                javaFlag = true;
                vm.javaError = [];
                vm.javaError[0] = line;
            }
            if(line.indexOf('[java.lang.Throwable$WrappedPrintStream:println:-1]: java.lang.NoSuchMethodError: com.google.common.io.CharSource.readLines(Lcom/google/common/io/LineProcessor;)Ljava/lang/Object;')!= -1){
                vm.crack = true;
                lineObject.mark = 2;
            }
            if(line.indexOf('Caused by:')!= -1){
                causeFlag = true;
                lineObject.mark = 1;
                vm.cause = line;
            }
            if(line.indexOf('Program Files (x86)')!= -1){
                vm.falseJava = true;
            }
            if(line.indexOf('...')!= -1){
                causeFlag = false;
            }
            if(line.indexOf('at')!= -1 && causeFlag){
                lineObject.mark = 1;
            }
            if(line.indexOf('Starting download of')!= -1 || line.indexOf('Expected MD5:')!= -1){
                lineObject.mark = 3;
            }
            if(line.indexOf('[WARNING]')!= -1){
                lineObject.mark = 4;
            }
            if(line.indexOf('org.lwjgl.LWJGLException: Pixel format not accelerated')!= -1 ){
                vm.notAcc = true;
            }
            if(line.indexOf('[STDOUT]')!= -1 && crashFlag){
                lineObject.mark = 1;
            }
            lineNum++;
        });
        console.log(lines);
        console.log(vm.launcherBuild);
        console.log(sortedLines);
        vm.launches = launch;
        vm.latest = sortedLines[launch];
        vm.loaded = true;
        var url = 'http://api.technicpack.net/modpack/'+vm.pack+'?build=99';
        $http.get('http://bochen415.info/loggify.php?url='+url).then(function (res) {
            vm.packInfo = res.data;
            if(vm.packInfo.solder){
                $http.get('http://bochen415.info/loggify.php?url='+vm.packInfo.solder+'modpack/'+vm.packInfo.name).then(function (res) {
                    vm.packInfo.solderD = res.data;
                });
            }
        })
    }
});<|endoftext|>


<commit_before>var app = app || {}

$(function (){

	var storage = null
	var jqCanvas = $('#canvas')
	var viewport = $(window)
	var jqBody = $('body')
	var lineNumbers = $('#linenumbers')
	var lineMarker = $('#linemarker')
	var storageStatusElement = $('#storage-status')
	var tooltip = $('#tooltip')[0]
	var errorTooltip = $('#error-tooltip')[0]
	var textarea = document.getElementById('textarea')
	var imgLink = document.getElementById('savebutton')
	var fileLink = document.getElementById('saveTextbutton')
	var linkLink = document.getElementById('linkbutton')
	var canvasElement = document.getElementById('canvas')
	var canvasPanner = document.getElementById('canvas-panner')
	var canvasTools = document.getElementById('canvas-tools')
	var defaultSource = document.getElementById('defaultGraph').innerHTML
	var fileName;
	var zoomLevel = 0
	var offset = {x:0, y:0}
	var mouseDownPoint = false
	var vm = skanaar.vector

	var editor = CodeMirror.fromTextArea(textarea, {
		lineNumbers: true,
		mode: 'jdl',
		matchBrackets: true,
		autoCloseBrackets: true,
		theme: 'solarized dark',
		keyMap: 'sublime',
		extraKeys: {
			"Ctrl-Space": "autocomplete"
	   }
	});

	$(document).bind('keydown', function(e) {
		if (e.keyCode == 83 && (navigator.platform.match("Mac") ? e.metaKey : e.ctrlKey)) {
			e.preventDefault()
			fileLink.click()
			return false
		}
	});

	var editorElement = editor.getWrapperElement()

	window.addEventListener('hashchange', reloadStorage);
	window.addEventListener('resize', _.throttle(sourceChanged, 750, {leading: true}))
	editor.on('changes', _.debounce(sourceChanged, 300))
	canvasPanner.addEventListener('mouseenter', classToggler(jqBody, 'canvas-mode', true))
	canvasPanner.addEventListener('mouseleave', classToggler(jqBody, 'canvas-mode', false))
	canvasTools.addEventListener('mouseenter', classToggler(jqBody, 'canvas-mode', true))
	canvasTools.addEventListener('mouseleave', classToggler(jqBody, 'canvas-mode', false))
	canvasPanner.addEventListener('mousedown', mouseDown)
	window.addEventListener('mousemove', _.throttle(mouseMove,50))
	canvasPanner.addEventListener('mouseup', mouseUp)
	canvasPanner.addEventListener('mouseleave', mouseUp)
	canvasPanner.addEventListener('wheel', _.throttle(magnify, 50))
	initImageDownloadLink(imgLink, canvasElement)
	initFileDownloadLink(fileLink)
	initToolbarTooltips()
	initDialog('.upload-dialog')
	reloadStorage()

	function initDialog(className) {

		$(className).magnificPopup({
			type: 'inline',
			fixedContentPos: false,
			fixedBgPos: true,
			overflowY: 'auto',
			closeBtnInside: true,
			preloader: false,
			removalDelay: 300,
			mainClass: 'my-mfp-slide-bottom'
		});
	}
	function classToggler(element, className, state){
		var jqElement = $(element)
		return _.bind(jqElement.toggleClass, jqElement, className, state)
	}

	function mouseDown(e){
		$(canvasPanner).css({width: '100%'})
		mouseDownPoint = vm.diff({ x: e.pageX, y: e.pageY }, offset)
	}

	function mouseMove(e){
		if (mouseDownPoint){
			offset = vm.diff({ x: e.pageX, y: e.pageY }, mouseDownPoint)
			sourceChanged()
		}
	}

	function mouseUp(){
		mouseDownPoint = false
		$(canvasPanner).css({width: '33%'})
	}

	function magnify(e){
		zoomLevel = Math.min(10, zoomLevel - (e.deltaY < 0 ? -1 : 1))
		sourceChanged()
	}

	app.magnifyViewport = function (diff){
		zoomLevel = Math.min(10, zoomLevel + diff)
		sourceChanged()
	}

	app.resetViewport = function (){
		zoomLevel = 0
		offset = {x: 0, y: 0}
		sourceChanged()
	}

	app.toggleSidebar = function (id){
		var sidebars = ['reference', 'about']
		_.each(sidebars, function (key){
			if (id !== key) $(document.getElementById(key)).toggleClass('visible', false)
		})
		$(document.getElementById(id)).toggleClass('visible')
	}

	app.confirmDiscardCurrentGraph = function (){
		$.magnificPopup.open({
			items: {
				src: '#discard-dialog'
			},
			type: 'inline',
			fixedContentPos: false,
			fixedBgPos: true,
			overflowY: 'auto',
			closeBtnInside: true,
			preloader: false,
			removalDelay: 300,
			mainClass: 'my-mfp-slide-bottom'
		});
	}
	app.dismissDialog = function (){
		$.magnificPopup.close();
	}

	app.discardCurrentGraph = function (){
		app.dismissDialog()
		setCurrentText(defaultSource)
		sourceChanged()
	}

	app.saveViewModeToStorage = function (){
		var question =
		'Do you want to overwrite the diagram in ' +
		'localStorage with the currently viewed diagram?'
		if (confirm(question)){
			storage.moveToLocalStorage()
			window.location = './'
		}
	}

	app.exitViewMode = function (){
		window.location = './'
	}

	app.importJDL = function() {
		app.dismissDialog()
		//Retrieve the first (and only!) File from the FileList object
		var f = document.getElementById('jdlFileInput').files[0]

		if(!f) {
			alert("Failed to load file")
		} else if (!f.type.match('text.*') && !f.name.endsWith('.jh')) {
			alert(f.name + " is not a valid JDL or text file.")
		} else {
			var r = new FileReader()
			r.onload = function(e) {
				var contents = e.target.result;
				console.log( "Got the file\n"
					+"name: " + f.name + "\n"
					+"type: " + f.type + "\n"
					+"size: " + f.size + " bytes\n"
					+ "starts with: " + contents.substr(0, contents.indexOf("\n"))
				)
				setCurrentText(contents)
			}
			r.readAsText(f)
		}
		ga('send', 'event', 'JDL File', 'upload', 'JDL File upload');
		ga('jdlTracker.send', 'event', 'JDL File', 'upload', 'JDL File upload');
	}

	// Adapted from http://meyerweb.com/eric/tools/dencoder/
	function urlEncode(unencoded) {
		return encodeURIComponent(unencoded).replace(/'/g,'%27').replace(/"/g,'%22')
	}

	function urlDecode(encoded) {
		return decodeURIComponent(encoded.replace(/\+/g, ' '))
	}

	function setShareableLink(str){
		var base = '#view/'
		linkLink.href = base + urlEncode(str)
	}

	function buildStorage(locationHash){
		var key = 'jdlstudio.lastSource'
		if (locationHash.substring(0,6) === '#view/')
		return {
			read: function (){ return urlDecode(locationHash.substring(6)) },
			save: function (){ setShareableLink(currentText()) },
			moveToLocalStorage: function (){ localStorage[key] = currentText() },
			isReadonly: true
		}
		return {
			read: function (){ return localStorage[key] || defaultSource },
			save: function (source){
				setShareableLink(currentText())
				localStorage[key] = source
			},
			moveToLocalStorage: function (){},
			isReadonly: false
		}
	}

	function initImageDownloadLink(link, canvasElement){
		link.addEventListener('click', downloadImage, false);
		function downloadImage(){
			var url = canvasElement.toDataURL('image/png')
			link.href = url;
			ga('send', 'event', 'JDL Image', 'download', 'JDL Image download');
			ga('jdlTracker.send', 'event', 'JDL Image', 'download', 'JDL Image download');
		}
	}

	function initFileDownloadLink(link){
		link.addEventListener('click', downloadFile, false);
		function downloadFile(){
			var textToWrite = currentText()
			var textFileAsBlob = new Blob([textToWrite], {type:'text/plain'})
			var URL = window.URL || window.webkitURL
			if (URL != null) {
				link.href = window.URL.createObjectURL(textFileAsBlob)
			}
			ga('send', 'event', 'JDL File', 'download', 'JDL File download');
			ga('jdlTracker.send', 'event', 'JDL File', 'download', 'JDL File download');
		}
	}

	function initToolbarTooltips(){
		$('.tools a').each(function (i, link){
			link.onmouseover = function (){ tooltip.textContent  = $(link).attr('title') }
			link.onmouseout = function (){ tooltip.textContent  = '' }
		})
	}

	function positionCanvas(rect, superSampling, offset){
		var w = rect.width / superSampling
		var h = (rect.height / superSampling) - 60
		jqCanvas.css({
			top: (300 * (1 - h/viewport.height()) + offset.y) + 50,
			left: 150 + (viewport.width() - w)/2 + offset.x,
			width: w,
			height: h
		})
	}

	function setFilename(filename){
		fileLink.download = filename + '.jh'
		imgLink.download = filename + '.png'
	}

	function reloadStorage(){
		storage = buildStorage(location.hash)
		editor.setValue(storage.read())
		sourceChanged()
		if (storage.isReadonly) storageStatusElement.show()
		else storageStatusElement.hide()
	}

	function currentText(){
		return editor.getValue()
	}

	function setCurrentText(value){
		return editor.setValue(value)
	}

	function handleError(e){
		lineNumbers.toggleClass('error', true)
		if (e.location){
			var lineHeight = parseFloat($(editorElement).css('line-height'))
			lineMarker.css('top', 35 + lineHeight*e.location.start.line)
			errorTooltip.textContent = e.message + ': line -> ' + e.location.start.line
		} else {
			throw e
		}
	}

	function sourceChanged(){
		try {
			lineMarker.css('top', -35)
			lineNumbers.toggleClass('error', false)
			errorTooltip.textContent = ''
			var superSampling = window.devicePixelRatio || 1
			var scale = superSampling * Math.exp(zoomLevel/10)

			var model = nomnoml.draw(canvasElement, currentText(), scale)
			positionCanvas(canvasElement, superSampling, offset)
			setFilename(model.config.title)
			storage.save(currentText())
		} catch (e){
			handleError(e)
		}
	}
})
<commit_msg>change error highlight<commit_after>var app = app || {}

$(function (){

	var storage = null
	var jqCanvas = $('#canvas')
	var viewport = $(window)
	var jqBody = $('body')
	var lineNumbers = $('#linenumbers')
	var lineMarker = $('#linemarker')
	var storageStatusElement = $('#storage-status')
	var tooltip = $('#tooltip')[0]
	var errorTooltip = $('#error-tooltip')[0]
	var textarea = document.getElementById('textarea')
	var imgLink = document.getElementById('savebutton')
	var fileLink = document.getElementById('saveTextbutton')
	var linkLink = document.getElementById('linkbutton')
	var canvasElement = document.getElementById('canvas')
	var canvasPanner = document.getElementById('canvas-panner')
	var canvasTools = document.getElementById('canvas-tools')
	var defaultSource = document.getElementById('defaultGraph').innerHTML
	var fileName;
	var zoomLevel = 0
	var offset = {x:0, y:0}
	var mouseDownPoint = false
	var vm = skanaar.vector

	var editor = CodeMirror.fromTextArea(textarea, {
		lineNumbers: true,
		mode: 'jdl',
		matchBrackets: true,
		autoCloseBrackets: true,
		theme: 'solarized dark',
		keyMap: 'sublime',
		extraKeys: {
			"Ctrl-Space": "autocomplete"
	   }
	});

	$(document).bind('keydown', function(e) {
		if (e.keyCode == 83 && (navigator.platform.match("Mac") ? e.metaKey : e.ctrlKey)) {
			e.preventDefault()
			fileLink.click()
			return false
		}
	});

	var editorElement = editor.getWrapperElement()

	window.addEventListener('hashchange', reloadStorage);
	window.addEventListener('resize', _.throttle(sourceChanged, 750, {leading: true}))
	editor.on('changes', _.debounce(sourceChanged, 300))
	canvasPanner.addEventListener('mouseenter', classToggler(jqBody, 'canvas-mode', true))
	canvasPanner.addEventListener('mouseleave', classToggler(jqBody, 'canvas-mode', false))
	canvasTools.addEventListener('mouseenter', classToggler(jqBody, 'canvas-mode', true))
	canvasTools.addEventListener('mouseleave', classToggler(jqBody, 'canvas-mode', false))
	canvasPanner.addEventListener('mousedown', mouseDown)
	window.addEventListener('mousemove', _.throttle(mouseMove,50))
	canvasPanner.addEventListener('mouseup', mouseUp)
	canvasPanner.addEventListener('mouseleave', mouseUp)
	canvasPanner.addEventListener('wheel', _.throttle(magnify, 50))
	initImageDownloadLink(imgLink, canvasElement)
	initFileDownloadLink(fileLink)
	initToolbarTooltips()
	initDialog('.upload-dialog')
	reloadStorage()

	function initDialog(className) {

		$(className).magnificPopup({
			type: 'inline',
			fixedContentPos: false,
			fixedBgPos: true,
			overflowY: 'auto',
			closeBtnInside: true,
			preloader: false,
			removalDelay: 300,
			mainClass: 'my-mfp-slide-bottom'
		});
	}
	function classToggler(element, className, state){
		var jqElement = $(element)
		return _.bind(jqElement.toggleClass, jqElement, className, state)
	}

	function mouseDown(e){
		$(canvasPanner).css({width: '100%'})
		mouseDownPoint = vm.diff({ x: e.pageX, y: e.pageY }, offset)
	}

	function mouseMove(e){
		if (mouseDownPoint){
			offset = vm.diff({ x: e.pageX, y: e.pageY }, mouseDownPoint)
			sourceChanged()
		}
	}

	function mouseUp(){
		mouseDownPoint = false
		$(canvasPanner).css({width: '33%'})
	}

	function magnify(e){
		zoomLevel = Math.min(10, zoomLevel - (e.deltaY < 0 ? -1 : 1))
		sourceChanged()
	}

	app.magnifyViewport = function (diff){
		zoomLevel = Math.min(10, zoomLevel + diff)
		sourceChanged()
	}

	app.resetViewport = function (){
		zoomLevel = 0
		offset = {x: 0, y: 0}
		sourceChanged()
	}

	app.toggleSidebar = function (id){
		var sidebars = ['reference', 'about']
		_.each(sidebars, function (key){
			if (id !== key) $(document.getElementById(key)).toggleClass('visible', false)
		})
		$(document.getElementById(id)).toggleClass('visible')
	}

	app.confirmDiscardCurrentGraph = function (){
		$.magnificPopup.open({
			items: {
				src: '#discard-dialog'
			},
			type: 'inline',
			fixedContentPos: false,
			fixedBgPos: true,
			overflowY: 'auto',
			closeBtnInside: true,
			preloader: false,
			removalDelay: 300,
			mainClass: 'my-mfp-slide-bottom'
		});
	}
	app.dismissDialog = function (){
		$.magnificPopup.close();
	}

	app.discardCurrentGraph = function (){
		app.dismissDialog()
		setCurrentText(defaultSource)
		sourceChanged()
	}

	app.saveViewModeToStorage = function (){
		var question =
		'Do you want to overwrite the diagram in ' +
		'localStorage with the currently viewed diagram?'
		if (confirm(question)){
			storage.moveToLocalStorage()
			window.location = './'
		}
	}

	app.exitViewMode = function (){
		window.location = './'
	}

	app.importJDL = function() {
		app.dismissDialog()
		//Retrieve the first (and only!) File from the FileList object
		var f = document.getElementById('jdlFileInput').files[0]

		if(!f) {
			alert("Failed to load file")
		} else if (!f.type.match('text.*') && !f.name.endsWith('.jh')) {
			alert(f.name + " is not a valid JDL or text file.")
		} else {
			var r = new FileReader()
			r.onload = function(e) {
				var contents = e.target.result;
				console.log( "Got the file\n"
					+"name: " + f.name + "\n"
					+"type: " + f.type + "\n"
					+"size: " + f.size + " bytes\n"
					+ "starts with: " + contents.substr(0, contents.indexOf("\n"))
				)
				setCurrentText(contents)
			}
			r.readAsText(f)
		}
		ga('send', 'event', 'JDL File', 'upload', 'JDL File upload');
		ga('jdlTracker.send', 'event', 'JDL File', 'upload', 'JDL File upload');
	}

	// Adapted from http://meyerweb.com/eric/tools/dencoder/
	function urlEncode(unencoded) {
		return encodeURIComponent(unencoded).replace(/'/g,'%27').replace(/"/g,'%22')
	}

	function urlDecode(encoded) {
		return decodeURIComponent(encoded.replace(/\+/g, ' '))
	}

	function setShareableLink(str){
		var base = '#view/'
		linkLink.href = base + urlEncode(str)
	}

	function buildStorage(locationHash){
		var key = 'jdlstudio.lastSource'
		if (locationHash.substring(0,6) === '#view/')
		return {
			read: function (){ return urlDecode(locationHash.substring(6)) },
			save: function (){ setShareableLink(currentText()) },
			moveToLocalStorage: function (){ localStorage[key] = currentText() },
			isReadonly: true
		}
		return {
			read: function (){ return localStorage[key] || defaultSource },
			save: function (source){
				setShareableLink(currentText())
				localStorage[key] = source
			},
			moveToLocalStorage: function (){},
			isReadonly: false
		}
	}

	function initImageDownloadLink(link, canvasElement){
		link.addEventListener('click', downloadImage, false);
		function downloadImage(){
			var url = canvasElement.toDataURL('image/png')
			link.href = url;
			ga('send', 'event', 'JDL Image', 'download', 'JDL Image download');
			ga('jdlTracker.send', 'event', 'JDL Image', 'download', 'JDL Image download');
		}
	}

	function initFileDownloadLink(link){
		link.addEventListener('click', downloadFile, false);
		function downloadFile(){
			var textToWrite = currentText()
			var textFileAsBlob = new Blob([textToWrite], {type:'text/plain'})
			var URL = window.URL || window.webkitURL
			if (URL != null) {
				link.href = window.URL.createObjectURL(textFileAsBlob)
			}
			ga('send', 'event', 'JDL File', 'download', 'JDL File download');
			ga('jdlTracker.send', 'event', 'JDL File', 'download', 'JDL File download');
		}
	}

	function initToolbarTooltips(){
		$('.tools a').each(function (i, link){
			link.onmouseover = function (){ tooltip.textContent  = $(link).attr('title') }
			link.onmouseout = function (){ tooltip.textContent  = '' }
		})
	}

	function positionCanvas(rect, superSampling, offset){
		var w = rect.width / superSampling
		var h = (rect.height / superSampling) - 60
		jqCanvas.css({
			top: (300 * (1 - h/viewport.height()) + offset.y) + 50,
			left: 150 + (viewport.width() - w)/2 + offset.x,
			width: w,
			height: h
		})
	}

	function setFilename(filename){
		fileLink.download = filename + '.jh'
		imgLink.download = filename + '.png'
	}

	function reloadStorage(){
		storage = buildStorage(location.hash)
		editor.setValue(storage.read())
		sourceChanged()
		if (storage.isReadonly) storageStatusElement.show()
		else storageStatusElement.hide()
	}

	function currentText(){
		return editor.getValue()
	}

	function setCurrentText(value){
		return editor.setValue(value)
	}

	function handleError(e){
		lineNumbers.toggleClass('error', true)
		if (e.location){
			var lineHeight = parseFloat($(editorElement).css('line-height'))
			lineMarker.css('top', 35 + lineHeight*e.location.start.line)
			errorTooltip.textContent = e.message + ' -> line: ' + e.location.start.line
		} else {
			throw e
		}
	}

	function sourceChanged(){
		try {
			lineMarker.css('top', -35)
			lineNumbers.toggleClass('error', false)
			errorTooltip.textContent = ''
			var superSampling = window.devicePixelRatio || 1
			var scale = superSampling * Math.exp(zoomLevel/10)

			var model = nomnoml.draw(canvasElement, currentText(), scale)
			positionCanvas(canvasElement, superSampling, offset)
			setFilename(model.config.title)
			storage.save(currentText())
		} catch (e){
			handleError(e)
		}
	}
})
<|endoftext|>


<commit_before>define(['components'], function(components) {
    'use strict';

    var _init = function() {
        var menuOptions = {
            op1: 'Videos',
            op2: 'Posts',
            op3: 'Books'
        };
        components.upMenu('Sphere');
        components.upMenu.prototype.insertTitle();
        components.upMenu.prototype.insertMenu(menuOptions);
    };

    return {
        init: _init
    };
});
<commit_msg>improve app.js<commit_after>define(['topBar'], function(topBar) {
    'use strict';

    var _init = function() {
        var menuOptions = {
            op1: 'Videos',
            op2: 'Posts',
            op3: 'Books'
        };
        topBar.upMenu('Sphere');
        topBar.upMenu.prototype.insertTitle();
        topBar.upMenu.prototype.insertMenu(menuOptions);
    };

    return {
        init: _init
    };
});
<|endoftext|>


<commit_before>(function () {
  "use strict";
    var request = new XMLHttpRequest();
    request.open('GET', 'https://klatelbat.com:12345/getMSGThreads', true);
    console.log("loading..");
    request.onload = function() {
        if (this.status === 200) {
            var jsonResponse = JSON.parse(this.responseText);
            for (var i = 0; i < jsonResponse.length; i++) {
                var new_word = document.createElement("div");
                new_word.className = "word";
                new_word.setAttribute("_lat", jsonResponse[i].lat);
                new_word.setAttribute("_lng", jsonResponse[i].lon);
                new_word.setAttribute("_pop", jsonResponse[i].pop);
                new_word.setAttribute("_id", jsonResponse[i].mongoID);
                new_word.setAttribute("_latestMessage", jsonResponse[i].latestMessage);
                new_word.innerText = jsonResponse[i].messageHeading;
                new_word.addEventListener("click", loadMessages);
                document.getElementById("words").appendChild(new_word);
                console.log("done!");
            }
        }
        else {
            console.log('Request failed.  Returned status of ' + this.status);
        }
    };

    request.send();

document.getElementById("send").addEventListener("click", sendMessage);
document.getElementById("create").addEventListener("click", createThread);
document.getElementById("chatLog").addEventListener("click", closeChatLog);

function closeChatLog() {
    document.getElementById('chatLog').style.display = "none";
    document.getElementById('send').disabled = true;
    document.getElementById('create').disabled = false;
}

function loadMessages() {
    document.getElementById('send').disabled = false;
    document.getElementById('create').disabled = true;
    document.getElementById('chatLog').style.display = "block";

    document.getElementById('chatLog').innerHTML = "";

    var request = new XMLHttpRequest();
    var url = "https://klatelbat.com:12345/getMSGThreadMessages/" + this.getAttribute("_id");
    var save = this.getAttribute("_id");
    request.open('GET', url, true);
    request.withCredentials = false;
    request.onload = function() {
        if (this.status === 200) {
            var jsonResponse = JSON.parse(this.responseText);
            for (var i = 0; i < jsonResponse.length; i++) {
                var new_message = document.createElement("h2");
                new_message.className = "message";
                new_message.innerText = jsonResponse[i].msg;
                document.getElementById("chatLog").appendChild(new_message);
                document.getElementById("typeBox").setAttribute("_msgId",  save);
            }
        }
        else {
            alert('Request failed.  Returned status of ' + this.status);
        }
    };
    request.send();
}

function sendMessage() {
  var data = JSON.stringify({
  "msg": document.getElementById("typeBox").value,
  "msgID": document.getElementById("typeBox").getAttribute("_msgId")
  });

  var xhr = new XMLHttpRequest();
  xhr.withCredentials = false;

  xhr.addEventListener("readystatechange", function () {

    console.log(this.responseText);
    var new_message = document.createElement("h2");
    new_message.className = "message";
    new_message.innerText = document.getElementById("typeBox").value;
    document.getElementById("chatLog").appendChild(new_message);
    document.getElementById("typeBox").value = "";
  });

  xhr.open("POST", "https://klatelbat.com:12345/newMSG/post");
  xhr.setRequestHeader("content-type", "application/json");

  xhr.send(data);
}

function createThread() {
  var title = document.getElementById("typeBox").value;
  var lat = positionCurrent.lat;
  var lng = positionCurrent.lng;

  var data = JSON.stringify({
    "msgHead": title,
    "lat": lat,
    "lon": lng
  });

  var request = new XMLHttpRequest();
  request.withCredentials = false;

  request.addEventListener("readystatechange", function() {
    if(this.readyState == 4) {
      console.log(this.responseText);
      var jsonResponse = JSON.parse(this.responseText);

      //show the new word to represent thread
      var newWord = document.createElement("div");
      newWord.className = "word";
      newWord.setAttribute("_lat", lat);
      newWord.setAttribute("_lng", lng);
      newWord.setAttribute("_pop", 0);
      newWord.setAttribute("_id", jsonResponse.mongoID);
      newWord.setAttribute("_latestMessage", jsonResponse.latestMessage);
      newWord.innerText = title;
      newWord.addEventListener("click", loadMessages);
      document.getElementById("words").appendChild(newWord);
    }
  });

  request.open("POST", "https://klatelbat.com:12345/newmsgthread/post");
  request.setRequestHeader("content-type", "application/json");
  request.setRequestHeader("cache-control", "no-cache");
  request.send(data);
}

    //set to true for debugging output
  var debug = false;

  // our current position
  var positionCurrent = {
    lat: null,
    lng: null,
    hng: null
  };

  // elements that ouput our position
  var positionLat = document.getElementById("position-lat");
  var positionLng = document.getElementById("position-lng");
  var positionHng = document.getElementById("position-hng");

  // // debug outputs
  // var debugOrientation = document.getElementById("debug-orientation");
  // var debugOrientationDefault = document.getElementById("debug-orientation-default");
  //
  //
  // // info popup elements, pus buttons that open popups
  // var popup = document.getElementById("popup");
  // var popupContents = document.getElementById("popup-contents");
  // var popupInners = document.querySelectorAll(".popup__inner");
  // var btnsPopup = document.querySelectorAll(".btn-popup");

  // buttons at the bottom of the screen
  // var btnLockOrientation = document.getElementById("btn-lock-orientation");
  // var btnNightmode = document.getElementById("btn-nightmode");
  // var btnMap = document.getElementById("btn-map");
  // var btnInfo = document.getElementById("btn-info");

  // if we have shown the heading unavailable warning yet
  var warningHeadingShown = false;

  // switches keeping track of our current app state
  var isOrientationLockable = false;
  var isOrientationLocked = false;
  var isNightMode = false;

  // the orientation of the device on app load
  var defaultOrientation;

  // browser agnostic orientation
  function getBrowserOrientation() {
    var orientation;
    if (screen.orientation && screen.orientation.type) {
      orientation = screen.orientation.type;
    } else {
      orientation = screen.orientation ||
                    screen.mozOrientation ||
                    screen.msOrientation;
    }

    /*
      'portait-primary':      for (screen width < screen height, e.g. phone, phablet, small tablet)
                                device is in 'normal' orientation
                              for (screen width > screen height, e.g. large tablet, laptop)
                                device has been turned 90deg clockwise from normal

      'portait-secondary':    for (screen width < screen height)
                                device has been turned 180deg from normal
                              for (screen width > screen height)
                                device has been turned 90deg anti-clockwise (or 270deg clockwise) from normal

      'landscape-primary':    for (screen width < screen height)
                                device has been turned 90deg clockwise from normal
                              for (screen width > screen height)
                                device is in 'normal' orientation

      'landscape-secondary':  for (screen width < screen height)
                                device has been turned 90deg anti-clockwise (or 270deg clockwise) from normal
                              for (screen width > screen height)
                                device has been turned 180deg from normal
    */

    return orientation;
  }

    // Converts from degrees to radians.
    Math.radians = function(degrees) {
        return degrees * Math.PI / 180;
    };

    // Converts from radians to degrees.
    Math.degrees = function(radians) {
        return radians * 180 / Math.PI;
    };

    // called on device orientation change
    function onHeadingChange(event) {
        var heading = event.alpha;

        if (typeof event.webkitCompassHeading !== "undefined") {
            heading = event.webkitCompassHeading; //iOS non-standard
        }

        var orientation = getBrowserOrientation();

        if (typeof heading !== "undefined" && heading !== null) { // && typeof orientation !== "undefined") {
            // we have a browser that reports device heading and orientation

            // what adjustment we have to add to rotation to allow for current device orientation
            var adjustment = 0;
            if (defaultOrientation === "landscape") {
                adjustment -= 90;
            }

            if (typeof orientation !== "undefined") {
                var currentOrientation = orientation.split("-");

                if (defaultOrientation !== currentOrientation[0]) {
                    if (defaultOrientation === "landscape") {
                        adjustment -= 270;
                    } else {
                        adjustment -= 90;
                    }
                }

                if (currentOrientation[1] === "secondary") {
                    adjustment -= 180;
                }
            }

            positionCurrent.hng = heading + adjustment;
            var phase = positionCurrent.hng < 0 ? 360 + positionCurrent.hng : positionCurrent.hng;
            positionHng.textContent = (360 - phase | 0) + "°";

            // // apply rotation to compass rose
            // if (typeof rose.style.transform !== "undefined") {
            //     rose.style.transform = "rotateZ(" + positionCurrent.hng + "deg)";
            // } else if (typeof rose.style.webkitTransform !== "undefined") {
            //     rose.style.webkitTransform = "rotateZ(" + positionCurrent.hng + "deg)";
            // }
            var words = document.getElementsByClassName("word");
            var lng1 = Math.radians(positionCurrent.lng);
            var lat1 = Math.radians(positionCurrent.lat);
            for (var i = 0; i < words.length; ++i) {
                var item = words[i];
                var lng2 = Math.radians(item.getAttribute("_lng"));
                var lat2 = Math.radians(item.getAttribute("_lat"));
                var y = Math.sin(lng2-lng1) * Math.cos(lat2);
                var x = Math.cos(lat1)*Math.sin(lat2) -
                    Math.sin(lat1)*Math.cos(lat2)*Math.cos(lng2-lng1);
                var brng = Math.degrees(Math.atan2(y, x));

                var angle = positionCurrent.hng - brng;

                var radius_earth = 6371e3; // metres
                var delta_lat = lat2-lat1;
                var delta_lng = lng2-lng1;

                var a = Math.sin(delta_lat/2) * Math.sin(delta_lat/2) +
                    Math.cos(lat1) * Math.cos(lat2) *
                    Math.sin(delta_lng/2) * Math.sin(delta_lng/2);
                var c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1-a));

                var distance = radius_earth * c;
                if (distance < 1) {
                    distance = 1;
                }
                // Distance Debug
                // item.innerText = parseInt(distance) + "m";

                // Apply corresponding font effects.
                item.style.fontSize = (90 + (item.getAttribute("_pop") * 10)) + "%";
                var isCloseToInteractWith;
                if (distance <= 10) {
                    item.style.color = "white";
                    item.style.fontSizeAdjust = "1.2";
                    isCloseToInteractWith = true;
                } else {
                    item.style.color = "#A9A9A9";
                    item.style.fontSizeAdjust = "1.0";
                    isCloseToInteractWith = false;
                }

                // Apply correct transforms
                if (typeof item.style.transform !== "undefined") {
                    item.style.transform = "rotateZ(" + (-1 * angle) + "deg)";
                    item.style.transformOrigin = "50% 200px";
                    item.style.transform += "translate(0px, " + ((distance / -0.2) - (!isCloseToInteractWith * 50)) + "px)";
                } else if (typeof item.style.webkitTransform !== "undefined") {
                    item.style.webkitTransform = "rotateZ(-" + (-1 * angle) + "deg)";
                    item.style.webkitTransformOrigin = "50% 200px";
                    item.style.webkitTransform += "translate(0px, " + ((distance / -0.2) - (!isCloseToInteractWith * 50))  + "px)";
                }

                //making new topics glow potentialls
                /*
                var prevLatestMessage = item.getAttribute("latestMessage");
                watch(locationUpdate, function(){
                  var newLatestMessage = item.getAttribute("latestMessage");
                  if(prevLatestMessage < newLatestMessage) {
                    item.style.boxShadow = "0 0 10px";
                    prevLatestMessage = newLatestMessage;
                  }
                })
                */
            }

        } else {
            positionHng.textContent = "n/a";
            showHeadingWarning();
        }
    }

    function showHeadingWarning() {
        if (!warningHeadingShown) {
            console.log("No orientation!");
            warningHeadingShown = true;
        }
    }

  function onFullscreenChange() {
    if (isOrientationLockable && getBrowserFullscreenElement()) {
      if (screen.orientation && screen.orientation.lock) {
        screen.orientation.lock(getBrowserOrientation()).then(function () {
        }).catch(function () {
        });
      }
    } else {
      lockOrientationRequest(false);
    }
  }

  function toggleOrientationLockable(lockable) {
    isOrientationLockable = lockable;
  }

  function checkLockable() {
    if (screen.orientation && screen.orientation.lock) {
      screen.orientation.lock(getBrowserOrientation()).then(function () {
        toggleOrientationLockable(true);
        browserUnlockOrientation();
      }).catch(function (event) {
        if (event.code === 18) { // The page needs to be fullscreen in order to call lockOrientation(), but is lockable
          toggleOrientationLockable(true);
          browserUnlockOrientation(); //needed as chrome was locking orientation (even if not in fullscreen, bug??)
        } else {  // lockOrientation() is not available on this device (or other error)
          toggleOrientationLockable(false);
        }
      });
    } else {
      toggleOrientationLockable(false);
    }
  }

  function lockOrientationRequest(doLock) {
    if (isOrientationLockable) {
      if (doLock) {
        browserRequestFullscreen();
        lockOrientation(true);
      } else {
        browserUnlockOrientation();
        browserExitFullscreen();
        lockOrientation(false);
      }
    }
  }

  function lockOrientation(locked) {
    if (locked) {
      btnLockOrientation.classList.add("active");
    } else {
      btnLockOrientation.classList.remove("active");
    }

    isOrientationLocked = locked;
  }

  function toggleOrientationLock() {
    if (isOrientationLockable) {
      lockOrientationRequest(!isOrientationLocked);
    }
  }

  function locationUpdate(position) {
    positionCurrent.lat = position.coords.latitude;
    positionCurrent.lng = position.coords.longitude;

    positionLat.textContent = positionCurrent.lat;
    positionLng.textContent = positionCurrent.lng;
  }

  function locationUpdateFail(error) {
    positionLat.textContent = "n/a";
    positionLng.textContent = "n/a";
    console.log("location fail: ", error);
  }

    if (screen.width > screen.height) {
        defaultOrientation = "landscape";
    } else {
        defaultOrientation = "portrait";
    }

    document.addEventListener("fullscreenchange", onFullscreenChange);
    document.addEventListener("webkitfullscreenchange", onFullscreenChange);
    document.addEventListener("mozfullscreenchange", onFullscreenChange);
    document.addEventListener("MSFullscreenChange", onFullscreenChange);
    window.addEventListener("deviceorientation", onHeadingChange);

  navigator.geolocation.watchPosition(locationUpdate, locationUpdateFail, {
      enableHighAccuracy: true,
      maximumAge: 0,
      timeout: 30000 //large timeout to accomodate slow GPS lock on some devices
  });
  checkLockable();

}());
<commit_msg>Update app.js<commit_after>(function () {
  "use strict";
    var request = new XMLHttpRequest();
    request.open('GET', 'https://klatelbat.com:12345/getMSGThreads', true);
    console.log("loading..");
    request.onload = function() {
        if (this.status === 200) {
            var jsonResponse = JSON.parse(this.responseText);
            for (var i = 0; i < jsonResponse.length; i++) {
                var new_word = document.createElement("div");
                new_word.className = "word";
                new_word.setAttribute("_lat", jsonResponse[i].lat);
                new_word.setAttribute("_lng", jsonResponse[i].lon);
                new_word.setAttribute("_pop", jsonResponse[i].pop);
                new_word.setAttribute("_id", jsonResponse[i].mongoID);
                new_word.setAttribute("_latestMessage", jsonResponse[i].latestMessage);
                new_word.innerText = jsonResponse[i].messageHeading;
                new_word.addEventListener("click", loadMessages);
                document.getElementById("words").appendChild(new_word);
                console.log("done!");
            }
        }
        else {
            console.log('Request failed.  Returned status of ' + this.status);
        }
    };

    request.send();

document.getElementById("send").addEventListener("click", sendMessage);
document.getElementById("create").addEventListener("click", createThread);
document.getElementById("chatLog").addEventListener("click", closeChatLog);

function closeChatLog() {
    document.getElementById('chatLog').style.display = "none";
    document.getElementById('send').disabled = true;
    document.getElementById('create').disabled = false;
}

function loadMessages() {
    document.getElementById('send').disabled = false;
    document.getElementById('create').disabled = true;
    document.getElementById('chatLog').style.display = "block";

    document.getElementById('chatLog').innerHTML = "";

    var request = new XMLHttpRequest();
    var url = "https://klatelbat.com:12345/getMSGThreadMessages/" + this.getAttribute("_id");
    var save = this.getAttribute("_id");
    request.open('GET', url, true);
    request.withCredentials = false;
    request.onload = function() {
        if (this.status === 200) {
            var jsonResponse = JSON.parse(this.responseText);
            for (var i = 0; i < jsonResponse.length; i++) {
                var new_message = document.createElement("h2");
                new_message.className = "message";
                new_message.innerText = jsonResponse[i].msg;
                document.getElementById("chatLog").appendChild(new_message);
                document.getElementById("typeBox").setAttribute("_msgId",  save);
            }
        }
        else {
            alert('Request failed.  Returned status of ' + this.status);
        }
    };
    request.send();
}

function sendMessage() {
  var data = JSON.stringify({
  "msg": document.getElementById("typeBox").value,
  "msgID": document.getElementById("typeBox").getAttribute("_msgId")
  });

  var xhr = new XMLHttpRequest();
  xhr.withCredentials = false;

  xhr.addEventListener("readystatechange", function () {

    console.log(this.responseText);
    var new_message = document.createElement("h2");
    new_message.className = "message";
    new_message.innerText = document.getElementById("typeBox").value;
    document.getElementById("chatLog").appendChild(new_message);
    document.getElementById("typeBox").value = "";
  });

  xhr.open("POST", "https://klatelbat.com:12345/newMSG/post");
  xhr.setRequestHeader("content-type", "application/json");

  xhr.send(data);
}

function createThread() {
  var title = document.getElementById("typeBox").value;
  var lat = positionCurrent.lat;
  var lng = positionCurrent.lng;

  var data = JSON.stringify({
    "msgHead": title,
    "lat": lat,
    "lon": lng
  });

  var request = new XMLHttpRequest();
  request.withCredentials = false;

  request.addEventListener("readystatechange", function() {
    if(this.readyState == 4) {
      console.log(this.responseText);
      var jsonResponse = JSON.parse(this.responseText);

      //show the new word to represent thread
      var newWord = document.createElement("div");
      newWord.className = "word";
      newWord.setAttribute("_lat", lat);
      newWord.setAttribute("_lng", lng);
      newWord.setAttribute("_pop", 0);
      newWord.setAttribute("_id", jsonResponse.mongoID);
      newWord.setAttribute("_latestMessage", jsonResponse.latestMessage);
      newWord.innerText = title;
      newWord.addEventListener("click", loadMessages);
      document.getElementById("words").appendChild(newWord);
    }
  });

  request.open("POST", "https://klatelbat.com:12345/newmsgthread/post");
  request.setRequestHeader("content-type", "application/json");
  //request.setRequestHeader("cache-control", "no-cache");
  request.send(data);
}

    //set to true for debugging output
  var debug = false;

  // our current position
  var positionCurrent = {
    lat: null,
    lng: null,
    hng: null
  };

  // elements that ouput our position
  var positionLat = document.getElementById("position-lat");
  var positionLng = document.getElementById("position-lng");
  var positionHng = document.getElementById("position-hng");

  // // debug outputs
  // var debugOrientation = document.getElementById("debug-orientation");
  // var debugOrientationDefault = document.getElementById("debug-orientation-default");
  //
  //
  // // info popup elements, pus buttons that open popups
  // var popup = document.getElementById("popup");
  // var popupContents = document.getElementById("popup-contents");
  // var popupInners = document.querySelectorAll(".popup__inner");
  // var btnsPopup = document.querySelectorAll(".btn-popup");

  // buttons at the bottom of the screen
  // var btnLockOrientation = document.getElementById("btn-lock-orientation");
  // var btnNightmode = document.getElementById("btn-nightmode");
  // var btnMap = document.getElementById("btn-map");
  // var btnInfo = document.getElementById("btn-info");

  // if we have shown the heading unavailable warning yet
  var warningHeadingShown = false;

  // switches keeping track of our current app state
  var isOrientationLockable = false;
  var isOrientationLocked = false;
  var isNightMode = false;

  // the orientation of the device on app load
  var defaultOrientation;

  // browser agnostic orientation
  function getBrowserOrientation() {
    var orientation;
    if (screen.orientation && screen.orientation.type) {
      orientation = screen.orientation.type;
    } else {
      orientation = screen.orientation ||
                    screen.mozOrientation ||
                    screen.msOrientation;
    }

    /*
      'portait-primary':      for (screen width < screen height, e.g. phone, phablet, small tablet)
                                device is in 'normal' orientation
                              for (screen width > screen height, e.g. large tablet, laptop)
                                device has been turned 90deg clockwise from normal

      'portait-secondary':    for (screen width < screen height)
                                device has been turned 180deg from normal
                              for (screen width > screen height)
                                device has been turned 90deg anti-clockwise (or 270deg clockwise) from normal

      'landscape-primary':    for (screen width < screen height)
                                device has been turned 90deg clockwise from normal
                              for (screen width > screen height)
                                device is in 'normal' orientation

      'landscape-secondary':  for (screen width < screen height)
                                device has been turned 90deg anti-clockwise (or 270deg clockwise) from normal
                              for (screen width > screen height)
                                device has been turned 180deg from normal
    */

    return orientation;
  }

    // Converts from degrees to radians.
    Math.radians = function(degrees) {
        return degrees * Math.PI / 180;
    };

    // Converts from radians to degrees.
    Math.degrees = function(radians) {
        return radians * 180 / Math.PI;
    };

    // called on device orientation change
    function onHeadingChange(event) {
        var heading = event.alpha;

        if (typeof event.webkitCompassHeading !== "undefined") {
            heading = event.webkitCompassHeading; //iOS non-standard
        }

        var orientation = getBrowserOrientation();

        if (typeof heading !== "undefined" && heading !== null) { // && typeof orientation !== "undefined") {
            // we have a browser that reports device heading and orientation

            // what adjustment we have to add to rotation to allow for current device orientation
            var adjustment = 0;
            if (defaultOrientation === "landscape") {
                adjustment -= 90;
            }

            if (typeof orientation !== "undefined") {
                var currentOrientation = orientation.split("-");

                if (defaultOrientation !== currentOrientation[0]) {
                    if (defaultOrientation === "landscape") {
                        adjustment -= 270;
                    } else {
                        adjustment -= 90;
                    }
                }

                if (currentOrientation[1] === "secondary") {
                    adjustment -= 180;
                }
            }

            positionCurrent.hng = heading + adjustment;
            var phase = positionCurrent.hng < 0 ? 360 + positionCurrent.hng : positionCurrent.hng;
            positionHng.textContent = (360 - phase | 0) + "°";

            // // apply rotation to compass rose
            // if (typeof rose.style.transform !== "undefined") {
            //     rose.style.transform = "rotateZ(" + positionCurrent.hng + "deg)";
            // } else if (typeof rose.style.webkitTransform !== "undefined") {
            //     rose.style.webkitTransform = "rotateZ(" + positionCurrent.hng + "deg)";
            // }
            var words = document.getElementsByClassName("word");
            var lng1 = Math.radians(positionCurrent.lng);
            var lat1 = Math.radians(positionCurrent.lat);
            for (var i = 0; i < words.length; ++i) {
                var item = words[i];
                var lng2 = Math.radians(item.getAttribute("_lng"));
                var lat2 = Math.radians(item.getAttribute("_lat"));
                var y = Math.sin(lng2-lng1) * Math.cos(lat2);
                var x = Math.cos(lat1)*Math.sin(lat2) -
                    Math.sin(lat1)*Math.cos(lat2)*Math.cos(lng2-lng1);
                var brng = Math.degrees(Math.atan2(y, x));

                var angle = positionCurrent.hng - brng;

                var radius_earth = 6371e3; // metres
                var delta_lat = lat2-lat1;
                var delta_lng = lng2-lng1;

                var a = Math.sin(delta_lat/2) * Math.sin(delta_lat/2) +
                    Math.cos(lat1) * Math.cos(lat2) *
                    Math.sin(delta_lng/2) * Math.sin(delta_lng/2);
                var c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1-a));

                var distance = radius_earth * c;
                if (distance < 1) {
                    distance = 1;
                }
                // Distance Debug
                // item.innerText = parseInt(distance) + "m";

                // Apply corresponding font effects.
                item.style.fontSize = (90 + (item.getAttribute("_pop") * 10)) + "%";
                var isCloseToInteractWith;
                if (distance <= 10) {
                    item.style.color = "white";
                    item.style.fontSizeAdjust = "1.2";
                    isCloseToInteractWith = true;
                } else {
                    item.style.color = "#A9A9A9";
                    item.style.fontSizeAdjust = "1.0";
                    isCloseToInteractWith = false;
                }

                // Apply correct transforms
                if (typeof item.style.transform !== "undefined") {
                    item.style.transform = "rotateZ(" + (-1 * angle) + "deg)";
                    item.style.transformOrigin = "50% 200px";
                    item.style.transform += "translate(0px, " + ((distance / -0.2) - (!isCloseToInteractWith * 50)) + "px)";
                } else if (typeof item.style.webkitTransform !== "undefined") {
                    item.style.webkitTransform = "rotateZ(-" + (-1 * angle) + "deg)";
                    item.style.webkitTransformOrigin = "50% 200px";
                    item.style.webkitTransform += "translate(0px, " + ((distance / -0.2) - (!isCloseToInteractWith * 50))  + "px)";
                }

                //making new topics glow potentialls
                /*
                var prevLatestMessage = item.getAttribute("latestMessage");
                watch(locationUpdate, function(){
                  var newLatestMessage = item.getAttribute("latestMessage");
                  if(prevLatestMessage < newLatestMessage) {
                    item.style.boxShadow = "0 0 10px";
                    prevLatestMessage = newLatestMessage;
                  }
                })
                */
            }

        } else {
            positionHng.textContent = "n/a";
            showHeadingWarning();
        }
    }

    function showHeadingWarning() {
        if (!warningHeadingShown) {
            console.log("No orientation!");
            warningHeadingShown = true;
        }
    }

  function onFullscreenChange() {
    if (isOrientationLockable && getBrowserFullscreenElement()) {
      if (screen.orientation && screen.orientation.lock) {
        screen.orientation.lock(getBrowserOrientation()).then(function () {
        }).catch(function () {
        });
      }
    } else {
      lockOrientationRequest(false);
    }
  }

  function toggleOrientationLockable(lockable) {
    isOrientationLockable = lockable;
  }

  function checkLockable() {
    if (screen.orientation && screen.orientation.lock) {
      screen.orientation.lock(getBrowserOrientation()).then(function () {
        toggleOrientationLockable(true);
        browserUnlockOrientation();
      }).catch(function (event) {
        if (event.code === 18) { // The page needs to be fullscreen in order to call lockOrientation(), but is lockable
          toggleOrientationLockable(true);
          browserUnlockOrientation(); //needed as chrome was locking orientation (even if not in fullscreen, bug??)
        } else {  // lockOrientation() is not available on this device (or other error)
          toggleOrientationLockable(false);
        }
      });
    } else {
      toggleOrientationLockable(false);
    }
  }

  function lockOrientationRequest(doLock) {
    if (isOrientationLockable) {
      if (doLock) {
        browserRequestFullscreen();
        lockOrientation(true);
      } else {
        browserUnlockOrientation();
        browserExitFullscreen();
        lockOrientation(false);
      }
    }
  }

  function lockOrientation(locked) {
    if (locked) {
      btnLockOrientation.classList.add("active");
    } else {
      btnLockOrientation.classList.remove("active");
    }

    isOrientationLocked = locked;
  }

  function toggleOrientationLock() {
    if (isOrientationLockable) {
      lockOrientationRequest(!isOrientationLocked);
    }
  }

  function locationUpdate(position) {
    positionCurrent.lat = position.coords.latitude;
    positionCurrent.lng = position.coords.longitude;

    positionLat.textContent = positionCurrent.lat;
    positionLng.textContent = positionCurrent.lng;
  }

  function locationUpdateFail(error) {
    positionLat.textContent = "n/a";
    positionLng.textContent = "n/a";
    console.log("location fail: ", error);
  }

    if (screen.width > screen.height) {
        defaultOrientation = "landscape";
    } else {
        defaultOrientation = "portrait";
    }

    document.addEventListener("fullscreenchange", onFullscreenChange);
    document.addEventListener("webkitfullscreenchange", onFullscreenChange);
    document.addEventListener("mozfullscreenchange", onFullscreenChange);
    document.addEventListener("MSFullscreenChange", onFullscreenChange);
    window.addEventListener("deviceorientation", onHeadingChange);

  navigator.geolocation.watchPosition(locationUpdate, locationUpdateFail, {
      enableHighAccuracy: true,
      maximumAge: 0,
      timeout: 30000 //large timeout to accomodate slow GPS lock on some devices
  });
  checkLockable();

}());
<|endoftext|>


<commit_before>var stats, scene, renderer, composer;
var camera, cameraControls;

var cube = new THREE.Object3D();

var cameraDistance = 15;

var partsInCubeFace = 3;
var cubePartSize = 1.5;
var cubePartDepth = 0.5;
var colors = {
	'white' : {
		'hex' : 0xffffff,
		'count' : 9
	},
	'black' : {
		'hex' : 0x000000,
		'count' : 9
	},
	'red'   : {
		'hex' : 0xff0000,
		'count' : 9
	},
	'green' : {
		'hex' : 0x00ff00,
		'count' : 9
	},
	'blue'  : {
		'hex' : 0x0000ff,
		'count' : 9
	},
	'yellow': {
		'hex' : 0xffff00,
		'count' : 9
	}
};

var cubesIDs = [];

var rotations = {
	'LTR'   : {
		'CW' : new THREE.Euler(Math.PI / 2, 0, 0, 'XYZ'),
		'CCW' : new THREE.Euler(-Math.PI / 2, 0, 0, 'XYZ')
	},
	'TTB'   : {
		'CW' : new THREE.Euler(0, 0, Math.PI / 2, 'XYZ'),
		'CCW' : new THREE.Euler(0, 0, -Math.PI / 2, 'XYZ')
	},
	'FTH' : {
		'CW' : new THREE.Euler(0, Math.PI / 2, 0, 'XYZ'),
		'CCW' : new THREE.Euler(0, -Math.PI / 2, 0, 'XYZ')
	}
};

var groupingFunctions = {
	'TTB' : function(layer) {
		var groupedCubes = new THREE.Object3D();
		for (var i = 0; i < cubesIDs.length; i++) {
			for (var j = 0; j < cubesIDs[i].length; j++) {
				groupedCubes.add(
					cube.getObjectById(
						cubesIDs[i][j][layer]
					)
				);
			}
		}
		return groupedCubes;
	},
	'LTR' : function(layer) {
		var groupedCubes = new THREE.Object3D();
		for (var i = 0; i < cubesIDs[layer].length; i++) {
			for (var j = 0; j < cubesIDs[layer][i].length; j++) {
				groupedCubes.add(
					cube.getObjectById(
						cubesIDs[layer][i][j]
					)
				);
			}
		}

		return groupedCubes;
	},
	'FTH' : function(layer) {
		var groupedCubes = new THREE.Object3D();
		for (var i = 0; i < cubesIDs.length; i++) {
			for (var j = 0; j < cubesIDs[i][layer].length; j++) {
				groupedCubes.add(
					cube.getObjectById(
						cubesIDs[i][layer][j]
					)
				);
			}
		}

		return groupedCubes;
	}
}

function pickRandomProperty(obj) {
    var result;
    var count = 0;
    for (var prop in obj)
        if (Math.random() < 1 / ++count)
           result = prop;
    return result;
};

if( !init() )	animate();

function addCubePart(size, color, rotation, position) {
	if (rotation === undefined) {
		rotation = new THREE.Euler(0, 0, 0, 'XYZ');
	}
	if (position === undefined) {
		position = new THREE.Vector3(0, 0, 0);
	}
	var geometry = new THREE.BoxGeometry(size, size, size);
	for ( var i = 0; i < geometry.faces.length; i += 2) {
	    geometry.faces[i].color.setHex(color.hex);
	    geometry.faces[i + 1].color.setHex(color.hex);
	}

	var material = new THREE.MeshBasicMaterial( { color: 0xffffff, vertexColors: THREE.FaceColors } );

	var cube = new THREE.Mesh( geometry, material );
	var box = new THREE.BoxHelper( cube );

	var obj = new THREE.Object3D();
	obj.add(cube);
	obj.add(box);

	obj.position.copy(position);
	obj.rotation.copy(rotation);

	return obj;
};

function getNewColor() {
	var color = colors[pickRandomProperty(colors)];
	while (color.count < 1) {
		color = colors[pickRandomProperty(colors)];
	}
	colors[pickRandomProperty(colors)].count--;
	return color;
};

function createCube() {
	var cubePart;
	// Create a face of the cube
	for (var i = 0; i < partsInCubeFace; i++) {
		cubesIDs.push([]);
		for (var j = 0; j < partsInCubeFace; j++) {
			cubesIDs[i].push([]);
			for (var k = 0; k < partsInCubeFace; k++) {
				cubePart = 	addCubePart(
					cubePartSize,
					getNewColor(),
					undefined,
					new THREE.Vector3(
						(i - 1) * cubePartSize,
						(j - 1) * cubePartSize,
						(k - 1) * cubePartSize
					)
				);
				cubesIDs[i][j].push(cubePart.id);
				cube.add(cubePart);
			}
		}
	}

	cube.rotation.copy(new THREE.Euler(Math.PI / 2, 0, 0, 'XYZ'));
}

function rotateCube(rotation, direction, layer) {
	var groupedCubes = groupingFunctions[rotation](layer);

	groupedCubes.rotation.copy(rotations[rotation][direction]);
	groupedCubes.updateMatrixWorld();
	var child;
	while (groupedCubes.children.length > 0) {
		child = groupedCubes.children[0];
		cube.add(
			groupedCubes.children[0]
		);
		child.position.copy((new THREE.Vector3()).setFromMatrixPosition(child.matrixWorld));
	}
}

function addCubeFace(position, rotation) {
	if (rotation === undefined) {
		rotation = new THREE.Euler(0, 0, 0, 'XYZ');
	}
	if (position === undefined) {
		position = new THREE.Vector3(0, 0, 0);
	}

	var face = new THREE.Object3D();
	// Create a face of the cube
	for (var i = 0; i < partsInCubeFace; i++) {
		for (var j = 0; j < partsInCubeFace; j++) {
			face.add(
				addCubePart(
					cubePartSize,
					pickRandomProperty(colors),
					undefined,
					new THREE.Vector3(-1.5 + j * cubePartSize, -1.5 + i * cubePartSize, 0)
				)
			);
		}
	}

	face.position.copy(position);
	face.rotation.copy(rotation);

	return face;
}

// init the scene
function init(){

	if( Detector.webgl ){
		renderer = new THREE.WebGLRenderer({
			antialias		: true,	// to get smoother output
			preserveDrawingBuffer	: true	// to allow screenshot
		});
		renderer.setClearColor( 0xbbbbbb );
	}else{
		renderer	= new THREE.CanvasRenderer();
	}
	renderer.setSize( window.innerWidth, window.innerHeight );
	document.getElementById('container').appendChild(renderer.domElement);

	// add Stats.js - https://github.com/mrdoob/stats.js
	stats = new Stats();
	stats.domElement.style.position	= 'absolute';
	stats.domElement.style.bottom	= '0px';
	document.body.appendChild( stats.domElement );

	// create a scene
	scene = new THREE.Scene();

	// put a camera in the scene
	camera	= new THREE.PerspectiveCamera(35, window.innerWidth / window.innerHeight, 1, 10000 );
	camera.position.set(0, 0, cameraDistance);
	scene.add(camera);

	// create a camera contol
	cameraControls	= new THREE.TrackballControls( camera )

	// transparently support window resize
	THREEx.WindowResize.bind(renderer, camera);
	// allow 'p' to make screenshot
	THREEx.Screenshot.bindKey(renderer);
	// allow 'f' to go fullscreen where this feature is supported
	if( THREEx.FullScreen.available() ){
		THREEx.FullScreen.bindKey();
		document.getElementById('inlineDoc').innerHTML	+= "- f for fullscreen";
	}

	// here you add your objects
	// - you will most likely replace this part by your own
	var light	= new THREE.AmbientLight( Math.random() * 0xffffff );
	scene.add( light );
	var light	= new THREE.DirectionalLight( Math.random() * 0xffffff );
	light.position.set( Math.random(), Math.random(), Math.random() ).normalize();
	scene.add( light );
	var light	= new THREE.DirectionalLight( Math.random() * 0xffffff );
	light.position.set( Math.random(), Math.random(), Math.random() ).normalize();
	scene.add( light );
	var light	= new THREE.PointLight( Math.random() * 0xffffff );
	light.position.set( Math.random()-0.5, Math.random()-0.5, Math.random()-0.5 )
				.normalize().multiplyScalar(1.2);
	scene.add( light );
	var light	= new THREE.PointLight( Math.random() * 0xffffff );
	light.position.set( Math.random()-0.5, Math.random()-0.5, Math.random()-0.5 )
				.normalize().multiplyScalar(1.2);
	scene.add( light );

	createCube();
	scene.add(
		cube
	);

}

function handleKeyUp(event) {
	window.keyEvent = {
		pressed : true,
	};
	switch (event.keyCode) {
		case 81: // 'Q'
		case 87: // 'W'
			window.keyEvent.rotation = 'TTB';
			window.keyEvent.direction = event.keyCode === 81 ? 'CW' : 'CCW';
			window.keyEvent.layer = 0;
			break;
		case 65: // 'A'
		case 83: // 'S'
			window.keyEvent.rotation = 'TTB';
			window.keyEvent.direction = event.keyCode === 65 ? 'CW' : 'CCW';
			window.keyEvent.layer = 1;
			break;
		case 88: //'X'
		case 90: //'Z'
			window.keyEvent.rotation = 'TTB';
			window.keyEvent.direction = event.keyCode === 90 ? 'CW' : 'CCW';
			window.keyEvent.layer = 2;
			break;

		default:
			window.keyEvent.pressed = false;
	}
}

window.addEventListener('keyup', handleKeyUp, false);

// animation loop
function animate() {

	// loop on request animation loop
	// - it has to be at the begining of the function
	// - see details at http://my.opera.com/emoller/blog/2011/12/20/requestanimationframe-for-smart-er-animating
	requestAnimationFrame( animate );

	if (window.keyEvent === undefined) {
		window.keyEvent = {};
	}

	if (window.keyEvent.pressed) {
		window.keyEvent.pressed = false;
		rotateCube(window.keyEvent.rotation, window.keyEvent.direction, window.keyEvent.layer);
	}

	// do the render
	render();

	// update stats
	stats.update();
}

// render the scene
function render() {
	// variable which is increase by Math.PI every seconds - usefull for animation
	var PIseconds	= Date.now() * Math.PI;

	// update camera controls
	cameraControls.update();

	// actually render the scene
	renderer.render( scene, camera );
}<commit_msg>All rotation now works<commit_after>var stats, scene, renderer, composer;
var camera, cameraControls;

var cube = new THREE.Object3D();

var cameraDistance = 15;

var partsInCubeFace = 3;
var cubePartSize = 1.5;
var cubePartDepth = 0.5;
var colors = {
	'white' : {
		'hex' : 0xffffff,
		'count' : 9
	},
	'black' : {
		'hex' : 0x000000,
		'count' : 9
	},
	'red'   : {
		'hex' : 0xff0000,
		'count' : 9
	},
	'green' : {
		'hex' : 0x00ff00,
		'count' : 9
	},
	'blue'  : {
		'hex' : 0x0000ff,
		'count' : 9
	},
	'yellow': {
		'hex' : 0xffff00,
		'count' : 9
	}
};

var cubesIDs = [];

var rotations = {
	'LTR'   : {
		'CW' : new THREE.Euler(Math.PI / 2, 0, 0, 'XYZ'),
		'CCW' : new THREE.Euler(-Math.PI / 2, 0, 0, 'XYZ')
	},
	'TTB'   : {
		'CW' : new THREE.Euler(0, 0, Math.PI / 2, 'XYZ'),
		'CCW' : new THREE.Euler(0, 0, -Math.PI / 2, 'XYZ')
	},
	'FTH' : {
		'CW' : new THREE.Euler(0, Math.PI / 2, 0, 'XYZ'),
		'CCW' : new THREE.Euler(0, -Math.PI / 2, 0, 'XYZ')
	}
};

var groupingFunctions = {
	'TTB' : function(layer) {
		var groupedCubes = new THREE.Object3D();
		for (var i = 0; i < cubesIDs.length; i++) {
			for (var j = 0; j < cubesIDs[i].length; j++) {
				groupedCubes.add(
					cube.getObjectById(
						cubesIDs[i][j][layer]
					)
				);
			}
		}
		return groupedCubes;
	},
	'LTR' : function(layer) {
		var groupedCubes = new THREE.Object3D();
		for (var i = 0; i < cubesIDs[layer].length; i++) {
			for (var j = 0; j < cubesIDs[layer][i].length; j++) {
				groupedCubes.add(
					cube.getObjectById(
						cubesIDs[layer][i][j]
					)
				);
			}
		}

		return groupedCubes;
	},
	'FTH' : function(layer) {
		var groupedCubes = new THREE.Object3D();
		for (var i = 0; i < cubesIDs.length; i++) {
			for (var j = 0; j < cubesIDs[i][layer].length; j++) {
				groupedCubes.add(
					cube.getObjectById(
						cubesIDs[i][layer][j]
					)
				);
			}
		}

		return groupedCubes;
	}
}

function pickRandomProperty(obj) {
    var result;
    var count = 0;
    for (var prop in obj)
        if (Math.random() < 1 / ++count)
           result = prop;
    return result;
};

if( !init() )	animate();

function addCubePart(size, color, rotation, position) {
	if (rotation === undefined) {
		rotation = new THREE.Euler(0, 0, 0, 'XYZ');
	}
	if (position === undefined) {
		position = new THREE.Vector3(0, 0, 0);
	}
	var geometry = new THREE.BoxGeometry(size, size, size);
	for ( var i = 0; i < geometry.faces.length; i += 2) {
	    geometry.faces[i].color.setHex(color.hex);
	    geometry.faces[i + 1].color.setHex(color.hex);
	}

	var material = new THREE.MeshBasicMaterial( { color: 0xffffff, vertexColors: THREE.FaceColors } );

	var cube = new THREE.Mesh( geometry, material );
	var box = new THREE.BoxHelper( cube );

	var obj = new THREE.Object3D();
	obj.add(cube);
	obj.add(box);

	obj.position.copy(position);
	obj.rotation.copy(rotation);

	return obj;
};

function getNewColor() {
	var color = colors[pickRandomProperty(colors)];
	while (color.count < 1) {
		color = colors[pickRandomProperty(colors)];
	}
	colors[pickRandomProperty(colors)].count--;
	return color;
};

function createCube() {
	var cubePart;
	// Create a face of the cube
	for (var i = 0; i < partsInCubeFace; i++) {
		cubesIDs.push([]);
		for (var j = 0; j < partsInCubeFace; j++) {
			cubesIDs[i].push([]);
			for (var k = 0; k < partsInCubeFace; k++) {
				cubePart = 	addCubePart(
					cubePartSize,
					getNewColor(),
					undefined,
					new THREE.Vector3(
						(i - 1) * cubePartSize,
						(j - 1) * cubePartSize,
						(k - 1) * cubePartSize
					)
				);
				cubesIDs[i][j].push(cubePart.id);
				cube.add(cubePart);
			}
		}
	}

	cube.rotation.copy(new THREE.Euler(Math.PI / 2, 0, 0, 'XYZ'));
}

function rotateCube(rotation, direction, layer) {
	var groupedCubes = groupingFunctions[rotation](layer);

	groupedCubes.rotation.copy(rotations[rotation][direction]);
	groupedCubes.updateMatrixWorld();
	var child;
	while (groupedCubes.children.length > 0) {
		child = groupedCubes.children[0];
		cube.add(
			groupedCubes.children[0]
		);
		child.position.copy((new THREE.Vector3()).setFromMatrixPosition(child.matrixWorld));
	}
}

function addCubeFace(position, rotation) {
	if (rotation === undefined) {
		rotation = new THREE.Euler(0, 0, 0, 'XYZ');
	}
	if (position === undefined) {
		position = new THREE.Vector3(0, 0, 0);
	}

	var face = new THREE.Object3D();
	// Create a face of the cube
	for (var i = 0; i < partsInCubeFace; i++) {
		for (var j = 0; j < partsInCubeFace; j++) {
			face.add(
				addCubePart(
					cubePartSize,
					pickRandomProperty(colors),
					undefined,
					new THREE.Vector3(-1.5 + j * cubePartSize, -1.5 + i * cubePartSize, 0)
				)
			);
		}
	}

	face.position.copy(position);
	face.rotation.copy(rotation);

	return face;
}

// init the scene
function init(){

	if( Detector.webgl ){
		renderer = new THREE.WebGLRenderer({
			antialias		: true,	// to get smoother output
			preserveDrawingBuffer	: true	// to allow screenshot
		});
		renderer.setClearColor( 0xbbbbbb );
	}else{
		renderer	= new THREE.CanvasRenderer();
	}
	renderer.setSize( window.innerWidth, window.innerHeight );
	document.getElementById('container').appendChild(renderer.domElement);

	// add Stats.js - https://github.com/mrdoob/stats.js
	stats = new Stats();
	stats.domElement.style.position	= 'absolute';
	stats.domElement.style.bottom	= '0px';
	document.body.appendChild( stats.domElement );

	// create a scene
	scene = new THREE.Scene();

	// put a camera in the scene
	camera	= new THREE.PerspectiveCamera(35, window.innerWidth / window.innerHeight, 1, 10000 );
	camera.position.set(0, 0, cameraDistance);
	scene.add(camera);

	// create a camera contol
	cameraControls	= new THREE.TrackballControls( camera )

	// transparently support window resize
	THREEx.WindowResize.bind(renderer, camera);
	// allow 'p' to make screenshot
	THREEx.Screenshot.bindKey(renderer);
	// allow 'f' to go fullscreen where this feature is supported
	if( THREEx.FullScreen.available() ){
		THREEx.FullScreen.bindKey();
		document.getElementById('inlineDoc').innerHTML	+= "- f for fullscreen";
	}

	// here you add your objects
	// - you will most likely replace this part by your own
	var light	= new THREE.AmbientLight( Math.random() * 0xffffff );
	scene.add( light );
	var light	= new THREE.DirectionalLight( Math.random() * 0xffffff );
	light.position.set( Math.random(), Math.random(), Math.random() ).normalize();
	scene.add( light );
	var light	= new THREE.DirectionalLight( Math.random() * 0xffffff );
	light.position.set( Math.random(), Math.random(), Math.random() ).normalize();
	scene.add( light );
	var light	= new THREE.PointLight( Math.random() * 0xffffff );
	light.position.set( Math.random()-0.5, Math.random()-0.5, Math.random()-0.5 )
				.normalize().multiplyScalar(1.2);
	scene.add( light );
	var light	= new THREE.PointLight( Math.random() * 0xffffff );
	light.position.set( Math.random()-0.5, Math.random()-0.5, Math.random()-0.5 )
				.normalize().multiplyScalar(1.2);
	scene.add( light );

	createCube();
	scene.add(
		cube
	);

}

function handleKeyUp(event) {
	window.keyEvent = {
		pressed : true,
	};
	switch (event.keyCode) {
		// --- TOP TO BOTTOM --- //
		case 81: // 'Q'
		case 87: // 'W'
			window.keyEvent.rotation = 'TTB';
			window.keyEvent.direction = event.keyCode === 81 ? 'CW' : 'CCW';
			window.keyEvent.layer = 0;
			break;
		case 65: // 'A'
		case 83: // 'S'
			window.keyEvent.rotation = 'TTB';
			window.keyEvent.direction = event.keyCode === 65 ? 'CW' : 'CCW';
			window.keyEvent.layer = 1;
			break;
		case 88: //'X'
		case 90: //'Z'
			window.keyEvent.rotation = 'TTB';
			window.keyEvent.direction = event.keyCode === 90 ? 'CW' : 'CCW';
			window.keyEvent.layer = 2;
			break;
		// --------------------- //
		// --- LEFT TO RIGHT --- //
		case 69: // 'E'
		case 82: // 'R'
			window.keyEvent.rotation = 'LTR';
			window.keyEvent.direction = event.keyCode === 69 ? 'CW' : 'CCW';
			window.keyEvent.layer = 0;
			break;
		case 68: // 'D'
		case 70: // 'F'
			window.keyEvent.rotation = 'LTR';
			window.keyEvent.direction = event.keyCode === 68 ? 'CW' : 'CCW';
			window.keyEvent.layer = 1;
			break;
		case 67: //'C'
		case 86: //'V'
			window.keyEvent.rotation = 'LTR';
			window.keyEvent.direction = event.keyCode === 67 ? 'CW' : 'CCW';
			window.keyEvent.layer = 2;
			break;
		// --------------------- //
		// --- FRONT TO HIND --- //
		case 84: // 'T'
		case 89: // 'Y'
			window.keyEvent.rotation = 'FTH';
			window.keyEvent.direction = event.keyCode === 84 ? 'CW' : 'CCW';
			window.keyEvent.layer = 0;
			break;
		case 71: // 'G'
		case 72: // 'H'
			window.keyEvent.rotation = 'FTH';
			window.keyEvent.direction = event.keyCode === 71 ? 'CW' : 'CCW';
			window.keyEvent.layer = 1;
			break;
		case 66: //'B'
		case 78: //'N'
			window.keyEvent.rotation = 'FTH';
			window.keyEvent.direction = event.keyCode === 66 ? 'CW' : 'CCW';
			window.keyEvent.layer = 2;
			break;
		// ---------------------- /

		default:
			window.keyEvent.pressed = false;
	}
}

window.addEventListener('keyup', handleKeyUp, false);

// animation loop
function animate() {

	// loop on request animation loop
	// - it has to be at the begining of the function
	// - see details at http://my.opera.com/emoller/blog/2011/12/20/requestanimationframe-for-smart-er-animating
	requestAnimationFrame( animate );

	if (window.keyEvent === undefined) {
		window.keyEvent = {};
	}

	if (window.keyEvent.pressed) {
		window.keyEvent.pressed = false;
		rotateCube(window.keyEvent.rotation, window.keyEvent.direction, window.keyEvent.layer);
	}

	// do the render
	render();

	// update stats
	stats.update();
}

// render the scene
function render() {
	// variable which is increase by Math.PI every seconds - usefull for animation
	var PIseconds	= Date.now() * Math.PI;

	// update camera controls
	cameraControls.update();

	// actually render the scene
	renderer.render( scene, camera );
}<|endoftext|>


<commit_before>/**
 * Created by mjwunderlich on 3/27/15.
 */

$(function() {

  var States = { NONE:0, PLAYING:1, PAUSED:2 };

  // Initialization
  var
    field = new Field(100, 40),
    displayTimer = null,
    delay = 90,
    state = States.NONE,
    startbtn = $('#start'),
    pausebtn = $('#stop');

  function toggleState() {
    switch (state) {
      case States.NONE:
      case States.PAUSED:
        play();
        break;
      case States.PLAYING:
        pause();
        break;
    }
  }

  function updateUi() {
    switch (state) {
      case States.NONE:
        startbtn.text('Start');
        pausebtn.hide();
        break;

      case States.PLAYING:
        startbtn.text('Restart');
        pausebtn.fadeIn(1000).text('Pause');
        break;

      case States.PAUSED:
        startbtn.text('Restart');
        pausebtn.show().text('Resume');
        break;
    }
  }

  function restart() {
    field.setup();
    play();
  }

  function play() {
    clearInterval(displayTimer);
    displayTimer = setInterval(runLoop, delay);
    state = States.PLAYING;
  }

  function pause() {
    clearInterval(displayTimer);
    displayTimer = null;
    state = States.PAUSED;
  }

  $('#start').unbind().click(function () {
    restart();
    updateUi();
  });

  $('#stop').unbind().click(function () {
    toggleState();
    updateUi();
  });

  // Setup Presets
  var presets = [
    {
      text: 'Black & White',
      values: Utils.shallowExtend(globals, {
        rWhich: 'r', gWhich: 'r', bWhich: 'r',
        rCoeff: 1.0, gCoeff: 1.0, bCoeff: 1.0
      })
    }, {
      text: 'Colorful',
      values: Utils.shallowExtend(globals, {
        rWhich: 'r', gWhich: 'g', bWhich: 'b',
        rCoeff: 1.0, gCoeff: 1.0, bCoeff: 1.0
      })
    }, {
      text: 'Saturated Colorful',
      values: Utils.shallowExtend(globals, {
        rWhich: 'r', gWhich: 'g', bWhich: 'b',
        rCoeff: 2.0, gCoeff: 2.0, bCoeff: 2.0
      })
    }
  ];

  // Configure fields that will appear in the editor
  var fields = [
    {
      field: 'rWhich',
      text: 'R Channel use: r, g, b',
      type:'text' },
    {
      field: 'gWhich',
      text: 'G Channel use: r, g, b',
      type: 'text'
    },
    {
      field: 'bWhich',
      text: 'B Channel use: r, g, b',
      type: 'text'
    },

    {
      field: 'rCoeff',
      text: 'R Factor',
      type: 'float'
    },
    {
      field: 'gCoeff',
      text: 'G Factor',
      type: 'float'
    },
    {
      field: 'bCoeff',
      text: 'B Factor',
      type: 'float'
    },

    {
      field: 'samplingDepth',
      text: 'Sampling Depth (recursive)',
      type: 'float'
    },
  ];
  var editor = makeEditor(globals, fields);
  $('#editor-wrapper').append(editor);

  var presetEditor = makePresets(presets, globals);
  $('#editor-wrapper').prepend(presetEditor);

  function runLoop() {
    field.display(delay);
  }
});
<commit_msg>Start simulation as soon as page loads<commit_after>/**
 * Created by mjwunderlich on 3/27/15.
 */

$(function() {

  var States = { NONE:0, PLAYING:1, PAUSED:2 };

  // Initialization
  var
    field = new Field(100, 40),
    displayTimer = null,
    delay = 90,
    state = States.NONE,
    startbtn = $('#start'),
    pausebtn = $('#stop');

  function toggleState() {
    switch (state) {
      case States.NONE:
      case States.PAUSED:
        play();
        break;
      case States.PLAYING:
        pause();
        break;
    }
  }

  function updateUi() {
    switch (state) {
      case States.NONE:
        startbtn.text('Start');
        pausebtn.hide();
        break;

      case States.PLAYING:
        startbtn.text('Restart');
        pausebtn.fadeIn(1000).text('Pause');
        break;

      case States.PAUSED:
        startbtn.text('Restart');
        pausebtn.show().text('Resume');
        break;
    }
  }

  function restart() {
    field.setup();
    play();
  }

  function play() {
    if (state == States.NONE) {
      field.setup();
    }
    clearInterval(displayTimer);
    displayTimer = setInterval(runLoop, delay);
    state = States.PLAYING;
  }

  function pause() {
    clearInterval(displayTimer);
    displayTimer = null;
    state = States.PAUSED;
  }

  // Start running the simulation
  play();

  $('#start').unbind().click(function () {
    restart();
    updateUi();
  });

  $('#stop').unbind().click(function () {
    toggleState();
    updateUi();
  });

  // Setup Presets
  var presets = [
    {
      text: 'Black & White',
      values: Utils.shallowExtend(globals, {
        rWhich: 'r', gWhich: 'r', bWhich: 'r',
        rCoeff: 1.0, gCoeff: 1.0, bCoeff: 1.0
      })
    }, {
      text: 'Colorful',
      values: Utils.shallowExtend(globals, {
        rWhich: 'r', gWhich: 'g', bWhich: 'b',
        rCoeff: 1.0, gCoeff: 1.0, bCoeff: 1.0
      })
    }, {
      text: 'Saturated Colorful',
      values: Utils.shallowExtend(globals, {
        rWhich: 'r', gWhich: 'g', bWhich: 'b',
        rCoeff: 2.0, gCoeff: 2.0, bCoeff: 2.0
      })
    }
  ];

  // Configure fields that will appear in the editor
  var fields = [
    {
      field: 'rWhich',
      text: 'R Channel use: r, g, b',
      type:'text' },
    {
      field: 'gWhich',
      text: 'G Channel use: r, g, b',
      type: 'text'
    },
    {
      field: 'bWhich',
      text: 'B Channel use: r, g, b',
      type: 'text'
    },

    {
      field: 'rCoeff',
      text: 'R Factor',
      type: 'float'
    },
    {
      field: 'gCoeff',
      text: 'G Factor',
      type: 'float'
    },
    {
      field: 'bCoeff',
      text: 'B Factor',
      type: 'float'
    },

    {
      field: 'samplingDepth',
      text: 'Sampling Depth (recursive)',
      type: 'float'
    },
  ];
  var editor = makeEditor(globals, fields);
  $('#editor-wrapper').append(editor);

  var presetEditor = makePresets(presets, globals);
  $('#editor-wrapper').prepend(presetEditor);

  function runLoop() {
    field.display(delay);
  }
});
<|endoftext|>


<commit_before>$(function(){
  init();
});

var katieAndJamieSpreadsheet = 'https://docs.google.com/spreadsheet/pub?key=0AmhWglGO45rldGNoYy12ZDk2bU1EWTRZTWFtVEpJd2c&output=html';
var happenings;
var theMap;
var theMarkerLayer;
var playIt;

// Read the spreadsheet first, then execute the callback
function init() {
  Tabletop.init( { key: katieAndJamieSpreadsheet,
                   callback: showInfo,
                   simpleSheet: true } )
}

// Spreadsheet callback
function showInfo(data, tabletop) {
  console.log('Successfully processed!')
  console.log(data);

  // Create a map... with yet another callback
  mapbox.auto('map', 'jugglingnutcase.map-rxoo73qt', function(map) {
    theMap = map;

    // Create an empty markers layer
    theMarkerLayer = mapbox.markers.layer();

    // Add interaction to this marker layer. This
    // binds tooltips to each marker that has title
    // and description defined.
    mapbox.markers.interaction(theMarkerLayer).hideOnMove(true);
    var interaction = mapbox.markers.interaction(theMarkerLayer);

    theMap.addLayer(theMarkerLayer);

    // Set a custom formatter for tooltips
    // Provide a function that returns html to be used in tooltip
    interaction.formatter(function(feature) {
      var o;

      o = '
' + feature.properties.title + '
';
      o = o + '
';

      if (feature.properties.description != '') {
        o = o + feature.properties.description + '
';
      }

      if (feature.properties.image != undefined) {
        o = o + '';
      }

      o = o + '' + feature.properties.date.format('MMMM Do YYYY') + '';
      o = o + '
';

      return o;
    });

    // Convert the times to moment
    data.forEach(function(datum) {
      datum.date = moment(datum.date);
    })

    // Convert the data from the spreadsheet into features for insertion as markers
    happenings = data.map(function(happyHappening) {
      var lat = parseFloat(happyHappening.latitude);
      var lng = parseFloat(happyHappening.longitude);

      // Set defaults if i can't parse it
      if ( isNaN(lat) || isNaN(lng) ) {
        lat = 43.14
        lng = -77.58
      }

      return { 'geometry' : {"coordinates": [lng, lat]},
               'properties' : {
                 'marker-color': '#000',
                 'marker-symbol': happyHappening.marker,
                 title: happyHappening.title,
                 description: happyHappening.description,
                 date: happyHappening.date,
                 image: happyHappening.image
               }
             };
    })
    console.log('Happenings!');
    console.log(happenings);

    // Add the markers into the map!
    theMarkerLayer.features(happenings);
    var markers = theMarkerLayer.markers().sort(function(a, b) {
      return a.data.properties.date.unix() - b.data.properties.date.unix()
    })

    // Ease to and show the initial marker
    theMap.ease.location(markers[0].location).zoom(13).optimal();
    markers[0].showTooltip();

    // Set an interval to ease between markers
    var currentMarkerIndex = 1; // we'll start looping on the second marker and display the first
    var totalMarkers = happenings.length;
    var playIt = function() {
      var timerId = setInterval(function() {
        // Find the current marker
        var currentMarker = markers[currentMarkerIndex]

        // Ease to the marker
        theMap.ease.location(currentMarker.location).zoom(15).optimal();

        // Show the marker's popup
        currentMarker.showTooltip();

        // Increment the marker or start over again
        if  (currentMarkerIndex == totalMarkers - 1) {
          currentMarkerIndex = 0;
        }
        else {
          currentMarkerIndex++;
        }
      }, 12000);

      return timerId;
    };

    // Start it off
    var id = playIt();
    var playing = true

    // Set the start and stop handler
    $('#play').click(function() {
      if (playing) {
        // Then stop it
        clearInterval(id);
        playing = false;
        $(this).text('Play!');
      }
      else {
        id = playIt();
        playing = true;
        $(this).text('Stop!');
      }
    });
  });
}

<commit_msg>jshint<commit_after>$(function(){
  init();
});

var katieAndJamieSpreadsheet = 'https://docs.google.com/spreadsheet/pub?key=0AmhWglGO45rldGNoYy12ZDk2bU1EWTRZTWFtVEpJd2c&output=html';
var happenings;
var theMap;
var theMarkerLayer;
var playIt;

// Read the spreadsheet first, then execute the callback
function init() {
  Tabletop.init({
   key: katieAndJamieSpreadsheet,
   callback: showInfo,
   simpleSheet: true });
}

// Spreadsheet callback
function showInfo(data, tabletop) {
  console.log('Successfully processed!');
  console.log(data);

  // Create a map... with yet another callback
  mapbox.auto('map', 'jugglingnutcase.map-rxoo73qt', function(map) {
    theMap = map;

    // Create an empty markers layer
    theMarkerLayer = mapbox.markers.layer();

    // Add interaction to this marker layer. This
    // binds tooltips to each marker that has title
    // and description defined.
    mapbox.markers.interaction(theMarkerLayer).hideOnMove(true);
    var interaction = mapbox.markers.interaction(theMarkerLayer);

    theMap.addLayer(theMarkerLayer);

    // Set a custom formatter for tooltips
    // Provide a function that returns html to be used in tooltip
    interaction.formatter(function(feature) {
      var o;

      o = '
' + feature.properties.title + '
';
      o = o + '
';

      if (feature.properties.description !== '') {
        o = o + feature.properties.description + '
';
      }

      if (feature.properties.image !== undefined) {
        o = o + '';
      }

      o = o + '' + feature.properties.date.format('MMMM Do YYYY') + '';
      o = o + '
';

      return o;
    });

    // Convert the times to moment
    data.forEach(function(datum) {
      datum.date = moment(datum.date);
    });

    // Convert the data from the spreadsheet into features for insertion as markers
    happenings = data.map(function(happyHappening) {
      var lat = parseFloat(happyHappening.latitude);
      var lng = parseFloat(happyHappening.longitude);

      // Set defaults if i can't parse it
      if ( isNaN(lat) || isNaN(lng) ) {
        lat = 43.14;
        lng = -77.58;
      }

      return {
        'geometry' : { "coordinates": [lng, lat]},
        'properties' : {
          'marker-color': '#000',
          'marker-symbol': happyHappening.marker,
          title: happyHappening.title,
          description: happyHappening.description,
          date: happyHappening.date,
          image: happyHappening.image
        }
      };
    });

    console.log('Happenings!');
    console.log(happenings);

    // Add the markers into the map!
    theMarkerLayer.features(happenings);
    var markers = theMarkerLayer.markers().sort(function(a, b) {
      return a.data.properties.date.unix() - b.data.properties.date.unix();
    });

    // Ease to and show the initial marker
    theMap.ease.location(markers[0].location).zoom(13).optimal();
    markers[0].showTooltip();

    // Set an interval to ease between markers
    var currentMarkerIndex = 1; // we'll start looping on the second marker and display the first
    var totalMarkers = happenings.length;
    var playIt = function() {
      var timerId = setInterval(function() {
        // Find the current marker
        var currentMarker = markers[currentMarkerIndex];

        // Ease to the marker
        theMap.ease.location(currentMarker.location).zoom(15).optimal();

        // Show the marker's popup
        currentMarker.showTooltip();

        // Increment the marker or start over again
        if  (currentMarkerIndex == totalMarkers - 1) {
          currentMarkerIndex = 0;
        }
        else {
          currentMarkerIndex++;
        }
      }, 12000);

      return timerId;
    };

    // Start it off
    var id = playIt();
    var playing = true;

    // Set the start and stop handler
    $('#play').click(function() {
      if (playing) {
        // Then stop it
        clearInterval(id);
        playing = false;
        $(this).text('Play!');
      }
      else {
        id = playIt();
        playing = true;
        $(this).text('Stop!');
      }
    });
  });
}
<|endoftext|>


<commit_before>Calci = {
  handleKeyPress: function(key) {
    if(["AC", "DEL", "="].indexOf($(key).text()) == -1) {
      $('#preview').html(
        $('#preview').html() + $(key).text()
      );
    } else {
      console.log($(key).text());
    }
  }
};

$(document).ready(function() {
  $('.key').click(function(event){
    Calci.handleKeyPress(this);
  });
});<commit_msg>Clearing the preview after pressing 'AC'<commit_after>Calci = {
  clearPreview: function() {
    $('#preview').html("");
  },
  handleKeyPress: function(key) {
    switch($(key).text()) {
    case "AC":
      Calci.clearPreview();
      break;
    case "DEL":
      console.log($(key).text());
      break;
    case "=":
      console.log($(key).text());
      break;
    default:
      $('#preview').html(
        $('#preview').html() + $(key).text()
      );
    }
  }
};

$(document).ready(function() {
  $('.key').click(function(event){
    Calci.handleKeyPress(this);
  });
});<|endoftext|>