diff --git a/dlls/riched20/editor.c b/dlls/riched20/editor.c index ec584eb2820..bbb0cc01bc2 100644 --- a/dlls/riched20/editor.c +++ b/dlls/riched20/editor.c @@ -533,7 +533,7 @@ void ME_RTFCharAttrHook(RTF_Info *info) ME_Style *style2; RTFFlushOutputBuffer(info); /* FIXME too slow ? how come ? */ - style2 = ME_ApplyStyle(info->style, &fmt); + style2 = ME_ApplyStyle(info->editor, info->style, &fmt); ME_ReleaseStyle(info->style); info->style = style2; info->styleChanged = TRUE; @@ -2920,6 +2920,7 @@ ME_TextEditor *ME_MakeEditor(ITextHost *texthost, BOOL bEmulateVersion10, DWORD ed->wheel_remain = 0; + list_init( &ed->style_list ); OleInitialize(NULL); return ed; @@ -2929,6 +2930,7 @@ void ME_DestroyEditor(ME_TextEditor *editor) { ME_DisplayItem *pFirst = editor->pBuffer->pFirst; ME_DisplayItem *p = pFirst, *pNext = NULL; + ME_Style *s, *cursor2; int i; ME_ClearTempStyle(editor); @@ -2938,6 +2940,10 @@ void ME_DestroyEditor(ME_TextEditor *editor) ME_DestroyDisplayItem(p); p = pNext; } + + LIST_FOR_EACH_ENTRY_SAFE( s, cursor2, &editor->style_list, ME_Style, entry ) + ME_DestroyStyle( s ); + ME_ReleaseStyle(editor->pBuffer->pDefaultStyle); for (i=0; ipBuffer->pCharStyle) editor->pBuffer->pCharStyle = ME_GetInsertStyle(editor, 0); - s = ME_ApplyStyle(editor->pBuffer->pCharStyle, pFmt); + s = ME_ApplyStyle(editor, editor->pBuffer->pCharStyle, pFmt); ME_ReleaseStyle(editor->pBuffer->pCharStyle); editor->pBuffer->pCharStyle = s; } else { @@ -753,7 +753,7 @@ void ME_SetCharFormat(ME_TextEditor *editor, ME_Cursor *start, ME_Cursor *end, C for (run = start_run; run != end_run; run = ME_FindItemFwd( run, diRun )) { - ME_Style *new_style = ME_ApplyStyle(run->member.run.style, pFmt); + ME_Style *new_style = ME_ApplyStyle(editor, run->member.run.style, pFmt); add_undo_set_char_fmt( editor, run->member.run.para->nCharOfs + run->member.run.nCharOfs, run->member.run.len, &run->member.run.style->fmt ); diff --git a/dlls/riched20/style.c b/dlls/riched20/style.c index 37f56d92eb6..06c0e6f65eb 100644 --- a/dlls/riched20/style.c +++ b/dlls/riched20/style.c @@ -150,21 +150,22 @@ ME_Style *ME_MakeStyle(CHARFORMAT2W *style) memset(&s->tm, 0, sizeof(s->tm)); s->tm.tmAscent = -1; s->script_cache = NULL; + list_init(&s->entry); all_refs++; TRACE_(richedit_style)("ME_MakeStyle %p, total refs=%d\n", s, all_refs); return s; } #define COPY_STYLE_ITEM(mask, member) \ - if (style->dwMask & mask) { \ - s->fmt.dwMask |= mask;\ - s->fmt.member = style->member;\ + if (mod->dwMask & mask) { \ + fmt.dwMask |= mask;\ + fmt.member = mod->member;\ } #define COPY_STYLE_ITEM_MEMCPY(mask, member) \ - if (style->dwMask & mask) { \ - s->fmt.dwMask |= mask;\ - CopyMemory(s->fmt.member, style->member, sizeof(style->member));\ + if (mod->dwMask & mask) { \ + fmt.dwMask |= mask;\ + CopyMemory(fmt.member, mod->member, sizeof(mod->member));\ } void ME_InitCharFormat2W(CHARFORMAT2W *pFmt) @@ -173,10 +174,12 @@ void ME_InitCharFormat2W(CHARFORMAT2W *pFmt) pFmt->cbSize = sizeof(CHARFORMAT2W); } -ME_Style *ME_ApplyStyle(ME_Style *sSrc, CHARFORMAT2W *style) +ME_Style *ME_ApplyStyle(ME_TextEditor *editor, ME_Style *sSrc, CHARFORMAT2W *mod) { - ME_Style *s = ME_MakeStyle(&sSrc->fmt); - assert(style->cbSize == sizeof(CHARFORMAT2W)); + CHARFORMAT2W fmt = sSrc->fmt; + ME_Style *s; + + assert(mod->cbSize == sizeof(CHARFORMAT2W)); COPY_STYLE_ITEM(CFM_ANIMATION, bAnimation); COPY_STYLE_ITEM(CFM_BACKCOLOR, crBackColor); COPY_STYLE_ITEM(CFM_CHARSET, bCharSet); @@ -186,9 +189,9 @@ ME_Style *ME_ApplyStyle(ME_Style *sSrc, CHARFORMAT2W *style) COPY_STYLE_ITEM(CFM_LCID, lcid); COPY_STYLE_ITEM(CFM_OFFSET, yOffset); COPY_STYLE_ITEM(CFM_REVAUTHOR, bRevAuthor); - if (style->dwMask & CFM_SIZE) { - s->fmt.dwMask |= CFM_SIZE; - s->fmt.yHeight = min(style->yHeight, yHeightCharPtsMost * 20); + if (mod->dwMask & CFM_SIZE) { + fmt.dwMask |= CFM_SIZE; + fmt.yHeight = min(mod->yHeight, yHeightCharPtsMost * 20); } COPY_STYLE_ITEM(CFM_SPACING, sSpacing); COPY_STYLE_ITEM(CFM_STYLE, sStyle); @@ -197,31 +200,46 @@ ME_Style *ME_ApplyStyle(ME_Style *sSrc, CHARFORMAT2W *style) /* FIXME: this is not documented this way, but that's the more logical */ COPY_STYLE_ITEM(CFM_FACE, bPitchAndFamily); - s->fmt.dwEffects &= ~(style->dwMask); - s->fmt.dwEffects |= style->dwEffects & style->dwMask; - s->fmt.dwMask |= style->dwMask; - if (style->dwMask & CFM_COLOR) + fmt.dwEffects &= ~(mod->dwMask); + fmt.dwEffects |= mod->dwEffects & mod->dwMask; + fmt.dwMask |= mod->dwMask; + if (mod->dwMask & CFM_COLOR) { - if (style->dwEffects & CFE_AUTOCOLOR) - s->fmt.dwEffects |= CFE_AUTOCOLOR; + if (mod->dwEffects & CFE_AUTOCOLOR) + fmt.dwEffects |= CFE_AUTOCOLOR; else - s->fmt.dwEffects &= ~CFE_AUTOCOLOR; + fmt.dwEffects &= ~CFE_AUTOCOLOR; } - if (style->dwMask & CFM_UNDERLINE) + if (mod->dwMask & CFM_UNDERLINE) { - s->fmt.dwMask |= CFM_UNDERLINETYPE; - s->fmt.bUnderlineType = (style->dwEffects & CFM_UNDERLINE) ? + fmt.dwMask |= CFM_UNDERLINETYPE; + fmt.bUnderlineType = (mod->dwEffects & CFM_UNDERLINE) ? CFU_CF1UNDERLINE : CFU_UNDERLINENONE; } - if (style->dwMask & CFM_BOLD && !(style->dwMask & CFM_WEIGHT)) + if (mod->dwMask & CFM_BOLD && !(mod->dwMask & CFM_WEIGHT)) { - s->fmt.wWeight = (style->dwEffects & CFE_BOLD) ? FW_BOLD : FW_NORMAL; - } else if (style->dwMask & CFM_WEIGHT && !(style->dwMask & CFM_BOLD)) { - if (style->wWeight > FW_NORMAL) - s->fmt.dwEffects |= CFE_BOLD; + fmt.wWeight = (mod->dwEffects & CFE_BOLD) ? FW_BOLD : FW_NORMAL; + } else if (mod->dwMask & CFM_WEIGHT && !(mod->dwMask & CFM_BOLD)) { + if (mod->wWeight > FW_NORMAL) + fmt.dwEffects |= CFE_BOLD; else - s->fmt.dwEffects &= ~CFE_BOLD; + fmt.dwEffects &= ~CFE_BOLD; } + + LIST_FOR_EACH_ENTRY(s, &editor->style_list, ME_Style, entry) + { + if (!memcmp( &s->fmt, &fmt, sizeof(fmt) )) + { + TRACE_(richedit_style)("found existing style %p\n", s); + ME_AddRefStyle( s ); + return s; + } + } + + s = ME_MakeStyle( &fmt ); + if (s) + list_add_head( &editor->style_list, &s->entry ); + TRACE_(richedit_style)("created new style %p\n", s); return s; } @@ -423,8 +441,9 @@ void ME_UnselectStyleFont(ME_Context *c, ME_Style *s, HFONT hOldFont) s->font_cache = NULL; } -static void ME_DestroyStyle(ME_Style *s) +void ME_DestroyStyle(ME_Style *s) { + list_remove( &s->entry ); if (s->font_cache) { release_font_cache( s->font_cache ); @@ -524,7 +543,7 @@ void ME_SetDefaultCharFormat(ME_TextEditor *editor, CHARFORMAT2W *mod) ME_Style *style, *def = editor->pBuffer->pDefaultStyle; assert(mod->cbSize == sizeof(CHARFORMAT2W)); - style = ME_ApplyStyle(def, mod); + style = ME_ApplyStyle(editor, def, mod); def->fmt = style->fmt; def->tm = style->tm; if (def->font_cache)