0

我有一个班级和一个表格。该类旨在在引发事件时执行一些处理并将值返回到表单以仅显示。我在将值传递回表单时遇到问题。例如,我在课堂上有这段代码print

  public class PrintClass : Form1
{

    public void printEventHandler(object sender, EventArgs e)
    {

        string text = "Process Completed";
        append_Tbox(text);

    }

}

以及 form1 中显示文本的方法:

  public void append_Tbox(string s)
    {

        TboxPrint.AppendText(s);
    }

但是,什么都没有显示。我相信有什么问题,但我无法弄清楚。将值从类传递到表单的最快方法是什么?

4

3 回答 3

1

首先,您的处理类不应该扩展Form1. 这给您一种错觉,即您可以访问现有表单的方法,但它并没有按照您的想法进行操作。当你这样做时,你正在创建一个全新的表单,只是没有显示它。该表单具有自己的所有实例字段集,因此您无需访问主表单的控件。即使这会起作用(并且不会),它也不是一个设计良好的解决方案。

这样做的正确方法实际上要容易得多。你只需要让你的其他类从它的方法返回一个值:

public class PrintClass
{
    public string DoWork()
    {
        Thread.Sleep(2000);//placeholder for real work.
        return "Process Completed";
    }
}

现在您的主窗体可以调用该方法并将返回值附加到文本框。

一旦你这样做,你将有一个完全独立的问题。如果您在 UI 线程中进行工作,您将在工作发生时阻塞该 UI 线程,从而阻止重新绘制表单或处理任何其他事件。您需要在后台线程中完成工作,然后编组回 UI 线程以使用结果更新 UI。有很多方法可以做到这一点,但如果你有 C# 5.0,那么使用await是迄今为止最简单的:

public class Form1 : Form
{
    private void SomeEventHandler(object sender, EventArgs args)
    {
        string result = await Task.Run(()=>new PrintClass().DoWork());
        TboxPrint.AppendText(result);
    }
}

如果您需要一个 C# 4.0 解决方案,您可以使用ContinueWith,这或多或少是上面将被翻译成的内容,但它的语法并不那么干净。

public class Form1 : Form
{
    private void SomeEventHandler(object sender, EventArgs args)
    {
        Task.Factory.StartNew(()=>new PrintClass().DoWork())
            .ContinueWith(t => TboxPrint.AppendText(t.Result)
                , CancellationToken.None
                , TaskContinuationOptions.None
                , TaskScheduler.FromCurrentSynchronizationContext());
    }
}
于 2013-02-25T06:50:11.753 回答
0

我在主窗体中创建了委托

 public delegate void LoginDelegate(string s);

 public partial class AirLineReservationMDI : Form
    {
        LoginDelegate loginAirLineDelegate;

    }

loginAirLineDelegate = new LoginDelegate(DisableToolStripMenuItems);


 public void DisableToolStripMenuItems(string s)
        {
           this.viewToolStripMenuItem.Visible = true;
            this.bookingToolStripMenuItem.Visible = true;
            this.existingUserToolStripMenuItem.Visible = false;
            this.newUserToolStripMenuItem.Visible = false;
            this.toolStripStatusUserID.Text = "USerID :- "+s;             
           this.LoginUserId = s;
        }

在另一个类中,(我已将 delagete 对象传递给此类)我解雇了代表

  logDelegate(textBoxUserName.Text);
于 2013-02-25T06:39:18.080 回答
0

我使用Action<T>委托来解决问题。这是代码,它工作正常。

 class PrintClass 
{
    public Action<string> DisplayDelegate;


    public void printEventHandler(object sender, EventArgs e)
    {
        string text = "Event Handled, and text value is passed";

        var copy = DisplayDelegate;

        if (copy != null)
        {
           copy(text);
        }
    }

}

在“Form1.cs”中:

 private void Form1_Load(object sender, EventArgs e)
    {
        PrintClass p = new PrintClass();
        BtnPrint.Click += p.printEventHandler;

        //subscrite the displayevent method to action delegate
        p.DisplayDelegate += DisplayEvent;

    }


    public void DisplayEvent(string s)
    {

        Invoke(new Action(() => TboxPrint.AppendText(s)));
    }

因此文本“事件已处理,并且文本值已传递”显示在文本框中。

我不确定这是否是有效的方法。多谢你们。

于 2013-02-27T04:01:16.523 回答