Solved

Colors in Disabled DropList Combo Box

Posted on 1997-08-24
17
675 Views
Last Modified: 2013-11-20
Environment:  VC++ 4.0  Win95

Hello,

What am I to do to show the edit control part of a Disabled-DropList-ComboBox in the colors of an enabled readonly edit control?  Or, in other words, all I want to do is to show the text of the above mentioned Disabled-DropList-ComboBox not dimmed, but black.

Overriding the OnCtlControl handler doesn't help - there is no problem to change the text background color, but the text color still appears dimmed.

Moshe.
0
Comment
Question by:stolar
  • 10
  • 4
  • 2
  • +1
17 Comments
 
LVL 4

Expert Comment

by:mbhakta
ID: 1304679
You have to make your combo box ownerdraw enables. Now make sure you override the OnDrawItem of the combo box. In the ondrawItem you will have a structure DRAWITEMSTRUCT passed to you containing draw related stuff such as DC, hWnd, rect etc. Using this you can do individual textout's for each item by choosing a back color, fore color and font of your choice. However, the edit control of the combo box will need a different handling routine as combobox is a combination of a list box and edit box. Check a few samples in the Win32 SDK or the VC++ CD.
0
 

Author Comment

by:stolar
ID: 1304680
As you put it --

"The edit control of the combo box" -- that (and not the list control) is exactly the subject of my question -- "will need a different handling routine" -- what kind? -- "as combobox is a combination of a list box and edit box" -- I knew that -- "Check a few samples in the Win32 SDK or the VC++ CD." -- please give me a lead.

I still can't proceed...
0
 

Author Comment

by:stolar
ID: 1304681
Adjusted points to 100
0
 

Author Comment

by:stolar
ID: 1304682
Adjusted points to 150
0
 

Author Comment

by:stolar
ID: 1304683
Adjusted points to 200
0
 
LVL 10

Expert Comment

by:RONSLOW
ID: 1304684
OnCtlColor should work (in theory), set the text color as well as returning the background brush.

You will probably want to respond to CTLCOLOR_EDIT (but check which ones you actually get)

I seem to be changing colors ok for my own combo boxes.

I'll double check my own code and see if I can change the text color as well - but I don't see it being a problem.

0
 

Author Comment

by:stolar
ID: 1304685
Eager to hear from you --
 
Are you changing TEXT (and not only background) colors in your DISabled DropLIST combo boxes?  

0
 
LVL 10

Expert Comment

by:RONSLOW
ID: 1304686
Yeup - disabled controls always show text in grey (and the V-button on the combo-box drop down).

Had to respond to CTLCOLOR_STATIC to get background color to change - but text color wouldn't work unless the control is enabled.

Mind you - there is the question of WHY do you want to fiddle with the standard colors - its generally not a good thing to do as it can create confusion in the user (as if they don't get confused enough already).

I think the only colution would be an owner-drawn combo box where you have complete control over the drawing. However, even here the drop-down button will by grey instead black.

Roger

0
Maximize Your Threat Intelligence Reporting

Reporting is one of the most important and least talked about aspects of a world-class threat intelligence program. Here’s how to do it right.

 

Author Comment

by:stolar
ID: 1304687
I have posted an article to Zafir Anjum's Home Page.  It contains a picture that illustrates my point.  

I don't want the V-button to appear in black, I want it to appear dimmed.

You may see the picture at
http://www.codeguru.com/misc/color_in_disabled_combo.html

Moshe
0
 

Expert Comment

by:nate091597
ID: 1304688
 You can do this easily with ownerdraw.  First, create a class derived from CComboBox and use ClassWizard to override DrawItem:

class CDisCombo : public CComboBox
{
//////////////// Irrelevant details omitted
// Overrides
      // ClassWizard generated virtual function overrides
      //{{AFX_VIRTUAL(CDisCombo)
      public:
      virtual void DrawItem(LPDRAWITEMSTRUCT lpDrawItemStruct);
      //}}AFX_VIRTUAL
};

  Next, fill in the code for DrawItem:

void CDisCombo::DrawItem(LPDRAWITEMSTRUCT lpDIS)
{
      if (-1 == lpDIS->itemData) // empty box or edit-part
      { return; }

      CString text;
      GetLBText(lpDIS->itemID, text);

      CDC dc;
      BOOL ok = dc.Attach(lpDIS->hDC);
      ASSERT(ok);

      ok = dc.DrawText(text, &(lpDIS->rcItem), DT_LEFT);
      ASSERT(ok);

      (void) dc.Detach();
}

  To use this combo in a dialog, you must add the combo to the resource, set the styles to drop list, owner draw fixed, and has-strings.  Next, add a member variable of type CDisCombo to your dialog:

#include "discombo.h"

class CDiscomboDlg : public CDialog
{
//////////////////// Irrelevant details omitted
private:
        CDisCombo m_combo;
};

Finally, set up the combo in OnInitDialog:

BOOL CDiscomboDlg::OnInitDialog()
{
      VERIFY(m_combo.SubclassDlgItem(IDC_COMBO1, this));
      VERIFY(CB_ERR != m_combo.AddString("one"));
      VERIFY(CB_ERR != m_combo.AddString("two"));
      VERIFY(CB_ERR != m_combo.AddString("three"));

                 return TRUE;
}

0
 

Author Comment

by:stolar
ID: 1304689
Hello,

I did exactly as being told.  It still DOES NOT give me the possibility to (quote from my original question) "show the text of the ... Disabled-DropList-ComboBox not dimmed, but black".

I will repeat it again:

The combo box is DISabled.  I want control over the color of the TEXT in the combo box's EDIT CONTROL.

What your method provides is --

A)  The possibility to control colors in the combo's LIST control.  I tried the following --

