Nano Hash - криптовалюты, майнинг, программирование

Вызов события Timer Tick после включения таймера в другом классе

Я должен делать что-то совершенно неправильно, но я не могу понять это. У меня есть форма, и я добавляю в VS таймер. У меня также есть класс, который следит за запуском приложения (notepad.exe). Когда событие приходит, предполагается включить таймер, установить интервал и на каждом тике что-то делать (например, запустить окно сообщения или изменить метку). Кажется, этого не происходит. Взгляните на код, чтобы помочь кому-нибудь дать мне ключ. Код ниже:

public partial class Monitor : Form
{
    EventWatcher eventWatch = new EventWatcher();
    ManagementEventWatcher startWatcher = new ManagementEventWatcher();
    ManagementEventWatcher endWatcher = new ManagementEventWatcher();


    public Monitor()
    {
        InitializeComponent();
        startWatcher  = eventWatch.WatchForProcessStart("notepad.exe");
        endWatcher =   eventWatch.WatchForProcessEnd("notepad.exe");
    }

    private void appTimer_Tick(object sender, EventArgs e)
    {
        label1.Text = "tick";
        MessageBox.Show("Tick");
    }

}

И класс наблюдателя

class EventWatcher
{

    public ManagementEventWatcher WatchForProcessStart(string processName)
    {
        string queryString =
            "SELECT TargetInstance" +
            "  FROM __InstanceCreationEvent " +
            "WITHIN  2 " +
            " WHERE TargetInstance ISA 'Win32_Process' " +
            "   AND TargetInstance.Name = '" + processName + "'";

        // The dot in the scope means use the current machine
        string scope = @"\\.\root\CIMV2";

        // Create a watcher and listen for events
        ManagementEventWatcher watcher = new ManagementEventWatcher(scope, queryString);
        watcher.EventArrived += ProcessStarted;
        watcher.Start();
        return watcher;
    }


    public void ProcessStarted(object sender, EventArrivedEventArgs e)
    {
       Monitor monitor = new Monitor();
       //set timer interval and start time for Monitor class. (form)
       monitor.appTimer.Interval = 5000;
       monitor.appTimer.Enabled = true;

       MessageBox.Show("notepad started");


    }
}

Я заметил две вещи:

Когда notepad.exe запускается, и я закомментировал строку MessageBox.Show("notpad started");, сообщение в событии тика таймера не сработает. Если это так, как показано выше, оно покажет мне оба окна сообщений (блокнот запущен и установлен). Однако label1.Text не изменится ни на что.

Я не уверен, что я делаю неправильно. Я уверен, что это как-то связано с обработкой события таймера, но я не уверен, что мне следует делать. Любые идеи?

05.02.2012

Ответы:


1

Ваш код создает новый экземпляр Monitor. Таким образом, вы не получаете доступ к свойствам экземпляра монитора, в котором вы вызвали eventWatch.WaitForProcessStart(), поэтому они не меняются. Одним из способов решения этой проблемы может быть событие, которое запускается, как только запускается ProcessStarted(). Ваш код может выглядеть так:

class EventWatcher
{

    public event EventHandler<EventArrivedEventArgs> ProcessStarted;

    public ManagementEventWatcher WatchForProcessStart(string processName)
    {
        string queryString =
            "SELECT TargetInstance" +
            "  FROM __InstanceCreationEvent " +
            "WITHIN  2 " +
            " WHERE TargetInstance ISA 'Win32_Process' " +
            "   AND TargetInstance.Name = '" + processName + "'";

        // The dot in the scope means use the current machine
        string scope = @"\\.\root\CIMV2";

        // Create a watcher and listen for events
        ManagementEventWatcher watcher = new ManagementEventWatcher(scope, queryString);
        watcher.EventArrived += OnProcessStarted;
        watcher.Start();
        return watcher;
    }


    protected virtual void OnProcessStarted(object sender, EventArrivedEventArgs e)
    {

        EventHandler<EventArrivedEventArgs> copy = ProcessStarted;
        if (copy != null)
            copy(sender, e); // fire the event

    }
}

