ReactOS 0.4.16-dev-1405-gc14a14e
richole.c
Go to the documentation of this file.
1/*
2 * Tests for IRichEditOle and friends.
3 *
4 * Copyright 2008 Google (Dan Hipschman)
5 *
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
10 *
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
15 *
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
19 */
20
21#define COBJMACROS
22
23#include <stdarg.h>
24
25#include <windef.h>
26#include <winbase.h>
27#include <wingdi.h>
28#include <winuser.h>
29#include <initguid.h>
30#include <ole2.h>
31#include <richedit.h>
32#include <richole.h>
33#include <tom.h>
34#include <imm.h>
35#include <textserv.h>
36#include <wine/test.h>
37#ifdef __REACTOS__
38#define debugstr_guid wine_dbgstr_guid
39#endif
40
41#define EXPECT_TODO_WINE 0x80000000UL
42
44{
47 int line;
48
50
51 const CLSID *clsid;
55};
56
58{
60}
61
63{
64 if (IsEqualGUID(riid, &IID_IUnknown) || IsEqualGUID(riid, &IID_IRichEditOleCallback)) {
65 IRichEditOleCallback_AddRef(iface);
66 *obj = iface;
67 return S_OK;
68 }
69 *obj = NULL;
70 return E_NOINTERFACE;
71}
72
74{
77 return ref;
78}
79
81{
84 if (!ref) free(This);
85 return ref;
86}
87
89{
90 return E_NOTIMPL;
91}
92
94 IOleInPlaceFrame **frame,
96 OLEINPLACEFRAMEINFO *frame_info)
97{
98 return E_INVALIDARG;
99}
100
102{
103 return S_OK;
104}
105
108{
110 ULONG expect = This->expect_queryinsertobject;
111
113 ok_(__FILE__,This->line)( expect & ~EXPECT_TODO_WINE,
114 "unexpected call to IRichEditOleCallback_QueryInsertObject\n");
115 if (!(expect & ~EXPECT_TODO_WINE)) return S_OK;
116 This->expect_queryinsertobject--;
117
118 if (This->clsid && clsid)
119 ok_(__FILE__,This->line)( IsEqualGUID(This->clsid, clsid),
120 "QueryInsertObject clsid expected %s, got %s\n",
122 else
123 ok_(__FILE__,This->line)( This->clsid == clsid,
124 "QueryInsertObject clsid expected %p, got %p\n", This->clsid, clsid );
125 ok_(__FILE__,This->line)( This->stg == stg, "QueryInsertObject stg expected %p, got %p\n", This->stg, stg );
126 ok_(__FILE__,This->line)( This->cp == cp, "QueryInsertObject cp expected %ld, got %ld\n", This->cp, cp );
127 return This->queryinsertobject_result;
128}
129
131{
132 return S_OK;
133}
134
136 CLIPFORMAT *cf_format, DWORD reco, BOOL really,
137 HGLOBAL metapict)
138{
139 return S_OK;
140}
141
143{
144 return S_OK;
145}
146
148 DWORD reco, IDataObject **dataobj)
149{
150 return E_NOTIMPL;
151}
152
154 DWORD key_state, DWORD *effect)
155{
156 if (effect) *effect = DROPEFFECT_COPY;
157 return S_OK;
158}
159
161 IOleObject *oleobj, CHARRANGE *chrg, HMENU *hmenu)
162{
163 return E_NOTIMPL;
164}
165
166static const struct IRichEditOleCallbackVtbl reolecb_obj_Vtbl = {
180};
181
183{
184 struct reolecb_obj *obj;
185
186 obj = calloc(sizeof(struct reolecb_obj), 1);
187 if (!obj) return E_OUTOFMEMORY;
188
189#ifdef __REACTOS__
190 obj->IRichEditOleCallback_iface.lpVtbl = (IRichEditOleCallbackVtbl*)&reolecb_obj_Vtbl;
191#else
192 obj->IRichEditOleCallback_iface.lpVtbl = &reolecb_obj_Vtbl;
193#endif
194 obj->ref = 1;
195
196 *objptr = obj;
197 return S_OK;
198}
199
202{
203 if (!This) return;
204
205 This->line = line;
206 This->expect_queryinsertobject = expect;
207 This->clsid = clsid;
208 This->stg = stg;
209 This->cp = cp;
210 This->queryinsertobject_result = result;
211}
212
214{
215 if (!This) return;
216
217 todo_wine_if(This->expect_queryinsertobject & EXPECT_TODO_WINE)
218 ok( !(This->expect_queryinsertobject & ~EXPECT_TODO_WINE),
219 "expected IRichEditOleCallback_QueryInsertObject to be called\n" );
220
222}
223
224DEFINE_GUID(CLSID_testoleobj, 0x4484082e, 0x6d18, 0x4932, 0xa0, 0x86, 0x5b, 0x4d, 0xcf, 0x36, 0xb3, 0xde);
225
229 int line;
231
235
237};
238
240{
241 return CONTAINING_RECORD( iface, struct testoleobj, IOleObject_iface );
242}
243
245{
246 struct testoleobj *This = impl_from_IOleObject( iface );
247
249 {
250 *obj = iface;
251 }
252 else if (IsEqualGUID( riid, &IID_IViewObject ))
253 {
254 *obj = &This->IViewObject_iface;
255 }
256 else
257 {
258 if (!IsEqualGUID( riid, &IID_IOleLink ) &&
260 !IsEqualGUID( riid, &IID_IMarshal ))
261 {
262 trace( "Unsupported interface: %s\n", debugstr_guid( riid ));
263 }
264 *obj = NULL;
265 return E_NOINTERFACE;
266 }
267
268 IUnknown_AddRef( (IUnknown *)*obj );
269 return S_OK;
270}
271
273{
274 struct testoleobj *This = impl_from_IOleObject( iface );
276 return ref;
277}
278
280{
281 struct testoleobj *This = impl_from_IOleObject( iface );
283 if (!ref)
284 {
285 if (This->advise_holder)
286 {
287 IOleAdviseHolder_Release( This->advise_holder );
288 This->advise_holder = NULL;
289 }
290 if (This->clientsite)
291 {
292 IOleClientSite_Release( This->clientsite );
293 This->clientsite = NULL;
294 }
295 free( This );
296 }
297 return ref;
298}
299
301{
302 struct testoleobj *This = impl_from_IOleObject( iface );
303
304 if (This->clientsite != clientsite)
305 {
306 if (This->clientsite) IOleClientSite_Release( This->clientsite );
307 This->clientsite = clientsite;
308 if (This->clientsite) IOleClientSite_AddRef( This->clientsite );
309 }
310
311 return S_OK;
312}
313
315{
316 struct testoleobj *This = impl_from_IOleObject( iface );
317
318 if (This->clientsite) IOleClientSite_AddRef( This->clientsite );
319 *clientsite = This->clientsite;
320
321 return S_OK;
322}
323
325 LPCOLESTR container_app,
326 LPCOLESTR container_obj )
327{
328 return S_OK;
329}
330
332{
333 return S_OK;
334}
335
337 DWORD which_moniker, IMoniker *mk )
338{
339 return S_OK;
340}
341
343 DWORD which_moniker, IMoniker **mk )
344{
345 struct testoleobj *This = impl_from_IOleObject( iface );
346
347 *mk = NULL;
348
349 if (!This->clientsite) return E_UNEXPECTED;
350
351 return IOleClientSite_GetMoniker( This->clientsite, assign, which_moniker, mk );
352}
353
355 BOOL creation, DWORD reserved )
356{
357 return E_NOTIMPL;
358}
359
361 IDataObject **dataobj )
362{
363 *dataobj = NULL;
364 return E_NOTIMPL;
365}
366
368 IOleClientSite *activesite, LONG index,
369 HWND parentwnd, LPCRECT posrect )
370{
371 return E_NOTIMPL;
372}
373
375{
376 *enumoleverb = NULL;
377 return OLEOBJ_E_NOVERBS;
378}
379
381{
382 return S_OK;
383}
384
386{
387 return S_OK;
388}
389
391{
392 *clsid = CLSID_testoleobj;
393 return S_OK;
394}
395
397{
398 static const OLECHAR typename[] = L"richole testoleobj";
399
400 *user_type = CoTaskMemAlloc( sizeof(typename) );
401 if (!*user_type) return E_OUTOFMEMORY;
402
403 memcpy( *user_type, typename, sizeof(typename) );
404 return S_OK;
405}
406
408{
409 struct testoleobj *This = impl_from_IOleObject( iface );
410
411 if (draw_aspect != DVASPECT_CONTENT) return E_FAIL;
412
413 This->extent = *sizel;
414 return S_OK;
415}
416
418{
419 struct testoleobj *This = impl_from_IOleObject( iface );
420
421 if (draw_aspect != DVASPECT_CONTENT) return E_FAIL;
422
423 *sizel = This->extent;
424 return S_OK;
425}
426
428{
429 struct testoleobj *This = impl_from_IOleObject( iface );
430 HRESULT hr = S_OK;
431
432 if (!This->advise_holder) hr = CreateOleAdviseHolder( &This->advise_holder );
433 if (SUCCEEDED( hr )) hr = IOleAdviseHolder_Advise( This->advise_holder, adv_sink, connection );
434 return hr;
435}
436
438{
439 struct testoleobj *This = impl_from_IOleObject( iface );
440
441 if (!This->advise_holder) return OLE_E_NOCONNECTION;
442 return IOleAdviseHolder_Unadvise( This->advise_holder, connection );
443}
444
446{
447 struct testoleobj *This = impl_from_IOleObject( iface );
448
449 if (!This->advise_holder)
450 {
451 *enum_advise = NULL;
452 return S_OK;
453 }
454 return IOleAdviseHolder_EnumAdvise( This->advise_holder, enum_advise );
455}
456
458{
459 *status = 0;
460 return S_OK;
461}
462
464{
465 return E_NOTIMPL;
466}
467
468static const struct IOleObjectVtbl testoleobj_IOleObject_Vtbl = {
493};
494
496{
497 return CONTAINING_RECORD( iface, struct testoleobj, IViewObject_iface );
498}
499
501{
502 struct testoleobj *This = impl_from_IViewObject( iface );
503 return IOleObject_QueryInterface( &This->IOleObject_iface, riid, obj );
504}
505
507{
508 struct testoleobj *This = impl_from_IViewObject( iface );
509 return IOleObject_AddRef( &This->IOleObject_iface );
510}
511
513{
514 struct testoleobj *This = impl_from_IViewObject( iface );
515 return IOleObject_Release( &This->IOleObject_iface );
516}
517
519 LONG index, void *aspect, DVTARGETDEVICE *td,
520 HDC hdc_target_dev, HDC hdc_draw,
521 LPCRECTL bounds, LPCRECTL wbounds,
522 BOOL (CALLBACK *fn_continue)(ULONG_PTR),
523 ULONG_PTR arg_continue )
524{
525 struct testoleobj *This = impl_from_IViewObject( iface );
526 SIZEL dpi;
527
528 if (draw_aspect != DVASPECT_CONTENT || index != -1) return E_NOTIMPL;
529
530 ok_(__FILE__,This->line)( td == NULL, "expected td to be NULL, got %p\n", td );
531 ok_(__FILE__,This->line)( hdc_target_dev == NULL, "expected hdc_target_dev to be NULL, got %p\n", hdc_target_dev );
532 ok_(__FILE__,This->line)( wbounds == NULL, "expected wbounds to be NULL, got %p\n", wbounds );
533
534 dpi.cx = GetDeviceCaps(hdc_draw, LOGPIXELSX);
535 dpi.cy = GetDeviceCaps(hdc_draw, LOGPIXELSY);
536
537 ok_(__FILE__,This->line)( bounds->right - bounds->left == MulDiv( This->extent.cx, dpi.cx, 2540 ),
538 "bounds->right (= %ld) - bounds->left (= %ld) != "
539 "MulDiv( This->extent.cx (= %ld), dpi.cx (= %ld), 2540 )\n",
540 bounds->right, bounds->left, This->extent.cx, dpi.cx );
541 ok_(__FILE__,This->line)( bounds->bottom - bounds->top == MulDiv( This->extent.cy, dpi.cy, 2540 ),
542 "bounds->bottom (= %ld) - bounds->top (= %ld) != "
543 "MulDiv( This->extent.cy (= %ld), dpi.cy (= %ld), 2540 )\n",
544 bounds->bottom, bounds->top, This->extent.cy, dpi.cy );
545
546 FillRect( hdc_draw, (const RECT *)bounds, GetStockObject( DKGRAY_BRUSH ));
547 This->draw_count++;
548
549 return S_OK;
550}
551
553 LONG index, void *aspect, DVTARGETDEVICE *td,
554 HDC hdc_target_dev, LOGPALETTE **color_set )
555{
556 *color_set = NULL;
557 return E_NOTIMPL;
558}
559
561 LONG index, void *aspect, DWORD *freeze )
562{
563 *freeze = 0;
564 return E_NOTIMPL;
565}
566
568{
569 return E_NOTIMPL;
570}
571
573 DWORD advf, IAdviseSink *adv_sink )
574{
575 return E_NOTIMPL;
576}
577
579 DWORD *advf, IAdviseSink **adv_sink )
580{
581 *aspects = 0;
582 *advf = 0;
583 *adv_sink = NULL;
584 return E_NOTIMPL;
585}
586
587static const struct IViewObjectVtbl testoleobj_IViewObject_Vtbl = {
597};
598
599static HRESULT testoleobj_Create( struct testoleobj **objptr )
600{
601 struct testoleobj *obj;
602
603 obj = calloc( sizeof(struct testoleobj), 1 );
604 *objptr = obj;
605 if (!obj) return E_OUTOFMEMORY;
606
607
608#ifdef __REACTOS__
609 obj->IOleObject_iface.lpVtbl = (IOleObjectVtbl*)&testoleobj_IOleObject_Vtbl;
610#else
611 obj->IOleObject_iface.lpVtbl = &testoleobj_IOleObject_Vtbl;
612#endif
613 obj->ref = 1;
614#ifdef __REACTOS__
615 obj->IViewObject_iface.lpVtbl = (IViewObjectVtbl*)&testoleobj_IViewObject_Vtbl;
616#else
617 obj->IViewObject_iface.lpVtbl = &testoleobj_IViewObject_Vtbl;
618#endif
619
620 return S_OK;
621}
622
624
625DEFINE_GUID(GUID_NULL, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0);
626DEFINE_GUID(IID_ITextServices, 0x8d33f740, 0xcf58, 0x11ce, 0xa8, 0x9d, 0x00, 0xaa, 0x00, 0x6c, 0xad, 0xc5);
627
628static const WCHAR sysW[] = {'S','y','s','t','e','m',0};
629
630#define EXPECT_REF(obj,ref) _expect_ref((IUnknown*)obj, ref, __LINE__)
632{
633 ULONG rc;
634 IUnknown_AddRef(obj);
635 rc = IUnknown_Release(obj);
636 ok_(__FILE__,line)(rc == ref, "expected refcount %ld, got %ld\n", ref, rc);
637}
638
639static HWND new_window(LPCSTR lpClassName, DWORD dwStyle, HWND parent)
640{
641 HWND hwnd = CreateWindowA(lpClassName, NULL,
643 0, 0, 200, 60, parent, NULL, hmoduleRichEdit, NULL);
644 ok(hwnd != NULL, "class: %s, error: %d\n", lpClassName, (int) GetLastError());
645 return hwnd;
646}
647
649{
651}
652
654{
655 HANDLE file;
656
659
661 return FALSE;
663 return TRUE;
664}
665
667{
668 HANDLE file;
669
671 OPEN_EXISTING, 0, NULL);
673 return FALSE;
675 return TRUE;
676}
677
678static void create_interfaces(HWND *w, IRichEditOle **reOle, ITextDocument **txtDoc,
679 ITextSelection **txtSel)
680{
681 *w = new_richedit(NULL);
683 IRichEditOle_QueryInterface(*reOle, &IID_ITextDocument,
684 (void **) txtDoc);
685 ITextDocument_GetSelection(*txtDoc, txtSel);
686}
687
688static void release_interfaces(HWND *w, IRichEditOle **reOle, ITextDocument **txtDoc,
689 ITextSelection **txtSel)
690{
691 if(txtSel)
692 ITextSelection_Release(*txtSel);
693 ITextDocument_Release(*txtDoc);
694 IRichEditOle_Release(*reOle);
696}
697
699{
700 IUnknown_AddRef(iface);
701 return IUnknown_Release(iface);
702}
703
704#define CHECK_TYPEINFO(disp,expected_riid) _check_typeinfo((IDispatch *)disp, expected_riid, __LINE__)
705static void _check_typeinfo(IDispatch* disp, REFIID expected_riid, int line)
706{
708 TYPEATTR *typeattr;
709 UINT count;
710 HRESULT hr;
711
712 count = 10;
713 hr = IDispatch_GetTypeInfoCount(disp, &count);
714 ok_(__FILE__,line)(hr == S_OK, "IDispatch_GetTypeInfoCount failed: 0x%08lx.\n", hr);
715 ok_(__FILE__,line)(count == 1, "got wrong count: %u.\n", count);
716
717 hr = IDispatch_GetTypeInfo(disp, 0, LOCALE_SYSTEM_DEFAULT, &typeinfo);
718 ok_(__FILE__,line)(hr == S_OK, "IDispatch_GetTypeInfo failed: 0x%08lx.\n", hr);
719
720 hr = ITypeInfo_GetTypeAttr(typeinfo, &typeattr);
721 ok_(__FILE__,line)(hr == S_OK, "ITypeInfo_GetTypeAttr failed: 0x%08lx.\n", hr);
722 ok_(__FILE__,line)(IsEqualGUID(&typeattr->guid, expected_riid),
723 "Unexpected type guid: %s.\n", wine_dbgstr_guid(&typeattr->guid));
724
725 ITypeInfo_ReleaseTypeAttr(typeinfo, typeattr);
726 ITypeInfo_Release(typeinfo);
727}
728
729static void test_Interfaces(void)
730{
731 IRichEditOle *reOle = NULL, *reOle1 = NULL;
732 ITextDocument *txtDoc = NULL;
733 ITextDocument2Old *txtDoc2Old = NULL;
734 ITextSelection *txtSel = NULL, *txtSel2;
735 IUnknown *punk;
737 LRESULT res;
738 HWND w;
739 ULONG refcount;
740 IUnknown *unk, *unk2;
741
743 if (!w) {
744 skip("Couldn't create window\n");
745 return;
746 }
747
749 ok(res, "SendMessage\n");
750 ok(reOle != NULL, "EM_GETOLEINTERFACE\n");
751 EXPECT_REF(reOle, 2);
752
753 res = SendMessageA(w, EM_GETOLEINTERFACE, 0, (LPARAM)&reOle1);
754 ok(res == 1, "SendMessage\n");
755 ok(reOle1 == reOle, "Should not return a new IRichEditOle interface\n");
756 EXPECT_REF(reOle, 3);
757
758 hres = IRichEditOle_QueryInterface(reOle, &IID_ITextDocument,
759 (void **) &txtDoc);
760 ok(hres == S_OK, "IRichEditOle_QueryInterface\n");
761 ok(txtDoc != NULL, "IRichEditOle_QueryInterface\n");
762 CHECK_TYPEINFO(txtDoc, &IID_ITextDocument);
763
764 hres = ITextDocument_GetSelection(txtDoc, NULL);
765 ok(hres == E_INVALIDARG, "ITextDocument_GetSelection: 0x%lx\n", hres);
766
767 EXPECT_REF(txtDoc, 4);
768
769 hres = ITextDocument_GetSelection(txtDoc, &txtSel);
770 ok(hres == S_OK, "got 0x%08lx\n", hres);
771
772 hres = ITextDocument_QueryInterface(txtDoc, &IID_IUnknown, (void **)&unk);
773 ok(hres == S_OK, "got 0x%08lx\n", hres);
774 hres = ITextSelection_QueryInterface(txtSel, &IID_IUnknown, (void **)&unk2);
775 ok(hres == S_OK, "got 0x%08lx\n", hres);
776 ok(unk != unk2, "unknowns are the same\n");
777 IUnknown_Release(unk2);
778 IUnknown_Release(unk);
779
780 EXPECT_REF(txtDoc, 4);
781 EXPECT_REF(txtSel, 2);
782
783 hres = ITextDocument_GetSelection(txtDoc, &txtSel2);
784 ok(hres == S_OK, "got 0x%08lx\n", hres);
785 ok(txtSel2 == txtSel, "got %p, %p\n", txtSel, txtSel2);
786
787 EXPECT_REF(txtDoc, 4);
788 EXPECT_REF(txtSel, 3);
789
790 ITextSelection_Release(txtSel2);
791
792 punk = NULL;
793 hres = ITextSelection_QueryInterface(txtSel, &IID_ITextSelection, (void **) &punk);
794 ok(hres == S_OK, "ITextSelection_QueryInterface\n");
795 ok(punk != NULL, "ITextSelection_QueryInterface\n");
796 IUnknown_Release(punk);
797
798 punk = NULL;
799 hres = ITextSelection_QueryInterface(txtSel, &IID_ITextRange, (void **) &punk);
800 ok(hres == S_OK, "ITextSelection_QueryInterface\n");
801 ok(punk != NULL, "ITextSelection_QueryInterface\n");
802 IUnknown_Release(punk);
803
804 punk = NULL;
805 hres = ITextSelection_QueryInterface(txtSel, &IID_IDispatch, (void **) &punk);
806 ok(hres == S_OK, "ITextSelection_QueryInterface\n");
807 ok(punk != NULL, "ITextSelection_QueryInterface\n");
808 IUnknown_Release(punk);
809
810 punk = NULL;
811 hres = IRichEditOle_QueryInterface(reOle, &IID_IOleClientSite, (void **) &punk);
812 ok(hres == E_NOINTERFACE, "IRichEditOle_QueryInterface\n");
813
814 punk = NULL;
815 hres = IRichEditOle_QueryInterface(reOle, &IID_IOleWindow, (void **) &punk);
816 ok(hres == E_NOINTERFACE, "IRichEditOle_QueryInterface\n");
817
818 punk = NULL;
819 hres = IRichEditOle_QueryInterface(reOle, &IID_IOleInPlaceSite, (void **) &punk);
820 ok(hres == E_NOINTERFACE, "IRichEditOle_QueryInterface\n");
821
822 hres = IRichEditOle_QueryInterface(reOle, &IID_ITextDocument2Old, (void **)&txtDoc2Old);
823 ok(hres == S_OK, "IRichEditOle_QueryInterface\n");
824 ok(txtDoc2Old != NULL, "IRichEditOle_QueryInterface\n");
825 ok((ITextDocument *)txtDoc2Old == txtDoc, "interface pointer isn't equal.\n");
826 EXPECT_REF(txtDoc2Old, 5);
827 EXPECT_REF(reOle, 5);
828 CHECK_TYPEINFO(txtDoc2Old, &IID_ITextDocument);
829
830 ITextDocument2Old_Release(txtDoc2Old);
831
832 ITextDocument_Release(txtDoc);
833 IRichEditOle_Release(reOle);
834 refcount = IRichEditOle_Release(reOle);
835 ok(refcount == 1, "got wrong ref count: %ld\n", refcount);
837
838 /* Methods should return CO_E_RELEASED if the backing document has
839 been released. One test should suffice. */
840 hres = ITextSelection_CanEdit(txtSel, NULL);
841 ok(hres == CO_E_RELEASED, "ITextSelection after ITextDocument destroyed\n");
842
843 ITextSelection_Release(txtSel);
844
847 ok(res, "SendMessage\n");
848 ok(reOle != NULL, "EM_GETOLEINTERFACE\n");
849
850 hres = IRichEditOle_QueryInterface(reOle, &IID_ITextDocument2Old, (void **)&txtDoc2Old);
851 ok(hres == S_OK, "IRichEditOle_QueryInterface failed: 0x%08lx.\n", hres);
852 ok(txtDoc2Old != NULL, "IRichEditOle_QueryInterface\n");
853 CHECK_TYPEINFO(txtDoc2Old, &IID_ITextDocument);
854 ITextDocument2Old_Release(txtDoc2Old);
855 IRichEditOle_Release(reOle);
857}
858
859static void test_ITextDocument_Open(void)
860{
861 IRichEditOle *reOle = NULL;
862 ITextDocument *txtDoc = NULL;
863 ITextSelection *txtSel = NULL;
865 HWND w;
867 VARIANT testfile;
868 WCHAR filename[] = {'t', 'e', 's', 't','.','t','x','t', 0};
869 int result;
870 DWORD dw;
871 static const CHAR chACP[] = "TestSomeText";
872 static const CHAR chUTF8[] = "\xef\xbb\xbfTextWithUTF8BOM";
873 static const WCHAR chUTF16[] = {0xfeff, 'T', 'e', 's', 't', 'S', 'o', 'm',
874 'e', 'T', 'e', 'x', 't', 0};
875
876#define MAX_BUF_LEN 1024
877 CHAR bufACP[MAX_BUF_LEN];
878 WCHAR bufUnicode[MAX_BUF_LEN];
879
880 static const int tomConstantsSingle[] =
881 {
885 };
886
887 static const int tomConstantsMulti[] =
888 {
895 };
896
897 int tomNumSingle = ARRAY_SIZE(tomConstantsSingle);
898 int tomNumMulti = ARRAY_SIZE(tomConstantsMulti);
899 int i;
900
901 V_VT(&testfile) = VT_BSTR;
902 V_BSTR(&testfile) = SysAllocString(filename);
903
904 for(i=0; i < tomNumSingle; i++)
905 {
907 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
908 hres = ITextDocument_Open(txtDoc, &testfile, tomConstantsSingle[i], CP_ACP);
909 todo_wine ok(hres == S_OK, "ITextDocument_Open: Filename:test.txt Flags:0x%x Codepage:CP_ACP hres:0x%lx\n",
910 tomConstantsSingle[i], hres);
911 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
913
915 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
916 hres = ITextDocument_Open(txtDoc, &testfile, tomConstantsSingle[i], CP_UTF8);
917 todo_wine ok(hres == S_OK, "ITextDocument_Open: Filename:test.txt Flags:0x%x Codepage:CP_UTF8 hres:0x%lx\n",
918 tomConstantsSingle[i], hres);
919 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
921 }
922
923 for(i=0; i < tomNumMulti; i++)
924 {
926 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
927 hres = ITextDocument_Open(txtDoc, &testfile, tomConstantsMulti[i], CP_ACP);
928 todo_wine ok(hres == S_OK, "ITextDocument_Open: Filename:test.txt Flags:0x%x Codepage:CP_ACP hres:0x%lx\n",
929 tomConstantsMulti[i], hres);
930 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
932
934 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
935 hres = ITextDocument_Open(txtDoc, &testfile, tomConstantsMulti[i], CP_UTF8);
936 todo_wine ok(hres == S_OK, "ITextDocument_Open: Filename:test.txt Flags:0x%x Codepage:CP_UTF8 hres:0x%lx\n",
937 tomConstantsMulti[i], hres);
938 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
940 }
941
942 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
943 hres = ITextDocument_Open(txtDoc, &testfile, tomCreateAlways, CP_ACP);
944 todo_wine ok(hres == S_OK, "ITextDocument_Open should success Codepage:CP_ACP\n");
945 todo_wine ok(is_existing_file(filename), "ITextDocument_Open should create a file\n");
946 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
948
949 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
950 hres = ITextDocument_Open(txtDoc, &testfile, tomCreateAlways, CP_UTF8);
951 todo_wine ok(hres == S_OK, "ITextDocument_Open should success Codepage:CP_UTF8\n");
952 todo_wine ok(is_existing_file(filename), "ITextDocument_Open should create a file\n");
953 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
955
956 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
957 hres = ITextDocument_Open(txtDoc, &testfile, tomOpenAlways, CP_ACP);
958 todo_wine ok(hres == S_OK, "ITextDocument_Open should success Codepage:CP_ACP\n");
959 todo_wine ok(is_existing_file(filename), "ITextDocument_Open should create a file\n");
960 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
962
963 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
964 hres = ITextDocument_Open(txtDoc, &testfile, tomOpenAlways, CP_UTF8);
965 todo_wine ok(hres == S_OK, "ITextDocument_Open should success Codepage:CP_UTF8\n");
966 todo_wine ok(is_existing_file(filename), "ITextDocument_Open should create a file\n");
967 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
969
970 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
971 hres = ITextDocument_Open(txtDoc, &testfile, tomCreateNew, CP_ACP);
972 todo_wine ok(hres == S_OK, "ITextDocument_Open should success Codepage:CP_ACP\n");
973 todo_wine ok(is_existing_file(filename), "ITextDocument_Open should create a file\n");
974 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
976
977 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
978 hres = ITextDocument_Open(txtDoc, &testfile, tomCreateNew, CP_UTF8);
979 todo_wine ok(hres == S_OK, "ITextDocument_Open should success Codepage:CP_UTF8\n");
980 todo_wine ok(is_existing_file(filename), "ITextDocument_Open should create a file\n");
981 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
983
984 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
986 hres = ITextDocument_Open(txtDoc, &testfile, tomCreateNew, CP_ACP);
987 todo_wine ok(hres == HRESULT_FROM_WIN32(ERROR_FILE_EXISTS), "ITextDocument_Open should fail Codepage:CP_ACP\n");
988 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
990
991 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
993 hres = ITextDocument_Open(txtDoc, &testfile, tomCreateNew, CP_UTF8);
994 todo_wine ok(hres == HRESULT_FROM_WIN32(ERROR_FILE_EXISTS), "ITextDocument_Open should fail Codepage:CP_UTF8\n");
995 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
997
998 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
999 hres = ITextDocument_Open(txtDoc, &testfile, tomOpenExisting, CP_ACP);
1000 todo_wine ok(hres == HRESULT_FROM_WIN32(ERROR_FILE_NOT_FOUND), "ITextDocument_Open should fail Codepage:CP_ACP\n");
1001 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
1002
1003 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
1004 hres = ITextDocument_Open(txtDoc, &testfile, tomOpenExisting, CP_UTF8);
1005 todo_wine ok(hres == HRESULT_FROM_WIN32(ERROR_FILE_NOT_FOUND), "ITextDocument_Open should fail Codepage:CP_UTF8\n");
1006 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
1007
1008 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
1010 hres = ITextDocument_Open(txtDoc, &testfile, tomText, CP_ACP);
1011todo_wine {
1012 ok(hres == S_OK, "got 0x%08lx\n", hres);
1013 ok(is_existing_file(filename) == TRUE, "a file should be created default\n");
1014}
1015 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
1017
1018 /* test of share mode */
1020 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
1021 hres = ITextDocument_Open(txtDoc, &testfile, tomShareDenyRead, CP_ACP);
1022 todo_wine
1023 ok(hres == S_OK, "got 0x%08lx\n", hres);
1024 SetLastError(0xdeadbeef);
1027 todo_wine ok(GetLastError() == ERROR_SHARING_VIOLATION, "ITextDocument_Open should fail\n");
1029 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
1031
1033 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
1034 hres = ITextDocument_Open(txtDoc, &testfile, tomShareDenyWrite, CP_ACP);
1035 todo_wine
1036 ok(hres == S_OK, "got 0x%08lx\n", hres);
1037 SetLastError(0xdeadbeef);
1040 todo_wine ok(GetLastError() == ERROR_SHARING_VIOLATION, "ITextDocument_Open should fail\n");
1042 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
1044
1046 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
1047 SetLastError(0xdeadbeef);
1048 hres = ITextDocument_Open(txtDoc, &testfile, tomShareDenyWrite|tomShareDenyRead, CP_ACP);
1049 todo_wine
1050 ok(hres == S_OK, "got 0x%08lx\n", hres);
1053 todo_wine ok(GetLastError() == ERROR_SHARING_VIOLATION, "ITextDocument_Open should fail\n");
1055 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
1057
1058 /* tests to check the content */
1061 WriteFile(hFile, chACP, sizeof(chACP)-sizeof(CHAR), &dw, NULL);
1063 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
1064 hres = ITextDocument_Open(txtDoc, &testfile, tomReadOnly, CP_ACP);
1065 todo_wine
1066 ok(hres == S_OK, "got 0x%08lx\n", hres);
1067 result = SendMessageA(w, WM_GETTEXT, 1024, (LPARAM)bufACP);
1068 todo_wine ok(result == 12, "ITextDocument_Open: Test ASCII returned %d, expected 12\n", result);
1069 result = strcmp(bufACP, chACP);
1070 todo_wine ok(result == 0, "ITextDocument_Open: Test ASCII set wrong text: Result: %s\n", bufACP);
1071 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
1073
1076 WriteFile(hFile, chUTF8, sizeof(chUTF8)-sizeof(CHAR), &dw, NULL);
1078 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
1079 hres = ITextDocument_Open(txtDoc, &testfile, tomReadOnly, CP_UTF8);
1080 todo_wine
1081 ok(hres == S_OK, "got 0x%08lx\n", hres);
1082 result = SendMessageA(w, WM_GETTEXT, 1024, (LPARAM)bufACP);
1083 todo_wine ok(result == 15, "ITextDocument_Open: Test UTF-8 returned %d, expected 15\n", result);
1084 result = strcmp(bufACP, &chUTF8[3]);
1085 todo_wine ok(result == 0, "ITextDocument_Open: Test UTF-8 set wrong text: Result: %s\n", bufACP);
1086 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
1088
1091 WriteFile(hFile, chUTF16, sizeof(chUTF16)-sizeof(WCHAR), &dw, NULL);
1093 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
1094 hres = ITextDocument_Open(txtDoc, &testfile, tomReadOnly, 1200);
1095 todo_wine
1096 ok(hres == S_OK, "got 0x%08lx\n", hres);
1097 result = SendMessageW(w, WM_GETTEXT, 1024, (LPARAM)bufUnicode);
1098 todo_wine ok(result == 12, "ITextDocument_Open: Test UTF-16 returned %d, expected 12\n", result);
1099 result = lstrcmpW(bufUnicode, &chUTF16[1]);
1100 todo_wine ok(result == 0, "ITextDocument_Open: Test UTF-16 set wrong text: Result: %s\n", wine_dbgstr_w(bufUnicode));
1101 release_interfaces(&w, &reOle, &txtDoc, &txtSel);
1103
1104 VariantClear(&testfile);
1105}
1106
1107static void test_GetText(void)
1108{
1109 HWND w;
1110 IRichEditOle *reOle = NULL;
1111 ITextDocument *txtDoc = NULL;
1112 ITextSelection *txtSel = NULL;
1113 HRESULT hres;
1114 BSTR bstr = NULL;
1115 int first, lim;
1116 static const CHAR test_text1[] = "TestSomeText";
1117 static const WCHAR bufW1[] = {'T', 'e', 's', 't', 0};
1118 static const WCHAR bufW2[] = {'T', 'e', 'x', 't', '\r', 0};
1119 static const WCHAR bufW3[] = {'T', 'e', 'x', 't', 0};
1120 static const WCHAR bufW4[] = {'T', 'e', 's', 't', 'S', 'o', 'm',
1121 'e', 'T', 'e', 'x', 't', '\r', 0};
1122 static const WCHAR bufW5[] = {'\r', 0};
1123 static const WCHAR bufW6[] = {'T','e','s','t','S','o','m','e','T',0};
1124 BOOL is64bit = sizeof(void *) > sizeof(int);
1126
1127 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
1128 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
1129
1130 /* ITextSelection */
1131 first = 0; lim = 4;
1132 SendMessageA(w, EM_SETSEL, first, lim);
1133 hres = ITextSelection_GetText(txtSel, &bstr);
1134 ok(hres == S_OK, "ITextSelection_GetText\n");
1135 ok(!lstrcmpW(bstr, bufW1), "got wrong text: %s\n", wine_dbgstr_w(bstr));
1136 SysFreeString(bstr);
1137
1138 first = 4; lim = 0;
1139 SendMessageA(w, EM_SETSEL, first, lim);
1140 hres = ITextSelection_GetText(txtSel, &bstr);
1141 ok(hres == S_OK, "ITextSelection_GetText\n");
1142 ok(!lstrcmpW(bstr, bufW1), "got wrong text: %s\n", wine_dbgstr_w(bstr));
1143 SysFreeString(bstr);
1144
1145 first = 1; lim = 1;
1146 SendMessageA(w, EM_SETSEL, first, lim);
1147 hres = ITextSelection_GetText(txtSel, &bstr);
1148 ok(hres == S_OK, "ITextSelection_GetText\n");
1149 ok(!bstr, "got wrong text: %s\n", wine_dbgstr_w(bstr));
1150
1151 if (!is64bit)
1152 {
1153 hres = ITextSelection_GetText(txtSel, NULL);
1154 ok(hres == E_INVALIDARG, "ITextSelection_GetText\n");
1155 }
1156
1157 first = 8; lim = 12;
1158 SendMessageA(w, EM_SETSEL, first, lim);
1159 hres = ITextSelection_GetText(txtSel, &bstr);
1160 ok(hres == S_OK, "ITextSelection_GetText\n");
1161 ok(!lstrcmpW(bstr, bufW3), "got wrong text: %s\n", wine_dbgstr_w(bstr));
1162 SysFreeString(bstr);
1163
1164 first = 8; lim = 13;
1165 SendMessageA(w, EM_SETSEL, first, lim);
1166 hres = ITextSelection_GetText(txtSel, &bstr);
1167 ok(hres == S_OK, "ITextSelection_GetText\n");
1168 ok(!lstrcmpW(bstr, bufW2), "got wrong text: %s\n", wine_dbgstr_w(bstr));
1169 SysFreeString(bstr);
1170
1171 first = 12; lim = 13;
1172 SendMessageA(w, EM_SETSEL, first, lim);
1173 hres = ITextSelection_GetText(txtSel, &bstr);
1174 ok(hres == S_OK, "ITextSelection_GetText\n");
1175 ok(!lstrcmpW(bstr, bufW5), "got wrong text: %s\n", wine_dbgstr_w(bstr));
1176 SysFreeString(bstr);
1177
1178 first = 0; lim = -1;
1179 SendMessageA(w, EM_SETSEL, first, lim);
1180 hres = ITextSelection_GetText(txtSel, &bstr);
1181 ok(hres == S_OK, "ITextSelection_GetText\n");
1182 ok(!lstrcmpW(bstr, bufW4), "got wrong text: %s\n", wine_dbgstr_w(bstr));
1183 SysFreeString(bstr);
1184
1185 first = -1; lim = 9;
1186 SendMessageA(w, EM_SETSEL, first, lim);
1187 hres = ITextSelection_GetText(txtSel, &bstr);
1188 ok(hres == S_OK, "ITextSelection_GetText\n");
1189 ok(!bstr, "got wrong text: %s\n", wine_dbgstr_w(bstr));
1190
1191 /* ITextRange */
1192 hres = ITextDocument_Range(txtDoc, 0, 4, &range);
1193 ok(hres == S_OK, "got 0x%08lx\n", hres);
1194 hres = ITextRange_GetText(range, &bstr);
1195 ok(hres == S_OK, "got 0x%08lx\n", hres);
1196 ok(!lstrcmpW(bstr, bufW1), "got wrong text: %s\n", wine_dbgstr_w(bstr));
1197
1198 SysFreeString(bstr);
1199 ITextRange_Release(range);
1200
1201 hres = ITextDocument_Range(txtDoc, 4, 0, &range);
1202 ok(hres == S_OK, "got 0x%08lx\n", hres);
1203 hres = ITextRange_GetText(range, &bstr);
1204 ok(hres == S_OK, "got 0x%08lx\n", hres);
1205 ok(!lstrcmpW(bstr, bufW1), "got wrong text: %s\n", wine_dbgstr_w(bstr));
1206
1207 SysFreeString(bstr);
1208 ITextRange_Release(range);
1209
1210 hres = ITextDocument_Range(txtDoc, 1, 1, &range);
1211 ok(hres == S_OK, "got 0x%08lx\n", hres);
1212 hres = ITextRange_GetText(range, &bstr);
1213 ok(hres == S_OK, "got 0x%08lx\n", hres);
1214 ok(!bstr, "got wrong text: %s\n", wine_dbgstr_w(bstr));
1215 if (!is64bit)
1216 {
1217 hres = ITextRange_GetText(range, NULL);
1218 ok(hres == E_INVALIDARG, "got 0x%08lx\n", hres);
1219 }
1220 ITextRange_Release(range);
1221
1222 hres = ITextDocument_Range(txtDoc, 8, 12, &range);
1223 ok(hres == S_OK, "got 0x%08lx\n", hres);
1224 hres = ITextRange_GetText(range, &bstr);
1225 ok(hres == S_OK, "got 0x%08lx\n", hres);
1226 ok(!lstrcmpW(bstr, bufW3), "got wrong text: %s\n", wine_dbgstr_w(bstr));
1227
1228 SysFreeString(bstr);
1229 ITextRange_Release(range);
1230
1231 hres = ITextDocument_Range(txtDoc, 8, 13, &range);
1232 ok(hres == S_OK, "got 0x%08lx\n", hres);
1233 hres = ITextRange_GetText(range, &bstr);
1234 ok(hres == S_OK, "got 0x%08lx\n", hres);
1235 ok(!lstrcmpW(bstr, bufW2), "got wrong text: %s\n", wine_dbgstr_w(bstr));
1236
1237 SysFreeString(bstr);
1238 ITextRange_Release(range);
1239
1240 hres = ITextDocument_Range(txtDoc, 12, 13, &range);
1241 ok(hres == S_OK, "got 0x%08lx\n", hres);
1242 hres = ITextRange_GetText(range, &bstr);
1243 ok(hres == S_OK, "got 0x%08lx\n", hres);
1244 ok(!lstrcmpW(bstr, bufW5), "got wrong text: %s\n", wine_dbgstr_w(bstr));
1245
1246 SysFreeString(bstr);
1247 ITextRange_Release(range);
1248
1249 hres = ITextDocument_Range(txtDoc, 0, -1, &range);
1250 ok(hres == S_OK, "got 0x%08lx\n", hres);
1251 hres = ITextRange_GetText(range, &bstr);
1252 ok(hres == S_OK, "got 0x%08lx\n", hres);
1253 ok(!bstr, "got wrong text: %s\n", wine_dbgstr_w(bstr));
1254 ITextRange_Release(range);
1255
1256 hres = ITextDocument_Range(txtDoc, -1, 9, &range);
1257 ok(hres == S_OK, "got 0x%08lx\n", hres);
1258 hres = ITextRange_GetText(range, &bstr);
1259 ok(hres == S_OK, "got 0x%08lx\n", hres);
1260 ok(!lstrcmpW(bstr, bufW6), "got wrong text: %s\n", wine_dbgstr_w(bstr));
1261
1262 SysFreeString(bstr);
1263
1264 release_interfaces(&w, &reOle, &txtDoc, NULL);
1265
1266 /* detached selection/range */
1267 if (is64bit) {
1268 bstr = (void*)0xdeadbeef;
1269 hres = ITextSelection_GetText(txtSel, &bstr);
1270 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1271 todo_wine
1272 ok(bstr == NULL, "got %p\n", bstr);
1273
1274 bstr = (void*)0xdeadbeef;
1275 hres = ITextRange_GetText(range, &bstr);
1276 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1277 todo_wine
1278 ok(bstr == NULL, "got %p\n", bstr);
1279 }
1280 else {
1281 hres = ITextSelection_GetText(txtSel, NULL);
1282 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1283
1284 hres = ITextRange_GetText(range, NULL);
1285 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1286 }
1287
1288 ITextRange_Release(range);
1289 ITextSelection_Release(txtSel);
1290}
1291
1293{
1294 static const CHAR test_text1[] = "TestSomeText";
1295 HWND w;
1296 IRichEditOle *reOle = NULL;
1297 ITextDocument *txtDoc = NULL;
1298 ITextRange *txtRge, *range2;
1299 HRESULT hres;
1300 LONG value;
1301
1302 create_interfaces(&w, &reOle, &txtDoc, NULL);
1303 hres = ITextDocument_Range(txtDoc, 0, 0, &txtRge);
1304 ok(hres == S_OK, "ITextDocument_Range fails 0x%lx.\n", hres);
1305 EXPECT_REF(txtRge, 1);
1306
1307 hres = ITextDocument_Range(txtDoc, 0, 0, &range2);
1308 ok(hres == S_OK, "ITextDocument_Range fails 0x%lx.\n", hres);
1309 ok(range2 != txtRge, "A new pointer should be returned\n");
1310 ITextRange_Release(range2);
1311
1312 hres = ITextDocument_Range(txtDoc, 0, 0, NULL);
1313 ok(hres == E_INVALIDARG, "ITextDocument_Range should fail 0x%lx.\n", hres);
1314
1315 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
1316
1317 hres = ITextDocument_Range(txtDoc, 8, 30, &range2);
1318 ok(hres == S_OK, "ITextDocument_Range fails 0x%lx.\n", hres);
1319 hres = ITextRange_GetStart(range2, &value);
1320 ok(hres == S_OK, "got 0x%08lx\n", hres);
1321 ok(value == 8, "got %ld\n", value);
1322
1323 hres = ITextRange_GetEnd(range2, &value);
1324 ok(hres == S_OK, "got 0x%08lx\n", hres);
1325 ok(value == 13, "got %ld\n", value);
1326 ITextRange_Release(range2);
1327
1328 release_interfaces(&w, &reOle, &txtDoc, NULL);
1329 hres = ITextRange_CanEdit(txtRge, NULL);
1330 ok(hres == CO_E_RELEASED, "ITextRange after ITextDocument destroyed\n");
1331 ITextRange_Release(txtRge);
1332}
1333
1335{
1336 HWND w;
1337 IRichEditOle *reOle = NULL;
1338 ITextDocument *txtDoc = NULL;
1339 ITextRange *txtRge = NULL;
1340 HRESULT hres;
1341 LONG pch;
1342 int first, lim;
1343 static const CHAR test_text1[] = "TestSomeText";
1344
1345 first = 0, lim = 4;
1346 create_interfaces(&w, &reOle, &txtDoc, NULL);
1347 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
1348 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
1349 ok(hres == S_OK, "got 0x%08lx\n", hres);
1350 pch = 0xdeadbeef;
1351 hres = ITextRange_GetChar(txtRge, &pch);
1352 ok(hres == S_OK, "ITextRange_GetChar\n");
1353 ok(pch == 'T', "got wrong char: %c\n", (char)pch);
1354 ITextRange_Release(txtRge);
1355 release_interfaces(&w, &reOle, &txtDoc, NULL);
1356
1357 first = 0; lim = 0;
1358 create_interfaces(&w, &reOle, &txtDoc, NULL);
1359 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
1360 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
1361 ok(hres == S_OK, "got 0x%08lx\n", hres);
1362 pch = 0xdeadbeef;
1363 hres = ITextRange_GetChar(txtRge, &pch);
1364 ok(hres == S_OK, "ITextRange_GetChar\n");
1365 ok(pch == 'T', "got wrong char: %c\n", (char)pch);
1366 ITextRange_Release(txtRge);
1367 release_interfaces(&w, &reOle, &txtDoc, NULL);
1368
1369 first = 12; lim = 12;
1370 create_interfaces(&w, &reOle, &txtDoc, NULL);
1371 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
1372 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
1373 ok(hres == S_OK, "got 0x%08lx\n", hres);
1374 pch = 0xdeadbeef;
1375 hres = ITextRange_GetChar(txtRge, &pch);
1376 ok(hres == S_OK, "ITextRange_GetChar\n");
1377 ok(pch == '\r', "got wrong char: %c\n", (char)pch);
1378 ITextRange_Release(txtRge);
1379 release_interfaces(&w, &reOle, &txtDoc, NULL);
1380
1381 first = 13; lim = 13;
1382 create_interfaces(&w, &reOle, &txtDoc, NULL);
1383 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
1384 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
1385 ok(hres == S_OK, "got 0x%08lx\n", hres);
1386 pch = 0xdeadbeef;
1387 hres = ITextRange_GetChar(txtRge, &pch);
1388 ok(hres == S_OK, "ITextRange_GetChar\n");
1389 ok(pch == '\r', "got wrong char: %c\n", (char)pch);
1390 ITextRange_Release(txtRge);
1391 release_interfaces(&w, &reOle, &txtDoc, NULL);
1392
1393 create_interfaces(&w, &reOle, &txtDoc, NULL);
1394 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
1395 first = 12; lim = 12;
1396 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
1397 ok(hres == S_OK, "got 0x%08lx\n", hres);
1398 hres = ITextRange_GetChar(txtRge, NULL);
1399 ok(hres == E_INVALIDARG, "ITextRange_GetChar\n");
1400
1401 release_interfaces(&w, &reOle, &txtDoc, NULL);
1402
1403 hres = ITextRange_GetChar(txtRge, NULL);
1404 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1405
1406 hres = ITextRange_GetChar(txtRge, &pch);
1407 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1408
1409 ITextRange_Release(txtRge);
1410}
1411
1412/* Helper function for testing ITextRange_ScrollIntoView */
1413static void check_range(HWND w, ITextDocument* doc, int first, int lim,
1414 LONG bStart, int expected_nonzero)
1415{
1416 SCROLLINFO si;
1417 ITextRange *txtRge = NULL;
1418 HRESULT hres;
1419
1420 si.cbSize = sizeof(SCROLLINFO);
1421 si.fMask = SIF_POS | SIF_RANGE;
1422
1423 hres = ITextDocument_Range(doc, first, lim, &txtRge);
1424 ok(hres == S_OK, "got 0x%08lx\n", hres);
1425 hres = ITextRange_ScrollIntoView(txtRge, bStart);
1426 ok(hres == S_OK, "got 0x%08lx\n", hres);
1427 GetScrollInfo(w, SB_VERT, &si);
1428 if (expected_nonzero) {
1429 ok(si.nPos != 0,
1430 "Scrollbar at 0, should be >0. (TextRange %d-%d, scroll range %d-%d.)\n",
1431 first, lim, si.nMin, si.nMax);
1432 } else {
1433 ok(si.nPos == 0,
1434 "Scrollbar at %d, should be 0. (TextRange %d-%d, scroll range %d-%d.)\n",
1435 si.nPos, first, lim, si.nMin, si.nMax);
1436 }
1437}
1438
1440{
1441 HWND w;
1442 IRichEditOle *reOle = NULL;
1443 ITextDocument *txtDoc = NULL;
1444 ITextRange *txtRge = NULL;
1445 HRESULT hres;
1446 static const CHAR test_text1[] = "1\n2\n3\n4\n5\n6\n7\n8\n9\n10";
1447
1448 create_interfaces(&w, &reOle, &txtDoc, NULL);
1449 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
1450
1451 /* Scroll to the top. */
1452 check_range(w, txtDoc, 0, 1, tomStart, 0);
1453 check_range(w, txtDoc, 0, 1, tomEnd, 0);
1454
1455 /* Scroll to the bottom. */
1456 check_range(w, txtDoc, 19, 20, tomStart, 1);
1457 check_range(w, txtDoc, 19, 20, tomEnd, 1);
1458
1459 /* Back up to the top. */
1460 check_range(w, txtDoc, 0, 1, tomStart, 0);
1461 check_range(w, txtDoc, 0, 1, tomEnd, 0);
1462
1463 /* Large range */
1464 check_range(w, txtDoc, 0, 20, tomStart, 0);
1465 check_range(w, txtDoc, 0, 20, tomEnd, 1);
1466
1467 hres = ITextDocument_Range(txtDoc, 0, 0, &txtRge);
1468 ok(hres == S_OK, "got 0x%08lx\n", hres);
1469 release_interfaces(&w, &reOle, &txtDoc, NULL);
1470 hres = ITextRange_ScrollIntoView(txtRge, tomStart);
1471 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1472 ITextRange_Release(txtRge);
1473}
1474
1476{
1477 HWND w;
1478 IRichEditOle *reOle = NULL;
1479 ITextDocument *txtDoc = NULL;
1480 ITextSelection *txtSel = NULL;
1481 HRESULT hres;
1482 LONG pch;
1483 int first, lim;
1484 static const CHAR test_text1[] = "TestSomeText";
1485
1486 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
1487 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
1488
1489 first = 0; lim = 4;
1490 SendMessageA(w, EM_SETSEL, first, lim);
1491 pch = 0xdeadbeef;
1492 hres = ITextSelection_GetChar(txtSel, &pch);
1493 ok(hres == S_OK, "ITextSelection_GetChar\n");
1494 ok(pch == 'T', "got wrong char: %c\n", (char)pch);
1495
1496 first = 0; lim = 0;
1497 SendMessageA(w, EM_SETSEL, first, lim);
1498 pch = 0xdeadbeef;
1499 hres = ITextSelection_GetChar(txtSel, &pch);
1500 ok(hres == S_OK, "ITextSelection_GetChar\n");
1501 ok(pch == 'T', "got wrong char: %c\n", (char)pch);
1502
1503 first = 12; lim = 12;
1504 SendMessageA(w, EM_SETSEL, first, lim);
1505 pch = 0xdeadbeef;
1506 hres = ITextSelection_GetChar(txtSel, &pch);
1507 ok(hres == S_OK, "ITextSelection_GetChar\n");
1508 ok(pch == '\r', "got wrong char: %c\n", (char)pch);
1509
1510 first = 13; lim = 13;
1511 SendMessageA(w, EM_SETSEL, first, lim);
1512 pch = 0xdeadbeef;
1513 hres = ITextSelection_GetChar(txtSel, &pch);
1514 ok(hres == S_OK, "ITextSelection_GetChar\n");
1515 ok(pch == '\r', "got wrong char: %c\n", (char)pch);
1516
1517 hres = ITextSelection_GetChar(txtSel, NULL);
1518 ok(hres == E_INVALIDARG, "ITextSelection_GetChar\n");
1519
1520 release_interfaces(&w, &reOle, &txtDoc, NULL);
1521
1522 hres = ITextSelection_GetChar(txtSel, NULL);
1523 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1524
1525 hres = ITextSelection_GetChar(txtSel, &pch);
1526 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1527
1528 ITextSelection_Release(txtSel);
1529}
1530
1532{
1533 HWND w;
1534 IRichEditOle *reOle = NULL;
1535 ITextDocument *txtDoc = NULL;
1536 ITextRange *txtRge = NULL;
1537 HRESULT hres;
1538 int first, lim;
1539 LONG start, end;
1540 static const CHAR test_text1[] = "TestSomeText";
1541
1542 create_interfaces(&w, &reOle, &txtDoc, NULL);
1543 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
1544
1545 first = 1; lim = 6;
1546 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
1547 ok(hres == S_OK, "got 0x%08lx\n", hres);
1548 start = 0xdeadbeef;
1549 hres = ITextRange_GetStart(txtRge, &start);
1550 ok(hres == S_OK, "ITextRange_GetStart\n");
1551 ok(start == 1, "got wrong start value: %ld\n", start);
1552 end = 0xdeadbeef;
1553 hres = ITextRange_GetEnd(txtRge, &end);
1554 ok(hres == S_OK, "ITextRange_GetEnd\n");
1555 ok(end == 6, "got wrong end value: %ld\n", end);
1556 ITextRange_Release(txtRge);
1557
1558 first = 6; lim = 1;
1559 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
1560 ok(hres == S_OK, "got 0x%08lx\n", hres);
1561 start = 0xdeadbeef;
1562 hres = ITextRange_GetStart(txtRge, &start);
1563 ok(hres == S_OK, "ITextRange_GetStart\n");
1564 ok(start == 1, "got wrong start value: %ld\n", start);
1565 end = 0xdeadbeef;
1566 hres = ITextRange_GetEnd(txtRge, &end);
1567 ok(hres == S_OK, "ITextRange_GetEnd\n");
1568 ok(end == 6, "got wrong end value: %ld\n", end);
1569 ITextRange_Release(txtRge);
1570
1571 first = -1; lim = 13;
1572 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
1573 ok(hres == S_OK, "got 0x%08lx\n", hres);
1574 start = 0xdeadbeef;
1575 hres = ITextRange_GetStart(txtRge, &start);
1576 ok(hres == S_OK, "ITextRange_GetStart\n");
1577 ok(start == 0, "got wrong start value: %ld\n", start);
1578 end = 0xdeadbeef;
1579 hres = ITextRange_GetEnd(txtRge, &end);
1580 ok(hres == S_OK, "ITextRange_GetEnd\n");
1581 ok(end == 13, "got wrong end value: %ld\n", end);
1582 ITextRange_Release(txtRge);
1583
1584 first = 13; lim = 13;
1585 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
1586 ok(hres == S_OK, "got 0x%08lx\n", hres);
1587 start = 0xdeadbeef;
1588 hres = ITextRange_GetStart(txtRge, &start);
1589 ok(hres == S_OK, "ITextRange_GetStart\n");
1590 ok(start == 12, "got wrong start value: %ld\n", start);
1591 end = 0xdeadbeef;
1592 hres = ITextRange_GetEnd(txtRge, &end);
1593 ok(hres == S_OK, "ITextRange_GetEnd\n");
1594 ok(end == 12, "got wrong end value: %ld\n", end);
1595
1596 /* SetStart */
1597 hres = ITextRange_SetStart(txtRge, 0);
1598 ok(hres == S_OK, "got 0x%08lx\n", hres);
1599
1600 /* same value */
1601 hres = ITextRange_SetStart(txtRge, 0);
1602 ok(hres == S_FALSE, "got 0x%08lx\n", hres);
1603
1604 hres = ITextRange_SetStart(txtRge, 1);
1605 ok(hres == S_OK, "got 0x%08lx\n", hres);
1606
1607 /* negative resets to 0, return value is S_FALSE when
1608 position wasn't changed */
1609 hres = ITextRange_SetStart(txtRge, -1);
1610 ok(hres == S_OK, "got 0x%08lx\n", hres);
1611
1612 hres = ITextRange_SetStart(txtRge, -1);
1613 ok(hres == S_FALSE, "got 0x%08lx\n", hres);
1614
1615 hres = ITextRange_SetStart(txtRge, 0);
1616 ok(hres == S_FALSE, "got 0x%08lx\n", hres);
1617
1618 start = -1;
1619 hres = ITextRange_GetStart(txtRge, &start);
1620 ok(hres == S_OK, "got 0x%08lx\n", hres);
1621 ok(start == 0, "got %ld\n", start);
1622
1623 /* greater than initial end, but less than total char count */
1624 hres = ITextRange_SetStart(txtRge, 1);
1625 ok(hres == S_OK, "got 0x%08lx\n", hres);
1626
1627 hres = ITextRange_SetEnd(txtRge, 3);
1628 ok(hres == S_OK, "got 0x%08lx\n", hres);
1629
1630 hres = ITextRange_SetStart(txtRge, 10);
1631 ok(hres == S_OK, "got 0x%08lx\n", hres);
1632
1633 start = 0;
1634 hres = ITextRange_GetStart(txtRge, &start);
1635 ok(hres == S_OK, "got 0x%08lx\n", hres);
1636 ok(start == 10, "got %ld\n", start);
1637
1638 end = 0;
1639 hres = ITextRange_GetEnd(txtRge, &end);
1640 ok(hres == S_OK, "got 0x%08lx\n", hres);
1641 ok(end == 10, "got %ld\n", end);
1642
1643 /* more that total text length */
1644 hres = ITextRange_SetStart(txtRge, 50);
1645 ok(hres == S_OK, "got 0x%08lx\n", hres);
1646
1647 start = 0;
1648 hres = ITextRange_GetStart(txtRge, &start);
1649 ok(hres == S_OK, "got 0x%08lx\n", hres);
1650 ok(start == 12, "got %ld\n", start);
1651
1652 end = 0;
1653 hres = ITextRange_GetEnd(txtRge, &end);
1654 ok(hres == S_OK, "got 0x%08lx\n", hres);
1655 ok(end == 12, "got %ld\n", end);
1656
1657 /* SetEnd */
1658 hres = ITextRange_SetStart(txtRge, 0);
1659 ok(hres == S_OK, "got 0x%08lx\n", hres);
1660
1661 /* same value */
1662 hres = ITextRange_SetEnd(txtRge, 5);
1663 ok(hres == S_OK, "got 0x%08lx\n", hres);
1664
1665 hres = ITextRange_SetEnd(txtRge, 5);
1666 ok(hres == S_FALSE, "got 0x%08lx\n", hres);
1667
1668 /* negative resets to 0 */
1669 hres = ITextRange_SetEnd(txtRge, -1);
1670 ok(hres == S_OK, "got 0x%08lx\n", hres);
1671
1672 end = -1;
1673 hres = ITextRange_GetEnd(txtRge, &end);
1674 ok(hres == S_OK, "got 0x%08lx\n", hres);
1675 ok(end == 0, "got %ld\n", end);
1676
1677 start = -1;
1678 hres = ITextRange_GetStart(txtRge, &start);
1679 ok(hres == S_OK, "got 0x%08lx\n", hres);
1680 ok(start == 0, "got %ld\n", start);
1681
1682 /* greater than initial end, but less than total char count */
1683 hres = ITextRange_SetStart(txtRge, 3);
1684 ok(hres == S_OK, "got 0x%08lx\n", hres);
1685
1686 hres = ITextRange_SetEnd(txtRge, 1);
1687 ok(hres == S_OK, "got 0x%08lx\n", hres);
1688
1689 start = 0;
1690 hres = ITextRange_GetStart(txtRge, &start);
1691 ok(hres == S_OK, "got 0x%08lx\n", hres);
1692 ok(start == 1, "got %ld\n", start);
1693
1694 end = 0;
1695 hres = ITextRange_GetEnd(txtRge, &end);
1696 ok(hres == S_OK, "got 0x%08lx\n", hres);
1697 ok(end == 1, "got %ld\n", end);
1698
1699 /* more than total count */
1700 hres = ITextRange_SetEnd(txtRge, 50);
1701 ok(hres == S_OK, "got 0x%08lx\n", hres);
1702
1703 start = 0;
1704 hres = ITextRange_GetStart(txtRge, &start);
1705 ok(hres == S_OK, "got 0x%08lx\n", hres);
1706 ok(start == 1, "got %ld\n", start);
1707
1708 end = 0;
1709 hres = ITextRange_GetEnd(txtRge, &end);
1710 ok(hres == S_OK, "got 0x%08lx\n", hres);
1711 ok(end == 13, "got %ld\n", end);
1712
1713 /* zero */
1714 hres = ITextRange_SetEnd(txtRge, 0);
1715 ok(hres == S_OK, "got 0x%08lx\n", hres);
1716
1717 start = 0;
1718 hres = ITextRange_GetStart(txtRge, &start);
1719 ok(hres == S_OK, "got 0x%08lx\n", hres);
1720 ok(start == 0, "got %ld\n", start);
1721
1722 end = 0;
1723 hres = ITextRange_GetEnd(txtRge, &end);
1724 ok(hres == S_OK, "got 0x%08lx\n", hres);
1725 ok(end == 0, "got %ld\n", end);
1726
1727 release_interfaces(&w, &reOle, &txtDoc, NULL);
1728
1729 /* detached range */
1730 hres = ITextRange_SetStart(txtRge, 0);
1731 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1732
1733 hres = ITextRange_SetEnd(txtRge, 3);
1734 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1735
1736 hres = ITextRange_GetStart(txtRge, &start);
1737 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1738
1739 hres = ITextRange_GetStart(txtRge, NULL);
1740 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1741
1742 hres = ITextRange_GetEnd(txtRge, &end);
1743 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1744
1745 hres = ITextRange_GetEnd(txtRge, NULL);
1746 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1747
1748 ITextRange_Release(txtRge);
1749}
1750
1752{
1753 HWND w;
1754 IRichEditOle *reOle = NULL;
1755 ITextDocument *txtDoc = NULL;
1756 ITextSelection *txtSel = NULL;
1757 HRESULT hres;
1758 int first, lim;
1759 LONG start, end;
1760 static const CHAR test_text1[] = "TestSomeText";
1761
1762 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
1763 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
1764
1765 first = 2; lim = 5;
1766 SendMessageA(w, EM_SETSEL, first, lim);
1767 start = 0xdeadbeef;
1768 hres = ITextSelection_GetStart(txtSel, &start);
1769 ok(hres == S_OK, "ITextSelection_GetStart\n");
1770 ok(start == 2, "got wrong start value: %ld\n", start);
1771 end = 0xdeadbeef;
1772 hres = ITextSelection_GetEnd(txtSel, &end);
1773 ok(hres == S_OK, "ITextSelection_GetEnd\n");
1774 ok(end == 5, "got wrong end value: %ld\n", end);
1775
1776 first = 5; lim = 2;
1777 SendMessageA(w, EM_SETSEL, first, lim);
1778 start = 0xdeadbeef;
1779 hres = ITextSelection_GetStart(txtSel, &start);
1780 ok(hres == S_OK, "ITextSelection_GetStart\n");
1781 ok(start == 2, "got wrong start value: %ld\n", start);
1782 end = 0xdeadbeef;
1783 hres = ITextSelection_GetEnd(txtSel, &end);
1784 ok(hres == S_OK, "ITextSelection_GetEnd\n");
1785 ok(end == 5, "got wrong end value: %ld\n", end);
1786
1787 first = 0; lim = -1;
1788 SendMessageA(w, EM_SETSEL, first, lim);
1789 start = 0xdeadbeef;
1790 hres = ITextSelection_GetStart(txtSel, &start);
1791 ok(hres == S_OK, "ITextSelection_GetStart\n");
1792 ok(start == 0, "got wrong start value: %ld\n", start);
1793 end = 0xdeadbeef;
1794 hres = ITextSelection_GetEnd(txtSel, &end);
1795 ok(hres == S_OK, "ITextSelection_GetEnd\n");
1796 ok(end == 13, "got wrong end value: %ld\n", end);
1797
1798 first = 13; lim = 13;
1799 SendMessageA(w, EM_SETSEL, first, lim);
1800 start = 0xdeadbeef;
1801 hres = ITextSelection_GetStart(txtSel, &start);
1802 ok(hres == S_OK, "ITextSelection_GetStart\n");
1803 ok(start == 12, "got wrong start value: %ld\n", start);
1804 end = 0xdeadbeef;
1805 hres = ITextSelection_GetEnd(txtSel, &end);
1806 ok(hres == S_OK, "ITextSelection_GetEnd\n");
1807 ok(end == 12, "got wrong end value: %ld\n", end);
1808
1809 /* SetStart/SetEnd */
1810 hres = ITextSelection_SetStart(txtSel, 0);
1811 ok(hres == S_OK, "got 0x%08lx\n", hres);
1812
1813 /* same value */
1814 hres = ITextSelection_SetStart(txtSel, 0);
1815 ok(hres == S_FALSE, "got 0x%08lx\n", hres);
1816
1817 hres = ITextSelection_SetStart(txtSel, 1);
1818 ok(hres == S_OK, "got 0x%08lx\n", hres);
1819
1820 /* negative resets to 0, return value is S_FALSE when
1821 position wasn't changed */
1822 hres = ITextSelection_SetStart(txtSel, -1);
1823 ok(hres == S_OK, "got 0x%08lx\n", hres);
1824
1825 hres = ITextSelection_SetStart(txtSel, -1);
1826 ok(hres == S_FALSE, "got 0x%08lx\n", hres);
1827
1828 hres = ITextSelection_SetStart(txtSel, 0);
1829 ok(hres == S_FALSE, "got 0x%08lx\n", hres);
1830
1831 start = -1;
1832 hres = ITextSelection_GetStart(txtSel, &start);
1833 ok(hres == S_OK, "got 0x%08lx\n", hres);
1834 ok(start == 0, "got %ld\n", start);
1835
1836 /* greater than initial end, but less than total char count */
1837 hres = ITextSelection_SetStart(txtSel, 1);
1838 ok(hres == S_OK, "got 0x%08lx\n", hres);
1839
1840 hres = ITextSelection_SetEnd(txtSel, 3);
1841 ok(hres == S_OK, "got 0x%08lx\n", hres);
1842
1843 hres = ITextSelection_SetStart(txtSel, 10);
1844 ok(hres == S_OK, "got 0x%08lx\n", hres);
1845
1846 start = 0;
1847 hres = ITextSelection_GetStart(txtSel, &start);
1848 ok(hres == S_OK, "got 0x%08lx\n", hres);
1849 ok(start == 10, "got %ld\n", start);
1850
1851 end = 0;
1852 hres = ITextSelection_GetEnd(txtSel, &end);
1853 ok(hres == S_OK, "got 0x%08lx\n", hres);
1854 ok(end == 10, "got %ld\n", end);
1855
1856 /* more that total text length */
1857 hres = ITextSelection_SetStart(txtSel, 50);
1858 ok(hres == S_OK, "got 0x%08lx\n", hres);
1859
1860 start = 0;
1861 hres = ITextSelection_GetStart(txtSel, &start);
1862 ok(hres == S_OK, "got 0x%08lx\n", hres);
1863 ok(start == 12, "got %ld\n", start);
1864
1865 end = 0;
1866 hres = ITextSelection_GetEnd(txtSel, &end);
1867 ok(hres == S_OK, "got 0x%08lx\n", hres);
1868 ok(end == 12, "got %ld\n", end);
1869
1870 /* SetEnd */
1871 hres = ITextSelection_SetStart(txtSel, 0);
1872 ok(hres == S_OK, "got 0x%08lx\n", hres);
1873
1874 /* same value */
1875 hres = ITextSelection_SetEnd(txtSel, 5);
1876 ok(hres == S_OK, "got 0x%08lx\n", hres);
1877
1878 hres = ITextSelection_SetEnd(txtSel, 5);
1879 ok(hres == S_FALSE, "got 0x%08lx\n", hres);
1880
1881 /* negative resets to 0 */
1882 hres = ITextSelection_SetEnd(txtSel, -1);
1883 ok(hres == S_OK, "got 0x%08lx\n", hres);
1884
1885 end = -1;
1886 hres = ITextSelection_GetEnd(txtSel, &end);
1887 ok(hres == S_OK, "got 0x%08lx\n", hres);
1888 ok(end == 0, "got %ld\n", end);
1889
1890 start = -1;
1891 hres = ITextSelection_GetStart(txtSel, &start);
1892 ok(hres == S_OK, "got 0x%08lx\n", hres);
1893 ok(start == 0, "got %ld\n", start);
1894
1895 /* greater than initial end, but less than total char count */
1896 hres = ITextSelection_SetStart(txtSel, 3);
1897 ok(hres == S_OK, "got 0x%08lx\n", hres);
1898
1899 hres = ITextSelection_SetEnd(txtSel, 1);
1900 ok(hres == S_OK, "got 0x%08lx\n", hres);
1901
1902 start = 0;
1903 hres = ITextSelection_GetStart(txtSel, &start);
1904 ok(hres == S_OK, "got 0x%08lx\n", hres);
1905 ok(start == 1, "got %ld\n", start);
1906
1907 end = 0;
1908 hres = ITextSelection_GetEnd(txtSel, &end);
1909 ok(hres == S_OK, "got 0x%08lx\n", hres);
1910 ok(end == 1, "got %ld\n", end);
1911
1912 /* more than total count */
1913 hres = ITextSelection_SetEnd(txtSel, 50);
1914 ok(hres == S_OK, "got 0x%08lx\n", hres);
1915
1916 start = 0;
1917 hres = ITextSelection_GetStart(txtSel, &start);
1918 ok(hres == S_OK, "got 0x%08lx\n", hres);
1919 ok(start == 1, "got %ld\n", start);
1920
1921 end = 0;
1922 hres = ITextSelection_GetEnd(txtSel, &end);
1923 ok(hres == S_OK, "got 0x%08lx\n", hres);
1924 ok(end == 13, "got %ld\n", end);
1925
1926 /* zero */
1927 hres = ITextSelection_SetEnd(txtSel, 0);
1928 ok(hres == S_OK, "got 0x%08lx\n", hres);
1929
1930 start = 0;
1931 hres = ITextSelection_GetStart(txtSel, &start);
1932 ok(hres == S_OK, "got 0x%08lx\n", hres);
1933 ok(start == 0, "got %ld\n", start);
1934
1935 end = 0;
1936 hres = ITextSelection_GetEnd(txtSel, &end);
1937 ok(hres == S_OK, "got 0x%08lx\n", hres);
1938 ok(end == 0, "got %ld\n", end);
1939
1940 release_interfaces(&w, &reOle, &txtDoc, NULL);
1941
1942 /* detached selection */
1943 hres = ITextSelection_GetStart(txtSel, NULL);
1944 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1945
1946 hres = ITextSelection_GetStart(txtSel, &start);
1947 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1948
1949 hres = ITextSelection_GetEnd(txtSel, NULL);
1950 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1951
1952 hres = ITextSelection_GetEnd(txtSel, &end);
1953 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1954
1955 ITextSelection_Release(txtSel);
1956}
1957
1959{
1960 HWND w;
1961 IRichEditOle *reOle = NULL;
1962 ITextDocument *txtDoc = NULL;
1963 ITextRange *txtRge = NULL;
1964 ITextRange *txtRgeDup = NULL;
1965 HRESULT hres;
1966 LONG first, lim, start, end;
1967 static const CHAR test_text1[] = "TestSomeText";
1968
1969 create_interfaces(&w, &reOle, &txtDoc, NULL);
1970 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
1971 first = 0; lim = 4;
1972 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
1973 ok(hres == S_OK, "ITextDocument_Range fails 0x%lx.\n", hres);
1974
1975 hres = ITextRange_GetDuplicate(txtRge, &txtRgeDup);
1976 ok(hres == S_OK, "ITextRange_GetDuplicate\n");
1977 ok(txtRgeDup != txtRge, "A new pointer should be returned\n");
1978 hres = ITextRange_GetStart(txtRgeDup, &start);
1979 ok(hres == S_OK, "got 0x%08lx\n", hres);
1980 ok(start == first, "got wrong value: %ld\n", start);
1981 hres = ITextRange_GetEnd(txtRgeDup, &end);
1982 ok(hres == S_OK, "got 0x%08lx\n", hres);
1983 ok(end == lim, "got wrong value: %ld\n", end);
1984
1985 ITextRange_Release(txtRgeDup);
1986
1987 hres = ITextRange_GetDuplicate(txtRge, NULL);
1988 ok(hres == E_INVALIDARG, "ITextRange_GetDuplicate\n");
1989
1990 release_interfaces(&w, &reOle, &txtDoc, NULL);
1991
1992 hres = ITextRange_GetDuplicate(txtRge, NULL);
1993 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1994
1995 hres = ITextRange_GetDuplicate(txtRge, &txtRgeDup);
1996 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
1997
1998 ITextRange_Release(txtRge);
1999}
2000
2002{
2003 HWND w;
2004 IRichEditOle *reOle = NULL;
2005 ITextDocument *txtDoc = NULL;
2006 ITextRange *txtRge = NULL;
2007 HRESULT hres;
2008 LONG first, lim, start, end;
2009 static const CHAR test_text1[] = "TestSomeText";
2010
2011 create_interfaces(&w, &reOle, &txtDoc, NULL);
2012 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
2013
2014 first = 4; lim = 8;
2015 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
2016 ok(hres == S_OK, "got 0x%08lx\n", hres);
2017 hres = ITextRange_Collapse(txtRge, tomTrue);
2018 ok(hres == S_OK, "ITextRange_Collapse\n");
2019 hres = ITextRange_GetStart(txtRge, &start);
2020 ok(hres == S_OK, "got 0x%08lx\n", hres);
2021 ok(start == 4, "got wrong start value: %ld\n", start);
2022 hres = ITextRange_GetEnd(txtRge, &end);
2023 ok(hres == S_OK, "got 0x%08lx\n", hres);
2024 ok(end == 4, "got wrong end value: %ld\n", end);
2025 ITextRange_Release(txtRge);
2026
2027 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
2028 ok(hres == S_OK, "got 0x%08lx\n", hres);
2029 hres = ITextRange_Collapse(txtRge, tomStart);
2030 ok(hres == S_OK, "ITextRange_Collapse\n");
2031 hres = ITextRange_GetStart(txtRge, &start);
2032 ok(hres == S_OK, "got 0x%08lx\n", hres);
2033 ok(start == 4, "got wrong start value: %ld\n", start);
2034 hres = ITextRange_GetEnd(txtRge, &end);
2035 ok(hres == S_OK, "got 0x%08lx\n", hres);
2036 ok(end == 4, "got wrong end value: %ld\n", end);
2037 ITextRange_Release(txtRge);
2038
2039 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
2040 ok(hres == S_OK, "got 0x%08lx\n", hres);
2041 hres = ITextRange_Collapse(txtRge, tomFalse);
2042 ok(hres == S_OK, "ITextRange_Collapse\n");
2043 hres = ITextRange_GetStart(txtRge, &start);
2044 ok(hres == S_OK, "got 0x%08lx\n", hres);
2045 ok(start == 8, "got wrong start value: %ld\n", start);
2046 hres = ITextRange_GetEnd(txtRge, &end);
2047 ok(hres == S_OK, "got 0x%08lx\n", hres);
2048 ok(end == 8, "got wrong end value: %ld\n", end);
2049 ITextRange_Release(txtRge);
2050
2051 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
2052 ok(hres == S_OK, "got 0x%08lx\n", hres);
2053 hres = ITextRange_Collapse(txtRge, tomEnd);
2054 ok(hres == S_OK, "ITextRange_Collapse\n");
2055 hres = ITextRange_GetStart(txtRge, &start);
2056 ok(hres == S_OK, "got 0x%08lx\n", hres);
2057 ok(start == 8, "got wrong start value: %ld\n", start);
2058 hres = ITextRange_GetEnd(txtRge, &end);
2059 ok(hres == S_OK, "got 0x%08lx\n", hres);
2060 ok(end == 8, "got wrong end value: %ld\n", end);
2061 ITextRange_Release(txtRge);
2062
2063 /* tomStart is the default */
2064 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
2065 ok(hres == S_OK, "got 0x%08lx\n", hres);
2066 hres = ITextRange_Collapse(txtRge, 256);
2067 ok(hres == S_OK, "ITextRange_Collapse\n");
2068 hres = ITextRange_GetStart(txtRge, &start);
2069 ok(hres == S_OK, "got 0x%08lx\n", hres);
2070 ok(start == 4, "got wrong start value: %ld\n", start);
2071 hres = ITextRange_GetEnd(txtRge, &end);
2072 ok(hres == S_OK, "got 0x%08lx\n", hres);
2073 ok(end == 4, "got wrong end value: %ld\n", end);
2074 ITextRange_Release(txtRge);
2075
2076 first = 6; lim = 6;
2077 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
2078 ok(hres == S_OK, "got 0x%08lx\n", hres);
2079 hres = ITextRange_Collapse(txtRge, tomEnd);
2080 ok(hres == S_FALSE, "ITextRange_Collapse\n");
2081 hres = ITextRange_GetStart(txtRge, &start);
2082 ok(hres == S_OK, "got 0x%08lx\n", hres);
2083 ok(start == 6, "got wrong start value: %ld\n", start);
2084 hres = ITextRange_GetEnd(txtRge, &end);
2085 ok(hres == S_OK, "got 0x%08lx\n", hres);
2086 ok(end == 6, "got wrong end value: %ld\n", end);
2087 ITextRange_Release(txtRge);
2088
2089 first = 8; lim = 8;
2090 hres = ITextDocument_Range(txtDoc, first, lim, &txtRge);
2091 ok(hres == S_OK, "got 0x%08lx\n", hres);
2092 hres = ITextRange_Collapse(txtRge, tomStart);
2093 ok(hres == S_FALSE, "ITextRange_Collapse\n");
2094 hres = ITextRange_GetStart(txtRge, &start);
2095 ok(hres == S_OK, "got 0x%08lx\n", hres);
2096 ok(start == 8, "got wrong start value: %ld\n", start);
2097 hres = ITextRange_GetEnd(txtRge, &end);
2098 ok(hres == S_OK, "got 0x%08lx\n", hres);
2099 ok(end == 8, "got wrong end value: %ld\n", end);
2100
2101 release_interfaces(&w, &reOle, &txtDoc, NULL);
2102
2103 hres = ITextRange_Collapse(txtRge, tomStart);
2104 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
2105
2106 hres = ITextRange_Collapse(txtRge, tomUndefined);
2107 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
2108
2109 ITextRange_Release(txtRge);
2110}
2111
2113{
2114 HWND w;
2115 IRichEditOle *reOle = NULL;
2116 ITextDocument *txtDoc = NULL;
2117 ITextSelection *txtSel = NULL;
2118 HRESULT hres;
2119 LONG first, lim, start, end;
2120 static const CHAR test_text1[] = "TestSomeText";
2121
2122 create_interfaces(&w, &reOle, &txtDoc, &txtSel);
2123 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
2124
2125 first = 4; lim = 8;
2126 SendMessageA(w, EM_SETSEL, first, lim);
2127 hres = ITextSelection_Collapse(txtSel, tomTrue);
2128 ok(hres == S_OK, "ITextSelection_Collapse\n");
2130 ok(start == 4, "got wrong start value: %ld\n", start);
2131 ok(end == 4, "got wrong end value: %ld\n", end);
2132
2133 SendMessageA(w, EM_SETSEL, first, lim);
2134 hres = ITextSelection_Collapse(txtSel, tomStart);
2135 ok(hres == S_OK, "ITextSelection_Collapse\n");
2137 ok(start == 4, "got wrong start value: %ld\n", start);
2138 ok(end == 4, "got wrong end value: %ld\n", end);
2139
2140 SendMessageA(w, EM_SETSEL, first, lim);
2141 hres = ITextSelection_Collapse(txtSel, tomFalse);
2142 ok(hres == S_OK, "ITextSelection_Collapse\n");
2144 ok(start == 8, "got wrong start value: %ld\n", start);
2145 ok(end == 8, "got wrong end value: %ld\n", end);
2146
2147 SendMessageA(w, EM_SETSEL, first, lim);
2148 hres = ITextSelection_Collapse(txtSel, tomEnd);
2149 ok(hres == S_OK, "ITextSelection_Collapse\n");
2151 ok(start == 8, "got wrong start value: %ld\n", start);
2152 ok(end == 8, "got wrong end value: %ld\n", end);
2153
2154 /* tomStart is the default */
2155 SendMessageA(w, EM_SETSEL, first, lim);
2156 hres = ITextSelection_Collapse(txtSel, 256);
2157 ok(hres == S_OK, "ITextSelection_Collapse\n");
2159 ok(start == 4, "got wrong start value: %ld\n", start);
2160 ok(end == 4, "got wrong end value: %ld\n", end);
2161
2162 first = 6; lim = 6;
2163 SendMessageA(w, EM_SETSEL, first, lim);
2164 hres = ITextSelection_Collapse(txtSel, tomEnd);
2165 ok(hres == S_FALSE, "ITextSelection_Collapse\n");
2167 ok(start == 6, "got wrong start value: %ld\n", start);
2168 ok(end == 6, "got wrong end value: %ld\n", end);
2169
2170 first = 8; lim = 8;
2171 SendMessageA(w, EM_SETSEL, first, lim);
2172 hres = ITextSelection_Collapse(txtSel, tomStart);
2173 ok(hres == S_FALSE, "ITextSelection_Collapse\n");
2175 ok(start == 8, "got wrong start value: %ld\n", start);
2176 ok(end == 8, "got wrong end value: %ld\n", end);
2177
2178 release_interfaces(&w, &reOle, &txtDoc, NULL);
2179
2180 hres = ITextSelection_Collapse(txtSel, tomStart);
2181 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
2182
2183 hres = ITextSelection_Collapse(txtSel, tomUndefined);
2184 ok(hres == CO_E_RELEASED, "got 0x%08lx\n", hres);
2185
2186 ITextSelection_Release(txtSel);
2187}
2188
2189static void test_GetClientSite(void)
2190{
2191 HWND w;
2192 IRichEditOle *reOle = NULL, *reOle1 = NULL;
2193 ITextDocument *txtDoc = NULL;
2194 IOleClientSite *clientSite = NULL, *clientSite1 = NULL, *clientSite2 = NULL;
2195 IOleWindow *oleWin = NULL, *oleWin1 = NULL;
2196 IOleInPlaceSite *olePlace = NULL, *olePlace1 = NULL;
2197 HRESULT hres;
2198 LONG refcount1, refcount2;
2199
2200 create_interfaces(&w, &reOle, &txtDoc, NULL);
2201 hres = IRichEditOle_GetClientSite(reOle, &clientSite);
2202 ok(hres == S_OK, "IRichEditOle_QueryInterface: 0x%08lx\n", hres);
2203 EXPECT_REF(clientSite, 1);
2204
2205 hres = IOleClientSite_QueryInterface(clientSite, &IID_IRichEditOle, (void **)&reOle1);
2206 ok(hres == E_NOINTERFACE, "IOleClientSite_QueryInterface: %lx\n", hres);
2207
2208 hres = IRichEditOle_GetClientSite(reOle, &clientSite1);
2209 ok(hres == S_OK, "got 0x%08lx\n", hres);
2210 ok(clientSite != clientSite1, "got %p, %p\n", clientSite, clientSite1);
2211 IOleClientSite_Release(clientSite1);
2212
2213 hres = IOleClientSite_QueryInterface(clientSite, &IID_IOleClientSite, (void **)&clientSite1);
2214 ok(hres == S_OK, "IOleClientSite_QueryInterface: 0x%08lx\n", hres);
2215 ok(clientSite == clientSite1, "Should not return a new pointer.\n");
2216 EXPECT_REF(clientSite, 2);
2217
2218 /* IOleWindow interface */
2219 hres = IOleClientSite_QueryInterface(clientSite, &IID_IOleWindow, (void **)&oleWin);
2220 ok(hres == S_OK, "IOleClientSite_QueryInterface: 0x%08lx\n", hres);
2221 refcount1 = get_refcount((IUnknown *)clientSite);
2222 refcount2 = get_refcount((IUnknown *)oleWin);
2223 ok(refcount1 == refcount2, "got wrong ref count.\n");
2224
2225 hres = IOleClientSite_QueryInterface(clientSite, &IID_IOleWindow, (void **)&oleWin1);
2226 ok(hres == S_OK, "IOleClientSite_QueryInterface: 0x%08lx\n", hres);
2227 ok(oleWin == oleWin1, "Should not return a new pointer.\n");
2228 refcount1 = get_refcount((IUnknown *)clientSite);
2229 refcount2 = get_refcount((IUnknown *)oleWin);
2230 ok(refcount1 == refcount2, "got wrong ref count.\n");
2231
2232 hres = IOleWindow_QueryInterface(oleWin, &IID_IOleClientSite, (void **)&clientSite2);
2233 ok(hres == S_OK, "IOleWindow_QueryInterface: 0x%08lx\n", hres);
2234 ok(clientSite2 == clientSite1, "got wrong pointer\n");
2235
2236 /* IOleInPlaceSite interface */
2237 hres = IOleClientSite_QueryInterface(clientSite, &IID_IOleInPlaceSite, (void **)&olePlace);
2238 ok(hres == S_OK, "IOleClientSite_QueryInterface: 0x%08lx\n", hres);
2239 refcount1 = get_refcount((IUnknown *)olePlace);
2240 refcount2 = get_refcount((IUnknown *)clientSite);
2241 ok(refcount1 == refcount2, "got wrong ref count.\n");
2242
2243 hres = IOleClientSite_QueryInterface(clientSite, &IID_IOleInPlaceSite, (void **)&olePlace1);
2244 ok(hres == S_OK, "IOleClientSite_QueryInterface: 0x%08lx\n", hres);
2245 ok(olePlace == olePlace1, "Should not return a new pointer.\n");
2246 IOleInPlaceSite_Release(olePlace1);
2247
2248 hres = IOleWindow_QueryInterface(oleWin, &IID_IOleInPlaceSite, (void **)&olePlace1);
2249 ok(hres == S_OK, "IOleWindow_QueryInterface: 0x%08lx\n", hres);
2250 refcount1 = get_refcount((IUnknown *)olePlace1);
2251 refcount2 = get_refcount((IUnknown *)oleWin);
2252 ok(refcount1 == refcount2, "got wrong ref count.\n");
2253
2254 IOleInPlaceSite_Release(olePlace1);
2255 IOleInPlaceSite_Release(olePlace);
2256 IOleWindow_Release(oleWin1);
2257 IOleWindow_Release(oleWin);
2258 IOleClientSite_Release(clientSite2);
2259 IOleClientSite_Release(clientSite1);
2260 IOleClientSite_Release(clientSite);
2261 release_interfaces(&w, &reOle, &txtDoc, NULL);
2262}
2263
2265{
2266 HWND w;
2267 IRichEditOle *reOle = NULL;
2268 ITextDocument *txtDoc = NULL;
2269 IOleClientSite *clientSite = NULL;
2270 IOleWindow *oleWin = NULL;
2271 HRESULT hres;
2272 HWND hwnd;
2273
2274 create_interfaces(&w, &reOle, &txtDoc, NULL);
2275 hres = IRichEditOle_GetClientSite(reOle, &clientSite);
2276 ok(hres == S_OK, "IRichEditOle_QueryInterface: 0x%08lx\n", hres);
2277
2278 hres = IOleClientSite_QueryInterface(clientSite, &IID_IOleWindow, (void **)&oleWin);
2279 ok(hres == S_OK, "IOleClientSite_QueryInterface: 0x%08lx\n", hres);
2280 hres = IOleWindow_GetWindow(oleWin, &hwnd);
2281 ok(hres == S_OK, "IOleClientSite_GetWindow: 0x%08lx\n", hres);
2282 ok(w == hwnd, "got wrong pointer\n");
2283
2284 hres = IOleWindow_GetWindow(oleWin, NULL);
2285 ok(hres == E_INVALIDARG, "IOleClientSite_GetWindow: 0x%08lx\n", hres);
2286
2287 IOleWindow_Release(oleWin);
2288 IOleClientSite_Release(clientSite);
2289 release_interfaces(&w, &reOle, &txtDoc, NULL);
2290}
2291
2293{
2294 HWND w;
2295 IRichEditOle *reOle = NULL;
2296 ITextDocument *txtDoc = NULL;
2297 IOleClientSite *clientSite = NULL;
2298 IOleInPlaceSite *olePlace = NULL;
2299 HRESULT hres;
2300 HWND hwnd;
2301
2302 create_interfaces(&w, &reOle, &txtDoc, NULL);
2303 hres = IRichEditOle_GetClientSite(reOle, &clientSite);
2304 ok(hres == S_OK, "IRichEditOle_QueryInterface: 0x%08lx\n", hres);
2305
2306 hres = IOleClientSite_QueryInterface(clientSite, &IID_IOleInPlaceSite, (void **)&olePlace);
2307 ok(hres == S_OK, "IOleClientSite_QueryInterface: 0x%08lx\n", hres);
2308 hres = IOleInPlaceSite_GetWindow(olePlace, &hwnd);
2309 ok(hres == S_OK, "IOleInPlaceSite_GetWindow: 0x%08lx\n", hres);
2310 ok(w == hwnd, "got wrong pointer.\n");
2311
2312 hres = IOleInPlaceSite_GetWindow(olePlace, NULL);
2313 ok(hres == E_INVALIDARG, "IOleInPlaceSite_GetWindow: 0x%08lx\n", hres);
2314
2315 IOleInPlaceSite_Release(olePlace);
2316 IOleClientSite_Release(clientSite);
2317 release_interfaces(&w, &reOle, &txtDoc, NULL);
2318}
2319
2320static void test_GetFont(void)
2321{
2322 static const CHAR test_text1[] = "TestSomeText";
2323 IRichEditOle *reOle = NULL;
2324 ITextDocument *doc = NULL;
2327 ITextFont *font, *font2;
2329 LONG value;
2330 float size;
2331 HRESULT hr;
2332 HWND hwnd;
2333 BOOL ret;
2334
2335 create_interfaces(&hwnd, &reOle, &doc, NULL);
2336 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
2337
2338 hr = ITextDocument_GetSelection(doc, &selection);
2339 ok(hr == S_OK, "got 0x%08lx\n", hr);
2340 hr = ITextSelection_GetFont(selection, &font);
2341 ok(hr == S_OK, "got 0x%08lx\n", hr);
2342 hr = ITextSelection_GetFont(selection, &font2);
2343 ok(hr == S_OK, "got 0x%08lx\n", hr);
2344 ok(font != font2, "got %p, %p\n", font, font2);
2345 ITextFont_Release(font2);
2346 ITextFont_Release(font);
2347 ITextSelection_Release(selection);
2348
2349 EXPECT_REF(reOle, 3);
2350 EXPECT_REF(doc, 3);
2351
2352 hr = ITextDocument_Range(doc, 0, 4, &range);
2353 ok(hr == S_OK, "got 0x%08lx\n", hr);
2354
2355 EXPECT_REF(reOle, 3);
2356 EXPECT_REF(doc, 3);
2357 EXPECT_REF(range, 1);
2358
2359 hr = ITextRange_GetFont(range, NULL);
2360 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2361
2362 hr = ITextRange_GetFont(range, &font);
2363 ok(hr == S_OK, "got 0x%08lx\n", hr);
2364
2365 EXPECT_REF(reOle, 3);
2366 EXPECT_REF(doc, 3);
2367 EXPECT_REF(range, 2);
2368 EXPECT_REF(font, 1);
2369
2370 hr = ITextRange_GetFont(range, &font2);
2371 ok(hr == S_OK, "got 0x%08lx\n", hr);
2372 ok(font != font2, "got %p, %p\n", font, font2);
2373
2374 EXPECT_REF(reOle, 3);
2375 EXPECT_REF(doc, 3);
2376 EXPECT_REF(range, 3);
2377 EXPECT_REF(font, 1);
2378 EXPECT_REF(font2, 1);
2379
2380 ITextFont_Release(font2);
2381
2382 /* set different font style within a range */
2383 hr = ITextFont_GetItalic(font, NULL);
2384 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2385
2386 hr = ITextFont_GetSize(font, NULL);
2387 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2388
2389 size = 0.0;
2390 hr = ITextFont_GetSize(font, &size);
2391 ok(hr == S_OK, "got 0x%08lx\n", hr);
2392 ok(size > 0.0, "size %.2f\n", size);
2393
2394 value = 0;
2395 hr = ITextFont_GetLanguageID(font, &value);
2396 ok(hr == S_OK, "got 0x%08lx\n", hr);
2397 ok(value == GetSystemDefaultLCID(), "got lcid %lx, user lcid %lx\n", value,
2399
2400 /* range is non-italic */
2401 value = tomTrue;
2402 hr = ITextFont_GetItalic(font, &value);
2403 ok(hr == S_OK, "got 0x%08lx\n", hr);
2404 ok(value == tomFalse, "got %ld\n", value);
2405
2406 cf.cbSize = sizeof(CHARFORMAT2A);
2407 cf.dwMask = CFM_ITALIC|CFM_SIZE;
2408 cf.dwEffects = CFE_ITALIC;
2409 cf.yHeight = 24.0;
2410
2411 SendMessageA(hwnd, EM_SETSEL, 2, 3);
2413 ok(ret, "got %d\n", ret);
2414
2415 /* now range is partially italicized */
2416 value = tomFalse;
2417 hr = ITextFont_GetItalic(font, &value);
2418 ok(hr == S_OK, "got 0x%08lx\n", hr);
2419 ok(value == tomUndefined, "got %ld\n", value);
2420
2421 size = 0.0;
2422 hr = ITextFont_GetSize(font, &size);
2423 ok(hr == S_OK, "got 0x%08lx\n", hr);
2424 ok(size == tomUndefined, "size %.2f\n", size);
2425
2426 ITextFont_Release(font);
2427 release_interfaces(&hwnd, &reOle, &doc, NULL);
2428
2429 hr = ITextRange_GetFont(range, NULL);
2430 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
2431
2432 hr = ITextRange_GetFont(range, &font2);
2433 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
2434
2435 ITextRange_Release(range);
2436}
2437
2438static void test_GetPara(void)
2439{
2440 static const CHAR test_text1[] = "TestSomeText";
2441 IRichEditOle *reOle = NULL;
2442 ITextDocument *doc = NULL;
2445 ITextPara *para, *para2;
2446 HRESULT hr;
2447 HWND hwnd;
2448
2449 create_interfaces(&hwnd, &reOle, &doc, &selection);
2450 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
2451
2452 EXPECT_REF(reOle, 3);
2453 EXPECT_REF(doc, 3);
2454
2455 hr = ITextDocument_Range(doc, 0, 4, &range);
2456 ok(hr == S_OK, "got 0x%08lx\n", hr);
2457
2458 EXPECT_REF(reOle, 3);
2459 EXPECT_REF(doc, 3);
2460 EXPECT_REF(range, 1);
2461
2462 hr = ITextRange_GetPara(range, NULL);
2463 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2464
2465 hr = ITextRange_GetPara(range, &para);
2466 ok(hr == S_OK, "got 0x%08lx\n", hr);
2467
2468 EXPECT_REF(reOle, 3);
2469 EXPECT_REF(doc, 3);
2470 EXPECT_REF(range, 2);
2471 EXPECT_REF(para, 1);
2472
2473 hr = ITextRange_GetPara(range, &para2);
2474 ok(hr == S_OK, "got 0x%08lx\n", hr);
2475 ok(para != para2, "got %p, %p\n", para, para2);
2476
2477 EXPECT_REF(reOle, 3);
2478 EXPECT_REF(doc, 3);
2479 EXPECT_REF(range, 3);
2480 EXPECT_REF(para, 1);
2481 EXPECT_REF(para2, 1);
2482
2483 ITextPara_Release(para);
2484 ITextPara_Release(para2);
2485
2486 EXPECT_REF(reOle, 3);
2487 EXPECT_REF(doc, 3);
2489
2490 hr = ITextSelection_GetPara(selection, &para);
2491 ok(hr == S_OK, "got 0x%08lx\n", hr);
2492
2493 EXPECT_REF(reOle, 3);
2494 EXPECT_REF(doc, 3);
2496 EXPECT_REF(para, 1);
2497
2498 hr = ITextSelection_GetPara(selection, &para2);
2499 ok(hr == S_OK, "got 0x%08lx\n", hr);
2500 ok(para != para2, "got %p, %p\n", para, para2);
2501
2502 ITextPara_Release(para);
2503 ITextPara_Release(para2);
2504 release_interfaces(&hwnd, &reOle, &doc, NULL);
2505
2506 hr = ITextRange_GetPara(range, NULL);
2507 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
2508
2509 hr = ITextRange_GetPara(range, &para);
2510 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
2511
2512 hr = ITextSelection_GetPara(selection, NULL);
2513 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
2514
2515 hr = ITextSelection_GetPara(selection, &para);
2516 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
2517
2518 ITextSelection_Release(selection);
2519 ITextRange_Release(range);
2520}
2521
2522static void test_dispatch(void)
2523{
2524 static const WCHAR testnameW[] = {'G','e','t','T','e','x','t',0};
2525 static const WCHAR testname2W[] = {'T','e','x','t',0};
2526 IRichEditOle *reOle = NULL;
2527 ITextDocument *doc = NULL;
2529 WCHAR *nameW;
2530 DISPID dispid;
2531 HRESULT hr;
2532 UINT count;
2533 HWND hwnd;
2534
2535 create_interfaces(&hwnd, &reOle, &doc, NULL);
2536
2537 range = NULL;
2538 hr = ITextDocument_Range(doc, 0, 0, &range);
2539 ok(hr == S_OK, "got 0x%08lx\n", hr);
2540 ok(range != NULL, "got %p\n", range);
2541
2542 dispid = 123;
2543 nameW = (WCHAR*)testnameW;
2544 hr = ITextRange_GetIDsOfNames(range, &IID_NULL, &nameW, 1, LOCALE_USER_DEFAULT, &dispid);
2545 ok(hr == DISP_E_UNKNOWNNAME, "got 0x%08lx\n", hr);
2546 ok(dispid == DISPID_UNKNOWN, "got %ld\n", dispid);
2547
2548 dispid = 123;
2549 nameW = (WCHAR*)testname2W;
2550 hr = ITextRange_GetIDsOfNames(range, &IID_NULL, &nameW, 1, LOCALE_USER_DEFAULT, &dispid);
2551 ok(hr == S_OK, "got 0x%08lx\n", hr);
2552 ok(dispid == DISPID_VALUE, "got %ld\n", dispid);
2553
2554 release_interfaces(&hwnd, &reOle, &doc, NULL);
2555
2556 /* try dispatch methods on detached range */
2557 hr = ITextRange_GetTypeInfoCount(range, &count);
2558 ok(hr == S_OK, "got 0x%08lx\n", hr);
2559
2560 dispid = 123;
2561 nameW = (WCHAR*)testname2W;
2562 hr = ITextRange_GetIDsOfNames(range, &IID_NULL, &nameW, 1, LOCALE_USER_DEFAULT, &dispid);
2563 ok(hr == S_OK, "got 0x%08lx\n", hr);
2564 ok(dispid == DISPID_VALUE, "got %ld\n", dispid);
2565
2566 ITextRange_Release(range);
2567}
2568
2570{
2571 HRESULT hr, hrexp = duplicate ? S_OK : CO_E_RELEASED;
2572 LONG value;
2573 float size;
2574 BSTR str;
2575
2576 hr = ITextFont_GetBold(font, NULL);
2577 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2578
2579 hr = ITextFont_GetBold(font, &value);
2580 ok(hr == hrexp, "got 0x%08lx\n", hr);
2581
2582 hr = ITextFont_GetForeColor(font, NULL);
2583 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2584
2585 hr = ITextFont_GetForeColor(font, &value);
2586 ok(hr == hrexp, "got 0x%08lx\n", hr);
2587
2588 hr = ITextFont_GetItalic(font, NULL);
2589 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2590
2591 hr = ITextFont_GetItalic(font, &value);
2592 ok(hr == hrexp, "got 0x%08lx\n", hr);
2593
2594 hr = ITextFont_GetLanguageID(font, NULL);
2595 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2596
2597 hr = ITextFont_GetLanguageID(font, &value);
2598 ok(hr == hrexp, "got 0x%08lx\n", hr);
2599
2600 hr = ITextFont_GetName(font, NULL);
2601 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2602
2603 hr = ITextFont_GetName(font, &str);
2604 ok(hr == hrexp, "got 0x%08lx\n", hr);
2605
2606 hr = ITextFont_GetSize(font, NULL);
2607 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2608
2609 hr = ITextFont_GetSize(font, &size);
2610 ok(hr == hrexp, "got 0x%08lx\n", hr);
2611
2612 hr = ITextFont_GetStrikeThrough(font, NULL);
2613 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2614
2615 hr = ITextFont_GetStrikeThrough(font, &value);
2616 ok(hr == hrexp, "got 0x%08lx\n", hr);
2617
2618 hr = ITextFont_GetSubscript(font, NULL);
2619 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2620
2621 hr = ITextFont_GetSubscript(font, &value);
2622 ok(hr == hrexp, "got 0x%08lx\n", hr);
2623
2624 hr = ITextFont_GetSuperscript(font, NULL);
2625 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2626
2627 hr = ITextFont_GetSuperscript(font, &value);
2628 ok(hr == hrexp, "got 0x%08lx\n", hr);
2629
2630 hr = ITextFont_GetUnderline(font, NULL);
2631 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2632
2633 hr = ITextFont_GetUnderline(font, &value);
2634 ok(hr == hrexp, "got 0x%08lx\n", hr);
2635}
2636
2638{
2639 float valuef;
2640 LONG value;
2641 HRESULT hr;
2642 BSTR str;
2643
2645 hr = ITextFont_GetAllCaps(font, &value);
2646 ok(hr == S_OK, "got 0x%08lx\n", hr);
2647 ok(value == tomFalse, "got %ld\n", value);
2648
2650 hr = ITextFont_GetAnimation(font, &value);
2651 ok(hr == S_OK, "got 0x%08lx\n", hr);
2652 ok(value == tomFalse, "got %ld\n", value);
2653
2655 hr = ITextFont_GetBackColor(font, &value);
2656 ok(hr == S_OK, "got 0x%08lx\n", hr);
2657 ok(value == tomAutoColor, "got %ld\n", value);
2658
2660 hr = ITextFont_GetBold(font, &value);
2661 ok(hr == S_OK, "got 0x%08lx\n", hr);
2662 ok(value == tomFalse || value == tomTrue, "got %ld\n", value);
2663
2665 hr = ITextFont_GetEmboss(font, &value);
2666 ok(hr == S_OK, "got 0x%08lx\n", hr);
2667 ok(value == tomFalse, "got %ld\n", value);
2668
2670 hr = ITextFont_GetForeColor(font, &value);
2671 ok(hr == S_OK, "got 0x%08lx\n", hr);
2672 ok(value == tomAutoColor, "got %ld\n", value);
2673
2675 hr = ITextFont_GetHidden(font, &value);
2676 ok(hr == S_OK, "got 0x%08lx\n", hr);
2677 ok(value == tomFalse, "got %ld\n", value);
2678
2680 hr = ITextFont_GetEngrave(font, &value);
2681 ok(hr == S_OK, "got 0x%08lx\n", hr);
2682 ok(value == tomFalse, "got %ld\n", value);
2683
2685 hr = ITextFont_GetItalic(font, &value);
2686 ok(hr == S_OK, "got 0x%08lx\n", hr);
2687 ok(value == tomFalse, "got %ld\n", value);
2688
2689 valuef = 1.0;
2690 hr = ITextFont_GetKerning(font, &valuef);
2691 ok(hr == S_OK, "got 0x%08lx\n", hr);
2692 ok(valuef == 0.0, "got %.2f\n", valuef);
2693
2695 hr = ITextFont_GetLanguageID(font, &value);
2696 ok(hr == S_OK, "got 0x%08lx\n", hr);
2697 ok(value == GetSystemDefaultLCID(), "got %ld\n", value);
2698
2699 str = NULL;
2700 hr = ITextFont_GetName(font, &str);
2701 ok(hr == S_OK, "got 0x%08lx\n", hr);
2702 ok(!lstrcmpW(sysW, str), "%s\n", wine_dbgstr_w(str));
2704
2706 hr = ITextFont_GetOutline(font, &value);
2707 ok(hr == S_OK, "got 0x%08lx\n", hr);
2708 ok(value == tomFalse, "got %ld\n", value);
2709
2710 valuef = 1.0;
2711 hr = ITextFont_GetPosition(font, &valuef);
2712 ok(hr == S_OK, "got 0x%08lx\n", hr);
2713 ok(valuef == 0.0, "got %.2f\n", valuef);
2714
2716 hr = ITextFont_GetProtected(font, &value);
2717 ok(hr == S_OK, "got 0x%08lx\n", hr);
2718 ok(value == tomFalse, "got %ld\n", value);
2719
2721 hr = ITextFont_GetShadow(font, &value);
2722 ok(hr == S_OK, "got 0x%08lx\n", hr);
2723 ok(value == tomFalse, "got %ld\n", value);
2724
2725 valuef = 0.0;
2726 hr = ITextFont_GetSize(font, &valuef);
2727 ok(hr == S_OK, "got 0x%08lx\n", hr);
2728 ok(valuef >= 0.0, "got %.2f\n", valuef);
2729
2731 hr = ITextFont_GetSmallCaps(font, &value);
2732 ok(hr == S_OK, "got 0x%08lx\n", hr);
2733 ok(value == tomFalse, "got %ld\n", value);
2734
2735 valuef = 1.0;
2736 hr = ITextFont_GetSpacing(font, &valuef);
2737 ok(hr == S_OK, "got 0x%08lx\n", hr);
2738 ok(valuef == 0.0, "got %.2f\n", valuef);
2739
2741 hr = ITextFont_GetStrikeThrough(font, &value);
2742 ok(hr == S_OK, "got 0x%08lx\n", hr);
2743 ok(value == tomFalse, "got %ld\n", value);
2744
2746 hr = ITextFont_GetSubscript(font, &value);
2747 ok(hr == S_OK, "got 0x%08lx\n", hr);
2748 ok(value == tomFalse, "got %ld\n", value);
2749
2751 hr = ITextFont_GetSuperscript(font, &value);
2752 ok(hr == S_OK, "got 0x%08lx\n", hr);
2753 ok(value == tomFalse, "got %ld\n", value);
2754
2756 hr = ITextFont_GetUnderline(font, &value);
2757 ok(hr == S_OK, "got 0x%08lx\n", hr);
2758 ok(value == tomFalse, "got %ld\n", value);
2759
2761 hr = ITextFont_GetWeight(font, &value);
2762 ok(hr == S_OK, "got 0x%08lx\n", hr);
2763 ok(value == FW_NORMAL || value == FW_BOLD, "got %ld\n", value);
2764}
2765
2767{
2768 float valuef;
2769 LONG value;
2770 HRESULT hr;
2771
2772 value = tomFalse;
2773 hr = ITextFont_GetAllCaps(font, &value);
2774 ok(hr == S_OK, "got 0x%08lx\n", hr);
2775 ok(value == tomUndefined, "got %ld\n", value);
2776
2777 value = tomFalse;
2778 hr = ITextFont_GetAnimation(font, &value);
2779 ok(hr == S_OK, "got 0x%08lx\n", hr);
2780 ok(value == tomUndefined, "got %ld\n", value);
2781
2782 value = tomFalse;
2783 hr = ITextFont_GetBackColor(font, &value);
2784 ok(hr == S_OK, "got 0x%08lx\n", hr);
2785 ok(value == tomUndefined, "got %ld\n", value);
2786
2787 value = tomFalse;
2788 hr = ITextFont_GetBold(font, &value);
2789 ok(hr == S_OK, "got 0x%08lx\n", hr);
2790 ok(value == tomUndefined, "got %ld\n", value);
2791
2792 value = tomFalse;
2793 hr = ITextFont_GetEmboss(font, &value);
2794 ok(hr == S_OK, "got 0x%08lx\n", hr);
2795 ok(value == tomUndefined, "got %ld\n", value);
2796
2797 value = tomFalse;
2798 hr = ITextFont_GetForeColor(font, &value);
2799 ok(hr == S_OK, "got 0x%08lx\n", hr);
2800 ok(value == tomUndefined, "got %ld\n", value);
2801
2802 value = tomFalse;
2803 hr = ITextFont_GetHidden(font, &value);
2804 ok(hr == S_OK, "got 0x%08lx\n", hr);
2805 ok(value == tomUndefined, "got %ld\n", value);
2806
2807 value = tomFalse;
2808 hr = ITextFont_GetEngrave(font, &value);
2809 ok(hr == S_OK, "got 0x%08lx\n", hr);
2810 ok(value == tomUndefined, "got %ld\n", value);
2811
2812 value = tomFalse;
2813 hr = ITextFont_GetItalic(font, &value);
2814 ok(hr == S_OK, "got 0x%08lx\n", hr);
2815 ok(value == tomUndefined, "got %ld\n", value);
2816
2817 valuef = 0.0;
2818 hr = ITextFont_GetKerning(font, &valuef);
2819 ok(hr == S_OK, "got 0x%08lx\n", hr);
2820 ok(valuef == tomUndefined, "got %.2f\n", valuef);
2821
2822 value = tomFalse;
2823 hr = ITextFont_GetLanguageID(font, &value);
2824 ok(hr == S_OK, "got 0x%08lx\n", hr);
2825 ok(value == tomUndefined, "got %ld\n", value);
2826
2827 value = tomFalse;
2828 hr = ITextFont_GetOutline(font, &value);
2829 ok(hr == S_OK, "got 0x%08lx\n", hr);
2830 ok(value == tomUndefined, "got %ld\n", value);
2831
2832 valuef = 0.0;
2833 hr = ITextFont_GetPosition(font, &valuef);
2834 ok(hr == S_OK, "got 0x%08lx\n", hr);
2835 ok(valuef == tomUndefined, "got %.2f\n", valuef);
2836
2837 value = tomFalse;
2838 hr = ITextFont_GetProtected(font, &value);
2839 ok(hr == S_OK, "got 0x%08lx\n", hr);
2840 ok(value == tomUndefined, "got %ld\n", value);
2841
2842 value = tomFalse;
2843 hr = ITextFont_GetShadow(font, &value);
2844 ok(hr == S_OK, "got 0x%08lx\n", hr);
2845 ok(value == tomUndefined, "got %ld\n", value);
2846
2847 valuef = 0.0;
2848 hr = ITextFont_GetSize(font, &valuef);
2849 ok(hr == S_OK, "got 0x%08lx\n", hr);
2850 ok(valuef == tomUndefined, "got %.2f\n", valuef);
2851
2852 value = tomFalse;
2853 hr = ITextFont_GetSmallCaps(font, &value);
2854 ok(hr == S_OK, "got 0x%08lx\n", hr);
2855 ok(value == tomUndefined, "got %ld\n", value);
2856
2857 valuef = 0.0;
2858 hr = ITextFont_GetSpacing(font, &valuef);
2859 ok(hr == S_OK, "got 0x%08lx\n", hr);
2860 ok(valuef == tomUndefined, "got %.2f\n", valuef);
2861
2862 value = tomFalse;
2863 hr = ITextFont_GetStrikeThrough(font, &value);
2864 ok(hr == S_OK, "got 0x%08lx\n", hr);
2865 ok(value == tomUndefined, "got %ld\n", value);
2866
2867 value = tomFalse;
2868 hr = ITextFont_GetSubscript(font, &value);
2869 ok(hr == S_OK, "got 0x%08lx\n", hr);
2870 ok(value == tomUndefined, "got %ld\n", value);
2871
2872 value = tomFalse;
2873 hr = ITextFont_GetSuperscript(font, &value);
2874 ok(hr == S_OK, "got 0x%08lx\n", hr);
2875 ok(value == tomUndefined, "got %ld\n", value);
2876
2877 value = tomFalse;
2878 hr = ITextFont_GetUnderline(font, &value);
2879 ok(hr == S_OK, "got 0x%08lx\n", hr);
2880 ok(value == tomUndefined, "got %ld\n", value);
2881
2882 value = tomFalse;
2883 hr = ITextFont_GetWeight(font, &value);
2884 ok(hr == S_OK, "got 0x%08lx\n", hr);
2885 ok(value == tomUndefined, "got %ld\n", value);
2886}
2887
2889{
2890 return value * 72.0 / 1440;
2891}
2892
2893static void test_ITextFont(void)
2894{
2895 static const WCHAR arialW[] = {'A','r','i','a','l',0};
2896 static const CHAR test_text1[] = "TestSomeText";
2897 ITextFont *font, *font2, *font3;
2898 FLOAT size, position, kerning;
2899 IRichEditOle *reOle = NULL;
2900 ITextDocument *doc = NULL;
2903 LONG value;
2904 HRESULT hr;
2905 HWND hwnd;
2906 BOOL ret;
2907 BSTR str;
2908
2909 create_interfaces(&hwnd, &reOle, &doc, NULL);
2910 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
2911
2912 hr = ITextDocument_Range(doc, 0, 10, &range);
2913 ok(hr == S_OK, "got 0x%08lx\n", hr);
2914
2915 hr = ITextRange_GetFont(range, &font);
2916 ok(hr == S_OK, "got 0x%08lx\n", hr);
2917
2918 hr = ITextFont_Reset(font, tomUseTwips);
2919 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2920
2921 hr = ITextFont_Reset(font, tomUsePoints);
2922 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2923
2924 hr = ITextFont_GetName(font, NULL);
2925 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2926
2927 /* default font size unit is point */
2928 size = 0.0;
2929 hr = ITextFont_GetSize(font, &size);
2930 ok(hr == S_OK, "got 0x%08lx\n", hr);
2931
2932 /* set to some non-zero values */
2933 hr = ITextFont_SetPosition(font, 20.0);
2934 ok(hr == S_OK, "got 0x%08lx\n", hr);
2935
2936 hr = ITextFont_SetKerning(font, 10.0);
2937 ok(hr == S_OK, "got 0x%08lx\n", hr);
2938
2939 position = 0.0;
2940 hr = ITextFont_GetPosition(font, &position);
2941 ok(hr == S_OK, "got 0x%08lx\n", hr);
2942
2943 kerning = 0.0;
2944 hr = ITextFont_GetKerning(font, &kerning);
2945 ok(hr == S_OK, "got 0x%08lx\n", hr);
2946
2947 memset(&cf, 0, sizeof(cf));
2948 cf.cbSize = sizeof(cf);
2950
2951 /* CHARFORMAT members are in twips */
2952 SendMessageA(hwnd, EM_SETSEL, 0, 10);
2954 ok(ret, "got %d\n", ret);
2955 ok(size == twips_to_points(cf.yHeight), "got yHeight %ld, size %.2f\n", cf.yHeight, size);
2956 ok(position == twips_to_points(cf.yOffset), "got yOffset %ld, position %.2f\n", cf.yOffset, position);
2957 ok(kerning == twips_to_points(cf.wKerning), "got wKerning %d, kerning %.2f\n", cf.wKerning, kerning);
2958
2959 hr = ITextFont_Reset(font, tomUseTwips);
2960 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2961
2962 hr = ITextFont_Reset(font, tomUsePoints);
2963 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2964
2965 hr = ITextFont_GetDuplicate(font, &font2);
2966 ok(hr == S_OK, "got 0x%08lx\n", hr);
2967
2968 hr = ITextFont_Reset(font2, tomUseTwips);
2969 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2970
2971 hr = ITextFont_Reset(font2, tomUsePoints);
2972 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
2973
2974 ITextFont_Release(font2);
2975
2976 /* default font name */
2977 str = NULL;
2978 hr = ITextFont_GetName(font, &str);
2979 ok(hr == S_OK, "got 0x%08lx\n", hr);
2980 ok(!lstrcmpW(str, sysW), "got %s\n", wine_dbgstr_w(str));
2982
2983 /* change font name for an inner subrange */
2984 memset(&cf, 0, sizeof(cf));
2985 cf.cbSize = sizeof(cf);
2986 cf.dwMask = CFM_FACE;
2987 strcpy(cf.szFaceName, "Arial");
2988
2989 SendMessageA(hwnd, EM_SETSEL, 3, 4);
2991 ok(ret, "got %d\n", ret);
2992
2993 /* still original name */
2994 str = NULL;
2995 hr = ITextFont_GetName(font, &str);
2996 ok(hr == S_OK, "got 0x%08lx\n", hr);
2997 ok(!lstrcmpW(str, sysW), "got %s\n", wine_dbgstr_w(str));
2999
3000 SendMessageA(hwnd, EM_SETSEL, 1, 2);
3002 ok(ret, "got %d\n", ret);
3003
3004 str = NULL;
3005 hr = ITextFont_GetName(font, &str);
3006 ok(hr == S_OK, "got 0x%08lx\n", hr);
3007 ok(!lstrcmpW(str, sysW), "got %s\n", wine_dbgstr_w(str));
3009
3010 /* name is returned for first position within a range */
3011 SendMessageA(hwnd, EM_SETSEL, 0, 1);
3013 ok(ret, "got %d\n", ret);
3014
3015 str = NULL;
3016 hr = ITextFont_GetName(font, &str);
3017 ok(hr == S_OK, "got 0x%08lx\n", hr);
3018 ok(!lstrcmpW(str, arialW), "got %s\n", wine_dbgstr_w(str));
3020
3021 /* GetDuplicate() */
3022 hr = ITextFont_GetDuplicate(font, NULL);
3023 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
3024
3025 EXPECT_REF(range, 2);
3026 font2 = NULL;
3027 hr = ITextFont_GetDuplicate(font, &font2);
3028 ok(hr == S_OK, "got 0x%08lx\n", hr);
3029 EXPECT_REF(range, 2);
3030
3031 /* set whole range to italic */
3032 cf.cbSize = sizeof(CHARFORMAT2A);
3033 cf.dwMask = CFM_ITALIC;
3034 cf.dwEffects = CFE_ITALIC;
3035
3036 SendMessageA(hwnd, EM_SETSEL, 0, 10);
3038 ok(ret, "got %d\n", ret);
3039
3040 value = tomFalse;
3041 hr = ITextFont_GetItalic(font, &value);
3042 ok(hr == S_OK, "got 0x%08lx\n", hr);
3043 ok(value == tomTrue, "got %ld\n", value);
3044
3045 /* duplicate retains original value */
3046 value = tomTrue;
3047 hr = ITextFont_GetItalic(font2, &value);
3048 ok(hr == S_OK, "got 0x%08lx\n", hr);
3049 ok(value == tomFalse, "got %ld\n", value);
3050
3051 /* get a duplicate from a cloned font */
3052 hr = ITextFont_GetDuplicate(font2, &font3);
3053 ok(hr == S_OK, "got 0x%08lx\n", hr);
3054 ITextFont_Release(font3);
3055
3056 ITextRange_Release(range);
3057 release_interfaces(&hwnd, &reOle, &doc, NULL);
3058
3059 hr = ITextFont_GetDuplicate(font, NULL);
3060 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
3061
3064
3065 /* get a duplicate of detached font */
3066 hr = ITextFont_GetDuplicate(font2, &font3);
3067 ok(hr == S_OK, "got 0x%08lx\n", hr);
3068 ITextFont_Release(font3);
3069
3070 /* reset detached font to undefined */
3072 hr = ITextFont_GetBold(font2, &value);
3073 ok(hr == S_OK, "got 0x%08lx\n", hr);
3074 ok(value != tomUndefined, "got %ld\n", value);
3075
3076 /* reset to undefined for detached font */
3077 hr = ITextFont_Reset(font2, tomUndefined);
3078 ok(hr == S_OK, "got 0x%08lx\n", hr);
3080
3081 /* font is detached, default means global TOM defaults */
3082 hr = ITextFont_Reset(font2, tomDefault);
3083 ok(hr == S_OK, "got 0x%08lx\n", hr);
3085
3086 hr = ITextFont_GetDuplicate(font2, &font3);
3087 ok(hr == S_OK, "got 0x%08lx\n", hr);
3089
3090 hr = ITextFont_Reset(font2, tomApplyNow);
3091 ok(hr == S_OK, "got 0x%08lx\n", hr);
3093
3094 hr = ITextFont_Reset(font2, tomApplyLater);
3095 ok(hr == S_OK, "got 0x%08lx\n", hr);
3097
3098 hr = ITextFont_Reset(font2, tomTrackParms);
3099 ok(hr == S_OK, "got 0x%08lx\n", hr);
3101
3102 hr = ITextFont_SetItalic(font2, tomUndefined);
3103 ok(hr == S_OK, "got 0x%08lx\n", hr);
3104
3105 hr = ITextFont_GetItalic(font2, &value);
3106 ok(hr == S_OK, "got 0x%08lx\n", hr);
3107 ok(value == tomFalse, "got %ld\n", value);
3108
3109 hr = ITextFont_Reset(font2, tomCacheParms);
3110 ok(hr == S_OK, "got 0x%08lx\n", hr);
3112
3113 ITextFont_Release(font3);
3114 ITextFont_Release(font2);
3115
3116 font2 = (void*)0xdeadbeef;
3117 hr = ITextFont_GetDuplicate(font, &font2);
3118 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3119 ok(font2 == NULL, "got %p\n", font2);
3120
3121 hr = ITextFont_Reset(font, tomDefault);
3122 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3123
3124 ITextFont_Release(font);
3125
3126 /* Reset() */
3127 create_interfaces(&hwnd, &reOle, &doc, NULL);
3128 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
3129
3130 hr = ITextDocument_Range(doc, 0, 10, &range);
3131 ok(hr == S_OK, "got 0x%08lx\n", hr);
3132
3133 hr = ITextRange_GetFont(range, &font);
3134 ok(hr == S_OK, "got 0x%08lx\n", hr);
3135
3137 hr = ITextFont_GetBold(font, &value);
3138 ok(hr == S_OK, "got 0x%08lx\n", hr);
3139 ok(value != tomUndefined, "got %ld\n", value);
3140
3141 /* reset to undefined for attached font */
3142 hr = ITextFont_Reset(font, tomUndefined);
3143 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
3144
3146 hr = ITextFont_GetBold(font, &value);
3147 ok(hr == S_OK, "got 0x%08lx\n", hr);
3148 ok(value != tomUndefined, "got %ld\n", value);
3149
3150 /* tomCacheParms/tomTrackParms */
3151 hr = ITextFont_Reset(font, tomCacheParms);
3152 ok(hr == S_OK, "got 0x%08lx\n", hr);
3153
3154 hr = ITextFont_GetItalic(font, &value);
3155 ok(hr == S_OK, "got 0x%08lx\n", hr);
3156 ok(value == tomFalse, "got %ld\n", value);
3157
3158 memset(&cf, 0, sizeof(cf));
3159 cf.cbSize = sizeof(CHARFORMAT2A);
3160 cf.dwMask = CFM_ITALIC;
3161
3162 cf.dwEffects = CFE_ITALIC;
3163 SendMessageA(hwnd, EM_SETSEL, 0, 10);
3165 ok(ret, "got %d\n", ret);
3166
3167 /* still cached value */
3168 hr = ITextFont_GetItalic(font, &value);
3169 ok(hr == S_OK, "got 0x%08lx\n", hr);
3170 ok(value == tomFalse, "got %ld\n", value);
3171
3172 hr = ITextFont_Reset(font, tomTrackParms);
3173 ok(hr == S_OK, "got 0x%08lx\n", hr);
3174
3175 hr = ITextFont_GetItalic(font, &value);
3176 ok(hr == S_OK, "got 0x%08lx\n", hr);
3177 ok(value == tomTrue, "got %ld\n", value);
3178
3179 /* switch back to cache - value retained */
3180 hr = ITextFont_Reset(font, tomCacheParms);
3181 ok(hr == S_OK, "got 0x%08lx\n", hr);
3182
3183 hr = ITextFont_GetItalic(font, &value);
3184 ok(hr == S_OK, "got 0x%08lx\n", hr);
3185 ok(value == tomTrue, "got %ld\n", value);
3186
3187 /* tomApplyLater */
3188 hr = ITextFont_Reset(font, tomApplyLater);
3189 ok(hr == S_OK, "got 0x%08lx\n", hr);
3190
3191 hr = ITextFont_SetItalic(font, tomFalse);
3192 ok(hr == S_OK, "got 0x%08lx\n", hr);
3193
3194 hr = ITextFont_GetItalic(font, &value);
3195 ok(hr == S_OK, "got 0x%08lx\n", hr);
3196 ok(value == tomFalse, "got %ld\n", value);
3197
3198 cf.dwEffects = 0;
3199 SendMessageA(hwnd, EM_SETSEL, 0, 10);
3201 ok(ret, "got %d\n", ret);
3202 ok((cf.dwEffects & CFE_ITALIC) == CFE_ITALIC, "got 0x%08lx\n", cf.dwEffects);
3203
3204 hr = ITextFont_Reset(font, tomApplyNow);
3205 ok(hr == S_OK, "got 0x%08lx\n", hr);
3206
3207 cf.dwEffects = 0;
3208 SendMessageA(hwnd, EM_SETSEL, 0, 10);
3210 ok(ret, "got %d\n", ret);
3211 ok((cf.dwEffects & CFE_ITALIC) == 0, "got 0x%08lx\n", cf.dwEffects);
3212
3213 hr = ITextFont_SetItalic(font, tomUndefined);
3214 ok(hr == S_OK, "got 0x%08lx\n", hr);
3215
3216 hr = ITextFont_GetItalic(font, &value);
3217 ok(hr == S_OK, "got 0x%08lx\n", hr);
3218 ok(value == tomFalse, "got %ld\n", value);
3219
3220 hr = ITextFont_SetItalic(font, tomAutoColor);
3221 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
3222
3223 cf.dwEffects = 0;
3224 SendMessageA(hwnd, EM_SETSEL, 0, 10);
3226 ok(ret, "got %d\n", ret);
3227 ok((cf.dwEffects & CFE_ITALIC) == 0, "got 0x%08lx\n", cf.dwEffects);
3228
3229 ITextRange_Release(range);
3230 ITextFont_Release(font);
3231 release_interfaces(&hwnd, &reOle, &doc, NULL);
3232}
3233
3234static void test_Delete(void)
3235{
3236 static const CHAR test_text1[] = "TestSomeText";
3237 IRichEditOle *reOle = NULL;
3238 ITextDocument *doc = NULL;
3239 ITextRange *range, *range2;
3240 LONG value;
3241 HRESULT hr;
3242 HWND hwnd;
3243
3244 create_interfaces(&hwnd, &reOle, &doc, NULL);
3245 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
3246
3247 hr = ITextDocument_Range(doc, 0, 4, &range);
3248 ok(hr == S_OK, "got 0x%08lx\n", hr);
3249
3250 hr = ITextDocument_Range(doc, 1, 2, &range2);
3251 ok(hr == S_OK, "got 0x%08lx\n", hr);
3252
3253 hr = ITextRange_GetEnd(range, &value);
3254 ok(hr == S_OK, "got 0x%08lx\n", hr);
3255 ok(value == 4, "got %ld\n", value);
3256
3257 /* unit type doesn't matter is count is 0 */
3258 value = 0;
3259 hr = ITextRange_Delete(range2, tomSentence, 0, &value);
3260todo_wine {
3261 ok(hr == S_OK, "got 0x%08lx\n", hr);
3262 ok(value == 1, "got %ld\n", value);
3263}
3264 value = 1;
3265 hr = ITextRange_Delete(range2, tomCharacter, 0, &value);
3266todo_wine {
3267 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3268 ok(value == 0, "got %ld\n", value);
3269}
3270 hr = ITextRange_GetEnd(range, &value);
3271 ok(hr == S_OK, "got 0x%08lx\n", hr);
3272 todo_wine
3273 ok(value == 3, "got %ld\n", value);
3274
3275 hr = ITextRange_GetStart(range2, &value);
3276 ok(hr == S_OK, "got 0x%08lx\n", hr);
3277 ok(value == 1, "got %ld\n", value);
3278
3279 hr = ITextRange_GetEnd(range2, &value);
3280 ok(hr == S_OK, "got 0x%08lx\n", hr);
3281 todo_wine
3282 ok(value == 1, "got %ld\n", value);
3283
3284 ITextRange_Release(range);
3285 ITextRange_Release(range2);
3286 release_interfaces(&hwnd, &reOle, &doc, NULL);
3287}
3288
3289static void test_SetText(void)
3290{
3291 static const CHAR test_text1[] = "TestSomeText";
3292 static const WCHAR textW[] = {'a','b','c','d','e','f','g','h','i',0};
3293 IRichEditOle *reOle = NULL;
3294 ITextDocument *doc = NULL;
3295 ITextRange *range, *range2;
3296 LONG value;
3297 HRESULT hr;
3298 HWND hwnd;
3299 BSTR str;
3300
3301 create_interfaces(&hwnd, &reOle, &doc, NULL);
3302 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
3303
3304 hr = ITextDocument_Range(doc, 0, 4, &range);
3305 ok(hr == S_OK, "got 0x%08lx\n", hr);
3306
3307 hr = ITextDocument_Range(doc, 0, 4, &range2);
3308 ok(hr == S_OK, "got 0x%08lx\n", hr);
3309
3310 value = 1;
3311 hr = ITextRange_GetStart(range2, &value);
3312 ok(hr == S_OK, "got 0x%08lx\n", hr);
3313 ok(value == 0, "got %ld\n", value);
3314
3315 value = 0;
3316 hr = ITextRange_GetEnd(range2, &value);
3317 ok(hr == S_OK, "got 0x%08lx\n", hr);
3318 ok(value == 4, "got %ld\n", value);
3319
3320 hr = ITextRange_SetText(range, NULL);
3321 ok(hr == S_OK, "got 0x%08lx\n", hr);
3322
3323 value = 1;
3324 hr = ITextRange_GetEnd(range2, &value);
3325 ok(hr == S_OK, "got 0x%08lx\n", hr);
3326 ok(value == 0, "got %ld\n", value);
3327
3329 hr = ITextRange_SetText(range, str);
3330 ok(hr == S_OK, "got 0x%08lx\n", hr);
3332
3333 value = 1;
3334 hr = ITextRange_GetStart(range, &value);
3335 ok(hr == S_OK, "got 0x%08lx\n", hr);
3336 ok(value == 0, "got %ld\n", value);
3337
3338 value = 0;
3339 hr = ITextRange_GetEnd(range, &value);
3340 ok(hr == S_OK, "got 0x%08lx\n", hr);
3341 ok(value == 9, "got %ld\n", value);
3342
3343 value = 1;
3344 hr = ITextRange_GetStart(range2, &value);
3345 ok(hr == S_OK, "got 0x%08lx\n", hr);
3346 ok(value == 0, "got %ld\n", value);
3347
3348 value = 0;
3349 hr = ITextRange_GetEnd(range2, &value);
3350 ok(hr == S_OK, "got 0x%08lx\n", hr);
3351 ok(value == 0, "got %ld\n", value);
3352
3354 hr = ITextRange_SetText(range, str);
3355 ok(hr == S_OK, "got 0x%08lx\n", hr);
3356 value = 1;
3357 hr = ITextRange_GetEnd(range, &value);
3358 ok(hr == S_OK, "got 0x%08lx\n", hr);
3359 ok(value == 0, "got %ld\n", value);
3361
3362 ITextRange_Release(range2);
3363 release_interfaces(&hwnd, &reOle, &doc, NULL);
3364
3365 hr = ITextRange_SetText(range, NULL);
3366 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3367
3369 hr = ITextRange_SetText(range, str);
3370 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3372
3373 ITextRange_Release(range);
3374}
3375
3376static void test_InRange(void)
3377{
3378 static const CHAR test_text1[] = "TestSomeText";
3379 ITextRange *range, *range2, *range3;
3380 IRichEditOle *reOle = NULL;
3381 ITextDocument *doc = NULL;
3383 LONG value;
3384 HRESULT hr;
3385 HWND hwnd;
3386
3387 create_interfaces(&hwnd, &reOle, &doc, &selection);
3388 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
3389 SendMessageA(hwnd, EM_SETSEL, 1, 2);
3390
3391 hr = ITextDocument_Range(doc, 0, 4, &range);
3392 ok(hr == S_OK, "got 0x%08lx\n", hr);
3393
3394 hr = ITextDocument_Range(doc, 0, 4, &range2);
3395 ok(hr == S_OK, "got 0x%08lx\n", hr);
3396
3397 /* matches selection */
3398 hr = ITextDocument_Range(doc, 1, 2, &range3);
3399 ok(hr == S_OK, "got 0x%08lx\n", hr);
3400
3401 hr = ITextRange_InRange(range, NULL, NULL);
3402 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3403
3404 value = tomTrue;
3405 hr = ITextRange_InRange(range, NULL, &value);
3406 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3407 ok(value == tomFalse, "got %ld\n", value);
3408
3409 hr = ITextRange_InRange(range, range2, NULL);
3410 ok(hr == S_OK, "got 0x%08lx\n", hr);
3411
3412 value = tomFalse;
3413 hr = ITextRange_InRange(range, range2, &value);
3414 ok(hr == S_OK, "got 0x%08lx\n", hr);
3415 ok(value == tomTrue, "got %ld\n", value);
3416
3417 /* selection */
3418 hr = ITextSelection_InRange(selection, NULL, NULL);
3419 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3420
3421 value = tomTrue;
3422 hr = ITextSelection_InRange(selection, NULL, &value);
3423 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3424 ok(value == tomFalse, "got %ld\n", value);
3425
3426 hr = ITextSelection_InRange(selection, range2, NULL);
3427 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3428
3429 value = tomTrue;
3430 hr = ITextSelection_InRange(selection, range2, &value);
3431 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3432 ok(value == tomFalse, "got %ld\n", value);
3433
3434 value = tomTrue;
3435 hr = ITextSelection_InRange(selection, range3, &value);
3436 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3437 ok(value == tomFalse, "got %ld\n", value);
3438
3439 /* seems to work on ITextSelection ranges only */
3440 value = tomFalse;
3441 hr = ITextSelection_InRange(selection, (ITextRange*)selection, &value);
3442 ok(hr == S_OK, "got 0x%08lx\n", hr);
3443 ok(value == tomTrue, "got %ld\n", value);
3444
3445 release_interfaces(&hwnd, &reOle, &doc, NULL);
3446
3447 hr = ITextRange_InRange(range, NULL, NULL);
3448 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3449
3450 value = tomTrue;
3451 hr = ITextRange_InRange(range, NULL, &value);
3452 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3453 ok(value == tomFalse, "got %ld\n", value);
3454
3455 hr = ITextRange_InRange(range, range2, NULL);
3456 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3457
3458 value = tomTrue;
3459 hr = ITextRange_InRange(range, range2, &value);
3460 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3461 ok(value == tomFalse, "got %ld\n", value);
3462
3463 /* selection */
3464 hr = ITextSelection_InRange(selection, NULL, NULL);
3465 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3466
3467 value = tomTrue;
3468 hr = ITextSelection_InRange(selection, NULL, &value);
3469 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3470 ok(value == tomFalse, "got %ld\n", value);
3471
3472 hr = ITextSelection_InRange(selection, range2, NULL);
3473 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3474
3475 value = tomTrue;
3476 hr = ITextSelection_InRange(selection, range2, &value);
3477 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3478 ok(value == tomFalse, "got %ld\n", value);
3479
3480 ITextRange_Release(range);
3481 ITextRange_Release(range2);
3482 ITextRange_Release(range3);
3483 ITextSelection_Release(selection);
3484}
3485
3487{
3488 static const CHAR test_text1[] = "TestSomeText";
3489 ITextRange *range, *range2, *range3;
3490 IRichEditOle *reOle = NULL;
3491 ITextDocument *doc = NULL;
3493 LONG value;
3494 HRESULT hr;
3495 HWND hwnd;
3496
3497 create_interfaces(&hwnd, &reOle, &doc, &selection);
3498 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
3499 SendMessageA(hwnd, EM_SETSEL, 1, 2);
3500
3501 hr = ITextDocument_Range(doc, 0, 4, &range);
3502 ok(hr == S_OK, "got 0x%08lx\n", hr);
3503
3504 hr = ITextDocument_Range(doc, 0, 4, &range2);
3505 ok(hr == S_OK, "got 0x%08lx\n", hr);
3506
3507 /* matches selection */
3508 hr = ITextDocument_Range(doc, 1, 2, &range3);
3509 ok(hr == S_OK, "got 0x%08lx\n", hr);
3510
3511 hr = ITextRange_IsEqual(range, NULL, NULL);
3512 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3513
3514 value = tomTrue;
3515 hr = ITextRange_IsEqual(range, NULL, &value);
3516 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3517 ok(value == tomFalse, "got %ld\n", value);
3518
3519 hr = ITextRange_IsEqual(range, range2, NULL);
3520 ok(hr == S_OK, "got 0x%08lx\n", hr);
3521
3522 value = tomFalse;
3523 hr = ITextRange_IsEqual(range, range2, &value);
3524 ok(hr == S_OK, "got 0x%08lx\n", hr);
3525 ok(value == tomTrue, "got %ld\n", value);
3526
3527 value = tomTrue;
3528 hr = ITextRange_IsEqual(range, range3, &value);
3529 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3530 ok(value == tomFalse, "got %ld\n", value);
3531
3532 /* selection */
3533 hr = ITextSelection_IsEqual(selection, NULL, NULL);
3534 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3535
3536 value = tomTrue;
3537 hr = ITextSelection_IsEqual(selection, NULL, &value);
3538 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3539 ok(value == tomFalse, "got %ld\n", value);
3540
3541 hr = ITextSelection_IsEqual(selection, range2, NULL);
3542 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3543
3544 value = tomTrue;
3545 hr = ITextSelection_IsEqual(selection, range2, &value);
3546 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3547 ok(value == tomFalse, "got %ld\n", value);
3548
3549 value = tomTrue;
3550 hr = ITextSelection_IsEqual(selection, range3, &value);
3551 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
3552 ok(value == tomFalse, "got %ld\n", value);
3553
3554 /* seems to work on ITextSelection ranges only */
3555 value = tomFalse;
3556 hr = ITextSelection_IsEqual(selection, (ITextRange*)selection, &value);
3557 ok(hr == S_OK, "got 0x%08lx\n", hr);
3558 ok(value == tomTrue, "got %ld\n", value);
3559
3560 release_interfaces(&hwnd, &reOle, &doc, NULL);
3561
3562 hr = ITextRange_IsEqual(range, NULL, NULL);
3563 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3564
3565 value = tomTrue;
3566 hr = ITextRange_IsEqual(range, NULL, &value);
3567 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3568 ok(value == tomFalse, "got %ld\n", value);
3569
3570 hr = ITextRange_IsEqual(range, range2, NULL);
3571 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3572
3573 value = tomTrue;
3574 hr = ITextRange_IsEqual(range, range2, &value);
3575 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3576 ok(value == tomFalse, "got %ld\n", value);
3577
3578 /* selection */
3579 hr = ITextSelection_IsEqual(selection, NULL, NULL);
3580 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3581
3582 value = tomTrue;
3583 hr = ITextSelection_IsEqual(selection, NULL, &value);
3584 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3585 ok(value == tomFalse, "got %ld\n", value);
3586
3587 hr = ITextSelection_IsEqual(selection, range2, NULL);
3588 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3589
3590 value = tomTrue;
3591 hr = ITextSelection_IsEqual(selection, range2, &value);
3592 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3593 ok(value == tomFalse, "got %ld\n", value);
3594
3595 ITextRange_Release(range);
3596 ITextRange_Release(range2);
3597 ITextRange_Release(range3);
3598 ITextSelection_Release(selection);
3599}
3600
3602{
3603 POINT p = {-1, -1};
3605 ok(p.x != -1 && p.y != -1, "p.x:%ld p.y:%ld\n", p.x, p.y);
3606 return p.y;
3607}
3608
3609static void test_Select(void)
3610{
3611 static const CHAR test_text1[] = "TestSomeText";
3612 static const CHAR test_text2[] = "text\nwith\nbreak\n"
3613 "lines\ntest\ntest\n";
3614 IRichEditOle *reOle = NULL;
3615 ITextDocument *doc = NULL;
3618 int scroll_pos1;
3619 int scroll_pos2;
3620 LONG value;
3621 HRESULT hr;
3622 HWND hwnd;
3623
3624 create_interfaces(&hwnd, &reOle, &doc, &selection);
3625 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
3626 SendMessageA(hwnd, EM_SETSEL, 1, 2);
3627
3628 hr = ITextDocument_Range(doc, 0, 4, &range);
3629 ok(hr == S_OK, "got 0x%08lx\n", hr);
3630
3631 scroll_pos1 = get_scroll_pos_y(hwnd);
3632 hr = ITextRange_Select(range);
3633 ok(hr == S_OK, "got 0x%08lx\n", hr);
3634 scroll_pos2 = get_scroll_pos_y(hwnd);
3635 ok(scroll_pos1 == scroll_pos2, "%d != %d\n", scroll_pos1, scroll_pos2);
3636
3637 value = 1;
3638 hr = ITextSelection_GetStart(selection, &value);
3639 ok(hr == S_OK, "got 0x%08lx\n", hr);
3640 ok(value == 0, "got %ld\n", value);
3641
3642 hr = ITextRange_Select(range);
3643 ok(hr == S_OK, "got 0x%08lx\n", hr);
3644
3645 hr = ITextSelection_Select(selection);
3646 ok(hr == S_OK, "got 0x%08lx\n", hr);
3647
3648 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text2);
3649 SendMessageA(hwnd, EM_SETSEL, 1, 2);
3650 hr = ITextDocument_Range(doc, 10, 16, &range);
3651 ok(hr == S_OK, "got 0x%08lx\n", hr);
3652 scroll_pos1 = get_scroll_pos_y(hwnd);
3653 hr = ITextRange_Select(range);
3654 ok(hr == S_OK, "got 0x%08lx\n", hr);
3655 scroll_pos2 = get_scroll_pos_y(hwnd);
3656 ok(scroll_pos1 != scroll_pos2, "%d == %d\n", scroll_pos1, scroll_pos2);
3657
3658 release_interfaces(&hwnd, &reOle, &doc, NULL);
3659
3660 hr = ITextRange_Select(range);
3661 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3662
3663 hr = ITextSelection_Select(selection);
3664 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3665
3666 ITextRange_Release(range);
3667 ITextSelection_Release(selection);
3668}
3669
3670static void test_GetStoryType(void)
3671{
3672 static const CHAR test_text1[] = "TestSomeText";
3673 IRichEditOle *reOle = NULL;
3674 ITextDocument *doc = NULL;
3677 LONG value;
3678 HRESULT hr;
3679 HWND hwnd;
3680
3681 create_interfaces(&hwnd, &reOle, &doc, &selection);
3682 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
3683 SendMessageA(hwnd, EM_SETSEL, 1, 2);
3684
3685 hr = ITextDocument_Range(doc, 0, 4, &range);
3686 ok(hr == S_OK, "got 0x%08lx\n", hr);
3687
3688 hr = ITextRange_GetStoryType(range, NULL);
3689 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
3690
3692 hr = ITextRange_GetStoryType(range, &value);
3693 ok(hr == S_OK, "got 0x%08lx\n", hr);
3694 ok(value == tomUnknownStory, "got %ld\n", value);
3695
3696 hr = ITextSelection_GetStoryType(selection, NULL);
3697 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
3698
3700 hr = ITextSelection_GetStoryType(selection, &value);
3701 ok(hr == S_OK, "got 0x%08lx\n", hr);
3702 ok(value == tomUnknownStory, "got %ld\n", value);
3703
3704 release_interfaces(&hwnd, &reOle, &doc, NULL);
3705
3706 hr = ITextRange_GetStoryType(range, NULL);
3707 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3708
3709 value = 123;
3710 hr = ITextRange_GetStoryType(range, &value);
3711 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3712 ok(value == 123, "got %ld\n", value);
3713
3714 hr = ITextSelection_GetStoryType(selection, NULL);
3715 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3716
3717 value = 123;
3718 hr = ITextSelection_GetStoryType(selection, &value);
3719 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3720 ok(value == 123, "got %ld\n", value);
3721
3722 ITextRange_Release(range);
3723 ITextSelection_Release(selection);
3724}
3725
3726static void test_SetFont(void)
3727{
3728 static const CHAR test_text1[] = "TestSomeText";
3729 IRichEditOle *reOle = NULL;
3730 ITextDocument *doc = NULL;
3732 ITextRange *range, *range2;
3733 ITextFont *font, *font2;
3734 LONG value;
3735 HRESULT hr;
3736 HWND hwnd;
3737
3738 create_interfaces(&hwnd, &reOle, &doc, &selection);
3739 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
3740 SendMessageA(hwnd, EM_SETSEL, 1, 2);
3741
3742 hr = ITextDocument_Range(doc, 0, 4, &range);
3743 ok(hr == S_OK, "got 0x%08lx\n", hr);
3744
3745 hr = ITextDocument_Range(doc, 5, 2, &range2);
3746 ok(hr == S_OK, "got 0x%08lx\n", hr);
3747
3748 EXPECT_REF(range, 1);
3749 hr = ITextRange_GetFont(range, &font);
3750 ok(hr == S_OK, "got 0x%08lx\n", hr);
3751 EXPECT_REF(range, 2);
3752
3753 EXPECT_REF(range2, 1);
3754 hr = ITextRange_GetFont(range2, &font2);
3755 ok(hr == S_OK, "got 0x%08lx\n", hr);
3756 EXPECT_REF(range2, 2);
3757
3758 hr = ITextRange_SetFont(range, NULL);
3759 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
3760
3761 /* setting same font, no-op */
3762 EXPECT_REF(range, 2);
3763 hr = ITextRange_SetFont(range, font);
3764 ok(hr == S_OK, "got 0x%08lx\n", hr);
3765 EXPECT_REF(range, 2);
3766
3767 EXPECT_REF(range2, 2);
3768 EXPECT_REF(range, 2);
3769 hr = ITextRange_SetFont(range, font2);
3770 ok(hr == S_OK, "got 0x%08lx\n", hr);
3771 EXPECT_REF(range2, 2);
3772 EXPECT_REF(range, 2);
3773
3774 /* originally range 0-4 is non-italic */
3775 value = tomTrue;
3776 hr = ITextFont_GetItalic(font, &value);
3777 ok(hr == S_OK, "got 0x%08lx\n", hr);
3778 ok(value == tomFalse, "got %ld\n", value);
3779
3780 /* set range 5-2 to italic, then set this font to range 0-4 */
3781 hr = ITextFont_SetItalic(font2, tomTrue);
3782 ok(hr == S_OK, "got 0x%08lx\n", hr);
3783
3784 hr = ITextRange_SetFont(range, font2);
3785 ok(hr == S_OK, "got 0x%08lx\n", hr);
3786
3787 value = tomFalse;
3788 hr = ITextFont_GetItalic(font, &value);
3789 ok(hr == S_OK, "got 0x%08lx\n", hr);
3790 ok(value == tomTrue, "got %ld\n", value);
3791
3792 release_interfaces(&hwnd, &reOle, &doc, NULL);
3793
3794 hr = ITextRange_SetFont(range, NULL);
3795 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
3796
3797 hr = ITextRange_SetFont(range, font);
3798 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3799
3800 hr = ITextSelection_SetFont(selection, NULL);
3801 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
3802
3803 hr = ITextSelection_SetFont(selection, font);
3804 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
3805
3806 ITextFont_Release(font);
3807 ITextFont_Release(font2);
3808 ITextRange_Release(range);
3809 ITextRange_Release(range2);
3810 ITextSelection_Release(selection);
3811}
3812
3813static void fill_reobject_struct(REOBJECT *reobj, LONG cp, LPOLEOBJECT poleobj,
3814 LPSTORAGE pstg, LPOLECLIENTSITE polesite, LONG sizel_cx,
3815 LONG sizel_cy, DWORD aspect, DWORD flags, DWORD user)
3816{
3817 reobj->cbStruct = sizeof(*reobj);
3818 reobj->clsid = CLSID_NULL;
3819 reobj->cp = cp;
3820 reobj->poleobj = poleobj;
3821 reobj->pstg = pstg;
3822 reobj->polesite = polesite;
3823 reobj->sizel.cx = sizel_cx;
3824 reobj->sizel.cy = sizel_cy;
3825 reobj->dvaspect = aspect;
3826 reobj->dwFlags = flags;
3827 reobj->dwUser = user;
3828}
3829
3830#define CHECK_REOBJECT_STRUCT(reole,index,flags,cp,cp_check,poleobj,pstg,polesite,user) \
3831 _check_reobject_struct(reole, index, flags, cp, cp_check, poleobj, pstg, polesite, user, __LINE__)
3833 LPOLEOBJECT poleobj, LPSTORAGE pstg, LPOLECLIENTSITE polesite, DWORD user, int line)
3834{
3835 REOBJECT reobj;
3836 HRESULT hr;
3837
3838 reobj.cbStruct = sizeof(reobj);
3839 reobj.cp = cp;
3840 hr = IRichEditOle_GetObject(reole, index, &reobj, flags);
3841 ok(hr == S_OK, "IRichEditOle_GetObject failed: %#lx.\n", hr);
3842 ok_(__FILE__,line)(reobj.cp == cp_check, "expected cp = %ld, got %ld.\n", cp_check, reobj.cp);
3843 ok_(__FILE__,line)(reobj.poleobj == poleobj, "got wrong object interface.\n");
3844 ok_(__FILE__,line)(reobj.pstg == pstg, "got wrong storage interface.\n");
3845 ok_(__FILE__,line)(reobj.polesite == polesite, "got wrong site interface.\n");
3846 ok_(__FILE__,line)(reobj.dwUser == user, "got wrong user-defined value.\n");
3847}
3848
3849#define INSERT_REOBJECT(callback,reole,reobj,cp,user) \
3850 _insert_reobject(callback, reole, reobj, cp, user, __LINE__)
3852 REOBJECT *reobj, LONG cp, DWORD user, int line)
3853{
3855 HRESULT hr;
3856
3858 &CLSID_NULL, NULL, REO_CP_SELECTION /* cp overridden */, S_OK);
3859 hr = IRichEditOle_GetClientSite(reole, &clientsite);
3860 ok_(__FILE__,line)(hr == S_OK, "IRichEditOle_GetClientSite got hr %#lx.\n", hr);
3861 fill_reobject_struct(reobj, cp, NULL, NULL, clientsite, 10, 10, DVASPECT_CONTENT, 0, user);
3862 hr = IRichEditOle_InsertObject(reole, reobj);
3863 ok_(__FILE__,line)(hr == S_OK, "IRichEditOle_InsertObject got hr %#lx.\n", hr);
3864 IOleClientSite_Release(clientsite);
3866}
3867
3869{
3870 MSG msg;
3871 while (PeekMessageW( &msg, NULL, 0, 0, PM_REMOVE ))
3872 {
3875 }
3876}
3877
3879{
3880 static CHAR test_text1[] = "abcdefg";
3881 IRichEditOle *reole = NULL;
3882 ITextDocument *doc = NULL;
3883 REOBJECT reo1, reo2, reo3, received_reo;
3884 HRESULT hr;
3885 HWND hwnd;
3886 const WCHAR *expected_string, *string;
3887 const CHAR *expected_stringA;
3889 IDataObject *dataobject;
3890 TEXTRANGEA textrange;
3891 FORMATETC formatetc;
3892 CHARRANGE charrange;
3893 GETTEXTEX gettextex;
3894 STGMEDIUM stgmedium;
3895 WCHAR buffer[1024];
3896 CHAR bufferA[1024];
3897 LONG count, result;
3899 BSTR bstr;
3900 struct testoleobj *testobj;
3902 REOBJECT reobj;
3903 BOOL bad_getsel;
3904 DWORD gle;
3905
3906 create_interfaces(&hwnd, &reole, &doc, &selection);
3907 if (callback)
3908 {
3909 LRESULT sendres = SendMessageA(hwnd, EM_SETOLECALLBACK, 0, (LPARAM)&callback->IRichEditOleCallback_iface);
3910 ok( !!sendres, "EM_SETOLECALLBACK should succeed\n" );
3911 }
3912
3914 SendMessageA(hwnd, EM_SETSEL, 0, -1);
3915 *bufferA = '\0';
3916 SetLastError(0xdeadbeef);
3917 result = SendMessageA(hwnd, EM_GETSELTEXT, 0, (LPARAM)bufferA);
3918 gle = GetLastError();
3919 ok((result > 0 && gle == 0xdeadbeef) ||
3920 broken(result == 0 && gle == ERROR_INVALID_PARAMETER /* Hindi */),
3921 "EM_GETSELTEXT returned %ld gle=%lu\n", result, gle);
3922 bad_getsel = (gle != 0xdeadbeef);
3923 if (bad_getsel)
3924 trace("EM_GETSELTEXT is broken, some tests will be ignored\n");
3925
3926 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
3927
3928 hr = IRichEditOle_InsertObject(reole, NULL);
3929 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
3930
3931 /* insert object1 in (0, 1)*/
3932 SendMessageA(hwnd, EM_SETSEL, 0, 1);
3933 INSERT_REOBJECT(callback, reole, &reo1, REO_CP_SELECTION, 1);
3934 count = IRichEditOle_GetObjectCount(reole);
3935 ok(count == 1, "got wrong object count: %ld\n", count);
3936
3937 /* insert object2 in (2, 3)*/
3938 SendMessageA(hwnd, EM_SETSEL, 2, 3);
3939 INSERT_REOBJECT(callback, reole, &reo2, REO_CP_SELECTION, 2);
3940 count = IRichEditOle_GetObjectCount(reole);
3941 ok(count == 2, "got wrong object count: %ld\n", count);
3942
3943 /* insert object3 in (1, 2)*/
3944 SendMessageA(hwnd, EM_SETSEL, 1, 2);
3945 INSERT_REOBJECT(callback, reole, &reo3, REO_CP_SELECTION, 3);
3946 count = IRichEditOle_GetObjectCount(reole);
3947 ok(count == 3, "got wrong object count: %ld\n", count);
3948
3949 if (callback)
3950 {
3951 /* (fail to) insert object1 in (3, 4)*/
3952 SendMessageA(hwnd, EM_SETSEL, 3, 4);
3953
3954 hr = IRichEditOle_GetClientSite(reole, &clientsite);
3955 ok(hr == S_OK, "IRichEditOle_GetClientSite got hr %#lx.\n", hr);
3956
3958 &CLSID_NULL, NULL, REO_CP_SELECTION, S_FALSE);
3959 fill_reobject_struct(&reobj, REO_CP_SELECTION, NULL, NULL, clientsite, 10, 10, DVASPECT_CONTENT, 0, 0);
3960 hr = IRichEditOle_InsertObject(reole, &reobj);
3961 ok(hr == S_FALSE, "IRichEditOle_InsertObject got hr %#lx.\n", hr);
3963
3964 IOleClientSite_Release(clientsite);
3965
3966 count = IRichEditOle_GetObjectCount(reole);
3967 ok(count == 3, "got wrong object count: %ld\n", count);
3968 }
3969
3970 /* tests below show that order of rebject (from 0 to 2) is: reo1,reo3,reo2 */
3971 CHECK_REOBJECT_STRUCT(reole, 0, REO_GETOBJ_ALL_INTERFACES, 0, 0, NULL, NULL, reo1.polesite, 1);
3972 CHECK_REOBJECT_STRUCT(reole, 1, REO_GETOBJ_ALL_INTERFACES, 0, 1, NULL, NULL, reo3.polesite, 3);
3973 CHECK_REOBJECT_STRUCT(reole, 2, REO_GETOBJ_ALL_INTERFACES, 0, 2, NULL, NULL, reo2.polesite, 2);
3974
3975 hr = IRichEditOle_GetObject(reole, 2, NULL, REO_GETOBJ_ALL_INTERFACES);
3976 ok(hr == E_INVALIDARG, "IRichEditOle_GetObject should fail: 0x%08lx\n", hr);
3977
3978 received_reo.cbStruct = 0;
3979 hr = IRichEditOle_GetObject(reole, 2, &received_reo, REO_GETOBJ_ALL_INTERFACES);
3980 ok(hr == E_INVALIDARG, "IRichEditOle_GetObject should fail: 0x%08lx\n", hr);
3981
3982 CHECK_REOBJECT_STRUCT(reole, 2, REO_GETOBJ_PSTG, 0, 2, NULL, NULL, NULL, 2);
3983 CHECK_REOBJECT_STRUCT(reole, 2, REO_GETOBJ_POLESITE, 0, 2, NULL, NULL, reo2.polesite, 2);
3984
3985 hr = IRichEditOle_GetObject(reole, 3, &received_reo, REO_GETOBJ_POLESITE);
3986 ok(hr == E_INVALIDARG, "IRichEditOle_GetObject should fail: 0x%08lx\n", hr);
3987
3988 hr = IRichEditOle_GetObject(reole, 4, &received_reo, REO_GETOBJ_POLESITE);
3989 ok(hr == E_INVALIDARG, "IRichEditOle_GetObject should fail: 0x%08lx\n", hr);
3990
3991 hr = IRichEditOle_GetObject(reole, 1024, &received_reo, REO_GETOBJ_POLESITE);
3992 ok(hr == E_INVALIDARG, "IRichEditOle_GetObject should fail: 0x%08lx\n", hr);
3993
3994 hr = IRichEditOle_GetObject(reole, -10, &received_reo, REO_GETOBJ_POLESITE);
3995 ok(hr == E_INVALIDARG, "IRichEditOle_GetObject should fail: 0x%08lx\n", hr);
3996
3997 /* received_reo will be zeroed before be used */
3998 received_reo.cbStruct = sizeof(received_reo);
3999 received_reo.polesite = (IOleClientSite *)0xdeadbeef;
4000 hr = IRichEditOle_GetObject(reole, 2, &received_reo, REO_GETOBJ_NO_INTERFACES);
4001 ok(hr == S_OK, "IRichEditOle_GetObject failed: 0x%08lx\n", hr);
4002 ok(received_reo.polesite == NULL, "Got wrong site interface.\n");
4003
4004 CHECK_REOBJECT_STRUCT(reole, REO_IOB_USE_CP, REO_GETOBJ_ALL_INTERFACES, 0, 0, NULL, NULL, reo1.polesite, 1);
4005 CHECK_REOBJECT_STRUCT(reole, REO_IOB_USE_CP, REO_GETOBJ_ALL_INTERFACES, 1, 1, NULL, NULL, reo3.polesite, 3);
4006 CHECK_REOBJECT_STRUCT(reole, REO_IOB_USE_CP, REO_GETOBJ_ALL_INTERFACES, 2, 2, NULL, NULL, reo2.polesite, 2);
4007
4008 received_reo.cbStruct = sizeof(received_reo);
4009 received_reo.polesite = (IOleClientSite *)0xdeadbeef;
4010 received_reo.dwUser = 4;
4011 received_reo.cp = 4;
4012 hr = IRichEditOle_GetObject(reole, REO_IOB_USE_CP, &received_reo, REO_GETOBJ_ALL_INTERFACES);
4013 ok(hr == E_INVALIDARG, "IRichEditOle_GetObject should fail: 0x%08lx\n", hr);
4014 ok(received_reo.polesite == (IOleClientSite *)0xdeadbeef, "Got wrong site interface.\n");
4015 ok(received_reo.dwUser == 4, "Got wrong user-defined value: %ld.\n", received_reo.dwUser);
4016
4017 SendMessageA(hwnd, EM_SETSEL, 0, 1);
4018 CHECK_REOBJECT_STRUCT(reole, REO_IOB_SELECTION, REO_GETOBJ_ALL_INTERFACES, 0, 0, NULL, NULL, reo1.polesite, 1);
4019
4020 SendMessageA(hwnd, EM_SETSEL, 1, 2);
4021 CHECK_REOBJECT_STRUCT(reole, REO_IOB_SELECTION, REO_GETOBJ_ALL_INTERFACES, 0, 1, NULL, NULL, reo3.polesite, 3);
4022
4023 SendMessageA(hwnd, EM_SETSEL, 2, 3);
4024 CHECK_REOBJECT_STRUCT(reole, REO_IOB_SELECTION, REO_GETOBJ_ALL_INTERFACES, 0, 2, NULL, NULL, reo2.polesite, 2);
4025
4026 SendMessageA(hwnd, EM_SETSEL, 0, 2);
4027 CHECK_REOBJECT_STRUCT(reole, REO_IOB_SELECTION, REO_GETOBJ_ALL_INTERFACES, 0, 0, NULL, NULL, reo1.polesite, 1);
4028
4029 SendMessageA(hwnd, EM_SETSEL, 1, 3);
4030 CHECK_REOBJECT_STRUCT(reole, REO_IOB_SELECTION, REO_GETOBJ_ALL_INTERFACES, 0, 1, NULL, NULL, reo3.polesite, 3);
4031
4032 SendMessageA(hwnd, EM_SETSEL, 2, 0);
4033 CHECK_REOBJECT_STRUCT(reole, REO_IOB_SELECTION, REO_GETOBJ_ALL_INTERFACES, 0, 0, NULL, NULL, reo1.polesite, 1);
4034
4035 SendMessageA(hwnd, EM_SETSEL, 0, 6);
4036 CHECK_REOBJECT_STRUCT(reole, REO_IOB_SELECTION, REO_GETOBJ_ALL_INTERFACES, 0, 0, NULL, NULL, reo1.polesite, 1);
4037
4038 SendMessageA(hwnd, EM_SETSEL, 4, 5);
4039 received_reo.cbStruct = sizeof(received_reo);
4040 received_reo.cp = 0;
4041 hr = IRichEditOle_GetObject(reole, REO_IOB_SELECTION, &received_reo, REO_GETOBJ_ALL_INTERFACES);
4042 ok(hr == E_INVALIDARG, "IRichEditOle_GetObject should fail: 0x%08lx\n", hr);
4043
4044 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
4045
4046 /* "abc|d|efg" */
4047 INSERT_REOBJECT(callback, reole, &reo1, 3, 1);
4048 INSERT_REOBJECT(callback, reole, &reo2, 5, 2);
4049
4050 SendMessageW(hwnd, EM_SETSEL, 2, 3);
4052 ok(result == SEL_TEXT, "Got selection type: %lx.\n", result);
4053
4054 SendMessageW(hwnd, EM_SETSEL, 3, 4);
4056 ok(result == SEL_OBJECT, "Got selection type: %lx.\n", result);
4057 CHECK_REOBJECT_STRUCT(reole, REO_IOB_SELECTION, REO_GETOBJ_ALL_INTERFACES, 1, 3, NULL, NULL, reo1.polesite, 1);
4058
4059 SendMessageW(hwnd, EM_SETSEL, 2, 4);
4061 ok(result == (SEL_TEXT | SEL_OBJECT), "Got selection type: %lx.\n", result);
4062
4063 SendMessageW(hwnd, EM_SETSEL, 5, 6);
4064 CHECK_REOBJECT_STRUCT(reole, REO_IOB_SELECTION, REO_GETOBJ_ALL_INTERFACES, 1, 5, NULL, NULL, reo2.polesite, 2);
4065
4066#ifdef __REACTOS__
4067 expected_string = L"abc\xfffc"L"d\xfffc"L"efg";
4068#else
4069 expected_string = L"abc\xfffc""d\xfffc""efg";
4070#endif
4071
4072 gettextex.cb = sizeof(buffer);
4073 gettextex.flags = GT_DEFAULT;
4074 gettextex.codepage = 1200;
4075 gettextex.lpDefaultChar = NULL;
4076 gettextex.lpUsedDefChar = NULL;
4078 ok(result == lstrlenW(expected_string), "Got wrong length: %ld.\n", result);
4079 todo_wine ok(!lstrcmpW(buffer, expected_string), "Got wrong content: %s.\n", debugstr_w(buffer));
4080
4081 gettextex.flags = GT_RAWTEXT;
4082 memset(buffer, 0, sizeof(buffer));
4084 ok(result == lstrlenW(expected_string), "Got wrong length: %ld.\n", result);
4085 todo_wine ok(!lstrcmpW(buffer, expected_string), "Got wrong content: %s.\n", debugstr_w(buffer));
4086
4087 gettextex.flags = GT_NOHIDDENTEXT;
4088 memset(buffer, 0, sizeof(buffer));
4090 ok(result == lstrlenW(expected_string), "Got wrong length: %ld.\n", result);
4091 todo_wine ok(!lstrcmpW(buffer, expected_string), "Got wrong content: %s.\n", debugstr_w(buffer));
4092
4093 gettextex.flags = GT_SELECTION;
4094 memset(buffer, 0, sizeof(buffer));
4095 SendMessageW(hwnd, EM_SETSEL, 0, -1);
4097 ok(result == lstrlenW(expected_string), "Got wrong length: %ld.\n", result);
4098 todo_wine ok(!lstrcmpW(buffer, expected_string), "Got wrong content: %s.\n", debugstr_w(buffer));
4099
4100 expected_string = L"abc d efg";
4101 gettextex.flags = GT_USECRLF;
4102 memset(buffer, 0, sizeof(buffer));
4104 ok(result == lstrlenW(expected_string), "Got wrong length: %ld.\n", result);
4105 ok(!lstrcmpW(buffer, expected_string), "Got wrong content: %s.\n", debugstr_w(buffer));
4106
4107 expected_stringA = "abc d efg";
4108 memset(bufferA, 0, sizeof(bufferA));
4109 SendMessageA(hwnd, EM_SETSEL, 0, -1);
4110 SetLastError(0xdeadbeef);
4111 result = SendMessageA(hwnd, EM_GETSELTEXT, 0, (LPARAM)bufferA);
4112 gle = GetLastError();
4113 ok(result == strlen(expected_stringA) || broken(bad_getsel && result == 0),
4114 "Got wrong length: %ld (gle %lu)\n", result, gle);
4115 ok(!strcmp(bufferA, expected_stringA) || broken(bad_getsel && !*bufferA),
4116 "Got wrong content: %s (gle %lu)\n", bufferA, gle);
4117
4118 memset(bufferA, 0, sizeof(bufferA));
4119 textrange.lpstrText = bufferA;
4120 textrange.chrg.cpMin = 0;
4121 textrange.chrg.cpMax = 11;
4122 result = SendMessageA(hwnd, EM_GETTEXTRANGE, 0, (LPARAM)&textrange);
4123 ok(result == strlen(expected_stringA), "Got wrong length: %ld.\n", result);
4124 ok(!strcmp(bufferA, expected_stringA), "Got wrong content: %s.\n", bufferA);
4125
4126#ifdef __REACTOS__
4127 expected_string = L"abc\xfffc"L"d\xfffc"L"efg\r";
4128#else
4129 expected_string = L"abc\xfffc""d\xfffc""efg\r";
4130#endif
4131
4132 hr = ITextDocument_Range(doc, 0, 11, &range);
4133 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4134 hr = ITextRange_GetText(range, &bstr);
4135 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4136 ok(lstrlenW(bstr) == lstrlenW(expected_string), "Got wrong length: %d.\n", lstrlenW(bstr));
4137 todo_wine ok(!lstrcmpW(bstr, expected_string), "Got text: %s.\n", wine_dbgstr_w(bstr));
4138 SysFreeString(bstr);
4139 hr = ITextRange_SetRange(range, 3, 4);
4140 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4141 hr = ITextRange_GetChar(range, &result);
4142 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4143 todo_wine ok(result == 0xfffc, "Got char: %lc\n", (WCHAR)result);
4144 ITextRange_Release(range);
4145
4146 SendMessageW(hwnd, EM_SETSEL, 0, -1);
4147 hr = ITextSelection_GetText(selection, &bstr);
4148 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4149 ok(lstrlenW(bstr) == lstrlenW(expected_string), "Got wrong length: %d.\n", lstrlenW(bstr));
4150 todo_wine ok(!lstrcmpW(bstr, expected_string), "Got text: %s.\n", wine_dbgstr_w(bstr));
4151 SysFreeString(bstr);
4152 SendMessageW(hwnd, EM_SETSEL, 3, 4);
4153 result = 0;
4154 hr = ITextSelection_GetChar(selection, &result);
4155 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4156 todo_wine ok(result == 0xfffc, "Got char: %lc\n", (WCHAR)result);
4157
4160 ok(!result, "Got result %lx.\n", result);
4161 /* "abc|d|efg" */
4162 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
4163 INSERT_REOBJECT(callback, reole, &reo1, 3, 1);
4164 INSERT_REOBJECT(callback, reole, &reo2, 5, 2);
4165
4166 expected_string = L"abc d efg";
4167 charrange.cpMin = 0;
4168 charrange.cpMax = 11;
4169 hr = IRichEditOle_GetClipboardData(reole, &charrange, 1, &dataobject);
4170 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4171 formatetc.cfFormat = CF_UNICODETEXT;
4172 formatetc.dwAspect = DVASPECT_CONTENT;
4173 formatetc.ptd = NULL;
4174 formatetc.tymed = TYMED_HGLOBAL;
4175 formatetc.lindex = -1;
4176 hr = IDataObject_GetData(dataobject, &formatetc, &stgmedium);
4177 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4178 string = GlobalLock(stgmedium.hGlobal);
4179 ok(lstrlenW(string) == lstrlenW(expected_string), "Got wrong length: %d.\n", lstrlenW(string));
4180 ok(!lstrcmpW(string, expected_string), "Got wrong content: %s.\n", debugstr_w(string));
4181 GlobalUnlock(stgmedium.hGlobal);
4182
4183#ifdef __REACTOS__
4184 expected_string = L"abc\xfffc"L"d\xfffc"L"efg";
4185#else
4186 expected_string = L"abc\xfffc""d\xfffc""efg";
4187#endif
4188
4189 gettextex.cb = sizeof(buffer);
4190 gettextex.flags = GT_DEFAULT;
4191 gettextex.codepage = 1200;
4192 gettextex.lpDefaultChar = NULL;
4193 gettextex.lpUsedDefChar = NULL;
4195 ok(result == lstrlenW(expected_string), "Got wrong length: %ld.\n", result);
4196 todo_wine ok(!lstrcmpW(buffer, expected_string), "Got wrong content: %s.\n", debugstr_w(buffer));
4197
4198 gettextex.flags = GT_RAWTEXT;
4199 memset(buffer, 0, sizeof(buffer));
4201 ok(result == lstrlenW(expected_string), "Got wrong length: %ld.\n", result);
4202 todo_wine ok(!lstrcmpW(buffer, expected_string), "Got wrong content: %s.\n", debugstr_w(buffer));
4203
4204 expected_stringA = "abc d efg";
4205 memset(bufferA, 0, sizeof(bufferA));
4206 SendMessageA(hwnd, EM_SETSEL, 0, -1);
4207 SetLastError(0xdeadbeef);
4208 result = SendMessageA(hwnd, EM_GETSELTEXT, 0, (LPARAM)bufferA);
4209 gle = GetLastError();
4210 ok(result == strlen(expected_stringA) || broken(bad_getsel && result == 0),
4211 "Got wrong length: %ld (gle %lu)\n", result, gle);
4212 ok(!strcmp(bufferA, expected_stringA) || broken(bad_getsel && !*bufferA),
4213 "Got wrong content: %s (gle %lu)\n", bufferA, gle);
4214
4215 memset(bufferA, 0, sizeof(bufferA));
4216 textrange.lpstrText = bufferA;
4217 textrange.chrg.cpMin = 0;
4218 textrange.chrg.cpMax = 11;
4219 result = SendMessageA(hwnd, EM_GETTEXTRANGE, 0, (LPARAM)&textrange);
4220 ok(result == strlen(expected_stringA), "Got wrong length: %ld.\n", result);
4221 ok(!strcmp(bufferA, expected_stringA), "Got wrong content: %s.\n", bufferA);
4222
4223#ifdef __REACTOS__
4224 expected_string = L"abc\xfffc"L"d\xfffc"L"efg";
4225#else
4226 expected_string = L"abc\xfffc""d\xfffc""efg";
4227#endif
4228
4229 hr = ITextDocument_Range(doc, 0, 11, &range);
4230 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4231 hr = ITextRange_GetText(range, &bstr);
4232 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4233 todo_wine ok(lstrlenW(bstr) == lstrlenW(expected_string), "Got wrong length: %d.\n", lstrlenW(bstr));
4234 todo_wine ok(!lstrcmpW(bstr, expected_string), "Got text: %s.\n", wine_dbgstr_w(bstr));
4235 SysFreeString(bstr);
4236 hr = ITextRange_SetRange(range, 3, 4);
4237 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4238 hr = ITextRange_GetChar(range, &result);
4239 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4240 todo_wine ok(result == 0xfffc, "Got char: %lc\n", (WCHAR)result);
4241 ITextRange_Release(range);
4242
4243 SendMessageW(hwnd, EM_SETSEL, 0, -1);
4244 hr = ITextSelection_GetText(selection, &bstr);
4245 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4246 todo_wine ok(lstrlenW(bstr) == lstrlenW(expected_string), "Got wrong length: %d.\n", lstrlenW(bstr));
4247 todo_wine ok(!lstrcmpW(bstr, expected_string), "Got text: %s.\n", wine_dbgstr_w(bstr));
4248 SysFreeString(bstr);
4249 SendMessageW(hwnd, EM_SETSEL, 3, 4);
4250 result = 0;
4251 hr = ITextSelection_GetChar(selection, &result);
4252 ok(hr == S_OK, "Got hr %#lx.\n", hr);
4253 todo_wine ok(result == 0xfffc, "Got char: %lc\n", (WCHAR)result);
4254
4256 ok(hr == S_OK, "testoleobj_Create got hr %#lx.\n", hr);
4257 testobj->extent.cx = 800;
4258 testobj->extent.cy = 400;
4259
4261 testobj->draw_count = 0;
4262 testobj->line = __LINE__;
4263
4264 hr = IRichEditOle_GetClientSite(reole, &clientsite);
4265 ok(hr == S_OK, "IRichEditOle_GetClientSite got hr %#lx.\n", hr);
4266 hr = IOleObject_SetClientSite(&testobj->IOleObject_iface, clientsite);
4267 ok(hr == S_OK, "IOleObject_SetClientSite got hr %#lx.\n", hr);
4268
4270 &CLSID_testoleobj, NULL, REO_CP_SELECTION, S_OK);
4271 fill_reobject_struct(&reobj, REO_CP_SELECTION, &testobj->IOleObject_iface, NULL, clientsite, 800, 400, DVASPECT_CONTENT, 0, 0);
4272 reobj.clsid = CLSID_testoleobj;
4273 hr = IRichEditOle_InsertObject(reole, &reobj);
4274 ok(hr == S_OK, "IRichEditOle_InsertObject got hr %#lx.\n", hr);
4276
4277 IOleClientSite_Release(clientsite);
4278
4279 testobj->line = __LINE__;
4281 testobj->line = __LINE__;
4283 ok(testobj->draw_count != 0, "expected draw_count to be nonzero, got %d\n", testobj->draw_count);
4284
4286 testobj->draw_count = 0;
4287 testobj->line = __LINE__;
4288
4289 hr = IRichEditOle_GetClientSite(reole, &clientsite);
4290 ok(hr == S_OK, "IRichEditOle_GetClientSite got hr %#lx.\n", hr);
4291 hr = IOleObject_SetClientSite(&testobj->IOleObject_iface, clientsite);
4292 ok(hr == S_OK, "IOleObject_SetClientSite got hr %#lx.\n", hr);
4293
4295 &CLSID_testoleobj, NULL, REO_CP_SELECTION, S_OK);
4296 fill_reobject_struct(&reobj, REO_CP_SELECTION, &testobj->IOleObject_iface, NULL, clientsite, 0, 0, DVASPECT_CONTENT, 0, 0);
4297 reobj.clsid = CLSID_testoleobj;
4298 hr = IRichEditOle_InsertObject(reole, &reobj);
4299 ok(hr == S_OK, "IRichEditOle_InsertObject got hr %#lx.\n", hr);
4301
4302 memset(&reobj, 0xcc, sizeof(reobj));
4303 reobj.cbStruct = sizeof(reobj);
4304 hr = IRichEditOle_GetObject(reole, 0, &reobj, REO_GETOBJ_NO_INTERFACES);
4305 ok(hr == S_OK, "IRichEditOle_GetObject got hr %#lx.\n", hr);
4306 ok(reobj.sizel.cx == 800, "expected reobj.sizel.cx to be %ld, got %ld\n", 800L, reobj.sizel.cx);
4307 ok(reobj.sizel.cy == 400, "expected reobj.sizel.cy to be %ld, got %ld\n", 400L, reobj.sizel.cy);
4308 IOleClientSite_Release(clientsite);
4309
4310 testobj->line = __LINE__;
4312 testobj->line = __LINE__;
4314 ok(testobj->draw_count != 0, "expected draw_count to be nonzero, got %d\n", testobj->draw_count);
4315
4317 IOleObject_Release(&testobj->IOleObject_iface);
4318
4319 if (callback)
4320 {
4321 LRESULT sendres = SendMessageA(hwnd, EM_SETOLECALLBACK, 0, 0);
4322 ok( !!sendres, "EM_SETOLECALLBACK should succeed\n" );
4323 }
4324
4325 release_interfaces(&hwnd, &reole, &doc, &selection);
4326}
4327
4328static void test_InsertObject(void)
4329{
4330 struct reolecb_obj *callback;
4331 HRESULT hr;
4332 ULONG ref;
4333
4335
4337 ok(SUCCEEDED(hr), "reolecb_obj_Create returned %#lx\n", hr);
4338 if (SUCCEEDED(hr))
4339 {
4341 ref = IRichEditOleCallback_Release(&callback->IRichEditOleCallback_iface);
4342 ok(ref == 0, "expected IRichEditOleCallback recount to be 0, got %lu\n", ref);
4343 }
4344 else
4345 {
4346 skip("cannot test InsertObject with callback\n");
4347 }
4348}
4349
4350static void test_GetStoryLength(void)
4351{
4352 static const CHAR test_text1[] = "TestSomeText";
4353 IRichEditOle *reOle = NULL;
4354 ITextDocument *doc = NULL;
4357 LONG value;
4358 HRESULT hr;
4359 HWND hwnd;
4360
4361 create_interfaces(&hwnd, &reOle, &doc, &selection);
4362 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
4363 SendMessageA(hwnd, EM_SETSEL, 1, 2);
4364
4365 hr = ITextDocument_Range(doc, 0, 4, &range);
4366 ok(hr == S_OK, "got 0x%08lx\n", hr);
4367
4368 hr = ITextRange_GetStoryLength(range, NULL);
4369 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
4370
4371 value = 0;
4372 hr = ITextRange_GetStoryLength(range, &value);
4373 ok(hr == S_OK, "got 0x%08lx\n", hr);
4374 ok(value == 13, "got %ld\n", value);
4375
4376 hr = ITextSelection_GetStoryLength(selection, NULL);
4377 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
4378
4379 value = 0;
4380 hr = ITextSelection_GetStoryLength(selection, &value);
4381 ok(hr == S_OK, "got 0x%08lx\n", hr);
4382 ok(value == 13, "got %ld\n", value);
4383
4385
4386 value = 0;
4387 hr = ITextRange_GetStoryLength(range, &value);
4388 ok(hr == S_OK, "got 0x%08lx\n", hr);
4389 ok(value == 1, "got %ld\n", value);
4390
4391 value = 0;
4392 hr = ITextSelection_GetStoryLength(selection, &value);
4393 ok(hr == S_OK, "got 0x%08lx\n", hr);
4394 ok(value == 1, "got %ld\n", value);
4395
4396 release_interfaces(&hwnd, &reOle, &doc, NULL);
4397
4398 hr = ITextRange_GetStoryLength(range, NULL);
4399 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4400
4401 value = 100;
4402 hr = ITextRange_GetStoryLength(range, &value);
4403 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4404 ok(value == 100, "got %ld\n", value);
4405
4406 hr = ITextSelection_GetStoryLength(selection, NULL);
4407 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4408
4409 value = 100;
4410 hr = ITextSelection_GetStoryLength(selection, &value);
4411 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4412 ok(value == 100, "got %ld\n", value);
4413
4414 ITextSelection_Release(selection);
4415 ITextRange_Release(range);
4416}
4417
4419{
4420 static const CHAR test_text1[] = "TestSomeText";
4421 IRichEditOle *reOle = NULL;
4422 ITextDocument *doc = NULL;
4423 ITextSelection *selection, *sel2;
4424 ITextRange *range, *range2;
4425 ITextFont *font;
4426 LONG value;
4427 HRESULT hr;
4428 HWND hwnd;
4429
4430 create_interfaces(&hwnd, &reOle, &doc, &selection);
4431 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
4432 SendMessageA(hwnd, EM_SETSEL, 1, 2);
4433
4434 hr = ITextSelection_GetDuplicate(selection, NULL);
4435 ok(hr == E_INVALIDARG, "got 0x%08lx\n", hr);
4436
4438
4439 hr = ITextSelection_GetDuplicate(selection, &range);
4440 ok(hr == S_OK, "got 0x%08lx\n", hr);
4441
4442 hr = ITextSelection_GetDuplicate(selection, &range2);
4443 ok(hr == S_OK, "got 0x%08lx\n", hr);
4444 ok(range != range2, "got %p, %p\n", range, range2);
4445
4447 EXPECT_REF(range, 1);
4448 EXPECT_REF(range2, 1);
4449
4450 ITextRange_Release(range2);
4451
4452 value = 0;
4453 hr = ITextRange_GetStart(range, &value);
4454 ok(hr == S_OK, "got 0x%08lx\n", hr);
4455 ok(value == 1, "got %ld\n", value);
4456
4457 value = 0;
4458 hr = ITextRange_GetEnd(range, &value);
4459 ok(hr == S_OK, "got 0x%08lx\n", hr);
4460 ok(value == 2, "got %ld\n", value);
4461
4462 SendMessageA(hwnd, EM_SETSEL, 2, 3);
4463
4464 value = 0;
4465 hr = ITextRange_GetStart(range, &value);
4466 ok(hr == S_OK, "got 0x%08lx\n", hr);
4467 ok(value == 1, "got %ld\n", value);
4468
4469 value = 0;
4470 hr = ITextRange_GetEnd(range, &value);
4471 ok(hr == S_OK, "got 0x%08lx\n", hr);
4472 ok(value == 2, "got %ld\n", value);
4473
4474 hr = ITextRange_QueryInterface(range, &IID_ITextSelection, (void**)&sel2);
4475 ok(hr == E_NOINTERFACE, "got 0x%08lx\n", hr);
4476
4477 release_interfaces(&hwnd, &reOle, &doc, NULL);
4478
4479 hr = ITextSelection_GetDuplicate(selection, NULL);
4480 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4481
4482 hr = ITextSelection_GetDuplicate(selection, &range);
4483 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4484
4485 hr = ITextRange_GetFont(range, &font);
4486 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4487
4488 ITextSelection_Release(selection);
4489 ITextRange_Release(range);
4490}
4491
4492#define RESET_RANGE(range,start,end) \
4493 _reset_range(range, start, end, __LINE__)
4495{
4496 HRESULT hr;
4497
4498 hr = ITextRange_SetStart(range, start);
4499 ok_(__FILE__,line)(hr == S_OK, "SetStart failed: 0x%08lx\n", hr);
4500 hr = ITextRange_SetEnd(range, end);
4501 ok_(__FILE__,line)(hr == S_OK, "SetEnd failed: 0x%08lx\n", hr);
4502}
4503
4504#define CHECK_RANGE(range,expected_start,expected_end) \
4505 _check_range(range, expected_start, expected_end, __LINE__)
4506static void _check_range(ITextRange* range, LONG expected_start, LONG expected_end, int line)
4507{
4508 HRESULT hr;
4509 LONG value;
4510
4511 hr = ITextRange_GetStart(range, &value);
4512 ok_(__FILE__,line)(hr == S_OK, "GetStart failed: 0x%08lx\n", hr);
4513 ok_(__FILE__,line)(value == expected_start, "Expected start %ld got %ld\n",
4514 expected_start, value);
4515 hr = ITextRange_GetEnd(range, &value);
4516 ok_(__FILE__,line)(hr == S_OK, "GetEnd failed: 0x%08lx\n", hr);
4517 ok_(__FILE__,line)(value == expected_end, "Expected end %ld got %ld\n",
4518 expected_end, value);
4519}
4520
4521#define RESET_SELECTION(selection,start,end) \
4522 _reset_selection(selection, start, end, __LINE__)
4524{
4525 HRESULT hr;
4526
4527 hr = ITextSelection_SetStart(selection, start);
4528 ok_(__FILE__,line)(hr == S_OK, "SetStart failed: 0x%08lx\n", hr);
4529 hr = ITextSelection_SetEnd(selection, end);
4530 ok_(__FILE__,line)(hr == S_OK, "SetEnd failed: 0x%08lx\n", hr);
4531}
4532
4533#define CHECK_SELECTION(selection,expected_start,expected_end) \
4534 _check_selection(selection, expected_start, expected_end, __LINE__)
4535static void _check_selection(ITextSelection *selection, LONG expected_start, LONG expected_end, int line)
4536{
4537 HRESULT hr;
4538 LONG value;
4539
4540 hr = ITextSelection_GetStart(selection, &value);
4541 ok_(__FILE__,line)(hr == S_OK, "GetStart failed: 0x%08lx\n", hr);
4542 ok_(__FILE__,line)(value == expected_start, "Expected start %ld got %ld\n",
4543 expected_start, value);
4544 hr = ITextSelection_GetEnd(selection, &value);
4545 ok_(__FILE__,line)(hr == S_OK, "GetEnd failed: 0x%08lx\n", hr);
4546 ok_(__FILE__,line)(value == expected_end, "Expected end %ld got %ld\n",
4547 expected_end, value);
4548}
4549
4551{
4552 static const CHAR test_text1[] = "TestSomeText";
4553 ITextDocument *txtDoc = NULL;
4554 IRichEditOle *reOle = NULL;
4555 ITextRange *txtRge = NULL;
4556 HRESULT hr;
4557 HWND w;
4558
4559 create_interfaces(&w, &reOle, &txtDoc, NULL);
4560 SendMessageA(w, WM_SETTEXT, 0, (LPARAM)test_text1);
4561 ITextDocument_Range(txtDoc, 0, 0, &txtRge);
4562
4563 hr = ITextRange_SetRange(txtRge, 2, 4);
4564 ok(hr == S_OK, "got 0x%08lx.\n", hr);
4565 CHECK_RANGE(txtRge, 2, 4);
4566
4567 hr = ITextRange_SetRange(txtRge, 2, 4);
4568 ok(hr == S_FALSE, "got 0x%08lx.\n", hr);
4569 CHECK_RANGE(txtRge, 2, 4);
4570
4571 hr = ITextRange_SetRange(txtRge, 4, 2);
4572 ok(hr == S_FALSE, "got 0x%08lx.\n", hr);
4573 CHECK_RANGE(txtRge, 2, 4);
4574
4575 hr = ITextRange_SetRange(txtRge, 14, 14);
4576 ok(hr == S_OK, "got 0x%08lx.\n", hr);
4577 CHECK_RANGE(txtRge, 12, 12);
4578
4579 hr = ITextRange_SetRange(txtRge, 15, 15);
4580 ok(hr == S_FALSE, "got 0x%08lx.\n", hr);
4581 CHECK_RANGE(txtRge, 12, 12);
4582
4583 hr = ITextRange_SetRange(txtRge, 14, 1);
4584 ok(hr == S_OK, "got 0x%08lx.\n", hr);
4585 CHECK_RANGE(txtRge, 1, 13);
4586
4587 hr = ITextRange_SetRange(txtRge, -1, 4);
4588 ok(hr == S_OK, "got 0x%08lx.\n", hr);
4589 CHECK_RANGE(txtRge, 0, 4);
4590
4591 ITextRange_Release(txtRge);
4592 release_interfaces(&w, &reOle, &txtDoc, NULL);
4593}
4594
4595static void test_Expand(void)
4596{
4597 static const char test_text1[] = "TestSomeText";
4598 IRichEditOle *reole = NULL;
4599 ITextDocument *doc = NULL;
4602 LONG value;
4603 HRESULT hr;
4604 HWND hwnd;
4605
4606 create_interfaces(&hwnd, &reole, &doc, &selection);
4607 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
4608 SendMessageA(hwnd, EM_SETSEL, 1, 2);
4609
4610 hr = ITextDocument_Range(doc, 0, 4, &range);
4611 ok(hr == S_OK, "got 0x%08lx\n", hr);
4612
4613 hr = ITextRange_Expand(range, tomStory, NULL);
4614 ok(hr == S_OK, "got 0x%08lx\n", hr);
4615 CHECK_RANGE(range, 0, 13);
4616
4617 hr = ITextSelection_Expand(selection, tomStory, NULL);
4618 ok(hr == S_OK, "got 0x%08lx\n", hr);
4619 CHECK_SELECTION(selection, 0, 13);
4620
4621 RESET_RANGE(range, 1, 2);
4623
4624 value = 0;
4625 hr = ITextRange_Expand(range, tomStory, &value);
4626 ok(hr == S_OK, "got 0x%08lx\n", hr);
4627 ok(value == 12, "got %ld\n", value);
4628 CHECK_RANGE(range, 0, 13);
4629
4630 value = 0;
4631 hr = ITextSelection_Expand(selection, tomStory, &value);
4632 ok(hr == S_OK, "got 0x%08lx\n", hr);
4633 ok(value == 12, "got %ld\n", value);
4634 CHECK_SELECTION(selection, 0, 13);
4635
4636 release_interfaces(&hwnd, &reole, &doc, NULL);
4637
4638 hr = ITextRange_Expand(range, tomStory, NULL);
4639 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4640
4641 hr = ITextRange_Expand(range, tomStory, &value);
4642 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4643
4644 hr = ITextSelection_Expand(selection, tomStory, NULL);
4645 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4646
4647 hr = ITextSelection_Expand(selection, tomStory, &value);
4648 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4649
4650 ITextSelection_Release(selection);
4651 ITextRange_Release(range);
4652}
4653
4654static void test_MoveEnd_story(void)
4655{
4656 static const char test_text1[] = "Word1 Word2";
4657 IRichEditOle *reole = NULL;
4658 ITextDocument *doc = NULL;
4661 LONG delta;
4662 HRESULT hr;
4663 HWND hwnd;
4664
4665 create_interfaces(&hwnd, &reole, &doc, &selection);
4666 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
4667 SendMessageA(hwnd, EM_SETSEL, 1, 2);
4668
4669 hr = ITextDocument_Range(doc, 1, 2, &range);
4670 ok(hr == S_OK, "got 0x%08lx\n", hr);
4671
4672 hr = ITextRange_MoveEnd(range, tomStory, 0, &delta);
4673 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
4674 ok(delta == 0, "got %ld\n", delta);
4675 CHECK_RANGE(range, 1, 2);
4676
4677 hr = ITextRange_MoveEnd(range, tomStory, -1, &delta);
4678 ok(hr == S_OK, "got 0x%08lx\n", hr);
4679 ok(delta == -1, "got %ld\n", delta);
4680 CHECK_RANGE(range, 0, 0);
4681
4682 hr = ITextRange_MoveEnd(range, tomStory, 1, &delta);
4683 ok(hr == S_OK, "got 0x%08lx\n", hr);
4684 ok(delta == 1, "got %ld\n", delta);
4685 CHECK_RANGE(range, 0, 12);
4686
4687 hr = ITextRange_MoveEnd(range, tomStory, 1, &delta);
4688 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
4689 ok(delta == 0, "got %ld\n", delta);
4690 CHECK_RANGE(range, 0, 12);
4691
4692 RESET_RANGE(range, 1, 2);
4693
4694 hr = ITextRange_MoveEnd(range, tomStory, 3, &delta);
4695 ok(hr == S_OK, "got 0x%08lx\n", hr);
4696 ok(delta == 1, "got %ld\n", delta);
4697 CHECK_RANGE(range, 1, 12);
4698
4699 RESET_RANGE(range, 2, 3);
4700
4701 hr = ITextRange_MoveEnd(range, tomStory, -3, &delta);
4702 ok(hr == S_OK, "got 0x%08lx\n", hr);
4703 ok(delta == -1, "got %ld\n", delta);
4704 CHECK_RANGE(range, 0, 0);
4705
4706 hr = ITextRange_MoveEnd(range, tomStory, -1, &delta);
4707 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
4708 ok(delta == 0, "got %ld\n", delta);
4709 CHECK_RANGE(range, 0, 0);
4710
4711 hr = ITextSelection_MoveEnd(selection, tomStory, 0, &delta);
4712 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
4713 ok(delta == 0, "got %ld\n", delta);
4715
4716 hr = ITextSelection_MoveEnd(selection, tomStory, -1, &delta);
4717 ok(hr == S_OK, "got 0x%08lx\n", hr);
4718 ok(delta == -1, "got %ld\n", delta);
4720
4721 hr = ITextSelection_MoveEnd(selection, tomStory, 1, &delta);
4722 ok(hr == S_OK, "got 0x%08lx\n", hr);
4723 ok(delta == 1, "got %ld\n", delta);
4724 CHECK_SELECTION(selection, 0, 12);
4725
4726 hr = ITextSelection_MoveEnd(selection, tomStory, 1, &delta);
4727 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
4728 ok(delta == 0, "got %ld\n", delta);
4729 CHECK_SELECTION(selection, 0, 12);
4730
4732
4733 hr = ITextSelection_MoveEnd(selection, tomStory, 3, &delta);
4734 ok(hr == S_OK, "got 0x%08lx\n", hr);
4735 ok(delta == 1, "got %ld\n", delta);
4736 CHECK_SELECTION(selection, 1, 12);
4737
4739
4740 hr = ITextSelection_MoveEnd(selection, tomStory, -3, &delta);
4741 ok(hr == S_OK, "got 0x%08lx\n", hr);
4742 ok(delta == -1, "got %ld\n", delta);
4744
4745 hr = ITextSelection_MoveEnd(selection, tomStory, -1, &delta);
4746 ok(hr == S_FALSE, "got 0x%08lx\n", hr);
4747 ok(delta == 0, "got %ld\n", delta);
4749
4750 release_interfaces(&hwnd, &reole, &doc, NULL);
4751
4752 hr = ITextRange_MoveEnd(range, tomStory, 1, NULL);
4753 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4754
4755 hr = ITextRange_MoveEnd(range, tomStory, 1, &delta);
4756 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4757
4758 hr = ITextSelection_MoveEnd(selection, tomStory, 1, NULL);
4759 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4760
4761 hr = ITextSelection_MoveEnd(selection, tomStory, 1, &delta);
4762 ok(hr == CO_E_RELEASED, "got 0x%08lx\n", hr);
4763
4764 ITextSelection_Release(selection);
4765 ITextRange_Release(range);
4766}
4767
4768static void test_character_movestart(ITextRange *range, int textlen, int i, int j, LONG target)
4769{
4770 HRESULT hr;
4771 LONG delta = 0;
4772 LONG expected_delta;
4773 LONG expected_start = target;
4774
4775 if (expected_start < 0)
4776 expected_start = 0;
4777 else if (expected_start > textlen)
4778 expected_start = textlen;
4779 expected_delta = expected_start - i;
4780 hr = ITextRange_SetRange(range, i, j);
4781 ok(SUCCEEDED(hr), "got 0x%08lx\n", hr);
4782 hr = ITextRange_MoveStart(range, tomCharacter, target - i, &delta);
4783 if (expected_start == i) {
4784 ok(hr == S_FALSE, "(%d,%d) move by %ld got hr=0x%08lx\n", i, j, target - i, hr);
4785 ok(delta == 0, "(%d,%d) move by %ld got delta %ld\n", i, j, target - i, delta);
4786 CHECK_RANGE(range, i, j);
4787 } else {
4788 ok(hr == S_OK, "(%d,%d) move by %ld got hr=0x%08lx\n", i, j, target - i, hr);
4789 ok(delta == expected_delta, "(%d,%d) move by %ld got delta %ld\n", i, j, target - i, delta);
4790 if (expected_start <= j)
4791 CHECK_RANGE(range, expected_start, j);
4792 else
4793 CHECK_RANGE(range, expected_start, expected_start);
4794 }
4795}
4796
4797static void test_character_moveend(ITextRange *range, int textlen, int i, int j, LONG target)
4798{
4799 HRESULT hr;
4800 LONG delta;
4801 LONG expected_delta;
4802 LONG expected_end = target;
4803
4804 if (expected_end < 0)
4805 expected_end = 0;
4806 else if (expected_end > textlen + 1)
4807 expected_end = textlen + 1;
4808 expected_delta = expected_end - j;
4809 hr = ITextRange_SetRange(range, i, j);
4810 ok(SUCCEEDED(hr), "got 0x%08lx\n", hr);
4811 hr = ITextRange_MoveEnd(range, tomCharacter, target - j, &delta);
4812 if (expected_end == j) {
4813 ok(hr == S_FALSE, "(%d,%d) move by %ld got hr=0x%08lx\n", i, j, target - j, hr);
4814 ok(delta == 0, "(%d,%d) move by %ld got delta %ld\n", i, j, target - j, delta);
4815 CHECK_RANGE(range, i, j);
4816 } else {
4817 ok(hr == S_OK, "(%d,%d) move by %ld got hr=0x%08lx\n", i, j, target - j, hr);
4818 ok(delta == expected_delta, "(%d,%d) move by %ld got delta %ld\n", i, j, target - j, delta);
4819 if (i <= expected_end)
4820 CHECK_RANGE(range, i, expected_end);
4821 else
4822 CHECK_RANGE(range, expected_end, expected_end);
4823 }
4824}
4825
4826static void test_character_move(ITextRange *range, int textlen, int i, int j, LONG target)
4827{
4828 HRESULT hr;
4829 LONG move_by;
4830 LONG delta = 0;
4831 LONG expected_delta;
4832 LONG expected_location = target;
4833
4834 if (expected_location < 0)
4835 expected_location = 0;
4836 else if (expected_location > textlen)
4837 expected_location = textlen;
4838
4839 if (target <= i) {
4840 move_by = target - i;
4841 expected_delta = expected_location - i;
4842 if (i != j) {
4843 --move_by;
4844 --expected_delta;
4845 }
4846 } else if (j <= target) {
4847 move_by = target - j;
4848 expected_delta = expected_location - j;
4849 if (i != j) {
4850 ++move_by;
4851 ++expected_delta;
4852 }
4853 } else {
4854 /* There's no way to move to a point between start and end: */
4855 return;
4856 }
4857
4858 hr = ITextRange_SetRange(range, i, j);
4859 ok(SUCCEEDED(hr), "got 0x%08lx\n", hr);
4860 hr = ITextRange_Move(range, tomCharacter, move_by, &delta);
4861 if (expected_delta == 0) {
4862 ok(hr == S_FALSE, "(%d,%d) move by %ld got hr=0x%08lx\n", i, j, move_by, hr);
4863 ok(delta == 0, "(%d,%d) move by %ld got delta %ld\n", i, j, move_by, delta);
4864 CHECK_RANGE(range, expected_location, expected_location);
4865 } else {
4866 ok(hr == S_OK, "(%d,%d) move by %ld got hr=0x%08lx\n", i, j, move_by, hr);
4867 ok(delta == expected_delta, "(%d,%d) move by %ld got delta %ld\n", i, j, move_by, delta);
4868 CHECK_RANGE(range, expected_location, expected_location);
4869 }
4870}
4871
4872static void test_character_startof(ITextRange *range, int textlen, int i, int j)
4873{
4874 HRESULT hr;
4875 LONG delta;
4876
4877 hr = ITextRange_SetRange(range, i, j);
4878 ok(SUCCEEDED(hr), "got 0x%08lx\n", hr);
4879 hr = ITextRange_StartOf(range, tomCharacter, tomMove, &delta);
4880 if (i == j) {
4881 ok(hr == S_FALSE, "(%d,%d) tomMove got hr=0x%08lx\n", i, j, hr);
4882 ok(delta == 0, "(%d,%d) tomMove got delta %ld\n", i, j, delta);
4883 } else {
4884 ok(hr == S_OK, "(%d,%d) tomMove got hr=0x%08lx\n", i, j, hr);
4885 ok(delta == -1, "(%d,%d) tomMove got delta %ld\n", i, j, delta);
4886 }
4887 CHECK_RANGE(range, i, i);
4888
4889 hr = ITextRange_SetRange(range, i, j);
4890 ok(SUCCEEDED(hr), "got 0x%08lx\n", hr);
4891 hr = ITextRange_StartOf(range, tomCharacter, tomExtend, &delta);
4892 ok(hr == S_FALSE, "(%d,%d) tomExtend got hr=0x%08lx\n", i, j, hr);
4893 ok(delta == 0, "(%d,%d) tomExtend got delta %ld\n", i, j, delta);
4894 CHECK_RANGE(range, i, j);
4895}
4896
4897static void test_character_endof(ITextRange *range, int textlen, int i, int j)
4898{
4899 HRESULT hr;
4900 LONG end;
4901 LONG delta;
4902
4903 hr = ITextRange_SetRange(range, i, j);
4904 ok(SUCCEEDED(hr), "got 0x%08lx\n", hr);
4905 hr = ITextRange_EndOf(range, tomCharacter, tomMove, &delta);
4906
4907 /* A character "end", apparently cannot be before the very first character */
4908 end = j;
4909 if (j == 0)
4910 ++end;
4911
4912 if (i == end) {
4913 ok(hr == S_FALSE, "(%d,%d) tomMove got hr=0x%08lx\n", i, j, hr);
4914 ok(delta == 0, "(%d,%d) tomMove got delta %ld\n", i, j, delta);
4915 } else {
4916 ok(hr == S_OK, "(%d,%d) tomMove got hr=0x%08lx\n", i, j, hr);
4917 ok(delta == 1, "(%d,%d) tomMove got delta %ld\n", i, j, delta);
4918 }
4920
4921 hr = ITextRange_SetRange(range, i, j);
4922 ok(SUCCEEDED(hr), "got 0x%08lx\n", hr);
4923 hr = ITextRange_EndOf(range, tomCharacter, tomExtend, &delta);
4924 if (0 < j) {
4925 ok(hr == S_FALSE, "(%d,%d) tomExtend got hr=0x%08lx\n", i, j, hr);
4926 ok(delta == 0, "(%d,%d) tomExtend got delta %ld\n", i, j, delta);
4927 } else {
4928 ok(hr == S_OK, "(%d,%d) tomExtend got hr=0x%08lx\n", i, j, hr);
4929 ok(delta == 1, "(%d,%d) tomExtend got delta %ld\n", i, j, delta);
4930 }
4932}
4933
4935{
4936 static const char test_text1[] = "ab\n c";
4937 IRichEditOle *reole = NULL;
4938 ITextDocument *doc = NULL;
4941 HRESULT hr;
4942 HWND hwnd;
4943 int i, j;
4944 const int textlen = strlen(test_text1);
4945
4946 create_interfaces(&hwnd, &reole, &doc, &selection);
4947 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)test_text1);
4948
4949 hr = ITextDocument_Range(doc, 0, 0, &range);
4950 ok(hr == S_OK, "got 0x%08lx\n", hr);
4951
4952 /* Exhaustive test of every possible combination of (start,end) locations,
4953 * against every possible target location to move to. */
4954 for (i = 0; i <= textlen; i++) {
4955 for (j = i; j <= textlen; j++) {
4956 LONG target;
4957 for (target = -2; target <= textlen + 3; target++) {
4958 test_character_moveend(range, textlen, i, j, target);
4960 test_character_move(range, textlen, i, j, target);
4961 }
4962 test_character_startof(range, textlen, i, j);
4963 test_character_endof(range, textlen, i, j);
4964 }
4965 }
4966
4967 release_interfaces(&hwnd, &reole, &doc, NULL);
4968 ITextSelection_Release(selection);
4969 ITextRange_Release(range);
4970}
4971
4973{
4975 while (1)
4976 {
4979 return ret;
4980 if (GetTickCount() - start > 100)
4981 {
4982 char classname[256];
4983 DWORD le = GetLastError();
4984 HWND clipwnd = GetOpenClipboardWindow();
4985 /* Provide a hint as to the source of interference:
4986 * - The class name would typically be CLIPBRDWNDCLASS if the
4987 * clipboard was opened by a Windows application using the
4988 * ole32 API.
4989 * - And it would be __wine_clipboard_manager if it was opened in
4990 * response to a native application.
4991 */
4993 trace("%p (%s) opened the clipboard\n", clipwnd, classname);
4994 SetLastError(le);
4995 return ret;
4996 }
4997 Sleep(15);
4998 }
4999}
5000
5001#define CLIPBOARD_RANGE_CONTAINS(range, start, end, expected) _clipboard_range_contains(range, start, end, expected, __LINE__, 0);
5002#define TODO_CLIPBOARD_RANGE_CONTAINS(range, start, end, expected) _clipboard_range_contains(range, start, end, expected, __LINE__, 1);
5004{
5005 HRESULT hr;
5006 BOOL clipboard_open;
5008 const char *clipboard_text;
5009
5010 hr = ITextRange_SetRange(range, start, end);
5011 ok_(__FILE__,line)(SUCCEEDED(hr), "SetRange failed: 0x%08lx\n", hr);
5012 hr = ITextRange_Copy(range, NULL);
5013 ok_(__FILE__,line)(hr == S_OK, "Copy failed: 0x%08lx\n", hr);
5014
5015 clipboard_open = open_clipboard(NULL);
5016 ok_(__FILE__,line)(clipboard_open, "OpenClipboard failed: %ld\n", GetLastError());
5018 ok_(__FILE__,line)(global != NULL, "GetClipboardData failed: %p\n", global);
5019 clipboard_text = GlobalLock(global);
5020 ok_(__FILE__,line)(clipboard_text != NULL, "GlobalLock failed: %p\n", clipboard_text);
5021#ifdef __REACTOS__
5022 if (expected != NULL && clipboard_text != NULL)
5023 todo_wine_if(todo) ok_(__FILE__,line)(!strcmp(expected, clipboard_text), "unexpected contents: %s\n", wine_dbgstr_a(clipboard_text));
5024 else
5025 todo_wine_if(todo) ok_(__FILE__,line)(FALSE, "Either 'expected' or 'clipboard_text' was NULL\n");
5026#else
5027 todo_wine_if(todo) ok_(__FILE__,line)(!strcmp(expected, clipboard_text), "unexpected contents: %s\n", wine_dbgstr_a(clipboard_text));
5028#endif
5031}
5032
5033static void test_clipboard(void)
5034{
5035 static const char text_in[] = "ab\n c";
5036 IRichEditOle *reole = NULL;
5037 ITextDocument *doc = NULL;
5040 HRESULT hr;
5041 HWND hwnd;
5042
5043 create_interfaces(&hwnd, &reole, &doc, &selection);
5044 SendMessageA(hwnd, WM_SETTEXT, 0, (LPARAM)text_in);
5045
5046 hr = ITextDocument_Range(doc, 0, 0, &range);
5047 ok(hr == S_OK, "got 0x%08lx\n", hr);
5048
5049 CLIPBOARD_RANGE_CONTAINS(range, 0, 5, "ab\r\n c")
5050 CLIPBOARD_RANGE_CONTAINS(range, 0, 0, "ab\r\n c")
5051 CLIPBOARD_RANGE_CONTAINS(range, 1, 1, "ab\r\n c")
5054
5055 /* Setting password char does not stop Copy */
5058
5059 /* Cut can be undone */
5060 hr = ITextRange_SetRange(range, 0, 1);
5061 ok(SUCCEEDED(hr), "SetRange failed: 0x%08lx\n", hr);
5062 hr = ITextRange_Cut(range, NULL);
5063 ok(hr == S_OK, "Cut failed: 0x%08lx\n", hr);
5064 CLIPBOARD_RANGE_CONTAINS(range, 0, 4, "b\r\n c");
5065 hr = ITextDocument_Undo(doc, 1, NULL);
5066 ok(hr == S_OK, "Undo failed: 0x%08lx\n", hr);
5067 CLIPBOARD_RANGE_CONTAINS(range, 0, 5, "ab\r\n c");
5068
5069 /* Cannot cut when read-only */
5071 hr = ITextRange_SetRange(range, 0, 1);
5072 ok(SUCCEEDED(hr), "SetRange failed: 0x%08lx\n", hr);
5073 hr = ITextRange_Cut(range, NULL);
5074 ok(hr == E_ACCESSDENIED, "got 0x%08lx\n", hr);
5075
5076 release_interfaces(&hwnd, &reole, &doc, NULL);
5077 ITextSelection_Release(selection);
5078 ITextRange_Release(range);
5079}
5080
5081static void subtest_undo(const char *dummy_text)
5082{
5083 static const char *text_seq[] = {
5084 "",
5085 "1-alpha",
5086 "2-beta",
5087 "3-gamma",
5088 "4-delta",
5089 "5-epsilon",
5090 "6-zeta",
5091 "7-eta",
5092 };
5093 static LONG seq[] = { -1, -2, -3, -1, 1, 2, 3, 1, -5, 2, -1, 3, 1, 0 };
5094 LONG i = 0, stack_pos = 0;
5095 IRichEditOle *reole = NULL;
5096 ITextDocument *doc = NULL;
5098 char buffer[1024] = "";
5099 HRESULT hr;
5100 HWND hwnd;
5101 LONG count = 0;
5102
5103 winetest_push_context("(%Iu)", dummy_text ? strlen(dummy_text) : 0);
5104
5105 create_interfaces(&hwnd, &reole, &doc, &selection);
5106
5107 for (i = -2; i <= 2; i++)
5108 {
5109 if (i != tomFalse && i != tomTrue)
5110 {
5111 hr = ITextDocument_Undo(doc, i, NULL);
5112 todo_wine_if(i >= 1)
5113 ok(hr == (i >= 1 ? S_OK : S_FALSE), "(%ld@0) Undo: %#lx\n", i, hr);
5114
5115 count = 0xcccccccc;
5116 hr = ITextDocument_Undo(doc, i, &count);
5117 todo_wine_if(i >= 1)
5118 ok(hr == (i >= 1 ? S_OK : S_FALSE), "(%ld@0) Undo: %#lx\n", i, hr);
5119 todo_wine_if(i >= 1)
5120 ok(count == (i >= 1 ? i : 0), "(%ld@0) Expected %ld, got %ld\n", i, i >= 0 ? i : 0, count);
5121 }
5122
5123 hr = ITextDocument_Redo(doc, i, NULL);
5124 ok(hr == (i == 0 ? S_OK : S_FALSE), "(%ld@0) Redo: %#lx\n", i, hr);
5125
5126 count = 0xcccccccc;
5127 hr = ITextDocument_Redo(doc, i, &count);
5128 ok(hr == (i == 0 ? S_OK : S_FALSE), "(%ld@0) Redo: %#lx\n", i, hr);
5129 ok(count == 0, "(%ld@0) got %ld\n", i, count);
5130 }
5131
5132 while (stack_pos < ARRAY_SIZE(text_seq) - 1)
5133 {
5134 stack_pos++;
5135 if (dummy_text)
5136 {
5137 hr = ITextDocument_Undo(doc, tomSuspend, NULL);
5138 ok(hr == S_FALSE, "(@%ld) Undo: %#lx\n", stack_pos, hr);
5139 if (SUCCEEDED(hr))
5140 {
5141 SendMessageA(hwnd, EM_SETSEL, 0, 0);
5142 SendMessageA(hwnd, EM_REPLACESEL, TRUE, (LPARAM)dummy_text);
5143 SendMessageA(hwnd, EM_SETSEL, 0, strlen(dummy_text));
5145 hr = ITextDocument_Undo(doc, tomResume, NULL);
5146 ok(hr == S_FALSE, "(@%ld) Undo: %#lx\n", stack_pos, hr);
5147 }
5148 }
5149 SendMessageA(hwnd, EM_SETSEL, 0, -1);
5150 SendMessageA(hwnd, EM_REPLACESEL, TRUE, (LPARAM)text_seq[stack_pos]);
5151 }
5152
5153 for (i = 0; i < ARRAY_SIZE(seq); i++)
5154 {
5155 LONG expect_count;
5156
5157 memset(buffer, 0, sizeof(buffer));
5159 ok(strcmp(buffer, text_seq[stack_pos]) == 0, "Expected %s, got %s\n",
5160 wine_dbgstr_a(text_seq[stack_pos]), wine_dbgstr_a(buffer));
5161
5162 if (!seq[i]) break;
5163
5164 count = 0xcccccccc;
5165 expect_count = labs(stack_pos - min(max(stack_pos + seq[i], 0), (LONG)ARRAY_SIZE(seq) - 1));
5166 if (seq[i] < 0)
5167 {
5168 hr = ITextDocument_Undo(doc, -seq[i], &count);
5169 ok(hr == S_OK, "(%ld@%ld) Undo: %#lx\n", i, stack_pos, hr);
5170 ok(count == expect_count, "(%ld@%ld) Expected %ld, got %ld\n", i, stack_pos, expect_count, count);
5171 stack_pos -= count;
5172 }
5173 else
5174 {
5175 hr = ITextDocument_Redo(doc, seq[i], &count);
5176 ok(hr == (expect_count ? S_OK : S_FALSE), "(%ld@%ld) Redo: %#lx\n", i, stack_pos, hr);
5177 ok(count == expect_count, "(%ld@%ld) Expected %ld, got %ld\n", i, stack_pos, expect_count, count);
5178 stack_pos += count;
5179 }
5180
5181 if (FAILED(hr) || count <= 0) break;
5182 }
5183
5184 release_interfaces(&hwnd, &reole, &doc, &selection);
5186}
5187
5188static void test_undo(void)
5189{
5191 subtest_undo("dummy 12345");
5192}
5193
5194#define ok_msg_result(h,m,w,l,r) ok_msg_result_(__LINE__,#m,h,m,w,l,r)
5196{
5198 ok_(__FILE__,line)(lresult == expect, "%s: Expected %Id, got %Id\n", desc, expect, lresult);
5199}
5200
5207};
5208
5216 numUndoActions = 5
5218
5226};
5227
5229{
5237};
5238
5240{
5241 HRESULT hr = S_OK;
5242
5243 if (count) *count = 0xcccccccc;
5244
5245 switch (action)
5246 {
5247 case undoActionNoOp:
5248 if (count) *count = 0;
5249 break;
5250 case undoActionEnable:
5252 {
5253 LONG_PTR cur_undo_limit = SendMessageA(inst->hwnd, EM_SETUNDOLIMIT, inst->undo_limit, 0);
5254 ok(cur_undo_limit == inst->undo_limit, "Expected undo limit %Id, got %Id\n",
5255 inst->undo_limit, cur_undo_limit);
5256 if (count) *count = 0;
5257 }
5258 else
5259 {
5260 hr = ITextDocument_Undo(inst->doc, tomTrue, count);
5261 ok(hr == S_FALSE, "Undo: %#lx\n", hr);
5262 }
5263 if (SUCCEEDED(hr))
5264 {
5265 if (inst->undo_ctl_state == undoStateDisabled)
5266 {
5268 }
5269 inst->last_undo_status = TRUE;
5270 }
5271 break;
5272 case undoActionDisable:
5273 hr = ITextDocument_Undo(inst->doc, tomFalse, count);
5274 ok(hr == S_OK, "Undo: %#lx\n", hr);
5275 if (SUCCEEDED(hr))
5276 {
5278 inst->last_undo_status = FALSE;
5279 inst->last_redo_status = FALSE;
5280 }
5281 break;
5282 case undoActionSuspend:
5283 hr = ITextDocument_Undo(inst->doc, tomSuspend, count);
5284 ok(hr == S_FALSE, "Undo: %#lx\n", hr);
5285 if (SUCCEEDED(hr) && inst->undo_ctl_state == undoStateActive)
5286 {
5288 }
5289 break;
5290 case undoActionResume:
5291 hr = ITextDocument_Undo(inst->doc, tomResume, count);
5292 ok(hr == S_FALSE, "Undo: %#lx\n", hr);
5293 if (SUCCEEDED(hr))
5294 {
5296 }
5297 break;
5298 default:
5299 ok(0, "unreachable\n");
5300 break;
5301 }
5302
5303 if (count)
5304 {
5305 ok(*count == 0, "Got %ld\n", *count);
5306 }
5307 return hr;
5308}
5309
5311{
5312 HRESULT hr = S_OK;
5313 if (inst->undo_ctl_state == state) return hr;
5314 switch (state)
5315 {
5316 case undoStateActive:
5319 break;
5320 case undoStateSuspended:
5323 break;
5324 case undoStateDisabled:
5326 break;
5327 default:
5328 ok(0, "unreachable\n");
5329 break;
5330 }
5331 ok(inst->undo_ctl_state == state, "expected state %d, got %d\n", state, inst->undo_ctl_state);
5332 ok(SUCCEEDED(hr), "cannot set state to %d: %#lx\n", undoStateActive, hr);
5333 return hr;
5334}
5335
5336#define perform_undo(i,c) perform_undo_(i,c,__LINE__)
5337static BOOL perform_undo_(struct undo_test *inst, BOOL can_undo, int line)
5338{
5339 LONG count;
5340 HRESULT hr;
5342
5344 {
5345 LRESULT lres = SendMessageA(inst->hwnd, EM_UNDO, 0, 0);
5346 ok_(__FILE__, line)(lres == FALSE || lres == TRUE, "unexpected LRESULT %#Ix\n", lres);
5347 result = lres;
5348 }
5349 else
5350 {
5351 count = 0xcccccccc;
5352 hr = ITextDocument_Undo(inst->doc, 1, &count);
5353 ok_(__FILE__, line)(SUCCEEDED(hr), "got hr %#lx\n", hr);
5354 ok_(__FILE__, line)(count == (hr == S_OK), "expected count %d, got %ld\n", hr == S_OK, count);
5355 result = hr == S_OK && count > 0;
5356 }
5357
5358 expect = FALSE;
5359 if (inst->undo_ctl_state == undoStateActive)
5360 {
5361 if (can_undo) inst->last_undo_status = TRUE;
5362 expect = inst->last_undo_status;
5363 }
5364 todo_wine_if(!can_undo && !result && expect)
5365 ok_(__FILE__, line)(result == expect, "state %d: expected %d, got %d\n", inst->undo_ctl_state, expect, result);
5366
5367 return can_undo && result;
5368}
5369
5370#define perform_redo(i,c) perform_redo_(i,c,__LINE__)
5371static BOOL perform_redo_(struct undo_test *inst, BOOL can_redo, int line)
5372{
5373 LONG count;
5374 HRESULT hr;
5376
5378 {
5379 LRESULT lres = SendMessageA(inst->hwnd, EM_REDO, 0, 0);
5380 ok_(__FILE__, line)(lres == FALSE || lres == TRUE, "unexpected LRESULT %#Ix\n", lres);
5381 result = lres;
5382 }
5383 else
5384 {
5385 count = 0xcccccccc;
5386 hr = ITextDocument_Redo(inst->doc, 1, &count);
5387 ok_(__FILE__, line)(SUCCEEDED(hr), "got hr %#lx\n", hr);
5388 ok_(__FILE__, line)(count == (hr == S_OK), "expected count %d, got %ld\n", hr == S_OK, count);
5389 result = hr == S_OK && count > 0;
5390 }
5391
5392 expect = FALSE;
5393 if (inst->undo_ctl_state == undoStateActive)
5394 {
5395 if (can_redo) inst->last_redo_status = TRUE;
5396 expect = inst->last_redo_status;
5397 }
5398 todo_wine_if(!can_redo && !result && expect)
5399 ok_(__FILE__, line)(result == expect, "state %d: expected %d, got %d\n", inst->undo_ctl_state, expect, result);
5400
5401 return can_redo && result;
5402}
5403
5405{
5406 LONG undo_count, redo_count, count;
5407 static const char text_foo[] = "foo";
5408 static const char text_bar[] = "bar";
5409 static const char *last_text, *last_text2;
5410 char buffer[1024] = "";
5411 HRESULT hr;
5412
5413 SendMessageA(inst->hwnd, EM_EMPTYUNDOBUFFER, 0, 0);
5414 undo_count = redo_count = 0;
5415 ok_msg_result(inst->hwnd, EM_CANUNDO, 0, 0, undo_count > 0);
5416 ok_msg_result(inst->hwnd, EM_CANREDO, 0, 0, redo_count > 0);
5417
5418 SendMessageA(inst->hwnd, WM_SETTEXT, 0, (LPARAM)(last_text = ""));
5420 last_text = "";
5421 ok(strcmp(buffer, last_text) == 0,
5422 "Expected %s, got %s\n", wine_dbgstr_a(""), wine_dbgstr_a(buffer));
5423
5424 SendMessageA(inst->hwnd, EM_SETSEL, 0, -1);
5425 SendMessageA(inst->hwnd, EM_REPLACESEL, TRUE, (LPARAM)(last_text = text_foo));
5426 if (inst->undo_ctl_state == undoStateActive) undo_count++, redo_count = 0;
5427 ok_msg_result(inst->hwnd, EM_CANUNDO, 0, 0, undo_count > 0);
5428 ok_msg_result(inst->hwnd, EM_CANREDO, 0, 0, redo_count > 0);
5430 ok(strcmp(buffer, last_text) == 0, "Expected %s, got %s\n", wine_dbgstr_a(text_foo), wine_dbgstr_a(buffer));
5431
5433 ok(SUCCEEDED(hr), "got %#lx\n", hr);
5434 if (FAILED(hr)) return hr;
5435 if (inst->undo_ctl_state == undoStateDisabled) undo_count = redo_count = 0;
5436 ok_msg_result(inst->hwnd, EM_CANUNDO, 0, 0, undo_count > 0);
5437 ok_msg_result(inst->hwnd, EM_CANREDO, 0, 0, redo_count > 0);
5438
5439 if (inst->test_flags & undoTestDoFirstUndo)
5440 {
5441 if (perform_undo(inst, undo_count > 0)) undo_count--, redo_count++, last_text = "";
5442 ok_msg_result(inst->hwnd, EM_CANUNDO, 0, 0, undo_count > 0);
5443 ok_msg_result(inst->hwnd, EM_CANREDO, 0, 0, redo_count > 0);
5445 ok(strcmp(buffer, last_text) == 0, "Expected %s, got %s\n", wine_dbgstr_a(last_text), wine_dbgstr_a(buffer));
5446 }
5447
5449 {
5451 ok(SUCCEEDED(hr), "got %#lx\n", hr);
5452 if (FAILED(hr)) return hr;
5453 ok_msg_result(inst->hwnd, EM_CANUNDO, 0, 0, undo_count > 0);
5454 ok_msg_result(inst->hwnd, EM_CANREDO, 0, 0, redo_count > 0);
5455
5456 if (perform_undo(inst, undo_count > 0)) undo_count--, redo_count++, last_text = "";
5457 ok_msg_result(inst->hwnd, EM_CANUNDO, 0, 0, undo_count > 0);
5458 ok_msg_result(inst->hwnd, EM_CANREDO, 0, 0, redo_count > 0);
5460 ok(strcmp(buffer, last_text) == 0, "Expected %s, got %s\n", wine_dbgstr_a(last_text), wine_dbgstr_a(buffer));
5461 }
5462
5463 if (inst->test_flags & undoTestDoFirstRedo)
5464 {
5465 if (perform_redo(inst, redo_count > 0)) undo_count++, redo_count--, last_text = text_foo;
5466 ok_msg_result(inst->hwnd, EM_CANUNDO, 0, 0, undo_count > 0);
5467 ok_msg_result(inst->hwnd, EM_CANREDO, 0, 0, redo_count > 0);
5469 ok(strcmp(buffer, last_text) == 0, "Expected %s, got %s\n", wine_dbgstr_a(last_text), wine_dbgstr_a(buffer));
5470 }
5471
5472 SendMessageA(inst->hwnd, EM_SETSEL, 0, -1);
5473 SendMessageA(inst->hwnd, EM_REPLACESEL, TRUE, (LPARAM)(last_text2 = text_bar));
5474 if (inst->undo_ctl_state == undoStateActive) undo_count++, redo_count = 0;
5475 ok_msg_result(inst->hwnd, EM_CANUNDO, 0, 0, undo_count > 0);
5476 ok_msg_result(inst->hwnd, EM_CANREDO, 0, 0, redo_count > 0);
5478 ok(strcmp(buffer, last_text2) == 0, "Expected %s, got %s\n", wine_dbgstr_a(last_text2), wine_dbgstr_a(buffer));
5479
5480 if (perform_undo(inst, undo_count > 0)) undo_count--, redo_count++, last_text2 = last_text;
5481 ok_msg_result(inst->hwnd, EM_CANUNDO, 0, 0, undo_count > 0);
5482 ok_msg_result(inst->hwnd, EM_CANREDO, 0, 0, redo_count > 0);
5484 ok(strcmp(buffer, last_text2) == 0, "Expected %s, got %s\n", wine_dbgstr_a(last_text2), wine_dbgstr_a(buffer));
5485
5486 if (perform_redo(inst, redo_count > 0)) undo_count++, redo_count--, last_text2 = text_bar;
5487 ok_msg_result(inst->hwnd, EM_CANUNDO, 0, 0, undo_count > 0);
5488 ok_msg_result(inst->hwnd, EM_CANREDO, 0, 0, redo_count > 0);
5490 ok(strcmp(buffer, last_text2) == 0, "Expected %s, got %s\n", wine_dbgstr_a(last_text2), wine_dbgstr_a(buffer));
5491
5492 return S_OK;
5493}
5494
5495static void test_undo_control(void)
5496{
5497 enum editorUndoState state0;
5498 enum editorUndoStateAction action0, action1;
5499 IRichEditOle *reole = NULL;
5501 struct undo_test inst = { NULL };
5502 HRESULT hr;
5503
5504 create_interfaces(&inst.hwnd, &reole, &inst.doc, &selection);
5506 inst.last_undo_status = TRUE;
5507 inst.last_redo_status = TRUE;
5508 inst.undo_limit = SendMessageA(inst.hwnd, EM_SETUNDOLIMIT, 100, 0);
5509 ok(inst.undo_limit >= 1, "Message EM_SETUNDOLIMIT returned %#Ix\n", inst.undo_limit);
5510
5511 if (SUCCEEDED(ITextDocument_Undo(inst.doc, 1, NULL)))
5512 {
5513 for (inst.test_flags = 0; inst.test_flags < undoTestMaxFlag; inst.test_flags++)
5514 {
5515 for (state0 = firstUndoState; state0 < numUndoStates; state0++)
5516 {
5517 for (action0 = firstUndoAction; action0 < numUndoActions; action0++)
5518 {
5519 for (action1 = firstUndoAction; action1 < numUndoActions; action1++)
5520 {
5521 winetest_push_context("%x:%d:%d >?:%d", inst.test_flags, state0, action0, action1);
5522 hr = set_editor_undo_state(&inst, state0);
5524
5525 if (FAILED(hr)) continue;
5526
5527 winetest_push_context("%x:%d:%d+>?:%d", inst.test_flags, state0, action0, action1);
5528 hr = subtest_undo_control(&inst, action0);
5530
5531 if (FAILED(hr)) continue;
5532
5533 winetest_push_context("%x:%d:%d>%d:%d+", inst.test_flags, state0, action0, inst.undo_ctl_state, action1);
5534 subtest_undo_control(&inst, action1);
5536 }
5537 }
5538 }
5539 }
5540 }
5541
5542 release_interfaces(&inst.hwnd, &reole, &inst.doc, &selection);
5543}
5544
5545static void test_freeze(void)
5546{
5548 DWORD lasterr, style1, style2;
5549 IRichEditOle *reole = NULL;
5551 HRESULT hr;
5552 LONG count;
5553 HWND hwnd;
5554
5555 create_interfaces(&hwnd, &reole, &doc, &selection);
5556
5557 SetLastError(0xdeadbeef);
5558 style1 = GetWindowLongW(hwnd, GWL_STYLE);
5559 lasterr = GetLastError();
5560 ok(lasterr == 0xdeadbeefUL, "GetLastError() returned %#lx\n", lasterr);
5561
5562 count = 0xdeadbeef;
5563 hr = ITextDocument_Freeze(doc, &count);
5564 ok(hr == S_OK, "ITextDocument_Freeze returned %#lx\n", hr);
5565 ok(count == 1, "expected count to be %d, got %ld\n", 1, count);
5566
5567 style2 = GetWindowLongW(hwnd, GWL_STYLE);
5568 ok(style2 == style1, "expected window style to not change from %#lx, got %#lx\n", style1, style2);
5569
5570 count = 0xdeadbeef;
5571 hr = ITextDocument_Freeze(doc, &count);
5572 ok(hr == S_OK, "ITextDocument_Freeze returned %#lx\n", hr);
5573 ok(count == 2, "expected count to be %d, got %ld\n", 2, count);
5574
5575 count = 0xdeadbeef;
5576 hr = ITextDocument_Unfreeze(doc, &count);
5577 ok(hr == S_FALSE, "ITextDocument_Unfreeze returned %#lx\n", hr);
5578 ok(count == 1, "expected count to be %d, got %ld\n", 1, count);
5579
5580 count = 0xdeadbeef;
5581 hr = ITextDocument_Unfreeze(doc, &count);
5582 ok(hr == S_OK, "ITextDocument_Unfreeze returned %#lx\n", hr);
5583 ok(count == 0, "expected count to be %d, got %ld\n", 0, count);
5584
5585 count = 0xdeadbeef;
5586 hr = ITextDocument_Unfreeze(doc, &count);
5587 ok(hr == S_OK, "ITextDocument_Unfreeze returned %#lx\n", hr);
5588 ok(count == 0, "expected count to be %d, got %ld\n", 0, count);
5589
5590 count = 0xdeadbeef;
5591 hr = ITextDocument_Freeze(doc, &count);
5592 ok(hr == S_OK, "ITextDocument_Freeze returned %#lx\n", hr);
5593 ok(count == 1, "expected count to be %d, got %ld\n", 1, count);
5594
5595 count = 0xdeadbeef;
5596 hr = ITextDocument_Unfreeze(doc, &count);
5597 ok(hr == S_OK, "ITextDocument_Unfreeze returned %#lx\n", hr);
5598 ok(count == 0, "expected count to be %d, got %ld\n", 0, count);
5599
5600 count = 0xdeadbeef;
5601 hr = ITextDocument_Freeze(doc, NULL);
5602 ok(hr == S_OK, "ITextDocument_Freeze returned %#lx\n", hr);
5603
5604 count = 0xdeadbeef;
5605 hr = ITextDocument_Unfreeze(doc, NULL);
5606 ok(hr == S_OK, "ITextDocument_Unfreeze returned %#lx\n", hr);
5607
5608 release_interfaces(&hwnd, &reole, &doc, &selection);
5609}
5610
5612{
5613 /* Must explicitly LoadLibrary(). The test has no references to functions in
5614 * RICHED20.DLL, so the linker doesn't actually link to it. */
5615 hmoduleRichEdit = LoadLibraryA("riched20.dll");
5616 ok(hmoduleRichEdit != NULL, "error: %d\n", (int) GetLastError());
5617
5620 test_GetText();
5634 test_GetFont();
5635 test_GetPara();
5636 test_dispatch();
5638 test_Delete();
5639 test_SetText();
5640 test_InRange();
5642 test_Select();
5644 test_SetFont();
5648 test_Expand();
5652 test_undo();
5654 test_freeze();
5655}
@ lparam
Definition: SystemMenu.c:31
@ wparam
Definition: SystemMenu.c:30
#define expect(EXPECTED, GOT)
Definition: SystemMenu.c:483
int strcmp(const char *String1, const char *String2)
Definition: utclib.c:469
ACPI_SIZE strlen(const char *String)
Definition: utclib.c:269
static int state
Definition: maze.c:121
#define InterlockedIncrement
Definition: armddk.h:53
#define InterlockedDecrement
Definition: armddk.h:52
#define trace
Definition: atltest.h:70
#define ok(value,...)
Definition: atltest.h:57
#define skip(...)
Definition: atltest.h:64
#define broken(x)
Definition: atltest.h:178
#define START_TEST(x)
Definition: atltest.h:75
#define ok_(x1, x2)
Definition: atltest.h:61
#define msg(x)
Definition: auth_time.c:54
static const WCHAR nameW[]
Definition: main.c:49
#define CF_UNICODETEXT
Definition: constants.h:408
#define CF_TEXT
Definition: constants.h:396
void user(int argc, const char *argv[])
Definition: cmds.c:1350
#define ARRAY_SIZE(A)
Definition: main.h:20
const GUID IID_IUnknown
#define STDMETHODCALLTYPE
Definition: bdasup.h:9
int selection
Definition: ctm.c:92
#define E_OUTOFMEMORY
Definition: ddrawi.h:100
#define E_INVALIDARG
Definition: ddrawi.h:101
#define E_NOTIMPL
Definition: ddrawi.h:99
#define E_FAIL
Definition: ddrawi.h:102
#define free
Definition: debug_ros.c:5
#define NULL
Definition: types.h:112
#define TRUE
Definition: types.h:120
#define FALSE
Definition: types.h:117
#define CloseHandle
Definition: compat.h:739
#define ERROR_INVALID_PARAMETER
Definition: compat.h:101
#define CP_ACP
Definition: compat.h:109
#define OPEN_EXISTING
Definition: compat.h:775
#define SetLastError(x)
Definition: compat.h:752
#define INVALID_HANDLE_VALUE
Definition: compat.h:731
WCHAR OLECHAR
Definition: compat.h:2292
OLECHAR * BSTR
Definition: compat.h:2293
#define GENERIC_READ
Definition: compat.h:135
#define CreateFileW
Definition: compat.h:741
#define FILE_ATTRIBUTE_NORMAL
Definition: compat.h:137
#define CALLBACK
Definition: compat.h:35
#define ERROR_ACCESS_DENIED
Definition: compat.h:97
#define FILE_SHARE_READ
Definition: compat.h:136
@ VT_BSTR
Definition: compat.h:2303
#define lstrlenW
Definition: compat.h:750
BOOL WINAPI DeleteFileW(IN LPCWSTR lpFileName)
Definition: delete.c:39
BOOL WINAPI WriteFile(IN HANDLE hFile, IN LPCVOID lpBuffer, IN DWORD nNumberOfBytesToWrite OPTIONAL, OUT LPDWORD lpNumberOfBytesWritten, IN LPOVERLAPPED lpOverlapped OPTIONAL)
Definition: rw.c:24
HINSTANCE WINAPI DECLSPEC_HOTPATCH LoadLibraryA(LPCSTR lpLibFileName)
Definition: loader.c:111
int WINAPI lstrcmpW(LPCWSTR str1, LPCWSTR str2)
Definition: locale.c:4246
LCID WINAPI GetSystemDefaultLCID(void)
Definition: locale.c:1235
ULONG WINAPI DECLSPEC_HOTPATCH GetTickCount(void)
Definition: sync.c:182
static FLOAT twips_to_points(LONG value)
Definition: richole.c:399
return ret
Definition: mutex.c:146
action
Definition: namespace.c:707
#define L(x)
Definition: resources.c:13
r parent
Definition: btrfs.c:3010
r reserved
Definition: btrfs.c:3006
int global
Definition: ehframes.cpp:22
unsigned int BOOL
Definition: ntddk_ex.h:94
unsigned long DWORD
Definition: ntddk_ex.h:95
unsigned short WORD
Definition: ntddk_ex.h:93
GLuint start
Definition: gl.h:1545
GLuint GLuint GLsizei count
Definition: gl.h:1545
GLuint GLuint end
Definition: gl.h:1545
GLuint res
Definition: glext.h:9613
GLuint buffer
Definition: glext.h:5915
GLsizeiptr size
Definition: glext.h:5919
GLuint index
Definition: glext.h:6031
GLenum GLint * range
Definition: glext.h:7539
GLbitfield flags
Definition: glext.h:7161
const GLint * first
Definition: glext.h:5794
GLuint64EXT * result
Definition: glext.h:11304
GLfloat GLfloat p
Definition: glext.h:8902
GLubyte GLubyte GLubyte GLubyte w
Definition: glext.h:6102
GLenum target
Definition: glext.h:7315
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint i
Definition: glfuncs.h:248
GLsizei GLenum const GLvoid GLsizei GLenum GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLint GLint GLint GLshort GLshort GLshort GLubyte GLubyte GLubyte GLuint GLuint GLuint GLushort GLushort GLushort GLbyte GLbyte GLbyte GLbyte GLdouble GLdouble GLdouble GLdouble GLfloat GLfloat GLfloat GLfloat GLint GLint GLint GLint GLshort GLshort GLshort GLshort GLubyte GLubyte GLubyte GLubyte GLuint GLuint GLuint GLuint GLushort GLushort GLushort GLushort GLboolean const GLdouble const GLfloat const GLint const GLshort const GLbyte const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLdouble const GLfloat const GLfloat const GLint const GLint const GLshort const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort const GLdouble const GLfloat const GLint const GLshort GLenum GLenum GLenum GLfloat GLenum GLint GLenum GLenum GLenum GLfloat GLenum GLenum GLint GLenum GLfloat GLenum GLint GLint GLushort GLenum GLenum GLfloat GLenum GLenum GLint GLfloat const GLubyte GLenum GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLint GLint GLsizei GLsizei GLint GLenum GLenum const GLvoid GLenum GLenum const GLfloat GLenum GLenum const GLint GLenum GLenum const GLdouble GLenum GLenum const GLfloat GLenum GLenum const GLint GLsizei GLuint GLfloat GLuint GLbitfield GLfloat GLint GLuint GLboolean GLenum GLfloat GLenum GLbitfield GLenum GLfloat GLfloat GLint GLint const GLfloat GLenum GLfloat GLfloat GLint GLint GLfloat GLfloat GLint GLint const GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat GLint GLfloat GLfloat const GLdouble const GLfloat const GLdouble const GLfloat GLint GLint GLint j
Definition: glfuncs.h:250
LPVOID NTAPI GlobalLock(HGLOBAL hMem)
Definition: heapmem.c:755
BOOL NTAPI GlobalUnlock(HGLOBAL hMem)
Definition: heapmem.c:1190
LPVOID WINAPI CoTaskMemAlloc(SIZE_T size)
Definition: ifs.c:426
_Check_return_ long __cdecl labs(_In_ long x)
REFIID riid
Definition: atlbase.h:39
REFIID LPVOID DWORD_PTR dw
Definition: atlbase.h:40
#define S_OK
Definition: intsafe.h:52
#define SUCCEEDED(hr)
Definition: intsafe.h:50
#define FAILED(hr)
Definition: intsafe.h:51
const char * filename
Definition: ioapi.h:137
#define debugstr_guid
Definition: kernel32.h:35
#define debugstr_w
Definition: kernel32.h:32
#define wine_dbgstr_w
Definition: kernel32.h:34
#define GUID_NULL
Definition: ks.h:106
POINT cp
Definition: magnifier.c:59
#define pch(ap)
Definition: match.c:418
#define memcpy(s1, s2, n)
Definition: mkisofs.h:878
char string[160]
Definition: util.h:11
#define CREATE_ALWAYS
Definition: disk.h:72
#define ERROR_FILE_NOT_FOUND
Definition: disk.h:79
static HDC
Definition: imagelist.c:88
BOOL todo
Definition: filedlg.c:313
static const WCHAR textW[]
Definition: itemdlg.c:1559
static IPrintDialogCallback callback
Definition: printdlg.c:326
static const WCHAR desc[]
Definition: protectdata.c:36
BOOL expected
Definition: store.c:2063
HRESULT hres
Definition: protocol.c:465
#define todo_wine_if(is_todo)
Definition: custom.c:86
#define todo_wine
Definition: custom.c:89
static LPOLESTR
Definition: stg_prop.c:27
#define open_clipboard(hwnd)
Definition: editor.c:4816
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_Advise(IOleObject *iface, IAdviseSink *adv_sink, DWORD *connection)
Definition: richole.c:427
static void _check_selection(ITextSelection *selection, LONG expected_start, LONG expected_end, int line)
Definition: richole.c:4535
static struct testoleobj * impl_from_IOleObject(IOleObject *iface)
Definition: richole.c:239
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_GetUserType(IOleObject *iface, DWORD form_of_type, LPOLESTR *user_type)
Definition: richole.c:396
static HRESULT STDMETHODCALLTYPE reolecb_obj_QueryAcceptData(IRichEditOleCallback *iface, IDataObject *dataobj, CLIPFORMAT *cf_format, DWORD reco, BOOL really, HGLOBAL metapict)
Definition: richole.c:135
static void subtest_InsertObject(struct reolecb_obj *callback)
Definition: richole.c:3878
static ULONG STDMETHODCALLTYPE testoleobj_Release(IOleObject *iface)
Definition: richole.c:279
static void test_Interfaces(void)
Definition: richole.c:729
static void test_Expand(void)
Definition: richole.c:4595
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_EnumAdvise(IOleObject *iface, IEnumSTATDATA **enum_advise)
Definition: richole.c:445
static void _reset_range(ITextRange *range, LONG start, LONG end, int line)
Definition: richole.c:4494
static void test_SetText(void)
Definition: richole.c:3289
static void test_character_movement(void)
Definition: richole.c:4934
static void test_ITextSelection_GetDuplicate(void)
Definition: richole.c:4418
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_GetUserClassID(IOleObject *iface, CLSID *clsid)
Definition: richole.c:390
static void _insert_reobject(struct reolecb_obj *callback, IRichEditOle *reole, REOBJECT *reobj, LONG cp, DWORD user, int line)
Definition: richole.c:3851
static HRESULT set_editor_undo_state(struct undo_test *inst, enum editorUndoState state)
Definition: richole.c:5310
#define perform_undo(i, c)
Definition: richole.c:5336
static void test_character_moveend(ITextRange *range, int textlen, int i, int j, LONG target)
Definition: richole.c:4797
static const struct IViewObjectVtbl testoleobj_IViewObject_Vtbl
Definition: richole.c:587
#define EXPECT_TODO_WINE
Definition: richole.c:41
static void fill_reobject_struct(REOBJECT *reobj, LONG cp, LPOLEOBJECT poleobj, LPSTORAGE pstg, LPOLECLIENTSITE polesite, LONG sizel_cx, LONG sizel_cy, DWORD aspect, DWORD flags, DWORD user)
Definition: richole.c:3813
static void test_character_startof(ITextRange *range, int textlen, int i, int j)
Definition: richole.c:4872
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_GetMiscStatus(IOleObject *iface, DWORD aspect, DWORD *status)
Definition: richole.c:457
static void test_ITextSelection_GetStart_GetEnd(void)
Definition: richole.c:1751
static void test_GetPara(void)
Definition: richole.c:2438
static void test_detached_font_getters(ITextFont *font, BOOL duplicate)
Definition: richole.c:2569
#define CLIPBOARD_RANGE_CONTAINS(range, start, end, expected)
Definition: richole.c:5001
static void test_character_endof(ITextRange *range, int textlen, int i, int j)
Definition: richole.c:4897
static void test_GetClientSite(void)
Definition: richole.c:2189
static HRESULT subtest_undo_control(struct undo_test *inst, enum editorUndoStateAction action)
Definition: richole.c:5404
static void test_GetStoryLength(void)
Definition: richole.c:4350
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_GetExtent(IOleObject *iface, DWORD draw_aspect, SIZEL *sizel)
Definition: richole.c:417
static HRESULT STDMETHODCALLTYPE reolecb_obj_QueryInsertObject(IRichEditOleCallback *iface, CLSID *clsid, IStorage *stg, LONG cp)
Definition: richole.c:106
static HMODULE hmoduleRichEdit
Definition: richole.c:623
#define INSERT_REOBJECT(callback, reole, reobj, cp, user)
Definition: richole.c:3849
static void test_textfont_undefined(ITextFont *font)
Definition: richole.c:2766
static void test_IOleInPlaceSite_GetWindow(void)
Definition: richole.c:2292
static void subtest_undo(const char *dummy_text)
Definition: richole.c:5081
static HWND new_richedit(HWND parent)
Definition: richole.c:648
static void test_ITextRange_GetDuplicate(void)
Definition: richole.c:1958
editorUndoStateAction
Definition: richole.c:5209
@ undoActionDisable
Definition: richole.c:5213
@ undoActionEnable
Definition: richole.c:5212
@ firstUndoAction
Definition: richole.c:5210
@ undoActionSuspend
Definition: richole.c:5214
@ undoActionResume
Definition: richole.c:5215
@ numUndoActions
Definition: richole.c:5216
@ undoActionNoOp
Definition: richole.c:5211
static void test_character_move(ITextRange *range, int textlen, int i, int j, LONG target)
Definition: richole.c:4826
static void test_Delete(void)
Definition: richole.c:3234
static HRESULT STDMETHODCALLTYPE testoleobj_IViewObject_GetAdvise(IViewObject *iface, DWORD *aspects, DWORD *advf, IAdviseSink **adv_sink)
Definition: richole.c:578
static void test_undo_control(void)
Definition: richole.c:5495
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_SetMoniker(IOleObject *iface, DWORD which_moniker, IMoniker *mk)
Definition: richole.c:336
static HRESULT STDMETHODCALLTYPE testoleobj_IViewObject_QueryInterface(IViewObject *iface, REFIID riid, void **obj)
Definition: richole.c:500
static void test_ITextSelection_GetChar(void)
Definition: richole.c:1475
#define CHECK_TYPEINFO(disp, expected_riid)
Definition: richole.c:704
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_GetClientSite(IOleObject *iface, IOleClientSite **clientsite)
Definition: richole.c:314
static void test_clipboard(void)
Definition: richole.c:5033
static HRESULT STDMETHODCALLTYPE testoleobj_QueryInterface(IOleObject *iface, REFIID riid, void **obj)
Definition: richole.c:244
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_Unadvise(IOleObject *iface, DWORD connection)
Definition: richole.c:437
static HRESULT STDMETHODCALLTYPE testoleobj_IViewObject_Freeze(IViewObject *iface, DWORD draw_aspect, LONG index, void *aspect, DWORD *freeze)
Definition: richole.c:560
static void _expect_ref(IUnknown *obj, ULONG ref, int line)
Definition: richole.c:631
static struct testoleobj * impl_from_IViewObject(IViewObject *iface)
Definition: richole.c:495
static void test_InRange(void)
Definition: richole.c:3376
static const struct IRichEditOleCallbackVtbl reolecb_obj_Vtbl
Definition: richole.c:166
static void test_GetStoryType(void)
Definition: richole.c:3670
static HRESULT perform_editor_undo_state_action(struct undo_test *inst, enum editorUndoStateAction action, LONG *count)
Definition: richole.c:5239
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_Close(IOleObject *iface, DWORD save_option)
Definition: richole.c:331
#define RESET_RANGE(range, start, end)
Definition: richole.c:4492
static BOOL touch_file(LPCWSTR filename)
Definition: richole.c:653
static HRESULT testoleobj_Create(struct testoleobj **objptr)
Definition: richole.c:599
static void ok_msg_result_(int line, const char *desc, HWND hwnd, UINT message, WPARAM wparam, LPARAM lparam, LRESULT expect)
Definition: richole.c:5195
static void test_ITextRange_GetStart_GetEnd(void)
Definition: richole.c:1531
static HRESULT STDMETHODCALLTYPE reolecb_obj_GetContextMenu(IRichEditOleCallback *iface, WORD seltype, IOleObject *oleobj, CHARRANGE *chrg, HMENU *hmenu)
Definition: richole.c:160
static const struct IOleObjectVtbl testoleobj_IOleObject_Vtbl
Definition: richole.c:468
static ULONG STDMETHODCALLTYPE reolecb_obj_AddRef(IRichEditOleCallback *iface)
Definition: richole.c:73
static void _check_reobject_struct(IRichEditOle *reole, LONG index, DWORD flags, LONG cp, LONG cp_check, LPOLEOBJECT poleobj, LPSTORAGE pstg, LPOLECLIENTSITE polesite, DWORD user, int line)
Definition: richole.c:3832
static void test_ITextRange_IsEqual(void)
Definition: richole.c:3486
static HRESULT STDMETHODCALLTYPE testoleobj_IViewObject_GetColorSet(IViewObject *iface, DWORD draw_aspect, LONG index, void *aspect, DVTARGETDEVICE *td, HDC hdc_target_dev, LOGPALETTE **color_set)
Definition: richole.c:552
#define CHECK_REOBJECT_STRUCT(reole, index, flags, cp, cp_check, poleobj, pstg, polesite, user)
Definition: richole.c:3830
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_SetColorScheme(IOleObject *iface, LOGPALETTE *palette)
Definition: richole.c:463
#define perform_redo(i, c)
Definition: richole.c:5370
static void test_ITextDocument_Open(void)
Definition: richole.c:859
static void test_ITextRange_Collapse(void)
Definition: richole.c:2001
static void create_interfaces(HWND *w, IRichEditOle **reOle, ITextDocument **txtDoc, ITextSelection **txtSel)
Definition: richole.c:678
static ULONG STDMETHODCALLTYPE testoleobj_IViewObject_AddRef(IViewObject *iface)
Definition: richole.c:506
static BOOL is_existing_file(LPCWSTR filename)
Definition: richole.c:666
static HRESULT STDMETHODCALLTYPE reolecb_obj_QueryInterface(IRichEditOleCallback *iface, REFIID riid, void **obj)
Definition: richole.c:62
#define CHECK_SELECTION(selection, expected_start, expected_end)
Definition: richole.c:4533
static void test_IOleWindow_GetWindow(void)
Definition: richole.c:2264
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_EnumVerbs(IOleObject *iface, IEnumOLEVERB **enumoleverb)
Definition: richole.c:374
static void test_ITextRange_ScrollIntoView(void)
Definition: richole.c:1439
static ULONG STDMETHODCALLTYPE testoleobj_AddRef(IOleObject *iface)
Definition: richole.c:272
static void flush_dispatch_messages(void)
Definition: richole.c:3868
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_InitFromData(IOleObject *iface, IDataObject *dataobj, BOOL creation, DWORD reserved)
Definition: richole.c:354
static void test_dispatch(void)
Definition: richole.c:2522
static void test_textfont_global_defaults(ITextFont *font)
Definition: richole.c:2637
static BOOL perform_redo_(struct undo_test *inst, BOOL can_redo, int line)
Definition: richole.c:5371
#define ok_msg_result(h, m, w, l, r)
Definition: richole.c:5194
#define MAX_BUF_LEN
static void _reset_selection(ITextSelection *selection, LONG start, LONG end, int line)
Definition: richole.c:4523
#define EXPECT_REF(obj, ref)
Definition: richole.c:630
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_DoVerb(IOleObject *iface, LONG verb, MSG *msg, IOleClientSite *activesite, LONG index, HWND parentwnd, LPCRECT posrect)
Definition: richole.c:367
static void test_ITextSelection_Collapse(void)
Definition: richole.c:2112
static int get_scroll_pos_y(HWND hwnd)
Definition: richole.c:3601
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_Update(IOleObject *iface)
Definition: richole.c:380
static ULONG STDMETHODCALLTYPE reolecb_obj_Release(IRichEditOleCallback *iface)
Definition: richole.c:80
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_IsUpToDate(IOleObject *iface)
Definition: richole.c:385
static void test_Select(void)
Definition: richole.c:3609
static ULONG STDMETHODCALLTYPE testoleobj_IViewObject_Release(IViewObject *iface)
Definition: richole.c:512
static void olecb_expect_QueryInsertObject(struct reolecb_obj *This, int line, ULONG expect, const CLSID *clsid, IStorage *stg, LONG cp, HRESULT result)
Definition: richole.c:200
static void test_ITextRange_SetRange(void)
Definition: richole.c:4550
static const WCHAR sysW[]
Definition: richole.c:628
static void test_undo(void)
Definition: richole.c:5188
static void release_interfaces(HWND *w, IRichEditOle **reOle, ITextDocument **txtDoc, ITextSelection **txtSel)
Definition: richole.c:688
static void test_GetFont(void)
Definition: richole.c:2320
static void olecb_check_QueryInsertObject(struct reolecb_obj *This, int line)
Definition: richole.c:213
#define CHECK_RANGE(range, expected_start, expected_end)
Definition: richole.c:4504
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_SetExtent(IOleObject *iface, DWORD draw_aspect, SIZEL *sizel)
Definition: richole.c:407
static void test_character_movestart(ITextRange *range, int textlen, int i, int j, LONG target)
Definition: richole.c:4768
static struct reolecb_obj * impl_from_IRichEditOleCallback(IRichEditOleCallback *iface)
Definition: richole.c:57
static void test_ITextFont(void)
Definition: richole.c:2893
static HRESULT STDMETHODCALLTYPE reolecb_obj_ShowContainerUI(IRichEditOleCallback *iface, BOOL show)
Definition: richole.c:101
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_GetClipboardData(IOleObject *iface, DWORD reserved, IDataObject **dataobj)
Definition: richole.c:360
#define RESET_SELECTION(selection, start, end)
Definition: richole.c:4521
static HRESULT STDMETHODCALLTYPE reolecb_obj_DeleteObject(IRichEditOleCallback *iface, IOleObject *oleobj)
Definition: richole.c:130
static void test_ITextRange_GetChar(void)
Definition: richole.c:1334
static HRESULT reolecb_obj_Create(struct reolecb_obj **objptr)
Definition: richole.c:182
static void _check_range(ITextRange *range, LONG expected_start, LONG expected_end, int line)
Definition: richole.c:4506
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_GetMoniker(IOleObject *iface, DWORD assign, DWORD which_moniker, IMoniker **mk)
Definition: richole.c:342
static void check_range(HWND w, ITextDocument *doc, int first, int lim, LONG bStart, int expected_nonzero)
Definition: richole.c:1413
static HRESULT STDMETHODCALLTYPE reolecb_obj_GetInPlaceContext(IRichEditOleCallback *iface, IOleInPlaceFrame **frame, IOleInPlaceUIWindow **doc, OLEINPLACEFRAMEINFO *frame_info)
Definition: richole.c:93
static HRESULT STDMETHODCALLTYPE testoleobj_IViewObject_Unfreeze(IViewObject *iface, DWORD freeze)
Definition: richole.c:567
static HRESULT STDMETHODCALLTYPE reolecb_obj_GetDragDropEffect(IRichEditOleCallback *iface, BOOL drag, DWORD key_state, DWORD *effect)
Definition: richole.c:153
static HWND new_window(LPCSTR lpClassName, DWORD dwStyle, HWND parent)
Definition: richole.c:639
static void _check_typeinfo(IDispatch *disp, REFIID expected_riid, int line)
Definition: richole.c:705
static void test_GetText(void)
Definition: richole.c:1107
static void _clipboard_range_contains(ITextRange *range, LONG start, LONG end, const char *expected, int line, int todo)
Definition: richole.c:5003
static HRESULT STDMETHODCALLTYPE testoleobj_IViewObject_SetAdvise(IViewObject *iface, DWORD aspects, DWORD advf, IAdviseSink *adv_sink)
Definition: richole.c:572
static void test_InsertObject(void)
Definition: richole.c:4328
static void test_MoveEnd_story(void)
Definition: richole.c:4654
static HRESULT STDMETHODCALLTYPE reolecb_obj_GetNewStorage(IRichEditOleCallback *iface, IStorage **stg)
Definition: richole.c:88
static BOOL perform_undo_(struct undo_test *inst, BOOL can_undo, int line)
Definition: richole.c:5337
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_SetHostNames(IOleObject *iface, LPCOLESTR container_app, LPCOLESTR container_obj)
Definition: richole.c:324
static ULONG get_refcount(IUnknown *iface)
Definition: richole.c:698
editorUndoState
Definition: richole.c:5201
@ undoStateSuspended
Definition: richole.c:5204
@ undoStateDisabled
Definition: richole.c:5205
@ undoStateActive
Definition: richole.c:5203
@ numUndoStates
Definition: richole.c:5206
@ firstUndoState
Definition: richole.c:5202
static void test_SetFont(void)
Definition: richole.c:3726
static HRESULT STDMETHODCALLTYPE reolecb_obj_ContextSensitiveHelp(IRichEditOleCallback *iface, BOOL enter_mode)
Definition: richole.c:142
static void test_ITextDocument_Range(void)
Definition: richole.c:1292
static HRESULT STDMETHODCALLTYPE testoleobj_IOleObject_SetClientSite(IOleObject *iface, IOleClientSite *clientsite)
Definition: richole.c:300
static HRESULT STDMETHODCALLTYPE testoleobj_IViewObject_Draw(IViewObject *iface, DWORD draw_aspect, LONG index, void *aspect, DVTARGETDEVICE *td, HDC hdc_target_dev, HDC hdc_draw, LPCRECTL bounds, LPCRECTL wbounds, BOOL(CALLBACK *fn_continue)(ULONG_PTR), ULONG_PTR arg_continue)
Definition: richole.c:518
static HRESULT STDMETHODCALLTYPE reolecb_obj_GetClipboardData(IRichEditOleCallback *iface, CHARRANGE *chrg, DWORD reco, IDataObject **dataobj)
Definition: richole.c:147
editorUndoStateTestFlags
Definition: richole.c:5219
@ undoTestDoSecondUndoAfterEnable
Definition: richole.c:5224
@ undoTestResetUndoLimit
Definition: richole.c:5221
@ undoTestDoFirstUndo
Definition: richole.c:5222
@ undoTestDoFirstRedo
Definition: richole.c:5223
@ undoTestUseWindowMessages
Definition: richole.c:5220
@ undoTestMaxFlag
Definition: richole.c:5225
static void test_freeze(void)
Definition: richole.c:5545
static const CLSID *static CLSID *static const GUID VARIANT VARIANT *static IServiceProvider DWORD *static HMENU
Definition: ordinal.c:63
static VARIANTARG static DISPID
Definition: ordinal.c:52
static HPALETTE palette
Definition: clipboard.c:1345
static HMENU hmenu
Definition: win.c:66
static IDispatch testobj
Definition: run.c:299
#define min(a, b)
Definition: monoChain.cc:55
REFCLSID clsid
Definition: msctf.c:82
__int3264 LONG_PTR
Definition: mstsclib_h.h:276
_In_ HANDLE hFile
Definition: mswsock.h:90
INT WINAPI MulDiv(INT nNumber, INT nNumerator, INT nDenominator)
Definition: muldiv.c:25
Definition: mk_font.cpp:20
unsigned int UINT
Definition: ndis.h:50
#define GENERIC_WRITE
Definition: nt_native.h:90
#define LOCALE_USER_DEFAULT
#define LOCALE_SYSTEM_DEFAULT
interface IStorage * LPSTORAGE
Definition: objfwd.h:30
HRESULT WINAPI CreateOleAdviseHolder(IOleAdviseHolder **ppOAHolder)
Definition: oleobj.c:875
BSTR WINAPI SysAllocString(LPCOLESTR str)
Definition: oleaut.c:238
void WINAPI DECLSPEC_HOTPATCH SysFreeString(BSTR str)
Definition: oleaut.c:271
BSTR WINAPI SysAllocStringLen(const OLECHAR *str, unsigned int len)
Definition: oleaut.c:339
#define V_VT(A)
Definition: oleauto.h:211
#define V_BSTR(A)
Definition: oleauto.h:226
const GUID IID_IOleInPlaceSite
const GUID IID_IViewObject
const GUID IID_IOleWindow
const GUID IID_IRunnableObject
const GUID IID_IOleClientSite
const GUID IID_IDispatch
const GUID IID_IOleLink
const GUID IID_IOleObject
#define WS_POPUP
Definition: pedump.c:616
#define WS_VSCROLL
Definition: pedump.c:627
#define WS_VISIBLE
Definition: pedump.c:620
long LONG
Definition: pedump.c:60
#define WS_HSCROLL
Definition: pedump.c:628
#define ES_MULTILINE
Definition: pedump.c:667
#define DEFINE_GUID(name, l, w1, w2, b1, b2, b3, b4, b5, b6, b7, b8)
Definition: guiddef.h:68
#define IsEqualGUID(rguid1, rguid2)
Definition: guiddef.h:147
#define CLSID_NULL
Definition: guiddef.h:99
#define REFIID
Definition: guiddef.h:118
#define IID_NULL
Definition: guiddef.h:98
#define GT_DEFAULT
Definition: richedit.h:1036
#define EM_CANREDO
Definition: richedit.h:118
#define SEL_OBJECT
Definition: richedit.h:824
#define EM_SETOLECALLBACK
Definition: richedit.h:103
#define EM_REDO
Definition: richedit.h:117
#define EM_GETSELTEXT
Definition: richedit.h:95
#define CFM_OFFSET
Definition: richedit.h:359
#define CFE_ITALIC
Definition: richedit.h:407
#define SCF_SELECTION
Definition: richedit.h:235
#define EM_GETCHARFORMAT
Definition: richedit.h:91
#define SEL_TEXT
Definition: richedit.h:823
#define EM_SETCHARFORMAT
Definition: richedit.h:101
#define RICHEDIT_CLASS20A
Definition: richedit.h:43
#define CFM_KERNING
Definition: richedit.h:352
#define CFM_ITALIC
Definition: richedit.h:333
#define EM_GETTEXTRANGE
Definition: richedit.h:108
#define EM_SETTEXTMODE
Definition: richedit.h:123
#define CFM_SIZE
Definition: richedit.h:362
#define GT_RAWTEXT
Definition: richedit.h:1039
#define GT_SELECTION
Definition: richedit.h:1038
#define EM_GETSCROLLPOS
Definition: richedit.h:165
struct _charformat2a CHARFORMAT2A
#define EM_SELECTIONTYPE
Definition: richedit.h:99
#define TM_PLAINTEXT
Definition: richedit.h:1028
#define GT_NOHIDDENTEXT
Definition: richedit.h:1040
#define GT_USECRLF
Definition: richedit.h:1037
#define CFM_FACE
Definition: richedit.h:360
#define EM_GETOLEINTERFACE
Definition: richedit.h:93
#define EM_GETTEXTEX
Definition: richedit.h:128
#define EM_SETUNDOLIMIT
Definition: richedit.h:116
WCHAR classname[128]
Definition: startup.c:15
#define calloc
Definition: rosglue.h:14
const WCHAR * str
#define CP_UTF8
Definition: nls.h:20
const char int int int static __inline const char * wine_dbgstr_a(const char *s)
Definition: debug.h:187
static __inline const char * wine_dbgstr_guid(const GUID *id)
Definition: debug.h:197
void __winetest_cdecl winetest_push_context(const char *fmt,...)
void winetest_pop_context(void)
strcpy
Definition: string.h:131
#define memset(x, y, z)
Definition: compat.h:39
HRESULT hr
Definition: shlfolder.c:183
long bottom
Definition: polytest.cpp:53
long right
Definition: polytest.cpp:53
long top
Definition: polytest.cpp:53
long left
Definition: polytest.cpp:53
LONG cx
Definition: kdterminal.h:27
LONG cy
Definition: kdterminal.h:28
LONG cpMax
Definition: richedit.h:501
LONG cpMin
Definition: richedit.h:500
DWORD cb
Definition: richedit.h:706
DWORD flags
Definition: richedit.h:707
LPCSTR lpDefaultChar
Definition: richedit.h:709
LPBOOL lpUsedDefChar
Definition: richedit.h:710
UINT codepage
Definition: richedit.h:708
DWORD dwUser
Definition: richole.idl:67
CLSID clsid
Definition: richole.idl:60
DWORD dwFlags
Definition: richole.idl:66
LPSTORAGE pstg
Definition: richole.idl:62
LPOLEOBJECT poleobj
Definition: richole.idl:61
DWORD dvaspect
Definition: richole.idl:65
LPOLECLIENTSITE polesite
Definition: richole.idl:63
DWORD cbStruct
Definition: richole.idl:58
LONG cp
Definition: richole.idl:59
SIZEL sizel
Definition: richole.idl:64
CHARRANGE chrg
Definition: richedit.h:508
LPSTR lpstrText
Definition: richedit.h:509
Definition: fci.c:127
Definition: parser.c:49
Definition: tftpd.h:60
Definition: send.c:48
IRichEditOleCallback IRichEditOleCallback_iface
Definition: richole.c:45
IStorage * stg
Definition: richole.c:52
int line
Definition: richole.c:47
ULONG expect_queryinsertobject
Definition: richole.c:49
const CLSID * clsid
Definition: richole.c:51
LONG ref
Definition: richole.c:46
HRESULT queryinsertobject_result
Definition: richole.c:54
LONG cp
Definition: richole.c:53
Definition: ps.c:97
int draw_count
Definition: richole.c:230
LONG ref
Definition: richole.c:228
int line
Definition: richole.c:229
IOleObject IOleObject_iface
Definition: richole.c:227
SIZEL extent
Definition: richole.c:234
IOleClientSite * clientsite
Definition: richole.c:232
IViewObject IViewObject_iface
Definition: richole.c:236
IOleAdviseHolder * advise_holder
Definition: richole.c:233
HWND hwnd
Definition: richole.c:5230
BOOL last_undo_status
Definition: richole.c:5235
ITextDocument * doc
Definition: richole.c:5231
int test_flags
Definition: richole.c:5232
enum editorUndoState undo_ctl_state
Definition: richole.c:5233
LONG_PTR undo_limit
Definition: richole.c:5234
BOOL last_redo_status
Definition: richole.c:5236
#define max(a, b)
Definition: svc.c:63
VOID WINAPI DECLSPEC_HOTPATCH Sleep(IN DWORD dwMilliseconds)
Definition: synch.c:790
EXTERN_C const IID IID_ITextServices
Definition: textserv.h:36
@ tomUseTwips
Definition: tom.idl:46
@ tomAutoColor
Definition: tom.idl:32
@ tomRTF
Definition: tom.idl:178
@ tomApplyNow
Definition: tom.idl:38
@ tomPasteFile
Definition: tom.idl:172
@ tomSentence
Definition: tom.idl:120
@ tomEnd
Definition: tom.idl:66
@ tomText
Definition: tom.idl:179
@ tomOpenExisting
Definition: tom.idl:175
@ tomUnknownStory
Definition: tom.idl:139
@ tomStory
Definition: tom.idl:123
@ tomResume
Definition: tom.idl:35
@ tomUsePoints
Definition: tom.idl:45
@ tomDefault
Definition: tom.idl:33
@ tomExtend
Definition: tom.idl:51
@ tomCreateAlways
Definition: tom.idl:174
@ tomApplyLater
Definition: tom.idl:39
@ tomSuspend
Definition: tom.idl:34
@ tomReadOnly
Definition: tom.idl:169
@ tomCharacter
Definition: tom.idl:118
@ tomTextFrameStory
Definition: tom.idl:144
@ tomShareDenyWrite
Definition: tom.idl:171
@ tomMove
Definition: tom.idl:50
@ tomTruncateExisting
Definition: tom.idl:177
@ tomStart
Definition: tom.idl:67
@ tomCacheParms
Definition: tom.idl:41
@ tomShareDenyRead
Definition: tom.idl:170
@ tomTrue
Definition: tom.idl:29
@ tomOpenAlways
Definition: tom.idl:176
@ tomFalse
Definition: tom.idl:28
@ tomCreateNew
Definition: tom.idl:173
@ tomTrackParms
Definition: tom.idl:40
@ tomUndefined
Definition: tom.idl:30
FT_UInt FT_UInt FT_Vector * kerning
Definition: ttdriver.c:207
TW_UINT32 TW_UINT16 TW_UINT16 MSG
Definition: twain.h:1829
float FLOAT
Definition: typedefs.h:69
uint32_t ULONG_PTR
Definition: typedefs.h:65
#define CONTAINING_RECORD(address, type, field)
Definition: typedefs.h:260
uint32_t ULONG
Definition: typedefs.h:59
static uacpi_status enter_mode(enum hw_mode mode, uacpi_bool *did_change)
Definition: uacpi.c:249
Definition: pdh_main.c:96
HRESULT WINAPI DECLSPEC_HOTPATCH VariantClear(VARIANTARG *pVarg)
Definition: variant.c:648
#define dpi
Definition: sysparams.c:23
DWORD WINAPI GetLastError(void)
Definition: except.c:1042
_In_ LONG _In_ HWND hwnd
Definition: winddi.h:4023
LONG_PTR LPARAM
Definition: windef.h:208
LONG_PTR LRESULT
Definition: windef.h:209
UINT_PTR WPARAM
Definition: windef.h:207
#define S_FALSE
Definition: winerror.h:2357
#define OLE_E_NOCONNECTION
Definition: winerror.h:2618
#define ERROR_SHARING_VIOLATION
Definition: winerror.h:135
#define E_NOINTERFACE
Definition: winerror.h:2364
#define E_ACCESSDENIED
Definition: winerror.h:2849
#define ERROR_FILE_EXISTS
Definition: winerror.h:165
#define OLEOBJ_E_NOVERBS
Definition: winerror.h:2722
#define E_UNEXPECTED
Definition: winerror.h:2456
#define HRESULT_FROM_WIN32(x)
Definition: winerror.h:92
#define DISP_E_UNKNOWNNAME
Definition: winerror.h:2515
#define CO_E_RELEASED
Definition: winerror.h:2818
HGDIOBJ WINAPI GetStockObject(_In_ int)
int WINAPI GetDeviceCaps(_In_opt_ HDC, _In_ int)
#define DKGRAY_BRUSH
Definition: wingdi.h:897
#define FW_BOLD
Definition: wingdi.h:378
#define LOGPIXELSY
Definition: wingdi.h:719
#define FW_NORMAL
Definition: wingdi.h:373
#define LOGPIXELSX
Definition: wingdi.h:718
int WINAPI FillRect(HDC, LPCRECT, HBRUSH)
#define EM_SETREADONLY
Definition: winuser.h:2034
BOOL WINAPI TranslateMessage(_In_ const MSG *)
struct tagSCROLLINFO SCROLLINFO
#define CreateWindowA(a, b, c, d, e, f, g, h, i, j, k)
Definition: winuser.h:4391
#define SIF_RANGE
Definition: winuser.h:1246
#define EM_GETSEL
Definition: winuser.h:2016
#define EM_SETPASSWORDCHAR
Definition: winuser.h:2033
#define SB_VERT
Definition: winuser.h:553
int WINAPI GetClassNameA(_In_ HWND hWnd, _Out_writes_to_(nMaxCount, return) LPSTR lpClassName, _In_ int nMaxCount)
#define EM_EMPTYUNDOBUFFER
Definition: winuser.h:2004
LONG WINAPI GetWindowLongW(_In_ HWND, _In_ int)
HWND WINAPI GetOpenClipboardWindow(void)
Definition: ntwrapper.h:214
#define EM_REPLACESEL
Definition: winuser.h:2025
BOOL WINAPI CloseClipboard(void)
Definition: ntwrapper.h:178
LRESULT WINAPI SendMessageA(_In_ HWND, _In_ UINT, _In_ WPARAM, _In_ LPARAM)
#define WM_GETTEXT
Definition: winuser.h:1637
BOOL WINAPI OpenClipboard(_In_opt_ HWND)
HANDLE WINAPI GetClipboardData(_In_ UINT)
#define WM_SETTEXT
Definition: winuser.h:1636
#define EM_CANUNDO
Definition: winuser.h:2002
BOOL WINAPI PeekMessageW(_Out_ LPMSG, _In_opt_ HWND, _In_ UINT, _In_ UINT, _In_ UINT)
#define EM_UNDO
Definition: winuser.h:2040
#define PM_REMOVE
Definition: winuser.h:1207
BOOL WINAPI UpdateWindow(_In_ HWND)
#define EM_SETSEL
Definition: winuser.h:2037
LRESULT WINAPI DispatchMessageW(_In_ const MSG *)
#define SIF_POS
Definition: winuser.h:1245
#define GWL_STYLE
Definition: winuser.h:863
BOOL WINAPI GetScrollInfo(_In_ HWND, _In_ int, _Inout_ LPSCROLLINFO)
BOOL WINAPI DestroyWindow(_In_ HWND)
LRESULT WINAPI SendMessageW(_In_ HWND, _In_ UINT, _In_ WPARAM, _In_ LPARAM)
const char * LPCSTR
Definition: xmlstorage.h:183
__wchar_t WCHAR
Definition: xmlstorage.h:180
const WCHAR * LPCWSTR
Definition: xmlstorage.h:185
char CHAR
Definition: xmlstorage.h:175