Имя: Пароль:
1C
 
Размещение и динамическое обновление на форме списка
,
0 ViciousVVV
 
naïve
17.11.24
15:51
Доброго времени суток.
Стоит такая задача - необходимо при выделении контрагента в форме списка выводить информацию о нем - юридический и фактический адрес, телефон и почту. Для этого я написал вот такой код:

&НаКлиенте
Процедура СписокПриАктивизацииСтроки(Элемент)
	Код = Элемент.ТекущиеДанные.Код;
	ПоискИПолучениеИнформацииКонтрагента(Код);
	
КонецПроцедуры

&НаСервереБезКонтекста
Процедура ПоискИПолучениеИнформацииКонтрагента(Код)
	
	КонтрагентСсылка = Справочники.Контрагенты.НайтиПоКоду(Код);

	КонтактнаяИнформация = КонтрагентСсылка.КонтактнаяИнформация.ВыгрузитьКолонку("Вид");
	
	Для Индекс = 0 По КонтактнаяИнформация.Количество() - 1 Цикл
		
		Если КонтактнаяИнформация[Индекс] = Справочники.ВидыКонтактнойИнформации.ЮридическийАдресКонтрагента Тогда
		  Сообщить(КонтрагентСсылка.КонтактнаяИнформация.ВыгрузитьКолонку("Значение")[0]);
		  ЮрАдрес = КонтрагентСсылка.КонтактнаяИнформация.ВыгрузитьКолонку("Значение")[0];	
	  КонецЕсли;
	  
	  Если КонтактнаяИнформация[Индекс] = Справочники.ВидыКонтактнойИнформации.ФактическийАдресКонтрагента Тогда
		  Сообщить(КонтрагентСсылка.КонтактнаяИнформация.ВыгрузитьКолонку("Значение")[0]);
		  ФактическийАдрес = КонтрагентСсылка.КонтактнаяИнформация.ВыгрузитьКолонку("Значение")[0];	
	  КонецЕсли;
	  
	  
	  Если КонтактнаяИнформация[Индекс] = Справочники.ВидыКонтактнойИнформации.EmailКонтрагента Тогда
		  Сообщить(КонтрагентСсылка.КонтактнаяИнформация.ВыгрузитьКолонку("Значение")[0]);
		  Email = КонтрагентСсылка.КонтактнаяИнформация.ВыгрузитьКолонку("Значение")[0];	
	  КонецЕсли;
	  
	  Если КонтактнаяИнформация[Индекс] = Справочники.ВидыКонтактнойИнформации.ТелефонКонтрагента Тогда
		  Сообщить(КонтрагентСсылка.КонтактнаяИнформация.ВыгрузитьКолонку("Значение")[0]);
		  Телефон = КонтрагентСсылка.КонтактнаяИнформация.ВыгрузитьКолонку("Значение")[0];	
	  КонецЕсли;
	  
	  
	КонецЦикла;
	

КонецПроцедуры


Информация получается, но на форму почему-то не выводится, не могли бы вы помочь мне понять, почему?
1 ViciousVVV
 
naïve
17.11.24
15:15
Заранее сорри за возможные косяки в оформлении темы, в первый раз сюда пишу
2 ViciousVVV
 
naïve
17.11.24
15:18
Вот так выглядит сама форма - https://radikal.cloud/i/RTjSx3
3 Волшебник
 
17.11.24
15:51
Вы программировать умеете?
4 Волшебник
 
17.11.24
15:54
Давайте избавимся от поиска контрагента по коду.
В списке уже есть ссылка на контрагента. Её и передавайте в процедуру.

Множественные "Если" замените на один "Если... ИначеЕсли... ИначеЕсли... КонецЕсли"

Вместо цикла по индексу сделайте цикл Для Каждого Вид Из ВидыКИ Цикл
5 Волшебник
 
17.11.24
15:55
После триумфального присвоения значений переменным:
- ЮрАдрес
- ФактическийАдрес
- Email
- Телефон

их надо как-то вернуть на форму. Какие планы?
6 ViciousVVV
 
naïve
17.11.24
15:57
(3) Учусь
8 Волшебник
 
17.11.24
17:20
&НаКлиенте
Процедура СписокПриАктивизацииСтроки(Элемент)
	ТелефоныСтрокой = ПолучитьКИ(Элемент.ТекущиеДанные, "Телефон");	
        // присвоить элементу формы, повторить до готовности...
КонецПроцедуры

&НаСервереБезКонтекста
Функция ПолучитьКИ(Контрагент, сВидКИ)
	
    Результат = ""; Разд = "";
    ВидКИ = Справочники.ВидыКонтактнойИнформации[сВидКИ];
    СписокКИ = Контрагент.КонтактнаяИнформация.НайтиСтроки(Новый Структура("Вид", ВидКИ));
    Для Каждого элКИ Из СписокКИ Цикл
        Результат = Результат + СокрЛП(элКИ.Значение) + Разд;
        Разд = ", ";
    КонецЦикла;

    Возврат Результат;
КонецФункции
9 Ненавижу 1С
 
гуру
17.11.24
19:30
(8) от ручной конкатенации в цикле запахло нафталином. Есть же СтрСоединить
10 Garykom
 
