Документ на основание

1. _7445_ 04.03.19 17:18 Сейчас в теме
Здравствуйте. Я плохо знаю русский. Извините за этого. Я еще новичок в 1С программирование. В УТ 10.3. В документе заказ покупателя есть 2 галочка (Директор по продажам и Главный бухгалтер). Чтобы на основании этого заказа можно было реализовать товар только если они оба подтвердили этот заказ. Если оба они не подтвердили тогда при создании реализации на основании этого заказа выдавало ошибку с текстом НЕ ПОДТВЕРЖДЕН.... В документа реализация - модуль объекта - обработка заполнения добавил код. Код показывает сообщению когда не подтвердили оба они. Но есть токая проблема что показывает сообщению но после этого открывает новый пустой документ. Надо что если документ не подтверждён тогда проста показывал сообщению. Можете дать подсказку что как исправится с этим?
Два варианта пробовал но не работает. Вызвать Исключение не надо. Надо простая сообщение. И не открылся документ реализация.
Спасибо всем за ранее.
Процедура ОбработкаЗаполнения(Основание)
	
	 Если ТипЗнч(Основание) <> Тип("ДокументСсылка.ЗаказПокупателя")
		И ТипЗнч(Основание) <> Тип("ДокументСсылка.СчетНаОплатуПокупателю")
		И ТипЗнч(Основание) <> Тип("ДокументСсылка.ПоступлениеТоваровУслуг") Тогда
		возврат;
	КонецЕсли;
	
	Если ТипЗнч(Основание) = Тип("ДокументСсылка.ЗаказПокупателя")
	 ИЛИ ТипЗнч(Основание) = Тип("ДокументСсылка.СчетНаОплатуПокупателю") Тогда
	 
	 
	 Если ТипЗнч(Основание) = Тип("ДокументСсылка.ЗаказПокупателя") Тогда
		 Если Основание.ДиректорПоПродажам = Ложь ИЛИ Основание.ГлавныйБухгалтер = Ложь Тогда
			 Если Основание.ДиректорПоПродажам = Ложь Тогда
				 Отказ = Истина; // Первый вариант
				 //ВызватьИсключение "Директор по продажам еще не подтвердил заказ покупателя."; // Второй вариант
			 ИначеЕсли Основание.ГлавныйБухгалтер = Ложь Тогда
				 Отказ = Истина;
				 //ВызватьИсключение "Главный бухгалтер еще не подтвердил заказ покупателя.";
			 КонецЕсли;	 
		 КонецЕсли;
	 КонецЕсли;


	 
		//Заполним реквизиты из стандартного набора по документу основанию.
		ЗаполнениеДокументов.ЗаполнитьШапкуДокументаПоОснованию(ЭтотОбъект, Основание);

		ЗаполнениеДокументов.ЗаполнитьДанныеДоставкиПоОснованию(ЭтотОбъект, Основание);

		ВидОперации = Перечисления.ВидыОперацийРеализацияТоваров.ПродажаКомиссия;
		ВидПередачи = Перечисления.ВидыПередачиТоваров.СоСклада;

		Если Не ЗначениеЗаполнено(Склад) Тогда
			Склад = УправлениеПользователями.ПолучитьЗначениеПоУмолчанию(глЗначениеПеременной("глТекущийПользователь"), "ОсновнойСклад");
		КонецЕсли;

		#Если Клиент Тогда
			Если Не ЗначениеЗаполнено(Склад) И НЕ мУказаниеСкладовВТЧ И ТипЗнч(Основание) = Тип("ДокументСсылка.ЗаказПокупателя") Тогда
				ВвестиЗначение(Склад, "Выберите склад", Тип("СправочникСсылка.Склады"));
			КонецЕсли;
		#КонецЕсли

		Если ТипЗнч(Основание) = Тип("ДокументСсылка.ЗаказПокупателя")
		 Или (ТипЗнч(Основание) = Тип("ДокументСсылка.СчетНаОплатуПокупателю")
		      И ДоговорКонтрагента.ВедениеВзаиморасчетов = Перечисления.ВедениеВзаиморасчетовПоДоговорам.ПоСчетам) Тогда
			Сделка = Основание;
		Иначе
			Сделка = Основание.ЗаказПокупателя;
		КонецЕсли;

		Если ТипЗнч(Основание) = Тип("ДокументСсылка.СчетНаОплатуПокупателю") Тогда

			СкопироватьТовары(Основание);
			СкопироватьВозвратнуюТару(Основание);
			СкопироватьУслуги(Основание);

		ИначеЕсли Основание.Проведен Тогда // Заказ покупателя
			
			// Заполним табличные части неполученными ТМЦ (резервом) по заказу покупателя.
			ЗаполнитьТабличнуюЧастьПоЗаказуПокупателяУпр(Товары, Основание);
			ЗаполнитьТабличнуюЧастьПоЗаказуПокупателяУпр(ВозвратнаяТара, Основание);
			ЗаполнитьУслугиПоОстаткамУпр();

		КонецЕсли;

	ИначеЕсли ТипЗнч(Основание) = Тип("ДокументСсылка.ПоступлениеТоваровУслуг") Тогда

		// Заполним реквизиты шапки по документу основанию.
		Организация   = Основание.Организация;
		Подразделение = Основание.Подразделение;
		ВидОперации   = Перечисления.ВидыОперацийРеализацияТоваров.ПродажаКомиссия;
		ВидПередачи   = Перечисления.ВидыПередачиТоваров.СоСклада;

		Если Основание.ВидПоступления = Перечисления.ВидыПоступленияТоваров.НаСклад Тогда
			Склад = Основание.СкладОрдер;
		Иначе
			Склад = Основание.СкладОрдер.Склад;
		КонецЕсли;

		МассивЗаказов = Неопределено;
