Добро пожаловать в форум, Guest  >>   Войти | Регистрация | Поиск | Правила | В избранное | Подписаться
Все форумы / Delphi Новый топик    Ответить
Топик располагается на нескольких страницах: Ctrl  назад   1 [2] 3 4 5   вперед  Ctrl      все
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
Bellic
Member

Откуда: Ростов-на-Дону
Сообщений: 123
Няшик
Хотя. Ты используешь модуль System.SysUtils ????

Ну в шапке кода написано - я код свой проверенный, рабочий выложил!

У Вас возможно реализация красивее с CASE выглядит, но я свой Тестовый писал не на выставку, а чтоб понятней было что-куда!
Посему - не придирайтесь так уж!
Для меня важнее было совсем другое!

И всеж - я не понимаю, почему Функция в перемешку с Процедурой???
Может всеж правильнее было так(?):
+
function IndexIArray(const str: string; const arr: TArray<string>): Integer;
  var
    I: Integer;
  begin
    for I := Low(arr) to High(arr) do
      if str.ToLower = arr[I].ToLower then
        exit(I);
  end;
//------------------------------------------------------------------------------
procedure TMainForm.AllButtonClick(Sender: TObject);
var
  obj: TButton;
begin
  obj := TButton(Sender);
  if not SButtonEnebled then
  begin
    if obj.Name = 'SButton' then
      SButtonEnebled := true
    else
      MMemo.Lines.Add('Кряя. Надо нажать на SButton');
    exit;
  end;

  case IndexIArray(obj.Name, ['Button1', 'Button2', 'Button3']) of
    0:
      begin
        MMemo.Lines.Add('Нажата кн."Продолжить"');
      end;
    1:
      begin
        MMemo.Lines.Add('Нажата кн."Пропустить"');
      end;
    2:
      begin
        MMemo.Lines.Add('Счет Остановлен!');
      end;
    3:
      begin
        Exit;
      end;
  end;
  SButtonEnebled := False;
end;
И следующие две строчки - исправьте согласно правил Дэлфи!
+
if str.ToLower = arr[I].ToLower then
        exit(I);
3 янв 18, 03:03    [21079655]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
Bellic
Member

Откуда: Ростов-на-Дону
Сообщений: 123
AllButtonClick - процедура клика на каждую из кнопок?
3 янв 18, 03:06    [21079657]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
Bellic
Member

Откуда: Ростов-на-Дону
Сообщений: 123
Няшик, для меня было важно...эээ, попробую выразиться правильным языком:
- важно было то, что передача флагов вполне возможна в Рун-Тайме основного цикла процедуры, при этом процедуры обработки кликов по клавишам отработали как-бы параллельно, выполнив всего лишь одну операцию FlagХ:=True;
Остальной анализ и разветвления - уже опять в основной процедуре цикла!

Все остальное - мелочи вариантов реализации!

И еще - Вы не правильно сделали! Ваши "MMemo.Lines.Add" в CASE отработали в обработчике нажатия клавиш, а Основная процедура осталась без результата нажатия! А для меня именно это нужно было!
Можно конечно вместо "MMemo.Lines.Add" написать "FlagХ:=True;", а уже в основной процедуре анализировать их и выполнять нужную ветку. Но все ж!
3 янв 18, 03:26    [21079667]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
Няшик
Member

Откуда: Екатеринбург
Сообщений: 796
Bellic
AllButtonClick - процедура клика на каждую из кнопок?


Верно.

Bellic
а чтоб понятней было что-куда!


А вышло так, что всех запутал. Неправильно реализованной задачей.

Bellic
Функция в перемешку с Процедурой???


Она не в перемешку, она в своей области видимости.
Т.е в общей области недоступна.


Bellic
И следующие две строчки - исправьте согласно правил Дэлфи!


Не понмиаю, что у вас не так. Всё по стандартам record helper for
3 янв 18, 03:28    [21079670]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
Няшик
Member

Откуда: Екатеринбург
Сообщений: 796
Bellic,

Зачем нужны какие то флаги???

Почитайте о компоненте ApplicationEvents и установите нормальный обработчик для клавиш нажатых

Или нужна глобальная область??? (Вне программы)
3 янв 18, 03:36    [21079675]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
Bellic
Member

