kempo 1.2.6 → 1.4.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.
@@ -1 +1 @@
1
- import Component from"./Component.js";export default class Icon extends Component{constructor(){super(),this.registerAttributes({src:"",name:""})}async render(t){if(await super.render(t)){if(this.src){const t=await fetch(this.src);200===t.status?(this.innerHTML=await t.text(),this.fixSVG()):this.innerHTML.length||(this.innerHTML=Icon.fallback)}else if(this.name){const t=await fetch(`${Icon.pathToIcons}/${this.name}.svg`);200===t.status?(this.innerHTML=await t.text(),this.fixSVG()):this.innerHTML.length||(this.innerHTML=Icon.fallback)}else this.rendered=!1,this.innerHTML.length||(this.innerHTML=Icon.fallback);return!0}return!1}attributeChangedCallback(t,e,n){["src","name"].includes(t)&&this.render(!0)}fixSVG(){const t=this.querySelector("svg");t.removeAttribute("width"),t.removeAttribute("height"),t.querySelectorAll("path, rect, circle").forEach((t=>{t.setAttribute("fill","currentColor")}))}get shadowStyles(){return"\n :host {\n display: inline-block;\n vertical-align: bottom;\n }\n ::slotted(svg){\n height: 1.35em;\n vertical-align: middle;\n }\n "}static observedAttributes=["name","src"];static pathToIcons="/icons";static fallback='\n <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 -960 960 960"><path fill="currnetColor" d="M480-79q-16 0-30.5-6T423-102L102-423q-11-12-17-26.5T79-480q0-16 6-31t17-26l321-321q12-12 26.5-17.5T480-881q16 0 31 5.5t26 17.5l321 321q12 11 17.5 26t5.5 31q0 16-5.5 30.5T858-423L537-102q-11 11-26 17t-31 6Zm0-80 321-321-321-321-321 321 321 321Zm-40-281h80v-240h-80v240Zm40 120q17 0 28.5-11.5T520-360q0-17-11.5-28.5T480-400q-17 0-28.5 11.5T440-360q0 17 11.5 28.5T480-320Zm0-160Z"/></svg>\n '}window.customElements.define("k-icon",Icon);
1
+ import Component from"./Component.js";const getIconByName=t=>{const e=async e=>{try{const n=await fetch(`${e}/${t}.svg`);if(200===n.status)return await n.text()}catch(t){console.log(t)}return!1};return new Promise((async(t,n)=>{let s;for(let t=0;t<Icon.pathToIcons.length&&!s;t++)s=await e(Icon.pathToIcons[t]);s?t(s):n("Icon not found")}))};export default class Icon extends Component{constructor(){super(),this.registerAttributes({src:"",name:""})}connectedCallback(){}async render(t){if(await super.render(t)){if(this.src){const t=await fetch(this.src);200===t.status?(this.innerHTML=await t.text(),this.fixSVG()):this.innerHTML.length||(this.innerHTML=Icon.fallback)}else if(this.name){const t=await getIconByName(this.name);t?(this.innerHTML=t,this.fixSVG()):this.innerHTML.length||(this.innerHTML=Icon.fallback)}else this.rendered=!1,this.innerHTML.length||(this.innerHTML=Icon.fallback);return!0}return!1}attributeChangedCallback(t,e,n){super.attributeChangedCallback(t,e,n),["src","name"].includes(t)&&n&&this.render(!0)}fixSVG(){const t=this.querySelector("svg");t.removeAttribute("width"),t.removeAttribute("height"),t.querySelectorAll("path, rect, circle").forEach((t=>{t.setAttribute("fill","currentColor")}))}get shadowStyles(){return"\n :host {\n display: inline-block;\n vertical-align: bottom;\n }\n ::slotted(svg){\n height: 1.35em;\n vertical-align: middle;\n }\n "}static observedAttributes=["name","src"];static pathToIcons=["/icons"];static fallback='\n <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 -960 960 960"><path fill="currnetColor" d="M480-79q-16 0-30.5-6T423-102L102-423q-11-12-17-26.5T79-480q0-16 6-31t17-26l321-321q12-12 26.5-17.5T480-881q16 0 31 5.5t26 17.5l321 321q12 11 17.5 26t5.5 31q0 16-5.5 30.5T858-423L537-102q-11 11-26 17t-31 6Zm0-80 321-321-321-321-321 321 321 321Zm-40-281h80v-240h-80v240Zm40 120q17 0 28.5-11.5T520-360q0-17-11.5-28.5T480-400q-17 0-28.5 11.5T440-360q0 17 11.5 28.5T480-320Zm0-160Z"/></svg>\n '}window.customElements.define("k-icon",Icon);
@@ -0,0 +1 @@
1
+ import Component from"./Component.js";import{onEvent,offEvent,dispatchEvent}from"../utils/element.js";const tagsInputChangeHandler=Symbol(),tagsInputCommaHandler=Symbol();export default class Tags extends Component{constructor(){super(),this[tagsInputChangeHandler]=()=>{const t=this.shadowRoot.getElementById("tagsInput"),n=t.value;n&&(this.addTag(n),t.value="")},this[tagsInputCommaHandler]=t=>{if(","===t.data||"insertFromPaste"===t.inputType){const t=this.shadowRoot.getElementById("tagsInput"),n=t.value.split(",").filter((t=>!!t));n.length&&(n.forEach((t=>this.addTag(t))),t.value="")}},this.registerAttributes({value:"",allowedTags:"",disallowedTags:""})}attributeChangedCallback(t,n,e){if(super.attributeChangedCallback(t,n,e),"value"===t){const t=this.validateTags();t!==e?this.value=t:(dispatchEvent(this,"change",{oldValue:n,newValue:e}),this.renderTags())}else if(["allowed-tags","disallowed-tags"].includes(t)){const a=this.validateTags();a!==e?this.value=a:(dispatchEvent(this,`${t.replace("-","")}change`,{oldValue:n,newValue:e}),this.renderTags())}}async render(t){if(await super.render(t)){const t=this.shadowRoot.getElementById("tagsInput");return onEvent(t,"change",this[tagsInputChangeHandler]),onEvent(t,"input",this[tagsInputCommaHandler]),!0}return!1}disconnectedCallback(){super.disconnectedCallback();const t=this.shadowRoot.getElementById("tagsInput");offEvent(t,"change",this[tagsInputChangeHandler]),offEvent(t,"input",this[tagsInputCommaHandler])}async renderTags(){this.render(!1),await window.customElements.whenDefined("k-tag");const t=this.shadowRoot.getElementById("tags");t.innerHTML="";const n=this.value;n&&n.split(",").forEach((n=>{t.appendChild(new Tag(n))}))}addTag(t){const n=new Set(this.value.split(",").filter((t=>!!t)));n.add(t),this.value=[...n].filter((t=>!!t)).join(","),dispatchEvent(this,"addtag",{tag:t})}removeTag(t){const n=new Set(this.value.split(",").filter((t=>!!t)));n.delete(t),this.value=[...n].join(","),dispatchEvent(this,"removetag",{tag:t})}validateTags(){return this.value.split(",").map((t=>t.trim())).map((t=>{const n=new Set(this.allowedTags.split(",").filter((t=>!!t)));if(n.size)return n.has(t)?t:"";const e=new Set(this.disallowedTags.split(",").filter((t=>!!t)));return e.size&&e.has(t)?"":t})).filter((t=>!!t)).join(",")}get shadowTemplate(){return`\n <label for="tagsInput">\n ${super.shadowTemplate}\n <div id="tagsHolder">\n <span id="tags"></span>\n <input id="tagsInput" />\n </div>\n </label>\n `}get shadowStyles(){return`\n ${super.shadowStyles}\n :host {\n \n }\n #tagsHolder {\n display: flex;\n flex-wrap: wrap;\n align-items: flex-start;\n width: 100%;\n background-color: var(--input_bg);\n color: var(--input_tc);\n border: var(--input_border_width) solid var(--c_border);\n padding: 0;\n margin-bottom: var(--spacer);\n border-radius: var(--radius);\n outline: none;\n transition: box-shadow var(--animation_ms);\n cursor: default;\n }\n #tagsHolder:focus-within {\n box-shadow: var(--focus_shadow);\n }\n #tags {\n display: contents;\n }\n #tagsInput {\n display: inline-block;\n min-width: 5rem;\n width: auto;\n max-width: 100%;\n background-color: transparent;\n color: inherit;\n border: 0 solid transparent;\n margin-bottom: 0;\n border-radius: 0;\n transition: none;\n }\n #tagsInput {\n box-shadow: 0 0 0 transparent;\n }\n `}static observedAttributes=[...Component.observedAttributes,"value","allowed-tags","disallowed-tags"]}window.customElements.define("k-tags",Tags);const tagClickHandler=Symbol();class Tag extends Component{constructor(t){super(),this[tagClickHandler]=()=>{this.getRootNode().host.removeTag(t)},this.innerHTML=t}async render(t){return!!await super.render(t)&&(onEvent(this,"click",this[tagClickHandler]),!0)}disconnectedCallback(){super.disconnectedCallback(),offEvent(this,"click",this[tagClickHandler])}get shadowStyles(){return`\n ${super.shadowStyles}\n :host {\n display: inline-block;\n width: min-content;\n margin: var(--spacer_q);\n padding: var(--spacer_q) var(--spacer_h);\n border: 1px solid var(--c_border);\n border-radius: var(--radius);\n cursor: pointer;\n }\n :host(:hover) {\n text-decoration: line-through;\n }\n `}}window.customElements.define("k-tag",Tag);
package/dist/index.js CHANGED
@@ -1 +1 @@
1
- import Card from"./components/Card.js";import CodeEditor from"./components/CodeEditor.js";import Component from"./components/Component.js";import Dialog from"./components/Dialog.js";import FocusCapture from"./components/FocusCapture.js";import Icon from"./components/Icon.js";import Import from"./components/Import.js";import LazyComponent from"./components/LazyComponent.js";import ReactiveComponent from"./components/ReactiveComponent.js";import ReactiveLazyComponent from"./components/ReactiveLazyComponent.js";import Resize from"./components/Resize.js";import Search from"./components/Search.js";import ShowMore from"./components/ShowMore.js";import SideMenu from"./components/SideMenu.js";import Split from"./components/Split.js";import Tabs from"./components/Tabs.js";import ThemeSwitcher from"./components/ThemeSwitcher.js";import Timestamp from"./components/Timestamp.js";import Toggle from"./components/Toggle.js";import WebSnippetEditor from"./components/WebSnippetEditor.js";import cli from"./utils/cli.js";import cookie from"./utils/cookie.js";import debounce from"./utils/debounce.js";import drag from"./utils/drag.js";import element from"./utils/element.js";import formatTimestamp from"./utils/formatTimestamp.js";import fuzzyMatch from"./utils/fuzzyMatch.js";import getPreferredTheme from"./utils/getPreferredTheme.js";import loadCss from"./utils/loadCss.js";import loadScript from"./utils/loadScript.js";import object from"./utils/object.js";import string from"./utils/string.js";import toFunction from"./utils/toFunction.js";import type from"./utils/type.js";import waitFrames from"./utils/waitFrames.js";export default{Card:Card,CodeEditor:CodeEditor,Component:Component,Dialog:Dialog,FocusCapture:FocusCapture,Icon:Icon,Import:Import,LazyComponent:LazyComponent,ReactiveComponent:ReactiveComponent,ReactiveLazyComponent:ReactiveLazyComponent,Resize:Resize,Search:Search,ShowMore:ShowMore,SideMenu:SideMenu,Split:Split,Tabs:Tabs,ThemeSwitcher:ThemeSwitcher,Timestamp:Timestamp,Toggle:Toggle,WebSnippetEditor:WebSnippetEditor,cli:cli,cookie:cookie,debounce:debounce,drag:drag,element:element,formatTimestamp:formatTimestamp,fuzzyMatch:fuzzyMatch,getPreferredTheme:getPreferredTheme,loadCss:loadCss,loadScript:loadScript,object:object,string:string,toFunction:toFunction,type:type,waitFrames:waitFrames};
1
+ import Card from"./components/Card.js";import CodeEditor from"./components/CodeEditor.js";import Component from"./components/Component.js";import Dialog from"./components/Dialog.js";import FocusCapture from"./components/FocusCapture.js";import Icon from"./components/Icon.js";import Import from"./components/Import.js";import LazyComponent from"./components/LazyComponent.js";import ReactiveComponent from"./components/ReactiveComponent.js";import ReactiveLazyComponent from"./components/ReactiveLazyComponent.js";import Resize from"./components/Resize.js";import Search from"./components/Search.js";import ShowMore from"./components/ShowMore.js";import SideMenu from"./components/SideMenu.js";import Split from"./components/Split.js";import Tabs from"./components/Tabs.js";import Tags from"./components/Tags.js";import ThemeSwitcher from"./components/ThemeSwitcher.js";import Timestamp from"./components/Timestamp.js";import Toggle from"./components/Toggle.js";import WebSnippetEditor from"./components/WebSnippetEditor.js";import cli from"./utils/cli.js";import cookie from"./utils/cookie.js";import debounce from"./utils/debounce.js";import drag from"./utils/drag.js";import element from"./utils/element.js";import formatTimestamp from"./utils/formatTimestamp.js";import fuzzyMatch from"./utils/fuzzyMatch.js";import getPreferredTheme from"./utils/getPreferredTheme.js";import loadCss from"./utils/loadCss.js";import loadScript from"./utils/loadScript.js";import object from"./utils/object.js";import string from"./utils/string.js";import toFunction from"./utils/toFunction.js";import type from"./utils/type.js";import waitFrames from"./utils/waitFrames.js";export default{Card:Card,CodeEditor:CodeEditor,Component:Component,Dialog:Dialog,FocusCapture:FocusCapture,Icon:Icon,Import:Import,LazyComponent:LazyComponent,ReactiveComponent:ReactiveComponent,ReactiveLazyComponent:ReactiveLazyComponent,Resize:Resize,Search:Search,ShowMore:ShowMore,SideMenu:SideMenu,Split:Split,Tabs:Tabs,Tags:Tags,ThemeSwitcher:ThemeSwitcher,Timestamp:Timestamp,Toggle:Toggle,WebSnippetEditor:WebSnippetEditor,cli:cli,cookie:cookie,debounce:debounce,drag:drag,element:element,formatTimestamp:formatTimestamp,fuzzyMatch:fuzzyMatch,getPreferredTheme:getPreferredTheme,loadCss:loadCss,loadScript:loadScript,object:object,string:string,toFunction:toFunction,type:type,waitFrames:waitFrames};
@@ -0,0 +1 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path fill="currentColor" d="M14.06 9.02l.92.92L5.92 19H5v-.92l9.06-9.06M17.66 3c-.25 0-.51.1-.7.29l-1.83 1.83 3.75 3.75 1.83-1.83c.39-.39.39-1.02 0-1.41l-2.34-2.34c-.2-.2-.45-.29-.71-.29zm-3.6 3.19L3 17.25V21h3.75L17.81 9.94l-3.75-3.75z"/></svg>
package/docs/index.html CHANGED
@@ -8,6 +8,9 @@
8
8
  </head>
