2012-01-17 25 views
4
私はCEditのために、コントロールの変数を作成し

C++/MFCエラーアクセスコントロールの変数

class CGateDlg : public CDialog 
{ 
    ... 
    public: 
     // here is my control's variable 
     CEdit m_edit_a; 
     // here I map variable to control 
     virtual void DoDataExchange(CDataExchange* pDX); 
} 

をそして、これは私がコントロールに私の変数をマッピングする方法である:

void CGateDlg::DoDataExchange(CDataExchange* pDX) 
{ 
    CDialog::DoDataExchange(pDX); 
    DDX_Control(pDX, IDC_EDIT_A, m_edit_a); 
} 

これは、それがどのように動作するかです:ユーザーはテキストを編集ボックスに入力します。次に、 "リセット"ボタンを押して編集ボックスをクリアします。

void CGateDlg::OnBnClickedReset() 
{ 
    // clear edit box 
    m_edit_a.SetWindowTextW(L""); 
} 

アプリケーションはエラーなしで開始します。これは、リセットボタンをクリックした後にエディットボックスをクリアするコードです。 EditBoxにテキストを入力し、「リセット」ボタンを押します。それから私は、()(これを確実に)私はwinocc.cppにつながるエラー、ライン245を得る:

void CWnd::SetWindowText(LPCTSTR lpszString) 
{ 
    ENSURE(this); 
    ENSURE(::IsWindow(m_hWnd) || (m_pCtrlSite != NULL)); 

    if (m_pCtrlSite == NULL) 
      ::SetWindowText(m_hWnd, lpszString); 
    else 
      m_pCtrlSite->SetWindowText(lpszString); 
} 

私は問題はhWndをしていると思う:

this 0x0030fa54 {CEdit hWnd=0x00000000} CWnd * const 

が、それを修正する方法?私はこれを使用して、私のコントロールの値にアクセスするとき

すべてが正常に動作します:私は間違って

CEdit *m_edit_a; 
m_edit_a = reinterpret_cast<CEdit *>(GetDlgItem(IDC_EDIT_A)); 
m_edit_a->SetWindowTextW(L""); 

何をしているのですか?

+0

クラス全体のコードを投稿することはできますか? –

+0

'CGateDlg'はどうやって作りますか?あなたがリソースIDからそれを作成していない場合、 'DDX_Control'があなたのために働いていない可能性があり、' CEdit 'を使う前に 'CGateDlg'の' OnCreate'オーバーロードで 'm_edit_a.Create'を明示的に呼び出す必要があるかもしれません' – AJG85

+0

「リソースIDから作成する」という正確な意味は?どのように表示されるべきかをわかるリンクやサンプルを投稿してください。私は現時点で仕事中ですが、家に帰って必要に応じてヘッダーとクラス全体を貼り付けると、あなたのアイデアをすべて試してみます。 –

答えて

8

私は2つの可能性を見ることができます:ダイアログが起動したとき

  1. コントロールが存在しません。 CDialog :: OnInitDialogが最初に行うことは、DoDataExchangeを呼び出すことです。したがって、初期化プロセスの後半でコントロールを作成する場合は、それが遅すぎます。

  2. 独自のOnInitDialogはCDialog :: OnInitDialogを呼び出さないため、DoDataExchangeは呼び出されません。

+0

解決策は私が予想したほど複雑ではないように見えます。私は私のCGateDlg :: OnInitDialogでCDialog :: OnInitDialogを呼び出さなかった。しかし、私はまだウィザードから離れているので、私は正しい方法でMFCを学ぶことができます:) –

0

私はあなたに間違いを見つけることができません。私はVC6.0を使用して新しいプロジェクトを作成し、編集に変数を関連付けるだけでリンクします。 exeは正常に動作します。

class CEditTestDlg : public CDialog 
{ 
// Construction 
public: 
CEditTestDlg(CWnd* pParent = NULL); // standard constructor 

// Dialog Data 
//{{AFX_DATA(CEditTestDlg) 
enum { IDD = IDD_EDITTEST_DIALOG }; 
CEdit m_Edit; 
//}}AFX_DATA 

// ClassWizard generated virtual function overrides 
//{{AFX_VIRTUAL(CEditTestDlg) 
protected: 
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support 
//}}AFX_VIRTUAL 

......

た.cpp

void CEditTestDlg::DoDataExchange(CDataExchange* pDX) 
{ 
    CDialog::DoDataExchange(pDX); 
    //{{AFX_DATA_MAP(CEditTestDlg) 
    DDX_Control(pDX, IDC_EDIT1, m_Edit); 
    //}}AFX_DATA_MAP 
} 
void CEditTestDlg::OnBnClickedReset() 
{ 
    // TODO: Add your control notification handler code here 
    m_Edit.SetWindowText("tttt"); 
} 

ので、私はそれがproblem.Youは、もう一度試して良くなかったコードではないと思います。

1

私はあなたが直接役に立たない(この場合m_edit_aで)あなたのコントロールのmeberをすべきだと思います。代わりに、あなたは、memeber変数を使用するのがCStrimg m_edit_dataを言わせて、あなたがコントロールにリンクする必要がありする必要があります

DDX_Text(pDX, IDC_EDIT_A, m_edit_data); // as you did it in DDC_Cotrol 

今、あなたは、変数をdirecty使用することができますが、コントロールが更新されるためには、次のコードを使用する必要がありますそれを使用する前に:

UpdateData(true); // unlocks the control in a sense 
m_edit_data = "this is my test"; 
UpdateData(false); // locks the control again (in a sense) 

これはMFCの通常の手順です。

おお...あなたはまた、文字列テーブルにコントロールを追加する必要があります...あなたのダイアログがオフのCDialog :: OnInitDialogをを(呼び出しを開始した場合

0

を(あなたが知らないなら、私が知っている))とあなたのDoDataExchangeが開始されますオフCDialog :: DoDataExchangeを呼び出すが、null hWndポインターがあり、CNotSupportedExceptionを取得し、リソース(rc)ファイルのダイアログテンプレートにすべてのコントロール(IDC_)が含まれ、DoDataExchangeにそのようなものが含まれていることを確認します。

リソースを提供するDLLを使用している場合は、定義の上書きを確認してください。