fix(script): properly load jQuery and Bootstrap in sequence
Ensures jQuery is fully loaded before attempting to load Bootstrap, improving the reliability of modal handling and iframe interactions. This change corrects potential race conditions where Bootstrap functions might be accessed before jQuery is available. This improves the stability and predictability of modal displays and iframe content interactions.
This commit is contained in:
parent
110ac67686
commit
4ac9f46986
1 changed files with 135 additions and 132 deletions
267
script.js
267
script.js
|
@ -42,173 +42,176 @@
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
waitForGlobalVariable("bootstrap")
|
waitForGlobalVariable("$")
|
||||||
.then(() => {
|
.then(() => {
|
||||||
console.log("Bootstrap loaded successfully");
|
waitForGlobalVariable("bootstrap")
|
||||||
|
.then(() => {
|
||||||
|
console.log("Bootstrap loaded successfully");
|
||||||
|
|
||||||
var myModal = $("#fullScreenModal");
|
var myModal = $("#fullScreenModal");
|
||||||
|
|
||||||
myModal[0].addEventListener("shown.bs.modal", function () {
|
myModal[0].addEventListener("shown.bs.modal", function () {
|
||||||
const modalIframe = window.$("#modal-iframe");
|
const modalIframe = window.$("#modal-iframe");
|
||||||
|
|
||||||
modalIframe.css("width", "100%");
|
modalIframe.css("width", "100%");
|
||||||
modalIframe.css("height", "100%");
|
modalIframe.css("height", "100%");
|
||||||
modalIframe.css("border", "none");
|
modalIframe.css("border", "none");
|
||||||
|
|
||||||
// Add event handler to iframe load events
|
// Add event handler to iframe load events
|
||||||
modalIframe[0].addEventListener("load", function () {
|
modalIframe[0].addEventListener("load", function () {
|
||||||
const newLocation = modalIframe[0].contentWindow.location.href;
|
const newLocation = modalIframe[0].contentWindow.location.href;
|
||||||
|
|
||||||
// If the iframe now contains a course page, open it in the parent window
|
// If the iframe now contains a course page, open it in the parent window
|
||||||
if (newLocation.includes("/course/view.php?id=")) {
|
if (newLocation.includes("/course/view.php?id=")) {
|
||||||
window.top.location.href = newLocation;
|
window.top.location.href = newLocation;
|
||||||
};
|
};
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
var scriptId = "script-" + Math.random().toString(36).substring(2, 9);
|
var scriptId = "script-" + Math.random().toString(36).substring(2, 9);
|
||||||
currentScript.id = scriptId;
|
currentScript.id = scriptId;
|
||||||
|
|
||||||
var contentUrl = "/mod/exp360/view_content.php?id=" + $(currentScript).attr("data-activity-id");
|
var contentUrl = "/mod/exp360/view_content.php?id=" + $(currentScript).attr("data-activity-id");
|
||||||
|
|
||||||
function openInModal(url, block) {
|
function openInModal(url, block) {
|
||||||
$("#modal-iframe").attr("src", url);
|
$("#modal-iframe").attr("src", url);
|
||||||
if (block) {
|
if (block) {
|
||||||
$("#fullScreenModal").attr("data-block", block);
|
$("#fullScreenModal").attr("data-block", block);
|
||||||
} else {
|
} else {
|
||||||
$("#fullScreenModal").removeAttr("data-block");
|
$("#fullScreenModal").removeAttr("data-block");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function showContent(url, block) {
|
function showContent(url, block) {
|
||||||
bootstrap.Modal.getOrCreateInstance(
|
bootstrap.Modal.getOrCreateInstance(
|
||||||
document.getElementById("fullScreenModal")
|
document.getElementById("fullScreenModal")
|
||||||
).show();
|
).show();
|
||||||
if (url) {
|
if (url) {
|
||||||
openInModal(url, block);
|
openInModal(url, block);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function hideContent() {
|
function hideContent() {
|
||||||
bootstrap.Modal.getOrCreateInstance(
|
bootstrap.Modal.getOrCreateInstance(
|
||||||
document.getElementById("fullScreenModal")
|
document.getElementById("fullScreenModal")
|
||||||
).hide();
|
).hide();
|
||||||
openInModal("about:blank");
|
openInModal("about:blank");
|
||||||
}
|
}
|
||||||
|
|
||||||
async function nextContent() {
|
async function nextContent() {
|
||||||
var modal = $("#fullScreenModal");
|
var modal = $("#fullScreenModal");
|
||||||
var currentLi = $("#" + modal.attr("data-block"));
|
var currentLi = $("#" + modal.attr("data-block"));
|
||||||
|
|
||||||
var nextLi = currentLi.next("li.section");
|
var nextLi = currentLi.next("li.section");
|
||||||
|
|
||||||
var aLink = nextLi.find("a.stretched-link");
|
var aLink = nextLi.find("a.stretched-link");
|
||||||
|
|
||||||
if (aLink.length > 0) {
|
if (aLink.length > 0) {
|
||||||
let hrefValue = aLink.attr("href");
|
let hrefValue = aLink.attr("href");
|
||||||
|
|
||||||
if (hrefValue.includes("feedback")) {
|
if (hrefValue.includes("feedback")) {
|
||||||
hrefValue = hrefValue.replace("view", "complete");
|
hrefValue = hrefValue.replace("view", "complete");
|
||||||
hrefValue = hrefValue + "&embed=1";
|
hrefValue = hrefValue + "&embed=1";
|
||||||
} else if (hrefValue.includes("/quiz/")) {
|
} else if (hrefValue.includes("/quiz/")) {
|
||||||
hrefValue = hrefValue.replace("view", "attempt");
|
hrefValue = hrefValue.replace("view", "attempt");
|
||||||
|
|
||||||
try {
|
try {
|
||||||
const response = await fetch(hrefValue);
|
const response = await fetch(hrefValue);
|
||||||
hrefValue = response.url;
|
hrefValue = response.url;
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.error('Error fetching the URL:', error);
|
console.error('Error fetching the URL:', error);
|
||||||
|
}
|
||||||
|
|
||||||
|
hrefValue = hrefValue + "&embed=1";
|
||||||
|
}
|
||||||
|
|
||||||
|
return openInModal(hrefValue, nextLi.attr("id"));
|
||||||
|
} else {
|
||||||
|
var button = nextLi.find("button.btn-primary");
|
||||||
|
|
||||||
|
if (button.length > 0) {
|
||||||
|
return button.click();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
hrefValue = hrefValue + "&embed=1";
|
hideContent();
|
||||||
}
|
}
|
||||||
|
|
||||||
return openInModal(hrefValue, nextLi.attr("id"));
|
function openUrlInQuizModal(href) {
|
||||||
} else {
|
$("#regular-modal-iframe").attr("src", href);
|
||||||
var button = nextLi.find("button.btn-primary");
|
$("#regularModal").modal("show");
|
||||||
|
|
||||||
if (button.length > 0) {
|
|
||||||
return button.click();
|
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
hideContent();
|
// Function to open a quiz modal
|
||||||
}
|
async function openQuizModal(number, openNext = true) {
|
||||||
|
openNextFlag = openNext; // Store the flag in the global variable
|
||||||
|
|
||||||
function openUrlInQuizModal(href) {
|
let href = getFeedbackLinks()[number - 1];
|
||||||
$("#regular-modal-iframe").attr("src", href);
|
const quizLink = $(`a.stretched-link[href="${href}"]`).closest("li.section");
|
||||||
$("#regularModal").modal("show");
|
|
||||||
}
|
|
||||||
|
|
||||||
// Function to open a quiz modal
|
if (href.includes("/feedback/")) {
|
||||||
async function openQuizModal(number, openNext = true) {
|
href = href.replace("view", "complete");
|
||||||
openNextFlag = openNext; // Store the flag in the global variable
|
} else if (href.includes("/quiz/")) {
|
||||||
|
href = href.replace("view", "attempt");
|
||||||
|
try {
|
||||||
|
const response = await fetch(href);
|
||||||
|
href = response.url;
|
||||||
|
} catch (error) {
|
||||||
|
console.error('Error fetching the URL:', error);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
let href = getFeedbackLinks()[number - 1];
|
href = href + "&embed=1&modal=1";
|
||||||
const quizLink = $(`a.stretched-link[href="${href}"]`).closest("li.section");
|
openUrlInQuizModal(href);
|
||||||
|
|
||||||
if (href.includes("/feedback/")) {
|
if (openNext) {
|
||||||
href = href.replace("view", "complete");
|
// Set the data-block attribute to the block containing the current quiz
|
||||||
} else if (href.includes("/quiz/")) {
|
$("#fullScreenModal").attr("data-block", quizLink.attr("id"));
|
||||||
href = href.replace("view", "attempt");
|
}
|
||||||
try {
|
|
||||||
const response = await fetch(href);
|
|
||||||
href = response.url;
|
|
||||||
} catch (error) {
|
|
||||||
console.error('Error fetching the URL:', error);
|
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
href = href + "&embed=1&modal=1";
|
// Function to close the quiz modal
|
||||||
openUrlInQuizModal(href);
|
function closeQuizModal() {
|
||||||
|
$("#regularModal").modal("hide");
|
||||||
|
$("#regular-modal-iframe").attr("src", "about:blank");
|
||||||
|
|
||||||
if (openNext) {
|
if (openNextFlag) {
|
||||||
// Set the data-block attribute to the block containing the current quiz
|
nextContent(); // Open the next activity
|
||||||
$("#fullScreenModal").attr("data-block", quizLink.attr("id"));
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
// Function to close the quiz modal
|
function goToCourse(id) {
|
||||||
function closeQuizModal() {
|
window.top.location.href = "/course/view.php?id=" + id;
|
||||||
$("#regularModal").modal("hide");
|
}
|
||||||
$("#regular-modal-iframe").attr("src", "about:blank");
|
|
||||||
|
|
||||||
if (openNextFlag) {
|
// Attach global functions to window.top
|
||||||
nextContent(); // Open the next activity
|
window.top.nextContent = nextContent;
|
||||||
}
|
window.top.openQuizModal = openQuizModal;
|
||||||
}
|
window.top.openModal = openQuizModal;
|
||||||
|
window.top.closeQuizModal = closeQuizModal;
|
||||||
|
window.top.goToQuiz = window.top.nextContent;
|
||||||
|
window.top.goToCourse = goToCourse;
|
||||||
|
|
||||||
function goToCourse(id) {
|
var contentName = $(currentScript).attr("data-activity-name");
|
||||||
window.top.location.href = "/course/view.php?id=" + id;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Attach global functions to window.top
|
$(currentScript)
|
||||||
window.top.nextContent = nextContent;
|
.parent()
|
||||||
window.top.openQuizModal = openQuizModal;
|
.append(
|
||||||
window.top.openModal = openQuizModal;
|
`<button id="contentButton-` +
|
||||||
window.top.closeQuizModal = closeQuizModal;
|
scriptId +
|
||||||
window.top.goToQuiz = window.top.nextContent;
|
`" class="btn btn-primary" type="button">` +
|
||||||
window.top.goToCourse = goToCourse;
|
contentName +
|
||||||
|
`</button>`
|
||||||
|
);
|
||||||
|
|
||||||
var contentName = $(currentScript).attr("data-activity-name");
|
var button = $("#contentButton-" + scriptId);
|
||||||
|
button.click(function () {
|
||||||
$(currentScript)
|
showContent(
|
||||||
.parent()
|
contentUrl,
|
||||||
.append(
|
$(currentScript).closest("li.section").attr("id")
|
||||||
`<button id="contentButton-` +
|
);
|
||||||
scriptId +
|
});
|
||||||
`" class="btn btn-primary" type="button">` +
|
})
|
||||||
contentName +
|
|
||||||
`</button>`
|
|
||||||
);
|
|
||||||
|
|
||||||
var button = $("#contentButton-" + scriptId);
|
|
||||||
button.click(function () {
|
|
||||||
showContent(
|
|
||||||
contentUrl,
|
|
||||||
$(currentScript).closest("li.section").attr("id")
|
|
||||||
);
|
|
||||||
});
|
|
||||||
})
|
})
|
||||||
.catch((error) => {
|
.catch((error) => {
|
||||||
console.error(error.message);
|
console.error(error.message);
|
||||||
|
|
Loading…
Reference in a new issue