<commit_before>navigator.getUserMedia = Modernizr.prefixed("getUserMedia", navigator);

function getSources() {
    var def = $.Deferred();

    window.MediaStreamTrack.getSources(function(sources){
        def.resolve(sources);
    });

    return def;
}

function color(c) {
    document.getElementsByClassName("match")[0].style['background-color'] = c;
}

function QRScanner() {
    this.videos_idx = 0;
    this.api = null;
    qrcode.debug = true;
    this.lock = false;
}
QRScanner.prototype = {
    gum_success: function gum_success(stream) {
        console.log(stream);
        this.video.src = window.URL.createObjectURL(stream)
    },

    gum_failure: function gum_failure(error) {
        alert("Failed!");
    },

    timerCallback: function timerCallback() {
        if (this.video.paused || this.video.ended) {
            return;
        }

        this.ctx.drawImage(this.video, 0, 0)

        this.do_decode();
        setTimeout(this.timerCallback.bind(this), 125);
    },

    do_decode: function do_decode() {
        try {
            this.qrcode_callback(qrcode.decode());
        } catch (e) {
            if (e !== "Couldn't find enough finder patterns") {
                console.log("Error: " + e);
            }
        }
    },

    qrcode_callback: _.debounce(function qrcode_callback(data) {
        document.getElementById("data").innerHTML = data;

        if (!/^[0-9]+\$\$[a-z0-9]+\$\$[A-Za-z0-9]+$/.exec(data)) {
            document.getElementById("data").innerHTML += " is invalid";
            return;
        }

        while(this.lock) {}
        this.lock = true;
        color("green");
        this.api.scanRequest(data);
        this.lock = false;
        setTimeout('color("red")', 500);
    }, 500),

    play_callback: function play_callback() {
        setTimeout(
            function(){
                this.c1.width = this.video.videoWidth;
                this.c1.height = this.video.videoHeight;
            }.bind(this),
            125
        )

        this.timerCallback();
    },

    getSourcesCallback: function getSourcesCallback(sources) {
        var videos = (
            sources
            .filter(function(q) { return q.kind == "video" })
        )
        var env = videos.filter(function(q) { return q.facing == "environment" });
        if (env.length != 0) videos = env;

        this.getUserMedia(videos[0].id);
    },

    getCamera: function getCamera() {
        if (typeof MediaStreamTrack !== "undefined") {
            getSources().then($.proxy(this.getSourcesCallback, this));
        } else {
            this.getUserMedia();
        }
    },

    getUserMedia: function getUserMedia(id) {
        var video = (
            (id !== undefined) ?
            {optional: [{sourceId: id}]} :
            {}
        )

        navigator.getUserMedia(
            {'video': video},
            $.proxy(this.gum_success, this),
            this.gum_failure
        )
    },

    ready: function ready() {
        'use strict';
        this.video = document.getElementById("video");
        this.c1 = document.getElementById("qr-canvas");
        this.ctx = this.c1.getContext("2d");

        this.video.addEventListener("play", this.play_callback.bind(this), false);

        this.api = new QrAPI(
            "/ticket/signin",
            prompt("API password?")
        );

        this.getCamera();
    }
}

var inst = new QRScanner();

if (navigator.getUserMedia) {
    $(document).ready(function(){
        try {
            inst.ready()
        } catch (e) {
            alert(e);
        }
    })
} else {
    alert("No getUserMedia support");
}
<commit_msg>Split out camera stuff<commit_after>navigator.getUserMedia = Modernizr.prefixed("getUserMedia", navigator);

function getSources() {
    var def = $.Deferred();

    window.MediaStreamTrack.getSources(function(sources){
        def.resolve(sources);
    });

    return def;
}

function getSourcesCallback(sources) {
    var videos = (
        sources
        .filter(function(q) { return q.kind == "video" })
    )
    var env = videos.filter(function(q) { return q.facing == "environment" });
    if (env.length != 0) videos = env;

    return getUserMedia(videos[0].id);
}

function getCamera() {
    if (typeof MediaStreamTrack !== "undefined") {
        return getSources().then(getSourcesCallback);
    } else {
        return this.getUserMedia();
    }
}

function getUserMedia(id) {
    var video = (
        (id !== undefined) ?
        {optional: [{sourceId: id}]} :
        {}
    )

    var def = $.Deferred();

    navigator.getUserMedia(
        {'video': video},
        def.resolve,
        def.reject
    );

    return def;
}

function color(c) {
    document.getElementsByClassName("match")[0].style['background-color'] = c;
}

function QRScanner() {
    this.videos_idx = 0;
    this.api = null;
    qrcode.debug = true;
    this.lock = false;
}
QRScanner.prototype = {
    gum_success: function gum_success(stream) {
        console.log(stream);
        this.video.src = window.URL.createObjectURL(stream)
    },

    gum_failure: function gum_failure(error) {
        alert("Failed!");
    },

    timerCallback: function timerCallback() {
        if (this.video.paused || this.video.ended) {
            return;
        }

        this.ctx.drawImage(this.video, 0, 0)

        this.do_decode();
        setTimeout(this.timerCallback.bind(this), 125);
    },

    do_decode: function do_decode() {
        try {
            this.qrcode_callback(qrcode.decode());
        } catch (e) {
            if (e !== "Couldn't find enough finder patterns") {
                console.log("Error: " + e);
            }
        }
    },

    qrcode_callback: _.debounce(function qrcode_callback(data) {
        document.getElementById("data").innerHTML = data;

        if (!/^[0-9]+\$\$[a-z0-9]+\$\$[A-Za-z0-9]+$/.exec(data)) {
            document.getElementById("data").innerHTML += " is invalid";
            return;
        }

        while(this.lock) {}
        this.lock = true;
        color("green");
        this.api.scanRequest(data);
        this.lock = false;
        setTimeout('color("red")', 500);
    }, 500),

    play_callback: function play_callback() {
        setTimeout(
            function(){
                this.c1.width = this.video.videoWidth;
                this.c1.height = this.video.videoHeight;
            }.bind(this),
            125
        )

        this.timerCallback();
    },

    ready: function ready() {
        'use strict';
        this.video = document.getElementById("video");
        this.c1 = document.getElementById("qr-canvas");
        this.ctx = this.c1.getContext("2d");

        this.video.addEventListener("play", this.play_callback.bind(this), false);

        this.api = new QrAPI(
            "/ticket/signin",
            prompt("API password?")
        );

        getCamera().then(
            $.proxy(this.gum_success, this),
            $.proxy(this.gum_failure, this)
        )
    }
}

var inst = new QRScanner();

if (navigator.getUserMedia) {
    $(document).ready(function(){
        try {
            inst.ready()
        } catch (e) {
            alert(e);
        }
    })
} else {
    alert("No getUserMedia support");
}
<|endoftext|>


