|
@@ -72,12 +72,18 @@
|
|
|
</div>
|
|
</div>
|
|
|
<div class="modal-body">
|
|
<div class="modal-body">
|
|
|
<label for="bulk_order_number" class="form-label">Номер заказа</label>
|
|
<label for="bulk_order_number" class="form-label">Номер заказа</label>
|
|
|
- <select class="form-select @error('bulk_order_number') is-invalid @enderror" id="bulk_order_number" name="bulk_order_number" required>
|
|
|
|
|
- <option value="">Выберите номер заказа</option>
|
|
|
|
|
- @foreach($order_numbers as $order_number)
|
|
|
|
|
- <option value="{{ $order_number }}" @selected(old('bulk_order_number') === $order_number)>{{ $order_number }}</option>
|
|
|
|
|
- @endforeach
|
|
|
|
|
- </select>
|
|
|
|
|
|
|
+ <div class="position-relative">
|
|
|
|
|
+ <input type="text"
|
|
|
|
|
+ class="form-control @error('bulk_order_number') is-invalid @enderror"
|
|
|
|
|
+ id="bulk_order_number"
|
|
|
|
|
+ name="bulk_order_number"
|
|
|
|
|
+ value="{{ old('bulk_order_number') }}"
|
|
|
|
|
+ placeholder="Начните вводить номер заказа"
|
|
|
|
|
+ autocomplete="off"
|
|
|
|
|
+ required>
|
|
|
|
|
+ <div class="autocomplete-dropdown autocomplete-dropdown--order" id="bulk_order_number_dropdown"></div>
|
|
|
|
|
+ </div>
|
|
|
|
|
+ <div class="form-text">Доступны только заказы со статусом «Заказан».</div>
|
|
|
@error('bulk_order_number')
|
|
@error('bulk_order_number')
|
|
|
<div class="invalid-feedback d-block">{{ $message }}</div>
|
|
<div class="invalid-feedback d-block">{{ $message }}</div>
|
|
|
@enderror
|
|
@enderror
|
|
@@ -101,6 +107,137 @@
|
|
|
$('#sku_form').slideDown();
|
|
$('#sku_form').slideDown();
|
|
|
});
|
|
});
|
|
|
|
|
|
|
|
|
|
+ waitForJQuery(function () {
|
|
|
|
|
+ const $modal = $('#setOrderInStockModal');
|
|
|
|
|
+ const $input = $modal.find('#bulk_order_number');
|
|
|
|
|
+ const $dropdown = $modal.find('#bulk_order_number_dropdown');
|
|
|
|
|
+ const orderNumbers = @json(($orderedOrderNumbers ?? collect())->values());
|
|
|
|
|
+ let currentFocus = -1;
|
|
|
|
|
+
|
|
|
|
|
+ function escapeHtml(text) {
|
|
|
|
|
+ return String(text)
|
|
|
|
|
+ .replace(/&/g, '&')
|
|
|
|
|
+ .replace(/</g, '<')
|
|
|
|
|
+ .replace(/>/g, '>')
|
|
|
|
|
+ .replace(/"/g, '"')
|
|
|
|
|
+ .replace(/'/g, ''');
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ function escapeRegex(str) {
|
|
|
|
|
+ return String(str).replace(/[.*+?^${}()|[\]\\]/g, '\\$&');
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ function highlightMatch(text, query) {
|
|
|
|
|
+ if (!text || !query) {
|
|
|
|
|
+ return escapeHtml(text || '');
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ const safeText = escapeHtml(text);
|
|
|
|
|
+ const regex = new RegExp('(' + escapeRegex(query) + ')', 'gi');
|
|
|
|
|
+ return safeText.replace(regex, '<strong>$1</strong>');
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ function hideDropdown() {
|
|
|
|
|
+ $dropdown.hide();
|
|
|
|
|
+ currentFocus = -1;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ function showDropdown(items, query) {
|
|
|
|
|
+ $dropdown.empty();
|
|
|
|
|
+ currentFocus = -1;
|
|
|
|
|
+
|
|
|
|
|
+ if (!items.length) {
|
|
|
|
|
+ $dropdown.html('<div class="autocomplete-item text-muted">Ничего не найдено</div>');
|
|
|
|
|
+ $dropdown.show();
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ items.forEach(function (item) {
|
|
|
|
|
+ $dropdown.append(
|
|
|
|
|
+ '<div class="autocomplete-item" data-value="' + escapeHtml(item) + '">' +
|
|
|
|
|
+ '<div class="article">' + highlightMatch(item, query) + '</div>' +
|
|
|
|
|
+ '</div>'
|
|
|
|
|
+ );
|
|
|
|
|
+ });
|
|
|
|
|
+
|
|
|
|
|
+ $dropdown.show();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ function selectValue(value) {
|
|
|
|
|
+ $input.val(value).removeClass('is-invalid');
|
|
|
|
|
+ hideDropdown();
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ function setActive($items) {
|
|
|
|
|
+ $items.removeClass('active');
|
|
|
|
|
+ if (currentFocus >= 0 && currentFocus < $items.length) {
|
|
|
|
|
+ const $active = $items.eq(currentFocus);
|
|
|
|
|
+ $active.addClass('active');
|
|
|
|
|
+ $active[0].scrollIntoView({block: 'nearest'});
|
|
|
|
|
+ }
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ function searchOrderNumbers(query) {
|
|
|
|
|
+ const normalized = String(query || '').trim().toLowerCase();
|
|
|
|
|
+
|
|
|
|
|
+ if (normalized.length < 1) {
|
|
|
|
|
+ showDropdown(orderNumbers.slice(0, 50), '');
|
|
|
|
|
+ return;
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ const filtered = orderNumbers.filter(function (item) {
|
|
|
|
|
+ return String(item).toLowerCase().includes(normalized);
|
|
|
|
|
+ });
|
|
|
|
|
+
|
|
|
|
|
+ showDropdown(filtered.slice(0, 50), normalized);
|
|
|
|
|
+ }
|
|
|
|
|
+
|
|
|
|
|
+ $input.on('input focus', function () {
|
|
|
|
|
+ searchOrderNumbers($(this).val());
|
|
|
|
|
+ });
|
|
|
|
|
+
|
|
|
|
|
+ $input.on('keydown', function (e) {
|
|
|
|
|
+ const $items = $dropdown.find('.autocomplete-item:not(.text-muted)');
|
|
|
|
|
+
|
|
|
|
|
+ if (e.key === 'ArrowDown') {
|
|
|
|
|
+ e.preventDefault();
|
|
|
|
|
+ currentFocus++;
|
|
|
|
|
+ if (currentFocus >= $items.length) {
|
|
|
|
|
+ currentFocus = 0;
|
|
|
|
|
+ }
|
|
|
|
|
+ setActive($items);
|
|
|
|
|
+ } else if (e.key === 'ArrowUp') {
|
|
|
|
|
+ e.preventDefault();
|
|
|
|
|
+ currentFocus--;
|
|
|
|
|
+ if (currentFocus < 0) {
|
|
|
|
|
+ currentFocus = $items.length - 1;
|
|
|
|
|
+ }
|
|
|
|
|
+ setActive($items);
|
|
|
|
|
+ } else if (e.key === 'Enter') {
|
|
|
|
|
+ if ($items.length > 0 && currentFocus > -1) {
|
|
|
|
|
+ e.preventDefault();
|
|
|
|
|
+ selectValue(String($items.eq(currentFocus).data('value') || ''));
|
|
|
|
|
+ }
|
|
|
|
|
+ } else if (e.key === 'Escape') {
|
|
|
|
|
+ hideDropdown();
|
|
|
|
|
+ }
|
|
|
|
|
+ });
|
|
|
|
|
+
|
|
|
|
|
+ $dropdown.on('click', '.autocomplete-item:not(.text-muted)', function () {
|
|
|
|
|
+ selectValue(String($(this).data('value') || ''));
|
|
|
|
|
+ });
|
|
|
|
|
+
|
|
|
|
|
+ $(document).on('click', function (e) {
|
|
|
|
|
+ if (!$(e.target).closest('#bulk_order_number, #bulk_order_number_dropdown').length) {
|
|
|
|
|
+ hideDropdown();
|
|
|
|
|
+ }
|
|
|
|
|
+ });
|
|
|
|
|
+
|
|
|
|
|
+ $modal.on('hidden.bs.modal', function () {
|
|
|
|
|
+ hideDropdown();
|
|
|
|
|
+ });
|
|
|
|
|
+ });
|
|
|
|
|
+
|
|
|
@if($errors->has('bulk_order_number') && hasRole('admin,assistant_head'))
|
|
@if($errors->has('bulk_order_number') && hasRole('admin,assistant_head'))
|
|
|
const setOrderInStockModalElement = document.getElementById('setOrderInStockModal');
|
|
const setOrderInStockModalElement = document.getElementById('setOrderInStockModal');
|
|
|
if (setOrderInStockModalElement) {
|
|
if (setOrderInStockModalElement) {
|