9
9
  <body>
10
10
  <k-import src="./nav.inc.html"></k-import>
11
+ <main>
12
+
13
+ </main>
11
14
  <script type="module" src="./kempo/components/Import.js"></script>
12
15
  </body>
13
16
  </html>
@@ -1 +1 @@
1
- import Component from"./Component.js";export default class Icon extends Component{constructor(){super(),this.registerAttributes({src:"",name:""})}async render(t){if(await super.render(t)){if(this.src){const t=await fetch(this.src);200===t.status?(this.innerHTML=await t.text(),this.fixSVG()):this.innerHTML.length||(this.innerHTML=Icon.fallback)}else if(this.name){const t=await fetch(`${Icon.pathToIcons}/${this.name}.svg`);200===t.status?(this.innerHTML=await t.text(),this.fixSVG()):this.innerHTML.length||(this.innerHTML=Icon.fallback)}else this.rendered=!1,this.innerHTML.length||(this.innerHTML=Icon.fallback);return!0}return!1}attributeChangedCallback(t,e,n){["src","name"].includes(t)&&this.render(!0)}fixSVG(){const t=this.querySelector("svg");t.removeAttribute("width"),t.removeAttribute("height"),t.querySelectorAll("path, rect, circle").forEach((t=>{t.setAttribute("fill","currentColor")}))}get shadowStyles(){return"\n :host {\n display: inline-block;\n vertical-align: bottom;\n }\n ::slotted(svg){\n height: 1.35em;\n vertical-align: middle;\n }\n "}static observedAttributes=["name","src"];static pathToIcons="/icons";static fallback='\n <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 -960 960 960"><path fill="currnetColor" d="M480-79q-16 0-30.5-6T423-102L102-423q-11-12-17-26.5T79-480q0-16 6-31t17-26l321-321q12-12 26.5-17.5T480-881q16 0 31 5.5t26 17.5l321 321q12 11 17.5 26t5.5 31q0 16-5.5 30.5T858-423L537-102q-11 11-26 17t-31 6Zm0-80 321-321-321-321-321 321 321 321Zm-40-281h80v-240h-80v240Zm40 120q17 0 28.5-11.5T520-360q0-17-11.5-28.5T480-400q-17 0-28.5 11.5T440-360q0 17 11.5 28.5T480-320Zm0-160Z"/></svg>\n '}window.customElements.define("k-icon",Icon);
1
+ import Component from"./Component.js";const getIconByName=t=>{const e=async e=>{try{const n=await fetch(`${e}/${t}.svg`);if(200===n.status)return await n.text()}catch(t){console.log(t)}return!1};return new Promise((async(t,n)=>{let s;for(let t=0;t<Icon.pathToIcons.length&&!s;t++)s=await e(Icon.pathToIcons[t]);s?t(s):n("Icon not found")}))};export default class Icon extends Component{constructor(){super(),this.registerAttributes({src:"",name:""})}connectedCallback(){}async render(t){if(await super.render(t)){if(this.src){const t=await fetch(this.src);200===t.status?(this.innerHTML=await t.text(),this.fixSVG()):this.innerHTML.length||(this.innerHTML=Icon.fallback)}else if(this.name){const t=await getIconByName(this.name);t?(this.innerHTML=t,this.fixSVG()):this.innerHTML.length||(this.innerHTML=Icon.fallback)}else this.rendered=!1,this.innerHTML.length||(this.innerHTML=Icon.fallback);return!0}return!1}attributeChangedCallback(t,e,n){super.attributeChangedCallback(t,e,n),["src","name"].includes(t)&&n&&this.render(!0)}fixSVG(){const t=this.querySelector("svg");t.removeAttribute("width"),t.removeAttribute("height"),t.querySelectorAll("path, rect, circle").forEach((t=>{t.setAttribute("fill","currentColor")}))}get shadowStyles(){return"\n :host {\n display: inline-block;\n vertical-align: bottom;\n }\n ::slotted(svg){\n height: 1.35em;\n vertical-align: middle;\n }\n "}static observedAttributes=["name","src"];static pathToIcons=["/icons"];static fallback='\n <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 -960 960 960"><path fill="currnetColor" d="M480-79q-16 0-30.5-6T423-102L102-423q-11-12-17-26.5T79-480q0-16 6-31t17-26l321-321q12-12 26.5-17.5T480-881q16 0 31 5.5t26 17.5l321 321q12 11 17.5 26t5.5 31q0 16-5.5 30.5T858-423L537-102q-11 11-26 17t-31 6Zm0-80 321-321-321-321-321 321 321 321Zm-40-281h80v-240h-80v240Zm40 120q17 0 28.5-11.5T520-360q0-17-11.5-28.5T480-400q-17 0-28.5 11.5T440-360q0 17 11.5 28.5T480-320Zm0-160Z"/></svg>\n '}window.customElements.define("k-icon",Icon);
@@ -0,0 +1 @@
1
+ import Component from"./Component.js";import{onEvent,offEvent,dispatchEvent}from"../utils/element.js";const tagsInputChangeHandler=Symbol(),tagsInputCommaHandler=Symbol();export default class Tags extends Component{constructor(){super(),this[tagsInputChangeHandler]=()=>{const t=this.shadowRoot.getElementById("tagsInput"),n=t.value;n&&(this.addTag(n),t.value="")},this[tagsInputCommaHandler]=t=>{if(","===t.data||"insertFromPaste"===t.inputType){const t=this.shadowRoot.getElementById("tagsInput"),n=t.value.split(",").filter((t=>!!t));n.length&&(n.forEach((t=>this.addTag(t))),t.value="")}},this.registerAttributes({value:"",allowedTags:"",disallowedTags:""})}attributeChangedCallback(t,n,e){if(super.attributeChangedCallback(t,n,e),"value"===t){const t=this.validateTags();t!==e?this.value=t:(dispatchEvent(this,"change",{oldValue:n,newValue:e}),this.renderTags())}else if(["allowed-tags","disallowed-tags"].includes(t)){const a=this.validateTags();a!==e?this.value=a:(dispatchEvent(this,`${t.replace("-","")}change`,{oldValue:n,newValue:e}),this.renderTags())}}async render(t){if(await super.render(t)){const t=this.shadowRoot.getElementById("tagsInput");return onEvent(t,"change",this[tagsInputChangeHandler]),onEvent(t,"input",this[tagsInputCommaHandler]),!0}return!1}disconnectedCallback(){super.disconnectedCallback();const t=this.shadowRoot.getElementById("tagsInput");offEvent(t,"change",this[tagsInputChangeHandler]),offEvent(t,"input",this[tagsInputCommaHandler])}async renderTags(){this.render(!1),await window.customElements.whenDefined("k-tag");const t=this.shadowRoot.getElementById("tags");t.innerHTML="";const n=this.value;n&&n.split(",").forEach((n=>{t.appendChild(new Tag(n))}))}addTag(t){const n=new Set(this.value.split(",").filter((t=>!!t)));n.add(t),this.value=[...n].filter((t=>!!t)).join(","),dispatchEvent(this,"addtag",{tag:t})}removeTag(t){const n=new Set(this.value.split(",").filter((t=>!!t)));n.delete(t),this.value=[...n].join(","),dispatchEvent(this,"removetag",{tag:t})}validateTags(){return this.value.split(",").map((t=>t.trim())).map((t=>{const n=new Set(this.allowedTags.split(",").filter((t=>!!t)));if(n.size)return n.has(t)?t:"";const e=new Set(this.disallowedTags.split(",").filter((t=>!!t)));return e.size&&e.has(t)?"":t})).filter((t=>!!t)).join(",")}get shadowTemplate(){return`\n <label for="tagsInput">\n ${super.shadowTemplate}\n <div id="tagsHolder">\n <span id="tags"></span>\n <input id="tagsInput" />\n </div>\n </label>\n `}get shadowStyles(){return`\n ${super.shadowStyles}\n :host {\n \n }\n #tagsHolder {\n display: flex;\n flex-wrap: wrap;\n align-items: flex-start;\n width: 100%;\n background-color: var(--input_bg);\n color: var(--input_tc);\n border: var(--input_border_width) solid var(--c_border);\n padding: 0;\n margin-bottom: var(--spacer);\n border-radius: var(--radius);\n outline: none;\n transition: box-shadow var(--animation_ms);\n cursor: default;\n }\n #tagsHolder:focus-within {\n box-shadow: var(--focus_shadow);\n }\n #tags {\n display: contents;\n }\n #tagsInput {\n display: inline-block;\n min-width: 5rem;\n width: auto;\n max-width: 100%;\n background-color: transparent;\n color: inherit;\n border: 0 solid transparent;\n margin-bottom: 0;\n border-radius: 0;\n transition: none;\n }\n #tagsInput {\n box-shadow: 0 0 0 transparent;\n }\n `}static observedAttributes=[...Component.observedAttributes,"value","allowed-tags","disallowed-tags"]}window.customElements.define("k-tags",Tags);const tagClickHandler=Symbol();class Tag extends Component{constructor(t){super(),this[tagClickHandler]=()=>{this.getRootNode().host.removeTag(t)},this.innerHTML=t}async render(t){return!!await super.render(t)&&(onEvent(this,"click",this[tagClickHandler]),!0)}disconnectedCallback(){super.disconnectedCallback(),offEvent(this,"click",this[tagClickHandler])}get shadowStyles(){return`\n ${super.shadowStyles}\n :host {\n display: inline-block;\n width: min-content;\n margin: var(--spacer_q);\n padding: var(--spacer_q) var(--spacer_h);\n border: 1px solid var(--c_border);\n border-radius: var(--radius);\n cursor: pointer;\n }\n :host(:hover) {\n text-decoration: line-through;\n }\n `}}window.customElements.define("k-tag",Tag);
@@ -1 +1 @@
1
- import Card from"./components/Card.js";import CodeEditor from"./components/CodeEditor.js";import Component from"./components/Component.js";import Dialog from"./components/Dialog.js";import FocusCapture from"./components/FocusCapture.js";import Icon from"./components/Icon.js";import Import from"./components/Import.js";import LazyComponent from"./components/LazyComponent.js";import ReactiveComponent from"./components/ReactiveComponent.js";import ReactiveLazyComponent from"./components/ReactiveLazyComponent.js";import Resize from"./components/Resize.js";import Search from"./components/Search.js";import ShowMore from"./components/ShowMore.js";import SideMenu from"./components/SideMenu.js";import Split from"./components/Split.js";import Tabs from"./components/Tabs.js";import ThemeSwitcher from"./components/ThemeSwitcher.js";import Timestamp from"./components/Timestamp.js";import Toggle from"./components/Toggle.js";import WebSnippetEditor from"./components/WebSnippetEditor.js";import cli from"./utils/cli.js";import cookie from"./utils/cookie.js";import debounce from"./utils/debounce.js";import drag from"./utils/drag.js";import element from"./utils/element.js";import formatTimestamp from"./utils/formatTimestamp.js";import fuzzyMatch from"./utils/fuzzyMatch.js";import getPreferredTheme from"./utils/getPreferredTheme.js";import loadCss from"./utils/loadCss.js";import loadScript from"./utils/loadScript.js";import object from"./utils/object.js";import string from"./utils/string.js";import toFunction from"./utils/toFunction.js";import type from"./utils/type.js";import waitFrames from"./utils/waitFrames.js";export default{Card:Card,CodeEditor:CodeEditor,Component:Component,Dialog:Dialog,FocusCapture:FocusCapture,Icon:Icon,Import:Import,LazyComponent:LazyComponent,ReactiveComponent:ReactiveComponent,ReactiveLazyComponent:ReactiveLazyComponent,Resize:Resize,Search:Search,ShowMore:ShowMore,SideMenu:SideMenu,Split:Split,Tabs:Tabs,ThemeSwitcher:ThemeSwitcher,Timestamp:Timestamp,Toggle:Toggle,WebSnippetEditor:WebSnippetEditor,cli:cli,cookie:cookie,debounce:debounce,drag:drag,element:element,formatTimestamp:formatTimestamp,fuzzyMatch:fuzzyMatch,getPreferredTheme:getPreferredTheme,loadCss:loadCss,loadScript:loadScript,object:object,string:string,toFunction:toFunction,type:type,waitFrames:waitFrames};
1
+ import Card from"./components/Card.js";import CodeEditor from"./components/CodeEditor.js";import Component from"./components/Component.js";import Dialog from"./components/Dialog.js";import FocusCapture from"./components/FocusCapture.js";import Icon from"./components/Icon.js";import Import from"./components/Import.js";import LazyComponent from"./components/LazyComponent.js";import ReactiveComponent from"./components/ReactiveComponent.js";import ReactiveLazyComponent from"./components/ReactiveLazyComponent.js";import Resize from"./components/Resize.js";import Search from"./components/Search.js";import ShowMore from"./components/ShowMore.js";import SideMenu from"./components/SideMenu.js";import Split from"./components/Split.js";import Tabs from"./components/Tabs.js";import Tags from"./components/Tags.js";import ThemeSwitcher from"./components/ThemeSwitcher.js";import Timestamp from"./components/Timestamp.js";import Toggle from"./components/Toggle.js";import WebSnippetEditor from"./components/WebSnippetEditor.js";import cli from"./utils/cli.js";import cookie from"./utils/cookie.js";import debounce from"./utils/debounce.js";import drag from"./utils/drag.js";import element from"./utils/element.js";import formatTimestamp from"./utils/formatTimestamp.js";import fuzzyMatch from"./utils/fuzzyMatch.js";import getPreferredTheme from"./utils/getPreferredTheme.js";import loadCss from"./utils/loadCss.js";import loadScript from"./utils/loadScript.js";import object from"./utils/object.js";import string from"./utils/string.js";import toFunction from"./utils/toFunction.js";import type from"./utils/type.js";import waitFrames from"./utils/waitFrames.js";export default{Card:Card,CodeEditor:CodeEditor,Component:Component,Dialog:Dialog,FocusCapture:FocusCapture,Icon:Icon,Import:Import,LazyComponent:LazyComponent,ReactiveComponent:ReactiveComponent,ReactiveLazyComponent:ReactiveLazyComponent,Resize:Resize,Search:Search,ShowMore:ShowMore,SideMenu:SideMenu,Split:Split,Tabs:Tabs,Tags:Tags,ThemeSwitcher:ThemeSwitcher,Timestamp:Timestamp,Toggle:Toggle,WebSnippetEditor:WebSnippetEditor,cli:cli,cookie:cookie,debounce:debounce,drag:drag,element:element,formatTimestamp:formatTimestamp,fuzzyMatch:fuzzyMatch,getPreferredTheme:getPreferredTheme,loadCss:loadCss,loadScript:loadScript,object:object,string:string,toFunction:toFunction,type:type,waitFrames:waitFrames};
package/icons/edit.svg ADDED
@@ -0,0 +1 @@
1
+ <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path fill="currentColor" d="M14.06 9.02l.92.92L5.92 19H5v-.92l9.06-9.06M17.66 3c-.25 0-.51.1-.7.29l-1.83 1.83 3.75 3.75 1.83-1.83c.39-.39.39-1.02 0-1.41l-2.34-2.34c-.2-.2-.45-.29-.71-.29zm-3.6 3.19L3 17.25V21h3.75L17.81 9.94l-3.75-3.75z"/></svg>
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "kempo",
3
- "version": "1.2.6",
3
+ "version": "1.4.0",
4
4
  "type": "module",
