dipping-charts 0.1.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +216 -0
- package/dist/__tests__/FullFeaturedChart.test.d.ts +2 -0
- package/dist/__tests__/FullFeaturedChart.test.d.ts.map +1 -0
- package/dist/__tests__/indicators-accuracy.test.d.ts +2 -0
- package/dist/__tests__/indicators-accuracy.test.d.ts.map +1 -0
- package/dist/__tests__/indicators.test.d.ts +2 -0
- package/dist/__tests__/indicators.test.d.ts.map +1 -0
- package/dist/__tests__/setup.d.ts +1 -0
- package/dist/__tests__/setup.d.ts.map +1 -0
- package/dist/__tests__/validateCandle.test.d.ts +2 -0
- package/dist/__tests__/validateCandle.test.d.ts.map +1 -0
- package/dist/chart/index.d.ts +2 -0
- package/dist/chart/index.js +5 -0
- package/dist/chart/index.js.map +1 -0
- package/dist/components/TradingChart.d.ts +24 -0
- package/dist/components/TradingChart.d.ts.map +1 -0
- package/dist/components/TradingChart.js +100 -0
- package/dist/components/TradingChart.js.map +1 -0
- package/dist/components/index.d.ts +3 -0
- package/dist/components/index.d.ts.map +1 -0
- package/dist/dipping-charts.css +1 -0
- package/dist/index.d.ts +5 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +28 -0
- package/dist/index.js.map +1 -0
- package/dist/indicators/atr.d.ts +15 -0
- package/dist/indicators/atr.d.ts.map +1 -0
- package/dist/indicators/atr.js +30 -0
- package/dist/indicators/atr.js.map +1 -0
- package/dist/indicators/bollingerBands.d.ts +11 -0
- package/dist/indicators/bollingerBands.d.ts.map +1 -0
- package/dist/indicators/bollingerBands.js +39 -0
- package/dist/indicators/bollingerBands.js.map +1 -0
- package/dist/indicators/currencyStrength.d.ts +43 -0
- package/dist/indicators/currencyStrength.d.ts.map +1 -0
- package/dist/indicators/currencyStrength.js +53 -0
- package/dist/indicators/currencyStrength.js.map +1 -0
- package/dist/indicators/ema.d.ts +11 -0
- package/dist/indicators/ema.d.ts.map +1 -0
- package/dist/indicators/ema.js +24 -0
- package/dist/indicators/ema.js.map +1 -0
- package/dist/indicators/index.d.ts +19 -0
- package/dist/indicators/index.d.ts.map +1 -0
- package/dist/indicators/index.js +23 -0
- package/dist/indicators/index.js.map +1 -0
- package/dist/indicators/macd.d.ts +11 -0
- package/dist/indicators/macd.d.ts.map +1 -0
- package/dist/indicators/macd.js +52 -0
- package/dist/indicators/macd.js.map +1 -0
- package/dist/indicators/rsi.d.ts +11 -0
- package/dist/indicators/rsi.d.ts.map +1 -0
- package/dist/indicators/rsi.js +29 -0
- package/dist/indicators/rsi.js.map +1 -0
- package/dist/indicators/sma.d.ts +13 -0
- package/dist/indicators/sma.d.ts.map +1 -0
- package/dist/indicators/sma.js +22 -0
- package/dist/indicators/sma.js.map +1 -0
- package/dist/indicators/stochastic.d.ts +15 -0
- package/dist/indicators/stochastic.d.ts.map +1 -0
- package/dist/indicators/stochastic.js +34 -0
- package/dist/indicators/stochastic.js.map +1 -0
- package/dist/indicators/types.d.ts +102 -0
- package/dist/indicators/types.d.ts.map +1 -0
- package/dist/indicators/vwap.d.ts +14 -0
- package/dist/indicators/vwap.d.ts.map +1 -0
- package/dist/indicators/vwap.js +17 -0
- package/dist/indicators/vwap.js.map +1 -0
- package/dist/indicators/williamsR.d.ts +17 -0
- package/dist/indicators/williamsR.d.ts.map +1 -0
- package/dist/indicators/williamsR.js +19 -0
- package/dist/indicators/williamsR.js.map +1 -0
- package/dist/react/FullFeaturedChart.d.ts +3 -0
- package/dist/react/FullFeaturedChart.d.ts.map +1 -0
- package/dist/react/FullFeaturedChart.js +640 -0
- package/dist/react/FullFeaturedChart.js.map +1 -0
- package/dist/react/components/IndicatorSettings.d.ts +20 -0
- package/dist/react/components/IndicatorSettings.d.ts.map +1 -0
- package/dist/react/components/IndicatorSettings.js +748 -0
- package/dist/react/components/IndicatorSettings.js.map +1 -0
- package/dist/react/hooks/useChart.d.ts +15 -0
- package/dist/react/hooks/useChart.d.ts.map +1 -0
- package/dist/react/hooks/useChart.js +155 -0
- package/dist/react/hooks/useChart.js.map +1 -0
- package/dist/react/hooks/useIndicators.d.ts +10 -0
- package/dist/react/hooks/useIndicators.d.ts.map +1 -0
- package/dist/react/hooks/useIndicators.js +264 -0
- package/dist/react/hooks/useIndicators.js.map +1 -0
- package/dist/react/hooks/useLineTools.d.ts +26 -0
- package/dist/react/hooks/useLineTools.d.ts.map +1 -0
- package/dist/react/hooks/useLineTools.js +189 -0
- package/dist/react/hooks/useLineTools.js.map +1 -0
- package/dist/react/hooks/useShiftSnap.d.ts +12 -0
- package/dist/react/hooks/useShiftSnap.d.ts.map +1 -0
- package/dist/react/hooks/useShiftSnap.js +54 -0
- package/dist/react/hooks/useShiftSnap.js.map +1 -0
- package/dist/react/index.d.ts +14 -0
- package/dist/react/index.d.ts.map +1 -0
- package/dist/react/index.js +18 -0
- package/dist/react/index.js.map +1 -0
- package/dist/react/loadLightweightCharts.d.ts +18 -0
- package/dist/react/loadLightweightCharts.d.ts.map +1 -0
- package/dist/react/loadLightweightCharts.js +32 -0
- package/dist/react/loadLightweightCharts.js.map +1 -0
- package/dist/react/locale.d.ts +79 -0
- package/dist/react/locale.d.ts.map +1 -0
- package/dist/react/locale.js +158 -0
- package/dist/react/locale.js.map +1 -0
- package/dist/react/types.d.ts +130 -0
- package/dist/react/types.d.ts.map +1 -0
- package/dist/types/index.d.ts +24 -0
- package/dist/types/index.d.ts.map +1 -0
- package/dist/utils/getToolId.d.ts +9 -0
- package/dist/utils/getToolId.d.ts.map +1 -0
- package/dist/utils/getToolId.js +12 -0
- package/dist/utils/getToolId.js.map +1 -0
- package/dist/utils/mockData.d.ts +10 -0
- package/dist/utils/mockData.d.ts.map +1 -0
- package/dist/utils/mockData.js +61 -0
- package/dist/utils/mockData.js.map +1 -0
- package/dist/utils/snapCrosshair.d.ts +25 -0
- package/dist/utils/snapCrosshair.d.ts.map +1 -0
- package/dist/utils/validateCandle.d.ts +30 -0
- package/dist/utils/validateCandle.d.ts.map +1 -0
- package/dist/utils/validateCandle.js +21 -0
- package/dist/utils/validateCandle.js.map +1 -0
- package/examples/css/base.css +209 -0
- package/examples/css/chart.css +282 -0
- package/examples/css/indicators.css +255 -0
- package/examples/index.html +163 -0
- package/examples/js/chart.js +370 -0
- package/examples/js/indicators.js +27 -0
- package/examples/js/main.js +6 -0
- package/examples/js/ui.js +1641 -0
- package/lib/lightweight-charts.standalone.production.js +7 -0
- package/package.json +106 -0
- package/src/react/FullFeaturedChart.css +1007 -0
|
@@ -0,0 +1,43 @@
|
|
|
1
|
+
import { CandleData } from '../types';
|
|
2
|
+
import { IndicatorDataPoint } from './types';
|
|
3
|
+
/**
|
|
4
|
+
* Currency Strength 옵션
|
|
5
|
+
*
|
|
6
|
+
* 참고: 이 지표는 Forex 전용이며, 여러 통화쌍의 데이터가 필요합니다.
|
|
7
|
+
*/
|
|
8
|
+
export interface CurrencyStrengthOptions {
|
|
9
|
+
/** 통화쌍 데이터 맵 (예: { 'EURUSD': [...], 'USDJPY': [...], ... }) */
|
|
10
|
+
pairs: {
|
|
11
|
+
EURUSD?: CandleData[];
|
|
12
|
+
USDJPY?: CandleData[];
|
|
13
|
+
USDCHF?: CandleData[];
|
|
14
|
+
GBPUSD?: CandleData[];
|
|
15
|
+
AUDUSD?: CandleData[];
|
|
16
|
+
USDCAD?: CandleData[];
|
|
17
|
+
NZDUSD?: CandleData[];
|
|
18
|
+
};
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* Currency Strength 결과
|
|
22
|
+
*/
|
|
23
|
+
export interface CurrencyStrengthResult {
|
|
24
|
+
EUR: IndicatorDataPoint[];
|
|
25
|
+
GBP: IndicatorDataPoint[];
|
|
26
|
+
JPY: IndicatorDataPoint[];
|
|
27
|
+
AUD: IndicatorDataPoint[];
|
|
28
|
+
NZD: IndicatorDataPoint[];
|
|
29
|
+
CAD: IndicatorDataPoint[];
|
|
30
|
+
CHF: IndicatorDataPoint[];
|
|
31
|
+
USD: IndicatorDataPoint[];
|
|
32
|
+
}
|
|
33
|
+
/**
|
|
34
|
+
* Currency Strength (통화 강도)
|
|
35
|
+
*
|
|
36
|
+
* 참고: 이 지표는 Forex 거래 전용입니다.
|
|
37
|
+
* 7개의 주요 통화쌍 데이터가 필요합니다: EURUSD, USDJPY, USDCHF, GBPUSD, AUDUSD, USDCAD, NZDUSD
|
|
38
|
+
*
|
|
39
|
+
* @param options - Currency Strength 옵션 (통화쌍 데이터)
|
|
40
|
+
* @returns 각 통화의 강도 지표
|
|
41
|
+
*/
|
|
42
|
+
export declare function calculateCurrencyStrength(options: CurrencyStrengthOptions): CurrencyStrengthResult;
|
|
43
|
+
//# sourceMappingURL=currencyStrength.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"currencyStrength.d.ts","sourceRoot":"","sources":["../../src/indicators/currencyStrength.ts"],"names":[],"mappings":"AAAA;;;;;;;;;;;;;;;;;;;;;;;GAuBG;AAEH,OAAO,EAAE,UAAU,EAAE,MAAM,UAAU,CAAC;AACtC,OAAO,EAAE,kBAAkB,EAAE,MAAM,SAAS,CAAC;AAE7C;;;;GAIG;AACH,MAAM,WAAW,uBAAuB;IACtC,+DAA+D;IAC/D,KAAK,EAAE;QACL,MAAM,CAAC,EAAE,UAAU,EAAE,CAAC;QACtB,MAAM,CAAC,EAAE,UAAU,EAAE,CAAC;QACtB,MAAM,CAAC,EAAE,UAAU,EAAE,CAAC;QACtB,MAAM,CAAC,EAAE,UAAU,EAAE,CAAC;QACtB,MAAM,CAAC,EAAE,UAAU,EAAE,CAAC;QACtB,MAAM,CAAC,EAAE,UAAU,EAAE,CAAC;QACtB,MAAM,CAAC,EAAE,UAAU,EAAE,CAAC;KACvB,CAAC;CACH;AAED;;GAEG;AACH,MAAM,WAAW,sBAAsB;IACrC,GAAG,EAAE,kBAAkB,EAAE,CAAC;IAC1B,GAAG,EAAE,kBAAkB,EAAE,CAAC;IAC1B,GAAG,EAAE,kBAAkB,EAAE,CAAC;IAC1B,GAAG,EAAE,kBAAkB,EAAE,CAAC;IAC1B,GAAG,EAAE,kBAAkB,EAAE,CAAC;IAC1B,GAAG,EAAE,kBAAkB,EAAE,CAAC;IAC1B,GAAG,EAAE,kBAAkB,EAAE,CAAC;IAC1B,GAAG,EAAE,kBAAkB,EAAE,CAAC;CAC3B;AAiCD;;;;;;;;GAQG;AACH,wBAAgB,yBAAyB,CACvC,OAAO,EAAE,uBAAuB,GAC/B,sBAAsB,CA4HxB"}
|
|
@@ -0,0 +1,53 @@
|
|
|
1
|
+
function h(U, e) {
|
|
2
|
+
return (e - U) / ((e + U) / 2) * 1e4;
|
|
3
|
+
}
|
|
4
|
+
function p(U, e, V, c) {
|
|
5
|
+
return h(U * V, e * c);
|
|
6
|
+
}
|
|
7
|
+
function r(U, e, V, c) {
|
|
8
|
+
return h(U / V, e / c);
|
|
9
|
+
}
|
|
10
|
+
function ss(U) {
|
|
11
|
+
const { pairs: e } = U, V = ["EURUSD", "USDJPY", "USDCHF", "GBPUSD", "AUDUSD", "USDCAD", "NZDUSD"];
|
|
12
|
+
for (const s of V)
|
|
13
|
+
if (!e[s] || e[s].length === 0)
|
|
14
|
+
throw new Error(`Missing required currency pair: ${s}`);
|
|
15
|
+
const c = e.EURUSD, l = e.USDJPY, t = e.USDCHF, n = e.GBPUSD, a = e.AUDUSD, u = e.USDCAD, D = e.NZDUSD, k = Math.min(
|
|
16
|
+
c.length,
|
|
17
|
+
l.length,
|
|
18
|
+
t.length,
|
|
19
|
+
n.length,
|
|
20
|
+
a.length,
|
|
21
|
+
u.length,
|
|
22
|
+
D.length
|
|
23
|
+
), d = {
|
|
24
|
+
EUR: [],
|
|
25
|
+
GBP: [],
|
|
26
|
+
JPY: [],
|
|
27
|
+
AUD: [],
|
|
28
|
+
NZD: [],
|
|
29
|
+
CAD: [],
|
|
30
|
+
CHF: [],
|
|
31
|
+
USD: []
|
|
32
|
+
}, o = {
|
|
33
|
+
EUR: 0,
|
|
34
|
+
GBP: 0,
|
|
35
|
+
JPY: 0,
|
|
36
|
+
AUD: 0,
|
|
37
|
+
NZD: 0,
|
|
38
|
+
CAD: 0,
|
|
39
|
+
CHF: 0,
|
|
40
|
+
USD: 0
|
|
41
|
+
};
|
|
42
|
+
for (let s = 1; s < k; s++) {
|
|
43
|
+
const i = h(c[s - 1].close, c[s].close), S = h(n[s - 1].close, n[s].close), C = h(l[s - 1].close, l[s].close), P = h(a[s - 1].close, a[s].close), f = h(D[s - 1].close, D[s].close), A = h(u[s - 1].close, u[s].close), y = h(t[s - 1].close, t[s].close), v = r(c[s].close, c[s - 1].close, n[s].close, n[s - 1].close), E = p(c[s].close, c[s - 1].close, l[s].close, l[s - 1].close), b = r(c[s].close, c[s - 1].close, a[s].close, a[s - 1].close), j = r(c[s].close, c[s - 1].close, D[s].close, D[s - 1].close), z = r(c[s].close, c[s - 1].close, u[s].close, u[s - 1].close), B = p(c[s].close, c[s - 1].close, t[s].close, t[s - 1].close), F = p(n[s].close, n[s - 1].close, l[s].close, l[s - 1].close), G = r(n[s].close, n[s - 1].close, a[s].close, a[s - 1].close), H = r(n[s].close, n[s - 1].close, D[s].close, D[s - 1].close), J = r(n[s].close, n[s - 1].close, u[s].close, u[s - 1].close), N = p(n[s].close, n[s - 1].close, t[s].close, t[s - 1].close), R = r(l[s].close, l[s - 1].close, a[s].close, a[s - 1].close), Y = r(l[s].close, l[s - 1].close, D[s].close, D[s - 1].close), Z = r(l[s].close, l[s - 1].close, u[s].close, u[s - 1].close), m = r(l[s].close, l[s - 1].close, t[s].close, t[s - 1].close), M = r(a[s].close, a[s - 1].close, D[s].close, D[s - 1].close), q = r(a[s].close, a[s - 1].close, u[s].close, u[s - 1].close), w = p(a[s].close, a[s - 1].close, t[s].close, t[s - 1].close), x = r(D[s].close, D[s - 1].close, u[s].close, u[s - 1].close), L = p(D[s].close, D[s - 1].close, t[s].close, t[s - 1].close), $ = p(u[s].close, u[s - 1].close, t[s].close, t[s - 1].close), I = (i + v + E + b + j + z + B) / 7, K = (S - v + F + G + H + J + N) / 7, O = (C - E - F - R - Y - Z - m) / 7, Q = (P - b - G + R - M - q - w) / 7, T = (f - j - H + Y + M - x - L) / 7, W = (A - z - J + Z + q + x - $) / 7, X = (y - B - N + m + w + L + $) / 7, _ = (-i - S + C - P - f + A + y) / 7;
|
|
44
|
+
o.EUR += I, o.GBP += K, o.JPY += O, o.AUD += Q, o.NZD += T, o.CAD += W, o.CHF += X, o.USD += _;
|
|
45
|
+
const g = c[s].time;
|
|
46
|
+
d.EUR.push({ time: g, value: o.EUR }), d.GBP.push({ time: g, value: o.GBP }), d.JPY.push({ time: g, value: o.JPY }), d.AUD.push({ time: g, value: o.AUD }), d.NZD.push({ time: g, value: o.NZD }), d.CAD.push({ time: g, value: o.CAD }), d.CHF.push({ time: g, value: o.CHF }), d.USD.push({ time: g, value: o.USD });
|
|
47
|
+
}
|
|
48
|
+
return d;
|
|
49
|
+
}
|
|
50
|
+
export {
|
|
51
|
+
ss as calculateCurrencyStrength
|
|
52
|
+
};
|
|
53
|
+
//# sourceMappingURL=currencyStrength.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"currencyStrength.js","sources":["../../src/indicators/currencyStrength.ts"],"sourcesContent":["/**\n * ==========================================\n * Currency Strength (통화 강도) - Forex 전용 고급 지표\n * ==========================================\n *\n * 주의:\n * - 이 지표는 FullFeaturedChart에서 사용하지 않습니다.\n * - Forex 거래 전용 고급 지표입니다.\n * - 7개의 주요 통화쌍 데이터가 필요합니다 (EURUSD, USDJPY, USDCHF, GBPUSD, AUDUSD, USDCAD, NZDUSD).\n * - 고급 사용자가 직접 import하여 사용할 수 있도록 제공됩니다.\n *\n * 사용 예시:\n * ```typescript\n * import { calculateCurrencyStrength } from 'dipping-charts/indicators';\n *\n * const result = calculateCurrencyStrength({\n * pairs: {\n * EURUSD: eurusdData,\n * USDJPY: usdjpyData,\n * // ... 나머지 통화쌍\n * }\n * });\n * ```\n */\n\nimport { CandleData } from '../types';\nimport { IndicatorDataPoint } from './types';\n\n/**\n * Currency Strength 옵션\n *\n * 참고: 이 지표는 Forex 전용이며, 여러 통화쌍의 데이터가 필요합니다.\n */\nexport interface CurrencyStrengthOptions {\n /** 통화쌍 데이터 맵 (예: { 'EURUSD': [...], 'USDJPY': [...], ... }) */\n pairs: {\n EURUSD?: CandleData[];\n USDJPY?: CandleData[];\n USDCHF?: CandleData[];\n GBPUSD?: CandleData[];\n AUDUSD?: CandleData[];\n USDCAD?: CandleData[];\n NZDUSD?: CandleData[];\n };\n}\n\n/**\n * Currency Strength 결과\n */\nexport interface CurrencyStrengthResult {\n EUR: IndicatorDataPoint[];\n GBP: IndicatorDataPoint[];\n JPY: IndicatorDataPoint[];\n AUD: IndicatorDataPoint[];\n NZD: IndicatorDataPoint[];\n CAD: IndicatorDataPoint[];\n CHF: IndicatorDataPoint[];\n USD: IndicatorDataPoint[];\n}\n\n/**\n * 가격 변화율 계산\n */\nfunction calculateChange(prevVal: number, currVal: number): number {\n return ((currVal - prevVal) / ((currVal + prevVal) / 2)) * 10000;\n}\n\n/**\n * 곱셈 기반 변화율 계산\n */\nfunction calculateChangeMultiply(\n prevVal1: number,\n currVal1: number,\n prevVal2: number,\n currVal2: number\n): number {\n return calculateChange(prevVal1 * prevVal2, currVal1 * currVal2);\n}\n\n/**\n * 나눗셈 기반 변화율 계산\n */\nfunction calculateChangeDivide(\n prevVal1: number,\n currVal1: number,\n prevVal2: number,\n currVal2: number\n): number {\n return calculateChange(prevVal1 / prevVal2, currVal1 / currVal2);\n}\n\n/**\n * Currency Strength (통화 강도)\n *\n * 참고: 이 지표는 Forex 거래 전용입니다.\n * 7개의 주요 통화쌍 데이터가 필요합니다: EURUSD, USDJPY, USDCHF, GBPUSD, AUDUSD, USDCAD, NZDUSD\n *\n * @param options - Currency Strength 옵션 (통화쌍 데이터)\n * @returns 각 통화의 강도 지표\n */\nexport function calculateCurrencyStrength(\n options: CurrencyStrengthOptions\n): CurrencyStrengthResult {\n const { pairs } = options;\n\n // 필수 통화쌍 체크\n const requiredPairs = ['EURUSD', 'USDJPY', 'USDCHF', 'GBPUSD', 'AUDUSD', 'USDCAD', 'NZDUSD'] as const;\n for (const pair of requiredPairs) {\n if (!pairs[pair] || pairs[pair]!.length === 0) {\n throw new Error(`Missing required currency pair: ${pair}`);\n }\n }\n\n const eurusd = pairs.EURUSD!;\n const usdjpy = pairs.USDJPY!;\n const usdchf = pairs.USDCHF!;\n const gbpusd = pairs.GBPUSD!;\n const audusd = pairs.AUDUSD!;\n const usdcad = pairs.USDCAD!;\n const nzdusd = pairs.NZDUSD!;\n\n // 모든 데이터의 길이가 같은지 확인\n const minLength = Math.min(\n eurusd.length,\n usdjpy.length,\n usdchf.length,\n gbpusd.length,\n audusd.length,\n usdcad.length,\n nzdusd.length\n );\n\n const result: CurrencyStrengthResult = {\n EUR: [],\n GBP: [],\n JPY: [],\n AUD: [],\n NZD: [],\n CAD: [],\n CHF: [],\n USD: [],\n };\n\n // 각 통화의 누적 강도 추적\n const cumulativeStrength = {\n EUR: 0,\n GBP: 0,\n JPY: 0,\n AUD: 0,\n NZD: 0,\n CAD: 0,\n CHF: 0,\n USD: 0,\n };\n\n for (let i = 1; i < minLength; i++) {\n // 직접 거래쌍\n const eurusdVal = calculateChange(eurusd[i - 1].close, eurusd[i].close);\n const gbpusdVal = calculateChange(gbpusd[i - 1].close, gbpusd[i].close);\n const usdjpyVal = calculateChange(usdjpy[i - 1].close, usdjpy[i].close);\n const audusdVal = calculateChange(audusd[i - 1].close, audusd[i].close);\n const nzdusdVal = calculateChange(nzdusd[i - 1].close, nzdusd[i].close);\n const usdcadVal = calculateChange(usdcad[i - 1].close, usdcad[i].close);\n const usdchfVal = calculateChange(usdchf[i - 1].close, usdchf[i].close);\n\n // 파생 거래쌍\n const eurgbpVal = calculateChangeDivide(eurusd[i].close, eurusd[i - 1].close, gbpusd[i].close, gbpusd[i - 1].close);\n const eurjpyVal = calculateChangeMultiply(eurusd[i].close, eurusd[i - 1].close, usdjpy[i].close, usdjpy[i - 1].close);\n const euraudVal = calculateChangeDivide(eurusd[i].close, eurusd[i - 1].close, audusd[i].close, audusd[i - 1].close);\n const eurnzdVal = calculateChangeDivide(eurusd[i].close, eurusd[i - 1].close, nzdusd[i].close, nzdusd[i - 1].close);\n const eurcadVal = calculateChangeDivide(eurusd[i].close, eurusd[i - 1].close, usdcad[i].close, usdcad[i - 1].close);\n const eurchfVal = calculateChangeMultiply(eurusd[i].close, eurusd[i - 1].close, usdchf[i].close, usdchf[i - 1].close);\n\n const gbpjpyVal = calculateChangeMultiply(gbpusd[i].close, gbpusd[i - 1].close, usdjpy[i].close, usdjpy[i - 1].close);\n const gbpaudVal = calculateChangeDivide(gbpusd[i].close, gbpusd[i - 1].close, audusd[i].close, audusd[i - 1].close);\n const gbpnzdVal = calculateChangeDivide(gbpusd[i].close, gbpusd[i - 1].close, nzdusd[i].close, nzdusd[i - 1].close);\n const gbpcadVal = calculateChangeDivide(gbpusd[i].close, gbpusd[i - 1].close, usdcad[i].close, usdcad[i - 1].close);\n const gbpchfVal = calculateChangeMultiply(gbpusd[i].close, gbpusd[i - 1].close, usdchf[i].close, usdchf[i - 1].close);\n\n const jpyaudVal = calculateChangeDivide(usdjpy[i].close, usdjpy[i - 1].close, audusd[i].close, audusd[i - 1].close);\n const jpynzdVal = calculateChangeDivide(usdjpy[i].close, usdjpy[i - 1].close, nzdusd[i].close, nzdusd[i - 1].close);\n const jpycadVal = calculateChangeDivide(usdjpy[i].close, usdjpy[i - 1].close, usdcad[i].close, usdcad[i - 1].close);\n const jpychfVal = calculateChangeDivide(usdjpy[i].close, usdjpy[i - 1].close, usdchf[i].close, usdchf[i - 1].close);\n\n const audnzdVal = calculateChangeDivide(audusd[i].close, audusd[i - 1].close, nzdusd[i].close, nzdusd[i - 1].close);\n const audcadVal = calculateChangeDivide(audusd[i].close, audusd[i - 1].close, usdcad[i].close, usdcad[i - 1].close);\n const audchfVal = calculateChangeMultiply(audusd[i].close, audusd[i - 1].close, usdchf[i].close, usdchf[i - 1].close);\n\n const nzdcadVal = calculateChangeDivide(nzdusd[i].close, nzdusd[i - 1].close, usdcad[i].close, usdcad[i - 1].close);\n const nzdchfVal = calculateChangeMultiply(nzdusd[i].close, nzdusd[i - 1].close, usdchf[i].close, usdchf[i - 1].close);\n\n const cadchfVal = calculateChangeMultiply(usdcad[i].close, usdcad[i - 1].close, usdchf[i].close, usdchf[i - 1].close);\n\n // 각 통화의 평균 강도 계산\n const strengthEUR = (eurusdVal + eurgbpVal + eurjpyVal + euraudVal + eurnzdVal + eurcadVal + eurchfVal) / 7;\n const strengthGBP = (gbpusdVal - eurgbpVal + gbpjpyVal + gbpaudVal + gbpnzdVal + gbpcadVal + gbpchfVal) / 7;\n const strengthJPY = (usdjpyVal - eurjpyVal - gbpjpyVal - jpyaudVal - jpynzdVal - jpycadVal - jpychfVal) / 7;\n const strengthAUD = (audusdVal - euraudVal - gbpaudVal + jpyaudVal - audnzdVal - audcadVal - audchfVal) / 7;\n const strengthNZD = (nzdusdVal - eurnzdVal - gbpnzdVal + jpynzdVal + audnzdVal - nzdcadVal - nzdchfVal) / 7;\n const strengthCAD = (usdcadVal - eurcadVal - gbpcadVal + jpycadVal + audcadVal + nzdcadVal - cadchfVal) / 7;\n const strengthCHF = (usdchfVal - eurchfVal - gbpchfVal + jpychfVal + audchfVal + nzdchfVal + cadchfVal) / 7;\n const strengthUSD = (-eurusdVal - gbpusdVal + usdjpyVal - audusdVal - nzdusdVal + usdcadVal + usdchfVal) / 7;\n\n // 누적\n cumulativeStrength.EUR += strengthEUR;\n cumulativeStrength.GBP += strengthGBP;\n cumulativeStrength.JPY += strengthJPY;\n cumulativeStrength.AUD += strengthAUD;\n cumulativeStrength.NZD += strengthNZD;\n cumulativeStrength.CAD += strengthCAD;\n cumulativeStrength.CHF += strengthCHF;\n cumulativeStrength.USD += strengthUSD;\n\n const time = eurusd[i].time;\n\n result.EUR.push({ time, value: cumulativeStrength.EUR });\n result.GBP.push({ time, value: cumulativeStrength.GBP });\n result.JPY.push({ time, value: cumulativeStrength.JPY });\n result.AUD.push({ time, value: cumulativeStrength.AUD });\n result.NZD.push({ time, value: cumulativeStrength.NZD });\n result.CAD.push({ time, value: cumulativeStrength.CAD });\n result.CHF.push({ time, value: cumulativeStrength.CHF });\n result.USD.push({ time, value: cumulativeStrength.USD });\n }\n\n return result;\n}\n"],"names":["calculateChange","prevVal","currVal","calculateChangeMultiply","prevVal1","currVal1","prevVal2","currVal2","calculateChangeDivide","calculateCurrencyStrength","options","pairs","requiredPairs","pair","eurusd","usdjpy","usdchf","gbpusd","audusd","usdcad","nzdusd","minLength","result","cumulativeStrength","i","eurusdVal","gbpusdVal","usdjpyVal","audusdVal","nzdusdVal","usdcadVal","usdchfVal","eurgbpVal","eurjpyVal","euraudVal","eurnzdVal","eurcadVal","eurchfVal","gbpjpyVal","gbpaudVal","gbpnzdVal","gbpcadVal","gbpchfVal","jpyaudVal","jpynzdVal","jpycadVal","jpychfVal","audnzdVal","audcadVal","audchfVal","nzdcadVal","nzdchfVal","cadchfVal","strengthEUR","strengthGBP","strengthJPY","strengthAUD","strengthNZD","strengthCAD","strengthCHF","strengthUSD","time"],"mappings":"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"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { CandleData } from '../types';
|
|
2
|
+
import { IndicatorDataPoint, EMAOptions } from './types';
|
|
3
|
+
/**
|
|
4
|
+
* Exponential Moving Average (지수이동평균)
|
|
5
|
+
*
|
|
6
|
+
* @param data - 캔들 데이터 배열
|
|
7
|
+
* @param options - EMA 옵션 (period: 기간, source: 데이터 소스)
|
|
8
|
+
* @returns EMA 계산 결과
|
|
9
|
+
*/
|
|
10
|
+
export declare function calculateEMA(data: CandleData[], options?: EMAOptions): IndicatorDataPoint[];
|
|
11
|
+
//# sourceMappingURL=ema.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ema.d.ts","sourceRoot":"","sources":["../../src/indicators/ema.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,UAAU,CAAC;AACtC,OAAO,EAAE,kBAAkB,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AAEzD;;;;;;GAMG;AACH,wBAAgB,YAAY,CAC1B,IAAI,EAAE,UAAU,EAAE,EAClB,OAAO,GAAE,UAA4C,GACpD,kBAAkB,EAAE,CAiCtB"}
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
function n(l, s = { period: 20, source: "close" }) {
|
|
2
|
+
const { period: t, source: u = "close" } = s, r = [];
|
|
3
|
+
if (l.length < t)
|
|
4
|
+
return r;
|
|
5
|
+
const c = 2 / (t + 1);
|
|
6
|
+
let i = 0;
|
|
7
|
+
for (let e = 0; e < t; e++)
|
|
8
|
+
i += l[e][u];
|
|
9
|
+
let o = i / t;
|
|
10
|
+
r.push({
|
|
11
|
+
time: l[t - 1].time,
|
|
12
|
+
value: o
|
|
13
|
+
});
|
|
14
|
+
for (let e = t; e < l.length; e++)
|
|
15
|
+
o = (l[e][u] - o) * c + o, r.push({
|
|
16
|
+
time: l[e].time,
|
|
17
|
+
value: o
|
|
18
|
+
});
|
|
19
|
+
return r;
|
|
20
|
+
}
|
|
21
|
+
export {
|
|
22
|
+
n as calculateEMA
|
|
23
|
+
};
|
|
24
|
+
//# sourceMappingURL=ema.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"ema.js","sources":["../../src/indicators/ema.ts"],"sourcesContent":["import { CandleData } from '../types';\nimport { IndicatorDataPoint, EMAOptions } from './types';\n\n/**\n * Exponential Moving Average (지수이동평균)\n *\n * @param data - 캔들 데이터 배열\n * @param options - EMA 옵션 (period: 기간, source: 데이터 소스)\n * @returns EMA 계산 결과\n */\nexport function calculateEMA(\n data: CandleData[],\n options: EMAOptions = { period: 20, source: 'close' }\n): IndicatorDataPoint[] {\n const { period, source = 'close' } = options;\n const result: IndicatorDataPoint[] = [];\n\n if (data.length < period) {\n return result;\n }\n\n // 평활 계수 (smoothing factor)\n const multiplier = 2 / (period + 1);\n\n // 첫 EMA는 SMA로 시작\n let sum = 0;\n for (let i = 0; i < period; i++) {\n sum += data[i][source];\n }\n let ema = sum / period;\n\n result.push({\n time: data[period - 1].time,\n value: ema,\n });\n\n // 이후 EMA 계산\n for (let i = period; i < data.length; i++) {\n ema = (data[i][source] - ema) * multiplier + ema;\n result.push({\n time: data[i].time,\n value: ema,\n });\n }\n\n return result;\n}\n"],"names":["calculateEMA","data","options","period","source","result","multiplier","sum","i","ema"],"mappings":"AAUO,SAASA,EACdC,GACAC,IAAsB,EAAE,QAAQ,IAAI,QAAQ,WACtB;AACtB,QAAM,EAAE,QAAAC,GAAQ,QAAAC,IAAS,QAAA,IAAYF,GAC/BG,IAA+B,CAAA;AAErC,MAAIJ,EAAK,SAASE;AAChB,WAAOE;AAIT,QAAMC,IAAa,KAAKH,IAAS;AAGjC,MAAII,IAAM;AACV,WAASC,IAAI,GAAGA,IAAIL,GAAQK;AAC1B,IAAAD,KAAON,EAAKO,CAAC,EAAEJ,CAAM;AAEvB,MAAIK,IAAMF,IAAMJ;AAEhB,EAAAE,EAAO,KAAK;AAAA,IACV,MAAMJ,EAAKE,IAAS,CAAC,EAAE;AAAA,IACvB,OAAOM;AAAA,EAAA,CACR;AAGD,WAASD,IAAIL,GAAQK,IAAIP,EAAK,QAAQO;AACpC,IAAAC,KAAOR,EAAKO,CAAC,EAAEJ,CAAM,IAAIK,KAAOH,IAAaG,GAC7CJ,EAAO,KAAK;AAAA,MACV,MAAMJ,EAAKO,CAAC,EAAE;AAAA,MACd,OAAOC;AAAA,IAAA,CACR;AAGH,SAAOJ;AACT;"}
|
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Technical Indicators for Tradingview-lib
|
|
3
|
+
*
|
|
4
|
+
* 이 모듈은 다양한 기술적 지표 계산 함수를 제공합니다.
|
|
5
|
+
* tradingview-lightweight-charts와 함께 사용할 수 있습니다.
|
|
6
|
+
*/
|
|
7
|
+
export * from './types';
|
|
8
|
+
export { calculateSMA } from './sma';
|
|
9
|
+
export { calculateEMA } from './ema';
|
|
10
|
+
export { calculateRSI } from './rsi';
|
|
11
|
+
export { calculateMACD } from './macd';
|
|
12
|
+
export { calculateBollingerBands } from './bollingerBands';
|
|
13
|
+
export { calculateATR } from './atr';
|
|
14
|
+
export { calculateStochastic } from './stochastic';
|
|
15
|
+
export { calculateWilliamsR } from './williamsR';
|
|
16
|
+
export { calculateVWAP } from './vwap';
|
|
17
|
+
export { calculateCurrencyStrength } from './currencyStrength';
|
|
18
|
+
export type { CurrencyStrengthOptions, CurrencyStrengthResult } from './currencyStrength';
|
|
19
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/indicators/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAGH,cAAc,SAAS,CAAC;AAGxB,OAAO,EAAE,YAAY,EAAE,MAAM,OAAO,CAAC;AACrC,OAAO,EAAE,YAAY,EAAE,MAAM,OAAO,CAAC;AAGrC,OAAO,EAAE,YAAY,EAAE,MAAM,OAAO,CAAC;AACrC,OAAO,EAAE,aAAa,EAAE,MAAM,QAAQ,CAAC;AAGvC,OAAO,EAAE,uBAAuB,EAAE,MAAM,kBAAkB,CAAC;AAC3D,OAAO,EAAE,YAAY,EAAE,MAAM,OAAO,CAAC;AAGrC,OAAO,EAAE,mBAAmB,EAAE,MAAM,cAAc,CAAC;AACnD,OAAO,EAAE,kBAAkB,EAAE,MAAM,aAAa,CAAC;AAGjD,OAAO,EAAE,aAAa,EAAE,MAAM,QAAQ,CAAC;AAGvC,OAAO,EAAE,yBAAyB,EAAE,MAAM,oBAAoB,CAAC;AAC/D,YAAY,EAAE,uBAAuB,EAAE,sBAAsB,EAAE,MAAM,oBAAoB,CAAC"}
|
|
@@ -0,0 +1,23 @@
|
|
|
1
|
+
import { calculateSMA as t } from "./sma.js";
|
|
2
|
+
import { calculateEMA as c } from "./ema.js";
|
|
3
|
+
import { calculateRSI as o } from "./rsi.js";
|
|
4
|
+
import { calculateMACD as u } from "./macd.js";
|
|
5
|
+
import { calculateBollingerBands as p } from "./bollingerBands.js";
|
|
6
|
+
import { calculateATR as A } from "./atr.js";
|
|
7
|
+
import { calculateStochastic as n } from "./stochastic.js";
|
|
8
|
+
import { calculateWilliamsR as s } from "./williamsR.js";
|
|
9
|
+
import { calculateVWAP as R } from "./vwap.js";
|
|
10
|
+
import { calculateCurrencyStrength as h } from "./currencyStrength.js";
|
|
11
|
+
export {
|
|
12
|
+
A as calculateATR,
|
|
13
|
+
p as calculateBollingerBands,
|
|
14
|
+
h as calculateCurrencyStrength,
|
|
15
|
+
c as calculateEMA,
|
|
16
|
+
u as calculateMACD,
|
|
17
|
+
o as calculateRSI,
|
|
18
|
+
t as calculateSMA,
|
|
19
|
+
n as calculateStochastic,
|
|
20
|
+
R as calculateVWAP,
|
|
21
|
+
s as calculateWilliamsR
|
|
22
|
+
};
|
|
23
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sources":[],"sourcesContent":[],"names":[],"mappings":";;;;;;;;;;"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { CandleData } from '../types';
|
|
2
|
+
import { MACDOptions, MACDResult } from './types';
|
|
3
|
+
/**
|
|
4
|
+
* Moving Average Convergence Divergence (이동평균수렴확산)
|
|
5
|
+
*
|
|
6
|
+
* @param data - 캔들 데이터 배열
|
|
7
|
+
* @param options - MACD 옵션
|
|
8
|
+
* @returns MACD 계산 결과 (macd, signal, histogram)
|
|
9
|
+
*/
|
|
10
|
+
export declare function calculateMACD(data: CandleData[], options?: MACDOptions): MACDResult;
|
|
11
|
+
//# sourceMappingURL=macd.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"macd.d.ts","sourceRoot":"","sources":["../../src/indicators/macd.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,UAAU,CAAC;AACtC,OAAO,EAAE,WAAW,EAAE,UAAU,EAAsB,MAAM,SAAS,CAAC;AA+BtE;;;;;;GAMG;AACH,wBAAgB,aAAa,CAC3B,IAAI,EAAE,UAAU,EAAE,EAClB,OAAO,GAAE,WAKR,GACA,UAAU,CAwDZ"}
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
function h(s, l) {
|
|
2
|
+
const n = [];
|
|
3
|
+
if (s.length < l)
|
|
4
|
+
return n;
|
|
5
|
+
const i = 2 / (l + 1);
|
|
6
|
+
let c = 0;
|
|
7
|
+
for (let e = 0; e < l; e++)
|
|
8
|
+
c += s[e];
|
|
9
|
+
let o = c / l;
|
|
10
|
+
n.push(o);
|
|
11
|
+
for (let e = l; e < s.length; e++)
|
|
12
|
+
o = (s[e] - o) * i + o, n.push(o);
|
|
13
|
+
return n;
|
|
14
|
+
}
|
|
15
|
+
function M(s, l = {
|
|
16
|
+
fastPeriod: 12,
|
|
17
|
+
slowPeriod: 26,
|
|
18
|
+
signalPeriod: 9,
|
|
19
|
+
source: "close"
|
|
20
|
+
}) {
|
|
21
|
+
const { fastPeriod: n, slowPeriod: i, signalPeriod: c, source: o = "close" } = l, e = [], a = [], r = [];
|
|
22
|
+
if (s.length < i)
|
|
23
|
+
return { macd: e, signal: a, histogram: r };
|
|
24
|
+
const f = s.map((t) => t[o]), P = h(f, n), V = h(f, i), m = [], g = i - 1;
|
|
25
|
+
for (let t = 0; t < V.length; t++) {
|
|
26
|
+
const u = P[t + (n - i)] - V[t];
|
|
27
|
+
m.push(u), e.push({
|
|
28
|
+
time: s[g + t].time,
|
|
29
|
+
value: u
|
|
30
|
+
});
|
|
31
|
+
}
|
|
32
|
+
const d = h(m, c);
|
|
33
|
+
for (let t = 0; t < d.length; t++) {
|
|
34
|
+
const u = d[t], p = m[t + (c - 1)] - u;
|
|
35
|
+
a.push({
|
|
36
|
+
time: s[g + t + (c - 1)].time,
|
|
37
|
+
value: u
|
|
38
|
+
}), r.push({
|
|
39
|
+
time: s[g + t + (c - 1)].time,
|
|
40
|
+
value: p
|
|
41
|
+
});
|
|
42
|
+
}
|
|
43
|
+
return {
|
|
44
|
+
macd: e,
|
|
45
|
+
signal: a,
|
|
46
|
+
histogram: r
|
|
47
|
+
};
|
|
48
|
+
}
|
|
49
|
+
export {
|
|
50
|
+
M as calculateMACD
|
|
51
|
+
};
|
|
52
|
+
//# sourceMappingURL=macd.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"macd.js","sources":["../../src/indicators/macd.ts"],"sourcesContent":["import { CandleData } from '../types';\nimport { MACDOptions, MACDResult, IndicatorDataPoint } from './types';\n\n/**\n * EMA 계산 헬퍼 함수\n */\nfunction calculateEMAValues(values: number[], period: number): number[] {\n const result: number[] = [];\n\n if (values.length < period) {\n return result;\n }\n\n const multiplier = 2 / (period + 1);\n\n // 첫 EMA는 SMA로 시작\n let sum = 0;\n for (let i = 0; i < period; i++) {\n sum += values[i];\n }\n let ema = sum / period;\n result.push(ema);\n\n // 이후 EMA 계산\n for (let i = period; i < values.length; i++) {\n ema = (values[i] - ema) * multiplier + ema;\n result.push(ema);\n }\n\n return result;\n}\n\n/**\n * Moving Average Convergence Divergence (이동평균수렴확산)\n *\n * @param data - 캔들 데이터 배열\n * @param options - MACD 옵션\n * @returns MACD 계산 결과 (macd, signal, histogram)\n */\nexport function calculateMACD(\n data: CandleData[],\n options: MACDOptions = {\n fastPeriod: 12,\n slowPeriod: 26,\n signalPeriod: 9,\n source: 'close',\n }\n): MACDResult {\n const { fastPeriod, slowPeriod, signalPeriod, source = 'close' } = options;\n\n const macdLine: IndicatorDataPoint[] = [];\n const signalLine: IndicatorDataPoint[] = [];\n const histogram: IndicatorDataPoint[] = [];\n\n if (data.length < slowPeriod) {\n return { macd: macdLine, signal: signalLine, histogram };\n }\n\n // 소스 데이터 추출\n const sourceValues = data.map(candle => candle[source]);\n\n // Fast EMA와 Slow EMA 계산\n const fastEMA = calculateEMAValues(sourceValues, fastPeriod);\n const slowEMA = calculateEMAValues(sourceValues, slowPeriod);\n\n // MACD Line 계산 (Fast EMA - Slow EMA)\n const macdValues: number[] = [];\n const startIndex = slowPeriod - 1;\n\n for (let i = 0; i < slowEMA.length; i++) {\n const macdValue = fastEMA[i + (fastPeriod - slowPeriod)] - slowEMA[i];\n macdValues.push(macdValue);\n\n macdLine.push({\n time: data[startIndex + i].time,\n value: macdValue,\n });\n }\n\n // Signal Line 계산 (MACD의 EMA)\n const signalValues = calculateEMAValues(macdValues, signalPeriod);\n\n for (let i = 0; i < signalValues.length; i++) {\n const signalValue = signalValues[i];\n const macdValue = macdValues[i + (signalPeriod - 1)];\n const histValue = macdValue - signalValue;\n\n signalLine.push({\n time: data[startIndex + i + (signalPeriod - 1)].time,\n value: signalValue,\n });\n\n histogram.push({\n time: data[startIndex + i + (signalPeriod - 1)].time,\n value: histValue,\n });\n }\n\n return {\n macd: macdLine,\n signal: signalLine,\n histogram,\n };\n}\n"],"names":["calculateEMAValues","values","period","result","multiplier","sum","i","ema","calculateMACD","data","options","fastPeriod","slowPeriod","signalPeriod","source","macdLine","signalLine","histogram","sourceValues","candle","fastEMA","slowEMA","macdValues","startIndex","macdValue","signalValues","signalValue","histValue"],"mappings":"AAMA,SAASA,EAAmBC,GAAkBC,GAA0B;AACtE,QAAMC,IAAmB,CAAA;AAEzB,MAAIF,EAAO,SAASC;AAClB,WAAOC;AAGT,QAAMC,IAAa,KAAKF,IAAS;AAGjC,MAAIG,IAAM;AACV,WAASC,IAAI,GAAGA,IAAIJ,GAAQI;AAC1B,IAAAD,KAAOJ,EAAOK,CAAC;AAEjB,MAAIC,IAAMF,IAAMH;AAChB,EAAAC,EAAO,KAAKI,CAAG;AAGf,WAASD,IAAIJ,GAAQI,IAAIL,EAAO,QAAQK;AACtC,IAAAC,KAAON,EAAOK,CAAC,IAAIC,KAAOH,IAAaG,GACvCJ,EAAO,KAAKI,CAAG;AAGjB,SAAOJ;AACT;AASO,SAASK,EACdC,GACAC,IAAuB;AAAA,EACrB,YAAY;AAAA,EACZ,YAAY;AAAA,EACZ,cAAc;AAAA,EACd,QAAQ;AACV,GACY;AACZ,QAAM,EAAE,YAAAC,GAAY,YAAAC,GAAY,cAAAC,GAAc,QAAAC,IAAS,YAAYJ,GAE7DK,IAAiC,CAAA,GACjCC,IAAmC,CAAA,GACnCC,IAAkC,CAAA;AAExC,MAAIR,EAAK,SAASG;AAChB,WAAO,EAAE,MAAMG,GAAU,QAAQC,GAAY,WAAAC,EAAA;AAI/C,QAAMC,IAAeT,EAAK,IAAI,CAAAU,MAAUA,EAAOL,CAAM,CAAC,GAGhDM,IAAUpB,EAAmBkB,GAAcP,CAAU,GACrDU,IAAUrB,EAAmBkB,GAAcN,CAAU,GAGrDU,IAAuB,CAAA,GACvBC,IAAaX,IAAa;AAEhC,WAASN,IAAI,GAAGA,IAAIe,EAAQ,QAAQf,KAAK;AACvC,UAAMkB,IAAYJ,EAAQd,KAAKK,IAAaC,EAAW,IAAIS,EAAQf,CAAC;AACpE,IAAAgB,EAAW,KAAKE,CAAS,GAEzBT,EAAS,KAAK;AAAA,MACZ,MAAMN,EAAKc,IAAajB,CAAC,EAAE;AAAA,MAC3B,OAAOkB;AAAA,IAAA,CACR;AAAA,EACH;AAGA,QAAMC,IAAezB,EAAmBsB,GAAYT,CAAY;AAEhE,WAASP,IAAI,GAAGA,IAAImB,EAAa,QAAQnB,KAAK;AAC5C,UAAMoB,IAAcD,EAAanB,CAAC,GAE5BqB,IADYL,EAAWhB,KAAKO,IAAe,EAAE,IACrBa;AAE9B,IAAAV,EAAW,KAAK;AAAA,MACd,MAAMP,EAAKc,IAAajB,KAAKO,IAAe,EAAE,EAAE;AAAA,MAChD,OAAOa;AAAA,IAAA,CACR,GAEDT,EAAU,KAAK;AAAA,MACb,MAAMR,EAAKc,IAAajB,KAAKO,IAAe,EAAE,EAAE;AAAA,MAChD,OAAOc;AAAA,IAAA,CACR;AAAA,EACH;AAEA,SAAO;AAAA,IACL,MAAMZ;AAAA,IACN,QAAQC;AAAA,IACR,WAAAC;AAAA,EAAA;AAEJ;"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
import { CandleData } from '../types';
|
|
2
|
+
import { IndicatorDataPoint, RSIOptions } from './types';
|
|
3
|
+
/**
|
|
4
|
+
* Relative Strength Index (상대강도지수)
|
|
5
|
+
*
|
|
6
|
+
* @param data - 캔들 데이터 배열
|
|
7
|
+
* @param options - RSI 옵션 (period: 기간, source: 데이터 소스)
|
|
8
|
+
* @returns RSI 계산 결과
|
|
9
|
+
*/
|
|
10
|
+
export declare function calculateRSI(data: CandleData[], options?: RSIOptions): IndicatorDataPoint[];
|
|
11
|
+
//# sourceMappingURL=rsi.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"rsi.d.ts","sourceRoot":"","sources":["../../src/indicators/rsi.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,UAAU,CAAC;AACtC,OAAO,EAAE,kBAAkB,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AAEzD;;;;;;GAMG;AACH,wBAAgB,YAAY,CAC1B,IAAI,EAAE,UAAU,EAAE,EAClB,OAAO,GAAE,UAA4C,GACpD,kBAAkB,EAAE,CAsDtB"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
function f(l, p = { period: 14, source: "close" }) {
|
|
2
|
+
const { period: s, source: g = "close" } = p, n = [];
|
|
3
|
+
if (l.length < s + 1)
|
|
4
|
+
return n;
|
|
5
|
+
const r = [], c = [];
|
|
6
|
+
for (let e = 1; e < l.length; e++) {
|
|
7
|
+
const i = l[e][g] - l[e - 1][g];
|
|
8
|
+
r.push(i > 0 ? i : 0), c.push(i < 0 ? -i : 0);
|
|
9
|
+
}
|
|
10
|
+
let o = 0, t = 0;
|
|
11
|
+
for (let e = 0; e < s; e++)
|
|
12
|
+
o += r[e], t += c[e];
|
|
13
|
+
o /= s, t /= s;
|
|
14
|
+
let u = t === 0 ? 100 : o / t, h = 100 - 100 / (1 + u);
|
|
15
|
+
n.push({
|
|
16
|
+
time: l[s].time,
|
|
17
|
+
value: h
|
|
18
|
+
});
|
|
19
|
+
for (let e = s; e < r.length; e++)
|
|
20
|
+
o = (o * (s - 1) + r[e]) / s, t = (t * (s - 1) + c[e]) / s, u = t === 0 ? 100 : o / t, h = 100 - 100 / (1 + u), n.push({
|
|
21
|
+
time: l[e + 1].time,
|
|
22
|
+
value: h
|
|
23
|
+
});
|
|
24
|
+
return n;
|
|
25
|
+
}
|
|
26
|
+
export {
|
|
27
|
+
f as calculateRSI
|
|
28
|
+
};
|
|
29
|
+
//# sourceMappingURL=rsi.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"rsi.js","sources":["../../src/indicators/rsi.ts"],"sourcesContent":["import { CandleData } from '../types';\nimport { IndicatorDataPoint, RSIOptions } from './types';\n\n/**\n * Relative Strength Index (상대강도지수)\n *\n * @param data - 캔들 데이터 배열\n * @param options - RSI 옵션 (period: 기간, source: 데이터 소스)\n * @returns RSI 계산 결과\n */\nexport function calculateRSI(\n data: CandleData[],\n options: RSIOptions = { period: 14, source: 'close' }\n): IndicatorDataPoint[] {\n const { period, source = 'close' } = options;\n const result: IndicatorDataPoint[] = [];\n\n if (data.length < period + 1) {\n return result;\n }\n\n const gains: number[] = [];\n const losses: number[] = [];\n\n // 가격 변화 계산\n for (let i = 1; i < data.length; i++) {\n const change = data[i][source] - data[i - 1][source];\n gains.push(change > 0 ? change : 0);\n losses.push(change < 0 ? -change : 0);\n }\n\n // 첫 번째 평균 계산 (SMA)\n let avgGain = 0;\n let avgLoss = 0;\n\n for (let i = 0; i < period; i++) {\n avgGain += gains[i];\n avgLoss += losses[i];\n }\n\n avgGain /= period;\n avgLoss /= period;\n\n // 첫 번째 RSI\n let rs = avgLoss === 0 ? 100 : avgGain / avgLoss;\n let rsi = 100 - 100 / (1 + rs);\n\n result.push({\n time: data[period].time,\n value: rsi,\n });\n\n // 이후 RSI 계산 (EMA 방식)\n for (let i = period; i < gains.length; i++) {\n avgGain = (avgGain * (period - 1) + gains[i]) / period;\n avgLoss = (avgLoss * (period - 1) + losses[i]) / period;\n\n rs = avgLoss === 0 ? 100 : avgGain / avgLoss;\n rsi = 100 - 100 / (1 + rs);\n\n result.push({\n time: data[i + 1].time,\n value: rsi,\n });\n }\n\n return result;\n}\n"],"names":["calculateRSI","data","options","period","source","result","gains","losses","i","change","avgGain","avgLoss","rs","rsi"],"mappings":"AAUO,SAASA,EACdC,GACAC,IAAsB,EAAE,QAAQ,IAAI,QAAQ,WACtB;AACtB,QAAM,EAAE,QAAAC,GAAQ,QAAAC,IAAS,QAAA,IAAYF,GAC/BG,IAA+B,CAAA;AAErC,MAAIJ,EAAK,SAASE,IAAS;AACzB,WAAOE;AAGT,QAAMC,IAAkB,CAAA,GAClBC,IAAmB,CAAA;AAGzB,WAASC,IAAI,GAAGA,IAAIP,EAAK,QAAQO,KAAK;AACpC,UAAMC,IAASR,EAAKO,CAAC,EAAEJ,CAAM,IAAIH,EAAKO,IAAI,CAAC,EAAEJ,CAAM;AACnD,IAAAE,EAAM,KAAKG,IAAS,IAAIA,IAAS,CAAC,GAClCF,EAAO,KAAKE,IAAS,IAAI,CAACA,IAAS,CAAC;AAAA,EACtC;AAGA,MAAIC,IAAU,GACVC,IAAU;AAEd,WAASH,IAAI,GAAGA,IAAIL,GAAQK;AAC1B,IAAAE,KAAWJ,EAAME,CAAC,GAClBG,KAAWJ,EAAOC,CAAC;AAGrB,EAAAE,KAAWP,GACXQ,KAAWR;AAGX,MAAIS,IAAKD,MAAY,IAAI,MAAMD,IAAUC,GACrCE,IAAM,MAAM,OAAO,IAAID;AAE3B,EAAAP,EAAO,KAAK;AAAA,IACV,MAAMJ,EAAKE,CAAM,EAAE;AAAA,IACnB,OAAOU;AAAA,EAAA,CACR;AAGD,WAASL,IAAIL,GAAQK,IAAIF,EAAM,QAAQE;AACrC,IAAAE,KAAWA,KAAWP,IAAS,KAAKG,EAAME,CAAC,KAAKL,GAChDQ,KAAWA,KAAWR,IAAS,KAAKI,EAAOC,CAAC,KAAKL,GAEjDS,IAAKD,MAAY,IAAI,MAAMD,IAAUC,GACrCE,IAAM,MAAM,OAAO,IAAID,IAEvBP,EAAO,KAAK;AAAA,MACV,MAAMJ,EAAKO,IAAI,CAAC,EAAE;AAAA,MAClB,OAAOK;AAAA,IAAA,CACR;AAGH,SAAOR;AACT;"}
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import { CandleData } from '../types';
|
|
2
|
+
import { IndicatorDataPoint, SMAOptions } from './types';
|
|
3
|
+
/**
|
|
4
|
+
* Simple Moving Average (단순이동평균)
|
|
5
|
+
*
|
|
6
|
+
* 슬라이딩 윈도우 방식으로 O(n) 시간 복잡도로 계산합니다.
|
|
7
|
+
*
|
|
8
|
+
* @param data - 캔들 데이터 배열
|
|
9
|
+
* @param options - SMA 옵션 (period: 기간, source: 데이터 소스)
|
|
10
|
+
* @returns SMA 계산 결과
|
|
11
|
+
*/
|
|
12
|
+
export declare function calculateSMA(data: CandleData[], options?: SMAOptions): IndicatorDataPoint[];
|
|
13
|
+
//# sourceMappingURL=sma.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sma.d.ts","sourceRoot":"","sources":["../../src/indicators/sma.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,UAAU,EAAE,MAAM,UAAU,CAAC;AACtC,OAAO,EAAE,kBAAkB,EAAE,UAAU,EAAE,MAAM,SAAS,CAAC;AAEzD;;;;;;;;GAQG;AACH,wBAAgB,YAAY,CAC1B,IAAI,EAAE,UAAU,EAAE,EAClB,OAAO,GAAE,UAA4C,GACpD,kBAAkB,EAAE,CA8BtB"}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
function s(l, i = { period: 20, source: "close" }) {
|
|
2
|
+
const { period: o, source: t = "close" } = i, r = [];
|
|
3
|
+
if (l.length < o)
|
|
4
|
+
return r;
|
|
5
|
+
let u = 0;
|
|
6
|
+
for (let e = 0; e < o; e++)
|
|
7
|
+
u += l[e][t];
|
|
8
|
+
r.push({
|
|
9
|
+
time: l[o - 1].time,
|
|
10
|
+
value: u / o
|
|
11
|
+
});
|
|
12
|
+
for (let e = o; e < l.length; e++)
|
|
13
|
+
u += l[e][t] - l[e - o][t], r.push({
|
|
14
|
+
time: l[e].time,
|
|
15
|
+
value: u / o
|
|
16
|
+
});
|
|
17
|
+
return r;
|
|
18
|
+
}
|
|
19
|
+
export {
|
|
20
|
+
s as calculateSMA
|
|
21
|
+
};
|
|
22
|
+
//# sourceMappingURL=sma.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"sma.js","sources":["../../src/indicators/sma.ts"],"sourcesContent":["import { CandleData } from '../types';\nimport { IndicatorDataPoint, SMAOptions } from './types';\n\n/**\n * Simple Moving Average (단순이동평균)\n *\n * 슬라이딩 윈도우 방식으로 O(n) 시간 복잡도로 계산합니다.\n *\n * @param data - 캔들 데이터 배열\n * @param options - SMA 옵션 (period: 기간, source: 데이터 소스)\n * @returns SMA 계산 결과\n */\nexport function calculateSMA(\n data: CandleData[],\n options: SMAOptions = { period: 20, source: 'close' }\n): IndicatorDataPoint[] {\n const { period, source = 'close' } = options;\n const result: IndicatorDataPoint[] = [];\n\n if (data.length < period) {\n return result;\n }\n\n // 첫 번째 윈도우의 합 계산\n let sum = 0;\n for (let i = 0; i < period; i++) {\n sum += data[i][source];\n }\n\n result.push({\n time: data[period - 1].time,\n value: sum / period,\n });\n\n // 슬라이딩 윈도우: 새 값 추가, 오래된 값 제거\n for (let i = period; i < data.length; i++) {\n sum += data[i][source] - data[i - period][source];\n\n result.push({\n time: data[i].time,\n value: sum / period,\n });\n }\n\n return result;\n}\n"],"names":["calculateSMA","data","options","period","source","result","sum","i"],"mappings":"AAYO,SAASA,EACdC,GACAC,IAAsB,EAAE,QAAQ,IAAI,QAAQ,WACtB;AACtB,QAAM,EAAE,QAAAC,GAAQ,QAAAC,IAAS,QAAA,IAAYF,GAC/BG,IAA+B,CAAA;AAErC,MAAIJ,EAAK,SAASE;AAChB,WAAOE;AAIT,MAAIC,IAAM;AACV,WAASC,IAAI,GAAGA,IAAIJ,GAAQI;AAC1B,IAAAD,KAAOL,EAAKM,CAAC,EAAEH,CAAM;AAGvB,EAAAC,EAAO,KAAK;AAAA,IACV,MAAMJ,EAAKE,IAAS,CAAC,EAAE;AAAA,IACvB,OAAOG,IAAMH;AAAA,EAAA,CACd;AAGD,WAASI,IAAIJ,GAAQI,IAAIN,EAAK,QAAQM;AACpC,IAAAD,KAAOL,EAAKM,CAAC,EAAEH,CAAM,IAAIH,EAAKM,IAAIJ,CAAM,EAAEC,CAAM,GAEhDC,EAAO,KAAK;AAAA,MACV,MAAMJ,EAAKM,CAAC,EAAE;AAAA,MACd,OAAOD,IAAMH;AAAA,IAAA,CACd;AAGH,SAAOE;AACT;"}
|
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
import { CandleData } from '../types';
|
|
2
|
+
import { StochasticOptions, StochasticResult } from './types';
|
|
3
|
+
/**
|
|
4
|
+
* Stochastic Oscillator
|
|
5
|
+
*
|
|
6
|
+
* 1. Fast %K = (Close - Lowest Low) / (Highest High - Lowest Low) * 100
|
|
7
|
+
* 2. %K = SMA(Fast %K, smooth)
|
|
8
|
+
* 3. %D = SMA(%K, dPeriod)
|
|
9
|
+
*
|
|
10
|
+
* @param candles OHLCV data
|
|
11
|
+
* @param options kPeriod (lookback for high/low), dPeriod (signal smoothing), smooth (%K smoothing)
|
|
12
|
+
* @returns StochasticResult with k and d arrays
|
|
13
|
+
*/
|
|
14
|
+
export declare function calculateStochastic(candles: CandleData[], options?: StochasticOptions): StochasticResult;
|
|
15
|
+
//# sourceMappingURL=stochastic.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"stochastic.d.ts","sourceRoot":"","sources":["../../src/indicators/stochastic.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,UAAU,CAAC;AAC3C,OAAO,KAAK,EAAE,iBAAiB,EAAE,gBAAgB,EAAsB,MAAM,SAAS,CAAC;AAkBvF;;;;;;;;;;GAUG;AACH,wBAAgB,mBAAmB,CACjC,OAAO,EAAE,UAAU,EAAE,EACrB,OAAO,GAAE,iBAA0D,GAClE,gBAAgB,CA0ClB"}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
function k(t, i) {
|
|
2
|
+
const e = [];
|
|
3
|
+
if (t.length < i) return e;
|
|
4
|
+
let s = 0;
|
|
5
|
+
for (let o = 0; o < i; o++) s += t[o];
|
|
6
|
+
e.push(s / i);
|
|
7
|
+
for (let o = i; o < t.length; o++)
|
|
8
|
+
s += t[o] - t[o - i], e.push(s / i);
|
|
9
|
+
return e;
|
|
10
|
+
}
|
|
11
|
+
function y(t, i = { kPeriod: 14, dPeriod: 3, smooth: 3 }) {
|
|
12
|
+
const { kPeriod: e, dPeriod: s, smooth: o } = i, I = { k: [], d: [] };
|
|
13
|
+
if (!t || t.length < e) return I;
|
|
14
|
+
const l = [], f = [];
|
|
15
|
+
for (let n = e - 1; n < t.length; n++) {
|
|
16
|
+
let h = -1 / 0, u = 1 / 0;
|
|
17
|
+
for (let r = n - e + 1; r <= n; r++)
|
|
18
|
+
t[r].high > h && (h = t[r].high), t[r].low < u && (u = t[r].low);
|
|
19
|
+
const g = h - u;
|
|
20
|
+
l.push(g === 0 ? 50 : (t[n].close - u) / g * 100), f.push(t[n].time);
|
|
21
|
+
}
|
|
22
|
+
const c = k(l, o), m = o - 1, P = k(c, s), a = s - 1, p = c.map((n, h) => ({
|
|
23
|
+
time: f[m + h],
|
|
24
|
+
value: n
|
|
25
|
+
})), x = P.map((n, h) => ({
|
|
26
|
+
time: f[m + a + h],
|
|
27
|
+
value: n
|
|
28
|
+
}));
|
|
29
|
+
return { k: p, d: x };
|
|
30
|
+
}
|
|
31
|
+
export {
|
|
32
|
+
y as calculateStochastic
|
|
33
|
+
};
|
|
34
|
+
//# sourceMappingURL=stochastic.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"stochastic.js","sources":["../../src/indicators/stochastic.ts"],"sourcesContent":["import type { CandleData } from '../types';\nimport type { StochasticOptions, StochasticResult, IndicatorDataPoint } from './types';\n\n/**\n * Simple Moving Average helper (internal)\n */\nfunction sma(values: number[], period: number): number[] {\n const result: number[] = [];\n if (values.length < period) return result;\n let sum = 0;\n for (let i = 0; i < period; i++) sum += values[i];\n result.push(sum / period);\n for (let i = period; i < values.length; i++) {\n sum += values[i] - values[i - period];\n result.push(sum / period);\n }\n return result;\n}\n\n/**\n * Stochastic Oscillator\n *\n * 1. Fast %K = (Close - Lowest Low) / (Highest High - Lowest Low) * 100\n * 2. %K = SMA(Fast %K, smooth)\n * 3. %D = SMA(%K, dPeriod)\n *\n * @param candles OHLCV data\n * @param options kPeriod (lookback for high/low), dPeriod (signal smoothing), smooth (%K smoothing)\n * @returns StochasticResult with k and d arrays\n */\nexport function calculateStochastic(\n candles: CandleData[],\n options: StochasticOptions = { kPeriod: 14, dPeriod: 3, smooth: 3 },\n): StochasticResult {\n const { kPeriod, dPeriod, smooth } = options;\n const empty: StochasticResult = { k: [], d: [] };\n\n if (!candles || candles.length < kPeriod) return empty;\n\n // Step 1: Fast %K\n const fastK: number[] = [];\n const fastKTimes: number[] = [];\n for (let i = kPeriod - 1; i < candles.length; i++) {\n let hh = -Infinity;\n let ll = Infinity;\n for (let j = i - kPeriod + 1; j <= i; j++) {\n if (candles[j].high > hh) hh = candles[j].high;\n if (candles[j].low < ll) ll = candles[j].low;\n }\n const range = hh - ll;\n fastK.push(range === 0 ? 50 : ((candles[i].close - ll) / range) * 100);\n fastKTimes.push(candles[i].time);\n }\n\n // Step 2: %K = SMA(Fast %K, smooth)\n const kValues = sma(fastK, smooth);\n const kStartIdx = smooth - 1;\n\n // Step 3: %D = SMA(%K, dPeriod)\n const dValues = sma(kValues, dPeriod);\n const dStartIdx = dPeriod - 1;\n\n // Build %K result\n const kResult: IndicatorDataPoint[] = kValues.map((v, i) => ({\n time: fastKTimes[kStartIdx + i],\n value: v,\n }));\n\n // Build %D result (aligned with %K)\n const dResult: IndicatorDataPoint[] = dValues.map((v, i) => ({\n time: fastKTimes[kStartIdx + dStartIdx + i],\n value: v,\n }));\n\n return { k: kResult, d: dResult };\n}\n"],"names":["sma","values","period","result","sum","i","calculateStochastic","candles","options","kPeriod","dPeriod","smooth","empty","fastK","fastKTimes","hh","ll","j","range","kValues","kStartIdx","dValues","dStartIdx","kResult","v","dResult"],"mappings":"AAMA,SAASA,EAAIC,GAAkBC,GAA0B;AACvD,QAAMC,IAAmB,CAAA;AACzB,MAAIF,EAAO,SAASC,EAAQ,QAAOC;AACnC,MAAIC,IAAM;AACV,WAASC,IAAI,GAAGA,IAAIH,GAAQG,IAAK,CAAAD,KAAOH,EAAOI,CAAC;AAChD,EAAAF,EAAO,KAAKC,IAAMF,CAAM;AACxB,WAASG,IAAIH,GAAQG,IAAIJ,EAAO,QAAQI;AACtC,IAAAD,KAAOH,EAAOI,CAAC,IAAIJ,EAAOI,IAAIH,CAAM,GACpCC,EAAO,KAAKC,IAAMF,CAAM;AAE1B,SAAOC;AACT;AAaO,SAASG,EACdC,GACAC,IAA6B,EAAE,SAAS,IAAI,SAAS,GAAG,QAAQ,KAC9C;AAClB,QAAM,EAAE,SAAAC,GAAS,SAAAC,GAAS,QAAAC,EAAA,IAAWH,GAC/BI,IAA0B,EAAE,GAAG,CAAA,GAAI,GAAG,CAAA,EAAC;AAE7C,MAAI,CAACL,KAAWA,EAAQ,SAASE,EAAS,QAAOG;AAGjD,QAAMC,IAAkB,CAAA,GAClBC,IAAuB,CAAA;AAC7B,WAAST,IAAII,IAAU,GAAGJ,IAAIE,EAAQ,QAAQF,KAAK;AACjD,QAAIU,IAAK,QACLC,IAAK;AACT,aAASC,IAAIZ,IAAII,IAAU,GAAGQ,KAAKZ,GAAGY;AACpC,MAAIV,EAAQU,CAAC,EAAE,OAAOF,MAAIA,IAAKR,EAAQU,CAAC,EAAE,OACtCV,EAAQU,CAAC,EAAE,MAAMD,MAAIA,IAAKT,EAAQU,CAAC,EAAE;AAE3C,UAAMC,IAAQH,IAAKC;AACnB,IAAAH,EAAM,KAAKK,MAAU,IAAI,MAAOX,EAAQF,CAAC,EAAE,QAAQW,KAAME,IAAS,GAAG,GACrEJ,EAAW,KAAKP,EAAQF,CAAC,EAAE,IAAI;AAAA,EACjC;AAGA,QAAMc,IAAUnB,EAAIa,GAAOF,CAAM,GAC3BS,IAAYT,IAAS,GAGrBU,IAAUrB,EAAImB,GAAST,CAAO,GAC9BY,IAAYZ,IAAU,GAGtBa,IAAgCJ,EAAQ,IAAI,CAACK,GAAGnB,OAAO;AAAA,IAC3D,MAAMS,EAAWM,IAAYf,CAAC;AAAA,IAC9B,OAAOmB;AAAA,EAAA,EACP,GAGIC,IAAgCJ,EAAQ,IAAI,CAACG,GAAGnB,OAAO;AAAA,IAC3D,MAAMS,EAAWM,IAAYE,IAAYjB,CAAC;AAAA,IAC1C,OAAOmB;AAAA,EAAA,EACP;AAEF,SAAO,EAAE,GAAGD,GAAS,GAAGE,EAAA;AAC1B;"}
|
|
@@ -0,0 +1,102 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* 지표 결과의 단일 데이터 포인트
|
|
3
|
+
*/
|
|
4
|
+
export interface IndicatorDataPoint {
|
|
5
|
+
time: number;
|
|
6
|
+
value: number;
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* 다중 라인 지표 결과
|
|
10
|
+
*/
|
|
11
|
+
export interface MultiLineIndicatorResult {
|
|
12
|
+
[key: string]: IndicatorDataPoint[];
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* 지표 옵션 기본 인터페이스
|
|
16
|
+
*/
|
|
17
|
+
export interface IndicatorOptions {
|
|
18
|
+
source?: 'open' | 'high' | 'low' | 'close';
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* SMA 옵션
|
|
22
|
+
*/
|
|
23
|
+
export interface SMAOptions extends IndicatorOptions {
|
|
24
|
+
period: number;
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* EMA 옵션
|
|
28
|
+
*/
|
|
29
|
+
export interface EMAOptions extends IndicatorOptions {
|
|
30
|
+
period: number;
|
|
31
|
+
}
|
|
32
|
+
/**
|
|
33
|
+
* RSI 옵션
|
|
34
|
+
*/
|
|
35
|
+
export interface RSIOptions extends IndicatorOptions {
|
|
36
|
+
period: number;
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* MACD 옵션
|
|
40
|
+
*/
|
|
41
|
+
export interface MACDOptions extends IndicatorOptions {
|
|
42
|
+
fastPeriod: number;
|
|
43
|
+
slowPeriod: number;
|
|
44
|
+
signalPeriod: number;
|
|
45
|
+
}
|
|
46
|
+
/**
|
|
47
|
+
* MACD 결과
|
|
48
|
+
*/
|
|
49
|
+
export interface MACDResult {
|
|
50
|
+
macd: IndicatorDataPoint[];
|
|
51
|
+
signal: IndicatorDataPoint[];
|
|
52
|
+
histogram: IndicatorDataPoint[];
|
|
53
|
+
}
|
|
54
|
+
/**
|
|
55
|
+
* Bollinger Bands 옵션
|
|
56
|
+
*/
|
|
57
|
+
export interface BollingerBandsOptions extends IndicatorOptions {
|
|
58
|
+
period: number;
|
|
59
|
+
stdDev: number;
|
|
60
|
+
maType?: 'SMA' | 'EMA';
|
|
61
|
+
}
|
|
62
|
+
/**
|
|
63
|
+
* Bollinger Bands 결과
|
|
64
|
+
*/
|
|
65
|
+
export interface BollingerBandsResult {
|
|
66
|
+
upper: IndicatorDataPoint[];
|
|
67
|
+
middle: IndicatorDataPoint[];
|
|
68
|
+
lower: IndicatorDataPoint[];
|
|
69
|
+
}
|
|
70
|
+
/**
|
|
71
|
+
* Stochastic 옵션
|
|
72
|
+
*/
|
|
73
|
+
export interface StochasticOptions {
|
|
74
|
+
kPeriod: number;
|
|
75
|
+
dPeriod: number;
|
|
76
|
+
smooth: number;
|
|
77
|
+
}
|
|
78
|
+
/**
|
|
79
|
+
* Stochastic 결과
|
|
80
|
+
*/
|
|
81
|
+
export interface StochasticResult {
|
|
82
|
+
k: IndicatorDataPoint[];
|
|
83
|
+
d: IndicatorDataPoint[];
|
|
84
|
+
}
|
|
85
|
+
/**
|
|
86
|
+
* ATR 옵션
|
|
87
|
+
*/
|
|
88
|
+
export interface ATROptions {
|
|
89
|
+
period: number;
|
|
90
|
+
}
|
|
91
|
+
/**
|
|
92
|
+
* VWAP 옵션
|
|
93
|
+
*/
|
|
94
|
+
export interface VWAPOptions {
|
|
95
|
+
}
|
|
96
|
+
/**
|
|
97
|
+
* Williams %R 옵션
|
|
98
|
+
*/
|
|
99
|
+
export interface WilliamsROptions {
|
|
100
|
+
period: number;
|
|
101
|
+
}
|
|
102
|
+
//# sourceMappingURL=types.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../src/indicators/types.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,MAAM,WAAW,kBAAkB;IACjC,IAAI,EAAE,MAAM,CAAC;IACb,KAAK,EAAE,MAAM,CAAC;CACf;AAED;;GAEG;AACH,MAAM,WAAW,wBAAwB;IACvC,CAAC,GAAG,EAAE,MAAM,GAAG,kBAAkB,EAAE,CAAC;CACrC;AAED;;GAEG;AACH,MAAM,WAAW,gBAAgB;IAC/B,MAAM,CAAC,EAAE,MAAM,GAAG,MAAM,GAAG,KAAK,GAAG,OAAO,CAAC;CAC5C;AAED;;GAEG;AACH,MAAM,WAAW,UAAW,SAAQ,gBAAgB;IAClD,MAAM,EAAE,MAAM,CAAC;CAChB;AAED;;GAEG;AACH,MAAM,WAAW,UAAW,SAAQ,gBAAgB;IAClD,MAAM,EAAE,MAAM,CAAC;CAChB;AAED;;GAEG;AACH,MAAM,WAAW,UAAW,SAAQ,gBAAgB;IAClD,MAAM,EAAE,MAAM,CAAC;CAChB;AAED;;GAEG;AACH,MAAM,WAAW,WAAY,SAAQ,gBAAgB;IACnD,UAAU,EAAE,MAAM,CAAC;IACnB,UAAU,EAAE,MAAM,CAAC;IACnB,YAAY,EAAE,MAAM,CAAC;CACtB;AAED;;GAEG;AACH,MAAM,WAAW,UAAU;IACzB,IAAI,EAAE,kBAAkB,EAAE,CAAC;IAC3B,MAAM,EAAE,kBAAkB,EAAE,CAAC;IAC7B,SAAS,EAAE,kBAAkB,EAAE,CAAC;CACjC;AAED;;GAEG;AACH,MAAM,WAAW,qBAAsB,SAAQ,gBAAgB;IAC7D,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,EAAE,MAAM,CAAC;IACf,MAAM,CAAC,EAAE,KAAK,GAAG,KAAK,CAAC;CACxB;AAED;;GAEG;AACH,MAAM,WAAW,oBAAoB;IACnC,KAAK,EAAE,kBAAkB,EAAE,CAAC;IAC5B,MAAM,EAAE,kBAAkB,EAAE,CAAC;IAC7B,KAAK,EAAE,kBAAkB,EAAE,CAAC;CAC7B;AAED;;GAEG;AACH,MAAM,WAAW,iBAAiB;IAChC,OAAO,EAAE,MAAM,CAAC;IAChB,OAAO,EAAE,MAAM,CAAC;IAChB,MAAM,EAAE,MAAM,CAAC;CAChB;AAED;;GAEG;AACH,MAAM,WAAW,gBAAgB;IAC/B,CAAC,EAAE,kBAAkB,EAAE,CAAC;IACxB,CAAC,EAAE,kBAAkB,EAAE,CAAC;CACzB;AAED;;GAEG;AACH,MAAM,WAAW,UAAU;IACzB,MAAM,EAAE,MAAM,CAAC;CAChB;AAED;;GAEG;AACH,MAAM,WAAW,WAAW;CAE3B;AAED;;GAEG;AACH,MAAM,WAAW,gBAAgB;IAC/B,MAAM,EAAE,MAAM,CAAC;CAChB"}
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { CandleData } from '../types';
|
|
2
|
+
import { VWAPOptions, IndicatorDataPoint } from './types';
|
|
3
|
+
/**
|
|
4
|
+
* Volume Weighted Average Price (VWAP)
|
|
5
|
+
*
|
|
6
|
+
* TP = (High + Low + Close) / 3
|
|
7
|
+
* VWAP = Cumulative(TP * Volume) / Cumulative(Volume)
|
|
8
|
+
*
|
|
9
|
+
* @param candles OHLCV data
|
|
10
|
+
* @param _options reserved for future use
|
|
11
|
+
* @returns IndicatorDataPoint[]
|
|
12
|
+
*/
|
|
13
|
+
export declare function calculateVWAP(candles: CandleData[], _options?: VWAPOptions): IndicatorDataPoint[];
|
|
14
|
+
//# sourceMappingURL=vwap.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"vwap.d.ts","sourceRoot":"","sources":["../../src/indicators/vwap.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,UAAU,CAAC;AAC3C,OAAO,KAAK,EAAE,WAAW,EAAE,kBAAkB,EAAE,MAAM,SAAS,CAAC;AAE/D;;;;;;;;;GASG;AACH,wBAAgB,aAAa,CAC3B,OAAO,EAAE,UAAU,EAAE,EACrB,QAAQ,GAAE,WAAgB,GACzB,kBAAkB,EAAE,CAuBtB"}
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
function m(t, h = {}) {
|
|
2
|
+
const u = [];
|
|
3
|
+
if (!t || t.length === 0) return u;
|
|
4
|
+
let i = 0, e = 0;
|
|
5
|
+
for (let o = 0; o < t.length; o++) {
|
|
6
|
+
const r = (t[o].high + t[o].low + t[o].close) / 3, l = t[o].volume;
|
|
7
|
+
i += r * l, e += l, e !== 0 && u.push({
|
|
8
|
+
time: t[o].time,
|
|
9
|
+
value: i / e
|
|
10
|
+
});
|
|
11
|
+
}
|
|
12
|
+
return u;
|
|
13
|
+
}
|
|
14
|
+
export {
|
|
15
|
+
m as calculateVWAP
|
|
16
|
+
};
|
|
17
|
+
//# sourceMappingURL=vwap.js.map
|