void CDisCombo::DrawItem(LPDRAWITEMSTRUCT lpDIS)
{
//MY COMMENT if (-1 == lpDIS->itemData) //empty box or edit part
//             { return; }

since it is the edit part I want to work with, but also in vain.  Placing a breakpoint on the following line I discovered that CDisCombo::DrawItem does not get called to process the edit part of the combo.

B) The combo box appears with the cursor blinking in the edit part and the text may be modified.  That's not my goal.  One can not change the text that appears in a DropLIST combo box.

Moshe.

NB:  In CDiscomboDlg::OnInitDialog() I have a CDialog::OnInitDialog() call after
VERIFY(CB_ERR != m_combo.AddString("three"));
0
 

Accepted Solution

by:
nate091597 earned 200 total points
ID: 1304690
 Thanks for explaining what happened in detail; I see your mistake.  You set the style to drop down, not drop list.  That's why you see an edit box with the cursor blinking.  Set the combo's style to drop list, and you will see the behavior you want.      As for the first line of DrawItem, I'm sorry if my comment was misleading.  lpDIS->itemData is -1 if the "edit" part is empty or the lbox is empty.  Perhaps it would be more clear to compare lpDIS->itemID to -1 instead; it works the same.
    Finally, you're right, you need a call to CDialog::OnInitDialog; I should have commented that I was leaving some of the wizard-generated stuff out.

0
 

Author Comment

by:stolar
ID: 1304691
The following text is addressed to Expert "nate"
================================================


Hello,

It works!  How stupid of me to "forget" to set the style to DropList!  For some reason I was sure I have done it and didn't check.  Moreover, you _did_ say that setting DropList style is required.

Regardless of whether you answer the following or not I am going to grade your help as "Excelent!".

Now, I do have three more questions with regard to the method and I would like the answers from _you_, if you can kindly provide them.

My hesitation to grade your answer on the spot comes from the fact that when I do so, any other expert may "lock" my questions that follow.  Also, I won't mind increasing the points promised, since I realize there is more work to do.

Question 1.
===========
Before my application calls DoModal to invoke the dialog, it sets a member variable, CDiscomboDlg.mode, to "enabled" or "disabled", and the combo box is to appear accordingly.  In OnInitDialog I have the following construction:

if(mode==ENABLED) {
    // invoke combo enabled
}
else {  //mode==DISABLED  
    // invoke combo disabled
}

Thanks to your help, I can now display the DISabled combo box with the text color of my choice.  

However, in case the combo is to be ENabled, I want it to behave in the standard DropList way, that is, to have the ability to scroll the selection in the combo's list with the arrow keys,
to see the selected item's text in the "selected" color, to have the "focus bar" around the selection, etc.

In other words:  How do I cause a DropList combo box that is defined in the resource editor as "Owner draw: Fixed" to appear as if defined "Owner draw: No" ?

Note:  I don't need the AddString functions, the item texts are defined in the resource editor.

