@k3000/ce 0.1.0 → 0.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +12 -6
- package/app/comp/comp-test.mjs +1 -1
- package/app/comp/nav-bar.mjs +1 -1
- package/app/comp/page-container.mjs +1 -1
- package/app/comp/tab-bar.mjs +1 -1
- package/app/index.html +1 -1
- package/bin.mjs +48 -0
- package/ce.mjs +1 -0
- package/comm/router-view.mjs +1 -1
- package/console/components/common-action-button.mjs +1 -1
- package/console/components/common-header.mjs +1 -1
- package/console/components/common-input.mjs +1 -1
- package/console/components/common-modal.mjs +1 -1
- package/console/components/common-pagination.mjs +1 -1
- package/console/components/common-toolbar.mjs +1 -1
- package/console/components/layout-menu.mjs +1 -1
- package/console/index.html +1 -1
- package/index.mjs +1 -1
- package/package.json +8 -2
- package/console/components/console-header.mjs +0 -26
package/README.md
CHANGED
|
@@ -16,12 +16,20 @@
|
|
|
16
16
|
|
|
17
17
|
## 🚀 快速上手
|
|
18
18
|
|
|
19
|
-
### 1.
|
|
19
|
+
### 1. 全局安装
|
|
20
|
+
```
|
|
21
|
+
.\> npm i @k3000/ce -g #全局安装使用ce命令
|
|
22
|
+
.\> cd demo #进入需要的目录
|
|
23
|
+
.\demo> ce copy #复制核心框架文件可以带参数,ce copy dist.js,将ce.mjs复制到当前目录,并改名为:dist.js
|
|
24
|
+
.\demo> ce demo #复制使用示例一共三个目录和一个数据文件:/app、/comm、/console、/info.json
|
|
25
|
+
```
|
|
26
|
+
|
|
27
|
+
### 2. 项目引入
|
|
20
28
|
在 `index.html` 中通过 Script 标签引入核心框架:
|
|
21
29
|
|
|
22
30
|
```html
|
|
23
31
|
<script type="module">
|
|
24
|
-
import { config } from '../
|
|
32
|
+
import { config } from '../ce.mjs'
|
|
25
33
|
|
|
26
34
|
config({
|
|
27
35
|
dir: './console/components',
|
|
@@ -30,15 +38,13 @@
|
|
|
30
38
|
</script>
|
|
31
39
|
```
|
|
32
40
|
|
|
33
|
-
###
|
|
41
|
+
### 3. 定义组件
|
|
34
42
|
每个组件为一个独立的 `.mjs` 文件。
|
|
35
43
|
|
|
36
44
|
**示例: `my-counter.mjs`**
|
|
37
45
|
|
|
38
|
-
**更多示例参照: `/app`,`/console`**
|
|
39
|
-
|
|
40
46
|
```javascript
|
|
41
|
-
import { useWatch } from "../../
|
|
47
|
+
import { useWatch } from "../../ce.mjs";
|
|
42
48
|
|
|
43
49
|
// 1. 定义 HTML 结构 (支持插值 {{ }})
|
|
44
50
|
export const innerHTML = `
|
package/app/comp/comp-test.mjs
CHANGED
package/app/comp/nav-bar.mjs
CHANGED
package/app/comp/tab-bar.mjs
CHANGED
package/app/index.html
CHANGED
|
@@ -6,7 +6,7 @@
|
|
|
6
6
|
content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0, viewport-fit=cover"/>
|
|
7
7
|
<title>demo</title>
|
|
8
8
|
<script type="module">
|
|
9
|
-
import { config } from '../
|
|
9
|
+
import { config } from '../ce.mjs'
|
|
10
10
|
|
|
11
11
|
config({
|
|
12
12
|
dir: './app/comp',
|
package/bin.mjs
ADDED
|
@@ -0,0 +1,48 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import {cpSync, existsSync, mkdirSync} from "node:fs";
|
|
3
|
+
import {resolve, dirname} from "node:path";
|
|
4
|
+
|
|
5
|
+
const [, , key, value] = process.argv
|
|
6
|
+
|
|
7
|
+
const path = import.meta.url.substring(process.platform === 'win32' ? 8 : 7)
|
|
8
|
+
|
|
9
|
+
const getDir = path => decodeURI(dirname(path));
|
|
10
|
+
/**
|
|
11
|
+
* 将本目录下的文件或者文件夹复制到项目运行目录
|
|
12
|
+
* @param {string} source 自动加上'/'
|
|
13
|
+
* @param {string} destination
|
|
14
|
+
* @param {boolean} force
|
|
15
|
+
* @example
|
|
16
|
+
* myCopyFn('source', 'destination')
|
|
17
|
+
*/
|
|
18
|
+
const myCopyFn = (source, destination = source, force = false) => {
|
|
19
|
+
|
|
20
|
+
return cpSync( `${getDir(path)}/${source}`, destination, {recursive: true, force})
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
// console.log(`key: ${key}, value: ${value}, path: ${path}, getDir: ${getDir(path)}`);
|
|
24
|
+
|
|
25
|
+
switch (key) {
|
|
26
|
+
|
|
27
|
+
case 'copy':
|
|
28
|
+
|
|
29
|
+
let target = value || 'ce.mjs'
|
|
30
|
+
|
|
31
|
+
if (!target.endsWith('.mjs') && !target.endsWith('.js')) {
|
|
32
|
+
|
|
33
|
+
target += '.js'
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
myCopyFn('index.mjs', target, true)
|
|
37
|
+
|
|
38
|
+
break
|
|
39
|
+
|
|
40
|
+
case 'demo':
|
|
41
|
+
|
|
42
|
+
myCopyFn('app', 'app', !!value)
|
|
43
|
+
myCopyFn('comm', 'comm', !!value)
|
|
44
|
+
myCopyFn('console', 'console', !!value)
|
|
45
|
+
myCopyFn('info.json', 'info.json', !!value)
|
|
46
|
+
|
|
47
|
+
break
|
|
48
|
+
}
|
package/ce.mjs
ADDED
|
@@ -0,0 +1 @@
|
|
|
1
|
+
let dir="./comp",ext="mjs",getVariables=e=>{const t=e.match(/\{\{.+?}}/g);if(!t)return new Set;const o=new Set,n=new Set(["true","false","null","undefined","this","new","typeof","in","instanceof"]);return t.forEach((e=>{const t=e.slice(2,-2).match(/\b[a-zA-Z_$][\w$]*(?:\s*\.\s*[a-zA-Z_$][\w$]*)*(?!\s*\()/g);t&&t.forEach((e=>{n.has(e)||o.add(e)}))})),o},createTmpNode=(e="")=>document.createTextNode(""),literalsCode=e=>`with (scope) {\n\treturn \`${e.replace(/{{(.*?)}}/g,((e,t)=>`\${${t}}`))}\` \n}`,functionCode=e=>`with (scope) {\n\treturn ${e} \n}`,handleArray=(e,t)=>{const o=e.ownerElement;if(e.nodeMap||(e.nodeMap=[],e.mark=createTmpNode("数组结束标记"),o.parentNode.replaceChild(e.mark,o),e.ownerElement=o.cloneNode(!0)),!Array.isArray(t))return e;const n=e.mark.parentNode;let r=0;for(;r<t.length;r++)if(void 0!==e.nodeMap[r]){if(e.nodeMap[r][0]!==t[r]){const s=o.cloneNode(!0);try{t[r]._=e.scope}catch(e){}bindNode(t[r],s,!0),n.replaceChild(s,e.nodeMap[r][1]),e.nodeMap[r]=[t[r],s]}}else{const s=o.cloneNode(!0);try{t[r]._=e.scope}catch(e){}bindNode(t[r],s,!0),n.insertBefore(s,e.mark),e.nodeMap[r]=[t[r],s]}const s=r;for(;r<e.nodeMap.length;r++)n.removeChild(e.nodeMap[r][1]);return e.nodeMap.splice(s,e.nodeMap.length-s),e};export const config=e=>{e.dir&&(dir=e.dir),e.ext&&(ext=e.ext),"function"==typeof e.getVariables&&(getVariables=e.getVariables),"function"==typeof e.createTmpNode&&(createTmpNode=e.createTmpNode),"function"==typeof e.literalsCode&&(literalsCode=e.literalsCode),"function"==typeof e.functionCode&&(functionCode=e.functionCode),"function"==typeof e.handleArray&&(handleArray=e.handleArray)};const getCEName=e=>e.tagName.includes("-")?e.tagName.toLowerCase():e.hasAttribute("is")?e.getAttribute("is"):void 0;export const throttle=(e,t=41)=>{let o;return(...n)=>{clearTimeout(o),o=setTimeout((()=>e(...n)),t)}};const objectPool=new WeakMap,importPool=new WeakSet,addListener=(e,t,o)=>{getVariables(t).forEach((t=>{let n="",r=e,s=0,a=t.split(".");for([s,n]of a.entries()){if(s===a.length-1)break;if(null===r||"object"!=typeof r||!Reflect.has(r,n))return;if(Array.isArray(r[n])&&s===a.length-2)break;r=r[n]}if(null!==r&&"object"==typeof r&&(!Object.getOwnPropertyDescriptor(r,n)||Object.getOwnPropertyDescriptor(r,n).configurable))if(objectPool.has(r)){const e=objectPool.get(r);if(e.has(n))e.get(n).add(o);else{const t=new Set([o]);e.set(n,t);let s=r[n];Object.defineProperty(r,n,{get:()=>s,set:e=>{s!==e&&(s=e,t.forEach((e=>e())))}})}}else{const e=new Set([o]);objectPool.set(r,new Map([[n,e]]));let t=r[n];Object.defineProperty(r,n,{get:()=>t,set:o=>{t!==o&&(t=o,e.forEach((e=>e())))}})}}))},ceMap=Object.create(null),disposeCE=(e,t)=>{if(e.querySelectorAll("*:not(:defined)").forEach((e=>importCE(e))),ceMap[t].shadowRoot&&(e.attachShadow({mode:"open"}),e.shadowRoot.appendChild(ceMap[t].shadowRoot.create(e))),ceMap[t].innerHTML||ceMap[t].outerHTML){const o=(ceMap[t].innerHTML||ceMap[t].outerHTML).create(e);if(!ceMap[t].shadowRoot){const t=Array.from(o.querySelectorAll("slot")),n=t.reduce(((e,t)=>(e[t.getAttribute("name")||""]=t,e)),{}),r=Array.from(e.childNodes);for(const e of r){const t="function"==typeof e.getAttribute&&e.getAttribute("slot")||"";n[t]&&n[t].parentNode.insertBefore(e,n[t])}for(const e of t)e.parentNode.removeChild(e)}if(ceMap[t].outerHTML){for(;o.firstChild;)e.parentElement.insertBefore(o.firstChild,e);e.parentElement.removeChild(e)}else e.appendChild(o)}"function"==typeof e.ready&&e.ready()};let tmp=null;const importCE=(e,t=void 0)=>{if(t=t??getCEName(e),importPool.has(e))return;if(importPool.add(e),void 0!==customElements.get(t))return void disposeCE(e,t);const o=e.nodeName.includes("-");let n=dir;if(e.attributes.dir&&e.attributes.dir.nodeValue){const t=e.attributes.dir.nodeValue;e.removeAttribute("dir"),n=t.startsWith("/")||t.startsWith("./")?t:`${n}/${t}`}import(`${n}/${t}.${ext}`).then((n=>{void 0===customElements.get(t)&&(ceMap[t]=Object.create(null),"string"==typeof n.innerHTML&&(ceMap[t].innerHTML=bind(n.innerHTML)),"string"==typeof n.outerHTML&&(ceMap[t].outerHTML=bind(n.outerHTML)),"string"==typeof n.shadowRoot&&(ceMap[t].shadowRoot=bind(n.shadowRoot)),o?customElements.define(t,n.default):customElements.define(t,n.default,{extends:e.nodeName.toLowerCase()})),disposeCE(e,t)})).catch((e=>{console.error(e)}))},disposeNode=(e,t)=>{const o=t.nodeValue;if(null===o.match(/{{(.*?)}}/))return;const n=new Function("scope",literalsCode(o));addListener(e,o,throttle((()=>t.nodeValue=n.call(t,e)))),t.nodeValue=n.call(t,e)},disposeAttrValue=(e,t,o,n)=>{if(!n.startsWith("{{")||!n.endsWith("}}")||n.slice(2).includes("{{")){const r=new Function("scope",literalsCode(n));return()=>o.nodeValue=r.call(t,e)}const r=new Function("scope",functionCode(n.slice(2,-2)));return()=>{const n=r.call(t,e);switch(n){case!0:o.nodeValue="",t.attributes.setNamedItem(o);break;case!1:t.removeAttribute(o.nodeName);break;default:o.nodeValue=n,t.attributes.setNamedItem(o)}}},disposeSpecialAttr=(e,t,o,n)=>{const r=t.ownerElement;let s=t.nodeName;if(s.startsWith("on")){if(r.removeAttribute(s),!o.includes("(")){const t=o.split(".");let n="",a=e,i=0;for([i,n]of t.entries()){if(i===t.length-1)break;if(null===a||"object"!=typeof a||!Reflect.has(a,n)){a={};break}a=a[n]}if("function"==typeof a[n])return r[s]=e=>a[n](e),!0}const t=new Function("scope","event",functionCode(o));return r[s]=o=>t.call(r,e,o),!0}if("connect"===s){r.removeAttribute(s);const n=new Function("scope",functionCode(o)),a=createTmpNode("节点断开重连的标记"),i=()=>{n(e)?a.parentNode?.replaceChild(r,a):r.parentNode?.replaceChild(a,r)};return addListener(e,t.nodeValue,throttle((()=>i()))),i(),!0}if("each"===s){r.removeAttribute(s);let n={ownerElement:r,scope:e};if(Reflect.has(e,o)){const r=()=>n=handleArray(n,e[o]);return addListener(e,t.nodeValue,throttle((()=>r()))),r(),!0}const a=new Function("scope",functionCode(o));return handleArray(n,a(e)),!0}if(n){r.removeAttribute(s);const n=new Function("scope",functionCode(o));s.includes("-")&&(s=s.split("-").map(((e,t)=>e&&t?e[0].toUpperCase()+e.slice(1):e)).join(""));const a=()=>{const t=n(e);r[s]="function"==typeof t?t.bind(e):t};return addListener(e,t.nodeValue,throttle((()=>a()))),a(),!0}return!1},disposeAttr=(e,t,o)=>{const n=t.nodeValue;if(null===n.match(/{{(.*?)}}/))return;if(n.startsWith("{{")&&n.endsWith("}}")&&disposeSpecialAttr(e,t,n.slice(2,-2),o))return;const r=disposeAttrValue(e,t.ownerElement,t,n);addListener(e,n,throttle((()=>r()))),r()};export const bindNode=(e,t,o)=>{const n=o?[t]:Array.from(t.childNodes);for(const o of n){if(o.attributes)for(const n of Array.from(o.attributes))if(disposeAttr(e,n,getCEName(o)),"each"===n.nodeName&&n.nodeValue.startsWith("{{")&&n.nodeValue.endsWith("}}"))return t;if(o.childNodes&&bindNode(e,o),3===o.nodeType&&null!==o.nodeValue&&disposeNode(e,o),1===o.nodeType){const e=getCEName(o);e&&importCE(o,e)}}return t};export const bind=e=>{const t=document.createElement("template");return t.innerHTML=e,{create:e=>bindNode(e,document.importNode(t.content,!0))}};const style=document.createElement("style");style.innerHTML="\n*:not(:defined) {\n display: none\n}\n",document.head.appendChild(style),addEventListener("DOMContentLoaded",(()=>document.querySelectorAll("*:not(:defined)").forEach((e=>importCE(e)))));class EventBus{value=void 0;targets=new Map;add(e,t=Object.create(null)){this.targets.set(e,t),t.preValue&&void 0!==this.value&&e(...this.value)}remove(e){this.targets.delete(e)}dispatch(...e){return this.value=e,Promise.allSettled(this.targets.entries().map((([t,{once:o}])=>(o&&this.targets.delete(t),t(...e)))))}}const eventBusObj=Object.create(null),eventBus=Object.defineProperties(Object.create(null),{add:{value:(e,t,o)=>{Reflect.has(eventBusObj,e)||(eventBusObj[e]=new EventBus),eventBusObj[e].add(t,o)}},remove:{value:(e,t)=>{Reflect.has(eventBusObj,e)&&eventBusObj[e].remove(t)}},dispatch:{value:(e,...t)=>(Reflect.has(eventBusObj,e)||(eventBusObj[e]=new EventBus),eventBusObj[e].dispatch(...t))}});export const useEvent=()=>eventBus;export const useRef=e=>{const t=Object.create(null);for(const o of e.querySelectorAll("[ref]"))t[o.attributes.ref.nodeValue]=o;return t};export const useAttr=e=>{const t=Object.create(null);for(const o of e.attributes)t[o.nodeName]=o.nodeValue;return t};export const useWatch=e=>(t,o=!1)=>{for(const[n,r]of Object.entries(t)){if("function"!=typeof r)continue;let t=e[n];Object.defineProperty(e,n,{get:()=>t,set:e=>{if(!1!==r(e,t))return t=e}}),o&&r(t,t)}};
|
package/comm/router-view.mjs
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import {throttle, useWatch} from "../../
|
|
1
|
+
import {throttle, useWatch} from "../../ce.mjs";
|
|
2
2
|
|
|
3
3
|
export const innerHTML = `
|
|
4
4
|
<div class="px-6 py-4 border-t border-white/20 dark:border-white/5 bg-white/30 dark:bg-white/5 backdrop-blur-md flex items-center justify-between">
|
package/console/index.html
CHANGED
package/index.mjs
CHANGED
|
@@ -178,7 +178,7 @@ let handleArray = (data, array) => {
|
|
|
178
178
|
* 调用该方法完成可配置参数合方法的初始化
|
|
179
179
|
* @param options
|
|
180
180
|
* @example
|
|
181
|
-
* import { config } from '../
|
|
181
|
+
* import { config } from '../ce.mjs'
|
|
182
182
|
* config({
|
|
183
183
|
* dir: './app/comp',
|
|
184
184
|
* getVariables: () => {...}
|
package/package.json
CHANGED
|
@@ -1,26 +0,0 @@
|
|
|
1
|
-
import {useAttr} from "../../index.mjs";
|
|
2
|
-
|
|
3
|
-
export const innerHTML = `
|
|
4
|
-
<div class="flex flex-col sm:flex-row sm:items-center justify-between gap-4">
|
|
5
|
-
<div>
|
|
6
|
-
<h1 class="text-2xl font-bold text-gray-800 dark:text-white tracking-tight">{{title}}</h1>
|
|
7
|
-
<p class="text-sm text-gray-500 dark:text-gray-400 mt-1">{{description}}</p>
|
|
8
|
-
</div>
|
|
9
|
-
<div class="flex items-center gap-3">
|
|
10
|
-
<slot></slot>
|
|
11
|
-
</div>
|
|
12
|
-
</div>
|
|
13
|
-
`
|
|
14
|
-
|
|
15
|
-
export default class extends HTMLElement {
|
|
16
|
-
title = ''
|
|
17
|
-
description = ''
|
|
18
|
-
|
|
19
|
-
constructor() {
|
|
20
|
-
super()
|
|
21
|
-
const attr = useAttr(this)
|
|
22
|
-
this.title = attr.title
|
|
23
|
-
this.description = attr.description
|
|
24
|
-
// console.log([this])
|
|
25
|
-
}
|
|
26
|
-
}
|