2 * Copyright 2011 Jacek Caban for CodeWeavers
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.
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.
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
19 #include "wshom_private.h"
25 #include <wine/unicode.h>
27 static IWshShell3 WshShell3
;
31 IWshCollection IWshCollection_iface
;
37 IWshShortcut IWshShortcut_iface
;
46 IWshEnvironment IWshEnvironment_iface
;
50 static inline WshCollection
*impl_from_IWshCollection( IWshCollection
*iface
)
52 return CONTAINING_RECORD(iface
, WshCollection
, IWshCollection_iface
);
55 static inline WshShortcut
*impl_from_IWshShortcut( IWshShortcut
*iface
)
57 return CONTAINING_RECORD(iface
, WshShortcut
, IWshShortcut_iface
);
60 static inline WshEnvironment
*impl_from_IWshEnvironment( IWshEnvironment
*iface
)
62 return CONTAINING_RECORD(iface
, WshEnvironment
, IWshEnvironment_iface
);
65 static HRESULT WINAPI
WshEnvironment_QueryInterface(IWshEnvironment
*iface
, REFIID riid
, void **obj
)
67 WshEnvironment
*This
= impl_from_IWshEnvironment(iface
);
69 TRACE("(%p)->(%s, %p)\n", This
, debugstr_guid(riid
), obj
);
71 if (IsEqualGUID(riid
, &IID_IUnknown
) ||
72 IsEqualGUID(riid
, &IID_IDispatch
) ||
73 IsEqualGUID(riid
, &IID_IWshEnvironment
))
77 FIXME("Unknown iface %s\n", debugstr_guid(riid
));
82 IUnknown_AddRef((IUnknown
*)*obj
);
86 static ULONG WINAPI
WshEnvironment_AddRef(IWshEnvironment
*iface
)
88 WshEnvironment
*This
= impl_from_IWshEnvironment(iface
);
89 LONG ref
= InterlockedIncrement(&This
->ref
);
90 TRACE("(%p) ref = %d\n", This
, ref
);
94 static ULONG WINAPI
WshEnvironment_Release(IWshEnvironment
*iface
)
96 WshEnvironment
*This
= impl_from_IWshEnvironment(iface
);
97 LONG ref
= InterlockedDecrement(&This
->ref
);
98 TRACE("(%p) ref = %d\n", This
, ref
);
101 HeapFree(GetProcessHeap(), 0, This
);
106 static HRESULT WINAPI
WshEnvironment_GetTypeInfoCount(IWshEnvironment
*iface
, UINT
*pctinfo
)
108 WshEnvironment
*This
= impl_from_IWshEnvironment(iface
);
109 TRACE("(%p)->(%p)\n", This
, pctinfo
);
114 static HRESULT WINAPI
WshEnvironment_GetTypeInfo(IWshEnvironment
*iface
, UINT iTInfo
, LCID lcid
, ITypeInfo
**ppTInfo
)
116 WshEnvironment
*This
= impl_from_IWshEnvironment(iface
);
117 TRACE("(%p)->(%u %u %p)\n", This
, iTInfo
, lcid
, ppTInfo
);
118 return get_typeinfo(IWshEnvironment_tid
, ppTInfo
);
121 static HRESULT WINAPI
WshEnvironment_GetIDsOfNames(IWshEnvironment
*iface
, REFIID riid
, LPOLESTR
*rgszNames
,
122 UINT cNames
, LCID lcid
, DISPID
*rgDispId
)
124 WshEnvironment
*This
= impl_from_IWshEnvironment(iface
);
128 TRACE("(%p)->(%s %p %u %u %p)\n", This
, debugstr_guid(riid
), rgszNames
, cNames
, lcid
, rgDispId
);
130 hr
= get_typeinfo(IWshEnvironment_tid
, &typeinfo
);
133 hr
= ITypeInfo_GetIDsOfNames(typeinfo
, rgszNames
, cNames
, rgDispId
);
134 ITypeInfo_Release(typeinfo
);
140 static HRESULT WINAPI
WshEnvironment_Invoke(IWshEnvironment
*iface
, DISPID dispIdMember
, REFIID riid
, LCID lcid
,
141 WORD wFlags
, DISPPARAMS
*pDispParams
, VARIANT
*pVarResult
, EXCEPINFO
*pExcepInfo
, UINT
*puArgErr
)
143 WshEnvironment
*This
= impl_from_IWshEnvironment(iface
);
147 TRACE("(%p)->(%d %s %d %d %p %p %p %p)\n", This
, dispIdMember
, debugstr_guid(riid
),
148 lcid
, wFlags
, pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
150 hr
= get_typeinfo(IWshEnvironment_tid
, &typeinfo
);
153 hr
= ITypeInfo_Invoke(typeinfo
, &This
->IWshEnvironment_iface
, dispIdMember
, wFlags
,
154 pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
155 ITypeInfo_Release(typeinfo
);
161 static HRESULT WINAPI
WshEnvironment_get_Item(IWshEnvironment
*iface
, BSTR name
, BSTR
*value
)
163 WshEnvironment
*This
= impl_from_IWshEnvironment(iface
);
166 TRACE("(%p)->(%s %p)\n", This
, debugstr_w(name
), value
);
171 len
= GetEnvironmentVariableW(name
, NULL
, 0);
172 *value
= SysAllocStringLen(NULL
, len
);
174 return E_OUTOFMEMORY
;
177 GetEnvironmentVariableW(name
, *value
, len
+1);
182 static HRESULT WINAPI
WshEnvironment_put_Item(IWshEnvironment
*iface
, BSTR name
, BSTR value
)
184 WshEnvironment
*This
= impl_from_IWshEnvironment(iface
);
185 FIXME("(%p)->(%s %s): stub\n", This
, debugstr_w(name
), debugstr_w(value
));
189 static HRESULT WINAPI
WshEnvironment_Count(IWshEnvironment
*iface
, LONG
*count
)
191 WshEnvironment
*This
= impl_from_IWshEnvironment(iface
);
192 FIXME("(%p)->(%p): stub\n", This
, count
);
196 static HRESULT WINAPI
WshEnvironment_get_length(IWshEnvironment
*iface
, LONG
*len
)
198 WshEnvironment
*This
= impl_from_IWshEnvironment(iface
);
199 FIXME("(%p)->(%p): stub\n", This
, len
);
203 static HRESULT WINAPI
WshEnvironment__NewEnum(IWshEnvironment
*iface
, IUnknown
**penum
)
205 WshEnvironment
*This
= impl_from_IWshEnvironment(iface
);
206 FIXME("(%p)->(%p): stub\n", This
, penum
);
210 static HRESULT WINAPI
WshEnvironment_Remove(IWshEnvironment
*iface
, BSTR name
)
212 WshEnvironment
*This
= impl_from_IWshEnvironment(iface
);
213 FIXME("(%p)->(%s): stub\n", This
, debugstr_w(name
));
217 static const IWshEnvironmentVtbl WshEnvironmentVtbl
= {
218 WshEnvironment_QueryInterface
,
219 WshEnvironment_AddRef
,
220 WshEnvironment_Release
,
221 WshEnvironment_GetTypeInfoCount
,
222 WshEnvironment_GetTypeInfo
,
223 WshEnvironment_GetIDsOfNames
,
224 WshEnvironment_Invoke
,
225 WshEnvironment_get_Item
,
226 WshEnvironment_put_Item
,
227 WshEnvironment_Count
,
228 WshEnvironment_get_length
,
229 WshEnvironment__NewEnum
,
230 WshEnvironment_Remove
233 static HRESULT
WshEnvironment_Create(IWshEnvironment
**env
)
235 WshEnvironment
*This
;
237 This
= HeapAlloc(GetProcessHeap(), 0, sizeof(*This
));
238 if (!This
) return E_OUTOFMEMORY
;
240 This
->IWshEnvironment_iface
.lpVtbl
= &WshEnvironmentVtbl
;
243 *env
= &This
->IWshEnvironment_iface
;
248 static HRESULT WINAPI
WshCollection_QueryInterface(IWshCollection
*iface
, REFIID riid
, void **ppv
)
250 WshCollection
*This
= impl_from_IWshCollection(iface
);
252 TRACE("(%p)->(%s, %p)\n", This
, debugstr_guid(riid
), ppv
);
254 if (IsEqualGUID(riid
, &IID_IUnknown
) ||
255 IsEqualGUID(riid
, &IID_IDispatch
) ||
256 IsEqualGUID(riid
, &IID_IWshCollection
))
260 FIXME("Unknown iface %s\n", debugstr_guid(riid
));
262 return E_NOINTERFACE
;
265 IUnknown_AddRef((IUnknown
*)*ppv
);
269 static ULONG WINAPI
WshCollection_AddRef(IWshCollection
*iface
)
271 WshCollection
*This
= impl_from_IWshCollection(iface
);
272 LONG ref
= InterlockedIncrement(&This
->ref
);
273 TRACE("(%p) ref = %d\n", This
, ref
);
277 static ULONG WINAPI
WshCollection_Release(IWshCollection
*iface
)
279 WshCollection
*This
= impl_from_IWshCollection(iface
);
280 LONG ref
= InterlockedDecrement(&This
->ref
);
281 TRACE("(%p) ref = %d\n", This
, ref
);
284 HeapFree(GetProcessHeap(), 0, This
);
289 static HRESULT WINAPI
WshCollection_GetTypeInfoCount(IWshCollection
*iface
, UINT
*pctinfo
)
291 WshCollection
*This
= impl_from_IWshCollection(iface
);
292 TRACE("(%p)->(%p)\n", This
, pctinfo
);
297 static HRESULT WINAPI
WshCollection_GetTypeInfo(IWshCollection
*iface
, UINT iTInfo
, LCID lcid
, ITypeInfo
**ppTInfo
)
299 WshCollection
*This
= impl_from_IWshCollection(iface
);
300 TRACE("(%p)->(%u %u %p)\n", This
, iTInfo
, lcid
, ppTInfo
);
301 return get_typeinfo(IWshCollection_tid
, ppTInfo
);
304 static HRESULT WINAPI
WshCollection_GetIDsOfNames(IWshCollection
*iface
, REFIID riid
, LPOLESTR
*rgszNames
,
305 UINT cNames
, LCID lcid
, DISPID
*rgDispId
)
307 WshCollection
*This
= impl_from_IWshCollection(iface
);
311 TRACE("(%p)->(%s %p %u %u %p)\n", This
, debugstr_guid(riid
), rgszNames
, cNames
, lcid
, rgDispId
);
313 hr
= get_typeinfo(IWshCollection_tid
, &typeinfo
);
316 hr
= ITypeInfo_GetIDsOfNames(typeinfo
, rgszNames
, cNames
, rgDispId
);
317 ITypeInfo_Release(typeinfo
);
323 static HRESULT WINAPI
WshCollection_Invoke(IWshCollection
*iface
, DISPID dispIdMember
, REFIID riid
, LCID lcid
,
324 WORD wFlags
, DISPPARAMS
*pDispParams
, VARIANT
*pVarResult
, EXCEPINFO
*pExcepInfo
, UINT
*puArgErr
)
326 WshCollection
*This
= impl_from_IWshCollection(iface
);
330 TRACE("(%p)->(%d %s %d %d %p %p %p %p)\n", This
, dispIdMember
, debugstr_guid(riid
),
331 lcid
, wFlags
, pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
333 hr
= get_typeinfo(IWshCollection_tid
, &typeinfo
);
336 hr
= ITypeInfo_Invoke(typeinfo
, &This
->IWshCollection_iface
, dispIdMember
, wFlags
,
337 pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
338 ITypeInfo_Release(typeinfo
);
344 static HRESULT WINAPI
WshCollection_Item(IWshCollection
*iface
, VARIANT
*index
, VARIANT
*value
)
346 WshCollection
*This
= impl_from_IWshCollection(iface
);
347 static const WCHAR allusersdesktopW
[] = {'A','l','l','U','s','e','r','s','D','e','s','k','t','o','p',0};
348 static const WCHAR allusersprogramsW
[] = {'A','l','l','U','s','e','r','s','P','r','o','g','r','a','m','s',0};
349 static const WCHAR desktopW
[] = {'D','e','s','k','t','o','p',0};
350 PIDLIST_ABSOLUTE pidl
;
351 WCHAR pathW
[MAX_PATH
];
356 TRACE("(%p)->(%s %p)\n", This
, debugstr_variant(index
), value
);
358 if (V_VT(index
) != VT_BSTR
)
360 FIXME("only BSTR index supported, got %d\n", V_VT(index
));
364 folder
= V_BSTR(index
);
365 if (!strcmpiW(folder
, desktopW
))
366 kind
= CSIDL_DESKTOP
;
367 else if (!strcmpiW(folder
, allusersdesktopW
))
368 kind
= CSIDL_COMMON_DESKTOPDIRECTORY
;
369 else if (!strcmpiW(folder
, allusersprogramsW
))
370 kind
= CSIDL_COMMON_PROGRAMS
;
373 FIXME("folder kind %s not supported\n", debugstr_w(folder
));
377 hr
= SHGetSpecialFolderLocation(NULL
, kind
, &pidl
);
378 if (hr
!= S_OK
) return hr
;
380 if (SHGetPathFromIDListW(pidl
, pathW
))
382 V_VT(value
) = VT_BSTR
;
383 V_BSTR(value
) = SysAllocString(pathW
);
384 hr
= V_BSTR(value
) ? S_OK
: E_OUTOFMEMORY
;
394 static HRESULT WINAPI
WshCollection_Count(IWshCollection
*iface
, LONG
*count
)
396 WshCollection
*This
= impl_from_IWshCollection(iface
);
397 FIXME("(%p)->(%p): stub\n", This
, count
);
401 static HRESULT WINAPI
WshCollection_get_length(IWshCollection
*iface
, LONG
*count
)
403 WshCollection
*This
= impl_from_IWshCollection(iface
);
404 FIXME("(%p)->(%p): stub\n", This
, count
);
408 static HRESULT WINAPI
WshCollection__NewEnum(IWshCollection
*iface
, IUnknown
*Enum
)
410 WshCollection
*This
= impl_from_IWshCollection(iface
);
411 FIXME("(%p)->(%p): stub\n", This
, Enum
);
415 static const IWshCollectionVtbl WshCollectionVtbl
= {
416 WshCollection_QueryInterface
,
417 WshCollection_AddRef
,
418 WshCollection_Release
,
419 WshCollection_GetTypeInfoCount
,
420 WshCollection_GetTypeInfo
,
421 WshCollection_GetIDsOfNames
,
422 WshCollection_Invoke
,
425 WshCollection_get_length
,
426 WshCollection__NewEnum
429 static HRESULT
WshCollection_Create(IWshCollection
**collection
)
433 This
= HeapAlloc(GetProcessHeap(), 0, sizeof(*This
));
434 if (!This
) return E_OUTOFMEMORY
;
436 This
->IWshCollection_iface
.lpVtbl
= &WshCollectionVtbl
;
439 *collection
= &This
->IWshCollection_iface
;
445 static HRESULT WINAPI
WshShortcut_QueryInterface(IWshShortcut
*iface
, REFIID riid
, void **ppv
)
447 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
449 TRACE("(%p)->(%s, %p)\n", This
, debugstr_guid(riid
), ppv
);
451 if (IsEqualGUID(riid
, &IID_IUnknown
) ||
452 IsEqualGUID(riid
, &IID_IDispatch
) ||
453 IsEqualGUID(riid
, &IID_IWshShortcut
))
457 FIXME("Unknown iface %s\n", debugstr_guid(riid
));
459 return E_NOINTERFACE
;
462 IUnknown_AddRef((IUnknown
*)*ppv
);
466 static ULONG WINAPI
WshShortcut_AddRef(IWshShortcut
*iface
)
468 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
469 LONG ref
= InterlockedIncrement(&This
->ref
);
470 TRACE("(%p) ref = %d\n", This
, ref
);
474 static ULONG WINAPI
WshShortcut_Release(IWshShortcut
*iface
)
476 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
477 LONG ref
= InterlockedDecrement(&This
->ref
);
478 TRACE("(%p) ref = %d\n", This
, ref
);
482 SysFreeString(This
->path_link
);
483 IShellLinkW_Release(This
->link
);
484 HeapFree(GetProcessHeap(), 0, This
);
490 static HRESULT WINAPI
WshShortcut_GetTypeInfoCount(IWshShortcut
*iface
, UINT
*pctinfo
)
492 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
493 TRACE("(%p)->(%p)\n", This
, pctinfo
);
498 static HRESULT WINAPI
WshShortcut_GetTypeInfo(IWshShortcut
*iface
, UINT iTInfo
, LCID lcid
, ITypeInfo
**ppTInfo
)
500 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
501 TRACE("(%p)->(%u %u %p)\n", This
, iTInfo
, lcid
, ppTInfo
);
502 return get_typeinfo(IWshShortcut_tid
, ppTInfo
);
505 static HRESULT WINAPI
WshShortcut_GetIDsOfNames(IWshShortcut
*iface
, REFIID riid
, LPOLESTR
*rgszNames
,
506 UINT cNames
, LCID lcid
, DISPID
*rgDispId
)
508 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
512 TRACE("(%p)->(%s %p %u %u %p)\n", This
, debugstr_guid(riid
), rgszNames
, cNames
, lcid
, rgDispId
);
514 hr
= get_typeinfo(IWshShortcut_tid
, &typeinfo
);
517 hr
= ITypeInfo_GetIDsOfNames(typeinfo
, rgszNames
, cNames
, rgDispId
);
518 ITypeInfo_Release(typeinfo
);
524 static HRESULT WINAPI
WshShortcut_Invoke(IWshShortcut
*iface
, DISPID dispIdMember
, REFIID riid
, LCID lcid
,
525 WORD wFlags
, DISPPARAMS
*pDispParams
, VARIANT
*pVarResult
, EXCEPINFO
*pExcepInfo
, UINT
*puArgErr
)
527 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
531 TRACE("(%p)->(%d %s %d %d %p %p %p %p)\n", This
, dispIdMember
, debugstr_guid(riid
),
532 lcid
, wFlags
, pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
534 hr
= get_typeinfo(IWshShortcut_tid
, &typeinfo
);
537 hr
= ITypeInfo_Invoke(typeinfo
, &This
->IWshShortcut_iface
, dispIdMember
, wFlags
,
538 pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
539 ITypeInfo_Release(typeinfo
);
545 static HRESULT WINAPI
WshShortcut_get_FullName(IWshShortcut
*iface
, BSTR
*name
)
547 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
548 FIXME("(%p)->(%p): stub\n", This
, name
);
552 static HRESULT WINAPI
WshShortcut_get_Arguments(IWshShortcut
*iface
, BSTR
*Arguments
)
554 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
555 WCHAR buffW
[INFOTIPSIZE
];
558 TRACE("(%p)->(%p)\n", This
, Arguments
);
565 hr
= IShellLinkW_GetArguments(This
->link
, buffW
, sizeof(buffW
)/sizeof(WCHAR
));
569 *Arguments
= SysAllocString(buffW
);
570 return *Arguments
? S_OK
: E_OUTOFMEMORY
;
573 static HRESULT WINAPI
WshShortcut_put_Arguments(IWshShortcut
*iface
, BSTR Arguments
)
575 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
577 TRACE("(%p)->(%s)\n", This
, debugstr_w(Arguments
));
579 return IShellLinkW_SetArguments(This
->link
, Arguments
);
582 static HRESULT WINAPI
WshShortcut_get_Description(IWshShortcut
*iface
, BSTR
*Description
)
584 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
585 FIXME("(%p)->(%p): stub\n", This
, Description
);
589 static HRESULT WINAPI
WshShortcut_put_Description(IWshShortcut
*iface
, BSTR Description
)
591 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
592 TRACE("(%p)->(%s)\n", This
, debugstr_w(Description
));
593 return IShellLinkW_SetDescription(This
->link
, Description
);
596 static HRESULT WINAPI
WshShortcut_get_Hotkey(IWshShortcut
*iface
, BSTR
*Hotkey
)
598 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
599 FIXME("(%p)->(%p): stub\n", This
, Hotkey
);
603 static HRESULT WINAPI
WshShortcut_put_Hotkey(IWshShortcut
*iface
, BSTR Hotkey
)
605 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
606 FIXME("(%p)->(%s): stub\n", This
, debugstr_w(Hotkey
));
610 static HRESULT WINAPI
WshShortcut_get_IconLocation(IWshShortcut
*iface
, BSTR
*IconPath
)
612 static const WCHAR fmtW
[] = {'%','s',',',' ','%','d',0};
613 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
614 WCHAR buffW
[MAX_PATH
], pathW
[MAX_PATH
];
618 TRACE("(%p)->(%p)\n", This
, IconPath
);
623 hr
= IShellLinkW_GetIconLocation(This
->link
, buffW
, sizeof(buffW
)/sizeof(WCHAR
), &icon
);
624 if (FAILED(hr
)) return hr
;
626 sprintfW(pathW
, fmtW
, buffW
, icon
);
627 *IconPath
= SysAllocString(pathW
);
628 if (!*IconPath
) return E_OUTOFMEMORY
;
633 static HRESULT WINAPI
WshShortcut_put_IconLocation(IWshShortcut
*iface
, BSTR IconPath
)
635 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
641 TRACE("(%p)->(%s)\n", This
, debugstr_w(IconPath
));
643 /* scan for icon id */
644 ptr
= strrchrW(IconPath
, ',');
647 WARN("icon index not found\n");
651 path
= SysAllocStringLen(IconPath
, ptr
-IconPath
);
653 /* skip spaces if any */
654 while (isspaceW(*++ptr
))
659 hr
= IShellLinkW_SetIconLocation(This
->link
, path
, icon
);
665 static HRESULT WINAPI
WshShortcut_put_RelativePath(IWshShortcut
*iface
, BSTR rhs
)
667 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
668 FIXME("(%p)->(%s): stub\n", This
, debugstr_w(rhs
));
672 static HRESULT WINAPI
WshShortcut_get_TargetPath(IWshShortcut
*iface
, BSTR
*Path
)
674 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
675 FIXME("(%p)->(%p): stub\n", This
, Path
);
679 static HRESULT WINAPI
WshShortcut_put_TargetPath(IWshShortcut
*iface
, BSTR Path
)
681 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
682 TRACE("(%p)->(%s)\n", This
, debugstr_w(Path
));
683 return IShellLinkW_SetPath(This
->link
, Path
);
686 static HRESULT WINAPI
WshShortcut_get_WindowStyle(IWshShortcut
*iface
, int *ShowCmd
)
688 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
689 TRACE("(%p)->(%p)\n", This
, ShowCmd
);
690 return IShellLinkW_GetShowCmd(This
->link
, ShowCmd
);
693 static HRESULT WINAPI
WshShortcut_put_WindowStyle(IWshShortcut
*iface
, int ShowCmd
)
695 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
696 TRACE("(%p)->(%d)\n", This
, ShowCmd
);
697 return IShellLinkW_SetShowCmd(This
->link
, ShowCmd
);
700 static HRESULT WINAPI
WshShortcut_get_WorkingDirectory(IWshShortcut
*iface
, BSTR
*WorkingDirectory
)
702 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
703 WCHAR buffW
[MAX_PATH
];
706 TRACE("(%p)->(%p)\n", This
, WorkingDirectory
);
708 if (!WorkingDirectory
)
711 *WorkingDirectory
= NULL
;
712 hr
= IShellLinkW_GetWorkingDirectory(This
->link
, buffW
, sizeof(buffW
)/sizeof(WCHAR
));
713 if (FAILED(hr
)) return hr
;
715 *WorkingDirectory
= SysAllocString(buffW
);
716 return *WorkingDirectory
? S_OK
: E_OUTOFMEMORY
;
719 static HRESULT WINAPI
WshShortcut_put_WorkingDirectory(IWshShortcut
*iface
, BSTR WorkingDirectory
)
721 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
722 TRACE("(%p)->(%s)\n", This
, debugstr_w(WorkingDirectory
));
723 return IShellLinkW_SetWorkingDirectory(This
->link
, WorkingDirectory
);
726 static HRESULT WINAPI
WshShortcut_Load(IWshShortcut
*iface
, BSTR PathLink
)
728 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
729 FIXME("(%p)->(%s): stub\n", This
, debugstr_w(PathLink
));
733 static HRESULT WINAPI
WshShortcut_Save(IWshShortcut
*iface
)
735 WshShortcut
*This
= impl_from_IWshShortcut(iface
);
739 TRACE("(%p)\n", This
);
741 IShellLinkW_QueryInterface(This
->link
, &IID_IPersistFile
, (void**)&file
);
742 hr
= IPersistFile_Save(file
, This
->path_link
, TRUE
);
743 IPersistFile_Release(file
);
748 static const IWshShortcutVtbl WshShortcutVtbl
= {
749 WshShortcut_QueryInterface
,
752 WshShortcut_GetTypeInfoCount
,
753 WshShortcut_GetTypeInfo
,
754 WshShortcut_GetIDsOfNames
,
756 WshShortcut_get_FullName
,
757 WshShortcut_get_Arguments
,
758 WshShortcut_put_Arguments
,
759 WshShortcut_get_Description
,
760 WshShortcut_put_Description
,
761 WshShortcut_get_Hotkey
,
762 WshShortcut_put_Hotkey
,
763 WshShortcut_get_IconLocation
,
764 WshShortcut_put_IconLocation
,
765 WshShortcut_put_RelativePath
,
766 WshShortcut_get_TargetPath
,
767 WshShortcut_put_TargetPath
,
768 WshShortcut_get_WindowStyle
,
769 WshShortcut_put_WindowStyle
,
770 WshShortcut_get_WorkingDirectory
,
771 WshShortcut_put_WorkingDirectory
,
776 static HRESULT
WshShortcut_Create(const WCHAR
*path
, IDispatch
**shortcut
)
783 This
= HeapAlloc(GetProcessHeap(), 0, sizeof(*This
));
784 if (!This
) return E_OUTOFMEMORY
;
786 This
->IWshShortcut_iface
.lpVtbl
= &WshShortcutVtbl
;
789 hr
= CoCreateInstance(&CLSID_ShellLink
, NULL
, CLSCTX_INPROC_SERVER
,
790 &IID_IShellLinkW
, (void**)&This
->link
);
793 HeapFree(GetProcessHeap(), 0, This
);
797 This
->path_link
= SysAllocString(path
);
798 if (!This
->path_link
)
800 IShellLinkW_Release(This
->link
);
801 HeapFree(GetProcessHeap(), 0, This
);
802 return E_OUTOFMEMORY
;
805 *shortcut
= (IDispatch
*)&This
->IWshShortcut_iface
;
810 static HRESULT WINAPI
WshShell3_QueryInterface(IWshShell3
*iface
, REFIID riid
, void **ppv
)
812 TRACE("(%s, %p)\n", debugstr_guid(riid
), ppv
);
816 if(IsEqualGUID(riid
, &IID_IUnknown
) ||
817 IsEqualGUID(riid
, &IID_IDispatch
) ||
818 IsEqualGUID(riid
, &IID_IWshShell3
))
822 else if (IsEqualGUID(riid
, &IID_IDispatchEx
))
824 return E_NOINTERFACE
;
828 FIXME("Unknown iface %s\n", debugstr_guid(riid
));
829 return E_NOINTERFACE
;
832 IWshShell3_AddRef(iface
);
836 static ULONG WINAPI
WshShell3_AddRef(IWshShell3
*iface
)
842 static ULONG WINAPI
WshShell3_Release(IWshShell3
*iface
)
848 static HRESULT WINAPI
WshShell3_GetTypeInfoCount(IWshShell3
*iface
, UINT
*pctinfo
)
850 TRACE("(%p)\n", pctinfo
);
855 static HRESULT WINAPI
WshShell3_GetTypeInfo(IWshShell3
*iface
, UINT iTInfo
, LCID lcid
, ITypeInfo
**ppTInfo
)
857 TRACE("(%u %u %p)\n", iTInfo
, lcid
, ppTInfo
);
858 return get_typeinfo(IWshShell3_tid
, ppTInfo
);
861 static HRESULT WINAPI
WshShell3_GetIDsOfNames(IWshShell3
*iface
, REFIID riid
, LPOLESTR
*rgszNames
,
862 UINT cNames
, LCID lcid
, DISPID
*rgDispId
)
867 TRACE("(%s %p %u %u %p)\n", debugstr_guid(riid
), rgszNames
, cNames
, lcid
, rgDispId
);
869 hr
= get_typeinfo(IWshShell3_tid
, &typeinfo
);
872 hr
= ITypeInfo_GetIDsOfNames(typeinfo
, rgszNames
, cNames
, rgDispId
);
873 ITypeInfo_Release(typeinfo
);
879 static HRESULT WINAPI
WshShell3_Invoke(IWshShell3
*iface
, DISPID dispIdMember
, REFIID riid
, LCID lcid
,
880 WORD wFlags
, DISPPARAMS
*pDispParams
, VARIANT
*pVarResult
, EXCEPINFO
*pExcepInfo
, UINT
*puArgErr
)
885 TRACE("(%d %s %d %d %p %p %p %p)\n", dispIdMember
, debugstr_guid(riid
),
886 lcid
, wFlags
, pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
888 hr
= get_typeinfo(IWshShell3_tid
, &typeinfo
);
891 hr
= ITypeInfo_Invoke(typeinfo
, &WshShell3
, dispIdMember
, wFlags
,
892 pDispParams
, pVarResult
, pExcepInfo
, puArgErr
);
893 ITypeInfo_Release(typeinfo
);
899 static HRESULT WINAPI
WshShell3_get_SpecialFolders(IWshShell3
*iface
, IWshCollection
**folders
)
901 TRACE("(%p)\n", folders
);
902 return WshCollection_Create(folders
);
905 static HRESULT WINAPI
WshShell3_get_Environment(IWshShell3
*iface
, VARIANT
*type
, IWshEnvironment
**env
)
907 FIXME("(%s %p): semi-stub\n", debugstr_variant(type
), env
);
908 return WshEnvironment_Create(env
);
911 static HRESULT WINAPI
WshShell3_Run(IWshShell3
*iface
, BSTR cmd
, VARIANT
*style
, VARIANT
*WaitOnReturn
, int *exit_code
)
913 SHELLEXECUTEINFOW info
;
918 TRACE("(%s %s %s %p)\n", debugstr_w(cmd
), debugstr_variant(style
), debugstr_variant(WaitOnReturn
), exit_code
);
921 hr
= VariantChangeType(&s
, style
, 0, VT_I4
);
924 ERR("failed to convert style argument, 0x%08x\n", hr
);
929 hr
= VariantChangeType(&w
, WaitOnReturn
, 0, VT_I4
);
932 ERR("failed to convert wait argument, 0x%08x\n", hr
);
936 memset(&info
, 0, sizeof(info
));
937 info
.cbSize
= sizeof(info
);
939 waitforprocess
= V_I4(&w
);
941 info
.fMask
= waitforprocess
? SEE_MASK_NOASYNC
| SEE_MASK_NOCLOSEPROCESS
: SEE_MASK_DEFAULT
;
943 info
.nShow
= V_I4(&s
);
945 if (!ShellExecuteExW(&info
))
947 TRACE("ShellExecute failed, %d\n", GetLastError());
948 return HRESULT_FROM_WIN32(GetLastError());
957 GetExitCodeProcess(info
.hProcess
, &code
);
960 CloseHandle(info
.hProcess
);
963 if (exit_code
) *exit_code
= 0;
969 static HRESULT WINAPI
WshShell3_Popup(IWshShell3
*iface
, BSTR Text
, VARIANT
* SecondsToWait
, VARIANT
*Title
, VARIANT
*Type
, int *button
)
971 FIXME("(%s %s %s %s %p): stub\n", debugstr_w(Text
), debugstr_variant(SecondsToWait
),
972 debugstr_variant(Title
), debugstr_variant(Type
), button
);
976 static HRESULT WINAPI
WshShell3_CreateShortcut(IWshShell3
*iface
, BSTR PathLink
, IDispatch
** Shortcut
)
978 TRACE("(%s %p)\n", debugstr_w(PathLink
), Shortcut
);
979 return WshShortcut_Create(PathLink
, Shortcut
);
982 static HRESULT WINAPI
WshShell3_ExpandEnvironmentStrings(IWshShell3
*iface
, BSTR Src
, BSTR
* Dst
)
986 TRACE("(%s %p)\n", debugstr_w(Src
), Dst
);
988 if (!Src
|| !Dst
) return E_POINTER
;
990 ret
= ExpandEnvironmentStringsW(Src
, NULL
, 0);
991 *Dst
= SysAllocStringLen(NULL
, ret
);
992 if (!*Dst
) return E_OUTOFMEMORY
;
994 if (ExpandEnvironmentStringsW(Src
, *Dst
, ret
))
1000 return HRESULT_FROM_WIN32(GetLastError());
1004 static HRESULT WINAPI
WshShell3_RegRead(IWshShell3
*iface
, BSTR Name
, VARIANT
* out_Value
)
1006 FIXME("(%s %p): stub\n", debugstr_w(Name
), out_Value
);
1010 static HRESULT WINAPI
WshShell3_RegWrite(IWshShell3
*iface
, BSTR Name
, VARIANT
*Value
, VARIANT
*Type
)
1012 FIXME("(%s %s %s): stub\n", debugstr_w(Name
), debugstr_variant(Value
), debugstr_variant(Type
));
1016 static HRESULT WINAPI
WshShell3_RegDelete(IWshShell3
*iface
, BSTR Name
)
1018 FIXME("(%s): stub\n", debugstr_w(Name
));
1022 static HRESULT WINAPI
WshShell3_LogEvent(IWshShell3
*iface
, VARIANT
*Type
, BSTR Message
, BSTR Target
, VARIANT_BOOL
*out_Success
)
1024 FIXME("(%s %s %s %p): stub\n", debugstr_variant(Type
), debugstr_w(Message
), debugstr_w(Target
), out_Success
);
1028 static HRESULT WINAPI
WshShell3_AppActivate(IWshShell3
*iface
, VARIANT
*App
, VARIANT
*Wait
, VARIANT_BOOL
*out_Success
)
1030 FIXME("(%s %s %p): stub\n", debugstr_variant(App
), debugstr_variant(Wait
), out_Success
);
1034 static HRESULT WINAPI
WshShell3_SendKeys(IWshShell3
*iface
, BSTR Keys
, VARIANT
*Wait
)
1036 FIXME("(%s %p): stub\n", debugstr_w(Keys
), Wait
);
1040 static const IWshShell3Vtbl WshShell3Vtbl
= {
1041 WshShell3_QueryInterface
,
1044 WshShell3_GetTypeInfoCount
,
1045 WshShell3_GetTypeInfo
,
1046 WshShell3_GetIDsOfNames
,
1048 WshShell3_get_SpecialFolders
,
1049 WshShell3_get_Environment
,
1052 WshShell3_CreateShortcut
,
1053 WshShell3_ExpandEnvironmentStrings
,
1056 WshShell3_RegDelete
,
1058 WshShell3_AppActivate
,
1062 static IWshShell3 WshShell3
= { &WshShell3Vtbl
};
1064 HRESULT WINAPI
WshShellFactory_CreateInstance(IClassFactory
*iface
, IUnknown
*outer
, REFIID riid
, void **ppv
)
1066 TRACE("(%p %s %p)\n", outer
, debugstr_guid(riid
), ppv
);
1068 return IWshShell3_QueryInterface(&WshShell3
, riid
, ppv
);