msi/test: Uninstall the test product when skipping patch tests.
[wine] / dlls / mshtml / htmlimg.c
1 /*
2  * Copyright 2008 Jacek Caban for CodeWeavers
3  *
4  * This library is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU Lesser General Public
6  * License as published by the Free Software Foundation; either
7  * version 2.1 of the License, or (at your option) any later version.
8  *
9  * This library is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
12  * Lesser General Public License for more details.
13  *
14  * You should have received a copy of the GNU Lesser General Public
15  * License along with this library; if not, write to the Free Software
16  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
17  */
18
19 #include <stdarg.h>
20
21 #define COBJMACROS
22
23 #include "windef.h"
24 #include "winbase.h"
25 #include "winuser.h"
26 #include "ole2.h"
27
28 #include "wine/debug.h"
29
30 #include "mshtml_private.h"
31 #include "htmlevent.h"
32
33 WINE_DEFAULT_DEBUG_CHANNEL(mshtml);
34
35 typedef struct {
36     HTMLElement element;
37
38     const IHTMLImgElementVtbl *lpHTMLImgElementVtbl;
39
40     nsIDOMHTMLImageElement *nsimg;
41 } HTMLImgElement;
42
43 #define HTMLIMG(x)  ((IHTMLImgElement*)  &(x)->lpHTMLImgElementVtbl)
44
45 #define HTMLIMG_THIS(iface) DEFINE_THIS(HTMLImgElement, HTMLImgElement, iface)
46
47 static HRESULT WINAPI HTMLImgElement_QueryInterface(IHTMLImgElement *iface, REFIID riid, void **ppv)
48 {
49     HTMLImgElement *This = HTMLIMG_THIS(iface);
50
51     return IHTMLDOMNode_QueryInterface(HTMLDOMNODE(&This->element.node), riid, ppv);
52 }
53
54 static ULONG WINAPI HTMLImgElement_AddRef(IHTMLImgElement *iface)
55 {
56     HTMLImgElement *This = HTMLIMG_THIS(iface);
57
58     return IHTMLDOMNode_AddRef(HTMLDOMNODE(&This->element.node));
59 }
60
61 static ULONG WINAPI HTMLImgElement_Release(IHTMLImgElement *iface)
62 {
63     HTMLImgElement *This = HTMLIMG_THIS(iface);
64
65     return IHTMLDOMNode_Release(HTMLDOMNODE(&This->element.node));
66 }
67
68 static HRESULT WINAPI HTMLImgElement_GetTypeInfoCount(IHTMLImgElement *iface, UINT *pctinfo)
69 {
70     HTMLImgElement *This = HTMLIMG_THIS(iface);
71     return IDispatchEx_GetTypeInfoCount(DISPATCHEX(&This->element.node.dispex), pctinfo);
72 }
73
74 static HRESULT WINAPI HTMLImgElement_GetTypeInfo(IHTMLImgElement *iface, UINT iTInfo,
75                                               LCID lcid, ITypeInfo **ppTInfo)
76 {
77     HTMLImgElement *This = HTMLIMG_THIS(iface);
78     return IDispatchEx_GetTypeInfo(DISPATCHEX(&This->element.node.dispex), iTInfo, lcid, ppTInfo);
79 }
80
81 static HRESULT WINAPI HTMLImgElement_GetIDsOfNames(IHTMLImgElement *iface, REFIID riid,
82                                                 LPOLESTR *rgszNames, UINT cNames,
83                                                 LCID lcid, DISPID *rgDispId)
84 {
85     HTMLImgElement *This = HTMLIMG_THIS(iface);
86     return IDispatchEx_GetIDsOfNames(DISPATCHEX(&This->element.node.dispex), riid, rgszNames, cNames, lcid, rgDispId);
87 }
88
89 static HRESULT WINAPI HTMLImgElement_Invoke(IHTMLImgElement *iface, DISPID dispIdMember,
90                             REFIID riid, LCID lcid, WORD wFlags, DISPPARAMS *pDispParams,
91                             VARIANT *pVarResult, EXCEPINFO *pExcepInfo, UINT *puArgErr)
92 {
93     HTMLImgElement *This = HTMLIMG_THIS(iface);
94     return IDispatchEx_Invoke(DISPATCHEX(&This->element.node.dispex), dispIdMember, riid, lcid, wFlags, pDispParams,
95             pVarResult, pExcepInfo, puArgErr);
96 }
97
98 static HRESULT WINAPI HTMLImgElement_put_isMap(IHTMLImgElement *iface, VARIANT_BOOL v)
99 {
100     HTMLImgElement *This = HTMLIMG_THIS(iface);
101     FIXME("(%p)->(%x)\n", This, v);
102     return E_NOTIMPL;
103 }
104
105 static HRESULT WINAPI HTMLImgElement_get_isMap(IHTMLImgElement *iface, VARIANT_BOOL *p)
106 {
107     HTMLImgElement *This = HTMLIMG_THIS(iface);
108     FIXME("(%p)->(%p)\n", This, p);
109     return E_NOTIMPL;
110 }
111
112 static HRESULT WINAPI HTMLImgElement_put_useMap(IHTMLImgElement *iface, BSTR v)
113 {
114     HTMLImgElement *This = HTMLIMG_THIS(iface);
115     FIXME("(%p)->(%s)\n", This, debugstr_w(v));
116     return E_NOTIMPL;
117 }
118
119 static HRESULT WINAPI HTMLImgElement_get_useMap(IHTMLImgElement *iface, BSTR *p)
120 {
121     HTMLImgElement *This = HTMLIMG_THIS(iface);
122     FIXME("(%p)->(%p)\n", This, p);
123     return E_NOTIMPL;
124 }
125
126 static HRESULT WINAPI HTMLImgElement_get_mimeType(IHTMLImgElement *iface, BSTR *p)
127 {
128     HTMLImgElement *This = HTMLIMG_THIS(iface);
129     FIXME("(%p)->(%p)\n", This, p);
130     return E_NOTIMPL;
131 }
132
133 static HRESULT WINAPI HTMLImgElement_get_fileSize(IHTMLImgElement *iface, BSTR *p)
134 {
135     HTMLImgElement *This = HTMLIMG_THIS(iface);
136     FIXME("(%p)->(%p)\n", This, p);
137     return E_NOTIMPL;
138 }
139
140 static HRESULT WINAPI HTMLImgElement_get_fileCreatedDate(IHTMLImgElement *iface, BSTR *p)
141 {
142     HTMLImgElement *This = HTMLIMG_THIS(iface);
143     FIXME("(%p)->(%p)\n", This, p);
144     return E_NOTIMPL;
145 }
146
147 static HRESULT WINAPI HTMLImgElement_get_fileModifiedDate(IHTMLImgElement *iface, BSTR *p)
148 {
149     HTMLImgElement *This = HTMLIMG_THIS(iface);
150     FIXME("(%p)->(%p)\n", This, p);
151     return E_NOTIMPL;
152 }
153
154 static HRESULT WINAPI HTMLImgElement_get_fileUpdatedDate(IHTMLImgElement *iface, BSTR *p)
155 {
156     HTMLImgElement *This = HTMLIMG_THIS(iface);
157     FIXME("(%p)->(%p)\n", This, p);
158     return E_NOTIMPL;
159 }
160
161 static HRESULT WINAPI HTMLImgElement_get_protocol(IHTMLImgElement *iface, BSTR *p)
162 {
163     HTMLImgElement *This = HTMLIMG_THIS(iface);
164     FIXME("(%p)->(%p)\n", This, p);
165     return E_NOTIMPL;
166 }
167
168 static HRESULT WINAPI HTMLImgElement_get_href(IHTMLImgElement *iface, BSTR *p)
169 {
170     HTMLImgElement *This = HTMLIMG_THIS(iface);
171     FIXME("(%p)->(%p)\n", This, p);
172     return E_NOTIMPL;
173 }
174
175 static HRESULT WINAPI HTMLImgElement_get_nameProp(IHTMLImgElement *iface, BSTR *p)
176 {
177     HTMLImgElement *This = HTMLIMG_THIS(iface);
178     FIXME("(%p)->(%p)\n", This, p);
179     return E_NOTIMPL;
180 }
181
182 static HRESULT WINAPI HTMLImgElement_put_border(IHTMLImgElement *iface, VARIANT v)
183 {
184     HTMLImgElement *This = HTMLIMG_THIS(iface);
185     FIXME("(%p)->()\n", This);
186     return E_NOTIMPL;
187 }
188
189 static HRESULT WINAPI HTMLImgElement_get_border(IHTMLImgElement *iface, VARIANT *p)
190 {
191     HTMLImgElement *This = HTMLIMG_THIS(iface);
192     FIXME("(%p)->(%p)\n", This, p);
193     return E_NOTIMPL;
194 }
195
196 static HRESULT WINAPI HTMLImgElement_put_vspace(IHTMLImgElement *iface, LONG v)
197 {
198     HTMLImgElement *This = HTMLIMG_THIS(iface);
199     FIXME("(%p)->(%d)\n", This, v);
200     return E_NOTIMPL;
201 }
202
203 static HRESULT WINAPI HTMLImgElement_get_vspace(IHTMLImgElement *iface, LONG *p)
204 {
205     HTMLImgElement *This = HTMLIMG_THIS(iface);
206     FIXME("(%p)->(%p)\n", This, p);
207     return E_NOTIMPL;
208 }
209
210 static HRESULT WINAPI HTMLImgElement_put_hspace(IHTMLImgElement *iface, LONG v)
211 {
212     HTMLImgElement *This = HTMLIMG_THIS(iface);
213     FIXME("(%p)->(%d)\n", This, v);
214     return E_NOTIMPL;
215 }
216
217 static HRESULT WINAPI HTMLImgElement_get_hspace(IHTMLImgElement *iface, LONG *p)
218 {
219     HTMLImgElement *This = HTMLIMG_THIS(iface);
220     FIXME("(%p)->(%p)\n", This, p);
221     return E_NOTIMPL;
222 }
223
224 static HRESULT WINAPI HTMLImgElement_put_alt(IHTMLImgElement *iface, BSTR v)
225 {
226     HTMLImgElement *This = HTMLIMG_THIS(iface);
227     nsAString alt_str;
228     nsresult nsres;
229
230     TRACE("(%p)->(%s)\n", This, debugstr_w(v));
231
232     nsAString_InitDepend(&alt_str, v);
233     nsres = nsIDOMHTMLImageElement_SetAlt(This->nsimg, &alt_str);
234     nsAString_Finish(&alt_str);
235     if(NS_FAILED(nsres))
236         ERR("SetAlt failed: %08x\n", nsres);
237
238     return S_OK;
239 }
240
241 static HRESULT WINAPI HTMLImgElement_get_alt(IHTMLImgElement *iface, BSTR *p)
242 {
243     HTMLImgElement *This = HTMLIMG_THIS(iface);
244     nsAString alt_str;
245     nsresult nsres;
246
247     TRACE("(%p)->(%p)\n", This, p);
248
249     nsAString_Init(&alt_str, NULL);
250     nsres = nsIDOMHTMLImageElement_GetAlt(This->nsimg, &alt_str);
251     if(NS_SUCCEEDED(nsres)) {
252         const PRUnichar *alt;
253
254         nsAString_GetData(&alt_str, &alt);
255         *p = *alt ? SysAllocString(alt) : NULL;
256     }else {
257         ERR("GetAlt failed: %08x\n", nsres);
258     }
259     nsAString_Finish(&alt_str);
260
261     return NS_SUCCEEDED(nsres) ? S_OK : E_FAIL;
262 }
263
264 static HRESULT WINAPI HTMLImgElement_put_src(IHTMLImgElement *iface, BSTR v)
265 {
266     HTMLImgElement *This = HTMLIMG_THIS(iface);
267     nsAString src_str;
268     nsresult nsres;
269
270     TRACE("(%p)->(%s)\n", This, debugstr_w(v));
271
272     nsAString_InitDepend(&src_str, v);
273     nsres = nsIDOMHTMLImageElement_SetSrc(This->nsimg, &src_str);
274     nsAString_Finish(&src_str);
275     if(NS_FAILED(nsres))
276         ERR("SetSrc failed: %08x\n", nsres);
277
278     return NS_OK;
279 }
280
281 static HRESULT WINAPI HTMLImgElement_get_src(IHTMLImgElement *iface, BSTR *p)
282 {
283     HTMLImgElement *This = HTMLIMG_THIS(iface);
284     const PRUnichar *src;
285     nsAString src_str;
286     nsresult nsres;
287     HRESULT hres;
288
289     TRACE("(%p)->(%p)\n", This, p);
290
291     nsAString_Init(&src_str, NULL);
292     nsres = nsIDOMHTMLImageElement_GetSrc(This->nsimg, &src_str);
293     if(NS_FAILED(nsres)) {
294         ERR("GetSrc failed: %08x\n", nsres);
295         return E_FAIL;
296     }
297
298     nsAString_GetData(&src_str, &src);
299     hres = nsuri_to_url(src, TRUE, p);
300     nsAString_Finish(&src_str);
301
302     return hres;
303 }
304
305 static HRESULT WINAPI HTMLImgElement_put_lowsrc(IHTMLImgElement *iface, BSTR v)
306 {
307     HTMLImgElement *This = HTMLIMG_THIS(iface);
308     FIXME("(%p)->(%s)\n", This, debugstr_w(v));
309     return E_NOTIMPL;
310 }
311
312 static HRESULT WINAPI HTMLImgElement_get_lowsrc(IHTMLImgElement *iface, BSTR *p)
313 {
314     HTMLImgElement *This = HTMLIMG_THIS(iface);
315     FIXME("(%p)->(%p)\n", This, p);
316     return E_NOTIMPL;
317 }
318
319 static HRESULT WINAPI HTMLImgElement_put_vrml(IHTMLImgElement *iface, BSTR v)
320 {
321     HTMLImgElement *This = HTMLIMG_THIS(iface);
322     FIXME("(%p)->(%s)\n", This, debugstr_w(v));
323     return E_NOTIMPL;
324 }
325
326 static HRESULT WINAPI HTMLImgElement_get_vrml(IHTMLImgElement *iface, BSTR *p)
327 {
328     HTMLImgElement *This = HTMLIMG_THIS(iface);
329     FIXME("(%p)->(%p)\n", This, p);
330     return E_NOTIMPL;
331 }
332
333 static HRESULT WINAPI HTMLImgElement_put_dynsrc(IHTMLImgElement *iface, BSTR v)
334 {
335     HTMLImgElement *This = HTMLIMG_THIS(iface);
336     FIXME("(%p)->(%s)\n", This, debugstr_w(v));
337     return E_NOTIMPL;
338 }
339
340 static HRESULT WINAPI HTMLImgElement_get_dynsrc(IHTMLImgElement *iface, BSTR *p)
341 {
342     HTMLImgElement *This = HTMLIMG_THIS(iface);
343     FIXME("(%p)->(%p)\n", This, p);
344     return E_NOTIMPL;
345 }
346
347 static HRESULT WINAPI HTMLImgElement_get_readyState(IHTMLImgElement *iface, BSTR *p)
348 {
349     HTMLImgElement *This = HTMLIMG_THIS(iface);
350     FIXME("(%p)->(%p)\n", This, p);
351     return E_NOTIMPL;
352 }
353
354 static HRESULT WINAPI HTMLImgElement_get_complete(IHTMLImgElement *iface, VARIANT_BOOL *p)
355 {
356     HTMLImgElement *This = HTMLIMG_THIS(iface);
357     FIXME("(%p)->(%p)\n", This, p);
358     return E_NOTIMPL;
359 }
360
361 static HRESULT WINAPI HTMLImgElement_put_loop(IHTMLImgElement *iface, VARIANT v)
362 {
363     HTMLImgElement *This = HTMLIMG_THIS(iface);
364     FIXME("(%p)->()\n", This);
365     return E_NOTIMPL;
366 }
367
368 static HRESULT WINAPI HTMLImgElement_get_loop(IHTMLImgElement *iface, VARIANT *p)
369 {
370     HTMLImgElement *This = HTMLIMG_THIS(iface);
371     FIXME("(%p)->(%p)\n", This, p);
372     return E_NOTIMPL;
373 }
374
375 static HRESULT WINAPI HTMLImgElement_put_align(IHTMLImgElement *iface, BSTR v)
376 {
377     HTMLImgElement *This = HTMLIMG_THIS(iface);
378     FIXME("(%p)->(%s)\n", This, debugstr_w(v));
379     return E_NOTIMPL;
380 }
381
382 static HRESULT WINAPI HTMLImgElement_get_align(IHTMLImgElement *iface, BSTR *p)
383 {
384     HTMLImgElement *This = HTMLIMG_THIS(iface);
385     FIXME("(%p)->(%p)\n", This, p);
386     return E_NOTIMPL;
387 }
388
389 static HRESULT WINAPI HTMLImgElement_put_onload(IHTMLImgElement *iface, VARIANT v)
390 {
391     HTMLImgElement *This = HTMLIMG_THIS(iface);
392
393     TRACE("(%p)->(%s)\n", This, debugstr_variant(&v));
394
395     return set_node_event(&This->element.node, EVENTID_LOAD, &v);
396 }
397
398 static HRESULT WINAPI HTMLImgElement_get_onload(IHTMLImgElement *iface, VARIANT *p)
399 {
400     HTMLImgElement *This = HTMLIMG_THIS(iface);
401
402     TRACE("(%p)->(%p)\n", This, p);
403
404     return get_node_event(&This->element.node, EVENTID_LOAD, p);
405 }
406
407 static HRESULT WINAPI HTMLImgElement_put_onerror(IHTMLImgElement *iface, VARIANT v)
408 {
409     HTMLImgElement *This = HTMLIMG_THIS(iface);
410     FIXME("(%p)->()\n", This);
411     return E_NOTIMPL;
412 }
413
414 static HRESULT WINAPI HTMLImgElement_get_onerror(IHTMLImgElement *iface, VARIANT *p)
415 {
416     HTMLImgElement *This = HTMLIMG_THIS(iface);
417     FIXME("(%p)->(%p)\n", This, p);
418     return E_NOTIMPL;
419 }
420
421 static HRESULT WINAPI HTMLImgElement_put_onabort(IHTMLImgElement *iface, VARIANT v)
422 {
423     HTMLImgElement *This = HTMLIMG_THIS(iface);
424     FIXME("(%p)->()\n", This);
425     return E_NOTIMPL;
426 }
427
428 static HRESULT WINAPI HTMLImgElement_get_onabort(IHTMLImgElement *iface, VARIANT *p)
429 {
430     HTMLImgElement *This = HTMLIMG_THIS(iface);
431     FIXME("(%p)->(%p)\n", This, p);
432     return E_NOTIMPL;
433 }
434
435 static HRESULT WINAPI HTMLImgElement_put_name(IHTMLImgElement *iface, BSTR v)
436 {
437     HTMLImgElement *This = HTMLIMG_THIS(iface);
438     FIXME("(%p)->(%s)\n", This, debugstr_w(v));
439     return E_NOTIMPL;
440 }
441
442 static HRESULT WINAPI HTMLImgElement_get_name(IHTMLImgElement *iface, BSTR *p)
443 {
444     HTMLImgElement *This = HTMLIMG_THIS(iface);
445     nsAString strName;
446     nsresult nsres;
447
448     TRACE("(%p)->(%p)\n", This, p);
449
450     nsAString_Init(&strName, NULL);
451     nsres = nsIDOMHTMLImageElement_GetName(This->nsimg, &strName);
452     if(NS_SUCCEEDED(nsres)) {
453         const PRUnichar *str;
454
455         nsAString_GetData(&strName, &str);
456         *p = *str ? SysAllocString(str) : NULL;
457     }else {
458         ERR("GetName failed: %08x\n", nsres);
459     }
460     nsAString_Finish(&strName);
461
462     return NS_SUCCEEDED(nsres) ? S_OK : E_FAIL;
463 }
464
465 static HRESULT WINAPI HTMLImgElement_put_width(IHTMLImgElement *iface, LONG v)
466 {
467     HTMLImgElement *This = HTMLIMG_THIS(iface);
468     nsresult nsres;
469
470     TRACE("(%p)->(%d)\n", This, v);
471
472     nsres = nsIDOMHTMLImageElement_SetWidth(This->nsimg, v);
473     if(NS_FAILED(nsres)) {
474         ERR("SetWidth failed: %08x\n", nsres);
475         return E_FAIL;
476     }
477
478     return S_OK;
479 }
480
481 static HRESULT WINAPI HTMLImgElement_get_width(IHTMLImgElement *iface, LONG *p)
482 {
483     HTMLImgElement *This = HTMLIMG_THIS(iface);
484     PRInt32 width;
485     nsresult nsres;
486
487     TRACE("(%p)->(%p)\n", This, p);
488
489     nsres = nsIDOMHTMLImageElement_GetWidth(This->nsimg, &width);
490     if(NS_FAILED(nsres)) {
491         ERR("GetWidth failed: %08x\n", nsres);
492         return E_FAIL;
493     }
494
495     *p = width;
496     return S_OK;
497 }
498
499 static HRESULT WINAPI HTMLImgElement_put_height(IHTMLImgElement *iface, LONG v)
500 {
501     HTMLImgElement *This = HTMLIMG_THIS(iface);
502     nsresult nsres;
503
504     TRACE("(%p)->(%d)\n", This, v);
505
506     nsres = nsIDOMHTMLImageElement_SetHeight(This->nsimg, v);
507     if(NS_FAILED(nsres)) {
508         ERR("SetHeight failed: %08x\n", nsres);
509         return E_FAIL;
510     }
511
512     return S_OK;
513 }
514
515 static HRESULT WINAPI HTMLImgElement_get_height(IHTMLImgElement *iface, LONG *p)
516 {
517     HTMLImgElement *This = HTMLIMG_THIS(iface);
518     PRInt32 height;
519     nsresult nsres;
520
521     TRACE("(%p)->(%p)\n", This, p);
522
523     nsres = nsIDOMHTMLImageElement_GetHeight(This->nsimg, &height);
524     if(NS_FAILED(nsres)) {
525         ERR("GetHeight failed: %08x\n", nsres);
526         return E_FAIL;
527     }
528
529     *p = height;
530     return S_OK;
531 }
532
533 static HRESULT WINAPI HTMLImgElement_put_start(IHTMLImgElement *iface, BSTR v)
534 {
535     HTMLImgElement *This = HTMLIMG_THIS(iface);
536     FIXME("(%p)->()\n", This);
537     return E_NOTIMPL;
538 }
539
540 static HRESULT WINAPI HTMLImgElement_get_start(IHTMLImgElement *iface, BSTR *p)
541 {
542     HTMLImgElement *This = HTMLIMG_THIS(iface);
543     FIXME("(%p)->(%p)\n", This, p);
544     return E_NOTIMPL;
545 }
546
547 #undef HTMLIMG_THIS
548
549 static const IHTMLImgElementVtbl HTMLImgElementVtbl = {
550     HTMLImgElement_QueryInterface,
551     HTMLImgElement_AddRef,
552     HTMLImgElement_Release,
553     HTMLImgElement_GetTypeInfoCount,
554     HTMLImgElement_GetTypeInfo,
555     HTMLImgElement_GetIDsOfNames,
556     HTMLImgElement_Invoke,
557     HTMLImgElement_put_isMap,
558     HTMLImgElement_get_isMap,
559     HTMLImgElement_put_useMap,
560     HTMLImgElement_get_useMap,
561     HTMLImgElement_get_mimeType,
562     HTMLImgElement_get_fileSize,
563     HTMLImgElement_get_fileCreatedDate,
564     HTMLImgElement_get_fileModifiedDate,
565     HTMLImgElement_get_fileUpdatedDate,
566     HTMLImgElement_get_protocol,
567     HTMLImgElement_get_href,
568     HTMLImgElement_get_nameProp,
569     HTMLImgElement_put_border,
570     HTMLImgElement_get_border,
571     HTMLImgElement_put_vspace,
572     HTMLImgElement_get_vspace,
573     HTMLImgElement_put_hspace,
574     HTMLImgElement_get_hspace,
575     HTMLImgElement_put_alt,
576     HTMLImgElement_get_alt,
577     HTMLImgElement_put_src,
578     HTMLImgElement_get_src,
579     HTMLImgElement_put_lowsrc,
580     HTMLImgElement_get_lowsrc,
581     HTMLImgElement_put_vrml,
582     HTMLImgElement_get_vrml,
583     HTMLImgElement_put_dynsrc,
584     HTMLImgElement_get_dynsrc,
585     HTMLImgElement_get_readyState,
586     HTMLImgElement_get_complete,
587     HTMLImgElement_put_loop,
588     HTMLImgElement_get_loop,
589     HTMLImgElement_put_align,
590     HTMLImgElement_get_align,
591     HTMLImgElement_put_onload,
592     HTMLImgElement_get_onload,
593     HTMLImgElement_put_onerror,
594     HTMLImgElement_get_onerror,
595     HTMLImgElement_put_onabort,
596     HTMLImgElement_get_onabort,
597     HTMLImgElement_put_name,
598     HTMLImgElement_get_name,
599     HTMLImgElement_put_width,
600     HTMLImgElement_get_width,
601     HTMLImgElement_put_height,
602     HTMLImgElement_get_height,
603     HTMLImgElement_put_start,
604     HTMLImgElement_get_start
605 };
606
607 #define HTMLIMG_NODE_THIS(iface) DEFINE_THIS2(HTMLImgElement, element.node, iface)
608
609 static HRESULT HTMLImgElement_QI(HTMLDOMNode *iface, REFIID riid, void **ppv)
610 {
611     HTMLImgElement *This = HTMLIMG_NODE_THIS(iface);
612
613     *ppv = NULL;
614
615     if(IsEqualGUID(&IID_IHTMLImgElement, riid)) {
616         TRACE("(%p)->(IID_IHTMLImgElement %p)\n", This, ppv);
617         *ppv = HTMLIMG(This);
618     }else {
619         return HTMLElement_QI(&This->element.node, riid, ppv);
620     }
621
622     IUnknown_AddRef((IUnknown*)*ppv);
623     return S_OK;
624 }
625
626 static void HTMLImgElement_destructor(HTMLDOMNode *iface)
627 {
628     HTMLImgElement *This = HTMLIMG_NODE_THIS(iface);
629
630     if(This->nsimg)
631         nsIDOMHTMLImageElement_Release(This->nsimg);
632
633     HTMLElement_destructor(&This->element.node);
634 }
635
636 static HRESULT HTMLImgElement_get_readystate(HTMLDOMNode *iface, BSTR *p)
637 {
638     HTMLImgElement *This = HTMLIMG_NODE_THIS(iface);
639
640     return IHTMLImgElement_get_readyState(HTMLIMG(This), p);
641 }
642
643 #undef HTMLIMG_NODE_THIS
644
645 static const NodeImplVtbl HTMLImgElementImplVtbl = {
646     HTMLImgElement_QI,
647     HTMLImgElement_destructor,
648     NULL,
649     NULL,
650     NULL,
651     NULL,
652     NULL,
653     HTMLImgElement_get_readystate
654 };
655
656 static const tid_t HTMLImgElement_iface_tids[] = {
657     HTMLELEMENT_TIDS,
658     IHTMLImgElement_tid,
659     0
660 };
661 static dispex_static_data_t HTMLImgElement_dispex = {
662     NULL,
663     DispHTMLImg_tid,
664     NULL,
665     HTMLImgElement_iface_tids
666 };
667
668 HTMLElement *HTMLImgElement_Create(HTMLDocumentNode *doc, nsIDOMHTMLElement *nselem)
669 {
670     HTMLImgElement *ret = heap_alloc_zero(sizeof(HTMLImgElement));
671     nsresult nsres;
672
673     ret->lpHTMLImgElementVtbl = &HTMLImgElementVtbl;
674     ret->element.node.vtbl = &HTMLImgElementImplVtbl;
675
676     nsres = nsIDOMHTMLElement_QueryInterface(nselem, &IID_nsIDOMHTMLImageElement, (void**)&ret->nsimg);
677     if(NS_FAILED(nsres))
678         ERR("Could not get nsIDOMHTMLImageElement: %08x\n", nsres);
679
680     HTMLElement_Init(&ret->element, doc, nselem, &HTMLImgElement_dispex);
681
682     return &ret->element;
683 }
684
685 #define HTMLIMGFACTORY_THIS(iface) DEFINE_THIS(HTMLImageElementFactory, HTMLImageElementFactory, iface)
686
687 static HRESULT WINAPI HTMLImageElementFactory_QueryInterface(IHTMLImageElementFactory *iface,
688         REFIID riid, void **ppv)
689 {
690     HTMLImageElementFactory *This = HTMLIMGFACTORY_THIS(iface);
691
692     *ppv = NULL;
693
694     if(IsEqualGUID(&IID_IUnknown, riid)) {
695         TRACE("(%p)->(IID_Unknown %p)\n", This, ppv);
696         *ppv = HTMLIMGFACTORY(This);
697     }else if(IsEqualGUID(&IID_IHTMLImageElementFactory, riid)) {
698         TRACE("(%p)->(IID_IHTMLImageElementFactory %p)\n", This, ppv);
699         *ppv = HTMLIMGFACTORY(This);
700     }else if(dispex_query_interface(&This->dispex, riid, ppv))
701         return *ppv ? S_OK : E_NOINTERFACE;
702
703     if(*ppv) {
704         IUnknown_AddRef((IUnknown*)*ppv);
705         return S_OK;
706     }
707
708     WARN("(%p)->(%s %p)\n", This, debugstr_guid(riid), ppv);
709     return E_NOINTERFACE;
710 }
711
712 static ULONG WINAPI HTMLImageElementFactory_AddRef(IHTMLImageElementFactory *iface)
713 {
714     HTMLImageElementFactory *This = HTMLIMGFACTORY_THIS(iface);
715     LONG ref = InterlockedIncrement(&This->ref);
716
717     TRACE("(%p) ref=%d\n", This, ref);
718
719     return ref;
720 }
721
722 static ULONG WINAPI HTMLImageElementFactory_Release(IHTMLImageElementFactory *iface)
723 {
724     HTMLImageElementFactory *This = HTMLIMGFACTORY_THIS(iface);
725     LONG ref = InterlockedDecrement(&This->ref);
726
727     TRACE("(%p) ref=%d\n", This, ref);
728
729     if(!ref)
730         heap_free(This);
731
732     return ref;
733 }
734
735 static HRESULT WINAPI HTMLImageElementFactory_GetTypeInfoCount(IHTMLImageElementFactory *iface,
736         UINT *pctinfo)
737 {
738     HTMLImageElementFactory *This = HTMLIMGFACTORY_THIS(iface);
739     FIXME("(%p)->(%p)\n", This, pctinfo);
740     return E_NOTIMPL;
741 }
742
743 static HRESULT WINAPI HTMLImageElementFactory_GetTypeInfo(IHTMLImageElementFactory *iface,
744         UINT iTInfo, LCID lcid, ITypeInfo **ppTInfo)
745 {
746     HTMLImageElementFactory *This = HTMLIMGFACTORY_THIS(iface);
747     FIXME("(%p)->(%u %u %p)\n", This, iTInfo, lcid, ppTInfo);
748     return E_NOTIMPL;
749 }
750
751 static HRESULT WINAPI HTMLImageElementFactory_GetIDsOfNames(IHTMLImageElementFactory *iface,
752         REFIID riid, LPOLESTR *rgszNames, UINT cNames, LCID lcid,
753         DISPID *rgDispId)
754 {
755     HTMLImageElementFactory *This = HTMLIMGFACTORY_THIS(iface);
756     FIXME("(%p)->(%s %p %u %u %p)\n", This, debugstr_guid(riid), rgszNames,
757             cNames, lcid, rgDispId);
758     return E_NOTIMPL;
759 }
760
761 static HRESULT WINAPI HTMLImageElementFactory_Invoke(IHTMLImageElementFactory *iface,
762         DISPID dispIdMember, REFIID riid, LCID lcid, WORD wFlags,
763         DISPPARAMS *pDispParams, VARIANT *pVarResult, EXCEPINFO *pExcepInfo,
764         UINT *puArgErr)
765 {
766     HTMLImageElementFactory *This = HTMLIMGFACTORY_THIS(iface);
767     FIXME("(%p)->(%d %s %d %d %p %p %p %p)\n", This, dispIdMember, debugstr_guid(riid),
768             lcid, wFlags, pDispParams, pVarResult, pExcepInfo, puArgErr);
769     return E_NOTIMPL;
770 }
771
772 static LONG var_to_size(const VARIANT *v)
773 {
774     switch(V_VT(v)) {
775     case VT_EMPTY:
776         return 0;
777     case VT_I4:
778         return V_I4(v);
779     case VT_BSTR: {
780         LONG ret;
781         HRESULT hres;
782
783         hres = VarI4FromStr(V_BSTR(v), 0, 0, &ret);
784         if(FAILED(hres)) {
785             FIXME("VarI4FromStr failed: %08x\n", hres);
786             return 0;
787         }
788         return ret;
789     }
790     default:
791         FIXME("unsupported size %s\n", debugstr_variant(v));
792     }
793     return 0;
794 }
795
796 static HRESULT WINAPI HTMLImageElementFactory_create(IHTMLImageElementFactory *iface,
797         VARIANT width, VARIANT height, IHTMLImgElement **img_elem)
798 {
799     HTMLImageElementFactory *This = HTMLIMGFACTORY_THIS(iface);
800     IHTMLImgElement *img;
801     HTMLElement *elem;
802     nsIDOMHTMLElement *nselem;
803     LONG l;
804     HRESULT hres;
805
806     static const PRUnichar imgW[] = {'I','M','G',0};
807
808     TRACE("(%p)->(%s %s %p)\n", This, debugstr_variant(&width),
809             debugstr_variant(&height), img_elem);
810
811     if(!This->window || !This->window->doc) {
812         WARN("NULL doc\n");
813         return E_UNEXPECTED;
814     }
815
816     *img_elem = NULL;
817
818     hres = create_nselem(This->window->doc, imgW, &nselem);
819     if(FAILED(hres))
820         return hres;
821
822     elem = HTMLElement_Create(This->window->doc, (nsIDOMNode*)nselem, FALSE);
823     if(!elem) {
824         ERR("HTMLElement_Create failed\n");
825         return E_FAIL;
826     }
827
828     hres = IHTMLElement_QueryInterface(HTMLELEM(elem), &IID_IHTMLImgElement, (void**)&img);
829     if(FAILED(hres)) {
830         ERR("IHTMLElement_QueryInterface failed: 0x%08x\n", hres);
831         return hres;
832     }
833
834     nsIDOMHTMLElement_Release(nselem);
835
836     l = var_to_size(&width);
837     if(l)
838         IHTMLImgElement_put_width(img, l);
839     l = var_to_size(&height);
840     if(l)
841         IHTMLImgElement_put_height(img, l);
842
843     *img_elem = img;
844     return S_OK;
845 }
846
847 static HRESULT HTMLImageElementFactory_value(IUnknown *iface, LCID lcid,
848         WORD flags, DISPPARAMS *params, VARIANT *res, EXCEPINFO *ei,
849         IServiceProvider *caller)
850 {
851     HTMLImageElementFactory *This = HTMLIMGFACTORY_THIS(iface);
852     IHTMLImgElement *img;
853     VARIANT empty, *width, *height;
854     HRESULT hres;
855     int argc = params->cArgs - params->cNamedArgs;
856
857     V_VT(res) = VT_NULL;
858
859     V_VT(&empty) = VT_EMPTY;
860
861     width = argc >= 1 ? params->rgvarg + (params->cArgs - 1) : &empty;
862     height = argc >= 2 ? params->rgvarg + (params->cArgs - 2) : &empty;
863
864     hres = IHTMLImageElementFactory_create(HTMLIMGFACTORY(This), *width, *height, &img);
865     if(FAILED(hres))
866         return hres;
867
868     V_VT(res) = VT_DISPATCH;
869     V_DISPATCH(res) = (IDispatch*)img;
870
871     return S_OK;
872 }
873
874 #undef HTMLIMGFACTORY_THIS
875
876 static const IHTMLImageElementFactoryVtbl HTMLImageElementFactoryVtbl = {
877     HTMLImageElementFactory_QueryInterface,
878     HTMLImageElementFactory_AddRef,
879     HTMLImageElementFactory_Release,
880     HTMLImageElementFactory_GetTypeInfoCount,
881     HTMLImageElementFactory_GetTypeInfo,
882     HTMLImageElementFactory_GetIDsOfNames,
883     HTMLImageElementFactory_Invoke,
884     HTMLImageElementFactory_create
885 };
886
887 static const tid_t HTMLImageElementFactory_iface_tids[] = {
888     IHTMLImageElementFactory_tid,
889     0
890 };
891
892 static const dispex_static_data_vtbl_t HTMLImageElementFactory_dispex_vtbl = {
893     HTMLImageElementFactory_value,
894     NULL,
895     NULL
896 };
897
898 static dispex_static_data_t HTMLImageElementFactory_dispex = {
899     &HTMLImageElementFactory_dispex_vtbl,
900     IHTMLImageElementFactory_tid,
901     NULL,
902     HTMLImageElementFactory_iface_tids
903 };
904
905 HTMLImageElementFactory *HTMLImageElementFactory_Create(HTMLWindow *window)
906 {
907     HTMLImageElementFactory *ret;
908
909     ret = heap_alloc(sizeof(HTMLImageElementFactory));
910
911     ret->lpHTMLImageElementFactoryVtbl = &HTMLImageElementFactoryVtbl;
912     ret->ref = 1;
913     ret->window = window;
914
915     init_dispex(&ret->dispex, (IUnknown*)HTMLIMGFACTORY(ret), &HTMLImageElementFactory_dispex);
916
917     return ret;
918 }