Переключение на Главную Страницу Страницы: 1 ОтправитьПечать
Горячая тема (более 10 ответов) Перехватывали-перехватывали, да не выперехватили (число прочтений - 6332 )
orefkov
1c++ developer
1c++ moderator
Отсутствует


I Love YaBB 2!

Сообщений: 896
Зарегистрирован: 20. Мая 2006
Перехватывали-перехватывали, да не выперехватили
19. Марта 2010 :: 11:41
Печать  
Такой вопрос.
Почему для обработчика перехвата можно использовать только метод КОПа?
В чем глубокий сермяжный смысл?
Или я плохо читал доку?
  
Наверх
 
IP записан
 
artbear
1c++ developer
1c++ moderator
Отсутствует


Эх, дайте что-нибудь новенькое
да полезное потести

Сообщений: 6303
Местоположение: Москва
Зарегистрирован: 19. Мая 2006
Пол: Мужской
Re: Перехватывали-перехватывали, да не выперехватили
Ответ #1 - 19. Марта 2010 :: 12:27
Печать  
Вообще вопрос не понятен.
напиши подробнее, в чем проблема?
тебе не нравится, что перехват идет через КОП-ы или что?
я не понимаю.
  

OpenConf developer :: http://openconf.1cpp.ru&&FormEx developer :: http://formex.dorex.ru&&1C++ active developer && tester :: www.1cpp.ru
Наверх
GTalkSkype/VoIPICQ  
IP записан
 
orefkov
1c++ developer
1c++ moderator
Отсутствует


I Love YaBB 2!

Сообщений: 896
Зарегистрирован: 20. Мая 2006
Re: Перехватывали-перехватывали, да не выперехватили
Ответ #2 - 19. Марта 2010 :: 12:31
Печать  
Угу. Почему допустим нельзя создать ВыполняемыйМодуль с методом ПриОткрытии, подключить его к перехвату, открыть док, отработать что надо в Выполняемом модуле, вернуть статусвозврата(0), отключить перехват, убить выполняемый модуль.
  
Наверх
 
IP записан
 
artbear
1c++ developer
1c++ moderator
Отсутствует


Эх, дайте что-нибудь новенькое
да полезное потести

Сообщений: 6303
Местоположение: Москва
Зарегистрирован: 19. Мая 2006
Пол: Мужской
Re: Перехватывали-перехватывали, да не выперехватили
Ответ #3 - 19. Марта 2010 :: 12:34
Печать  
В свое время посчитал, что через КОП надежнее и удобнее в плане сопровождения и анализа кода.
В принципе, никто не мешает создать класс на лету Улыбка
  

OpenConf developer :: http://openconf.1cpp.ru&&FormEx developer :: http://formex.dorex.ru&&1C++ active developer && tester :: www.1cpp.ru
Наверх
GTalkSkype/VoIPICQ  
IP записан
 
orefkov
1c++ developer
1c++ moderator
Отсутствует


I Love YaBB 2!

Сообщений: 896
Зарегистрирован: 20. Мая 2006
Re: Перехватывали-перехватывали, да не выперехватили
Ответ #4 - 20. Марта 2010 :: 19:40
Печать  
Все равно придется создавать класс 1С++.
А если я не хочу? Если у меня есть свой объект (наследник от CBLContext) с нужными методами?
Создавать на лету класс 1С++ - обертку над моим объектом?
Сорцы смотрел, вижу, что идет каст от CBLContext'а к CComponentClassImpl.
То есть просто передать любой объект с нужными методами не покатит?
Или мне надо какой-то интерфейс реализовать в своем объекте?
  
Наверх
 
IP записан
 
artbear
1c++ developer
1c++ moderator
Отсутствует


Эх, дайте что-нибудь новенькое
да полезное потести

Сообщений: 6303
Местоположение: Москва
Зарегистрирован: 19. Мая 2006
Пол: Мужской
Re: Перехватывали-перехватывали, да не выперехватили
Ответ #5 - 22. Марта 2010 :: 09:39
Печать  
orefkov писал(а) 20. Марта 2010 :: 19:40:
Все равно придется создавать класс 1С++.
А если я не хочу? Если у меня есть свой объект (наследник от CBLContext) с нужными методами?
Создавать на лету класс 1С++ - обертку над моим объектом?
Сорцы смотрел, вижу, что идет каст от CBLContext'а к CComponentClassImpl.
То есть просто передать любой объект с нужными методами не покатит?
Или мне надо какой-то интерфейс реализовать в своем объекте?

Нет, интерфейсы С++ для перехвата я не реализовывал, хотя это не очень сложно должно быть.
Пока только вариант создания класса 1С++ - обертки над твоим классом.
  

