| フォーム (ウィンドウ) |
|---|
| タイトルバー以外でフォームをドラッグ1 |
| タイトルバー以外でフォームをドラッグ2 |
| フォームのサイズ変更を制限する |
| フォームのシステムメニューにメニューを追加する |
| フォームを完全に表示してから何か処理をする |
| メインのフォームを非表示で起動する |
| タスクバーのアイコンを消す |
| タイトルバーの高さを得る |
| ドラッグ&ドロップでファイル名を受け取る |
| コンポーネント (コントロール) |
| ラベル、ヒントのCaptionを複数行にする |
| タブ順にフォーカスを移動 |
| デスクトップからの絶対座標を得る |
| コントロールの四隅の位置を一度に取得する |
| コンポーネントの境界プロパティを一度に変更する |
| マウスでコントロールの位置を移動する |
| パネル (Panel) |
| マウスで位置を移動する |
| リストボックス (ListBox) |
| 水平スクロールバーを表示させる |
| コンボボックス (ComboBox) |
| ドロップダウンリストを表示させる |
| 行毎に文字列と数値を扱う |
| ストリンググリッド (StringGrid) |
| リバースカーソルを消す |
| セルの文字の色を変えてみる |
| リストビュー (ListView) |
| 任意の位置にカーソルを移動する |
| 任意の位置を編集状態にする |
| チェックボックスの変化に対応する |
| 指定行の文字色を変更 |
| ツリービュー (TreeView) |
| 任意の位置を編集状態にする |
| キャンバス (イメージ) |
| 画面(デスクトップ)のキャプチャー |
| 一部分の再描画 |
| ビットマップとJPEGイメージの相互変換 |
| キーボード マウス |
| マウスカーソルの表示/非表示 |
| マウスカーソルの移動範囲を制御する |
| キーバッファやマウスイベントをクリアする |
| プログラムでキーボードを押したと思わせる |
| アイコン |
| HWNDからアイコン(HICON)を取得する |
| タスクトレイ |
| タスクトレイにアイコンを表示 |
| タスクトレイに表示したアイコンでマウスイベントを受ける |
| タスクトレイに表示したアイコンをアニメーションしてみる |
| クリップボード |
| 文字を転送/取得する |
| 画像を転送/取得する |
| ファイル名 |
| パスからドライブ名を取得 |
| パスからドライブ名+ディレクトリを取得 |
| パスからファイル名を取得 |
| パスからファイル名の拡張子を取得 |
| ファイル名の拡張子を変更する |
| パスから拡張子無しのファイル名のみを取得する |
| その他 |
| 二重起動の防止 |
| フォーム(ウィンドウ)− タイトルバー以外でフォームをドラッグ1 |
|
フォームのMouseDownイベントに記述します。 if( Button == mbLeft ){ ReleaseCapture( ); SendMessage( Handle, WM_SYSCOMMAND, SC_MOVE | 2, 0 ); } PanelのMouseDownに記述すればPanelをドラッグでフォームを移動できます。 |
| フォーム(ウィンドウ)− タイトルバー以外でフォームをドラッグ2 |
|
ヘッダーの public: // ユーザー宣言 __fastcall TForm1(TComponent* Owner); の下あたりに以下の行を追加します。 protected: void __fastcall WMLButtonDown(TWMLButtonDown &Msg) { SendMessage( Handle, WM_SYSCOMMAND, SC_MOVE | 2, 0 ); } BEGIN_MESSAGE_MAP MESSAGE_HANDLER(WM_LBUTTONDOWN,TWMLButtonDown,WMLButtonDown) END_MESSAGE_MAP(TForm) |
| フォーム(ウィンドウ)− フォームのサイズ変更を制限する |
|
ヘッダーーの public: // ユーザー宣言 __fastcall TForm1(TComponent* Owner); の下あたりに以下の行を追加します。 protected: void __fastcall WMGetMinMaxInfo(TWMGetMinMaxInfo &Msg) { // 最小サイズ Msg.MinMaxInfo->ptMinTrackSize.x= 200; Msg.MinMaxInfo->ptMinTrackSize.y= 200; // 最大サイズ Msg.MinMaxInfo->ptMaxTrackSize.x= 800; Msg.MinMaxInfo->ptMaxTrackSize.y= 600; // 最大化サイズ Msg.MinMaxInfo->ptMaxSize.x= 800; Msg.MinMaxInfo->ptMaxSize.y= 600; } BEGIN_MESSAGE_MAP MESSAGE_HANDLER(WM_GETMINMAXINFO,TWMGetMinMaxInfo,WMGetMinMaxInfo) END_MESSAGE_MAP(TForm) ※ Builder5からオブジェクトインスペクタでできます。 |
| フォーム(ウィンドウ)− フォームのシステムメニューにメニューを追加する |
|
とりあえずフォームのコンストラクタ辺りに以下の行を追加 HMENU hm = GetSystemMenu( Handle, false ); // メニューの一番上に追加 InsertMenu( hm, SC_RESTORE, MF_BYCOMMAND | MFT_STRING, 10, "めにゅ〜1" ); // 次に追加 InsertMenu( hm, SC_RESTORE, MF_BYCOMMAND | MFT_STRING, 11, "めにゅ〜2" ); // メニューの一番下に追加 AppendMenu( hm, MF_STRING, 12, "めにゅ〜3" ); DrawMenuBar( Handle ); // ※id(10,11,12)は任意の値だが0xF000より小さい値にするらしい ヘッダーの public: // ユーザー宣言 __fastcall TForm1(TComponent* Owner); の下あたりに以下の行を追加します。 protected: void __fastcall WMSysCommand( TWMSysCommand Msg ) { HMENU hm = GetSystemMenu( Handle, false ); switch( Msg.CmdType ){ case 10: // めにゅ〜1 if( GetMenuState( hm, Msg.CmdType, MF_BYCOMMAND ) & MFS_CHECKED ){ // チェックを外す CheckMenuItem( hm, Msg.CmdType, MF_BYCOMMAND | MFS_UNCHECKED ); } else{ // チェックをを付ける CheckMenuItem( hm, Msg.CmdType, MF_BYCOMMAND | MFS_CHECKED ); } break; case 11: // めにゅ〜2 break; case 12: // めにゅ〜3 break; } DefaultHandler( &Msg ); } BEGIN_MESSAGE_MAP MESSAGE_HANDLER( WM_SYSCOMMAND, TWMSysCommand, WMSysCommand ) END_MESSAGE_MAP(TForm) |
| フォーム(ウィンドウ)− フォームを完全に表示してから何か処理をする |
|
コンストラクタ辺りに以下の行を追加 Application->OnIdle = FormIdle; ヘッダーのprivate辺りに以下の行を追加 private: // ユーザー宣言 void __fastcall FormIdle(TObject *Sender, bool &Done) { Application->OnIdle = NULL; // NULLを入れて再突入を防止しとく // ここで何かする } |
| フォーム(ウィンドウ)− メインのフォームを非表示で起動する |
|
コンストラクタ辺りに以下の行を追加 Application->ShowMainForm = false; |
| フォーム(ウィンドウ)− タスクバーのアイコンを消す |
|
コンストラクタ辺りに以下の行を追加 ShowWindow( Application->Handle, SW_HIDE ); |
| フォーム(ウィンドウ)− タイトルバーの高さを得る |
|
int height = GetSystemMetrics( SM_CYCAPTION ); |
| フォーム(ウィンドウ)− ドラッグ&ドロップでファイル名を受け取る |
|
コンストラクタ辺りに以下の行を追加。 DragAcceptFiles( Handle, true ); ヘッダーの public: // ユーザー宣言 __fastcall TForm1(TComponent* Owner); の下辺りに以下を追加します。 protected: void __fastcall WMDropFiles( TWMDropFiles &Msg ) { int cnt = DragQueryFile( (HDROP)Msg.Drop, 0xFFFFFFFF, NULL, MAX_PATH ); char buff[MAX_PATH+2]; for( int i = 0; i < cnt; i ++ ){ DragQueryFile( (HDROP)Msg.Drop, i, buff, MAX_PATH ); // buffにファイル名が入ったので、ここで何か処理しましょう } DragFinish( (HDROP)Msg.Drop ); } BEGIN_MESSAGE_MAP MESSAGE_HANDLER( WM_DROPFILES, TWMDropFiles, WMDropFiles ) END_MESSAGE_MAP(TForm) |
| コンポーネント(コントロール)− ラベル、ヒントのCaptionを複数行にする |
|
Caption = "1行目\n2行目"; |
| コンポーネント(コントロール)− タブ順にフォーカスを移動 |
|
FindNextControl( ActiveControl, true, true, false )->SetFocus( ); |
| コンポーネント(コントロール)− デスクトップからの絶対座標を得る |
|
Image1の座標を得る場合は TPoint p = ClientToScreen( Point(Image1->Left, Image1->Top) ); |
| コンポーネント(コントロール)− コントロールの四隅の位置を一度に取得する |
|
BoundsRectを使用します。 Panel1の4隅を取得する場合。 TRect rect = Panel1->BoundsRect; |
| コンポーネント(コントロール)− コンポーネントの境界プロパティを一度に変更する |
|
SetBoundsを使用します。 例えばForm1の大きさを半分にする場合。 TRect r = BoundsRect; SetBounds( r.Left, r.Top, (r.Right - r.Left) / 2, (r.Bottom - r.Top) / 2 ); |
| コンポーネント(コントロール)− マウスでコントロールの位置を移動する |
|
MouseDown、MouseMove、MouseUpイベントを使用します。 ヘッダーのprivate辺りにでも以下を追加 int Sx; int Sy; bool Flg; TImageを動かしてみる場合。 // Image1のMouseDownイベント void __fastcall TForm1::Image1MouseDown(TObject *Sender, TMouseButton Button, TShiftState Shift, int X, int Y) { if( Button != mbLeft ) return; Sx = X; Sy = Y; Flg = true; } // Image1のMouseMoveイベント void __fastcall TForm1::Image1MouseMove(TObject *Sender, TShiftState Shift, int X, int Y) { if( Flg == false ) return; Image1->SetBounds( Image1->Left + (X - Sx), Image1->Top + (Y - Sy), Image1->Width, Image1->Height ); } // Image1のMouseUpイベント void __fastcall TForm1::Image1MouseUp(TObject *Sender, TMouseButton Button, TShiftState Shift, int X, int Y) { Flg = false; } |
| パネル(Panel)− マウスで位置を移動する |
|
コンポーネント(コントロール)のマウスでコントロールの位置を移動するとかぶってますが、こっちは楽です。 void __fastcall TForm1::Panel1MouseDown(TObject *Sender, TMouseButton Button, TShiftState Shift, int X, int Y) { ReleaseCapture( ); dynamic_cast<TPanel *>(Sender)->Perform( WM_SYSCOMMAND, 0xF012, 0 ); } |
| リストボックス(ListBox)− 水平スクロールバーを表示させる |
|
int m = 0; for( int i= 0, w; i < ListBox1->Items->Count; i++ ){ w = Canvas->TextWidth( ListBox1->Items->Strings[i] ); m = m < w ? w : m; } SendMessage( ListBox1->Handle, LB_SETHORIZONTALEXTENT, m, 0 ); 又は ListBox1->Perform( LB_SETHORIZONTALEXTENT, m, 0 ); どっちでも同じ結果みたいです。 ちなみにm(ピクセル)をそのまま指定しても短いかも知れません。 その場合はm + 10とかして、適当に足して調整して下さい。 |
| コンボボックス(ComboBox)− ドロップダウンリストを表示させる |
|
ComboBox1->DroppedDown = true; |
| コンボボックス(ComboBox)− 行毎に文字列と数値を扱う |
|
リストを追加 ComboBox1->Items->AddObject( "aaaaaaaaaaa", (TObject *)10 ); ComboBox1->Items->AddObject( "bbbbbbbbbbb", (TObject *)20 ); ComboBox1->Items->AddObject( "ccccccccccc", (TObject *)30 ); 参照 Caption = (int)ComboBox1->Items->Objects[ComboBox1->ItemIndex]; |
| ストリンググリッド(StringGrid)− リバースカーソルを消す |
|
void __fastcall TForm1::StringGrid1DrawCell(TObject *Sender, int ACol, int ARow, TRect &Rect, TGridDrawState State) { TStringGrid *sg = dynamic_cast if( !sg->Focused( ) ){ if( sg->Row == ARow && sg->Col == ACol ){ sg->Canvas->Brush->Color = sg->Color; sg->Canvas->FillRect( Rect ); sg->Canvas->Font->Color = sg->Font->Color; sg->Canvas->TextOut( Rect.Left + 2, Rect.Top + 2, sg->Cells[ACol][ARow] ); } } } |
| ストリンググリッド(StringGrid)− セルの文字の色を変えてみる |
|
void __fastcall TForm1::StringGrid1DrawCell(TObject *Sender, int ACol, int ARow, TRect &Rect, TGridDrawState State) { TStringGrid *sg = dynamic_cast // 色を指定 sg->Canvas->Font->Color = clBlue; // 文字を書き直す sg->Canvas->TextOut( Rect.Left + 2, Rect.Top + 2, sg->Cells[ACol][ARow] ); } フォントやサイズも変更可能です。 特定のセルで行いたい場合はAColやARowでセルを指定します。 |
| リストビュー(ListView)− 任意の位置にカーソルを移動する |
|
int sp = 移動したいインデックス // カーソルを移動 ListView1->Selected = ListView1->Items->Item[sp]; // その場所を表示 ListView1->Items->Item[sp]->MakeVisible( false ); |
| リストビュー(ListView)− 任意の位置を編集状態にする |
|
int sp = 編集したいインデックス // 編集状態にする ListView1->Items->Item[sp]->EditCaption( ); |
| リストビュー(ListView)− チェックボックスの変化に対応する |
|
void __fastcall TMain::ListView1Change(TObject *Sender, TListItem *Item, TItemChange Change) { if( (int)Item->Data != (int)Item->Checked ){ / 変わった } Item->Data = Pointer( Item->Checked ); } |
| リストビュー(ListView)− 指定行の文字色を変更 |
|
OnCustomDrawItemイベント内で行います if( (int)Item->Data == 2 ) Sender->Canvas->Font->Color = clRed; |
| ツリービュー(TreeView)− 任意の位置を編集状態にする |
|
int sp = 編集したいインデックス // カーソルを移動 TreeView1->Selected = TreeView1->Items->Item[sp]; // 編集状態にする TreeView1->Items->Item[sp]->EditText( ); |
| キャンバス(イメージ)− 画面(デスクトップ)のキャプチャー |
|
HWND dc = GetDC( 0 ); BitBlt( Image1->Canvas->Handle, 0, 0, Screen->Width, Screen->Height, dc, 0, Screen->Height - Image1->Height, SRCCOPY ); ReleaseDC( 0, dc ); |
| キャンバス(イメージ)− 一部分の再描画 |
|
例えばPaintBox1の左上100x100を再描画させる場合 TRect rect = Rect( 0, 0, 100, 100 ); InvalidateRect( PaintBox1->Parent->Handle, (LPRECT)&rect, true ); |
| キャンバス(イメージ)− ビットマップとJPEGイメージの相互変換 |
|
Jpeg.hppが無かったらインクルードしときます。 ・JPEGをビットマップへ TJPEGImage *jpg = new TJPEGImage; jpg->LoadFromFile( "123.jpg" ); Image1->Picture->Bitmap->Assign( jpg ); delete jpg; Image1->Picture->SaveToFile( "123.bmp" ); ・ビットマップをJPEGへ Image1->Picture->LoadFromFile( "123.bmp" ); TJPEGImage *jpg = new TJPEGImage; jpg->Assign( Image1->Picture->Bitmap ); jpg->SaveToFile( "123.jpg" ); delete jpg; |
| キーボード&マウス− マウスカーソルの表示/非表示 |
|
// 消す Screen->Cursor = crNone; // 出す Screen->Cursor = crDefault; |
| キーボード&マウス− マウスカーソルの移動範囲を制御する |
|
以下はフォームからマウスカーソルを出さないようにしてます。 RECT r = BoundsRect; ClipCursor( &r ); ※ 上の例ではフォームを移動したらだめです。 ※ 終了時には必ず移動範囲を戻しましょう。 |
| キーボード&マウス− キーバッファやマウスイベントをクリアする |
|
MSG msg; // キーボード while( PeekMessage( &msg, Handle, WM_KEYFIRST, WM_KEYLAST, PM_REMOVE ) ); // マウス while( PeekMessage( &msg, Handle, WM_MOUSEFIRST, WM_MOUSELAST, PM_REMOVE ) ); |
| キーボード&マウス− プログラムでキーボードを押したと思わせる |
|
// Enterキーを押す keybd_event( VK_RETURN, 0, 0, 0 ); // Enterキーを放す keybd_event( VK_RETURN, 0, KEYEVENTF_KEYUP, 0 ); |
| アイコン− HWNDからアイコン(HICON)を取得する |
|
以下の関数はスモールアイコンを取得します。 アイコンが取れない場合はNULLが返ると思います。 HICON GetHIcon( const HWND Wnd ) { HICON icon = (HICON)GetClassLong( Wnd, GCL_HICONSM ); if( !icon ) icon = (HICON)SendMessage( Wnd, WM_GETICON, ICON_SMALL, 0 ); if( !icon ) icon = (HICON)SendMessage( Wnd, WM_GETICON, ICON_BIG, 0 ); return icon; } 最後のSendMessageはICON_BIGとなっていますが、これはC++Builder5以前(4は不明)では 取れなかったので、これで取れます。(表示する側で16x16に縮小すると思うので・・・) |
| タスクトレイ− タスクトレイにアイコンを表示 |
|
ヘッダーの上の方に以下の行を追加。 #define WM_NOTIFY_TASKTRAY (WM_USER + 1) ヘッダーのprivate:に以下の行を追加します。 NOTIFYICONDATA NotifyID; 以下の関数を追加。 void __fastcall TasktrayIcon( NOTIFYICONDATA *Notify ) { Notify->hWnd = Handle; Notify->uFlags = NIF_ICON | NIF_MESSAGE | NIF_TIP; Notify->hIcon = Application->Icon->Handle; Notify->uCallbackMessage = WM_NOTIFY_TASKTRAY; Notify->cbSize = sizeof( NOTIFYICONDATA ); Notify->uID = 1; lstrcpy( Notify->szTip, Application->Title.c_str( ) ); Shell_NotifyIcon( NIM_ADD, Notify ); } コンストラクタ辺りに以下の行を追加し、作成した関数を呼びます。 TasktrayIcon( &NotifyID ); Closeイベント辺りに以下の行を追加します。 Shell_NotifyIcon( NIM_DELETE, &NotifyID ); |
| タスクトレイ− タスクトレイに表示したアイコンでマウスイベントを受ける |
|
ヘッダーの public: // ユーザー宣言 __fastcall TForm1(TComponent* Owner); の下あたりに以下の行を追加します。 protected: void __fastcall WMTrayIcon( TMessage Msg ) { switch( Msg.LParam ){ case WM_LBUTTONDBLCLK: // 左ボタンダブルクリック Visible = Visible == true ? false : true; break; case WM_RBUTTONUP: // 右ボタンクリック { POINT pos; GetCursorPos( &pos ); SetForegroundWindow( Handle ); PopupMenu1->Popup( pos.x, pos.y ); } break; } } BEGIN_MESSAGE_MAP MESSAGE_HANDLER( WM_NOTIFY_TASKTRAY, TMessage, WMTrayIcon ) END_MESSAGE_MAP(TForm) この例では、左ボタンダブルクリックで表示/非表示を切り替えし、 右ボタンクリックでポップアップメニューを表示してます。 |
| タスクトレイ− タスクトレイに表示したアイコンをアニメーションしてみる |
|
タスクトレイにアイコンを表示の続きです。 ImageListに表示したいアイコンを追加します。 タイマーイベントで順次アイコンを変更していきます。 まず、ImageListからアイコンをゲット(変数は適当に定義して下さい)します。 ImageList1->GetIcon( IconIndex, Icon ); で、NotifyIDにアイコンをセットします。 NotifyID.hIcon = Icon->Handle; Shell_NotifyIcon( NIM_MODIFY, &NotifyID );を呼んでアイコンの変更をします。 |
| クリップボード− 文字を転送/取得する |
|
Clipbrd.hppをインクルードします。 Edit1の内容をクリップボードにコピー Clipboard()->AsText = Edit1->Text; クリップボードの内容をEdit1にコピー if( Clipboard( )->HasFormat( CF_TEXT ) ){ Edit1->Text = Clipboard( )->AsText; } |
| クリップボード− 画像を転送/取得する |
|
Clipbrd.hppをインクルードします。 Image1の内容をクリップボードにコピー Clipboard( )->Assign( Image1->Picture ); クリップボードの内容をImage1にコピー if( Clipboard( )->HasFormat( CF_BITMAP ) == true ){ Image->Picture->Bitmap->Assign( Clipboard( ) ); } |
| ファイル名− パスからドライブ名を取得 |
|
ExtractFileDriveを使います |
| ファイル名− パスからドライブ名+ディレクトリを取得 |
|
ExtractFileDir // 最後に¥が付かない ExtractFilePath // 最後に¥が付く |
| ファイル名− パスからファイル名を取得 |
|
ExtractFileNameを使います |
| ファイル名− パスからファイル名の拡張子を取得 |
|
ExtractFileExtを使います |
| ファイル名− ファイル名の拡張子を変更する |
|
ChangeFileExtを使います |
| ファイル名− パスから拡張子無しのファイル名のみを取得する |
|
// 自分のファイル名のみを取得 ExtractFileName( ChangeFileExt( Application->ExeName, "" ) ); |
| その他− 二重起動の防止 |
|
プロジェクトソースに記述します。 WINAPI WinMain(HINSTANCE, HINSTANCE, LPSTR, int) { HANDLE mutexhandle = CreateMutex( NULL, false, "My program" ); if( mutexhandle != NULL && GetLastError( ) == ERROR_ALREADY_EXISTS ){ Application->MessageBox( "二重起動です", "確認", MB_ICONSTOP ); CloseHandle( mutexhandle ); return -1; } try { Application->Initialize(); Application->CreateForm(__classid(TForm1), &Form1); Application->Run(); } catch (Exception &exception) { Application->ShowException(&exception); } if( mutexhandle != NULL ) CloseHandle( mutexhandle ); return 0; } CreateMutexの第3パラメータは適当に名前を入れます。 |