Ecosyste.ms: Awesome
An open API service indexing awesome lists of open source software.
https://github.com/lifeart/glimmer-next
GXT is `glimmer-vm` runtime alternative, only 7kb gzipped
https://github.com/lifeart/glimmer-next
compiler dom-manipulation glimmer-js glimmer-next glimmer-vm gxt handlebars handlebars-js reactive-framework template ui vite
Last synced: 3 months ago
JSON representation
GXT is `glimmer-vm` runtime alternative, only 7kb gzipped
- Host: GitHub
- URL: https://github.com/lifeart/glimmer-next
- Owner: lifeart
- License: mit
- Created: 2023-12-28T07:57:05.000Z (about 1 year ago)
- Default Branch: master
- Last Pushed: 2024-05-22T17:42:35.000Z (8 months ago)
- Last Synced: 2024-05-23T06:27:31.925Z (8 months ago)
- Topics: compiler, dom-manipulation, glimmer-js, glimmer-next, glimmer-vm, gxt, handlebars, handlebars-js, reactive-framework, template, ui, vite
- Language: TypeScript
- Homepage: https://g-next.netlify.app
- Size: 1.31 MB
- Stars: 25
- Watchers: 5
- Forks: 3
- Open Issues: 36
-
Metadata Files:
- Readme: README.md
- License: LICENSE
Awesome Lists containing this project
README
# GXT [![Netlify Status](https://api.netlify.com/api/v1/badges/43af359b-56a7-4607-9e01-04ca3a545470/deploy-status)](https://app.netlify.com/sites/g-next/deploys)
`GXT` is a cutting-edge, compilable runtime environment designed as `glimmer-vm` alternative, showcasing the power and flexibility of modern web component development. This repo includes a live example of how `GXT` can be used in real-world applications, providing developers with a practical and interactive experience. Explore our [sample](https://g-next.netlify.app/) at netlify.
## Benefits
- π₯ Hot Module Replacement (Reloading)
- π Native shadow-dom support
- β Async element destructors support
- π₯οΈ Server Side Rendering
- π§ Rehydration
- π§ Ember Developer Tools support
- π Runtime code tree-shaking
- π¦ Small Bundle Size
- βοΈ Typed Templates with Glint
- π€ Ember syntax compatibility
- π 40% performance improvement compared to GlimmerVM
- πΎ 2x less memory usage compared to GlimmerVM
- π§Ή Template linting support via Ember Template Lint
- βοΈ Built-in reactivity system## Development tools for VS Code
- [Language Server](https://marketplace.visualstudio.com/items?itemName=lifeart.vscode-ember-unstable)
- [Template Syntax](https://marketplace.visualstudio.com/items?itemName=lifeart.vscode-glimmer-syntax)
- [Templates Type checking](https://marketplace.visualstudio.com/items?itemName=typed-ember.glint-vscode)## Quick Links
- Related issue: [glimmer-vm/issues/1540](https://github.com/glimmerjs/glimmer-vm/issues/1540)
- Related PR: [glimmer-vm/pull/1541](https://github.com/glimmerjs/glimmer-vm/pull/1541)
- Sample App: [js-framework-benchmark](https://github.com/krausest/js-framework-benchmark/tree/master/frameworks/keyed/gxt)## Component sample
Based on [template imports RFC](https://rfcs.emberjs.com/id/0779-first-class-component-templates/)
```gjs
import { RemoveIcon } from "./RemoveIcon.gts";
import type { Item } from "@/utils/data";
import { type Cell, cellFor, Component } from "@lifeart/gxt";type RowArgs = {
Args: {
item: Item;
selectedCell: Cell;
onRemove: (item: Item) => void;
};
};export class Row extends Component {
get labelCell() {
return cellFor(this.args.item, "label");
}
get id() {
return this.args.item.id;
}
get selected() {
return this.args.selectedCell.value;
}
set selected(value: number) {
this.args.selectedCell.value = value;
}
get isSelected() {
return this.selected === this.id;
}
get className() {
return this.isSelected ? "danger" : "";
}
onClick = () => {
this.selected = this.isSelected ? 0 : this.id;
};
onClickRemove = (e: Event) => {
this.args.onRemove(this.args.item);
};
{{this.id}}
{{this.labelCell}}
}
```## Key Features
### Simple and Expressive Component Model
- Component as Functions: Every component in gNext is a function, executed only once for efficiency and better performance.
- Class based components: Class based components are supported as well.
- Basic Glint Support: Integration with Glint for improved TypeScript support and developer experience.
- Comprehensive Slot Support: Full support for different kinds of slots, including {{yield}}, enhancing the flexibility in component composition.
- Modifiers and Helpers APIs:
Modifiers for element-specific logic.
Helpers for reusable logic across components.
- Template Imports: Import templates from other files, enabling better code organization and reusability.
- Template Compilation: Compile templates to JavaScript functions for improved performance and efficiency.
- Opcodes tree-shaking: Opcodes tree-shaking for smaller bundle size. We don't include unused DOM and component, flow-control opcodes in the bundle.### Reactive Primitives
- Mutable State with `cell`: Use cell for creating reactive, mutable states. Updating and accessing cell values is straightforward and efficient.
- Derived State with `formula`: Create derived states that automatically update when dependencies change, ensuring reactive and responsive UIs.
- Support for destructors: Enables clean-up and resource management, preventing memory leaks.## Benefits and Use Cases
gNext serves as a powerful tool for web developers looking to harness the capabilities of Glimmer-VM in a real-world setting. Its benefits and use cases include:
- Efficient DOM Rendering: Experience fast and efficient DOM updates and rendering, crucial for high-performance web applications.
- Reactive State Management: Manage component states reactively, ensuring UIs are always up-to-date with the underlying data.
- Enhanced Developer Experience: Enjoy a seamless development experience with features like TypeScript support, comprehensive API documentation, and easy-to-understand examples.
- Flexible Component Composition: Leverage advanced component composition techniques to build complex UIs with ease.
- Resource Management: Efficiently manage resources with destructors, preventing common issues like memory leaks.gNext is not just a library; it's a gateway to building modern, efficient, and reactive web applications using Glimmer-VM. Whether you are building dynamic user interfaces, complex single-page applications, or just experimenting with new front-end technologies, gNext provides the tools and capabilities to bring your ideas to life.
Explore gNext and elevate your web development experience!
### Notes
#
- modifiers API:
```js
function modifier(element: Element, ...args: Args) {
return () => {
// destructor
}
}
```- helpers API:
```js
function helper(...args: Args): string | boolean | number | null {
// helper logic
return 3 + 2;
}
```### Reactive primitives
- `@tracked` - decorator to mark class property as reactive primitive. It's autotrack dependencies and update when any of them changed. Note, to use it you need to add `import 'decorator-transforms/globals';` in top-level file.
- `cell(value)` - reactive primitive, for mutable state. We could update cel calling `cell.update(value)`, to get cell value we could use `cell.value`.
- `formula(fn: () => unknown)` - reactive primitive, for derived state.`formula` could be used to create derived state from `Cell`'s. It's autotrack dependencies and update when any of them changed.
`scope` function is used to suspend `ts` error about unused variables. It's not required for runtime, but required for `ts` compilation.
`destructors` supported.
```ts
import { registerDestructor, hbs, scope } from "@lifeart/gxt";export function Icon() {
registerDestructor(this, () => {
console.log("destructor");
});return hbs``;
}
```### Setup
Start project from this template: https://github.com/lifeart/template-gxt
or
```
pnpm create vite my-app --template vanilla-ts
pnpm install @lifeart/gxt
```Edit `vite.config.mts` to import compiler:
```js
import { defineConfig } from "vite";
import { compiler } from "@lifeart/gxt/compiler";export default defineConfig(({ mode }) => ({
plugins: [compiler(mode)],
}));
```To render root component, use `renderComponent` function.
```js
import { renderComponent } from "@lifeart/gxt";
import App from "./App.gts";const Instance = renderComponent(
new App().template(),
document.getElementById("app"),
);
```To destroy component, use `destroyElement` function.
```js
import { destroyElement } from "@lifeart/gxt";destroyElement(Instance);
```