Initial commit: AIFO official portal web.

Add static site, shared layout, and Node dev server with standard .gitignore.

Co-authored-by: Cursor <cursoragent@cursor.com>
This commit is contained in:
2026-06-30 15:29:50 +08:00
commit 4d30803b60
1154 changed files with 184340 additions and 0 deletions
+85
View File
@@ -0,0 +1,85 @@
/**
* Footer newsletter validation (client-side).
* Loaded by layout.js after footer inject.
*/
(function () {
var EMAIL_RE = /^[^\s@]+@[^\s@]+\.[^\s@]+$/;
function initNewsletter(root) {
var form = root.querySelector("#aifo-footer-newsletter");
if (!form) return;
var field = form.querySelector("#aifo-footer-newsletter-field");
var input = form.querySelector('[name="email"]');
var errorEl = form.querySelector("#aifo-footer-newsletter-error");
var errorTextEl = errorEl
? errorEl.querySelector(".aifo-foot__form-tooltip-text")
: null;
var successEl = form.querySelector("#aifo-footer-newsletter-success");
function hideMessages() {
if (errorEl) errorEl.hidden = true;
if (successEl) successEl.hidden = true;
if (field) field.classList.remove("is-invalid");
}
function showError(message) {
if (errorEl) {
if (errorTextEl) {
errorTextEl.textContent = message;
} else {
errorEl.textContent = message;
}
errorEl.hidden = false;
}
if (successEl) successEl.hidden = true;
if (field) field.classList.add("is-invalid");
}
function showSuccess(message) {
if (successEl) {
successEl.textContent = message;
successEl.hidden = false;
}
if (errorEl) errorEl.hidden = true;
if (field) field.classList.remove("is-invalid");
}
form.addEventListener("submit", function (e) {
e.preventDefault();
var value = (input.value || "").trim();
if (!value) {
showError("Please enter your email address.");
input.focus();
return;
}
if (!EMAIL_RE.test(value)) {
showError("Please enter a valid email address.");
input.focus();
return;
}
showSuccess("Thank you for subscribing!");
form.reset();
});
input.addEventListener("input", hideMessages);
input.addEventListener("blur", function () {
var value = (input.value || "").trim();
if (!value) {
hideMessages();
return;
}
if (!EMAIL_RE.test(value)) {
showError("Please enter a valid email address.");
}
});
}
window.initAifoFooter = function (root) {
if (!root) return;
initNewsletter(root);
};
})();