From 524f75797a29f7327b60eedf6fdda4b8163bac29 Mon Sep 17 00:00:00 2001 From: Huong Nguyen Date: Thu, 16 Dec 2021 15:41:52 +0700 Subject: [PATCH 1/4] MDL-72783 usertours: Fix the tour display for pages with drawers --- admin/tool/usertours/amd/build/tour.min.js | 2 +- admin/tool/usertours/amd/build/tour.min.js.map | 2 +- admin/tool/usertours/amd/src/tour.js | 12 ++++++++---- 3 files changed, 10 insertions(+), 6 deletions(-) diff --git a/admin/tool/usertours/amd/build/tour.min.js b/admin/tool/usertours/amd/build/tour.min.js index 79ee2be3df8..9aa89c46b95 100644 --- a/admin/tool/usertours/amd/build/tour.min.js +++ b/admin/tool/usertours/amd/build/tour.min.js @@ -1,2 +1,2 @@ -define ("tool_usertours/tour",["exports","jquery","core/aria","core/popper","core/event_dispatcher","./events","core/str","core/prefetch"],function(a,b,c,d,e,f,g,h){"use strict";Object.defineProperty(a,"__esModule",{value:!0});a.default=void 0;b=k(b);c=j(c);d=k(d);var s;function i(){if("function"!=typeof WeakMap)return null;var a=new WeakMap;i=function(){return a};return a}function j(a){if(a&&a.__esModule){return a}if(null===a||"object"!==n(a)&&"function"!=typeof a){return{default:a}}var b=i();if(b&&b.has(a)){return b.get(a)}var c={},d=Object.defineProperty&&Object.getOwnPropertyDescriptor;for(var e in a){if(Object.prototype.hasOwnProperty.call(a,e)){var f=d?Object.getOwnPropertyDescriptor(a,e):null;if(f&&(f.get||f.set)){Object.defineProperty(c,e,f)}else{c[e]=a[e]}}}c.default=a;if(b){b.set(a,c)}return c}function k(a){return a&&a.__esModule?a:{default:a}}function l(a,b){var c=Object.keys(a);if(Object.getOwnPropertySymbols){var d=Object.getOwnPropertySymbols(a);if(b)d=d.filter(function(b){return Object.getOwnPropertyDescriptor(a,b).enumerable});c.push.apply(c,d)}return c}function m(a){for(var b=1,c;ba){return this.endTour()}var c=this.getStepConfig(a);if(null===c){return this.endTour()}return this._gotoStep(c,b)}},{key:"_gotoStep",value:function _gotoStep(a,b){if(!a){return this.endTour()}if("undefined"!=typeof a.delay&&a.delay&&!a.delayed){a.delayed=!0;window.setTimeout(this._gotoStep.bind(this),a.delay,a,b);return this}else if(!a.orphan&&!this.isStepActuallyVisible(a)){var d=-1==b?"getPreviousStepNumber":"getNextStepNumber";return this.gotoStep(this[d](a.stepNumber),b)}this.hide();var c=this.dispatchEvent(f.eventTypes.stepRender,{stepConfig:a},!0);if(!c.defaultPrevented){this.renderStep(a);this.dispatchEvent(f.eventTypes.stepRendered,{stepConfig:a})}return this}},{key:"getStepConfig",value:function getStepConfig(a){if(null===a||0>a||a>=this.steps.length){return null}var c=this.normalizeStepConfig(this.steps[a]);c=b.default.extend(c,{stepNumber:a});return c}},{key:"normalizeStepConfig",value:function normalizeStepConfig(a){if("undefined"!=typeof a.reflex&&"undefined"==typeof a.moveAfterClick){a.moveAfterClick=a.reflex}if("undefined"!=typeof a.element&&"undefined"==typeof a.target){a.target=a.element}if("undefined"!=typeof a.content&&"undefined"==typeof a.body){a.body=a.content}a=b.default.extend({},this.stepDefaults,a);a=b.default.extend({},{attachTo:a.target,attachPoint:"after"},a);if(a.attachTo){a.attachTo=(0,b.default)(a.attachTo).first()}return a}},{key:"getStepTarget",value:function getStepTarget(a){if(a.target){return(0,b.default)(a.target)}return null}},{key:"dispatchEvent",value:function dispatchEvent(a){var b=1").html(a.template).hide(),e=(0,b.default)("body, html").stop(!0,!0);if(this.isStepActuallyVisible(a)){var f=this.getStepTarget(a);if(f.parents("[data-usertour=\"scroller\"]").length){e=f.parents("[data-usertour=\"scroller\"]")}f.data("flexitour","target");var g=this.calculateZIndex(f);if(g){a.zIndex=g+1}if(a.zIndex){c.css("zIndex",a.zIndex+1)}this.positionBackdrop(a);(0,b.default)(document.body).append(c);this.currentStepNode=c;this.currentStepNode.css({top:0,left:0});e.animate({scrollTop:this.calculateScrollTop(a)}).promise().then(function(){this.positionStep(a);this.revealStep(a)}.bind(this)).catch(function(){})}else if(a.orphan){a.isOrphan=!0;a.attachTo=(0,b.default)("body").first();a.attachPoint="append";this.positionBackdrop(a);c.addClass("orphan");(0,b.default)(document.body).append(c);this.currentStepNode=c;this.currentStepNode.offset(this.calculateStepPositionInPage());this.currentStepNode.css("position","fixed");this.currentStepPopper=new d.default((0,b.default)("body"),this.currentStepNode[0],{removeOnDestroy:!0,placement:a.placement+"-start",arrowElement:"[data-role=\"arrow\"]",modifiers:{hide:{enabled:!1},applyStyle:{onLoad:null,enabled:!1}}});this.revealStep(a)}return this}},{key:"revealStep",value:function revealStep(a){this.currentStepNode.fadeIn("",b.default.proxy(function(){this.announceStep(a);this.currentStepNode.focus();window.setTimeout(b.default.proxy(function(){if(this.currentStepNode){this.currentStepNode.focus()}},this),100)},this));return this}},{key:"announceStep",value:function announceStep(a){var b="tour-step-"+this.tourName+"-"+a.stepNumber;this.currentStepNode.attr("id",b);var c=this.currentStepNode.find("[data-placeholder=\"body\"]").first();c.attr("id",b+"-body");c.attr("role","document");var d=this.currentStepNode.find("[data-placeholder=\"title\"]").first();d.attr("id",b+"-title");d.attr("aria-labelledby",b+"-body");this.currentStepNode.attr("role","dialog");this.currentStepNode.attr("tabindex",0);this.currentStepNode.attr("aria-labelledby",b+"-title");this.currentStepNode.attr("aria-describedby",b+"-body");var e=this.getStepTarget(a);if(e){if(!e.attr("tabindex")){e.attr("tabindex",0)}e.data("original-describedby",e.attr("aria-describedby")).attr("aria-describedby",b+"-body")}this.accessibilityShow(a);return this}},{key:"handleKeyDown",value:function handleKeyDown(a){var c="a[href], link[href], [draggable=true], [contenteditable=true], ";c+=":input:enabled, [tabindex], button:enabled";switch(a.keyCode){case 27:this.endTour();break;case 9:(function(){if(!this.currentStepConfig.hasBackdrop){return}var d=(0,b.default)(document.activeElement),e=this.getStepTarget(this.currentStepConfig),f=(0,b.default)(c),g=(0,b.default)("span[data-flexitour=\"container\"]"),h;if(e){f=f.filter(function(a,b){return null!==e&&(e.has(b).length||g.has(b).length||e.is(b)||g.is(b))})}f.each(function(a,b){if(d.is(b)){h=a;return!1}return!0});var i,j,k;if(void 0!=h){var l=1;if(a.shiftKey){l=-1}i=h;do{i+=l;j=(0,b.default)(f[i])}while(j.length&&j.is(":disabled")||j.is(":hidden"));if(j.length){k=j.closest(e).length;k=k||j.closest(this.currentStepNode).length}else{k=!1}}if(k){j.focus()}else{if(a.shiftKey){this.currentStepNode.find(c).last().focus()}else{if(this.currentStepConfig.isOrphan){this.currentStepNode.focus()}else{e.focus()}}}a.preventDefault()}).call(this);break;}}},{key:"startTour",value:function startTour(a){if(this.storage&&"undefined"==typeof a){var c=this.storage.getItem(this.storageKey);if(c){var d=parseInt(c,10);if(d<=this.steps.length){a=d}}}if("undefined"==typeof a){a=this.getCurrentStepNumber()}var b=this.dispatchEvent(f.eventTypes.tourStart,{startAt:a},!0);if(!b.defaultPrevented){this.gotoStep(a);this.tourRunning=!0;this.dispatchEvent(f.eventTypes.tourStarted,{startAt:a})}return this}},{key:"restartTour",value:function restartTour(){return this.startTour(0)}},{key:"endTour",value:function endTour(){var a=this.dispatchEvent(f.eventTypes.tourEnd,{},!0);if(a.defaultPrevented){return this}if(this.currentStepConfig){var b=this.getStepTarget(this.currentStepConfig);if(b){if(!b.attr("tabindex")){b.attr("tabindex","-1")}b.focus()}}this.hide(!0);this.tourRunning=!1;this.dispatchEvent(f.eventTypes.tourEnded);return this}},{key:"hide",value:function hide(a){var c=this.dispatchEvent(f.eventTypes.stepHide,{},!0);if(c.defaultPrevented){return this}if(this.currentStepNode&&this.currentStepNode.length){this.currentStepNode.hide();if(this.currentStepPopper){this.currentStepPopper.destroy()}}if(this.currentStepConfig){var e=this.getStepTarget(this.currentStepConfig);if(e){if(e.data("original-labelledby")){e.attr("aria-labelledby",e.data("original-labelledby"))}if(e.data("original-describedby")){e.attr("aria-describedby",e.data("original-describedby"))}if(e.data("original-tabindex")){e.attr("tabindex",e.data("tabindex"))}}this.currentStepConfig=null}var d=0;if(a){d=400}(0,b.default)("[data-flexitour=\"step-background\"]").remove();(0,b.default)("[data-flexitour=\"step-backdrop\"]").removeAttr("data-flexitour");(0,b.default)("[data-flexitour=\"backdrop\"]").fadeOut(d,function(){(0,b.default)(this).remove()});if(this.currentStepNode&&this.currentStepNode.length){var g=this.currentStepNode.attr("id");if(g){var h="[aria-describedby=\""+g+"-body\"]";(0,b.default)(h).removeAttr("tabindex");(0,b.default)(h).removeAttr("aria-describedby")}}this.resetStepListeners();this.accessibilityHide();this.dispatchEvent(f.eventTypes.stepHidden);this.currentStepNode=null;this.currentStepPopper=null;return this}},{key:"show",value:function show(){var a=this.getCurrentStepNumber();return this.gotoStep(a)}},{key:"getStepContainer",value:function getStepContainer(){return(0,b.default)(this.currentStepNode)}},{key:"calculateScrollTop",value:function calculateScrollTop(a){var c=(0,b.default)(window).height(),d=this.getStepTarget(a),e=(0,b.default)(window);if(d.parents("[data-usertour=\"scroller\"]").length){e=d.parents("[data-usertour=\"scroller\"]")}var f=e.scrollTop();if("top"===a.placement){f=d.offset().top-c/2}else if("bottom"===a.placement){f=d.offset().top+d.height()+f-c/2}else if(d.height()<=.8*c){f=d.offset().top-(c-d.height())/2}else{f=d.offset().top-.2*c}f=Math.max(0,f);f=Math.min((0,b.default)(document).height()-c,f);return Math.ceil(f)}},{key:"calculateStepPositionInPage",value:function calculateStepPositionInPage(){var a=(0,b.default)(window).height(),c=this.currentStepNode.height(),d=(0,b.default)(window).width(),e=this.currentStepNode.width();return{top:Math.ceil((a-c)/2),left:Math.ceil((d-e)/2)}}},{key:"positionStep",value:function positionStep(a){var c=this.currentStepNode;if(!c||!c.length){return this}a.placement=this.recalculatePlacement(a);var e;switch(a.placement){case"left":e=["left","right","top","bottom"];break;case"right":e=["right","left","top","bottom"];break;case"top":e=["top","bottom","right","left"];break;case"bottom":e=["bottom","top","right","left"];break;default:e="flip";break;}var f=this.getStepTarget(a),g={placement:a.placement+"-start",removeOnDestroy:!0,modifiers:{flip:{behaviour:e},arrow:{element:"[data-role=\"arrow\"]"}},onCreate:function onCreate(a){h(a)},onUpdate:function onUpdate(a){h(a)}},h=function(a){var c=a.placement.split("-")[0],d=-1!==["left","right"].indexOf(c),e=a.instance.popper.querySelector("[data-role=\"arrow\"]"),f=(0,b.default)(a.instance.popper.querySelector("[data-role=\"flexitour-step\"]"));if(d){var g=parseFloat(window.getComputedStyle(e).height),h=parseFloat(window.getComputedStyle(e).top),i=parseFloat(window.getComputedStyle(a.instance.popper).height),j=parseFloat(window.getComputedStyle(a.instance.popper).top),k=parseFloat(f.css("borderTopWidth")),l=2*parseFloat(f.css("borderTopLeftRadius")),m=h+g/2,n=i+j-k-l,o=j+k+l;if(m>=n||m<=o){var y=0;if(m>i/2){y=n-g}else{y=o+g}(0,b.default)(e).css("top",y)}}else{var p=parseFloat(window.getComputedStyle(e).width),q=parseFloat(window.getComputedStyle(e).left),r=parseFloat(window.getComputedStyle(a.instance.popper).width),s=parseFloat(window.getComputedStyle(a.instance.popper).left),t=parseFloat(f.css("borderTopWidth")),u=2*parseFloat(f.css("borderTopLeftRadius")),v=q+p/2,w=r+s-t-u,x=s+t+u;if(v>=w||v<=x){var z=0;if(v>r/2){z=w-p}else{z=x+p}(0,b.default)(e).css("left",z)}}},i=(0,b.default)("[data-flexitour=\"step-background\"]");if(i.length){f=i}this.currentStepPopper=new d.default(f,c[0],g);return this}},{key:"recalculatePlacement",value:function recalculatePlacement(a){var b=this.getStepTarget(a),c=this.currentStepNode.width()+16,d=b.offset().left-10,e=b.offset().left+b.width()+10,f=a.placement;if(-1!==["left","right"].indexOf(f)){if(ddocument.documentElement.clientWidth){f="top"}}return f}},{key:"positionBackdrop",value:function positionBackdrop(a){if(a.backdrop){this.currentStepConfig.hasBackdrop=!0;var f=(0,b.default)("
");if(a.zIndex){if("append"===a.attachPoint){a.attachTo.append(f)}else{f.insertAfter(a.attachTo)}}else{(0,b.default)("body").append(f)}if(this.isStepActuallyVisible(a)){var g=(0,b.default)("[data-flexitour=\"step-background\"]");if(!g.length){g=(0,b.default)("
")}var c=this.getStepTarget(a),d=10,e=c;if(d){e=(0,b.default)("body")}var h=0;if(c.parents("[data-usertour=\"scroller\"]").length){h=c.parents("[data-usertour=\"scroller\"]").scrollTop();g.css({position:"fixed"})}g.css({width:c.outerWidth()+d+d,height:c.outerHeight()+d+d,left:c.offset().left-d,top:c.offset().top+h-d,backgroundColor:this.calculateInherittedBackgroundColor(e)});if(c.offset().left").hide();(0,b.default)("body").append(c);var d=c.css("backgroundColor");c.remove();a=(0,b.default)(a);while(a.length&&a[0]!==document){var e=a.css("backgroundColor");if(e!==d){return e}a=a.parent()}return null}},{key:"calculatePosition",value:function calculatePosition(a){a=(0,b.default)(a);while(a.length&&a[0]!==document){var c=a.css("position");if("static"!==c){return c}a=a.parent()}return null}},{key:"accessibilityShow",value:function accessibilityShow(){var a=function(a){var b=a.data("flexitour");if(b){switch(b){case"container":case"target":return;}}var d=a.attr("aria-hidden");if(!d){a.attr("data-has-hidden",!0);c.hide(a)}};this.currentStepNode.siblings().each(function(c,d){a((0,b.default)(d))});this.currentStepNode.parentsUntil("body").siblings().each(function(c,d){a((0,b.default)(d))})}},{key:"accessibilityHide",value:function accessibilityHide(){var a=function(a){var b=a.attr("data-has-hidden");if("undefined"!=typeof b){a.removeAttr("data-has-hidden");c.unhide(a)}};(0,b.default)("[data-has-hidden]").each(function(c,d){a((0,b.default)(d))})}}]);return a}(),s);a.default=t;return a.default}); +define ("tool_usertours/tour",["exports","jquery","core/aria","core/popper","core/event_dispatcher","./events","core/str","core/prefetch"],function(a,b,c,d,e,f,g,h){"use strict";Object.defineProperty(a,"__esModule",{value:!0});a.default=void 0;b=k(b);c=j(c);d=k(d);var s;function i(){if("function"!=typeof WeakMap)return null;var a=new WeakMap;i=function(){return a};return a}function j(a){if(a&&a.__esModule){return a}if(null===a||"object"!==n(a)&&"function"!=typeof a){return{default:a}}var b=i();if(b&&b.has(a)){return b.get(a)}var c={},d=Object.defineProperty&&Object.getOwnPropertyDescriptor;for(var e in a){if(Object.prototype.hasOwnProperty.call(a,e)){var f=d?Object.getOwnPropertyDescriptor(a,e):null;if(f&&(f.get||f.set)){Object.defineProperty(c,e,f)}else{c[e]=a[e]}}}c.default=a;if(b){b.set(a,c)}return c}function k(a){return a&&a.__esModule?a:{default:a}}function l(a,b){var c=Object.keys(a);if(Object.getOwnPropertySymbols){var d=Object.getOwnPropertySymbols(a);if(b)d=d.filter(function(b){return Object.getOwnPropertyDescriptor(a,b).enumerable});c.push.apply(c,d)}return c}function m(a){for(var b=1,c;ba){return this.endTour()}var c=this.getStepConfig(a);if(null===c){return this.endTour()}return this._gotoStep(c,b)}},{key:"_gotoStep",value:function _gotoStep(a,b){if(!a){return this.endTour()}if("undefined"!=typeof a.delay&&a.delay&&!a.delayed){a.delayed=!0;window.setTimeout(this._gotoStep.bind(this),a.delay,a,b);return this}else if(!a.orphan&&!this.isStepActuallyVisible(a)){var d=-1==b?"getPreviousStepNumber":"getNextStepNumber";return this.gotoStep(this[d](a.stepNumber),b)}this.hide();var c=this.dispatchEvent(f.eventTypes.stepRender,{stepConfig:a},!0);if(!c.defaultPrevented){this.renderStep(a);this.dispatchEvent(f.eventTypes.stepRendered,{stepConfig:a})}return this}},{key:"getStepConfig",value:function getStepConfig(a){if(null===a||0>a||a>=this.steps.length){return null}var c=this.normalizeStepConfig(this.steps[a]);c=b.default.extend(c,{stepNumber:a});return c}},{key:"normalizeStepConfig",value:function normalizeStepConfig(a){if("undefined"!=typeof a.reflex&&"undefined"==typeof a.moveAfterClick){a.moveAfterClick=a.reflex}if("undefined"!=typeof a.element&&"undefined"==typeof a.target){a.target=a.element}if("undefined"!=typeof a.content&&"undefined"==typeof a.body){a.body=a.content}a=b.default.extend({},this.stepDefaults,a);a=b.default.extend({},{attachTo:a.target,attachPoint:"after"},a);if(a.attachTo){a.attachTo=(0,b.default)(a.attachTo).first()}return a}},{key:"getStepTarget",value:function getStepTarget(a){if(a.target){return(0,b.default)(a.target)}return null}},{key:"dispatchEvent",value:function dispatchEvent(a){var b=1").html(a.template).hide(),e=(0,b.default)("body, html").stop(!0,!0);if(this.isStepActuallyVisible(a)){var f=this.getStepTarget(a);if(f.parents("[data-usertour=\"scroller\"]").length){e=f.parents("[data-usertour=\"scroller\"]")}f.data("flexitour","target");var g=this.calculateZIndex(f);if(g){a.zIndex=g+1}if(a.zIndex){c.css("zIndex",a.zIndex+1)}this.positionBackdrop(a);(0,b.default)(document.body).append(c);this.currentStepNode=c;this.currentStepNode.css({top:0,left:0});e.animate({scrollTop:this.calculateScrollTop(a)}).promise().then(function(){this.positionStep(a);this.revealStep(a)}.bind(this)).catch(function(){})}else if(a.orphan){a.isOrphan=!0;a.attachTo=(0,b.default)("body").first();a.attachPoint="append";this.positionBackdrop(a);c.addClass("orphan");(0,b.default)(document.body).append(c);this.currentStepNode=c;this.currentStepNode.offset(this.calculateStepPositionInPage());this.currentStepNode.css("position","fixed");this.currentStepPopper=new d.default((0,b.default)("body"),this.currentStepNode[0],{removeOnDestroy:!0,placement:a.placement+"-start",arrowElement:"[data-role=\"arrow\"]",modifiers:{hide:{enabled:!1},applyStyle:{onLoad:null,enabled:!1}}});this.revealStep(a)}return this}},{key:"revealStep",value:function revealStep(a){this.currentStepNode.fadeIn("",b.default.proxy(function(){this.announceStep(a);this.currentStepNode.focus();window.setTimeout(b.default.proxy(function(){if(this.currentStepNode){this.currentStepNode.focus()}},this),100)},this));return this}},{key:"announceStep",value:function announceStep(a){var b="tour-step-"+this.tourName+"-"+a.stepNumber;this.currentStepNode.attr("id",b);var c=this.currentStepNode.find("[data-placeholder=\"body\"]").first();c.attr("id",b+"-body");c.attr("role","document");var d=this.currentStepNode.find("[data-placeholder=\"title\"]").first();d.attr("id",b+"-title");d.attr("aria-labelledby",b+"-body");this.currentStepNode.attr("role","dialog");this.currentStepNode.attr("tabindex",0);this.currentStepNode.attr("aria-labelledby",b+"-title");this.currentStepNode.attr("aria-describedby",b+"-body");var e=this.getStepTarget(a);if(e){if(!e.attr("tabindex")){e.attr("tabindex",0)}e.data("original-describedby",e.attr("aria-describedby")).attr("aria-describedby",b+"-body")}this.accessibilityShow(a);return this}},{key:"handleKeyDown",value:function handleKeyDown(a){var c="a[href], link[href], [draggable=true], [contenteditable=true], ";c+=":input:enabled, [tabindex], button:enabled";switch(a.keyCode){case 27:this.endTour();break;case 9:(function(){if(!this.currentStepConfig.hasBackdrop){return}var d=(0,b.default)(document.activeElement),e=this.getStepTarget(this.currentStepConfig),f=(0,b.default)(c),g=(0,b.default)("span[data-flexitour=\"container\"]"),h;if(e){f=f.filter(function(a,b){return null!==e&&(e.has(b).length||g.has(b).length||e.is(b)||g.is(b))})}f.each(function(a,b){if(d.is(b)){h=a;return!1}return!0});var i,j,k;if(void 0!=h){var l=1;if(a.shiftKey){l=-1}i=h;do{i+=l;j=(0,b.default)(f[i])}while(j.length&&j.is(":disabled")||j.is(":hidden"));if(j.length){k=j.closest(e).length;k=k||j.closest(this.currentStepNode).length}else{k=!1}}if(k){j.focus()}else{if(a.shiftKey){this.currentStepNode.find(c).last().focus()}else{if(this.currentStepConfig.isOrphan){this.currentStepNode.focus()}else{e.focus()}}}a.preventDefault()}).call(this);break;}}},{key:"startTour",value:function startTour(a){if(this.storage&&"undefined"==typeof a){var c=this.storage.getItem(this.storageKey);if(c){var d=parseInt(c,10);if(d<=this.steps.length){a=d}}}if("undefined"==typeof a){a=this.getCurrentStepNumber()}var b=this.dispatchEvent(f.eventTypes.tourStart,{startAt:a},!0);if(!b.defaultPrevented){this.gotoStep(a);this.tourRunning=!0;this.dispatchEvent(f.eventTypes.tourStarted,{startAt:a})}return this}},{key:"restartTour",value:function restartTour(){return this.startTour(0)}},{key:"endTour",value:function endTour(){var a=this.dispatchEvent(f.eventTypes.tourEnd,{},!0);if(a.defaultPrevented){return this}if(this.currentStepConfig){var b=this.getStepTarget(this.currentStepConfig);if(b){if(!b.attr("tabindex")){b.attr("tabindex","-1")}b.focus()}}this.hide(!0);this.tourRunning=!1;this.dispatchEvent(f.eventTypes.tourEnded);return this}},{key:"hide",value:function hide(a){var c=this.dispatchEvent(f.eventTypes.stepHide,{},!0);if(c.defaultPrevented){return this}if(this.currentStepNode&&this.currentStepNode.length){this.currentStepNode.hide();if(this.currentStepPopper){this.currentStepPopper.destroy()}}if(this.currentStepConfig){var e=this.getStepTarget(this.currentStepConfig);if(e){if(e.data("original-labelledby")){e.attr("aria-labelledby",e.data("original-labelledby"))}if(e.data("original-describedby")){e.attr("aria-describedby",e.data("original-describedby"))}if(e.data("original-tabindex")){e.attr("tabindex",e.data("tabindex"))}}this.currentStepConfig=null}var d=0;if(a){d=400}(0,b.default)("[data-flexitour=\"step-background\"]").remove();(0,b.default)("[data-flexitour=\"step-backdrop\"]").removeAttr("data-flexitour");(0,b.default)("[data-flexitour=\"backdrop\"]").fadeOut(d,function(){(0,b.default)(this).remove()});if(this.currentStepNode&&this.currentStepNode.length){var g=this.currentStepNode.attr("id");if(g){var h="[aria-describedby=\""+g+"-body\"]";(0,b.default)(h).removeAttr("tabindex");(0,b.default)(h).removeAttr("aria-describedby")}}this.resetStepListeners();this.accessibilityHide();this.dispatchEvent(f.eventTypes.stepHidden);this.currentStepNode=null;this.currentStepPopper=null;return this}},{key:"show",value:function show(){var a=this.getCurrentStepNumber();return this.gotoStep(a)}},{key:"getStepContainer",value:function getStepContainer(){return(0,b.default)(this.currentStepNode)}},{key:"calculateScrollTop",value:function calculateScrollTop(a){var c=(0,b.default)(window).height(),d=this.getStepTarget(a),e=(0,b.default)(window);if(d.parents("[data-usertour=\"scroller\"]").length){e=d.parents("[data-usertour=\"scroller\"]")}var f=e.scrollTop();if("top"===a.placement){f=d.offset().top-c/2}else if("bottom"===a.placement){f=d.offset().top+d.height()+f-c/2}else if(d.height()<=.8*c){f=d.offset().top-(c-d.height())/2}else{f=d.offset().top-.2*c}f=Math.max(0,f);f=Math.min((0,b.default)(document).height()-c,f);return Math.ceil(f)}},{key:"calculateStepPositionInPage",value:function calculateStepPositionInPage(){var a=(0,b.default)(window).height(),c=this.currentStepNode.height(),d=(0,b.default)(window).width(),e=this.currentStepNode.width();return{top:Math.ceil((a-c)/2),left:Math.ceil((d-e)/2)}}},{key:"positionStep",value:function positionStep(a){var c=this.currentStepNode;if(!c||!c.length){return this}a.placement=this.recalculatePlacement(a);var e;switch(a.placement){case"left":e=["left","right","top","bottom"];break;case"right":e=["right","left","top","bottom"];break;case"top":e=["top","bottom","right","left"];break;case"bottom":e=["bottom","top","right","left"];break;default:e="flip";break;}var f=this.getStepTarget(a),g={placement:a.placement+"-start",removeOnDestroy:!0,modifiers:{flip:{behaviour:e},arrow:{element:"[data-role=\"arrow\"]"}},onCreate:function onCreate(a){h(a)},onUpdate:function onUpdate(a){h(a)}},h=function(a){var c=a.placement.split("-")[0],d=-1!==["left","right"].indexOf(c),e=a.instance.popper.querySelector("[data-role=\"arrow\"]"),f=(0,b.default)(a.instance.popper.querySelector("[data-role=\"flexitour-step\"]"));if(d){var g=parseFloat(window.getComputedStyle(e).height),h=parseFloat(window.getComputedStyle(e).top),i=parseFloat(window.getComputedStyle(a.instance.popper).height),j=parseFloat(window.getComputedStyle(a.instance.popper).top),k=parseFloat(f.css("borderTopWidth")),l=2*parseFloat(f.css("borderTopLeftRadius")),m=h+g/2,n=i+j-k-l,o=j+k+l;if(m>=n||m<=o){var y=0;if(m>i/2){y=n-g}else{y=o+g}(0,b.default)(e).css("top",y)}}else{var p=parseFloat(window.getComputedStyle(e).width),q=parseFloat(window.getComputedStyle(e).left),r=parseFloat(window.getComputedStyle(a.instance.popper).width),s=parseFloat(window.getComputedStyle(a.instance.popper).left),t=parseFloat(f.css("borderTopWidth")),u=2*parseFloat(f.css("borderTopLeftRadius")),v=q+p/2,w=r+s-t-u,x=s+t+u;if(v>=w||v<=x){var z=0;if(v>r/2){z=w-p}else{z=x+p}(0,b.default)(e).css("left",z)}}},i=(0,b.default)("[data-flexitour=\"step-background\"]");if(i.length){f=i}this.currentStepPopper=new d.default(f,c[0],g);return this}},{key:"recalculatePlacement",value:function recalculatePlacement(a){var b=this.getStepTarget(a),c=this.currentStepNode.width()+16,d=b.offset().left-10,e=b.offset().left+b.width()+10,f=a.placement;if(-1!==["left","right"].indexOf(f)){if(ddocument.documentElement.clientWidth){f="top"}}return f}},{key:"positionBackdrop",value:function positionBackdrop(a){if(a.backdrop){this.currentStepConfig.hasBackdrop=!0;var h=(0,b.default)("
");if(a.zIndex){if("append"===a.attachPoint){a.attachTo.append(h)}else{h.insertAfter(a.attachTo)}}else{(0,b.default)("body").append(h)}if(this.isStepActuallyVisible(a)){var i=(0,b.default)("[data-flexitour=\"step-background\"]");if(!i.length){i=(0,b.default)("
")}var c=this.getStepTarget(a),d=10,e=c;if(d){e=(0,b.default)("body")}var j=0;if(c.parents("[data-usertour=\"scroller\"]").length){var f=c.parents("[data-usertour=\"scroller\"]"),g=f.offset().top;if(f.scrollTop()>=g){j=f.scrollTop()-g;i.css({position:"fixed"})}}i.css({width:c.outerWidth()+d+d,height:c.outerHeight()+d+d,left:c.offset().left-d,top:c.offset().top+j-d,backgroundColor:this.calculateInherittedBackgroundColor(e)});if(c.offset().left").hide();(0,b.default)("body").append(c);var d=c.css("backgroundColor");c.remove();a=(0,b.default)(a);while(a.length&&a[0]!==document){var e=a.css("backgroundColor");if(e!==d){return e}a=a.parent()}return null}},{key:"calculatePosition",value:function calculatePosition(a){a=(0,b.default)(a);while(a.length&&a[0]!==document){var c=a.css("position");if("static"!==c){return c}a=a.parent()}return null}},{key:"accessibilityShow",value:function accessibilityShow(){var a=function(a){var b=a.data("flexitour");if(b){switch(b){case"container":case"target":return;}}var d=a.attr("aria-hidden");if(!d){a.attr("data-has-hidden",!0);c.hide(a)}};this.currentStepNode.siblings().each(function(c,d){a((0,b.default)(d))});this.currentStepNode.parentsUntil("body").siblings().each(function(c,d){a((0,b.default)(d))})}},{key:"accessibilityHide",value:function accessibilityHide(){var a=function(a){var b=a.attr("data-has-hidden");if("undefined"!=typeof b){a.removeAttr("data-has-hidden");c.unhide(a)}};(0,b.default)("[data-has-hidden]").each(function(c,d){a((0,b.default)(d))})}}]);return a}(),s);a.default=t;return a.default}); //# sourceMappingURL=tour.min.js.map diff --git a/admin/tool/usertours/amd/build/tour.min.js.map b/admin/tool/usertours/amd/build/tour.min.js.map index 2df22d9cd29..266a79dba3d 100644 --- a/admin/tool/usertours/amd/build/tour.min.js.map +++ b/admin/tool/usertours/amd/build/tour.min.js.map @@ -1 +1 @@ -{"version":3,"sources":["../src/tour.js"],"names":["Tour","config","init","eventHandlers","reset","originalConfiguration","configure","apply","arguments","storage","window","sessionStorage","storageKey","tourName","e","hide","resetStepListeners","steps","currentStepNumber","eventName","forEach","handler","addEventHandler","resetStepDefaults","template","templateContent","checkMinimumRequirements","Error","length","loadOriginalConfiguration","stepDefaults","setStepDefaults","$","extend","element","placement","delay","moveOnClick","moveAfterTime","orphan","direction","parseInt","stepNumber","setItem","code","DOMException","QUOTA_EXCEEDED_ERR","removeItem","getCurrentStepNumber","nextStepNumber","isStepPotentiallyVisible","getStepConfig","previousStepNumber","getNextStepNumber","stepConfig","isStepActuallyVisible","position","result","stepId","stepid","target","getStepTarget","is","gotoStep","getPreviousStepNumber","endTour","_gotoStep","delayed","setTimeout","bind","fn","stepRenderEvent","dispatchEvent","eventTypes","stepRender","defaultPrevented","renderStep","stepRendered","normalizeStepConfig","reflex","moveAfterClick","content","body","attachTo","attachPoint","first","detail","cancelable","tour","document","push","listeners","node","currentStepNode","args","proxy","next","handleKeyDown","targetNode","parents","listener","on","off","currentStepConfig","setCurrentStepNumber","getTemplateContent","find","html","title","nextBtn","endBtn","isLastStep","removeClass","addClass","prop","then","value","catch","attr","displaystepnumbers","stepsPotentiallyVisible","getPotentiallyVisibleSteps","totalStepsPotentiallyVisible","total","addStepToPage","processStepListeners","clone","animationTarget","stop","data","zIndex","calculateZIndex","css","positionBackdrop","append","top","left","animate","scrollTop","calculateScrollTop","promise","positionStep","revealStep","isOrphan","offset","calculateStepPositionInPage","currentStepPopper","Popper","removeOnDestroy","arrowElement","modifiers","enabled","applyStyle","onLoad","fadeIn","announceStep","focus","bodyRegion","headerRegion","accessibilityShow","tabbableSelector","keyCode","hasBackdrop","activeElement","stepTarget","tabbableNodes","dialogContainer","currentIndex","filter","index","has","each","nextIndex","nextNode","focusRelevant","shiftKey","closest","last","preventDefault","call","startAt","storageStartValue","getItem","storageStartAt","tourStartEvent","tourStart","tourRunning","tourStarted","startTour","tourEndEvent","tourEnd","previousTarget","tourEnded","transition","stepHideEvent","stepHide","destroy","fadeTime","remove","removeAttr","fadeOut","currentStepElement","accessibilityHide","stepHidden","viewportHeight","height","scrollParent","Math","max","min","ceil","stepHeight","viewportWidth","width","stepWidth","recalculatePlacement","flipBehavior","flip","behaviour","arrow","onCreate","recalculateArrowPosition","onUpdate","split","isVertical","indexOf","instance","popper","querySelector","stepElement","arrowHeight","parseFloat","getComputedStyle","arrowOffset","popperHeight","popperOffset","popperBorderWidth","popperBorderRadiusWidth","arrowPos","maxPos","minPos","newArrowPos","arrowWidth","popperWidth","background","widthContent","targetOffsetLeft","targetOffsetRight","documentElement","clientWidth","backdrop","insertAfter","buffer","colorNode","drawertop","outerWidth","outerHeight","backgroundColor","calculateInherittedBackgroundColor","targetRadius","targetPosition","calculatePosition","fader","opacity","targetClone","elem","isNaN","parent","fakeNode","fakeElemColor","color","hideFunction","child","flexitourRole","hidden","Aria","siblings","parentsUntil","showFunction","unhide"],"mappings":"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","sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle. If not, see .\n\n/**\n * A user tour.\n *\n * @module tool_usertours/tour\n * @copyright 2018 Andrew Nicols \n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\n\n/**\n * A list of steps.\n *\n * @typedef {Object[]} StepList\n * @property {Number} stepId The id of the step in the database\n * @property {Number} position The position of the step within the tour (zero-indexed)\n */\n\nimport $ from 'jquery';\nimport * as Aria from 'core/aria';\nimport Popper from 'core/popper';\nimport {dispatchEvent} from 'core/event_dispatcher';\nimport {eventTypes} from './events';\nimport {get_string as getString} from 'core/str';\nimport {prefetchStrings} from 'core/prefetch';\n\n/**\n * A user tour.\n *\n * @class tool_usertours/tour\n * @property {boolean} tourRunning Whether the tour is currently running.\n */\nconst Tour = class {\n tourRunning = false;\n\n /**\n * @param {object} config The configuration object.\n */\n constructor(config) {\n this.init(config);\n }\n\n /**\n * Initialise the tour.\n *\n * @method init\n * @param {Object} config The configuration object.\n * @chainable\n * @return {Object} this.\n */\n init(config) {\n // Unset all handlers.\n this.eventHandlers = {};\n\n // Reset the current tour states.\n this.reset();\n\n // Store the initial configuration.\n this.originalConfiguration = config || {};\n\n // Apply configuration.\n this.configure.apply(this, arguments);\n\n try {\n this.storage = window.sessionStorage;\n this.storageKey = 'tourstate_' + this.tourName;\n } catch (e) {\n this.storage = false;\n this.storageKey = '';\n }\n\n prefetchStrings('tool_usertours', [\n 'nextstep_sequence',\n 'skip_tour'\n ]);\n\n return this;\n }\n\n /**\n * Reset the current tour state.\n *\n * @method reset\n * @chainable\n * @return {Object} this.\n */\n reset() {\n // Hide the current step.\n this.hide();\n\n // Unset all handlers.\n this.eventHandlers = [];\n\n // Unset all listeners.\n this.resetStepListeners();\n\n // Unset the original configuration.\n this.originalConfiguration = {};\n\n // Reset the current step number and list of steps.\n this.steps = [];\n\n // Reset the current step number.\n this.currentStepNumber = 0;\n\n return this;\n }\n\n /**\n * Prepare tour configuration.\n *\n * @method configure\n * @param {Object} config The configuration object.\n * @chainable\n * @return {Object} this.\n */\n configure(config) {\n if (typeof config === 'object') {\n // Tour name.\n if (typeof config.tourName !== 'undefined') {\n this.tourName = config.tourName;\n }\n\n // Set up eventHandlers.\n if (config.eventHandlers) {\n for (let eventName in config.eventHandlers) {\n config.eventHandlers[eventName].forEach(function(handler) {\n this.addEventHandler(eventName, handler);\n }, this);\n }\n }\n\n // Reset the step configuration.\n this.resetStepDefaults(true);\n\n // Configure the steps.\n if (typeof config.steps === 'object') {\n this.steps = config.steps;\n }\n\n if (typeof config.template !== 'undefined') {\n this.templateContent = config.template;\n }\n }\n\n // Check that we have enough to start the tour.\n this.checkMinimumRequirements();\n\n return this;\n }\n\n /**\n * Check that the configuration meets the minimum requirements.\n *\n * @method checkMinimumRequirements\n */\n checkMinimumRequirements() {\n // Need a tourName.\n if (!this.tourName) {\n throw new Error(\"Tour Name required\");\n }\n\n // Need a minimum of one step.\n if (!this.steps || !this.steps.length) {\n throw new Error(\"Steps must be specified\");\n }\n }\n\n /**\n * Reset step default configuration.\n *\n * @method resetStepDefaults\n * @param {Boolean} loadOriginalConfiguration Whether to load the original configuration supplied with the Tour.\n * @chainable\n * @return {Object} this.\n */\n resetStepDefaults(loadOriginalConfiguration) {\n if (typeof loadOriginalConfiguration === 'undefined') {\n loadOriginalConfiguration = true;\n }\n\n this.stepDefaults = {};\n if (!loadOriginalConfiguration || typeof this.originalConfiguration.stepDefaults === 'undefined') {\n this.setStepDefaults({});\n } else {\n this.setStepDefaults(this.originalConfiguration.stepDefaults);\n }\n\n return this;\n }\n\n /**\n * Set the step defaults.\n *\n * @method setStepDefaults\n * @param {Object} stepDefaults The step defaults to apply to all steps\n * @chainable\n * @return {Object} this.\n */\n setStepDefaults(stepDefaults) {\n if (!this.stepDefaults) {\n this.stepDefaults = {};\n }\n $.extend(\n this.stepDefaults,\n {\n element: '',\n placement: 'top',\n delay: 0,\n moveOnClick: false,\n moveAfterTime: 0,\n orphan: false,\n direction: 1,\n },\n stepDefaults\n );\n\n return this;\n }\n\n /**\n * Retrieve the current step number.\n *\n * @method getCurrentStepNumber\n * @return {Number} The current step number\n */\n getCurrentStepNumber() {\n return parseInt(this.currentStepNumber, 10);\n }\n\n /**\n * Store the current step number.\n *\n * @method setCurrentStepNumber\n * @param {Number} stepNumber The current step number\n * @chainable\n */\n setCurrentStepNumber(stepNumber) {\n this.currentStepNumber = stepNumber;\n if (this.storage) {\n try {\n this.storage.setItem(this.storageKey, stepNumber);\n } catch (e) {\n if (e.code === DOMException.QUOTA_EXCEEDED_ERR) {\n this.storage.removeItem(this.storageKey);\n }\n }\n }\n }\n\n /**\n * Get the next step number after the currently displayed step.\n *\n * @method getNextStepNumber\n * @param {Number} stepNumber The current step number\n * @return {Number} The next step number to display\n */\n getNextStepNumber(stepNumber) {\n if (typeof stepNumber === 'undefined') {\n stepNumber = this.getCurrentStepNumber();\n }\n let nextStepNumber = stepNumber + 1;\n\n // Keep checking the remaining steps.\n while (nextStepNumber <= this.steps.length) {\n if (this.isStepPotentiallyVisible(this.getStepConfig(nextStepNumber))) {\n return nextStepNumber;\n }\n nextStepNumber++;\n }\n\n return null;\n }\n\n /**\n * Get the previous step number before the currently displayed step.\n *\n * @method getPreviousStepNumber\n * @param {Number} stepNumber The current step number\n * @return {Number} The previous step number to display\n */\n getPreviousStepNumber(stepNumber) {\n if (typeof stepNumber === 'undefined') {\n stepNumber = this.getCurrentStepNumber();\n }\n let previousStepNumber = stepNumber - 1;\n\n // Keep checking the remaining steps.\n while (previousStepNumber >= 0) {\n if (this.isStepPotentiallyVisible(this.getStepConfig(previousStepNumber))) {\n return previousStepNumber;\n }\n previousStepNumber--;\n }\n\n return null;\n }\n\n /**\n * Is the step the final step number?\n *\n * @method isLastStep\n * @param {Number} stepNumber Step number to test\n * @return {Boolean} Whether the step is the final step\n */\n isLastStep(stepNumber) {\n let nextStepNumber = this.getNextStepNumber(stepNumber);\n\n return nextStepNumber === null;\n }\n\n /**\n * Is this step potentially visible?\n *\n * @method isStepPotentiallyVisible\n * @param {Object} stepConfig The step configuration to normalise\n * @return {Boolean} Whether the step is the potentially visible\n */\n isStepPotentiallyVisible(stepConfig) {\n if (!stepConfig) {\n // Without step config, there can be no step.\n return false;\n }\n\n if (this.isStepActuallyVisible(stepConfig)) {\n // If it is actually visible, it is already potentially visible.\n return true;\n }\n\n if (typeof stepConfig.orphan !== 'undefined' && stepConfig.orphan) {\n // Orphan steps have no target. They are always visible.\n return true;\n }\n\n if (typeof stepConfig.delay !== 'undefined' && stepConfig.delay) {\n // Only return true if the activated has not been used yet.\n return true;\n }\n\n // Not theoretically, or actually visible.\n return false;\n }\n\n /**\n * Get potentially visible steps in a tour.\n *\n * @returns {StepList} A list of ordered steps\n */\n getPotentiallyVisibleSteps() {\n let position = 1;\n let result = [];\n // Checking the total steps.\n for (let stepNumber = 0; stepNumber < this.steps.length; stepNumber++) {\n const stepConfig = this.getStepConfig(stepNumber);\n if (this.isStepPotentiallyVisible(stepConfig)) {\n result[stepNumber] = {stepId: stepConfig.stepid, position: position};\n position++;\n }\n }\n\n return result;\n }\n\n /**\n * Is this step actually visible?\n *\n * @method isStepActuallyVisible\n * @param {Object} stepConfig The step configuration to normalise\n * @return {Boolean} Whether the step is actually visible\n */\n isStepActuallyVisible(stepConfig) {\n if (!stepConfig) {\n // Without step config, there can be no step.\n return false;\n }\n\n let target = this.getStepTarget(stepConfig);\n if (target && target.length && target.is(':visible')) {\n // Without a target, there can be no step.\n return !!target.length;\n }\n\n return false;\n }\n\n /**\n * Go to the next step in the tour.\n *\n * @method next\n * @chainable\n * @return {Object} this.\n */\n next() {\n return this.gotoStep(this.getNextStepNumber());\n }\n\n /**\n * Go to the previous step in the tour.\n *\n * @method previous\n * @chainable\n * @return {Object} this.\n */\n previous() {\n return this.gotoStep(this.getPreviousStepNumber(), -1);\n }\n\n /**\n * Go to the specified step in the tour.\n *\n * @method gotoStep\n * @param {Number} stepNumber The step number to display\n * @param {Number} direction Next or previous step\n * @chainable\n * @return {Object} this.\n * @fires tool_usertours/stepRender\n * @fires tool_usertours/stepRendered\n * @fires tool_usertours/stepHide\n * @fires tool_usertours/stepHidden\n */\n gotoStep(stepNumber, direction) {\n if (stepNumber < 0) {\n return this.endTour();\n }\n\n let stepConfig = this.getStepConfig(stepNumber);\n if (stepConfig === null) {\n return this.endTour();\n }\n\n return this._gotoStep(stepConfig, direction);\n }\n\n _gotoStep(stepConfig, direction) {\n if (!stepConfig) {\n return this.endTour();\n }\n\n if (typeof stepConfig.delay !== 'undefined' && stepConfig.delay && !stepConfig.delayed) {\n stepConfig.delayed = true;\n window.setTimeout(this._gotoStep.bind(this), stepConfig.delay, stepConfig, direction);\n\n return this;\n } else if (!stepConfig.orphan && !this.isStepActuallyVisible(stepConfig)) {\n let fn = direction == -1 ? 'getPreviousStepNumber' : 'getNextStepNumber';\n return this.gotoStep(this[fn](stepConfig.stepNumber), direction);\n }\n\n this.hide();\n\n const stepRenderEvent = this.dispatchEvent(eventTypes.stepRender, {stepConfig}, true);\n if (!stepRenderEvent.defaultPrevented) {\n this.renderStep(stepConfig);\n this.dispatchEvent(eventTypes.stepRendered, {stepConfig});\n }\n\n return this;\n }\n\n /**\n * Fetch the normalised step configuration for the specified step number.\n *\n * @method getStepConfig\n * @param {Number} stepNumber The step number to fetch configuration for\n * @return {Object} The step configuration\n */\n getStepConfig(stepNumber) {\n if (stepNumber === null || stepNumber < 0 || stepNumber >= this.steps.length) {\n return null;\n }\n\n // Normalise the step configuration.\n let stepConfig = this.normalizeStepConfig(this.steps[stepNumber]);\n\n // Add the stepNumber to the stepConfig.\n stepConfig = $.extend(stepConfig, {stepNumber: stepNumber});\n\n return stepConfig;\n }\n\n /**\n * Normalise the supplied step configuration.\n *\n * @method normalizeStepConfig\n * @param {Object} stepConfig The step configuration to normalise\n * @return {Object} The normalised step configuration\n */\n normalizeStepConfig(stepConfig) {\n\n if (typeof stepConfig.reflex !== 'undefined' && typeof stepConfig.moveAfterClick === 'undefined') {\n stepConfig.moveAfterClick = stepConfig.reflex;\n }\n\n if (typeof stepConfig.element !== 'undefined' && typeof stepConfig.target === 'undefined') {\n stepConfig.target = stepConfig.element;\n }\n\n if (typeof stepConfig.content !== 'undefined' && typeof stepConfig.body === 'undefined') {\n stepConfig.body = stepConfig.content;\n }\n\n stepConfig = $.extend({}, this.stepDefaults, stepConfig);\n\n stepConfig = $.extend({}, {\n attachTo: stepConfig.target,\n attachPoint: 'after',\n }, stepConfig);\n\n if (stepConfig.attachTo) {\n stepConfig.attachTo = $(stepConfig.attachTo).first();\n }\n\n return stepConfig;\n }\n\n /**\n * Fetch the actual step target from the selector.\n *\n * This should not be called until after any delay has completed.\n *\n * @method getStepTarget\n * @param {Object} stepConfig The step configuration\n * @return {$}\n */\n getStepTarget(stepConfig) {\n if (stepConfig.target) {\n return $(stepConfig.target);\n }\n\n return null;\n }\n\n /**\n * Fire any event handlers for the specified event.\n *\n * @param {String} eventName The name of the event\n * @param {Object} [detail={}] Any additional details to pass into the eveent\n * @param {Boolean} [cancelable=false] Whether preventDefault() can be called\n * @returns {CustomEvent}\n */\n dispatchEvent(\n eventName,\n detail = {},\n cancelable = false\n ) {\n return dispatchEvent(eventName, {\n // Add the tour to the detail.\n tour: this,\n ...detail,\n }, document, {\n cancelable,\n });\n }\n\n /**\n * @method addEventHandler\n * @param {string} eventName The name of the event to listen for\n * @param {function} handler The event handler to call\n * @return {Object} this.\n */\n addEventHandler(eventName, handler) {\n if (typeof this.eventHandlers[eventName] === 'undefined') {\n this.eventHandlers[eventName] = [];\n }\n\n this.eventHandlers[eventName].push(handler);\n\n return this;\n }\n\n /**\n * Process listeners for the step being shown.\n *\n * @method processStepListeners\n * @param {object} stepConfig The configuration for the step\n * @chainable\n * @return {Object} this.\n */\n processStepListeners(stepConfig) {\n this.listeners.push(\n // Next button.\n {\n node: this.currentStepNode,\n args: ['click', '[data-role=\"next\"]', $.proxy(this.next, this)]\n },\n\n // Close and end tour buttons.\n {\n node: this.currentStepNode,\n args: ['click', '[data-role=\"end\"]', $.proxy(this.endTour, this)]\n },\n\n // Click backdrop and hide tour.\n {\n node: $('[data-flexitour=\"backdrop\"]'),\n args: ['click', $.proxy(this.hide, this)]\n },\n\n // Keypresses.\n {\n node: $('body'),\n args: ['keydown', $.proxy(this.handleKeyDown, this)]\n });\n\n if (stepConfig.moveOnClick) {\n var targetNode = this.getStepTarget(stepConfig);\n this.listeners.push({\n node: targetNode,\n args: ['click', $.proxy(function(e) {\n if ($(e.target).parents('[data-flexitour=\"container\"]').length === 0) {\n // Ignore clicks when they are in the flexitour.\n window.setTimeout($.proxy(this.next, this), 500);\n }\n }, this)]\n });\n }\n\n this.listeners.forEach(function(listener) {\n listener.node.on.apply(listener.node, listener.args);\n });\n\n return this;\n }\n\n /**\n * Reset step listeners.\n *\n * @method resetStepListeners\n * @chainable\n * @return {Object} this.\n */\n resetStepListeners() {\n // Stop listening to all external handlers.\n if (this.listeners) {\n this.listeners.forEach(function(listener) {\n listener.node.off.apply(listener.node, listener.args);\n });\n }\n this.listeners = [];\n\n return this;\n }\n\n /**\n * The standard step renderer.\n *\n * @method renderStep\n * @param {Object} stepConfig The step configuration of the step\n * @chainable\n * @return {Object} this.\n */\n renderStep(stepConfig) {\n // Store the current step configuration for later.\n this.currentStepConfig = stepConfig;\n this.setCurrentStepNumber(stepConfig.stepNumber);\n\n // Fetch the template and convert it to a $ object.\n let template = $(this.getTemplateContent());\n\n // Title.\n template.find('[data-placeholder=\"title\"]')\n .html(stepConfig.title);\n\n // Body.\n template.find('[data-placeholder=\"body\"]')\n .html(stepConfig.body);\n\n // Buttons.\n const nextBtn = template.find('[data-role=\"next\"]');\n const endBtn = template.find('[data-role=\"end\"]');\n\n // Is this the final step?\n if (this.isLastStep(stepConfig.stepNumber)) {\n nextBtn.hide();\n endBtn.removeClass(\"btn-secondary\").addClass(\"btn-primary\");\n } else {\n nextBtn.prop('disabled', false);\n // Use Skip tour label for the End tour button.\n getString('skip_tour', 'tool_usertours').then(value => {\n endBtn.html(value);\n return;\n }).catch();\n }\n\n nextBtn.attr('role', 'button');\n endBtn.attr('role', 'button');\n\n if (this.originalConfiguration.displaystepnumbers) {\n const stepsPotentiallyVisible = this.getPotentiallyVisibleSteps();\n const totalStepsPotentiallyVisible = stepsPotentiallyVisible.length;\n const position = stepsPotentiallyVisible[stepConfig.stepNumber].position;\n if (totalStepsPotentiallyVisible > 1) {\n // Change the label of the Next button to include the sequence.\n getString('nextstep_sequence', 'tool_usertours',\n {position: position, total: totalStepsPotentiallyVisible}).then(value => {\n nextBtn.html(value);\n return;\n }).catch();\n }\n }\n\n // Replace the template with the updated version.\n stepConfig.template = template;\n\n // Add to the page.\n this.addStepToPage(stepConfig);\n\n // Process step listeners after adding to the page.\n // This uses the currentNode.\n this.processStepListeners(stepConfig);\n\n return this;\n }\n\n /**\n * Getter for the template content.\n *\n * @method getTemplateContent\n * @return {$}\n */\n getTemplateContent() {\n return $(this.templateContent).clone();\n }\n\n /**\n * Helper to add a step to the page.\n *\n * @method addStepToPage\n * @param {Object} stepConfig The step configuration of the step\n * @chainable\n * @return {Object} this.\n */\n addStepToPage(stepConfig) {\n // Create the stepNode from the template data.\n let currentStepNode = $('')\n .html(stepConfig.template)\n .hide();\n\n // The scroll animation occurs on the body or html.\n let animationTarget = $('body, html')\n .stop(true, true);\n\n if (this.isStepActuallyVisible(stepConfig)) {\n let targetNode = this.getStepTarget(stepConfig);\n\n if (targetNode.parents('[data-usertour=\"scroller\"]').length) {\n animationTarget = targetNode.parents('[data-usertour=\"scroller\"]');\n }\n\n targetNode.data('flexitour', 'target');\n\n let zIndex = this.calculateZIndex(targetNode);\n if (zIndex) {\n stepConfig.zIndex = zIndex + 1;\n }\n\n if (stepConfig.zIndex) {\n currentStepNode.css('zIndex', stepConfig.zIndex + 1);\n }\n\n // Add the backdrop.\n this.positionBackdrop(stepConfig);\n\n $(document.body).append(currentStepNode);\n this.currentStepNode = currentStepNode;\n\n // Ensure that the step node is positioned.\n // Some situations mean that the value is not properly calculated without this step.\n this.currentStepNode.css({\n top: 0,\n left: 0,\n });\n\n animationTarget\n .animate({\n scrollTop: this.calculateScrollTop(stepConfig),\n }).promise().then(function() {\n this.positionStep(stepConfig);\n this.revealStep(stepConfig);\n return;\n }.bind(this))\n .catch(function() {\n // Silently fail.\n });\n\n } else if (stepConfig.orphan) {\n stepConfig.isOrphan = true;\n\n // This will be appended to the body instead.\n stepConfig.attachTo = $('body').first();\n stepConfig.attachPoint = 'append';\n\n // Add the backdrop.\n this.positionBackdrop(stepConfig);\n\n // This is an orphaned step.\n currentStepNode.addClass('orphan');\n\n // It lives in the body.\n $(document.body).append(currentStepNode);\n this.currentStepNode = currentStepNode;\n\n this.currentStepNode.offset(this.calculateStepPositionInPage());\n this.currentStepNode.css('position', 'fixed');\n\n this.currentStepPopper = new Popper(\n $('body'),\n this.currentStepNode[0], {\n removeOnDestroy: true,\n placement: stepConfig.placement + '-start',\n arrowElement: '[data-role=\"arrow\"]',\n // Empty the modifiers. We've already placed the step and don't want it moved.\n modifiers: {\n hide: {\n enabled: false,\n },\n applyStyle: {\n onLoad: null,\n enabled: false,\n },\n }\n }\n );\n\n this.revealStep(stepConfig);\n }\n\n return this;\n }\n\n /**\n * Make the given step visible.\n *\n * @method revealStep\n * @param {Object} stepConfig The step configuration of the step\n * @chainable\n * @return {Object} this.\n */\n revealStep(stepConfig) {\n // Fade the step in.\n this.currentStepNode.fadeIn('', $.proxy(function() {\n // Announce via ARIA.\n this.announceStep(stepConfig);\n\n // Focus on the current step Node.\n this.currentStepNode.focus();\n window.setTimeout($.proxy(function() {\n // After a brief delay, focus again.\n // There seems to be an issue with Jaws where it only reads the dialogue title initially.\n // This second focus helps it to read the full dialogue.\n if (this.currentStepNode) {\n this.currentStepNode.focus();\n }\n }, this), 100);\n\n }, this));\n\n return this;\n }\n\n /**\n * Helper to announce the step on the page.\n *\n * @method announceStep\n * @param {Object} stepConfig The step configuration of the step\n * @chainable\n * @return {Object} this.\n */\n announceStep(stepConfig) {\n // Setup the step Dialogue as per:\n // * https://www.w3.org/TR/wai-aria-practices/#dialog_nonmodal\n // * https://www.w3.org/TR/wai-aria-practices/#dialog_modal\n\n // Generate an ID for the current step node.\n let stepId = 'tour-step-' + this.tourName + '-' + stepConfig.stepNumber;\n this.currentStepNode.attr('id', stepId);\n\n let bodyRegion = this.currentStepNode.find('[data-placeholder=\"body\"]').first();\n bodyRegion.attr('id', stepId + '-body');\n bodyRegion.attr('role', 'document');\n\n let headerRegion = this.currentStepNode.find('[data-placeholder=\"title\"]').first();\n headerRegion.attr('id', stepId + '-title');\n headerRegion.attr('aria-labelledby', stepId + '-body');\n\n // Generally, a modal dialog has a role of dialog.\n this.currentStepNode.attr('role', 'dialog');\n this.currentStepNode.attr('tabindex', 0);\n this.currentStepNode.attr('aria-labelledby', stepId + '-title');\n this.currentStepNode.attr('aria-describedby', stepId + '-body');\n\n // Configure ARIA attributes on the target.\n let target = this.getStepTarget(stepConfig);\n if (target) {\n if (!target.attr('tabindex')) {\n target.attr('tabindex', 0);\n }\n\n target\n .data('original-describedby', target.attr('aria-describedby'))\n .attr('aria-describedby', stepId + '-body')\n ;\n }\n\n this.accessibilityShow(stepConfig);\n\n return this;\n }\n\n /**\n * Handle key down events.\n *\n * @method handleKeyDown\n * @param {EventFacade} e\n */\n handleKeyDown(e) {\n let tabbableSelector = 'a[href], link[href], [draggable=true], [contenteditable=true], ';\n tabbableSelector += ':input:enabled, [tabindex], button:enabled';\n switch (e.keyCode) {\n case 27:\n this.endTour();\n break;\n\n // 9 == Tab - trap focus for items with a backdrop.\n case 9:\n // Tab must be handled on key up only in this instance.\n (function() {\n if (!this.currentStepConfig.hasBackdrop) {\n // Trapping tab focus is only handled for those steps with a backdrop.\n return;\n }\n\n // Find all tabbable locations.\n let activeElement = $(document.activeElement);\n let stepTarget = this.getStepTarget(this.currentStepConfig);\n let tabbableNodes = $(tabbableSelector);\n let dialogContainer = $('span[data-flexitour=\"container\"]');\n let currentIndex;\n // Filter out element which is not belong to target section or dialogue.\n if (stepTarget) {\n tabbableNodes = tabbableNodes.filter(function(index, element) {\n return stepTarget !== null\n && (stepTarget.has(element).length\n || dialogContainer.has(element).length\n || stepTarget.is(element)\n || dialogContainer.is(element));\n });\n }\n\n // Find index of focusing element.\n tabbableNodes.each(function(index, element) {\n if (activeElement.is(element)) {\n currentIndex = index;\n return false;\n }\n // Keep looping.\n return true;\n });\n\n let nextIndex;\n let nextNode;\n let focusRelevant;\n if (currentIndex != void 0) {\n let direction = 1;\n if (e.shiftKey) {\n direction = -1;\n }\n nextIndex = currentIndex;\n do {\n nextIndex += direction;\n nextNode = $(tabbableNodes[nextIndex]);\n } while (nextNode.length && nextNode.is(':disabled') || nextNode.is(':hidden'));\n if (nextNode.length) {\n // A new f\n focusRelevant = nextNode.closest(stepTarget).length;\n focusRelevant = focusRelevant || nextNode.closest(this.currentStepNode).length;\n } else {\n // Unable to find the target somehow.\n focusRelevant = false;\n }\n }\n\n if (focusRelevant) {\n nextNode.focus();\n } else {\n if (e.shiftKey) {\n // Focus on the last tabbable node in the step.\n this.currentStepNode.find(tabbableSelector).last().focus();\n } else {\n if (this.currentStepConfig.isOrphan) {\n // Focus on the step - there is no target.\n this.currentStepNode.focus();\n } else {\n // Focus on the step target.\n stepTarget.focus();\n }\n }\n }\n e.preventDefault();\n }).call(this);\n break;\n }\n }\n\n /**\n * Start the current tour.\n *\n * @method startTour\n * @param {Number} startAt Which step number to start at. If not specified, starts at the last point.\n * @chainable\n * @return {Object} this.\n * @fires tool_usertours/tourStart\n * @fires tool_usertours/tourStarted\n */\n startTour(startAt) {\n if (this.storage && typeof startAt === 'undefined') {\n let storageStartValue = this.storage.getItem(this.storageKey);\n if (storageStartValue) {\n let storageStartAt = parseInt(storageStartValue, 10);\n if (storageStartAt <= this.steps.length) {\n startAt = storageStartAt;\n }\n }\n }\n\n if (typeof startAt === 'undefined') {\n startAt = this.getCurrentStepNumber();\n }\n\n const tourStartEvent = this.dispatchEvent(eventTypes.tourStart, {startAt}, true);\n if (!tourStartEvent.defaultPrevented) {\n this.gotoStep(startAt);\n this.tourRunning = true;\n this.dispatchEvent(eventTypes.tourStarted, {startAt});\n }\n\n return this;\n }\n\n /**\n * Restart the tour from the beginning, resetting the completionlag.\n *\n * @method restartTour\n * @chainable\n * @return {Object} this.\n */\n restartTour() {\n return this.startTour(0);\n }\n\n /**\n * End the current tour.\n *\n * @method endTour\n * @chainable\n * @return {Object} this.\n * @fires tool_usertours/tourEnd\n * @fires tool_usertours/tourEnded\n */\n endTour() {\n const tourEndEvent = this.dispatchEvent(eventTypes.tourEnd, {}, true);\n if (tourEndEvent.defaultPrevented) {\n return this;\n }\n\n if (this.currentStepConfig) {\n let previousTarget = this.getStepTarget(this.currentStepConfig);\n if (previousTarget) {\n if (!previousTarget.attr('tabindex')) {\n previousTarget.attr('tabindex', '-1');\n }\n previousTarget.focus();\n }\n }\n\n this.hide(true);\n\n this.tourRunning = false;\n this.dispatchEvent(eventTypes.tourEnded);\n\n return this;\n }\n\n /**\n * Hide any currently visible steps.\n *\n * @method hide\n * @param {Bool} transition Animate the visibility change\n * @chainable\n * @return {Object} this.\n * @fires tool_usertours/stepHide\n * @fires tool_usertours/stepHidden\n */\n hide(transition) {\n const stepHideEvent = this.dispatchEvent(eventTypes.stepHide, {}, true);\n if (stepHideEvent.defaultPrevented) {\n return this;\n }\n\n if (this.currentStepNode && this.currentStepNode.length) {\n this.currentStepNode.hide();\n if (this.currentStepPopper) {\n this.currentStepPopper.destroy();\n }\n }\n\n // Restore original target configuration.\n if (this.currentStepConfig) {\n let target = this.getStepTarget(this.currentStepConfig);\n if (target) {\n if (target.data('original-labelledby')) {\n target.attr('aria-labelledby', target.data('original-labelledby'));\n }\n\n if (target.data('original-describedby')) {\n target.attr('aria-describedby', target.data('original-describedby'));\n }\n\n if (target.data('original-tabindex')) {\n target.attr('tabindex', target.data('tabindex'));\n }\n }\n\n // Clear the step configuration.\n this.currentStepConfig = null;\n }\n\n let fadeTime = 0;\n if (transition) {\n fadeTime = 400;\n }\n\n // Remove the backdrop features.\n $('[data-flexitour=\"step-background\"]').remove();\n $('[data-flexitour=\"step-backdrop\"]').removeAttr('data-flexitour');\n $('[data-flexitour=\"backdrop\"]').fadeOut(fadeTime, function() {\n $(this).remove();\n });\n\n // Remove aria-describedby and tabindex attributes.\n if (this.currentStepNode && this.currentStepNode.length) {\n let stepId = this.currentStepNode.attr('id');\n if (stepId) {\n let currentStepElement = '[aria-describedby=\"' + stepId + '-body\"]';\n $(currentStepElement).removeAttr('tabindex');\n $(currentStepElement).removeAttr('aria-describedby');\n }\n }\n\n // Reset the listeners.\n this.resetStepListeners();\n\n this.accessibilityHide();\n\n this.dispatchEvent(eventTypes.stepHidden);\n\n this.currentStepNode = null;\n this.currentStepPopper = null;\n return this;\n }\n\n /**\n * Show the current steps.\n *\n * @method show\n * @chainable\n * @return {Object} this.\n */\n show() {\n // Show the current step.\n let startAt = this.getCurrentStepNumber();\n\n return this.gotoStep(startAt);\n }\n\n /**\n * Return the current step node.\n *\n * @method getStepContainer\n * @return {jQuery}\n */\n getStepContainer() {\n return $(this.currentStepNode);\n }\n\n /**\n * Calculate scrollTop.\n *\n * @method calculateScrollTop\n * @param {Object} stepConfig The step configuration of the step\n * @return {Number}\n */\n calculateScrollTop(stepConfig) {\n let viewportHeight = $(window).height();\n let targetNode = this.getStepTarget(stepConfig);\n\n let scrollParent = $(window);\n if (targetNode.parents('[data-usertour=\"scroller\"]').length) {\n scrollParent = targetNode.parents('[data-usertour=\"scroller\"]');\n }\n let scrollTop = scrollParent.scrollTop();\n\n if (stepConfig.placement === 'top') {\n // If the placement is top, center scroll at the top of the target.\n scrollTop = targetNode.offset().top - (viewportHeight / 2);\n } else if (stepConfig.placement === 'bottom') {\n // If the placement is bottom, center scroll at the bottom of the target.\n scrollTop = targetNode.offset().top + targetNode.height() + scrollTop - (viewportHeight / 2);\n } else if (targetNode.height() <= (viewportHeight * 0.8)) {\n // If the placement is left/right, and the target fits in the viewport, centre screen on the target\n scrollTop = targetNode.offset().top - ((viewportHeight - targetNode.height()) / 2);\n } else {\n // If the placement is left/right, and the target is bigger than the viewport, set scrollTop to target.top + buffer\n // and change step attachmentTarget to top+.\n scrollTop = targetNode.offset().top - (viewportHeight * 0.2);\n }\n\n // Never scroll over the top.\n scrollTop = Math.max(0, scrollTop);\n\n // Never scroll beyond the bottom.\n scrollTop = Math.min($(document).height() - viewportHeight, scrollTop);\n\n return Math.ceil(scrollTop);\n }\n\n /**\n * Calculate dialogue position for page middle.\n *\n * @method calculateScrollTop\n * @return {Number}\n */\n calculateStepPositionInPage() {\n let viewportHeight = $(window).height();\n let stepHeight = this.currentStepNode.height();\n\n let viewportWidth = $(window).width();\n let stepWidth = this.currentStepNode.width();\n\n return {\n top: Math.ceil((viewportHeight - stepHeight) / 2),\n left: Math.ceil((viewportWidth - stepWidth) / 2)\n };\n }\n\n /**\n * Position the step on the page.\n *\n * @method positionStep\n * @param {Object} stepConfig The step configuration of the step\n * @chainable\n * @return {Object} this.\n */\n positionStep(stepConfig) {\n let content = this.currentStepNode;\n if (!content || !content.length) {\n // Unable to find the step node.\n return this;\n }\n\n stepConfig.placement = this.recalculatePlacement(stepConfig);\n let flipBehavior;\n switch (stepConfig.placement) {\n case 'left':\n flipBehavior = ['left', 'right', 'top', 'bottom'];\n break;\n case 'right':\n flipBehavior = ['right', 'left', 'top', 'bottom'];\n break;\n case 'top':\n flipBehavior = ['top', 'bottom', 'right', 'left'];\n break;\n case 'bottom':\n flipBehavior = ['bottom', 'top', 'right', 'left'];\n break;\n default:\n flipBehavior = 'flip';\n break;\n }\n\n let target = this.getStepTarget(stepConfig);\n var config = {\n placement: stepConfig.placement + '-start',\n removeOnDestroy: true,\n modifiers: {\n flip: {\n behaviour: flipBehavior,\n },\n arrow: {\n element: '[data-role=\"arrow\"]',\n },\n },\n onCreate: function(data) {\n recalculateArrowPosition(data);\n },\n onUpdate: function(data) {\n recalculateArrowPosition(data);\n },\n };\n\n let recalculateArrowPosition = function(data) {\n let placement = data.placement.split('-')[0];\n const isVertical = ['left', 'right'].indexOf(placement) !== -1;\n const arrowElement = data.instance.popper.querySelector('[data-role=\"arrow\"]');\n const stepElement = $(data.instance.popper.querySelector('[data-role=\"flexitour-step\"]'));\n if (isVertical) {\n let arrowHeight = parseFloat(window.getComputedStyle(arrowElement).height);\n let arrowOffset = parseFloat(window.getComputedStyle(arrowElement).top);\n let popperHeight = parseFloat(window.getComputedStyle(data.instance.popper).height);\n let popperOffset = parseFloat(window.getComputedStyle(data.instance.popper).top);\n let popperBorderWidth = parseFloat(stepElement.css('borderTopWidth'));\n let popperBorderRadiusWidth = parseFloat(stepElement.css('borderTopLeftRadius')) * 2;\n let arrowPos = arrowOffset + (arrowHeight / 2);\n let maxPos = popperHeight + popperOffset - popperBorderWidth - popperBorderRadiusWidth;\n let minPos = popperOffset + popperBorderWidth + popperBorderRadiusWidth;\n if (arrowPos >= maxPos || arrowPos <= minPos) {\n let newArrowPos = 0;\n if (arrowPos > (popperHeight / 2)) {\n newArrowPos = maxPos - arrowHeight;\n } else {\n newArrowPos = minPos + arrowHeight;\n }\n $(arrowElement).css('top', newArrowPos);\n }\n } else {\n let arrowWidth = parseFloat(window.getComputedStyle(arrowElement).width);\n let arrowOffset = parseFloat(window.getComputedStyle(arrowElement).left);\n let popperWidth = parseFloat(window.getComputedStyle(data.instance.popper).width);\n let popperOffset = parseFloat(window.getComputedStyle(data.instance.popper).left);\n let popperBorderWidth = parseFloat(stepElement.css('borderTopWidth'));\n let popperBorderRadiusWidth = parseFloat(stepElement.css('borderTopLeftRadius')) * 2;\n let arrowPos = arrowOffset + (arrowWidth / 2);\n let maxPos = popperWidth + popperOffset - popperBorderWidth - popperBorderRadiusWidth;\n let minPos = popperOffset + popperBorderWidth + popperBorderRadiusWidth;\n if (arrowPos >= maxPos || arrowPos <= minPos) {\n let newArrowPos = 0;\n if (arrowPos > (popperWidth / 2)) {\n newArrowPos = maxPos - arrowWidth;\n } else {\n newArrowPos = minPos + arrowWidth;\n }\n $(arrowElement).css('left', newArrowPos);\n }\n }\n };\n\n let background = $('[data-flexitour=\"step-background\"]');\n if (background.length) {\n target = background;\n }\n this.currentStepPopper = new Popper(target, content[0], config);\n\n return this;\n }\n\n /**\n * For left/right placement, checks that there is room for the step at current window size.\n *\n * If there is not enough room, changes placement to 'top'.\n *\n * @method recalculatePlacement\n * @param {Object} stepConfig The step configuration of the step\n * @return {String} The placement after recalculate\n */\n recalculatePlacement(stepConfig) {\n const buffer = 10;\n const arrowWidth = 16;\n let target = this.getStepTarget(stepConfig);\n let widthContent = this.currentStepNode.width() + arrowWidth;\n let targetOffsetLeft = target.offset().left - buffer;\n let targetOffsetRight = target.offset().left + target.width() + buffer;\n let placement = stepConfig.placement;\n\n if (['left', 'right'].indexOf(placement) !== -1) {\n if ((targetOffsetLeft < (widthContent + buffer)) &&\n ((targetOffsetRight + widthContent + buffer) > document.documentElement.clientWidth)) {\n placement = 'top';\n }\n }\n return placement;\n }\n\n /**\n * Add the backdrop.\n *\n * @method positionBackdrop\n * @param {Object} stepConfig The step configuration of the step\n * @chainable\n * @return {Object} this.\n */\n positionBackdrop(stepConfig) {\n if (stepConfig.backdrop) {\n this.currentStepConfig.hasBackdrop = true;\n let backdrop = $('
');\n\n if (stepConfig.zIndex) {\n if (stepConfig.attachPoint === 'append') {\n stepConfig.attachTo.append(backdrop);\n } else {\n backdrop.insertAfter(stepConfig.attachTo);\n }\n } else {\n $('body').append(backdrop);\n }\n\n if (this.isStepActuallyVisible(stepConfig)) {\n // The step has a visible target.\n // Punch a hole through the backdrop.\n let background = $('[data-flexitour=\"step-background\"]');\n if (!background.length) {\n background = $('
');\n }\n\n let targetNode = this.getStepTarget(stepConfig);\n\n let buffer = 10;\n\n let colorNode = targetNode;\n if (buffer) {\n colorNode = $('body');\n }\n\n let drawertop = 0;\n if (targetNode.parents('[data-usertour=\"scroller\"]').length) {\n drawertop = targetNode.parents('[data-usertour=\"scroller\"]').scrollTop();\n background.css({\n position: 'fixed'\n });\n }\n\n background.css({\n width: targetNode.outerWidth() + buffer + buffer,\n height: targetNode.outerHeight() + buffer + buffer,\n left: targetNode.offset().left - buffer,\n top: targetNode.offset().top + drawertop - buffer,\n backgroundColor: this.calculateInherittedBackgroundColor(colorNode),\n });\n\n if (targetNode.offset().left < buffer) {\n background.css({\n width: targetNode.outerWidth() + targetNode.offset().left + buffer,\n left: targetNode.offset().left,\n });\n }\n\n if ((targetNode.offset().top + drawertop) < buffer) {\n background.css({\n height: targetNode.outerHeight() + targetNode.offset().top + buffer,\n top: targetNode.offset().top,\n });\n }\n\n let targetRadius = targetNode.css('borderRadius');\n if (targetRadius && targetRadius !== $('body').css('borderRadius')) {\n background.css('borderRadius', targetRadius);\n }\n\n let targetPosition = this.calculatePosition(targetNode);\n if (targetPosition === 'fixed') {\n background.css('top', 0);\n } else if (targetPosition === 'absolute') {\n background.css('position', 'fixed');\n }\n\n let fader = background.clone();\n fader.css({\n backgroundColor: backdrop.css('backgroundColor'),\n opacity: backdrop.css('opacity'),\n });\n fader.attr('data-flexitour', 'step-background-fader');\n\n if (targetNode.parents('[data-region=\"fixed-drawer\"]').length) {\n let targetClone = targetNode.clone();\n background.append(targetClone);\n }\n\n if (stepConfig.zIndex) {\n if (stepConfig.attachPoint === 'append') {\n stepConfig.attachTo.append(background);\n } else {\n fader.insertAfter(stepConfig.attachTo);\n background.insertAfter(stepConfig.attachTo);\n }\n } else {\n $('body').append(fader);\n $('body').append(background);\n }\n\n // Add the backdrop data to the actual target.\n // This is the part which actually does the work.\n targetNode.attr('data-flexitour', 'step-backdrop');\n\n if (stepConfig.zIndex) {\n backdrop.css('zIndex', stepConfig.zIndex);\n background.css('zIndex', stepConfig.zIndex + 1);\n targetNode.css('zIndex', stepConfig.zIndex + 2);\n }\n\n fader.fadeOut('2000', function() {\n $(this).remove();\n });\n }\n }\n return this;\n }\n\n /**\n * Calculate the inheritted z-index.\n *\n * @method calculateZIndex\n * @param {jQuery} elem The element to calculate z-index for\n * @return {Number} Calculated z-index\n */\n calculateZIndex(elem) {\n elem = $(elem);\n while (elem.length && elem[0] !== document) {\n // Ignore z-index if position is set to a value where z-index is ignored by the browser\n // This makes behavior of this function consistent across browsers\n // WebKit always returns auto if the element is positioned.\n let position = elem.css(\"position\");\n if (position === \"absolute\" || position === \"relative\" || position === \"fixed\") {\n // IE returns 0 when zIndex is not specified\n // other browsers return a string\n // we ignore the case of nested elements with an explicit value of 0\n //
\n let value = parseInt(elem.css(\"zIndex\"), 10);\n if (!isNaN(value) && value !== 0) {\n return value;\n }\n }\n elem = elem.parent();\n }\n\n return 0;\n }\n\n /**\n * Calculate the inheritted background colour.\n *\n * @method calculateInherittedBackgroundColor\n * @param {jQuery} elem The element to calculate colour for\n * @return {String} Calculated background colour\n */\n calculateInherittedBackgroundColor(elem) {\n // Use a fake node to compare each element against.\n let fakeNode = $('
').hide();\n $('body').append(fakeNode);\n let fakeElemColor = fakeNode.css('backgroundColor');\n fakeNode.remove();\n\n elem = $(elem);\n while (elem.length && elem[0] !== document) {\n let color = elem.css('backgroundColor');\n if (color !== fakeElemColor) {\n return color;\n }\n elem = elem.parent();\n }\n\n return null;\n }\n\n /**\n * Calculate the inheritted position.\n *\n * @method calculatePosition\n * @param {jQuery} elem The element to calculate position for\n * @return {String} Calculated position\n */\n calculatePosition(elem) {\n elem = $(elem);\n while (elem.length && elem[0] !== document) {\n let position = elem.css('position');\n if (position !== 'static') {\n return position;\n }\n elem = elem.parent();\n }\n\n return null;\n }\n\n /**\n * Perform accessibility changes for step shown.\n *\n * This will add aria-hidden=\"true\" to all siblings and parent siblings.\n *\n * @method accessibilityShow\n */\n accessibilityShow() {\n let stateHolder = 'data-has-hidden';\n let attrName = 'aria-hidden';\n let hideFunction = function(child) {\n let flexitourRole = child.data('flexitour');\n if (flexitourRole) {\n switch (flexitourRole) {\n case 'container':\n case 'target':\n return;\n }\n }\n\n let hidden = child.attr(attrName);\n if (!hidden) {\n child.attr(stateHolder, true);\n Aria.hide(child);\n }\n };\n\n this.currentStepNode.siblings().each(function(index, node) {\n hideFunction($(node));\n });\n this.currentStepNode.parentsUntil('body').siblings().each(function(index, node) {\n hideFunction($(node));\n });\n }\n\n /**\n * Perform accessibility changes for step hidden.\n *\n * This will remove any newly added aria-hidden=\"true\".\n *\n * @method accessibilityHide\n */\n accessibilityHide() {\n let stateHolder = 'data-has-hidden';\n let showFunction = function(child) {\n let hidden = child.attr(stateHolder);\n if (typeof hidden !== 'undefined') {\n child.removeAttr(stateHolder);\n Aria.unhide(child);\n }\n };\n\n $('[' + stateHolder + ']').each(function(index, node) {\n showFunction($(node));\n });\n }\n};\n\nexport default Tour;\n"],"file":"tour.min.js"} \ No newline at end of file +{"version":3,"sources":["../src/tour.js"],"names":["Tour","config","init","eventHandlers","reset","originalConfiguration","configure","apply","arguments","storage","window","sessionStorage","storageKey","tourName","e","hide","resetStepListeners","steps","currentStepNumber","eventName","forEach","handler","addEventHandler","resetStepDefaults","template","templateContent","checkMinimumRequirements","Error","length","loadOriginalConfiguration","stepDefaults","setStepDefaults","$","extend","element","placement","delay","moveOnClick","moveAfterTime","orphan","direction","parseInt","stepNumber","setItem","code","DOMException","QUOTA_EXCEEDED_ERR","removeItem","getCurrentStepNumber","nextStepNumber","isStepPotentiallyVisible","getStepConfig","previousStepNumber","getNextStepNumber","stepConfig","isStepActuallyVisible","position","result","stepId","stepid","target","getStepTarget","is","gotoStep","getPreviousStepNumber","endTour","_gotoStep","delayed","setTimeout","bind","fn","stepRenderEvent","dispatchEvent","eventTypes","stepRender","defaultPrevented","renderStep","stepRendered","normalizeStepConfig","reflex","moveAfterClick","content","body","attachTo","attachPoint","first","detail","cancelable","tour","document","push","listeners","node","currentStepNode","args","proxy","next","handleKeyDown","targetNode","parents","listener","on","off","currentStepConfig","setCurrentStepNumber","getTemplateContent","find","html","title","nextBtn","endBtn","isLastStep","removeClass","addClass","prop","then","value","catch","attr","displaystepnumbers","stepsPotentiallyVisible","getPotentiallyVisibleSteps","totalStepsPotentiallyVisible","total","addStepToPage","processStepListeners","clone","animationTarget","stop","data","zIndex","calculateZIndex","css","positionBackdrop","append","top","left","animate","scrollTop","calculateScrollTop","promise","positionStep","revealStep","isOrphan","offset","calculateStepPositionInPage","currentStepPopper","Popper","removeOnDestroy","arrowElement","modifiers","enabled","applyStyle","onLoad","fadeIn","announceStep","focus","bodyRegion","headerRegion","accessibilityShow","tabbableSelector","keyCode","hasBackdrop","activeElement","stepTarget","tabbableNodes","dialogContainer","currentIndex","filter","index","has","each","nextIndex","nextNode","focusRelevant","shiftKey","closest","last","preventDefault","call","startAt","storageStartValue","getItem","storageStartAt","tourStartEvent","tourStart","tourRunning","tourStarted","startTour","tourEndEvent","tourEnd","previousTarget","tourEnded","transition","stepHideEvent","stepHide","destroy","fadeTime","remove","removeAttr","fadeOut","currentStepElement","accessibilityHide","stepHidden","viewportHeight","height","scrollParent","Math","max","min","ceil","stepHeight","viewportWidth","width","stepWidth","recalculatePlacement","flipBehavior","flip","behaviour","arrow","onCreate","recalculateArrowPosition","onUpdate","split","isVertical","indexOf","instance","popper","querySelector","stepElement","arrowHeight","parseFloat","getComputedStyle","arrowOffset","popperHeight","popperOffset","popperBorderWidth","popperBorderRadiusWidth","arrowPos","maxPos","minPos","newArrowPos","arrowWidth","popperWidth","background","widthContent","targetOffsetLeft","targetOffsetRight","documentElement","clientWidth","backdrop","insertAfter","buffer","colorNode","drawertop","scrollerElement","navigationBuffer","outerWidth","outerHeight","backgroundColor","calculateInherittedBackgroundColor","targetRadius","targetPosition","calculatePosition","fader","opacity","targetClone","elem","isNaN","parent","fakeNode","fakeElemColor","color","hideFunction","child","flexitourRole","hidden","Aria","siblings","parentsUntil","showFunction","unhide"],"mappings":"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","sourcesContent":["// This file is part of Moodle - http://moodle.org/\n//\n// Moodle is free software: you can redistribute it and/or modify\n// it under the terms of the GNU General Public License as published by\n// the Free Software Foundation, either version 3 of the License, or\n// (at your option) any later version.\n//\n// Moodle is distributed in the hope that it will be useful,\n// but WITHOUT ANY WARRANTY; without even the implied warranty of\n// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the\n// GNU General Public License for more details.\n//\n// You should have received a copy of the GNU General Public License\n// along with Moodle. If not, see .\n\n/**\n * A user tour.\n *\n * @module tool_usertours/tour\n * @copyright 2018 Andrew Nicols \n * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later\n */\n\n/**\n * A list of steps.\n *\n * @typedef {Object[]} StepList\n * @property {Number} stepId The id of the step in the database\n * @property {Number} position The position of the step within the tour (zero-indexed)\n */\n\nimport $ from 'jquery';\nimport * as Aria from 'core/aria';\nimport Popper from 'core/popper';\nimport {dispatchEvent} from 'core/event_dispatcher';\nimport {eventTypes} from './events';\nimport {get_string as getString} from 'core/str';\nimport {prefetchStrings} from 'core/prefetch';\n\n/**\n * A user tour.\n *\n * @class tool_usertours/tour\n * @property {boolean} tourRunning Whether the tour is currently running.\n */\nconst Tour = class {\n tourRunning = false;\n\n /**\n * @param {object} config The configuration object.\n */\n constructor(config) {\n this.init(config);\n }\n\n /**\n * Initialise the tour.\n *\n * @method init\n * @param {Object} config The configuration object.\n * @chainable\n * @return {Object} this.\n */\n init(config) {\n // Unset all handlers.\n this.eventHandlers = {};\n\n // Reset the current tour states.\n this.reset();\n\n // Store the initial configuration.\n this.originalConfiguration = config || {};\n\n // Apply configuration.\n this.configure.apply(this, arguments);\n\n try {\n this.storage = window.sessionStorage;\n this.storageKey = 'tourstate_' + this.tourName;\n } catch (e) {\n this.storage = false;\n this.storageKey = '';\n }\n\n prefetchStrings('tool_usertours', [\n 'nextstep_sequence',\n 'skip_tour'\n ]);\n\n return this;\n }\n\n /**\n * Reset the current tour state.\n *\n * @method reset\n * @chainable\n * @return {Object} this.\n */\n reset() {\n // Hide the current step.\n this.hide();\n\n // Unset all handlers.\n this.eventHandlers = [];\n\n // Unset all listeners.\n this.resetStepListeners();\n\n // Unset the original configuration.\n this.originalConfiguration = {};\n\n // Reset the current step number and list of steps.\n this.steps = [];\n\n // Reset the current step number.\n this.currentStepNumber = 0;\n\n return this;\n }\n\n /**\n * Prepare tour configuration.\n *\n * @method configure\n * @param {Object} config The configuration object.\n * @chainable\n * @return {Object} this.\n */\n configure(config) {\n if (typeof config === 'object') {\n // Tour name.\n if (typeof config.tourName !== 'undefined') {\n this.tourName = config.tourName;\n }\n\n // Set up eventHandlers.\n if (config.eventHandlers) {\n for (let eventName in config.eventHandlers) {\n config.eventHandlers[eventName].forEach(function(handler) {\n this.addEventHandler(eventName, handler);\n }, this);\n }\n }\n\n // Reset the step configuration.\n this.resetStepDefaults(true);\n\n // Configure the steps.\n if (typeof config.steps === 'object') {\n this.steps = config.steps;\n }\n\n if (typeof config.template !== 'undefined') {\n this.templateContent = config.template;\n }\n }\n\n // Check that we have enough to start the tour.\n this.checkMinimumRequirements();\n\n return this;\n }\n\n /**\n * Check that the configuration meets the minimum requirements.\n *\n * @method checkMinimumRequirements\n */\n checkMinimumRequirements() {\n // Need a tourName.\n if (!this.tourName) {\n throw new Error(\"Tour Name required\");\n }\n\n // Need a minimum of one step.\n if (!this.steps || !this.steps.length) {\n throw new Error(\"Steps must be specified\");\n }\n }\n\n /**\n * Reset step default configuration.\n *\n * @method resetStepDefaults\n * @param {Boolean} loadOriginalConfiguration Whether to load the original configuration supplied with the Tour.\n * @chainable\n * @return {Object} this.\n */\n resetStepDefaults(loadOriginalConfiguration) {\n if (typeof loadOriginalConfiguration === 'undefined') {\n loadOriginalConfiguration = true;\n }\n\n this.stepDefaults = {};\n if (!loadOriginalConfiguration || typeof this.originalConfiguration.stepDefaults === 'undefined') {\n this.setStepDefaults({});\n } else {\n this.setStepDefaults(this.originalConfiguration.stepDefaults);\n }\n\n return this;\n }\n\n /**\n * Set the step defaults.\n *\n * @method setStepDefaults\n * @param {Object} stepDefaults The step defaults to apply to all steps\n * @chainable\n * @return {Object} this.\n */\n setStepDefaults(stepDefaults) {\n if (!this.stepDefaults) {\n this.stepDefaults = {};\n }\n $.extend(\n this.stepDefaults,\n {\n element: '',\n placement: 'top',\n delay: 0,\n moveOnClick: false,\n moveAfterTime: 0,\n orphan: false,\n direction: 1,\n },\n stepDefaults\n );\n\n return this;\n }\n\n /**\n * Retrieve the current step number.\n *\n * @method getCurrentStepNumber\n * @return {Number} The current step number\n */\n getCurrentStepNumber() {\n return parseInt(this.currentStepNumber, 10);\n }\n\n /**\n * Store the current step number.\n *\n * @method setCurrentStepNumber\n * @param {Number} stepNumber The current step number\n * @chainable\n */\n setCurrentStepNumber(stepNumber) {\n this.currentStepNumber = stepNumber;\n if (this.storage) {\n try {\n this.storage.setItem(this.storageKey, stepNumber);\n } catch (e) {\n if (e.code === DOMException.QUOTA_EXCEEDED_ERR) {\n this.storage.removeItem(this.storageKey);\n }\n }\n }\n }\n\n /**\n * Get the next step number after the currently displayed step.\n *\n * @method getNextStepNumber\n * @param {Number} stepNumber The current step number\n * @return {Number} The next step number to display\n */\n getNextStepNumber(stepNumber) {\n if (typeof stepNumber === 'undefined') {\n stepNumber = this.getCurrentStepNumber();\n }\n let nextStepNumber = stepNumber + 1;\n\n // Keep checking the remaining steps.\n while (nextStepNumber <= this.steps.length) {\n if (this.isStepPotentiallyVisible(this.getStepConfig(nextStepNumber))) {\n return nextStepNumber;\n }\n nextStepNumber++;\n }\n\n return null;\n }\n\n /**\n * Get the previous step number before the currently displayed step.\n *\n * @method getPreviousStepNumber\n * @param {Number} stepNumber The current step number\n * @return {Number} The previous step number to display\n */\n getPreviousStepNumber(stepNumber) {\n if (typeof stepNumber === 'undefined') {\n stepNumber = this.getCurrentStepNumber();\n }\n let previousStepNumber = stepNumber - 1;\n\n // Keep checking the remaining steps.\n while (previousStepNumber >= 0) {\n if (this.isStepPotentiallyVisible(this.getStepConfig(previousStepNumber))) {\n return previousStepNumber;\n }\n previousStepNumber--;\n }\n\n return null;\n }\n\n /**\n * Is the step the final step number?\n *\n * @method isLastStep\n * @param {Number} stepNumber Step number to test\n * @return {Boolean} Whether the step is the final step\n */\n isLastStep(stepNumber) {\n let nextStepNumber = this.getNextStepNumber(stepNumber);\n\n return nextStepNumber === null;\n }\n\n /**\n * Is this step potentially visible?\n *\n * @method isStepPotentiallyVisible\n * @param {Object} stepConfig The step configuration to normalise\n * @return {Boolean} Whether the step is the potentially visible\n */\n isStepPotentiallyVisible(stepConfig) {\n if (!stepConfig) {\n // Without step config, there can be no step.\n return false;\n }\n\n if (this.isStepActuallyVisible(stepConfig)) {\n // If it is actually visible, it is already potentially visible.\n return true;\n }\n\n if (typeof stepConfig.orphan !== 'undefined' && stepConfig.orphan) {\n // Orphan steps have no target. They are always visible.\n return true;\n }\n\n if (typeof stepConfig.delay !== 'undefined' && stepConfig.delay) {\n // Only return true if the activated has not been used yet.\n return true;\n }\n\n // Not theoretically, or actually visible.\n return false;\n }\n\n /**\n * Get potentially visible steps in a tour.\n *\n * @returns {StepList} A list of ordered steps\n */\n getPotentiallyVisibleSteps() {\n let position = 1;\n let result = [];\n // Checking the total steps.\n for (let stepNumber = 0; stepNumber < this.steps.length; stepNumber++) {\n const stepConfig = this.getStepConfig(stepNumber);\n if (this.isStepPotentiallyVisible(stepConfig)) {\n result[stepNumber] = {stepId: stepConfig.stepid, position: position};\n position++;\n }\n }\n\n return result;\n }\n\n /**\n * Is this step actually visible?\n *\n * @method isStepActuallyVisible\n * @param {Object} stepConfig The step configuration to normalise\n * @return {Boolean} Whether the step is actually visible\n */\n isStepActuallyVisible(stepConfig) {\n if (!stepConfig) {\n // Without step config, there can be no step.\n return false;\n }\n\n let target = this.getStepTarget(stepConfig);\n if (target && target.length && target.is(':visible')) {\n // Without a target, there can be no step.\n return !!target.length;\n }\n\n return false;\n }\n\n /**\n * Go to the next step in the tour.\n *\n * @method next\n * @chainable\n * @return {Object} this.\n */\n next() {\n return this.gotoStep(this.getNextStepNumber());\n }\n\n /**\n * Go to the previous step in the tour.\n *\n * @method previous\n * @chainable\n * @return {Object} this.\n */\n previous() {\n return this.gotoStep(this.getPreviousStepNumber(), -1);\n }\n\n /**\n * Go to the specified step in the tour.\n *\n * @method gotoStep\n * @param {Number} stepNumber The step number to display\n * @param {Number} direction Next or previous step\n * @chainable\n * @return {Object} this.\n * @fires tool_usertours/stepRender\n * @fires tool_usertours/stepRendered\n * @fires tool_usertours/stepHide\n * @fires tool_usertours/stepHidden\n */\n gotoStep(stepNumber, direction) {\n if (stepNumber < 0) {\n return this.endTour();\n }\n\n let stepConfig = this.getStepConfig(stepNumber);\n if (stepConfig === null) {\n return this.endTour();\n }\n\n return this._gotoStep(stepConfig, direction);\n }\n\n _gotoStep(stepConfig, direction) {\n if (!stepConfig) {\n return this.endTour();\n }\n\n if (typeof stepConfig.delay !== 'undefined' && stepConfig.delay && !stepConfig.delayed) {\n stepConfig.delayed = true;\n window.setTimeout(this._gotoStep.bind(this), stepConfig.delay, stepConfig, direction);\n\n return this;\n } else if (!stepConfig.orphan && !this.isStepActuallyVisible(stepConfig)) {\n let fn = direction == -1 ? 'getPreviousStepNumber' : 'getNextStepNumber';\n return this.gotoStep(this[fn](stepConfig.stepNumber), direction);\n }\n\n this.hide();\n\n const stepRenderEvent = this.dispatchEvent(eventTypes.stepRender, {stepConfig}, true);\n if (!stepRenderEvent.defaultPrevented) {\n this.renderStep(stepConfig);\n this.dispatchEvent(eventTypes.stepRendered, {stepConfig});\n }\n\n return this;\n }\n\n /**\n * Fetch the normalised step configuration for the specified step number.\n *\n * @method getStepConfig\n * @param {Number} stepNumber The step number to fetch configuration for\n * @return {Object} The step configuration\n */\n getStepConfig(stepNumber) {\n if (stepNumber === null || stepNumber < 0 || stepNumber >= this.steps.length) {\n return null;\n }\n\n // Normalise the step configuration.\n let stepConfig = this.normalizeStepConfig(this.steps[stepNumber]);\n\n // Add the stepNumber to the stepConfig.\n stepConfig = $.extend(stepConfig, {stepNumber: stepNumber});\n\n return stepConfig;\n }\n\n /**\n * Normalise the supplied step configuration.\n *\n * @method normalizeStepConfig\n * @param {Object} stepConfig The step configuration to normalise\n * @return {Object} The normalised step configuration\n */\n normalizeStepConfig(stepConfig) {\n\n if (typeof stepConfig.reflex !== 'undefined' && typeof stepConfig.moveAfterClick === 'undefined') {\n stepConfig.moveAfterClick = stepConfig.reflex;\n }\n\n if (typeof stepConfig.element !== 'undefined' && typeof stepConfig.target === 'undefined') {\n stepConfig.target = stepConfig.element;\n }\n\n if (typeof stepConfig.content !== 'undefined' && typeof stepConfig.body === 'undefined') {\n stepConfig.body = stepConfig.content;\n }\n\n stepConfig = $.extend({}, this.stepDefaults, stepConfig);\n\n stepConfig = $.extend({}, {\n attachTo: stepConfig.target,\n attachPoint: 'after',\n }, stepConfig);\n\n if (stepConfig.attachTo) {\n stepConfig.attachTo = $(stepConfig.attachTo).first();\n }\n\n return stepConfig;\n }\n\n /**\n * Fetch the actual step target from the selector.\n *\n * This should not be called until after any delay has completed.\n *\n * @method getStepTarget\n * @param {Object} stepConfig The step configuration\n * @return {$}\n */\n getStepTarget(stepConfig) {\n if (stepConfig.target) {\n return $(stepConfig.target);\n }\n\n return null;\n }\n\n /**\n * Fire any event handlers for the specified event.\n *\n * @param {String} eventName The name of the event\n * @param {Object} [detail={}] Any additional details to pass into the eveent\n * @param {Boolean} [cancelable=false] Whether preventDefault() can be called\n * @returns {CustomEvent}\n */\n dispatchEvent(\n eventName,\n detail = {},\n cancelable = false\n ) {\n return dispatchEvent(eventName, {\n // Add the tour to the detail.\n tour: this,\n ...detail,\n }, document, {\n cancelable,\n });\n }\n\n /**\n * @method addEventHandler\n * @param {string} eventName The name of the event to listen for\n * @param {function} handler The event handler to call\n * @return {Object} this.\n */\n addEventHandler(eventName, handler) {\n if (typeof this.eventHandlers[eventName] === 'undefined') {\n this.eventHandlers[eventName] = [];\n }\n\n this.eventHandlers[eventName].push(handler);\n\n return this;\n }\n\n /**\n * Process listeners for the step being shown.\n *\n * @method processStepListeners\n * @param {object} stepConfig The configuration for the step\n * @chainable\n * @return {Object} this.\n */\n processStepListeners(stepConfig) {\n this.listeners.push(\n // Next button.\n {\n node: this.currentStepNode,\n args: ['click', '[data-role=\"next\"]', $.proxy(this.next, this)]\n },\n\n // Close and end tour buttons.\n {\n node: this.currentStepNode,\n args: ['click', '[data-role=\"end\"]', $.proxy(this.endTour, this)]\n },\n\n // Click backdrop and hide tour.\n {\n node: $('[data-flexitour=\"backdrop\"]'),\n args: ['click', $.proxy(this.hide, this)]\n },\n\n // Keypresses.\n {\n node: $('body'),\n args: ['keydown', $.proxy(this.handleKeyDown, this)]\n });\n\n if (stepConfig.moveOnClick) {\n var targetNode = this.getStepTarget(stepConfig);\n this.listeners.push({\n node: targetNode,\n args: ['click', $.proxy(function(e) {\n if ($(e.target).parents('[data-flexitour=\"container\"]').length === 0) {\n // Ignore clicks when they are in the flexitour.\n window.setTimeout($.proxy(this.next, this), 500);\n }\n }, this)]\n });\n }\n\n this.listeners.forEach(function(listener) {\n listener.node.on.apply(listener.node, listener.args);\n });\n\n return this;\n }\n\n /**\n * Reset step listeners.\n *\n * @method resetStepListeners\n * @chainable\n * @return {Object} this.\n */\n resetStepListeners() {\n // Stop listening to all external handlers.\n if (this.listeners) {\n this.listeners.forEach(function(listener) {\n listener.node.off.apply(listener.node, listener.args);\n });\n }\n this.listeners = [];\n\n return this;\n }\n\n /**\n * The standard step renderer.\n *\n * @method renderStep\n * @param {Object} stepConfig The step configuration of the step\n * @chainable\n * @return {Object} this.\n */\n renderStep(stepConfig) {\n // Store the current step configuration for later.\n this.currentStepConfig = stepConfig;\n this.setCurrentStepNumber(stepConfig.stepNumber);\n\n // Fetch the template and convert it to a $ object.\n let template = $(this.getTemplateContent());\n\n // Title.\n template.find('[data-placeholder=\"title\"]')\n .html(stepConfig.title);\n\n // Body.\n template.find('[data-placeholder=\"body\"]')\n .html(stepConfig.body);\n\n // Buttons.\n const nextBtn = template.find('[data-role=\"next\"]');\n const endBtn = template.find('[data-role=\"end\"]');\n\n // Is this the final step?\n if (this.isLastStep(stepConfig.stepNumber)) {\n nextBtn.hide();\n endBtn.removeClass(\"btn-secondary\").addClass(\"btn-primary\");\n } else {\n nextBtn.prop('disabled', false);\n // Use Skip tour label for the End tour button.\n getString('skip_tour', 'tool_usertours').then(value => {\n endBtn.html(value);\n return;\n }).catch();\n }\n\n nextBtn.attr('role', 'button');\n endBtn.attr('role', 'button');\n\n if (this.originalConfiguration.displaystepnumbers) {\n const stepsPotentiallyVisible = this.getPotentiallyVisibleSteps();\n const totalStepsPotentiallyVisible = stepsPotentiallyVisible.length;\n const position = stepsPotentiallyVisible[stepConfig.stepNumber].position;\n if (totalStepsPotentiallyVisible > 1) {\n // Change the label of the Next button to include the sequence.\n getString('nextstep_sequence', 'tool_usertours',\n {position: position, total: totalStepsPotentiallyVisible}).then(value => {\n nextBtn.html(value);\n return;\n }).catch();\n }\n }\n\n // Replace the template with the updated version.\n stepConfig.template = template;\n\n // Add to the page.\n this.addStepToPage(stepConfig);\n\n // Process step listeners after adding to the page.\n // This uses the currentNode.\n this.processStepListeners(stepConfig);\n\n return this;\n }\n\n /**\n * Getter for the template content.\n *\n * @method getTemplateContent\n * @return {$}\n */\n getTemplateContent() {\n return $(this.templateContent).clone();\n }\n\n /**\n * Helper to add a step to the page.\n *\n * @method addStepToPage\n * @param {Object} stepConfig The step configuration of the step\n * @chainable\n * @return {Object} this.\n */\n addStepToPage(stepConfig) {\n // Create the stepNode from the template data.\n let currentStepNode = $('')\n .html(stepConfig.template)\n .hide();\n\n // The scroll animation occurs on the body or html.\n let animationTarget = $('body, html')\n .stop(true, true);\n\n if (this.isStepActuallyVisible(stepConfig)) {\n let targetNode = this.getStepTarget(stepConfig);\n\n if (targetNode.parents('[data-usertour=\"scroller\"]').length) {\n animationTarget = targetNode.parents('[data-usertour=\"scroller\"]');\n }\n\n targetNode.data('flexitour', 'target');\n\n let zIndex = this.calculateZIndex(targetNode);\n if (zIndex) {\n stepConfig.zIndex = zIndex + 1;\n }\n\n if (stepConfig.zIndex) {\n currentStepNode.css('zIndex', stepConfig.zIndex + 1);\n }\n\n // Add the backdrop.\n this.positionBackdrop(stepConfig);\n\n $(document.body).append(currentStepNode);\n this.currentStepNode = currentStepNode;\n\n // Ensure that the step node is positioned.\n // Some situations mean that the value is not properly calculated without this step.\n this.currentStepNode.css({\n top: 0,\n left: 0,\n });\n\n animationTarget\n .animate({\n scrollTop: this.calculateScrollTop(stepConfig),\n }).promise().then(function() {\n this.positionStep(stepConfig);\n this.revealStep(stepConfig);\n return;\n }.bind(this))\n .catch(function() {\n // Silently fail.\n });\n\n } else if (stepConfig.orphan) {\n stepConfig.isOrphan = true;\n\n // This will be appended to the body instead.\n stepConfig.attachTo = $('body').first();\n stepConfig.attachPoint = 'append';\n\n // Add the backdrop.\n this.positionBackdrop(stepConfig);\n\n // This is an orphaned step.\n currentStepNode.addClass('orphan');\n\n // It lives in the body.\n $(document.body).append(currentStepNode);\n this.currentStepNode = currentStepNode;\n\n this.currentStepNode.offset(this.calculateStepPositionInPage());\n this.currentStepNode.css('position', 'fixed');\n\n this.currentStepPopper = new Popper(\n $('body'),\n this.currentStepNode[0], {\n removeOnDestroy: true,\n placement: stepConfig.placement + '-start',\n arrowElement: '[data-role=\"arrow\"]',\n // Empty the modifiers. We've already placed the step and don't want it moved.\n modifiers: {\n hide: {\n enabled: false,\n },\n applyStyle: {\n onLoad: null,\n enabled: false,\n },\n }\n }\n );\n\n this.revealStep(stepConfig);\n }\n\n return this;\n }\n\n /**\n * Make the given step visible.\n *\n * @method revealStep\n * @param {Object} stepConfig The step configuration of the step\n * @chainable\n * @return {Object} this.\n */\n revealStep(stepConfig) {\n // Fade the step in.\n this.currentStepNode.fadeIn('', $.proxy(function() {\n // Announce via ARIA.\n this.announceStep(stepConfig);\n\n // Focus on the current step Node.\n this.currentStepNode.focus();\n window.setTimeout($.proxy(function() {\n // After a brief delay, focus again.\n // There seems to be an issue with Jaws where it only reads the dialogue title initially.\n // This second focus helps it to read the full dialogue.\n if (this.currentStepNode) {\n this.currentStepNode.focus();\n }\n }, this), 100);\n\n }, this));\n\n return this;\n }\n\n /**\n * Helper to announce the step on the page.\n *\n * @method announceStep\n * @param {Object} stepConfig The step configuration of the step\n * @chainable\n * @return {Object} this.\n */\n announceStep(stepConfig) {\n // Setup the step Dialogue as per:\n // * https://www.w3.org/TR/wai-aria-practices/#dialog_nonmodal\n // * https://www.w3.org/TR/wai-aria-practices/#dialog_modal\n\n // Generate an ID for the current step node.\n let stepId = 'tour-step-' + this.tourName + '-' + stepConfig.stepNumber;\n this.currentStepNode.attr('id', stepId);\n\n let bodyRegion = this.currentStepNode.find('[data-placeholder=\"body\"]').first();\n bodyRegion.attr('id', stepId + '-body');\n bodyRegion.attr('role', 'document');\n\n let headerRegion = this.currentStepNode.find('[data-placeholder=\"title\"]').first();\n headerRegion.attr('id', stepId + '-title');\n headerRegion.attr('aria-labelledby', stepId + '-body');\n\n // Generally, a modal dialog has a role of dialog.\n this.currentStepNode.attr('role', 'dialog');\n this.currentStepNode.attr('tabindex', 0);\n this.currentStepNode.attr('aria-labelledby', stepId + '-title');\n this.currentStepNode.attr('aria-describedby', stepId + '-body');\n\n // Configure ARIA attributes on the target.\n let target = this.getStepTarget(stepConfig);\n if (target) {\n if (!target.attr('tabindex')) {\n target.attr('tabindex', 0);\n }\n\n target\n .data('original-describedby', target.attr('aria-describedby'))\n .attr('aria-describedby', stepId + '-body')\n ;\n }\n\n this.accessibilityShow(stepConfig);\n\n return this;\n }\n\n /**\n * Handle key down events.\n *\n * @method handleKeyDown\n * @param {EventFacade} e\n */\n handleKeyDown(e) {\n let tabbableSelector = 'a[href], link[href], [draggable=true], [contenteditable=true], ';\n tabbableSelector += ':input:enabled, [tabindex], button:enabled';\n switch (e.keyCode) {\n case 27:\n this.endTour();\n break;\n\n // 9 == Tab - trap focus for items with a backdrop.\n case 9:\n // Tab must be handled on key up only in this instance.\n (function() {\n if (!this.currentStepConfig.hasBackdrop) {\n // Trapping tab focus is only handled for those steps with a backdrop.\n return;\n }\n\n // Find all tabbable locations.\n let activeElement = $(document.activeElement);\n let stepTarget = this.getStepTarget(this.currentStepConfig);\n let tabbableNodes = $(tabbableSelector);\n let dialogContainer = $('span[data-flexitour=\"container\"]');\n let currentIndex;\n // Filter out element which is not belong to target section or dialogue.\n if (stepTarget) {\n tabbableNodes = tabbableNodes.filter(function(index, element) {\n return stepTarget !== null\n && (stepTarget.has(element).length\n || dialogContainer.has(element).length\n || stepTarget.is(element)\n || dialogContainer.is(element));\n });\n }\n\n // Find index of focusing element.\n tabbableNodes.each(function(index, element) {\n if (activeElement.is(element)) {\n currentIndex = index;\n return false;\n }\n // Keep looping.\n return true;\n });\n\n let nextIndex;\n let nextNode;\n let focusRelevant;\n if (currentIndex != void 0) {\n let direction = 1;\n if (e.shiftKey) {\n direction = -1;\n }\n nextIndex = currentIndex;\n do {\n nextIndex += direction;\n nextNode = $(tabbableNodes[nextIndex]);\n } while (nextNode.length && nextNode.is(':disabled') || nextNode.is(':hidden'));\n if (nextNode.length) {\n // A new f\n focusRelevant = nextNode.closest(stepTarget).length;\n focusRelevant = focusRelevant || nextNode.closest(this.currentStepNode).length;\n } else {\n // Unable to find the target somehow.\n focusRelevant = false;\n }\n }\n\n if (focusRelevant) {\n nextNode.focus();\n } else {\n if (e.shiftKey) {\n // Focus on the last tabbable node in the step.\n this.currentStepNode.find(tabbableSelector).last().focus();\n } else {\n if (this.currentStepConfig.isOrphan) {\n // Focus on the step - there is no target.\n this.currentStepNode.focus();\n } else {\n // Focus on the step target.\n stepTarget.focus();\n }\n }\n }\n e.preventDefault();\n }).call(this);\n break;\n }\n }\n\n /**\n * Start the current tour.\n *\n * @method startTour\n * @param {Number} startAt Which step number to start at. If not specified, starts at the last point.\n * @chainable\n * @return {Object} this.\n * @fires tool_usertours/tourStart\n * @fires tool_usertours/tourStarted\n */\n startTour(startAt) {\n if (this.storage && typeof startAt === 'undefined') {\n let storageStartValue = this.storage.getItem(this.storageKey);\n if (storageStartValue) {\n let storageStartAt = parseInt(storageStartValue, 10);\n if (storageStartAt <= this.steps.length) {\n startAt = storageStartAt;\n }\n }\n }\n\n if (typeof startAt === 'undefined') {\n startAt = this.getCurrentStepNumber();\n }\n\n const tourStartEvent = this.dispatchEvent(eventTypes.tourStart, {startAt}, true);\n if (!tourStartEvent.defaultPrevented) {\n this.gotoStep(startAt);\n this.tourRunning = true;\n this.dispatchEvent(eventTypes.tourStarted, {startAt});\n }\n\n return this;\n }\n\n /**\n * Restart the tour from the beginning, resetting the completionlag.\n *\n * @method restartTour\n * @chainable\n * @return {Object} this.\n */\n restartTour() {\n return this.startTour(0);\n }\n\n /**\n * End the current tour.\n *\n * @method endTour\n * @chainable\n * @return {Object} this.\n * @fires tool_usertours/tourEnd\n * @fires tool_usertours/tourEnded\n */\n endTour() {\n const tourEndEvent = this.dispatchEvent(eventTypes.tourEnd, {}, true);\n if (tourEndEvent.defaultPrevented) {\n return this;\n }\n\n if (this.currentStepConfig) {\n let previousTarget = this.getStepTarget(this.currentStepConfig);\n if (previousTarget) {\n if (!previousTarget.attr('tabindex')) {\n previousTarget.attr('tabindex', '-1');\n }\n previousTarget.focus();\n }\n }\n\n this.hide(true);\n\n this.tourRunning = false;\n this.dispatchEvent(eventTypes.tourEnded);\n\n return this;\n }\n\n /**\n * Hide any currently visible steps.\n *\n * @method hide\n * @param {Bool} transition Animate the visibility change\n * @chainable\n * @return {Object} this.\n * @fires tool_usertours/stepHide\n * @fires tool_usertours/stepHidden\n */\n hide(transition) {\n const stepHideEvent = this.dispatchEvent(eventTypes.stepHide, {}, true);\n if (stepHideEvent.defaultPrevented) {\n return this;\n }\n\n if (this.currentStepNode && this.currentStepNode.length) {\n this.currentStepNode.hide();\n if (this.currentStepPopper) {\n this.currentStepPopper.destroy();\n }\n }\n\n // Restore original target configuration.\n if (this.currentStepConfig) {\n let target = this.getStepTarget(this.currentStepConfig);\n if (target) {\n if (target.data('original-labelledby')) {\n target.attr('aria-labelledby', target.data('original-labelledby'));\n }\n\n if (target.data('original-describedby')) {\n target.attr('aria-describedby', target.data('original-describedby'));\n }\n\n if (target.data('original-tabindex')) {\n target.attr('tabindex', target.data('tabindex'));\n }\n }\n\n // Clear the step configuration.\n this.currentStepConfig = null;\n }\n\n let fadeTime = 0;\n if (transition) {\n fadeTime = 400;\n }\n\n // Remove the backdrop features.\n $('[data-flexitour=\"step-background\"]').remove();\n $('[data-flexitour=\"step-backdrop\"]').removeAttr('data-flexitour');\n $('[data-flexitour=\"backdrop\"]').fadeOut(fadeTime, function() {\n $(this).remove();\n });\n\n // Remove aria-describedby and tabindex attributes.\n if (this.currentStepNode && this.currentStepNode.length) {\n let stepId = this.currentStepNode.attr('id');\n if (stepId) {\n let currentStepElement = '[aria-describedby=\"' + stepId + '-body\"]';\n $(currentStepElement).removeAttr('tabindex');\n $(currentStepElement).removeAttr('aria-describedby');\n }\n }\n\n // Reset the listeners.\n this.resetStepListeners();\n\n this.accessibilityHide();\n\n this.dispatchEvent(eventTypes.stepHidden);\n\n this.currentStepNode = null;\n this.currentStepPopper = null;\n return this;\n }\n\n /**\n * Show the current steps.\n *\n * @method show\n * @chainable\n * @return {Object} this.\n */\n show() {\n // Show the current step.\n let startAt = this.getCurrentStepNumber();\n\n return this.gotoStep(startAt);\n }\n\n /**\n * Return the current step node.\n *\n * @method getStepContainer\n * @return {jQuery}\n */\n getStepContainer() {\n return $(this.currentStepNode);\n }\n\n /**\n * Calculate scrollTop.\n *\n * @method calculateScrollTop\n * @param {Object} stepConfig The step configuration of the step\n * @return {Number}\n */\n calculateScrollTop(stepConfig) {\n let viewportHeight = $(window).height();\n let targetNode = this.getStepTarget(stepConfig);\n\n let scrollParent = $(window);\n if (targetNode.parents('[data-usertour=\"scroller\"]').length) {\n scrollParent = targetNode.parents('[data-usertour=\"scroller\"]');\n }\n let scrollTop = scrollParent.scrollTop();\n\n if (stepConfig.placement === 'top') {\n // If the placement is top, center scroll at the top of the target.\n scrollTop = targetNode.offset().top - (viewportHeight / 2);\n } else if (stepConfig.placement === 'bottom') {\n // If the placement is bottom, center scroll at the bottom of the target.\n scrollTop = targetNode.offset().top + targetNode.height() + scrollTop - (viewportHeight / 2);\n } else if (targetNode.height() <= (viewportHeight * 0.8)) {\n // If the placement is left/right, and the target fits in the viewport, centre screen on the target\n scrollTop = targetNode.offset().top - ((viewportHeight - targetNode.height()) / 2);\n } else {\n // If the placement is left/right, and the target is bigger than the viewport, set scrollTop to target.top + buffer\n // and change step attachmentTarget to top+.\n scrollTop = targetNode.offset().top - (viewportHeight * 0.2);\n }\n\n // Never scroll over the top.\n scrollTop = Math.max(0, scrollTop);\n\n // Never scroll beyond the bottom.\n scrollTop = Math.min($(document).height() - viewportHeight, scrollTop);\n\n return Math.ceil(scrollTop);\n }\n\n /**\n * Calculate dialogue position for page middle.\n *\n * @method calculateScrollTop\n * @return {Number}\n */\n calculateStepPositionInPage() {\n let viewportHeight = $(window).height();\n let stepHeight = this.currentStepNode.height();\n\n let viewportWidth = $(window).width();\n let stepWidth = this.currentStepNode.width();\n\n return {\n top: Math.ceil((viewportHeight - stepHeight) / 2),\n left: Math.ceil((viewportWidth - stepWidth) / 2)\n };\n }\n\n /**\n * Position the step on the page.\n *\n * @method positionStep\n * @param {Object} stepConfig The step configuration of the step\n * @chainable\n * @return {Object} this.\n */\n positionStep(stepConfig) {\n let content = this.currentStepNode;\n if (!content || !content.length) {\n // Unable to find the step node.\n return this;\n }\n\n stepConfig.placement = this.recalculatePlacement(stepConfig);\n let flipBehavior;\n switch (stepConfig.placement) {\n case 'left':\n flipBehavior = ['left', 'right', 'top', 'bottom'];\n break;\n case 'right':\n flipBehavior = ['right', 'left', 'top', 'bottom'];\n break;\n case 'top':\n flipBehavior = ['top', 'bottom', 'right', 'left'];\n break;\n case 'bottom':\n flipBehavior = ['bottom', 'top', 'right', 'left'];\n break;\n default:\n flipBehavior = 'flip';\n break;\n }\n\n let target = this.getStepTarget(stepConfig);\n var config = {\n placement: stepConfig.placement + '-start',\n removeOnDestroy: true,\n modifiers: {\n flip: {\n behaviour: flipBehavior,\n },\n arrow: {\n element: '[data-role=\"arrow\"]',\n },\n },\n onCreate: function(data) {\n recalculateArrowPosition(data);\n },\n onUpdate: function(data) {\n recalculateArrowPosition(data);\n },\n };\n\n let recalculateArrowPosition = function(data) {\n let placement = data.placement.split('-')[0];\n const isVertical = ['left', 'right'].indexOf(placement) !== -1;\n const arrowElement = data.instance.popper.querySelector('[data-role=\"arrow\"]');\n const stepElement = $(data.instance.popper.querySelector('[data-role=\"flexitour-step\"]'));\n if (isVertical) {\n let arrowHeight = parseFloat(window.getComputedStyle(arrowElement).height);\n let arrowOffset = parseFloat(window.getComputedStyle(arrowElement).top);\n let popperHeight = parseFloat(window.getComputedStyle(data.instance.popper).height);\n let popperOffset = parseFloat(window.getComputedStyle(data.instance.popper).top);\n let popperBorderWidth = parseFloat(stepElement.css('borderTopWidth'));\n let popperBorderRadiusWidth = parseFloat(stepElement.css('borderTopLeftRadius')) * 2;\n let arrowPos = arrowOffset + (arrowHeight / 2);\n let maxPos = popperHeight + popperOffset - popperBorderWidth - popperBorderRadiusWidth;\n let minPos = popperOffset + popperBorderWidth + popperBorderRadiusWidth;\n if (arrowPos >= maxPos || arrowPos <= minPos) {\n let newArrowPos = 0;\n if (arrowPos > (popperHeight / 2)) {\n newArrowPos = maxPos - arrowHeight;\n } else {\n newArrowPos = minPos + arrowHeight;\n }\n $(arrowElement).css('top', newArrowPos);\n }\n } else {\n let arrowWidth = parseFloat(window.getComputedStyle(arrowElement).width);\n let arrowOffset = parseFloat(window.getComputedStyle(arrowElement).left);\n let popperWidth = parseFloat(window.getComputedStyle(data.instance.popper).width);\n let popperOffset = parseFloat(window.getComputedStyle(data.instance.popper).left);\n let popperBorderWidth = parseFloat(stepElement.css('borderTopWidth'));\n let popperBorderRadiusWidth = parseFloat(stepElement.css('borderTopLeftRadius')) * 2;\n let arrowPos = arrowOffset + (arrowWidth / 2);\n let maxPos = popperWidth + popperOffset - popperBorderWidth - popperBorderRadiusWidth;\n let minPos = popperOffset + popperBorderWidth + popperBorderRadiusWidth;\n if (arrowPos >= maxPos || arrowPos <= minPos) {\n let newArrowPos = 0;\n if (arrowPos > (popperWidth / 2)) {\n newArrowPos = maxPos - arrowWidth;\n } else {\n newArrowPos = minPos + arrowWidth;\n }\n $(arrowElement).css('left', newArrowPos);\n }\n }\n };\n\n let background = $('[data-flexitour=\"step-background\"]');\n if (background.length) {\n target = background;\n }\n this.currentStepPopper = new Popper(target, content[0], config);\n\n return this;\n }\n\n /**\n * For left/right placement, checks that there is room for the step at current window size.\n *\n * If there is not enough room, changes placement to 'top'.\n *\n * @method recalculatePlacement\n * @param {Object} stepConfig The step configuration of the step\n * @return {String} The placement after recalculate\n */\n recalculatePlacement(stepConfig) {\n const buffer = 10;\n const arrowWidth = 16;\n let target = this.getStepTarget(stepConfig);\n let widthContent = this.currentStepNode.width() + arrowWidth;\n let targetOffsetLeft = target.offset().left - buffer;\n let targetOffsetRight = target.offset().left + target.width() + buffer;\n let placement = stepConfig.placement;\n\n if (['left', 'right'].indexOf(placement) !== -1) {\n if ((targetOffsetLeft < (widthContent + buffer)) &&\n ((targetOffsetRight + widthContent + buffer) > document.documentElement.clientWidth)) {\n placement = 'top';\n }\n }\n return placement;\n }\n\n /**\n * Add the backdrop.\n *\n * @method positionBackdrop\n * @param {Object} stepConfig The step configuration of the step\n * @chainable\n * @return {Object} this.\n */\n positionBackdrop(stepConfig) {\n if (stepConfig.backdrop) {\n this.currentStepConfig.hasBackdrop = true;\n let backdrop = $('
');\n\n if (stepConfig.zIndex) {\n if (stepConfig.attachPoint === 'append') {\n stepConfig.attachTo.append(backdrop);\n } else {\n backdrop.insertAfter(stepConfig.attachTo);\n }\n } else {\n $('body').append(backdrop);\n }\n\n if (this.isStepActuallyVisible(stepConfig)) {\n // The step has a visible target.\n // Punch a hole through the backdrop.\n let background = $('[data-flexitour=\"step-background\"]');\n if (!background.length) {\n background = $('
');\n }\n\n let targetNode = this.getStepTarget(stepConfig);\n\n let buffer = 10;\n\n let colorNode = targetNode;\n if (buffer) {\n colorNode = $('body');\n }\n\n let drawertop = 0;\n if (targetNode.parents('[data-usertour=\"scroller\"]').length) {\n const scrollerElement = targetNode.parents('[data-usertour=\"scroller\"]');\n const navigationBuffer = scrollerElement.offset().top;\n if (scrollerElement.scrollTop() >= navigationBuffer) {\n drawertop = scrollerElement.scrollTop() - navigationBuffer;\n background.css({\n position: 'fixed'\n });\n }\n }\n\n background.css({\n width: targetNode.outerWidth() + buffer + buffer,\n height: targetNode.outerHeight() + buffer + buffer,\n left: targetNode.offset().left - buffer,\n top: targetNode.offset().top + drawertop - buffer,\n backgroundColor: this.calculateInherittedBackgroundColor(colorNode),\n });\n\n if (targetNode.offset().left < buffer) {\n background.css({\n width: targetNode.outerWidth() + targetNode.offset().left + buffer,\n left: targetNode.offset().left,\n });\n }\n\n if ((targetNode.offset().top + drawertop) < buffer) {\n background.css({\n height: targetNode.outerHeight() + targetNode.offset().top + buffer,\n top: targetNode.offset().top,\n });\n }\n\n let targetRadius = targetNode.css('borderRadius');\n if (targetRadius && targetRadius !== $('body').css('borderRadius')) {\n background.css('borderRadius', targetRadius);\n }\n\n let targetPosition = this.calculatePosition(targetNode);\n if (targetPosition === 'fixed') {\n background.css('top', 0);\n } else if (targetPosition === 'absolute') {\n background.css('position', 'fixed');\n }\n\n let fader = background.clone();\n fader.css({\n backgroundColor: backdrop.css('backgroundColor'),\n opacity: backdrop.css('opacity'),\n });\n fader.attr('data-flexitour', 'step-background-fader');\n\n if (targetNode.parents('[data-region=\"fixed-drawer\"]').length) {\n let targetClone = targetNode.clone();\n background.append(targetClone);\n }\n\n if (stepConfig.zIndex) {\n if (stepConfig.attachPoint === 'append') {\n stepConfig.attachTo.append(background);\n } else {\n fader.insertAfter(stepConfig.attachTo);\n background.insertAfter(stepConfig.attachTo);\n }\n } else {\n $('body').append(fader);\n $('body').append(background);\n }\n\n // Add the backdrop data to the actual target.\n // This is the part which actually does the work.\n targetNode.attr('data-flexitour', 'step-backdrop');\n\n if (stepConfig.zIndex) {\n backdrop.css('zIndex', stepConfig.zIndex);\n background.css('zIndex', stepConfig.zIndex + 1);\n targetNode.css('zIndex', stepConfig.zIndex + 2);\n }\n\n fader.fadeOut('2000', function() {\n $(this).remove();\n });\n }\n }\n return this;\n }\n\n /**\n * Calculate the inheritted z-index.\n *\n * @method calculateZIndex\n * @param {jQuery} elem The element to calculate z-index for\n * @return {Number} Calculated z-index\n */\n calculateZIndex(elem) {\n elem = $(elem);\n while (elem.length && elem[0] !== document) {\n // Ignore z-index if position is set to a value where z-index is ignored by the browser\n // This makes behavior of this function consistent across browsers\n // WebKit always returns auto if the element is positioned.\n let position = elem.css(\"position\");\n if (position === \"absolute\" || position === \"relative\" || position === \"fixed\") {\n // IE returns 0 when zIndex is not specified\n // other browsers return a string\n // we ignore the case of nested elements with an explicit value of 0\n //
\n let value = parseInt(elem.css(\"zIndex\"), 10);\n if (!isNaN(value) && value !== 0) {\n return value;\n }\n }\n elem = elem.parent();\n }\n\n return 0;\n }\n\n /**\n * Calculate the inheritted background colour.\n *\n * @method calculateInherittedBackgroundColor\n * @param {jQuery} elem The element to calculate colour for\n * @return {String} Calculated background colour\n */\n calculateInherittedBackgroundColor(elem) {\n // Use a fake node to compare each element against.\n let fakeNode = $('
').hide();\n $('body').append(fakeNode);\n let fakeElemColor = fakeNode.css('backgroundColor');\n fakeNode.remove();\n\n elem = $(elem);\n while (elem.length && elem[0] !== document) {\n let color = elem.css('backgroundColor');\n if (color !== fakeElemColor) {\n return color;\n }\n elem = elem.parent();\n }\n\n return null;\n }\n\n /**\n * Calculate the inheritted position.\n *\n * @method calculatePosition\n * @param {jQuery} elem The element to calculate position for\n * @return {String} Calculated position\n */\n calculatePosition(elem) {\n elem = $(elem);\n while (elem.length && elem[0] !== document) {\n let position = elem.css('position');\n if (position !== 'static') {\n return position;\n }\n elem = elem.parent();\n }\n\n return null;\n }\n\n /**\n * Perform accessibility changes for step shown.\n *\n * This will add aria-hidden=\"true\" to all siblings and parent siblings.\n *\n * @method accessibilityShow\n */\n accessibilityShow() {\n let stateHolder = 'data-has-hidden';\n let attrName = 'aria-hidden';\n let hideFunction = function(child) {\n let flexitourRole = child.data('flexitour');\n if (flexitourRole) {\n switch (flexitourRole) {\n case 'container':\n case 'target':\n return;\n }\n }\n\n let hidden = child.attr(attrName);\n if (!hidden) {\n child.attr(stateHolder, true);\n Aria.hide(child);\n }\n };\n\n this.currentStepNode.siblings().each(function(index, node) {\n hideFunction($(node));\n });\n this.currentStepNode.parentsUntil('body').siblings().each(function(index, node) {\n hideFunction($(node));\n });\n }\n\n /**\n * Perform accessibility changes for step hidden.\n *\n * This will remove any newly added aria-hidden=\"true\".\n *\n * @method accessibilityHide\n */\n accessibilityHide() {\n let stateHolder = 'data-has-hidden';\n let showFunction = function(child) {\n let hidden = child.attr(stateHolder);\n if (typeof hidden !== 'undefined') {\n child.removeAttr(stateHolder);\n Aria.unhide(child);\n }\n };\n\n $('[' + stateHolder + ']').each(function(index, node) {\n showFunction($(node));\n });\n }\n};\n\nexport default Tour;\n"],"file":"tour.min.js"} \ No newline at end of file diff --git a/admin/tool/usertours/amd/src/tour.js b/admin/tool/usertours/amd/src/tour.js index 99b48e08c35..ca3b7a26023 100644 --- a/admin/tool/usertours/amd/src/tour.js +++ b/admin/tool/usertours/amd/src/tour.js @@ -1435,10 +1435,14 @@ const Tour = class { let drawertop = 0; if (targetNode.parents('[data-usertour="scroller"]').length) { - drawertop = targetNode.parents('[data-usertour="scroller"]').scrollTop(); - background.css({ - position: 'fixed' - }); + const scrollerElement = targetNode.parents('[data-usertour="scroller"]'); + const navigationBuffer = scrollerElement.offset().top; + if (scrollerElement.scrollTop() >= navigationBuffer) { + drawertop = scrollerElement.scrollTop() - navigationBuffer; + background.css({ + position: 'fixed' + }); + } } background.css({ From 87f233e698197cf067a90d0f867e054c0440d7b6 Mon Sep 17 00:00:00 2001 From: Huong Nguyen Date: Fri, 17 Dec 2021 11:01:31 +0700 Subject: [PATCH 2/4] MDL-72783 usertours: Improve the tours maching Improve the regex so the Tour can detect the URL match is pointing to Dashboard (/my/) or My Course (/my/courses.php) correctly --- admin/tool/usertours/classes/cache.php | 15 ++++++++++++--- admin/tool/usertours/tests/cache_test.php | 2 +- 2 files changed, 13 insertions(+), 4 deletions(-) diff --git a/admin/tool/usertours/classes/cache.php b/admin/tool/usertours/classes/cache.php index 71857e4eec8..6035466789a 100644 --- a/admin/tool/usertours/classes/cache.php +++ b/admin/tool/usertours/classes/cache.php @@ -84,13 +84,22 @@ EOF; // Attempt to determine whether this is the front page. // This is a special case because the frontpage uses a shortened page path making it difficult to detect exactly. $isfrontpage = $targetmatch->compare(new \moodle_url('/'), URL_MATCH_BASE); + $isdashboard = $targetmatch->compare(new \moodle_url('/my/'), URL_MATCH_BASE); $target = $targetmatch->out_as_local_url(); - return array_filter($tours, function($tour) use ($isfrontpage, $target) { - if ($isfrontpage && $tour->pathmatch === 'FRONTPAGE') { + return array_filter($tours, function($tour) use ($isfrontpage, $isdashboard, $target) { + if (($isfrontpage || $isdashboard) && $tour->pathmatch === 'FRONTPAGE') { return true; } $pattern = preg_quote($tour->pathmatch, '@'); - $pattern = str_replace('%', '.*', $pattern); + if (strpos($pattern, '%') !== false) { + // The URL match format is something like: /my/%. + // We need to find all the URLs which match the first part of the pattern. + $pattern = str_replace('%', '.*', $pattern); + } else { + // The URL match format is something like: /my/courses.php. + // We need to find all the URLs which match with whole pattern. + $pattern .= '$'; + } return !!preg_match("@{$pattern}@", $target); }); } diff --git a/admin/tool/usertours/tests/cache_test.php b/admin/tool/usertours/tests/cache_test.php index 557e0755e29..0870d966fd9 100644 --- a/admin/tool/usertours/tests/cache_test.php +++ b/admin/tool/usertours/tests/cache_test.php @@ -164,7 +164,7 @@ class cache_testcase extends advanced_testcase { 'Matches expected glob' => [ $tourconfigs, '/my/index.php', - ['my_glob_1', 'my_glob_2'], + ['my_glob_1', 'my_glob_2', 'frontpage_match'], ], 'Matches expected glob and exact' => [ $tourconfigs, From c59d3d749631cf58db58c4a99090f7864c9d4beb Mon Sep 17 00:00:00 2001 From: Huong Nguyen Date: Mon, 24 Jan 2022 09:54:37 +0700 Subject: [PATCH 3/4] MDL-72783 usertours: Make tour name and description translatable We can use the Moodle language format for tour's name and description now. Also, several existing bugs were fixed in this commit when we use the Moodle language format for step's title and content. Now, it will display the translated text in the breadcrumb, editing page instead of displaying the [identifier][component] --- admin/tool/usertours/classes/helper.php | 79 ++++++++++++----- .../classes/local/forms/editstep.php | 3 +- .../classes/local/forms/edittour.php | 2 + .../classes/local/table/step_list.php | 2 +- admin/tool/usertours/classes/manager.php | 18 ++-- admin/tool/usertours/classes/output/step.php | 5 +- admin/tool/usertours/classes/step.php | 20 +---- .../tool/usertours/lang/en/tool_usertours.php | 6 ++ admin/tool/usertours/lib.php | 9 +- .../tests/behat/tour_content_type.feature | 20 +++++ admin/tool/usertours/tests/helper_test.php | 84 +++++++++++++++++++ admin/tool/usertours/tests/step_test.php | 45 ---------- 12 files changed, 197 insertions(+), 96 deletions(-) create mode 100644 admin/tool/usertours/tests/helper_test.php diff --git a/admin/tool/usertours/classes/helper.php b/admin/tool/usertours/classes/helper.php index 8eb71bcea1d..dcb12f6353a 100644 --- a/admin/tool/usertours/classes/helper.php +++ b/admin/tool/usertours/classes/helper.php @@ -24,6 +24,7 @@ namespace tool_usertours; +use core\output\inplace_editable; use tool_usertours\local\clientside_filter\clientside_filter; defined('MOODLE_INTERNAL') || die(); @@ -51,6 +52,11 @@ class helper { */ private static $bootstrapped = false; + /** + * @var string Regex to check any matching lang string. + */ + protected const LANG_STRING_REGEX = '|^([a-zA-Z][a-zA-Z0-9\.:/_-]*),([a-zA-Z][a-zA-Z0-9\.:/_-]*)$|'; + /** * Get the link to edit the step. * @@ -302,18 +308,19 @@ class helper { /** * Render the inplace editable used to edit the tour name. * - * @param tour $tour The tour to edit. - * @return string + * @param tour $tour The tour to edit. + * @return inplace_editable */ - public static function render_tourname_inplace_editable(tour $tour) { - return new \core\output\inplace_editable( + public static function render_tourname_inplace_editable(tour $tour): inplace_editable { + $name = format_text(static::get_string_from_input($tour->get_name()), FORMAT_HTML); + return new inplace_editable( 'tool_usertours', 'tourname', $tour->get_id(), true, \html_writer::link( $tour->get_view_link(), - $tour->get_name() + $name ), $tour->get_name() ); @@ -322,16 +329,17 @@ class helper { /** * Render the inplace editable used to edit the tour description. * - * @param tour $tour The tour to edit. - * @return string + * @param tour $tour The tour to edit. + * @return inplace_editable */ - public static function render_tourdescription_inplace_editable(tour $tour) { - return new \core\output\inplace_editable( + public static function render_tourdescription_inplace_editable(tour $tour): inplace_editable { + $description = format_text(static::get_string_from_input($tour->get_description()), FORMAT_HTML); + return new inplace_editable( 'tool_usertours', 'tourdescription', $tour->get_id(), true, - $tour->get_description(), + $description, $tour->get_description() ); } @@ -339,10 +347,10 @@ class helper { /** * Render the inplace editable used to edit the tour enable state. * - * @param tour $tour The tour to edit. - * @return string + * @param tour $tour The tour to edit. + * @return inplace_editable */ - public static function render_tourenabled_inplace_editable(tour $tour) { + public static function render_tourenabled_inplace_editable(tour $tour): inplace_editable { global $OUTPUT; if ($tour->is_enabled()) { @@ -355,7 +363,7 @@ class helper { $value = 0; } - $editable = new \core\output\inplace_editable( + $editable = new inplace_editable( 'tool_usertours', 'tourenabled', $tour->get_id(), @@ -373,13 +381,13 @@ class helper { /** * Render the inplace editable used to edit the step name. * - * @param step $step The step to edit. - * @return string + * @param step $step The step to edit. + * @return inplace_editable */ - public static function render_stepname_inplace_editable(step $step) { - $title = format_text(step::get_string_from_input($step->get_title()), FORMAT_HTML); + public static function render_stepname_inplace_editable(step $step): inplace_editable { + $title = format_text(static::get_string_from_input($step->get_title()), FORMAT_HTML); - return new \core\output\inplace_editable( + return new inplace_editable( 'tool_usertours', 'stepname', $step->get_id(), @@ -585,4 +593,37 @@ class helper { return $filters; } + + /** + * Attempt to fetch any matching langstring if the content is in the + * format identifier,component. + * + * @param string $content Step's content or Tour's name or Tour's description + * @return string Processed content, any langstring will be converted to translated text + */ + public static function get_string_from_input(string $content): string { + $content = trim($content); + + if (preg_match(static::LANG_STRING_REGEX, $content, $matches)) { + if ($matches[2] === 'moodle') { + $matches[2] = 'core'; + } + + if (get_string_manager()->string_exists($matches[1], $matches[2])) { + $content = get_string($matches[1], $matches[2]); + } + } + + return $content; + } + + /** + * Check if the given string contains any matching langstring. + * + * @param string $string + * @return bool + */ + public static function is_language_string_from_input(string $string): bool { + return preg_match(static::LANG_STRING_REGEX, $string) == true; + } } diff --git a/admin/tool/usertours/classes/local/forms/editstep.php b/admin/tool/usertours/classes/local/forms/editstep.php index b6e416a5ae6..51173711a3f 100644 --- a/admin/tool/usertours/classes/local/forms/editstep.php +++ b/admin/tool/usertours/classes/local/forms/editstep.php @@ -25,6 +25,7 @@ namespace tool_usertours\local\forms; use stdClass; +use tool_usertours\helper; use tool_usertours\step; defined('MOODLE_INTERNAL') || die('Direct access to this script is forbidden.'); @@ -188,7 +189,7 @@ class editstep extends \moodleform { public function set_data($data): void { $data = (object) $data; if (!isset($data->contenttype)) { - if (!empty($data->content['text']) && step::is_language_string_from_input($data->content['text'])) { + if (!empty($data->content['text']) && helper::is_language_string_from_input($data->content['text'])) { $data->contenttype = static::CONTENTTYPE_LANGSTRING; $data->contentlangstring = $data->content['text']; diff --git a/admin/tool/usertours/classes/local/forms/edittour.php b/admin/tool/usertours/classes/local/forms/edittour.php index 69830bb7dda..80409b1aa78 100644 --- a/admin/tool/usertours/classes/local/forms/edittour.php +++ b/admin/tool/usertours/classes/local/forms/edittour.php @@ -67,10 +67,12 @@ class edittour extends \moodleform { $mform->addElement('text', 'name', get_string('name', 'tool_usertours')); $mform->addRule('name', get_string('required'), 'required', null, 'client'); $mform->setType('name', PARAM_TEXT); + $mform->addHelpButton('name', 'name', 'tool_usertours'); // Admin-only descriptions. $mform->addElement('textarea', 'description', get_string('description', 'tool_usertours')); $mform->setType('description', PARAM_RAW); + $mform->addHelpButton('description', 'description', 'tool_usertours'); // Application. $mform->addElement('text', 'pathmatch', get_string('pathmatch', 'tool_usertours')); diff --git a/admin/tool/usertours/classes/local/table/step_list.php b/admin/tool/usertours/classes/local/table/step_list.php index 8da8be90f8e..b4a80e083b7 100644 --- a/admin/tool/usertours/classes/local/table/step_list.php +++ b/admin/tool/usertours/classes/local/table/step_list.php @@ -101,7 +101,7 @@ class step_list extends \flexible_table { $content = file_rewrite_pluginfile_urls($content, 'pluginfile.php', $systemcontext->id, 'tool_usertours', 'stepcontent', $step->get_id()); - return format_text(step::get_string_from_input($content), $step->get_contentformat()); + return format_text(helper::get_string_from_input($content), $step->get_contentformat()); } /** diff --git a/admin/tool/usertours/classes/manager.php b/admin/tool/usertours/classes/manager.php index 5016a36e035..33dfffea827 100644 --- a/admin/tool/usertours/classes/manager.php +++ b/admin/tool/usertours/classes/manager.php @@ -353,7 +353,7 @@ class manager { global $PAGE; if ($id) { $tour = tour::instance($id); - $PAGE->navbar->add($tour->get_name(), $tour->get_edit_link()); + $PAGE->navbar->add(helper::get_string_from_input($tour->get_name()), $tour->get_edit_link()); } else { $tour = new tour(); @@ -393,7 +393,8 @@ class manager { notification::add(get_string('modifyshippedtourwarning', 'tool_usertours'), notification::WARNING); } - $this->header($tour->get_name()); + $tourname = !empty($tour->get_name()) ? helper::get_string_from_input($tour->get_name()) : ''; + $this->header($tourname); $data = $tour->prepare_data_for_form(); // Prepare filter values for the form. @@ -475,12 +476,13 @@ class manager { protected function view_tour($tourid) { global $PAGE; $tour = helper::get_tour($tourid); + $tourname = helper::get_string_from_input($tour->get_name()); - $PAGE->navbar->add($tour->get_name(), $tour->get_view_link()); + $PAGE->navbar->add($tourname, $tour->get_view_link()); - $this->header($tour->get_name()); + $this->header($tourname); echo \html_writer::span(get_string('viewtour_info', 'tool_usertours', [ - 'tourname' => $tour->get_name(), + 'tourname' => $tourname, 'path' => $tour->get_pathmatch(), ])); echo \html_writer::div(get_string('viewtour_edit', 'tool_usertours', [ @@ -728,9 +730,9 @@ class manager { notification::add(get_string('modifyshippedtourwarning', 'tool_usertours'), notification::WARNING); } - $PAGE->navbar->add($tour->get_name(), $tour->get_view_link()); + $PAGE->navbar->add(helper::get_string_from_input($tour->get_name()), $tour->get_view_link()); if (isset($id)) { - $PAGE->navbar->add($step->get_title(), $step->get_edit_link()); + $PAGE->navbar->add(helper::get_string_from_input($step->get_title()), $step->get_edit_link()); } else { $PAGE->navbar->add(get_string('newstep', 'tool_usertours'), $step->get_edit_link()); } @@ -746,7 +748,7 @@ class manager { if (empty($id)) { $this->header(get_string('newstep', 'tool_usertours')); } else { - $this->header(get_string('editstep', 'tool_usertours', $step->get_title())); + $this->header(get_string('editstep', 'tool_usertours', helper::get_string_from_input($step->get_title()))); } $form->set_data($step->prepare_data_for_form()); diff --git a/admin/tool/usertours/classes/output/step.php b/admin/tool/usertours/classes/output/step.php index 8aecf7c06dc..cffc90c6251 100644 --- a/admin/tool/usertours/classes/output/step.php +++ b/admin/tool/usertours/classes/output/step.php @@ -28,6 +28,7 @@ defined('MOODLE_INTERNAL') || die(); require_once($CFG->libdir . "/filelib.php"); +use tool_usertours\helper; use tool_usertours\step as stepsource; /** @@ -70,13 +71,13 @@ class step implements \renderable { $result = (object) [ 'stepid' => $step->get_id(), 'title' => external_format_text( - stepsource::get_string_from_input($step->get_title()), + helper::get_string_from_input($step->get_title()), FORMAT_HTML, $PAGE->context->id, 'tool_usertours' )[0], 'content' => external_format_text( - stepsource::get_string_from_input($content), + helper::get_string_from_input($content), $step->get_contentformat(), $PAGE->context->id, 'tool_usertours' diff --git a/admin/tool/usertours/classes/step.php b/admin/tool/usertours/classes/step.php index 80559b47bc9..41e968eeda4 100644 --- a/admin/tool/usertours/classes/step.php +++ b/admin/tool/usertours/classes/step.php @@ -92,11 +92,6 @@ class step { */ protected $dirty = false; - /** - * @var string Regex to check any matching lang string. - */ - protected const LANG_STRING_REGEX = '|^([a-zA-Z][a-zA-Z0-9\.:/_-]*),([a-zA-Z][a-zA-Z0-9\.:/_-]*)$|'; - /** * @var bool $isimporting Whether the step is being imported or not. */ @@ -801,13 +796,16 @@ class step { * Attempt to fetch any matching langstring if the string is in the * format identifier,component. * + * @deprecated since Moodle 4.0 MDL-72783. Please use helper::get_string_from_input() instead. * @param string $string * @return string */ public static function get_string_from_input($string) { + debugging('Use of ' . __FUNCTION__ . + '() have been deprecated, please update your code to use helper::get_string_from_input()', DEBUG_DEVELOPER); $string = trim($string); - if (preg_match(static::LANG_STRING_REGEX, $string, $matches)) { + if (preg_match('|^([a-zA-Z][a-zA-Z0-9\.:/_-]*),([a-zA-Z][a-zA-Z0-9\.:/_-]*)$|', $string, $matches)) { if ($matches[2] === 'moodle') { $matches[2] = 'core'; } @@ -819,14 +817,4 @@ class step { return $string; } - - /** - * Check if the given string contains any matching langstring. - * - * @param string $string Tour step content - * @return bool - */ - public static function is_language_string_from_input(string $string): bool { - return preg_match(static::LANG_STRING_REGEX, $string) == true; - } } diff --git a/admin/tool/usertours/lang/en/tool_usertours.php b/admin/tool/usertours/lang/en/tool_usertours.php index e0611138605..710ca43ef46 100644 --- a/admin/tool/usertours/lang/en/tool_usertours.php +++ b/admin/tool/usertours/lang/en/tool_usertours.php @@ -31,6 +31,9 @@ $string['block_named'] = 'Block named \'{$a}\''; $string['cachedef_stepdata'] = 'List of user tour steps'; $string['cachedef_tourdata'] = 'List of enabled user tours information which is fetched on every page'; $string['description'] = 'Description'; +$string['description_help'] = 'The description of a tour may be added as plain text, enclosed in multilang tags (for use with the multi-language content filter) if required. + +Alternatively, a language string ID may be entered in the format identifier,component (with no brackets or space after the comma).'; $string['displaystepnumbers'] = 'Display step numbers'; $string['displaystepnumbers_help'] = 'Whether to display a step number count e.g. 1/4, 2/4 etc. to indicate the length of the user tour.'; $string['confirmstepremovalquestion'] = 'Are you sure that you wish to remove this step?'; @@ -93,6 +96,9 @@ $string['movestepup'] = 'Move step up'; $string['movetourdown'] = 'Move tour down'; $string['movetourup'] = 'Move tour up'; $string['name'] = 'Name'; +$string['name_help'] = 'The name of a tour may be added as plain text, enclosed in multilang tags (for use with the multi-language content filter) if required. + +Alternatively, a language string ID may be entered in the format identifier,component (with no brackets or space after the comma).'; $string['newstep'] = 'Create step'; $string['newstep'] = 'New step'; $string['newtour'] = 'Create a new tour'; diff --git a/admin/tool/usertours/lib.php b/admin/tool/usertours/lib.php index 9d017968564..9591ea80059 100644 --- a/admin/tool/usertours/lib.php +++ b/admin/tool/usertours/lib.php @@ -24,15 +24,16 @@ defined('MOODLE_INTERNAL') || die(); +use core\output\inplace_editable; use tool_usertours\helper; /** * Manage inplace editable saves. * - * @param string $itemtype The type of item. - * @param int $itemid The ID of the item. - * @param mixed $newvalue The new value - * @return string + * @param string $itemtype The type of item. + * @param int $itemid The ID of the item. + * @param mixed $newvalue The new value + * @return inplace_editable */ function tool_usertours_inplace_editable($itemtype, $itemid, $newvalue) { $context = \context_system::instance(); diff --git a/admin/tool/usertours/tests/behat/tour_content_type.feature b/admin/tool/usertours/tests/behat/tour_content_type.feature index 2e59815c179..46a3c381a79 100644 --- a/admin/tool/usertours/tests/behat/tour_content_type.feature +++ b/admin/tool/usertours/tests/behat/tour_content_type.feature @@ -11,6 +11,11 @@ Feature: Apply content type to a tour | Description | My first tour | | Apply to URL match | /my/% | | Tour is enabled | 1 | + And I add a new user tour with: + | Name | tour_activityinfo_activity_student_title,tool_usertours | + | Description | tour_activityinfo_activity_student_content,tool_usertours | + | Apply to URL match | /my/% | + | Tour is enabled | 0 | @javascript Scenario: User can choose the the content type of the tour step @@ -42,6 +47,7 @@ Feature: Apply content type to a tour And I should see "New: Activity information" And I should see "New course settings 'Show completion conditions' and 'Show activity dates' enable you to choose whether activity completion conditions (if set) and/or dates are displayed for students on the course page." And I click on "Edit" "link" in the "New: Activity information" "table_row" + And I should see "Editing \"New: Activity information\"" And the field "Title" matches value "tour_activityinfo_course_teacher_title,tool_usertours" And the field "Moodle language identifier" matches value "tour_activityinfo_course_teacher_content,tool_usertours" @@ -57,6 +63,20 @@ Feature: Apply content type to a tour And I should see "New: Activity information" And I should see "Test content" And I click on "Edit" "link" in the "New: Activity information" "table_row" + And I should see "Editing \"New: Activity information\"" And I should not see "Moodle language identifier" And the field "Title" matches value "tour_activityinfo_course_teacher_title,tool_usertours" And the field "id_content" matches value "Test content" + + @javascript + Scenario: Tour name and description can be translatable + Given I open the User tour settings page + And I should see "New: Activity information" + And I should see "Activity dates plus what to do to complete the activity are shown on the activity page." + When I click on "View" "link" in the "New: Activity information" "table_row" + Then I should see "New: Activity information" + And I should see "This is the 'New: Activity information' tour. It applies to the path '/my/%'." + And I click on "edit the tour defaults" "link" + And I should see "New: Activity information" + And the field "Name" matches value "tour_activityinfo_activity_student_title,tool_usertours" + And the field "Description" matches value "tour_activityinfo_activity_student_content,tool_usertours" diff --git a/admin/tool/usertours/tests/helper_test.php b/admin/tool/usertours/tests/helper_test.php new file mode 100644 index 00000000000..f6c574b3077 --- /dev/null +++ b/admin/tool/usertours/tests/helper_test.php @@ -0,0 +1,84 @@ +. + +/** + * Tests for helper. + * + * @package tool_usertours + * @copyright 2022 Huong Nguyen + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ + +namespace tool_usertours; + +use advanced_testcase; + +defined('MOODLE_INTERNAL') || die(); + +/** + * Tests for helper. + * + * @package tool_usertours + * @copyright 2022 Huong Nguyen + * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later + */ +class helper_test extends advanced_testcase { + + /** + * Data Provider for get_string_from_input. + * + * @return array + */ + public function get_string_from_input_provider(): array { + return [ + 'Text' => [ + 'example', + 'example', + ], + 'Text which looks like a langstring' => [ + 'example,fakecomponent', + 'example,fakecomponent', + ], + 'Text which is a langstring' => [ + 'administration,core', + 'Administration', + ], + 'Text which is a langstring but uses "moodle" instead of "core"' => [ + 'administration,moodle', + 'Administration', + ], + 'Text which is a langstring, but with extra whitespace' => [ + ' administration,moodle ', + 'Administration', + ], + 'Looks like a langstring, but has incorrect space around comma' => [ + 'administration , moodle', + 'administration , moodle', + ], + ]; + } + + /** + * Ensure that the get_string_from_input function returns langstring strings correctly. + * + * @dataProvider get_string_from_input_provider + * @param string $string The string to test + * @param string $expected The expected result + */ + public function test_get_string_from_input($string, $expected) { + $this->assertEquals($expected, helper::get_string_from_input($string)); + } +} diff --git a/admin/tool/usertours/tests/step_test.php b/admin/tool/usertours/tests/step_test.php index 70538b289a0..6937b776d69 100644 --- a/admin/tool/usertours/tests/step_test.php +++ b/admin/tool/usertours/tests/step_test.php @@ -823,49 +823,4 @@ class step_testcase extends advanced_testcase { $this->assertEquals($value, $step->$getter()); } - - /** - * Data Provider for get_string_from_input. - * - * @return array - */ - public function get_string_from_input_provider() { - return [ - 'Text' => [ - 'example', - 'example', - ], - 'Text which looks like a langstring' => [ - 'example,fakecomponent', - 'example,fakecomponent', - ], - 'Text which is a langstring' => [ - 'administration,core', - 'Administration', - ], - 'Text which is a langstring but uses "moodle" instead of "core"' => [ - 'administration,moodle', - 'Administration', - ], - 'Text which is a langstring, but with extra whitespace' => [ - ' administration,moodle ', - 'Administration', - ], - 'Looks like a langstring, but has incorrect space around comma' => [ - 'administration , moodle', - 'administration , moodle', - ], - ]; - } - - /** - * Ensure that the get_string_from_input function returns langstring strings correctly. - * - * @dataProvider get_string_from_input_provider - * @param string $string The string to test - * @param string $expected The expected result - */ - public function test_get_string_from_input($string, $expected) { - $this->assertEquals($expected, \tool_usertours\step::get_string_from_input($string)); - } } From 4a7caad27266299372bcd99d322dd09a7e9ef3a6 Mon Sep 17 00:00:00 2001 From: Huong Nguyen Date: Mon, 24 Jan 2022 15:06:20 +0700 Subject: [PATCH 4/4] MDL-72783 usertours: Create tours for the new navigation of Moodle 4.0 --- .../classes/local/table/step_list.php | 5 ++- admin/tool/usertours/classes/manager.php | 4 ++ admin/tool/usertours/classes/output/step.php | 5 ++- admin/tool/usertours/classes/step.php | 25 +++++++++++ admin/tool/usertours/db/upgrade.php | 5 ++- .../tool/usertours/lang/en/tool_usertours.php | 22 ++++++++++ .../pix/tour/tour_course_admin_1.png | Bin 0 -> 24515 bytes .../pix/tour/tour_course_admin_2.png | Bin 0 -> 24977 bytes .../pix/tour/tour_course_admin_3.png | Bin 0 -> 26331 bytes .../pix/tour/tour_course_student.png | Bin 0 -> 10979 bytes .../usertours/pix/tour/tour_dashboard.png | Bin 0 -> 27155 bytes .../usertours/pix/tour/tour_mycourses.png | Bin 0 -> 25923 bytes admin/tool/usertours/tests/step_test.php | 22 ++++++++++ .../40_tour_navigation_course_student.json | 22 ++++++++++ .../40_tour_navigation_course_teacher.json | 40 ++++++++++++++++++ .../tours/40_tour_navigation_dashboard.json | 22 ++++++++++ .../tours/40_tour_navigation_mycourse.json | 22 ++++++++++ admin/tool/usertours/version.php | 2 +- 18 files changed, 191 insertions(+), 5 deletions(-) create mode 100644 admin/tool/usertours/pix/tour/tour_course_admin_1.png create mode 100644 admin/tool/usertours/pix/tour/tour_course_admin_2.png create mode 100644 admin/tool/usertours/pix/tour/tour_course_admin_3.png create mode 100644 admin/tool/usertours/pix/tour/tour_course_student.png create mode 100644 admin/tool/usertours/pix/tour/tour_dashboard.png create mode 100644 admin/tool/usertours/pix/tour/tour_mycourses.png create mode 100644 admin/tool/usertours/tours/40_tour_navigation_course_student.json create mode 100644 admin/tool/usertours/tours/40_tour_navigation_course_teacher.json create mode 100644 admin/tool/usertours/tours/40_tour_navigation_dashboard.json create mode 100644 admin/tool/usertours/tours/40_tour_navigation_mycourse.json diff --git a/admin/tool/usertours/classes/local/table/step_list.php b/admin/tool/usertours/classes/local/table/step_list.php index b4a80e083b7..c774c6e63f6 100644 --- a/admin/tool/usertours/classes/local/table/step_list.php +++ b/admin/tool/usertours/classes/local/table/step_list.php @@ -101,7 +101,10 @@ class step_list extends \flexible_table { $content = file_rewrite_pluginfile_urls($content, 'pluginfile.php', $systemcontext->id, 'tool_usertours', 'stepcontent', $step->get_id()); - return format_text(helper::get_string_from_input($content), $step->get_contentformat()); + $content = helper::get_string_from_input($content); + $content = step::get_step_image_from_input($content); + + return format_text($content, $step->get_contentformat()); } /** diff --git a/admin/tool/usertours/classes/manager.php b/admin/tool/usertours/classes/manager.php index 33dfffea827..13f6cad6e63 100644 --- a/admin/tool/usertours/classes/manager.php +++ b/admin/tool/usertours/classes/manager.php @@ -864,6 +864,10 @@ class manager { // the format filename => version. The version value needs to // be increased if the tour has been updated. $shippedtours = [ + '40_tour_navigation_dashboard.json' => 1, + '40_tour_navigation_mycourse.json' => 1, + '40_tour_navigation_course_teacher.json' => 1, + '40_tour_navigation_course_student.json' => 1, ]; // These are tours that we used to ship but don't ship any longer. diff --git a/admin/tool/usertours/classes/output/step.php b/admin/tool/usertours/classes/output/step.php index cffc90c6251..c62094bf586 100644 --- a/admin/tool/usertours/classes/output/step.php +++ b/admin/tool/usertours/classes/output/step.php @@ -68,6 +68,9 @@ class step implements \renderable { $content = file_rewrite_pluginfile_urls($content, 'pluginfile.php', $systemcontext->id, 'tool_usertours', 'stepcontent', $step->get_id()); + $content = helper::get_string_from_input($content); + $content = $step::get_step_image_from_input($content); + $result = (object) [ 'stepid' => $step->get_id(), 'title' => external_format_text( @@ -77,7 +80,7 @@ class step implements \renderable { 'tool_usertours' )[0], 'content' => external_format_text( - helper::get_string_from_input($content), + $content, $step->get_contentformat(), $PAGE->context->id, 'tool_usertours' diff --git a/admin/tool/usertours/classes/step.php b/admin/tool/usertours/classes/step.php index 41e968eeda4..0fe9b6999a3 100644 --- a/admin/tool/usertours/classes/step.php +++ b/admin/tool/usertours/classes/step.php @@ -817,4 +817,29 @@ class step { return $string; } + + /** + * Attempt to replace PIXICON placeholder with the correct images for tour step content. + * + * @param string $content Tour content + * @return string Processed tour content + */ + public static function get_step_image_from_input(string $content): string { + global $OUTPUT; + + if (preg_match('/(?<=@@PIXICON::).*?(?=@@)/', $content, $matches)) { + $bits = explode('::', $matches[0]); + $identifier = $bits[0]; + $component = $bits[1]; + if ($component == 'moodle') { + $component = 'core'; + } + $image = \html_writer::img($OUTPUT->image_url($identifier, $component)->out(false), + '', ['class' => 'img-fluid']); + $contenttoreplace = '@@PIXICON::' . $matches[0] . '@@'; + $content = str_replace($contenttoreplace, $image, $content); + } + + return $content; + } } diff --git a/admin/tool/usertours/db/upgrade.php b/admin/tool/usertours/db/upgrade.php index b299b85f1be..487cb65190a 100644 --- a/admin/tool/usertours/db/upgrade.php +++ b/admin/tool/usertours/db/upgrade.php @@ -114,11 +114,12 @@ function xmldb_tool_usertours_upgrade($oldversion) { upgrade_plugin_savepoint(true, 2021101300, 'tool', 'usertours'); } - if ($oldversion < 2021101301) { + if ($oldversion < 2021101302) { // Update shipped tours. + // Normally, we just bump the version numbers because we need to call update_shipped_tours only once. manager::update_shipped_tours(); - upgrade_plugin_savepoint(true, 2021101301, 'tool', 'usertours'); + upgrade_plugin_savepoint(true, 2021101302, 'tool', 'usertours'); } return true; diff --git a/admin/tool/usertours/lang/en/tool_usertours.php b/admin/tool/usertours/lang/en/tool_usertours.php index 710ca43ef46..03dfbc6fb2e 100644 --- a/admin/tool/usertours/lang/en/tool_usertours.php +++ b/admin/tool/usertours/lang/en/tool_usertours.php @@ -266,6 +266,28 @@ $string['tour_activityinfo_course_student_content'] = 'Activity dates and/or wha $string['tour_activityinfo_course_teacher_title'] = 'New: Activity information'; $string['tour_activityinfo_course_teacher_content'] = 'New course settings \'Show completion conditions\' and \'Show activity dates\' enable you to choose whether activity completion conditions (if set) and/or dates are displayed for students on the course page.'; +// 4.0 New navigation tour. +$string['tour_navigation_course_announcements_teacher_content'] = '@@PIXICON::tour/tour_course_admin_3::tool_usertours@@
Post important news here.'; +$string['tour_navigation_course_announcements_teacher_title'] = 'Something to tell everyone?'; +$string['tour_navigation_course_edit_teacher_content'] = '@@PIXICON::tour/tour_course_admin_1::tool_usertours@@
Add new content or edit existing content.'; +$string['tour_navigation_course_edit_teacher_title'] = 'Activate edit mode'; +$string['tour_navigation_course_index_student_content'] = '@@PIXICON::tour/tour_course_student::tool_usertours@@
Browse through activities and track your progress.'; +$string['tour_navigation_course_index_student_title'] = 'Find your way around'; +$string['tour_navigation_course_index_teacher_content'] = '@@PIXICON::tour/tour_course_admin_2::tool_usertours@@
Drag and drop activities to re-order course content.'; +$string['tour_navigation_course_index_teacher_title'] = 'Course index'; +$string['tour_navigation_course_student_tour_des'] = 'Where to browse through activities in a course'; +$string['tour_navigation_course_student_tour_name'] = 'Course index'; +$string['tour_navigation_course_teacher_tour_des'] = 'Edit mode, drag and drop of activities and posting announcements in a course'; +$string['tour_navigation_course_teacher_tour_name'] = 'Course editing'; +$string['tour_navigation_dashboard_content'] = '@@PIXICON::tour/tour_dashboard::tool_usertours@@
This side panel can contain more features.'; +$string['tour_navigation_dashboard_title'] = 'Expand to explore!'; +$string['tour_navigation_dashboard_tour_des'] = 'Where blocks can be found on the Dashboard'; +$string['tour_navigation_dashboard_tour_name'] = 'Block drawer'; +$string['tour_navigation_mycourses_content'] = '@@PIXICON::tour/tour_mycourses::tool_usertours@@
Add, copy, delete and hide courses from this menu.'; +$string['tour_navigation_mycourses_title'] = 'Courses and categories'; +$string['tour_navigation_mycourses_tour_des'] = 'Course management options on the My courses page'; +$string['tour_navigation_mycourses_tour_name'] = 'Course management'; + $string['tour_final_step_title'] = 'End of tour'; $string['tour_final_step_content'] = 'This is the end of your user tour. It won\'t show again unless you reset it using the link in the footer.'; diff --git a/admin/tool/usertours/pix/tour/tour_course_admin_1.png b/admin/tool/usertours/pix/tour/tour_course_admin_1.png new file mode 100644 index 0000000000000000000000000000000000000000..29e6f8493f9ea4636bcb184207a0bc86e1430ae5 GIT binary patch literal 24515 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 literal 0 HcmV?d00001 diff --git a/admin/tool/usertours/pix/tour/tour_course_admin_2.png b/admin/tool/usertours/pix/tour/tour_course_admin_2.png new file mode 100644 index 0000000000000000000000000000000000000000..a460a816feaabdd1de656c721da3ea9b6bc6a75b GIT binary patch literal 24977 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 XOe&xC&f6bgXhWK6TB^m$=Ar)qDoxyl literal 0 HcmV?d00001 diff --git a/admin/tool/usertours/pix/tour/tour_course_admin_3.png b/admin/tool/usertours/pix/tour/tour_course_admin_3.png new file mode 100644 index 0000000000000000000000000000000000000000..5f37de859a93bf57111c88c67e25846f1ea11394 GIT binary patch literal 26331 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 literal 0 HcmV?d00001 diff --git a/admin/tool/usertours/pix/tour/tour_course_student.png b/admin/tool/usertours/pix/tour/tour_course_student.png new file mode 100644 index 0000000000000000000000000000000000000000..d066c9292f987c462a09c9654730bede96972347 GIT binary patch literal 10979 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 literal 0 HcmV?d00001 diff --git a/admin/tool/usertours/pix/tour/tour_dashboard.png b/admin/tool/usertours/pix/tour/tour_dashboard.png new file mode 100644 index 0000000000000000000000000000000000000000..51709c9ad6d283c0b5d09941021a72637485637a GIT binary patch literal 27155 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 literal 0 HcmV?d00001 diff --git a/admin/tool/usertours/tests/step_test.php b/admin/tool/usertours/tests/step_test.php index 6937b776d69..d6c78d0dea5 100644 --- a/admin/tool/usertours/tests/step_test.php +++ b/admin/tool/usertours/tests/step_test.php @@ -823,4 +823,26 @@ class step_testcase extends advanced_testcase { $this->assertEquals($value, $step->$getter()); } + + /** + * Ensure that the get_step_image_from_input function replace PIXICON placeholder with the correct images correctly. + */ + public function test_get_step_image_from_input() { + $stepcontent = '@@PIXICON::tour/tour_mycourses::tool_usertours@@
Test'; + $stepcontent = \tool_usertours\step::get_step_image_from_input($stepcontent); + + // If the format is correct, PIXICON placeholder will be replaced with the img tag. + $this->assertStringStartsWith('assertStringEndsWith('Test', $stepcontent); + $this->assertStringNotContainsString('PIXICON', $stepcontent); + + $stepcontent = '@@PIXICON::tour/tour_mycourses
Test'; + $stepcontent = \tool_usertours\step::get_step_image_from_input($stepcontent); + + // If the format is not correct, PIXICON placeholder will not be replaced with the img tag. + $this->assertStringStartsNotWith('assertStringStartsWith('@@PIXICON', $stepcontent); + $this->assertStringEndsWith('Test', $stepcontent); + $this->assertStringContainsString('PIXICON', $stepcontent); + } } diff --git a/admin/tool/usertours/tours/40_tour_navigation_course_student.json b/admin/tool/usertours/tours/40_tour_navigation_course_student.json new file mode 100644 index 00000000000..c44950e7d61 --- /dev/null +++ b/admin/tool/usertours/tours/40_tour_navigation_course_student.json @@ -0,0 +1,22 @@ +{ + "name": "tour_navigation_course_student_tour_name,tool_usertours", + "description": "tour_navigation_course_student_tour_des,tool_usertours", + "pathmatch": "\/course\/view.php%", + "enabled": "1", + "sortorder": "3", + "endtourlabel": "", + "configdata": "{\"placement\":\"right\",\"orphan\":\"0\",\"backdrop\":\"1\",\"reflex\":\"0\",\"filtervalues\":{\"accessdate\":{\"filter_accessdate\":\"tool_usertours_accountcreation\",\"filter_accessdate_range\":0,\"filter_accessdate_enabled\":\"0\"},\"category\":[],\"course\":[],\"courseformat\":[],\"role\":[\"student\"],\"theme\":[\"boost\"],\"cssselector\":[]},\"majorupdatetime\":1641972472,\"shipped_tour\":true,\"shipped_filename\":\"40_tour_navigation_course_student.json\",\"shipped_version\":1}", + "displaystepnumbers": true, + "version": "2021101301", + "steps": [ + { + "title": "tour_navigation_course_index_student_title,tool_usertours", + "content": "tour_navigation_course_index_student_content,tool_usertours", + "contentformat": "1", + "targettype": "0", + "targetvalue": "#theme_boost-drawers-courseindex .drawercontent", + "sortorder": "0", + "configdata": "{}" + } + ] +} diff --git a/admin/tool/usertours/tours/40_tour_navigation_course_teacher.json b/admin/tool/usertours/tours/40_tour_navigation_course_teacher.json new file mode 100644 index 00000000000..30791351dd7 --- /dev/null +++ b/admin/tool/usertours/tours/40_tour_navigation_course_teacher.json @@ -0,0 +1,40 @@ +{ + "name": "tour_navigation_course_teacher_tour_name,tool_usertours", + "description": "tour_navigation_course_teacher_tour_des,tool_usertours", + "pathmatch": "\/course\/view.php%", + "enabled": "1", + "sortorder": "2", + "endtourlabel": "", + "configdata": "{\"placement\":\"bottom\",\"orphan\":\"0\",\"backdrop\":\"1\",\"reflex\":\"0\",\"filtervalues\":{\"accessdate\":{\"filter_accessdate\":\"tool_usertours_accountcreation\",\"filter_accessdate_range\":0,\"filter_accessdate_enabled\":\"0\"},\"category\":[],\"course\":[],\"courseformat\":[],\"role\":[\"-1\",\"coursecreator\",\"manager\",\"teacher\",\"editingteacher\"],\"theme\":[\"boost\"],\"cssselector\":[]},\"majorupdatetime\":1641972470,\"shipped_tour\":true,\"shipped_filename\":\"40_tour_navigation_course_teacher.json\",\"shipped_version\":1}", + "displaystepnumbers": true, + "version": "2021101301", + "steps": [ + { + "title": "tour_navigation_course_edit_teacher_title,tool_usertours", + "content": "tour_navigation_course_edit_teacher_content,tool_usertours", + "contentformat": "1", + "targettype": "0", + "targetvalue": "form.editmode-switch-form", + "sortorder": "0", + "configdata": "{}" + }, + { + "title": "tour_navigation_course_index_teacher_title,tool_usertours", + "content": "tour_navigation_course_index_teacher_content,tool_usertours", + "contentformat": "1", + "targettype": "0", + "targetvalue": "#theme_boost-drawers-courseindex .drawercontent", + "sortorder": "1", + "configdata": "{\"placement\":\"right\"}" + }, + { + "title": "tour_navigation_course_announcements_teacher_title,tool_usertours", + "content": "tour_navigation_course_announcements_teacher_content,tool_usertours", + "contentformat": "1", + "targettype": "0", + "targetvalue": ".course-content .course-content-item-content .activity-item[data-activityname=\"Announcements\"]", + "sortorder": "2", + "configdata": "{\"placement\":\"left\"}" + } + ] +} diff --git a/admin/tool/usertours/tours/40_tour_navigation_dashboard.json b/admin/tool/usertours/tours/40_tour_navigation_dashboard.json new file mode 100644 index 00000000000..671e1012aee --- /dev/null +++ b/admin/tool/usertours/tours/40_tour_navigation_dashboard.json @@ -0,0 +1,22 @@ +{ + "name": "tour_navigation_dashboard_tour_name,tool_usertours", + "description": "tour_navigation_dashboard_tour_des,tool_usertours", + "pathmatch": "FRONTPAGE", + "enabled": "1", + "sortorder": "0", + "endtourlabel": "", + "configdata": "{\"placement\":\"left\",\"orphan\":\"0\",\"backdrop\":\"1\",\"reflex\":\"0\",\"filtervalues\":{\"accessdate\":{\"filter_accessdate\":\"tool_usertours_accountcreation\",\"filter_accessdate_range\":0,\"filter_accessdate_enabled\":\"0\"},\"category\":[],\"course\":[],\"courseformat\":[],\"role\":[],\"theme\":[\"boost\"],\"cssselector\":[]},\"majorupdatetime\":1641972465,\"shipped_tour\":true,\"shipped_filename\":\"40_tour_navigation_dashboard.json\",\"shipped_version\":1}", + "displaystepnumbers": true, + "version": "2021101301", + "steps": [ + { + "title": "tour_navigation_dashboard_title,tool_usertours", + "content": "tour_navigation_dashboard_content,tool_usertours", + "contentformat": "1", + "targettype": "0", + "targetvalue": ".drawer-toggles .drawer-toggler.drawer-right-toggle", + "sortorder": "0", + "configdata": "{\"placement\":\"left\"}" + } + ] +} diff --git a/admin/tool/usertours/tours/40_tour_navigation_mycourse.json b/admin/tool/usertours/tours/40_tour_navigation_mycourse.json new file mode 100644 index 00000000000..48c091014e3 --- /dev/null +++ b/admin/tool/usertours/tours/40_tour_navigation_mycourse.json @@ -0,0 +1,22 @@ +{ + "name": "tour_navigation_mycourses_tour_name,tool_usertours", + "description": "tour_navigation_mycourses_tour_des,tool_usertours", + "pathmatch": "\/my\/courses.php", + "enabled": "1", + "sortorder": "1", + "endtourlabel": "I understand", + "configdata": "{\"placement\":\"bottom\",\"orphan\":\"0\",\"backdrop\":\"1\",\"reflex\":\"0\",\"filtervalues\":{\"accessdate\":{\"filter_accessdate\":\"tool_usertours_accountcreation\",\"filter_accessdate_range\":0,\"filter_accessdate_enabled\":\"0\"},\"category\":[],\"course\":[],\"courseformat\":[],\"role\":[],\"theme\":[\"boost\"],\"cssselector\":[]},\"majorupdatetime\":1641972468,\"shipped_tour\":true,\"shipped_filename\":\"40_tour_navigation_mycourse.json\",\"shipped_version\":1}", + "displaystepnumbers": true, + "version": "2021101301", + "steps": [ + { + "title": "tour_navigation_mycourses_title,tool_usertours", + "content": "tour_navigation_mycourses_content,tool_usertours", + "contentformat": "1", + "targettype": "0", + "targetvalue": ".header-actions-container .btn-group", + "sortorder": "0", + "configdata": "{}" + } + ] +} diff --git a/admin/tool/usertours/version.php b/admin/tool/usertours/version.php index 05c0e8108c4..80ad9e0976e 100644 --- a/admin/tool/usertours/version.php +++ b/admin/tool/usertours/version.php @@ -24,6 +24,6 @@ defined('MOODLE_INTERNAL') || die(); -$plugin->version = 2021101301; // The current module version (Date: YYYYMMDDXX). +$plugin->version = 2021101302; // The current module version (Date: YYYYMMDDXX). $plugin->requires = 2021052500; // Requires this Moodle version. $plugin->component = 'tool_usertours'; // Full name of the plugin (used for diagnostics).