open-index/open-npm huggingface dataset:
npm package: @nepse-toolkit/analysis
Description: Technical indicators, screening strategies, and backtesting for NEPSE
Latest version: 0.2.5

# @nepse-toolkit/analysis

Technical indicators, screening strategies, valuation helpers, and backtesting utilities for NEPSE.

Part of the [nepse-toolkit](https://github.com/pawanpaudel93/nepse-toolkit) monorepo.

## Overview

- 9 technical indicators (SMA, EMA, RSI, MACD, Bollinger, ATR, VWAP, OBV, Stochastic)
- 7 built-in screening strategies
- Backtesting with optimization, walk-forward validation, and Monte Carlo stress testing
- Portfolio/valuation helpers with NEPSE-oriented assumptions

## Install

```bash
npm install @nepse-toolkit/analysis
```

## Quick Start

```typescript
import {
  analyzeTechnicals,
  runScreen,
  backtest,
  optimizeStrategy,
  monteCarloStressTest,
  walkForwardValidate,
} from "@nepse-toolkit/analysis";

const technicals = analyzeTechnicals(history);

const opportunities = runScreen(
  "oversold_bounce",
  new Map([["NABIL", { quote, history }]])
);

const result = backtest(new Map([["NABIL", history]]), {
  strategy: "momentum_breakout",
  holdingPeriod: 10,
  startCapital: 1_000_000,
  positionSize: 10,
  slippageBps: 10,
  feePercent: 0.4,
  maxConcurrentPositions: 5,
  maxPortfolioExposurePercent: 80,
});

const optimization = optimizeStrategy(
  new Map([["NABIL", history]]),
  {
    strategy: "momentum_breakout",
    startCapital: 1_000_000,
    positionSize: 10,
  },
  {
    holdingPeriods: [8, 10, 12],
    stopLossPercents: [5, 8],
    takeProfitPercents: [12, 20],
    topN: 5,
  }
);

const stress = monteCarloStressTest(
  new Map([["NABIL", history]]),
  {
    strategy: "momentum_breakout",
    holdingPeriod: 10,
    startCapital: 1_000_000,
    positionSize: 10,
    slippageBps: 10,
    feePercent: 0.4,
  },
  {
    simulations: 300,
    confidence: 0.95,
    slippageJitterBps: 5,
    feeJitterPercent: 0.1,
    shockPercent: 8,
    seed: 42,
  }
);

const walkForward = walkForwardValidate(
  new Map([["NABIL", history]]),
  {
    strategy: "momentum_breakout",
    baseConfig: {
      startCapital: 1_000_000,
      positionSize: 10,
    },
    sweep: {
      holdingPeriods: [8, 10, 12],
      stopLossPercents: [5, 8],
      takeProfitPercents: [12, 20],
      topN: 5,
    },
    trainWindow: 160,
    testWindow: 60,
    stepWindow: 60,
    maxFolds: 4,
  }
);
```

## Export Groups

- Indicators: moving averages, oscillators, volatility, volume metrics
- Signals and screeners: predefined NEPSE-oriented trade setups
- Backtesting: engine, optimizer, stress and walk-forward modules
- Valuation and portfolio utilities: intrinsic value, tax and sizing helpers

## Development

```bash
bun --filter @nepse-toolkit/analysis run build
bun --filter @nepse-toolkit/analysis run typecheck
bun --filter @nepse-toolkit/analysis run test
```

## License

MIT
npm package: @nepse-toolkit/cli
Description: CLI for Nepal Stock Exchange — market data, analysis, screening, portfolio tracking
Latest version: 0.2.5

# @nepse-toolkit/cli

CLI for Nepal Stock Exchange market data, analysis, screening, backtesting, and local operations.

Part of the [nepse-toolkit](https://github.com/pawanpaudel93/nepse-toolkit) monorepo.

## Overview

- 22 subcommands
- Supports JSON output via `--json` on command surfaces
- Covers market data, stock analysis, opportunities, portfolio, alerts, sync, and provider telemetry ops

## Install

```bash
npm install -g @nepse-toolkit/cli
```

Run without installing:

```bash
npx @nepse-toolkit/cli market
```

## Quick Start

```bash
nepse market
nepse stock NABIL -a
nepse opportunities
nepse providers
nepse telemetry --hours 24 --top 10
```

## Command Groups

- Market and index: `market`, `holidays`, `breadth`, `market-history`, `reference`, `participants`, `media`, `marcap`, `sectors`
- Stock and screening: `stock`, `screen`, `opportunities`, `compare`, `floorsheet`, `ipo`
- Portfolio ops: `watchlist`, `portfolio`, `alert`
- Strategy and ops: `backtest`, `providers`, `telemetry`, `sync`

## Exact Usage

```bash
nepse market [--sentiment] [--json]
nepse holidays [--year YYYY] [--json]
nepse breadth [--indexId N] [--json]
nepse market-history [--fromDate YYYY-MM-DD] [--toDate YYYY-MM-DD] [--page N] [--size N] [--json]
nepse reference [--resource <name>] [--page N] [--size N] [--detailId N] [--debentureType TYPE] [--json]
nepse participants [--type member|dealer] [--page N] [--size N] [--json]
nepse media [--type press-release|company-news|investor-awareness|companies-disclosure] [--page N] [--size N] [--json]
nepse marcap [--fromDate YYYY-MM-DD] [--toDate YYYY-MM-DD] [--page N] [--size N] [--json]
nepse stock <SYMBOL> [-a|--analysis] [-h|--history] [--news] [--metadata] [--disclosures] [--fromDate YYYY-MM-DD] [--toDate YYYY-MM-DD] [--page N] [--size N] [--json]
nepse screen [-s|--sector <sector>] [-v|--minVolume <n>] [--gainers] [--losers] [-n|--limit <n>] [--json]
nepse opportunities [-s|--strategy <strategy>] [-n|--limit <n>] [--json]
nepse compare <SYMBOL> [SYMBOL ...] [--json]
nepse floorsheet <SYMBOL> [-d|--date YYYY-MM-DD] [-b|--brokers] [-n|--limit <n>] [--json]
nepse sectors [--json]
nepse watchlist [-n|--name <name>] [-a|--add <symbol>] [-r|--remove <symbol>] [-l|--list] [--json]
nepse portfolio [--add -s <symbol> -q <qty> -p <price> -d <date>] [--remove <id>] [--json]
nepse alert [-s <symbol> --above <price> | -s <symbol> --below <price> | -r <id> | -c] [--json]
nepse backtest [-s|--strategy <name>] [-h|--holding <days>] [-c|--capital <npr>] [-p|--position <percent>] [--slippage <bps>] [--fee <percent>] [--maxPositions <n>] [--maxExposure <percent>] [--symbols <csv>] [--json]
nepse providers [--json]
nepse telemetry [--limitEndpoints N] [--hours N] [--top N] [--json]
nepse sync [--json]
nepse ipo [--fromDate YYYY-MM-DD] [--toDate YYYY-MM-DD] [--page N] [--size N] [--json]
```

## Development

```bash
bun --filter @nepse-toolkit/cli run build
bun --filter @nepse-toolkit/cli run typecheck
bun test packages/cli/tests/
```

## License

MIT
npm package: @nepse-toolkit/core
Description: Core data models, providers, and utilities for Nepal Stock Exchange (NEPSE)
Latest version: 0.2.5

# @nepse-toolkit/core

Core models, provider clients, and utilities that power the NEPSE toolkit.

Part of the [nepse-toolkit](https://github.com/pawanpaudel93/nepse-toolkit) monorepo.

## Overview

- Domain models for market, stock, history, floorsheet, fundamentals, actions, and IPOs
- Provider implementations: NEPSE, MeroLagani, ShareSansar
- Provider failover manager with health tracking and auto-heal
- Payload-schema telemetry capture helpers
- Shared HTTP utilities and Nepali date utilities

## Install

```bash
npm install @nepse-toolkit/core
```

## Quick Start

```typescript
import {
  NepseProvider,
  MeroLaganiProvider,
  ShareSansarProvider,
  ProviderManager,
  NEPSE_TOOLKIT_VERSION,
} from "@nepse-toolkit/core";

const nepse = new NepseProvider();
const quote = await nepse.getStockQuote("NABIL");

const providers = new ProviderManager({
  providers: [
    new NepseProvider(),
    new MeroLaganiProvider(),
    new ShareSansarProvider(),
  ],
});

const stocks = await providers.execute((p) => p.getStockList());
console.log(NEPSE_TOOLKIT_VERSION, quote.symbol, stocks.length);
```

## Provider Notes

- `NepseProvider`: primary official API client with token auth and fallback endpoint logic
- `MeroLaganiProvider`: supplemental live/historical/fundamental/sentiment coverage
- `ShareSansarProvider`: CSRF/session-backed data extraction and fallback feeds
- `ProviderManager`: capability-aware execution with failover

## Development

```bash
bun --filter @nepse-toolkit/core run build
bun --filter @nepse-toolkit/core run typecheck
bun test packages/core/tests/
```

## License

MIT
npm package: @nepse-toolkit/mcp
Description: MCP server for Nepal Stock Exchange — 19 tools + 5 prompts for AI agents
Latest version: 0.2.5

# @nepse-toolkit/mcp

MCP (Model Context Protocol) server for NEPSE toolkit data and analysis workflows.

Part of the [nepse-toolkit](https://github.com/pawanpaudel93/nepse-toolkit) monorepo.

## Overview

- 19 tools for market, stock, providers, portfolio, screening, and backtesting tasks
- 5 reusable prompts for common NEPSE analysis workflows
- Runs over stdio for Claude, Codex, and other MCP clients

## Install

```bash
npm install @nepse-toolkit/mcp
```

## Quick Start

```bash
npx @nepse-toolkit/mcp
```

## Client Setup

### Claude Code

```bash
claude mcp add nepse-toolkit -- npx -y @nepse-toolkit/mcp
```

### Codex CLI

`mcp-config.json`:

```json
{
  "mcpServers": {
    "nepse-toolkit": {
      "command": "npx",
      "args": ["-y", "@nepse-toolkit/mcp"]
    }
  }
}
```

Start Codex with:

```bash
codex --mcp-config mcp-config.json
```

## Tooling Surface

- Tools: 19
- Prompts: 5

For the full tool/prompt catalog and examples, see the root [README](../../README.md).

## Development

```bash
bun --filter @nepse-toolkit/mcp run build
bun --filter @nepse-toolkit/mcp run typecheck
bun test packages/mcp/tests/
```

## License

MIT
npm package: @nepse-toolkit/store
Description: SQLite storage layer for NEPSE toolkit with migrations and WAL mode
Latest version: 0.2.5

# @nepse-toolkit/store

SQLite persistence layer for NEPSE toolkit data and operations.

Part of the [nepse-toolkit](https://github.com/pawanpaudel93/nepse-toolkit) monorepo.

## Overview

- Local-first SQLite database (`better-sqlite3`, WAL mode)
- Auto-applied migrations
- Storage for prices, floorsheet, fundamentals, watchlists, portfolio, and alerts
- Persistent provider payload telemetry history and dashboard aggregation
- Persistent telemetry anomaly sink and ack/silence control state
- Telemetry retention pruning and dead-letter persistence for failed alert deliveries

## Install

```bash
npm install @nepse-toolkit/store
```

## Quick Start

```typescript
import { NepseDatabase } from "@nepse-toolkit/store";

const db = new NepseDatabase();

db.upsertDailyPrices(ohlcvData);
const history = db.getDailyPrices("NABIL", {
  from: "2024-01-01",
  to: "2024-12-31",
});

db.addPosition("NABIL", 100, 850, "2024-06-15");
const positions = db.getPortfolio();

db.insertPayloadTelemetrySnapshots(liveSnapshots);
const dashboard = db.getPayloadTelemetryDashboard({ hours: 24, topEndpoints: 20 });
const pruneResult = db.prunePayloadTelemetryHistory({ retentionDays: 30 });

const sink = db.upsertPayloadTelemetryAlertSink({
  type: "webhook",
  target: "https://alerts.example.com/webhook",
  enabled: true,
});

const control = db.upsertPayloadTelemetryAlertControl({
  provider: "nepse",
  endpoint: "/api/nots/nepse-data/marketdepth/131",
  silencedUntil: new Date(Date.now() + 60_000).toISOString(),
  note: "known noisy endpoint",
});

const deadLetter = db.insertPayloadTelemetryAlertDeadLetter({
  provider: "nepse",
  endpoint: "/api/nots/nepse-data/marketdepth/131",
  sinkType: "webhook",
  sinkTarget: "https://alerts.example.com/webhook",
  payload: { event: { provider: "nepse" } },
  attempts: 3,
  maxAttempts: 3,
  lastError: "HTTP 500 upstream error",
});

const unresolvedDeadLetters = db.listPayloadTelemetryAlertDeadLetters({
  unresolvedOnly: true,
  limit: 50,
});
```

## Runtime Note

`@nepse-toolkit/store` uses `better-sqlite3` (native addon), so use Node.js runtime for this package.

## Development

```bash
bun --filter @nepse-toolkit/store run build
bun --filter @nepse-toolkit/store run typecheck
node --import tsx --test packages/store/tests/database.test.ts
```

## License

MIT
npm package: @neptune3d/dom
Description: Helper classes and functions for the DOM.
Author: Dusan Jovanov
Latest version: 0.0.17

# @neptune3d/dom

Helper classes and functions for fluent DOM manipulation, styling, and event handling.

[![NPM Version](https://img.shields.io/npm/v/%40neptune3d%2Fdom)](https://www.npmjs.com/package/@neptune3d/dom)

## 🚀 Getting Started

Install the package:

```bash
npm install @neptune3d/dom
```

## Usage

```ts
import {
  $window,
  $document,
  $head,
  $body,
  $style,
  $sheet,
  $,
  $btn,
} from "@neptune3d/dom";

const win = $window();
const doc = $document();
const head = $head();
const body = $body();

const style = $style();

head.add(style);

const sheet = $sheet(style);

sheet.cssRule(".shown").display("block");

sheet.cssRule(".hidden").display("none");

const title = $("h1").text("Hello World").fontSize(24).color("blue");

let isToggledVisible = true;

const toggled = $("div").className("shown").text("I am visible");

const button = $btn()
  .text("Click me")
  .on("click", () => {
    isToggledVisible = !isToggledVisible;

    toggled.toggle(isToggledVisible ? "shown" : "hidden");
  });

body.add(title, button, toggled);

const onResize = () => {
  console.log("window has resized");
};

win.on("resize", onResize);

// on cleanup

win.off("resize", onResize);
```

## Features

- Fluent, chainable DOM manipulation.
- Wrapper classes with helper methods for HTML, SVG elements ( including body and head ) as well as document and window.
- Symmetrical styling API for both inline styles and css with chaining.
- Separate class for unique elements like iframe, canvas, form input, select, text area ..etc elements.
- Fully written in Typescript.
npm package: @neptune3d/electron-ipc
Description: Helpers for creating typed IPC APIs to easily send messages between main and renderer processes in Electron.
Author: Dusan Jovanov
Latest version: 0.0.3

# @neptune3d/electron-ipc

Helpers for creating typed IPC APIs to easily send messages between main and renderer processes in Electron.

## ✨ Features

- Strongly typed IPC contracts
- One-way and two-way communication from renderer to main
- One-way event dispatch from main to renderer
- Secure preload exposure via `contextBridge`
- Symmetric API structure for clarity and maintainability

## 📦 Installation

```bash
npm install @neptune3d/electron-ipc
```

## 🚀 Basic Usage

### 1. Define your IPC API

```ts
// ipc-api.ts
import { oneWayAction, twoWayAction } from "@neptune3d/electron-ipc";

export const toMain = {
  logMessage: oneWayAction<string>(),
  fetchData: twoWayAction<{ id: number }, { name: string }>(),
};

export const toRenderer = {
  notify: oneWayAction<string>(),
};
```

### 2. Create the IPC API

```ts
// shared-ipc.ts
import { createIpcApi } from "@neptune3d/electron-ipc";
import { toMain, toRenderer } from "./ipc-api";

export const ipc = createIpcApi({
  ipcKey: "myIpc",
  toMain,
  toRenderer,
});
```

### 3. Preload Setup

```ts
// preload.ts
import { contextBridge, ipcRenderer } from "electron";
import { ipc } from "./shared-ipc";

ipc.preload({ contextBridge, ipcRenderer });
```

### 4. Main Process Setup

```ts
// main.ts
import { ipcMain, BrowserWindow } from "electron";
import { ipc } from "./shared-ipc";

ipc.main.fromRenderer({
  ipcMain,
  handlers: {
    logMessage: (msg) => console.log("Renderer says:", msg),
    fetchData: async ({ id }) => ({ name: `Item ${id}` }),
  },
});

const win = new BrowserWindow({ ... });
const rendererApi = ipc.main.toRenderer({ window: win });
rendererApi.notify("Hello from main!");
```

### 5. Renderer Usage

```ts
// renderer.ts
import { ipc } from "./shared-ipc";

const toMain = ipc.renderer.toMain();
toMain.logMessage("Hello main!");
toMain.fetchData({ id: 42 }).then((result) => {
  console.log("Received:", result);
});

ipc.renderer.fromMain({
  handlers: {
    notify: (msg) => {
      console.log("Main says:", msg);
    },
  },
});
```

## 🧠 Notes

- Two-way actions use `ipcRenderer.invoke()` and `ipcMain.handle()`.
- One-way actions use `ipcRenderer.send()` and `ipcMain.on()` or `webContents.send()`.
npm package: @neptune3d/focus-manager
Description: Accessible, spec-compliant focus state manager
Author: Dusan Jovanov
Latest version: 0.0.3

# @neptune3d/focus-manager

Accessible, spec-compliant focus state manager

[![NPM Version](https://img.shields.io/npm/v/%40neptune3d%2Ffocus-manager)](https://www.npmjs.com/package/@neptune3d/focus-manager)

```bash
npm install @neptune3d/focus-manager
```

## Usage

```ts
import { FocusManager, ListFocusManager } from "@neptune3d/focus-manager";

const focusManager = new FocusManager({
  areas: {
    toolbar: new ListFocusManager({
      getKeys: () => ["back", "forward", "refresh"], // or dynamic
      getOrientation: () => "horizontal",
      getInitialKeyOnAreaFocus: () => "back", // usually the first key, but can be dynamic
      wrapAround: true,
    }),
    tableBody: new ListFocusManager({
      getKeys: () => {
        return table.rowKeys;
      },
      getFirstVisibleIndex: () => {
        return table.firstVisibleIndex; // this needs to be dynamically calculated based on the viewport, scroll offset, and item height(s).
      },
      getLastVisibleIndex: () => {
        return table.lastVisibleIndex; // this needs to be dynamically calculated based on the viewport, scroll offset, and item height(s).
      },
      getOrientation: () => "vertical",
      getInitialKeyOnAreaFocus: () => {
        if (table.hasSelection) {
          return table.selectedKey; // assumes only a single selection is possible
        }
        //
        else {
          return table.rowKeys[0] ?? null;
        }
      },
      wrapAround: true,
    }),
  },
});

// native focus by Tab key

toolbarBackBtn.addEventListener("focus", () => {
  // area + key
  focusManager.focusAreaKey("toolbar", "back", "keyboard");

  // update UI
});

tableBody.addEventListener("focus", () => {
  // just area, key might be set if getInitialKeyOnAreaFocus returns a key.
  focusManager.focusArea("tableBody", "keyboard");

  // update UI
});

// arrow keys

window.addEventListener("keydown", (e) => {
  if (e.code === "ArrowRight") {
    // moves the focus within the current area, if an area is focused.
    focusManager.focusOnArrowRight();

    // update UI
  }
});

// click on button

toolbarBackBtn.addEventListener("pointerdown", () => {
  // unless pointerdown already automatically triggers focus
  focusManager.focusAreaKey("toolbar", "back", "pointer");
});

// restore focus

focusManager.goBack(); // or focusManager.go(-1)

// update UI

tableBody.classList.toggle("focused", focusManager.entry?.key === "tableBody");

// dynamic areas

// for multiple "instances" of the same focus area definition and other dynamic data,
// the meta field can be used

const focusManager = new FocusManager({
  areas: {
    paneTabs: new ListFocusManager<{ pane: Pane }>({
      getKeys: (ctx) => {
        return ctx.meta?.pane.tabKeys ?? [];
      },
      // ...
    }),
  },
});

// meta passed as the last argument and attached to the focus area entry
focusManager.focusAreaKey("paneTabs", tab.id, "keyboard", { pane: myPane });
```
npm package: @neptune3d/icon-font
Description: Library for creating icon fonts with composition.
Author: Dusan Jovanov
Latest version: 0.0.15

# @neptune3d/icon-font

Library for creating icon fonts with composition.

[![NPM Version](https://img.shields.io/npm/v/%40neptune3d%2Ficon-font)](https://www.npmjs.com/package/@neptune3d/icon-font)

```bash
npm install @neptune3d/icon-font
```

> ℹ️ Note: When installing you might get an error like this: `error: install script from "ttf2woff2" exited with 1` - should be fine, if not, just try running install again.

## Example

```ts
import { IconPath, IconGlyph, IconFont } from "@neptune3d/icon-font";

// all of the paths are in a 24x24 design space ( which is the default )

// a filled file path with a dog ear in the top right corner
const textFilePath = new IconPath(24).rect({
  x: 0,
  y: 0,
  width: 24,
  height: 19,
  corners: {
    tr: { kind: "chamfer", rx: 6, ry: 6 },
  },
});

// a template path for a text line - a basic rectangle with sharp corners
const textLinePath = new IconPath().rect({ x: 0, y: 0, width: 15, height: 2 });

// three text line paths merged into one IconPath
// one below the other
const textLinesPath = IconPath.merge([
  textLinePath.clone().translate(4, 8),
  textLinePath.clone().translate(4, 12),
  textLinePath.clone().translate(4, 16),
]).center(0, 0, 24, 19); // centered in the bounding box of the text file path

// create the font
const myIconFont = new IconFont({
  familyName: "myIcons",
  prefix: "mi", // css class prefix
  icons: [
    new IconGlyph({
      name: "text-file",
      unicode: 0xe001, // first unicode in the PUA ( Private Use Area )
      path: IconPath.merge([textFilePath, textLinesPath]).center(),
    }),
  ],
});

// write woff2 and css files
await Promise.all([
  writeFile(`../public/${myIconFont.familyName}.woff2`, myIconFont.toWoff2()),
  writeFile(
    "../src/icons.css",
    myIconFont.toCss(`/${myIconFont.familyName}.woff2`)
  ),
]);

// use the icon
import "./icons.css";

<div class="mi mi-text-file" style="font-size: 24px; color: #fff;"></div>;
```

## Browser support

When using this library in the browser with `vite` ( e.g. for previewing the font in the canvas ), you might get a console error like this:

```
Uncaught sync fetching of the wasm failed: you can preload it to Module["wasmBinary"] manually, or emcc.py will do that for you when generating HTML (but not JS)
```

The error comes from the `ttf2woff2` dependency of this package and you solve it by stubbing out the ttf2woff2 module:

```ts
// create a stub file src/ttf2woff2-stub.js:
export default {};

// and have these fields in the vite config:
import { defineConfig } from "vite";

export default defineConfig({
  resolve: {
    alias: {
      ttf2woff2: "./src/ttf2woff2-stub.js",
    },
  },
  optimizeDeps: {
    force: true,
    include: ["@neptune3d/icon-font"],
  },
});
```

Of course, this means you won't be able to use the `ttf2woff2` features ( `IconFont.toWoff2()` ) in the browser, but you probably don't need it in the browser anyway.
npm package: @neptune3d/path
Description: Library for parsing and manipulating path data.
Author: Dusan Jovanov
Latest version: 0.0.6

# @neptune3d/path

Library for parsing and manipulating path data.

[![NPM Version](https://img.shields.io/npm/v/%40neptune3d%2Fpath)](https://www.npmjs.com/package/@neptune3d/path)

```bash
npm install @neptune3d/path
```
npm package: @neptune3d/pointer-tracker
Description: Lightweight utility for tracking pointer interactions, supporting multi-touch, pointer lock, and gesture composition.
Author: Dusan Jovanov
Latest version: 0.0.4

# @neptune3d/pointer-tracker

A lightweight utility for managing pointer interactions across mouse, touch, and stylus input. Tracks active pointers, abstracts pointer capture, and supports gesture composition for drag, pinch, and pointer lock scenarios.

## 🚀 Installation

```bash
npm install @neptune3d/pointer-tracker
```

## 📦 Basic Usage

```ts
import { PointerTracker } from "@neptune3d/pointer-tracker";

const tracker = new PointerTracker({
  onPointerDown: (e) => {
    console.log("Pointer down:", e.pointerId);
  },
  onActivePointerMove: (e) => {
    console.log("Pointer move:", e.pointerId, e.pageX, e.pageY);
  },
  onPointerEnd: (e) => {
    console.log("Pointer ended:", e.pointerId);
  },
});

tracker.connect(myElement); // Attach to a DOM element
```

## ✨ Features

- Tracks multiple active pointers (`pointerId`, position, button)
- Automatically manages pointer capture and release
- Supports pointer lock (`mousemove` deltas)
- Emits synthetic resume events for multi-touch transitions
- Provides helper methods:
  - `getPointer(id)` – latest position and button
  - `getActivePointers()` – all tracked pointers
  - `getCenter()` – centroid of active pointers
  - `getDistance(a, b)` – distance between two pointers
  - `getNDCPoint(id, element)` – normalized device coordinates

## 🧹 Cleanup

```ts
tracker.disconnect(); // Removes all listeners and clears state
```
npm package: @neptune3d/selection-manager
Description: Accessible, spec-compliant selection state managers
Author: Dusan Jovanov
Latest version: 0.0.2

# @neptune3d/selection-manager

Accessible, spec-compliant selection state managers

[![NPM Version](https://img.shields.io/npm/v/%40neptune3d%2Fselection-manager)](https://www.npmjs.com/package/@neptune3d/selection-manager)

```bash
npm install @neptune3d/selection-manager
```

## Usage

```ts
import { ListSelectionManager } from "@neptune3d/selection-manager";

const selection = new ListSelectionManager({
  getKeys: () => ["a", "b", "c"],
});

window.addEventListener("keydown", (e) => {
  if (e.code === "ArrowDown") {
    // get next focused key
    // const focusedKey = ...

    // or e.metaKey instead of e.ctrlKey if on MacOS
    selection.selectOnKeyboardArrow(focusedKey, e.shiftKey, e.ctrlKey);

    // update selection ( and focus ) UI
  }
  //
  else if (e.code === "PageUp") {
    // get next page jump focused key
    // const focusedKey = ...

    selection.selectOnKeyboardPage(focusedKey, e.shiftKey, e.ctrlKey);

    // update selection ( and focus ) UI
  }
});

// update UI

tableRow.classList.toggle("selected", selection.isKeySelected(tableRow.key));
```
npm package: @neptune3d/virtual-scroll
Description: Math and helpers for implementing a virtual scrollbar.
Author: Dusan Jovanov
Latest version: 0.0.13

# @neptune3d/virtual-scroll

Math and helpers for implementing a virtual scrollbar.

[![NPM Version](https://img.shields.io/npm/v/%40neptune3d%2Fvirtual-scroll)](https://www.npmjs.com/package/@neptune3d/virtual-scroll)

```bash
npm install neptune3d/virtual-scroll
```

## Basic example:

```ts
const scroll = new VirtualScroll({
  getViewportSize: () => 800, // or something like scrollContainer.clientHeight
  getContentSize: () => 1200,
  getTrackSize: () => 800,
  onScroll: () => {
    // thumbOffset is a getter that uses the newest scrollOffset value
    thumb.style.transform = `translateY(${scroll.thumbOffset}px)`;

    // also update the list position etc...
  },
});

const track = document.createElement("div");

track.style.height = 800;
track.style.position = "relative";
// other track styles

// or even better if you can calculate this without reading from the DOM
const trackRect = track.getBoundingClientRect();

track.addEventListener("click", (e) => {
  // updates scrollOffset and calls onScroll
  scroll.handleTrackClick(e.clientY, trackRect.top); 
});

const thumb = document.createElement("div");

thumb.style.position = "absolute";
// other thumb styles

track.append(thumb);
```
npm package: @neptune_payments/neptune-card-elements
Description: The Neptune Card Element is a custom element that allows you to accept payments in your web application. It is a wrapper around the Neptune Payment API.
Author: Neptune Developers
Latest version: 1.0.0

# Neptune Card Element

The Neptune Card Element is a custom element that allows you to accept payments in your web application. It is a wrapper around the Neptune Payment API.

## Custom payment flow

Learn how to embed the Neptune Card Element in your web application and customize the payment flow.

### Step 1: Create a Neptune account

If you don't have a Neptune account, [sign up](https://neptunepayments.com/contact) for one.

### Step 2: Create a Merchant

If you don't have a Merchant, [create one](https://dashboard.neptunepayments.com/) in your Neptune account.

### Step 3: Add Neptune Card Element to your web application

Add Neptune Card Element to your web application by using a package manager.

```bash
npm install neptune-payment-element
```

```bash
yarn add neptune-payment-element
```

### Step 4: Add Neptune Card Element to your react application

Add Neptune Card Element to your react application by importing the Neptune Card Element component.

```js
import NeptunePaymentElement from 'neptune-payment-element';
```

### Step 7: Start using Neptune Card Element

Start using Neptune Card Element by adding the NeptunePaymentElement component to your react application.

```js
const merchantPubKey = <<merchantPubKey>>
const [tokenizer, setTokenizer] = useState<Tokenizer>();

<NeptunePaymentElement merchantPubKey={merchantPubKey} setTokenizer={setTokenizer}/>
```

### Step 8: Customize Neptune Card Element

Customize Neptune Card Element by passing the following props to the NeptunePaymentElement component.

| Prop | Type | Description |
| --- | --- | --- |
| `merchantPubKey` | `string` | The public api key of the Merchant. |
| `setTokenizer` | `function` | The setter for the tokenizer state. |
| `isDevMode` | `boolean` | Defines whether to use sandbox or not. |
| `onSuccess` | `function` | The callback function that is called when the payment is successful. |
| `onError` | `function` | The callback function that is called when the payment is unsuccessful. |
| `settings` | `object` | Addition setup using fluidPay <https://sandbox.fluidpay.com/docs/tokenizer/#paay-integration> |
npm package: @neptunemutual/sdk
Description: Neptune Mutual SDK
Author: Neptune Mutual Team
Latest version: 0.6.1-beta

# Neptune Mutual SDK

The Neptune Mutual SDK assists developers to build on top of Neptune Mutual protocol. The SDK supports any Javascript environment so that you can interact with the SDK from both frontend and backend.

**Install Package**

```
npm install @neptunemutual/sdk
```

**Requirements**

- Node version: >= v18

## Multiple Blockchain Support

Since the SDK supports multiple blockchains, you may want to quickly check the list of supported blockchains before you actually implement anything.

```javascript
import { ChainId } from '@neptunemutual/sdk'

console.info('Supported Chains %s', ChainId)

/********************************************
Supported Chains {
  '1': 'Ethereum',
  '42161': 'Arbitrum',
  '3': 'Ropsten',
  '56': 'BinanceSmartChain',
  '43113': 'Fuji',
  '80001': 'Mumbai',
  Ethereum: 1,
  Arbitrum: 42161,
  Ropsten: 3,
  BinanceSmartChain: 56,
  Fuji: 43113,
  Mumbai: 80001
}
********************************************/
```

## Signer or Provider

The SDK automatically creates a default readonly provider for you. Therefore, you do not need to specify a signer or provider for such operations. However, for write operations, you must pass a signer as the last argument.

**Getting Cover Info by Passing a Provider**

```javascript
import { JsonRpcProvider } from '@ethersproject/providers'
import { Wallet } from '@ethersproject/wallet'
import { ChainId, cover } from '@neptunemutual/sdk'

const myProvider = () => {
  const fakePrivateKey = '0586782a6b30a2526f960bfde45db0470c51919c0ac2ae9ad5ad39b847955109'
  const provider = new JsonRpcProvider('https://rpc-mumbai.maticvigil.com')
  return new Wallet(fakePrivateKey, provider)
}

const readCoverInfo = async () => {
  const key = '0x70726f746f3a636f6e7472616374733a636f7665723a6366633a303100000001'
  const provider = myProvider()

  const coverInfo = await cover.getCoverInfo(ChainId.Mumbai, key, provider)
  console.log(coverInfo)
}

readCoverInfo()
```

In this case, you're only reading from the blockchain. The above code can be simplified to this: 


```javascript
import { ChainId, cover } from '@neptunemutual/sdk'

const readCoverInfo = async () => {
  const key = '0x70726f746f3a636f6e7472616374733a636f7665723a6366633a303100000001'

  const coverInfo = await cover.getCoverInfo(ChainId.Mumbai, key)
  console.log(coverInfo)
}

readCoverInfo()
```

## Initialize

Certain functionality of the SDK depends on store smart contract. Store contract address can be set using the `initialize` function

```js
import sdk, { ChainId } from '@neptunemutual/sdk'

sdk.initialize({
  store: {
    [ChainId.Mumbai]: '0x...'
  }
})

const coverKey = sdk.utils.keyUtil.toBytes32('binance')
const coverInfo = await sdk.cover.getCoverInfo(ChainId.Mumbai, coverKey, provider)

console.log(coverInfo);
```

[Read the Full Documentation](https://neptunemutual.com/docs/sdk/quickstart/)