2012-07-26 25 views
0

我已經寫了幾個簡單的GUI應用程序,但所有的邏輯基本上都寫在我給出的默認Form1類。從窗體/控件繼承和編寫模塊代碼

所以我想也許我會將GUI邏輯重寫到他們自己的類中。例如,FileOpenDialog的類,ListView的另一個類等等。這樣我的Form1類沒有太多不必要的方法,只是在那裏處理一些基本的東西,可能在其他GUI方法移動後並不是很多。

寫這樣的事情作爲第一次嘗試得到的地方

namespace WindowsFormsApplication1 
{ 
    class OpenFileDialog1 : OpenFileDialog 
    { 
    } 
} 

但隨後VS告訴我,我不能從密封型派生。

我還沒有嘗試與其他類,但我可能會遇到同一問題在某些時候。我沒有正確地繼承它嗎?或者我必須使用某種解決方法將每個GUI元素分離到他們自己的類中?

也許這不是一個好方法?

+0

你不能從密封類繼承,你有可能不想做你認爲你在做什麼?你可以擴展一個類來改進/修改它的功能。這聽起來像你想在你的表單上做部分課程。 – 2012-07-26 18:50:07

+0

因此,我只需製作另一個表單類,並將所有文件打開邏輯?我只想說「好的,所以用戶想打開一個文件,我不在乎你是怎麼做的,只是以某種方式提示他,並從用戶那裏返回一些東西」。我可能會用一組不同的方法來打開文件,但是我的主窗體類不應該知道任何關於它的信息。 – MxyL 2012-07-26 18:52:57

+0

我並不十分理解你的追求,但它聽起來像你需要使用一些工廠類來滿足你的願望。我會在代碼中澄清。 – 2012-07-26 19:08:52

回答

1

根據您的澄清意見,這聽起來像你要麼需要一些工具類或工廠類。也許喜歡的東西如下:

public interface IFileOpener 
{ 
    public bool PresentFileOpenDialogToUser(); 
    public string RequestedFilePath { get; } 
} 

public class DefaultFileOpener : IFileOpener 
{ 
    private string filePath = default(string); 

    public bool PresentFileOpenDialogToUser() 
    { 
     OpenFileDialog ofd = new OpenFileDialog(); 
     DialogResult dr = ofd.ShowDialog(); 
     if (dr == DialogResult.Cancel) 
     { 
      this.filePath = default(string); 
      return false; 
     } 
     else 
     { 
      this.filePath = ofd.FileName; 
      return true; 
     } 
    } 

    public string RequestedFilePath 
    { 
     get 
     { 
      return this.filePath; 
     } 
    } 
} 

public class FileOpenerFactory 
{ 
    public static IFileOpener CreateFileOpener() 
    { 
     return new DefaultFileOpener(); 
    } 
} 

而且在你的表格:

private void btnOpenFile_Click(object sender, EventArgs e) 
    { 
     IFileOpener opener = FileOpenerFactory.CreateFileOpener(); 
     if (opener.PresentFileOpenDialogToUser()) 
     { 
      //do something with opener.RequestedFilePath; 
     } 
    } 

你甚至可以在你的主要形式做了部分類的東西,所以你有類似

private void btnOpenFile_Click(object sender, EventArgs e) 
    { 
     this.OpenMyFile(); 
    } 

和在你的部分課程中你有:

public partial class Form1 
{ 
    private void OpenMyFile() 
    { 
     IFileOpener opener = FileOpenerFactory.CreateFileOpener(); 
     if (opener.PresentFileOpenDialogToUser()) 
     { 
      //do something with opener.RequestedFilePath; 
     } 
    } 
} 

很多時候,使用部分類作爲接口或專注功能的實現非常有用。

+0

是的,工廠模式是我正在尋找的(名字沒有找到我)。根據你寫的代碼,我對主表單的理解是,它就像處理所有事件和請求的某種「驅動程序」? – MxyL 2012-07-26 19:28:28

+0

正確,正如我試圖暗示的那樣,你甚至可以將它分成部分類,所以一個「部分」部分只是初始化,一個是事件處理等。 – 2012-07-26 19:33:17

1

根據c#規範,密封類不能被繼承到另一個類。你必須直接發起。

如果OpenFileDialog是密封類,那麼您不能繼承它。

2

一個很好的方法。但不要從OpenFileDialog繼承。只需創建一個簡單的課程並將其放在那裏。

像這樣的東西(就像一個想法):

class FileDialogStuff 
{ 
    static OpenFileDialog dialog = new OpenFileDialog(); 

    public static string GetFile() 
    { 
     DialogResult result = dialog.ShowDialog(); 
     //Do stuff 
     return dialog.FileName; 
    } 
} 
+0

@inspiro所以假設我定義了一個名爲「MyFileOpenPrompt」的類,並且它調用了OpenFileDialog。我可能希望避免實例化MyFileOpenPrompt的實例,因爲我只是將其定義爲使代碼更清晰。相反,我想說「MyFileOpenPrompt.prompt_user()」。靜態方法是實現這一目標的唯一方法嗎? – MxyL 2012-07-26 19:02:11

+0

查看我的編輯(在我看到您的評論之前編寫)。靜態方法有什麼問題?不要讓整個課程變成靜態的 - 它不會幫助你(除了防止你意外地創建非靜態的東西。) – ispiro 2012-07-26 19:04:21

+0

很好地工作,雖然它看起來像我必須在我的Form1中定義FileDialogStuff_FileOK方法類。有沒有辦法將這一點轉移到這個新班級中? – MxyL 2012-07-26 19:13:59