Перейти к публикации

Программа на VisualBasic - как её остановить?


asd

Рекомендованные сообщения

Я написал программу на VB с использованием Windows Forms. Программа запускается из под NX как user function. В окне программы есть кнопка, запускающая циклическую процедуру, обрабатывающую группу файлов. Эта процедура, в зависимости от количества файлов, может быть очень длительной и хотелось бы иметь нормальный способ её прерывания из самой программы.

Я вставил специальную кнопку для остановки и внёс соответствующие изменения в программу, чтобы процедура прерывалась после нажатия кнопки, в начале очередного цикла. Нажатия на эту кнопку, сколь угодно многочисленные, имеют нулевой эффект. Такое впечатление, что во время работы процедуры клики мыши вообще до окна приложения не доходят (за исключением "крестика" и кнопок рядом с ним). Действительно ли это так и нельзя ли что нибудь с этим сделать?

Ссылка на сообщение
Поделиться на других сайтах


Ну наверное так и должно быть, иначе был бы полный бред,

ведь выполнение идет в одном потоке.

Как вариант - выделить цикл в отдельный поток, и анализировать в нем

глобальную переменную (которая меняется при нажатии кнопки останова цикла).

Примера нет, т.к. с VBA не работаю.

Ссылка на сообщение
Поделиться на других сайтах

В общем, проблему решил, через DoEvents. Работает плохо, в смысле далеко не на каждый клик срабатывает, но хоть что-то.

Как вариант - выделить цикл в отдельный поток, и анализировать в нем

глобальную переменную (которая меняется при нажатии кнопки останова цикла).

Да, прочел и об этом тоже и попробовал. К сожалению, NX рушится на первом же проходе цикла. Даже выяснил на какой команде, но что толку... Хотя успеваю увидеть, что кнопка срабатывает мгновенно и надежно.
Ссылка на сообщение
Поделиться на других сайтах

Я написал программу на VB с использованием Windows Forms. Программа запускается из под NX как user function. В окне программы есть кнопка, запускающая циклическую процедуру, обрабатывающую группу файлов. Эта процедура, в зависимости от количества файлов, может быть очень длительной и хотелось бы иметь нормальный способ её прерывания из самой программы.

Я вставил специальную кнопку для остановки и внёс соответствующие изменения в программу, чтобы процедура прерывалась после нажатия кнопки, в начале очередного цикла. Нажатия на эту кнопку, сколь угодно многочисленные, имеют нулевой эффект. Такое впечатление, что во время работы процедуры клики мыши вообще до окна приложения не доходят (за исключением "крестика" и кнопок рядом с ним). Действительно ли это так и нельзя ли что нибудь с этим сделать?

В общем, проблему решил, через DoEvents. Работает плохо, в смысле далеко не на каждый клик срабатывает, но хоть что-то.

Да, прочел и об этом тоже и попробовал. К сожалению, NX рушится на первом же проходе цикла. Даже выяснил на какой команде, но что толку... Хотя успеваю увидеть, что кнопка срабатывает мгновенно и надежно.

А нажатие клавиш `ESC`, `CTRL+С` или `CTRL+BREAK` не вызывает прерывание выполнения ? Или нужна именно кнопка?

Если вызывает, то можно попробовать что-то типа:

' периодически активировать Вашу программу на VB ипередавать ей значение `CTRL+BREAK`

AppActivate ReturnValue"

SendKeys "^{BREAK}", True ' Send `CTRL+BREAK` to...

Хотя тут не понятно: Вы пишите про "VB", `koner` говорит про `VBA` ?!... Так с чем же мы имеем дело?

ИМХО Ваша `user function` передает полное управление под NX и пока NX не отработает все, `Windows Forms` никакие события не принимает...

Еще есть события `MouseDown`, `Stop`...

Еще вариант: в программе определять "счетчик", равный допустим 10 или 50 процентов от кол-ва обрабатываемых файлов. По достижениии этого кол-ва прерывать(делать паузу) программу. Этот счетчик вывести на форму, чтобы его можно было менять - получится что-то типа "настроек"... :-)

PS я в NX не работал, только в VB (не VBA) - (через exe-файлы) для SW, ACAD, Corel, MSOffice...

Ссылка на сообщение
Поделиться на других сайтах

А нажатие клавиш `ESC`, `CTRL+С` или `CTRL+BREAK` не вызывает прерывание выполнения ?

Нет, не вызывает.

Хотя тут не понятно: Вы пишите про "VB", `koner` говорит про `VBA` ?!... Так с чем же мы имеем дело?

Мы имеем дело с программой на VB.net, использующей функции NXOpen API.

ИМХО Ваша `user function` передает полное управление под NX и пока NX не отработает все, `Windows Forms` никакие события не принимает...

Я тоже думал что-то вроде этого, но теперь понимаю что это не совсем так. Главное окно моей `user function` передает полное управление длинной процедуре, входящей в эту же `user function`. Конечно, эта процедура в свою очередь использует функции NXOpen API, но это не принципиально, поскольку ни одна из этих функций в отдельности не исполняется слишком долго, то есть управление в мою длинную процедуру возвращается достаточно часто.

То есть `Windows Forms` действительно не принимает никаких событий (если не использовать второй поток или DoEvents или что-то мне пока неизвестное), но NX к этому отношения не имеет. Если бы я это понял сразу, то и вопрос свой здесь не было бы нужды задавать.

А вот к чему NX может иметь отношение - почему он не хочет надежно работать при использовании второго потока? Это ограничение NXOpen?

