スタティックテキストの色変更 – プログラミング – Home

スタティックテキストの色変更
 
通知
すべてクリア

[解決済] スタティックテキストの色変更


PING
 PING
(@PING)
ゲスト
結合: 23年前
投稿: 3
Topic starter  

1秒ごとにスタティックテキストの背景色等を変更するプログラムを
作っているのですが、約1時間半ぐらいで、スタティックテキスト部分が白くなり
ダイアログが崩れていってしまいます。
下記の通り書いてるのですが不具合箇所がどなたかお分かりでしょうか?
よろしくお願いします。
1秒を10msでやると50秒ほどで白くなり色が付かなくなります。
Invalidate()をやりすぎるといけないのでしょうか?

HBRUSH CSrvMonitorDlg::OnCtlColor(CDC* pDC, CWnd* pWnd, UINT nCtlColor)
{
  HBRUSH hbr = CDialog::OnCtlColor(pDC, pWnd, nCtlColor);
  // TODO : ここで DC の属性を変更してください。
  if(nCtlColor==CTLCOLOR_STATIC){
    if(pWnd->GetDlgCtrlID() == IDC_STATIC1){
       pDC->SetBkMode(TRANSPARENT);//背景色を見せる
       pDC->SetTextColor(RGB(f_aka,f_green,f_blue));//文字色      
       return ::CreateSolidBrush(RGB(b_aka,b_green,b_blue));//背景色
}
  }
  // TODO : 既定値を使用したくない場合は別のブラシを返します。
  return hbr;
}

//色を変える部分★★ここを1秒ごと呼んでます。
void CSrvMonitorDlg::ColorChange()
{
  CStatic *static1=(CStatic*)GetDlgItem(IDC_STATIC1);
  static1->SetFocus();
  static1->Invalidate(TRUE);
}


引用未解決
トピックタグ
くたくた
 くたくた
(@くたくた)
ゲスト
結合: 23年前
投稿: 119
 

「CreateSolidBrush()に対するDeleteObject()が無い」のが原因ではないでしょうか。


返信引用
アイススケーター
 アイススケーター
(@アイススケーター)
ゲスト
結合: 23年前
投稿: 280
 

リソースの問題では・・・
CreateSolidBrushの後で、DeleteObjectが必要です。(HELPを見てね)


返信引用
ん
 ん
(@ん)
ゲスト
結合: 23年前
投稿: 81
 

::CreateSolidBrush() じゃーなくて CBrush を使ったほうが
簡単ではないでしょうか。
私はそうしてますんで。


返信引用
PING
 PING
(@PING)
ゲスト
結合: 23年前
投稿: 3
Topic starter  

DeleteObjectを追加したら時間的に長くなったので一部解決しました。
大変助かりました。ありがとうございます。

がしかし、まだ同様な不具合が発生するので当方で確認したところ、
スレッドでSrvCheck()が1秒ごとに呼ばれ、
SetDlgItemText(IDC_STATIC1,実行中);//状態表示

上記のようにスタティックテキストに書いているのですが、
これをコメントアウトすると継続的に動作し、正常に動いているみたいなのですが、
このSetDlgItemText()でのスタティックへの書き方は悪いのでしょうか?
他に良い方法はありますでしょうか?

void CSrvMonitorDlg::ColorChange()
{
  CStatic *static1=(CStatic*)GetDlgItem(IDC_STATIC1);
  static1->SetFocus();
  static1->Invalidate(TRUE);
DeleteObject(hBrush);<<追加したらOKになりました。ありがとうございました。
}

//スレッドで呼ばれるところ
void CTestColorDlg::SrvCheck()
{
SetDlgItemText(IDC_STATIC1,実行中);//情報を表示

f_aka=f_green=f_blue=255; //フォント色:白
b_aka=0;b_green=128;b_blue=255; //背景色:青
ColorChange();

}


返信引用
アイススケーター
 アイススケーター
(@アイススケーター)
ゲスト
結合: 23年前
投稿: 280
 

文章を読んでいて、どういう現象になってどういう異常になったのかが
解らないんですが・・・

後、CreateとDeleteはなるべく同じサブルーチン内で行ったほうが
バグにならないと思うのですが。


返信引用
kazuma
 kazuma
(@kazuma)
ゲスト
結合: 24年前
投稿: 217
 

OnCtlColorは再描画が必要になるたびに呼ばれますから、
CSrvMonitorDlg::ColorChange
でDeleteObjectしても、CreateSolidBrushとDeleteObjectとが1対1に対応しません。

解決策は、
1.CSrvMonitorDlgに、CBrush型のメンバ変数を追加します。
2.CSrvMonitorDlg::OnInitDialogで一度だけCreateSolidBrushを呼びます。
3.CSrvMonitorDlg::OnCtlColorではそのブラシのハンドルを返すだけでいいです。


返信引用
kazuma
 kazuma
(@kazuma)
ゲスト
結合: 24年前
投稿: 217
 

あ、途中で色が変わるんですね。

その場合は先に挙げた1.~3.に加えて、
4.色を変えたいところ(CTestColorDlg::SrvCheckなど)で、DeleteObjectして、
CreateSolidBrushしなおします。


返信引用
PING
 PING
(@PING)
ゲスト
結合: 23年前
投稿: 3
Topic starter  

みなさん回答ありがとうございました。
おかげさまで、問題解決致しました。大変助かりました。

みなさんの意見を参考にCreateとDeleteを同じところで
やりましたら、うまくいきました。文字の書き込みをしても
色が抜けたり、画面が崩壊しなくなりました。

一部理解できない表現がありましたところは、お詫び致します。
ありがとうございました。


返信引用

返信する

投稿者名

投稿者メールアドレス

タイトル *

プレビュー 0リビジョン 保存しました
共有:
タイトルとURLをコピーしました