NumericUpDownコントロールで”00”表示する方法

[戻る]
KEN 2007/03/27(火) 10:29:01
お世話になります。

VC++ .NET2005 CLRで開発しています。

NumericUpDownコントロールにて初期値で"00"を表示させたいのですが方法が見つかりま
せん。NumericUpDownでは内部で数値を decimal 型として扱っているため無理そうでし
ょうか?どなたかアドバイスをお願い致します。

iijima 2007/03/27(火) 14:26:28
テキストボックス部に表示される文字列が"0"のときは"00"に書き換えるように
カスタマイズしたNumericUpDownの派生クラスを定義してはいかがでしょうか。

// 例
using namespace System;

ref class CustomNumericUpDown : public System::Windows::Forms::NumericUpDown {
public:
    CustomNumericUpDown(){}
protected:
    virtual void OnTextBoxTextChanged( Object^ source, EventArgs^ e ) override 
{
        if( this->Text->Equals( "0" ) ) {
            this->Text = "00";
        }
        else {
            NumericUpDown::OnTextBoxTextChanged( source, e );
        }
    }
};

KEN 2007/03/27(火) 16:30:43
iijimaさん

アドバイスありがとうございます。サンプルクラスとどのように連動させるのかが分か
りません。現在、フォーム上(form1)にnumericUpDown1という名前のコントロールが配
置されています。

Blue 2007/03/27(火) 16:36:45
C++/CLIならデザインコードも見えるので,Form1クラスの中に
iijimaさんの
>ref class CustomNumericUpDown 
のコードを入れて、

自動生成されている

System::Windows::Forms::NumericUpDown^ numericUpDown1;

を

CustomNumericUpDown^ numericUpDown1;

に

numericUpDown1 = gcnew System::Windows::Forms::NumericUpDown();

を

numericUpDown1 = gcnew CustomNumericUpDown();

に変更するだけで使えるようになると思います。


ただし、デザインモードが使えなくなるかもしれません。

KEN 2007/03/27(火) 16:36:50
if( this->Text->Equals( "0" ) ) {
            this->Text = "00";
}

上記のコード実行時に条件式に入るのですが実際の表示は"00"でなく"0"となってしまい
ます。

KEN 2007/03/27(火) 16:47:57
Blueさん

System::Windows::Forms::NumericUpDown^ numericUpDown1;

を

CustomNumericUpDown^ numericUpDown1;

上記で

c:\temp\test\test\Form1.h(52) : error C2143: 構文エラー : ';' が '^' の前にあり
ません。
c:\temp\test\test\Form1.h(52) : error C4430: 型指定子がありません - int と仮定
しました。メモ: C++ は int を既定値としてサポートしていません
c:\temp\test\test\Form1.h(52) : error C4430: 型指定子がありません - int と仮定
しました。メモ: C++ は int を既定値としてサポートしていません
c:\temp\test\test\Form1.h(76) : error C2039: 'numericUpDown1' : 'test::Form1' 
のメンバではありません。
        c:\temp\test\test\Form1.h(22) : 'test::Form1' の宣言を確認してくださ
い。
c:\temp\test\test\Form1.h(77) : error C2039: 'numericUpDown1' : 'test::Form1' 
のメンバではありません。
        c:\temp\test\test\Form1.h(22) : 'test::Form1' の宣言を確認してくださ
い。

とエラーが出てしまいました。

Blue 2007/03/27(火) 16:55:39
>Form1クラスの中に
>iijimaさんの
>>ref class CustomNumericUpDown 
>のコードを入れて、
はやりましたか?

