• ベストアンサー

リストビューで選択行の背景を変える

お世話になります。リストビューの選択行の背景色を変えたいと思い、カスタムドローを用い以下のようにしましたが、選択していない所も赤になってしまいます。 if (lplvcd->nmcd.dwDrawStage == CDDS_ITEMPREPAINT) {  // 選択行の背景色を変更  if (lplvcd->nmcd.uItemState & CDIS_SELECTED) {   lplvcd->clrTextBk = RGB(255, 0, 0);   lplvcd->nmcd.uItemState &= ~CDIS_SELECTED;  } else {   lplvcd->clrTextBk = RGB(255, 255, 255);  }  return CDRF_NOTIFYSUBITEMDRAW; } デバッグモードで見ると、else以降の分は解釈されていないようです。 リストビューは g_hList = CreateWindowEx(0 , WC_LISTVIEW , 0 , WS_CHILD | WS_VISIBLE | LVS_REPORT | LVS_NOSORTHEADER | LVS_SHOWSELALWAYS, 1 , 1 , width , lv_height , g_hMain , (HMENU)1 , g_hInst , NULL); dwStyle = ListView_GetExtendedListViewStyle(g_hList); dwStyle |= LVS_EX_GRIDLINES | LVS_EX_FULLROWSELECT | LVS_EX_SUBITEMIMAGES; ListView_SetExtendedListViewStyle(g_hList, dwStyle); ListView_SetBkColor(g_hList, RGB(240,240,240)); のようにしています。宜しくお願いします

質問者が選んだベストアンサー

  • ベストアンサー
  • Oh-Orange
  • ベストアンサー率63% (854/1345)
回答No.1

★『CDIS_FOCUS』定数を付けてみて下さい。 ・つまり >if ( lplvcd->nmcd.uItemState & CDIS_SELECTED ){  ↑  ここの部分を  int check = (CDIS_SELECTED | CDIS_FOCUS);    if ( (lplvcd->nmcd.uItemState & check) == check ){  とします。 ・リストビューやツリービューでは選択された場所を CDIS_SELECTED と CDIS_FOCUS 定数の  両方のビットが立っているときです。CDIS_SELECTED 定数だけでは判定するのに不十分です。  他にも LVNI_SELECTED、LVNI_FOCUSED 定数も同じ考えで2つ指定してから判定します。 ・以上。

masaota56
質問者

補足

ありがとうございます、できました。 ただ複数行選択の場合にフォーカスがある行しか反映されません。この場合はどうしたらいいでしょうか。 色々いじったのですが分かりませんでした・・・ //行毎の描画 if (lplvcd->nmcd.dwDrawStage == CDDS_ITEMPREPAINT) {  // 選択行の背景色を変更  int check = (CDIS_SELECTED | CDIS_FOCUS);   if ((lplvcd->nmcd.uItemState & check) == check){    lplvcd->clrTextBk = RGB(0,0,0);    lplvcd->clrText = RGB(255,255,255);    lplvcd->nmcd.uItemState &= ~CDIS_SELECTED;   }   return CDRF_NEWFONT; }

その他の回答 (2)

  • iyomante
  • ベストアンサー率60% (14/23)
回答No.3

複数選択時にフォーカスのある行だけ反映されてしまうのは、 CDIS_FOCUS を追加してるからですよ。 LVS_SHOWSELALWAYS これはフォーカスがなくても選択状態を表示するオプションですですから、それを意図して組んでらっしゃるのだと思いますが。 その部分に関しては最初のソースが正しいと思います。 それでは。

masaota56
質問者

お礼

LVS_SHOWSELALWAYSをつけると希望の動作はできないのですね。 何度もありがとうございました。

  • iyomante
  • ベストアンサー率60% (14/23)
回答No.2

if (lplvcd->nmcd.dwDrawStage == CDDS_PREPAINT) { return CDRF_NOTIFYITEMDRAW; } if (lplvcd->nmcd.dwDrawStage == CDDS_ITEMPREPAINT) { if (lplvcd->nmcd.uItemState & CDIS_SELECTED) { lplvcd->clrTextBk = RGB(255, 0, 0); lplvcd->nmcd.uItemState &= ~CDIS_SELECTED; } else { lplvcd->clrTextBk = RGB(255, 255, 255); } return CDRF_NEWFONT; } これでいいんでは? CDDS_PREPAINT の場合の処理と CDRF_NEWFONT を返すようにする部分が、抜けていたのでは。

masaota56
質問者

お礼

すみません、補足の補足です。 CDRF_NEWFONTは最初つけていませんでした。今はつけています。

masaota56
質問者

補足

回答ありがとうございます。両方ともつけています。 どうもCDIS_SELECTEDのみだと選択していないものも検知してしまうようで、全てが赤になってしまいます。 当初の質問はNo.1さんの回答で解決したのですが、今度は複数選択時に苦戦しています。。。

関連するQ&A