I think i went somewhat over my head with a little tool i wanted to make.

The idea was to bind certain keys(users choice) to countdown timers and progressbars.
But since the keys are never the same i have to save the chosen key for the selected progressbar.

So when the assigned key is pressed the timer & progressbar linked to that key will start a countdown timer.
But from what i can tell there is no simple way to do this.
Found some examples with keyboard hooks, but none of them where in WPF.

Hope i am making sense about what i want.
And any advice or examples would be much appreciated.

Recommended Answers

All 4 Replies

You should be able to add the key with the corresponding progressbar to something like a dictionary Dictionary<Char,ProgressBar> and then on keypress check your dictionary and retrieve the relevant entry

Ok, that not know about that.
I am going to look further into that, thanks for the tip.

Use in your main window a Dictionary with a Key and a specific class to store your progress information. Also, have a StackPanel in your main window, to display the ProgressBars.

private Dictionary<Key, Progress> progressBars = 
    new Dictionary<Key, Progress> { 
        { Key.O, new Progress() } , 
        { Key.L, new Progress() } 
    };

Bind your windows KeyDown event, and check for required keys.

private void Window_KeyDown(object sender, KeyEventArgs e)
{
    if ((e.Key == Key.O  || e.Key == Key.L) && !progressBars[e.Key].isActive)
    {
        progressBars[e.Key].isActive = true;
        progressBars[e.Key].StartProgress(main_stack); //main_stack is a StackPanel
    }
}

And for your Progress class, you can use something like this:

//pseudocode
class Progress
    ProgressBar pb
    bool isActive       // check if the current thread is active
    int time            // a certain amount of seconds for the timer
    BackgroundWorker bw // a thread to run your timer

Also, you'll need to bind the BackgroundWorker's events, such as DoWork, ProgressChanged and RunWorkerCompleted.
Here's my quick take on the Progress class:

class Progress
{
    public ProgressBar pb = new ProgressBar();
    public Boolean isActive = false;
    public BackgroundWorker bw = new System.ComponentModel.BackgroundWorker();
    public int time = 10;

    public Progress()
    {
        bw.WorkerReportsProgress = true;
        bw.DoWork += bw_DoWork;
        bw.ProgressChanged += bw_ProgressChanged;
        bw.RunWorkerCompleted += bw_RunWorkerCompleted;
        pb.Height = 20;
        pb.MaxWidth = 100;
    }

    void bw_RunWorkerCompleted(object sender, System.ComponentModel.RunWorkerCompletedEventArgs e)
    {
        (pb.Parent as StackPanel).Children.Remove(pb); //remove progressBar
        pb.Value = 0;                                  //reset the value
        isActive = false;                              //show it's done
    }

    void bw_ProgressChanged(object sender, System.ComponentModel.ProgressChangedEventArgs e)
    {
        this.pb.Value = Math.Min(e.ProgressPercentage, 100);
    }

    void bw_DoWork(object sender, System.ComponentModel.DoWorkEventArgs e)
    {
        for (int i = 0; i < time; i++)
        {
            bw.ReportProgress((100 * i) / time);
            System.Threading.Thread.Sleep(1000);
        }
    }

    public void StartProgress(StackPanel grid)
    {
        grid.Children.Add(pb);
        bw.RunWorkerAsync();
    }
}

Alright thanks, managed to get it to work with Dictionary.
Also then example helped a lot, thank you very much both of you.

Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.