From eafbc59e014f9f4f22192f551623e87f0db550c9 Mon Sep 17 00:00:00 2001 From: gthomas2 Date: Fri, 2 Aug 2024 15:24:56 +0100 Subject: [PATCH] ALLY-12: Fix behat tests for 4.3 (#61) --- amd/build/main.min.js | 2 +- amd/build/main.min.js.map | 2 +- amd/src/main.js | 23 ++++++++++++++++------- filter.php | 3 ++- 4 files changed, 20 insertions(+), 10 deletions(-) diff --git a/amd/build/main.min.js b/amd/build/main.min.js index 7d731a1..14b7f10 100644 --- a/amd/build/main.min.js +++ b/amd/build/main.min.js @@ -21,6 +21,6 @@ * @copyright Copyright (c) 2016 Open LMS / 2023 Anthology Inc. and its affiliates * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later */ -define("filter_ally/main",["jquery","core/templates","core/str","filter_ally/ally","filter_ally/imagecover","filter_ally/util"],(function($,Templates,Strings,Ally,ImageCover,Util){return new function(){var self=this;self.canViewFeedback=!1,self.canDownload=!1,self.initialised=!1,self.params={};var getNodeByXpath=function(xpath){return window.document.createExpression(xpath).evaluate(window.document,XPathResult.FIRST_ORDERED_NODE_TYPE).singleNodeValue},renderTemplate=function(data,pathHash,targetEl){var dfd=$.Deferred();return $(targetEl).parents(".filter-ally-wrapper").length?(dfd.resolve(),dfd.promise()):(data.canviewfeedback=self.canViewFeedback,data.candownload=self.canDownload,data.html='',Templates.render("filter_ally/wrapper",data).done((function(result){0==$(targetEl).next().find('span[data-file-id="'+pathHash+'"]').length&&($(targetEl).after(result),$("#content-target-"+pathHash).after(targetEl),$("#content-target-"+pathHash).remove()),dfd.resolve()})),dfd.promise())},placeHoldSelector=function(selector,map){var dfd=$.Deferred(),c=0,length=$(selector).length;return length||dfd.resolve(),$(selector).each((function(){var url,type,regex,checkComplete=function(){c===length&&dfd.resolve()};"a"===$(this).prop("tagName").toLowerCase()?(url=$(this).attr("href"),type="a"):(url=$(this).attr("src"),type="img"),regex=url.indexOf("?")>-1?/pluginfile.php\/(\d*)\/(.*)(\?)/:/pluginfile.php\/(\d*)\/(.*)/;var pathHash,match=url.match(regex);if(match){var path=match[1]+"/"+match[2];path=decodeURIComponent(path),pathHash=map[path]}if(void 0===pathHash){var query=Util.getQuery(url);if(query.file)regex=/\/(\d*)\/(.*)/,(match=decodeURIComponent(query.file).match(regex))&&(path=match[1]+"/"+match[2],path=decodeURIComponent(path),pathHash=map[path])}if(void 0===pathHash)return c++,void checkComplete();renderTemplate({isimage:"img"===type,fileid:pathHash,url:url},pathHash,$(this)).done((function(){c++,checkComplete()}))})),dfd.promise()},placeHoldForumModule=function(forumFileMapping){var dfd=$.Deferred();return placeHoldSelector('.forumpost .attachedimages img[src*="pluginfile.php"], .forumpost .body-content-container a[href*="pluginfile.php"]',forumFileMapping).done((function(){dfd.resolve()})),dfd.promise()},placeHoldAssignModule=function(assignFileMapping){var dfd=$.Deferred();return Util.whenTrue((function(){return $('div[id*="assign_files_tree"] .ygtvitem').length>0}),10).done((function(){placeHoldSelector('div[id*="assign_files_tree"] a[href*="pluginfile.php"]',assignFileMapping),dfd.resolve()})),dfd.promise()},placeHoldFolderModule=function(folderFileMapping){var dfd=$.Deferred();return Util.whenTrue((function(){return $(".foldertree > .filemanager .ygtvitem").length>0}),10).done((function(){placeHoldSelector('.foldertree > .filemanager span:not(.filter-ally-wrapper) > a[href*="pluginfile.php"]',folderFileMapping).done((function(){dfd.resolve()}))})),dfd.promise()},placeHoldGlossaryModule=function(glossaryFileMapping){var dfd=$.Deferred();$(".entry .attachments > br").each((function(){var mainAnchor=$(this).prev('a[href*="pluginfile.php"]');mainAnchor.addClass("ally-glossary-attachment");var iconAnchor=$(mainAnchor).prev('a[href*="pluginfile.php"]');$(this).after('
');var container=$(this).next(".ally-glossary-attachment-row");container.append(iconAnchor),container.append(mainAnchor),$(this).remove()}));return placeHoldSelector(".entry .attachments .ally-glossary-attachment",glossaryFileMapping).done((function(){dfd.resolve()})),dfd.promise()},urlEncodeFilePath=function(filePath){var parts=filePath.split("/");for(var p in parts)parts[p]=encodeURIComponent(parts[p]);return parts.join("/")},placeHoldLessonGeneral=function(map,selectorPrefix){var dfd=$.Deferred();if(0===map.length)dfd.resolve();else for(var c in map){var path=urlEncodeFilePath(c);placeHoldSelector(selectorPrefix+'img[src*="'+path+'"], '+selectorPrefix+'a[href*="'+path+'"]',map).done((function(){dfd.resolve()}))}return dfd.promise()},placeHoldLessonModule=function(lessonFileMapping){var dfd=$.Deferred(),pageContentsMap=lessonFileMapping.page_contents,pageAnswersMap=lessonFileMapping.page_answers,pageResponsesMap=lessonFileMapping.page_responses;return function(pageContentsMap){return placeHoldLessonGeneral(pageContentsMap,"")}(pageContentsMap).then((function(){return function(pageAnswersMap){return placeHoldLessonGeneral(pageAnswersMap,".studentanswer table tr:nth-child(1) ")}(pageAnswersMap)})).then((function(){return function(pageResponsesMap){return placeHoldLessonGeneral(pageResponsesMap,".studentanswer table tr.lastrow ")}(pageResponsesMap)})).then((function(){dfd.resolve()})),dfd.promise()},placeHoldResourceModule=function(moduleFileMapping){var dfd=$.Deferred(),c=0,checkAllProcessed=function(){++c>=Object.keys(moduleFileMapping).length&&dfd.resolve()};for(var moduleId in moduleFileMapping){var pathHash=moduleFileMapping[moduleId].content;if($("body").hasClass("theme-snap")&&!$("body").hasClass("format-tiles"))var moduleEl=$("#module-"+moduleId+":not(.snap-native) .activityinstance .snap-asset-link a:first-of-type:not(.clickable-region)");else moduleEl=$("#module-"+moduleId+" .activity-instance a:first-of-type:not(.clickable-region,.editing_move)");if(moduleEl.find(".filter-ally-wrapper").length>0)checkAllProcessed();else{var data={isimage:!1,fileid:pathHash,url:$(moduleEl).attr("href")};renderTemplate(data,pathHash,moduleEl).done(checkAllProcessed)}}return dfd.promise()},buildContentIdent=function(component,table,field,id){return[component,table,field,id].join(":")},annotateSections=function(sectionMapping){var dfd=$.Deferred();for(var s in sectionMapping){var sectionId=sectionMapping[s],ident=buildContentIdent("course","course_sections","summary",sectionId);$(["#"+s+' > .content div[class*="summarytext"] .no-overflow',"body.theme-snap #"+s+" > .content > .summary > div > .no-overflow"].join(",")).attr("data-ally-richcontent",ident)}return dfd.resolve(),dfd.promise()},annotateModuleIntros=function(introMapping,module,additionalSelectors){for(var i in introMapping){var annotation=introMapping[i],selectors=["body.path-mod-"+module+".cmid-"+i+" #intro > .no-overflow","li.activity.modtype_"+module+"#module-"+i+" .description .no-overflow > .no-overflow","li.snap-activity.modtype_"+module+"#module-"+i+" .contentafterlink > .no-overflow"];if(additionalSelectors)for(var a in additionalSelectors)selectors.push(additionalSelectors[a].replace("{{i}}",i));$(selectors.join(",")).attr("data-ally-richcontent",annotation)}},annotateLesson=function(mapping){var intros=mapping.intros;annotateModuleIntros(intros,"lesson",["li.snap-native.modtype_lesson#module-{{i}} .contentafterlink > .summary-text .no-overflow"]);var content=mapping.lesson_pages;for(var p in content)if("page-mod-lesson-edit"===document.body.id){var xpath='//a[@id="lesson-'+p+'"]//ancestor::table//tbody/tr/td/div[contains(@class, "no-overflow")]',annotation=content[p],node=getNodeByXpath(xpath);$(node).attr("data-ally-richcontent",annotation)}else{if(node=getNodeByXpath('//form[contains(@action, "continue.php")]//input[@name="pageid"]'))var pageId=$(node).val();else pageId=new URLSearchParams(window.location.search).get("pageid");if(pageId!=p)continue;annotation=content[p];$(["#page-mod-lesson-view #region-main .box.contents > .no-overflow","#page-mod-lesson-view #region-main form > fieldset > .fcontainer > .contents .no-overflow","li.snap-native.modtype_page#module-"+p+" .pagemod-content"].join(",")).attr("data-ally-richcontent",annotation)}Strings.get_strings([{key:"answer",component:"mod_lesson"},{key:"response",component:"mod_lesson"}]).then((function(strings){var answerLabel=strings[0],responseLabel=strings[1],answers=mapping.lesson_answers,processAnswerResponse=function(pageId,i,label,annotation){var nodes=function(xpath){var result=window.document.createExpression(xpath).evaluate(window.document,XPathResult.ANY_TYPE),nodes=[];do{var node=result.iterateNext();nodes.push(node)}while(node);return nodes}('//a[@id="lesson-'+pageId+'"]//ancestor::table//td/label[contains(text(),"'+label+" "+i+'")]/ancestor::tr/td[2]');for(var n in nodes){var node=nodes[n];$(node).attr("data-ally-richcontent",annotation)}};for(var a in answers){var annotation=answers[a],pageId=(tmpArr=a.split("_"))[0],ansId=tmpArr[1],anum=tmpArr[2];if("page-mod-lesson-edit"===document.body.id)processAnswerResponse(pageId,anum,answerLabel,annotation);else{if($('#page-mod-lesson-view label[for="id_answerid_'+ansId+'"]').attr("data-ally-richcontent",annotation),self.params.answerid&&self.params.answerid==ansId)$(".studentanswer tr:nth-of-type(1) > td div").attr("data-ally-richcontent",annotation);else{var answerWrapperId="answer_wrapper_"+ansId,answerEl=$("#id_answerid_"+ansId);if(1!=answerEl.data("annotated")){var contentEls=answerEl.nextAll();answerEl.parent("label").append(''),$("#"+answerWrapperId).append(contentEls)}answerEl.data("annotated",1)}$("#answer_wrapper_"+a).attr("data-ally-richcontent",annotation)}}var responses=mapping.lesson_answers_response;for(var r in responses){annotation=responses[r],pageId=(tmpArr=r.split("_"))[0];var tmpArr,respId=tmpArr[1],rnum=tmpArr[2];if("page-mod-lesson-edit"===document.body.id)processAnswerResponse(pageId,rnum,responseLabel,annotation);else if(self.params.answerid&&self.params.answerid==respId){var responseWrapperId="response_wrapper_"+respId;if(!$(".studentanswer tr.lastrow > td #"+responseWrapperId).length){contentEls=$(".studentanswer tr.lastrow > td > br").nextAll();$(".studentanswer tr.lastrow > td > br").after(''),$("#"+responseWrapperId).append(contentEls)}$("#"+responseWrapperId).attr("data-ally-richcontent",annotation)}}}))},annotateModules=function(moduleMapping){var dfd=$.Deferred();return void 0!==moduleMapping.mod_forum&&function(forumMapping){var intros=forumMapping.intros;annotateModuleIntros(intros,"forum");var discussions=forumMapping.posts;for(var d in discussions){var post="p"+d,annotation=discussions[d];$(["#page-mod-forum-discuss #"+post+" div.forumpost div.no-overflow"].join(",")).attr("data-ally-richcontent",annotation)}}(moduleMapping.mod_forum),void 0!==moduleMapping.mod_hsuforum&&function(forumMapping){var intros=forumMapping.intros;annotateModuleIntros(intros,"hsuforum",["#hsuforum-header .hsuforum_introduction > .no-overflow"]);var discussions=forumMapping.posts;for(var d in discussions){var annotation=discussions[d];$('article[id="p'+d+'"] div.posting').attr("data-ally-richcontent",annotation)}}(moduleMapping.mod_hsuforum),void 0!==moduleMapping.mod_glossary&&function(mapping){var intros=mapping.intros;annotateModuleIntros(intros,"glossary");var entries=mapping.entries;for(var e in entries){var annotation=entries[e],entryFooter=$('.entrylowersection .commands a[href*="id='+e+'"]'),entry=$(entryFooter).parents(".glossarypost").find(".entry .no-overflow");$(entry).attr("data-ally-richcontent",annotation)}}(moduleMapping.mod_glossary),void 0!==moduleMapping.mod_page&&function(mapping){var intros=mapping.intros;annotateModuleIntros(intros,"page",["li.snap-native.modtype_page#module-{{i}} .contentafterlink > .summary-text"]);var content=mapping.content;for(var c in content){var annotation=content[c],selectors=["#page-mod-page-view.cmid-".concat(c," #region-main .box.generalbox > .no-overflow"),"li.snap-native.modtype_page#module-".concat(c," .pagemod-content")];$(selectors.join(",")).attr("data-ally-richcontent",annotation)}}(moduleMapping.mod_page),void 0!==moduleMapping.mod_book&&function(mapping){var intros=mapping.intros;annotateModuleIntros(intros,"book",["li.snap-native.modtype_book#module-{{i}} .contentafterlink > .summary-text .no-overflow"]);var chapterId,content=mapping.chapters;if(self.params.chapterid)chapterId=self.params.chapterid;else{var urlParams=new URLSearchParams(window.location.search);chapterId=urlParams.get("chapterid")}$.each(content,(function(ch,annotation){chapterId==ch&&$(["#page-mod-book-view #region-main .box.generalbox.book_content > .no-overflow","li.snap-native.modtype_page#module-"+ch+" .pagemod-content"].join(",")).attr("data-ally-richcontent",annotation)}))}(moduleMapping.mod_book),void 0!==moduleMapping.mod_lesson&&annotateLesson(moduleMapping.mod_lesson),dfd.resolve(),dfd.promise()},annotateSnapCourseSummary=function(mapping){var dfd=$.Deferred(),snapFooterCourseSummary=$("#snap-course-footer-summary > div.no-overflow");if(snapFooterCourseSummary.length){var ident=buildContentIdent("course","course","summary",mapping.courseId);snapFooterCourseSummary.attr("data-ally-richcontent",ident)}return dfd.resolve(),dfd.promise()},annotateHtmlBlock=function(mapping){var dfd=$.Deferred(),items=mapping.block_html;for(var i in items){var ident=items[i],selector=["#inst"+i+".block_html > .card-body > .card-text > .no-overflow","#inst"+i+".block_html > .content > .no-overflow"].join(",");$(selector).attr("data-ally-richcontent",ident)}return dfd.resolve(),dfd.promise()},debounceApplyPlaceHolders=Util.debounce((function(){return function(){M.util.js_pending("filter_ally_applyPlaceHolders");var dfd=$.Deferred();if(void 0===ally_module_maps||void 0===ally_section_maps)return dfd.resolve(),dfd.promise();var tasks=[{mapVar:ally_module_maps.file_resources,method:placeHoldResourceModule},{mapVar:ally_module_maps.assignment_files,method:placeHoldAssignModule},{mapVar:ally_module_maps.folder_files,method:placeHoldFolderModule},{mapVar:ally_module_maps.forum_files,method:placeHoldForumModule},{mapVar:ally_module_maps.glossary_files,method:placeHoldGlossaryModule},{mapVar:ally_module_maps.lesson_files,method:placeHoldLessonModule},{mapVar:ally_section_maps,method:annotateSections},{mapVar:ally_annotation_maps,method:annotateModules},{mapVar:{courseId:self.courseId},method:annotateSnapCourseSummary},{mapVar:ally_annotation_maps,method:annotateHtmlBlock}];return $(document).ready((function(){var completed=0,onTaskComplete=function(){++completed===tasks.length&&(M.util.js_complete("filter_ally_applyPlaceHolders"),dfd.resolve())};for(var t in tasks){var task=tasks[t];Object.keys(task.mapVar).length>0?task.method(task.mapVar).done(onTaskComplete):onTaskComplete()}})),dfd.promise()}()}),1e3);this.initStageTwo=function(){const{jwt:jwt,config:config}=self;(self.canViewFeedback||self.canDownload)&&(debounceApplyPlaceHolders().done((function(){ImageCover.init(),Ally.init(jwt,config);try{var targetNode=$(".foldertree > .filemanager")[0];if(targetNode){new MutationObserver((function(mutationsList){mutationsList.filter((function(mutation){return"childList"===mutation.type})).forEach((function(){placeHoldFolderModule(ally_module_maps.folder_files)}))})).observe(targetNode,{attributes:!0,childList:!0,subtree:!0})}}catch(error){setInterval((function(){placeHoldFolderModule(ally_module_maps.folder_files)}),5e3)}self.initialised=!0})),$(document).ajaxComplete((function(){self.initialised&&debounceApplyPlaceHolders()})),$("body.theme-snap").length&&($(document).ajaxComplete((function(event,xhr,settings){settings.url.includes("ally.js")&&(setTimeout((function(){$(".ally-feedback.ally-active.ally-score-indicator-embedded span").each((function(){"none"==this.style.display&&(this.style.display="block","ally-scoreindicator-container"==this.getAttribute("class")&&(this.style.display="inline-block",this.children[0].style.display="inline-block"))}))}),5e3),$(document).off("ajaxComplete"))})),document.addEventListener("core_filters/contentUpdated",(()=>{self.initStageTwo()}))))},this.init=function(jwt,config,canViewFeedback,canDownload,courseId,params){self.canViewFeedback=canViewFeedback,self.canDownload=canDownload,self.courseId=courseId,self.params=params,self.jwt=jwt,self.config=config;var pluginJSURL=function(path){return M.cfg.wwwroot+"/pluginfile.php/"+M.cfg.contextid+"/filter_ally/"+path},polyfills={};if(document.evaluate||(polyfills["filter_ally/wgxpath"]=pluginJSURL("vendorjs/wgxpath.install")),"undefined"==typeof URLSearchParams&&(polyfills["filter_ally/urlsearchparams"]=["https://cdnjs.cloudflare.com/ajax/libs/url-search-params/1.1.0/url-search-params.amd.js",pluginJSURL("vendorjs/url-search-params.amd")]),polyfills==={})self.initStageTwo();else{require.config({enforceDefine:!1,paths:polyfills});var requires=Object.keys(polyfills);require(requires,(function(){"undefined"==typeof URLSearchParams&&(window.URLSearchParams=arguments[1]),self.initStageTwo()}))}}}})); +define("filter_ally/main",["jquery","core/templates","core/str","filter_ally/ally","filter_ally/imagecover","filter_ally/util"],(function($,Templates,Strings,Ally,ImageCover,Util){return new function(){var self=this;self.canViewFeedback=!1,self.canDownload=!1,self.initialised=!1,self.params={};var getNodeByXpath=function(xpath){return window.document.createExpression(xpath).evaluate(window.document,XPathResult.FIRST_ORDERED_NODE_TYPE).singleNodeValue},renderTemplate=function(data,pathHash,targetEl){var dfd=$.Deferred();return $(targetEl).parents(".filter-ally-wrapper").length?(dfd.resolve(),dfd.promise()):(data.canviewfeedback=self.canViewFeedback,data.candownload=self.canDownload,data.html='',Templates.render("filter_ally/wrapper",data).done((function(result){0==$(targetEl).next().find('span[data-file-id="'+pathHash+'"]').length&&($(targetEl).after(result),$("#content-target-"+pathHash).after(targetEl),$("#content-target-"+pathHash).remove()),dfd.resolve()})),dfd.promise())},placeHoldSelector=function(selector,map){var dfd=$.Deferred(),c=0,length=$(selector).length;return length||dfd.resolve(),$(selector).each((function(){var url,type,regex,checkComplete=function(){c===length&&dfd.resolve()};"a"===$(this).prop("tagName").toLowerCase()?(url=$(this).attr("href"),type="a"):(url=$(this).attr("src"),type="img"),regex=url.indexOf("?")>-1?/pluginfile.php\/(\d*)\/(.*)(\?)/:/pluginfile.php\/(\d*)\/(.*)/;var pathHash,match=url.match(regex);if(match){var path=match[1]+"/"+match[2];path=decodeURIComponent(path),pathHash=map[path]}if(void 0===pathHash){var query=Util.getQuery(url);if(query.file)regex=/\/(\d*)\/(.*)/,(match=decodeURIComponent(query.file).match(regex))&&(path=match[1]+"/"+match[2],path=decodeURIComponent(path),pathHash=map[path])}if(void 0===pathHash)return c++,void checkComplete();renderTemplate({isimage:"img"===type,fileid:pathHash,url:url},pathHash,$(this)).done((function(){c++,checkComplete()}))})),dfd.promise()},placeHoldForumModule=function(forumFileMapping){var dfd=$.Deferred();return placeHoldSelector('.forumpost .attachedimages img[src*="pluginfile.php"], .forumpost .body-content-container a[href*="pluginfile.php"]',forumFileMapping).done((function(){dfd.resolve()})),dfd.promise()},placeHoldAssignModule=function(assignFileMapping){var dfd=$.Deferred();return Util.whenTrue((function(){return $('div[id*="assign_files_tree"] .ygtvitem').length>0}),10).done((function(){placeHoldSelector('div[id*="assign_files_tree"] a[href*="pluginfile.php"]',assignFileMapping),dfd.resolve()})),dfd.promise()},placeHoldFolderModule=function(folderFileMapping){var dfd=$.Deferred();return Util.whenTrue((function(){return $(".foldertree > .filemanager .ygtvitem").length>0}),10).done((function(){placeHoldSelector('.foldertree > .filemanager span:not(.filter-ally-wrapper) > a[href*="pluginfile.php"]',folderFileMapping).done((function(){dfd.resolve()}))})),dfd.promise()},placeHoldGlossaryModule=function(glossaryFileMapping){var dfd=$.Deferred();$(".entry .attachments > br").each((function(){var mainAnchor=$(this).prev('a[href*="pluginfile.php"]');mainAnchor.addClass("ally-glossary-attachment");var iconAnchor=$(mainAnchor).prev('a[href*="pluginfile.php"]');$(this).after('
');var container=$(this).next(".ally-glossary-attachment-row");container.append(iconAnchor),container.append(mainAnchor),$(this).remove()}));return placeHoldSelector(".entry .attachments .ally-glossary-attachment",glossaryFileMapping).done((function(){dfd.resolve()})),dfd.promise()},urlEncodeFilePath=function(filePath){var parts=filePath.split("/");for(var p in parts)parts[p]=encodeURIComponent(parts[p]);return parts.join("/")},placeHoldLessonGeneral=function(map,selectorPrefix){var dfd=$.Deferred();if(0===map.length)dfd.resolve();else for(var c in map){var path=urlEncodeFilePath(c);placeHoldSelector(selectorPrefix+'img[src*="'+path+'"], '+selectorPrefix+'a[href*="'+path+'"]',map).done((function(){dfd.resolve()}))}return dfd.promise()},placeHoldLessonModule=function(lessonFileMapping){var dfd=$.Deferred(),pageContentsMap=lessonFileMapping.page_contents,pageAnswersMap=lessonFileMapping.page_answers,pageResponsesMap=lessonFileMapping.page_responses;return function(pageContentsMap){return placeHoldLessonGeneral(pageContentsMap,"")}(pageContentsMap).then((function(){return function(pageAnswersMap){return placeHoldLessonGeneral(pageAnswersMap,".studentanswer table tr:nth-child(1) ")}(pageAnswersMap)})).then((function(){return function(pageResponsesMap){return placeHoldLessonGeneral(pageResponsesMap,".studentanswer table tr.lastrow ")}(pageResponsesMap)})).then((function(){dfd.resolve()})),dfd.promise()},placeHoldResourceModule=function(moduleFileMapping){var dfd=$.Deferred(),c=0,checkAllProcessed=function(){++c>=Object.keys(moduleFileMapping).length&&dfd.resolve()};for(var moduleId in moduleFileMapping){var pathHash=moduleFileMapping[moduleId].content;if($("body").hasClass("theme-snap")&&!$("body").hasClass("format-tiles"))var moduleEl=$("#module-"+moduleId+":not(.snap-native) .activityinstance .snap-asset-link a:first-of-type:not(.clickable-region)");else moduleEl=$("#module-"+moduleId+" .activity-instance a:first-of-type:not(.clickable-region,.editing_move)");if(moduleEl.find(".filter-ally-wrapper").length>0)checkAllProcessed();else{var data={isimage:!1,fileid:pathHash,url:$(moduleEl).attr("href")};renderTemplate(data,pathHash,moduleEl).done(checkAllProcessed)}}return dfd.promise()},buildContentIdent=function(component,table,field,id){return[component,table,field,id].join(":")},annotateSections=function(sectionMapping){var dfd=$.Deferred();for(var s in sectionMapping){var sectionId=sectionMapping[s],ident=buildContentIdent("course","course_sections","summary",sectionId);$(["#"+s+' > .content div[class*="summarytext"] .no-overflow',"body.theme-snap #"+s+" > .content > .summary > div > .no-overflow"].join(",")).attr("data-ally-richcontent",ident)}return dfd.resolve(),dfd.promise()};const annotateModuleIntros=function(introMapping,module,additionalSelectors){for(const i in introMapping){const annotation=introMapping[i],selectors=["body.path-mod-"+module+".cmid-"+i+" #intro > .no-overflow",self.config.moodleversion>=2023100900?"li.activity.modtype_"+module+"#module-"+i+" .activity-description .no-overflow > .no-overflow":"li.activity.modtype_"+module+"#module-"+i+" .description .no-overflow > .no-overflow","li.snap-activity.modtype_"+module+"#module-"+i+" .contentafterlink > .no-overflow"];if(additionalSelectors)for(const a in additionalSelectors)selectors.push(additionalSelectors[a].replace("{{i}}",i));$(selectors.join(",")).attr("data-ally-richcontent",annotation)}};var annotateLesson=function(mapping){var intros=mapping.intros;annotateModuleIntros(intros,"lesson",["li.snap-native.modtype_lesson#module-{{i}} .contentafterlink > .summary-text .no-overflow"]);var content=mapping.lesson_pages;for(var p in content)if("page-mod-lesson-edit"===document.body.id){var xpath='//a[@id="lesson-'+p+'"]//ancestor::table//tbody/tr/td/div[contains(@class, "no-overflow")]',annotation=content[p],node=getNodeByXpath(xpath);$(node).attr("data-ally-richcontent",annotation)}else{if(node=getNodeByXpath('//form[contains(@action, "continue.php")]//input[@name="pageid"]'))var pageId=$(node).val();else pageId=new URLSearchParams(window.location.search).get("pageid");if(pageId!=p)continue;annotation=content[p];$(["#page-mod-lesson-view #region-main .box.contents > .no-overflow","#page-mod-lesson-view #region-main form > fieldset > .fcontainer > .contents .no-overflow","li.snap-native.modtype_page#module-"+p+" .pagemod-content"].join(",")).attr("data-ally-richcontent",annotation)}Strings.get_strings([{key:"answer",component:"mod_lesson"},{key:"response",component:"mod_lesson"}]).then((function(strings){var answerLabel=strings[0],responseLabel=strings[1],answers=mapping.lesson_answers,processAnswerResponse=function(pageId,i,label,annotation){var nodes=function(xpath){var result=window.document.createExpression(xpath).evaluate(window.document,XPathResult.ANY_TYPE),nodes=[];do{var node=result.iterateNext();nodes.push(node)}while(node);return nodes}('//a[@id="lesson-'+pageId+'"]//ancestor::table//td/label[contains(text(),"'+label+" "+i+'")]/ancestor::tr/td[2]');for(var n in nodes){var node=nodes[n];$(node).attr("data-ally-richcontent",annotation)}};for(var a in answers){var annotation=answers[a],pageId=(tmpArr=a.split("_"))[0],ansId=tmpArr[1],anum=tmpArr[2];if("page-mod-lesson-edit"===document.body.id)processAnswerResponse(pageId,anum,answerLabel,annotation);else{if($('#page-mod-lesson-view label[for="id_answerid_'+ansId+'"]').attr("data-ally-richcontent",annotation),self.params.answerid&&self.params.answerid==ansId)$(".studentanswer tr:nth-of-type(1) > td div").attr("data-ally-richcontent",annotation);else{var answerWrapperId="answer_wrapper_"+ansId,answerEl=$("#id_answerid_"+ansId);if(1!=answerEl.data("annotated")){var contentEls=answerEl.nextAll();answerEl.parent("label").append(''),$("#"+answerWrapperId).append(contentEls)}answerEl.data("annotated",1)}$("#answer_wrapper_"+a).attr("data-ally-richcontent",annotation)}}var responses=mapping.lesson_answers_response;for(var r in responses){annotation=responses[r],pageId=(tmpArr=r.split("_"))[0];var tmpArr,respId=tmpArr[1],rnum=tmpArr[2];if("page-mod-lesson-edit"===document.body.id)processAnswerResponse(pageId,rnum,responseLabel,annotation);else if(self.params.answerid&&self.params.answerid==respId){var responseWrapperId="response_wrapper_"+respId;if(!$(".studentanswer tr.lastrow > td #"+responseWrapperId).length){contentEls=$(".studentanswer tr.lastrow > td > br").nextAll();$(".studentanswer tr.lastrow > td > br").after(''),$("#"+responseWrapperId).append(contentEls)}$("#"+responseWrapperId).attr("data-ally-richcontent",annotation)}}}))},annotateModules=function(moduleMapping){var dfd=$.Deferred();return void 0!==moduleMapping.mod_forum&&function(forumMapping){var intros=forumMapping.intros;annotateModuleIntros(intros,"forum");var discussions=forumMapping.posts;for(var d in discussions){var post="p"+d,annotation=discussions[d];$(["#page-mod-forum-discuss #"+post+" div.forumpost div.no-overflow"].join(",")).attr("data-ally-richcontent",annotation)}}(moduleMapping.mod_forum),void 0!==moduleMapping.mod_hsuforum&&function(forumMapping){var intros=forumMapping.intros;annotateModuleIntros(intros,"hsuforum",["#hsuforum-header .hsuforum_introduction > .no-overflow"]);var discussions=forumMapping.posts;for(var d in discussions){var annotation=discussions[d];$('article[id="p'+d+'"] div.posting').attr("data-ally-richcontent",annotation)}}(moduleMapping.mod_hsuforum),void 0!==moduleMapping.mod_glossary&&function(mapping){var intros=mapping.intros;annotateModuleIntros(intros,"glossary");var entries=mapping.entries;for(var e in entries){var annotation=entries[e],entryFooter=$('.entrylowersection .commands a[href*="id='+e+'"]'),entry=$(entryFooter).parents(".glossarypost").find(".entry .no-overflow");$(entry).attr("data-ally-richcontent",annotation)}}(moduleMapping.mod_glossary),void 0!==moduleMapping.mod_page&&function(mapping){var intros=mapping.intros;annotateModuleIntros(intros,"page",["li.snap-native.modtype_page#module-{{i}} .contentafterlink > .summary-text"]);var content=mapping.content;for(var c in content){var annotation=content[c],selectors=["#page-mod-page-view.cmid-".concat(c," #region-main .box.generalbox > .no-overflow"),"li.snap-native.modtype_page#module-".concat(c," .pagemod-content")];$(selectors.join(",")).attr("data-ally-richcontent",annotation)}}(moduleMapping.mod_page),void 0!==moduleMapping.mod_book&&function(mapping){var intros=mapping.intros;annotateModuleIntros(intros,"book",["li.snap-native.modtype_book#module-{{i}} .contentafterlink > .summary-text .no-overflow"]);var chapterId,content=mapping.chapters;if(self.params.chapterid)chapterId=self.params.chapterid;else{var urlParams=new URLSearchParams(window.location.search);chapterId=urlParams.get("chapterid")}$.each(content,(function(ch,annotation){chapterId==ch&&$(["#page-mod-book-view #region-main .box.generalbox.book_content > .no-overflow","li.snap-native.modtype_page#module-"+ch+" .pagemod-content"].join(",")).attr("data-ally-richcontent",annotation)}))}(moduleMapping.mod_book),void 0!==moduleMapping.mod_lesson&&annotateLesson(moduleMapping.mod_lesson),dfd.resolve(),dfd.promise()},annotateSnapCourseSummary=function(mapping){var dfd=$.Deferred(),snapFooterCourseSummary=$("#snap-course-footer-summary > div.no-overflow");if(snapFooterCourseSummary.length){var ident=buildContentIdent("course","course","summary",mapping.courseId);snapFooterCourseSummary.attr("data-ally-richcontent",ident)}return dfd.resolve(),dfd.promise()},annotateHtmlBlock=function(mapping){var dfd=$.Deferred(),items=mapping.block_html;for(var i in items){var ident=items[i],selector=["#inst"+i+".block_html > .card-body > .card-text > .no-overflow","#inst"+i+".block_html > .content > .no-overflow"].join(",");$(selector).attr("data-ally-richcontent",ident)}return dfd.resolve(),dfd.promise()},debounceApplyPlaceHolders=Util.debounce((function(){return function(){M.util.js_pending("filter_ally_applyPlaceHolders");var dfd=$.Deferred();if(void 0===ally_module_maps||void 0===ally_section_maps)return dfd.resolve(),dfd.promise();var tasks=[{mapVar:ally_module_maps.file_resources,method:placeHoldResourceModule},{mapVar:ally_module_maps.assignment_files,method:placeHoldAssignModule},{mapVar:ally_module_maps.folder_files,method:placeHoldFolderModule},{mapVar:ally_module_maps.forum_files,method:placeHoldForumModule},{mapVar:ally_module_maps.glossary_files,method:placeHoldGlossaryModule},{mapVar:ally_module_maps.lesson_files,method:placeHoldLessonModule},{mapVar:ally_section_maps,method:annotateSections},{mapVar:ally_annotation_maps,method:annotateModules},{mapVar:{courseId:self.courseId},method:annotateSnapCourseSummary},{mapVar:ally_annotation_maps,method:annotateHtmlBlock}];return $(document).ready((function(){var completed=0,onTaskComplete=function(){++completed===tasks.length&&(M.util.js_complete("filter_ally_applyPlaceHolders"),dfd.resolve())};for(var t in tasks){var task=tasks[t];Object.keys(task.mapVar).length>0?task.method(task.mapVar).done(onTaskComplete):onTaskComplete()}})),dfd.promise()}()}),1e3);this.initStageTwo=function(){const{jwt:jwt,config:config}=self;(self.canViewFeedback||self.canDownload)&&(debounceApplyPlaceHolders().done((function(){ImageCover.init(),Ally.init(jwt,config);try{var targetNode=$(".foldertree > .filemanager")[0];if(targetNode){new MutationObserver((function(mutationsList){mutationsList.filter((function(mutation){return"childList"===mutation.type})).forEach((function(){placeHoldFolderModule(ally_module_maps.folder_files)}))})).observe(targetNode,{attributes:!0,childList:!0,subtree:!0})}}catch(error){setInterval((function(){placeHoldFolderModule(ally_module_maps.folder_files)}),5e3)}self.initialised=!0})),$(document).ajaxComplete((function(){self.initialised&&debounceApplyPlaceHolders()})),$("body.theme-snap").length&&($(document).ajaxComplete((function(event,xhr,settings){settings.url.includes("ally.js")&&(setTimeout((function(){$(".ally-feedback.ally-active.ally-score-indicator-embedded span").each((function(){"none"==this.style.display&&(this.style.display="block","ally-scoreindicator-container"==this.getAttribute("class")&&(this.style.display="inline-block",this.children[0].style.display="inline-block"))}))}),5e3),$(document).off("ajaxComplete"))})),document.addEventListener("core_filters/contentUpdated",(()=>{self.initStageTwo()}))))},this.init=function(jwt,config,canViewFeedback,canDownload,courseId,params){self.canViewFeedback=canViewFeedback,self.canDownload=canDownload,self.courseId=courseId,self.params=params,self.jwt=jwt,self.config=config;var pluginJSURL=function(path){return M.cfg.wwwroot+"/pluginfile.php/"+M.cfg.contextid+"/filter_ally/"+path},polyfills={};if(document.evaluate||(polyfills["filter_ally/wgxpath"]=pluginJSURL("vendorjs/wgxpath.install")),"undefined"==typeof URLSearchParams&&(polyfills["filter_ally/urlsearchparams"]=["https://cdnjs.cloudflare.com/ajax/libs/url-search-params/1.1.0/url-search-params.amd.js",pluginJSURL("vendorjs/url-search-params.amd")]),polyfills==={})self.initStageTwo();else{require.config({enforceDefine:!1,paths:polyfills});var requires=Object.keys(polyfills);require(requires,(function(){"undefined"==typeof URLSearchParams&&(window.URLSearchParams=arguments[1]),self.initStageTwo()}))}}}})); //# sourceMappingURL=main.min.js.map \ No newline at end of file diff --git a/amd/build/main.min.js.map b/amd/build/main.min.js.map index 9804d4f..a843421 100644 --- a/amd/build/main.min.js.map +++ b/amd/build/main.min.js.map @@ -1 +1 @@ -{"version":3,"file":"main.min.js","sources":["../src/main.js"],"sourcesContent":["/**\n * 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 * Main library.\n *\n * @package\n * @author Guy Thomas\n * @copyright Copyright (c) 2016 Open LMS / 2023 Anthology Inc. and its affiliates\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\n\ndefine(['jquery', 'core/templates', 'core/str', 'filter_ally/ally',\n 'filter_ally/imagecover', 'filter_ally/util'],\nfunction($, Templates, Strings, Ally, ImageCover, Util) {\n return new function() {\n\n var self = this;\n\n self.canViewFeedback = false;\n self.canDownload = false;\n self.initialised = false;\n self.params = {};\n\n /**\n * Get nodes by xpath.\n * @param {string} xpath\n * @returns {Array}\n */\n var getNodesByXpath = function(xpath) {\n var expression = window.document.createExpression(xpath);\n var result = expression.evaluate(window.document, XPathResult.ANY_TYPE);\n var nodes = [];\n do {\n var node = result.iterateNext();\n nodes.push(node);\n } while (node);\n return nodes;\n };\n\n /**\n * Get single node by xpath.\n * @param {string} xpath\n * @returns {Node}\n */\n var getNodeByXpath = function(xpath) {\n var expression = window.document.createExpression(xpath);\n var result = expression.evaluate(window.document, XPathResult.FIRST_ORDERED_NODE_TYPE);\n return result.singleNodeValue;\n };\n\n /**\n * Render template and insert result in appropriate place.\n * @param {object} data\n * @param {string} pathHash\n * @param {node} targetEl\n * @return {promise}\n */\n var renderTemplate = function(data, pathHash, targetEl) {\n var dfd = $.Deferred();\n\n if ($(targetEl).parents('.filter-ally-wrapper').length) {\n // This has already been processed.\n dfd.resolve();\n return dfd.promise();\n }\n\n // Too expensive to do at module level - this is a course level capability.\n data.canviewfeedback = self.canViewFeedback;\n data.candownload = self.canDownload;\n data.html = '';\n\n Templates.render('filter_ally/wrapper', data)\n .done(function(result) {\n var presentWrappers = $(targetEl).next().find('span[data-file-id=\"' + pathHash + '\"]');\n if (presentWrappers.length == 0) {\n $(targetEl).after(result);\n\n // We are inserting the module element next to the target as opposed to replacing the\n // target as we want to ensure any listeners attributed to the module element persist.\n $('#content-target-' + pathHash).after(targetEl);\n $('#content-target-' + pathHash).remove();\n }\n dfd.resolve();\n });\n\n return dfd.promise();\n };\n\n /**\n * Place holder items that are matched by selector.\n * @param {string} selector\n * @param {string} map\n * @return {promise}\n */\n var placeHoldSelector = function(selector, map) {\n var dfd = $.Deferred();\n\n var c = 0;\n\n var length = $(selector).length;\n if (!length) {\n dfd.resolve();\n }\n $(selector).each(function() {\n\n /**\n * Check that all selectors have been processed.\n */\n var checkComplete = function() {\n if (c === length) {\n dfd.resolve();\n }\n };\n var url,\n type;\n\n if ($(this).prop(\"tagName\").toLowerCase() === 'a') {\n url = $(this).attr('href');\n type = 'a';\n } else {\n url = $(this).attr('src');\n type = 'img';\n }\n var regex;\n if (url.indexOf('?') > -1) {\n regex = /pluginfile.php\\/(\\d*)\\/(.*)(\\?)/;\n } else {\n regex = /pluginfile.php\\/(\\d*)\\/(.*)/;\n }\n var match = url.match(regex);\n var pathHash;\n if (match) {\n var path = match[1] + '/' + match[2];\n path = decodeURIComponent(path);\n pathHash = map[path];\n }\n\n if (pathHash === undefined) {\n // Maybe 'slasharguments' setting is disabled for this host.\n // Let's see if the file URI is found in the URL query.\n var query = Util.getQuery(url);\n if (query.file) {\n var filePath = decodeURIComponent(query.file);\n regex = /\\/(\\d*)\\/(.*)/;\n\n match = filePath.match(regex);\n if (match) {\n path = match[1] + '/' + match[2];\n path = decodeURIComponent(path);\n pathHash = map[path];\n }\n }\n }\n\n // Pathhash was definitely not found :( .\n if (pathHash === undefined) {\n c++;\n checkComplete();\n return;\n }\n\n var data = {\n isimage: type === 'img',\n fileid: pathHash,\n url: url\n };\n\n renderTemplate(data, pathHash, $(this))\n .done(function() {\n c++;\n checkComplete();\n });\n });\n return dfd.promise();\n };\n\n /**\n * Add place holders for forum module image attachments (note, regular files are covered by php).\n * @param {array} forumFileMapping\n * @return {promise}\n */\n var placeHoldForumModule = function(forumFileMapping) {\n var dfd = $.Deferred();\n placeHoldSelector('.forumpost .attachedimages img[src*=\"pluginfile.php\"], ' +\n '.forumpost .body-content-container a[href*=\"pluginfile.php\"]', forumFileMapping)\n .done(function() {\n dfd.resolve();\n });\n return dfd.promise();\n };\n\n /**\n * Add place holders for assign module additional files.\n * @param {array} assignFileMapping\n * @return {promise}\n */\n var placeHoldAssignModule = function(assignFileMapping) {\n var dfd = $.Deferred();\n Util.whenTrue(function() {\n return $('div[id*=\"assign_files_tree\"] .ygtvitem').length > 0;\n }, 10)\n .done(function() {\n placeHoldSelector('div[id*=\"assign_files_tree\"] a[href*=\"pluginfile.php\"]', assignFileMapping);\n dfd.resolve();\n });\n return dfd.promise();\n };\n\n /**\n * Add place holders for folder module files.\n * @param {array} folderFileMapping\n * @return {promise}\n */\n var placeHoldFolderModule = function(folderFileMapping) {\n var dfd = $.Deferred();\n Util.whenTrue(function() {\n return $('.foldertree > .filemanager .ygtvitem').length > 0;\n }, 10)\n .done(function() {\n var unwrappedlinks = '.foldertree > .filemanager span:not(.filter-ally-wrapper) > a[href*=\"pluginfile.php\"]';\n placeHoldSelector(unwrappedlinks, folderFileMapping)\n .done(function() {\n dfd.resolve();\n });\n });\n return dfd.promise();\n };\n\n /**\n * Add place holders for glossary module files.\n * @param {array} glossaryFileMapping\n * @return {promise}\n */\n var placeHoldGlossaryModule = function(glossaryFileMapping) {\n var dfd = $.Deferred();\n\n // Glossary attachment markup is terrible!\n // The first thing we need to do is rewrite the glossary attachments so that they are encapsulated.\n $('.entry .attachments > br').each(function() {\n var mainAnchor = $(this).prev('a[href*=\"pluginfile.php\"]');\n mainAnchor.addClass('ally-glossary-attachment');\n var iconAnchor = $(mainAnchor).prev('a[href*=\"pluginfile.php\"]');\n $(this).after('
');\n var container = $(this).next('.ally-glossary-attachment-row');\n container.append(iconAnchor);\n container.append(mainAnchor);\n $(this).remove();\n });\n\n var unwrappedlinks = '.entry .attachments .ally-glossary-attachment';\n placeHoldSelector(unwrappedlinks, glossaryFileMapping)\n .done(function() {\n dfd.resolve();\n });\n return dfd.promise();\n };\n\n /**\n * Encode a file path so that it can be used to find things by uri.\n * @param {string} filePath\n * @returns {string}\n */\n var urlEncodeFilePath = function(filePath) {\n var parts = filePath.split('/');\n for (var p in parts) {\n parts[p] = encodeURIComponent(parts[p]);\n }\n var encoded = parts.join('/');\n return encoded;\n };\n\n /**\n * General function for finding lesson component file elements and then add mapping.\n * @param {array} map\n * @param {string} selectorPrefix\n * @return promise\n */\n var placeHoldLessonGeneral = function(map, selectorPrefix) {\n var dfd = $.Deferred();\n if (map.length === 0) {\n dfd.resolve();\n } else {\n for (var c in map) {\n var path = urlEncodeFilePath(c);\n var sel = selectorPrefix + 'img[src*=\"' + path + '\"], ' + selectorPrefix + 'a[href*=\"' + path + '\"]';\n placeHoldSelector(sel, map).done(function() {\n dfd.resolve();\n });\n }\n }\n return dfd.promise();\n };\n\n /**\n * Placehold lesson page contents.\n * @param {array} pageContentsMap\n * @returns promise\n */\n var placeHoldLessonPageContents = function(pageContentsMap) {\n return placeHoldLessonGeneral(pageContentsMap, '');\n };\n\n /**\n * Placehold lesson answers.\n * @param {array} pageAnswersMap\n * @returns promise\n */\n var placeHoldLessonAnswersContent = function(pageAnswersMap) {\n return placeHoldLessonGeneral(pageAnswersMap,\n '.studentanswer table tr:nth-child(1) '); // Space at end of selector intended.\n };\n\n /**\n * Placehold lesson responses.\n * @param {array} pageResponsesMap\n * @returns promise\n */\n var placeHoldLessonResponsesContent = function(pageResponsesMap) {\n return placeHoldLessonGeneral(pageResponsesMap,\n '.studentanswer table tr.lastrow '); // Space at end of selector intended.\n };\n\n /**\n * Add place holders for lesson module files.\n * @param {array} lessonFileMapping\n * @return {promise}\n */\n var placeHoldLessonModule = function(lessonFileMapping) {\n var dfd = $.Deferred();\n\n var pageContentsMap = lessonFileMapping.page_contents;\n var pageAnswersMap = lessonFileMapping.page_answers;\n var pageResponsesMap = lessonFileMapping.page_responses;\n\n placeHoldLessonPageContents(pageContentsMap)\n .then(function() {\n return placeHoldLessonAnswersContent(pageAnswersMap);\n })\n .then(function() {\n return placeHoldLessonResponsesContent(pageResponsesMap);\n })\n .then(function() {\n dfd.resolve();\n });\n return dfd.promise();\n };\n\n /**\n * Add place holders for resource module.\n * @param {object} moduleFileMapping\n * @return {promise}\n */\n var placeHoldResourceModule = function(moduleFileMapping) {\n var dfd = $.Deferred();\n var c = 0;\n\n /**\n * Once all modules processed, resolve promise for this function.\n */\n var checkAllProcessed = function() {\n c++;\n // All resource modules have been dealt with.\n if (c >= Object.keys(moduleFileMapping).length) {\n dfd.resolve();\n }\n };\n for (var moduleId in moduleFileMapping) {\n var pathHash = moduleFileMapping[moduleId].content;\n if ($('body').hasClass('theme-snap') && !$('body').hasClass('format-tiles')) {\n var moduleEl = $('#module-' + moduleId + ':not(.snap-native) .activityinstance ' +\n '.snap-asset-link a:first-of-type:not(.clickable-region)');\n } else {\n var moduleEl = $('#module-' + moduleId + ' .activity-instance ' +\n 'a:first-of-type:not(.clickable-region,.editing_move)');\n }\n var processed = moduleEl.find('.filter-ally-wrapper');\n if (processed.length > 0) {\n checkAllProcessed(); // Already processed.\n continue;\n }\n var data = {\n isimage: false,\n fileid: pathHash,\n url: $(moduleEl).attr('href')\n };\n renderTemplate(data, pathHash, moduleEl)\n .done(checkAllProcessed);\n }\n return dfd.promise();\n };\n\n var buildContentIdent = function(component, table, field, id) {\n return [component, table, field, id].join(':');\n };\n\n /**\n * Add annotations to sections content.\n * @param {array} sectionMapping\n */\n var annotateSections = function(sectionMapping) {\n var dfd = $.Deferred();\n\n for (var s in sectionMapping) {\n var sectionId = sectionMapping[s];\n var ident = buildContentIdent('course', 'course_sections', 'summary', sectionId);\n\n var selectors = [\n '#' + s + ' > .content div[class*=\"summarytext\"] .no-overflow',\n 'body.theme-snap #' + s + ' > .content > .summary > div > .no-overflow' // Snap.\n ];\n $(selectors.join(',')).attr('data-ally-richcontent', ident);\n }\n\n dfd.resolve();\n return dfd.promise();\n };\n\n /**\n * Annotate module introductions.\n * @param {array} introMapping\n * @param {string} module\n * @param {array} additionalSelectors\n */\n var annotateModuleIntros = function(introMapping, module, additionalSelectors) {\n for (var i in introMapping) {\n var annotation = introMapping[i];\n var selectors = [\n 'body.path-mod-' + module + '.cmid-' + i + ' #intro > .no-overflow',\n // We need to be specific here for non course pages to skip this.\n 'li.activity.modtype_' + module + '#module-' + i + ' .description .no-overflow > .no-overflow',\n 'li.snap-activity.modtype_' + module + '#module-' + i + ' .contentafterlink > .no-overflow'\n ];\n if (additionalSelectors) {\n for (var a in additionalSelectors) {\n selectors.push(additionalSelectors[a].replace('{{i}}', i));\n }\n }\n $(selectors.join(',')).attr('data-ally-richcontent', annotation);\n }\n };\n\n /**\n * Add annotations to forums.\n * @param {array} forumMapping\n */\n var annotateForums = function(forumMapping) {\n // Annotate introductions.\n var intros = forumMapping.intros;\n annotateModuleIntros(intros, 'forum');\n\n // Annotate discussions.\n var discussions = forumMapping.posts;\n for (var d in discussions) {\n var post = 'p' + d;\n var annotation = discussions[d];\n var selectors = [\n \"#page-mod-forum-discuss #\" + post +\n ' div.forumpost div.no-overflow'\n ];\n $(selectors.join(',')).attr('data-ally-richcontent', annotation);\n }\n };\n\n /**\n * Add annotations to Open Forums.\n * @param {array} forumMapping\n */\n var annotateMRForums = function(forumMapping) {\n\n // Annotate introductions.\n var intros = forumMapping.intros;\n annotateModuleIntros(intros, 'hsuforum', ['#hsuforum-header .hsuforum_introduction > .no-overflow']);\n\n var discussions = forumMapping.posts;\n for (var d in discussions) {\n var annotation = discussions[d];\n var postSelector = 'article[id=\"p' + d + '\"] div.posting';\n $(postSelector).attr('data-ally-richcontent', annotation);\n }\n };\n\n /**\n * Add annotations to glossary.\n * @param {array} mapping\n */\n var annotateGlossary = function(mapping) {\n // Annotate introductions.\n var intros = mapping.intros;\n annotateModuleIntros(intros, 'glossary');\n\n // Annotate entries.\n var entries = mapping.entries;\n for (var e in entries) {\n var annotation = entries[e];\n var entryFooter = $('.entrylowersection .commands a[href*=\"id=' + e + '\"]');\n var entry = $(entryFooter).parents('.glossarypost').find('.entry .no-overflow');\n $(entry).attr('data-ally-richcontent', annotation);\n }\n };\n\n /**\n * Add annotations to page.\n * @param {array} mapping\n */\n var annotatePage = function(mapping) {\n var intros = mapping.intros;\n annotateModuleIntros(intros, 'page', ['li.snap-native.modtype_page#module-{{i}} .contentafterlink > .summary-text']);\n\n // Annotate content.\n var content = mapping.content;\n for (var c in content) {\n var annotation = content[c];\n var selectors = [\n `#page-mod-page-view.cmid-${c} #region-main .box.generalbox > .no-overflow`,\n `li.snap-native.modtype_page#module-${c} .pagemod-content`\n ];\n $(selectors.join(',')).attr('data-ally-richcontent', annotation);\n }\n };\n\n /**\n * Add annotations to book.\n * @param {array} mapping\n */\n var annotateBook = function(mapping) {\n var intros = mapping.intros;\n\n // For book, the only place the intro shows is on the course page when you select \"display description on course page\"\n // in the module settings.\n annotateModuleIntros(intros, 'book',\n ['li.snap-native.modtype_book#module-{{i}} .contentafterlink > .summary-text .no-overflow']);\n\n // Annotate content.\n var content = mapping.chapters,\nchapterId;\n\n if (self.params.chapterid) {\n chapterId = self.params.chapterid;\n } else {\n var urlParams = new URLSearchParams(window.location.search);\n chapterId = urlParams.get('chapterid');\n }\n\n $.each(content, function(ch, annotation) {\n if (chapterId != ch) {\n return;\n }\n var selectors = [\n '#page-mod-book-view #region-main .box.generalbox.book_content > .no-overflow',\n 'li.snap-native.modtype_page#module-' + ch + ' .pagemod-content'\n ];\n $(selectors.join(',')).attr('data-ally-richcontent', annotation);\n });\n };\n\n /**\n * Add annotations to lesson.\n * @param {array} mapping\n */\n var annotateLesson = function(mapping) {\n var intros = mapping.intros;\n\n // For lesson, the only place the intro shows is on the course page when you select \"display description on course page\"\n // in the module settings.\n annotateModuleIntros(intros, 'lesson',\n ['li.snap-native.modtype_lesson#module-{{i}} .contentafterlink > .summary-text .no-overflow']);\n\n // Annotate content.\n var content = mapping.lesson_pages;\n for (var p in content) {\n if (document.body.id === \"page-mod-lesson-edit\") {\n var xpath = '//a[@id=\"lesson-' + p + '\"]//ancestor::table//tbody/tr/td/div[contains(@class, \"no-overflow\")]';\n var annotation = content[p];\n var node = getNodeByXpath(xpath);\n $(node).attr('data-ally-richcontent', annotation);\n } else {\n // Try get page from form.\n var node = getNodeByXpath('//form[contains(@action, \"continue.php\")]//input[@name=\"pageid\"]');\n if (node) {\n var pageId = $(node).val();\n } else {\n var urlParams = new URLSearchParams(window.location.search);\n var pageId = urlParams.get('pageid');\n }\n\n if (pageId != p) {\n continue;\n }\n var annotation = content[p];\n var selectors = [\n // Regular page.\n '#page-mod-lesson-view #region-main .box.contents > .no-overflow',\n // Question page.\n '#page-mod-lesson-view #region-main form > fieldset > .fcontainer > .contents .no-overflow',\n // Lesson page.\n 'li.snap-native.modtype_page#module-' + p + ' .pagemod-content'\n ];\n\n $(selectors.join(',')).attr('data-ally-richcontent', annotation);\n }\n }\n\n // Annotate answer answers.\n Strings.get_strings([\n {key: 'answer', component: 'mod_lesson'},\n {key: 'response', component: 'mod_lesson'}\n ]).then(function(strings) {\n var answerLabel = strings[0];\n var responseLabel = strings[1];\n var answers = mapping.lesson_answers;\n\n var processAnswerResponse = function(pageId, i, label, annotation) {\n var xpath = '//a[@id=\"lesson-' + pageId + '\"]//ancestor::table' +\n '//td/label[contains(text(),\"' + label + ' ' + i + '\")]/ancestor::tr/td[2]';\n var nodes = getNodesByXpath(xpath);\n for (var n in nodes) {\n var node = nodes[n];\n $(node).attr('data-ally-richcontent', annotation);\n }\n };\n\n for (var a in answers) {\n // Increment anum so that we can get the answer number.\n // Note, we can trust that this is correct because you can't order answers and the code in the lesson component\n // orders answers by id.\n var annotation = answers[a];\n\n var tmpArr = a.split('_');\n var pageId = tmpArr[0];\n var ansId = tmpArr[1];\n var anum = tmpArr[2];\n\n // Process answers when on lesson edit page.\n if (document.body.id === \"page-mod-lesson-edit\") {\n processAnswerResponse(pageId, anum, answerLabel, annotation);\n } else {\n // Wrap answers in labels.\n $('#page-mod-lesson-view label[for=\"id_answerid_' + ansId + '\"]').attr('data-ally-richcontent', annotation);\n\n if (self.params.answerid && self.params.answerid == ansId) {\n $('.studentanswer tr:nth-of-type(1) > td div').attr('data-ally-richcontent', annotation);\n } else {\n var answerWrapperId = 'answer_wrapper_' + ansId;\n var answerEl = $('#id_answerid_' + ansId);\n if (answerEl.data('annotated') != 1) {\n // We only want to wrap this once.\n var contentEls = answerEl.nextAll();\n answerEl.parent('label').append('');\n $('#' + answerWrapperId).append(contentEls);\n }\n answerEl.data('annotated', 1);\n }\n $('#answer_wrapper_' + a).attr('data-ally-richcontent', annotation);\n }\n }\n\n // Annotate answer responses.\n var responses = mapping.lesson_answers_response;\n for (var r in responses) {\n var annotation = responses[r];\n\n var tmpArr = r.split('_');\n var pageId = tmpArr[0];\n var respId = tmpArr[1];\n var rnum = tmpArr[2];\n\n if (document.body.id === \"page-mod-lesson-edit\") {\n processAnswerResponse(pageId, rnum, responseLabel, annotation);\n } else if (self.params.answerid && self.params.answerid == respId) {\n // Just incase you are wondering, yes answer ids ^ are the same as response ids ;-).\n var responseWrapperId = 'response_wrapper_' + respId;\n if (!$('.studentanswer tr.lastrow > td #' + responseWrapperId).length) {\n // We only want to wrap this once, hence above ! length check.\n var contentEls = $('.studentanswer tr.lastrow > td > br').nextAll();\n $('.studentanswer tr.lastrow > td > br').after('');\n $('#' + responseWrapperId).append(contentEls);\n }\n\n $('#' + responseWrapperId).attr('data-ally-richcontent', annotation);\n }\n\n }\n });\n };\n\n /**\n * Annotate supported modules\n * @param {array} moduleMapping\n */\n var annotateModules = function(moduleMapping) {\n var dfd = $.Deferred();\n if (moduleMapping.mod_forum !== undefined) {\n annotateForums(moduleMapping.mod_forum);\n }\n if (moduleMapping.mod_hsuforum !== undefined) {\n annotateMRForums(moduleMapping.mod_hsuforum);\n }\n if (moduleMapping.mod_glossary !== undefined) {\n annotateGlossary(moduleMapping.mod_glossary);\n }\n if (moduleMapping.mod_page !== undefined) {\n annotatePage(moduleMapping.mod_page);\n }\n if (moduleMapping.mod_book !== undefined) {\n annotateBook(moduleMapping.mod_book);\n }\n if (moduleMapping.mod_lesson !== undefined) {\n annotateLesson(moduleMapping.mod_lesson);\n }\n dfd.resolve();\n return dfd.promise();\n };\n\n /**\n * Annotates course summary if found on footer.\n * @param {object} mapping\n */\n var annotateSnapCourseSummary = function(mapping) {\n var dfd = $.Deferred();\n var snapFooterCourseSummary = $('#snap-course-footer-summary > div.no-overflow');\n if (snapFooterCourseSummary.length) {\n var ident = buildContentIdent('course', 'course', 'summary', mapping.courseId);\n snapFooterCourseSummary.attr('data-ally-richcontent', ident);\n }\n dfd.resolve();\n return dfd.promise();\n };\n\n /**\n * Annotate html block.\n * @param {object} mapping\n */\n var annotateHtmlBlock = function(mapping) {\n var dfd = $.Deferred();\n\n var items = mapping.block_html;\n for (var i in items) {\n var ident = items[i];\n var selectors = [\n '#inst' + i + '.block_html > .card-body > .card-text > .no-overflow',\n '#inst' + i + '.block_html > .content > .no-overflow'\n ];\n var selector = selectors.join(',');\n $(selector).attr('data-ally-richcontent', ident);\n }\n dfd.resolve();\n return dfd.promise();\n };\n\n /**\n * Apply place holders and add annotations to content.\n * @return {promise}\n */\n var applyPlaceHolders = function() {\n M.util.js_pending('filter_ally_applyPlaceHolders');\n var dfd = $.Deferred();\n\n if (ally_module_maps === undefined || ally_section_maps === undefined) {\n dfd.resolve();\n return dfd.promise();\n }\n\n var tasks = [{\n mapVar: ally_module_maps.file_resources,\n method: placeHoldResourceModule\n },\n {\n mapVar: ally_module_maps.assignment_files,\n method: placeHoldAssignModule\n },\n {\n mapVar: ally_module_maps.folder_files,\n method: placeHoldFolderModule\n },\n {\n mapVar: ally_module_maps.forum_files,\n method: placeHoldForumModule\n },\n {\n mapVar: ally_module_maps.glossary_files,\n method: placeHoldGlossaryModule\n },\n {\n mapVar: ally_module_maps.lesson_files,\n method: placeHoldLessonModule\n },\n {\n mapVar: ally_section_maps,\n method: annotateSections\n },\n {\n mapVar: ally_annotation_maps,\n method: annotateModules\n },\n {\n mapVar: {courseId: self.courseId},\n method: annotateSnapCourseSummary\n },\n {\n mapVar: ally_annotation_maps,\n method: annotateHtmlBlock\n }];\n\n $(document).ready(function() {\n var completed = 0;\n /**\n * Run this once a task has resolved.\n */\n var onTaskComplete = function() {\n completed++;\n if (completed === tasks.length) {\n // All tasks completed.\n M.util.js_complete('filter_ally_applyPlaceHolders');\n dfd.resolve();\n }\n };\n\n for (var t in tasks) {\n var task = tasks[t];\n if (Object.keys(task.mapVar).length > 0) {\n task.method(task.mapVar)\n .done(onTaskComplete);\n } else {\n // Skipped this task because mappings are empty.\n onTaskComplete();\n }\n }\n });\n return dfd.promise();\n };\n\n var debounceApplyPlaceHolders = Util.debounce(function() {\n return applyPlaceHolders();\n }, 1000);\n\n /**\n * Initialise JS stage two.\n */\n this.initStageTwo = function() {\n const {jwt, config} = self;\n if (self.canViewFeedback || self.canDownload) {\n debounceApplyPlaceHolders()\n .done(function() {\n ImageCover.init();\n Ally.init(jwt, config);\n try {\n var selector = $('.foldertree > .filemanager');\n var targetNode = selector[0];\n if (targetNode) {\n var observerConfig = {attributes: true, childList: true, subtree: true};\n var callback = function(mutationsList) {\n mutationsList.filter(function(mutation) {\n return mutation.type === 'childList';\n }).forEach(function() {\n placeHoldFolderModule(ally_module_maps.folder_files);\n });\n };\n var observer = new MutationObserver(callback);\n observer.observe(targetNode, observerConfig);\n }\n } catch (error) {\n setInterval(function() {\n placeHoldFolderModule(ally_module_maps.folder_files);\n }, 5000);\n }\n self.initialised = true;\n });\n\n $(document).ajaxComplete(function() {\n if (!self.initialised) {\n return;\n }\n debounceApplyPlaceHolders();\n });\n // For Snap theme.\n if ($('body.theme-snap').length) {\n $(document).ajaxComplete(function(event, xhr, settings) {\n // Search ally server response.\n if (settings.url.includes('ally.js')) {\n setTimeout(function() {\n // Show score icons that are hidden, see INT-18688.\n $('.ally-feedback.ally-active.ally-score-indicator-embedded span').each(function() {\n if (this.style.display == 'none') {\n this.style.display = 'block';\n if (this.getAttribute('class') == 'ally-scoreindicator-container') {\n this.style.display = 'inline-block';\n this.children[0].style.display = 'inline-block';\n }\n }\n });\n }, 5000);\n $(document).off('ajaxComplete');\n }\n });\n\n document.addEventListener('core_filters/contentUpdated', () => {\n // When Snap lazy loads a section it triggers this event.\n // We can ensure everything has been processed on lazy load by recalling the second\n // stage initialization.\n self.initStageTwo();\n });\n }\n }\n };\n\n /**\n * Init function.\n * @param {string} jwt\n * @param {object} config\n * @param {boolean} canViewFeedback\n * @param {boolean} canDownload\n * @param {int} courseId\n * @param {object} params\n */\n this.init = function(jwt, config, canViewFeedback, canDownload, courseId, params) {\n\n self.canViewFeedback = canViewFeedback;\n self.canDownload = canDownload;\n self.courseId = courseId;\n self.params = params;\n self.jwt = jwt;\n self.config = config;\n\n var pluginJSURL = function(path) {\n return M.cfg.wwwroot + \"/pluginfile.php/\" + M.cfg.contextid + \"/filter_ally/\" + path;\n };\n\n var polyfills = {};\n if (!document.evaluate) {\n polyfills['filter_ally/wgxpath'] = pluginJSURL(\"vendorjs/wgxpath.install\");\n }\n if (typeof (URLSearchParams) === 'undefined') {\n polyfills['filter_ally/urlsearchparams'] = [\n 'https://cdnjs.cloudflare.com/ajax/libs/url-search-params/1.1.0/url-search-params.amd.js',\n pluginJSURL('vendorjs/url-search-params.amd') // CDN fallback.\n ];\n }\n if (polyfills !== {}) {\n // Polyfill document.evaluate.\n require.config(\n {\n enforceDefine: false,\n paths: polyfills\n }\n );\n var requires = Object.keys(polyfills);\n\n require(requires, function() {\n if (typeof (URLSearchParams) === 'undefined') {\n window.URLSearchParams = arguments[1]; // Second arg in require (which is URLSearchParams)\n }\n self.initStageTwo();\n });\n\n return;\n }\n self.initStageTwo();\n };\n }();\n});\n"],"names":["define","$","Templates","Strings","Ally","ImageCover","Util","self","this","canViewFeedback","canDownload","initialised","params","getNodeByXpath","xpath","window","document","createExpression","evaluate","XPathResult","FIRST_ORDERED_NODE_TYPE","singleNodeValue","renderTemplate","data","pathHash","targetEl","dfd","Deferred","parents","length","resolve","promise","canviewfeedback","candownload","html","render","done","result","next","find","after","remove","placeHoldSelector","selector","map","c","each","url","type","regex","checkComplete","prop","toLowerCase","attr","indexOf","match","path","decodeURIComponent","undefined","query","getQuery","file","isimage","fileid","placeHoldForumModule","forumFileMapping","placeHoldAssignModule","assignFileMapping","whenTrue","placeHoldFolderModule","folderFileMapping","placeHoldGlossaryModule","glossaryFileMapping","mainAnchor","prev","addClass","iconAnchor","container","append","urlEncodeFilePath","filePath","parts","split","p","encodeURIComponent","join","placeHoldLessonGeneral","selectorPrefix","placeHoldLessonModule","lessonFileMapping","pageContentsMap","page_contents","pageAnswersMap","page_answers","pageResponsesMap","page_responses","placeHoldLessonPageContents","then","placeHoldLessonAnswersContent","placeHoldLessonResponsesContent","placeHoldResourceModule","moduleFileMapping","checkAllProcessed","Object","keys","moduleId","content","hasClass","moduleEl","buildContentIdent","component","table","field","id","annotateSections","sectionMapping","s","sectionId","ident","annotateModuleIntros","introMapping","module","additionalSelectors","i","annotation","selectors","a","push","replace","annotateLesson","mapping","intros","lesson_pages","body","node","pageId","val","URLSearchParams","location","search","get","get_strings","key","strings","answerLabel","responseLabel","answers","lesson_answers","processAnswerResponse","label","nodes","ANY_TYPE","iterateNext","getNodesByXpath","n","tmpArr","ansId","anum","answerid","answerWrapperId","answerEl","contentEls","nextAll","parent","responses","lesson_answers_response","r","respId","rnum","responseWrapperId","annotateModules","moduleMapping","mod_forum","forumMapping","discussions","posts","d","post","annotateForums","mod_hsuforum","annotateMRForums","mod_glossary","entries","e","entryFooter","entry","annotateGlossary","mod_page","annotatePage","mod_book","chapterId","chapters","chapterid","urlParams","ch","annotateBook","mod_lesson","annotateSnapCourseSummary","snapFooterCourseSummary","courseId","annotateHtmlBlock","items","block_html","debounceApplyPlaceHolders","debounce","M","util","js_pending","ally_module_maps","ally_section_maps","tasks","mapVar","file_resources","method","assignment_files","folder_files","forum_files","glossary_files","lesson_files","ally_annotation_maps","ready","completed","onTaskComplete","js_complete","t","task","applyPlaceHolders","initStageTwo","jwt","config","init","targetNode","MutationObserver","mutationsList","filter","mutation","forEach","observe","attributes","childList","subtree","error","setInterval","ajaxComplete","event","xhr","settings","includes","setTimeout","style","display","getAttribute","children","off","addEventListener","pluginJSURL","cfg","wwwroot","contextid","polyfills","require","enforceDefine","paths","requires","arguments"],"mappings":"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"} \ No newline at end of file +{"version":3,"file":"main.min.js","sources":["../src/main.js"],"sourcesContent":["/**\n * 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 * Main library.\n *\n * @package\n * @author Guy Thomas\n * @copyright Copyright (c) 2016 Open LMS / 2023 Anthology Inc. and its affiliates\n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\n\ndefine(['jquery', 'core/templates', 'core/str', 'filter_ally/ally',\n 'filter_ally/imagecover', 'filter_ally/util'],\nfunction($, Templates, Strings, Ally, ImageCover, Util) {\n return new function() {\n\n var self = this;\n\n self.canViewFeedback = false;\n self.canDownload = false;\n self.initialised = false;\n self.params = {};\n\n /**\n * Get nodes by xpath.\n * @param {string} xpath\n * @returns {Array}\n */\n var getNodesByXpath = function(xpath) {\n var expression = window.document.createExpression(xpath);\n var result = expression.evaluate(window.document, XPathResult.ANY_TYPE);\n var nodes = [];\n do {\n var node = result.iterateNext();\n nodes.push(node);\n } while (node);\n return nodes;\n };\n\n /**\n * Get single node by xpath.\n * @param {string} xpath\n * @returns {Node}\n */\n var getNodeByXpath = function(xpath) {\n var expression = window.document.createExpression(xpath);\n var result = expression.evaluate(window.document, XPathResult.FIRST_ORDERED_NODE_TYPE);\n return result.singleNodeValue;\n };\n\n /**\n * Render template and insert result in appropriate place.\n * @param {object} data\n * @param {string} pathHash\n * @param {node} targetEl\n * @return {promise}\n */\n var renderTemplate = function(data, pathHash, targetEl) {\n var dfd = $.Deferred();\n\n if ($(targetEl).parents('.filter-ally-wrapper').length) {\n // This has already been processed.\n dfd.resolve();\n return dfd.promise();\n }\n\n // Too expensive to do at module level - this is a course level capability.\n data.canviewfeedback = self.canViewFeedback;\n data.candownload = self.canDownload;\n data.html = '';\n\n Templates.render('filter_ally/wrapper', data)\n .done(function(result) {\n var presentWrappers = $(targetEl).next().find('span[data-file-id=\"' + pathHash + '\"]');\n if (presentWrappers.length == 0) {\n $(targetEl).after(result);\n\n // We are inserting the module element next to the target as opposed to replacing the\n // target as we want to ensure any listeners attributed to the module element persist.\n $('#content-target-' + pathHash).after(targetEl);\n $('#content-target-' + pathHash).remove();\n }\n dfd.resolve();\n });\n\n return dfd.promise();\n };\n\n /**\n * Place holder items that are matched by selector.\n * @param {string} selector\n * @param {string} map\n * @return {promise}\n */\n var placeHoldSelector = function(selector, map) {\n var dfd = $.Deferred();\n\n var c = 0;\n\n var length = $(selector).length;\n if (!length) {\n dfd.resolve();\n }\n $(selector).each(function() {\n\n /**\n * Check that all selectors have been processed.\n */\n var checkComplete = function() {\n if (c === length) {\n dfd.resolve();\n }\n };\n var url,\n type;\n\n if ($(this).prop(\"tagName\").toLowerCase() === 'a') {\n url = $(this).attr('href');\n type = 'a';\n } else {\n url = $(this).attr('src');\n type = 'img';\n }\n var regex;\n if (url.indexOf('?') > -1) {\n regex = /pluginfile.php\\/(\\d*)\\/(.*)(\\?)/;\n } else {\n regex = /pluginfile.php\\/(\\d*)\\/(.*)/;\n }\n var match = url.match(regex);\n var pathHash;\n if (match) {\n var path = match[1] + '/' + match[2];\n path = decodeURIComponent(path);\n pathHash = map[path];\n }\n\n if (pathHash === undefined) {\n // Maybe 'slasharguments' setting is disabled for this host.\n // Let's see if the file URI is found in the URL query.\n var query = Util.getQuery(url);\n if (query.file) {\n var filePath = decodeURIComponent(query.file);\n regex = /\\/(\\d*)\\/(.*)/;\n\n match = filePath.match(regex);\n if (match) {\n path = match[1] + '/' + match[2];\n path = decodeURIComponent(path);\n pathHash = map[path];\n }\n }\n }\n\n // Pathhash was definitely not found :( .\n if (pathHash === undefined) {\n c++;\n checkComplete();\n return;\n }\n\n var data = {\n isimage: type === 'img',\n fileid: pathHash,\n url: url\n };\n\n renderTemplate(data, pathHash, $(this))\n .done(function() {\n c++;\n checkComplete();\n });\n });\n return dfd.promise();\n };\n\n /**\n * Add place holders for forum module image attachments (note, regular files are covered by php).\n * @param {array} forumFileMapping\n * @return {promise}\n */\n var placeHoldForumModule = function(forumFileMapping) {\n var dfd = $.Deferred();\n placeHoldSelector('.forumpost .attachedimages img[src*=\"pluginfile.php\"], ' +\n '.forumpost .body-content-container a[href*=\"pluginfile.php\"]', forumFileMapping)\n .done(function() {\n dfd.resolve();\n });\n return dfd.promise();\n };\n\n /**\n * Add place holders for assign module additional files.\n * @param {array} assignFileMapping\n * @return {promise}\n */\n var placeHoldAssignModule = function(assignFileMapping) {\n var dfd = $.Deferred();\n Util.whenTrue(function() {\n return $('div[id*=\"assign_files_tree\"] .ygtvitem').length > 0;\n }, 10)\n .done(function() {\n placeHoldSelector('div[id*=\"assign_files_tree\"] a[href*=\"pluginfile.php\"]', assignFileMapping);\n dfd.resolve();\n });\n return dfd.promise();\n };\n\n /**\n * Add place holders for folder module files.\n * @param {array} folderFileMapping\n * @return {promise}\n */\n var placeHoldFolderModule = function(folderFileMapping) {\n var dfd = $.Deferred();\n Util.whenTrue(function() {\n return $('.foldertree > .filemanager .ygtvitem').length > 0;\n }, 10)\n .done(function() {\n var unwrappedlinks = '.foldertree > .filemanager span:not(.filter-ally-wrapper) > a[href*=\"pluginfile.php\"]';\n placeHoldSelector(unwrappedlinks, folderFileMapping)\n .done(function() {\n dfd.resolve();\n });\n });\n return dfd.promise();\n };\n\n /**\n * Add place holders for glossary module files.\n * @param {array} glossaryFileMapping\n * @return {promise}\n */\n var placeHoldGlossaryModule = function(glossaryFileMapping) {\n var dfd = $.Deferred();\n\n // Glossary attachment markup is terrible!\n // The first thing we need to do is rewrite the glossary attachments so that they are encapsulated.\n $('.entry .attachments > br').each(function() {\n var mainAnchor = $(this).prev('a[href*=\"pluginfile.php\"]');\n mainAnchor.addClass('ally-glossary-attachment');\n var iconAnchor = $(mainAnchor).prev('a[href*=\"pluginfile.php\"]');\n $(this).after('
');\n var container = $(this).next('.ally-glossary-attachment-row');\n container.append(iconAnchor);\n container.append(mainAnchor);\n $(this).remove();\n });\n\n var unwrappedlinks = '.entry .attachments .ally-glossary-attachment';\n placeHoldSelector(unwrappedlinks, glossaryFileMapping)\n .done(function() {\n dfd.resolve();\n });\n return dfd.promise();\n };\n\n /**\n * Encode a file path so that it can be used to find things by uri.\n * @param {string} filePath\n * @returns {string}\n */\n var urlEncodeFilePath = function(filePath) {\n var parts = filePath.split('/');\n for (var p in parts) {\n parts[p] = encodeURIComponent(parts[p]);\n }\n var encoded = parts.join('/');\n return encoded;\n };\n\n /**\n * General function for finding lesson component file elements and then add mapping.\n * @param {array} map\n * @param {string} selectorPrefix\n * @return promise\n */\n var placeHoldLessonGeneral = function(map, selectorPrefix) {\n var dfd = $.Deferred();\n if (map.length === 0) {\n dfd.resolve();\n } else {\n for (var c in map) {\n var path = urlEncodeFilePath(c);\n var sel = selectorPrefix + 'img[src*=\"' + path + '\"], ' + selectorPrefix + 'a[href*=\"' + path + '\"]';\n placeHoldSelector(sel, map).done(function() {\n dfd.resolve();\n });\n }\n }\n return dfd.promise();\n };\n\n /**\n * Placehold lesson page contents.\n * @param {array} pageContentsMap\n * @returns promise\n */\n var placeHoldLessonPageContents = function(pageContentsMap) {\n return placeHoldLessonGeneral(pageContentsMap, '');\n };\n\n /**\n * Placehold lesson answers.\n * @param {array} pageAnswersMap\n * @returns promise\n */\n var placeHoldLessonAnswersContent = function(pageAnswersMap) {\n return placeHoldLessonGeneral(pageAnswersMap,\n '.studentanswer table tr:nth-child(1) '); // Space at end of selector intended.\n };\n\n /**\n * Placehold lesson responses.\n * @param {array} pageResponsesMap\n * @returns promise\n */\n var placeHoldLessonResponsesContent = function(pageResponsesMap) {\n return placeHoldLessonGeneral(pageResponsesMap,\n '.studentanswer table tr.lastrow '); // Space at end of selector intended.\n };\n\n /**\n * Add place holders for lesson module files.\n * @param {array} lessonFileMapping\n * @return {promise}\n */\n var placeHoldLessonModule = function(lessonFileMapping) {\n var dfd = $.Deferred();\n\n var pageContentsMap = lessonFileMapping.page_contents;\n var pageAnswersMap = lessonFileMapping.page_answers;\n var pageResponsesMap = lessonFileMapping.page_responses;\n\n placeHoldLessonPageContents(pageContentsMap)\n .then(function() {\n return placeHoldLessonAnswersContent(pageAnswersMap);\n })\n .then(function() {\n return placeHoldLessonResponsesContent(pageResponsesMap);\n })\n .then(function() {\n dfd.resolve();\n });\n return dfd.promise();\n };\n\n /**\n * Add place holders for resource module.\n * @param {object} moduleFileMapping\n * @return {promise}\n */\n var placeHoldResourceModule = function(moduleFileMapping) {\n var dfd = $.Deferred();\n var c = 0;\n\n /**\n * Once all modules processed, resolve promise for this function.\n */\n var checkAllProcessed = function() {\n c++;\n // All resource modules have been dealt with.\n if (c >= Object.keys(moduleFileMapping).length) {\n dfd.resolve();\n }\n };\n for (var moduleId in moduleFileMapping) {\n var pathHash = moduleFileMapping[moduleId].content;\n if ($('body').hasClass('theme-snap') && !$('body').hasClass('format-tiles')) {\n var moduleEl = $('#module-' + moduleId + ':not(.snap-native) .activityinstance ' +\n '.snap-asset-link a:first-of-type:not(.clickable-region)');\n } else {\n var moduleEl = $('#module-' + moduleId + ' .activity-instance ' +\n 'a:first-of-type:not(.clickable-region,.editing_move)');\n }\n var processed = moduleEl.find('.filter-ally-wrapper');\n if (processed.length > 0) {\n checkAllProcessed(); // Already processed.\n continue;\n }\n var data = {\n isimage: false,\n fileid: pathHash,\n url: $(moduleEl).attr('href')\n };\n renderTemplate(data, pathHash, moduleEl)\n .done(checkAllProcessed);\n }\n return dfd.promise();\n };\n\n var buildContentIdent = function(component, table, field, id) {\n return [component, table, field, id].join(':');\n };\n\n /**\n * Add annotations to sections content.\n * @param {array} sectionMapping\n */\n var annotateSections = function(sectionMapping) {\n var dfd = $.Deferred();\n\n for (var s in sectionMapping) {\n var sectionId = sectionMapping[s];\n var ident = buildContentIdent('course', 'course_sections', 'summary', sectionId);\n\n var selectors = [\n '#' + s + ' > .content div[class*=\"summarytext\"] .no-overflow',\n 'body.theme-snap #' + s + ' > .content > .summary > div > .no-overflow' // Snap.\n ];\n $(selectors.join(',')).attr('data-ally-richcontent', ident);\n }\n\n dfd.resolve();\n return dfd.promise();\n };\n\n /**\n * Annotate module introductions.\n * @param {array} introMapping\n * @param {string} module\n * @param {array} additionalSelectors\n */\n const annotateModuleIntros = function(introMapping, module, additionalSelectors) {\n for (const i in introMapping) {\n const annotation = introMapping[i];\n\n // Description selector for when activity modules show a description on the course page.\n // We need to be specific here for non course pages to skip this.\n const descriptionSelector = self.config.moodleversion >= 2023100900 ?\n // Selector for Moodle 4.3+\n 'li.activity.modtype_' + module + '#module-' + i + ' .activity-description .no-overflow > .no-overflow' :\n // Selector for < Moodle 4.3\n 'li.activity.modtype_' + module + '#module-' + i + ' .description .no-overflow > .no-overflow';\n\n const selectors = [\n 'body.path-mod-' + module + '.cmid-' + i + ' #intro > .no-overflow',\n descriptionSelector,\n 'li.snap-activity.modtype_' + module + '#module-' + i + ' .contentafterlink > .no-overflow'\n ];\n\n if (additionalSelectors) {\n for (const a in additionalSelectors) {\n selectors.push(additionalSelectors[a].replace('{{i}}', i));\n }\n }\n $(selectors.join(',')).attr('data-ally-richcontent', annotation);\n }\n };\n\n /**\n * Add annotations to forums.\n * @param {array} forumMapping\n */\n var annotateForums = function(forumMapping) {\n // Annotate introductions.\n var intros = forumMapping.intros;\n annotateModuleIntros(intros, 'forum');\n\n // Annotate discussions.\n var discussions = forumMapping.posts;\n for (var d in discussions) {\n var post = 'p' + d;\n var annotation = discussions[d];\n var selectors = [\n \"#page-mod-forum-discuss #\" + post +\n ' div.forumpost div.no-overflow'\n ];\n $(selectors.join(',')).attr('data-ally-richcontent', annotation);\n }\n };\n\n /**\n * Add annotations to Open Forums.\n * @param {array} forumMapping\n */\n var annotateMRForums = function(forumMapping) {\n\n // Annotate introductions.\n var intros = forumMapping.intros;\n annotateModuleIntros(intros, 'hsuforum', ['#hsuforum-header .hsuforum_introduction > .no-overflow']);\n\n var discussions = forumMapping.posts;\n for (var d in discussions) {\n var annotation = discussions[d];\n var postSelector = 'article[id=\"p' + d + '\"] div.posting';\n $(postSelector).attr('data-ally-richcontent', annotation);\n }\n };\n\n /**\n * Add annotations to glossary.\n * @param {array} mapping\n */\n var annotateGlossary = function(mapping) {\n // Annotate introductions.\n var intros = mapping.intros;\n annotateModuleIntros(intros, 'glossary');\n\n // Annotate entries.\n var entries = mapping.entries;\n for (var e in entries) {\n var annotation = entries[e];\n var entryFooter = $('.entrylowersection .commands a[href*=\"id=' + e + '\"]');\n var entry = $(entryFooter).parents('.glossarypost').find('.entry .no-overflow');\n $(entry).attr('data-ally-richcontent', annotation);\n }\n };\n\n /**\n * Add annotations to page.\n * @param {array} mapping\n */\n var annotatePage = function(mapping) {\n var intros = mapping.intros;\n annotateModuleIntros(intros, 'page', ['li.snap-native.modtype_page#module-{{i}} .contentafterlink > .summary-text']);\n\n // Annotate content.\n var content = mapping.content;\n for (var c in content) {\n var annotation = content[c];\n var selectors = [\n `#page-mod-page-view.cmid-${c} #region-main .box.generalbox > .no-overflow`,\n `li.snap-native.modtype_page#module-${c} .pagemod-content`\n ];\n $(selectors.join(',')).attr('data-ally-richcontent', annotation);\n }\n };\n\n /**\n * Add annotations to book.\n * @param {array} mapping\n */\n var annotateBook = function(mapping) {\n var intros = mapping.intros;\n\n // For book, the only place the intro shows is on the course page when you select \"display description on course page\"\n // in the module settings.\n annotateModuleIntros(intros, 'book',\n ['li.snap-native.modtype_book#module-{{i}} .contentafterlink > .summary-text .no-overflow']);\n\n // Annotate content.\n var content = mapping.chapters,\nchapterId;\n\n if (self.params.chapterid) {\n chapterId = self.params.chapterid;\n } else {\n var urlParams = new URLSearchParams(window.location.search);\n chapterId = urlParams.get('chapterid');\n }\n\n $.each(content, function(ch, annotation) {\n if (chapterId != ch) {\n return;\n }\n var selectors = [\n '#page-mod-book-view #region-main .box.generalbox.book_content > .no-overflow',\n 'li.snap-native.modtype_page#module-' + ch + ' .pagemod-content'\n ];\n $(selectors.join(',')).attr('data-ally-richcontent', annotation);\n });\n };\n\n /**\n * Add annotations to lesson.\n * @param {array} mapping\n */\n var annotateLesson = function(mapping) {\n var intros = mapping.intros;\n\n // For lesson, the only place the intro shows is on the course page when you select \"display description on course page\"\n // in the module settings.\n annotateModuleIntros(intros, 'lesson',\n ['li.snap-native.modtype_lesson#module-{{i}} .contentafterlink > .summary-text .no-overflow']);\n\n // Annotate content.\n var content = mapping.lesson_pages;\n for (var p in content) {\n if (document.body.id === \"page-mod-lesson-edit\") {\n var xpath = '//a[@id=\"lesson-' + p + '\"]//ancestor::table//tbody/tr/td/div[contains(@class, \"no-overflow\")]';\n var annotation = content[p];\n var node = getNodeByXpath(xpath);\n $(node).attr('data-ally-richcontent', annotation);\n } else {\n // Try get page from form.\n var node = getNodeByXpath('//form[contains(@action, \"continue.php\")]//input[@name=\"pageid\"]');\n if (node) {\n var pageId = $(node).val();\n } else {\n var urlParams = new URLSearchParams(window.location.search);\n var pageId = urlParams.get('pageid');\n }\n\n if (pageId != p) {\n continue;\n }\n var annotation = content[p];\n var selectors = [\n // Regular page.\n '#page-mod-lesson-view #region-main .box.contents > .no-overflow',\n // Question page.\n '#page-mod-lesson-view #region-main form > fieldset > .fcontainer > .contents .no-overflow',\n // Lesson page.\n 'li.snap-native.modtype_page#module-' + p + ' .pagemod-content'\n ];\n\n $(selectors.join(',')).attr('data-ally-richcontent', annotation);\n }\n }\n\n // Annotate answer answers.\n Strings.get_strings([\n {key: 'answer', component: 'mod_lesson'},\n {key: 'response', component: 'mod_lesson'}\n ]).then(function(strings) {\n var answerLabel = strings[0];\n var responseLabel = strings[1];\n var answers = mapping.lesson_answers;\n\n var processAnswerResponse = function(pageId, i, label, annotation) {\n var xpath = '//a[@id=\"lesson-' + pageId + '\"]//ancestor::table' +\n '//td/label[contains(text(),\"' + label + ' ' + i + '\")]/ancestor::tr/td[2]';\n var nodes = getNodesByXpath(xpath);\n for (var n in nodes) {\n var node = nodes[n];\n $(node).attr('data-ally-richcontent', annotation);\n }\n };\n\n for (var a in answers) {\n // Increment anum so that we can get the answer number.\n // Note, we can trust that this is correct because you can't order answers and the code in the lesson component\n // orders answers by id.\n var annotation = answers[a];\n\n var tmpArr = a.split('_');\n var pageId = tmpArr[0];\n var ansId = tmpArr[1];\n var anum = tmpArr[2];\n\n // Process answers when on lesson edit page.\n if (document.body.id === \"page-mod-lesson-edit\") {\n processAnswerResponse(pageId, anum, answerLabel, annotation);\n } else {\n // Wrap answers in labels.\n $('#page-mod-lesson-view label[for=\"id_answerid_' + ansId + '\"]').attr('data-ally-richcontent', annotation);\n\n if (self.params.answerid && self.params.answerid == ansId) {\n $('.studentanswer tr:nth-of-type(1) > td div').attr('data-ally-richcontent', annotation);\n } else {\n var answerWrapperId = 'answer_wrapper_' + ansId;\n var answerEl = $('#id_answerid_' + ansId);\n if (answerEl.data('annotated') != 1) {\n // We only want to wrap this once.\n var contentEls = answerEl.nextAll();\n answerEl.parent('label').append('');\n $('#' + answerWrapperId).append(contentEls);\n }\n answerEl.data('annotated', 1);\n }\n $('#answer_wrapper_' + a).attr('data-ally-richcontent', annotation);\n }\n }\n\n // Annotate answer responses.\n var responses = mapping.lesson_answers_response;\n for (var r in responses) {\n var annotation = responses[r];\n\n var tmpArr = r.split('_');\n var pageId = tmpArr[0];\n var respId = tmpArr[1];\n var rnum = tmpArr[2];\n\n if (document.body.id === \"page-mod-lesson-edit\") {\n processAnswerResponse(pageId, rnum, responseLabel, annotation);\n } else if (self.params.answerid && self.params.answerid == respId) {\n // Just incase you are wondering, yes answer ids ^ are the same as response ids ;-).\n var responseWrapperId = 'response_wrapper_' + respId;\n if (!$('.studentanswer tr.lastrow > td #' + responseWrapperId).length) {\n // We only want to wrap this once, hence above ! length check.\n var contentEls = $('.studentanswer tr.lastrow > td > br').nextAll();\n $('.studentanswer tr.lastrow > td > br').after('');\n $('#' + responseWrapperId).append(contentEls);\n }\n\n $('#' + responseWrapperId).attr('data-ally-richcontent', annotation);\n }\n\n }\n });\n };\n\n /**\n * Annotate supported modules\n * @param {array} moduleMapping\n */\n var annotateModules = function(moduleMapping) {\n var dfd = $.Deferred();\n if (moduleMapping.mod_forum !== undefined) {\n annotateForums(moduleMapping.mod_forum);\n }\n if (moduleMapping.mod_hsuforum !== undefined) {\n annotateMRForums(moduleMapping.mod_hsuforum);\n }\n if (moduleMapping.mod_glossary !== undefined) {\n annotateGlossary(moduleMapping.mod_glossary);\n }\n if (moduleMapping.mod_page !== undefined) {\n annotatePage(moduleMapping.mod_page);\n }\n if (moduleMapping.mod_book !== undefined) {\n annotateBook(moduleMapping.mod_book);\n }\n if (moduleMapping.mod_lesson !== undefined) {\n annotateLesson(moduleMapping.mod_lesson);\n }\n dfd.resolve();\n return dfd.promise();\n };\n\n /**\n * Annotates course summary if found on footer.\n * @param {object} mapping\n */\n var annotateSnapCourseSummary = function(mapping) {\n var dfd = $.Deferred();\n var snapFooterCourseSummary = $('#snap-course-footer-summary > div.no-overflow');\n if (snapFooterCourseSummary.length) {\n var ident = buildContentIdent('course', 'course', 'summary', mapping.courseId);\n snapFooterCourseSummary.attr('data-ally-richcontent', ident);\n }\n dfd.resolve();\n return dfd.promise();\n };\n\n /**\n * Annotate html block.\n * @param {object} mapping\n */\n var annotateHtmlBlock = function(mapping) {\n var dfd = $.Deferred();\n\n var items = mapping.block_html;\n for (var i in items) {\n var ident = items[i];\n var selectors = [\n '#inst' + i + '.block_html > .card-body > .card-text > .no-overflow',\n '#inst' + i + '.block_html > .content > .no-overflow'\n ];\n var selector = selectors.join(',');\n $(selector).attr('data-ally-richcontent', ident);\n }\n dfd.resolve();\n return dfd.promise();\n };\n\n /**\n * Apply place holders and add annotations to content.\n * @return {promise}\n */\n var applyPlaceHolders = function() {\n M.util.js_pending('filter_ally_applyPlaceHolders');\n var dfd = $.Deferred();\n\n if (ally_module_maps === undefined || ally_section_maps === undefined) {\n dfd.resolve();\n return dfd.promise();\n }\n\n var tasks = [{\n mapVar: ally_module_maps.file_resources,\n method: placeHoldResourceModule\n },\n {\n mapVar: ally_module_maps.assignment_files,\n method: placeHoldAssignModule\n },\n {\n mapVar: ally_module_maps.folder_files,\n method: placeHoldFolderModule\n },\n {\n mapVar: ally_module_maps.forum_files,\n method: placeHoldForumModule\n },\n {\n mapVar: ally_module_maps.glossary_files,\n method: placeHoldGlossaryModule\n },\n {\n mapVar: ally_module_maps.lesson_files,\n method: placeHoldLessonModule\n },\n {\n mapVar: ally_section_maps,\n method: annotateSections\n },\n {\n mapVar: ally_annotation_maps,\n method: annotateModules\n },\n {\n mapVar: {courseId: self.courseId},\n method: annotateSnapCourseSummary\n },\n {\n mapVar: ally_annotation_maps,\n method: annotateHtmlBlock\n }];\n\n $(document).ready(function() {\n var completed = 0;\n /**\n * Run this once a task has resolved.\n */\n var onTaskComplete = function() {\n completed++;\n if (completed === tasks.length) {\n // All tasks completed.\n M.util.js_complete('filter_ally_applyPlaceHolders');\n dfd.resolve();\n }\n };\n\n for (var t in tasks) {\n var task = tasks[t];\n if (Object.keys(task.mapVar).length > 0) {\n task.method(task.mapVar)\n .done(onTaskComplete);\n } else {\n // Skipped this task because mappings are empty.\n onTaskComplete();\n }\n }\n });\n return dfd.promise();\n };\n\n var debounceApplyPlaceHolders = Util.debounce(function() {\n return applyPlaceHolders();\n }, 1000);\n\n /**\n * Initialise JS stage two.\n */\n this.initStageTwo = function() {\n const {jwt, config} = self;\n if (self.canViewFeedback || self.canDownload) {\n debounceApplyPlaceHolders()\n .done(function() {\n ImageCover.init();\n Ally.init(jwt, config);\n try {\n var selector = $('.foldertree > .filemanager');\n var targetNode = selector[0];\n if (targetNode) {\n var observerConfig = {attributes: true, childList: true, subtree: true};\n var callback = function(mutationsList) {\n mutationsList.filter(function(mutation) {\n return mutation.type === 'childList';\n }).forEach(function() {\n placeHoldFolderModule(ally_module_maps.folder_files);\n });\n };\n var observer = new MutationObserver(callback);\n observer.observe(targetNode, observerConfig);\n }\n } catch (error) {\n setInterval(function() {\n placeHoldFolderModule(ally_module_maps.folder_files);\n }, 5000);\n }\n self.initialised = true;\n });\n\n $(document).ajaxComplete(function() {\n if (!self.initialised) {\n return;\n }\n debounceApplyPlaceHolders();\n });\n // For Snap theme.\n if ($('body.theme-snap').length) {\n $(document).ajaxComplete(function(event, xhr, settings) {\n // Search ally server response.\n if (settings.url.includes('ally.js')) {\n setTimeout(function() {\n // Show score icons that are hidden, see INT-18688.\n $('.ally-feedback.ally-active.ally-score-indicator-embedded span').each(function() {\n if (this.style.display == 'none') {\n this.style.display = 'block';\n if (this.getAttribute('class') == 'ally-scoreindicator-container') {\n this.style.display = 'inline-block';\n this.children[0].style.display = 'inline-block';\n }\n }\n });\n }, 5000);\n $(document).off('ajaxComplete');\n }\n });\n\n document.addEventListener('core_filters/contentUpdated', () => {\n // When Snap lazy loads a section it triggers this event.\n // We can ensure everything has been processed on lazy load by recalling the second\n // stage initialization.\n self.initStageTwo();\n });\n }\n }\n };\n\n /**\n * Init function.\n * @param {string} jwt\n * @param {object} config\n * @param {boolean} canViewFeedback\n * @param {boolean} canDownload\n * @param {int} courseId\n * @param {object} params\n */\n this.init = function(jwt, config, canViewFeedback, canDownload, courseId, params) {\n\n self.canViewFeedback = canViewFeedback;\n self.canDownload = canDownload;\n self.courseId = courseId;\n self.params = params;\n self.jwt = jwt;\n self.config = config;\n\n var pluginJSURL = function(path) {\n return M.cfg.wwwroot + \"/pluginfile.php/\" + M.cfg.contextid + \"/filter_ally/\" + path;\n };\n\n var polyfills = {};\n if (!document.evaluate) {\n polyfills['filter_ally/wgxpath'] = pluginJSURL(\"vendorjs/wgxpath.install\");\n }\n if (typeof (URLSearchParams) === 'undefined') {\n polyfills['filter_ally/urlsearchparams'] = [\n 'https://cdnjs.cloudflare.com/ajax/libs/url-search-params/1.1.0/url-search-params.amd.js',\n pluginJSURL('vendorjs/url-search-params.amd') // CDN fallback.\n ];\n }\n if (polyfills !== {}) {\n // Polyfill document.evaluate.\n require.config(\n {\n enforceDefine: false,\n paths: polyfills\n }\n );\n var requires = Object.keys(polyfills);\n\n require(requires, function() {\n if (typeof (URLSearchParams) === 'undefined') {\n window.URLSearchParams = arguments[1]; // Second arg in require (which is URLSearchParams)\n }\n self.initStageTwo();\n });\n\n return;\n }\n self.initStageTwo();\n };\n }();\n});\n"],"names":["define","$","Templates","Strings","Ally","ImageCover","Util","self","this","canViewFeedback","canDownload","initialised","params","getNodeByXpath","xpath","window","document","createExpression","evaluate","XPathResult","FIRST_ORDERED_NODE_TYPE","singleNodeValue","renderTemplate","data","pathHash","targetEl","dfd","Deferred","parents","length","resolve","promise","canviewfeedback","candownload","html","render","done","result","next","find","after","remove","placeHoldSelector","selector","map","c","each","url","type","regex","checkComplete","prop","toLowerCase","attr","indexOf","match","path","decodeURIComponent","undefined","query","getQuery","file","isimage","fileid","placeHoldForumModule","forumFileMapping","placeHoldAssignModule","assignFileMapping","whenTrue","placeHoldFolderModule","folderFileMapping","placeHoldGlossaryModule","glossaryFileMapping","mainAnchor","prev","addClass","iconAnchor","container","append","urlEncodeFilePath","filePath","parts","split","p","encodeURIComponent","join","placeHoldLessonGeneral","selectorPrefix","placeHoldLessonModule","lessonFileMapping","pageContentsMap","page_contents","pageAnswersMap","page_answers","pageResponsesMap","page_responses","placeHoldLessonPageContents","then","placeHoldLessonAnswersContent","placeHoldLessonResponsesContent","placeHoldResourceModule","moduleFileMapping","checkAllProcessed","Object","keys","moduleId","content","hasClass","moduleEl","buildContentIdent","component","table","field","id","annotateSections","sectionMapping","s","sectionId","ident","annotateModuleIntros","introMapping","module","additionalSelectors","i","annotation","selectors","config","moodleversion","a","push","replace","annotateLesson","mapping","intros","lesson_pages","body","node","pageId","val","URLSearchParams","location","search","get","get_strings","key","strings","answerLabel","responseLabel","answers","lesson_answers","processAnswerResponse","label","nodes","ANY_TYPE","iterateNext","getNodesByXpath","n","tmpArr","ansId","anum","answerid","answerWrapperId","answerEl","contentEls","nextAll","parent","responses","lesson_answers_response","r","respId","rnum","responseWrapperId","annotateModules","moduleMapping","mod_forum","forumMapping","discussions","posts","d","post","annotateForums","mod_hsuforum","annotateMRForums","mod_glossary","entries","e","entryFooter","entry","annotateGlossary","mod_page","annotatePage","mod_book","chapterId","chapters","chapterid","urlParams","ch","annotateBook","mod_lesson","annotateSnapCourseSummary","snapFooterCourseSummary","courseId","annotateHtmlBlock","items","block_html","debounceApplyPlaceHolders","debounce","M","util","js_pending","ally_module_maps","ally_section_maps","tasks","mapVar","file_resources","method","assignment_files","folder_files","forum_files","glossary_files","lesson_files","ally_annotation_maps","ready","completed","onTaskComplete","js_complete","t","task","applyPlaceHolders","initStageTwo","jwt","init","targetNode","MutationObserver","mutationsList","filter","mutation","forEach","observe","attributes","childList","subtree","error","setInterval","ajaxComplete","event","xhr","settings","includes","setTimeout","style","display","getAttribute","children","off","addEventListener","pluginJSURL","cfg","wwwroot","contextid","polyfills","require","enforceDefine","paths","requires","arguments"],"mappings":"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"} \ No newline at end of file diff --git a/amd/src/main.js b/amd/src/main.js index 44da096..af425e7 100644 --- a/amd/src/main.js +++ b/amd/src/main.js @@ -434,17 +434,26 @@ function($, Templates, Strings, Ally, ImageCover, Util) { * @param {string} module * @param {array} additionalSelectors */ - var annotateModuleIntros = function(introMapping, module, additionalSelectors) { - for (var i in introMapping) { - var annotation = introMapping[i]; - var selectors = [ + const annotateModuleIntros = function(introMapping, module, additionalSelectors) { + for (const i in introMapping) { + const annotation = introMapping[i]; + + // Description selector for when activity modules show a description on the course page. + // We need to be specific here for non course pages to skip this. + const descriptionSelector = self.config.moodleversion >= 2023100900 ? + // Selector for Moodle 4.3+ + 'li.activity.modtype_' + module + '#module-' + i + ' .activity-description .no-overflow > .no-overflow' : + // Selector for < Moodle 4.3 + 'li.activity.modtype_' + module + '#module-' + i + ' .description .no-overflow > .no-overflow'; + + const selectors = [ 'body.path-mod-' + module + '.cmid-' + i + ' #intro > .no-overflow', - // We need to be specific here for non course pages to skip this. - 'li.activity.modtype_' + module + '#module-' + i + ' .description .no-overflow > .no-overflow', + descriptionSelector, 'li.snap-activity.modtype_' + module + '#module-' + i + ' .contentafterlink > .no-overflow' ]; + if (additionalSelectors) { - for (var a in additionalSelectors) { + for (const a in additionalSelectors) { selectors.push(additionalSelectors[a].replace('{{i}}', i)); } } diff --git a/filter.php b/filter.php index 463ab1b..61e24dc 100644 --- a/filter.php +++ b/filter.php @@ -553,7 +553,8 @@ public function setup($page, $context) { $configvars = (object) [ 'adminurl' => !empty($config->adminurl) ? $config->adminurl : null, 'pushurl' => !empty($config->pushurl) ? $config->pushurl : null, - 'clientid' => !empty($config->clientid) ? $config->clientid : null + 'clientid' => !empty($config->clientid) ? $config->clientid : null, + 'moodleversion' => $CFG->version ]; $params = new stdClass();