首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >ToolStripTextBox延迟TextChanged

ToolStripTextBox延迟TextChanged
EN

Stack Overflow用户
提问于 2018-02-01 09:00:25
回答 2查看 336关注 0票数 1

我需要检索TextChanged事件的ToolStripTextBox与一个延迟,做一些事情后,x秒钟停止按键盘。

我为TextBox找到了这个示例(并且很有用)。

https://www.codeproject.com/Articles/20068/Custom-TextBox-that-Delays-the-TextChanged-Event

我试图将其转换为ToolStripTextBox,但得到了以下错误:

代码语言:javascript
复制
void DelayTimer_Elapsed(object sender, ElapsedEventArgs e)
{
    // stop timer.
    DelayTimer.Enabled = false;

    // set timer elapsed to true, so the OnTextChange knows to fire
    TimerElapsed = true;

    try
    {
        // use invoke to get back on the UI thread.
        this.Invoke(new DelayOverHandler(DelayOver), null);
    }
    catch { }
}

“DelayToolStripTextBox”不包含“Invoke”的定义,也找不到接受'DelayToolStripTextBox‘类型的第一个参数的扩展方法'Invoke’(您缺少使用指令还是程序集引用?)

ToolStripTextBox没有'Invoke`‘方法。

有人能帮我吗?

提前感谢

EN

回答 2

Stack Overflow用户

回答已采纳

发布于 2018-02-01 09:15:51

为什么要使用一些外部代码?计时器可以轻松地完成你的工作:

定义一个Timer,它将在TextChange运行时启动。如果Timer正在运行,则应该重新部署。如果到达Timer.Intervall,我们知道我们没有得到新的输入,因为timmer没有重置。现在,Timer应该触发它的Tick-event。事件应该激发我们的方法,我们用t.Tick += ClearText;绑定到它。

代码语言:javascript
复制
// your trigger
private void textBox1_TextChanged(object sender, EventArgs e)
{
    StartEventAfterXSeconds();
}

private Timer t;

// your time-management
private void StartEventAfterXSeconds(int seconds = 10)
{
    if (t != null)
    {
        t.Stop();
    }
    else
    {
        t = new Timer();
        t.Tick += ClearText;
    }

    t.Interval = 1000 * seconds;
    t.Start();
}

// You action
public void ClearText(object sender, EventArgs args)
{
    this.textBox1.Text = null;
    t.Stop();
}

如果您想要使用这些TextBoxes中的多个,则应该将所有内容移动到一个类中。

  1. 继承文本框
  2. 添加应在延迟后触发的事件。
  3. 构建一个启动定时器并由普通TextChanged-event触发的方法。
  4. 实现勾选方法,该方法触发新事件并停止计时器。

关于不带计时器的自定义事件的一些信息-方法:simple custom event

代码语言:javascript
复制
public class TextBoxWithDelay : TextBox
{
    public TextBoxWithDelay()
    {
        this.DelayInSeconds = 10;

        this.TextChanged += OnTextChangedWaitForDelay;
    }

    public int DelayInSeconds { get; set; }
    public event EventHandler TextChangedWaitForDelay;

    private Timer t;
    private void OnTextChangedWaitForDelay(object sender, EventArgs args)
    {
        if (t != null)
        {
            t.Stop();
        }
        else
        {
            t = new Timer();
            t.Tick += DoIt;
        }

        t.Interval = 1000 * DelayInSeconds;
        t.Start();
    }

    public void DoIt(object sender, EventArgs args)
    {
        if (TextChangedWaitForDelay != null)
        {
            TextChangedWaitForDelay.Invoke(sender, args);
            t.Stop();
        }

    }
}
票数 2
EN

Stack Overflow用户

发布于 2018-02-06 19:12:48

我也在寻找一个类似于你的情况的解决方案。我知道如何使用setTimeout在Javascript中实现这一点,因此我开始通过任务在C#中执行类似的操作。我想出的是:

代码语言:javascript
复制
private Dictionary<string, CancellationTokenSource> DebounceActions = new Dictionary<string, CancellationTokenSource>();

private void Debounce(string key, int millisecondsDelay, Action action)
{
    if (DebounceActions.ContainsKey(key))
    {
        DebounceActions[key].Cancel();
    }
    DebounceActions[key] = new CancellationTokenSource();
    var token = DebounceActions[key].Token;
    Task.Delay(millisecondsDelay, token).ContinueWith((task) =>
    {
        if (token.IsCancellationRequested)
        {
            token.ThrowIfCancellationRequested();
        }
        else
        {
            action();
        }
    }, token);
}

只需传递一个唯一的key,以确定它从哪个方法调用。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/48558801

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档