[RICHED20] Sync with Wine Staging 1.7.55. CORE-10536
authorAmine Khaldi <amine.khaldi@reactos.org>
Mon, 23 Nov 2015 09:36:58 +0000 (09:36 +0000)
committerAmine Khaldi <amine.khaldi@reactos.org>
Mon, 23 Nov 2015 09:36:58 +0000 (09:36 +0000)
svn path=/trunk/; revision=70055

15 files changed:
reactos/dll/win32/riched20/caret.c
reactos/dll/win32/riched20/editor.c
reactos/dll/win32/riched20/editor.h
reactos/dll/win32/riched20/editstr.h
reactos/dll/win32/riched20/list.c
reactos/dll/win32/riched20/para.c
reactos/dll/win32/riched20/reader.c
reactos/dll/win32/riched20/rtf.h
reactos/dll/win32/riched20/run.c
reactos/dll/win32/riched20/style.c
reactos/dll/win32/riched20/txthost.c
reactos/dll/win32/riched20/txtsrv.c
reactos/dll/win32/riched20/undo.c
reactos/dll/win32/riched20/writer.c
reactos/media/doc/README.WINE

index e3e42cc..ca50f18 100644 (file)
@@ -446,7 +446,7 @@ BOOL ME_InternalDeleteText(ME_TextEditor *editor, ME_Cursor *start,
       continue;
     }
   }
-  if (delete_all) ME_SetDefaultParaFormat( start_para->member.para.pFmt );
+  if (delete_all) ME_SetDefaultParaFormat( editor, start_para->member.para.pFmt );
   return TRUE;
 }
 
index 8d995f7..6af6924 100644 (file)
@@ -96,7 +96,7 @@
   + EM_SETCHARFORMAT (partly done, no ANSI)
   - EM_SETEDITSTYLE
   + EM_SETEVENTMASK (few notifications supported)
-  - EM_SETFONTSIZE
+  + EM_SETFONTSIZE
   - EM_SETIMECOLOR 1.0asian
   - EM_SETIMEOPTIONS 1.0asian
   - EM_SETIMESTATUS
   
   - ES_AUTOHSCROLL
   - ES_AUTOVSCROLL
-  - ES_CENTER
+  + ES_CENTER
   + ES_DISABLENOSCROLL (scrollbar is always visible)
   - ES_EX_NOCALLOLEINIT
