<commit_before>var KEY_ENTER = 13;
var KEY_ESCAPE = 27;

var QuickLinksCard = {
    name: 'QuickLinksCard',
    dom_target: undefined,

    run_control: function(ev) {
        var target = $(this);
        var type = target.attr('data-linktype');

        if ("edit" == type) {
            return QuickLinksCard.display_edit_field(target);
        }

        QuickLinksCard._add_link({
            type: type,
            id: target.attr('data-linkid')
        });

        return false;
    },
    display_edit_field: function(target) {
        var link_id = target.attr('data-linkid');
        var id = "#custom-link-"+link_id;
        var custom_link = $(id);

        $("#custom-link-edit-id").val(link_id);
        $("#custom-link-edit-url").val(custom_link.attr('href'));
        $("#custom-link-edit-label").val(custom_link.text());

        var target_pos = target.closest('li').position();
        $("#custom-link-edit").css({left: target_pos.left, top: target_pos.top + 20});
        $("#custom-link-edit").show();

        $("#custom-link-edit-url").focus();
    },
    custom_add: function(ev) {
        if (KEY_ENTER == ev.which) {
            QuickLinksCard._save_new();
        }
    },
    _save_new: function() {
        $("#quicklink_saving").show();
        QuickLinksCard._add_link({
            type: "custom",
            url: $("#myuw-custom-qlink").val().trim()
        });
    },
    custom_edit: function(ev) {
        if (KEY_ENTER == ev.which) {
            QuickLinksCard._save_edit();
        }
    },
    _save_edit: function() {
        var label = $("#custom-link-edit-label").val().trim();
        if ("" == label) {
            $("#edit-label-required").show();
        }
        else {
            $("#edit-label-required").hide();
        }

        var csrf_token = $("input[name=csrfmiddlewaretoken]")[0].value;
        var values = {
            type: "custom-edit",
            url: $("#custom-link-edit-url").val(),
            label: label,
            id: $("#custom-link-edit-id").val()
        };

        $.ajax({
            url: "/api/v1/link",
            dataType: "JSON",
            async: true,
            type: "POST",
            headers: {
                 "X-CSRFToken": csrf_token
            },
            data: JSON.stringify(values),
            complete: QuickLinksCard.redraw
        });

        return false;
    },
    handle_escape: function(ev) {
        if (KEY_ESCAPE == ev.which) {
            QuickLinksCard.hide_edit_panel();
        }
    },
    hide_edit_panel: function() {
        $("#custom-link-edit").hide();
    },
    _add_link: function(values) {
        $("#error_saving").hide();
        var csrf_token = $("input[name=csrfmiddlewaretoken]")[0].value;
        $.ajax({
            url: "/api/v1/link",
            dataType: "JSON",
            async: true,
            type: "POST",
            headers: {
                 "X-CSRFToken": csrf_token
            },
            data: JSON.stringify(values),
            complete: QuickLinksCard.redraw
        });
    },

    redraw: function(response) {
        $("#quicklink_saving").hide();
        if (response.status == 200) {
            window.quicklink_data = response.responseJSON;
            $("#myuw-custom-qlink").val("");
            QuickLinksCard.render();
        }
        else {
            $("#error_saving").show();
        }
    },

    render_init: function() {
        QuickLinksCard.dom_target = $('#QuickLinksCard');
        QuickLinksCard.render();
    },

    render: function() {
        var source = $("#quicklinks").html();
        var template = Handlebars.compile(source);

        QuickLinksCard.dom_target.html(template({
            'links': window.quicklink_data
        }));
    }
};

$("body").on('click', '.control-link', QuickLinksCard.run_control);
$("body").on('click', '#close-custom-link-edit', QuickLinksCard.hide_edit_panel);
$("body").on('click', '#quicklinks-save-edits', QuickLinksCard._save_edit);
$("body").on('click', '#quicklinks-save-new', QuickLinksCard._save_new);
$("body").on('keydown', '#myuw-custom-qlink', QuickLinksCard.custom_add);
$("body").on('keydown', '#custom-link-edit', QuickLinksCard.custom_edit);
$("body").on('keydown', QuickLinksCard.handle_escape);
<commit_msg>jshint<commit_after>var KEY_ENTER = 13;
var KEY_ESCAPE = 27;

var QuickLinksCard = {
    name: 'QuickLinksCard',
    dom_target: undefined,

    run_control: function(ev) {
        var target = $(this);
        var type = target.attr('data-linktype');

        if ("edit" == type) {
            return QuickLinksCard.display_edit_field(target);
        }

        QuickLinksCard._add_link({
            type: type,
            id: target.attr('data-linkid')
        });

        return false;
    },
    display_edit_field: function(target) {
        var link_id = target.attr('data-linkid');
        var id = "#custom-link-"+link_id;
        var custom_link = $(id);

        $("#custom-link-edit-id").val(link_id);
        $("#custom-link-edit-url").val(custom_link.attr('href'));
        $("#custom-link-edit-label").val(custom_link.text());

        var target_pos = target.closest('li').position();
        $("#custom-link-edit").css({left: target_pos.left, top: target_pos.top + 20});
        $("#custom-link-edit").show();

        $("#custom-link-edit-url").focus();
    },
    custom_add: function(ev) {
        if (KEY_ENTER == ev.which) {
            QuickLinksCard._save_new();
        }
    },
    _save_new: function() {
        $("#quicklink_saving").show();
        QuickLinksCard._add_link({
            type: "custom",
            url: $("#myuw-custom-qlink").val().trim()
        });
    },
    custom_edit: function(ev) {
        if (KEY_ENTER == ev.which) {
            QuickLinksCard._save_edit();
        }
    },
    _save_edit: function() {
        var label = $("#custom-link-edit-label").val().trim();
        if ("" === label) {
            $("#edit-label-required").show();
        }
        else {
            $("#edit-label-required").hide();
        }

        var csrf_token = $("input[name=csrfmiddlewaretoken]")[0].value;
        var values = {
            type: "custom-edit",
            url: $("#custom-link-edit-url").val(),
            label: label,
            id: $("#custom-link-edit-id").val()
        };

        $.ajax({
            url: "/api/v1/link",
            dataType: "JSON",
            async: true,
            type: "POST",
            headers: {
                 "X-CSRFToken": csrf_token
            },
            data: JSON.stringify(values),
            complete: QuickLinksCard.redraw
        });

        return false;
    },
    handle_escape: function(ev) {
        if (KEY_ESCAPE == ev.which) {
            QuickLinksCard.hide_edit_panel();
        }
    },
    hide_edit_panel: function() {
        $("#custom-link-edit").hide();
    },
    _add_link: function(values) {
        $("#error_saving").hide();
        var csrf_token = $("input[name=csrfmiddlewaretoken]")[0].value;
        $.ajax({
            url: "/api/v1/link",
            dataType: "JSON",
            async: true,
            type: "POST",
            headers: {
                 "X-CSRFToken": csrf_token
            },
            data: JSON.stringify(values),
            complete: QuickLinksCard.redraw
        });
    },

    redraw: function(response) {
        $("#quicklink_saving").hide();
        if (response.status == 200) {
            window.quicklink_data = response.responseJSON;
            $("#myuw-custom-qlink").val("");
            QuickLinksCard.render();
        }
        else {
            $("#error_saving").show();
        }
    },

    render_init: function() {
        QuickLinksCard.dom_target = $('#QuickLinksCard');
        QuickLinksCard.render();
    },

    render: function() {
        var source = $("#quicklinks").html();
        var template = Handlebars.compile(source);

        QuickLinksCard.dom_target.html(template({
            'links': window.quicklink_data
        }));
    }
};

$("body").on('click', '.control-link', QuickLinksCard.run_control);
$("body").on('click', '#close-custom-link-edit', QuickLinksCard.hide_edit_panel);
$("body").on('click', '#quicklinks-save-edits', QuickLinksCard._save_edit);
$("body").on('click', '#quicklinks-save-new', QuickLinksCard._save_new);
$("body").on('keydown', '#myuw-custom-qlink', QuickLinksCard.custom_add);
$("body").on('keydown', '#custom-link-edit', QuickLinksCard.custom_edit);
$("body").on('keydown', QuickLinksCard.handle_escape);
<|endoftext|>


<commit_before>import React from 'react';

export default function SvgAddLocation(props) {
  return (
    <svg
      width="1em"
      height="1em"
      viewBox="0 0 24 24"
      fill="currentColor"
      xmlns="http://www.w3.org/2000/svg"
      {...props}
    >
      <path
        d="M18.4737 2.5V4.95455H21V6.59091H18.4737V9.04545H16.7895V6.59091H14.2632V4.95455H16.7895V2.5H18.4737ZM11.7368 12.3182C12.6632 12.3182 13.4211 11.5818 13.4211 10.6818C13.4211 9.78182 12.6632 9.04545 11.7368 9.04545C10.8105 9.04545 10.0526 9.78182 10.0526 10.6818C10.0526 11.5818 10.8105 12.3182 11.7368 12.3182ZM13.4211 4.34091V7.40909H15.9474V9.86364H18.4063C18.4484 10.1827 18.4737 10.51 18.4737 10.8455C18.4737 13.5618 16.2253 16.7773 11.7368 20.5C7.24842 16.7773 5 13.5618 5 10.8455C5 6.77091 8.2 4.13636 11.7368 4.13636C12.3095 4.13636 12.8737 4.20182 13.4211 4.34091Z"
        fill="currentColor" />
    </svg>
  );
}
<commit_msg>fix: lint issue<commit_after>import React from 'react';

export default function SvgAddLocation(props) {
  return (
    <svg
      width="1em"
      height="1em"
      viewBox="0 0 24 24"
      fill="currentColor"
      xmlns="http://www.w3.org/2000/svg"
      {...props}
    >
      <path
        d="M18.4737 2.5V4.95455H21V6.59091H18.4737V9.04545H16.7895V6.59091H14.2632V4.95455H16.7895V2.5H18.4737ZM11.7368 12.3182C12.6632 12.3182 13.4211 11.5818 13.4211 10.6818C13.4211 9.78182 12.6632 9.04545 11.7368 9.04545C10.8105 9.04545 10.0526 9.78182 10.0526 10.6818C10.0526 11.5818 10.8105 12.3182 11.7368 12.3182ZM13.4211 4.34091V7.40909H15.9474V9.86364H18.4063C18.4484 10.1827 18.4737 10.51 18.4737 10.8455C18.4737 13.5618 16.2253 16.7773 11.7368 20.5C7.24842 16.7773 5 13.5618 5 10.8455C5 6.77091 8.2 4.13636 11.7368 4.13636C12.3095 4.13636 12.8737 4.20182 13.4211 4.34091Z"
        fill="currentColor"
      />
    </svg>
  );
}
<|endoftext|>


<commit_before>var KEY_ENTER = 13;
var KEY_ESCAPE = 27;

