News:

Masm32 SDK description, downloads and other helpful links
Message to All Guests

Main Menu

how to change background color of static control, and add text - resolved

Started by quarantined, August 14, 2022, 05:44:08 AM

Previous topic - Next topic

quarantined

Newbie questions I know...

What I want to do, is change the color of a static control (to show it has been 'selected')
Once selected, press number on keyboard/keypad to 'enter' a number to be written to the static control.
Once a number has been written, revert background color to its original

Seems there is no way to do what I intend simply using WM_XXXXXXXX messages. I had created a colored static control, but
could not set the text with a call to SetWindowText. (that code has been recycled)

So thereofore I know I will need to do what is required using device contexts, DrawText, etc. But exactly how can this be accomplished without too much aggravation?

Just need to be pointed in the right direction, I dont expect anyone to write the code for me.

Attempting to write a sudoku game (Not sudoku solver - that would be much later)
The basic code is here:

Source for succesful demonstration of static control with colored background and (black) text in my last post in this thread

NoCforMe

WM_CTLCOLORSTATIC is your friend here:


Recipe for Delicious Colored Text
---------------------------------

How to present text (in a static control used for output) in a color other than basic black.


1. Set the color:

$colorDkRed EQU 192
$highlightColor EQU $colorDkRed


2. Create a color and a brush that color of the (dialog, window) background:

BkColor DD ?
BkBrush HBRUSH ?

INVOKE GetSysColor, COLOR_BTNFACE ;Color of (default) dialog background.
MOV BkColor, EAX
INVOKE CreateSolidBrush, EAX
MOV BkBrush, EAX


3. Store the handle of the control we want to colorize:

ChordLenOutHandle HWND ?

INVOKE GetDlgItem, hWin, $chordLenOut ;If it's in a dialog.
MOV ChordLenOutHandle, EAX


4. Catch the WM_CTLCOLORSTATIC message (in the parent window proc of the control):

MOV EAX, uMsg
CMP EAX, WM_INITDIALOG
JE do_init

. . .

CMP EAX, WM_CTLCOLORSTATIC ;Look for controls we want to display in diff. colors.
JE doClr


5. Handle the message:

; Look for handles of controls where we want different color text.
; lParam = handle of control that sent message:
doClr: MOV EAX, lParam
CMP EAX, ChordLenOutHandle
JE setclr
CMP EAX, ArcAngleOutHandle
JNE dodefault

setclr: INVOKE SetTextColor, wParam, $highlightColor ;wParam = HDC.
INVOKE SetBkColor, wParam, BkColor

; Return with background brush:
MOV EAX, BkBrush
RET


This code is for a dialog, but it could just as easily be used for any window that "owns" controls (i.e., the parent of child static controls).

Nice thing here is you don't have to mess with device contexts here, except to use the pre-packaged one that Windows passes you in wParam.

Keep in mind that you have to set the background color (by returning that brush) as well as the foreground color of the control, so you'll probably want to match the existing background of the static control so it doesn't look funny.

BTW, you can do the same thing for an edit control by handling WM_CTLCOLOREDIT.

(This is a "recipe" that I wrote for myself some time ago to do just what you want to do.)
Assembly language programming should be fun. That's why I do it.

quarantined

Quote from: NoCforMe on August 14, 2022, 06:24:20 AM
(This is a "recipe" that I wrote for myself some time ago to do just what you want to do.)

Thanks, NoCforMe. I'll work on it and post what I come up with.
I'm on my iPad right now, but I'll check it out when I'm back at my computer.

quarantined

Giving your code a quick look, I'm not sure it is what I'm after. What I want to do is change the background color of a static control when left clicked. Then a flag would be set indicating that the control is selected.

Once selected, I would then press a number on the keyboard and then write that number onto the static control that was selected after which I unset the 'selected' flag. Upon returning I want the background color to revert to original. Don't need to change the text color from black.

I might just revert to using bit maps to do my bidding. But I'll still experiment with CTLCOLORSTATIC in the meantime...

Since we are dealing with device context probably means handling WM_PAINT msgs.?..

NoCforMe

The code I showed you will do exactly what you want it to. You don't have to change the color of the text; that's just what's usually done with this message. It will change the background color to whatever you want, using both SetBkColor() and by setting the background brush that you return.

