import { describe, expect, it } from 'vitest';
import {
aberrationShiftAt,
blurKernel,
blurStrengthAt,
pulseEnvelope,
pulseTotal,
shimmerOffsetY
} from '../postSim';
describe('blurStrengthAt', () => {
it('глобальный режим: сила постоянна', () => {
expect(blurStrengthAt(0, 0, 4)).toBe(4);
expect(blurStrengthAt(1000, 0, 4)).toBe(4);
});
it('пик в центре, гладкий спад до нуля на радиусе', () => {
expect(blurStrengthAt(0, 100, 4)).toBe(4);
expect(blurStrengthAt(100, 100, 4)).toBe(0);
expect(blurStrengthAt(150, 100, 4)).toBe(0); // за радиусом — 0
const mid = blurStrengthAt(50, 100, 4);
expect(mid).toBeGreaterThan(0);
expect(mid).toBeLessThan(4);
});
it('спад симметричен и монотонен', () => {
let prev = Infinity;
for (let d = 0; d <= 100; d += 5) {
const v = blurStrengthAt(d, 100, 4);
expect(v).toBeLessThanOrEqual(prev);
prev = v;
}
});
});
describe('blurKernel', () => {
it('смещения в пределах единичного круга и различны', () => {
const k = blurKernel(8);
expect(k.length).toBe(8);
const seen = new Set(k.map(([x, y]) => `${x.toFixed(4)},${y.toFixed(4)}`));
expect(seen.size).toBe(8);
for (const [x, y] of k) {
expect(Math.hypot(x, y)).toBeLessThanOrEqual(1);
}
});
});
describe('aberrationShiftAt', () => {
it('тот же профиль спада, что у блюра', () => {
expect(aberrationShiftAt(0, 100, 2)).toBe(2);
expect(aberrationShiftAt(100, 100, 2)).toBe(0);
expect(aberrationShiftAt(0, 0, 2)).toBe(2); // глобальный режим
});
});
describe('shimmerOffsetY', () => {
it('периодичен по X и по времени', () => {
const p = { amp: 1.5, wavelength: 40, speed: 2 };
expect(shimmerOffsetY(0, 0, p)).toBeCloseTo(0);
expect(shimmerOffsetY(40, 0, p)).toBeCloseTo(0); // период по X = wavelength
expect(shimmerOffsetY(0, 0.5, p)).toBeCloseTo(0); // период по t = 1/speed
expect(Math.abs(shimmerOffsetY(10, 0, p))).toBeCloseTo(p.amp); // четверть волны
});
});
describe('переэкспорт pulseEnvelope', () => {
it('атака/плато/спад сходятся', () => {
const spec = { attack: 0.1, hold: 0.2, decay: 0.3 };
expect(pulseTotal(spec)).toBeCloseTo(0.6);
expect(pulseEnvelope(0.05, spec)).toBeCloseTo(0.5);
expect(pulseEnvelope(0.2, spec)).toBe(1);
expect(pulseEnvelope(0.45, spec)).toBeCloseTo(0.5);
expect(pulseEnvelope(0.7, spec)).toBe(0);
});
});