Why does my window style change when I call SetWindowText?


A customer observed some strange behavior with window styles:

We ran some weird behavior: Calling the Set­Window­Text function causes a change in window styles. Specifically, calling Set­Window­Text results in the WM_STYLE­CHANGING and WM_STYLE­CHANGED messages, and sometimes the result is that the WS_TAB­STOP style is removed. Is this a bug? What would cause this?

The Set­Window­Text message sends the WM_SET­TEXT message to the control, at which point anything that happens is the window's own responsibility. If it wants to change styles based on the text you sent, then that's what happens. The window manager doesn't do anything special to force it to happen or to prevent it.

That's weird, because I'm not even listening for WM_SET­TEXT messages. I also verified that there is no call into my code during the call to the the Set­Window­Text function.

I'm assuming that the window belongs to the same process as the caller. If the window belongs to another process, then the rules are different.

I'm changing the text of a window created by the same thread.

Okay, so let's see what we have so far. The customer is calling the Set­Window­Text function to change the text of a window created on the same thread. There is no handler for the WM_SET­TEXT message, and yet the window style is changing. At this point, you might start looking for more obscure sources for the problem, like say a global hook of some sort. While I considered the possibilities, the customer added,

It may be worth noting that I'm using the Sys­Link.

Okay, now things are starting to make sense, and it didn't help that the customer provided misleading information in the description of the problem. For example, when the customer wrote, "There is no handler for the WM_SET­TEXT message," the customer was not referring to the window whose window text is changing but to some other unrelated window.

It's like responding to the statement "A confirmation letter should have been sent to the account holder" with "I never got the confirmation letter," and then the person spends another day trying to figure out why the confirmation letter was never sent before you casually mention, "Oh, I'm not the account holder."

The WM_SET­TEXT message is sent to the window you passed to Set­Window­Text; in this case, it's the Sys­Link window. It is therefore the window procedure of the Sys­Link window that is relevant here.

The Sys­Link control remembers whether it was originally created with the WS_TAB­STOP, and if the markup it is given has no tab stops, then it removes the style; if the markup has tab stops, then it re-adds the style.

How do I add a tab stop to a string? I couldn't find any reference to it and all my guesses failed.

The tab stops in question are the hyperlinks you added when you used the <A>...</A> notation. If the text has no hyperlinks, then the control removes the WS_TAB­STOP style because it is no longer something you can tab to.

Comments (9)
  1. Gabe says:

    For those wondering what a SysLink is, it's a text control that can have embedded hyperlinks: msdn.microsoft.com/…/bb760706.aspx

  2. chentiangemalc says:

    I find this is pretty common with support – people providing misleading info. As a result I've developed strong sense of skepticism when told "facts" About an issue…have to think "in theory is there any potential for this result with suggested conditions" if no 9 out of 10 times one of the "facts" was not really investigated or confirmed, rather it was assumed. Of course you still have the odd case where there really is a strange obscure bug.

  3. It's all too common that an end user gathers symptoms A, B, C and then concludes that it must be "D" that's the root cause.  They then complain about "D" and C – psychic powers (similar to Raymond's) eventually draw out A and B and lead to the correct conclusion "E".  I then, as the ISV, go whinge to the customer's IT support people that then really need to fix "E" since it's not our issue, but that I've fixed it for them this time..   (I just finished such a call) :)

  4. Feeling a bit inflated ? says:

    Oh my, Oh my… many customers are morons but it doesn't help that the customer support are arrogant a-holes either….

    Common ground, people, read about it !

    We have all been beginners. So is it so hard to understand when other beginners fail at explaining wrong when they do not know what info we need ?

    I have always wondered how some learned people becomes arrogant with an over-inflated self-importance, that think they are special because of what they know.

    Elitism so disgusting and so illogical.

    Baffling indeed.

    Is it just something that goes wring in the head ?

  5. Drak says:

    @Inflated: Uhm.. right.. So when I ask 'have you got 3rd party software v8 installed?', the customer replies 'yes!', and later I find they have v9 installed, and I tell the customer 'I asked about v8' and they say 'I assumed v9 would be better than v8, so I said yes' then I'm the arrogant a-hole? Nice world view.

  6. No says:

    Raymond, your response is disingenuous. You know damned well that when the customer said he's "not even listening for WM_SET­TEXT messages", he means that he's not doing he thinks would cause styles to change in response WM_SETTEXT — clearly, if his code isn't changing the style, the style change must be a mystery, because he assumes that the operating system can't possibly be badly-designed enough to react to WM_SETTEXT that way.

    Now, this assumption turns out not to be valid, but that's not the poor customer's fault. It's our fault, and we should just fess up to it instead of blaming the victim for providing "incomplete" information. It doesn't help your case that the MSDN documentation to which you linked doesn't mention SysLink's silly WS_TABSTOP behavior.

    The right response is "Sorry about that. We've filed a doc bug."

  7. Evan says:

    @No: "You know damned well that when the customer said he's "not even listening for WM_SETTEXT messages", he means that he's not doing he thinks would cause styles to change in response WM_SETTEXT"

    What? That's not what I get out of that at all. My reading of "I'm not even listening for WM_SETTEXT" is much closer to "not only am I not doing anything actively that would cause styles to change on WM_SETTEXT, I'm not even grabbing WM_SETTEXT messages in the first place, so I can't!"

    What do you think "not even" means?

  8. @No, @Evan:  exactly, don't blame the customer for not having source code to the SysLink control!!  I assume Raymond was linking to this section of the MSDN page about SysLink creation:  "Specifying the WS_TABSTOP style ensures that the user will be able to select a link by tabbing to it and pressing the Enter key."  Nowhere does it say anything about modification of WS_TABSTOP style on WM_SETTEXT.  Without access to the source code like Raymond had, the customer had no choice but to go by what is stated in MSDN – which states nothing about this behavior.  So they assumed there was a bug.

    A more interesting question would be why did the customer notice this in the first place?

  9. And think about the typical usage of the SysLink control.  I can't fathom a reason why I would have special handling for WM_SETTEXT.  So most customers, probably including this one, aren't going to do anything special, and just defer to the SysLink control's default handling…

Comments are closed.