<commit_before>define(function (require, exports, module) {
    "use strict";

    /* beautify preserve:start */
    var CommandManager  = brackets.getModule("command/CommandManager");
    var Menus           = brackets.getModule("command/Menus");
    var FileSystem      = brackets.getModule("filesystem/FileSystem");
    var ProjectManager  = brackets.getModule("project/ProjectManager");
    var AppInit         = brackets.getModule("utils/AppInit");
    var ExtensionUtils  = brackets.getModule("utils/ExtensionUtils");
    var NodeDomain      = brackets.getModule("utils/NodeDomain");
    var MainViewManager = brackets.getModule("view/MainViewManager");

    var Dialog              = require("src/Dialog");
    var Strings             = require("strings");
    var ungitViewerTemplate = require("text!templates/ungit.html");
    if (typeof Promise !== "function") {
        Promise         = require("src/Promise");
    }

    var BASE_URL          = "http://localhost:8448/#/repository?path=";
    var STATUS_ERROR      = 0;
    var STATUS_INITIAL    = 1;
    var STATUS_INSTALLING = 2;
    var STATUS_INSTALLED  = 3;
    var STATUS_RUNNING    = 4;
    var STATUS_OPEN       = 5;
    /* beautify preserve:end */

    var nodeDomain = new NodeDomain("hirseUngit", ExtensionUtils.getModulePath(module, "domain"));
    var npmDomain = new NodeDomain("hirseNpm", ExtensionUtils.getModulePath(module, "npmDomain"));
    var currentPath;
    var status = STATUS_INITIAL;
    var $viewer;
    var $toolbarButton;

    function installUngit() {
        status = STATUS_INSTALLING;
        $toolbarButton.removeClass();
        $toolbarButton.addClass("installing");
        $toolbarButton.attr("title", Strings.TOOLBAR_ICON_TOOLTIP_INSTALLING);
        npmDomain.exec("install");
        npmDomain.on("out", function (event, message) {
            Dialog.appendLog(message);
        });
        npmDomain.on("installComplete", function (event, code) {
            $toolbarButton.removeClass();
            if (code === 0) {
                Dialog.openInstallationCompleteDialog();
                $toolbarButton.attr("title", Strings.TOOLBAR_ICON_TOOLTIP);
                status = STATUS_INSTALLED;
            } else {
                Dialog.openInstallationErrorDialog();
                $toolbarButton.addClass("error");
                status = STATUS_ERROR;
            }
        });
    }

    function startUngit() {
        if (status === STATUS_RUNNING) {
            return Promise.resolve();
        }
        return new Promise(function (resolve, reject) {
            $toolbarButton.addClass("starting");
            nodeDomain.exec("start");
            nodeDomain.on("error", function () {
                $toolbarButton.removeClass();
                $toolbarButton.addClass("error");
                status = STATUS_INSTALLED;
                reject();
            });
            nodeDomain.on("out", function (event, message) {
                if (message.indexOf("## Ungit started ##") !== -1 || message.indexOf("Ungit server already running") !== -1) {
                    $toolbarButton.removeClass();
                    $toolbarButton.addClass("enabled");
                    status = STATUS_RUNNING;
                    resolve();
                }
            });
        });
    }

    function killUngit() {
        if (status === STATUS_OPEN) {
            closeUngit();
        }
        nodeDomain.exec("kill");
        nodeDomain.on("close", function () {
            $toolbarButton.removeClass();
            status = STATUS_INSTALLED;
            $viewer.find("iframe").attr("src", "");
            currentPath = "";
        });
    }

    function openUngit() {
        startUngit().then(function () {
            var projectPath = ProjectManager.getProjectRoot().fullPath;
            if (currentPath !== projectPath) {
                currentPath = projectPath;
                $viewer.find("iframe").attr("src", BASE_URL + currentPath);
            }
            $viewer.fadeIn("fast");
            status = STATUS_OPEN;
        });
    }

    function closeUngit() {
        $viewer.fadeOut("fast");
        status = STATUS_RUNNING;
        CommandManager.execute("brackets-git.refreshAll");
    }

    $viewer = $(Mustache.render(ungitViewerTemplate, {
        Strings: Strings
    }));
    $viewer.find("button#hirse-ungit-close").click(closeUngit);
    $viewer.appendTo(".main-view .content");

    ExtensionUtils.loadStyleSheet(module, "styles/styles.css");

    MainViewManager.on("currentFileChange", function () {
        if (status === STATUS_OPEN) {
            closeUngit();
        }
    });

    CommandManager.register(Strings.OPEN_UNGIT_CMD, "hirse.ungit.open", openUngit);
    CommandManager.register(Strings.KILL_UNGIT_CMD, "hirse.ungit.kill", killUngit);
    var menu = Menus.getMenu(Menus.AppMenuBar.NAVIGATE_MENU);
    menu.addMenuDivider();
    menu.addMenuItem("hirse.ungit.open", "Ctrl-Alt-U");
    menu.addMenuItem("hirse.ungit.kill", "Ctrl-Alt-K");

    $toolbarButton = $(document.createElement("a"))
        .attr("id", "hirse-ungit-toolbar-icon")
        .addClass("warning")
        .attr("href", "#")
        .on("click", function () {
            if (status === STATUS_ERROR) {
                Dialog.openInstallationErrorDialog();
            } else if (status === STATUS_INSTALLING) {
                Dialog.openInstallDialog();
            } else if (status >= STATUS_INSTALLED) {
                if (status !== STATUS_OPEN) {
                    openUngit();
                } else {
                    closeUngit();
                }
            }
        })
        .appendTo($("#main-toolbar .buttons"));

    AppInit.appReady(function () {
        var nodeModules = FileSystem.getDirectoryForPath(ExtensionUtils.getModulePath(module, "node_modules"));
        nodeModules.exists(function (error, exists) {
            if (!exists) {
                installUngit();
            } else {
                $toolbarButton.removeClass();
                $toolbarButton.attr("title", Strings.TOOLBAR_ICON_TOOLTIP);
                status = STATUS_INSTALLED;
            }
        });
    });
});
<commit_msg>Add var for Promise, see #4<commit_after>define(function (require, exports, module) {
    "use strict";

    /* beautify preserve:start */
    var CommandManager  = brackets.getModule("command/CommandManager");
    var Menus           = brackets.getModule("command/Menus");
    var FileSystem      = brackets.getModule("filesystem/FileSystem");
    var ProjectManager  = brackets.getModule("project/ProjectManager");
    var AppInit         = brackets.getModule("utils/AppInit");
    var ExtensionUtils  = brackets.getModule("utils/ExtensionUtils");
    var NodeDomain      = brackets.getModule("utils/NodeDomain");
    var MainViewManager = brackets.getModule("view/MainViewManager");

    var Dialog              = require("src/Dialog");
    var Strings             = require("strings");
    var ungitViewerTemplate = require("text!templates/ungit.html");
    if (typeof Promise !== "function") {
        var Promise         = require("src/Promise");
    }

    var BASE_URL          = "http://localhost:8448/#/repository?path=";
    var STATUS_ERROR      = 0;
    var STATUS_INITIAL    = 1;
    var STATUS_INSTALLING = 2;
    var STATUS_INSTALLED  = 3;
    var STATUS_RUNNING    = 4;
    var STATUS_OPEN       = 5;
    /* beautify preserve:end */

    var nodeDomain = new NodeDomain("hirseUngit", ExtensionUtils.getModulePath(module, "domain"));
    var npmDomain = new NodeDomain("hirseNpm", ExtensionUtils.getModulePath(module, "npmDomain"));
    var currentPath;
    var status = STATUS_INITIAL;
    var $viewer;
    var $toolbarButton;

    function installUngit() {
        status = STATUS_INSTALLING;
        $toolbarButton.removeClass();
        $toolbarButton.addClass("installing");
        $toolbarButton.attr("title", Strings.TOOLBAR_ICON_TOOLTIP_INSTALLING);
        npmDomain.exec("install");
        npmDomain.on("out", function (event, message) {
            Dialog.appendLog(message);
        });
        npmDomain.on("installComplete", function (event, code) {
            $toolbarButton.removeClass();
            if (code === 0) {
                Dialog.openInstallationCompleteDialog();
                $toolbarButton.attr("title", Strings.TOOLBAR_ICON_TOOLTIP);
                status = STATUS_INSTALLED;
            } else {
                Dialog.openInstallationErrorDialog();
                $toolbarButton.addClass("error");
                status = STATUS_ERROR;
            }
        });
    }

    function startUngit() {
        if (status === STATUS_RUNNING) {
            return Promise.resolve();
        }
        return new Promise(function (resolve, reject) {
            $toolbarButton.addClass("starting");
            nodeDomain.exec("start");
            nodeDomain.on("error", function () {
                $toolbarButton.removeClass();
                $toolbarButton.addClass("error");
                status = STATUS_INSTALLED;
                reject();
            });
            nodeDomain.on("out", function (event, message) {
                if (message.indexOf("## Ungit started ##") !== -1 || message.indexOf("Ungit server already running") !== -1) {
                    $toolbarButton.removeClass();
                    $toolbarButton.addClass("enabled");
                    status = STATUS_RUNNING;
                    resolve();
                }
            });
        });
    }

    function killUngit() {
        if (status === STATUS_OPEN) {
            closeUngit();
        }
        nodeDomain.exec("kill");
        nodeDomain.on("close", function () {
            $toolbarButton.removeClass();
            status = STATUS_INSTALLED;
            $viewer.find("iframe").attr("src", "");
            currentPath = "";
        });
    }

    function openUngit() {
        startUngit().then(function () {
            var projectPath = ProjectManager.getProjectRoot().fullPath;
            if (currentPath !== projectPath) {
                currentPath = projectPath;
                $viewer.find("iframe").attr("src", BASE_URL + currentPath);
            }
            $viewer.fadeIn("fast");
            status = STATUS_OPEN;
        });
    }

    function closeUngit() {
        $viewer.fadeOut("fast");
        status = STATUS_RUNNING;
        CommandManager.execute("brackets-git.refreshAll");
    }

    $viewer = $(Mustache.render(ungitViewerTemplate, {
        Strings: Strings
    }));
    $viewer.find("button#hirse-ungit-close").click(closeUngit);
    $viewer.appendTo(".main-view .content");

    ExtensionUtils.loadStyleSheet(module, "styles/styles.css");

    MainViewManager.on("currentFileChange", function () {
        if (status === STATUS_OPEN) {
            closeUngit();
        }
    });

    CommandManager.register(Strings.OPEN_UNGIT_CMD, "hirse.ungit.open", openUngit);
    CommandManager.register(Strings.KILL_UNGIT_CMD, "hirse.ungit.kill", killUngit);
    var menu = Menus.getMenu(Menus.AppMenuBar.NAVIGATE_MENU);
    menu.addMenuDivider();
    menu.addMenuItem("hirse.ungit.open", "Ctrl-Alt-U");
    menu.addMenuItem("hirse.ungit.kill", "Ctrl-Alt-K");

    $toolbarButton = $(document.createElement("a"))
        .attr("id", "hirse-ungit-toolbar-icon")
        .addClass("warning")
        .attr("href", "#")
        .on("click", function () {
            if (status === STATUS_ERROR) {
                Dialog.openInstallationErrorDialog();
            } else if (status === STATUS_INSTALLING) {
                Dialog.openInstallDialog();
            } else if (status >= STATUS_INSTALLED) {
                if (status !== STATUS_OPEN) {
                    openUngit();
                } else {
                    closeUngit();
                }
            }
        })
        .appendTo($("#main-toolbar .buttons"));

    AppInit.appReady(function () {
        var nodeModules = FileSystem.getDirectoryForPath(ExtensionUtils.getModulePath(module, "node_modules"));
        nodeModules.exists(function (error, exists) {
            if (!exists) {
                installUngit();
            } else {
                $toolbarButton.removeClass();
                $toolbarButton.attr("title", Strings.TOOLBAR_ICON_TOOLTIP);
                status = STATUS_INSTALLED;
            }
        });
    });
});
<|endoftext|>


<commit_before>var __actions = {
    _: {
        click: function (selector) {
            var elem = document.querySelector(selector);
            elem && elem.click && elem.click();
        },
        showTray: function () {
            var $tray = $('.utility-tray');
            $tray.show();
            return $tray;
        },
        hideTray: function () {
            var $tray = $('.utility-tray');
            $tray.hide();
            return $tray;
        },
        getTourElements: function () {
            return $('.introjs-overlay, .introjs-helperLayer, .introjs-tooltipReferenceLayer');
        },
        hideTour: function () {
            this.getTourElements().hide();
        },
        showTour: function () {
            this.getTourElements().show();
        },
        waitForElement: function (selector, cb, max) {
            if (max === 0) {
                // We tried our best :(
                return;
            }
            if (typeof max === 'undefined') {
                max = 100;
            }
            var found = $(selector).is(':visible');
            if (found) {
                cb(document.querySelector(selector));
            } else {
                setTimeout(_.bind(this.waitForElement, this, selector, cb, max--), 300);
            }
        }
    },
    resetMega: function () {
        // Determine if it is active
        var isActive = document.querySelector('.mega-menu.active');
        if (isActive) {
            // It is active... Find the menu that is open and then close it.
            var activeMenu = document.querySelector('.primary-nav .active > a');
            activeMenu && activeMenu.click && activeMenu.click();
        }
        this._.hideTray();
    },
    reset: function (step, index, self) {
        this.resetMega(step, index, self);
        var $body = $(document.body);
        var dockedClass = 'introjs-docked';
        var dockedPosition = 'introjs-docked-position';
        $body.removeAttr(dockedPosition);
        if (step && step.docked) {
            $body.addClass(dockedClass);
            if (step.dockposition) {
                $body.attr(dockedPosition, step.dockposition);
            }
        } else {
            $body.removeClass(dockedClass);
        }
        // Look for and remove last class
        var previousStepClass = $body.data('introjs-step-class');
        if (previousStepClass) {
            $body.removeClass(previousStepClass);
        }
        if (step && step.stepClass) {
            // Save a ref to class we are adding for this step.
            $body.data('introjs-step-class', step.stepClass);
            $body.addClass(step.stepClass);
        }
    },
    openProducts: function () {
        this._.hideTray();
        this._.click('#nav-products > a');
    },
    openTools: function () {
        this._.click('#nav-tools > a');
    },
    openSecurity: function () {
        this._.click('#nav-security > a');
    },
    openCommunity: function () {
        this._.click('#nav-community > a');
    },
    openProfile: function () {
        var $tray = this._.showTray();
        $tray.children().hide();
        $('#account-info').css('opacity', '1').show();
    },
    stripFixParents: function () {
        $('.introjs-fixParent').removeClass('introjs-fixParent');
    },
    returnToLaunch: function () {
        if (window.location.host === 'www.redhat.com') {
            window.location = 'https://access.redhat.com/start/';
        } else {
            window.location = '/start/';
        }
    },
    ensurePath: function (step, index) {
        function _bounce() {
            var searchObj = searchToObject();
            $(document.body).addClass('introjs-hidden');
            var newPath = (step.path + '?tour=' + searchObj.tour + '&step=' + index);
            if (step.hash) {
                newPath += step.hash;
            }
            if (step.hostname) {
                return window.location = (window.location.protocol + '//' + step.hostname + newPath);
            }
            window.location = newPath;
        }
        var path = window.location.pathname;
        var hash = window.location.hash;
        if (step && step.path && path) {
            if (path !== step.path) {
                _bounce();
            }
        }
        if (step && step.hash && hash) {
            if (hash !== step.hash) {
                _bounce();
            }
        }
    },
    waitThenRefresh: function (step, index, tour) {
        var loadingClass = 'introjs-loading';
        var refresh = this.refreshPosition;
        var $body = $(document.body);
        $body.addClass(loadingClass);
        this._.waitForElement(step._element, function (element) {
            var currentStep = tour.intro._introItems[tour.intro._currentStep];
            currentStep.element = element;
            refresh(step, index, tour);
            $body.removeClass(loadingClass);
        });
    },
    refreshPosition: function (step, index, tour) {
        // refresh the tour on the next tick
        setTimeout(function () {
            // paranoid
            if (tour && tour.intro) {
                tour.intro.refresh();
            }
        }, 0);
    },
    loadRecommendations: function (step, index, tour) {
        function _loadRecommendations() {
            try {
                var $scope = angular.element('#rha-product-select').scope();
                var rhel = $scope.ProductsService.products[0];
                $scope.CaseService.kase.product = rhel.value || rhel.code;
                $scope.CaseService.onProductSelectChange();
                $scope.RecommendationsService.getRecommendations();
                this._.waitForElement('#sticky-ricky-static', function () {
                    tour.intro.refresh();
                })
            } catch (e) {}
        }
        this._.waitForElement(step.element, _.bind(_loadRecommendations, this));
    },
    scrollTop: function () {
        window.scrollTo(0, 0);
    }
};
<commit_msg>fix looking for missing element<commit_after>var __actions = {
    _: {
        click: function (selector) {
            var elem = document.querySelector(selector);
            elem && elem.click && elem.click();
        },
        showTray: function () {
            var $tray = $('.utility-tray');
            $tray.show();
            return $tray;
        },
        hideTray: function () {
            var $tray = $('.utility-tray');
            $tray.hide();
            return $tray;
        },
        getTourElements: function () {
            return $('.introjs-overlay, .introjs-helperLayer, .introjs-tooltipReferenceLayer');
        },
        hideTour: function () {
            this.getTourElements().hide();
        },
        showTour: function () {
            this.getTourElements().show();
        },
        waitForElement: function (selector, cb, max) {
            if (max === 0) {
                // We tried our best :(
                return;
            }
            if (typeof max === 'undefined') {
                max = 100;
            }
            var found = $(selector).is(':visible');
            if (found) {
                cb(document.querySelector(selector));
            } else {
                setTimeout(_.bind(this.waitForElement, this, selector, cb, max--), 300);
            }
        }
    },
    resetMega: function () {
        // Determine if it is active
        var isActive = document.querySelector('.mega-menu.active');
        if (isActive) {
            // It is active... Find the menu that is open and then close it.
            var activeMenu = document.querySelector('.primary-nav .active > a');
            activeMenu && activeMenu.click && activeMenu.click();
        }
        this._.hideTray();
    },
    reset: function (step, index, self) {
        this.resetMega(step, index, self);
        var $body = $(document.body);
        var dockedClass = 'introjs-docked';
        var dockedPosition = 'introjs-docked-position';
        $body.removeAttr(dockedPosition);
        if (step && step.docked) {
            $body.addClass(dockedClass);
            if (step.dockposition) {
                $body.attr(dockedPosition, step.dockposition);
            }
        } else {
            $body.removeClass(dockedClass);
        }
        // Look for and remove last class
        var previousStepClass = $body.data('introjs-step-class');
        if (previousStepClass) {
            $body.removeClass(previousStepClass);
        }
        if (step && step.stepClass) {
            // Save a ref to class we are adding for this step.
            $body.data('introjs-step-class', step.stepClass);
            $body.addClass(step.stepClass);
        }
    },
    openProducts: function () {
        this._.hideTray();
        this._.click('#nav-products > a');
    },
    openTools: function () {
        this._.click('#nav-tools > a');
    },
    openSecurity: function () {
        this._.click('#nav-security > a');
    },
    openCommunity: function () {
        this._.click('#nav-community > a');
    },
    openProfile: function () {
        var $tray = this._.showTray();
        $tray.children().hide();
        $('#account-info').css('opacity', '1').show();
    },
    stripFixParents: function () {
        $('.introjs-fixParent').removeClass('introjs-fixParent');
    },
    returnToLaunch: function () {
        if (window.location.host === 'www.redhat.com') {
            window.location = 'https://access.redhat.com/start/';
        } else {
            window.location = '/start/';
        }
    },
    ensurePath: function (step, index) {
        function _bounce() {
            var searchObj = searchToObject();
            $(document.body).addClass('introjs-hidden');
            var newPath = (step.path + '?tour=' + searchObj.tour + '&step=' + index);
            if (step.hash) {
                newPath += step.hash;
            }
            if (step.hostname) {
                return window.location = (window.location.protocol + '//' + step.hostname + newPath);
            }
            window.location = newPath;
        }
        var path = window.location.pathname;
        var hash = window.location.hash;
        if (step && step.path && path) {
            if (path !== step.path) {
                _bounce();
            }
        }
        if (step && step.hash && hash) {
            if (hash !== step.hash) {
                _bounce();
            }
        }
    },
    waitThenRefresh: function (step, index, tour) {
        var loadingClass = 'introjs-loading';
        var refresh = this.refreshPosition;
        var $body = $(document.body);
        $body.addClass(loadingClass);
        this._.waitForElement(step._element, function (element) {
            var currentStep = tour.intro._introItems[tour.intro._currentStep];
            currentStep.element = element;
            refresh(step, index, tour);
            $body.removeClass(loadingClass);
        });
    },
    refreshPosition: function (step, index, tour) {
        // refresh the tour on the next tick
        setTimeout(function () {
            // paranoid
            if (tour && tour.intro) {
                tour.intro.refresh();
            }
        }, 0);
    },
    loadRecommendations: function (step, index, tour) {
        function _loadRecommendations() {
            try {
                var $scope = angular.element('#rha-product-select').scope();
                var rhel = $scope.ProductsService.products[0];
                $scope.CaseService.kase.product = rhel.value || rhel.code;
                $scope.CaseService.onProductSelectChange();
                $scope.RecommendationsService.getRecommendations();
                var refresh = this.refreshPosition;
                this._.waitForElement('#rha-recommendation-section', function () {
                    refresh(step, index, tour);
                });
            } catch (e) {}
        }
        this._.waitForElement(step.element, _.bind(_loadRecommendations, this));
    },
    scrollTop: function () {
        window.scrollTo(0, 0);
    }
};
<|endoftext|>