#Если Клиент Тогда

		СтруктТабЧастей = Новый Структура;
		СтруктТабЧастей.Вставить("Товары",         "Заказ");
		СтруктТабЧастей.Вставить("ВозвратнаяТара", "Заказ");

		СтруктПараметры = Новый Структура;
		СтруктПараметры.Вставить("ТабЧасти", СтруктТабЧастей);
		
		ЗаказыВТабЧасти = Константы.УказаниеЗаказовВТабличнойЧастиДокументов.Получить();
		СтруктПараметры.Вставить("ЗаказВТабЧасти",
			    ЗаказыВТабЧасти = Перечисления.ВариантыУказанияЗаказовВТабличнойЧастиДокументов.ДляДокументовРеализации
			Или ЗаказыВТабЧасти = Перечисления.ВариантыУказанияЗаказовВТабличнойЧастиДокументов.ДляДокументовПоступленияРеализации);

		РезультатВыбораЗаказа = УправлениеЗаказами.ВыбратьЗаказИзДокументаОснования(Основание, СтруктПараметры);

		Если РезультатВыбораЗаказа.ВыборСделан Тогда

			Контрагент         = РезультатВыбораЗаказа.Контрагент;

			Если ЗаполнениеДокументов.МожноИспользоватьДоговорДляДокумента(РезультатВыбораЗаказа.Договор, Контрагент, Организация, мСтруктураПараметровДляПолученияДоговора) Тогда
				ДоговорКонтрагента = РезультатВыбораЗаказа.Договор;
			КонецЕсли;

			МассивЗаказов      = РезультатВыбораЗаказа.Заказ;
			Если МассивЗаказов.Количество() = 1 Тогда
				Сделка         = МассивЗаказов[0];
			КонецЕсли;
		КонецЕсли;
#Иначе
		Контрагент         = УправлениеПользователями.ПолучитьЗначениеПоУмолчанию(глЗначениеПеременной("глТекущийПользователь"), "ОсновнойПокупатель");
