functionscraping_dllcallcode_getcomputername:
Store:=ClipboardAll  ;****Store clipboard ****
	Clipboard=
(  Join`r`n
; ===============================================================================================================================
; Function......: GetComputerName
; DLL...........: Kernel32.dll
; Library.......: Kernel32.lib
; U/ANSI........: GetComputerNameW (Unicode) and GetComputerNameA (ANSI)
; Author........: jNizM
; Modified......:
; Links.........: https://msdn.microsoft.com/en-us/library/ms724295.aspx
;                 https://msdn.microsoft.com/en-us/library/windows/desktop/ms724295.aspx
; ===============================================================================================================================
GetComputerName()
{
    static size := 31 + 1 * (A_IsUnicode ? 2 : 1), init := VarSetCapacity(buf, size, 0)
    if !(DllCall("kernel32.dll\GetComputerName", "Ptr", &buf, "UInt*", size))
        return DllCall("kernel32.dll\GetLastError")
    return StrGet(&buf, size, "UTF-16")
}
; ===============================================================================================================================

MsgBox `% GetComputerName()





/* C++ ==========================================================================================================================
BOOL WINAPI GetComputerName(                                                         // UInt
    _Out_    LPTSTR lpBuffer,                                                        // Ptr
    _Inout_  LPDWORD lpnSize                                                         // UInt*
`);
============================================================================================================================== */
)
	gosub Paste_and_Restore_Stored_Clipboard
return

functionscraping_PostMessagecode_启动屏幕保护程序:
Store:=ClipboardAll  ;****Store clipboard ****
	Clipboard=
(  Join`r`n
SendMessage, 0x112, 0xF140, 0,, Program Manager  ; 0x112 是 WM_SYSCOMMAND, 而 0xF140 是 SC_SCREENSAVE.
)
	gosub Paste_and_Restore_Stored_Clipboard
return

functionscraping_computecode_绝对值:
Store:=ClipboardAll  ;****Store clipboard ****
	Clipboard=
(  Join`r`n
MsgBox, `% Abs(-1.2) ; 返回 1.2
)
	gosub Paste_and_Restore_Stored_Clipboard
return

functionscraping_filecode_追加文本:
Store:=ClipboardAll  ;****Store clipboard ****
	Clipboard=
(  Join`r`n
FileAppend,
(
A line of text.
By default, the hard carriage return (Enter) between the previous line and this one will be written to the file.
    This line is indented with a tab; by default, that tab will also be written to the file.
Variable references such as `%Var`% are expanded by default.
`), C:\My File.txt
)
	gosub Paste_and_Restore_Stored_Clipboard
return
functionscraping_stringcode_字符串切割:
Store:=ClipboardAll  ;****Store clipboard ****
	Clipboard=