The only thing I'm not sure of is being able to catch a mouse click on the control; for that you'll probably have to subclass the control. (But since you're smarter than a box of rocks, that shouldn't be a problem.) You could also handle that by catching WM_RBUTTONDOWN in the parent window proc, then doing your own "hit test" to see if the click was over that static control (also not rocket surgery).
Assembly language programming should be fun. That's why I do it.

quarantined

If it would turn out to be more complex than it should (which it sounds like it might), as I said I'll just use bit maps. But thanks again for trying. I'll still play with this a bit before giving up though. I might have to find a sharper tool in the shed to do it though.  :tongue:

NoCforMe

Believe me, using bitmaps would be a much harder way to do this simple task. Not a sharper tool in this case. (Unless you want to change the imagery of your statics.)
Assembly language programming should be fun. That's why I do it.

hutch--

If you want an interactive control, a static control is not the right control to use. a "BUTTON" class control set to the BS_BITMAP style will do what you need with 2 bitmaps and a subclass to switch between the two.

NoCforMe

Hutch is right; if you want the control to respond to mouse clicks, then a button would be the way to go.

You may not need to use bitmaps, however: there's another CTLCOLOR message you can use, WM_CTLCOLORBTN. (See, they covered all the controls here with that functionality.) You can use this to set the background color. You wouldn't even need to subclass the control.

The only reason I can see for using bitmaps is if you wanted something besides a plain colored background for the rectangle.

If you do use this message, you'll need to create the button with the "owner draw" style (BS_OWNERDRAW), which means that you are now responsible for drawing all aspects of the control. Not that hard to do.
Assembly language programming should be fun. That's why I do it.

quarantined

Quote from: hutch-- on August 14, 2022, 09:23:35 AM
If you want an interactive control, a static control is not the right control to use.

I know your line of thinking, but if using SS_NOTIFY is or'ed in the window style, will enable interactivity similar as if it were a button.

Quote from: NoCforMe on August 14, 2022, 10:29:42 AM
... there's another CTLCOLOR message you can use, WM_CTLCOLORBTN

I've already had issues with WM_CTLCOLORxxx messages...

Quote...with the "owner draw" style (BS_OWNERDRAW), which means that you are now responsible for drawing all aspects of the control. Not that hard to do.
This is where the 'box of rocks' side of me comes in...  :undecided: I don't have any experience with using BS_OWNERDRAW, or a whole lot of experience working with device contexts in general.

Anyway, I'll figure it out eventually. I've found some examples with what I think might be useful techniques for doing what I endeavor to do. I'm experimenting as I'm writing this... I'll keep you guys posted with any progress or lack thereof.  :cool:


NoCforMe

Quote from: swordfish on August 14, 2022, 02:41:26 PM
Quote from: NoCforMe on August 14, 2022, 10:29:42 AM
... there's another CTLCOLOR message you can use, WM_CTLCOLORBTN

I've already had issues with WM_CTLCOLORxxx messages...

So what issues have you had? That's one of the easier message classes to implement responses to. Maybe we can help you through this.
Assembly language programming should be fun. That's why I do it.

quarantined

Quote from: NoCforMe on August 14, 2022, 04:15:01 PM
Quote from: swordfish on August 14, 2022, 02:41:26 PM
Quote from: NoCforMe on August 14, 2022, 10:29:42 AM
... there's another CTLCOLOR message you can use, WM_CTLCOLORBTN

I've already had issues with WM_CTLCOLORxxx messages...

So what issues have you had? That's one of the easier message classes to implement responses to. Maybe we can help you through this.

Thats alright. Currently I'm trying a different approach...

quarantined

Here's my nonconformist approach...   :biggrin:

Static control as the displayed 'cell'

Custom colored static control as the 'selection highlight' colored background

Only displaying one cell for this test. Once filled up, will have a 9x9 grid of cells. Have to write code so that only one cell can be selected at a time also disallow invalid cell entries following sudoku rules...
Looks like were off to the races (sharp tool speaking - lol)

Source for succesful demonstration of static control with colored background and (black) text in my last post in this thread

TimoVJL

May the source be with you

hutch--

The WM_CTLCOLORBTN only works on the button border, not the face of the button. You solve this with BS_BITMAP on a "BUTTON" class control and if you want to have the button appearance change, you create a subclass and switch the two bitmaps.