<commit_before>
"use strict";

// dependances

	const 	path = require('path'),
			fs = require('simplefs'),
			SimplePluginsManager = require('simplepluginsmanager'),
			Warcraft3SoundsDatabase = require(path.join(__dirname, 'database', 'database.js'));

// private

	function _freeSocket(socket) {

		socket.removeAllListeners('plugin.warcraft3sounds.races.get');
			socket.removeAllListeners('plugin.warcraft3sounds.characters.get');
				socket.removeAllListeners('plugin.warcraft3sounds.actions.get');
			socket.removeAllListeners('plugin.warcraft3sounds.musics.get');
			socket.removeAllListeners('plugin.warcraft3sounds.warnings.get');

		socket.removeAllListeners('plugin.warcraft3sounds.action.play');
		socket.removeAllListeners('plugin.warcraft3sounds.music.play');
		socket.removeAllListeners('plugin.warcraft3sounds.warning.play');

	}

// module

module.exports = class CronPlugin extends SimplePluginsManager.SimplePlugin {

	constructor () {

		super();

		this.database = new Warcraft3SoundsDatabase();
		this.basicurl = '/warcraft3sounds/';

	}

	load (Container) {

		var that = this;

			this.database.init().then(function() {

				Container.get('express').get(that.basicurl + ':file', function(req, res) {

					var file = path.join(__dirname, 'sounds', req.params.file);

					if (fs.fileExists(file)) {
						res.sendFile(file);
					}
					else {

						if (res.writeHead) {
							res.writeHead(404, {'Content-Type': 'text/plain'});
						}
						if (res.end) {
							res.end('Not found');
						}

					}

				});

				Container.get('websockets').onDisconnect(_freeSocket)
				.onLog(function(socket) {

					try {

						that.database.getRaces().then(function(races) {

							Container.get('websockets').emit('plugin.warcraft3sounds.races.get', races);

						}).catch(function(err) {
							Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get races : ' + ((err.message) ? err.message : err));
							Container.get('websockets').emit('plugins.warcraft3sounds.error', ((err.message) ? err.message : err));
						});

					}
					catch(e) {
						Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get races : ' + ((e.message) ? e.message : e));
						Container.get('websockets').emit('plugins.warcraft3sounds.error', ((e.message) ? e.message : e));
					}

					socket.on('plugin.warcraft3sounds.characters.get', function (data) {

						if (!data) {
							Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
						}
						else if (!data.race || !data.race.code) {
							Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing race code.');
						}
						else {

							try {

								that.database.getCharacters(data.race).then(function(characters) {

									Container.get('websockets').emit('plugin.warcraft3sounds.characters.get', characters);

								}).catch(function(err) {
									Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get characters : ' + ((err.message) ? err.message : err));
									Container.get('websockets').emit('plugins.warcraft3sounds.error', ((err.message) ? err.message : err));
								});

							}
							catch(e) {
								Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get characters : ' + ((e.message) ? e.message : e));
								Container.get('websockets').emit('plugins.warcraft3sounds.error', ((e.message) ? e.message : e));
							}

						}

					})
						.on('plugin.warcraft3sounds.actions.get', function (data) {

							if (!data) {
								Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
							}
							else if (!data.character || !data.character.code) {
								Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing character code.');
							}
							else {

								try {

									that.database.getActions(data.character).then(function(actions) {

										actions.forEach(function(action, i) {

											actions[i].url = that.basicurl + action.file;
											delete actions[i].file;

										});

										Container.get('websockets').emit('plugin.warcraft3sounds.actions.get', actions);

									}).catch(function(err) {
										Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get actions : ' + ((err.message) ? err.message : err));
										Container.get('websockets').emit('plugins.warcraft3sounds.error', ((err.message) ? err.message : err));
									});

								}
								catch(e) {
									Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get actions : ' + ((e.message) ? e.message : e));
									Container.get('websockets').emit('plugins.warcraft3sounds.error', ((e.message) ? e.message : e));
								}

							}

						})
					.on('plugin.warcraft3sounds.musics.get', function (data) {

						if (!data) {
							Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
						}
						else if (!data.race || !data.race.code) {
							Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing race code.');
						}
						else {

							try {

								that.database.getMusics(data.race).then(function(musics) {

									musics.forEach(function(music, i) {

										musics[i].url = that.basicurl + music.file;
										delete musics[i].file;

									});

									Container.get('websockets').emit('plugin.warcraft3sounds.musics.get', musics);

								}).catch(function(err) {
									Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get musics : ' + ((err.message) ? err.message : err));
									Container.get('websockets').emit('plugins.warcraft3sounds.error', ((err.message) ? err.message : err));
								});

							}
							catch(e) {
								Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get musics : ' + ((e.message) ? e.message : e));
								Container.get('websockets').emit('plugins.warcraft3sounds.error', ((e.message) ? e.message : e));
							}

						}

					})
					.on('plugin.warcraft3sounds.warnings.get', function (data) {

						if (!data) {
							Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
						}
						else if (!data.race || !data.race.code) {
							Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing race code.');
						}
						else {

							try {

								that.database.getWarnings(data.race).then(function(warnings) {

									warnings.forEach(function(warning, i) {

										warnings[i].url = that.basicurl + warning.file;
										delete warnings[i].file;

									});

									Container.get('websockets').emit('plugin.warcraft3sounds.warnings.get', warnings);

								}).catch(function(err) {
									Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get warnings : ' + ((err.message) ? err.message : err));
									Container.get('websockets').emit('plugins.warcraft3sounds.error', ((err.message) ? err.message : err));
								});

							}
							catch(e) {
								Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get warnings : ' + ((e.message) ? e.message : e));
								Container.get('websockets').emit('plugins.warcraft3sounds.error', ((e.message) ? e.message : e));
							}

						}

					})

					.on('plugin.warcraft3sounds.action.play', function (data) {

						if (!data) {
							Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
						}
						else if (!data.action) {
							socket.emit('plugin.warcraft3sounds.error', 'Missing \'action\' data');
						}
						else if (!data.action.url) {
							socket.emit('plugin.warcraft3sounds.error', 'Missing \'action.url\' data');
						}
						else {
							Container.get('childssockets').emitTo(data.child.token, 'child.sounds.play', data.action);
						}

					})
					.on('plugin.warcraft3sounds.music.play', function (data) {

						if (!data) {
							Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
						}
						else if (!data.music) {
							socket.emit('plugin.warcraft3sounds.error', 'Missing \'music\' data');
						}
						else if (!data.music.url) {
							socket.emit('plugin.warcraft3sounds.error', 'Missing \'music.url\' data');
						}
						else {
							Container.get('childssockets').emitTo(data.child.token, 'child.sounds.play', data.music);
						}

					})
					.on('plugin.warcraft3sounds.warning.play', function (data) {

						if (!data) {
							Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
						}
						else if (!data.warning) {
							socket.emit('plugin.warcraft3sounds.error', 'Missing \'warning\' data');
						}
						else if (!data.warning.url) {
							socket.emit('plugin.warcraft3sounds.error', 'Missing \'warning.url\' data');
						}
						else {
							Container.get('childssockets').emitTo(data.child.token, 'child.sounds.play', data.warning);
						}

					});

				});

			})
			.catch(function(err) {
				Container.get('logs').err('-- [plugins/Warcraft3Sounds] - init database : ' + ((err.message) ? err.message : err));
				Container.get('websockets').emit('plugins.warcraft3sounds.error', ((err.message) ? err.message : err));
			});

		}

	}

	unload (Container) {

		super.unload();
		Container.get('websockets').getSockets().forEach(_freeSocket);

		this.database.close();

	}

	install (Container) {

		if (fs.mkdirp(path.join(__dirname, 'sounds'))) {
			Container.get('logs').log("-- [plugins/Warcraft3Sounds] : Dossier des sons créé.");
		}
		else {
			Container.get('logs').err("-- [plugins/Warcraft3Sounds] : Impossible de créer le dossier des sons.");
		}

	}

	uninstall () {

		if (fs.dirExists(path.join(__dirname, 'sounds'))) {

			if (fs.rmdirp(path.join(__dirname, 'sounds'))) {
				Container.get('logs').log("-- [plugins/Warcraft3Sounds] : Dossier des sons supprimé.");
			}
			else {
				Container.get('logs').err("-- [plugins/Warcraft3Sounds] : Impossible de supprimer le dossier des sons.");
			}

		}

	}

};
<commit_msg>corrections<commit_after>
"use strict";

