virst v0.12.8
about virst
virst is:
- pronounced
/fɜrst/("technically" pun of first/fɜrst/and burst/bɜrst/); - new repo/library based on
@html_first/simple_signal;- which itself are inspired by
solidJSsignalbasedreactivity- which then
simple_signalwill be discontinued effective immediately;
- which then
- which itself are inspired by
- collections of library for creating:
reactive(and if necessary,declarative)SPA web app, including functionalities such as:- client side
routing(using query parameter with ourDefineQRouter); signalbased asyncrhonous reactivity, which supports:dataOnly;- with
domReflect(usingattributeName="...attributeValues;");
- optional templating using:
htmlpage based template;- our
Componentinstances;
- client side
- client side JS library that are relying on
attributeNameto track the element lifecycle, using ourLifecyleclass api:- you can use it to create your own
HATEOAS(likehtmx) client side library, to interprete returnedhtmlStringwhich have certainattributeName; - handle non editable
static site generatedexports/publish such as:bootstrap studio;pinegrow;WYSIWYG web builder;- or bassically any kind of
SSGsoftware;
- you can use it to create your own
- comes with
asyncQueuehandler in the background;- no need to scratch your head too much for
asyncprocesses;
- no need to scratch your head too much for
- all of our class api are
typedwithjsdoc:- if you cannot find the documentation in this
readme, you can allways rely on yourIDE intellisense
- if you cannot find the documentation in this
about this readme
- this
repo/libonly serves forapi-documentationpurposes; - as for
exampleon how to use on differentuseCaserefer to html-first-virst
how to install
npm i virst
// or
bun i virst
// or any js package manager with npm capabilityv0.^9.x
- drop supports for
Animation- it's better to use more dedicated library like animeJS
generate side effect for signal based reactivity such as for:
const letExample = new Let('')
new $(async(first)=>{
const value = test.value;
if(first){
return;
// return early if you want to opt out from handling the effect immediately,
// also by doing this you can make the `$` slightly more performance 1) when dealing with `async await` on hydration,
// such as data fetching;
}
// handle value
})
// 1) and when all of the effects is registered, you can call `letExample.call$` to call for effect in parallel;// bassically the same with `Let` but use `new Derived`App starter helper for module environtment:
- the sole purpose is just to auto import the necessary global file in your main js file;
- if it's
elementScopedinstances/statics methods, it will be better to just leave it for theparentModuleto import it accordingly;
component creation helper using class initiation; behaviour:
- it rendered directly to real DOM;
- library like
bootstrapcssand it'sjsparts can select yourelementsfor it's functionality; - you have to manually scope your style by
- library like
// on Component scope
html`<style>
[${thisInstance.attr}]{
...nestedCSSRules
}
</style>
...
`
- also you might need to explicitly use ">"
directChildOfselector, as when you try to renderchildComponent- it could also be accidentally selected;
- render method:
- you put returned value of
thisInstance.attron an html element, which- it will be rendered as it's
innerHTMLat theonConnectedevent, then- it will used
MutationObserverto look for changes;
CRUD wrapper class;
signalwill be updated from returned value ofread;readwill be called after callingthisInstance.create/update/delete_, that havetruerefreshSignal; /** @template V
- instantiate this class to opt in page templating, by saving html template string on a html document page;
// main page
<div ${templateName}="${path};${selector}"></div>// template document
<div ${targetAttribute}="${selector}"></div>- how it works:
- the class itself register a
LifecyclefortemplateName, which then upon connected, it will fetch thepaththen selectstargetAttribute="selector" as template that then replace main page element with selected element from template; - fetched page will be then be cached, along with any
[targetAttribute]on that page
- the class itself register a
allow the usage of search query based router through class instantiation;
- register by putting import this instance on your js
main file
create shortcuts through class instantiation;
- register by putting import this instance on your js
main file
create named storage (localStorage or sessionStorage) through class instantiation;
- register by putting import this instance on your js
main file
- this class is extended from
LetLet-signalbased reactivity, wich value are derived from reacting toLet<T>.valueeffects that are called in theasyncCallbackthis class instantiation;
// @ts-check
const letSingle = new Let(1);
const doubleExample = new Derived(async()=>{
const value = letSingle.value; // autoscubscribed to `letSingle` value changes;
return value * 2; // returned value are to be derivedValue
});dataOnly:
const dataOnlyExample = Derived.dataOnly(asyncCallback);
- this will automatically opt you out from
domReflector;- make sure to check
argumentdocumentation in yourIDEtypehint;
type helper for documentScope
use this instead of normal eventListener declaration for:
- creating
autoqueuedlistener; autoScope_static methods, insideComponentscope;
// @ts-check
someObject.addEventListener('click', Event_.listener( (event) => {
// code
}))- assign element to loop through 'List' as data to render child element using class instantiation;
- loped childElement:
- must have
HTMLElementas first children; - only first children will be used to loop through
List, all other children will be deleted from the dom beforeonConnectedevent of parentElement;
- must have
- use
ListInstancemethodhelpers to mutate the data;
signal based reactivity;
assigning newValue to Let insance:
const letSingle = new Let(1, ...args);
letSingle.value++; // 2;
letSingle.value = 3 // 3;dataOnly:
const dataOnlyExample = Let.dataOnly(args0);methods:call$: manually triggerseffectssubscribed tothisInstance;remove$: unubscribethisInstancefrom specificeffect;removeAll$: unubscribethisInstancefrom all of itseffects;
- helper class to track connected/disconnected/attributeChanged of an element;
type helper for lifecycleHandler & attributeChangedLifecycle
- helper class to create list that satisfy
Array<Record<string, string>>
const listExample = new List([
{key1: "test", ...keys},
{key1: "test3", ...keys},
])- usefull for
loops; - instance method: 'push'|'unshift'|'slice'|'splice'|'swap'|'modify'|'shift', serves as helper to mutate, and notify for
signalforeffects:sliceusessplicein the background, you don't need to manually reindex when using it;
trigger based callback integrated to the internal library queue handler; can be created using class instantiation;
- helper class to create
ShortCutthrough class instantiation; - call
thisInstance.pingto manually trigger action
error handling helper; method(s):
- async;
- sync;
helper class for registering and postMessage to webWorker
const worker = new WorkerMainThread(options);
worker.postMessage(message);helper class to define web worker thread;
new WorkerThread({
onMessage: ({ event, postMessage }) => {
const message = undefined;
// code to handle the message
postMessage(message);
},
});- auto
attributeNameassign forsignalbased reactifity stored in static Method of class_; - if you use our
Componentclass, use this class static method, instead of their respective class, for generatingattributeNameto watch, which then you can use it'sattrreturned value to mark the element
// on Component scope
onConnected(async()=>{
const data = _.l('test');
html`<div ${data.attr}="innerText"></div>`
})1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago
1 year ago