OpenConf developer :: http://openconf.1cpp.ru&&FormEx developer :: http://formex.dorex.ru&&1C++ active developer && tester :: www.1cpp.ru
Наверх
GTalkSkype/VoIPICQ  
IP записан
 
orefkov
1c++ developer
1c++ moderator
Отсутствует


I Love YaBB 2!

Сообщений: 896
Зарегистрирован: 20. Мая 2006
Re: Перехватывали-перехватывали, да не выперехватили
Ответ #6 - 22. Марта 2010 :: 13:46
Печать  
Понятненько
  
Наверх
 
IP записан
 
shmalevoz
Junior Member
**
Отсутствует


1C++ rocks!

Сообщений: 55
Зарегистрирован: 23. Апреля 2009
Re: Перехватывали-перехватывали, да не выперехватили
Ответ #7 - 22. Марта 2010 :: 17:25
Печать  
orefkov писал(а) 19. Марта 2010 :: 12:31:
Угу. Почему допустим нельзя создать ВыполняемыйМодуль с методом ПриОткрытии, подключить его к перехвату, открыть док, отработать что надо в Выполняемом модуле, вернуть статусвозврата(0), отключить перехват, убить выполняемый модуль.

Все это отлично работает и дает (по моим замерам) лучшие результаты.
  
Наверх
 
IP записан
 
orefkov
1c++ developer
1c++ moderator
Отсутствует


I Love YaBB 2!

Сообщений: 896
Зарегистрирован: 20. Мая 2006
Re: Перехватывали-перехватывали, да не выперехватили
Ответ #8 - 24. Марта 2010 :: 09:13
Печать  
shmalevoz писал(а) 22. Марта 2010 :: 17:25:
orefkov писал(а) 19. Марта 2010 :: 12:31:
Угу. Почему допустим нельзя создать ВыполняемыйМодуль с методом ПриОткрытии, подключить его к перехвату, открыть док, отработать что надо в Выполняемом модуле, вернуть статусвозврата(0), отключить перехват, убить выполняемый модуль.

Все это отлично работает и дает (по моим замерам) лучшие результаты.

То есть дока не соответствует реальности?
Проверю, как приспичит.
  
Наверх
 
IP записан
 
artbear
1c++ developer
1c++ moderator
Отсутствует


Эх, дайте что-нибудь новенькое
да полезное потести

Сообщений: 6303
Местоположение: Москва
Зарегистрирован: 19. Мая 2006
Пол: Мужской
Re: Перехватывали-перехватывали, да не выперехватили
Ответ #9 - 24. Марта 2010 :: 13:05
Печать  
shmalevoz писал(а) 22. Марта 2010 :: 17:25:
orefkov писал(а) 19. Марта 2010 :: 12:31:
Угу. Почему допустим нельзя создать ВыполняемыйМодуль с методом ПриОткрытии, подключить его к перехвату, открыть док, отработать что надо в Выполняемом модуле, вернуть статусвозврата(0), отключить перехват, убить выполняемый модуль.

Все это отлично работает и дает (по моим замерам) лучшие результаты.

Пример можешь выложить ?
Меня, как автора Перехватчика, это очень сильно порадует Улыбка
  

OpenConf developer :: http://openconf.1cpp.ru&&FormEx developer :: http://formex.dorex.ru&&1C++ active developer && tester :: www.1cpp.ru
Наверх
GTalkSkype/VoIPICQ  
IP записан
 
shmalevoz
Junior Member
**
Отсутствует


1C++ rocks!