Откуда: Ростов-на-Дону
Сообщений: 123
Няшик
А вышло так, что всех запутал. Неправильно реализованной задачей.
Я не вижу - в чем запутал всех?
Изначально думал, что придется запускать еще один Доп.Поток, но ситуация решилась и без него!
Что не так?

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

Не понмиаю, что у вас не так. Всё по стандартам record helper for
Картинка с другого сайта.
3 янв 18, 03:41    [21079677]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
Няшик
Member

Откуда: Екатеринбург
Сообщений: 796
Bellic
Что не так?


Описанием задачи.

Многие люди, что видят - то и думают, забывая про - то, что ТС сам не знает как реализовать правильно.

К сообщению приложен файл. Размер - 25Kb
3 янв 18, 03:44    [21079680]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
Bellic
Member

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

Почитайте о компоненте ApplicationEvents и установите нормальный обработчик для клавиш нажатых
А вот за подсказку - при много благодарен! Но похоже изучать и смотреть - пригодиться ли оно мне - уже буду утром!..)))
3 янв 18, 03:55    [21079684]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
YuRock
Member

Откуда: Донецк
Сообщений: 2609
Bellic
важно было то, что передача флагов вполне возможна в Рун-Тайме основного цикла процедуры, при этом процедуры обработки кликов по клавишам

Это не основной цикл, а дополнительный и полностью бессмысленный.
Основной крутится внутри Application.Run - нормальный цикл, ожидающий события получения сообщения, а не хрень со Sleep и ProcessMessages.

Тебе не нужны ни флаги ни цикл. Назначь кнопкам один обработчик (в object inspector на вкладке events) - это и будет твоя "процедура".
И установи им разное значение свойства Tag (в object inspector на вкладке properties). Это и будут твои флаги.

И в этой своей "основной процедуре" просто пиши
if TButton( Sender ).Tag = 2 then...
3 янв 18, 04:35    [21079695]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
Няшик
Member

Откуда: Екатеринбург
Сообщений: 796
Не благодари. Поставь компонент ApplicationEvents и на него событие onMessage

+
unit Unit1;

interface

uses
  Winapi.Windows, Winapi.Messages, System.SysUtils, System.Variants,
  System.Classes, Vcl.Graphics,
  Vcl.Controls, Vcl.Forms, Vcl.Dialogs, Vcl.StdCtrls, Vcl.AppEvnts;

type
  TForm1 = class(TForm)
    Button1: TButton;
    Button2: TButton;
    Button3: TButton;
    SButton: TButton;
    Memo1: TMemo;
    ApplicationEvents1: TApplicationEvents;
    procedure ApplicationEvents1Message(var Msg: tagMSG; var Handled: Boolean);
  private
    SButtonEnebled: Boolean;
    { Private declarations }
  public
    { Public declarations }
  end;

var
  Form1: TForm1;

implementation

{$R *.dfm}

procedure TForm1.ApplicationEvents1Message(var Msg: tagMSG;
  var Handled: Boolean);

var
  ActiveHandle, idx: NativeInt;
  str: string;
  function IndexIArray(const str: Integer; const arr: TArray<Integer>): Integer;
  var
    I: Integer;
  begin
    for I := Low(arr) to High(arr) do
    begin
      ActiveHandle := arr[I];
      if str = ActiveHandle then
        exit(I);
    end;
    ActiveHandle := 0;
  end;

begin
  if Msg.message = 513 then
  begin
    idx := IndexIArray(Msg.hwnd, [Button1.Handle, Button2.Handle,
      Button3.Handle, SButton.Handle]);

    if not SButtonEnebled then
    begin
      if ActiveHandle = SButton.Handle then
        SButtonEnebled := true
      else
        Memo1.Lines.Add('Кряя. Надо нажать на SButton');
      exit;
    end;

    case idx of
      0:
        begin
          Memo1.Lines.Add('Нажата кн."Продолжить"');
        end;
      1:
        begin
          Memo1.Lines.Add('Нажата кн."Пропустить"');
        end;
      2:
        begin
          Memo1.Lines.Add('Счет Остановлен!');
        end;
      3:
        exit;
    end;
    SButtonEnebled := false;
  end
  else if Msg.message = 257 then
  begin
    Memo1.Lines.Add('Нажата кнопка: ' + chr(Msg.wParam));
  end;

end;

end.
3 янв 18, 04:40    [21079701]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
Няшик
Member

