PageSourceSearch

https://potenciatech.com.br/assets/js/main.js?timestamp=1790595311

js potenciatech.com.br collected 2026-09-28 11:35:25 UTC 38,824 bytes, 1,170 lines download raw bytes

1"use strict";
2
3// Modo Ligth/Dark
4const toggleSwitch = document.querySelector(
5    '.theme-switch input[type="checkbox"]'
6);
7const currentTheme = localStorage.getItem("theme");
8
9if (toggleSwitch) {
10    if (currentTheme) {
11        document.documentElement.setAttribute("data-theme", currentTheme);
12
13        if (currentTheme === "dark") {
14            toggleSwitch.checked = true;
15        }
16    }
17
18    function switchTheme(e) {
19        if (e.target.checked) {
20            document.documentElement.setAttribute("data-theme", "dark");
21            localStorage.setItem("theme", "dark");
22        } else {
23            document.documentElement.setAttribute("data-theme", "light");
24            localStorage.setItem("theme", "light");
25        }
26    }
27    toggleSwitch.addEventListener("change", switchTheme, false);
28}
29
30function isValidURL(string) {
31    let expression = /^(ftp|http|https):\/\/[^ "]+$/;
32    let regex = new RegExp(expression);
33
34    if (!regex.test(string)) {
35        return false;
36    }
37
38    return true;
39}
40
41function debouncedSearch(func, wait, immediate) {
42    let timeout;
43    return function executedFunction() {
44        let context = this;
45        let args = arguments;
46        let later = function () {
47            timeout = null;
48            if (!immediate) func.apply(context, args);
49        };
50        let callNow = immediate && !timeout;
51        clearTimeout(timeout);
52        timeout = setTimeout(later, wait);
53        if (callNow) func.apply(context, args);
54    };
55}
56
57// Classe for Hide/Show Navbar.
58function hideShowNavbar() {
59    var prev = 0;
60    var $window = $(window);
61    var navBar = $("#mainNav");
62    var navGturmas = $(".nav-gestao-turmas");
63    var navGeneral = $(".nav-gestao-geral");
64
65    $window.on("scroll", function () {
66        var scrollTop = $window.scrollTop();
67        navBar.toggleClass("hiddenNavBarUP", scrollTop > prev); //Navbar scrollable
68        navBar.toggleClass("hiddenNavBarDown", scrollTop < prev); //Navbar scrollable
69
70        navGturmas.toggleClass("navGturmasUP", scrollTop > prev); //Navbar scrollable
71        navGturmas.toggleClass("navGturmasDown", scrollTop < prev); //Navbar scrollable
72
73        navGeneral.toggleClass("navGeneralUP", scrollTop > prev); //Navbar scrollable
74        navGeneral.toggleClass("navGeneralDown", scrollTop < prev); //Navbar scrollable
75
76        // aplica o fixed e styles especifica para a pagina de turmas
77        if (scrollTop > 32) {
78            $(".nav-gestao-turmas").addClass("active-min-turmas");
79        } else {
80            $(".nav-gestao-turmas").removeClass("active-min-turmas");
81        }
82
83        if (scrollTop > 32) {
84            $(".nav-gestao-geral").addClass("active-min-geral");
85        } else {
86            $(".nav-gestao-geral").removeClass("active-min-geral");
87        }
88
89        prev = scrollTop;
90    });
91}
92
93// Adiciona um contador de caracteres aos campos com a Class="contador-caracteres"
94let componentContCaracteres = ".contador-caracteres";
95let mostraCaracteres = "mostra-caracteres";
96
97$(componentContCaracteres).focusin(function () {
98    $(componentContCaracteres)
99        .parent()
100        .append("<small class=" + mostraCaracteres + "></small>");
101});
102$(componentContCaracteres).focusout(function () {
103    $("." + mostraCaracteres).remove();
104});
105
106$(document).on("input", componentContCaracteres, function () {
107    let limite = $(componentContCaracteres).attr("maxlength");
108    let informativo = "caracteres restantes.";
109    let caracteresDigitados = $(this).val().length;
110    let caracteresRestantes = limite - caracteresDigitados;
111    if (caracteresRestantes <= 0) {
112        $(".mostra-caracteres").text("0 " + informativo);
113    } else {
114        $(".mostra-caracteres").text(caracteresRestantes + " " + informativo);
115    }
116});
117// END - Adiciona um contador de caracteres aos campos com a Class="contador-caracteres"
118
119function proximoModal(element) {
120    var qtPaginas = $(element).find(".form-page").length;
121
122    if (qtPaginas > 1) {
123        var idPaginaAtual = $(element)
124            .find(".form-page:not(.d-none)")
125            .attr("id");
126
127        var paginaAtual = $(element)
128            .find(".form-page:not(.d-none)")
129            .attr("id")
130            .replace("page", "");
131
132        var preenchido = true;
133
134        $(element)
135            .find("#page" + paginaAtual + " :input[required]")
136            .each(function () {
137                if ($(this).val() == "") {
138                    $(this).focus();
139                    preenchido = false;
140                    return false;
141                }
142            });
143
144        if (!preenchido) {
145            swal(
146                "Atenção!",
147                "Você deve preencher todos os campos obrigatórios!",
148                "warning"
149            );
150
151            return;
152        }
153
154        if ($(element).find("#page" + (Number(paginaAtual) + 1)).length >= 1) {
155            $(element)
156                .find("#" + idPaginaAtual)
157                .addClass("d-none");
158            $(element)
159                .find("#page" + (Number(paginaAtual) + 1))
160                .removeClass("d-none");
161        }
162    }
163}
164
165function anteriorModal(element) {
166    var qtPaginas = $(element).find(".form-page").length;
167
168    if (qtPaginas > 1) {
169        var idPaginaAtual = $(element)
170            .find(".form-page:not(.d-none)")
171            .attr("id");
172
173        var paginaAtual = $(element)
174            .find(".form-page:not(.d-none)")
175            .attr("id")
176            .replace("page", "");
177
178        if ($(element).find("#page" + (Number(paginaAtual) - 1)).length >= 1) {
179            $(element)
180                .find("#" + idPaginaAtual)
181                .addClass("d-none");
182            $(element)
183                .find("#page" + (Number(paginaAtual) - 1))
184                .removeClass("d-none");
185        }
186    }
187}
188
189//Multiple items inputs
190function showInputMultiple(element) {
191    $(element).addClass("d-none");
192    $(element.parentNode).find("#txtInputMultiple").removeClass("d-none");
193    $(element.parentNode).find("#txtInputMultiple").focus();
194
195    // $("#" + element.parentNode.id + " > #divInputAutor").addClass('d-none');
196    // $("#" + element.parentNode.id + " > #txtInputAutor").removeClass('d-none');
197
198    // $("#" + element.parentNode.id + " > #txtInputAutor").focus();
199}
200
201function endInputMultiple(element) {
202    $(element).addClass("d-none");
203    $(element.parentNode).find("#divInputMultiple").removeClass("d-none");
204
205    var inputValue = element.value;
206
207    if (inputValue.indexOf(",") > 0) {
208        var valores = inputValue.split(", ");
209
210        valores.forEach((val) => {
211            if (val.indexOf(", ") > 0) val = val.replace(", ", "");
212            else val = val.replace(",", "");
213
214            var novoValor =
215                '<span class="tag-autor mr-2 p-1 px-3">' +
216                '<span class="autor-name">' +
217                val +
218                "</span>" +
219                '<button type="button" onclick="removerValor(this)" class="btn p-0 m-0 ml-1 text-white bg-transparent"><i class="far fa-times-circle"></i></button>' +
220                "</span>";
221
222            $(element.parentNode).find("#divInputMultiple").append(novoValor);
223        });
224    } else {
225        var novoValor =
226            '<span class="tag-autor mr-2 p-1 px-3">' +
227            '<span class="autor-name">' +
228            element.value +
229            "</span>" +
230            '<button type="button" onclick="removerValor(this)" class="btn p-0 m-0 ml-1 text-white bg-transparent"><i class="far fa-times-circle"></i></button>' +
231            "</span>";
232
233        $(element.parentNode).find("#divInputMultiple").append(novoValor);
234    }
235
236    element.value = "";
237
238    AtualizarInputMultiple(element.parentNode);
239}
240
241function removerValor(element) {
242    var divMain = element.parentNode.parentNode.parentNode;
243
244    if ($(divMain).first().find(".autor-name").length == 1) {
245        $(divMain).find("#divInputMultiple").addClass("d-none");
246        $(divMain).find("#txtInputMultiple").removeClass("d-none");
247    }
248
249    $(element.parentNode).remove();
250
251    AtualizarInputMultiple(divMain);
252
253    if (!e) var e = window.event;
254    e.cancelBubble = true;
255    if (e.stopPropagation) e.stopPropagation();
256}
257
258function AtualizarInputMultiple(element) {
259    if ($(element).find("#txtResultMultiple").length >= 1) {
260        $(element).find("#txtResultMultiple").val("");
261
262        var valores = [];
263
264        $(element)
265            .find("#divInputMultiple .autor-name")
266            .each(function () {
267                valores.push($(this).text());
268            });
269
270        $(element).find("#txtResultMultiple").val(JSON.stringify(valores));
271    } else if (
272        $(element.parentNode.parentNode.parentNode).find("#txtResultSumario")
273            .length >= 1
274    ) {
275        var divItensSumario = element.parentNode.parentNode.parentNode;
276
277        $(divItensSumario).find("#txtResultSumario").val();
278
279        var sumario = [];
280
281        $(divItensSumario)
282            .find(".item-sumario")
283            .each(function (index) {
284                var autores = [];
285
286                $(this)
287                    .find(".autores .input-autor .autor-name")
288                    .each(function (index2) {
289                        autores.push($(this).text());
290                    });
291
292                var palavras = [];
293
294                $(this)
295                    .find(".palavras .input-autor .autor-name")
296                    .each(function (index2) {
297                        palavras.push($(this).text());
298                    });
299
300                sumario.push({
301                    titulo: $(this).find("#txtTituloItemSumario").val(),
302                    autores: autores,
303                    palavras: palavras,
304                    pagina: $(this).find("#txtPaginaItemSumario").val(),
305                });
306            });
307
308        $(divItensSumario)
309            .find("#txtResultSumario")
310            .val(JSON.stringify(sumario));
311    }
312}
313
314function confirmLogout() {
315    swal({
316        title: i18n.leaving,
317        text: i18n.logoutPlatform,
318        icon: "warning",
319        buttons: [i18n.buttons.back, i18n.buttons.logout],
320        dangerMode: true,
321    }).then((willLogout) => {
322        if (willLogout) {
323            window.location.href = "/multiunidades/logout";
324        }
325    });
326}
327
328function mudouArquivoCapa(input) {
329    if (
330        input.accept
331            .toString()
332            .indexOf(
333                input.value.substring(input.value.length - 3).toLowerCase()
334            ) < 0
335    ) {
336        input.value = null;
337        swal("Atenção!", "Selecione um arquivo do tipo correto!", "warning");
338    }
339
340    var imgIcon = "";
341
342    if (input.id.indexOf("capa") >= 0) {
343        imgIcon =
344            '<i class="far fa-image fa-2x text-darkmode mr-2" style="vertical-align:sub;"></i>';
345    }
346
347    if (input.value != null && input.value != "") {
348        $("#" + input.parentNode.id + " #placeholder").addClass("d-none");
349        $("#" + input.parentNode.id + " #file-name").html(
350            imgIcon + input.value.split(/(\\|\/)/g).pop()
351        );
352        $("#" + input.parentNode.id + " #file-name").removeClass("d-none");
353    } else {
354        $(input.parentNode).css("background", "var(--primary-color)");
355        $("#" + input.parentNode.id + " #placeholder").removeClass("d-none");
356        $("#" + input.parentNode.id + " #file-name").addClass("d-none");
357    }
358
359    if (input.id.indexOf("capa") >= 0) {
360        if (input.files && input.files[0]) {
361            var reader = new FileReader();
362
363            reader.onload = function (e) {
364                $(input.parentNode).attr(
365                    "style",
366                    "color:white; background: url('" +
367                        e.target.result +
368                        "');background-size: contain;background-position: 50% 50%;background-repeat: no-repeat;"
369                );
370            };
371
372            reader.readAsDataURL(input.files[0]);
373        }
374    }
375}
376
377function mudouArquivoInput(input, limitUpload = 0) {
378    // if(input.accept.toString().indexOf(input.value.substring(input.value.length - 3).toLowerCase()) < 0)
379    // {
380    //     input.value = null;
381    //     swal("Ops!", "Selecione um arquivo do tipo correto!", "warning");
382    // }
383
384    if (limitUpload > 0 && input.files.length > 0 && input.files[0].size > limitUpload) {
385        swal("Arquivo muito grande!", "Seu arquivo passou do limite de upload.", "warning");
386        return
387    }
388
389    if (input.value != null && input.value != "") {
390        $(input.parentNode)
391            .find(".file-name")
392            .text(input.value.split(/(\\|\/)/g).pop());
393    } else {
394        $(input.parentNode).find(".file-name").text("Selecionar arquivo");
395    }
396}
397
398function enviouArquivo(input) {
399    if (
400        input.accept
401            .toString()
402            .indexOf(
403                input.value.substring(input.value.length - 3).toLowerCase()
404            ) < 0
405    ) {
406        input.value = null;
407        swal("", "Selecione um arquivo do tipo correto!", "warning");
408    }
409
410    if (input.value != null && input.value != "") {
411        $(input.parentNode).find("#placeholder").addClass("d-none");
412        $(input.parentNode).find(".file-name").removeClass("d-none");
413        $(input.parentNode)
414            .find(".file-name")
415            .text(input.value.split(/(\\|\/)/g).pop());
416    } else {
417        $(input.parentNode).find(".file-name").addClass("d-none");
418        $(input.parentNode).find("#placeholder").removeClass("d-none");
419    }
420}
421
422function excluirNotificacao(id) {
423    $.ajax({
424        url: appurl + "/notificacao/" + id + "/excluir",
425        type: "get",
426        dataType: "json",
427        success: function (_response) {
428            if (_response.success != null) {
429                if (id == "todas") {
430                    $(".box-notificacao").remove();
431                } else {
432                    $("#divNotificacao" + id).remove();
433                }
434
435                if (parseInt($("#lblQtNotificacoes").text()) > 1) {
436                    $("#lblQtNotificacoes").text(
437                        parseInt($("#lblQtNotificacoes").text()) - 1
438                    );
439                } else {
440                    $("#lblQtNotificacoes").addClass("d-none");
441                }
442
443                if ($("#divNotificacoes .dropdown-item").length == 0) {
444                    $("#divNotificacoes")
445                        .append(`<div class="dropdown-item px-4 py-3" style="color: #60748A;min-width:  340px;border-bottom:  2px solid #E3E5F0;">
446                            Você não possui notificações.
447                        </div>`);
448                }
449            }
450        },
451        error: (err) => {},
452    });
453}
454
455// accessibility - initial focus
456function setInitialFocus() {
457    const navIcon = document.getElementById('nav-icon3');
458    if (navIcon) {
459        navIcon.focus();
460    }
461}
462
463function isMobileSideMenuBreakpoint() {
464    const rootStyles = globalThis.getComputedStyle(document.documentElement);
465    const breakpoint = rootStyles.getPropertyValue("--navbar-side-menu-breakpoint").trim() || "1300px";
466    return globalThis.matchMedia(`(max-width: ${breakpoint})`).matches;
467}
468
469function getSidebarContainer() {
470    const $sidebar = $(".sidebar");
471    const $sideMenu = $("#side-menu");
472    const sidebarHasItems = $sidebar.find(".side-group-item").length > 0;
473    const sideMenuHasLinks = $sideMenu.find(".nav-link").length > 0;
474    const useMobileMenu = isMobileSideMenuBreakpoint();
475
476    // On responsive navbar breakpoints, prefer #side-menu only when
477    // there is no real sidebar menu (logged-out catalogue scenario).
478    if ($sideMenu.length && useMobileMenu && !sidebarHasItems && sideMenuHasLinks) {
479        return $sideMenu;
480    }
481
482    // Fallback: prefer #side-menu when no real sidebar menu items are present.
483    if ($sideMenu.length && (!$sidebar.length || !sidebarHasItems) && sideMenuHasLinks) {
484        return $sideMenu;
485    }
486
487    if ($sidebar.length) {
488        return $sidebar;
489    }
490
491    return $();
492}
493
494function setNavbarInteractiveTabIndex(tabIndex) {
495    const btnShowInput = document.getElementById("btnShowInput");
496    const linkLogo = document.getElementById("link-logo");
497    const dropdownNotificationsMenu = document.getElementById("dropdownNotificationsMenu");
498    const navbarDropdown = document.getElementById("navbarDropdown");
499    const dropdownSearchMenu = document.getElementById("dropdownSearchMenu");
500    const searchClearButtonSmall = document.getElementById("search-clear-button-small");
501
502    if (btnShowInput) btnShowInput.setAttribute("tabindex", tabIndex);
503    if (dropdownNotificationsMenu) dropdownNotificationsMenu.setAttribute("tabindex", tabIndex);
504    if (linkLogo) linkLogo.setAttribute("tabindex", tabIndex);
505    if (navbarDropdown) navbarDropdown.setAttribute("tabindex", tabIndex);
506    if (dropdownSearchMenu) {
507        const searchInput = dropdownSearchMenu.querySelector(".search-input");
508        if (searchInput) searchInput.setAttribute("tabindex", tabIndex);
509    }
510    if (searchClearButtonSmall) searchClearButtonSmall.setAttribute("tabindex", tabIndex);
511}
512
513function setSideMenuLinksTabIndex(sideMenu, fallbackMode, isOpening) {
514    if (!sideMenu) {
515        return;
516    }
517
518    let sideMenuTabIndex = "0";
519    if (isOpening) {
520        sideMenuTabIndex = fallbackMode ? "0" : "-1";
521    } else {
522        sideMenuTabIndex = fallbackMode ? "-1" : "0";
523    }
524
525    Array.from(sideMenu.querySelectorAll(".nav-link")).forEach((element) => {
526        element.setAttribute("tabindex", sideMenuTabIndex);
527    });
528}
529
530function setupSideMenuSubmenuAccordion() {
531    const sideMenu = document.getElementById("side-menu");
532    if (!sideMenu) {
533        return;
534    }
535
536    sideMenu.addEventListener("click", function (event) {
537        const toggleButton = event.target.closest(".submenu-toggle");
538        if (!toggleButton || !isMobileSideMenuBreakpoint()) {
539            return;
540        }
541
542        const menuItem = toggleButton.closest(".drodonw-links");
543        if (!menuItem) {
544            return;
545        }
546
547        event.preventDefault();
548
549        const isOpening = !menuItem.classList.contains("is-open");
550        const openItems = sideMenu.querySelectorAll(".drodonw-links.is-open");
551        openItems.forEach((item) => {
552            if (item === menuItem) {
553                return;
554            }
555
556            item.classList.remove("is-open");
557            const itemToggle = item.querySelector(".submenu-toggle");
558            const itemSubmenu = item.querySelector(".dropdown-subLinks");
559            if (itemToggle) itemToggle.setAttribute("aria-expanded", "false");
560            if (itemSubmenu) itemSubmenu.setAttribute("aria-hidden", "true");
561        });
562
563        menuItem.classList.toggle("is-open", isOpening);
564        toggleButton.setAttribute("aria-expanded", String(isOpening));
565        const submenu = menuItem.querySelector(".dropdown-subLinks");
566        if (submenu) submenu.setAttribute("aria-hidden", String(!isOpening));
567    });
568}
569
570function toggleSideMenu() {
571    const sidebar = getSidebarContainer();
572    if (!sidebar.length) {
573        return;
574    }
575
576    const fallbackMode = sidebar.attr("id") === "side-menu";
577    const navIcon = $("#nav-icon3");
578    navIcon.attr("aria-controls", fallbackMode ? "side-menu" : "sidebar");
579    const sidebarItems = document.querySelectorAll(".side-group-item");
580    const sideGroup = document.querySelector(".side-group");
581    const sideMenu = document.getElementById("side-menu");
582
583    navIcon.toggleClass("open");
584
585    if (sidebar.hasClass("show")) {
586        $("#nav-icon3 > i").removeClass("fa-times").addClass("fa-bars");
587        navIcon.attr("aria-expanded", "false");
588        navIcon.attr("aria-label", "Abrir menu lateral");
589        setNavbarInteractiveTabIndex("0");
590        setSideMenuLinksTabIndex(sideMenu, fallbackMode, false);
591
592        sidebarItems.forEach(item => {
593            item.setAttribute("tabindex", "-1");
594        });
595
596        if (fallbackMode) {
597            const sideMenuWidth = sidebar.outerWidth() || Math.min(window.innerWidth, 320);
598            sidebar.stop(true, true).animate({ left: -sideMenuWidth }, 300, function () {
599                sidebar.removeClass("show").addClass("hide");
600                setInitialFocus();
601            });
602        } else {
603            sidebar.animate({ left: -sidebar.outerWidth() }, 300, function () {
604                sidebar.removeClass("show").addClass("hide");
605                if (sideGroup) sideGroup.style.display = "none";
606                setInitialFocus();
607            });
608        }
609
610    } else {
611        $("#nav-icon3 > i").removeClass("fa-bars").addClass("fa-times");
612        navIcon.attr("aria-expanded", "true");
613        navIcon.attr("aria-label", "Fechar menu lateral");
614        setNavbarInteractiveTabIndex("-1");
615        setSideMenuLinksTabIndex(sideMenu, fallbackMode, true);
616
617        if (fallbackMode) {
618            const navHeight = document.getElementById("mainNav")?.offsetHeight || 64;
619            const sideMenuWidth = Math.min(window.innerWidth, 320);
620            const isDarkMode = document.body.dataset.colorMode === "dark"
621                || document.body.classList.contains("darkmode");
622
623            sidebar.css({
624                flexDirection: "column",
625                justifyContent: "flex-start",
626                alignItems: "stretch",
627                position: "fixed",
628                top: `${navHeight}px`,
629                bottom: "0",
630                left: `-${sideMenuWidth}px`,
631                width: `${sideMenuWidth}px`,
632                height: "auto",
633                minHeight: `calc(100dvh - ${navHeight}px)`,
634                padding: "16px",
635                overflowY: "auto",
636                background: isDarkMode ? "#000" : "#fff",
637                zIndex: "1060"
638            });
639        } else if (sideGroup) {
640            sideGroup.style.display = "block";
641        }
642
643        sidebar.removeClass("hide").addClass("show");
644
645        sidebar.stop(true, true).animate({ left: "0px" }, 300, function () {
646            const firstMenuItem = fallbackMode
647                ? sidebar.find(".nav-link:visible").first().get(0) || sidebar.find(".nav-link").first().get(0)
648                : document.querySelector(".side-group-item");
649            if (firstMenuItem) {
650                firstMenuItem.focus();
651            }
652        });
653
654        sidebarItems.forEach((item) => {
655            item.addEventListener('keydown', handleKeyDown);
656        });
657
658    }
659}
660
661// acessibility - close on ESC
662function closeMenuOnEsc(e) {
663    const sidebar = getSidebarContainer();
664    if (e.key === "Escape" && sidebar.length && sidebar.hasClass("show")) {
665        toggleSideMenu();
666        setInitialFocus();
667    }
668}
669
670document.addEventListener("keydown", function (e) {
671    if (e.key === "Escape") {
672        closeMenuOnEsc(e);
673    }
674});
675
676
677// accessibility - open on ENTER or SPACE
678function handleKeyDown(event) {
679    if (event.key === 'Enter' || event.key === ' ') {
680        event.preventDefault();
681        const navIcon = document.getElementById('nav-icon3');
682        navIcon.click();
683    } else if (event.key === 'Escape') {
684        closeMenuOnEsc(event);
685    }
686}
687
688// accessibility - arrow keys menu navigation
689function setupSideMenu() {
690    const sidebar = document.querySelector(".sidebar");
691    const sidebarItems = document.querySelectorAll(".side-group-item");
692    const navIcon = document.getElementById('nav-icon3');
693    const customMenu = document.getElementById('side-menu-a');
694    const firstSideItem = document.querySelector('.side-group-item')
695
696    if (!sidebar || !navIcon) {
697        return;
698    }
699
700    sidebar.addEventListener('keydown', function (event) {
701        if (event.key === 'ArrowDown' || event.key === 'ArrowUp') {
702            event.preventDefault();
703
704            let currentIndex = -1;
705            sidebarItems.forEach((item, index) => {
706                if (item === document.activeElement) {
707                    currentIndex = index;
708                }
709            });
710
711            let nextIndex;
712            if (event.key === 'ArrowDown') {
713                nextIndex = (currentIndex + 1) % sidebarItems.length;
714            } else if (event.key === 'ArrowUp') {
715                nextIndex = (currentIndex - 1 + sidebarItems.length) % sidebarItems.length;
716            }
717
718            sidebarItems[nextIndex].focus();
719        }
720    });
721
722    sidebar.addEventListener('focusout', function (event) {
723        if (!sidebar.contains(event.relatedTarget) && !event.relatedTarget.closest("#nav-icon3")) {
724            navIcon.focus();
725        }
726    });
727
728    if (customMenu) {
729        navIcon.addEventListener('keydown', (event) => {
730            const navIcon = document.getElementById('nav-icon3');
731            const firstSideItem = document.querySelector('.side-group.active');
732
733            if (document.activeElement === navIcon && event.key === 'Tab') {
734                if (firstSideItem) {
735                    firstSideItem.focus();
736                }
737            }
738        });
739
740        navIcon.addEventListener('keydown', function (event) {
741            if (event.key === 'Tab' && !event.shiftKey && customMenu) {
742                if (sidebar.classList.contains('show') && navIcon.querySelector('i').classList.contains('fa-times')) {
743                    firstSideItem.focus();
744                }
745            } else if (event.key === 'Tab' && !event.shiftKey && sidebar.classList.contains('show') && navIcon.querySelector('i').classList.contains('fa-times')) {
746                    event.preventDefault();
747                    //custom menu no sidebar
748                sidebarItems.focus();
749
750                navIcon.addEventListener('keydown', function (event) {
751                    if (event.key === 'Tab' && !event.shiftKey && sidebar.classList.contains('show')) {
752                        event.preventDefault();
753                        firstSideItem.focus();
754                    }
755                });
756                }
757        }
758        );
759    } else {
760        navIcon.addEventListener('keydown', function (event) {
761            if (sidebar.classList.contains('show') && navIcon.querySelector('i').classList.contains('fa-times')) {
762                event.preventDefault();
763                sidebarItems[0].focus();
764                firstSideItem.focus();
765            }
766            const firstMenuItem = document.querySelector(".side-group-item");
767                if (firstMenuItem) {
768                    firstMenuItem.focus();
769                }
770        });
771
772    }
773
774    setInitialFocus();
775}
776
777// accessibility - close on focus out
778function closeMenuOnFocusOut(event) {
779    const sidebar = document.querySelector(".sidebar");
780    const btnShowInput = document.getElementById("btnShowInput");
781    const linkLogo = document.getElementById("link-logo");
782    const dropdownNotificationsMenu = document.getElementById("dropdownNotificationsMenu");
783    const navbarDropdown = document.getElementById("navbarDropdown");
784    const sidebarItems = document.querySelectorAll(".side-group-item");
785    const sideGroup = document.querySelector(".side-group");
786
787    if (sidebar && !sidebar.contains(event.relatedTarget) && sidebar.classList.contains("show")) {
788        toggleSideMenu();
789        setInitialFocus();
790
791        if (btnShowInput) btnShowInput.setAttribute("tabindex", "0");
792        if (dropdownNotificationsMenu) dropdownNotificationsMenu.setAttribute("tabindex", "0");
793        if (linkLogo) linkLogo.setAttribute("tabindex", "0");
794        if (navbarDropdown) navbarDropdown.setAttribute("tabindex", "0");
795
796        sidebarItems.forEach(item => {
797            item.setAttribute("tabindex", "-1");
798        });
799
800        if (sideGroup) sideGroup.style.display = "none";
801    }
802}
803
804// accessibility - on load initial attributes
805document.addEventListener("DOMContentLoaded", function () {
806    setupSideMenuSubmenuAccordion();
807    setupSideMenu();
808    const navIcon = document.getElementById("nav-icon3");
809    const sidebarContainer = getSidebarContainer();
810    if (navIcon) {
811        navIcon.setAttribute("aria-expanded", "false");
812        if (sidebarContainer.length) {
813            let sidebarId = sidebarContainer.attr("id");
814            if (!sidebarId) {
815                sidebarId = "sidebar";
816                sidebarContainer.attr("id", sidebarId);
817            }
818            navIcon.setAttribute("aria-controls", sidebarId);
819        } else {
820            navIcon.setAttribute("aria-controls", "sidebar");
821        }
822    }
823
824    const sidebar = document.querySelector(".sidebar");
825    if (sidebar) {
826        sidebar.setAttribute("id", "sidebar");
827    }
828
829    const sidebarItems = document.querySelectorAll(".side-group-item");
830    sidebarItems.forEach(item => {
831        item.setAttribute("tabindex", "-1");
832    });
833
834    const sideGroup = document.querySelector(".side-group");
835    if (sideGroup) {
836        sideGroup.style.display = "none";
837    }
838
839    setInitialFocus();
840});
841
842document.addEventListener("click", function (event) {
843    const btnShowInput = document.getElementById("btnShowInput");
844    const linkLogo = document.getElementById("link-logo");
845    const dropdownNotificationsMenu = document.getElementById("dropdownNotificationsMenu");
846    const navbarDropdown = document.getElementById("navbarDropdown");
847    const sidebarItems = document.querySelectorAll(".side-group-item");
848    const sideGroup = document.querySelector(".side-group");
849
850    const sidebar = getSidebarContainer();
851    if (!sidebar.length) {
852        return;
853    }
854
855    const clickedInsideFallbackMenu = event.target.closest("#side-menu");
856    const clickedInsideDefaultSidebar = event.target.closest(".sidebar");
857    const clickedInMenu = clickedInsideFallbackMenu || clickedInsideDefaultSidebar;
858
859    if (!clickedInMenu && !event.target.closest("#nav-icon3") && sidebar.hasClass("show")) {
860        const menuWidth = sidebar.outerWidth() || Math.min(window.innerWidth, 320);
861        sidebar.stop(true, true).animate(
862            { left: -menuWidth },
863            300,
864            function () {
865                sidebar.removeClass("show").addClass("hide");
866                $("#nav-icon3").removeClass("open");
867                const icon = document.querySelector("#nav-icon3 > i");
868                if (icon) {
869                    icon.classList.replace("fa-times", "fa-bars");
870                }
871                $("#nav-icon3").attr("aria-label", "Abrir menu lateral");
872                $("#nav-icon3").attr("aria-expanded", "false");
873
874                if (btnShowInput) btnShowInput.setAttribute("tabindex", "0");
875                if (dropdownNotificationsMenu) dropdownNotificationsMenu.setAttribute("tabindex", "0");
876                if (linkLogo) linkLogo.setAttribute("tabindex", "0");
877                if (navbarDropdown) navbarDropdown.setAttribute("tabindex", "0");
878
879                sidebarItems.forEach(item => {
880                    item.setAttribute("tabindex", "-1");
881                });
882
883                if (sideGroup) sideGroup.style.display = "none";
884            }
885        );
886    }
887});
888
889function mostrarBarraPesquisa() {
890    if ($("#txtPesquisaPrincipal").hasClass("d-none")) {
891        $("#txtPesquisaPrincipal").removeClass("d-none");
892    } else {
893        $("#txtPesquisaPrincipal").addClass("d-none");
894
895        $("#formPesquisar").submit();
896    }
897}
898
899function findValueWhere(_array, _match, _needle) {
900    for (var i = 0; i < _array.length; i++) {
901        if (_array[i][_match] == _needle) {
902            return _array[i];
903        }
904    }
905}
906
907function showCodigoAula() {
908    if (!$(".sidebar").hasClass("show")) {
909        toggleSideMenu();
910    }
911
912    $(".sidebar #lblInserirCodigoAula").addClass("d-none");
913
914    $(".sidebar #formInserirCodigoAula").removeClass("d-none");
915
916    $(".sidebar [name='codigo']").focus();
917}
918
919function updateSelectPicker() {
920    $(".selectpicker").selectpicker("refresh");
921}
922
923/**
924 * Redireciona o usuário com parâmetros da URL
925 *
926 * Exemplo: { pesquisa: 'valor a ser pesquisado' }
927 * Resultado: Troca a URL e adiciona ou troca 'pesquisa' dos parâmetros da query
928 *
929 * @param Object
930 * @return Redirect
931 */
932function reloadWithQueryStringVars(queryStringVars) {
933    var existingQueryVars = location.search
934            ? location.search.substring(1).split("&")
935            : [],
936        currentUrl = location.search
937            ? location.href.replace(location.search, "")
938            : location.href,
939        newQueryVars = {},
940        newUrl = currentUrl + "?";
941    if (existingQueryVars.length > 0) {
942        for (var i = 0; i < existingQueryVars.length; i++) {
943            var pair = existingQueryVars[i].split("=");
944            newQueryVars[pair[0]] = pair[1];
945        }
946    }
947    if (queryStringVars) {
948        for (var queryStringVar in queryStringVars) {
949            newQueryVars[queryStringVar] = queryStringVars[queryStringVar];
950        }
951    }
952    if (newQueryVars) {
953        for (var newQueryVar in newQueryVars) {
954            newUrl += newQueryVar + "=" + newQueryVars[newQueryVar] + "&";
955        }
956        newUrl = newUrl.substring(0, newUrl.length - 1);
957        window.location.href = newUrl;
958    } else {
959        window.location.href = location.href;
960    }
961}
962
963/**
964 * Carrega todos os ciclos do sistema.
965 *
966 * @param $target Elemento (select) a ser preenchido. Ex: #selectInput
967 *
968 * @return UI_Update
969 */
970function loadCiclo($target) {
971    $.get("/v2/domains/list?type=ciclo", function (response) {
972        var defaultValue = $($target).attr("default-value");
973        var callback = $($target).attr("callback");
974
975        if (defaultValue) {
976            loadCicloEtapa('[data-api-list="ciclo_etapas"]', defaultValue);
977        }
978
979        $($target)
980            .unbind()
981            .on("change", function () {
982                var ciclosParams = [];
983
984                $(this)
985                    .find("option:selected")
986                    .each(function (i, e) {
987                        ciclosParams.push(e.value);
988                    });
989
990                loadCicloEtapa(
991                    '[data-api-list="ciclo_etapas"]',
992                    ciclosParams.join(",")
993                );
994                loadDisciplina('[data-api-list="disciplinas"]', "");
995            });
996
997        return updateList($target, response.data);
998    });
999}
1000
1001/**
1002 * Carrega todos os ciclo_etapas do sistema.
1003 *
1004 * @param $target Elemento (select) a ser preenchido. Ex: #selectInput
1005 * @param $ciclo_id ID do ciclo a ser buscado (opcional)
1006 *
1007 * @return UI_Update
1008 */
1009function loadCicloEtapa($target, $ciclo_id) {
1010    var url = "/v2/domains/list?type=ciclo_etapa";
1011
1012    if (typeof $ciclo_id !== "undefined") {
1013        url += "&ciclo_id=" + $ciclo_id;
1014    }
1015
1016    $.get(url, function (response) {
1017        var defaultValue = $($target).attr("default-value");
1018
1019        if (defaultValue) {
1020            loadDisciplina('[data-api-list="disciplinas"]', defaultValue);
1021        }
1022
1023        $($target)
1024            .unbind()
1025            .on("change", function () {
1026                var cicloEtapasParams = [];
1027
1028                $(this)
1029                    .find("option:selected")
1030                    .each(function (i, e) {
1031                        cicloEtapasParams.push(e.value);
1032                    });
1033
1034                loadDisciplina(
1035                    '[data-api-list="disciplinas"]',
1036                    cicloEtapasParams.join(",")
1037                );
1038            });
1039
1040        return updateList($target, response.data);
1041    });
1042}
1043
1044/**
1045 * Carrega todas as disciplinas do sistema.
1046 *
1047 * @param $target Elemento (select) a ser preenchido. Ex: #selectInput
1048 * @param $ciclo_etapa_id ID do ciclo_etapa a ser buscado (opcional)
1049 *
1050 * @return UI_Update
1051 */
1052function loadDisciplina($target, $ciclo_etapa_id) {
1053    var url = "/v2/domains/list?type=disciplinas";
1054
1055    if (typeof $ciclo_etapa_id !== "undefined") {
1056        url += "&ciclo_etapa_id=" + $ciclo_etapa_id;
1057    }
1058
1059    $.get(url, function (response) {
1060        return updateList($target, response.data);
1061    });
1062}
1063
1064/**
1065 * Atualiza a lista de um elemento com os títulos do array
1066 * recebido.
1067 *
1068 * @param target Elemento (select) a ser preenchido. Ex: #selectInput
1069 * @param list Array com a lista (os elementos do array devem possuir titulo)
1070 * @param defaultOption Ao atualizar a lista isso indica se deve haver um valor padrão ou não
1071 *
1072 * @return UI_Update
1073 */
1074function updateList(target, $list) {
1075    var $value = $(target).attr("default-value");
1076
1077    if (!$(target).hasClass("selectpicker")) {
1078        $(target).html(
1079            `<option value="" selected="true" disabled="disabled">Selecione</option>`
1080        );
1081    } else {
1082        $(target).html(``);
1083    }
1084
1085    if ($list && $list.length) {
1086        $list.forEach(function (item) {
1087            $(target).append(
1088                `<option value="${item.id}">${item.titulo}</option>`
1089            );
1090        });
1091    }
1092
1093    if ($value) {
1094        var selectedValues = String($value).indexOf(",") !== -1
1095            ? String($value).split(",").filter(Boolean)
1096            : $value;
1097        $(target).val(selectedValues);
1098    }
1099
1100    $(".selectpicker").selectpicker("refresh");
1101}
1102
1103function changeCicloEscola() {
1104    // $("[name='cicloetapa[]']").prop('disabled', false);
1105    // $("[name='disciplina[]']").prop('disabled', true);
1106    // $("[name='disciplina[]']").val('');
1107}
1108
1109function changeCicloEtapaEscola() {
1110    // $("[name='disciplina[]']").prop('disabled', false);
1111}
1112
1113/**
1114 *
1115 */
1116function setPredefinedOptions() {
1117    $(
1118        '[data-api-list="etapas"], [data-api-list="ciclo_etapas"], [data-api-list="disciplinas"]'
1119    ).each(function (item, el) {
1120        $(el).html(`<option value="" selected="true" disabled="disabled"> ${i18n.select} </option>`);
1121        $(el).selectpicker({
1122            selectAllText: i18n.selectAll,
1123            deselectAllText: i18n.deselectAll,
1124            noneSelectedText: i18n.nothingSelected,
1125        });
1126    });
1127}
1128
1129$(function () {
1130    loadCiclo('[data-api-list="etapas"]');
1131    setPredefinedOptions();
1132
1133    // loadDisciplina('[data-api-list="disciplinas"]');
1134
1135    /**
1136     * Dropdown Toolz
1137     */
1138    $(".dropdown-tz").on("click", function () {
1139        $(".dropdown-list-tz").removeClass("show");
1140        $(this).find(".dropdown-list-tz").addClass("show");
1141    });
1142
1143    $(document).on("click", function (e) {
1144        if (!$(e.target).closest(".dropdown-tz, .dropdown-list-tz").length) {
1145            $(".dropdown-list-tz").removeClass("show");
1146        }
1147    });
1148});
1149
1150function loadListApiParam(target, api) {
1151    const url = api;
1152
1153    $.get(url, function (result) {
1154        if (result) {
1155            result.data.forEach(function (item, index) {
1156                let combo = target;
1157                let opt = document.createElement("option");
1158                opt.value = item.id;
1159                opt.text = item.title;
1160                //  == undefined ? opt.text = item.title : opt.text = item.titulo;
1161                console.warn(opt.text);
1162                combo.add(opt, combo.options[index]);
1163            });
1164        } else {
1165            $($target).append(
1166                `<option value=''>Nenhum registro encontrado</option>`
1167            );
1168        }
1169    });
1170}

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.