【已解决】获取拖拽内容的脚本在 ahk u32 中乱码

遇到了问题?请先进行搜索(中文和英文),然后在此提问

Moderators: tmplinshi, arcticir

tmplinshi
Posts: 1604
Joined: 01 Oct 2013, 14:57

【已解决】获取拖拽内容的脚本在 ahk u32 中乱码

06 Sep 2014, 10:31

Code: Select all

; http://www.autohotkey.com/board/topic/82634-drag-url-info-from-chrome-address-bar-to-gui/?p=525764

#NoTrayIcon
#SingleInstance	Force

GuiOpen:
TempString := ""
Gui, +LastFound
Gui, Add, ListView, R20 W600, #|Format|Size|Data
Gui, Show, X10 Y10
hGui := WinExist()
VarSetCapacity(IDropSource,24,0), NumPut(&IDropSource+4,IDropSource), nParams=31132
Loop,	Parse,	nParams
	NumPut(RegisterCallback("IDropSource","",A_LoopField,A_Index-1),IDropSource,4*A_Index)
VarSetCapacity(IDropTarget,32,0), NumPut(&IDropTarget+4,IDropTarget), nParams=3116516
Loop,	Parse,	nParams
	NumPut(RegisterCallback("IDropTarget","",A_LoopField,A_Index-1),IDropTarget,4*A_Index)
DllCall("ole32\OleInitialize","Uint",0)
DllCall("ole32\RegisterDragDrop","Uint",hGui,"Uint",&IDropTarget)

Return
GuiClose:
;Clipboard := TempString
Gui, Destroy
DllCall("ole32\RevokeDragDrop","Uint",hGui)
DllCall("ole32\OleUninitialize")

ExitApp

#C::DllCall("ole32\OleGetClipboard","UintP",pdata)=0 ? (IEnumFormatEtc(pdata),DllCall(NumGet(NumGet(1*pdata)+8),"Uint",pdata)) : ""

IDropSource(this, escape=0, key=0)
{
	If	A_EventInfo = 3
		hResult := escape ? 0x00040101 : key&3 ? 0 : 0x00040100
	Else If	A_EventInfo = 4
		hResult := 0x00040102
	Else If	A_EventInfo = 0
		hResult := 0, NumPut(this,key+0)
	Else	hResult := 0
	Return	hResult
}

IDropTarget(this, pdata=0, key=0, x=0, y=0, peffect=0)
{
	If	A_EventInfo = 4
		NumPut(NumGet(y+0)&5,y+0)
	Else If	A_EventInfo = 3
		NumPut(NumGet(peffect+0)&5,peffect+0)
	Else If	A_EventInfo = 6
		NumPut(NumGet(peffect+0)&5,peffect+0), IEnumFormatEtc(pdata)
	Else If	A_EventInfo = 0
		NumPut(this,key+0)
	Return	0
}

