feat(dynamics): add PlusDI, MinusDI, PlusDM, MinusDM indicators

Complete thin Dx-composition wrapper indicators with full test coverage:

- PlusDi/MinusDi: Directional Indicator wrappers (DiPlus/DiMinus from Dx)
- PlusDm/MinusDm: Directional Movement wrappers (DmPlus/DmMinus from Dx)
- Individual validation tests per indicator directory (TALib, Skender, bounds)
- Combined unit tests (DiDm.Tests.cs) and validation tests (DiDm.Validation.Tests.cs)
- Quantower wrappers + tests for all 4 indicators
- PineScript v6 implementations with compensated RMA
- Normalized .md documentation for all indicators and categories
- 182 tests passing, 0 failures
This commit is contained in:
Miha Kralj
2026-03-11 20:21:52 -07:00
parent 56b86bebfb
commit 33d20f2a18
437 changed files with 4589 additions and 2792 deletions
+2 -39
View File
@@ -1,5 +1,7 @@
# EBSW: Ehlers Even Better Sinewave
> *Even Better Sinewave refines cycle detection by combining bandpass filtering with adaptive gain normalization.*
| Property | Value |
| ---------------- | -------------------------------- |
| **Category** | Cycle |
@@ -78,45 +80,6 @@ b = 2·a·cos(√2·π / ssfLength)
c₁ = (1 - b + a²) / 2
```
### Pseudo-code
```
function EBSW(source, hpLength, ssfLength):
// Precompute HP coefficient
α₁ ← (1 - sin(2π/hpLength)) / cos(2π/hpLength)
// Precompute SSF coefficients
a ← exp(-√2·π / ssfLength)
b ← 2·a·cos(√2·π / ssfLength)
c₁ ← (1 - b + a²) / 2
hp_prev ← 0; p_prev ← 0
filt_1 ← 0; filt_2 ← 0
for each price in source:
// High-pass filter
hp ← 0.5·(1 + α₁)·(price - p_prev) + α₁·hp_prev
// Super-smoother
filt ← c₁·(hp + hp_prev) + b·filt_1 - a²·filt_2
// Wave (3-bar average of filtered signal)
wave ← (filt + filt_1 + filt_2) / 3
// Power (3-bar RMS²)
power ← (filt² + filt_1² + filt_2²) / 3
// AGC normalization
ebsw ← (power > 0) ? wave / √power : 0
ebsw ← clamp(ebsw, -1, +1)
// Shift state
hp_prev ← hp; p_prev ← price
filt_2 ← filt_1; filt_1 ← filt
emit ebsw
```
### Output Interpretation
| Condition | Meaning |