// dependances

	const 	path = require('path'),
			fs = require('simplefs'),
			SimplePluginsManager = require('simplepluginsmanager'),
			Warcraft3SoundsDatabase = require(path.join(__dirname, 'database', 'database.js'));

// private

	function _freeSocket(socket) {

		socket.removeAllListeners('plugin.warcraft3sounds.races.get');
			socket.removeAllListeners('plugin.warcraft3sounds.characters.get');
				socket.removeAllListeners('plugin.warcraft3sounds.actions.get');
			socket.removeAllListeners('plugin.warcraft3sounds.musics.get');
			socket.removeAllListeners('plugin.warcraft3sounds.warnings.get');

		socket.removeAllListeners('plugin.warcraft3sounds.action.play');
		socket.removeAllListeners('plugin.warcraft3sounds.music.play');
		socket.removeAllListeners('plugin.warcraft3sounds.warning.play');

	}

// module

module.exports = class CronPlugin extends SimplePluginsManager.SimplePlugin {

	constructor () {

		super();

		this.database = new Warcraft3SoundsDatabase();
		this.basicurl = '/warcraft3sounds/';

	}

	load (Container) {

		var that = this;

		this.database.init().then(function() {

			Container.get('express').get(that.basicurl + ':file', function(req, res) {

				var file = path.join(__dirname, 'sounds', req.params.file);

				if (fs.fileExists(file)) {
					res.sendFile(file);
				}
				else {

					if (res.writeHead) {
						res.writeHead(404, {'Content-Type': 'text/plain'});
					}
					if (res.end) {
						res.end('Not found');
					}

				}

			});

			Container.get('websockets').onDisconnect(_freeSocket)
			.onLog(function(socket) {

				try {

					that.database.getRaces().then(function(races) {

						Container.get('websockets').emit('plugin.warcraft3sounds.races.get', races);

					}).catch(function(err) {
						Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get races : ' + ((err.message) ? err.message : err));
						Container.get('websockets').emit('plugins.warcraft3sounds.error', ((err.message) ? err.message : err));
					});

				}
				catch(e) {
					Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get races : ' + ((e.message) ? e.message : e));
					Container.get('websockets').emit('plugins.warcraft3sounds.error', ((e.message) ? e.message : e));
				}

				socket.on('plugin.warcraft3sounds.characters.get', function (data) {

					if (!data) {
						Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
					}
					else if (!data.race || !data.race.code) {
						Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing race code.');
					}
					else {

						try {

							that.database.getCharacters(data.race).then(function(characters) {

								Container.get('websockets').emit('plugin.warcraft3sounds.characters.get', characters);

							}).catch(function(err) {
								Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get characters : ' + ((err.message) ? err.message : err));
								Container.get('websockets').emit('plugins.warcraft3sounds.error', ((err.message) ? err.message : err));
							});

						}
						catch(e) {
							Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get characters : ' + ((e.message) ? e.message : e));
							Container.get('websockets').emit('plugins.warcraft3sounds.error', ((e.message) ? e.message : e));
						}

					}

				})
					.on('plugin.warcraft3sounds.actions.get', function (data) {

						if (!data) {
							Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
						}
						else if (!data.character || !data.character.code) {
							Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing character code.');
						}
						else {

							try {

								that.database.getActions(data.character).then(function(actions) {

									actions.forEach(function(action, i) {

										actions[i].url = that.basicurl + action.file;
										delete actions[i].file;

									});

									Container.get('websockets').emit('plugin.warcraft3sounds.actions.get', actions);

								}).catch(function(err) {
									Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get actions : ' + ((err.message) ? err.message : err));
									Container.get('websockets').emit('plugins.warcraft3sounds.error', ((err.message) ? err.message : err));
								});

							}
							catch(e) {
								Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get actions : ' + ((e.message) ? e.message : e));
								Container.get('websockets').emit('plugins.warcraft3sounds.error', ((e.message) ? e.message : e));
							}

						}

					})
				.on('plugin.warcraft3sounds.musics.get', function (data) {

					if (!data) {
						Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
					}
					else if (!data.race || !data.race.code) {
						Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing race code.');
					}
					else {

						try {

							that.database.getMusics(data.race).then(function(musics) {

								musics.forEach(function(music, i) {

									musics[i].url = that.basicurl + music.file;
									delete musics[i].file;

								});

								Container.get('websockets').emit('plugin.warcraft3sounds.musics.get', musics);

							}).catch(function(err) {
								Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get musics : ' + ((err.message) ? err.message : err));
								Container.get('websockets').emit('plugins.warcraft3sounds.error', ((err.message) ? err.message : err));
							});

						}
						catch(e) {
							Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get musics : ' + ((e.message) ? e.message : e));
							Container.get('websockets').emit('plugins.warcraft3sounds.error', ((e.message) ? e.message : e));
						}

					}

				})
				.on('plugin.warcraft3sounds.warnings.get', function (data) {

					if (!data) {
						Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
					}
					else if (!data.race || !data.race.code) {
						Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing race code.');
					}
					else {

						try {

							that.database.getWarnings(data.race).then(function(warnings) {

								warnings.forEach(function(warning, i) {

									warnings[i].url = that.basicurl + warning.file;
									delete warnings[i].file;

								});

								Container.get('websockets').emit('plugin.warcraft3sounds.warnings.get', warnings);

							}).catch(function(err) {
								Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get warnings : ' + ((err.message) ? err.message : err));
								Container.get('websockets').emit('plugins.warcraft3sounds.error', ((err.message) ? err.message : err));
							});

						}
						catch(e) {
							Container.get('logs').err('-- [plugins/Warcraft3Sounds] - get warnings : ' + ((e.message) ? e.message : e));
							Container.get('websockets').emit('plugins.warcraft3sounds.error', ((e.message) ? e.message : e));
						}

					}

				})

				.on('plugin.warcraft3sounds.action.play', function (data) {

					if (!data) {
						Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
					}
					else if (!data.action) {
						socket.emit('plugin.warcraft3sounds.error', 'Missing \'action\' data');
					}
					else if (!data.action.url) {
						socket.emit('plugin.warcraft3sounds.error', 'Missing \'action.url\' data');
					}
					else {
						Container.get('childssockets').emitTo(data.child.token, 'child.sounds.play', data.action);
					}

				})
				.on('plugin.warcraft3sounds.music.play', function (data) {

					if (!data) {
						Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
					}
					else if (!data.music) {
						socket.emit('plugin.warcraft3sounds.error', 'Missing \'music\' data');
					}
					else if (!data.music.url) {
						socket.emit('plugin.warcraft3sounds.error', 'Missing \'music.url\' data');
					}
					else {
						Container.get('childssockets').emitTo(data.child.token, 'child.sounds.play', data.music);
					}

				})
				.on('plugin.warcraft3sounds.warning.play', function (data) {

					if (!data) {
						Container.get('websockets').emit('plugin.warcraft3sounds.error', 'Missing data.');
					}
					else if (!data.warning) {
						socket.emit('plugin.warcraft3sounds.error', 'Missing \'warning\' data');
					}
					else if (!data.warning.url) {
						socket.emit('plugin.warcraft3sounds.error', 'Missing \'warning.url\' data');
					}
					else {
						Container.get('childssockets').emitTo(data.child.token, 'child.sounds.play', data.warning);
					}

				});

			});

		})
		.catch(function(err) {
			Container.get('logs').err('-- [plugins/Warcraft3Sounds] - init database : ' + ((err.message) ? err.message : err));
			Container.get('websockets').emit('plugins.warcraft3sounds.error', ((err.message) ? err.message : err));
		});

	}

	unload (Container) {

		super.unload();
		Container.get('websockets').getSockets().forEach(_freeSocket);

		this.database.close();

	}

	install (Container) {

		if (fs.mkdirp(path.join(__dirname, 'sounds'))) {
			Container.get('logs').log("-- [plugins/Warcraft3Sounds] : Dossier des sons créé.");
		}
		else {
			Container.get('logs').err("-- [plugins/Warcraft3Sounds] : Impossible de créer le dossier des sons.");
		}

	}

	uninstall () {

		if (fs.dirExists(path.join(__dirname, 'sounds'))) {

			if (fs.rmdirp(path.join(__dirname, 'sounds'))) {
				Container.get('logs').log("-- [plugins/Warcraft3Sounds] : Dossier des sons supprimé.");
			}
			else {
				Container.get('logs').err("-- [plugins/Warcraft3Sounds] : Impossible de supprimer le dossier des sons.");
			}

		}

	}

};
<|endoftext|>


<commit_before>angular.module('beamng.stuff', ['ngAnimate']);

angular.module('BeamNG.ui', ['ngMaterial', 'ngAnimate', 'ui.router', 'beamng.stuff', 'beamng.apps', 'vAccordion', 'pascalprecht.translate', 'ui.grid', 'ui.grid.grouping', 'ui.grid.resizeColumns'])

.filter('bytes', function() {
  return function(bytes, precision) {
    if(!bytes) return '';
    if (isNaN(parseFloat(bytes)) || !isFinite(bytes)) {return '-';}
    if (typeof precision === 'undefined') {precision = 1;}
    var units = ['bytes', 'kB', 'MB', 'GB', 'TB', 'PB'], number = Math.floor(Math.log(bytes) / Math.log(1024));
    return (bytes / Math.pow(1024, Math.floor(number))).toFixed(precision) +  ' ' + units[number];
  };
})

