Proyectos de Subversion Moodle

Rev

Rev 1 | Autoría | Comparar con el anterior | Ultima modificación | Ver Log |

{"version":3,"file":"dynamic.min.js","sources":["../src/dynamic.js"],"sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle.  If not, see <http://www.gnu.org/licenses/>.\n\n/**\n * Module to handle dynamic table features.\n *\n * @module     core_table/dynamic\n * @copyright  2020 Simey Lameze <simey@moodle.com>\n * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport * as Selectors from 'core_table/local/dynamic/selectors';\nimport Events from './local/dynamic/events';\nimport Pending from 'core/pending';\nimport {addIconToContainer} from 'core/loadingicon';\nimport {fetch as fetchTableData} from 'core_table/local/dynamic/repository';\nimport Notification from 'core/notification';\nimport {replaceNode} from 'core/templates';\n\nlet watching = false;\n\n/**\n * Ensure that a table is a dynamic table.\n *\n * @param {HTMLElement} tableRoot\n * @returns {Bool}\n */\nconst checkTableIsDynamic = tableRoot => {\n    if (!tableRoot) {\n        // The table is not a dynamic table.\n        throw new Error(\"The table specified is not a dynamic table and cannot be updated\");\n    }\n\n    if (!tableRoot.matches(Selectors.main.region)) {\n        // The table is not a dynamic table.\n        throw new Error(\"The table specified is not a dynamic table and cannot be updated\");\n    }\n\n    return true;\n};\n\n/**\n * Get the filterset data from a known dynamic table.\n *\n * @param {HTMLElement} tableRoot\n * @returns {Object}\n */\nconst getFiltersetFromTable = tableRoot => {\n    return JSON.parse(tableRoot.dataset.tableFilters);\n};\n\n/**\n * Update the specified table based on its current values.\n *\n * @param {HTMLElement} tableRoot\n * @param {Bool} resetContent\n * @returns {Promise}\n */\nexport const refreshTableContent = (tableRoot, resetContent = false) => {\n    const filterset = getFiltersetFromTable(tableRoot);\n    addIconToContainer(tableRoot);\n\n    const pendingPromise = new Pending('core_table/dynamic:refreshTableContent');\n\n    return fetchTableData(\n        tableRoot.dataset.tableComponent,\n        tableRoot.dataset.tableHandler,\n        tableRoot.dataset.tableUniqueid,\n        {\n            sortData: JSON.parse(tableRoot.dataset.tableSortData),\n            joinType: filterset.jointype,\n            filters: filterset.filters,\n            firstinitial: tableRoot.dataset.tableFirstInitial,\n            lastinitial: tableRoot.dataset.tableLastInitial,\n            pageNumber: tableRoot.dataset.tablePageNumber,\n            pageSize: tableRoot.dataset.tablePageSize,\n            hiddenColumns: JSON.parse(tableRoot.dataset.tableHiddenColumns),\n        },\n        resetContent,\n    )\n    .then(data => {\n        const tableRootReplacement = replaceNode(tableRoot, data.html, '');\n\n        // Update the tableRoot.\n        return tableRootReplacement[0];\n    }).then(tableRoot => {\n        tableRoot.dispatchEvent(new CustomEvent(Events.tableContentRefreshed, {\n            bubbles: true,\n        }));\n\n        return tableRoot;\n    })\n    .then(tableRoot => {\n        pendingPromise.resolve();\n\n        return tableRoot;\n    });\n};\n\nexport const updateTable = (tableRoot, {\n    sortBy = null,\n    sortOrder = null,\n    filters = null,\n    firstInitial = null,\n    lastInitial = null,\n    pageNumber = null,\n    pageSize = null,\n    hiddenColumns = null,\n} = {}, refreshContent = true) => {\n    checkTableIsDynamic(tableRoot);\n\n    const pendingPromise = new Pending('core_table/dynamic:updateTable');\n    let tableConfigChanged = false;\n\n    // Update sort fields.\n    if (sortBy && sortOrder) {\n        // Always update the table if requested and there were sort fields.\n        // These fields are only ever normalised in the backend.\n        tableConfigChanged = true;\n\n        const sortData = JSON.parse(tableRoot.dataset.tableSortData);\n        sortData.unshift({\n            sortby: sortBy,\n            sortorder: parseInt(sortOrder, 10),\n        });\n        tableRoot.dataset.tableSortData = JSON.stringify(sortData);\n    }\n\n    // Update initials.\n    if (firstInitial !== null) {\n        if (tableRoot.dataset.tableFirstInitial !== firstInitial) {\n            tableConfigChanged = true;\n        }\n\n        tableRoot.dataset.tableFirstInitial = firstInitial;\n    }\n\n    if (lastInitial !== null) {\n        if (tableRoot.dataset.tableLastInitial !== lastInitial) {\n            tableConfigChanged = true;\n        }\n\n        tableRoot.dataset.tableLastInitial = lastInitial;\n    }\n\n    if (pageSize !== null) {\n        if (tableRoot.dataset.tablePageSize != pageSize) {\n            tableConfigChanged = true;\n        }\n\n        tableRoot.dataset.tablePageSize = pageSize;\n    }\n\n    // Update filters.\n    if (filters) {\n        const filterJson = JSON.stringify(filters);\n\n        if (tableRoot.dataset.tableFilters !== filterJson) {\n            tableConfigChanged = true;\n        }\n\n        tableRoot.dataset.tableFilters = filterJson;\n    }\n\n    // Reset to page 1 when table content is being altered by filtering or sorting.\n    // This ensures the table page being loaded always exists, and gives a consistent experience.\n    if (tableConfigChanged) {\n        pageNumber = 1;\n    }\n\n    // Update hidden columns.\n    if (hiddenColumns) {\n        const columnJson = JSON.stringify(hiddenColumns);\n\n        if (tableRoot.dataset.tableHiddenColumns !== columnJson) {\n            tableConfigChanged = true;\n        }\n\n        tableRoot.dataset.tableHiddenColumns = columnJson;\n    }\n\n    if (pageNumber !== null) {\n        if (tableRoot.dataset.tablePageNumber != pageNumber) {\n            tableConfigChanged = true;\n        }\n\n        tableRoot.dataset.tablePageNumber = pageNumber;\n    }\n\n    // Refresh.\n    if (refreshContent && tableConfigChanged) {\n        return refreshTableContent(tableRoot)\n        .then(tableRoot => {\n            pendingPromise.resolve();\n            return tableRoot;\n        });\n    } else {\n        pendingPromise.resolve();\n        return Promise.resolve(tableRoot);\n    }\n};\n\n/**\n * Get the table dataset for the specified tableRoot, ensuring that the provided table is a dynamic table.\n *\n * @param {HTMLElement} tableRoot\n * @returns {DOMStringMap}\n */\nconst getTableData = tableRoot => {\n    checkTableIsDynamic(tableRoot);\n\n    return tableRoot.dataset;\n};\n\n/**\n * Update the specified table using the new filters.\n *\n * @param {HTMLElement} tableRoot\n * @param {Object} filters\n * @param {Bool} refreshContent\n * @returns {Promise}\n */\nexport const setFilters = (tableRoot, filters, refreshContent = true) =>\n    updateTable(tableRoot, {filters}, refreshContent);\n\n/**\n * Get the filter data for the specified table.\n *\n * @param {HTMLElement} tableRoot\n * @returns {Object}\n */\nexport const getFilters = tableRoot => {\n    checkTableIsDynamic(tableRoot);\n\n    return getFiltersetFromTable(tableRoot);\n};\n\n/**\n * Update the sort order.\n *\n * @param {HTMLElement} tableRoot\n * @param {String} sortBy\n * @param {Number} sortOrder\n * @param {Bool} refreshContent\n * @returns {Promise}\n */\nexport const setSortOrder = (tableRoot, sortBy, sortOrder, refreshContent = true) =>\n    updateTable(tableRoot, {sortBy, sortOrder}, refreshContent);\n\n/**\n * Set the page number.\n *\n * @param {HTMLElement} tableRoot\n * @param {String} pageNumber\n * @param {Bool} refreshContent\n * @returns {Promise}\n */\nexport const setPageNumber = (tableRoot, pageNumber, refreshContent = true) =>\n    updateTable(tableRoot, {pageNumber}, refreshContent);\n\n/**\n * Get the current page number.\n *\n * @param {HTMLElement} tableRoot\n * @returns {Number}\n */\nexport const getPageNumber = tableRoot => getTableData(tableRoot).tablePageNumber;\n\n/**\n * Set the page size.\n *\n * @param {HTMLElement} tableRoot\n * @param {Number} pageSize\n * @param {Bool} refreshContent\n * @returns {Promise}\n */\nexport const setPageSize = (tableRoot, pageSize, refreshContent = true) =>\n    updateTable(tableRoot, {pageSize, pageNumber: 1}, refreshContent);\n\n/**\n * Get the current page size.\n *\n * @param {HTMLElement} tableRoot\n * @returns {Number}\n */\nexport const getPageSize = tableRoot => getTableData(tableRoot).tablePageSize;\n\n/**\n * Update the first initial to show.\n *\n * @param {HTMLElement} tableRoot\n * @param {String} firstInitial\n * @param {Bool} refreshContent\n * @returns {Promise}\n */\nexport const setFirstInitial = (tableRoot, firstInitial, refreshContent = true) =>\n    updateTable(tableRoot, {firstInitial}, refreshContent);\n\n/**\n * Get the current first initial filter.\n *\n * @param {HTMLElement} tableRoot\n * @returns {String}\n */\nexport const getFirstInitial = tableRoot => getTableData(tableRoot).tableFirstInitial;\n\n/**\n * Update the last initial to show.\n *\n * @param {HTMLElement} tableRoot\n * @param {String} lastInitial\n * @param {Bool} refreshContent\n * @returns {Promise}\n */\nexport const setLastInitial = (tableRoot, lastInitial, refreshContent = true) =>\n    updateTable(tableRoot, {lastInitial}, refreshContent);\n\n/**\n * Get the current last initial filter.\n *\n * @param {HTMLElement} tableRoot\n * @returns {String}\n */\nexport const getLastInitial = tableRoot => getTableData(tableRoot).tableLastInitial;\n\n/**\n * Hide a column in the participants table.\n *\n * @param {HTMLElement} tableRoot\n * @param {String} columnToHide\n * @param {Bool} refreshContent\n * @returns {Promise}\n */\nexport const hideColumn = (tableRoot, columnToHide, refreshContent = true) => {\n    const hiddenColumns = JSON.parse(tableRoot.dataset.tableHiddenColumns);\n    hiddenColumns.push(columnToHide);\n\n    return updateTable(tableRoot, {hiddenColumns}, refreshContent);\n};\n\n/**\n * Make a hidden column visible in the participants table.\n *\n * @param {HTMLElement} tableRoot\n * @param {String} columnToShow\n * @param {Bool} refreshContent\n * @returns {Promise}\n */\nexport const showColumn = (tableRoot, columnToShow, refreshContent = true) => {\n    let hiddenColumns = JSON.parse(tableRoot.dataset.tableHiddenColumns);\n    hiddenColumns = hiddenColumns.filter(columnName => columnName !== columnToShow);\n\n    return updateTable(tableRoot, {hiddenColumns}, refreshContent);\n};\n\n/**\n * Reset table preferences.\n *\n * @param {HTMLElement} tableRoot\n * @returns {Promise}\n */\nconst resetTablePreferences = tableRoot => refreshTableContent(tableRoot, true);\n\n/**\n * Set up listeners to handle table updates.\n */\nexport const init = () => {\n    if (watching) {\n        // Already watching.\n        return;\n    }\n    watching = true;\n\n    document.addEventListener('click', e => {\n        const tableRoot = e.target.closest(Selectors.main.region);\n\n        if (!tableRoot) {\n            return;\n        }\n\n        const sortableLink = e.target.closest(Selectors.table.links.sortableColumn);\n        if (sortableLink) {\n            e.preventDefault();\n\n            setSortOrder(tableRoot, sortableLink.dataset.sortby, sortableLink.dataset.sortorder)\n            .catch(Notification.exception);\n        }\n\n        const firstInitialLink = e.target.closest(Selectors.initialsBar.links.firstInitial);\n        if (firstInitialLink !== null) {\n            e.preventDefault();\n\n            setFirstInitial(tableRoot, firstInitialLink.dataset.initial).catch(Notification.exception);\n        }\n\n        const lastInitialLink = e.target.closest(Selectors.initialsBar.links.lastInitial);\n        if (lastInitialLink !== null) {\n            e.preventDefault();\n\n            setLastInitial(tableRoot, lastInitialLink.dataset.initial).catch(Notification.exception);\n        }\n\n        const pageItem = e.target.closest(Selectors.paginationBar.links.pageItem);\n        if (pageItem) {\n            e.preventDefault();\n\n            setPageNumber(tableRoot, pageItem.dataset.pageNumber).catch(Notification.exception);\n        }\n\n        const hide = e.target.closest(Selectors.table.links.hide);\n        if (hide) {\n            e.preventDefault();\n\n            hideColumn(tableRoot, hide.dataset.column).catch(Notification.exception);\n        }\n\n        const show = e.target.closest(Selectors.table.links.show);\n        if (show) {\n            e.preventDefault();\n\n            showColumn(tableRoot, show.dataset.column).catch(Notification.exception);\n        }\n\n        const resetTablePreferencesLink = e.target.closest('.resettable a');\n        if (resetTablePreferencesLink) {\n            e.preventDefault();\n\n            resetTablePreferences(tableRoot).catch(Notification.exception);\n        }\n\n        const showCountLink = e.target.closest(Selectors.showCount.links.toggle);\n        if (showCountLink) {\n            e.preventDefault();\n\n            setPageSize(tableRoot, showCountLink.dataset.targetPageSize).catch(Notification.exception);\n        }\n    });\n};\n\n/**\n * Fetch the table via its table region id.\n *\n * @param {String} tableRegionId\n * @returns {HTMLElement}\n */\nexport const getTableFromId = tableRegionId => {\n    const tableRoot = document.querySelector(Selectors.main.fromRegionId(tableRegionId));\n\n\n    if (!tableRoot) {\n        // The table is not a dynamic table.\n        throw new Error(\"The table specified is not a dynamic table and cannot be updated\");\n    }\n\n    return tableRoot;\n};\n\nexport {\n    Events\n};\n"],"names":["watching","checkTableIsDynamic","tableRoot","Error","matches","Selectors","main","region","getFiltersetFromTable","JSON","parse","dataset","tableFilters","refreshTableContent","resetContent","filterset","pendingPromise","Pending","tableComponent","tableHandler","tableUniqueid","sortData","tableSortData","joinType","jointype","filters","firstinitial","tableFirstInitial","lastinitial","tableLastInitial","pageNumber","tablePageNumber","pageSize","tablePageSize","hiddenColumns","tableHiddenColumns","then","data","html","dispatchEvent","CustomEvent","Events","tableContentRefreshed","bubbles","resolve","updateTable","sortBy","sortOrder","firstInitial","lastInitial","refreshContent","tableConfigChanged","unshift","sortby","sortorder","parseInt","stringify","filterJson","columnJson","Promise","getTableData","setSortOrder","setPageNumber","setPageSize","setFirstInitial","setLastInitial","hideColumn","columnToHide","push","showColumn","columnToShow","filter","columnName","document","addEventListener","e","target","closest","sortableLink","table","links","sortableColumn","preventDefault","catch","Notification","exception","firstInitialLink","initialsBar","initial","lastInitialLink","pageItem","paginationBar","hide","column","show","resetTablePreferences","showCountLink","showCount","toggle","targetPageSize","tableRegionId","querySelector","fromRegionId"],"mappings":"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"}