public partial class Monitor : Form
{
    EventWatcher eventWatch = new EventWatcher();
    ManagementEventWatcher startWatcher = new ManagementEventWatcher();
    ManagementEventWatcher endWatcher = new ManagementEventWatcher();


    public Monitor()
    {
        InitializeComponent();
        startWatcher  = eventWatch.WatchForProcessStart("notepad.exe");
        startWatcher.ProcessStarted += startWatcher_ProcessStarted; // subscribe to the event
        endWatcher =   eventWatch.WatchForProcessEnd("notepad.exe");
    }

    private void startWatcher_ProcessStarted(object sender, EventArrivedEventArgs e)
    { 
        Monitor monitor = new Monitor();
        //set timer interval and start time for Monitor class. (form)
        monitor.appTimer.Interval = 5000;
        monitor.appTimer.Enabled = true;

        MessageBox.Show("notepad started");
    }

    private void appTimer_Tick(object sender, EventArgs e)
    {
        label1.Text = "tick";
        MessageBox.Show("Tick");
    }

}
05.02.2012
  • Спасибо за помощь, но, кажется, это не работает по-другому. Если окно сообщений, показывающее запущенный блокнот, отсутствует, другое окно сообщений не срабатывает в тикере. Метка не меняется в любом случае, и теперь я получаю ошибки с перекрестными потоками. Я подозревал, что вы сказали о новом экземпляре. Разве создание таймера в виде статического поля не решит эту проблему? Однако это не так. 05.02.2012

  • 2

    Также похоже, что label1.Text не изменится, поскольку вы работаете из другого потока. Вам нужно будет запустить вызов этой метки, чтобы обновить ее с ManagementEventWatcher.

    Используйте этот класс:

    using System;
    using System.Windows.Forms;
    
    public static class ControlExtensions
    {
        /// <summary> 
        /// Executes the Action asynchronously on the UI thread, does not block execution on the calling thread. 
        /// </summary> 
        /// <param name="control"></param> 
        /// <param name="code"></param> 
        public static void UIThread(this Control @this, Action code)
        {
            if (@this.InvokeRequired)
            {
                @this.BeginInvoke(code);
            }
            else
            {
                code.Invoke();
            }
        }
    }
    
    and replace `label1.Text = "tick" ` with
    
    this.UIThread(() => this.label1.Text = "tick"));
    
    05.02.2012
  • Кажется, это работает лучше в том смысле, что теперь метка1 меняется с моим старым кодом. Однако это происходит только в том случае, если у меня есть окно сообщений в функции ProcessStarted. 05.02.2012
  • Новые материалы

    Кластеризация: более глубокий взгляд
    Кластеризация — это метод обучения без учителя, в котором мы пытаемся найти группы в наборе данных на основе некоторых известных или неизвестных свойств, которые могут существовать. Независимо от..

    Как написать эффективное резюме
    Предложения по дизайну и макету, чтобы представить себя профессионально Вам не позвонили на собеседование после того, как вы несколько раз подали заявку на работу своей мечты? У вас может..

    Частный метод Python: улучшение инкапсуляции и безопасности
    Введение Python — универсальный и мощный язык программирования, известный своей простотой и удобством использования. Одной из ключевых особенностей, отличающих Python от других языков, является..

    Как я автоматизирую тестирование с помощью Jest
    Шутка для победы, когда дело касается автоматизации тестирования Одной очень важной частью разработки программного обеспечения является автоматизация тестирования, поскольку она создает..

    Работа с векторными символическими архитектурами, часть 4 (искусственный интеллект)
    Hyperseed: неконтролируемое обучение с векторными символическими архитектурами (arXiv) Автор: Евгений Осипов , Сачин Кахавала , Диланта Хапутантри , Тимал Кемпития , Дасвин Де Сильва ,..

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

    Обеспечение масштабируемости LLM: облачный анализ с помощью AWS Fargate и Copilot
    В динамичной области искусственного интеллекта все большее распространение получают модели больших языков (LLM). Они жизненно важны для различных приложений, таких как интеллектуальные..