-  - ES_LEFT
+  + ES_LEFT
   - ES_MULTILINE (currently single line controls aren't supported)
   - ES_NOIME
   - ES_READONLY (I'm not sure if beeping is the proper behaviour)
-  - ES_RIGHT
+  + ES_RIGHT
   - ES_SAVESEL
   - ES_SELFIME
   - ES_SUNKEN
@@ -530,7 +530,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;
@@ -1233,136 +1233,191 @@ static BOOL ME_RTFInsertOleObject(RTF_Info *info, HENHMETAFILE hemf, HBITMAP hbm
   return ret;
 }
 
-static void ME_RTFReadPictGroup(RTF_Info *info)
+static void ME_RTFReadShpPictGroup( RTF_Info *info )
 {
-  SIZEL         sz;
-  BYTE*         buffer = NULL;
-  unsigned      bufsz, bufidx;
-  BOOL          flip;
-  BYTE          val;
-  METAFILEPICT  mfp;
-  HENHMETAFILE  hemf;
-  HBITMAP       hbmp;
-  enum gfxkind {gfx_unknown = 0, gfx_enhmetafile, gfx_metafile, gfx_dib} gfx = gfx_unknown;
-
-  RTFGetToken (info);
-  if (info->rtfClass == rtfEOF)
-    return;
-  mfp.mm = MM_TEXT;
-  /* fetch picture type */
-  if (RTFCheckMM (info, rtfPictAttr, rtfWinMetafile))
-  {
-    mfp.mm = info->rtfParam;
-    gfx = gfx_metafile;
-  }
-  else if (RTFCheckMM (info, rtfPictAttr, rtfDevIndBitmap))
-  {
-    if (info->rtfParam != 0) FIXME("dibitmap should be 0 (%d)\n", info->rtfParam);
-    gfx = gfx_dib;
-  }
-  else if (RTFCheckMM (info, rtfPictAttr, rtfEmfBlip))
-  {
-    gfx = gfx_enhmetafile;
-  }
-  else
-  {
-    FIXME("%d %d\n", info->rtfMajor, info->rtfMinor);
-    goto skip_group;
-  }
-  sz.cx = sz.cy = 0;
-  /* fetch picture attributes */
-  for (;;)
-  {
-    RTFGetToken (info);
-    if (info->rtfClass == rtfEOF)
-      return;
-    if (info->rtfClass == rtfText)
-      break;
-    if (!RTFCheckCM (info, rtfControl, rtfPictAttr))
-    {
-      ERR("Expected picture attribute (%d %d)\n",
-        info->rtfClass, info->rtfMajor);
-      goto skip_group;
-    }
-    else if (RTFCheckMM (info, rtfPictAttr, rtfPicWid))
+    int level = 1;
+
+    for (;;)
     {
-      if (gfx == gfx_metafile) mfp.xExt = info->rtfParam;
+        RTFGetToken (info);
+
+        if (info->rtfClass == rtfEOF) return;
+        if (RTFCheckCM( info, rtfGroup, rtfEndGroup ))
+        {
+            if (--level == 0) break;
+        }
+        else if (RTFCheckCM( info, rtfGroup, rtfBeginGroup ))
+        {
+            level++;
+        }
+        else
+        {
+            RTFRouteToken( info );
+            if (RTFCheckCM( info, rtfGroup, rtfEndGroup ))
+                level--;
+        }
     }
-    else if (RTFCheckMM (info, rtfPictAttr, rtfPicHt))
+
+    RTFRouteToken( info ); /* feed "}" back to router */
+    return;
+}
+
+static DWORD read_hex_data( RTF_Info *info, BYTE **out )
+{
+    DWORD read = 0, size = 1024;
+    BYTE *buf, val;
+    BOOL flip;
+
+    *out = NULL;
+
+    if (info->rtfClass != rtfText)
     {
-      if (gfx == gfx_metafile) mfp.yExt = info->rtfParam;
+        ERR("Called with incorrect token\n");
+        return 0;
     }
-    else if (RTFCheckMM (info, rtfPictAttr, rtfPicGoalWid))
-      sz.cx = info->rtfParam;
-    else if (RTFCheckMM (info, rtfPictAttr, rtfPicGoalHt))
-      sz.cy = info->rtfParam;
-    else
-      FIXME("Non supported attribute: %d %d %d\n", info->rtfClass, info->rtfMajor, info->rtfMinor);
-  }
-  /* fetch picture data */
-  bufsz = 1024;
-  bufidx = 0;
-  buffer = HeapAlloc(GetProcessHeap(), 0, bufsz);
-  val = info->rtfMajor;
-  for (flip = TRUE;; flip = !flip)
-  {
-    RTFGetToken (info);
-    if (info->rtfClass == rtfEOF)
+
+    buf = HeapAlloc( GetProcessHeap(), 0, size );
+    if (!buf) return 0;
+
+    val = info->rtfMajor;
+    for (flip = TRUE;; flip = !flip)
     {
-      HeapFree(GetProcessHeap(), 0, buffer);
-      return; /* Warn ?? */
+        RTFGetToken( info );
+        if (info->rtfClass == rtfEOF)
+        {
+            HeapFree( GetProcessHeap(), 0, buf );
+            return 0;
+        }
+        if (info->rtfClass != rtfText) break;
+        if (flip)
+        {
+            if (read >= size)
+            {
+                size *= 2;
+                buf = HeapReAlloc( GetProcessHeap(), 0, buf, size );
+                if (!buf) return 0;
+            }
+            buf[read++] = RTFCharToHex(val) * 16 + RTFCharToHex(info->rtfMajor);
+        }
+        else
+            val = info->rtfMajor;
     }
-    if (RTFCheckCM(info, rtfGroup, rtfEndGroup))
-      break;
-    if (info->rtfClass != rtfText) goto skip_group;
-    if (flip)
+    if (flip) FIXME("wrong hex string\n");
+
+    *out = buf;
+    return read;
+}
+
+static void ME_RTFReadPictGroup(RTF_Info *info)
+{
+    SIZEL sz;
+    BYTE *buffer = NULL;
+    DWORD size = 0;
+    METAFILEPICT mfp;
+    HENHMETAFILE hemf;
+    HBITMAP hbmp;
+    enum gfxkind {gfx_unknown = 0, gfx_enhmetafile, gfx_metafile, gfx_dib} gfx = gfx_unknown;
+    int level = 1;
+
+    mfp.mm = MM_TEXT;
+    sz.cx = sz.cy = 0;
+
+    for (;;)
     {
-      if (bufidx >= bufsz &&
-          !(buffer = HeapReAlloc(GetProcessHeap(), 0, buffer, bufsz += 1024)))
-        goto skip_group;
-      buffer[bufidx++] = RTFCharToHex(val) * 16 + RTFCharToHex(info->rtfMajor);
+        RTFGetToken( info );
+
+        if (info->rtfClass == rtfText)
+        {
+            if (level == 1)
+            {
+                if (!buffer)
+                    size = read_hex_data( info, &buffer );
+            }
+            else
+            {
+                RTFSkipGroup( info );
+            }
+        } /* We potentially have a new token so fall through. */
+
+        if (info->rtfClass == rtfEOF) return;
+
+        if (RTFCheckCM( info, rtfGroup, rtfEndGroup ))
+        {
+            if (--level == 0) break;
+            continue;
+        }
+        if (RTFCheckCM( info, rtfGroup, rtfBeginGroup ))
+        {
+            level++;
+            continue;
+        }
+        if (!RTFCheckCM( info, rtfControl, rtfPictAttr ))
+        {
+            RTFRouteToken( info );
+            if (RTFCheckCM( info, rtfGroup, rtfEndGroup ))
+                level--;
+            continue;
+        }
+
+        if (RTFCheckMM( info, rtfPictAttr, rtfWinMetafile ))
+        {
+            mfp.mm = info->rtfParam;
+            gfx = gfx_metafile;
+        }
+        else if (RTFCheckMM( info, rtfPictAttr, rtfDevIndBitmap ))
+        {
+            if (info->rtfParam != 0) FIXME("dibitmap should be 0 (%d)\n", info->rtfParam);
+            gfx = gfx_dib;
+        }
+        else if (RTFCheckMM( info, rtfPictAttr, rtfEmfBlip ))
+            gfx = gfx_enhmetafile;
+        else if (RTFCheckMM( info, rtfPictAttr, rtfPicWid ))
+            mfp.xExt = info->rtfParam;
+        else if (RTFCheckMM( info, rtfPictAttr, rtfPicHt ))
+            mfp.yExt = info->rtfParam;
+        else if (RTFCheckMM( info, rtfPictAttr, rtfPicGoalWid ))
+            sz.cx = info->rtfParam;
+        else if (RTFCheckMM( info, rtfPictAttr, rtfPicGoalHt ))
+            sz.cy = info->rtfParam;
+        else
+            FIXME("Non supported attribute: %d %d %d\n", info->rtfClass, info->rtfMajor, info->rtfMinor);
     }
-    else
-      val = info->rtfMajor;
-  }
-  if (flip) FIXME("wrong hex string\n");
 
-  switch (gfx)
-  {
-  case gfx_enhmetafile:
-    if ((hemf = SetEnhMetaFileBits(bufidx, buffer)))
-      ME_RTFInsertOleObject(info, hemf, NULL, &sz);
-    break;
-  case gfx_metafile:
-    if ((hemf = SetWinMetaFileBits(bufidx, buffer, NULL, &mfp)))
-        ME_RTFInsertOleObject(info, hemf, NULL, &sz);
-    break;
-  case gfx_dib:
+    if (buffer)
     {
-      BITMAPINFO* bi = (BITMAPINFO*)buffer;
-      HDC         hdc = GetDC(0);
-      unsigned    nc = bi->bmiHeader.biClrUsed;
-
-      /* not quite right, especially for bitfields type of compression */
-      if (!nc && bi->bmiHeader.biBitCount <= 8)
-        nc = 1 << bi->bmiHeader.biBitCount;
-      if ((hbmp = CreateDIBitmap(hdc, &bi->bmiHeader,
-                                 CBM_INIT, (char*)(bi + 1) + nc * sizeof(RGBQUAD),
-                                 bi, DIB_RGB_COLORS)))
-          ME_RTFInsertOleObject(info, NULL, hbmp, &sz);
-      ReleaseDC(0, hdc);
+        switch (gfx)
+        {
+        case gfx_enhmetafile:
+            if ((hemf = SetEnhMetaFileBits( size, buffer )))
+                ME_RTFInsertOleObject( info, hemf, NULL, &sz );
+            break;
+        case gfx_metafile:
+            if ((hemf = SetWinMetaFileBits( size, buffer, NULL, &mfp )))
+                ME_RTFInsertOleObject( info, hemf, NULL, &sz );
+            break;
+        case gfx_dib:
+        {
+            BITMAPINFO *bi = (BITMAPINFO*)buffer;
+            HDC hdc = GetDC(0);
+            unsigned nc = bi->bmiHeader.biClrUsed;
+
+            /* not quite right, especially for bitfields type of compression */
+            if (!nc && bi->bmiHeader.biBitCount <= 8)
+                nc = 1 << bi->bmiHeader.biBitCount;
+            if ((hbmp = CreateDIBitmap( hdc, &bi->bmiHeader,
+                                        CBM_INIT, (char*)(bi + 1) + nc * sizeof(RGBQUAD),
+                                        bi, DIB_RGB_COLORS)) )
+                ME_RTFInsertOleObject( info, NULL, hbmp, &sz );
+            ReleaseDC( 0, hdc );
+            break;
+        }
+        default:
+            break;
+        }
     }
-    break;
-  default:
-    break;
-  }
-  HeapFree(GetProcessHeap(), 0, buffer);
-  RTFRouteToken (info);        /* feed "}" back to router */
-  return;
-skip_group:
-  HeapFree(GetProcessHeap(), 0, buffer);
-  RTFSkipGroup(info);
-  RTFRouteToken(info); /* feed "}" back to router */
+    HeapFree( GetProcessHeap(), 0, buffer );
+    RTFRouteToken( info ); /* feed "}" back to router */
+    return;
 }
 
 /* for now, lookup the \result part and use it, whatever the object */
@@ -1506,7 +1561,7 @@ static LRESULT ME_StreamIn(ME_TextEditor *editor, DWORD format, EDITSTREAM *stre
                           ME_GetTextLength(editor), FALSE);
     from = to = 0;
     ME_ClearTempStyle(editor);
-    ME_SetDefaultParaFormat(editor->pCursors[0].pPara->member.para.pFmt);
+    ME_SetDefaultParaFormat(editor, editor->pCursors[0].pPara->member.para.pFmt);
   }
 
 
@@ -1551,6 +1606,7 @@ static LRESULT ME_StreamIn(ME_TextEditor *editor, DWORD format, EDITSTREAM *stre
       WriterInit(&parser);
       RTFInit(&parser);
       RTFSetReadHook(&parser, ME_RTFReadHook);
+      RTFSetDestinationCallback(&parser, rtfShpPict, ME_RTFReadShpPictGroup);
       RTFSetDestinationCallback(&parser, rtfPict, ME_RTFReadPictGroup);
       RTFSetDestinationCallback(&parser, rtfObject, ME_RTFReadObjectGroup);
       if (!parser.editor->bEmulateVersion10) /* v4.1 */
@@ -2306,7 +2362,7 @@ ME_KeyDown(ME_TextEditor *editor, WORD nKey)
               ME_InsertTextFromCursor(editor, 0, &endl, 1,
                                       editor->pCursors[0].pRun->member.run.style);
               para = editor->pBuffer->pFirst->member.para.next_para;
-              ME_SetDefaultParaFormat(para->member.para.pFmt);
+              ME_SetDefaultParaFormat(editor, para->member.para.pFmt);
               para->member.para.nFlags = MEPF_REWRAP;
               editor->pCursors[0].pPara = para;
               editor->pCursors[0].pRun = ME_FindItemFwd(para, diRun);
@@ -2732,7 +2788,7 @@ static BOOL ME_ShowContextMenu(ME_TextEditor *editor, int x, int y)
   return TRUE;
 }
 
-ME_TextEditor *ME_MakeEditor(ITextHost *texthost, BOOL bEmulateVersion10)
+ME_TextEditor *ME_MakeEditor(ITextHost *texthost, BOOL bEmulateVersion10, DWORD csStyle)
 {
   ME_TextEditor *ed = ALLOC_OBJ(ME_TextEditor);
   int i;
@@ -2746,6 +2802,11 @@ ME_TextEditor *ME_MakeEditor(ITextHost *texthost, BOOL bEmulateVersion10)
   ed->reOle = NULL;
   ed->bEmulateVersion10 = bEmulateVersion10;
   ed->styleFlags = 0;
+  ed->alignStyle = PFA_LEFT;
+  if (csStyle & ES_RIGHT)
+      ed->alignStyle = PFA_RIGHT;
+  if (csStyle & ES_CENTER)
+      ed->alignStyle = PFA_CENTER;
   ITextHost_TxGetPropertyBits(texthost,
                               (TXTBIT_RICHTEXT|TXTBIT_MULTILINE|
                                TXTBIT_READONLY|TXTBIT_USEPASSWORD|
@@ -2857,6 +2918,7 @@ ME_TextEditor *ME_MakeEditor(ITextHost *texthost, BOOL bEmulateVersion10)
 
   ed->wheel_remain = 0;
 
+  list_init( &ed->style_list );
   OleInitialize(NULL);
 
   return ed;
@@ -2866,6 +2928,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);
@@ -2875,6 +2938,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; i<HFONT_CACHE_SIZE; i++)
   {
@@ -3262,7 +3329,6 @@ LRESULT ME_HandleMessage(ME_TextEditor *editor, UINT msg, WPARAM wParam,
   UNSUPPORTED_MSG(EM_SELECTIONTYPE)
   UNSUPPORTED_MSG(EM_SETBIDIOPTIONS)
   UNSUPPORTED_MSG(EM_SETEDITSTYLE)
-  UNSUPPORTED_MSG(EM_SETFONTSIZE)
   UNSUPPORTED_MSG(EM_SETLANGOPTIONS)
   UNSUPPORTED_MSG(EM_SETMARGINS)
   UNSUPPORTED_MSG(EM_SETPALETTE)
@@ -3338,6 +3404,48 @@ LRESULT ME_HandleMessage(ME_TextEditor *editor, UINT msg, WPARAM wParam,
 
     return settings;
   }
+  case EM_SETFONTSIZE:
+  {
+      CHARFORMAT2W cf;
+      LONG tmp_size, size;
+      BOOL is_increase = ((LONG)wParam > 0);
+
+      if (editor->mode & TM_PLAINTEXT)
+          return FALSE;
+
+      cf.cbSize = sizeof(cf);
+      cf.dwMask = CFM_SIZE;
+      ME_GetSelectionCharFormat(editor, &cf);
+      tmp_size = (cf.yHeight / 20) + wParam;
+
+      if (tmp_size <= 1)
+          size = 1;
+      else if (tmp_size > 12 && tmp_size < 28 && tmp_size % 2)
+          size = tmp_size + (is_increase ? 1 : -1);
+      else if (tmp_size > 28 && tmp_size < 36)
+          size = is_increase ? 36 : 28;
+      else if (tmp_size > 36 && tmp_size < 48)
+          size = is_increase ? 48 : 36;
+      else if (tmp_size > 48 && tmp_size < 72)
+          size = is_increase ? 72 : 48;
+      else if (tmp_size > 72 && tmp_size < 80)
+          size = is_increase ? 80 : 72;
+      else if (tmp_size > 80 && tmp_size < 1638)
+          size = 10 * (is_increase ? (tmp_size / 10 + 1) : (tmp_size / 10));
+      else if (tmp_size >= 1638)
+          size = 1638;
+      else
+          size = tmp_size;
+
+      cf.yHeight = size * 20; /*  convert twips to points */
+      ME_SetSelectionCharFormat(editor, &cf);
+      ME_CommitUndo(editor);
+      ME_WrapMarkedParagraphs(editor);
+      ME_UpdateScrollBar(editor);
+      ME_Repaint(editor);
+
+      return TRUE;
+  }
   case EM_SETOPTIONS:
   {
     /* these flags are equivalent to ES_* counterparts, except for
@@ -3723,7 +3831,10 @@ LRESULT ME_HandleMessage(ME_TextEditor *editor, UINT msg, WPARAM wParam,
 
     if (!wParam)
       wParam = (WPARAM)GetStockObject(SYSTEM_FONT);
-    GetObjectW((HGDIOBJ)wParam, sizeof(LOGFONTW), &lf);
+
+    if (!GetObjectW((HGDIOBJ)wParam, sizeof(LOGFONTW), &lf))
+      return 0;
+
     hDC = ITextHost_TxGetDC(editor->texthost);
     ME_CharFormatFromLogFont(hDC, &lf, &fmt);
     ITextHost_TxReleaseDC(editor->texthost, hDC);
index 4054c99..9ef6165 100644 (file)
@@ -104,9 +104,10 @@ static inline const char *debugstr_run( const ME_Run *run )
 /* style.c */
 ME_Style *ME_MakeStyle(CHARFORMAT2W *style) DECLSPEC_HIDDEN;
 void ME_AddRefStyle(ME_Style *item) DECLSPEC_HIDDEN;
+void ME_DestroyStyle(ME_Style *item) DECLSPEC_HIDDEN;
 void ME_ReleaseStyle(ME_Style *item) DECLSPEC_HIDDEN;
 ME_Style *ME_GetInsertStyle(ME_TextEditor *editor, int nCursor) DECLSPEC_HIDDEN;
-ME_Style *ME_ApplyStyle(ME_Style *sSrc, CHARFORMAT2W *style) DECLSPEC_HIDDEN;
+ME_Style *ME_ApplyStyle(ME_TextEditor *ed, ME_Style *sSrc, CHARFORMAT2W *style) DECLSPEC_HIDDEN;
 HFONT ME_SelectStyleFont(ME_Context *c, ME_Style *s) DECLSPEC_HIDDEN;
 void ME_UnselectStyleFont(ME_Context *c, ME_Style *s, HFONT hOldFont) DECLSPEC_HIDDEN;
 void ME_InitCharFormat2W(CHARFORMAT2W *pFmt) DECLSPEC_HIDDEN;
@@ -248,7 +249,7 @@ void ME_DumpParaStyleToBuf(const PARAFORMAT2 *pFmt, char buf[2048]) DECLSPEC_HID
 BOOL ME_SetSelectionParaFormat(ME_TextEditor *editor, const PARAFORMAT2 *pFmt) DECLSPEC_HIDDEN;
 void ME_GetSelectionParaFormat(ME_TextEditor *editor, PARAFORMAT2 *pFmt) DECLSPEC_HIDDEN;
 void ME_MarkAllForWrapping(ME_TextEditor *editor) DECLSPEC_HIDDEN;
-void ME_SetDefaultParaFormat(PARAFORMAT2 *pFmt) DECLSPEC_HIDDEN;
+void ME_SetDefaultParaFormat(ME_TextEditor *editor, PARAFORMAT2 *pFmt) DECLSPEC_HIDDEN;
 
 /* paint.c */
 void ME_PaintContent(ME_TextEditor *editor, HDC hDC, const RECT *rcUpdate) DECLSPEC_HIDDEN;
@@ -284,7 +285,7 @@ void ME_DeleteReObject(REOBJECT* reo) DECLSPEC_HIDDEN;
 void ME_GetITextDocumentInterface(IRichEditOle *iface, LPVOID *ppvObj) DECLSPEC_HIDDEN;
 
 /* editor.c */
-ME_TextEditor *ME_MakeEditor(ITextHost *texthost, BOOL bEmulateVersion10) DECLSPEC_HIDDEN;
+ME_TextEditor *ME_MakeEditor(ITextHost *texthost, BOOL bEmulateVersion10, DWORD csStyle) DECLSPEC_HIDDEN;
 void ME_DestroyEditor(ME_TextEditor *editor) DECLSPEC_HIDDEN;
 LRESULT ME_HandleMessage(ME_TextEditor *editor, UINT msg, WPARAM wParam,
                          LPARAM lParam, BOOL unicode, HRESULT* phresult) DECLSPEC_HIDDEN;
index cecd552..cf09010 100644 (file)
@@ -31,14 +31,25 @@ typedef struct tagME_String
   int nLen, nBuffer;
 } ME_String;
 
+typedef struct tagME_FontCacheItem
+{
+  LOGFONTW lfSpecs;
+  HFONT hFont;
+  int nRefs;
+  int nAge;
+} ME_FontCacheItem;
+
+#define HFONT_CACHE_SIZE 10
+
 typedef struct tagME_Style
 {
   CHARFORMAT2W fmt;
 
-  HFONT hFont; /* cached font for the style */
+  ME_FontCacheItem *font_cache; /* cached font for the style */
   TEXTMETRICW tm; /* cached font metrics for the style */
   int nRefs; /* reference count */
   SCRIPT_CACHE script_cache;
+  struct list entry;
 } ME_Style;
 
 typedef enum {
@@ -343,16 +354,6 @@ typedef struct tagME_OutStream {
   UINT nNestingLevel;
 } ME_OutStream;
 
-typedef struct tagME_FontCacheItem
-{
-  LOGFONTW lfSpecs;
-  HFONT hFont;
-  int nRefs;
-  int nAge;
-} ME_FontCacheItem;
-
-#define HFONT_CACHE_SIZE 10
-
 typedef struct tagME_TextEditor
 {
   HWND hWnd, hwndParent;
@@ -362,6 +363,7 @@ typedef struct tagME_TextEditor
   ME_TextBuffer *pBuffer;
   ME_Cursor *pCursors;
   DWORD styleFlags;
+  DWORD alignStyle;
   DWORD exStyleFlags;
   int nCursors;
   SIZE sizeWindow;
@@ -414,6 +416,7 @@ typedef struct tagME_TextEditor
 
   BOOL bMouseCaptured;
   int wheel_remain;
+  struct list style_list;
 } ME_TextEditor;
 
 typedef struct tagME_Context
index 10732e5..c57e526 100644 (file)
@@ -179,13 +179,6 @@ ME_DisplayItem *ME_MakeDI(ME_DIType type)
   ZeroMemory(item, sizeof(ME_DisplayItem));
   item->type = type;
   item->prev = item->next = NULL;
-  if (type == diParagraph)
-  {
-    item->member.para.pFmt = ALLOC_OBJ(PARAFORMAT2);
-    ME_SetDefaultParaFormat(item->member.para.pFmt);
-    item->member.para.nFlags = MEPF_REWRAP;
-  }
-    
   return item;
 }
 
index 8cf3d24..3ea98c5 100644 (file)
 
 WINE_DEFAULT_DEBUG_CHANNEL(richedit);
 
+static ME_DisplayItem *make_para(ME_TextEditor *editor)
+{
+    ME_DisplayItem *item = ME_MakeDI(diParagraph);
+
+    item->member.para.pFmt = ALLOC_OBJ(PARAFORMAT2);
+    ME_SetDefaultParaFormat(editor, item->member.para.pFmt);
+    item->member.para.nFlags = MEPF_REWRAP;
+    return item;
+}
+
 void ME_MakeFirstParagraph(ME_TextEditor *editor)
 {
   ME_Context c;
@@ -30,7 +40,7 @@ void ME_MakeFirstParagraph(ME_TextEditor *editor)
   LOGFONTW lf;
   HFONT hf;
   ME_TextBuffer *text = editor->pBuffer;
-  ME_DisplayItem *para = ME_MakeDI(diParagraph);
+  ME_DisplayItem *para = make_para(editor);
   ME_DisplayItem *run;
   ME_Style *style;
   int eol_len;
@@ -196,7 +206,7 @@ ME_DisplayItem *ME_SplitParagraph(ME_TextEditor *editor, ME_DisplayItem *run,
 {
   ME_DisplayItem *next_para = NULL;
   ME_DisplayItem *run_para = NULL;
-  ME_DisplayItem *new_para = ME_MakeDI(diParagraph);
+  ME_DisplayItem *new_para = make_para(editor);
   ME_DisplayItem *end_run;
   int ofs, i;
   ME_DisplayItem *pp;
@@ -619,12 +629,12 @@ void ME_GetSelectionParaFormat(ME_TextEditor *editor, PARAFORMAT2 *pFmt)
   }
 }
 
-void ME_SetDefaultParaFormat(PARAFORMAT2 *pFmt)
+void ME_SetDefaultParaFormat(ME_TextEditor *editor, PARAFORMAT2 *pFmt)
 {
     ZeroMemory(pFmt, sizeof(PARAFORMAT2));
     pFmt->cbSize = sizeof(PARAFORMAT2);
     pFmt->dwMask = PFM_ALL2;
-    pFmt->wAlignment = PFA_LEFT;
+    pFmt->wAlignment = editor->alignStyle;
     pFmt->sStyle = -1;
     pFmt->bOutlineLevel = TRUE;
 }
index 5e35d73..d723e6f 100644 (file)
@@ -1797,6 +1797,8 @@ static RTFKey     rtfKey[] =
        { rtfDestination,       rtfNeXTGraphic,         "NeXTGraphic",  0 },
        { rtfDestination,       rtfNestTableProps,      "nesttableprops", 0 },
        { rtfDestination,       rtfNoNestTables,        "nonesttables", 0 },
+        { rtfDestination,       rtfShpPict,             "shppict",      0 },
+        { rtfDestination,       rtfNonShpPict,          "nonshppict",   0 },
 
        /*
         * Font families
index 4b10744..b690ffa 100644 (file)
 # define               rtfGenerator            74
 # define               rtfNestTableProps       75
 # define               rtfNoNestTables         76
-# define               rtfMaxDestination       77      /* highest dest + 1 */
+# define                rtfShpPict              77
+# define                rtfNonShpPict           78
+# define                rtfMaxDestination       79      /* highest dest + 1 */
 
 # define       rtfFontFamily   4
 # define               rtfFFNil                0
index 4a93bbc..f3b4db6 100644 (file)
@@ -700,7 +700,7 @@ void ME_SetSelectionCharFormat(ME_TextEditor *editor, CHARFORMAT2W *pFmt)
     ME_Style *s;
     if (!editor->pBuffer->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 {
@@ -758,7 +758,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 );
@@ -768,25 +768,6 @@ void ME_SetCharFormat(ME_TextEditor *editor, ME_Cursor *start, ME_Cursor *end, C
   }
 }
 
-/******************************************************************************
- * ME_SetDefaultCharFormat
- * 
- * Applies a style change to the default character style.
- */     
-void ME_SetDefaultCharFormat(ME_TextEditor *editor, CHARFORMAT2W *mod)
-{
-  ME_Style *style;
-
-  assert(mod->cbSize == sizeof(CHARFORMAT2W));
-  style = ME_ApplyStyle(editor->pBuffer->pDefaultStyle, mod);
-  editor->pBuffer->pDefaultStyle->fmt = style->fmt;
-  editor->pBuffer->pDefaultStyle->tm = style->tm;
-  ScriptFreeCache( &editor->pBuffer->pDefaultStyle->script_cache );
-  ME_ReleaseStyle(style);
-  ME_MarkAllForWrapping(editor);
-  /*  pcf = editor->pBuffer->pDefaultStyle->fmt; */
-}
-
 static void ME_GetRunCharFormat(ME_TextEditor *editor, ME_DisplayItem *run, CHARFORMAT2W *pFmt)
 {
   ME_CopyCharFormat(pFmt, &run->member.run.style->fmt);
index 0817ea8..06c0e6f 100644 (file)
@@ -146,25 +146,26 @@ ME_Style *ME_MakeStyle(CHARFORMAT2W *style)
   assert(style->cbSize == sizeof(CHARFORMAT2W));
   s->fmt = *style;
   s->nRefs = 1;
-  s->hFont = NULL;
+  s->font_cache = NULL;
   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;
 }
 
@@ -383,8 +401,6 @@ HFONT ME_SelectStyleFont(ME_Context *c, ME_Style *s)
   {
     item = &c->editor->pFontCache[i];
     TRACE_(richedit_style)("font reused %d\n", i);
-
-    s->hFont = item->hFont;
     item->nRefs++;
   }
   else
@@ -397,44 +413,41 @@ HFONT ME_SelectStyleFont(ME_Context *c, ME_Style *s)
       DeleteObject(item->hFont);
       item->hFont = NULL;
     }
-    s->hFont = CreateFontIndirectW(&lf);
-    assert(s->hFont);
+    item->hFont = CreateFontIndirectW(&lf);
     TRACE_(richedit_style)("font created %d\n", nEmpty);
-    item->hFont = s->hFont;
     item->nRefs = 1;
     item->lfSpecs = lf;
   }
-  hOldFont = SelectObject(c->hDC, s->hFont);
+  s->font_cache = item;
+  hOldFont = SelectObject(c->hDC, item->hFont);
   /* should be cached too, maybe ? */
   GetTextMetricsW(c->hDC, &s->tm);
   return hOldFont;
 }
 
-void ME_UnselectStyleFont(ME_Context *c, ME_Style *s, HFONT hOldFont)
+static void release_font_cache(ME_FontCacheItem *item)
 {
-  int i;
-  
-  assert(s);
-  SelectObject(c->hDC, hOldFont);
-  for (i=0; i<HFONT_CACHE_SIZE; i++)
-  {
-    ME_FontCacheItem *pItem = &c->editor->pFontCache[i];
-    if (pItem->hFont == s->hFont && pItem->nRefs > 0)
+    if (item->nRefs > 0)
     {
-      pItem->nRefs--;
-      pItem->nAge = 0;
-      s->hFont = NULL;
-      return;
+        item->nRefs--;
+        item->nAge = 0;
     }
-  }
-  assert(0 == "UnselectStyleFont without SelectStyleFont");
 }
 
-static void ME_DestroyStyle(ME_Style *s) {
-  if (s->hFont)
+void ME_UnselectStyleFont(ME_Context *c, ME_Style *s, HFONT hOldFont)
+{
+  SelectObject(c->hDC, hOldFont);
+  release_font_cache(s->font_cache);
+  s->font_cache = NULL;
+}
+
+void ME_DestroyStyle(ME_Style *s)
+{
+  list_remove( &s->entry );
+  if (s->font_cache)
   {
-    DeleteObject(s->hFont);
-    s->hFont = NULL;
+    release_font_cache( s->font_cache );
+    s->font_cache = NULL;
   }
   ScriptFreeCache( &s->script_cache );
   FREE_OBJ(s);
@@ -514,3 +527,31 @@ void ME_ClearTempStyle(ME_TextEditor *editor)
   ME_ReleaseStyle(editor->pBuffer->pCharStyle);
   editor->pBuffer->pCharStyle = NULL;
 }
+
+/******************************************************************************
+ * ME_SetDefaultCharFormat
+ *
+ * Applies a style change to the default character style.
+ *
+ * The default style is special in that it is mutable - runs
+ * in the document that have this style should change if the
+ * default style changes.  That means we need to fix up this
+ * style manually.
+ */
+void ME_SetDefaultCharFormat(ME_TextEditor *editor, CHARFORMAT2W *mod)
+{
+    ME_Style *style, *def = editor->pBuffer->pDefaultStyle;
+
+    assert(mod->cbSize == sizeof(CHARFORMAT2W));
+    style = ME_ApplyStyle(editor, def, mod);
+    def->fmt = style->fmt;
+    def->tm = style->tm;
+    if (def->font_cache)
+    {
+        release_font_cache( def->font_cache );
+        def->font_cache = NULL;
+    }
+    ScriptFreeCache( &def->script_cache );
+    ME_ReleaseStyle( style );
+    ME_MarkAllForWrapping( editor );
+}
index 5f6862e..04e61ab 100644 (file)
@@ -44,7 +44,7 @@ ITextHost *ME_CreateTextHost(HWND hwnd, CREATESTRUCTW *cs, BOOL bEmulateVersion1
         texthost->hWnd = hwnd;
         texthost->bEmulateVersion10 = bEmulateVersion10;
 
-        editor = ME_MakeEditor(&texthost->ITextHost_iface, bEmulateVersion10);
+        editor = ME_MakeEditor(&texthost->ITextHost_iface, bEmulateVersion10, cs->style);
         editor->exStyleFlags = GetWindowLongW(hwnd, GWL_EXSTYLE);
         editor->styleFlags |= GetWindowLongW(hwnd, GWL_STYLE) & ES_WANTRETURN;
         editor->hWnd = hwnd; /* FIXME: Remove editor's dependence on hWnd */
index 4aacffa..e4a418c 100644 (file)
@@ -402,7 +402,7 @@ HRESULT WINAPI CreateTextServices(IUnknown  *pUnkOuter, ITextHost *pITextHost, I
    ITextImpl->pMyHost = pITextHost;
    ITextImpl->IUnknown_inner.lpVtbl = &textservices_inner_vtbl;
    ITextImpl->ITextServices_iface.lpVtbl = &textservices_vtbl;
-   ITextImpl->editor = ME_MakeEditor(pITextHost, FALSE);
+   ITextImpl->editor = ME_MakeEditor(pITextHost, FALSE, ES_LEFT);
    ITextImpl->editor->exStyleFlags = 0;
    ITextImpl->editor->rcFormat.left = 0;
    ITextImpl->editor->rcFormat.top = 0;
index 9db690e..7b22e6d 100644 (file)
@@ -341,6 +341,7 @@ static void ME_PlayUndoItem(ME_TextEditor *editor, struct undo_item *undo)
     add_undo_set_para_fmt( editor, &para->member.para );
     *para->member.para.pFmt = undo->u.set_para_fmt.fmt;
     para->member.para.border = undo->u.set_para_fmt.border;
+    para->member.para.nFlags |= MEPF_REWRAP;
     break;
   }
   case undo_set_char_fmt:
index bedfd3f..f38ea30 100644 (file)
@@ -59,6 +59,8 @@ ME_StreamOutFlush(ME_OutStream *pStream)
       return FALSE;
     /* Don't resend partial chunks if nWritten < pStream->pos */
   }
+  if (nWritten == pStream->pos)
+      pStream->written += nWritten;
   pStream->pos = 0;
   return TRUE;
 }
index ef8db21..06612bc 100644 (file)
@@ -162,7 +162,7 @@ reactos/dll/win32/qmgrprxy            # Synced to WineStaging-1.7.47
 reactos/dll/win32/query               # Synced to WineStaging-1.7.47
 reactos/dll/win32/rasapi32            # Synced to WineStaging-1.7.47
 reactos/dll/win32/resutils            # Synced to WineStaging-1.7.47
-reactos/dll/win32/riched20            # Synced to WineStaging-1.7.47
+reactos/dll/win32/riched20            # Synced to WineStaging-1.7.55
 reactos/dll/win32/riched32            # Synced to WineStaging-1.7.47
 reactos/dll/win32/rpcrt4              # Synced to WineStaging-1.7.55
 reactos/dll/win32/rsabase             # Synced to WineStaging-1.7.47