Ссылка на сообщение
Поделиться на других сайтах

...

А вот к чему NX может иметь отношение - почему он не хочет надежно работать при использовании второго потока? Это ограничение NXOpen?

Вот тут я пас - ничего не могу сказать - не владею темой :-(
Ссылка на сообщение
Поделиться на других сайтах

В UG_Open есть функции 

UF_ABORT_enable_abort ();

UF_ABORT_ask_flag_status (&abort_flag); флаг меняется в зависимости от нажатой кнопки СТОП. 

Соответственно, если процедура надолго затягивается - можно нажать кнопку " Stop" - и все остановится. 

Но это - в UG_Open, как в VISUAL BASIC - не знаю. 

Ссылка на сообщение
Поделиться на других сайтах

С потоками самому стало интересно.

Попробовал - все получилось. Кому интересно привожу код

Язык С#, VS2003, NX4.

public class Class1	{		public static void Main()		{			Form1 myForm = new Form1();			myForm.ShowDialog();		}		public static int GetUnloadOption(string arg)		{			return (int)Session.LibraryUnloadOption.Immediately;		}	}using System;using System.Threading;using System.Windows.Forms;public class MyClass	{ 	public  Form1 F=null;	public void NewProc()	{ int i=0;		while(true)				{					Thread.Sleep(100);					F.textBox1.Text=i.ToString();					i++;					if (i>100000) i=-1000000;				}			}	}public class Form1 : System.Windows.Forms.Form	{		private System.Windows.Forms.Button button1;		private System.Windows.Forms.Button button2;		public System.Windows.Forms.TextBox textBox1;		private System.ComponentModel.Container components = null;		public Thread Potok;		public Form1()		{			InitializeComponent();			Potok=null;		}...		private void button1_Click(object sender, System.EventArgs e)		{			MyClass A=new MyClass(); A.F=this;			Potok = new Thread(new ThreadStart(A.NewProc));			Potok.Start();		}		private void button2_Click(object sender, System.EventArgs e)		{			Potok.Abort(); 		}	}
Ссылка на сообщение
Поделиться на других сайтах

В UG_Open есть функции 

UF_ABORT_enable_abort ();

UF_ABORT_ask_flag_status (&abort_flag); флаг меняется в зависимости от нажатой кнопки СТОП. 

Нашел это хозяйство в NXOpen и попробовал. К сожалению, в моей программе это работает плохо. То ли флаг не всегда устанавливается, то ли иногда успевает сброситься, не знаю чем, пока я его проверю. Но самое неприятное - дается только одна попытка. Один раз нажал СТОП - и окошко с кнопкой пропало навсегда, то есть пока я не перезапущу всю свою user function. Может есть способ его программно вернуть обратно?
Ссылка на сообщение
Поделиться на других сайтах
  • 2 недели спустя...

Вот тут я пас - ничего не могу сказать - не владею темой :-(

Просто для информации

Все чуть сложнее чем потоки

Компиляция с ряда новомодных языков NET Java C++/CLI(Common Language Interface) происходит в псевдокод

и выполняется естественно на виртуальной машине

Ссылка на сообщение
Поделиться на других сайтах
  • 3 недели спустя...

Сопутствующий оффтопик на тему:

Session.LibraryUnloadOption.Immediately

Я обратил внимание, что буквально во всех примерах кода , которые я видел, используется именно Immediately. Возможно ли вообще использовать другие варианты (Explicitly, AtTermination)? У меня не получается. Пока работаешь с одним файлом, то всё нормально, но стоит его закрыть и открыть заново - при попытке работать с программой (не с той, о которой я начинал тему, с другой) она даёт сбой: "Attempt to use an object that is not alive". Это в принципе исправляется как-то?

Изменено пользователем asd
Ссылка на сообщение
Поделиться на других сайтах
  • 2 года спустя...

А вот к чему NX может иметь отношение - почему он не хочет надежно работать при использовании второго потока? Это ограничение NXOpen?

Не прошло и четырёх лет как я понял, в чём дело. :) Кому интересно:

Я начинал программу с создания окна. Это окно загружалось NX-ом в его собственный поток. Потом я запускал свою долгоиграющую функцию во втором потоке и пытался вызывать функции NX, который, естественно, работает в первом потоке. Такие вызовы недопустимы.

Нужно всё делать наоборот. После запуска приложения создать окно интерфейса во втором потоке, а свои функции запускать в первом потоке, чтобы они имели свободный доступ к NX.

Конечно, многопоточное программирование - не сахар, и придётся узнать много нового. Но в принципе этот подход работает.

Ссылка на сообщение
Поделиться на других сайтах

Уже заслуживает уважения то, что на протяжении стольких лет автор темы не оставил начатое дело, нашел решение, поделился им. По-моему - в этом залог успеха - если каждый день по чуть-чуть двигаться в каком-то одном направлении, любую поставленную цель можно достичь.

Ссылка на сообщение
Поделиться на других сайтах

Присоединяйтесь к обсуждению

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

Гость
Ответить в тему...

×   Вставлено в виде отформатированного текста.   Вставить в виде обычного текста

  Разрешено не более 75 эмодзи.

×   Ваша ссылка была автоматически встроена.   Отобразить как ссылку

×   Ваш предыдущий контент был восстановлен.   Очистить редактор

×   Вы не можете вставить изображения напрямую. Загрузите или вставьте изображения по ссылке.

  • Сейчас на странице   0 пользователей

    Нет пользователей, просматривающих эту страницу.



×
×
  • Создать...