@etsoo/website
Version:
ETSOO CMS Based NextJs Website Framework
206 lines (204 loc) • 7.58 kB
JavaScript
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
import Script from 'next/script';
import React from 'react';
import { SiteUtils } from './SiteUtils';
/**
* Local site class
* 本地站点类
*/
export class LocalSite {
/**
* Constructor
* 构造函数
* @param data Site data
*/
constructor(data) {
this.data = data;
}
/**
* Clear title format
* 清除标题格式
* @param title Title
*/
clearTitle(title) {
if (title == null)
return undefined;
const reg = /\[\[[^\[\]]+\]\]/g;
const parts = title.split(reg);
let match;
let index = 0;
while ((match = reg.exec(title)) !== null) {
const part = match[0].slice(2, -2);
parts.splice(index * 2 + 1, 0, part);
index++;
}
return parts.join('');
}
createMenuItem(t, hasIcon) {
var _a;
return hasIcon ? (_jsxs(React.Fragment, { children: [_jsx("i", { className: (_a = t.icon) !== null && _a !== void 0 ? _a : 'fa fa-fw' }), _jsx("span", { children: t.name })] })) : (t.name);
}
/**
* Create Bootstrap menu
* 创建 Bootstrap 菜单
* @param url Current URL
* @param hasIcon Take tab logo as icon
* @param dropdownClasses Dropdown classes
* @returns Component
*/
createBootstrapMenu(url, hasIcon, dropdownClasses) {
// Top menu items
const tabs = this.data.tabs;
const tops = tabs.filter((tab) => tab.parent == null);
dropdownClasses !== null && dropdownClasses !== void 0 ? dropdownClasses : (dropdownClasses = 'dropdown-menu shadow-sm fade-up m-0');
return (_jsx(React.Fragment, { children: tops.map((t) => {
const children = tabs.filter((tab) => tab.parent === t.id);
if (children.length === 0) {
// Skip if 'not display in menu'
if (t.layout === 1)
return;
return (_jsx("a", { href: this.formatUrl(t), className: 'nav-item nav-link' + this.matchUrl(t, url), children: this.createMenuItem(t, hasIcon) }, t.id));
}
else {
return (_jsxs("div", { className: "dropdown", children: [_jsx("a", { href: this.formatUrl(t), className: 'nav-item nav-link dropdown-toggle' +
this.matchUrl(t, url), "data-bs-toggle": "dropdown", children: this.createMenuItem(t, hasIcon) }), _jsx("div", { className: dropdownClasses, children: children.map((c) => (_jsx("a", { href: this.formatUrl(c), className: 'dropdown-item nav-link' +
this.matchUrl(c, url), children: c.name }, c.id))) })] }, t.id));
}
}) }));
}
/**
* Create Google Analytics service
* @returns Component
*/
createGAService() {
const ga = this.getService('GA');
if (ga == null)
return;
return (_jsxs(React.Fragment, { children: [_jsx(Script, { src: `https://www.googletagmanager.com/gtag/js?id=${ga.app}`, strategy: "afterInteractive" }), _jsx(Script, { id: "google-analytics", strategy: "afterInteractive", children: `
window.dataLayer = window.dataLayer || [];
function gtag() { dataLayer.push(arguments); }
gtag('js', new Date());
gtag('config', '${ga.app}');
` })] }));
}
/**
* Create Google reCAPTCHA service
* @param domain Service domain, 'R' for recaptcha.net, 'G' for google.com
* @returns Component
*/
createRECAPService(domain = 'G') {
const re = this.getService('RECAP');
if (re == null)
return;
const api = domain === 'G' ? 'google.com' : 'recaptcha.net';
return (_jsxs(React.Fragment, { children: [_jsx(Script, { src: `https://www.${api}/recaptcha/api.js?render=${re.app}`, strategy: "afterInteractive" }), _jsx(Script, { id: "google-recaptcha", strategy: "afterInteractive", children: `window.googleGecaptchaSiteKey = '${re.app}'` })] }));
}
createTabList(name, urlOrTabs, options) {
const tabs = typeof urlOrTabs === 'string'
? this.getListTab((tab) => tab.url === urlOrTabs)[1]
: urlOrTabs;
const { classNames = 'form-select', emptyOptionLabel = 'Choose...', ...rest } = options !== null && options !== void 0 ? options : {};
return (_jsxs("select", { name: name, id: name, className: classNames, ...rest, children: [_jsx("option", { value: "", children: emptyOptionLabel }), tabs.map((t) => (_jsx("option", { children: t.name }, t.id)))] }));
}
/**
* Create Wechat service
* @param onLoad On load handler
* @returns Component
*/
createWXService(onLoad) {
const wx = this.getService('WX');
if (wx == null)
return;
return (_jsx(Script, { src: "/js/jweixin-1.6.0.js", strategy: "lazyOnload", onLoad: () => onLoad }));
}
/**
* Format article URL
* 格式化文章链接
* @param item Article link item
* @returns Result
*/
formatLink(item) {
return SiteUtils.formatLink(item);
}
/**
* Format title
* 格式化标题
* @param title Title
*/
formatTitle(title, format) {
if (title == null)
return undefined;
const reg = /\[\[[^\[\]]+\]\]/g;
const parts = title.split(reg);
let match;
let index = 0;
while ((match = reg.exec(title)) !== null) {
const part = format(match[0].slice(2, -2), index);
parts.splice(index * 2 + 1, 0, part);
index++;
}
return parts;
}
/**
* Format tab URL
* 格式化栏目地址
* @param tab Tab
* @returns Result
*/
formatUrl(tab) {
return SiteUtils.formatUrl(tab);
}
/**
* Get resource
* 获取资源
* @param id Resource id
* @param defaultValue Default value
* @returns Result
*/
getResource(id, defaultValue) {
var _a, _b, _c;
return ((_c = (_b = (_a = this.data.resources.find((r) => r.id === id)) === null || _a === void 0 ? void 0 : _a.value) !== null && _b !== void 0 ? _b : defaultValue) !== null && _c !== void 0 ? _c : id);
}
/**
* Get service
* 获取服务
* @param id Service id
* @returns Result
*/
getService(id) {
return this.data.services.find((s) => s.id === id);
}
/**
* Get list tab
* 获取列表栏目
* @param filter Filter
* @returns Result
*/
getListTab(filter) {
filter !== null && filter !== void 0 ? filter : (filter = (t) => t.layout === 1);
const tab = this.data.tabs.find(filter);
if (tab == null)
return [undefined, []];
const children = this.data.tabs.filter((c) => c.parent === tab.id);
return [tab, children];
}
/**
* Match tab
* 匹配栏目
* @param tab Tab
* @param url URL
* @param matchClass Match style clsss name
* @returns Result
*/
matchUrl(tab, url, matchClass = 'active') {
let matched = false;
if (tab.parent == null) {
matched =
tab.url === url || (tab.url != '/' && url.startsWith(tab.url));
}
else {
matched = tab.url === url;
}
return matched ? ` ${matchClass}` : '';
}
}