Откуда: Екатеринбург
Сообщений: 796
Небольшой фикс
   end;
    ActiveHandle := -1;
  end;
3 янв 18, 05:30    [21079712]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
Vizit0r
Member

Откуда:
Сообщений: 463
Няшик, ты знаешь толк в извращениях.
Массив, поиск в нем по имени...и все это вместо того, чтобы трем кнопкам проставить Tag от нуля до двух, и сверяться с ним.
3 янв 18, 10:28    [21079786]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
makhaon
Member

Откуда: A galaxy far far away
Сообщений: 2193
Няшику, по последнему коду: TArray<Integer>, надежнее массив NativeUInt'ов, быстрее и проще TArray.BinarySearch, хотя в случае четырёх членов, думаю, пофиг.
YuRock
Это не основной цикл, а дополнительный и полностью бессмысленный.

Я так понимаю, что у него всё крутится в одном потоке и ему нужно как-то 'придержать' работу кода до нажатия на кнопки, которые находятся на форме.
3 янв 18, 10:54    [21079809]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
makhaon
Member

Откуда: A galaxy far far away
Сообщений: 2193
Vizit0r,

+1, проще case по тэгу. для четырёх то кнопок )
3 янв 18, 10:55    [21079811]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
makhaon
Member

Откуда: A galaxy far far away
Сообщений: 2193
Много думал, почему няшик так хитро делает. То названия, то зачем-то хендлы (причем не совсем верно - handle не integer ни разу, можно нарваться на глюки). Почему не просто tag? Боюсь, няшик, что картинку, которую ты постил, можешь применить и к себе
3 янв 18, 11:02    [21079818]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
makhaon
Member

Откуда: A galaxy far far away
Сообщений: 2193
Ладно, за деревьями леса не видно, как обычно :) Мой хрустальный шар выдал следующее. ТСу нужно что-то считать. Потом остановить счет, дождаться реакции нажатия на кнопку на этой же форме, где идёт расчет, и дальше продолжить, возможно в зависимости от того, что нажали. Если 'расчет' довольно быстрый, то, думаю, можно попробовать основным потоком обойтись. В общем - ждём пока нормального описания того, что нужно. Иначе можно долго гадать.
3 янв 18, 11:10    [21079823]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
Bellic
Member

Откуда: Ростов-на-Дону
Сообщений: 123
Няшик
Не благодари. Поставь компонент ApplicationEvents и на него событие onMessage
idx := IndexIArray(Msg.hwnd, [Button1.Handle, Button2.Handle,
      Button3.Handle, SButton.Handle]);
[dcc32 Error] Main_Module.pas(166): E2010 Incompatible types: 'System.TArray<System.Integer>' and 'Set' !!!

Возможно я не прав, Няшик, а Ваша процедура через себя все События Windows будет пропускать?
Может для начало нужно было отловить нажатие левой кнопки мыши (WM_LBUTTONDOWN), а потом проанализировать - а не по нужной ли кнопке мацнул юзер? Или из WM_COMMAND можно сразу Хэндл кнопки узнать?!
Я не иронизирую вовсе, просто в этих делах мало пока понимаю! Посему - убедительно прошу, проверяйте свой код перед публикацией и желательно с компиляцией - не хочется искать ошибки в чужих творениях!
Кстати - Вы привели обработчик событий, а что же в это время будет делать основной цикл в Осн.процедуре? Я про вот это имел ввиду:
while True do
          begin
               for i := 0 to 10 do
                     begin
                        ...
                     end;
          end;

makhaon
Я так понимаю, что у него всё крутится в одном потоке и ему нужно как-то 'придержать' работу кода до нажатия на кнопки, которые находятся на форме.
Браво!!! Совершенно верно! я вроде так и объяснял, не вдаваясь в подробности, даже Тестовый код приближенный к реальному воспроизвел!
Только маленькое уточнение! - Не "придержать работу", а после выбора юзером - продолжить выполнение по алгоритму, пропустить его часть или выйти с сохранением результата, полученного на это время.

makhaon
ТСу нужно что-то считать. Потом остановить счет, дождаться реакции нажатия на кнопку на этой же форме, где идёт расчет, и дальше продолжить, возможно в зависимости от того, что нажали. Если 'расчет' довольно быстрый, то, думаю, можно попробовать основным потоком обойтись.
И тут - Ваш хрустальный шар правильно предсказал!..)))