гуру
17.11.24
19:40
(9) прикольней вызов с клиента на сервер без контекста хз чего внутри Элемент.ТекущиеДанные
11 CepeLLlka
 
17.11.24
20:40
(9)А чё такого то? Мне кажется это дело привычки, или СтрСоединить как-то лучше работает?
12 Garykom
 
гуру
17.11.24
20:49
(11) Намного лучше и быстре
Либо можно использовать СтрШаблон:
Результат = СтрШаблон("%1%2%3", Результат, СокрЛП(элКИ.Значение), Разд);

ЗЫ
и
Разд = ", ";
в цикле это мощно ))
13 Волшебник
 
17.11.24
21:26
Ваши варианты здесь не сработают
14 Волшебник
 
18.11.24
09:29
(12) >> в цикле это мощно

Здесь цикл будет выполняться 1 раз, от силы 2 раза. Потому что ну сколько может быть телефонов у контрагента? Ну 1-3. Вряд ли кто-то будет вбивать туда десятки телефонов. Можно даже ограничитель поставить, макс. 3 телефона. То же самое с адресами и почтами.
15 Волшебник
 
18.11.24
09:30
Здесь можно даже извлекать данные запросом.
Поэтому и говорю, что у профессионалов запросы в цикле не тормозят.
Профессионал знает, сколько раз будет выполняться цикл, план запроса и количество строк в результате.
Отбор по контрагенту будет очень эффективным.

&НаКлиенте
Процедура СписокПриАктивизацииСтроки(Элемент)
	ТелефоныСтрокой = ПолучитьКИ(Элемент.ТекущиеДанные, "Телефон");	
        // присвоить элементу формы, повторить до готовности...
КонецПроцедуры

&НаСервереБезКонтекста
Функция ПолучитьКИ(Контрагент, сВидКИ)
	
    Результат = ""; Разд = "";
    Запрос = Новый Запрос("ВЫБРАТЬ Значение ИЗ Справочник.Контрагенты.КонтактнаяИнформация 
        |ГДЕ Ссылка = &Контрагент И Вид = &ВидКИ");
    Запрос.УстановитьПараметр("Контрагент", Контрагент);
    Запрос.УстановитьПараметр("ВидКИ", Справочники.ВидыКонтактнойИнформации[сВидКИ]);
    ВыборкаКИ = Запрос.Выполнить().Выбрать();
    Пока ВыборкаКИ.Следующий() Цикл
        Результат = Результат + ВыборкаКИ.Значение + Разд; Разд = ", ";
    КонецЦикла;

    Возврат Результат;
КонецФункции
16 Garykom
 
гуру
18.11.24
09:37
(15) Это промпты чатгопоты или аналога тесты?
Ибо в типовых есть ОбщегоНазначения.ЗначенияРеквизитовОбъекта
17 Garykom
 
гуру
18.11.24
09:38
(16)+ ВидКИ = 100% типовая на БСП
18 Волшебник
 
18.11.24
09:47
(16) Я не люблю типовые. Это чистый ванильный 1С
19 Ненавижу 1С
 
гуру
18.11.24
09:48
(15) еще раз - циклы читаются как многословие, как вода в реферате, вроде есть смысл, но можно и короче:

ЗначенияКИ = Запрос.Выполнить().Выгрузить().ВыгрузитьКолонку("Значение");
Результат = СтрСоединить(ЗначенияКИ,",");
20 Волшебник
 
18.11.24
09:48
(16) Эта функция не нужна, потому что она всего лишь имитирует точку:
Объект.Реквизит
21 Волшебник
 
18.11.24
09:49
(19) Повышенная когнитивная сложность, жонглирование типами. Говнокод
22 Ненавижу 1С
 
гуру
18.11.24
09:52
(21) как раз все абсолютно прозрачно. Просто ты сейчас до крайнего будешь упирать в свои циклы

Посмотри как в Java/C# давно изобрели функторы работы с коллекциями. А не вот это, именно что "жонглирование" в циклах, перебрасывая данные из одной коллекции в другую. И это почти всюду в алгоритмах 1С
23 Волшебник
 
18.11.24
09:59
(22) Очень плохо читаются. Для компилируемых языков вообще бесполезны. Для скриптовых ещё годятся (Python, PHP).
24 Ненавижу 1С
 
гуру
18.11.24
11:04
(23) ну да
Вот реальная задача: определить есть ли в коллекции позиции, для которых новая цена стала меньше старой
Вот так лаконично решается на шарпе:

bool result = Items.Any(i => i.NewPrice<i.OldPrice);
25 Волшебник
 
18.11.24
11:10
(24)
foreach (i in Items) { if (i.NewPrice<i.OldPrice) {result=true; break } }
26 Ненавижу 1С
 
гуру
18.11.24
12:19
(25) Все верно. Буквально почти дословно развернули функтор Any. Получается надо на каждую такую задачу дублировать код? Это же рутина
27 Волшебник
 
18.11.24
13:05
(26) Вы поймите, что циклы по любому будут, хоть вы промтами всё напишете. Где-то там внутри всё развернётся в цикл. Все эти декларативные описания — всего лишь синтаксический сахар.
28 Garykom
 
гуру
18.11.24
13:09
(27) чем ближе и нативней циклы к данным тем лучше
там оптимизация типа может лучше работать