diff --git a/amd/build/linkmodal.min.js b/amd/build/linkmodal.min.js index b6beaf1c..754b3e5e 100644 --- a/amd/build/linkmodal.min.js +++ b/amd/build/linkmodal.min.js @@ -1,10 +1,10 @@ -define("mod_learningmap/linkmodal",["exports","core/modal","core/ajax","core_course/manual_completion_toggle","mod_learningmap/renderer","core_course/events"],(function(_exports,_modal,_ajax,manualcompletion,_renderer,_events){function _getRequireWildcardCache(nodeInterop){if("function"!=typeof WeakMap)return null;var cacheBabelInterop=new WeakMap,cacheNodeInterop=new WeakMap;return(_getRequireWildcardCache=function(nodeInterop){return nodeInterop?cacheNodeInterop:cacheBabelInterop})(nodeInterop)}function _interopRequireDefault(obj){return obj&&obj.__esModule?obj:{default:obj}} +define("mod_learningmap/linkmodal",["exports","core/modal","core/modal_events","core/ajax","core/templates","core_course/manual_completion_toggle","mod_learningmap/renderer","core_course/events"],(function(_exports,_modal,_modal_events,_ajax,_templates,manualcompletion,_renderer,_events){function _getRequireWildcardCache(nodeInterop){if("function"!=typeof WeakMap)return null;var cacheBabelInterop=new WeakMap,cacheNodeInterop=new WeakMap;return(_getRequireWildcardCache=function(nodeInterop){return nodeInterop?cacheNodeInterop:cacheBabelInterop})(nodeInterop)}function _interopRequireDefault(obj){return obj&&obj.__esModule?obj:{default:obj}} /** * Helper for opening course modules in a modal that do not have a view page. * * @module mod_learningmap/linkmodal * @copyright 2025 ISB Bayern * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later - */Object.defineProperty(_exports,"__esModule",{value:!0}),_exports.openModal=_exports.init=void 0,_modal=_interopRequireDefault(_modal),_ajax=_interopRequireDefault(_ajax),manualcompletion=function(obj,nodeInterop){if(!nodeInterop&&obj&&obj.__esModule)return obj;if(null===obj||"object"!=typeof obj&&"function"!=typeof obj)return{default:obj};var cache=_getRequireWildcardCache(nodeInterop);if(cache&&cache.has(obj))return cache.get(obj);var newObj={},hasPropertyDescriptor=Object.defineProperty&&Object.getOwnPropertyDescriptor;for(var key in obj)if("default"!==key&&Object.prototype.hasOwnProperty.call(obj,key)){var desc=hasPropertyDescriptor?Object.getOwnPropertyDescriptor(obj,key):null;desc&&(desc.get||desc.set)?Object.defineProperty(newObj,key,desc):newObj[key]=obj[key]}newObj.default=obj,cache&&cache.set(obj,newObj);return newObj}(manualcompletion),_events=_interopRequireDefault(_events);_exports.init=async function(learningmapcmid){let inmodal=arguments.length>1&&void 0!==arguments[1]&&arguments[1];const container=document.getElementById("learningmap-render-container-"+learningmapcmid+(inmodal?"-modal":""));container&&(container.addEventListener("click",(async event=>{const target=event.target.closest("a[data-cmid]");if(target&&!target.hasAttribute("xlink:href")){event.preventDefault();target.getAttribute("data-cmid")&&await openModal(event,learningmapcmid,inmodal)}})),container.addEventListener("keydown",(async event=>{if("Enter"===event.key){const target=event.target.closest("a[data-cmid]");if(target&&!target.hasAttribute("xlink:href")){event.preventDefault();target.getAttribute("data-cmid")&&await openModal(event,learningmapcmid,inmodal)}}})))};const openModal=async(event,learningmapcmid,inmodal)=>{const target=event.target.closest("a[data-cmid]");if(target&&!target.hasAttribute("xlink:href")){event.preventDefault();const cmid=target.getAttribute("data-cmid");if(cmid){const data=await _ajax.default.call([{methodname:"mod_learningmap_get_cm",args:{cmid:cmid}}])[0],container=document.createElement("div");container.innerHTML=data.js;let js=Array.from(container.querySelectorAll("script")).map((s=>s.textContent||"")).join("\n");const modal=await _modal.default.create({title:data.name,body:data.completion+data.html,show:!1,removeOnClose:!0,large:!0});modal.bodyJS=js,modal.show(),manualcompletion.init(),document.addEventListener(_events.default.manualCompletionToggled,(()=>{(0,_renderer.renderLearningmap)(learningmapcmid,inmodal)}))}}};_exports.openModal=openModal})); + */Object.defineProperty(_exports,"__esModule",{value:!0}),_exports.openModal=_exports.init=void 0,_modal=_interopRequireDefault(_modal),_modal_events=_interopRequireDefault(_modal_events),_ajax=_interopRequireDefault(_ajax),_templates=_interopRequireDefault(_templates),manualcompletion=function(obj,nodeInterop){if(!nodeInterop&&obj&&obj.__esModule)return obj;if(null===obj||"object"!=typeof obj&&"function"!=typeof obj)return{default:obj};var cache=_getRequireWildcardCache(nodeInterop);if(cache&&cache.has(obj))return cache.get(obj);var newObj={},hasPropertyDescriptor=Object.defineProperty&&Object.getOwnPropertyDescriptor;for(var key in obj)if("default"!==key&&Object.prototype.hasOwnProperty.call(obj,key)){var desc=hasPropertyDescriptor?Object.getOwnPropertyDescriptor(obj,key):null;desc&&(desc.get||desc.set)?Object.defineProperty(newObj,key,desc):newObj[key]=obj[key]}newObj.default=obj,cache&&cache.set(obj,newObj);return newObj}(manualcompletion),_events=_interopRequireDefault(_events);_exports.init=async function(learningmapcmid){let inmodal=arguments.length>1&&void 0!==arguments[1]&&arguments[1];const container=document.getElementById("learningmap-render-container-"+learningmapcmid+(inmodal?"-modal":""));container&&(container.addEventListener("click",(async event=>{const target=event.target.closest("a[data-cmid]");if(target&&!target.hasAttribute("xlink:href")){event.preventDefault();target.getAttribute("data-cmid")&&await openModal(event,learningmapcmid,inmodal)}})),container.addEventListener("keydown",(async event=>{if("Enter"===event.key){const target=event.target.closest("a[data-cmid]");if(target&&!target.hasAttribute("xlink:href")){event.preventDefault();target.getAttribute("data-cmid")&&await openModal(event,learningmapcmid,inmodal)}}})))};const openModal=async(event,learningmapcmid,inmodal)=>{const target=event.target.closest("a[data-cmid]");if(target&&!target.hasAttribute("xlink:href")){event.preventDefault();const cmid=target.getAttribute("data-cmid");if(cmid){const data=await _ajax.default.call([{methodname:"mod_learningmap_get_cm",args:{cmid:cmid}}])[0],container=document.createElement("div");container.innerHTML=data.js;let js=Array.from(container.querySelectorAll("script")).map((s=>s.textContent||"")).join("\n");const modalbody=await _templates.default.renderForPromise("mod_learningmap/modal_body",{completion:data.completion,content:data.html}),modal=await _modal.default.create({title:data.name,body:modalbody.html,show:!1,removeOnClose:!0,large:!0});modal.bodyJS=js,modal.show(),manualcompletion.init();const completionToggleHandler=()=>{(0,_renderer.renderLearningmap)(learningmapcmid,inmodal)};document.addEventListener(_events.default.manualCompletionToggled,completionToggleHandler),modal.getRoot().on(_modal_events.default.hidden,(()=>{document.removeEventListener(_events.default.manualCompletionToggled,completionToggleHandler)}))}}};_exports.openModal=openModal})); //# sourceMappingURL=linkmodal.min.js.map \ No newline at end of file diff --git a/amd/build/linkmodal.min.js.map b/amd/build/linkmodal.min.js.map index 87d14af9..650cd185 100644 --- a/amd/build/linkmodal.min.js.map +++ b/amd/build/linkmodal.min.js.map @@ -1 +1 @@ -{"version":3,"file":"linkmodal.min.js","sources":["../src/linkmodal.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 .\n\nimport Modal from 'core/modal';\nimport Ajax from 'core/ajax';\nimport * as manualcompletion from 'core_course/manual_completion_toggle';\nimport {renderLearningmap} from 'mod_learningmap/renderer';\nimport CourseEvents from 'core_course/events';\n\n/**\n * Helper for opening course modules in a modal that do not have a view page.\n *\n * @module mod_learningmap/linkmodal\n * @copyright 2025 ISB Bayern\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\n\n/**\n * Initialize the link modal listener for a learning map.\n *\n * @param {number} learningmapcmid - The course module ID of the learning map.\n * @param {boolean} inmodal - Whether the learning map is already in a modal.\n */\nexport const init = async(learningmapcmid, inmodal = false) => {\n const container = document.getElementById('learningmap-render-container-' + learningmapcmid + (inmodal ? '-modal' : ''));\n if (container) {\n container.addEventListener('click', async(event) => {\n const target = event.target.closest('a[data-cmid]');\n if (target && !target.hasAttribute('xlink:href')) {\n event.preventDefault();\n const cmid = target.getAttribute('data-cmid');\n if (cmid) {\n await openModal(event, learningmapcmid, inmodal);\n }\n }\n });\n container.addEventListener('keydown', async(event) => {\n if (event.key === 'Enter') {\n const target = event.target.closest('a[data-cmid]');\n if (target && !target.hasAttribute('xlink:href')) {\n event.preventDefault();\n const cmid = target.getAttribute('data-cmid');\n if (cmid) {\n await openModal(event, learningmapcmid, inmodal);\n }\n }\n }\n });\n }\n};\n\n/**\n * Opens a modal for a course module link that does not have a view page.\n * @param {Event} event - The click or keydown event.\n * @param {number} learningmapcmid - The course module ID of the learning map.\n * @param {boolean} inmodal - Whether the learning map is already in a modal.\n */\nexport const openModal = async(event, learningmapcmid, inmodal) => {\n const target = event.target.closest('a[data-cmid]');\n if (target && !target.hasAttribute('xlink:href')) {\n event.preventDefault();\n const cmid = target.getAttribute('data-cmid');\n if (cmid) {\n const data = await Ajax.call([{\n methodname: 'mod_learningmap_get_cm',\n args: {\n cmid: cmid\n },\n }])[0];\n const container = document.createElement('div');\n container.innerHTML = data.js;\n let js = Array.from(container.querySelectorAll('script'))\n .map(s => s.textContent || '')\n .join('\\n');\n const modal = await Modal.create({\n title: data.name,\n body: data.completion + data.html,\n show: false,\n removeOnClose: true,\n large: true,\n });\n modal.bodyJS = js;\n modal.show();\n manualcompletion.init();\n document.addEventListener(CourseEvents.manualCompletionToggled, () => {\n renderLearningmap(learningmapcmid, inmodal);\n });\n }\n }\n};\n"],"names":["async","learningmapcmid","inmodal","container","document","getElementById","addEventListener","target","event","closest","hasAttribute","preventDefault","getAttribute","openModal","key","cmid","data","Ajax","call","methodname","args","createElement","innerHTML","js","Array","from","querySelectorAll","map","s","textContent","join","modal","Modal","create","title","name","body","completion","html","show","removeOnClose","large","bodyJS","manualcompletion","init","CourseEvents","manualCompletionToggled"],"mappings":";;;;;;;q5BAmCoBA,eAAMC,qBAAiBC,sEACjCC,UAAYC,SAASC,eAAe,gCAAkCJ,iBAAmBC,QAAU,SAAW,KAChHC,YACAA,UAAUG,iBAAiB,SAASN,MAAAA,cAC1BO,OAASC,MAAMD,OAAOE,QAAQ,mBAChCF,SAAWA,OAAOG,aAAa,cAAe,CAC9CF,MAAMG,iBACOJ,OAAOK,aAAa,oBAEvBC,UAAUL,MAAOP,gBAAiBC,aAIpDC,UAAUG,iBAAiB,WAAWN,MAAAA,WAChB,UAAdQ,MAAMM,IAAiB,OACjBP,OAASC,MAAMD,OAAOE,QAAQ,mBAChCF,SAAWA,OAAOG,aAAa,cAAe,CAC9CF,MAAMG,iBACOJ,OAAOK,aAAa,oBAEvBC,UAAUL,MAAOP,gBAAiBC,sBAcnDW,UAAYb,MAAMQ,MAAOP,gBAAiBC,iBAC7CK,OAASC,MAAMD,OAAOE,QAAQ,mBAChCF,SAAWA,OAAOG,aAAa,cAAe,CAC9CF,MAAMG,uBACAI,KAAOR,OAAOK,aAAa,gBAC7BG,KAAM,OACAC,WAAaC,cAAKC,KAAK,CAAC,CAC1BC,WAAY,yBACZC,KAAM,CACFL,KAAMA,SAEV,GACEZ,UAAYC,SAASiB,cAAc,OACzClB,UAAUmB,UAAYN,KAAKO,OACvBA,GAAKC,MAAMC,KAAKtB,UAAUuB,iBAAiB,WAC1CC,KAAIC,GAAKA,EAAEC,aAAe,KAC1BC,KAAK,YACJC,YAAcC,eAAMC,OAAO,CAC7BC,MAAOlB,KAAKmB,KACZC,KAAMpB,KAAKqB,WAAarB,KAAKsB,KAC7BC,MAAM,EACNC,eAAe,EACfC,OAAO,IAEXV,MAAMW,OAASnB,GACfQ,MAAMQ,OACNI,iBAAiBC,OACjBxC,SAASE,iBAAiBuC,gBAAaC,yBAAyB,qCAC1C7C,gBAAiBC"} \ No newline at end of file +{"version":3,"file":"linkmodal.min.js","sources":["../src/linkmodal.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 .\n\nimport Modal from 'core/modal';\nimport ModalEvents from 'core/modal_events';\nimport Ajax from 'core/ajax';\nimport Templates from 'core/templates';\nimport * as manualcompletion from 'core_course/manual_completion_toggle';\nimport {renderLearningmap} from 'mod_learningmap/renderer';\nimport CourseEvents from 'core_course/events';\n\n/**\n * Helper for opening course modules in a modal that do not have a view page.\n *\n * @module mod_learningmap/linkmodal\n * @copyright 2025 ISB Bayern\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\n\n/**\n * Initialize the link modal listener for a learning map.\n *\n * @param {number} learningmapcmid - The course module ID of the learning map.\n * @param {boolean} inmodal - Whether the learning map is already in a modal.\n */\nexport const init = async(learningmapcmid, inmodal = false) => {\n const container = document.getElementById('learningmap-render-container-' + learningmapcmid + (inmodal ? '-modal' : ''));\n if (container) {\n container.addEventListener('click', async(event) => {\n const target = event.target.closest('a[data-cmid]');\n if (target && !target.hasAttribute('xlink:href')) {\n event.preventDefault();\n const cmid = target.getAttribute('data-cmid');\n if (cmid) {\n await openModal(event, learningmapcmid, inmodal);\n }\n }\n });\n container.addEventListener('keydown', async(event) => {\n if (event.key === 'Enter') {\n const target = event.target.closest('a[data-cmid]');\n if (target && !target.hasAttribute('xlink:href')) {\n event.preventDefault();\n const cmid = target.getAttribute('data-cmid');\n if (cmid) {\n await openModal(event, learningmapcmid, inmodal);\n }\n }\n }\n });\n }\n};\n\n/**\n * Opens a modal for a course module link that does not have a view page.\n * @param {Event} event - The click or keydown event.\n * @param {number} learningmapcmid - The course module ID of the learning map.\n * @param {boolean} inmodal - Whether the learning map is already in a modal.\n */\nexport const openModal = async(event, learningmapcmid, inmodal) => {\n const target = event.target.closest('a[data-cmid]');\n if (target && !target.hasAttribute('xlink:href')) {\n event.preventDefault();\n const cmid = target.getAttribute('data-cmid');\n if (cmid) {\n const data = await Ajax.call([{\n methodname: 'mod_learningmap_get_cm',\n args: {\n cmid: cmid\n },\n }])[0];\n const container = document.createElement('div');\n container.innerHTML = data.js;\n let js = Array.from(container.querySelectorAll('script'))\n .map(s => s.textContent || '')\n .join('\\n');\n\n const modalbody = await Templates.renderForPromise('mod_learningmap/modal_body', {\n completion: data.completion,\n content: data.html,\n });\n\n const modal = await Modal.create({\n title: data.name,\n body: modalbody.html,\n show: false,\n removeOnClose: true,\n large: true,\n });\n modal.bodyJS = js;\n modal.show();\n manualcompletion.init();\n const completionToggleHandler = () => {\n renderLearningmap(learningmapcmid, inmodal);\n };\n document.addEventListener(CourseEvents.manualCompletionToggled, completionToggleHandler);\n modal.getRoot().on(ModalEvents.hidden, () => {\n document.removeEventListener(CourseEvents.manualCompletionToggled, completionToggleHandler);\n });\n }\n }\n};\n"],"names":["async","learningmapcmid","inmodal","container","document","getElementById","addEventListener","target","event","closest","hasAttribute","preventDefault","getAttribute","openModal","key","cmid","data","Ajax","call","methodname","args","createElement","innerHTML","js","Array","from","querySelectorAll","map","s","textContent","join","modalbody","Templates","renderForPromise","completion","content","html","modal","Modal","create","title","name","body","show","removeOnClose","large","bodyJS","manualcompletion","init","completionToggleHandler","CourseEvents","manualCompletionToggled","getRoot","on","ModalEvents","hidden","removeEventListener"],"mappings":";;;;;;;u/BAqCoBA,eAAMC,qBAAiBC,sEACjCC,UAAYC,SAASC,eAAe,gCAAkCJ,iBAAmBC,QAAU,SAAW,KAChHC,YACAA,UAAUG,iBAAiB,SAASN,MAAAA,cAC1BO,OAASC,MAAMD,OAAOE,QAAQ,mBAChCF,SAAWA,OAAOG,aAAa,cAAe,CAC9CF,MAAMG,iBACOJ,OAAOK,aAAa,oBAEvBC,UAAUL,MAAOP,gBAAiBC,aAIpDC,UAAUG,iBAAiB,WAAWN,MAAAA,WAChB,UAAdQ,MAAMM,IAAiB,OACjBP,OAASC,MAAMD,OAAOE,QAAQ,mBAChCF,SAAWA,OAAOG,aAAa,cAAe,CAC9CF,MAAMG,iBACOJ,OAAOK,aAAa,oBAEvBC,UAAUL,MAAOP,gBAAiBC,sBAcnDW,UAAYb,MAAMQ,MAAOP,gBAAiBC,iBAC7CK,OAASC,MAAMD,OAAOE,QAAQ,mBAChCF,SAAWA,OAAOG,aAAa,cAAe,CAC9CF,MAAMG,uBACAI,KAAOR,OAAOK,aAAa,gBAC7BG,KAAM,OACAC,WAAaC,cAAKC,KAAK,CAAC,CAC1BC,WAAY,yBACZC,KAAM,CACFL,KAAMA,SAEV,GACEZ,UAAYC,SAASiB,cAAc,OACzClB,UAAUmB,UAAYN,KAAKO,OACvBA,GAAKC,MAAMC,KAAKtB,UAAUuB,iBAAiB,WAC1CC,KAAIC,GAAKA,EAAEC,aAAe,KAC1BC,KAAK,YAEJC,gBAAkBC,mBAAUC,iBAAiB,6BAA8B,CAC7EC,WAAYlB,KAAKkB,WACjBC,QAASnB,KAAKoB,OAGZC,YAAcC,eAAMC,OAAO,CAC7BC,MAAOxB,KAAKyB,KACZC,KAAMX,UAAUK,KAChBO,MAAM,EACNC,eAAe,EACfC,OAAO,IAEXR,MAAMS,OAASvB,GACfc,MAAMM,OACNI,iBAAiBC,aACXC,wBAA0B,qCACVhD,gBAAiBC,UAEvCE,SAASE,iBAAiB4C,gBAAaC,wBAAyBF,yBAChEZ,MAAMe,UAAUC,GAAGC,sBAAYC,QAAQ,KACnCnD,SAASoD,oBAAoBN,gBAAaC,wBAAyBF"} \ No newline at end of file diff --git a/amd/build/renderer.min.js b/amd/build/renderer.min.js index 2fc3ed38..2f11d88d 100644 --- a/amd/build/renderer.min.js +++ b/amd/build/renderer.min.js @@ -6,6 +6,6 @@ define("mod_learningmap/renderer",["exports","core/ajax","core/log","core/pendin * @copyright 2021-2024, ISB Bayern * @author Philipp Memmel * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later - */Object.defineProperty(_exports,"__esModule",{value:!0}),_exports.selectors=_exports.renderLearningmap=_exports.init=void 0,_ajax=_interopRequireDefault(_ajax),_log=_interopRequireDefault(_log),_pending=_interopRequireDefault(_pending);const selectors={LEARNINGMAP_RENDER_CONTAINER_PREFIX:"learningmap-render-container-"};_exports.selectors=selectors;_exports.init=function(cmId){let inmodal=arguments.length>1&&void 0!==arguments[1]&&arguments[1];const rendererPendingPromise=new _pending.default("mod_learningmap/renderer-"+cmId);renderLearningmap(cmId,inmodal),rendererPendingPromise.resolve()};const renderLearningmap=cmId=>{_ajax.default.call([{methodname:"mod_learningmap_get_learningmap",args:{cmId:cmId}}])[0].then((data=>{let targetDiv=document.getElementById(selectors.LEARNINGMAP_RENDER_CONTAINER_PREFIX+cmId),svgnode=(new DOMParser).parseFromString(data.content,"image/svg+xml").querySelector("svg");return targetDiv&&targetDiv.replaceChildren(svgnode),targetDiv=document.getElementById(selectors.LEARNINGMAP_RENDER_CONTAINER_PREFIX+cmId+"-modal"),targetDiv&&(targetDiv.replaceChildren(svgnode),targetDiv.parentElement.previousElementSibling.outerHTML=data.completion),!0})).catch((error=>(_log.default.error(error),!1)))};_exports.renderLearningmap=renderLearningmap})); + */Object.defineProperty(_exports,"__esModule",{value:!0}),_exports.selectors=_exports.renderLearningmap=_exports.init=void 0,_ajax=_interopRequireDefault(_ajax),_log=_interopRequireDefault(_log),_pending=_interopRequireDefault(_pending);const selectors={LEARNINGMAP_RENDER_CONTAINER_PREFIX:"learningmap-render-container-",MODAL_BODY:".modal-body",MODAL_COMPLETION_CONTAINER:'[data-region="learningmap-modal-completion"]'};_exports.selectors=selectors;_exports.init=function(cmId){let inmodal=arguments.length>1&&void 0!==arguments[1]&&arguments[1];const rendererPendingPromise=new _pending.default("mod_learningmap/renderer-"+cmId);renderLearningmap(cmId,inmodal),rendererPendingPromise.resolve()};const renderLearningmap=cmId=>{_ajax.default.call([{methodname:"mod_learningmap_get_learningmap",args:{cmId:cmId}}])[0].then((data=>{let targetDiv=document.getElementById(selectors.LEARNINGMAP_RENDER_CONTAINER_PREFIX+cmId),svgnode=(new DOMParser).parseFromString(data.content,"image/svg+xml").querySelector("svg");return targetDiv&&targetDiv.replaceChildren(svgnode),targetDiv=document.getElementById(selectors.LEARNINGMAP_RENDER_CONTAINER_PREFIX+cmId+"-modal"),targetDiv&&(targetDiv.replaceChildren(svgnode),((modalTargetDiv,completionHtml)=>{const modalBody=modalTargetDiv.closest(selectors.MODAL_BODY);if(!modalBody)return;const completionContainer=modalBody.querySelector(selectors.MODAL_COMPLETION_CONTAINER);completionContainer&&(completionContainer.innerHTML=completionHtml)})(targetDiv,data.completion)),!0})).catch((error=>(_log.default.error(error),!1)))};_exports.renderLearningmap=renderLearningmap})); //# sourceMappingURL=renderer.min.js.map \ No newline at end of file diff --git a/amd/build/renderer.min.js.map b/amd/build/renderer.min.js.map index adb2c52e..ce9d9143 100644 --- a/amd/build/renderer.min.js.map +++ b/amd/build/renderer.min.js.map @@ -1 +1 @@ -{"version":3,"file":"renderer.min.js","sources":["../src/renderer.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 .\n\n/**\n * Renderer module for the learningmap.\n *\n * @module mod_learningmap/renderer\n * @copyright 2021-2024, ISB Bayern\n * @author Philipp Memmel\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport Ajax from 'core/ajax';\nimport Log from 'core/log';\nimport Pending from 'core/pending';\n\nexport const selectors = {\n LEARNINGMAP_RENDER_CONTAINER_PREFIX: 'learningmap-render-container-'\n};\n\n/**\n * Renders the learningmap into the correct div.\n *\n * @param {number} cmId the course module id of the learningmap\n * @param {boolean} inmodal whether the learningmap is being rendered in a modal\n */\nexport const init = (cmId, inmodal = false) => {\n const rendererPendingPromise = new Pending('mod_learningmap/renderer-' + cmId);\n renderLearningmap(cmId, inmodal);\n rendererPendingPromise.resolve();\n};\n\n/**\n * Render the learningmap with the given cmId into the corresponding div in the DOM.\n *\n * @param {number} cmId the course module id of the learningmap\n */\nexport const renderLearningmap = (cmId) => {\n const promises = Ajax.call(\n [\n {\n methodname: 'mod_learningmap_get_learningmap',\n args: {\n 'cmId': cmId\n }\n }\n ]);\n\n promises[0].then(data => {\n let targetDiv = document.getElementById(selectors.LEARNINGMAP_RENDER_CONTAINER_PREFIX + cmId);\n let svgdoc = new DOMParser().parseFromString(data.content, 'image/svg+xml');\n let svgnode = svgdoc.querySelector('svg');\n if (targetDiv) {\n targetDiv.replaceChildren(svgnode);\n }\n targetDiv = document.getElementById(selectors.LEARNINGMAP_RENDER_CONTAINER_PREFIX + cmId + '-modal');\n if (targetDiv) {\n targetDiv.replaceChildren(svgnode);\n targetDiv.parentElement.previousElementSibling.outerHTML = data.completion;\n }\n return true;\n }).catch((error) => {\n Log.error(error);\n return false;\n });\n};\n"],"names":["selectors","LEARNINGMAP_RENDER_CONTAINER_PREFIX","cmId","inmodal","rendererPendingPromise","Pending","renderLearningmap","resolve","Ajax","call","methodname","args","then","data","targetDiv","document","getElementById","svgnode","DOMParser","parseFromString","content","querySelector","replaceChildren","parentElement","previousElementSibling","outerHTML","completion","catch","error"],"mappings":";;;;;;;;sPA2BaA,UAAY,CACrBC,oCAAqC,4EASrB,SAACC,UAAMC,sEACjBC,uBAAyB,IAAIC,iBAAQ,4BAA8BH,MACzEI,kBAAkBJ,KAAMC,SACxBC,uBAAuBG,iBAQdD,kBAAqBJ,OACbM,cAAKC,KAClB,CACI,CACIC,WAAY,kCACZC,KAAM,MACMT,SAKf,GAAGU,MAAKC,WACTC,UAAYC,SAASC,eAAehB,UAAUC,oCAAsCC,MAEpFe,SADS,IAAIC,WAAYC,gBAAgBN,KAAKO,QAAS,iBACtCC,cAAc,cAC/BP,WACAA,UAAUQ,gBAAgBL,SAE9BH,UAAYC,SAASC,eAAehB,UAAUC,oCAAsCC,KAAO,UACvFY,YACAA,UAAUQ,gBAAgBL,SAC1BH,UAAUS,cAAcC,uBAAuBC,UAAYZ,KAAKa,aAE7D,KACRC,OAAOC,qBACFA,MAAMA,QACH"} \ No newline at end of file +{"version":3,"file":"renderer.min.js","sources":["../src/renderer.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 .\n\n/**\n * Renderer module for the learningmap.\n *\n * @module mod_learningmap/renderer\n * @copyright 2021-2024, ISB Bayern\n * @author Philipp Memmel\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\nimport Ajax from 'core/ajax';\nimport Log from 'core/log';\nimport Pending from 'core/pending';\n\nexport const selectors = {\n LEARNINGMAP_RENDER_CONTAINER_PREFIX: 'learningmap-render-container-',\n MODAL_BODY: '.modal-body',\n MODAL_COMPLETION_CONTAINER: '[data-region=\"learningmap-modal-completion\"]',\n};\n\n/**\n * Replace the completion header in the learningmap modal.\n *\n * @param {Element} modalTargetDiv The learningmap render container inside the modal.\n * @param {string} completionHtml The new completion header HTML.\n */\nconst replaceModalCompletionHeader = (modalTargetDiv, completionHtml) => {\n const modalBody = modalTargetDiv.closest(selectors.MODAL_BODY);\n if (!modalBody) {\n return;\n }\n\n const completionContainer = modalBody.querySelector(selectors.MODAL_COMPLETION_CONTAINER);\n if (completionContainer) {\n completionContainer.innerHTML = completionHtml;\n }\n};\n\n/**\n * Renders the learningmap into the correct div.\n *\n * @param {number} cmId the course module id of the learningmap\n * @param {boolean} inmodal whether the learningmap is being rendered in a modal\n */\nexport const init = (cmId, inmodal = false) => {\n const rendererPendingPromise = new Pending('mod_learningmap/renderer-' + cmId);\n renderLearningmap(cmId, inmodal);\n rendererPendingPromise.resolve();\n};\n\n/**\n * Render the learningmap with the given cmId into the corresponding div in the DOM.\n *\n * @param {number} cmId the course module id of the learningmap\n */\nexport const renderLearningmap = (cmId) => {\n const promises = Ajax.call(\n [\n {\n methodname: 'mod_learningmap_get_learningmap',\n args: {\n 'cmId': cmId\n }\n }\n ]);\n\n promises[0].then(data => {\n let targetDiv = document.getElementById(selectors.LEARNINGMAP_RENDER_CONTAINER_PREFIX + cmId);\n let svgdoc = new DOMParser().parseFromString(data.content, 'image/svg+xml');\n let svgnode = svgdoc.querySelector('svg');\n if (targetDiv) {\n targetDiv.replaceChildren(svgnode);\n }\n targetDiv = document.getElementById(selectors.LEARNINGMAP_RENDER_CONTAINER_PREFIX + cmId + '-modal');\n if (targetDiv) {\n targetDiv.replaceChildren(svgnode);\n replaceModalCompletionHeader(targetDiv, data.completion);\n }\n return true;\n }).catch((error) => {\n Log.error(error);\n return false;\n });\n};\n"],"names":["selectors","LEARNINGMAP_RENDER_CONTAINER_PREFIX","MODAL_BODY","MODAL_COMPLETION_CONTAINER","cmId","inmodal","rendererPendingPromise","Pending","renderLearningmap","resolve","Ajax","call","methodname","args","then","data","targetDiv","document","getElementById","svgnode","DOMParser","parseFromString","content","querySelector","replaceChildren","modalTargetDiv","completionHtml","modalBody","closest","completionContainer","innerHTML","replaceModalCompletionHeader","completion","catch","error"],"mappings":";;;;;;;;sPA2BaA,UAAY,CACrBC,oCAAqC,gCACrCC,WAAY,cACZC,2BAA4B,2FA2BZ,SAACC,UAAMC,sEACjBC,uBAAyB,IAAIC,iBAAQ,4BAA8BH,MACzEI,kBAAkBJ,KAAMC,SACxBC,uBAAuBG,iBAQdD,kBAAqBJ,OACbM,cAAKC,KAClB,CACI,CACIC,WAAY,kCACZC,KAAM,MACMT,SAKf,GAAGU,MAAKC,WACTC,UAAYC,SAASC,eAAelB,UAAUC,oCAAsCG,MAEpFe,SADS,IAAIC,WAAYC,gBAAgBN,KAAKO,QAAS,iBACtCC,cAAc,cAC/BP,WACAA,UAAUQ,gBAAgBL,SAE9BH,UAAYC,SAASC,eAAelB,UAAUC,oCAAsCG,KAAO,UACvFY,YACAA,UAAUQ,gBAAgBL,SAjDD,EAACM,eAAgBC,wBAC5CC,UAAYF,eAAeG,QAAQ5B,UAAUE,gBAC9CyB,uBAICE,oBAAsBF,UAAUJ,cAAcvB,UAAUG,4BAC1D0B,sBACAA,oBAAoBC,UAAYJ,iBA0C5BK,CAA6Bf,UAAWD,KAAKiB,cAE1C,KACRC,OAAOC,qBACFA,MAAMA,QACH"} \ No newline at end of file diff --git a/amd/src/linkmodal.js b/amd/src/linkmodal.js index 4d35a778..77328fa5 100644 --- a/amd/src/linkmodal.js +++ b/amd/src/linkmodal.js @@ -14,7 +14,9 @@ // along with Moodle. If not, see . import Modal from 'core/modal'; +import ModalEvents from 'core/modal_events'; import Ajax from 'core/ajax'; +import Templates from 'core/templates'; import * as manualcompletion from 'core_course/manual_completion_toggle'; import {renderLearningmap} from 'mod_learningmap/renderer'; import CourseEvents from 'core_course/events'; @@ -84,9 +86,15 @@ export const openModal = async(event, learningmapcmid, inmodal) => { let js = Array.from(container.querySelectorAll('script')) .map(s => s.textContent || '') .join('\n'); + + const modalbody = await Templates.renderForPromise('mod_learningmap/modal_body', { + completion: data.completion, + content: data.html, + }); + const modal = await Modal.create({ title: data.name, - body: data.completion + data.html, + body: modalbody.html, show: false, removeOnClose: true, large: true, @@ -94,8 +102,12 @@ export const openModal = async(event, learningmapcmid, inmodal) => { modal.bodyJS = js; modal.show(); manualcompletion.init(); - document.addEventListener(CourseEvents.manualCompletionToggled, () => { + const completionToggleHandler = () => { renderLearningmap(learningmapcmid, inmodal); + }; + document.addEventListener(CourseEvents.manualCompletionToggled, completionToggleHandler); + modal.getRoot().on(ModalEvents.hidden, () => { + document.removeEventListener(CourseEvents.manualCompletionToggled, completionToggleHandler); }); } } diff --git a/amd/src/renderer.js b/amd/src/renderer.js index 29739bd8..9178915e 100644 --- a/amd/src/renderer.js +++ b/amd/src/renderer.js @@ -26,7 +26,27 @@ import Log from 'core/log'; import Pending from 'core/pending'; export const selectors = { - LEARNINGMAP_RENDER_CONTAINER_PREFIX: 'learningmap-render-container-' + LEARNINGMAP_RENDER_CONTAINER_PREFIX: 'learningmap-render-container-', + MODAL_BODY: '.modal-body', + MODAL_COMPLETION_CONTAINER: '[data-region="learningmap-modal-completion"]', +}; + +/** + * Replace the completion header in the learningmap modal. + * + * @param {Element} modalTargetDiv The learningmap render container inside the modal. + * @param {string} completionHtml The new completion header HTML. + */ +const replaceModalCompletionHeader = (modalTargetDiv, completionHtml) => { + const modalBody = modalTargetDiv.closest(selectors.MODAL_BODY); + if (!modalBody) { + return; + } + + const completionContainer = modalBody.querySelector(selectors.MODAL_COMPLETION_CONTAINER); + if (completionContainer) { + completionContainer.innerHTML = completionHtml; + } }; /** @@ -67,7 +87,7 @@ export const renderLearningmap = (cmId) => { targetDiv = document.getElementById(selectors.LEARNINGMAP_RENDER_CONTAINER_PREFIX + cmId + '-modal'); if (targetDiv) { targetDiv.replaceChildren(svgnode); - targetDiv.parentElement.previousElementSibling.outerHTML = data.completion; + replaceModalCompletionHeader(targetDiv, data.completion); } return true; }).catch((error) => { diff --git a/templates/modal_body.mustache b/templates/modal_body.mustache new file mode 100644 index 00000000..459c0252 --- /dev/null +++ b/templates/modal_body.mustache @@ -0,0 +1,37 @@ +{{! + This file is part of Moodle - https://moodle.org/ + + Moodle is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Moodle is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Moodle. If not, see . +}} +{{! + @template mod_learningmap/modal_body + + Template for the learningmap modal body split into dedicated regions. + + Context variables required for this template: + * completion Completion header html + * content Main activity html + + Example context (json): + { + "completion": "
...
", + "content": "
...
" + } +}} +
+ {{{completion}}} +
+
+ {{{content}}} +