makhaon
В общем - ждём пока нормального описания того, что нужно. Иначе можно долго гадать.
Уже и не знаю, как упростить описание "Задания", что бы не грузить лишней информацией!? Ну не всю же процедуру сюда реальную копировать?
Есть предложение - давайте я попробую еще раз сформулировать задачу, но пусть это будет уже Новый топик, ибо этот звучит как "Обработка нажатия трех кнопок в параллельном потоке", а о потоках вроде как уже не говорим!
Модераторы могут возмутиться!
Иль тут продолжить?
3 янв 18, 12:06    [21079883]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
YuRock
Member

Откуда: Донецк
Сообщений: 2609
Vizit0r
Массив, поиск в нем по имени...и все это вместо того, чтобы трем кнопкам проставить Tag от нуля до двух, и сверяться с ним.

Можно даже проще.
if Sender = Button2 then
3 янв 18, 12:13    [21079892]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
YuRock
Member

Откуда: Донецк
Сообщений: 2609
Bellic
Уже и не знаю, как упростить описание "Задания", что бы не грузить лишней информацией!? Ну не всю же процедуру сюда реальную копировать?

Нет, процедуру не надо уже, упаси бог. Нужно "Задание" сюда скопировать.
3 янв 18, 12:16    [21079902]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
makhaon
Member

Откуда: A galaxy far far away
Сообщений: 2193
Bellic,

Понятно, я так и думал. Можно попробовать сделать так:
1. Считаем всё до момента необходимости выбора.
2. Включаем visible, либо, лучше, делаем enable кнопкам.
3. Ждём безо всяких циклов когда юзер нажмёт какую-то кнопку.
4. В обработчиках OnClick кнопок развешиваем остальные куски кода, в зависимости от того, что нажмут.
Согласен, что батонокидательство. Но, думаю, в этом случае, допустимое.
3 янв 18, 12:18    [21079915]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
Bellic
Member

Откуда: Ростов-на-Дону
Сообщений: 123
YuRock
Можно даже проще.
if Sender = Button2 then
Не пойму - зачем лишние проверки и массивы?
Чем плох код из этого сообщения?
Тем, что на каждой из кнопок - мизерный обработчик висит? - Возможно можно написать и Общий обработчик для трех кнопок, но тогда внутри него придется развернуть анализ...(
Или Три флага смущают?
3 янв 18, 12:22    [21079931]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
YuRock
Member

Откуда: Донецк
Сообщений: 2609
Bellic
но тогда внутри него придется развернуть анализ

Это именно этот анализ:
if Flag2=True then begin

И, это, еще так можно писать, чтоб точно враги не догадались:
if (Flag2=True)=True then begin


(это я к тому, что булево значение уже не надо сравнивать с True, вообще не надо ни с чем сравнивать, оно готово для использования в условиях - if Flag2 then)
3 янв 18, 12:34    [21079956]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
makhaon
Member

Откуда: A galaxy far far away
Сообщений: 2193
Bellic,

Плох Application.ProcessMessages + Sleep. Тем, что занимает ресурсы, сильно ухудшает отзывчивость программы, заставляя основной поток спать, потенциально может привести к трудноуловимым багам.
3 янв 18, 12:34    [21079958]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
YuRock
Member

Откуда: Донецк
Сообщений: 2609
Bellic
зачем лишние проверки и массивы?

Т.ч. проверок столько же, только лишних переменных, обработчиков и логики меньше.
А зачем массивы - я тоже не знаю.
3 янв 18, 12:34    [21079960]     Ответить | Цитировать Сообщить модератору
 Re: Обработка нажатия трех кнопок в параллельном потоке  [new]
makhaon
Member

Откуда: A galaxy far far away
Сообщений: 2193
автор
но тогда внутри него придется развернуть анализ


Вот весь анализ

case (Sender as TComponent).Tag of:
 0: {делаем что-то};
 1: {делаем что-то};
 2: {делаем что-то}; 
end;


Тэги в кнопках проставить только.
3 янв 18, 12:37    [21079963]     Ответить | Цитировать Сообщить модератору
Топик располагается на нескольких страницах: Ctrl  назад   1 [2] 3 4 5   вперед  Ctrl      все
Все форумы / Delphi Ответить