2013-01-12 32 views
1

我想知道正確的方式(最好看)來設置,例如,從我的MainWindow以外的類中設置的標籤。
從其他類別設置控制值的「正確」方式

此刻,我會做這樣的事情:

public partial class MainWindow: Window { 
    public MainWindow() { 
     InitializeComponent(); 

     MyClass a=new MyClass(this); 
     a.WriteToLabel(); 
    } 
} 

class MyClass { 
    MainWindow parent; 

    public MyClass(MainWindow parent) { 
     this.parent=parent; 
    } 

    public void WriteToLabel() { 
     parent.label1.Text="Test"; 
    } 
} 

但我覺得這是一種不好的做法。
當你有超過20個教學班,並都有一個字段或parent財產感覺真的不好。
你會如何解決這樣的問題?

+0

我想你的意思是'一個。 WriteToLabel();' – I4V

+0

啊,這是一個錯字...編輯謝謝! – Nick3

+0

的問題是,爲什麼你需要設置從一個不屬於'MainWIndow'一類'Label's'文本形式。您的標籤是它的控制器的GUI,類只需要_provide_你想在表單中顯示的內容。 –

回答

3

爲什麼不通過label1作爲參數?

有了:

class MyClass 
{ 
    public void WriteToLabel(Label label) 
    { 
     label.Content = "Test"; 
    } 
} 

你可以使用:

var a = new MyClass(); 
a.WriteToLabel(label1); 

這是傳統更好地避免耦合在代碼中儘可能多地。我不會添加對窗口的引用。我寧願儘可能地參數化我的方法。

+0

Exaktly,我真的想要避免耦合,但正如我在其他評論中所說的,我不知道該怎麼做,例如一個Thread想要寫入GUI,或者可能類似於文件是閱讀,然後在GUI中的東西應該更新。那麼這是行不通的。我怎麼能做到這一點? – Nick3

+1

@ Nick3耦合幾乎總是需要至少一次(否則你的模塊將無用),應該儘可能地避免耦合。如果您需要在不同線程的窗口上進行操作,您可以通過'ParametrizedThreadStart'委託來傳遞它,或者如果您真的需要引用它,則可以使用靜態的'Application.Current.MainWindow'。此外,在.NET 4.5中,你可以使用'async/await'關鍵字來完成異步執行,從而簡化代碼。 – Mir

0

使用Fluent interface

public partial class MainWindow : Window 
{ 
    public MainWindow() 
    { 
     InitializeComponent(); 
     MyClass a = new MyClass(this).WriteToLabel("Test"); 
    } 
} 

class MyClass 
{ 
    MainWindow parent; 

    public MyClass(MainWindow parent) 
    { 
     this.parent = parent; 
    } 

    public MyClass WriteToLabel(string txt) 
    { 
     parent.label1.Text = txt; 
     return this; 
    } 
} 
0

的問題是,爲什麼你需要從一個不屬於MainWindow類設置一個LabelText。您的標籤的形式是控制它的GUI,類只需要提供你想在表單中顯示的內容。

所以這是更好實踐。

public partial class MainWindow : Window 
{ 
    public MainWindow() 
    { 
     InitializeComponent(); 
     MyClass a = new MyClass(); 
     string data = a.GetData(); 
     label1.Text = text; 
    } 
} 

class MyClass 
{ 
    public MyClass() 
    { 
     this.parent = parent; 
    } 

    public stringGetData() 
    { 
     return "Test"; 
    } 
} 
+0

正如我在其他答案上所做的一樣,它可能不是最好的例子,但也許我在課堂上開始一個線程,並且我想在發生某些事情時設置文本。在這個例子中,這將起作用,但我想要在任何時候總是有一些東西,我想改變我的GUI中的某些東西 – Nick3

0

由於您的課程完全瞭解對方,因此一種好的方法是提供Property訪問器。

public partial class MainWindow : Window 
{ 
    public MainWindow() 
    { 
     InitializeComponent(); 
     MyClass a = new MyClass(this); 
     a.WriteToLabel(); 
    } 


    public string LabelText 
    { 
     get { return label1.Text; } 
     set { 
       if (this.InvokeRequired) 
       { 
        this.BeginInvoke(
         delegate() => 
           { 
            label1.Text =value; 
           })}; 
       } 
       else 
       { 
        label1.Text = value; 
       } 
       } 

} 

class MyClass 
{ 
    MainWindow parent; 

    public MyClass(MainWindow parent) 
    { 
     this.parent = parent; 
    } 
    public void WriteToLabel() 
    { 
     parent.LabelText = "Test"; 
    } 
} 
2

我覺得你的做法總體上不錯。但我也會「跟蹤」通過列表實例化的孩子,這樣我最終還可以使用Linq擴展搜索特定的孩子。 我也是在你的代碼糾正了一些小錯誤(命名約定的MyClass父成員和WriteToLabel的(虛空結果)被分配到MyClass的實例在父類的構造。

public partial class MainWindow : Window 
{ 
    private List<MyClass> children; 

    public MainWindow() 
    { 
     children = new List<MyClass>(); 

     InitializeComponent(); 

     MyClass child = InstantiateChild(); 
     child.WriteToLabel(); 
    } 

    private MyClass InstantiateChild() 
    { 
     MyClass child = new MyClass(this); 
     children.Add(child); 

     return child; 
    } 
} 

public class MyClass 
{ 
    private MainWindow m_Parent; 

    public MyClass(MainWindow parent) 
    { 
     m_Parent = parent; 
    } 

    public void WriteToLabel() 
    { 
     m_Parent.label1.Text = "Test"; 
    } 
} 
相關問題