in modules/ui/fields/combo.js [476:625]
value: displayValue(v),
isMixed: !commonValues.includes(v)
};
});
var currLength = utilUnicodeCharsCount(commonValues.join(';'));
// limit the input length to the remaining available characters
maxLength = context.maxCharsForTagValue() - currLength;
if (currLength > 0) {
// account for the separator if a new value will be appended to existing
maxLength -= 1;
}
}
// a negative maxlength doesn't make sense
maxLength = Math.max(0, maxLength);
var allowDragAndDrop = _isSemi // only semiCombo values are ordered
&& !Array.isArray(tags[field.key]);
// Exclude existing multikeys from combo options..
var available = objectDifference(_comboData, _multiData);
_combobox.data(available);
// Hide 'Add' button if this field uses fixed set of
// options and they're all currently used,
// or if the field is already at its character limit
var hideAdd = (!_allowCustomValues && !available.length) || maxLength <= 0;
_container.selectAll('.chiplist .input-wrap')
.style('display', hideAdd ? 'none' : null);
// Render chips
var chips = _container.selectAll('.chip')
.data(_multiData);
chips.exit()
.remove();
var enter = chips.enter()
.insert('li', '.input-wrap')
.attr('class', 'chip');
enter.append('span');
enter.append('a');
chips = chips.merge(enter)
.order()
.classed('raw-value', function(d) {
var k = d.key;
if (_isMulti) k = k.replace(field.key, '');
return !field.hasTextForStringId('options.' + k);
})
.classed('draggable', allowDragAndDrop)
.classed('mixed', function(d) {
return d.isMixed;
})
.attr('title', function(d) {
return d.isMixed ? t('inspector.unshared_value_tooltip') : null;
});
if (allowDragAndDrop) {
registerDragAndDrop(chips);
}
chips.select('span')
.html(function(d) { return d.value; });
chips.select('a')
.attr('href', '#')
.on('click', removeMultikey)
.attr('class', 'remove')
.text(function(d) {
// don't show 'x' on the digitalglobe/maxar label on ML road
// TODO: switch to check on __fbid__
return _entityIDs[0] && isFbRoadId(_entityIDs[0]) && field.key === 'source' && (d.value === 'digitalglobe' || d.value === 'maxar') ? '' : '×';
});
} else {
var isMixed = Array.isArray(tags[field.key]);
var mixedValues = isMixed && tags[field.key].map(function(val) {
return displayValue(val);
}).filter(Boolean);
var showsValue = !isMixed && tags[field.key] && !(field.type === 'typeCombo' && tags[field.key] === 'yes');
var isRawValue = showsValue && !field.hasTextForStringId('options.' + tags[field.key]);
var isKnownValue = showsValue && !isRawValue;
var isReadOnly = !_allowCustomValues || isKnownValue;
utilGetSetValue(_input, !isMixed ? displayValue(tags[field.key]) : '')
.classed('raw-value', isRawValue)
.classed('known-value', isKnownValue)
.attr('readonly', isReadOnly ? 'readonly' : undefined)
.attr('title', isMixed ? mixedValues.join('\n') : undefined)
.attr('placeholder', isMixed ? t('inspector.multiple_values') : _staticPlaceholder || '')
.classed('mixed', isMixed)
.on('keydown.deleteCapture', function(d3_event) {
if (isReadOnly &&
isKnownValue &&
(d3_event.keyCode === utilKeybinding.keyCodes['⌫'] ||
d3_event.keyCode === utilKeybinding.keyCodes['⌦'])) {
d3_event.preventDefault();
d3_event.stopPropagation();
var t = {};
t[field.key] = undefined;
dispatch.call('change', this, t);
}
});
}
};
function registerDragAndDrop(selection) {
// allow drag and drop re-ordering of chips
var dragOrigin, targetIndex;
selection.call(d3_drag()
.on('start', function(d3_event) {
dragOrigin = {
x: d3_event.x,
y: d3_event.y
};
targetIndex = null;
})
.on('drag', function(d3_event) {
var x = d3_event.x - dragOrigin.x,
y = d3_event.y - dragOrigin.y;
if (!d3_select(this).classed('dragging') &&
// don't display drag until dragging beyond a distance threshold
Math.sqrt(Math.pow(x, 2) + Math.pow(y, 2)) <= 5) return;
var index = selection.nodes().indexOf(this);
d3_select(this)
.classed('dragging', true);
targetIndex = null;
var targetIndexOffsetTop = null;
var draggedTagWidth = d3_select(this).node().offsetWidth;
if (field.key === 'destination' || field.key === 'via') { // meaning tags are full width
_container.selectAll('.chip')
.style('transform', function(d2, index2) {
var node = d3_select(this).node();
if (index === index2) {