.config(['$compileProvider', '$stateProvider', '$urlRouterProvider', '$mdThemingProvider', '$translateProvider',
  function($compileProvider, $stateProvider, $urlRouterProvider, $mdThemingProvider, $translateProvider) {

  $translateProvider.useStaticFilesLoader({
    prefix: 'locales/',
    suffix: '.json'
  });
  $translateProvider.useSanitizeValueStrategy('escaped');
  $translateProvider.preferredLanguage('en_US');
  $translateProvider.fallbackLanguage('en_US');

  //$translateProvider.use('de_DE');

  // ..... User Interface states
  $stateProvider

  .state('menu', {
    url: '/menu',
    templateUrl: 'menu.html'
  })

    // // Transition to this state is handled by some unknown dark force (Torque?).
    // // Until this chanages, keep the url hash to "mainmenu".
    // .state('mainmenu', {
    //   url: '/mainmenu',
    //   templateUrl: 'modules/mainmenu/mainmenu.html',
    //   controller:  'MainMenuController as mainmenu'
    // })

    .state('menu.levels', {
      url: '/levels',
      templateUrl: 'modules/levelselect/levelselect.html',
      controller:  'LevelSelectController as levels',
      resolve: {
        levelsList: ['$q', 'bngApi', 'InstalledMods',  function ($q, bngApi, InstalledMods) {
          var d = $q.defer();

          bngApi.engineLua('levels.getList()', function (res) {
            InstalledMods.levels = res;
            d.resolve();
          });
        }]
      }
    })

    .state('menu.environment', {
      url: '/environment',
      templateUrl: 'modules/environment/environment.html',
      controller:  'EnvironmentController as environment',
      resolve: {
        currentState: ['$q', 'bngApi', function ($q, bngApi) {
          var d = $q.defer();
          bngApi.engineLua('environment.getState()', function (res) { d.resolve(res); });
          return d.promise;
        }]
      }
    })

    .state('menu.scenarios', {
      url: '/scenarios',
      templateUrl: 'modules/scenarioselect/scenarioselect.html',
      controller: 'ScenarioSelectController'
    })

    .state('menu.apps', {
      url: '/apps',
      templateUrl: 'modules/appselect/appselect.html',
      controller: 'AppSelectController as apps',
      resolve: {
        populate: ['$q', 'bngApi', 'InstalledMods', function ($q, bngApi, InstalledMods) {
          var d = $q.defer();
          bngApi.engineLua('apps.getList()', function (response) {
            InstalledMods.apps = response.list;
            d.resolve();
          });
          return d.promise;
        }]
      }
    })

    .state('menu.vehicles', {
      url: '/vehicleselect',
      templateUrl: 'modules/vehicleselect/vehicleselect.html',
      controller: 'VehicleSelectController as vehicles',
      resolve: {
        populate: ['$q', 'bngApi', 'InstalledMods', function ($q, bngApi, InstalledMods) {
          var d = $q.defer();
          bngApi.engineLua('vehicles.getVehicleList()', function (response) {
            console.log('the vehicles:', response);
            if (response) {
              InstalledMods.vehicles.index = response.index;
              InstalledMods.vehicles.list  = response.list;
              for (var f in response.filters) {
                if (InstalledMods.vehicles.filters[f]) continue;
                else InstalledMods.vehicles.filters[f] = response.filters[f];
              }
            }
            d.resolve();
          });
          return d.promise;
        }]
      }
    })

    .state('menu.options', {
      url: '/options',
      templateUrl: 'modules/options2/options2.html',
      controller: 'Options2Controller'
    })

    .state('menu.controls', {
      url: '/controls',
      templateUrl: 'modules/options/options.html',
      controller: 'OptionsController'
    })

    .state('menu.debug', {
      url: '/debug',
      templateUrl: 'modules/debug/debug.html',
      controller:  'DebugController'
    })

    .state('menu.feedback', {
      url: '/feedback',
      templateUrl: 'modules/feedback/feedback.html',
      controller: 'FeedbackController'
    })

    .state('menu.vehicleconfig', {
      url: '/vehicle-config',
      templateUrl: 'modules/vehicleconfig/vehicleconfig.html',
      controller: 'VehicleconfigController'
    })

    .state('menu.help', {
      url: '/help:pageIndex',
      templateUrl: 'modules/help/help.html',
      controller: 'HelpController'
    })

    .state('menu.mods', {
      url: '/modemanager',
      templateUrl: 'modules/modmanager/modmanager.html',
      controller: 'ModManagerController'
    })

    .state('menu.mainmenu', {
      url: '/main',
      templateUrl: 'modules/mainmenu/mainmenu.html',
      controller: 'MainMenuController'
    })

  // Transition to this state is handled by some unknown dark force (Torque?).
  // Until this chanages, keep the url hash to "loading".
  .state('loading', {
    url: '/loading',
    templateUrl: 'modules/loading/loading.html',
    controller:  'LoadingController as loading'
  })

  .state('photomode', {
    url: '/photo-mode',
    templateUrl: 'modules/photomode/photomode.html',
    controller:  'PhotoModeController as photo',
    resolve: {
      steamStatus: ['$q', 'bngApi', function($q, bngApi) {
        var d = $q.defer();
        bngApi.engineLua('Steam.isWorking', function(res) { d.resolve(res); });
        return d.promise;
      }]
    }
  })

  .state('credits', {
    url: '/credits',
    templateUrl: 'modules/credits/credits.html',
    controller: 'CreditsController'
  });

  $urlRouterProvider.otherwise('/menu');

  $compileProvider.debugInfoEnabled(false);

  // whitelist for local:// prefix
  $compileProvider.aHrefSanitizationWhitelist(/^\s*(https?|ftp|mailto|local):/);
  $compileProvider.imgSrcSanitizationWhitelist(/^\s*(https?|ftp|mailto|local):/);

  $mdThemingProvider.theme('default')
    .primaryPalette('blue-grey')
    .accentPalette('orange')
    .warnPalette('red')
    .backgroundPalette('grey');
}])

.run(['$log', '$rootScope', '$window', '$animate', 'apiCallbacks', function ($log, $rootScope, $window, $animate, apiCallbacks) {

  $animate.enabled(false);

  // ..... Define all objects attached directly to the window object here

  $window.HookManager = {
    trigger: function (hookName, data) {
      if (hookName == 'MenuHide') return; // ignore until the autohide feature gets fixed.

      $log.debug('[HookManager] triggered', hookName, 'w/', data);
      $rootScope.$broadcast(hookName, data);
    }
  };

  // This should not be a function attached to the window object, but rather a HookManager event.
  // Until this is done, we just mock up the process.
  $window.updateProgress = function(val, txt) {
    $rootScope.$broadcast('UpdateProgress', {value: Math.floor(100 * val), text: txt });
  };

  $window.bngApiCallback = function(idx, result) {
    apiCallbacks[idx](result);
    apiCallbacks[idx] = undefined;
  };

  $window.sendCompleteObjectState = function (value, txt) {
    console.log('completeObjectState', value, 'and', txt)
  };

  $window.updatePhysicsState = function (value) {
    console.log('got updatePhysicsState w/', value);
  };

}]);

angular.module('beamng.stuff')

.value('InstalledMods', {
  levels:    { index: [], list: [] },
  scenarios: [],
  vehicles:  { index: [], list: [], filters: {} },
  campaigns: [],
  apps: []
})

.controller('LevelSelectController',  ['$location', 'bngApi', 'InstalledMods', function($location,  bngApi,  InstalledMods) {
    var vm = this;
    vm.installed = InstalledMods.levels;

    vm.selected = null;

    vm.select = function (level) {
      vm.selected = level;
    };

    vm.launch = function() {
      bngApi.sendGameEngine('startLevel("' + vm.selected.misFilePath + '");');
    };
}])

.controller('AppCtrl', ['$document', '$log', '$scope', '$state', '$mdToast', 'bngApi', '$translate',
  function($document, $log, $scope, $state, $mdToast, bngApi, $translate) {
  var vm = this;

  vm.showMenu = true;

  // REMOVE THIS!! ------------------------------------
  $scope.$watch(function () {
    return window.location.hash;
  }, function () {
    console.log('HASH CHANGE:', window.location.hash);
  });
  // -------------------------------------------------

  vm.menuEntries = {
    init: [],
    game: [
      { translateid: 'dashboard.levels',      icon: 'terrain',        state: 'menu.levels'     },
      { translateid: 'dashboard.environment', icon: 'cloud_queue',    state: 'menu.environment'},
      { translateid: 'dashboard.scenarios',   icon: 'directions',     state: 'menu.scenarios'  },
      { translateid: 'dashboard.vehicles',    icon: 'directions_car', state: 'menu.vehicles'   },
      { translateid: 'dashboard.options',     icon: 'tune',           state: 'menu.options'    },
      { translateid: 'dashboard.debug',       icon: 'bug_report',     state: 'menu.debug'      },
      { translateid: 'dashboard.feedback',    icon: 'gesture',        state: 'menu.feedback'   },
      { translateid: 'dashboard.apps',        icon: 'apps',           state: 'menu.apps'       },
      { translateid: 'dashboard.photomode',   icon: 'photo_camera',   state: 'photomode'       },
      { translateid: 'dashboard.credits',     icon: 'people',         state: 'credits'         },
      { translateid: 'dashboard.vehicleconfig', icon: 'settings_applications', state: 'menu.vehicleconfig' },
      { translateid: 'dashboard.help',        icon: 'help', state: 'menu.help' },
      { translateid: 'dashboard.mods',        icon: 'shop', state: 'menu.mods' },
      { translateid: 'dashboard.mainmenu',        icon: 'help', state: 'menu.mainmenu' },
      // { translateid: 'dashboard.controls', icon: 'games', state: 'menu.controls' }
    ]
  };

  $scope.$on('XIControllerChanged', function (event, data) {
    $log.debug('[AppCtrl] received XIControllerChanged', data);
    $mdToast.show(
      $mdToast.simple()
      .content('XBox controller (dis)connected.')
      .position('top right')
      .hideDelay(5000)
    );
  });

  // **************************************************************************
  // language switching tests
  // var langid = 0;
  // var lang_available = ['en_US', 'de_DE', 'el'];
  // function toggle_lang_example() {
  //   langid++;
  //   if(langid >= lang_available.length) langid = 0;
  //// console.log('switched language to: ', lang_available[langid]);
  //   $scope.$apply(function() {
  //     $translate.use(lang_available[langid]);
  //   });
  //   setTimeout(toggle_lang_example, 3000);
  // }
  // toggle_lang_example();
  // **************************************************************************

  $scope.$on('MenuToggle', function (event, data) {
    $log.debug('[AppCtrl] received MenuToggle', data);
    vm.showMenu = !vm.showMenu;

    if (!vm.showMenu) {
      console.log('going...');
      $state.go('menu');
    };

    $scope.$digest();

    // REMOVE THIS!!! (and bngApi injection)
    var luaCmd = {changes: ['streams'], streams: {escData: 1, engineInfo: 1, sensors: 1}};
    beamng.sendActiveObjectLua('guiUpdate(' + bngApi.serializeToLua(luaCmd) + ')');
    console.log('sent:', bngApi.serializeToLua(luaCmd));
  });

}]);