var QuickLinksCard = {
    name: 'QuickLinksCard',
    dom_target: undefined,
    opened_panels: {},
    hidden_panel: undefined,

    render_init: function() {
        WSData.fetch_link_data(QuickLinksCard.render_upon_data,
                               QuickLinksCard.render_error);
    },

    render_upon_data: function () {
        if (!WSData.link_data()) {
            return;
        }
        QuickLinksCard.render()
    },

    render: function() {
        var quicklink_data = WSData.link_data()
        QuickLinksCard.dom_target.html(
            QuickLinksCard.get_html(quicklink_data));
        QuickLinksCard.add_events();
    },

    render_error: function (status) {
        QuickLinksCard.get_html({has_error: true});
    },

    get_html: function(data) {
        var source = $("#quicklinks").html();
        var template = Handlebars.compile(source);
        return template({
            'links': data,
            'disable_actions': window.user.is_override_and_disable_actions
        });
    },

    run_control: function(ev) {
        var target = $(this);
        var type = target.attr('data-linktype');

        if ("edit" === type) {
            QuickLinksCard.display_edit_field(target);
            return false;
        }
        if ("remove" === type) {
            QuickLinksCard.hide_edit_panel();
        }

        QuickLinksCard._add_link({
            type: type,
            id: target.attr('data-linkid')
        });

        return false;
    },
    display_edit_field: function(target) {
        QuickLinksCard.display_edit_links();
        QuickLinksCard.hidden_panel = target.parent();
        QuickLinksCard.hidden_panel.css('display', 'none');
        var link_id = target.attr('data-linkid');
        var id = "#custom-link-"+link_id;
        var custom_link = $(id);

        $("#edit-label-required").hide();
        $("#edit-url-required").hide();
        $("#custom-link-edit-id").val(link_id);
        $("#custom-link-edit-url").val(custom_link.attr('href'));
        $("#custom-link-edit-label").val(custom_link.text());

        var target_pos = target.closest('li').position();
        $("#custom-link-edit").css({left: 0, top: target_pos.top + 20});
        $("#custom-link-edit").show();

        $("#custom-link-edit-control-"+link_id).attr({
            "aria-expanded" : "true"
        });

        $("#custom-link-edit-url").focus();
    },
    custom_add: function(ev) {
        if (KEY_ENTER === ev.which) {
            QuickLinksCard._save_new();
        }
    },
    _save_new: function() {
        $("#quicklink_saving").show();
        QuickLinksCard._add_link({
            type: "custom",
            url: $("#myuw-custom-qlink").val().trim(),
            label: $("#myuw-custom-qlink-label").val().trim()
        });
    },
    custom_edit: function(ev) {
        if (KEY_ENTER === ev.which) {
            QuickLinksCard._save_edit();
        }
    },
    _post_custom_edit_save: function(response) {
        if (response.status === 200) {
            QuickLinksCard.redraw(response);
            QuickLinksCard.hide_edit_panel();
        }
        QuickLinksCard.hide_custom_quicklinks_panel();
    },
    _save_edit: function() {
        function validate(field) {
            var value = $("#custom-link-edit-"+field).val().trim();
            if ("" === value) {
                $("#edit-"+field+"-required").show();
            }
            else {
                $("#edit-"+field+"-required").hide();
            }
        }
        validate("url");

        var label = $("#custom-link-edit-label").val().trim();
        if(label === ""){
            label = $("#custom-link-edit-url").val();
        }

        var csrf_token = $("input[name=csrfmiddlewaretoken]")[0].value;
        var values = {
            type: "custom-edit",
            url: $("#custom-link-edit-url").val(),
            label: label,
            id: $("#custom-link-edit-id").val()
        };

        $.ajax({
            url: "/api/v1/link",
            dataType: "JSON",
            async: true,
            type: "POST",
            headers: {
                 "X-CSRFToken": csrf_token
            },
            data: JSON.stringify(values),
            complete: QuickLinksCard._post_custom_edit_save
        });

        return false;
    },
    handle_escape: function(ev) {
        if (KEY_ESCAPE === ev.which) {
            QuickLinksCard.hide_edit_panel();
        }
    },
    display_edit_links: function() {
        if (QuickLinksCard.hidden_panel) {
            QuickLinksCard.hidden_panel.css('display', '');
        }
    },
    hide_edit_panel: function() {
        $("#custom-link-edit").hide();

        $(".link-controls .edit-link[aria-expanded=true]").attr({
            "aria-expanded" : "false"
        });

        QuickLinksCard.display_edit_links();
        return false;
    },
    hide_custom_quicklinks_panel: function() {
        $("#custom_qlinks").collapse({toggle: false});
        $("#custom_qlinks").collapse("hide");
    },
    _add_link: function(values) {
        $("#error_saving").hide();
        var csrf_token = $("input[name=csrfmiddlewaretoken]")[0].value;
        $.ajax({
            url: "/api/v1/link",
            dataType: "JSON",
            async: true,
            type: "POST",
            headers: {
                 "X-CSRFToken": csrf_token
            },
            data: JSON.stringify(values),
            complete: QuickLinksCard.redraw
        });
    },

    redraw: function(response) {
        $("#quicklink_saving").hide();
        if (response.status === 200) {
            quicklink_data = response.responseJSON;
            var html = $(QuickLinksCard.get_html(quicklink_data));
            var replace_ids = ['#popular_qlinks', '.myuw-qlinks-active', '.myuw-qlinks-recent',
                               '#custom-link-edit', '#custom_qlinks'];
            var i = 0;
            for (i = 0; i < replace_ids.length; i++) {
                var id = replace_ids[i];
                $(id).html(html.find(id).html());
            }
        }
        else {
            $("#error_saving").show();
        }
    },

    collapse_event: function(caller) {
        // Closing a collapse that hasn't been opened at least once results in
        // a regex error in jquery code...
        if ("popular" === caller) {
            if (QuickLinksCard.opened_panels.custom) {
                $("#custom_qlinks").collapse("hide");
            }
        }
        if ("custom" === caller) {
            if (QuickLinksCard.opened_panels.popular) {
                $("#popular_qlinks").collapse("hide");
            }
        }
        QuickLinksCard.opened_panels[caller] = true;
    },
    add_events: function() {
        if(window.user.is_override_and_disable_actions) {
            return;
        }
        if (QuickLinksCard.events_added) {
            return;
        }
        QuickLinksCard.events_added = true;

        $("#popular_qlinks").on("show.bs.collapse", function() { QuickLinksCard.collapse_event('popular'); });
        $("#custom_qlinks").on("show.bs.collapse", function() { QuickLinksCard.collapse_event('custom'); });
        $("body").on('click', '.control-link', QuickLinksCard.run_control);
        $("body").on('click', '#close-custom-link-edit', QuickLinksCard.hide_edit_panel);
        $("body").on('click', '#quicklinks-save-edits', QuickLinksCard._save_edit);
        $("body").on('click', '#quicklinks-save-new', QuickLinksCard._save_new);
        $("body").on('keydown', '#myuw-custom-qlink', QuickLinksCard.custom_add);
        $("body").on('keydown', '#custom-link-edit', QuickLinksCard.custom_edit);
        $("body").on('keydown', QuickLinksCard.handle_escape);
    }
};

/* node.js exports */
if (typeof exports === "undefined") {
    var exports = {};
}
exports.QuickLinksCard = QuickLinksCard;
<commit_msg>display in card error msg<commit_after>var KEY_ENTER = 13;
var KEY_ESCAPE = 27;

var QuickLinksCard = {
    name: 'QuickLinksCard',
    dom_target: undefined,
    opened_panels: {},
    hidden_panel: undefined,

    render_init: function() {
        WSData.fetch_link_data(QuickLinksCard.render_upon_data,
                               QuickLinksCard.render_error);
    },

    render_upon_data: function () {
        if (!WSData.link_data()) {
            return;
        }
        QuickLinksCard.render()
    },

    render: function() {
        var quicklink_data = WSData.link_data()
        QuickLinksCard.dom_target.html(
            QuickLinksCard.get_html(quicklink_data));
        QuickLinksCard.add_events();
    },

    render_error: function (status) {
        QuickLinksCard.dom_target.html(CardWithError.render("QuickLinks"));
    },

    get_html: function(data) {
        var source = $("#quicklinks").html();
        var template = Handlebars.compile(source);
        return template({
            'links': data,
            'disable_actions': window.user.is_override_and_disable_actions
        });
    },

    run_control: function(ev) {
        var target = $(this);
        var type = target.attr('data-linktype');

        if ("edit" === type) {
            QuickLinksCard.display_edit_field(target);
            return false;
        }
        if ("remove" === type) {
            QuickLinksCard.hide_edit_panel();
        }

        QuickLinksCard._add_link({
            type: type,
            id: target.attr('data-linkid')
        });

        return false;
    },
    display_edit_field: function(target) {
        QuickLinksCard.display_edit_links();
        QuickLinksCard.hidden_panel = target.parent();
        QuickLinksCard.hidden_panel.css('display', 'none');
        var link_id = target.attr('data-linkid');
        var id = "#custom-link-"+link_id;
        var custom_link = $(id);

        $("#edit-label-required").hide();
        $("#edit-url-required").hide();
        $("#custom-link-edit-id").val(link_id);
        $("#custom-link-edit-url").val(custom_link.attr('href'));
        $("#custom-link-edit-label").val(custom_link.text());

        var target_pos = target.closest('li').position();
        $("#custom-link-edit").css({left: 0, top: target_pos.top + 20});
        $("#custom-link-edit").show();

        $("#custom-link-edit-control-"+link_id).attr({
            "aria-expanded" : "true"
        });

        $("#custom-link-edit-url").focus();
    },
    custom_add: function(ev) {
        if (KEY_ENTER === ev.which) {
            QuickLinksCard._save_new();
        }
    },
    _save_new: function() {
        $("#quicklink_saving").show();
        QuickLinksCard._add_link({
            type: "custom",
            url: $("#myuw-custom-qlink").val().trim(),
            label: $("#myuw-custom-qlink-label").val().trim()
        });
    },
    custom_edit: function(ev) {
        if (KEY_ENTER === ev.which) {
            QuickLinksCard._save_edit();
        }
    },
    _post_custom_edit_save: function(response) {
        if (response.status === 200) {
            QuickLinksCard.redraw(response);
            QuickLinksCard.hide_edit_panel();
        }
        QuickLinksCard.hide_custom_quicklinks_panel();
    },
    _save_edit: function() {
        function validate(field) {
            var value = $("#custom-link-edit-"+field).val().trim();
            if ("" === value) {
                $("#edit-"+field+"-required").show();
            }
            else {
                $("#edit-"+field+"-required").hide();
            }
        }
        validate("url");

        var label = $("#custom-link-edit-label").val().trim();
        if(label === ""){
            label = $("#custom-link-edit-url").val();
        }

        var csrf_token = $("input[name=csrfmiddlewaretoken]")[0].value;
        var values = {
            type: "custom-edit",
            url: $("#custom-link-edit-url").val(),
            label: label,
            id: $("#custom-link-edit-id").val()
        };

        $.ajax({
            url: "/api/v1/link",
            dataType: "JSON",
            async: true,
            type: "POST",
            headers: {
                 "X-CSRFToken": csrf_token
            },
            data: JSON.stringify(values),
            complete: QuickLinksCard._post_custom_edit_save
        });

        return false;
    },
    handle_escape: function(ev) {
        if (KEY_ESCAPE === ev.which) {
            QuickLinksCard.hide_edit_panel();
        }
    },
    display_edit_links: function() {
        if (QuickLinksCard.hidden_panel) {
            QuickLinksCard.hidden_panel.css('display', '');
        }
    },
    hide_edit_panel: function() {
        $("#custom-link-edit").hide();

        $(".link-controls .edit-link[aria-expanded=true]").attr({
            "aria-expanded" : "false"
        });

        QuickLinksCard.display_edit_links();
        return false;
    },
    hide_custom_quicklinks_panel: function() {
        $("#custom_qlinks").collapse({toggle: false});
        $("#custom_qlinks").collapse("hide");
    },
    _add_link: function(values) {
        $("#error_saving").hide();
        var csrf_token = $("input[name=csrfmiddlewaretoken]")[0].value;
        $.ajax({
            url: "/api/v1/link",
            dataType: "JSON",
            async: true,
            type: "POST",
            headers: {
                 "X-CSRFToken": csrf_token
            },
            data: JSON.stringify(values),
            complete: QuickLinksCard.redraw
        });
    },

    redraw: function(response) {
        $("#quicklink_saving").hide();
        if (response.status === 200) {
            quicklink_data = response.responseJSON;
            var html = $(QuickLinksCard.get_html(quicklink_data));
            var replace_ids = ['#popular_qlinks', '.myuw-qlinks-active', '.myuw-qlinks-recent',
                               '#custom-link-edit', '#custom_qlinks'];
            var i = 0;
            for (i = 0; i < replace_ids.length; i++) {
                var id = replace_ids[i];
                $(id).html(html.find(id).html());
            }
        }
        else {
            $("#error_saving").show();
        }
    },

    collapse_event: function(caller) {
        // Closing a collapse that hasn't been opened at least once results in
        // a regex error in jquery code...
        if ("popular" === caller) {
            if (QuickLinksCard.opened_panels.custom) {
                $("#custom_qlinks").collapse("hide");
            }
        }
        if ("custom" === caller) {
            if (QuickLinksCard.opened_panels.popular) {
                $("#popular_qlinks").collapse("hide");
            }
        }
        QuickLinksCard.opened_panels[caller] = true;
    },
    add_events: function() {
        if(window.user.is_override_and_disable_actions) {
            return;
        }
        if (QuickLinksCard.events_added) {
            return;
        }
        QuickLinksCard.events_added = true;

        $("#popular_qlinks").on("show.bs.collapse", function() { QuickLinksCard.collapse_event('popular'); });
        $("#custom_qlinks").on("show.bs.collapse", function() { QuickLinksCard.collapse_event('custom'); });
        $("body").on('click', '.control-link', QuickLinksCard.run_control);
        $("body").on('click', '#close-custom-link-edit', QuickLinksCard.hide_edit_panel);
        $("body").on('click', '#quicklinks-save-edits', QuickLinksCard._save_edit);
        $("body").on('click', '#quicklinks-save-new', QuickLinksCard._save_new);
        $("body").on('keydown', '#myuw-custom-qlink', QuickLinksCard.custom_add);
        $("body").on('keydown', '#custom-link-edit', QuickLinksCard.custom_edit);
        $("body").on('keydown', QuickLinksCard.handle_escape);
    }
};

