MS Rich Edit Control ("RICHEDIT50W") bug? Control does unnecessary font substitutions.

simonx 126 Reputation points
2022-12-06T14:28:00.727+00:00

I am using the MS Rich Edit Control in my MFC Visual C++ application. Users can select certain symbols to insert into the text. I have had complaints that when they try to insert certain characters into the text, it switches to a different font, which causes problems. I initially assumed that this must be because the character was not available in the current font. But that's not the case.

For testing purposes, I was using Tahoma as the default font in the control (which is also the default font used by my users). This was specified both in the Rich Text Format, and using SetDefaultCharFormat, and it works fine.

Here are 4 examples of characters which, when inserted, cause a font switch:

  • Character Map code = U+2248 ("Almost equal to" - 2 wavy lines). If you insert this into the MS Rich Edit Control, it switches the font to "Cambria Math".
  • Character Map code = U+25B2 ("Black up-pointing triangle"). If you insert this into the MS Rich Edit Control, it switches the font to "Segoe UI Symbol".
  • Character Map code = U+2026 ("horizontal ellipsis"). If you insert this into the MS Rich Edit Control, it switches the font to "Segoe UI Symbol".
  • Character Map code = U+0153 ("Latin small ligature Oe"). If you insert this into the MS Rich Edit Control, it switches the font to "Segoe UI Symbol".

In all cases except the last, you cannot change the font to anything else for this character. The control will just ignore the font change. The exception is the last one (U+0153). You can't stop it setting the font to "Segoe UI Symbol" when you insert it, but you can then set the font for that character back to Tahoma.

Bear in mind that all of these characters exist in Tahoma. All of them can be pasted into Notepad.

For interest, some of this behaviour also happens in Wordpad (which I presume uses the MS Rich Edit Control). If you copy-and-paste the U+25B2 character, for example (from Notepad), it goes in as Segoe UI Symbol. If you copy-and-paste the U+2248 character from Notepad into Wordpad, it goes in as Cambria Math. And in both cases, Wordpad ignored all my attempts to change the fonts for these characters to anything else.

Is this a bug in the MS Rich Edit control? Anyone from Microsoft care to comment?

C++
C++
A high-level, general-purpose programming language, created as an extension of the C programming language, that has object-oriented, generic, and functional features in addition to facilities for low-level memory manipulation.
3,527 questions
{count} votes

4 answers

Sort by: Most helpful
  1. simonx 126 Reputation points
    2022-12-14T11:46:42.013+00:00

    I found the following article "RichEdit Font Binding" by Murray Sargent, posted on July 25th, 2021: https://devblogs.microsoft.com/math-in-office/richedit-font-binding

    It appears to be describing the behaviour that is causing my users so much grief. Apparently it is called "Font Binding". Is there any way to prevent this happening and to switch this behaviour off? In other words, I need the RichEdit control to behave like Notepad unless the user explicitly elects to use a rich text feature. If, for example, they paste text as plain text, I don't want the RichEdit control to interpret it as rich text (which is what happening now - with at least some characters).


  2. simonx 126 Reputation points
    2023-01-31T12:21:45.83+00:00

    Hi - I am still getting complaints about this issue from users of my application. The problem is that the Microsoft RichEdit control forces unnecessary and unwanted font switches using a process called "Font Binding", as described in the article "RichEdit Font Binding" by Murray Sargent, posted on July 25th, 2021: https://devblogs.microsoft.com/math-in-office/richedit-font-binding. For example, if they try to insert a smart quote (which is supported in the default font), instead of the default being used, the character is formatted by the RichEdit control as being in Segoe UI Symbol font. This causes all sorts of problems for them. They are going to great lengths to try to defeat this behaviour (saving, re-opening, reformatting - that kind of thing), and in some cases have not been able to find a workaround at all. There must be some way of preventing it from happening. Any help with this very much appreciated. Thank you.

    0 comments No comments

  3. simonx 126 Reputation points
    2023-01-31T12:24:04.7533333+00:00

    Is this the right place to post questions relating to the Microsoft RichEdit control? If not, where would be the right place?

    0 comments No comments

  4. simonx 126 Reputation points
    2023-01-31T15:18:58.7966667+00:00

    EM_SETCHARFORMAT is a Windows message for the RichEdit control. The wParam can be set to SCF_ASSOCIATEFONT. The documentation says about this: "RichEdit 4.1: Associates a font to a given script, thus changing the default font for that script. To specify the font, use the following members of CHARFORMAT2: yHeight, bCharSet, bPitchAndFamily, szFaceName, and lcid." Not sure what it means by 'script' but it looks as if it might be what I need to try and change the way font binding works. If I insert a smart quote, it gets switched to "Segoe UI Symbol" font, for example. So immediately after inserting the smart quote, I select it and do the following (I'm trying to get the RichEdit control to use "Tahoma" for symbols - and I'm assuming that the smart quote is being treated like a symbol):

    CHARFORMAT2 cf;
    memset(&cf, 0, sizeof(CHARFORMAT2));   
    cf.cbSize = sizeof(CHARFORMAT2);   
    cf.dwMask = CFM_FACE | CFM_SIZE | CFM_CHARSET | CFM_LCID;   
    cf.lcid = LOCALE_USER_DEFAULT;   
    cf.yHeight = 220;   
    cf.bPitchAndFamily = DEFAULT_PITCH | FF_DONTCARE; 
    cf.bCharSet = SYMBOL_CHARSET; 
    wcscpy(cf.szFaceName, L"Tahoma");   
    ::SendMessage(pRichEdit->m_hWnd, EM_SETCHARFORMAT, SCF_SELECTION | SCF_ASSOCIATEFONT, (LPARAM)&cf); 
    
    

    That has no effect. The smart quote is still in "Segoe UI Symbol". Is there an error in my code. Am I using EM_SETCHARFORMAT wrongly? Or have I misunderstood what it's for? All help with this very much appreciated. I'm really struggling.

    0 comments No comments