function parseBBCode(text) {
    text = text.replace(/\[url=http:\/\/([^\s\]]+)\](.*?(?=\[\/url\]))\[\/url\]/gi, '$2');
    text = text.replace(/\[forumurl=http:\/\/([^\s\]]+)\](\S*?(?=\[\/forumurl\]))\[\/forumurl\]/gi, '$2');
    text = text.replace(/\[url\]http:\/\/(.*?(?=\[\/url\]))\[\/b\]/gi, '$1');
    text = text.replace(/\[ico=([^\s\]]+)\s*\](.*?(?=\[\/ico\]))\[\/ico\]/gi, '$2');
    text = text.replace(/\[h1\](.*?(?=\[\/h1\]))\[\/h1\]/gi, '
$1
');
    text = text.replace(/\[img\](.*?(?=\[\/img\]))\[\/img\]/gi, '');
    text = text.replace(/\[list\]\r\n/gi, '
');
    text = text.replace(/\[\/list\]/gi, '
');
    text = text.replace(/\[olist\]/gi, '
');
    text = text.replace(/\[\/olist\]/gi, '
');
    text = text.replace(/\[\*\](.*?(?=\r))\r\n/gi, '
$1
');
    text = text.replace(/\[b\](.*?(?=\[\/b\]))\[\/b\]/gi, '$1');
    text = text.replace(/\[u\](.*?(?=\[\/u\]))\[\/u\]/gi, '$1');
    text = text.replace(/\[s\](.*?(?=\[\/s\]))\[\/s\]/gi, '<s>$1</s>');
    text = text.replace(/\[i\](.*?(?=\[\/i\]))\[\/i\]/gi, '$1');
    text = text.replace(/\[strike\](.*?(?=\[\/strike\]))\[\/strike\]/gi, '<s>$1</s>');
    text = text.replace(/\[ico=([^\s\]]+)\s*\]/gi, '');
    text = text.replace(/\[code\](.*?(?=\[\/code\]))\[\/code\]/gi, '$1');
    text = text.replace(/\[br\]/gi, '
');
    text = text.replace(/\n\n/gi, '
');
    text = text.replace(/\n/gi, '');
    return text;
  }

function convertTimestamp(stamp) {
  return new Date(stamp * 1000).toDateString();
}<commit_msg>temporary icon in dashmenu for mainmenu<commit_after>angular.module('beamng.stuff', ['ngAnimate']);

angular.module('BeamNG.ui', ['ngMaterial', 'ngAnimate', 'ui.router', 'beamng.stuff', 'beamng.apps', 'vAccordion', 'pascalprecht.translate', 'ui.grid', 'ui.grid.grouping', 'ui.grid.resizeColumns'])

.filter('bytes', function() {
  return function(bytes, precision) {
    if(!bytes) return '';
    if (isNaN(parseFloat(bytes)) || !isFinite(bytes)) {return '-';}
    if (typeof precision === 'undefined') {precision = 1;}
    var units = ['bytes', 'kB', 'MB', 'GB', 'TB', 'PB'], number = Math.floor(Math.log(bytes) / Math.log(1024));
    return (bytes / Math.pow(1024, Math.floor(number))).toFixed(precision) +  ' ' + units[number];
  };
})

.config(['$compileProvider', '$stateProvider', '$urlRouterProvider', '$mdThemingProvider', '$translateProvider',
  function($compileProvider, $stateProvider, $urlRouterProvider, $mdThemingProvider, $translateProvider) {

  $translateProvider.useStaticFilesLoader({
    prefix: 'locales/',
    suffix: '.json'
  });
  $translateProvider.useSanitizeValueStrategy('escaped');
  $translateProvider.preferredLanguage('en_US');
  $translateProvider.fallbackLanguage('en_US');

  //$translateProvider.use('de_DE');

  // ..... User Interface states
  $stateProvider

  .state('menu', {
    url: '/menu',
    templateUrl: 'menu.html'
  })

    // // Transition to this state is handled by some unknown dark force (Torque?).
    // // Until this chanages, keep the url hash to "mainmenu".
    // .state('mainmenu', {
    //   url: '/mainmenu',
    //   templateUrl: 'modules/mainmenu/mainmenu.html',
    //   controller:  'MainMenuController as mainmenu'
    // })

    .state('menu.levels', {
      url: '/levels',
      templateUrl: 'modules/levelselect/levelselect.html',
      controller:  'LevelSelectController as levels',
      resolve: {
        levelsList: ['$q', 'bngApi', 'InstalledMods',  function ($q, bngApi, InstalledMods) {
          var d = $q.defer();

          bngApi.engineLua('levels.getList()', function (res) {
            InstalledMods.levels = res;
            d.resolve();
          });
        }]
      }
    })

    .state('menu.environment', {
      url: '/environment',
      templateUrl: 'modules/environment/environment.html',
      controller:  'EnvironmentController as environment',
      resolve: {
        currentState: ['$q', 'bngApi', function ($q, bngApi) {
          var d = $q.defer();
          bngApi.engineLua('environment.getState()', function (res) { d.resolve(res); });
          return d.promise;
        }]
      }
    })

    .state('menu.scenarios', {
      url: '/scenarios',
      templateUrl: 'modules/scenarioselect/scenarioselect.html',
      controller: 'ScenarioSelectController'
    })

    .state('menu.apps', {
      url: '/apps',
      templateUrl: 'modules/appselect/appselect.html',
      controller: 'AppSelectController as apps',
      resolve: {
        populate: ['$q', 'bngApi', 'InstalledMods', function ($q, bngApi, InstalledMods) {
          var d = $q.defer();
          bngApi.engineLua('apps.getList()', function (response) {
            InstalledMods.apps = response.list;
            d.resolve();
          });
          return d.promise;
        }]
      }
    })

    .state('menu.vehicles', {
      url: '/vehicleselect',
      templateUrl: 'modules/vehicleselect/vehicleselect.html',
      controller: 'VehicleSelectController as vehicles',
      resolve: {
        populate: ['$q', 'bngApi', 'InstalledMods', function ($q, bngApi, InstalledMods) {
          var d = $q.defer();
          bngApi.engineLua('vehicles.getVehicleList()', function (response) {
            console.log('the vehicles:', response);
            if (response) {
              InstalledMods.vehicles.index = response.index;
              InstalledMods.vehicles.list  = response.list;
              for (var f in response.filters) {
                if (InstalledMods.vehicles.filters[f]) continue;
                else InstalledMods.vehicles.filters[f] = response.filters[f];
              }
            }
            d.resolve();
          });
          return d.promise;
        }]
      }
    })

    .state('menu.options', {
      url: '/options',
      templateUrl: 'modules/options2/options2.html',
      controller: 'Options2Controller'
    })

    .state('menu.controls', {
      url: '/controls',
      templateUrl: 'modules/options/options.html',
      controller: 'OptionsController'
    })

    .state('menu.debug', {
      url: '/debug',
      templateUrl: 'modules/debug/debug.html',
      controller:  'DebugController'
    })

    .state('menu.feedback', {
      url: '/feedback',
      templateUrl: 'modules/feedback/feedback.html',
      controller: 'FeedbackController'
    })

    .state('menu.vehicleconfig', {
      url: '/vehicle-config',
      templateUrl: 'modules/vehicleconfig/vehicleconfig.html',
      controller: 'VehicleconfigController'
    })

    .state('menu.help', {
      url: '/help:pageIndex',
      templateUrl: 'modules/help/help.html',
      controller: 'HelpController'
    })

    .state('menu.mods', {
      url: '/modemanager',
      templateUrl: 'modules/modmanager/modmanager.html',
      controller: 'ModManagerController'
    })

    .state('menu.mainmenu', {
      url: '/main',
      templateUrl: 'modules/mainmenu/mainmenu.html',
      controller: 'MainMenuController'
    })

  // Transition to this state is handled by some unknown dark force (Torque?).
  // Until this chanages, keep the url hash to "loading".
  .state('loading', {
    url: '/loading',
    templateUrl: 'modules/loading/loading.html',
    controller:  'LoadingController as loading'
  })

  .state('photomode', {
    url: '/photo-mode',
    templateUrl: 'modules/photomode/photomode.html',
    controller:  'PhotoModeController as photo',
    resolve: {
      steamStatus: ['$q', 'bngApi', function($q, bngApi) {
        var d = $q.defer();
        bngApi.engineLua('Steam.isWorking', function(res) { d.resolve(res); });
        return d.promise;
      }]
    }
  })

  .state('credits', {
    url: '/credits',
    templateUrl: 'modules/credits/credits.html',
    controller: 'CreditsController'
  });

  $urlRouterProvider.otherwise('/menu');

  $compileProvider.debugInfoEnabled(false);

  // whitelist for local:// prefix
  $compileProvider.aHrefSanitizationWhitelist(/^\s*(https?|ftp|mailto|local):/);
  $compileProvider.imgSrcSanitizationWhitelist(/^\s*(https?|ftp|mailto|local):/);

  $mdThemingProvider.theme('default')
    .primaryPalette('blue-grey')
    .accentPalette('orange')
    .warnPalette('red')
    .backgroundPalette('grey');
}])

.run(['$log', '$rootScope', '$window', '$animate', 'apiCallbacks', function ($log, $rootScope, $window, $animate, apiCallbacks) {

  $animate.enabled(false);

  // ..... Define all objects attached directly to the window object here

  $window.HookManager = {
    trigger: function (hookName, data) {
      if (hookName == 'MenuHide') return; // ignore until the autohide feature gets fixed.

      $log.debug('[HookManager] triggered', hookName, 'w/', data);
      $rootScope.$broadcast(hookName, data);
    }
  };

  // This should not be a function attached to the window object, but rather a HookManager event.
  // Until this is done, we just mock up the process.
  $window.updateProgress = function(val, txt) {
    $rootScope.$broadcast('UpdateProgress', {value: Math.floor(100 * val), text: txt });
  };

  $window.bngApiCallback = function(idx, result) {
    apiCallbacks[idx](result);
    apiCallbacks[idx] = undefined;
  };

  $window.sendCompleteObjectState = function (value, txt) {
    console.log('completeObjectState', value, 'and', txt)
  };

  $window.updatePhysicsState = function (value) {
    console.log('got updatePhysicsState w/', value);
  };

}]);

angular.module('beamng.stuff')

.value('InstalledMods', {
  levels:    { index: [], list: [] },
  scenarios: [],
  vehicles:  { index: [], list: [], filters: {} },
  campaigns: [],
  apps: []
})

.controller('LevelSelectController',  ['$location', 'bngApi', 'InstalledMods', function($location,  bngApi,  InstalledMods) {
    var vm = this;
    vm.installed = InstalledMods.levels;

    vm.selected = null;

    vm.select = function (level) {
      vm.selected = level;
    };

    vm.launch = function() {
      bngApi.sendGameEngine('startLevel("' + vm.selected.misFilePath + '");');
    };
}])

.controller('AppCtrl', ['$document', '$log', '$scope', '$state', '$mdToast', 'bngApi', '$translate',
  function($document, $log, $scope, $state, $mdToast, bngApi, $translate) {
  var vm = this;

  vm.showMenu = true;

  // REMOVE THIS!! ------------------------------------
  $scope.$watch(function () {
    return window.location.hash;
  }, function () {
    console.log('HASH CHANGE:', window.location.hash);
  });
  // -------------------------------------------------

  vm.menuEntries = {
    init: [],
    game: [
      { translateid: 'dashboard.levels',      icon: 'terrain',        state: 'menu.levels'     },
      { translateid: 'dashboard.environment', icon: 'cloud_queue',    state: 'menu.environment'},
      { translateid: 'dashboard.scenarios',   icon: 'directions',     state: 'menu.scenarios'  },
      { translateid: 'dashboard.vehicles',    icon: 'directions_car', state: 'menu.vehicles'   },
      { translateid: 'dashboard.options',     icon: 'tune',           state: 'menu.options'    },
      { translateid: 'dashboard.debug',       icon: 'bug_report',     state: 'menu.debug'      },
      { translateid: 'dashboard.feedback',    icon: 'gesture',        state: 'menu.feedback'   },
      { translateid: 'dashboard.apps',        icon: 'apps',           state: 'menu.apps'       },
      { translateid: 'dashboard.photomode',   icon: 'photo_camera',   state: 'photomode'       },
      { translateid: 'dashboard.credits',     icon: 'people',         state: 'credits'         },
      { translateid: 'dashboard.vehicleconfig', icon: 'settings_applications', state: 'menu.vehicleconfig' },
      { translateid: 'dashboard.help',        icon: 'help', state: 'menu.help' },
      { translateid: 'dashboard.mods',        icon: 'shop', state: 'menu.mods' },
      { translateid: 'dashboard.mainmenu',        icon: 'collections', state: 'menu.mainmenu' },
      // { translateid: 'dashboard.controls', icon: 'games', state: 'menu.controls' }
    ]
  };

  $scope.$on('XIControllerChanged', function (event, data) {
    $log.debug('[AppCtrl] received XIControllerChanged', data);
    $mdToast.show(
      $mdToast.simple()
      .content('XBox controller (dis)connected.')
      .position('top right')
      .hideDelay(5000)
    );
  });

  // **************************************************************************
  // language switching tests
  // var langid = 0;
  // var lang_available = ['en_US', 'de_DE', 'el'];
  // function toggle_lang_example() {
  //   langid++;
  //   if(langid >= lang_available.length) langid = 0;
  //// console.log('switched language to: ', lang_available[langid]);
  //   $scope.$apply(function() {
  //     $translate.use(lang_available[langid]);
  //   });
  //   setTimeout(toggle_lang_example, 3000);
  // }
  // toggle_lang_example();
  // **************************************************************************

  $scope.$on('MenuToggle', function (event, data) {
    $log.debug('[AppCtrl] received MenuToggle', data);
    vm.showMenu = !vm.showMenu;

    if (!vm.showMenu) {
      console.log('going...');
      $state.go('menu');
    };

    $scope.$digest();

    // REMOVE THIS!!! (and bngApi injection)
    var luaCmd = {changes: ['streams'], streams: {escData: 1, engineInfo: 1, sensors: 1}};
    beamng.sendActiveObjectLua('guiUpdate(' + bngApi.serializeToLua(luaCmd) + ')');
    console.log('sent:', bngApi.serializeToLua(luaCmd));
  });

}]);

function parseBBCode(text) {
    text = text.replace(/\[url=http:\/\/([^\s\]]+)\](.*?(?=\[\/url\]))\[\/url\]/gi, '$2');
    text = text.replace(/\[forumurl=http:\/\/([^\s\]]+)\](\S*?(?=\[\/forumurl\]))\[\/forumurl\]/gi, '$2');
    text = text.replace(/\[url\]http:\/\/(.*?(?=\[\/url\]))\[\/b\]/gi, '$1');
    text = text.replace(/\[ico=([^\s\]]+)\s*\](.*?(?=\[\/ico\]))\[\/ico\]/gi, '$2');
    text = text.replace(/\[h1\](.*?(?=\[\/h1\]))\[\/h1\]/gi, '
$1
');
    text = text.replace(/\[img\](.*?(?=\[\/img\]))\[\/img\]/gi, '');
    text = text.replace(/\[list\]\r\n/gi, '
');
    text = text.replace(/\[\/list\]/gi, '
');
    text = text.replace(/\[olist\]/gi, '
');
    text = text.replace(/\[\/olist\]/gi, '
');
    text = text.replace(/\[\*\](.*?(?=\r))\r\n/gi, '
$1
');
    text = text.replace(/\[b\](.*?(?=\[\/b\]))\[\/b\]/gi, '$1');
    text = text.replace(/\[u\](.*?(?=\[\/u\]))\[\/u\]/gi, '$1');
    text = text.replace(/\[s\](.*?(?=\[\/s\]))\[\/s\]/gi, '<s>$1</s>');
    text = text.replace(/\[i\](.*?(?=\[\/i\]))\[\/i\]/gi, '$1');
    text = text.replace(/\[strike\](.*?(?=\[\/strike\]))\[\/strike\]/gi, '<s>$1</s>');
    text = text.replace(/\[ico=([^\s\]]+)\s*\]/gi, '');
    text = text.replace(/\[code\](.*?(?=\[\/code\]))\[\/code\]/gi, '$1');
    text = text.replace(/\[br\]/gi, '
');
    text = text.replace(/\n\n/gi, '
');
    text = text.replace(/\n/gi, '');
    return text;
  }

function convertTimestamp(stamp) {
  return new Date(stamp * 1000).toDateString();
}<|endoftext|>


<commit_before>"use strict";

const DEFAULT_DELAY_TIME = 5;
const TEMP_DIRECTRY_PREFIX = 'kirakira';
const temp = require('temp').track();
const fs   = require('fs');
const util  = require('util');
const sprintf = require('sprintf').sprintf
const path = require('path');
const im = require('imagemagick');

function increaseVerbosity(v, total) {
  return total + 1;
}

let program = require('commander');
program.version('0.0.1');
program.usage('-i <input file> [options]');
program.option('-i, --input <path>', 'input file');
program.option('-o, --output [path]', 'output path');
program.option('-s, --saturation [percent value]', 'saturation value');
program.option('-p, --plain', 'Do NOT Kirakira effect', function(){return true}, 0);
program.option('--colors [value]', 'preferred number of colors in the image', parseInt);
program.option('--delay [time]', 'delay time', parseInt);
program.option('--framenum [integer]', 'frame number', parseInt);
program.option('--guruguru', 'enable guruguru effect', function(){return true}, 0);
program.parse(process.argv);
const input = program.input;
const output = program.output !== undefined ? program.output : "out.gif";
const delay = program.delay !== undefined ? program.delay : DEFAULT_DELAY_TIME;
const saturation = program.saturation !== undefined ? program.saturation : 100;
const frame_num = program.framenum !== undefined ? program.framenum : 10;

const doNothing = function(){};

const createFrames = function(dirPath, cb){
    let counter = 0;

    const filePaths = Array.apply(null, new Array(frame_num)).map(function(v, c){
        const filename = sprintf("%03d.gif", c);
        const filepath = path.join(dirPath, filename);
        return filepath;
    });

    const maybeFinished = function(){
        if(counter < frame_num){
            return;
        }
        cb(filePaths);
    };

    filePaths.forEach(function(outputPath, c){
        let imArgs = [input];
        if(!program.plain){
            imArgs = imArgs.concat(['-modulate',
                                    ['100', saturation, Math.floor(c * 360 / frame_num)].join(',')]);
        }
        if(program.colors !== undefined){
            imArgs = imArgs.concat(['-colors', program.colors]);
        }
        if(program.guruguru !== undefined){
            imArgs = imArgs.concat(['-clone', '0', '-distort', 'SRT',  Math.floor(c * 360 / frame_num)]);
        }
        imArgs.push(outputPath);
        im.convert(imArgs, function(err, stdout){
            if(err){
                console.log(stdout.trim());
                console.error(err);
                return;
            }
            counter++;
           maybeFinished();
        });
    });
};

const onAllocatedTempDirectory = function(err, dirPath) {
    if (err) {
        console.error(err);
        return;
    }
    createFrames(dirPath, function(filePaths){
        let imArgs = ['-dispose', 'Background',
                     '-delay', delay,
                     '-loop', '0'].concat(filePaths);
        imArgs.push(output)
        im.convert(imArgs, function(err, stdout){
            if(err){
                console.error(err);
                return;
            }
        });
    });
};

module.exports = function(){
    if(input === undefined){
        console.error('input file is required');
        return;
    }
    // file exists?
    fs.open(input, 'r', function(err, fd){
        if(err){
            console.error(err);
            return;
        }
        // create temp working dir if file exists
        temp.mkdir(TEMP_DIRECTRY_PREFIX, onAllocatedTempDirectory);
        fs.close(fd);
    });
};
<commit_msg>add impl reverse func<commit_after>"use strict";

const DEFAULT_DELAY_TIME = 5;
const TEMP_DIRECTRY_PREFIX = 'kirakira';
const temp = require('temp').track();
const fs   = require('fs');
const util  = require('util');
const sprintf = require('sprintf').sprintf
const path = require('path');
const im = require('imagemagick');
const returnTrue = function(){return true};

let program = require('commander');
program.version('0.0.1');
program.usage('-i <input file> [options]');
program.option('-i, --input <path>', 'input file');
program.option('-o, --output [path]', 'output path');
program.option('-s, --saturation [percent value]', 'saturation value');
program.option('-p, --plain', 'Do NOT Kirakira effect', returnTrue, 0);
program.option('--colors [value]', 'preferred number of colors in the image', parseInt);
program.option('--delay [time]', 'delay time', parseInt);
program.option('--framenum [integer]', 'frame number', parseInt);
program.option('--guruguru', 'enable guruguru effect', returnTrue, 0);
program.option('--reverse', 'Invert the effect time', returnTrue, 0);
program.parse(process.argv);
const input = program.input;
const output = program.output !== undefined ? program.output : "out.gif";
const delay = program.delay !== undefined ? program.delay : DEFAULT_DELAY_TIME;
const saturation = program.saturation !== undefined ? program.saturation : 100;
const frame_num = program.framenum !== undefined ? program.framenum : 10;

const doNothing = function(){};

const createFrames = function(dirPath, cb){
    let counter = 0;

    const filePaths = Array.apply(null, new Array(frame_num)).map(function(v, c){
        const filename = sprintf("%03d.gif", c);
        const filepath = path.join(dirPath, filename);
        return filepath;
    });

    const maybeFinished = function(){
        if(counter < frame_num){
            return;
        }
        cb(filePaths);
    };

    filePaths.forEach(function(outputPath, c){
        let imArgs = [input];
        const rotatenum = (program.reverse?-1:1) * Math.floor(c * 360 / frame_num);
        if(!program.plain){
            imArgs = imArgs.concat(['-modulate',
                                    ['100', saturation, rotatenum].join(',')]);
        }
        if(program.colors !== undefined){
            imArgs = imArgs.concat(['-colors', program.colors]);
        }
        if(program.guruguru !== undefined){
            imArgs = imArgs.concat(['-clone', '0', '-distort', 'SRT', rotatenum]);
        }
        imArgs.push(outputPath);
        im.convert(imArgs, function(err, stdout){
            if(err){
                console.log(stdout.trim());
                console.error(err);
                return;
            }
            counter++;
           maybeFinished();
        });
    });
};

const onAllocatedTempDirectory = function(err, dirPath) {
    if (err) {
        console.error(err);
        return;
    }
    createFrames(dirPath, function(filePaths){
        let imArgs = ['-dispose', 'Background',
                     '-delay', delay,
                     '-loop', '0'].concat(filePaths);
        imArgs.push(output)
        im.convert(imArgs, function(err, stdout){
            if(err){
                console.error(err);
                return;
            }
        });
    });
};

module.exports = function(){
    if(input === undefined){
        console.error('input file is required');
        return;
    }
    // file exists?
    fs.open(input, 'r', function(err, fd){
        if(err){
            console.error(err);
            return;
        }
        // create temp working dir if file exists
        temp.mkdir(TEMP_DIRECTRY_PREFIX, onAllocatedTempDirectory);
        fs.close(fd);
    });
};
<|endoftext|>


<commit_before>const path = require('path')

const express = require('express')
const bodyParser = require('body-parser')
const _ = require('lodash')

const catalogue = require("./catalogue.json")

const app = express()

var public_path = path.join(__dirname, 'public');

// Parse incoming json
app.use(bodyParser.json())
app.set('json spaces', 2);

// Serve static files from public dir
app.use('/public', express.static(public_path))

app.post("/api/purchase", function(req, res){
  var order = _.reduce(req.body, (order,item,line)=>{
    console.log(catalogue[item.id].price, item.count);
    order.count += item.count;
    order.total += (item.count * catalogue[item.id].price);
    return order;
  }, {
    status: "OK",
    count: 0,
    total: 0,
  })
  res.json(order)
})

app.get("/api/catalogue", function(req, res){
  res.json(catalogue)
})

// default is to render home page
app.get('/', function (req, res) {
  res.sendFile(path.join(public_path, 'index.html'));
})

app.listen(3000, function () {
  console.log('Example app listening on port 3000!')
})
<commit_msg>Better order logging message<commit_after>const path = require('path')

const express = require('express')
const bodyParser = require('body-parser')
const _ = require('lodash')

const catalogue = require("./catalogue.json")

const app = express()

var public_path = path.join(__dirname, 'public');

// Parse incoming json
app.use(bodyParser.json())
app.set('json spaces', 2);

// Serve static files from public dir
app.use('/public', express.static(public_path))

app.post("/api/purchase", function(req, res){
  var order = _.reduce(req.body, (order,item,line)=>{
    order.count += item.count;
    order.total += (item.count * catalogue[item.id].price);
    console.log("Order made: ", order);
    return order;
  }, {
    status: "OK",
    count: 0,
    total: 0,
  })
  res.json(order)
})

app.get("/api/catalogue", function(req, res){
  res.json(catalogue)
})

// default is to render home page
app.get('/', function (req, res) {
  res.sendFile(path.join(public_path, 'index.html'));
})

app.listen(3000, function () {
  console.log('Example app listening on port 3000!')
})
<|endoftext|>


<commit_before>const {app, Menu, Tray} = require('electron')
const path = require('path')
const notify = require('electron-main-notification')
const ping = require('ping')

let tray = null
let lastSeenState = null

//
// config
//

const iconPaths = {
  icon1: path.join(__dirname, 'arrows.png'),
  icon2: path.join(__dirname, 'arrows2.png')
}

const intervalDuration = 1000
const domainToPing = 'google.com'

//
// UI Interaction Code
//

const silentNotify = function (message) {
  notify(message, {
    silent: true
  })
}

const maybeNotify = function (lastResponseIsAlive) {
  if (lastResponseIsAlive !== lastSeenState) {
    if (lastResponseIsAlive === true) {
      silentNotify('Wifi back on')
    } else if (lastResponseIsAlive === false) {
      silentNotify('Wifi down')
    }
    lastSeenState = lastResponseIsAlive
  }
}

const maybeChangeIcon = function (lastResponseIsAlive) {
  if (lastResponseIsAlive) {
    tray.setImage(iconPaths.icon1)
  } else {
    tray.setImage(iconPaths.icon2)
  }
}

//
// ping code
//

const doThePing = function () {
  ping.promise.probe(domainToPing).then(onRecievePing)
}

const onRecievePing = function (pingResponse) {
  const lastResponseIsAlive = pingResponse.alive
  maybeNotify(lastResponseIsAlive)
  maybeChangeIcon(lastResponseIsAlive)
}

const startToPing = function () {
  setInterval(doThePing, intervalDuration)
}

//
// tray and menu
//

const setUpTrayAndContextMenu = function () {
  tray = new Tray(iconPaths.icon1)
  const contextMenu = Menu.buildFromTemplate([
    { role: 'quit' }
  ])
  tray.setToolTip('Electron Ping')
  tray.setContextMenu(contextMenu)
}

//
// app ready, "main"
//

app.on('ready', () => {
  setUpTrayAndContextMenu()
  startToPing()
})
<commit_msg>reorder method for clarity<commit_after>const {app, Menu, Tray} = require('electron')
const path = require('path')
const notify = require('electron-main-notification')
const ping = require('ping')

let tray = null
let lastSeenState = null

//
// config
//

const iconPaths = {
  icon1: path.join(__dirname, 'arrows.png'),
  icon2: path.join(__dirname, 'arrows2.png')
}

const intervalDuration = 1000
const domainToPing = 'google.com'

//
// UI Interaction Code
//

const silentNotify = function (message) {
  notify(message, {
    silent: true
  })
}

const maybeNotify = function (lastResponseIsAlive) {
  if (lastResponseIsAlive !== lastSeenState) {
    if (lastResponseIsAlive === true) {
      silentNotify('Wifi back on')
    } else if (lastResponseIsAlive === false) {
      silentNotify('Wifi down')
    }
    lastSeenState = lastResponseIsAlive
  }
}

const maybeChangeIcon = function (lastResponseIsAlive) {
  if (lastResponseIsAlive) {
    tray.setImage(iconPaths.icon1)
  } else {
    tray.setImage(iconPaths.icon2)
  }
}

//
// ping code
//

const onRecievePing = function (pingResponse) {
  const lastResponseIsAlive = pingResponse.alive
  maybeNotify(lastResponseIsAlive)
  maybeChangeIcon(lastResponseIsAlive)
}

const doThePing = function () {
  ping.promise.probe(domainToPing).then(onRecievePing)
}

const startToPing = function () {
  setInterval(doThePing, intervalDuration)
}

//
// tray and menu
//

const setUpTrayAndContextMenu = function () {
  tray = new Tray(iconPaths.icon1)
  const contextMenu = Menu.buildFromTemplate([
    { role: 'quit' }
  ])
  tray.setToolTip('Electron Ping')
  tray.setContextMenu(contextMenu)
}

//
// app ready, "main"
//

app.on('ready', () => {
  setUpTrayAndContextMenu()
  startToPing()
})
<|endoftext|>


<commit_before>var _ = require('./underscore');
var utility = require('./utility');

var b = 11,
    c = 12,
    d = 13,
    e = 14;

var data = [
    [0, 0, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0],
    [0, 0, 1, 0, 0, 1, 1, 0, 1, 0, 1, 1],
    [0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 1, 0],
    [0, 1, 0, 0, 1, 0, 0, 1, 1, 1, 1, 0],
    [0, 1, 0, 0, 1, 0, 0, 1, 1, 0, 0, 1],
    [0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 0, 1],
    [1, 0, 0, 0, 1, 0, 1, 1, 1, 1, 0 ,1],
    [1, 0, 0, 0, 1, 0, 1, 1, 1, 0, 1, 1],
    [1, 0, 0, 0, 1, 1, 0 ,1, 1, 0, 1, 1],
    [1, 1, 0 ,1, 1, 0, 0, 0, 1, 0, 0, 0],
    [1, 1, 0 ,1, 1, 0, 0, 0, 1, 1, 0, 0],
    [1, 1, 0 ,1, 1, 1, 0, 0, 1, 0, 0, 0]
];

var c;

var category = function(v) {
    var w = v[0] * 8 + v[1] * 4 + v[2] * 2 + v[3],
        y = v[4] * 8 + v[5] * 4 + v[6] * 2 + v[7],
        z = v[8] * 8 + v[9] * 4 + v[10] * 2 + v[11];

    var yc = (y === 6 || y === 11),
        zc = (z === 6 || z === 11);

    if (yc === true && zc === true) {
        c[0] ++;
    } else if (yc === false && zc === false) {
        c[2] ++;
    } else {
        c[1] ++;
    }
};

var a;
var sub = function(data, x) {
    var i, j;
    if (x < 0) {
        var v = Array.apply(null, new Array(12)).map(Number.prototype.valueOf,0);
        for (i = 0; i < data.length; i++) {
            if (a[i] === 1) {
                for (j = 0; j < 12; j++) {
                    v[j] = utility.xor(v[j], data[i][j]);
                }
            }
        }
        category(v);
    } else {
        for (i = 0; i < 2; i++) {
            a[x] = i;
            sub(data, x-1);
        }
    }
};

var output = function(d, c) {
    var dd = [];
    var i, j;
    for (i = 0; i < d.length; i++) {
        dd[i] = [];
        dd[i][0] = utility.hex(d[i][0] * 8 + d[i][1] * 4 + d[i][2] * 2 + d[i][3]);
        dd[i][1] = utility.hex(d[i][4] * 8 + d[i][5] * 4 + d[i][6] * 2 + d[i][7]);
        dd[i][2] = utility.hex(d[i][8] * 8 + d[i][9] * 4 + d[i][10] * 2 + d[i][11]);
    }
    for (i = 0; i < d.length; i++) {
        process.stdout.write('[');
        for (j = 0; j < 3 ; j++) {
            process.stdout.write(dd[i][j]);
            if (j < 2) process.stdout.write(',');
        }
        process.stdout.write(']');
    }
    process.stdout.write(' - (' + c[0] + ',' + c[1] + ',' + c[2] + ')');
    process.stdout.write('\n');
};

var perm = utility.permutation(data, 2);
var i;
for (i = 0; i < perm.length; i++) {
    var d = perm[i];
    d = _.difference(data, d);
    a = [];
    c = [0, 0, 0];
    sub(d, d.length - 1);
    output(d, c);
}<commit_msg>[bug] not consider the value should contain in the candidate set<commit_after>var _ = require('./underscore');
var utility = require('./utility');

var b = 11,
    c = 12,
    d = 13,
    e = 14;

var data = [
    [0, 0, 1, 0, 0, 1, 1, 0, 0, 1, 1, 0],
    [0, 0, 1, 0, 0, 1, 1, 0, 1, 0, 1, 1],
    [0, 0, 1, 0, 1, 0, 1, 1, 0, 1, 1, 0],
    [0, 1, 0, 0, 1, 0, 0, 1, 1, 1, 1, 0],
    [0, 1, 0, 0, 1, 0, 0, 1, 1, 0, 0, 1],
    [0, 1, 0, 0, 1, 1, 1, 0, 1, 0, 0, 1],
    [1, 0, 0, 0, 1, 0, 1, 1, 1, 1, 0 ,1],
    [1, 0, 0, 0, 1, 0, 1, 1, 1, 0, 1, 1],
    [1, 0, 0, 0, 1, 1, 0 ,1, 1, 0, 1, 1],
    [1, 1, 0 ,1, 1, 0, 0, 0, 1, 0, 0, 0],
    [1, 1, 0 ,1, 1, 0, 0, 0, 1, 1, 0, 0],
    [1, 1, 0 ,1, 1, 1, 0, 0, 1, 0, 0, 0]
];

var c;
var used;

var category = function(v) {
    var w = v[0] * 8 + v[1] * 4 + v[2] * 2 + v[3],
        y = v[4] * 8 + v[5] * 4 + v[6] * 2 + v[7],
        z = v[8] * 8 + v[9] * 4 + v[10] * 2 + v[11];
    var vv = w.toString() + ',' + y.toString() + ',' + z.toString();
    if (_.indexOf(used, vv) !== -1) {
        return;
    }
    used.push(vv);

    var yc, zc;
    var v1, v2;

    switch (w) {
        case 2:
            v1 = 6; v2 = 11;
            if (y === 0 || y === 1 || y === 7 || y === 10 || y === 12 || y === 13) return;
            if (z === 0 || z === 1 || z === 7 || z === 10 || z === 12 || z === 13) return;
            break;
        case 4:
            v1 = 9; v2 = 14;
            if (y === 0 || y === 1 || y === 6 || y === 7 || y === 8 || y === 15) return;
            if (z === 0 || z === 1 || z === 6 || z === 7 || z === 8 || z === 15) return;
            break;
        case 6:
            v1 = 1; v2 = 2;
            if (y === 3 || y === 4 || y === 5 || y === 6 || y === 7 || y === 0) return;
            if (z === 3 || z === 4 || z === 5 || z === 6 || z === 7 || z === 0) return;
            break;
        case 8:
            v1 = 11; v2 = 13;
            if (y === 0 || y === 2 || y === 4 || y === 6 || y === 9 || y === 15) return;
            if (z === 0 || z === 2 || z === 4 || z === 6 || z === 9 || z === 15) return;
            break;
        case 13:
            v1 = 8; v2 = 12;
            if (y === 0 || y === 1 || y === 4 || y === 5 || y === 9 || y === 13) return;
            if (z === 0 || z === 1 || z === 4 || z === 5 || z === 9 || z === 13) return;
            break;
        case 14:
            v1 = 4; v2 = 12;
            if (y === 0 || y === 2 || y === 6 || y === 8 || y === 10 || y === 14) return;
            if (z === 0 || z === 2 || z === 6 || z === 8 || z === 10 || z === 14) return;
            break;
        default:
            return;
    }

    yc = (y === v1 || y === v2);
    zc = (z === v1 || z === v2);

    if (yc === true && zc === true) {
        c[0] ++;
    } else if (yc === false && zc === false) {
        c[2] ++;
    } else {
        c[1] ++;
    }
};

var a;
var sub = function(data, x) {
    var i, j;
    if (x < 0) {
        var v = Array.apply(null, new Array(12)).map(Number.prototype.valueOf,0);
        for (i = 0; i < data.length; i++) {
            if (a[i] === 1) {
                for (j = 0; j < 12; j++) {
                    v[j] = utility.xor(v[j], data[i][j]);
                }
            }
        }
        category(v);
    } else {
        for (i = 0; i < 2; i++) {
            a[x] = i;
            sub(data, x-1);
        }
    }
};

var output = function(d, c) {
    var dd = [];
    var i, j;
    for (i = 0; i < d.length; i++) {
        dd[i] = [];
        dd[i][0] = utility.hex(d[i][0] * 8 + d[i][1] * 4 + d[i][2] * 2 + d[i][3]);
        dd[i][1] = utility.hex(d[i][4] * 8 + d[i][5] * 4 + d[i][6] * 2 + d[i][7]);
        dd[i][2] = utility.hex(d[i][8] * 8 + d[i][9] * 4 + d[i][10] * 2 + d[i][11]);
    }
    for (i = 0; i < d.length; i++) {
        process.stdout.write('[');
        for (j = 0; j < 3 ; j++) {
            process.stdout.write(dd[i][j]);
            if (j < 2) process.stdout.write(',');
        }
        process.stdout.write(']');
    }
    process.stdout.write(' - (' + c[0] + ',' + c[1] + ',' + c[2] + ')');
    process.stdout.write(' - ' + (c[0]+c[1]+c[2]));
    process.stdout.write('\n');
};

var perm = utility.permutation(data, 2);
var i;
for (i = 0; i < perm.length; i++) {
    var d = perm[i];
    d = _.difference(data, d);
    a = [];
    c = [0, 0, 0];
    used = [];
    sub(d, d.length - 1);
    output(d, c);
}<|endoftext|>