Question 2
==========
An irritating trifle:  Why does the owner draw combo appear to be a few pixels higher than defined in the resource editor?  

Note:  I could attach a tiny picture to illustrate this, but Experts Exchange doesn't allow it.

Question 3
==========
I found that instead of doing

    m_combo.SubclassDlgItem(IDC_COMBO1, this);

in CDiscomboDlg::OnInitDialog, I might as well do

    DDX_Control(pDX, IDC_COMBO1, m_combo);  
   
in CDiscomboDlg::DoDataExchange and have the same results.

I don't quite realize what consequences may be implyied.
Which is the "right" way to do it?


Thank you,
Moshe.

0
 

Expert Comment

by:nate091597
ID: 1304692
1)  There are two ways - easy and hard.  The hard way is to complete DrawItem to handle all the cases.  The easy way is to put two combos on top of each other in your dialog resource and hide the one you're not going to use.

2)  IMHO, this is a bug in the combo implementation.  It is very hard to fix, i.e., I spent some time once trying to work around it and decided it was way too much effort.  Still, if you want to try, here's a start.
    Override the combo's MeasureItem and set the size you want, e.g.,

void CDisCombo::MeasureItem
(LPMEASUREITEMSTRUCT lpMIS)
{ lpMIS->itemHeight = 15; }

    In OnInitDialog, create the combo yourself (no resources) with these styles:

WS_CHILD | WS_VISIBLE | WS_VSCROLL |            CBS_DROPDOWNLIST | CBS_OWNERDRAWFIXED | CBS_HASSTRINGS | CBS_SORT

    Next, set the font:

m_combo.SetFont(GetFont());

    Finally, add the items manually:

int rc = m_combo.AddString("one");
ASSERT(CB_ERR != rc);
rc = m_combo.AddString("two");
ASSERT(CB_ERR != rc);
rc = m_combo.AddString("three");
ASSERT(CB_ERR != rc);

3)  DDX_Control works because it automatically hooks up the control if the control's m_hWnd is NULL.  It calls SubclassWindow for you, so the two methods are equivalent.  I prefer the first method, though, because I think it is more clear.

0
 

Author Comment

by:stolar
ID: 1304693
I promised to Expert "nate" to increase the points (above).

When grading the last comment I did increase the points to 250, I graded "Excellent" and submitted.  Now I see that "nate" received only 200 points.

I feel very bad about this.  How do I give "nate" the 50 points that I owe him now, when my question is in the <paq> status?

Moshe.

0
 

Expert Comment

by:nate091597
ID: 1304694
Try emailing questions@experts-exchange.com.  Thanks.
0
 

Author Comment

by:stolar
ID: 1304695
I did, I also wrote to qna@experts-exchange.com.  No replies.
Here is what I'll do now --

I am going to post a new question and evaluate it to 50 points.  I'll entitle it "For nate only".  I will reject any expert that locks it, except for "nate".  When "nate" will lock the question I am going to grade it and this way "nate" will receive the 50 points that I owe him.

I hope this will outwit the Experts Exchange robot.

I take this opportunity to say that I did fully implement the methods that are described above in sections 1 and 2 and it works perfect and beautiful.
0

Featured Post

Enabling OSINT in Activity Based Intelligence

Activity based intelligence (ABI) requires access to all available sources of data. Recorded Future allows analysts to observe structured data on the open, deep, and dark web.

Join & Write a Comment

Suggested Solutions

Introduction: The undo support, implementing a stack. Continuing from the eigth article about sudoku.   We need a mechanism to keep track of the digits entered so as to implement an undo mechanism.  This should be a ‘Last In First Out’ collec…
Have you tried to learn about Unicode, UTF-8, and multibyte text encoding and all the articles are just too "academic" or too technical? This article aims to make the whole topic easy for just about anyone to understand.
This video will show you how to get GIT to work in Eclipse.   It will walk you through how to install the EGit plugin in eclipse and how to checkout an existing repository.
Get a first impression of how PRTG looks and learn how it works.   This video is a short introduction to PRTG, as an initial overview or as a quick start for new PRTG users.

743 members asked questions and received personalized solutions in the past 7 days.

Join the community of 500,000 technology professionals and ask your questions.

Join & Ask a Question

Need Help in Real-Time?

Connect with top rated Experts

13 Experts available now in Live!

Get 1:1 Help Now