Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
/**
|
2026-05-13 04:47:16 +00:00
|
|
|
* Strategy basket persistence — localStorage-backed, multi-symbol.
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
* Exposed as window.StrategyStore. No modules, no deps.
|
|
|
|
|
*
|
2026-05-13 04:47:16 +00:00
|
|
|
* Stored shape (key "optionsPricer:strategy", v2):
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
* {
|
2026-05-13 04:47:16 +00:00
|
|
|
* v: 2,
|
|
|
|
|
* active: "SPY", // currently-shown symbol
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
* updatedAt: "2026-05-13T...Z",
|
2026-05-13 04:47:16 +00:00
|
|
|
* baskets: {
|
|
|
|
|
* "SPY": { spotSnapshot: 738.18, legs: [ ...legs ] },
|
|
|
|
|
* "AAPL": { spotSnapshot: 0, legs: [ ...legs ] }
|
|
|
|
|
* }
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
* }
|
2026-05-13 04:47:16 +00:00
|
|
|
* leg = { id, symbol, expiry:"YYYY-MM-DD", type:"call"|"put", strike, side:"long"|"short",
|
|
|
|
|
* qty, entryPrice, iv, locked:bool, currentMark:number|null }
|
|
|
|
|
*
|
|
|
|
|
* `load()` returns the *active* basket in a flat back-compat shape, plus a
|
|
|
|
|
* `symbols` array of all symbols that currently have legs.
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
*/
|
|
|
|
|
(function () {
|
|
|
|
|
"use strict";
|
|
|
|
|
|
|
|
|
|
const KEY = "optionsPricer:strategy";
|
2026-05-13 04:47:16 +00:00
|
|
|
const VERSION = 2;
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
const MULTIPLIER = 100; // standard equity option contract size
|
|
|
|
|
|
2026-05-13 04:28:21 +00:00
|
|
|
/** Round a price to 2 decimals (kills float artifacts like 15.000000001). */
|
|
|
|
|
function round2(v) {
|
|
|
|
|
const n = Number(v);
|
|
|
|
|
return Number.isFinite(n) ? Math.round(n * 100) / 100 : 0;
|
|
|
|
|
}
|
|
|
|
|
|
2026-05-13 04:47:16 +00:00
|
|
|
function emptyDoc() { return { v: VERSION, active: "", updatedAt: null, baskets: {} }; }
|
|
|
|
|
|
|
|
|
|
function sanitizeLegs(legs) {
|
|
|
|
|
if (!Array.isArray(legs)) return [];
|
|
|
|
|
return legs
|
|
|
|
|
.filter((l) => l && Number.isFinite(Number(l.strike)) && (l.type === "call" || l.type === "put"))
|
|
|
|
|
.map((l) => ({
|
|
|
|
|
...l,
|
|
|
|
|
strike: round2(l.strike),
|
|
|
|
|
entryPrice: round2(l.entryPrice),
|
|
|
|
|
currentMark: typeof l.currentMark === "number" ? round2(l.currentMark) : (l.currentMark ?? null),
|
|
|
|
|
locked: l.locked === true,
|
|
|
|
|
}));
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
}
|
|
|
|
|
|
2026-05-13 04:47:16 +00:00
|
|
|
function loadDoc() {
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
try {
|
|
|
|
|
const raw = localStorage.getItem(KEY);
|
2026-05-13 04:47:16 +00:00
|
|
|
if (!raw) return emptyDoc();
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
const obj = JSON.parse(raw);
|
2026-05-13 04:47:16 +00:00
|
|
|
if (!obj || typeof obj !== "object") return emptyDoc();
|
|
|
|
|
|
|
|
|
|
// migrate v1 (single basket) -> v2
|
|
|
|
|
if (obj.v === 1 && Array.isArray(obj.legs)) {
|
|
|
|
|
const doc = emptyDoc();
|
|
|
|
|
const sym = obj.symbol || "";
|
|
|
|
|
const legs = sanitizeLegs(obj.legs);
|
|
|
|
|
if (sym && legs.length) {
|
|
|
|
|
doc.baskets[sym] = { spotSnapshot: Number(obj.spotSnapshot) || 0, legs };
|
|
|
|
|
doc.active = sym;
|
|
|
|
|
}
|
|
|
|
|
return doc;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (obj.v !== VERSION || !obj.baskets || typeof obj.baskets !== "object") return emptyDoc();
|
|
|
|
|
|
|
|
|
|
const doc = emptyDoc();
|
|
|
|
|
for (const sym of Object.keys(obj.baskets)) {
|
|
|
|
|
const b = obj.baskets[sym] || {};
|
|
|
|
|
const legs = sanitizeLegs(b.legs);
|
|
|
|
|
if (legs.length) doc.baskets[sym] = { spotSnapshot: Number(b.spotSnapshot) || 0, legs };
|
|
|
|
|
}
|
|
|
|
|
doc.active = obj.active && doc.baskets[obj.active] ? obj.active : (Object.keys(doc.baskets)[0] || "");
|
|
|
|
|
doc.updatedAt = obj.updatedAt || null;
|
|
|
|
|
return doc;
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
} catch {
|
2026-05-13 04:47:16 +00:00
|
|
|
return emptyDoc();
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2026-05-13 04:47:16 +00:00
|
|
|
function saveDoc(doc) {
|
|
|
|
|
doc.v = VERSION;
|
|
|
|
|
// drop empty baskets
|
|
|
|
|
for (const sym of Object.keys(doc.baskets)) {
|
|
|
|
|
const b = doc.baskets[sym];
|
|
|
|
|
if (!b || !Array.isArray(b.legs) || b.legs.length === 0) delete doc.baskets[sym];
|
|
|
|
|
}
|
|
|
|
|
if (!doc.baskets[doc.active]) doc.active = Object.keys(doc.baskets)[0] || "";
|
|
|
|
|
doc.updatedAt = new Date().toISOString();
|
|
|
|
|
try { localStorage.setItem(KEY, JSON.stringify(doc)); }
|
|
|
|
|
catch (e) { console.warn("[StrategyStore] save failed:", e); }
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// ---- active-basket view (flat, back-compat) -----------------------------
|
|
|
|
|
function load() {
|
|
|
|
|
const doc = loadDoc();
|
|
|
|
|
const sym = doc.active;
|
|
|
|
|
const b = (sym && doc.baskets[sym]) || { spotSnapshot: 0, legs: [] };
|
|
|
|
|
return {
|
|
|
|
|
v: VERSION,
|
|
|
|
|
symbol: sym || "",
|
|
|
|
|
spotSnapshot: b.spotSnapshot || 0,
|
|
|
|
|
updatedAt: doc.updatedAt,
|
|
|
|
|
legs: (b.legs || []).map((l) => ({ ...l })),
|
|
|
|
|
symbols: Object.keys(doc.baskets),
|
|
|
|
|
};
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/** Write a flat {symbol, spotSnapshot, legs} state back into that symbol's basket. */
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
function save(state) {
|
2026-05-13 04:47:16 +00:00
|
|
|
const doc = loadDoc();
|
|
|
|
|
const sym = state && state.symbol;
|
|
|
|
|
if (sym) {
|
|
|
|
|
const legs = sanitizeLegs(state.legs);
|
|
|
|
|
if (legs.length) {
|
|
|
|
|
doc.baskets[sym] = { spotSnapshot: Number(state.spotSnapshot) || 0, legs };
|
|
|
|
|
doc.active = sym;
|
|
|
|
|
} else {
|
|
|
|
|
delete doc.baskets[sym];
|
|
|
|
|
if (doc.active === sym) doc.active = Object.keys(doc.baskets)[0] || "";
|
|
|
|
|
}
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
}
|
2026-05-13 04:47:16 +00:00
|
|
|
saveDoc(doc);
|
|
|
|
|
return load();
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
}
|
|
|
|
|
|
2026-05-13 04:47:16 +00:00
|
|
|
/** Clear the ACTIVE basket only. */
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
function clear() {
|
2026-05-13 04:47:16 +00:00
|
|
|
const doc = loadDoc();
|
|
|
|
|
if (doc.active) {
|
|
|
|
|
delete doc.baskets[doc.active];
|
|
|
|
|
doc.active = Object.keys(doc.baskets)[0] || "";
|
|
|
|
|
}
|
|
|
|
|
saveDoc(doc);
|
|
|
|
|
return load();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/** Wipe every basket. */
|
|
|
|
|
function clearAll() {
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
try { localStorage.removeItem(KEY); } catch {}
|
2026-05-13 04:47:16 +00:00
|
|
|
return load();
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
function listSymbols() { return Object.keys(loadDoc().baskets); }
|
|
|
|
|
|
|
|
|
|
function setActive(symbol) {
|
|
|
|
|
const doc = loadDoc();
|
|
|
|
|
if (!symbol) return load();
|
|
|
|
|
if (!doc.baskets[symbol]) doc.baskets[symbol] = { spotSnapshot: 0, legs: [] };
|
|
|
|
|
doc.active = symbol;
|
|
|
|
|
saveDoc(doc);
|
|
|
|
|
return load();
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
function addLeg(leg) {
|
|
|
|
|
const strike = Number(leg && leg.strike);
|
|
|
|
|
if (!Number.isFinite(strike) || strike <= 0) {
|
|
|
|
|
console.warn("[StrategyStore] addLeg: invalid strike", leg);
|
2026-05-13 04:47:16 +00:00
|
|
|
return { state: load() };
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
}
|
2026-05-13 04:47:16 +00:00
|
|
|
const doc = loadDoc();
|
|
|
|
|
const sym = leg.symbol || doc.active || "MANUAL";
|
|
|
|
|
if (!doc.baskets[sym]) doc.baskets[sym] = { spotSnapshot: 0, legs: [] };
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
if (typeof leg.spotSnapshot === "number" && leg.spotSnapshot > 0) {
|
2026-05-13 04:47:16 +00:00
|
|
|
doc.baskets[sym].spotSnapshot = leg.spotSnapshot;
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
}
|
2026-05-13 04:47:16 +00:00
|
|
|
doc.baskets[sym].legs.push({
|
|
|
|
|
id: (typeof crypto !== "undefined" && crypto.randomUUID) ? crypto.randomUUID() : "id-" + Date.now() + "-" + Math.random().toString(36).slice(2),
|
|
|
|
|
symbol: sym,
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
expiry: leg.expiry,
|
|
|
|
|
type: leg.type,
|
2026-05-13 04:28:21 +00:00
|
|
|
strike: round2(strike),
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
side: leg.side === "short" ? "short" : "long",
|
|
|
|
|
qty: Math.max(1, Math.round(Number(leg.qty) || 1)),
|
2026-05-13 04:28:21 +00:00
|
|
|
entryPrice: round2(leg.entryPrice),
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
iv: Number(leg.iv) || 0,
|
2026-05-13 04:28:21 +00:00
|
|
|
locked: leg.locked === true,
|
2026-05-13 04:47:16 +00:00
|
|
|
currentMark: typeof leg.currentMark === "number" ? round2(leg.currentMark) : null,
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
});
|
2026-05-13 04:47:16 +00:00
|
|
|
doc.active = sym;
|
|
|
|
|
saveDoc(doc);
|
|
|
|
|
return { state: load() };
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
function basketOf(doc, id) {
|
|
|
|
|
for (const sym of Object.keys(doc.baskets)) {
|
|
|
|
|
if (doc.baskets[sym].legs.some((l) => l.id === id)) return sym;
|
|
|
|
|
}
|
|
|
|
|
return null;
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
function removeLeg(id) {
|
2026-05-13 04:47:16 +00:00
|
|
|
const doc = loadDoc();
|
|
|
|
|
const sym = basketOf(doc, id);
|
|
|
|
|
if (sym) {
|
|
|
|
|
doc.baskets[sym].legs = doc.baskets[sym].legs.filter((l) => l.id !== id);
|
|
|
|
|
if (doc.baskets[sym].legs.length === 0) {
|
|
|
|
|
delete doc.baskets[sym];
|
|
|
|
|
if (doc.active === sym) doc.active = Object.keys(doc.baskets)[0] || "";
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
saveDoc(doc);
|
|
|
|
|
return load();
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
function updateLeg(id, patch) {
|
2026-05-13 04:47:16 +00:00
|
|
|
const doc = loadDoc();
|
|
|
|
|
const sym = basketOf(doc, id);
|
|
|
|
|
if (sym) {
|
|
|
|
|
const leg = doc.baskets[sym].legs.find((l) => l.id === id);
|
|
|
|
|
if (leg) {
|
|
|
|
|
const p = { ...patch };
|
|
|
|
|
if ("entryPrice" in p) p.entryPrice = round2(p.entryPrice);
|
|
|
|
|
if ("currentMark" in p && p.currentMark != null) p.currentMark = round2(p.currentMark);
|
|
|
|
|
if ("strike" in p) p.strike = round2(p.strike);
|
|
|
|
|
Object.assign(leg, p);
|
|
|
|
|
}
|
2026-05-13 04:28:21 +00:00
|
|
|
}
|
2026-05-13 04:47:16 +00:00
|
|
|
saveDoc(doc);
|
|
|
|
|
return load();
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
}
|
|
|
|
|
|
2026-05-13 04:47:16 +00:00
|
|
|
/** multi-basket: adding a different symbol no longer wipes anything. */
|
|
|
|
|
function mismatch() { return null; }
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
|
2026-05-13 04:47:16 +00:00
|
|
|
/** legs in the active basket. */
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
function count() {
|
2026-05-13 04:47:16 +00:00
|
|
|
const doc = loadDoc();
|
|
|
|
|
const b = doc.baskets[doc.active];
|
|
|
|
|
return b ? b.legs.length : 0;
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
window.StrategyStore = {
|
|
|
|
|
KEY, VERSION, MULTIPLIER,
|
2026-05-13 04:47:16 +00:00
|
|
|
empty: () => ({ v: VERSION, symbol: "", spotSnapshot: 0, updatedAt: null, legs: [], symbols: [] }),
|
|
|
|
|
load, save, clear, clearAll, addLeg, removeLeg, updateLeg, mismatch, count, listSymbols, setActive,
|
Add strategy P/L analyzer + view-state persistence
- New strategy.html: thinkorswim-style P/L diagram (expiration + T+N curves
via Black-Scholes, days-to-expiry slider, net debit/credit, max profit/loss
with unbounded detection, breakevens, net Greeks, auto-detected strategy name)
- chain.html: per-row Buy/Sell buttons add legs to a localStorage basket;
basket badge in toolbar; auto-scroll to ATM row on load
- Persist per-page view state (symbol, expiry, loaded data, charts) across
navigation via viewstate-store.js for chain/surface/tracker/dashboard
- New assets: blackscholes.js (frontend BS port), strategy-store.js, viewstate-store.js
- Strategy P/L nav link added to all sidebars
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-13 04:01:57 +00:00
|
|
|
};
|
|
|
|
|
})();
|