Huge News!Announcing our $40M Series B led by Abstract Ventures.Learn More
Socket
Sign inDemoInstall
Socket

web-ui-pack

Package Overview
Dependencies
Maintainers
1
Versions
29
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

web-ui-pack

Web package with UI elements

  • 0.0.4
  • Source
  • npm
  • Socket score

Version published
Weekly downloads
112
decreased by-59.42%
Maintainers
1
Weekly downloads
 
Created
Source

logo web-ui-pack

Web package with high scalable WebComponents and helpers

npm version code coverage install size npm downloads License: MIT

Features

  • Possible to use with/without any frameworks like Angular, React, Vue etc. (because it's js-native logic)
  • Focus on accessibility (best practices)
  • High scalable and easy customizable (every component is developed to easy inherit and redefine/extend default logic)
  • Built-in css-variables to use custom color-themes
  • Built-in Typescript (coverage types 100%)
  • Built-in .jsx/.tsx support
  • Well documented via JSDoc (use intellisense power of your editor to get details about each property/option/usage)
  • Optimized for webpack (in build included only in-use components and helpers)
  • Zero dependancy (don't need to wait for bug-fixing of another packages)
  • Always 100% test coverage via e2e and unit tests (it's must-have and always will be so)
  • Focus on performance (it's important to have low-memory consumption)

Installing

Using npm:

npm install web-ui-pack

TODO

  • Basic helpers
  • Helper.Observer
  • PopupElement
  • FormElement, TextControl
  • PasswordControl
  • CheckControl
  • RadioControl
  • ComboControl, DropdownControl
  • Calendar
  • DateControl
  • TimeControl ?
  • DateTimeControl ?
  • ModalElement
  • ConfirmModalElement
  • FormModalElement
  • FileControl
  • ImageControl
  • SearchControl ?
  • TableElement ?

Demo

You can see demo here or just clone repo and run npm i & npm start

Components

Common rules:

  1. Naming
    • All components named as WUP....Element and <wup-...> (for html-tags)
    • Public properties/options/events/methods startsWith $... (events $onShow, $onHide, methods $show, $hide, props like $isOpen etc.)
    • Every component has at least static $defaults (common options for current class) and personal $options (per each component). See details in example
    • $options are observed. So changing options affects on component immediately (every component has static observedOptions as set of watched options)
  2. Usage
    • Since tree-shaking sometimes is not smart enough don't import from web-ui-pack directly. Instead use web-ui-pack/path-to-element or setup sideEffects in package.json (for webpack)
    • Every component has a good JSDoc so go ahead and read details directly during the coding
  3. Limitations
    • In jsx/tsx instead of className use class attribute (React issue)
    • If you change custom attributes it will update $options, but if you change some option it doesn't update related attribute (for performance reasons). Better to avoid customAttributes at all
  4. Inheritance
    • Components are developed to be easy customized and inherrited. Every rule/option/method is developed to be customized if defaultOptions are not enough. You can rewrite everything that you can imagine without digging a lot in a code. To be sure don't hesitate to take a look on *.d.ts or source code (there are enough comments to clarify even weird/difficult cases)
    • All Components inherrited from WUPBaseElement that extends default HTMLElement
    • All internal event-callbacks startsWith got... (gotReady, gotRemoved)
    • To redefine component just extend it and register with new html tag. See details in example
    • Inherritance Tree

PopupElement

WUPPopupElement, <wup-popup />

This is the most smart & crazy element you've ever seen (see Demo)

Typescript

import WUPPopupElement, { ShowCases } from "web-ui-pack/popup/popupElement";

// redefine some defaults; WARN: you can change placement rules here without changing $options per each element!!!
WUPPopupElement.$defaults.offset = [2, 2];
WUPPopupElement.$defaults.minWidthByTarget = true;
WUPPopupElement.$defaults.arrowEnable = true;

// create element
const el = document.createElement("wup-popup");
// WARN el.$options is a observable-clone of WUPPopupElement.$defaults
// WARN: ShowCases is const enum and import ShowCases available only in Typescript
el.$options.showCase = ShowCases.onClick | ShowCases.onFocus; // show popup by target.click and/or target.focus events
el.$options.target = document.querySelector("button");
/*
  Placement can be $top, $right, $bottom, $left (top - above at the target etc.)
  every placement has align options: $start, $middle, $end (left - to align at start of target)
  also you can set $adjust to allow Reduce popup to fit layout
*/
el.$options.placement = [
  WUPPopupElement.$placements.$top.$middle; // place at the top of target and align by vertical line
  WUPPopupElement.$placements.$bottom.$middle.$adjust, // adjust means 'ignore align to fit layout`
  WUPPopupElement.$placements.$bottom.$middle.$adjust.$resizeHeight, // resize means 'allow to resize to fit layout'
]
document.body.append(el);

HTML, JSX, TSX

<button id="btn1">Target</button>
<!-- You can skip pointing attribute 'target' if popup appended after target -->
<wup-popup target="#btn1" placement="top-start">Some content here</wup-popup>

How to extend/override

/// popup.ts

class Popup extends WUPPopupElement {
  // take a look on definition of WUPPopupElement and you will find internals
  protected override canShow(showCase: WUPPopup.ShowCases): boolean {
    if (showCase === WUPPopup.ShowCases.onHover) {
      return false;
    }
    return true;
  }
}

const tagName = "ext-popup";
customElements.define(tagName, Popup);
// That's it. New Popup with custom tag 'ext-popup' is ready

// add for intellisense (for *.ts only)
declare global {
  // add element to document.createElement
  interface HTMLElementTagNameMap {
    [tagName]: Popup;
  }

  // add element for tsx/jsx intellisense
  namespace JSX {
    interface IntrinsicElements {
      [tagName]: IntrinsicElements["wup-popup"];
    }
  }
}

Helpers

use import focusFirst from "web-ui-pack/helpers/focusFirst" etc. WARN: don't use import {focusFirst} from "web-ui-pack; because in this case the whole web-ui-pack module traps in compilation of dev-bundle and increases time of compilation

Helpers.Observer
import observer from "web-ui-pack/helpers/observer";

const rawNestedObj = { val: 1 };
const raw = { date: new Date(), period: 3, nestedObj: rawNestedObj, arr: ["a"] };
const obj = observer.make(raw);
const removeListener = observer.onPropChanged(obj, (e) => console.warn("prop changed", e)); // calls per each changing
const removeListener2 = observer.onChanged(obj, (e) => console.warn("object changed", e)); // calls once after changing of bunch props
obj.period = 5; // fire onPropChanged
obj.date.setHours(0, 0, 0, 0); // fire onPropChanged
obj.nestedObj.val = 2; // fire onPropChanged
obj.arr.push("b"); // fire onPropChanged

obj.nestedObj = rawNestedObj; // fire onPropChanged
obj.nestedObj = rawNestedObj; // WARNING: it fire events again because rawNestedObj !== obj.nestedObj

removeListener(); // unsubscribe
removeListener2(); // unsubscribe

// before timeout will be fired onChanged (single time)
setTimeout(() => {
  console.warn("WARNING: raw vs observable", {
    equal: raw === obj,
    equalByValueOf: raw.valueOf() === obj.valueOf(),
    isRawObserved: observer.isObserved(raw),
    isObjObserved: observer.isObserved(obj),
  });
  // because after assigning to observable it converted to observable also
  console.warn("WARNING: rawNestedObj vs observable", {
    equal: rawNestedObj === obj.nestedObj,
    equalByValueOf: rawNestedObj.valueOf() === obj.nestedObj.valueOf(),
    isRawObserved: observer.isObserved(rawNestedObj),
    isNestedObserved: observer.isObserved(obj.nestedObj),
  });
});
Troubleshooting & Rules
  • Every object assigned to observed is converted to observed also
  • When you change array in most cases you get changing length; also sort/reverse triggers events
  • WeakMap, WeakSet, HTMLElement are not supported (not observed)
  • All objects compares by valueOf() so you maybe interested in custom valueOf to avoid unexpected issues

Keywords

FAQs

Package last updated on 01 Apr 2022

Did you know?

Socket

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Install

Related posts

SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc