Форум 1С
Программистам, бухгалтерам, администраторам, пользователям
Задай вопрос - получи решение проблемы
15 дек 2024, 22:01

Отбор по контрагенту выводит пустой список

Автор Никита Курилов, 08 сен 2023, 15:39

0 Пользователей и 1 гость просматривают эту тему.

Никита Курилов

Здравствуйте! Выполняю тестовые задания на учебной конфигурации. На форме документа "ЗаказПокупателя" есть реквизит "Контрагент" (ссылка на соответствующий справочник) и реквизит КонтактноеЛицо (тоже ссылка на справочник). Передо мной стоит относительно простая задача: при выборе контрагента выводить в списке контактных лиц только те, которые относятся к этому контрагенту. Справочник "Контрагенты" является владельцем справочника "КонтактныеЛица". Для решения задачи воспользовался параметром "СвязиПараметровВывода", выставил следующие значения: "Отбор.Владелец, Контрагент, Очистить", однако, после этого форма выбора справочника "КонтактныеЛица" открывается абсолютно пустой. Я долгое время пытался понять, в чем проблема, но не нашел ответа. Если не выбирать контрагента и открыть форму выбора контактного лица, то выйдет полный список, из чего я могу сделать вывод, что отбор действительно происходит, просто не отбирается ни одно контактное лицо по какой-то причине.

Как я пытался решить проблему: пытался использовать "ПараметрыВыбора", однако в графе "Значение" не могу получить ничего кроме "<Пустое Значение>". Переводил "СвязиПараметровВывода" с реквизита модуля формы на реквизит модуля объекта, результат не менялся. Пытался настроить отбор программно, но это приводило меня к тому же результату: список выводится пустой.

Во время настройки отбора программно решил узнать, как он совершается внутри формы. Открыл форму выбора контактных лиц, в вкладке "ещё" выбрал "настроить список". В настройке сделал отбор по контрагенту и получил тот же самый результат: при выборе любого контрагента список становится пустым. Для примера прикрепляю скриншоты: на первом отбор списка по контрагенту "1С-Франч" выводит пустой список, на втором используется реквизит "контрагент" в боковой панели, и результатом является искомое контактное лицо (использовать этот реквизит по условиям задачи я не могу).

Код, который я использовал для программной настройки отбора находится в процедуре КонтактноеЛицоТестНачалоВыбора (в названии процедур и реквезитов, которые я создал сам есть приставка "Тест") на форме документа "ЗаказПокупателя":

    СтандартнаяОбработка = Ложь;
   Контрагент = Объект.Контрагент;
   
   ЗначениеОтбора = Новый Структура("Контрагент", Контрагент);
   СтруктураОтбора = Новый Структура("Отбор", ЗначениеОтбора);
   
   ОповещениеОВыборе = Новый ОписаниеОповещения;
   
   ОткрытьФорму("Справочник.КонтактныеЛица.ФормаВыбора", СтруктураОтбора, ЭтаФорма,,,,ОповещениеОВыборе);
   
На всякий случай прикладываю скриншот формы документа с названиями реквизитов

Такая простая задача поставила в тупик больше чем на несколько дней. Прошу, помогите! Найти рабочий вариант было бы хорошо, но ещё лучше понять, что я делаю не так!

antoneus

Так поле Владелец в контактных лицах заполнено?

Никита Курилов

antoneus, если речь об этом, то да

Никита Курилов

Обновление информации. Я кое-что понял. Оба справочника создавались не мной, в них уже были данные. Владельца я назначил сам. Из всех уроков, что я посмотрел и прочитал, сначала назначается владелец и только потом заполняются данные. Тогда они отображаются. Мне надо каким-то образом перезаполнить данные (?), тогда они будут отображаться. Не знаю, как это сделать. Надеюсь, не вручную.

antoneus

Это я и имел в виду. Да, нужно программно присвоить каждому контактному лицу владельца, или вывести поле Владелец на форму и заполнить руками.

Никита Курилов

antoneus, Я понял. Как это сделать программно? Или где найти информацию о том, как это сделать программно?

Никита Курилов

Ладно, можно и не программно. Главное, чтоб работало

antoneus

Я так понимаю, там контрагент еще в реквизите сидит? Тогда выборкой

Выборка = Справочники.КонтактныеЛица.Выбрать();
Пока Выборка.Следующий() Цикл
    СпрОбъект = Выборка.Ссылка.ПолучитьОбъект();
    СпрОбъект.Владелец = СпрОбъект.Контрагент;
    СпрОбъект.Записать()
КонецЦикла;

Никита Курилов

Я разобрался в своей проблеме. Большое спасибо antoneus. В конце концов я решил не использовать его способ, но его комментарии помогли разобраться в причинах проблемы. Дело действительно было в том, что отбор по владельцу не работал из-за не настроенного владельца, но я не стал его настраивать, чтобы следовать моему заданию: я не должен вмешиваться в другие формы.
Вместо этого я сделал отбор программно, вот мой код:

"КонтактноеЛицоТест" - название реквизита.

&НаКлиенте
Процедура КонтактноеЛицоТестНачалоВыбора(Элемент, ДанныеВыбора, СтандартнаяОбработка)   
    СтандартнаяОбработка = Ложь;
    Контрагент = Объект.Контрагент;
   
    ЗначениеОтбора = Новый Структура("Контрагент", Контрагент);
    ЗначениеОтбора.Вставить("ЕстьСвязи", Истина);
       
    СтруктураОтбора = Новый Структура("Отбор", ЗначениеОтбора);
    СтруктураОтбора.Вставить("РежимВыбора", Истина);
   
    ОповещениеОВыборе = Новый ОписаниеОповещения();
   
    ОткрытьФорму("Справочник.КонтактныеЛица.ФормаСписка", СтруктураОтбора, ЭтаФорма,,,,ОповещениеОВыборе,РежимОткрытияОкнаФормы.БлокироватьОкноВладельца);   
КонецПроцедуры

&НаКлиенте
Процедура ОбработкаВыбора(ВыбранноеЗначение, ИсточникВыбора)
    Объект.КонтактноеЛицоТест = ВыбранноеЗначение;   
КонецПроцедуры

Сейчас хочу пояснить свой код максимально подробно, на случай, если у кого-то будет такая же проблема. Мне очень помогло разобраться в программном отборе это видео:



Для начала мы отказываемся от стандартной обработки. Это создаст кучу проблем в будущем(которые мы исправим), но это необходимо. Ну, как необходимо. Если мы этого не сделаем, то просто будут параллельно открываться стандартная форма и ту, которую мы сделаем.

ЗначениеОтбора - это структура, в которую вкладываются параметры отбора, в моём случае это имя контрагента и наличие связи. Отбор, кстати, можно настроить внутри открытой формы руками, об этом есть речь в видео. Но, если коротко, в открываемой форме выбора можно нажать кнопку "ещё" -> "Настроить список..." и внутри окна настройки увидите все значения, по которым можно настроить отбор. Именно этот отбор мы и настраиваем программно.

Далее эта структура передает свои данные в следующую структуру - "СтрутураОтбора". Для меня это звучало дико, но это так работает. Опять же, все ответы, почему, я нашел в видео сверху. Помимо параметров отбора я вставляю в эту структуру "режим выбора". Что это такое, расскажу позже.

Параметр ОповещениеОВыборе игнорируйте, оно в данном случае ничего не делает. Ну, насколько я понял. Проверять я, конечно же, не буду.

Далее я открываю форму с введенными параметрами. Из-за того, что убрал стандартную обработку, контакты открываются не в отдельном окне, а на форме. Чтобы это исправить, последний параметр выставляю на "РежимОткрытияОкнаФормы.БлокироватьОкноВладельца".

Последнее, что нужно сделать, это в процедуре "ОбработкаВыбора" (процедура не привязана к КонтактноеЛицоТест, её я просто вызываю на форме) вернуть результат выбора в реквизит Контактов. Для этого мы присваиваем объекту значение "ВыбранноеЗначение". Оно стандартное для этой процедуры и появляется автоматически при создании. В нем как раз и хранится результат выбора и передается в объект. Опять же, этот кусок кода нужно прописать, потому что мы отказались от стандартной обработки.

Наконец расскажу про РежимВыбора. Я ещё совсем зеленый в 1С, но, насколько я понял, когда у метаданных есть и форма выбора и форма списка, для упрощения жизни форму выбора не делают, а запихивают её в форму списка. За это ответственен отдельный кусок кода в процедуре "ПриСоздании" внутри формы списка. Я долгое время чесал репу и не мог понять, почему, когда я вызываю форму выбора, то она открывается как обычный список. Даже выбрать ничего нельзя, когда нажимаешь на любое контактное лицо, тебя выкидывает на страницу редактирования. При этом данные не передаются в объект. Долго ломал голову и в итоге нашел в модуле формы списка переменную, которая отвечает за режим открытия окна: как список или для выбора. Именно поэтому я передаю значение истина вместе с этой переменной в параметры формы, таким образом она открывается так, как надо.

Я понимаю, что объясняю очевидные вещи примитивным языком, но я только учусь программировать и поэтому думаю, что кому-то с таким же уровнем знаний такой комментарий может помочь разобраться в проблеме.

Похожие темы (5)

Рейтинг@Mail.ru

Поиск