#КонецЕсли

		ЗаполнениеДокументов.ПриИзмененииЗначенияКонтрагента(ЭтотОбъект, мСтруктураПараметровДляПолученияДоговора);

		Если НЕ ЗначениеЗаполнено(ДоговорКонтрагента) Тогда
			ВалютаДокумента = мВалютаРегламентированногоУчета;
		Иначе
			ВалютаДокумента = ДоговорКонтрагента.ВалютаВзаиморасчетов;
		КонецЕсли;

		СтруктураКурсаВзаиморасчетов = МодульВалютногоУчета.ПолучитьКурсВалюты(ВалютаДокумента, ОбщегоНазначения.ПолучитьРабочуюДату());
		КурсВзаиморасчетов           = СтруктураКурсаВзаиморасчетов.Курс;
		КратностьВзаиморасчетов      = СтруктураКурсаВзаиморасчетов.Кратность;

		// ТипЦен.
		ТипЦен = ДоговорКонтрагента.ТипЦен;

		Если НЕ ЗначениеЗаполнено(ТипЦен) Тогда
			ТипЦен = УправлениеПользователями.ПолучитьЗначениеПоУмолчанию(глЗначениеПеременной("глТекущийПользователь"), "ОсновнойТипЦенПродажи");
		КонецЕсли;

		// Флаги включения налогов.
		УчитыватьНДС = Истина;
		Если ЗначениеЗаполнено(ТипЦен) Тогда

			// Если цены выбранного типа расчетные, то флаги включения налогов надо брать из базовой цены.
			ВремТипЦен       = ?(ТипЦен.Рассчитывается, ТипЦен.БазовыйТипЦен, ТипЦен);
			СуммаВключаетНДС = ВремТипЦен.ЦенаВключаетНДС;

		Иначе
			// Заполним значениями по умолчанию (не заполнен ТипЦен).
			СуммаВключаетНДС= Истина;
		КонецЕсли;

		Если Основание.Проведен Тогда

			// Заполним табличные части по документу основанию (Поступление товаров);
			// количество - минимум из того, что есть в документе основании и свободного остатка на складе.
			ЗаполнитьТоварыПоПоступлениюТоваровУпр(Основание,"Товары", МассивЗаказов);
			ЗаполнитьВозвратнуюТаруПоПоступлениюТоваровУпр(Основание, МассивЗаказов);

		КонецЕсли;

	КонецЕсли;

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

	Если ОбщегоНазначения.ЕстьРеквизитДокумента("ОтражатьВБухгалтерскомУчете", Основание.Метаданные()) Тогда
		ОтражатьВБухгалтерскомУчете = Основание.ОтражатьВБухгалтерскомУчете;
		ОтражатьВНалоговомУчете     = Основание.ОтражатьВНалоговомУчете;
	Иначе
		ОтражатьВБухгалтерскомУчете = УправлениеПользователями.ПолучитьЗначениеПоУмолчанию(глЗначениеПеременной("глТекущийПользователь"), "ОтражатьДокументыВБухгалтерскомУчете");

		Если ОтражатьВБухгалтерскомУчете Тогда
			ОтражатьВНалоговомУчете = УправлениеПользователями.ПолучитьЗначениеПоУмолчанию(глЗначениеПеременной("глТекущийПользователь"), "ОтражатьДокументыВНалоговомУчете");
		Иначе
			ОтражатьВНалоговомУчете = ОтражатьВБухгалтерскомУчете;
		КонецЕсли;
	КонецЕсли;

	Если ЗначениеЗаполнено(ДоговорКонтрагента) Тогда
		УправлениеВзаиморасчетами.ДополнитьСтруктуруПараметровДляЗаполненияТаблицыДокументовРа­счетов(ЭтотОбъект, мСтруктураПараметровВзаиморасчетов);
		УправлениеВзаиморасчетами.ЗаполнитьТаблицуДокументовРасчетовСКонтрагентом(ЭтотОбъект, мСтруктураПараметровВзаиморасчетов);
	КонецЕсли;
	
 

	
КонецПроцедуры // ОбработкаЗаполнения()
Показать
По теме из базы знаний
Ответы
Подписаться на ответы Инфостарт бот Сортировка: Древо развёрнутое
Свернуть все
3. dhurricane 04.03.19 19:14 Сейчас в теме
(1) Что же, раз Вам таки не подходит способ с использованием исключений, я могу поделиться с Вами и другими участниками форума еще одним интересным способом запрета ввода на основании, который мне удалось почерпнуть из вебинара по клиент-серверному взаимодействию. Идея его заключается в том, чтобы осуществлять необходимый контроль данных при получении формы, и в случае провала прекратить открытие стандартной формы, и вместо нее показать другую с сообщением об ошибке.