(  Join`r`n
MsgBox `% SubStr("123abc789", 4, 3) ; 返回 abc
)
	gosub Paste_and_Restore_Stored_Clipboard
return

functionscraping_graphicscode_findtext:
	Run,%A_ScriptDir%\auto\findtext().ahk
return

functionscraping_wincode_WinExist/WinClose:
Store:=ClipboardAll  ;****Store clipboard ****
	Clipboard=
(  Join`r`n
;一键关闭同类窗口
^!f4::
    wingetclass,sclass,A
    While winexist("ahk_class " . sclass)
    {
        WinClose
    }
return

)
	gosub Paste_and_Restore_Stored_Clipboard
return


functionscraping_comcode_speak:
Store:=ClipboardAll  ;****Store clipboard ****
	Clipboard=
(  Join`r`n
!F12::
  date = `%A_YYYY`%年`%A_MM`%月`%A_DD`%日
  Speak("今天日期是 " . date)
  time = `%A_Hour`%點 `%A_Min`%分 `%A_Sec`%秒
  Speak("現在時間是 " . time)
  return

Speak(say) {
  spovice:=ComObjCreate("sapi.spvoice")
  spovice.Speak(say)
}

)
	gosub Paste_and_Restore_Stored_Clipboard
Return


functionscraping_stringcode_instr:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
Haystack := "The Quick Brown Fox Jumps Over the Lazy Dog"
Needle := "the"
MsgBox `% InStr(Haystack, Needle, false, 1, 2) ; 不区分大小写的搜索, 返回第二次匹配的位置
MsgBox `% InStr(Haystack, Needle, true) ; 区分大小写的搜索, 返回首次匹配的位置, 结果同上
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_stringcode_RegExMatch:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox `% RegExMatch("xxxabc123xyz", "abc.*xyz")  ; 显示 4, 这是找到匹配的位置.
MsgBox `% RegExMatch("abc123123", "123$")  ; 显示 7, 因为 $ 要求在末端进行匹配.
MsgBox `% RegExMatch("abc123", "i)^ABC")  ; 显示 1, 因为通过不区分大小写选项实现了匹配.
MsgBox `% RegExMatch("abcXYZ123", "abc(.*)123", SubPat)  ; 显示 1, 并把 "XYZ" 保存到 SubPat1.
MsgBox `% RegExMatch("abc123abc456", "abc\d+", "", 2)  ; 显示 7 而不是 1, 这是由于 StartingPosition 为 2 而不是 1.
FoundPos := RegExMatch("Michiganroad 72", "O)(.*) (?<nr>\d+)", SubPat)  ; 开始的 "O)" 将 SubPat 变成一个对象.
Msgbox `% SubPat.Count() ": " SubPat.Value(1) " " SubPat.Name(2) "=" SubPat["nr"]  ; 显示 "2: Michiganroad nr=72"

)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_stringcode_RegExReplace:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox `% RegExReplace("abc123123", "123$", "xyz")  ; 显示 "abc123xyz" , 因为 $ 导致只能在末尾形成匹配.
MsgBox `% RegExReplace("abc123", "i)^ABC")  ; 显示 "123" 因为通过不区分大小写选项实现了匹配.
MsgBox `% RegExReplace("abcXYZ123", "abc(.*)123", "aaa$1zzz")  ; 显示 "aaaXYZzzz" 其中使用了 $1 后向引用.
MsgBox `% RegExReplace("abc123abc456", "abc\d+", "", ReplacementCount)  ; 显示 "" 并保存 2 到 ReplacementCount.
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_stringcode_StrLen:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
InputVar := "The Quick Brown Fox Jumps Over the Lazy Dog"
MsgBox `% "The length of InputVar is " . StrLen(InputVar) ; 结果为: 43
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_stringcode_StrReplace:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
; 移除剪贴板中所有的 CR+LF:
Clipboard := StrReplace(Clipboard, "`r`n")

; 用加号替换所有空格:
NewStr := StrReplace(OldStr, A_Space, "+")

; 移除变量中所有空行:
Loop
{
    MyString := StrReplace(MyString, "`r`n`r`n", "`r`n", Count)
    if (Count = 0)  ; 不再需要更多的替代.
        break
}
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_stringcode_StrSplit:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
TestString := "This is a test."
word_array := StrSplit(TestString, A_Space, ".")  ; 忽略句点. 
MsgBox `% "The 4th word is " word_array[4]

Colors := "red,green,blue"
ColorArray := StrSplit(Colors, ",")
Loop `% ColorArray.MaxIndex()
{
    this_color := ColorArray[a_index]
    MsgBox, Color number `%a_index`% is `%this_color`%.
}
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_stringcode_trim:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
text := "  text  "
MsgBox `% "No trim:`t '" text "'"
    . "``nTrim:``t '" Trim(text) "'"
    . "``nLTrim:``t '" LTrim(text) "'"
    . "``nRTrim:``t '" RTrim(text) "'"
MsgBox `% LTrim("00000123","0")
)
    gosub Paste_and_Restore_Stored_Clipboard
Return

functionscraping_funcionothercode_chr:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Chr(116) ; 显示 "t".
MsgBox, `% Chr(19968) ; 显示 "一"(Unicode), 显示空白(Ansi).
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_filecode_FileExist:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
if FileExist("D:\")
    MsgBox, 驱动器存在.
if FileExist("D:\Docs\*.txt")
    MsgBox, 至少有一个 .txt 文件存在.
if !FileExist("C:\Temp\FlagFile.txt")
    MsgBox, 目标文件不存在.
if InStr(FileExist("C:\My File.txt"), "H")
    MsgBox 文件是隐藏的.
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_F-GetKeyState:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
state := GetKeyState("RButton")  ; 鼠标右键.
state := GetKeyState("Joy2")  ; 你操纵杆的第二个按钮.

if GetKeyState("Shift")
    MsgBox At least one Shift key is down.
else
    MsgBox Neither Shift key is down.

state := GetKeyState("CapsLock", "T") ; True if CapsLock is ON, false otherwise.
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_wincode_WinActive:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
if WinActive("ahk_class Notepad") or WinActive("ahk_class" . ClassName)  ; "ahk_class" 后不需要空格.
    WinClose  ; 这里使用上次找到的窗口.
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_wincode_WinExist:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
if WinExist("ahk_class Notepad") or WinExist("ahk_class" . ClassName)
    WinActivate  ; 使用上次找到的窗口.

MsgBox `% "The active window's ID is " . WinExist("A")
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_Ceil:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Ceil(1.2)  ; 返回 2
MsgBox, `% Ceil(-1.2) ; 返回 -1
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_e的n次幂Exp:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Exp(1.2) ; 返回 3.320117
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_向下取整后的整数-floor:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Floor(1.2)  ; 返回 1
MsgBox, `% Floor(-1.2) ; 返回 -2
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_对数10为底:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Log(1.2) ; 返回 0.079181
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_底数为e的自然对数:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Ln(1.2) ; 返回 0.182322
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_最大值:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Max(2.11, -2, 0) ; 返回 2.11
array := [1, 2, 3, 4]
MsgBox, `% Max(array*) ; 返回 4
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_最小值:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Min(2.11, -2, 0) ; 返回 -2
array := [1, 2, 3, 4]
MsgBox, `% Min(array*) ; 返回 1
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_余数:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Mod(7.5, 2) ; 返回 1.5(2 x 3 + 1.5)
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_四舍五入:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Round(3.14, 1) ; 返回 3.1
MsgBox, `% Round(3.14)    ; 返回 3
MsgBox, `% Round(345, -1) ; 返回 350, 这里的 -1 表示 5, 所以向上取整.
MsgBox, `% Round(345, -2) ; 返回 300, 因为 -2 表示 4, 所以向下取整.
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_平方根:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Sqrt(16) ; 返回 4
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_正弦:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Sin(1.2) ; 返回 0.932039
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_余弦:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Cos(1.2) ; 返回 0.362358
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_正切:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Tan(1.2) ; 返回 2.572152
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_反正弦:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% ASin(0.2) ; 返回 0.201358
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_反余弦:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% ACos(0.2) ; 返回 1.369438
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_computecode_反正切:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% ATan(1.2) ; 返回 0.876058
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_抛出异常Exception:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
try
    SomeFunction()
catch e
    MsgBox `% "Error in " e.What ", which was called at line " e.Line 

SomeFunction() {
    throw Exception("Fail", -1)
}
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_filecode_打开文件（fileopen）:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
FileSelectFile, FileName, S16,, Create a new file:
if (FileName = "")
	return
file := FileOpen(FileName, "w")
if !IsObject(file)
{
	MsgBox Can't open "`%FileName`%" for writing.
	return
}
TestString := "This is a test string.``r``n"  ; 通过这种方式写入内容到文件时, 要使用 ``r``n 而不是 `n 来开始新行.
file.Write(TestString)
file.Close()

; 现在已经把内容写入文件了, 重新把它们读取回内存中.
file := FileOpen(FileName, "r-d") ; 读取文件 ("r"), 共享除删除 ("-d") 外的所有访问权限
if !IsObject(file)
{
	MsgBox Can't open "`%FileName`%" for reading.
	return
}
CharsToRead := StrLen(TestString)
TestString := file.Read(CharsToRead)
file.Close()
MsgBox The following string was read from the file: `%TestString`%
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_格式化Format:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
; 简单替换
s .= Format("{2}, {1}!``r``n", "World", "Hello")
; 填充空格
s .= Format("|{:-10}|``r``n|{:10}|``r``n", "Left", "Right")
; 十六进制
s .= Format("{1:#x} {2:X} 0x{3:x}``r``n", 3735928559, 195948557, 0)
; 浮点数
s .= Format("{1:0.3f} {1:.10f}", 4*ATan(1))

ListVars  ; 用 AutoHotkey 的主窗口显示等宽文本.
WinWaitActive ahk_class AutoHotkey
ControlSetText Edit1, `%s`%
WinWaitClose
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_函数引用Func:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
; 获取函数名为 "StrLen" 的函数引用.
fn := Func("StrLen")

; 显示函数的相关信息.
MsgBox `% fn.Name "() 是 " (fn.IsBuiltIn ? "内置函数." : "用户定义的函数.")
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_GetKeyName\GetKeyVK\GetKeySC:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
key  := "LWin" ; 任何一个按键都可以.

name := GetKeyName(key)
vk   := GetKeyVK(key)
sc   := GetKeySC(key)

MsgBox, `% Format("按键名称:`t{}`n虚拟键码:`t{:X}`n扫描键码:`t{:X}", name, vk, sc)
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_IsByRef:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
MsgBox, `% Function(MyVar)

Function(ByRef Param)
{
    return IsByRef(Param)
}
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_IsFunc:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
count := IsFunc("RegExReplace") ; 任意函数名称.
if count
  MsgBox, `% "函数存在且有 " count-1 " 个必须参数."
else
  MsgBox, `% "函数不存在."
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_IsLabel:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
if IsLabel("Label")
    MsgBox, 子程序存在
else
    MsgBox, 子程序不存在

Label:
return
if IsLabel("^#h")
    MsgBox, 热键存在
else
    MsgBox, 热键不存在

^#h::return
if IsLabel("::btw")
    MsgBox, 热字符串存在
else
    MsgBox, 热字符串不存在

::btw::by the way
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_IsObject:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
object := {key: "value"}

if IsObject(object)
    MsgBox, 是对象.
else
    MsgBox, 不是对象.
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_graphicscode_listview系列:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
; 允许用户最大化窗口或拖动来改变窗口的大小:
Gui +Resize

; 创建一些按钮:
Gui, Add, Button, Default gButtonLoadFolder, Load a folder
Gui, Add, Button, x+20 gButtonClear, Clear List
Gui, Add, Button, x+20, Switch View

; 通过 Gui Add 创建 ListView 及其列:
Gui, Add, ListView, xm r20 w700 vMyListView gMyListView, Name|In Folder|Size (KB)|Type
LV_ModifyCol(3, "Integer")  ; 为了排序, 表示 Size 列中的内容是整数.

; 创建图像列表, 这样 ListView 才可以显示图标:
ImageListID1 := IL_Create(10)
ImageListID2 := IL_Create(10, 10, true)  ; 大图标列表和小图标列表.

; 关联图像列表到 ListView, 然而它就可以显示图标了:
LV_SetImageList(ImageListID1)
LV_SetImageList(ImageListID2)

; 创建作为上下文菜单的弹出菜单:
Menu, MyContextMenu, Add, Open, ContextOpenFile
Menu, MyContextMenu, Add, Properties, ContextProperties
Menu, MyContextMenu, Add, Clear from ListView, ContextClearRows
Menu, MyContextMenu, Default, Open  ; 让 "Open" 粗体显示表示双击时会执行相同的操作.

; 显示窗口并返回. 当用户执行预期的动作时
; 操作系统会通知脚本:
Gui, Show
return

ButtonLoadFolder:
Gui +OwnDialogs  ; 强制用户解除此对话框后才可以操作主窗口.
FileSelectFolder, Folder,, 3, Select a folder to read:
if not Folder  ; 用户取消了对话框.
    return

; 检查文件夹名称的最后一个字符是否为反斜杠, 对于根目录则会如此,
; 例如 C:\. 如果是, 则移除这个反斜杠以避免之后出现两个反斜杠.
LastChar := SubStr(Folder, 0)
if (LastChar = "\")
    Folder := SubStr(Folder, 1, -1)  ; 移除尾随的反斜杠.

; 计算 SHFILEINFO 结构需要的缓存大小.
sfi_size := A_PtrSize + 8 + (A_IsUnicode ? 680 : 340)
VarSetCapacity(sfi, sfi_size)

; 获取所选择文件夹中的文件名列表并添加到 ListView:
GuiControl, -Redraw, MyListView  ; 在加载时禁用重绘来提升性能.
Loop `%Folder`%\*.*
{
    FileName := A_LoopFileFullPath  ; 必须保存到可写的变量中供后面使用.

    ; 建立唯一的扩展 ID 以避免变量名中的非法字符,
    ; 例如破折号. 这种使用唯一 ID 的方法也会执行地更好,
    ; 因为在数组中查找项目不需要进行搜索循环.
    SplitPath, FileName,,, FileExt  ; 获取文件扩展名.
    if FileExt in EXE,ICO,ANI,CUR
    {
        ExtID := FileExt  ; 特殊 ID 作为占位符.
        IconNumber := 0  ; 进行标记这样每种类型就含有唯一的图标.
    }
    else  ; 其他的扩展名/文件类型, 计算它们的唯一 ID.
    {
        ExtID := 0  ; 进行初始化来处理比其他更短的扩展名.
        Loop 7     ; 限制扩展名为 7 个字符, 这样之后计算的结果才能存放到 64 位值.
        {
            ExtChar := SubStr(FileExt, A_Index, 1)
            if not ExtChar  ; 没有更多字符了.
                break
            ; 把每个字符与不同的位位置进行运算来得到唯一 ID:
            ExtID := ExtID | (Asc(ExtChar) << (8 * (A_Index - 1)))
        }
        ; 检查此文件扩展名的图标是否已经在图像列表中. 如果是,
        ; 可以避免多次调用并极大提高性能,
        ; 尤其对于包含数以百计文件的文件夹而言:
        IconNumber := IconArray`%ExtID`%
    }
    if not IconNumber  ; 此扩展名还没有相应的图标, 所以进行加载.
    {
        ; 获取与此文件扩展名关联的高质量小图标:
        if not DllCall("Shell32\SHGetFileInfo" . (A_IsUnicode ? "W":"A"), "Str", FileName
            , "UInt", 0, "Ptr", &sfi, "UInt", sfi_size, "UInt", 0x101)  ; 0x101 为 SHGFI_ICON+SHGFI_SMALLICON
            IconNumber := 9999999  ; 把它设置到范围外来显示空图标.
        else ; 成功加载图标.
        {
            ; 从结构中提取 hIcon 成员:
            hIcon := NumGet(sfi, 0)
            ; 直接添加 HICON 到小图标和大图标列表.
            ; 下面加上 1 来把返回的索引从基于零转换到基于一:
            IconNumber := DllCall("ImageList_ReplaceIcon", "Ptr", ImageListID1, "Int", -1, "Ptr", hIcon) + 1
            DllCall("ImageList_ReplaceIcon", "Ptr", ImageListID2, "Int", -1, "Ptr", hIcon)
            ; 现在已经把它复制到图像列表, 所以应销毁原来的:
            DllCall("DestroyIcon", "Ptr", hIcon)
            ; 缓存图标来节省内存并提升加载性能:
            IconArray`%ExtID`% := IconNumber
        }
    }

    ; 在 ListView 中创建新行并把它和上面的图标编号进行关联:
    LV_Add("Icon" . IconNumber, A_LoopFileName, A_LoopFileDir, A_LoopFileSizeKB, FileExt)
}
GuiControl, +Redraw, MyListView  ; 重新启用重绘 (上面把它禁用了).
LV_ModifyCol()  ; 根据内容自动调整每列的大小.
LV_ModifyCol(3, 60) ; 把 Size 列加宽一些以便显示出它的标题.
return

ButtonClear:
LV_Delete()  ; 清理 ListView, 但为了简化保留了图标缓存.
return

ButtonSwitchView:
if not IconView
    GuiControl, +Icon, MyListView    ; 切换到图标视图.
else
    GuiControl, +Report, MyListView  ; 切换回详细信息视图.
IconView := not IconView             ; 进行反转以为下次做准备.
return

MyListView:
if (A_GuiEvent = "DoubleClick")  ; 脚本还可以检查许多其他的可能值.
{
    LV_GetText(FileName, A_EventInfo, 1) ; 从首个字段中获取文本.
    LV_GetText(FileDir, A_EventInfo, 2)  ; 从第二个字段中获取文本.
    Run `%FileDir`%\`%FileName`%,, UseErrorLevel
    if ErrorLevel
        MsgBox Could not open "`%FileDir`%\`%FileName`%".
}
return

GuiContextMenu:  ; 运行此标签来响应右键点击或按下 Appskey.
if (A_GuiControl != "MyListView")  ; 仅在 ListView 中点击时才显示菜单.
    return
; 在提供的坐标处显示菜单, A_GuiX 和 A_GuiY. 应该使用这些
; 因为即使用户按下 Appskey 它们也会提供正确的坐标:
Menu, MyContextMenu, Show, %A_GuiX%, %A_GuiY%
return

ContextOpenFile:  ; 用户在上下文菜单中选择了 "Open".
ContextProperties:  ; 用户在上下文菜单中选择了 "Properties".
; 为了简化, 仅对焦点行进行操作而不是所有选择的行:
FocusedRowNumber := LV_GetNext(0, "F")  ; 查找焦点行.
if not FocusedRowNumber  ; 没有焦点行.
    return
LV_GetText(FileName, FocusedRowNumber, 1) ; 获取首个字段的文本.
LV_GetText(FileDir, FocusedRowNumber, 2)  ; 获取第二个字段的文本.
if InStr(A_ThisMenuItem, "Open")  ; 用户在上下文菜单中选择了 "Open".
    Run `%FileDir`%\`%FileName`%,, UseErrorLevel
else  ; 用户在上下文菜单中选择了 "Properties".
    Run Properties "`%FileDir`%\`%FileName`%",, UseErrorLevel
if ErrorLevel
    MsgBox Could not perform requested action on "%FileDir%\%FileName%".
return

ContextClearRows:  ; 用户在上下文菜单中选择了 "Clear".
RowNumber := 0  ; 这会使得首次循环从顶部开始搜索.
Loop
{
    ; 由于删除了一行使得此行下面的所有行的行号都减小了,
    ; 所以把行号减 1, 这样搜索里包含的行号才会与之前找到的行号相一致
    ; (以防选择了相邻行):
    RowNumber := LV_GetNext(RowNumber - 1)
    if not RowNumber  ; 上面返回零, 所以没有更多选择的行了.
        break
    LV_Delete(RowNumber)  ; 从 ListView 中删除行.
}
return

GuiSize:  ; 扩大或缩小 ListView 来响应用户对窗口大小的改变.
if (A_EventInfo = 1)  ; 窗口被最小化了.  无需进行操作.
    return
; 否则, 窗口的大小被调整过或被最大化了. 调整 ListView 的大小来适应.
GuiControl, Move, MyListView, `% "W" . (A_GuiWidth - 20) . " H" . (A_GuiHeight - 40)
return

GuiClose:  ; 当窗口关闭时, 自动退出脚本:
ExitApp

)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_PostMessagecode_监听在GUI窗口中的鼠标点击OnMessage:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
Gui, Add, Text,, Click anywhere in this window.
Gui, Add, Edit, w200 vMyEdit
Gui, Show
OnMessage(0x201, "WM_LBUTTONDOWN")
return

WM_LBUTTONDOWN(wParam, lParam)
{
    X := lParam `& 0xFFFF
    Y := lParam >> 16
    if A_GuiControl
        Ctrl := "`n(in control " . A_GuiControl . ")"
    ToolTip You left-clicked in Gui window #`%A_Gui`% at client coordinates `%X`%x`%Y`%.`%Ctrl`%
}