public ref Form1 : System::Windows::Forms::Form
{
/*
    ここらへんに入れる !!!
*/
publuc:
    Form1()
    {
// 省略
};


となっていないと使えません。

iijima 2007/03/27(火) 17:20:24
Blueさんがおっしゃる方法でもできますが、その後デザインモードが使えなくなる
可能性があるのであまりお勧めではありません。

(1) メニューの[プロジェクト]-[クラスの追加]で[クラスの追加]ダイアログボックス
  を開く

(2) カテゴリの[C++]を選択して[追加]ボタンをクリックし[汎用C++クラスウィザード]
  ダイアログボックスを開く

(3) 次のように設定して[完了]ボタンをクリック
・クラス名:CustomNumericUpDown
・基本クラス:System::Windows::Forms::NumericUpDown
・「マネージ」チェックボックスをチェック

(4) するとCustomNumericUpDownクラスのファイル(*.h, *.cpp)が生成されるので、
  必要なコードを書き加える(この場合はOnTextBoxTextChangedのオーバーライド)

(5) ここで一旦ビルドすると、ツールボックスの[プロジェクト名]コンポーネントの
  ところに"CustomNumericUpDown"が追加される。

(6) 普通のコントロールと同様にそれをフォーム上に貼り付けると、初期化に必要なコ
  ードはデザイナによって自動生成される。

(7) Form1.hファイルの先頭付近に「#include "CustomNumericUpDown"」を加える。

これでいけると思います。
CustomNumericUpDownをどこかの名前空間に入れたりするなどは、お好みに応じて。

KEN 2007/03/27(火) 17:48:08
iijimaさん

アドバイスありがとうございます。

(4) するとCustomNumericUpDownクラスのファイル(*.h, *.cpp)が生成されるので、
  必要なコードを書き加える(この場合はOnTextBoxTextChangedのオーバーライド)

上記はCustomNumericUpDown.cpp内
CustomNumericUpDown::CustomNumericUpDown(void)
{
}
に
protected:
    virtual void OnTextBoxTextChanged( Object^ source, EventArgs^ e ) override 
{
        if( this->Text->Equals( "0" ) ) {
            this->Text = "00";
        }
        else {
            NumericUpDown::OnTextBoxTextChanged( source, e );
        }
    }

上記を記述するということでしょうか?本当、初心者ですみません(><)

iijima 2007/03/27(火) 17:59:01
hファイルとcppファイルに分けて定義するなら次のようになります。

// ***.hファイル
#pragma once
using namespace System;

ref class CustomNumericUpDown : public System::Windows::Forms::NumericUpDown {
public:
    CustomNumericUpDown();
protected:
    virtual void OnTextBoxTextChanged( Object^ source, EventArgs^ e ) override;
};


// ***.cppファイル
#include "StdAfx.h"
#include "CustomNumericUpDown.h"

CustomNumericUpDown::CustomNumericUpDown()
{
}

void CustomNumericUpDown::OnTextBoxTextChanged( Object^ source, EventArgs^ e )
{
    if( this->Text->Equals( "0" ) ) {
        this->Text = "00";
    }
    else {
        NumericUpDown::OnTextBoxTextChanged( source, e );
    }
}

# C++/CLIの前に標準C++をきちんと勉強することをお勧めします。

KEN 2007/03/27(火) 18:02:46
たびたびすみません。

#pragma once
using namespace System;

ref class CustomNumericUpDown :
public System::Windows::Forms::NumericUpDown
{
public:
    CustomNumericUpDown(void);

protected:
    virtual void OnTextBoxTextChanged( Object^ source, EventArgs^ e ) override 
{
        if( this->Text->Equals( "0" ) ) {
            this->Text = "00";
        }
        else {
            NumericUpDown::OnTextBoxTextChanged( source, e );
        }
    }
};

として上手くビルド出来たのですが肝心の"CustomNumericUpDown"が追加されていません

iijima 2007/03/27(火) 18:09:10
おそらくそのコードがコンパイルされていないから。
全てヘッダファイル(*.h)に書き、どのcppファイルでもインクルードしていないので
は?

Form1.hファイルの#pragma onceの次の行に

#include "CustomNumericUpDown.h"

を加えてからビルドすべし。

iijima 2007/03/27(火) 18:12:36
あるいは、フォームデザイナを表示していないとかではないですか。
フォームデザイナを表示していないときはツールボックスの中身も
表示されませんので。

KEN 2007/03/27(火) 19:09:09
Form1.hファイルの#pragma onceの次の行に

#include "CustomNumericUpDown.h"

を加えてからビルドすべし。

う〜ん、ヘッダファイルもインクルードしているのに追加されません。。もう少し考え
て見ます

KEN 2007/03/28(水) 10:53:19
上記アドバイスどおりやったのですがのカスタムコントロールを作成できなかったので

String^ a = numericUpDown1->Text;
                     
String^ b = a->PadLeft(2,'0');

numericUpDown1->Text::set(b);

と簡単に記述してみましたが"00"とは表示してくれませんでした・・・。

やりたいことは時刻を選択するアプリで

□:□として□をnumericUpDownで00,01,02,03と表示させたいのです。

つばさ 2007/03/28(水) 11:35:16
NumericUpDownを作って試してみたのですが
おそらく数値しか表示できないのではないかと思います
(Valueなどに00を入力しても強制的に0になるため)

ですので、NumericUpDownを継承してクラスを作成しても同様に"00"の表示は
できないかと思います

ですので
自作のNumericUpdownもどきを作成してみるのはどうでしょうか?

KEN 2007/03/28(水) 13:30:26
つばささん

アドバイスありがとうございます。

自作のNumericUpdownもどきを作成することにしました。

テキストボックスの右側にNumericUpDownコントロールの矢印だけを表示して似たような
コントロールを作成しました。

プログラム的なことで質問なのですが

文字列(00,01,02)をカウントアップさせるには一時的にint型に変換してテキストボッ
クスに戻すときに再度、string型に変換させようと思います。ところがstring型からint
型へ上手く変換できません。Cとかだとatoiで行けると思いますがVC++.NET CLIでは融通
が利かずに困っています。何か上手い方法を教えてください

Blue 2007/03/28(水) 13:42:47
int->String^

int::ToString
もしくは
String::Format


String^->int

int::TryParse
(int::Parse)
または
Convert::ToInt32

KEN 2007/03/28(水) 20:11:48
Blueさん

String^ a = domainUpDown1->Text;

で変数aをint型に変換したいのですがString^->intは出来ないようです。
何か上手い方法はありますでしょうか?Cのようにatoiを使用したいのですが・・。

KEN 2007/03/28(水) 20:42:29
すみません。下記のようにして無事に出来ました!

String^ b = domainUpDown1->Text;

int i = System::Convert::ToInt32(b);

KEN 2007/03/28(水) 20:56:56
NumericUpDownコントロールに近いdomainUpDownを使用することにしました。これな
ら"00"表示いけそうです。

domainUpDownコントロールですが↑矢印と↓矢印を押下した際のイベントは切り分けて
取得できるのでしょうか?初めて使用するコントロールでヘルプ等を見ましたがよくわ
かりません

Blue 2007/03/28(水) 23:09:42
>String^->intは出来ないようです。
ちょっと間際らしかったですね。
->はアロー演算子ではなくて → という意味で書いたのです。

String^ s = "00";
int n = int::Parse(s); // 数字以外がありうるならばTryParseでチェックしたほう
                       // が ベター

KEN 2007/03/29(木) 00:22:08
Blueさん

アドバイスありがとうございます。下記のほうがベターということですね!

String^ s = "00";
int n = int::Parse(s);

すぐにレスが頂けて大変助かります。また非常に勉強になります。今後とも宜しくお願
いしますm(−−)m

Blue 2007/03/29(木) 01:41:47
いろいろやってみたところ、継承してUpdateEditTextをオーバーライドすれば表示でき
るようです。

まずiijimaさんの
> 2007/03/27(火) 17:20:24
の方法でNumericUpDownクラスを継承したCustomNumericUpDownを作成します。

コードはこれだけ。

●CustomNumericUpDown.h

#pragma once

ref class CustomNumericUpDown :
public System::Windows::Forms::NumericUpDown
{
public:
    CustomNumericUpDown(void);
protected:
    virtual void UpdateEditText () override; // 追加!!
};


●CustomNumericUpDown.cpp

#include "StdAfx.h"
#include "CustomNumericUpDown.h"

CustomNumericUpDown::CustomNumericUpDown(void)
{
}

void CustomNumericUpDown::UpdateEditText()
{
    this->Text = this->Value.ToString(L"00");
}


ただし、これでビルドしても
>(5) ここで一旦ビルドすると、ツールボックスの[プロジェクト名]コンポーネントの
>  ところに"CustomNumericUpDown"が追加される。
にはならなかったので、
(そもそもツールボックスに[プロジェクト名]ってのがない)
手動でForm1.hを編集します。

>Form1.hファイルの#pragma onceの次の行に
>#include "CustomNumericUpDown.h"

>private: System::Windows::Forms::NumericUpDown^ numericUpDown1;
>を
>private: CustomNumericUpDown^ numericUpDown1;
>に
>this->numericUpDown1 = (gcnew System::Windows::Forms::NumericUpDown());
>を
>this->numericUpDown1 = (gcnew CustomNumericUpDown());

として、ビルドすればいいです。
一応デザインモードは使えているようです。

ちなみに私の環境は
Windows XP Pro SP2/Visual Studio 2005 Pro SP1
です。

KEN 2007/03/29(木) 10:11:02
BLUEさんへ

おはようございます。上記の方法でばっちりいけました!!デザインも問題なく
開けています。

NumericUpDownで文字列が表示できるとは思っていなかったので大変参考になりました。

本当にありがとうございます。

iijima 2007/03/29(木) 10:17:58
> ただし、これでビルドしても
>>(5) ここで一旦ビルドすると、ツールボックスの[プロジェクト名]コンポーネントの
>>  ところに"CustomNumericUpDown"が追加される。
> にはならなかったので、

例えば、プロジェクト名が"Test"だったとき、ツールボックスに「Testコンポーネン
ト」
というカテゴリがあって、その中に追加されませんか?

私の環境↓だと追加されます。

Windows Xp Pro. SP2
Visutl Srutio 2005 Pro.

Blueさんと環境同じですよね。

iijima 2007/03/29(木) 10:25:18
typo訂正

Visual Studio 2005 Pro.

KEN 2007/03/29(木) 11:03:21
iijimaさん

>>例えばプロジェクト名が"Test"だったとき、ツールボックスに「Testコンポーネン
>>ト」というカテゴリがあって、その中に追加されませんか?

プロジェクト名は表示されずにコンポーネントのみしか表示されませんでした。

私の環境も

Windows Xp Pro. SP2
Visual Srutio 2005 Pro

です。

iijima 2007/03/29(木) 11:43:18
あれー
私のだけ特別バージョン?(^^;

KEN 2007/03/29(木) 13:27:52
[[解決]]
iijimaさん、BLUEさんのおかげで無事に解決することが出来ましたので本件は解決済み
とさせて頂きます。貴重なアドバイス等ありがとうございました。

古いスレッドには追加発言できません。