/* node.js exports */
if (typeof exports === "undefined") {
    var exports = {};
}
exports.QuickLinksCard = QuickLinksCard;
<|endoftext|>


<commit_before>/**
 * @license
 * Copyright 2015 Google Inc. All Rights Reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

MODEL({
  package: 'foam.demos.sevenguis',
  name: 'CircleDrawer',
  extendsModel: 'foam.ui.View',

  traits: [ 'foam.memento.MementoMgr' ],

  requires: [
    'foam.graphics.CView',
    'foam.graphics.Circle',
    'foam.ui.DetailView', // TODO: This shouldn't be required
    'foam.ui.md.PopupView'
  ],

  constants: {
    SELECTED_COLOR:   '#ddd',
    UNSELECTED_COLOR: 'white'
  },

  models: [
    {
      name: 'DiameterDialog',
      extendsModel: 'foam.ui.DetailView',

      templates: [
        function toHTML() {/*

          Adjust the diameter of the circle at ($$x{mode: 'read-only'}, $$y{mode: 'read-only'}).

          $$r{model_: 'foam.ui.RangeView', maxValue: 200, onKeyMode: true}
        */}
      ]
    }
  ],

  properties: [
    {
      name: 'selected',
      postSet: function(o, n) {
        if ( o ) o.color = this.UNSELECTED_COLOR;
        if ( n ) n.color = this.SELECTED_COLOR;
      }
    },
    {
      name: 'memento',
      postSet: function(l, m) {
        if ( this.feedback_ ) return;
        this.canvas.children = [];
        for ( var i = 0 ; i < m.length ; i++ ) {
          var c = m[i];
          this.addCircle(c.x, c.y, c.r);
        }
        this.selected = null;
        this.canvas.view.paint(); // TODO: This shouldn't be necessary
      },
    },
    {
      name: 'mementoValue',
      factory: function() { return this.memento$; }
    },
    {
      name: 'canvas',
      factory: function() {
        return this.CView.create({width: 600, height: 500, background: '#f3f3f3'});
      }
    },
  ],
  methods: [
    function initHTML() {
      this.SUPER();
      this.canvas.$.addEventListener('click',       this.onClick);
      this.canvas.$.addEventListener('contextmenu', this.onRightClick);
    },
    function addCircle(x, y, opt_d) {
      var c = this.Circle.create({
        x: x,
        y: y,
        r: opt_d || 25,
        color: this.UNSELECTED_COLOR,
        border: 'black'});
      this.canvas.addChild(c);
      return c;
    },
    function updateMemento() {
      var m = [];
      var cs = this.canvas.children;
      for ( var i = 0 ; i < cs.length ; i++ ) {
        var c = cs[i];
        m.push({x: c.x, y: c.y, r: c.r});
      }
      this.feedback_ = true;
      this.memento = m;
      this.feedback_ = false;
    }
  ],
  listeners: [
    {
      name: 'onClick',
      code: function(evt) {
        var x = evt.offsetX;
        var y = evt.offsetY;
        var c = this.canvas.findChildAt(x, y);
        if ( c ) {
          this.selected = c;
        } else {
          this.selected = this.addCircle(x, y);
          this.updateMemento();
        }
        this.canvas.paint(); // TODO: This shouldn't be necessary
      }
    },
    {
      name: 'onRightClick',
      code: function(evt) {
        evt.preventDefault();
        if ( ! this.selected ) return;
        var p = this.PopupView.create({delegate: function() { return this.DiameterDialog.create({data: this.selected}); }.bind(this), layoutMode: 'relative'});
        p.open(this.$);

        // If the size is changed with the dialog, then create an updated memento
        var oldR = this.selected.r;
        var l = function(_, _, _, state) {
          if ( state === 'closed' ) {
            if ( this.selected.r !== oldR )
              this.updateMemento();
            p.state$.removeListener(l);
          }
        }.bind(this);
        p.state$.addListener(l);
      }
    }
  ],
  templates: [
    function CSS() {/*
      .CircleDrawer { width:610px; height: 600px; margin: 20px; }
      .CircleDrawer canvas { border: 1px solid black; }
      .CircleDrawer .md-card { font-size: 20px; }
      .CircleDrawer .actionButton { margin: 10px; }
      .CircleDrawer input[type='range'] { width: 400px; }
      .CircleDrawer .popup-view-container { width: 640px; height: 585px; }
    */},
    function toHTML() {/*

        $$back{label: 'Undo'} $$forth{label: 'Redo'}
        %%canvas

    */}
  ]
});
<commit_msg>CircleDrawer removed code no longer needed after improvements to CView.<commit_after>/**
 * @license
 * Copyright 2015 Google Inc. All Rights Reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *     http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

MODEL({
  package: 'foam.demos.sevenguis',
  name: 'CircleDrawer',
  extendsModel: 'foam.ui.View',

  traits: [ 'foam.memento.MementoMgr' ],

  requires: [
    'foam.graphics.CView',
    'foam.graphics.Circle',
    'foam.ui.DetailView', // TODO: This shouldn't be required
    'foam.ui.md.PopupView'
  ],

  constants: {
    SELECTED_COLOR:   '#ddd',
    UNSELECTED_COLOR: 'white'
  },

  models: [
    {
      name: 'DiameterDialog',
      extendsModel: 'foam.ui.DetailView',

      templates: [
        function toHTML() {/*
          Adjust the diameter of the circle at ($$x{mode: 'read-only'}, $$y{mode: 'read-only'}).

          $$r{model_: 'foam.ui.RangeView', maxValue: 200, onKeyMode: true}
        */}
      ]
    }
  ],

  properties: [
    {
      name: 'selected',
      postSet: function(o, n) {
        if ( o ) o.color = this.UNSELECTED_COLOR;
        if ( n ) n.color = this.SELECTED_COLOR;
      }
    },
    {
      name: 'memento',
      postSet: function(l, m) {
        if ( this.feedback_ ) return;
        this.canvas.removeAllChildren();
        for ( var i = 0 ; i < m.length ; i++ ) {
          var c = m[i];
          this.addCircle(c.x, c.y, c.r);
        }
        this.selected = null;
      },
    },
    {
      name: 'mementoValue',
      factory: function() { return this.memento$; }
    },
    {
      name: 'canvas',
      factory: function() {
        return this.CView.create({width: 600, height: 500, background: '#f3f3f3'});
      }
    },
  ],
  methods: [
    function initHTML() {
      this.SUPER();
      this.canvas.$.addEventListener('click',       this.onClick);
      this.canvas.$.addEventListener('contextmenu', this.onRightClick);
    },
    function addCircle(x, y, opt_d) {
      var c = this.Circle.create({
        x: x,
        y: y,
        r: opt_d || 25,
        color: this.UNSELECTED_COLOR,
        border: 'black'});
      this.canvas.addChild(c);
      return c;
    },
    function updateMemento() {
      var m = [];
      var cs = this.canvas.children;
      for ( var i = 0 ; i < cs.length ; i++ ) {
        var c = cs[i];
        m.push({x: c.x, y: c.y, r: c.r});
      }
      this.feedback_ = true;
      this.memento = m;
      this.feedback_ = false;
    }
  ],
  listeners: [
    {
      name: 'onClick',
      code: function(evt) {
        var x = evt.offsetX;
        var y = evt.offsetY;
        var c = this.canvas.findChildAt(x, y);
        if ( c ) {
          this.selected = c;
        } else {
          this.selected = this.addCircle(x, y);
          this.updateMemento();
        }
      }
    },
    {
      name: 'onRightClick',
      code: function(evt) {
        evt.preventDefault();
        if ( ! this.selected ) return;
        var p = this.PopupView.create({delegate: function() { return this.DiameterDialog.create({data: this.selected}); }.bind(this), layoutMode: 'relative'});
        p.open(this.$);

        // If the size is changed with the dialog, then create an updated memento
        var oldR = this.selected.r;
        var l = function(_, _, _, state) {
          if ( state === 'closed' ) {
            if ( this.selected.r !== oldR )
              this.updateMemento();
            p.state$.removeListener(l);
          }
        }.bind(this);
        p.state$.addListener(l);
      }
    }
  ],
  templates: [
    function CSS() {/*
      .CircleDrawer { width:610px; height: 600px; margin: 20px; }
      .CircleDrawer canvas { border: 1px solid black; }
      .CircleDrawer .md-card { font-size: 20px; }
      .CircleDrawer .actionButton { margin: 10px; }
      .CircleDrawer input[type='range'] { width: 400px; }
      .CircleDrawer .popup-view-container { width: 640px; height: 585px; }
    */},
    function toHTML() {/*

        $$back{label: 'Undo'} $$forth{label: 'Redo'}
        %%canvas

    */}
  ]
});
<|endoftext|>


