Skip to content

Commit

Permalink
performance(components): fix performance issue (#58)
Browse files Browse the repository at this point in the history
* refactor(button): performance issues

* style(eslint): type import
  • Loading branch information
MM25Zamanian authored Apr 7, 2024
1 parent b17813f commit 7b0f3e5
Show file tree
Hide file tree
Showing 49 changed files with 764 additions and 419 deletions.
7 changes: 7 additions & 0 deletions .eslintrc.json
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,13 @@
"new-cap": ["error", {"capIsNewExceptionPattern": "Mixin$"}],
"brace-style": ["error", "stroustrup", {"allowSingleLine": true}],
"indent": "off",
"@typescript-eslint/consistent-type-imports": [
"error",
{
"fixStyle": "separate-type-imports",
"prefer": "type-imports"
}
],
"@typescript-eslint/indent": [
"error",
2,
Expand Down
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,4 +20,4 @@ Hybrid UI is a cutting-edge web front-end framework that empowers developers to

## About the Package:

Hybrid UI is an open-source package developed by a team of experienced web engineers. It is not directly associated with the gecut company, but aligns with the company's mission of providing high-quality tools to developers.
Hybrid UI is an open-source package developed by a team of experienced web engineers. It is not directly associated with the gecut company, but aligns with the company's mission of providing high-quality tools to developers.
Binary file added demo/assets/placeholder.webp
Binary file not shown.
38 changes: 25 additions & 13 deletions demo/button/scripts.ts
Original file line number Diff line number Diff line change
@@ -1,33 +1,43 @@
/* eslint-disable max-len */
import {ButtonContent, gecutButton} from '@gecut/components';
import {gecutButton} from '@gecut/components';
import {map} from '@gecut/lit-helper';
import {html, render} from 'lit/html.js';

import type {ButtonContent} from '@gecut/components';

const buttonTypes: ButtonContent['type'][] = ['elevated', 'filled', 'filledTonal', 'outlined', 'text'];
const buttonsContents: Record<ButtonContent['type'], {name: string; icon?: string; loader?: string}> = {
const buttonsContents: Record<
ButtonContent['type'],
{name: string; iconSVG?: string; loaderSVG?: string} & Partial<ButtonContent>
> = {
elevated: {
name: 'Elevated Button',
name: 'Open In New Tag',
href: document.URL,
target: '_blank',
},
filled: {
name: 'Buy me a coffee',
loader:
loaderSVG:
'<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><g fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5"><path fill="currentColor" fill-opacity="0" stroke-dasharray="48" stroke-dashoffset="48" d="M17 9v9a3 3 0 0 1-3 3H8a3 3 0 0 1-3-3V9z"><animate fill="freeze" attributeName="stroke-dashoffset" dur="0.9s" values="48;0"/><animate fill="freeze" attributeName="fill-opacity" begin="1.2s" dur="0.225s" values="0;0.5"/></path><path stroke-dasharray="14" stroke-dashoffset="14" d="M17 14H20C20.55 14 21 13.55 21 13V10C21 9.45 20.55 9 20 9H17"><animate fill="freeze" attributeName="stroke-dashoffset" begin="0.9s" dur="0.3s" values="14;28"/></path></g><mask id="lineMdCoffeeTwotoneLoop0"><path fill="none" stroke="#fff" stroke-width="1.5" d="M8 0c0 2-2 2-2 4s2 2 2 4-2 2-2 4 2 2 2 4M12 0c0 2-2 2-2 4s2 2 2 4-2 2-2 4 2 2 2 4M16 0c0 2-2 2-2 4s2 2 2 4-2 2-2 4 2 2 2 4"><animateMotion calcMode="linear" dur="4.5s" path="M0 0v-8" repeatCount="indefinite"/></path></mask><rect width="24" height="0" y="7" fill="currentColor" mask="url(#lineMdCoffeeTwotoneLoop0)"><animate fill="freeze" attributeName="y" begin="1.2s" dur="0.9s" values="7;2"/><animate fill="freeze" attributeName="height" begin="1.2s" dur="0.9s" values="0;5"/></rect></svg>',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><mask id="lineMdBuyMeACoffeeTwotone0"><path fill="#fff" d="M5 6C5 4 7 6 11.5 6C16 6 19 4 19 6L19 7C19 8.5 17 9 12.5 9C8 9 5 9 5 7L5 6Z"/></mask><mask id="lineMdBuyMeACoffeeTwotone1"><path fill="#fff" d="M10.125 18.15C10.04 17.29 9.4 11.98 9.4 11.98C9.4 11.98 11.34 12.31 12.5 11.73C13.66 11.16 14.98 11 14.98 11C14.98 11 14.4 17.96 14.35 18.46C14.3 18.96 13.45 19.3 12.95 19.3L11.23 19.3C10.73 19.3 10.21 19 10.125 18.15Z"/></mask><g fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5"><path stroke-dasharray="32" stroke-dashoffset="32" d="M7.5 10.5C7.5 10.5 8.33 17.43 8.5 19C8.67 20.57 10 21 11 21L13 21C14.5 21 15.875 19.86 16 19C16.125 18.14 17 7 17 7"><animate fill="freeze" attributeName="stroke-dashoffset" dur="0.8s" values="32;0"/></path><path stroke-dasharray="12" stroke-dashoffset="12" d="M16.5 6C16.5 3.5 14 3 12 3C10 3 9.1 3.43 8 4"><animate fill="freeze" attributeName="stroke-dashoffset" begin="1.6s" dur="0.4s" values="12;24"/></path></g><rect width="16" height="5" x="20" y="4" fill="currentColor" mask="url(#lineMdBuyMeACoffeeTwotone0)"><animate fill="freeze" attributeName="x" begin="0.8s" dur="0.8s" values="20;4"/></rect><rect width="8" height="10" x="8" y="20" fill="currentColor" fill-opacity="0.5" mask="url(#lineMdBuyMeACoffeeTwotone1)"><animate fill="freeze" attributeName="y" begin="2s" dur="0.8s" values="20;10"/></rect></svg>',
iconSVG:
'<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><mask id="lineMdBuyMeACoffeeTwotone0"><path fill="#fff" d="M5 6C5 4 7 6 11.5 6C16 6 19 4 19 6L19 7C19 8.5 17 9 12.5 9C8 9 5 9 5 7L5 6Z"/></mask><mask id="lineMdBuyMeACoffeeTwotone1"><path fill="#fff" d="M10.125 18.15C10.04 17.29 9.4 11.98 9.4 11.98C9.4 11.98 11.34 12.31 12.5 11.73C13.66 11.16 14.98 11 14.98 11C14.98 11 14.4 17.96 14.35 18.46C14.3 18.96 13.45 19.3 12.95 19.3L11.23 19.3C10.73 19.3 10.21 19 10.125 18.15Z"/></mask><g fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5"><path stroke-dasharray="32" stroke-dashoffset="32" d="M7.5 10.5C7.5 10.5 8.33 17.43 8.5 19C8.67 20.57 10 21 11 21L13 21C14.5 21 15.875 19.86 16 19C16.125 18.14 17 7 17 7"><animate fill="freeze" attributeName="stroke-dashoffset" dur="0.8s" values="32;0"/></path><path stroke-dasharray="12" stroke-dashoffset="12" d="M16.5 6C16.5 3.5 14 3 12 3C10 3 9.1 3.43 8 4"><animate fill="freeze" attributeName="stroke-dashoffset" begin="1.6s" dur="0.4s" values="12;24"/></path></g><rect width="16" height="5" x="20" y="4" fill="currentColor" mask="url(#lineMdBuyMeACoffeeTwotone0)"><animate fill="freeze" attributeName="x" begin="0.8s" dur="0.8s" values="20;4"/></rect><rect width="8" height="10" x="8" y="20" fill="currentColor" fill-opacity="0.5" mask="url(#lineMdBuyMeACoffeeTwotone1)"><animate fill="freeze" attributeName="y" begin="2s" dur="0.8s" values="20;10"/></rect></svg>',
},
filledTonal: {
name: 'Download',
loader:
loaderSVG:
'<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><g fill="none" stroke="currentColor" stroke-linecap="round" stroke-width="1.5"><path stroke-dasharray="2 4" stroke-dashoffset="6" d="M12 3C16.9706 3 21 7.02944 21 12C21 16.9706 16.9706 21 12 21"><animate attributeName="stroke-dashoffset" dur="0.9s" repeatCount="indefinite" values="6;0"/></path><path stroke-dasharray="30" stroke-dashoffset="30" d="M12 21C7.02944 21 3 16.9706 3 12C3 7.02944 7.02944 3 12 3"><animate fill="freeze" attributeName="stroke-dashoffset" begin="0.15s" dur="0.45s" values="30;0"/></path><path stroke-dasharray="10" stroke-dashoffset="10" d="M12 8v7.5"><animate fill="freeze" attributeName="stroke-dashoffset" begin="0.75s" dur="0.3s" values="10;0"/></path><path stroke-dasharray="6" stroke-dashoffset="6" d="M12 15.5l3.5 -3.5M12 15.5l-3.5 -3.5"><animate fill="freeze" attributeName="stroke-dashoffset" begin="1.05s" dur="0.3s" values="6;0"/></path></g></svg>',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><g fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5"><path stroke-dasharray="14" stroke-dashoffset="14" d="M6 19h12"><animate fill="freeze" attributeName="stroke-dashoffset" begin="0.75s" dur="0.6s" values="14;0"/></path><path stroke-dasharray="18" stroke-dashoffset="18" d="M12 4 h2 v6 h2.5 L12 14.5M12 4 h-2 v6 h-2.5 L12 14.5"><animate fill="freeze" attributeName="stroke-dashoffset" dur="0.6s" values="18;0"/></path></g></svg>',
iconSVG:
'<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><g fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5"><path stroke-dasharray="14" stroke-dashoffset="14" d="M6 19h12"><animate fill="freeze" attributeName="stroke-dashoffset" begin="0.75s" dur="0.6s" values="14;0"/></path><path stroke-dasharray="18" stroke-dashoffset="18" d="M12 4 h2 v6 h2.5 L12 14.5M12 4 h-2 v6 h-2.5 L12 14.5"><animate fill="freeze" attributeName="stroke-dashoffset" dur="0.6s" values="18;0"/></path></g></svg>',
},
outlined: {
name: 'Add to Cart',
},
text: {
name: 'Upload',
loader:
loaderSVG:
'<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><g fill="none" stroke="currentColor" stroke-linecap="round" stroke-width="1.5"><path stroke-dasharray="2 4" stroke-dashoffset="6" d="M12 21C7.02944 21 3 16.9706 3 12C3 7.02944 7.02944 3 12 3"><animate attributeName="stroke-dashoffset" dur="0.6s" repeatCount="indefinite" values="6;0"/></path><path stroke-dasharray="30" stroke-dashoffset="30" d="M12 3C16.9706 3 21 7.02944 21 12C21 16.9706 16.9706 21 12 21"><animate fill="freeze" attributeName="stroke-dashoffset" begin="0.1s" dur="0.3s" values="30;0"/></path><path stroke-dasharray="10" stroke-dashoffset="10" d="M12 16v-7.5"><animate fill="freeze" attributeName="stroke-dashoffset" begin="0.5s" dur="0.2s" values="10;0"/></path><path stroke-dasharray="6" stroke-dashoffset="6" d="M12 8.5l3.5 3.5M12 8.5l-3.5 3.5"><animate fill="freeze" attributeName="stroke-dashoffset" begin="0.7s" dur="0.2s" values="6;0"/></path></g></svg>',
icon: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><g fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5"><path stroke-dasharray="14" stroke-dashoffset="14" d="M6 19h12"><animate fill="freeze" attributeName="stroke-dashoffset" begin="0.75s" dur="0.6s" values="14;0"/></path><path stroke-dasharray="18" stroke-dashoffset="18" d="M12 15 h2 v-6 h2.5 L12 4.5M12 15 h-2 v-6 h-2.5 L12 4.5"><animate fill="freeze" attributeName="stroke-dashoffset" dur="0.6s" values="18;0"/></path></g></svg>',
iconSVG:
'<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><g fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5"><path stroke-dasharray="14" stroke-dashoffset="14" d="M6 19h12"><animate fill="freeze" attributeName="stroke-dashoffset" begin="0.75s" dur="0.6s" values="14;0"/></path><path stroke-dasharray="18" stroke-dashoffset="18" d="M12 15 h2 v-6 h2.5 L12 4.5M12 15 h-2 v-6 h-2.5 L12 4.5"><animate fill="freeze" attributeName="stroke-dashoffset" dur="0.6s" values="18;0"/></path></g></svg>',
},
};

Expand All @@ -38,15 +48,15 @@ render(
${map(this, buttonTypes, (type) =>
gecutButton({
type,
loader: buttonsContents[type].loader
loader: buttonsContents[type].loaderSVG
? {
svg: buttonsContents[type].loader!,
svg: buttonsContents[type].loaderSVG!,
}
: undefined,
icon: buttonsContents[type].icon
icon: buttonsContents[type].iconSVG
? {
// eslint-disable-next-line max-len
svg: buttonsContents[type].icon!,
svg: buttonsContents[type].iconSVG!,
}
: undefined,
onClick: (event) => {
Expand All @@ -59,6 +69,8 @@ render(
}, 5120);
},
label: buttonsContents[type].name,
...buttonsContents[type],
}),
)}
</div>
Expand Down
4 changes: 2 additions & 2 deletions demo/index.html
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,9 @@
<script type="module" src="main/global.ts"></script>
</head>

<body class="bg-surface container mx-auto p-4 root">
<body class="bg-surface container mx-auto p-2 root">
<main role="main">
<div class="gecut-page scrollable">
<div class="gecut-page scrollable p-2">
<div class="typography-content">
<h1>Hybrid UI</h1>
<p>
Expand Down
11 changes: 11 additions & 0 deletions demo/lists/index.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
<!doctype html>
<html lang="en" class="color-scheme-auto bg-background font-roboto">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Gecut Lists</title>
<script type="module" src="../main/global.ts"></script>
<script type="module" src="./scripts.ts"></script>
</head>
<body class="bg-surface max-w-screen-sm mx-auto"></body>
</html>
Binary file added demo/lists/preview.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
67 changes: 67 additions & 0 deletions demo/lists/scripts.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,67 @@
/* eslint-disable max-len */
import {gecutItem} from '@gecut/components';
import {map} from 'lit/directives/map.js';
import {range} from 'lit/directives/range.js';
import {html, render} from 'lit/html.js';

import placeHolderImage from '../assets/placeholder.webp';

render(
html`
<main role="main">
<div class="flex flex-col">
${map(range(3), (i) =>
gecutItem({
leading: {
type: 'icon',
svg: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><g fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5"><path stroke-dasharray="20" stroke-dashoffset="20" d="M12 5C13.66 5 15 6.34 15 8C15 9.65685 13.6569 11 12 11C10.3431 11 9 9.65685 9 8C9 6.34315 10.3431 5 12 5z"><animate fill="freeze" attributeName="stroke-dashoffset" dur="0.6s" values="20;0"/></path><path stroke-dasharray="36" stroke-dashoffset="36" d="M12 14C16 14 19 16 19 17V19H5V17C5 16 8 14 12 14z" opacity="0"><set attributeName="opacity" begin="0.75s" to="1"/><animate fill="freeze" attributeName="stroke-dashoffset" begin="0.75s" dur="0.6s" values="36;0"/></path></g></svg>',
},
headline: 'List Item: ' + i,
}),
)}
${map(range(3), (i) =>
gecutItem({
onClick: console.log,
leading: {type: 'avatar:character', character: 'C'},
headline: 'List Item: ' + i,
supportingText:
'Hybrid UI is a cutting-edge web front-end framework that empowers developers to create high-performance, memory-safe, and visually stunning applications. It provides a comprehensive set of tools and features to streamline development and deliver exceptional user experiences.',
}),
)}
${map(range(3), (i) =>
gecutItem({
headline: 'List Item: ' + i,
leading: {
type: 'icon',
svg: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><g fill="none" stroke="currentColor" stroke-linecap="round" stroke-linejoin="round" stroke-width="1.5"><path stroke-dasharray="20" stroke-dashoffset="20" d="M12 5C13.66 5 15 6.34 15 8C15 9.65685 13.6569 11 12 11C10.3431 11 9 9.65685 9 8C9 6.34315 10.3431 5 12 5z"><animate fill="freeze" attributeName="stroke-dashoffset" dur="0.6s" values="20;0"/></path><path stroke-dasharray="36" stroke-dashoffset="36" d="M12 14C16 14 19 16 19 17V19H5V17C5 16 8 14 12 14z" opacity="0"><set attributeName="opacity" begin="0.75s" to="1"/><animate fill="freeze" attributeName="stroke-dashoffset" begin="0.75s" dur="0.6s" values="36;0"/></path></g></svg>',
},
supportingText:
'Hybrid UI is a cutting-edge web front-end framework that empowers developers to create high-performance, memory-safe, and visually stunning applications. It provides a comprehensive set of tools and features to streamline development and deliver exceptional user experiences.',
supportingTextTwoLine: true,
trailingSupportingText: {
type: 'number',
value: '1000',
maximum: 99,
},
}),
)}
${map(range(10), (i) =>
gecutItem({
href: '#' + i,
leading: {type: 'image', placeholder: placeHolderImage, source: 'https://picsum.photos/' + (i + 1) * 100},
headline: 'List Item: ' + i,
divider: true,
trailing: {
type: 'icon-button',
onClick: console.log,
svg: '<svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 24 24"><path fill="currentColor" d="M10.5 16.3q-.2 0-.35-.137T10 15.8V8.2q0-.225.15-.362t.35-.138q.05 0 .35.15l3.625 3.625q.125.125.175.25t.05.275q0 .15-.05.275t-.175.25L10.85 16.15q-.075.075-.162.113t-.188.037"/></svg>',
},
supportingText:
'Hybrid UI is a cutting-edge web front-end framework that empowers developers to create high-performance, memory-safe, and visually stunning applications. It provides a comprehensive set of tools and features to streamline development and deliver exceptional user experiences.',
}),
)}
</div>
</main>
`,
document.body,
);
5 changes: 5 additions & 0 deletions demo/main/scripts.ts
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,11 @@ const demos: Demo[] = [
href: '/top-bar/',
align: 'top',
},
{
title: 'Lists',
href: '/lists/',
align: 'top',
},
];

if (container)
Expand Down
2 changes: 1 addition & 1 deletion demo/postcss.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,4 +3,4 @@ export default {
tailwindcss: {},
autoprefixer: {},
},
}
};
4 changes: 2 additions & 2 deletions demo/vite.config.mts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import {defineConfig} from 'vite';
import Unfonts from 'unplugin-fonts/vite';
import tsconfigPaths from 'vite-tsconfig-paths';

const entrys = ['dialog', 'top-bar', 'button'];
const entrys = ['dialog', 'top-bar', 'button', 'lists'];
const DIST_PATH = './dist/';
const pages = entrys.reduce((result, name) => {
result[name] = `./${name}/index.html`;
Expand Down Expand Up @@ -38,7 +38,7 @@ export default defineConfig(() => {
families: [
{
name: 'Roboto',
styles: 'wght@500',
styles: 'wght@400',
defer: true,
},
],
Expand Down
Loading

0 comments on commit 7b0f3e5

Please sign in to comment.