Сообщений: 55
Зарегистрирован: 23. Апреля 2009
Re: Перехватывали-перехватывали, да не выперехватили
Ответ #10 - 24. Марта 2010 :: 18:47
Печать  
Код
Выбрать все
Функция ПолучитьШаблонПерехватаСобытий(СсылкаКонтекст)

	ТипКонтекста	= гСервис.ПолныйТипКонтекста(СсылкаКонтекст);
	Если гКэшНаличияДелегатов.НайтиСтроку("ОсновнойИндекс", ТипКонтекста, 0, 1) = 0 Тогда

		---------------
		// Построим шаблон
		ШаблонМетодов	= "";
		гТаблицаШаблонов.ВыбратьСтроки();
		Пока гТаблицаШаблонов.ПолучитьСтроку() = 1 Цикл

			ИдентификаторСобытия		= гТаблицаШаблонов.Ссылка.ПолучитьИдентификаторСобытия();
			ПубликоватьСобытияДоПосле	= гТаблицаШаблонов.Ссылка.ПубликоватьСобытияДоПосле();
			ЕстьДелегатыСобытия			= 0;
			Если ПубликоватьСобытияДоПосле = 1 Тогда
				ЕстьДелегатыСобытия	= Макс(гМенеджерСобытий.ЕстьДелегатыСобытия("ДоСобытия" + ИдентификаторСобытия, СсылкаКонтекст), гМенеджерСобытий.ЕстьДелегатыСобытия("ПослеСобытия"
 + ИдентификаторСобытия, СсылкаКонтекст));
			Иначе
				ЕстьДелегатыСобытия	= гМенеджерСобытий.ЕстьДелегатыСобытия(ИдентификаторСобытия, СсылкаКонтекст);
			КонецЕсли;
			Если ЕстьДелегатыСобытия = 0 Тогда
				Продолжить;
			КонецЕсли;
			Если гТаблицаШаблонов.Ссылка.ПринадлежитКонтексту(ТипКонтекста) = 0 Тогда
				Продолжить;
			КонецЕсли;

			КоличествоПараметров		= гТаблицаШаблонов.Ссылка.ПолучитьКоличествоПараметров();
			СтрокаПараметров			= "";
			Для НомерПараметра = 1 По КоличествоПараметров Цикл
				СтрокаПараметров	= СтрокаПараметров + ",Параметр" + НомерПараметра;
			КонецЦикла;

			ШаблонМетодов	= ШаблонМетодов + "
			| // Перехват события " + ИдентификаторСобытия + "
			| Функция " + ИдентификаторСобытия + "(" + Прав(СтрокаПараметров, СтрДлина(СтрокаПараметров) - 1) + ") Экспорт
			|	Событие			= СоздатьОбъект(""Общие.Событие"");
			|	Результат		= 1;
			|";

			Если ПубликоватьСобытияДоПосле = 1 Тогда
				ШаблонМетодов	= ШаблонМетодов + "
				|	Результат	= Событие.Опубликовать(""ДоСобытия" + ИдентификаторСобытия + """, гСсылкаКонтекст" + СтрокаПараметров + ");
				|";
			Иначе
				ШаблонМетодов	= ШаблонМетодов + "
				|	Результат	= Событие.Опубликовать(""" + ИдентификаторСобытия + """, гСсылкаКонтекст" + СтрокаПараметров + ");
				|";
			КонецЕсли;
			ШаблонМетодов	= ШаблонМетодов + "
			|	Если Результат = 1 Тогда
			|		Результат	= гПерехватчик.ВыполнитьОригинальноеСобытиеГК(гСсылкаКонтекст, """ + ИдентификаторСобытия + """" + СтрокаПараметров + ");
			|	КонецЕсли;
			|";
			Если ПубликоватьСобытияДоПосле = 1 Тогда
				ШаблонМетодов	= ШаблонМетодов + "
				| Если Результат = 1 Тогда
				|	Результат	= Событие.Опубликовать(""ПослеСобытия" + ИдентификаторСобытия + """, гСсылкаКонтекст" + СтрокаПараметров + ");
				| КонецЕсли;
				|";
			КонецЕсли;
			ШаблонМетодов	= ШаблонМетодов + "
			| 	Возврат Результат;
			| КонецФункции
			|";
		КонецЦикла;

		Если ПустаяСтрока(ШаблонМетодов) = 0 Тогда

			ШаблонМетодов	= "
			|
			| Перем гСсылкаКонтекст, гПерехватчик;
			|
			| Процедура УстановитьПараметры(СсылкаКонтекст) Экспорт
			|	гСсылкаКонтекст		= СсылкаКонтекст;
			|	гПерехватчик		= СоздатьОбъект(""Перехватчик"");
			| КонецПроцедуры
			|
			|" + ШаблонМетодов;

		КонецЕсли;

		гКэшНаличияДелегатов.НоваяСтрока();
		гКэшНаличияДелегатов.Индекс	= ТипКонтекста;
		гКэшНаличияДелегатов.Шаблон	= ШаблонМетодов;

	КонецЕсли;

	Возврат гКэшНаличияДелегатов.Шаблон;
КонецФункции // ПолучитьШаблонПерехватаСобытий()

...


// ОбработатьСобытие_СозданиеКонтекста(Параметры)
//
// Параметры:
//  Параметры
//
// Возвращаемое значение:
//  Нет
//
// Описание:
//  ТекстОписания
//
Функция ОбработатьСобытие_СозданиеКонтекста(Параметры)

	Результат		= 1;
	СсылкаКонтекст	= Параметры.ПолучитьЗначение(1);
	ТекстМодуля		= ПолучитьШаблонПерехватаСобытий(СсылкаКонтекст);

	Если ПустаяСтрока(ТекстМодуля) = 1 Тогда
		Возврат Результат;
	КонецЕсли;

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

	Возврат Результат;