<commit_before>/*
* jQuery Mobile Framework : "checkboxradio" plugin
* Copyright (c) jQuery Project
* Dual licensed under the MIT or GPL Version 2 licenses.
* http://jquery.org/license
*/
(function($, undefined ) {
$.widget( "mobile.checkboxradio", $.mobile.widget, {
	options: {
		theme: null
	},
	_create: function(){
		var input = this.element,
			label = $("label[for='" + input.attr( "id" ) + "']"),
			inputtype = input.attr( "type" ),
			checkedicon = "ui-icon-" + inputtype + "-on",
			uncheckedicon = "ui-icon-" + inputtype + "-off";

		if ( inputtype != "checkbox" && inputtype != "radio" ) { return; }

		// If there's no selected theme...
		if( !this.options.theme ) {
			this.options.theme = this.element.data( "theme" );
		}

		label
			.buttonMarkup({
				theme: this.options.theme,
				icon: this.element.parents( "[data-type='horizontal']" ).length ? undefined : uncheckedicon,
				shadow: false
			});

		// wrap the input + label in a div
		input
			.add( label )
			.wrapAll( "

" );

		label.bind({
			mouseover: function() {
				if( $(this).parent().is('.ui-disabled') ){ return false; }
			},

			mousedown: function() {
				if( $(this).parent().is('.ui-disabled') ){ return false; }
				label.data( "state", input.attr( "checked" ) );
			},

			click: function() {
				setTimeout(function() {
					if ( input.attr( "checked" ) === label.data( "state" ) ) {
						input.trigger( "click" );
					}
				}, 1);
			}
		});

		input
			.bind({

				click: function() {
					$( "input[name='" + input.attr( "name" ) + "'][type='" + inputtype + "']" ).checkboxradio( "refresh" );
				},

				focus: function() {
					label.addClass( "ui-focus" );
				},

				blur: function() {
					label.removeClass( "ui-focus" );
				}
			});

		this.refresh();

	},

	refresh: function( ){
		var input = this.element,
			label = $("label[for='" + input.attr( "id" ) + "']"),
			inputtype = input.attr( "type" ),
			icon = label.find( ".ui-icon" ),
			checkedicon = "ui-icon-" + inputtype + "-on",
			uncheckedicon = "ui-icon-" + inputtype + "-off";

		if ( input[0].checked ) {
			label.addClass( "ui-btn-active" );
			icon.addClass( checkedicon );
			icon.removeClass( uncheckedicon );

		} else {
			label.removeClass( "ui-btn-active" );
			icon.removeClass( checkedicon );
			icon.addClass( uncheckedicon );
		}

		if( input.is( ":disabled" ) ){
			this.disable();
		}
		else {
			this.enable();
		}
	},

	disable: function(){
		this.element.attr("disabled",true).parent().addClass("ui-disabled");
	},

	enable: function(){
		this.element.attr("disabled",false).parent().removeClass("ui-disabled");
	}
});
})( jQuery );
<commit_msg>https://github.com/jquery/jquery-mobile/issues#issue/578 Updated to use the selector that Scott suggested in order to make checkboxes not dissappear.  One issue I noticed is that the page still transitions to the 'new' page even though it is really the same page.  I have a fix for this that will post in a separate drop.<commit_after>/*
* jQuery Mobile Framework : "checkboxradio" plugin
* Copyright (c) jQuery Project
* Dual licensed under the MIT or GPL Version 2 licenses.
* http://jquery.org/license
*/
(function($, undefined ) {
$.widget( "mobile.checkboxradio", $.mobile.widget, {
	options: {
		theme: null
	},
	_create: function(){
		var input = this.element,
			label = $(input).closest("form,fieldset,[data-role='page']").find("label[for='" + input.attr( "id" ) + "']"),
			inputtype = input.attr( "type" ),
			checkedicon = "ui-icon-" + inputtype + "-on",
			uncheckedicon = "ui-icon-" + inputtype + "-off";

		if ( inputtype != "checkbox" && inputtype != "radio" ) { return; }

		// If there's no selected theme...
		if( !this.options.theme ) {
			this.options.theme = this.element.data( "theme" );
		}

		label
			.buttonMarkup({
				theme: this.options.theme,
				icon: this.element.parents( "[data-type='horizontal']" ).length ? undefined : uncheckedicon,
				shadow: false
			});

		// wrap the input + label in a div
		input
			.add( label )
			.wrapAll( "

" );

		label.bind({
			mouseover: function() {
				if( $(this).parent().is('.ui-disabled') ){ return false; }
			},

			mousedown: function() {
				if( $(this).parent().is('.ui-disabled') ){ return false; }
				label.data( "state", input.attr( "checked" ) );
			},

			click: function() {
				setTimeout(function() {
					if ( input.attr( "checked" ) === label.data( "state" ) ) {
						input.trigger( "click" );
					}
				}, 1);
			}
		});

		input
			.bind({

				click: function() {
					$( "input[name='" + input.attr( "name" ) + "'][type='" + inputtype + "']" ).checkboxradio( "refresh" );
				},

				focus: function() {
					label.addClass( "ui-focus" );
				},

				blur: function() {
					label.removeClass( "ui-focus" );
				}
			});

		this.refresh();

	},

	refresh: function( ){
		var input = this.element,
			label = $(input).closest("form,fieldset,[data-role='page']").find("label[for='" + input.attr( "id" ) + "']"),
			inputtype = input.attr( "type" ),
			icon = label.find( ".ui-icon" ),
			checkedicon = "ui-icon-" + inputtype + "-on",
			uncheckedicon = "ui-icon-" + inputtype + "-off";

		if ( input[0].checked ) {
			label.addClass( "ui-btn-active" );
			icon.addClass( checkedicon );
			icon.removeClass( uncheckedicon );

		} else {
			label.removeClass( "ui-btn-active" );
			icon.removeClass( checkedicon );
			icon.addClass( uncheckedicon );
		}

		if( input.is( ":disabled" ) ){
			this.disable();
		}
		else {
			this.enable();
		}
	},

	disable: function(){
		this.element.attr("disabled",true).parent().addClass("ui-disabled");
	},

	enable: function(){
		this.element.attr("disabled",false).parent().removeClass("ui-disabled");
	}
});
})( jQuery );
<|endoftext|>


<commit_before>import gulp from "gulp"
import prettier from "gulp-prettier"
import eslint from "gulp-eslint"
import plumber from "gulp-plumber"

import { getGitFiles } from "./core"

gulp.task("lint:js", () => {
  return gulp
    .src(getGitFiles(/\.(mjs|js|jsx)$/), { base: "." })
    .pipe(eslint())
    .pipe(eslint.format("node_modules/eslint-formatter-pretty"))
    .pipe(eslint.failAfterError())
})

gulp.task("pretty:js", () => {
  return gulp
    .src(getGitFiles(/\.(mjs|js|jsx)$/), { base: "." })
    .pipe(plumber())
    .pipe(prettier({
      printWidth: 111,
      tabWidth: 2,
      singleQuote: false,
      trailingComma: "none",
      bracketSpacing: true
    }))
    .pipe(eslint({ fix: true }))
    .pipe(eslint.format("node_modules/eslint-formatter-pretty"))
    .pipe(gulp.dest("."))
})

gulp.task("fix:js", () => {
  return gulp
    .src(getGitFiles(/\.(mjs|js|jsx)$/), { base: "." })
    .pipe(plumber())
    .pipe(eslint({ fix: true }))
    .pipe(eslint.format("node_modules/eslint-formatter-pretty"))
    .pipe(gulp.dest("."))
})
<commit_msg>Updated prettier config for new version<commit_after>import gulp from "gulp"
import prettier from "gulp-prettier"
import eslint from "gulp-eslint"
import plumber from "gulp-plumber"

import { getGitFiles } from "./core"

gulp.task("lint:js", () => {
  return gulp
    .src(getGitFiles(/\.(mjs|js|jsx)$/), { base: "." })
    .pipe(eslint())
    .pipe(eslint.format("node_modules/eslint-formatter-pretty"))
    .pipe(eslint.failAfterError())
})

gulp.task("pretty:js", () => {
  return gulp
    .src(getGitFiles(/\.(mjs|js|jsx)$/), { base: "." })
    .pipe(plumber())
    .pipe(prettier({
      printWidth: 111,
      tabWidth: 2,
      useTabs: false,
      singleQuote: false,
      trailingComma: "none",
      jsxBracketSameLine: true,
      bracketSpacing: true,
      semi: false
    }))
    .pipe(eslint({ fix: true }))
    .pipe(eslint.format("node_modules/eslint-formatter-pretty"))
    .pipe(gulp.dest("."))
})

gulp.task("fix:js", () => {
  return gulp
    .src(getGitFiles(/\.(mjs|js|jsx)$/), { base: "." })
    .pipe(plumber())
    .pipe(eslint({ fix: true }))
    .pipe(eslint.format("node_modules/eslint-formatter-pretty"))
    .pipe(gulp.dest("."))
})
<|endoftext|>


<commit_before><commit_msg>feat(gatsby-plugin-offline): Merge workboxConfig and default o… (#19437)<commit_after><|endoftext|>


<commit_before>import path from "path"
import sitemap from "sitemap"
import {
  defaultOptions,
  filterQuery,
  writeFile,
  renameFile,
  withoutTrailingSlash,
} from "./internals"
import { stripIndent } from "common-tags"
import { parse } from "gatsby/graphql"

const publicPath = `./public`

exports.onPostBuild = async (
  { graphql, pathPrefix, basePath = pathPrefix },
  pluginOptions
) => {
  const options = { ...pluginOptions }
  delete options.plugins
  delete options.createLinkInHead

  const {
    query,
    serialize,
    output,
    exclude,
    hostname,
    resolveSiteUrl,
    ...rest
  } = {
    ...defaultOptions,
    ...options,
  }

  const saved = path.join(publicPath, output)

  // Paths we're excluding...
  const excludeOptions = exclude.concat(defaultOptions.exclude)

  const queryRecords = await graphql(query)

  const filteredRecords = filterQuery(
    queryRecords,
    excludeOptions,
    basePath,
    resolveSiteUrl
  )
  const urls = serialize(filteredRecords)

  if (!rest.sitemapSize || urls.length <= rest.sitemapSize) {
    const map = sitemap.createSitemap(rest)
    urls.forEach(u => map.add(u))
    return writeFile(saved, map.toString())
  }

  const {
    site: {
      siteMetadata: { siteUrl },
    },
  } = filteredRecords
  return new Promise(resolve => {
    // sitemap-index.xml is default file name. (https://git.io/fhNgG)
    const indexFilePath = path.join(
      publicPath,
      `${rest.sitemapName || `sitemap`}-index.xml`
    )
    const sitemapIndexOptions = {
      ...rest,
      hostname:
        (hostname || withoutTrailingSlash(siteUrl)) +
        withoutTrailingSlash(pathPrefix || ``),
      targetFolder: publicPath,
      urls,
      callback: error => {
        if (error) throw new Error(error)
        renameFile(indexFilePath, saved).then(resolve)
      },
    }
    sitemap.createSitemapIndex(sitemapIndexOptions)
  })
}

exports.pluginOptionsSchema = ({ Joi }) =>
  Joi.object()
    .keys({
      output: Joi.string()
        .default(`/sitemap.xml`)
        .description(`The filepath and name`),
      exclude: Joi.array()
        .items(Joi.string())
        .description(`An array of paths to exclude from the sitemap`),
      createLinkInHead: Joi.boolean()
        .default(true)
        .description(
          `Whether to populate the \`<head>\` of your site with a link to the sitemap.`
        ),
      serialize: Joi.function().description(
        `Takes the output of the data query and lets you return an array of sitemap entries.`
      ),
      resolveSiteUrl: Joi.function().description(
        `Takes the output of the data query and lets you return the site URL.`
      ),
      query: Joi.string().description(
        stripIndent`
      The query for the data you need to generate the sitemap. It’s required to get the site’s URL,
      if you are not fetching it from site.siteMetadata.siteUrl, you will need to set a custom resolveSiteUrl function.
      If you override the query, you probably will also need to set a serializer to return the correct data for the sitemap.
      Due to how this plugin was built it is currently expected/required to fetch the page paths from allSitePage,
      but you may use the allSitePage.edges.node or allSitePage.nodes query structure.`
      ),
      sitemapSize: Joi.number().description(
        `The number of entries per sitemap file.`
      ),
    })
    .external(({ query }) => {
      if (query) {
        try {
          parse(query)
        } catch (e) {
          throw new Error(
            stripIndent`
            Invalid plugin options for "gatsby-plugin-sitemap":
            "query" must be a valid GraphQL query. Received the error "${e.message}"`
          )
        }
      }
    })
<commit_msg>feat(gatsby-plugin-sitemap): allow `serialize` plugin option to be async function # (#28207)<commit_after>import path from "path"
import sitemap from "sitemap"
import {
  defaultOptions,
  filterQuery,
  writeFile,
  renameFile,
  withoutTrailingSlash,
} from "./internals"
import { stripIndent } from "common-tags"
import { parse } from "gatsby/graphql"

const publicPath = `./public`

exports.onPostBuild = async (
  { graphql, pathPrefix, basePath = pathPrefix },
  pluginOptions
) => {
  const options = { ...pluginOptions }
  delete options.plugins
  delete options.createLinkInHead

  const {
    query,
    serialize,
    output,
    exclude,
    hostname,
    resolveSiteUrl,
    ...rest
  } = {
    ...defaultOptions,
    ...options,
  }

  const saved = path.join(publicPath, output)

  // Paths we're excluding...
  const excludeOptions = exclude.concat(defaultOptions.exclude)

  const queryRecords = await graphql(query)

  const filteredRecords = filterQuery(
    queryRecords,
    excludeOptions,
    basePath,
    resolveSiteUrl
  )
  const urls = await serialize(filteredRecords)

  if (!rest.sitemapSize || urls.length <= rest.sitemapSize) {
    const map = sitemap.createSitemap(rest)
    urls.forEach(u => map.add(u))
    return writeFile(saved, map.toString())
  }

  const {
    site: {
      siteMetadata: { siteUrl },
    },
  } = filteredRecords
  return new Promise(resolve => {
    // sitemap-index.xml is default file name. (https://git.io/fhNgG)
    const indexFilePath = path.join(
      publicPath,
      `${rest.sitemapName || `sitemap`}-index.xml`
    )
    const sitemapIndexOptions = {
      ...rest,
      hostname:
        (hostname || withoutTrailingSlash(siteUrl)) +
        withoutTrailingSlash(pathPrefix || ``),
      targetFolder: publicPath,
      urls,
      callback: error => {
        if (error) throw new Error(error)
        renameFile(indexFilePath, saved).then(resolve)
      },
    }
    sitemap.createSitemapIndex(sitemapIndexOptions)
  })
}

exports.pluginOptionsSchema = ({ Joi }) =>
  Joi.object()
    .keys({
      output: Joi.string()
        .default(`/sitemap.xml`)
        .description(`The filepath and name`),
      exclude: Joi.array()
        .items(Joi.string())
        .description(`An array of paths to exclude from the sitemap`),
      createLinkInHead: Joi.boolean()
        .default(true)
        .description(
          `Whether to populate the \`<head>\` of your site with a link to the sitemap.`
        ),
      serialize: Joi.function().description(
        `Takes the output of the data query and lets you return an array of sitemap entries.`
      ),
      resolveSiteUrl: Joi.function().description(
        `Takes the output of the data query and lets you return the site URL.`
      ),
      query: Joi.string().description(
        stripIndent`
      The query for the data you need to generate the sitemap. It’s required to get the site’s URL,
      if you are not fetching it from site.siteMetadata.siteUrl, you will need to set a custom resolveSiteUrl function.
      If you override the query, you probably will also need to set a serializer to return the correct data for the sitemap.
      Due to how this plugin was built it is currently expected/required to fetch the page paths from allSitePage,
      but you may use the allSitePage.edges.node or allSitePage.nodes query structure.`
      ),
      sitemapSize: Joi.number().description(
        `The number of entries per sitemap file.`
      ),
    })
    .external(({ query }) => {
      if (query) {
        try {
          parse(query)
        } catch (e) {
          throw new Error(
            stripIndent`
            Invalid plugin options for "gatsby-plugin-sitemap":
            "query" must be a valid GraphQL query. Received the error "${e.message}"`
          )
        }
      }
    })
<|endoftext|>


<commit_before>angular.module('multiselect-searchtree').run(['$templateCache', function ($templateCache) {
    'use strict';

    $templateCache.put('src/multiselect-searchtree.tpl.html',
      "
\n" +
      "\n" +
      "
\n" +
      "
\n" +
      "
" +
      "                      <input placeholder=\"Search...\" type=\"text\" ng-model=\"filterKeyword\" ng-click=\"onFilterClicked($event)\"\n" +
      "                       class=\"form-control\">\n" +
      " \n" +
      "                      " +
      "                     " +
      "                      " +
     "                      " +
      "                      Select All" +
      "                      " +
	       "                      " +
      "                      Clear All" +
      "                      " +
      "
" +
      "
\n" +
      "
\n" +
      "
\n" +
      "
\n" +
      "            <tree-item class=\"top-level\" ng-repeat=\"item in inputModel\" item=\"item\" ng-show=\"!item.isFiltered\"\n" +
      "                       use-callback=\"useCallback\" can-select-item=\"canSelectItem\"\n" +
      "                       multi-select=\"multiSelect\" item-selected=\"itemSelected(item)\"\n" +
      "                       on-active-item=\"onActiveItem(item)\" select-only-leafs=\"selectOnlyLeafs\"></tree-item>\n" +
      "
\n" +
      "
\n" +
      "
\n"
    );

    $templateCache.put('src/tree-item.tpl.html',
      "
\n" +
      "
\n" +
      "        \n" +
      "        \n" +
      "\n" +
      "
<input class=\"tree-checkbox\" type=\"checkbox\" ng-if=\"showCheckbox()\"\n" +
      "                                         ng-checked=\"item.selected\"/>{{item.name}}\n" +
      "
\n" +
      "
\n" +
      "
\n" +
      "        <tree-item item=\"child\" ng-class=\"{grayText: item.textColor === 'gray', blackText: item.textColor === 'black'}\" item-selected=\"subItemSelected(item)\" ng-show=\"!child.isFiltered\" use-callback=\"useCallback\"\n" +
      "                   can-select-item=\"canSelectItem\" multi-select=\"multiSelect\"\n" +
      "                   on-active-item=\"activeSubItem(item, $event)\"></tree-item>\n" +
      "
\n" +
      "
\n"
    );

}]);
<commit_msg>Revert "Update tpl.js for better display"<commit_after><|endoftext|>


<commit_before>const KolibriModule = require('kolibri_module');
const coreActions = require('kolibri.coreVue.vuex.actions');
const router = require('kolibri.coreVue.router');

const Vue = require('kolibri.lib.vue');

const RootVue = require('./vue');
const actions = require('./actions');
const store = require('./state/store');
const PageNames = require('./state/constants').PageNames;

const RECENT_URL_PATTERN = [
  ':class_id',
  '/recent',
  // ':channel_id'
].join('/');

const REPORTS_URL_PATTERN = [
  ':class_id',
  ':view_by_content_or_learners',
  ':channel_id',
  ':content_scope',
  ':content_scope_id',
  ':user_scope',
  ':user_scope_id',
  ':sort_column',
  ':sort_order',
].join('/');

class CoachToolsModule extends KolibriModule {
  ready() {
    coreActions.getCurrentSession(store).then(() => {
      const routes = [
        {
          name: PageNames.COACH_CLASS_LIST_PAGE,
          path: '/',
          handler: (toRoute, fromRoute) => {
            actions.showClassListPage(store);
          },
        },
        {
          name: PageNames.COACH_RECENT_PAGE,
          path: RECENT_URL_PATTERN,
          handler: (toRoute, fromRoute) => {
            actions.showRecentPage(store, toRoute.params);
          },
        },
        {
          name: PageNames.COACH_TOPICS_PAGE,
          path: REPORTS_URL_PATTERN,
          handler: (toRoute, fromRoute) => {
            actions.showReport(store, toRoute.params);
          },
        },
        {
          name: PageNames.COACH_EXAMS_PAGE,
          path: '/:class_id/exams',
          handler: (toRoute, fromRoute) => {
            actions.showExamsPage(store, toRoute.params);
          },
        },
        {
          name: PageNames.COACH_LEARNERS_PAGE,
          path: REPORTS_URL_PATTERN,
          handler: (toRoute, fromRoute) => {
            actions.showReport(store, toRoute.params);
          },
        },
        {
          name: PageNames.COACH_EXERCISE_RENDER_PAGE,
          path: '/:user_id/:content_id/exercise-render',
          handler: (toRoute, fromRoute) => {
            actions.showCoachExerciseRenderPage(store, toRoute.params);
          },
        },
        {
          name: PageNames.COACH_GROUPS_PAGE,
          path: '/:class_id/groups',
          handler: (toRoute, fromRoute) => {
            actions.showGroupsPage(store, toRoute.params.id);
          },
        },
      ];

      this.rootvue = new Vue({
        el: 'rootvue',
        render: createElement => createElement(RootVue),
        router: router.init(routes),
      });
    });
  }
}

module.exports = new CoachToolsModule();
<commit_msg>add exercise render page to app.js<commit_after>const KolibriModule = require('kolibri_module');
const coreActions = require('kolibri.coreVue.vuex.actions');
const router = require('kolibri.coreVue.router');

const Vue = require('kolibri.lib.vue');

const RootVue = require('./vue');
const actions = require('./actions');
const store = require('./state/store');
const PageNames = require('./state/constants').PageNames;

const RECENT_URL_PATTERN = [
  ':class_id',
  '/recent',
  // ':channel_id'
].join('/');

const REPORTS_URL_PATTERN = [
  ':class_id',
  ':view_by_content_or_learners',
  ':channel_id',
  ':content_scope',
  ':content_scope_id',
  ':user_scope',
  ':user_scope_id',
  ':sort_column',
  ':sort_order',
].join('/');

class CoachToolsModule extends KolibriModule {
  ready() {
    coreActions.getCurrentSession(store).then(() => {
      const routes = [
        {
          name: PageNames.COACH_CLASS_LIST_PAGE,
          path: '/',
          handler: (toRoute, fromRoute) => {
            actions.showClassListPage(store);
          },
        },
        {
          name: PageNames.COACH_RECENT_PAGE,
          path: RECENT_URL_PATTERN,
          handler: (toRoute, fromRoute) => {
            actions.showRecentPage(store, toRoute.params);
          },
        },
        {
          name: PageNames.COACH_TOPICS_PAGE,
          path: REPORTS_URL_PATTERN,
          handler: (toRoute, fromRoute) => {
            actions.showReport(store, toRoute.params);
          },
        },
        {
          name: PageNames.COACH_EXAMS_PAGE,
          path: '/:class_id/exams',
          handler: (toRoute, fromRoute) => {
            actions.showExamsPage(store, toRoute.params);
          },
        },
        {
          name: PageNames.COACH_LEARNERS_PAGE,
          path: REPORTS_URL_PATTERN,
          handler: (toRoute, fromRoute) => {
            actions.showReport(store, toRoute.params);
          },
        },
        {
          name: PageNames.COACH_EXERCISE_RENDER_PAGE,
          path: '/:user_id/:content_id/exercise-render',
          handler: (toRoute, fromRoute) => {
            actions.showCoachExerciseRenderPage(store, toRoute.params);
          },
        },
        {
          name: PageNames.COACH_GROUPS_PAGE,
          path: '/:class_id/groups',
          handler: (toRoute, fromRoute) => {
            actions.showGroupsPage(store, toRoute.params.id);
          },
        },
        {
          name: PageNames.COACH_EXERCISE_RENDER_PAGE,
          path: '/:user_id/:content_id/exercise-render',
          handler: (toRoute, fromRoute) => {
            actions.showCoachExerciseRenderPage(store, toRoute.params);
          },
        },
      ];

      this.rootvue = new Vue({
        el: 'rootvue',
        render: createElement => createElement(RootVue),
        router: router.init(routes),
      });
    });
  }
}

module.exports = new CoachToolsModule();
<|endoftext|>


<commit_before>wesabe.$class('views.pages.credentials.NewPage', function($class, $super, $package) {
  // import jQuery as $
  var $ = jQuery;

  $.extend($class.prototype, {
    _module: null,
    _form: null,
    _notification: null,

    _fiData: null,
    _credentialURL: null,
    _jobURL: null,
    _lastVersion: -1,

    init: function(module) {
      var me = this;

      me._module = module;

      me._notification = new wesabe.views.widgets.Notification();
      me._notification.setVisible(false);
      module.appendChildWidget(me._notification);

      me._form = new wesabe.views.widgets.Form();
      me._form.bind('submit', me._connectButtonWasClicked, me);
      module.appendChildWidget(me._form);

      var connectButton = wesabe.views.widgets.Button.withText('Connect');
      connectButton.bind('click', me._connectButtonWasClicked, me);
      me._form.appendChildWidget(connectButton);
    },

    setFinancialInstitution: function(fi) {
      this._fiData = fi;
      this._module.setTitle(fi.name)
      this._form.setEnabled(true);
      this._setFields(fi.login_fields, fi);
    },

    askSecurityQuestions: function(questions) {
      this._form.setEnabled(true);
      this._setFields(questions, null);
    },

    _setFields: function(fields, fi) {
      var form = this._form;

      form.clearFields();

      for (var i = 0, length = fields.length; i < length; i++) {
        var data = fields[i];

        switch (data.type) {
          case 'state':
            form.addField(this._createStateField(data, fi));
            break;
          case 'choice':
            form.addField(this._createChoiceField(data, fi));
            break;
          default:
            form.addField(this._createInputField(data, fi));
            break;
        }
      }

      form.focus();
    },

    _createInputField: function(data, fi) {
      var input = $('<input type="'+data.type+'">');

      var field = new wesabe.views.widgets.FadingLabelField(input);
      field.setName(data.key);

      field.setLabelFormatter({
        format: function(value) {
          var url = value && fi && (fi.login_url || fi.homepage_url);
          if (url) {
            var match = url.match(/\/\/(?:www\d*\.)?([^\/]+)/);
            if (match)
              return [value.label, 'for '+match[1]];
          }

          return value && value.label;
        }
      });

      field.setLabelValue(data);

      return field;
    },

    _createChoiceField: function(data, fi) {
      var field = new wesabe.views.widgets.DropDownField();
      field.setName(data.key);

      var choices = data.choices;
      for (var i = 0, length = choices.length; i < length; i++) {
        var choice = choices[i];
        field.addOption(choice.label, choice.value);
      }

      return field;
    },

    _createStateField: function(data, fi) {
      var field = new wesabe.views.widgets.StateDropDownField();
      field.setName(data.key);
      return field;
    },

    _connectButtonWasClicked: function() {
      var me = this,
          params = me._form.getFieldValues();

      me._notification.setVisible(false);

      for (var k in params) {
        if (params.hasOwnProperty(k)) {
          if (!params[k]) {
            me._showNotification('error',
              "Please fill out all fields",
              "All the fields below are required. "+
              "Please fill them out and try submitting the form again.");
            return;
          }
        }
      }

      me._form.setEnabled(false);

      $.ajax({
        type: me._credentialURL ? 'PUT' : 'POST',
        url: me._credentialURL || '/credentials',
        data: {creds: $.toJSON(params), fi: me._fiData.wesabe_id},
        success: function(data, textStatus, xhr) {
          if (me._credentialURL) {
            me._watchJob(me._jobURL);
          } else {
            me._credentialURL = xhr.getResponseHeader('Location');
            me._credentialCreated(me._credentialURL);
          }
        },
        error: function(xhr, textStatus, error) {
          me._reset();
          me._showNotification('error',
            "Unable to connect",
            "We couldn't save the credentials you entered. "+
            "Please check your internet connection.");
        }
      });
    },

    _credentialCreated: function(url) {
      var me = this;

      $.ajax({
        type: 'POST',
        url: url+'/jobs',
        success: function(data, textStatus, xhr) {
          me._showNotification('success',
            "Successfully connected to "+me._fiData.name+"!",
            "We're retrieving your statements.");
          me._jobURL = xhr.getResponseHeader('Location');
          me._watchJob(me._jobURL);
        },
        error: function(xhr, textStatus, error) {
          me._reset();
          me._showNotification('error',
            "Unable to start job",
            "We saved your credentials but we couldn't retrieve "+
            "your statements from "+me._fiData.name+".");
        }
      });
    },

    _watchJob: function(url) {
      var me = this,
          errorsLeft = 5;

      function pollStatus() {
        $.ajax({
          type: 'GET',
          url: url,
          success: function(data, textStatus, xhr) {
            // ignore ones we've already seen or are stale
            if (data.version <= me._lastVersion) {
              me._jobTimeout = setTimeout(pollStatus, 2000);
              console.log('skipping version', data.version, ' (we already have', me._lastVersion, ')');
              return;
            }

            console.log('updating from version', me._lastVersion, 'to', data.version);
            me._lastVersion = data.version;
            switch (data.status) {
              case 'successful':
                me._showNotification('success',
                  "Successfully retrieved statements from "+me._fiData.name+"!",
                  "We'll return you to My Accounts now so you can review.");
                setTimeout(function(){ window.location = '/accounts'; }, 1000);
                break;
              case 'pending':
                if (/^suspended\./.test(data.result)) {
                  me.askSecurityQuestions(data.data[data.result].questions);
                  me._showNotification('maintenance',
                    me._fiData.name+" needs more information from you",
                    "Please fill out all the fields below.");
                } else {
                  me._jobTimeout = setTimeout(pollStatus, 2000);
                }
                break;
              case 'failed':
                me._reset();
                me._showUnableToConnectNotification();
                break;
            }
          },
          error: function() {
            if (errorsLeft-- > 0)
              me._jobTimeout = setTimeout(pollStatus, 5000);
            else {
              me._reset();
              me._showUnableToConnectNotification();
            }
          }
        });
      }

      pollStatus();
    },

    _stopWatchingJob: function() {
      cancelTimeout(this._jobTimeout);
    },

    _reset: function() {
      this._form.setEnabled(true);
      this._credentialURL = null;
      this._jobURL = null;
      this._lastVersion = -1;
    },

    _showUnableToConnectNotification: function() {
      this._showNotification('error',
        "Unable to connect",
        "We saved the credentials, but we couldn't connect to "+
        this._fiData.name+". Please try again.");
    },

    _showNotification: function(style, title, message) {
      this._notification.setStyle(style);
      this._notification.showWithTitleAndMessage(title, message);
    }
  });
});
<commit_msg>Change the wording/signage of the "we managed to start the job" notification.<commit_after>wesabe.$class('views.pages.credentials.NewPage', function($class, $super, $package) {
  // import jQuery as $
  var $ = jQuery;

  $.extend($class.prototype, {
    _module: null,
    _form: null,
    _notification: null,

    _fiData: null,
    _credentialURL: null,
    _jobURL: null,
    _lastVersion: -1,

    init: function(module) {
      var me = this;

      me._module = module;

      me._notification = new wesabe.views.widgets.Notification();
      me._notification.setVisible(false);
      module.appendChildWidget(me._notification);

      me._form = new wesabe.views.widgets.Form();
      me._form.bind('submit', me._connectButtonWasClicked, me);
      module.appendChildWidget(me._form);

      var connectButton = wesabe.views.widgets.Button.withText('Connect');
      connectButton.bind('click', me._connectButtonWasClicked, me);
      me._form.appendChildWidget(connectButton);
    },

    setFinancialInstitution: function(fi) {
      this._fiData = fi;
      this._module.setTitle(fi.name)
      this._form.setEnabled(true);
      this._setFields(fi.login_fields, fi);
    },

    askSecurityQuestions: function(questions) {
      this._form.setEnabled(true);
      this._setFields(questions, null);
    },

    _setFields: function(fields, fi) {
      var form = this._form;

      form.clearFields();

      for (var i = 0, length = fields.length; i < length; i++) {
        var data = fields[i];

        switch (data.type) {
          case 'state':
            form.addField(this._createStateField(data, fi));
            break;
          case 'choice':
            form.addField(this._createChoiceField(data, fi));
            break;
          default:
            form.addField(this._createInputField(data, fi));
            break;
        }
      }

      form.focus();
    },

    _createInputField: function(data, fi) {
      var input = $('<input type="'+data.type+'">');

      var field = new wesabe.views.widgets.FadingLabelField(input);
      field.setName(data.key);

      field.setLabelFormatter({
        format: function(value) {
          var url = value && fi && (fi.login_url || fi.homepage_url);
          if (url) {
            var match = url.match(/\/\/(?:www\d*\.)?([^\/]+)/);
            if (match)
              return [value.label, 'for '+match[1]];
          }

          return value && value.label;
        }
      });

      field.setLabelValue(data);

      return field;
    },

    _createChoiceField: function(data, fi) {
      var field = new wesabe.views.widgets.DropDownField();
      field.setName(data.key);

      var choices = data.choices;
      for (var i = 0, length = choices.length; i < length; i++) {
        var choice = choices[i];
        field.addOption(choice.label, choice.value);
      }

      return field;
    },

    _createStateField: function(data, fi) {
      var field = new wesabe.views.widgets.StateDropDownField();
      field.setName(data.key);
      return field;
    },

    _connectButtonWasClicked: function() {
      var me = this,
          params = me._form.getFieldValues();

      me._notification.setVisible(false);

      for (var k in params) {
        if (params.hasOwnProperty(k)) {
          if (!params[k]) {
            me._showNotification('error',
              "Please fill out all fields",
              "All the fields below are required. "+
              "Please fill them out and try submitting the form again.");
            return;
          }
        }
      }

      me._form.setEnabled(false);

      $.ajax({
        type: me._credentialURL ? 'PUT' : 'POST',
        url: me._credentialURL || '/credentials',
        data: {creds: $.toJSON(params), fi: me._fiData.wesabe_id},
        success: function(data, textStatus, xhr) {
          if (me._credentialURL) {
            me._watchJob(me._jobURL);
          } else {
            me._credentialURL = xhr.getResponseHeader('Location');
            me._credentialCreated(me._credentialURL);
          }
        },
        error: function(xhr, textStatus, error) {
          me._reset();
          me._showNotification('error',
            "Unable to connect",
            "We couldn't save the credentials you entered. "+
            "Please check your internet connection.");
        }
      });
    },

    _credentialCreated: function(url) {
      var me = this;

      $.ajax({
        type: 'POST',
        url: url+'/jobs',
        success: function(data, textStatus, xhr) {
          me._showNotification('info',
            "Starting connection to "+me._fiData.name+"!",
            "We'll login and download your statements now. If we need any more information, we'll ask you momentarily.");
          me._jobURL = xhr.getResponseHeader('Location');
          me._watchJob(me._jobURL);
        },
        error: function(xhr, textStatus, error) {
          me._reset();
          me._showNotification('error',
            "Unable to start job",
            "We saved your credentials but we couldn't retrieve "+
            "your statements from "+me._fiData.name+".");
        }
      });
    },

    _watchJob: function(url) {
      var me = this,
          errorsLeft = 5;

      function pollStatus() {
        $.ajax({
          type: 'GET',
          url: url,
          success: function(data, textStatus, xhr) {
            // ignore ones we've already seen or are stale
            if (data.version <= me._lastVersion) {
              me._jobTimeout = setTimeout(pollStatus, 2000);
              console.log('skipping version', data.version, ' (we already have', me._lastVersion, ')');
              return;
            }

            console.log('updating from version', me._lastVersion, 'to', data.version);
            me._lastVersion = data.version;
            switch (data.status) {
              case 'successful':
                me._showNotification('success',
                  "Successfully retrieved statements from "+me._fiData.name+"!",
                  "We'll return you to My Accounts now so you can review.");
                setTimeout(function(){ window.location = '/accounts'; }, 1000);
                break;
              case 'pending':
                if (/^suspended\./.test(data.result)) {
                  me.askSecurityQuestions(data.data[data.result].questions);
                  me._showNotification('maintenance',
                    me._fiData.name+" needs more information from you",
                    "Please fill out all the fields below.");
                } else {
                  me._jobTimeout = setTimeout(pollStatus, 2000);
                }
                break;
              case 'failed':
                me._reset();
                me._showUnableToConnectNotification();
                break;
            }
          },
          error: function() {
            if (errorsLeft-- > 0)
              me._jobTimeout = setTimeout(pollStatus, 5000);
            else {
              me._reset();
              me._showUnableToConnectNotification();
            }
          }
        });
      }

      pollStatus();
    },

    _stopWatchingJob: function() {
      cancelTimeout(this._jobTimeout);
    },

    _reset: function() {
      this._form.setEnabled(true);
      this._credentialURL = null;
      this._jobURL = null;
      this._lastVersion = -1;
    },

    _showUnableToConnectNotification: function() {
      this._showNotification('error',
        "Unable to connect",
        "We saved the credentials, but we couldn't connect to "+
        this._fiData.name+". Please try again.");
    },

    _showNotification: function(style, title, message) {
      this._notification.setStyle(style);
      this._notification.showWithTitleAndMessage(title, message);
    }
  });
});
<|endoftext|>


<commit_before>$(document).ready(function() {

    // Pagination
    $('select#per_page').change(function() {
        this.form.submit();
    });

    // "Toggle" checkbox for object lists (PK column)
    $('input:checkbox.toggle').click(function() {
        $(this).closest('table').find('input:checkbox[name=pk]').prop('checked', $(this).prop('checked'));

        // Show the "select all" box if present
        if ($(this).is(':checked')) {
            $('#select_all_box').removeClass('hidden');
        } else {
            $('#select_all').prop('checked', false);
        }
    });

    // Uncheck the "toggle" and "select all" checkboxes if an item is unchecked
    $('input:checkbox[name=pk]').click(function (event) {
        if (!$(this).attr('checked')) {
            $('input:checkbox.toggle, #select_all').prop('checked', false);
        }
    });

    // Enable hidden buttons when "select all" is checked
    $('#select_all').click(function() {
        if ($(this).is(':checked')) {
            $('#select_all_box').find('button').prop('disabled', '');
        } else {
            $('#select_all_box').find('button').prop('disabled', 'disabled');
        }
    });

    // Slugify
    function slugify(s, num_chars) {
        s = s.replace(/[^\-\.\w\s]/g, '');          // Remove unneeded chars
        s = s.replace(/^[\s\.]+|[\s\.]+$/g, '');    // Trim leading/trailing spaces
        s = s.replace(/[\-\.\s]+/g, '-');           // Convert spaces and decimals to hyphens
        s = s.toLowerCase();                        // Convert to lowercase
        return s.substring(0, num_chars);           // Trim to first num_chars chars
    }
    var slug_field = $('#id_slug');
    slug_field.change(function() {
        $(this).attr('_changed', true);
    });
    if (slug_field) {
        var slug_source = $('#id_' + slug_field.attr('slug-source'));
        slug_source.on('keyup change', function() {
            if (slug_field && !slug_field.attr('_changed')) {
                slug_field.val(slugify($(this).val(), 50));
            }
        })
    }

    // Bulk edit nullification
    $('input:checkbox[name=_nullify]').click(function() {
        $('#id_' + this.value).toggle('disabled');
    });

    // Set formaction and submit using a link
    $('a.formaction').click(function(event) {
        event.preventDefault();
        var form = $(this).closest('form');
        form.attr('action', $(this).attr('href'));
        form.submit();
    });

    // Parse URLs which may contain variable refrences to other field values
    function parseURL(url) {
        var filter_regex = /\{\{([a-z_]+)\}\}/g;
        var match;
        var rendered_url = url;
        var filter_field;
        while (match = filter_regex.exec(url)) {
            filter_field = $('#id_' + match[1]);
            var custom_attr = $('option:selected', filter_field).attr('api-value');
            if (custom_attr) {
                rendered_url = rendered_url.replace(match[0], custom_attr);
            } else if (filter_field.val()) {
                rendered_url = rendered_url.replace(match[0], filter_field.val());
            } else if (filter_field.attr('nullable') == 'true') {
                rendered_url = rendered_url.replace(match[0], 'null');
            }
        }
        return rendered_url
    }

    // Assign color picker selection classes
    function colorPickerClassCopy(data, container) {
        if (data.element) {
            $(container).addClass($(data.element).attr("class"));
        }
        return data.text;
    }

    // Color Picker
    $('.netbox-select2-color-picker').select2({
        allowClear: true,
        placeholder: "---------",
        templateResult: colorPickerClassCopy,
        templateSelection: colorPickerClassCopy,
    })

    // Static choice selection
    $('.netbox-select2-static').select2({
        allowClear: true,
        placeholder: "---------",
    })

    // API backed selection
    // Includes live search and chained fields
    // The `multiple` setting may be controled via a data-* attribute
    $('.netbox-select2-api').select2({
        allowClear: true,
        placeholder: "---------",

        ajax: {
            delay: 500,

            url: function(params) {
                var element = this[0];
                var url = parseURL(element.getAttribute("data-url"));

                if (url.includes("{{")) {
                    // URL is not fully rendered yet, abort the request
                    return false;
                }
                return url;
            },

            data: function(params) {
                var element = this[0];
                // Paging
                var offset = params.page * 50 || 0;
                // Base query params
                var parameters = {
                    q: params.term,
                    brief: 1,
                    limit: 50,
                    offset: offset,
                };

                // filter-for fields from a chain
                var attr_name = "data-filter-for-" + $(element).attr("name");
                var form = $(element).closest('form');
                var filter_for_elements = form.find("select[" + attr_name + "]");

                filter_for_elements.each(function(index, filter_for_element) {
                    var param_name = $(filter_for_element).attr(attr_name);
                    var value = $(filter_for_element).val();

                    if (param_name && value) {
                        parameters[param_name] = value;
                    }
                });

                // Conditional query params
                $.each(element.attributes, function(index, attr){
                    if (attr.name.includes("data-conditional-query-param-")){
                        var conditional = attr.name.split("data-conditional-query-param-")[1].split("__");
                        var field = $("#id_" + conditional[0]);
                        var field_value = conditional[1];

                        if ($('option:selected', field).attr('api-value') === field_value){
                            var _val = attr.value.split("=");
                            parameters[_val[0]] = _val[1];
                        }
                    }
                })

                // Additional query params
                $.each(element.attributes, function(index, attr){
                    if (attr.name.includes("data-additional-query-param-")){
                        var param_name = attr.name.split("data-additional-query-param-")[1]
                        parameters[param_name] = attr.value;
                    }
                })

                // This will handle params with multiple values (i.e. for list filter forms)
                return $.param(parameters, true);
            },

            processResults: function (data) {
                var element = this.$element[0];
                var results = $.map(data.results, function (obj) {
                    obj.text = obj[element.getAttribute('display-field')] || obj.name;
                    obj.id = obj[element.getAttribute('value-field')] || obj.id;

                    if(element.getAttribute('disabled-indicator') && obj[element.getAttribute('disabled-indicator')]) {
                        // The disabled-indicator equated to true, so we disable this option
                        console.log("hello");
                        obj.disabled = true;
                    }
                    return obj;
                });

                // Handle the null option
                if (element.getAttribute('data-null-option')) {
                    var null_option = $(element).children()[0]
                    results.unshift({
                        id: null_option.value,
                        text: null_option.text
                    });
                }

                // Check if there are more results to page
                var page = data.next !== null;
                return {
                    results: results,
                    pagination: {
                        more: page
                    }
                };
            }
        }
    });

    // API backed tags
    var tags = $('#id_tags');
    if (tags.length > 0 && tags.val().length > 0){
        tags = $('#id_tags').val().split(/,\s*/);
    } else {
        tags = [];
    }
    tag_objs = $.map(tags, function (tag) {
        return {
            id: tag,
            text: tag,
            selected: true
        }
    });
    // Replace the django issued text input with a select element
    $('#id_tags').replaceWith('<select name="tags" id="id_tags" class="form-control"></select>');
    $('#id_tags').select2({
        tags: true,
        data: tag_objs,
        multiple: true,
        allowClear: true,
        placeholder: "Tags",

        ajax: {
            delay: 250,
            url: "/api/extras/tags/",

            data: function(params) {
                // paging
                var offset = params.page * 50 || 0;
                var parameters = {
                    q: params.term,
                    brief: 1,
                    limit: 50,
                    offset: offset,
                };
                return parameters;
            },

            processResults: function (data) {
                var results = $.map(data.results, function (obj) {
                    return {
                        id: obj.name,
                        text: obj.name
                    }
                });

                // Check if there are more results to page
                var page = data.next !== null;
                return {
                    results: results,
                    pagination: {
                        more: page
                    }
                };
            }
        }
    });
    $('#id_tags').closest('form').submit(function(event){
        // django-taggit can only accept a single comma seperated string value
        var value = $('#id_tags').val();
        if (value.length > 0){
            var final_tags = value.join(', ');
            $('#id_tags').val(null).trigger('change');
            var option = new Option(final_tags, final_tags, true, true);
            $('#id_tags').append(option).trigger('change');
        }
    });
});
<commit_msg>removed debug log<commit_after>$(document).ready(function() {

    // Pagination
    $('select#per_page').change(function() {
        this.form.submit();
    });

    // "Toggle" checkbox for object lists (PK column)
    $('input:checkbox.toggle').click(function() {
        $(this).closest('table').find('input:checkbox[name=pk]').prop('checked', $(this).prop('checked'));

        // Show the "select all" box if present
        if ($(this).is(':checked')) {
            $('#select_all_box').removeClass('hidden');
        } else {
            $('#select_all').prop('checked', false);
        }
    });

    // Uncheck the "toggle" and "select all" checkboxes if an item is unchecked
    $('input:checkbox[name=pk]').click(function (event) {
        if (!$(this).attr('checked')) {
            $('input:checkbox.toggle, #select_all').prop('checked', false);
        }
    });

    // Enable hidden buttons when "select all" is checked
    $('#select_all').click(function() {
        if ($(this).is(':checked')) {
            $('#select_all_box').find('button').prop('disabled', '');
        } else {
            $('#select_all_box').find('button').prop('disabled', 'disabled');
        }
    });

    // Slugify
    function slugify(s, num_chars) {
        s = s.replace(/[^\-\.\w\s]/g, '');          // Remove unneeded chars
        s = s.replace(/^[\s\.]+|[\s\.]+$/g, '');    // Trim leading/trailing spaces
        s = s.replace(/[\-\.\s]+/g, '-');           // Convert spaces and decimals to hyphens
        s = s.toLowerCase();                        // Convert to lowercase
        return s.substring(0, num_chars);           // Trim to first num_chars chars
    }
    var slug_field = $('#id_slug');
    slug_field.change(function() {
        $(this).attr('_changed', true);
    });
    if (slug_field) {
        var slug_source = $('#id_' + slug_field.attr('slug-source'));
        slug_source.on('keyup change', function() {
            if (slug_field && !slug_field.attr('_changed')) {
                slug_field.val(slugify($(this).val(), 50));
            }
        })
    }

    // Bulk edit nullification
    $('input:checkbox[name=_nullify]').click(function() {
        $('#id_' + this.value).toggle('disabled');
    });

    // Set formaction and submit using a link
    $('a.formaction').click(function(event) {
        event.preventDefault();
        var form = $(this).closest('form');
        form.attr('action', $(this).attr('href'));
        form.submit();
    });

    // Parse URLs which may contain variable refrences to other field values
    function parseURL(url) {
        var filter_regex = /\{\{([a-z_]+)\}\}/g;
        var match;
        var rendered_url = url;
        var filter_field;
        while (match = filter_regex.exec(url)) {
            filter_field = $('#id_' + match[1]);
            var custom_attr = $('option:selected', filter_field).attr('api-value');
            if (custom_attr) {
                rendered_url = rendered_url.replace(match[0], custom_attr);
            } else if (filter_field.val()) {
                rendered_url = rendered_url.replace(match[0], filter_field.val());
            } else if (filter_field.attr('nullable') == 'true') {
                rendered_url = rendered_url.replace(match[0], 'null');
            }
        }
        return rendered_url
    }

    // Assign color picker selection classes
    function colorPickerClassCopy(data, container) {
        if (data.element) {
            $(container).addClass($(data.element).attr("class"));
        }
        return data.text;
    }

    // Color Picker
    $('.netbox-select2-color-picker').select2({
        allowClear: true,
        placeholder: "---------",
        templateResult: colorPickerClassCopy,
        templateSelection: colorPickerClassCopy,
    })

    // Static choice selection
    $('.netbox-select2-static').select2({
        allowClear: true,
        placeholder: "---------",
    })

    // API backed selection
    // Includes live search and chained fields
    // The `multiple` setting may be controled via a data-* attribute
    $('.netbox-select2-api').select2({
        allowClear: true,
        placeholder: "---------",

        ajax: {
            delay: 500,

            url: function(params) {
                var element = this[0];
                var url = parseURL(element.getAttribute("data-url"));

                if (url.includes("{{")) {
                    // URL is not fully rendered yet, abort the request
                    return false;
                }
                return url;
            },

            data: function(params) {
                var element = this[0];
                // Paging
                var offset = params.page * 50 || 0;
                // Base query params
                var parameters = {
                    q: params.term,
                    brief: 1,
                    limit: 50,
                    offset: offset,
                };

                // filter-for fields from a chain
                var attr_name = "data-filter-for-" + $(element).attr("name");
                var form = $(element).closest('form');
                var filter_for_elements = form.find("select[" + attr_name + "]");

                filter_for_elements.each(function(index, filter_for_element) {
                    var param_name = $(filter_for_element).attr(attr_name);
                    var value = $(filter_for_element).val();

                    if (param_name && value) {
                        parameters[param_name] = value;
                    }
                });

                // Conditional query params
                $.each(element.attributes, function(index, attr){
                    if (attr.name.includes("data-conditional-query-param-")){
                        var conditional = attr.name.split("data-conditional-query-param-")[1].split("__");
                        var field = $("#id_" + conditional[0]);
                        var field_value = conditional[1];

                        if ($('option:selected', field).attr('api-value') === field_value){
                            var _val = attr.value.split("=");
                            parameters[_val[0]] = _val[1];
                        }
                    }
                })

                // Additional query params
                $.each(element.attributes, function(index, attr){
                    if (attr.name.includes("data-additional-query-param-")){
                        var param_name = attr.name.split("data-additional-query-param-")[1]
                        parameters[param_name] = attr.value;
                    }
                })

                // This will handle params with multiple values (i.e. for list filter forms)
                return $.param(parameters, true);
            },

            processResults: function (data) {
                var element = this.$element[0];
                var results = $.map(data.results, function (obj) {
                    obj.text = obj[element.getAttribute('display-field')] || obj.name;
                    obj.id = obj[element.getAttribute('value-field')] || obj.id;

                    if(element.getAttribute('disabled-indicator') && obj[element.getAttribute('disabled-indicator')]) {
                        // The disabled-indicator equated to true, so we disable this option
                        obj.disabled = true;
                    }
                    return obj;
                });

                // Handle the null option
                if (element.getAttribute('data-null-option')) {
                    var null_option = $(element).children()[0]
                    results.unshift({
                        id: null_option.value,
                        text: null_option.text
                    });
                }

                // Check if there are more results to page
                var page = data.next !== null;
                return {
                    results: results,
                    pagination: {
                        more: page
                    }
                };
            }
        }
    });

    // API backed tags
    var tags = $('#id_tags');
    if (tags.length > 0 && tags.val().length > 0){
        tags = $('#id_tags').val().split(/,\s*/);
    } else {
        tags = [];
    }
    tag_objs = $.map(tags, function (tag) {
        return {
            id: tag,
            text: tag,
            selected: true
        }
    });
    // Replace the django issued text input with a select element
    $('#id_tags').replaceWith('<select name="tags" id="id_tags" class="form-control"></select>');
    $('#id_tags').select2({
        tags: true,
        data: tag_objs,
        multiple: true,
        allowClear: true,
        placeholder: "Tags",

        ajax: {
            delay: 250,
            url: "/api/extras/tags/",

            data: function(params) {
                // paging
                var offset = params.page * 50 || 0;
                var parameters = {
                    q: params.term,
                    brief: 1,
                    limit: 50,
                    offset: offset,
                };
                return parameters;
            },

            processResults: function (data) {
                var results = $.map(data.results, function (obj) {
                    return {
                        id: obj.name,
                        text: obj.name
                    }
                });

                // Check if there are more results to page
                var page = data.next !== null;
                return {
                    results: results,
                    pagination: {
                        more: page
                    }
                };
            }
        }
    });
    $('#id_tags').closest('form').submit(function(event){
        // django-taggit can only accept a single comma seperated string value
        var value = $('#id_tags').val();
        if (value.length > 0){
            var final_tags = value.join(', ');
            $('#id_tags').val(null).trigger('change');
            var option = new Option(final_tags, final_tags, true, true);
            $('#id_tags').append(option).trigger('change');
        }
    });
});
<|endoftext|>