|
| 1 | +import { mount } from '@vue/test-utils' |
| 2 | +import { describe, expect, it } from 'vitest' |
| 3 | +import { createI18n } from 'vue-i18n' |
| 4 | + |
| 5 | +import RangeEditor from './RangeEditor.vue' |
| 6 | + |
| 7 | +const i18n = createI18n({ legacy: false, locale: 'en', messages: { en: {} } }) |
| 8 | + |
| 9 | +function mountEditor(props: InstanceType<typeof RangeEditor>['$props']) { |
| 10 | + return mount(RangeEditor, { |
| 11 | + props, |
| 12 | + global: { plugins: [i18n] } |
| 13 | + }) |
| 14 | +} |
| 15 | + |
| 16 | +describe('RangeEditor', () => { |
| 17 | + it('renders with min and max handles', () => { |
| 18 | + const wrapper = mountEditor({ modelValue: { min: 0.2, max: 0.8 } }) |
| 19 | + |
| 20 | + expect(wrapper.find('svg').exists()).toBe(true) |
| 21 | + expect(wrapper.find('[data-testid="handle-min"]').exists()).toBe(true) |
| 22 | + expect(wrapper.find('[data-testid="handle-max"]').exists()).toBe(true) |
| 23 | + }) |
| 24 | + |
| 25 | + it('highlights selected range in plain mode', () => { |
| 26 | + const wrapper = mountEditor({ modelValue: { min: 0.2, max: 0.8 } }) |
| 27 | + |
| 28 | + const highlight = wrapper.find('[data-testid="range-highlight"]') |
| 29 | + expect(highlight.attributes('x')).toBe('0.2') |
| 30 | + expect(highlight.attributes('width')).toBe('0.6000000000000001') |
| 31 | + }) |
| 32 | + |
| 33 | + it('dims area outside the range in histogram mode', () => { |
| 34 | + const histogram = new Uint32Array(256) |
| 35 | + for (let i = 0; i < 256; i++) |
| 36 | + histogram[i] = Math.floor(50 + 50 * Math.sin(i / 20)) |
| 37 | + |
| 38 | + const wrapper = mountEditor({ |
| 39 | + modelValue: { min: 0.2, max: 0.8 }, |
| 40 | + display: 'histogram', |
| 41 | + histogram |
| 42 | + }) |
| 43 | + |
| 44 | + const left = wrapper.find('[data-testid="range-dim-left"]') |
| 45 | + const right = wrapper.find('[data-testid="range-dim-right"]') |
| 46 | + expect(left.attributes('width')).toBe('0.2') |
| 47 | + expect(right.attributes('x')).toBe('0.8') |
| 48 | + }) |
| 49 | + |
| 50 | + it('hides midpoint handle by default', () => { |
| 51 | + const wrapper = mountEditor({ |
| 52 | + modelValue: { min: 0, max: 1, midpoint: 0.5 } |
| 53 | + }) |
| 54 | + |
| 55 | + expect(wrapper.find('[data-testid="handle-midpoint"]').exists()).toBe(false) |
| 56 | + }) |
| 57 | + |
| 58 | + it('shows midpoint handle when showMidpoint is true', () => { |
| 59 | + const wrapper = mountEditor({ |
| 60 | + modelValue: { min: 0, max: 1, midpoint: 0.5 }, |
| 61 | + showMidpoint: true |
| 62 | + }) |
| 63 | + |
| 64 | + expect(wrapper.find('[data-testid="handle-midpoint"]').exists()).toBe(true) |
| 65 | + }) |
| 66 | + |
| 67 | + it('renders gradient background when display is gradient', () => { |
| 68 | + const wrapper = mountEditor({ |
| 69 | + modelValue: { min: 0, max: 1 }, |
| 70 | + display: 'gradient', |
| 71 | + gradientStops: [ |
| 72 | + { offset: 0, color: [0, 0, 0] as const }, |
| 73 | + { offset: 1, color: [255, 255, 255] as const } |
| 74 | + ] |
| 75 | + }) |
| 76 | + |
| 77 | + expect(wrapper.find('[data-testid="gradient-bg"]').exists()).toBe(true) |
| 78 | + expect(wrapper.find('linearGradient').exists()).toBe(true) |
| 79 | + }) |
| 80 | + |
| 81 | + it('renders histogram path when display is histogram with data', () => { |
| 82 | + const histogram = new Uint32Array(256) |
| 83 | + for (let i = 0; i < 256; i++) |
| 84 | + histogram[i] = Math.floor(50 + 50 * Math.sin(i / 20)) |
| 85 | + |
| 86 | + const wrapper = mountEditor({ |
| 87 | + modelValue: { min: 0, max: 1 }, |
| 88 | + display: 'histogram', |
| 89 | + histogram |
| 90 | + }) |
| 91 | + |
| 92 | + expect(wrapper.find('[data-testid="histogram-path"]').exists()).toBe(true) |
| 93 | + }) |
| 94 | + |
| 95 | + it('renders inputs for min and max', () => { |
| 96 | + const wrapper = mountEditor({ modelValue: { min: 0.2, max: 0.8 } }) |
| 97 | + |
| 98 | + const inputs = wrapper.findAll('input') |
| 99 | + expect(inputs).toHaveLength(2) |
| 100 | + }) |
| 101 | + |
| 102 | + it('renders midpoint input when showMidpoint is true', () => { |
| 103 | + const wrapper = mountEditor({ |
| 104 | + modelValue: { min: 0, max: 1, midpoint: 0.5 }, |
| 105 | + showMidpoint: true |
| 106 | + }) |
| 107 | + |
| 108 | + const inputs = wrapper.findAll('input') |
| 109 | + expect(inputs).toHaveLength(3) |
| 110 | + }) |
| 111 | + |
| 112 | + it('normalizes handle positions with custom value range', () => { |
| 113 | + const wrapper = mountEditor({ |
| 114 | + modelValue: { min: 64, max: 192 }, |
| 115 | + valueMin: 0, |
| 116 | + valueMax: 255 |
| 117 | + }) |
| 118 | + |
| 119 | + const minHandle = wrapper.find('[data-testid="handle-min"]') |
| 120 | + const maxHandle = wrapper.find('[data-testid="handle-max"]') |
| 121 | + |
| 122 | + expect(minHandle.attributes('style')).toContain('left: 25.0') |
| 123 | + expect(maxHandle.attributes('style')).toContain('left: 75.') |
| 124 | + }) |
| 125 | +}) |
0 commit comments