КонецФункции // ОбработатьСобытие_СозданиеКонтекста()


 



Это все относительно событий контекста, для которых перехват всех событий ведет к излишнему расходу ресурсов (что очень заметно под linux). Такое же можно наверное повторить и для глобальных перехватов, но их не так много, и смысла в этом особо не ощущается.

Как кусок кода.
  
Наверх
 
IP записан
 
artbear
1c++ developer
1c++ moderator
Отсутствует


Эх, дайте что-нибудь новенькое
да полезное потести

Сообщений: 6303
Местоположение: Москва
Зарегистрирован: 19. Мая 2006
Пол: Мужской
Re: Перехватывали-перехватывали, да не выперехватили
Ответ #11 - 24. Августа 2010 :: 14:46
Печать  
orefkov писал(а) 20. Марта 2010 :: 19:40:
А если я не хочу? Если у меня есть свой объект (наследник от CBLContext) с нужными методами?
То есть просто передать любой объект с нужными методами не покатит?

Добавил возможность устанавливать любые контексты (Классы, ВыполняемыйМодуль, наследники от контекстов) в качестве обработчиков-перехвата Улыбка - это оказалось совсем несложно.
например, можете попробовать перехватить событие в ВыполняемомМодуле.

Приложил файл с тестовым вариантом компоненты - сделан на базе 3.2.2.3
Прошу проверить работу. Мои собственные автоматические тесты Перехватчика проходят все!

Вот кода рабочего теста из конфигурации тестирования 1С++
Цитата:
Процедура Тест_ПроизвольныйМодуль_ПерехватГрупповогоКонтекста_Событие() Экспорт
     Сам = Сам();

     ПутьКФорме = КаталогИБ()+"ExtForms\UnitTests\КлассПерехватчикГК_События.ert";
     Конт = Сам.ОткрытьФорму("Отчет", , ПутьКФорме);

     Журнал = Конт.Форма.Параметр; // TurboBL

     текстМодуля = "
           |Перем Журнал Экспорт;
           |Перем КонтФормы;
           |
           |Процедура Инициализация(конт, Журнал1) Экспорт
           |      КонтФормы = Конт;
           |
           |      Журнал = Журнал1;
           |      Журнал.ДобавитьЗапись(""ВМ::Инициализация"");
           |
           |КонецПроцедуры
           |            
           |Процедура Событие_ПриЗакрытии() Экспорт
           |      Журнал.ДобавитьЗапись(""ВМ::Событие_ПриЗакрытии"");
           |
           |      Перехватчик = СоздатьОбъект(""Перехватчик"");
           |      Перехватчик.ВыполнитьОригинальноеСобытиеГК(КонтФормы, ""ПриЗакрытии"");
           |КонецПроцедуры
           |";
     ВМ = СоздатьОбъект("ВыполняемыйМодуль");
     ВМ.УстановитьМодуль(текстМодуля);
     ВМ.КомпилироватьИВыполнитьМодуль();
     
     ВМ.Инициализация(Конт, Журнал);

     Перехватчик = СоздатьОбъект("Перехватчик");
     Перехватчик.ПерехватитьСобытияГК(Конт, ВМ);

     ВМ = 0;
     Сам.ЗакрытьФорму();

     Сам.ПроверитьРавенство(Журнал.стрЖурнал, "Форма::ПриОткрытии, ВМ::Инициализация, ВМ::Событие_ПриЗакрытии, Форма::ПриЗакрытии");
КонецПроцедуры
« Последняя редакция: 25. Августа 2010 :: 13:43 - artbear »  

icpp_3_2_2_3_Interceptor.7z ( 490 KB | Загрузки )

OpenConf developer :: http://openconf.1cpp.ru&&FormEx developer :: http://formex.dorex.ru&&1C++ active developer && tester :: www.1cpp.ru
Наверх
GTalkSkype/VoIPICQ  
IP записан
 
kms
1c++ power user
1c++ moderator
Отсутствует


я хочу, чтоб сюда проложили
дорогу оттуда...

Сообщений: 4632
Зарегистрирован: 19. Мая 2006
Re: Перехватывали-перехватывали, да не выперехватили
Ответ #12 - 25. Августа 2010 :: 18:13
Печать  
Изменения включены в состав icpp:
http://www.1cpp.ru/forum/YaBB.pl?num=1281717242/33#33
  

De quelle planète es-tu?
Наверх
 
IP записан
 
Переключение на Главную Страницу Страницы: 1
ОтправитьПечать