Итак.

1) Создаем общую форму, например "ФормаСПредупреждением". Ее мы будем использовать для отображения произвольного предупреждения пользователю. По сути это форма пустышка: ее пользователь никогда не увидит, поэтому ни реквизиты, ни элементы добавлять не нужно. Добавляем только ключевой параметр "ТекстПредупреждения" строкового типа и в обработчике события формы "ПриОткрытии" пишем:
&НаКлиенте
Процедура ПриОткрытии(Отказ)
	
	ПоказатьПредупреждение(, Параметры.ТекстПредупреждения);
	Отказ = Истина;
	
КонецПроцедуры

2) Убираем все проверки из модуля объекта создаваемого документа. Здесь они нам не понадобятся, т.к. данные на момент выполнения обработчика будут корректными.

3) Добавляем в документе реализации обработчик события "ОбработкаПолученияФормы" (модуль менеджера). Здесь как раз и будет осуществляться проверка основания, а также отмена открытия формы документа при отказе. В обработчике нужен примерно следующий код:
Процедура ОбработкаПолученияФормы(ВидФормы, Параметры, ВыбраннаяФорма, ДополнительнаяИнформация, СтандартнаяОбработка)
	
	Перем Основание;
	
	Отказ = Ложь;
	ТекстОшибки = "";
	
	// Проверяем, что октываемая форма есть форма нового документа, созданного на основании.
	Если ВидФормы = "ФормаОбъекта" 
		И Параметры.Свойство("Основание", Основание)
		И ЗначениеЗаполнено(Основание) Тогда
		
		// Контролируем заполнение реквизитов заказа покупателя
		Если ТипЗнч(Основание) = Тип("ДокументСсылка.ЗаказПокупателя") Тогда
			ВыполнитьКонтрольЗаказаПокупателя(Основание, Отказ, ТекстОшибки);			
		КонецЕсли; 
		
	КонецЕсли; 
	
	// Если контроль данных завершился ошибкой, вместо стандартной формы
	// показываем форму для отображения предупреждений.
	Если Отказ Тогда
		СтандартнаяОбработка = Ложь;
		ВыбраннаяФорма = Метаданные.ОбщиеФормы.ФормаСПредупреждением;
		Параметры.Вставить("ТекстПредупреждения", ТекстОшибки);
	КонецЕсли; 
	
КонецПроцедуры

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


В общем-то, готово.

Однако не могу не сообщить о своем отношении к приведенному решению. Во-первых, работать он будет только при интерактивном создании реализации на основании заказа. И только при использовании либо стандартных команд создания, либо при открытии формы с указанием стандартного имени документа (напр., Документ.РеализацияТоваровУслуг.ФормаОбъекта). При программном заполнении реализации методом "Заполнить()" проверка осуществляться не будет. Во-вторых, такой подход, равно как и прочие подобные "лайфхаки" затрудняют сопровождение продукта. Через пару месяцев Вы можете и не вспомнить о подобной реализации, а Ваш коллега-программист и вовсе потратит уйму времени, чтобы разобраться, как вообще происходит контроль данных, который срочно потребовалось доработать. Ну и в-третьих, использование метода "ВызватьИсключение" является стандартом разработки. Так работают типовые объекты, и именно к такому поведению 1С приучает пользователей.
https://its.1c.ru/db/v8std#content:2149184045:hdoc
2. spec8s 834 04.03.19 17:47 Сейчас в теме
Разработчики 1С везде используют ВызватьИсключение ТекстОшибки;

Если не хотите, можно в форме реализации, в событии ПередОткрытием выполнить свою проверку и там отказаться от дальнейшего открытия формы
Оставьте свое сообщение

Для получения уведомлений об ответах подключите телеграм бот:
Инфостарт бот