IEnumFormatEtc(this)
{
	LV_Delete()
	DllCall(NumGet(NumGet(1*this)+32),"Uint",this,"Uint",1,"UintP",penum) ; DATADIR_GET=1, DATADIR_SET=2
	Loop
	{
		VarSetCapacity(FormatEtc,20,0)
		If  DllCall(NumGet(NumGet(1*penum)+12), "Uint", penum, "Uint",1, "Uint", &FormatEtc, "Uint",0)
		    Break
		0+(nFormat:=NumGet(FormatEtc,0,"Ushort"))<18 ? RegExMatch("CF_TEXT CF_BITMAP CF_METAFILEPICT CF_SYLK CF_DIF CF_TIFF CF_OEMTEXT CF_DIB CF_PALETTE CF_PENDATA CF_RIFF CF_WAVE CF_UNICODETEXT CF_ENHMETAFILE CF_HDROP CF_LOCALE CF_DIBV5", "(?:\w+\s+){" . nFormat-1 . "}(?<FORMAT>\w+\b)", CF_) : nFormat>=0x80&&nFormat<=0x83 ? RegExMatch("CF_OWNERDISPLAY CF_DSPTEXT CF_DSPBITMAP CF_DSPMETAFILEPICT", "(?:\w+\s+){" . nFormat-0x80 . "}(?<FORMAT>\w+\b)", CF_) : nFormat=0x8E ? CF_FORMAT:="CF_DSPENHMETAFILE" : CF_FORMAT:=GetClipboardFormatName(nFormat)
		VarSetCapacity(StgMedium,12,0)
		If  DllCall(NumGet(NumGet(1*this)+12), "Uint", this, "Uint", &FormatEtc, "Uint", &StgMedium)
		    Continue
		If	NumGet(StgMedium,0)=1	; TYMED_HGLOBAL=1
		{
			hData:=NumGet(StgMedium,4)
			pData:=DllCall("GlobalLock", "Uint", hData)
			nSize:=DllCall("GlobalSize", "Uint", hData)
			VarSetCapacity(sData,1023), DllCall("wsprintf", "str", sData, "str", DllCall("advapi32\IsTextUnicode", "Uint", pData, "Uint", nSize, "Uint", 0) ? "%S" : "%s", "Uint", pData, "Cdecl")
			DllCall("GlobalUnlock", "Uint", hData)
			LV_Add("", A_Index, CF_FORMAT, nSize, sData)
		
		}
		Else	RegExMatch("TYMED_NULL TYMED_FILE TYMED_ISTREAM TYMED_ISTORAGE TYMED_GDI TYMED_MFPICT TYMED_ENHMF", "(?:\w+\s+){" . Floor(ln(NumGet(StgMedium)+1)/ln(2)) . "}(?<STGMEDIUM>\w+\b)", TYMED_), LV_Add("", A_Index, CF_FORMAT, "?", TYMED_STGMEDIUM)
		


	
	
		DllCall("ole32\ReleaseStgMedium","Uint",&StgMedium)
	}
	DllCall(NumGet(NumGet(1*penum)+8), "Uint", penum)
	LV_ModifyCol()
		LVRows := LV_GetCount()
	Loop, % LVRows
	{
		LV_GetText(C1, A_Index, 1) 
		LV_GetText(C2, A_Index, 2) 
		LV_GetText(C3, A_Index, 3) 
		LV_GetText(C4, A_Index, 4) 
		TempString := TempString . C1 . " " . C2 . " " . C3 . " " . C4 . "`n"
	}
	Clipboard := TempString
	MsgBox % Clipboard 
}

GetClipboardFormatName(nFormat)
{
	VarSetCapacity(sFormat, 255)
	DllCall("GetClipboardFormatName", "Uint", nFormat, "str", sFormat, "Uint", 256)
	Return	sFormat
}
这个脚本是用来获取拖拽内容的。使用方法是,将文件或者浏览器中的文字拖拽到界面上。

ANSI 版本运行正常,但 Unicode 版本中显示乱码或者不完整。
哪位帮忙修改下啊,谢谢了。
Last edited by tmplinshi on 10 Sep 2014, 06:15, edited 1 time in total.
arcticir
Posts: 694
Joined: 17 Nov 2013, 11:32

Re: 获取拖拽内容的脚本在 ahk u32 中乱码

07 Sep 2014, 22:07

唉,感叹下AHK中文的人才流失与稀缺...
User avatar
amnesiac
Posts: 186
Joined: 22 Nov 2013, 03:08
Location: Egret Island, China
Contact:

Re: 获取拖拽内容的脚本在 ahk u32 中乱码

10 Sep 2014, 04:55

这个脚本能做到接受各种内容不简单。回到问题:
tmplinshi wrote:

Code: Select all

VarSetCapacity(sData,1023), DllCall("wsprintf", "str", sData, "str", DllCall("advapi32\IsTextUnicode", "Uint", pData, "Uint", nSize, "Uint", 0) ? "%S" : "%s", "Uint", pData, "Cdecl")
替换为:

Code: Select all

VarSetCapacity(sData,1023), DllCall("wsprintf", "str", sData, "str", (DllCall("advapi32\IsTextUnicode", "Uint", pData, "Uint", nSize, "Uint", 0) & A_IsUnicode) ? "%s" : "%S", "Uint", pData, "Cdecl")
目标为能运行于 AutoHotkey_L 中的 ANSI 和 Unicode 构建,期待反馈。

Return to “请求帮助”

Who is online

Users browsing this forum: No registered users and 17 guests