Files
iD/test/spec/ui/fields/directional_combo.js
Kyℓe Hensel 2c0f8a4b5f handle cycleway:both=* (#9587)
this works for any `directionalCombo` field, including `sidewalk:both`
2025-02-05 10:41:48 +01:00

112 lines
4.3 KiB
JavaScript

describe('iD.uiFieldDirectionalCombo', () => {
/** @type {iD.Context} */
let context;
/** @type {import("d3-selection").Selection} */
let selection;
beforeEach(() => {
context = iD.coreContext().assetPath('../dist/').init();
selection = d3.select(document.createElement('div'));
});
describe.each(['cycleway', 'cycleway:both'])('preset uses %s', (commonKey) => {
/** if commonKey ends with :both, this is the key without :both. and vice-verca */
const otherCommonKey = commonKey.endsWith(':both')
? commonKey.replace(/:both$/, '')
: `${commonKey}:both`;
const field = iD.presetField('name', {
key: commonKey,
keys: ['cycleway:left', 'cycleway:right'],
});
it('populates the left/right fields using :left & :right', () => {
const instance = iD.uiFieldDirectionalCombo(field, context);
selection.call(instance);
instance.tags({ 'cycleway:left': 'lane' });
expect(selection.selectAll('input').nodes()).toHaveLength(2);
const [left, right] = selection.selectAll('input').nodes();
expect(left.value).toBe('lane');
expect(right.value).toBe('');
});
it('populates the left/right fields using :both', () => {
const instance = iD.uiFieldDirectionalCombo(field, context);
selection.call(instance);
instance.tags({ 'cycleway:both': 'lane' });
expect(selection.selectAll('input').nodes()).toHaveLength(2);
const [left, right] = selection.selectAll('input').nodes();
expect(left.value).toBe('lane');
expect(right.value).toBe('lane');
});
it('populates the left/right fields using the unprefixed tag', () => {
const instance = iD.uiFieldDirectionalCombo(field, context);
selection.call(instance);
instance.tags({ cycleway: 'lane' });
expect(selection.selectAll('input').nodes()).toHaveLength(2);
const [left, right] = selection.selectAll('input').nodes();
expect(left.value).toBe('lane');
expect(right.value).toBe('lane');
});
it(`setting left & right to the same value will use the ${commonKey}`, () => {
const instance = iD.uiFieldDirectionalCombo(field, context);
selection.call(instance);
const tags = { 'cycleway:left': 'lane', 'cycleway:right': 'shoulder' };
instance.tags(tags);
const onChange = vi.fn();
instance.on('change', v => onChange(v(tags)));
expect(selection.selectAll('input').nodes()).toHaveLength(2);
const [left, right] = selection.selectAll('input').nodes();
expect(left.value).toBe('lane');
expect(right.value).toBe('shoulder');
left.value = 'shoulder';
d3.select(left).dispatch('change');
expect(onChange).toHaveBeenCalledTimes(1);
expect(onChange).toHaveBeenCalledWith({ [commonKey]: 'shoulder' });
});
it(`can read the value from ${otherCommonKey}, but writes to ${commonKey}`, () => {
const instance = iD.uiFieldDirectionalCombo(field, context);
selection.call(instance);
let tags = { [otherCommonKey]: 'lane' };
instance.tags(tags);
const onChange = vi.fn();
instance.on('change', v => onChange(tags = v(tags)));
expect(selection.selectAll('input').nodes()).toHaveLength(2);
const [left, right] = selection.selectAll('input').nodes();
expect(left.value).toBe('lane');
expect(right.value).toBe('lane');
left.value = 'shoulder';
d3.select(left).dispatch('change');
expect(onChange).toHaveBeenCalledTimes(1);
expect(onChange).toHaveBeenNthCalledWith(1, {
'cycleway:left': 'shoulder', // left was updated
'cycleway:right': 'lane',
});
right.value = 'shoulder';
d3.select(right).dispatch('change');
expect(onChange).toHaveBeenCalledTimes(2);
expect(onChange).toHaveBeenNthCalledWith(2, {
[commonKey]: 'shoulder', // now left & right have been updated
});
});
});
});