5
5
  "description": "A web component library",
6
6
  "main": "dist/index.js",
@@ -1,5 +1,29 @@
1
1
  import Component from './Component.js';
2
2
 
3
+ const getIconByName = (name) => {
4
+ const tryDir = async (dir) => {
5
+ try {
6
+ const response = await fetch(`${dir}/${name}.svg`);
7
+ if(response.status === 200) return await (response).text();
8
+ } catch(e){
9
+ console.log(e);
10
+ }
11
+ return false;
12
+ }
13
+
14
+ return new Promise( async (resolve, reject) => {
15
+ let svg;
16
+ for(let i=0; i < Icon.pathToIcons.length && !svg; i++){
17
+ svg = await tryDir(Icon.pathToIcons[i]);
18
+ }
19
+ if(svg){
20
+ resolve(svg);
21
+ } else {
22
+ reject('Icon not found');
23
+ }
24
+ });
25
+ }
26
+
3
27
  export default class Icon extends Component {
4
28
  constructor(){
5
29
  super();
@@ -8,6 +32,11 @@ export default class Icon extends Component {
8
32
  name: ''
9
33
  });
10
34
  }
35
+ connectedCallback(){
36
+ // super.connectedCallback();
37
+ // do not call super.connectedCallback because it will attempt to render and then again on attribute change
38
+ // so we are overwriting the parent method and not calling it
39
+ }
11
40
  async render(force){
12
41
  if(await super.render(force)){
13
42
  if(this.src){
@@ -17,9 +46,9 @@ export default class Icon extends Component {
17
46
  this.fixSVG();
18
47
  } else if(!this.innerHTML.length) this.innerHTML = Icon.fallback;
19
48
  } else if(this.name){
20
- const response = await fetch(`${Icon.pathToIcons}/${this.name}.svg`);
21
- if(response.status === 200){
22
- this.innerHTML = await (response).text();
49
+ const svg = await getIconByName(this.name);
50
+ if(svg){
51
+ this.innerHTML = svg;
23
52
  this.fixSVG();
24
53
  } else if(!this.innerHTML.length) this.innerHTML = Icon.fallback;
25
54
  } else {
@@ -31,7 +60,8 @@ export default class Icon extends Component {
31
60
  return false;
32
61
  }
33
62
  attributeChangedCallback(n, oV, nV){
34
- if(['src', 'name'].includes(n)){
63
+ super.attributeChangedCallback(n, oV, nV);
64
+ if(['src', 'name'].includes(n) && nV){
35
65
  this.render(true);
36
66
  }
37
67
  }
@@ -61,7 +91,9 @@ export default class Icon extends Component {
61
91
  'src'
62
92
  ];
63
93
 
64
- static pathToIcons = '/icons';
94
+ static pathToIcons = [
95
+ '/icons'
96
+ ];
65
97
  static fallback = /*html*/`
66
98
  <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 -960 960 960"><path fill="currnetColor" d="M480-79q-16 0-30.5-6T423-102L102-423q-11-12-17-26.5T79-480q0-16 6-31t17-26l321-321q12-12 26.5-17.5T480-881q16 0 31 5.5t26 17.5l321 321q12 11 17.5 26t5.5 31q0 16-5.5 30.5T858-423L537-102q-11 11-26 17t-31 6Zm0-80 321-321-321-321-321 321 321 321Zm-40-281h80v-240h-80v240Zm40 120q17 0 28.5-11.5T520-360q0-17-11.5-28.5T480-400q-17 0-28.5 11.5T440-360q0 17 11.5 28.5T480-320Zm0-160Z"/></svg>
67
99
  `;
@@ -0,0 +1,224 @@
1
+ import Component from './Component.js';
2
+ import {
3
+ onEvent,
4
+ offEvent,
5
+ dispatchEvent
6
+ } from '../utils/element.js';
7
+
8
+ const tagsInputChangeHandler = Symbol(),
9
+ tagsInputCommaHandler = Symbol();
10
+ export default class Tags extends Component {
11
+ constructor(){
12
+ super();
13
+
14
+ this[tagsInputChangeHandler] = () => {
15
+ const $tagsInput = this.shadowRoot.getElementById('tagsInput');
16
+ const tag = $tagsInput.value;
17
+ if(tag){
18
+ this.addTag(tag);
19
+ $tagsInput.value = '';
20
+ }
21
+ }
22
+ this[tagsInputCommaHandler] = (event) => {
23
+ if(event.data === ',' || event.inputType === 'insertFromPaste'){
24
+ const $tagsInput = this.shadowRoot.getElementById('tagsInput');
25
+ const tags = $tagsInput.value.split(',').filter(i=>!!i);
26
+ if(tags.length){
27
+ tags.forEach(tag=>this.addTag(tag));
28
+ $tagsInput.value = '';
29
+ }
30
+ }
31
+ }
32
+
33
+ this.registerAttributes({
34
+ value: '',
35
+ allowedTags: '',
36
+ disallowedTags: ''
37
+ });
38
+ }
39
+ attributeChangedCallback(name, oldValue, newValue){
40
+ super.attributeChangedCallback(name, oldValue, newValue);
41
+ if(name === 'value'){
42
+ const validTags = this.validateTags();
43
+ if(validTags !== newValue){
44
+ this.value = validTags;
45
+ } else {
46
+ dispatchEvent(this, 'change', {
47
+ oldValue,
48
+ newValue
49
+ });
50
+ this.renderTags();
51
+ }
52
+ } else if(['allowed-tags', 'disallowed-tags'].includes(name)){
53
+ const validTags = this.validateTags();
54
+ if(validTags !== newValue){
55
+ this.value = validTags;
56
+ } else {
57
+ dispatchEvent(this, `${name.replace('-','')}change`, {
58
+ oldValue,
59
+ newValue
60
+ });
61
+ this.renderTags();
62
+ }
63
+ }
64
+ }
65
+ async render(force){
66
+ if(await super.render(force)){
67
+ const $tagsInput = this.shadowRoot.getElementById('tagsInput');
68
+ onEvent($tagsInput, 'change', this[tagsInputChangeHandler]);
69
+ onEvent($tagsInput, 'input', this[tagsInputCommaHandler]);
70
+ return true;
71
+ }
72
+ return false;
73
+ }
74
+ disconnectedCallback(){
75
+ super.disconnectedCallback();
76
+ const $tagsInput = this.shadowRoot.getElementById('tagsInput');
77
+ offEvent($tagsInput, 'change', this[tagsInputChangeHandler]);
78
+ offEvent($tagsInput, 'input', this[tagsInputCommaHandler]);
79
+ }
80
+ async renderTags(){
81
+ this.render(false);
82
+ await window.customElements.whenDefined('k-tag');
83
+ const $tags = this.shadowRoot.getElementById('tags');
84
+ $tags.innerHTML = '';
85
+ const v = this.value;
86
+ if(v) v.split(',').forEach(tag => {
87
+ $tags.appendChild(new Tag(tag));
88
+ });
89
+ }
90
+ addTag(tag){
91
+ const tags = new Set(this.value.split(',').filter(i=>!!i));
92
+ tags.add(tag);
93
+ this.value = [...tags].filter(i=>!!i).join(',');
94
+ dispatchEvent(this, 'addtag', {tag});
95
+ }
96
+ removeTag(tag){
97
+ const tags = new Set(this.value.split(',').filter(i=>!!i));
98
+ tags.delete(tag);
99
+ this.value = [...tags].join(',');
100
+ dispatchEvent(this, 'removetag', {tag});
101
+ }
102
+ validateTags(){
103
+ return this.value
104
+ .split(',')
105
+ .map(t=>t.trim())
106
+ .map(tag => {
107
+ const allowed = new Set(this.allowedTags.split(',').filter(i=>!!i));
108
+ if(allowed.size) return allowed.has(tag)?tag:'';
109
+ const disallowed = new Set(this.disallowedTags.split(',').filter(i=>!!i));
110
+ if(disallowed.size) return disallowed.has(tag)?'':tag;
111
+ return tag;
112
+ })
113
+ .filter(i=>!!i).join(',');
114
+ }
115
+
116
+ get shadowTemplate(){
117
+ return /*html*/`
118
+ <label for="tagsInput">
119
+ ${super.shadowTemplate}
120
+ <div id="tagsHolder">
121
+ <span id="tags"></span>
122
+ <input id="tagsInput" />
123
+ </div>
124
+ </label>
125
+ `;
126
+ }
127
+ get shadowStyles(){
128
+ return /*css*/`
129
+ ${super.shadowStyles}
130
+ :host {
131
+
132
+ }
133
+ #tagsHolder {
134
+ display: flex;
135
+ flex-wrap: wrap;
136
+ align-items: flex-start;
137
+ width: 100%;
138
+ background-color: var(--input_bg);
139
+ color: var(--input_tc);
140
+ border: var(--input_border_width) solid var(--c_border);
141
+ padding: 0;
142
+ margin-bottom: var(--spacer);
143
+ border-radius: var(--radius);
144
+ outline: none;
145
+ transition: box-shadow var(--animation_ms);
146
+ cursor: default;
147
+ }
148
+ #tagsHolder:focus-within {
149
+ box-shadow: var(--focus_shadow);
150
+ }
151
+ #tags {
152
+ display: contents;
153
+ }
154
+ #tagsInput {
155
+ display: inline-block;
156
+ min-width: 5rem;
157
+ width: auto;
158
+ max-width: 100%;
159
+ background-color: transparent;
160
+ color: inherit;
161
+ border: 0 solid transparent;
162
+ margin-bottom: 0;
163
+ border-radius: 0;
164
+ transition: none;
165
+ }
166
+ #tagsInput {
167
+ box-shadow: 0 0 0 transparent;
168
+ }
169
+ `;
170
+ }
171
+
172
+ static observedAttributes = [
173
+ ...Component.observedAttributes,
174
+ 'value',
175
+ 'allowed-tags',
176
+ 'disallowed-tags'
177
+ ];
178
+ }
179
+ window.customElements.define('k-tags', Tags);
180
+
181
+ const tagClickHandler = Symbol();
182
+ class Tag extends Component {
183
+ constructor(tag){
184
+ super();
185
+
186
+ /* Private Methods */
187
+ this[tagClickHandler] = () => {
188
+ this.getRootNode().host.removeTag(tag);
189
+ }
190
+
191
+ /* init */
192
+ this.innerHTML = tag;
193
+ }
194
+ async render(force){
195
+ if(await super.render(force)){
196
+ onEvent(this, 'click', this[tagClickHandler]);
197
+ return true;
198
+ }
199
+ return false;
200
+ }
201
+ disconnectedCallback(){
202
+ super.disconnectedCallback();
203
+ offEvent(this, 'click', this[tagClickHandler]);
204
+ }
205
+
206
+ get shadowStyles(){
207
+ return /*css*/`
208
+ ${super.shadowStyles}
209
+ :host {
210
+ display: inline-block;
211
+ width: min-content;
212
+ margin: var(--spacer_q);
213
+ padding: var(--spacer_q) var(--spacer_h);
214
+ border: 1px solid var(--c_border);
215
+ border-radius: var(--radius);
216
+ cursor: pointer;
217
+ }
218
+ :host(:hover) {
219
+ text-decoration: line-through;
220
+ }
221
+ `;
222
+ }
223
+ }
224
+ window.customElements.define('k-tag', Tag);