GuiClose:
ExitApp
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_返回指定字符串中首个字符的序号值:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
; Unicode 补充字符, 使用代理项对编码表示的字符, 例如 𤭢: U+24B62(十进制: 150370), 代理项对: D852 DF62(十进制: 55378 57186).
MsgBox, `% Ord("𤭢") ; 弹窗显示结果 150370.
MsgBox, `% Asc("𤭢") ; 弹窗显示结果 55378.
MsgBox, `% Ord("t") 
MsgBox, `% Ord("test")
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_从内存地址复制字符串strget:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
str := StrGet(address, "cp0")  ; 代码页 0, 未指定长度
str := StrGet(address, n, 0)   ; 最大 n 字符, 代码页 0
str := StrGet(address, 0)      ; 最大 0 字符(始终为空)
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_将字符串复制到内存地址strput:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
StrPut(str, address, "cp0")  ; 代码页 0, 未指定缓冲大小
StrPut(str, address, n, 0)   ; 最大 n 字符, 代码页 0
StrPut(str, address, 0)      ; 不支持(最大长度为 0 的字符)
;可以调用一次 StrPut, 来计算特定编码中的字符串所需的缓冲大小, 然后再次对字符串进行编码并将其写入缓冲. 这个过程可以通过在你的库中添加以下函数来简化
StrPutVar(string, ByRef var, encoding)
{
    ; 确定容量.
    VarSetCapacity( var, StrPut(string, encoding)
        ; StrPut 返回字符数, 但 VarSetCapacity 需要字节数.
        * ((encoding="utf-16"||encoding="cp1200") ? 2 : 1) )
    ; 复制或转换字符串.
    return StrPut(string, `&var, encoding)
}
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_显示了所有顶层窗口的摘要RegisterCallback:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
; 考虑到性能和内存的保持, 只为指定的回调调用一次 RegisterCallback():
if not EnumAddress  ; 由于只能从这个线程调用, 所以可以使用快速模式:
    EnumAddress := RegisterCallback("EnumWindowsProc", "Fast")

DetectHiddenWindows On  ; 由于是快速模式, 所以此设置也会在回调中生效.

; 把控制传给 EnumWindows(), 它会重复调用回调:
DllCall("EnumWindows", "Ptr", EnumAddress, "Ptr", 0)
MsgBox `%Output`%  ; 显示由回调收集的信息.
    
EnumWindowsProc(hwnd, lParam)
{
    global Output
    WinGetTitle, title, ahk_id `%hwnd`%
    WinGetClass, class, ahk_id `%hwnd`%
    if title
        Output .= "HWND: " . hwnd . "`tTitle: " . title . "`tClass: " . class . "`n"
    return true  ; 告知 EnumWindows() 继续执行, 一直到枚举完所有的窗口.
}
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_文本控件的背景颜色被改变为自定义颜色RegisterCallback:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
TextBackgroundColor := 0xFFBBBB  ; BGR 格式的自定义颜色.
TextBackgroundBrush := DllCall("CreateSolidBrush", "UInt", TextBackgroundColor)

Gui, Add, Text, HwndMyTextHwnd, Here is some text that is given`na custom background color.
Gui +LastFound
GuiHwnd := WinExist()

; 64 位脚本必须调用 SetWindowLongPtr 代替 SetWindowLong:
SetWindowLong := A_PtrSize=8 ? "SetWindowLongPtr" : "SetWindowLong"

WindowProcNew := RegisterCallback("WindowProc", ""  ; 指定 "" 来避免子类化中使用快速模式.
    , 4, MyTextHwnd)  ; 使用了 EventInfo 参数时必须明确指定 ParamCount.
WindowProcOld := DllCall(SetWindowLong,  "Ptr", GuiHwnd, "Int", -4  ; -4 是 GWL_WNDPROC
    ,  "Ptr", WindowProcNew,  "Ptr") ; 返回值必须设置为 Ptr 或 UPtr 而不是 Int.

Gui Show
return

WindowProc(hwnd, uMsg, wParam, lParam)
{
    Critical
    global TextBackgroundColor, TextBackgroundBrush, WindowProcOld
    if (uMsg = 0x138 `&`& lParam = A_EventInfo)  ; 0x138 为 WM_CTLCOLORSTATIC.
    {
        DllCall("SetBkColor", "Ptr", wParam, "UInt", TextBackgroundColor)
        return TextBackgroundBrush  ; 返回 HBRUSH 来通知操作系统我们改变了 HDC.
    }
    ; 否则 (如果上面没有返回), 传递所有的未处理事件到原来的 WindowProc.
    return DllCall("CallWindowProc", "Ptr", WindowProcOld, "Ptr", hwnd, "UInt", uMsg, "Ptr", wParam, "Ptr", lParam)
}

GuiClose:
ExitApp
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_graphicscode_treeview系列:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
; 下面的文件夹为 TreeView 的根文件夹. 请注意, 如果指定整个驱动器例如 C:\
; 那么可能需要很长加载时间:
TreeRoot := A_StartMenuCommon
TreeViewWidth := 280
ListViewWidth := A_ScreenWidth - TreeViewWidth - 30

; 让用户可以最大化或拖动调整窗口大小:
Gui +Resize

; 创建图像列表并在其中放入一些标准的系统图标:
ImageListID := IL_Create(5)
Loop 5 
    IL_Add(ImageListID, "shell32.dll", A_Index)
; 创建 TreeView 和 ListView, 让它们像在 Windows 资源管理器中那样靠在一起:
Gui, Add, TreeView, vMyTreeView r20 w`%TreeViewWidth`% gMyTreeView ImageList`%ImageListID`% ; ImageList
Gui, Add, ListView, vMyListView r20 w`%ListViewWidth`% x+10, Name|Modified

; 设置 ListView 的列宽(可选的):
Col2Width := 70  ; 缩小到只显示 YYYYMMDD 部分.
LV_ModifyCol(1, ListViewWidth - Col2Width - 30)  ; 允许垂直滚动条.
LV_ModifyCol(2, Col2Width)

; 创建状态栏, 显示文件夹数及其总大小的信息:
Gui, Add, StatusBar
SB_SetParts(60, 85)  ; 在状态栏中创建三个部分(第三部分占用所有剩余宽度).

; 添加文件夹及其子文件夹到树中. 如果加载需要很长时间, 则显示提示信息:
SplashTextOn, 200, 25, TreeView and StatusBar Example, Loading the tree...
AddSubFoldersToTree(TreeRoot)
SplashTextOff

; 显示窗口并返回. 每当用户执行符合条件的动作时, 操作系统会通知脚本:
Gui, Show,, `%TreeRoot`%  ; 在标题栏中显示源目录(TreeRoot).
return

AddSubFoldersToTree(Folder, ParentItemID = 0)
{
    ; 此函数添加指定文件夹中所有子文件夹到 TreeView.
    ; 它还可以调用自己来递归获取到任意深度的内嵌文件夹.
    Loop `%Folder`%\*.*, 2  ; 获取所有文件夹的子文件夹.
        AddSubFoldersToTree(A_LoopFileFullPath, TV_Add(A_LoopFileName, ParentItemID, "Icon4"))
}

MyTreeView:  ; 此子程序处理用户的操作(例如点击).
if (A_GuiEvent != "S")  ; 即除了"选择树中的新项目"以外的其他操作.
    return  ; 什么都不做.
; 否则, 把选择的文件夹中的内容放入 ListView.
; 首先确定选择的文件夹的完整路径:
TV_GetText(SelectedItemText, A_EventInfo)
ParentID := A_EventInfo
Loop  ; 建立到选择的文件夹的完整路径.
{
    ParentID := TV_GetParent(ParentID)
    if not ParentID  ; 没有更高层的项目了.
        break
    TV_GetText(ParentText, ParentID)
    SelectedItemText := ParentText "\" SelectedItemText
}
SelectedFullPath := TreeRoot "\" SelectedItemText

; 把文件放入 ListView:
LV_Delete()  ; 清除所有行.
GuiControl, -Redraw, MyListView  ; 加载过程中禁用重绘来提升性能.
FileCount := 0  ; 在下面循环之前初始化.
TotalSize := 0
Loop `%SelectedFullPath`%\*.*  ; 为了简化, 这里省略了文件夹, 所以只在 ListView 中显示文件.
{
    LV_Add("", A_LoopFileName, A_LoopFileTimeModified)
    FileCount += 1
    TotalSize += A_LoopFileSize
}
GuiControl, +Redraw, MyListView

; 更新状态栏的三个部分, 让它们显示当前选择的文件夹的信息:
SB_SetText(FileCount . " files", 1)
SB_SetText(Round(TotalSize / 1024, 1) . " KB", 2)
SB_SetText(SelectedFullPath, 3)
return

GuiSize:  ; 当用户改变窗口大小时扩展/收缩 ListView 和 TreeView.
if (A_EventInfo = 1)  ; 窗口被最小化了. 无需进行操作.
    return
; 否则, 窗口的大小被调整过或被最大化了. 调整控件大小以适应.
GuiControl, Move, MyTreeView, `% "H" . (A_GuiHeight - 30)  ; -30 用于状态栏和边距.
GuiControl, Move, MyListView, `% "H" . (A_GuiHeight - 30) . " W" . (A_GuiWidth - TreeViewWidth - 30)
return

GuiClose:  ; 当用户关闭 TreeView 所在的 GUI 窗口时退出脚本.
ExitApp
)
    gosub Paste_and_Restore_Stored_Clipboard
Return
functionscraping_funcionothercode_计算字符串需要的缓冲空间VarSetCapacity:
    Store:=ClipboardAll  ;****Store clipboard ****
    Clipboard=
    (  Join`r`n
; 计算字符串需要的缓冲空间.
bytes_per_char := A_IsUnicode ? 2 : 1
max_chars := 500
max_bytes := max_chars * bytes_per_char

Loop 2
{
    ; 分配用于 DllCall 的空间.
    VarSetCapacity(buf, max_bytes)

    if (A_Index = 1)
        ; 通过 DllCall 间接修改变量.
        DllCall("wsprintf", "Ptr", &buf, "Str", "0x`%08x", "UInt", 4919)
    else
        ; 使用 "str" 来自动更新长度:
        DllCall("wsprintf", "Str", buf, "Str", "0x`%08x", "UInt", 4919)

    ; 连接字符串以演示为什么需要更新长度:
    wrong_str := buf . "<end>"
    wrong_len := StrLen(buf)

    ; 更新变量的长度.
    VarSetCapacity(buf, -1)

    right_str := buf . "<end>"
    right_len := StrLen(buf)

    MsgBox,
    (
    Before updating
      String: `%wrong_str`%
      Length: `%wrong_len`%

    After updating
      String: `%right_str`%
      Length: `%right_len`%
    `)
}

)
    gosub Paste_and_Restore_Stored_Clipboard
Return