﻿#Region ;**** Directives created by AutoIt3Wrapper_GUI ****
#AutoIt3Wrapper_Compression=4
#AutoIt3Wrapper_Compile_Both=n
#AutoIt3Wrapper_UseX64=Y
#AutoIt3Wrapper_UseUpx=N
#AutoIt3Wrapper_Res_Language=1031
#EndRegion ;**** Directives created by AutoIt3Wrapper_GUI ****
#include "QRCreator.au3"
#include "statusbar_small.au3"
#include <GUIConstants.au3>
#include <GuiSlider.au3>
#include <WinAPIConstants.au3>
#include <WinAPISys.au3>
#include <Crypt.au3>

;~ Start()

;~ Func Start()
;~ MsgBox ($MB_OK + $MB_ICONWARNING,"Hinweis",RandomPassword(25, 0))	;RandomPassword(25, 0)
;~ EndFunc

;~ Exit

OnAutoItExitRegister('OnAutoItExit')

Global $hWnd, $inPath, $btPath, $cbPNG, $inFile, $cbBMP, $cbDummy, $slDummy
Global $r7, $r15, $r25, $r30
Global $editQR, $btFileExit
Global $sIssuer, $lblLabel2
Global $sKontoname
Global $editCode
Global $udMargin, $udPtSize, $udScale, $cbResize, $inResize
Global $btPreview, $slPreview, $btCopy2Clip, $btResizeSave, $btFileSave, $btDelete, $btCalculate
Global $iValSlider, $aWin, $bPreview = False, $iPtSizeLast = 2
Global $iTopBorder, $iSideBorder, $hBitmapPrev, $hGraphicPrev, $hQR_hBitmap
_SystemGetWindowBorder($iTopBorder, $iSideBorder)
Global $bEditEmpty = True, $bPNG = False, $bBMP = False, $iCorrLevel = 0
Global $sPath = @ScriptDir, $sFile, $aMsg, $iErr = 0
Global $aStatusBar
Global $g_sString, $g_sDecoded, $g_sEncoded
Global Const $BASE32CHARS = "ABCDEFGHIJKLMNOPQRSTUVWXYZ234567";
Global $_BASE32_DECODE_TABLE[128]
Global $BASE32_INIT = 0
Global $btFileExit, $btCalculate, $btRandomCode, $btRandomKey

Global Const $HC_ACTION = 0
Global $_gh_MouseProc = DllCallbackRegister("_MouseProc", "long", "int;wparam;lparam")
Global $_gh_mod = _WinAPI_GetModuleHandle(0)
Global $_gh_Hook = _WinAPI_SetWindowsHookEx($WH_MOUSE_LL, DllCallbackGetPtr($_gh_MouseProc), $_gh_mod)
Global $sEncodeCode, $g_sEncoded, $vCode, $vKey, $sKey, $vCreate

$hWnd = GUICreate("2FA QR-Code erstellen", 500, 650, 150, 100)

GUICtrlCreateGroup(' Dateieinstellungen ', 10, 10, 480, 83)
GUICtrlCreateLabel('Ordner:', 25, 33, 50, 17)
$inPath = GUICtrlCreateInput(@ScriptDir, 100, 30, 290, 20, $ES_READONLY)
$btPath = GUICtrlCreateButton('...', 395, 29, 22, 22)

; ********************************************************************
; Wird nicht mehr benötigt. PNG dauerhaft aktiviert
; Deshalb über den Dialog-Rand hinaus verschoben
$cbPNG = GUICtrlCreateCheckbox(' *.PNG', 430, 810, 50, 20)
$cbBMP = GUICtrlCreateCheckbox(' *.BMP', 430, 810, 50, 20)
; ********************************************************************

GUICtrlCreateLabel('Dateiname:', 25, 61, 70, 17)
$inFile = GUICtrlCreateInput('Exceltester', 100, 58, 317, 20)
$cbDummy = GUICtrlCreateDummy()
GUICtrlCreateGroup("", -99, -99, 1, 1)


; ********************************************************************
; Wird nicht mehr benötigt. Deshalb über den Dialog-Rand hinaus verschoben
; Werte dauerhaft aktiviert
GUICtrlCreateGroup(' Korrekturrate (kann nicht geändert werden) ', 10, 810, 480, 50)
$r7 = GUICtrlCreateRadio('7 %', 35, 810, 60, 20)
GUICtrlSetState(-1, $GUI_CHECKED)
GUICtrlSetState(-1, $GUI_DISABLE)
$r15 = GUICtrlCreateRadio('15 %', 165, 810, 60, 20)
GUICtrlSetState(-1, $GUI_DISABLE)
$r25 = GUICtrlCreateRadio('25 %', 305, 810, 60, 20)
GUICtrlSetState(-1, $GUI_DISABLE)
$r30 = GUICtrlCreateRadio('30 %', 425, 810, 60, 20)
GUICtrlSetState(-1, $GUI_DISABLE)
GUICtrlCreateGroup("", -99, -99, 1, 1)

GUICtrlCreateGroup(' Bildgröße (kann nicht geändert werden)', 10, 810, 480, 50)
GUICtrlCreateLabel('Margin size', 35, 810, 60, 17)
$udMargin = GUICtrlCreateInput('10', 95, 810, 50)
GUICtrlSetState(-1, $GUI_DISABLE)
GUICtrlSetLimit(-1, 10, 1)
GUICtrlCreateLabel('Size of created points', 250, 810, 110, 17)
$udPtSize = GUICtrlCreateInput('4', 360, 810, 50, 20)
GUICtrlSetState(-1, $GUI_DISABLE)
GUICtrlSetLimit(-1, 4, 1)
GUICtrlCreateGroup("", -99, -99, 1, 1)
; ********************************************************************

GUICtrlCreateLabel('Code eingeben (Nur Zahlen und Großbuchstaben):', 10, 110)
$editCode = GUICtrlCreateEdit('', 10, 125, 480, 25, BitOR($ES_WANTRETURN, $ES_MULTILINE))
GUICtrlCreateLabel('Secret (Base32):', 10, 175)
$editQR = GUICtrlCreateEdit('', 10, 190, 480, 25, BitOR($ES_WANTRETURN, $ES_MULTILINE, $ES_ReadOnly))
GUICtrlCreateLabel('Herausgeber:', 10, 240)
$sIssuer = GUICtrlCreateEdit('Exceltester', 10, 255, 480, 25, BitOR($ES_WANTRETURN, $ES_MULTILINE))
GUICtrlCreateLabel('Kontoname:', 10, 305)
$sKontoname = GUICtrlCreateEdit('Exceltester', 10, 320, 480, 25, BitOR($ES_WANTRETURN, $ES_MULTILINE))

; ********************************************************************
; Wird nicht mehr benötigt. Deshalb über den Dialog-Rand hinaus verschoben
; Werte dauerhaft aktiviert
$cbResize = GUICtrlCreateCheckbox('Dateigröße ändern (Breite in px)', 10, 810, 180, 20)
GUICtrlSetState(-1, $GUI_DISABLE)
$inResize = GUICtrlCreateInput('', 10, 810, 80, 20, BitOR($ES_NUMBER,$ES_CENTER))
GUICtrlSetState(-1, $GUI_DISABLE)
$udScale = GUICtrlCreateInput('1', 10, 810, 50, 20)
GUICtrlCreateUpdown(-1)
GUICtrlSetLimit(-1, 12, 1)
GUICtrlSetState(-1, $GUI_DISABLE)
; ********************************************************************

$btFileSave = GUICtrlCreateButton('Code erstellen', 355, 350, 135, 22)
GUICtrlCreateLabel('Verschlüsselungskennwort:', 10, 370)
$vCode = GUICtrlCreateEdit('', 10, 385, 480, 25, BitOR($ES_WANTRETURN, $ES_MULTILINE))
GUICtrlCreateLabel('Hash vom Verschlüsselungskennwort:', 10, 435)
$vKey = GUICtrlCreateEdit('', 10, 450, 480, 35, BitOR($ES_WANTRETURN, $ES_MULTILINE, $ES_ReadOnly))
GUICtrlCreateLabel('Verschlüsselter Base32-Code:', 10, 500)
$sKey = GUICtrlCreateEdit('', 10, 515, 480, 35, BitOR($ES_WANTRETURN, $ES_MULTILINE, $ES_ReadOnly))
$vCreate = GUICtrlCreateButton('Verschlüsseln', 355, 565, 135, 22)

$btFileExit = GUICtrlCreateButton('Beenden', 355, 595, 135, 22)
$btCalculate = GUICtrlCreateButton('Secret berechnen', 360, 160, 130, 22)
$btRandomCode = GUICtrlCreateButton('Zufallscode', 210, 160, 130, 22)
$btRandomKey = GUICtrlCreateButton('Zufallkennwort', 360, 415, 130, 22)
$aStatusBar = _StatusbarCreate($hWnd, '75|75|70|-1', '|||', 'c|c|c|l', 'Consolas|10|0')

Local $lblLabel0 = GUICtrlCreateLabel('', 10, 810, 180, 70)

_StatusbarSetColors($aStatusBar, -1, 0x001FD3)


;~ Global $hPreview = GUICreate('QR-Code Preview', -1, -1, -1, -1, BitOR($WS_CAPTION, $WS_SYSMENU), $WS_EX_MDICHILD, $hWnd)
;~ GUISetBkColor(0xE3E3E3, $hPreview)

GUISetState(@SW_SHOW, $hWnd)
GUICtrlSetState($cbPNG, $GUI_CHECKED)
$bPNG = (BitAND(GUICtrlRead($cbPNG), $GUI_CHECKED) = $GUI_CHECKED)
AdlibRegister('_EditChanged')
GuiRegisterMsg($WM_COMMAND, 'WM_COMMAND')



While True
	$aMsg = GUIGetMsg(1)
	Switch $aMsg[0]
		Case $btFileExit
			If $aMsg[1] = $hWnd Then
				Exit
			Else
;~ 				GUICtrlSetState($slPreview, $GUI_DISABLE)
;~ 				GUICtrlSetData($slPreview, 1)
;~ 			    GuiSetState(@SW_HIDE, $hPreview)
				_GDIPlus_GraphicsDispose($hGraphicPrev)
				_GDIPlus_BitmapDispose($hBitmapPrev)
				_GDIPlus_Shutdown()
			    _WinAPI_DeleteObject($hQR_hBitmap)
				$bPreview = False
			EndIf
		Case $btPath
            $sPath = FileSelectFolder('Selct storage path for QR-Image', '', 7)
            If $sPath = '' Then $sPath = @ScriptDir
			GUICtrlSetData($inPath, $sPath)
		Case $cbPNG ;, $cbBMP, $cbDummy
			$bPNG = (BitAND(GUICtrlRead($cbPNG), $GUI_CHECKED) = $GUI_CHECKED)
			;$bBMP = (BitAND(GUICtrlRead($cbBMP), $GUI_CHECKED) = $GUI_CHECKED)
		Case $r7
			If BitAND(GUICtrlRead($r7), $GUI_CHECKED) Then
				$iCorrLevel = 0
				GUICtrlSetLimit($udPtSize, 4, 1)
				GUICtrlSetData($udPtSize, 2)
				;If $bPreview Then _UpdatePreview()
			EndIf
		Case $btCalculate
				$sEncodeCode = GUICtrlRead($editCode)
				$g_sEncoded = _Base32_Encode($sEncodeCode)
				GUICtrlSetData($editQR,  $g_sEncoded)
			Case $btFileSave
			If $bPNG Then _QR_generatePNG("otpauth://totp/"  & GUICtrlRead($sKontoname) & "?secret=" & GUICtrlRead($editQR) & "&issuer=" & GUICtrlRead($sIssuer), _CreateFullPath() & 'png', GUICtrlRead($udMargin), GUICtrlRead($udPtSize), $iCorrLevel)
			$iErr = @error
			If $bBMP Then _QR_generateBMP("otpauth://totp/"  & GUICtrlRead($sKontoname) & "?secret=" & GUICtrlRead($editQR) & "&issuer=" & GUICtrlRead($sIssuer), _CreateFullPath() & 'bmp', GUICtrlRead($udMargin), GUICtrlRead($udPtSize), $iCorrLevel)
			$iErr += @error
			_StatusbarSetColors($aStatusBar, -1, 0x001FD3)
			_StatusBarShowResult()
;~ 			If $iErr Then
;~ 				GUICtrlSetData($lblLabel2,  'Der QR-Code konnte nicht erstellt werden.')
;~ 			Else
;~ 				GUICtrlSetData($lblLabel2,  'Der QR-Code wurde erfolgreich erstellt.')
;~ 			EndIf
		Case $vCreate
			;MsgBox ($MB_OK + $MB_ICONWARNING,"Hinweis","Funktion noch nicht integriert.")
			GUICtrlSetData($vKey, _Crypt_HashData(GUICtrlRead($vCode),$CALG_SHA_512))
			GUICtrlSetData($sKey, _Crypt_EncryptData(GUICtrlRead($editQR), GUICtrlRead($vKey), $CALG_AES_256))
			ClipPut(";Verschlüsselter Secret" & @CRLF & "Local $sSecret = '" & GUICtrlRead($sKey) & "'" & _
                    @CRLF & @CRLF & ";Hash-Wert des Verschlüsselungspasswortes" & @CRLF & "Local $sHash = '" & GUICtrlRead($vKey) & "'" & _
					@CRLF & @CRLF & "_Crypt_Startup()" & @CRLF & @CRLF & _
					"Local $PASSWORD_DECRYPTED = _Crypt_DecryptData($sSecret, $sHash, $CALG_AES_256)" & @CRLF & @CRLF & "_Crypt_Shutdown()" & _
					@CRLF & @CRLF & "$PASSWORD_DECRYPTED = BinaryToString($PASSWORD_DECRYPTED)")
		Case $btRandomCode
			GUICtrlSetData($editCode, RandomPassword(25, 0)) ;RandomPassword(25, 0)
		Case $btRandomKey
			GUICtrlSetData($vCode, RandomPassword(25, 0)) ;RandomPassword(25, 0)
	EndSwitch
WEnd

Func OnAutoItExit()
    _WinAPI_UnhookWindowsHookEx($_gh_Hook)
    DllCallbackFree($_gh_MouseProc)
EndFunc



Func _CreateFullPath()
	$sFile = GUICtrlRead($inFile)
	If $sFile = '' Then $sFile = _QR_FileDefault()
	If StringRegExp($sFile, '(?i)\.bmp|png') Then $sFile = StringTrimRight($sFile, 4)
	GUICtrlSetData($inFile, $sFile)
	Return StringFormat('%s\%s.', $sPath, $sFile)
EndFunc


Func _StatusBarShowResult()
	Local Static $iRed = 0xDB0E00, $iGreen = 0x289916
	Local $tRes = _QR_getLastCall()
	_StatusbarSetColors($aStatusBar, 1, ($tRes.success ? $iGreen : $iRed))
	Local $aText[4] = [($tRes.type = 'B' ? 'HBMP': ($tRes.type = 'C' ? 'CLIPBOARD' : ($tRes.type = 'R' ? 'RESIZED' : 'FILECREATE'))), _
	                  ($tRes.success ? 'SUCCES' : 'FAILED'), ($tRes.success ? StringFormat('%dx%d', $tRes.width, $tRes.width) : ''), _
					  ($tRes.type = 'F' ? _ShrinkPath($tRes.output) : '')]
	If $tRes.type = 'R' Then
		$aText[3] = ($tRes.width = -1 ? $tRes.output : _ShrinkPath($tRes.output))
		If $tRes.width = -1 Then _StatusbarSetColors($aStatusBar, 3, $iRed)
	EndIf
	_StatusbarSetText($aStatusBar, '0|1|2|3', $aText)
EndFunc


Func _ShrinkPath($_sPath)
	Local $sLeft = StringLeft($_sPath, 3)
	Local $sRight = StringTrimLeft($_sPath, (StringInStr($_sPath, '\', 0, -1) -1))
	Return StringFormat('%s..%s', $sLeft, $sRight)
EndFunc


;~ Func _CreatePreviewBmp()
;~ 	$hQR_hBitmap = _QR_getHBitmap("otpauth://totp/"  & GUICtrlRead($sKontoname) & "?secret=" & GUICtrlRead($editQR) & "&issuer=" & GUICtrlRead($sIssuer), GUICtrlRead($udMargin), GUICtrlRead($udPtSize), $iCorrLevel)
;~ 	If @error Then Return SetError(@error,0,MsgBox(262144+16, 'Error', 'QR-Code creation failed by Dll call.'))
;~ 	If Not $bPreview Then
;~ 		_GDIPlus_Startup()
;~ 		GuiSetState(@SW_SHOWNA, $hPreview)
;~ 		GUICtrlSetState($slPreview, $GUI_ENABLE)
;~ 	Else
;~ 	    _Preview(GUICtrlRead($slPreview))
;~ 	EndIf
;~ EndFunc


;~ Func _Preview($_iScale=1)
;~ 	Local Static $iGreen = 0x289916
;~ 	$hBitmapPrev = _GDIPlus_BitmapCreateFromHBITMAP($hQR_hBitmap)
;~ 	$hBitmapPrev = _GDIPlus_ImageScale($hBitmapPrev, $_iScale, $_iScale, $GDIP_INTERPOLATIONMODE_NEARESTNEIGHBOR)
;~     Local $iWidth, $iW = _GDIPlus_ImageGetWidth($hBitmapPrev)
;~ 	$iWidth = $iW
;~ 	WinSetTitle($hPreview, '', 'QR-Code Preview  [ *' & $_iScale & ' ]')
;~ 	If $iWidth < 250 Then $iWidth = 250
;~ 	$aWin = WinGetPos($hWnd)
;~ 	WinMove($hPreview, '', $aWin[0]+$aWin[2]+20, $aWin[1], 2*$iSideBorder+2*10+$iWidth, $iTopBorder+2*10+$iWidth+$iSideBorder)
;~ 	_GDIPlus_GraphicsClear($hGraphicPrev, 0xFFE3E3E3)
;~     $hGraphicPrev = _GDIPlus_GraphicsCreateFromHWND($hPreview)
;~     _GDIPlus_GraphicsDrawImage($hGraphicPrev, $hBitmapPrev, 10, 10)
;~ 	Local $aText[] = ['PREVIEW','SUCCESS',StringFormat('%dx%d', $iW, $iW), '']
;~ 	_StatusbarSetText($aStatusBar, '0|1|2|3', $aText)
;~ 	_StatusbarSetColors($aStatusBar, -1, 0x001FD3)
;~ 	_StatusbarSetColors($aStatusBar, 1, $iGreen)

;~ 	; ==== debugging
	__consoleResults()
;~ 	; ==============
;~ EndFunc


;~ Func _UpdatePreview()
;~ 	_CreatePreviewBmp()
;~ 	Local $tRes = _QR_getLastCall()
;~ 	If $tRes.sizept < $iPtSizeLast Then
;~  		Local $hDC = _WinAPI_GetWindowDC($hWnd)
;~     	Local $hPen = _WinAPI_CreatePen($PS_SOLID, 2, 0x0000FF)
;~     	Local $o_Orig = _WinAPI_SelectObject($hDC, $hPen)
;~ 		_WinAPI_DrawLine($hDC, 250+$iSideBorder, 180+$iTopBorder, 412+$iSideBorder, 180+$iTopBorder)
;~ 		_WinAPI_DrawLine($hDC, 412+$iSideBorder, 180+$iTopBorder, 412+$iSideBorder, 202+$iTopBorder)
;~ 		Sleep(500)
;~ 		_WinAPI_RedrawWindow($hWnd)
;~ 		Sleep(500)
;~ 		_WinAPI_DrawLine($hDC, 250+$iSideBorder, 180+$iTopBorder, 412+$iSideBorder, 180+$iTopBorder)
;~ 		_WinAPI_DrawLine($hDC, 412+$iSideBorder, 180+$iTopBorder, 412+$iSideBorder, 202+$iTopBorder)
;~ 		Sleep(500)
;~ 		_WinAPI_RedrawWindow($hWnd)
;~ 		_WinAPI_SelectObject($hDC, $o_Orig)
;~ 		_WinAPI_DeleteObject($hPen)
;~ 		_WinAPI_ReleaseDC(0, $hDC)
;~ 	EndIf
;~ 	$iPtSizeLast = $tRes.sizept
;~ 	GUICtrlSetData($udPtSize, $iPtSizeLast)
;~ EndFunc


Func _EditChanged()
	Local Static $bLastEmpty = True
	If $bEditEmpty = $bLastEmpty Then Return
	$bLastEmpty = $bEditEmpty
	GUICtrlSendToDummy($cbDummy) ; init a checkbox event to en/disable $btFileSave
	If $bEditEmpty Then
		GUICtrlSetState($btPreview, $GUI_DISABLE)
		GUICtrlSetState($slPreview, $GUI_DISABLE)
		GUICtrlSetState($btCopy2Clip, $GUI_DISABLE)
		GUICtrlSetState($inResize, $GUI_DISABLE)
		GUICtrlSetData($inResize, '')
	Else
		GUICtrlSetState($btPreview, $GUI_ENABLE)
		GUICtrlSetState($btCopy2Clip, $GUI_ENABLE)
		If BitAND(GUICtrlRead($cbResize), $GUI_CHECKED) Then _
			GUICtrlSetState($inResize, $GUI_ENABLE)
	EndIf
EndFunc


Func _SetDefaults()
	;GuiSetState(@SW_HIDE, $hPreview)
	GUICtrlSetState($cbPNG, $GUI_UNCHECKED)
	GUICtrlSetState($cbBMP, $GUI_UNCHECKED)
	GUICtrlSetState($cbResize, $GUI_UNCHECKED)
	GUICtrlSetState($r7, $GUI_CHECKED)
	GUICtrlSetState($btPreview, $GUI_DISABLE)
	GUICtrlSetState($slPreview, $GUI_DISABLE)
	GUICtrlSetState($btCopy2Clip, $GUI_DISABLE)
	GUICtrlSetState($btFileSave, $GUI_DISABLE)
	GUICtrlSetState($inResize, $GUI_DISABLE)
	GUICtrlSetData($inPath, @ScriptDir)
	GUICtrlSetData($inFile, '')
	GUICtrlSetData($udMargin, 4)
	GUICtrlSetData($udPtSize, 2)
	GUICtrlSetData($udScale, 1)
	GUICtrlSetData($editQR, '')
	GUICtrlSetData($slPreview, 0)
	GUICtrlSetData($inResize, '')
	$bEditEmpty = True
	$bPNG = True
	$bBMP = False
	$iCorrLevel = 0
	$iErr = 0
	_StatusbarSetText($aStatusBar, '0|1|2|3', '|||')
	_StatusbarSetColors($aStatusBar, -1, 0x001FD3)
EndFunc


Func WM_COMMAND($hWnd, $iMsg, $iwParam, $ilParam)
    Local $hWndFrom = $ilParam
    Local $hWndEdit = GUICtrlGetHandle($editQR)
    Local $iCode = BitShift($iwParam, 16)
    Switch $hWndFrom
        Case $hWndEdit
            Switch $iCode
                Case $EN_CHANGE
						If StringLen(GUICtrlRead($editQR)) = 0 Then
							$bEditEmpty = True
						Else
							$bEditEmpty = False
						EndIf
            EndSwitch
    EndSwitch
    Return $GUI_RUNDEFMSG
EndFunc

;~ Func Test()
;~ ; Beispiel 1 :
;~ $g_sString = "32ERQ67TZ6709WE65ERZ51E2TR91QW"
;~ $g_sEncoded = _Base32_Encode($g_sString)
;~ $g_sDecoded = _Base32_Decode($g_sEncoded)
;~ MsgBox(0, "Base32 - Beispiel 1 : ", _
;~ 		  "String  = " & $g_sString  & @CRLF & @CRLF & _
;~ 		  "Encoded = " & $g_sEncoded)
;~ 	  EndFunc

Func _SystemGetWindowBorder(ByRef $_iTopBorder, ByRef $_iSideBorder)
	Local Const $SM_CYCAPTION = 4, $SM_CYEDGE = 46, $SM_CYBORDER = 6, $SM_CXBORDER = 5, $SM_CXEDGE = 45
	Local $aMetrics[5][2] = [[$SM_CYCAPTION], [$SM_CYEDGE], [$SM_CYBORDER], [$SM_CXBORDER], [$SM_CXEDGE]]
	Local $dll = DllOpen("user32.dll"), $aRet
	For $i = 0 To 4
		$aRet = DllCall($dll, "int", "GetSystemMetrics", "int", $aMetrics[$i][0])
		If IsArray($aRet) Then $aMetrics[$i][1] = $aRet[0]
	Next
	DllClose($dll)
	$_iTopBorder  = $aMetrics[0][1] + $aMetrics[1][1] + $aMetrics[2][1]
	$_iSideBorder = $aMetrics[3][1] + $aMetrics[4][1]
EndFunc


; only for debugging
Func __consoleResults()
	Local $tRes = _QR_getLastCall()
	ConsoleWrite('.success   ' & $tRes.success   & @CRLF)
	ConsoleWrite('.error     ' & $tRes.error     & @CRLF)
	ConsoleWrite('.width     ' & $tRes.width     & @CRLF)
	ConsoleWrite('.type      ' & $tRes.type      & @CRLF)
	ConsoleWrite('.output    ' & $tRes.output    & @CRLF)
	ConsoleWrite('.margin    ' & $tRes.margin    & @CRLF)
	ConsoleWrite('.sizept    ' & $tRes.sizept    & @CRLF)
	ConsoleWrite('.corrlevel ' & $tRes.corrlevel & @CRLF & @CRLF)
EndFunc


Func _MouseProc($nCode, $wParam, $lParam)
	Local $info, $iX, $iY, $mouseData
	Local Static $tMousePos = DllStructCreate("struct; long X;long Y; endstruct")
	$info = DllStructCreate("int X;int Y;dword mouseData;dword flags;dword time;ulong_ptr dwExtraInfo", $lParam)
	$tMousePos.X = DllStructGetData($info, 1)
    $tMousePos.Y = DllStructGetData($info, 2)
;~ 	Local $tRect = _WinAPI_GetWindowRect($hPreview)
;~ 	Local $bOnPreview = (_WinAPI_PtInRect($tRect, $tMousePos) And BitAND(WinGetState($hPreview), $WIN_STATE_VISIBLE))
    $mouseData = DllStructGetData($info, 3)
   ; If $nCode < 0 Or Not $bOnPreview Then Return _WinAPI_CallNextHookEx($_gh_Hook, $nCode, $wParam, $lParam)
    If $nCode = $HC_ACTION Then
		Switch $wParam
			Case $WM_LBUTTONUP
				_SetSlider(1)
			Case $WM_RBUTTONUP
				_SetSlider(-1)
			Case $WM_MOUSEWHEEL
				If _WinAPI_HiWord($mouseData) > 0 Then
					_SetSlider(1)  ; "Forward"
				Else
					_SetSlider(-1) ; "Backward"
				EndIf
		EndSwitch
	EndIf
	Return _WinAPI_CallNextHookEx($_gh_Hook, $nCode, $wParam, $lParam)
EndFunc


Func _SetSlider($_n)
	Local $iSliderVal = GUICtrlRead($slPreview)
	If $_n = 1 Then
		If $iSliderVal < 12 Then GUICtrlSetData($slPreview, $iSliderVal +1)
	Else
		If $iSliderVal > 1 Then GUICtrlSetData($slPreview, $iSliderVal -1)
	EndIf
	GUICtrlSendToDummy($slDummy)
EndFunc

Func _Base32_Encode($vData)
	If $BASE32_INIT = 0 Then
		If Not _Base32_BuildTable() Then Return SetError(1, 0, 0)
	EndIf
	Local $data = __Split_Key($vData)
	Local $dataLength = UBound($data)
	If Not $dataLength > 0 Then Return SetError(1, 0, 0)
	Local $chars[$dataLength * 8 / 5 + (1 * (Mod($dataLength, 5) > 0))]
	Local $charsLength = UBound($chars)
	Local $i = 0, $j = 0, $index = 0, $b = 0
	Local $ALPHABET = __Split_Key($BASE32CHARS)
	For $i = 0 To $charsLength - 1
		If $index > 3 Then
			$b = BitAND(Asc($data[$j]), BitShift(0xFF, $index))
			$index = Mod($index + 5, 8)
			$b = BitShift($b, -$index)
			If $j < $dataLength - 1 Then
				$b = BitOR($b, BitShift(BitAND(Asc($data[$j + 1]), 0xFF), (8 - $index)))
			EndIf
			$chars[$i] = $ALPHABET[$b]
			$j += 1
		Else
			$chars[$i] = $ALPHABET[BitAND(BitShift(Asc($data[$j]), (8 - ($index + 5))), 0x1F)]
			$index = Mod($index + 5, 8)
			If $index = 0 Then
				$j += 1
			EndIf
		EndIf
	Next
	Local $sEncoded = ""
	For $x = 0 To UBound($chars) - 1
		$sEncoded &= $chars[$x]
	Next
	Return $sEncoded
EndFunc   ;==>_Base32_Encode

; ====================================================================================================
; Description ...: Decode a base32 encoded string
; Parameters ....: $vData - IN - Data to decode.
; Return values .: On Success - Decoded data
;                  On Failure - @error set to 1, 0 returned
; Author ........: Ported by Stephen Podhajecki {gehossafats at netmdc. com}
; Remarks .......: Works with text strings and files.
; Related .......: _Base32_Encode
; ====================================================================================================
Func _Base32_Decode($vData)
	If $BASE32_INIT = 0 Then
		If Not _Base32_BuildTable() Then Return SetError(1, 0, 0)
	EndIf
	Local $stringData = __Split_Key($vData)
	Local $stringDataLength = UBound($stringData)
	If Not $stringDataLength > 0 Then Return SetError(1, 0, 0)
	Local $data[(($stringDataLength * 5) / 8)]
	Local $dataLength = UBound($data)
	Local $i, $j = 0, $index = 0, $val = 0, $decoded = ""
	For $i = 0 To $stringDataLength - 1
		$val = 0
		$val = $_BASE32_DECODE_TABLE[Asc($stringData[$i])]
		If $val = 0xFF Then
			;;rem illegal character
			Return SetError(1, 0, 0)
		EndIf
		If ($index <= 3) Then
			$index = Mod($index + 5, 8)
			If $index = 0 Then
				$data[$j] = BitOR($data[$j], $val)
				$j += 1
			Else
				$data[$j] = BitOR($data[$j], BitShift($val, -(8 - $index)))
			EndIf
		Else
			$index = Mod($index + 5, 8)
			$data[$j] = BitOR($data[$j], BitShift($val, $index))
			$j += 1
			If $j < $dataLength Then
				$data[$j] = BitOR($data[$j], BitShift($val, -(8 - $index)))
				$data[$j] = BitAND($data[$j], 0xFF)
			EndIf
		EndIf
	Next
	For $x = 0 To UBound($data) - 1
		$decoded &= Chr($data[$x])
	Next
	Return $decoded
EndFunc   ;==>_Base32_Decode
; ====================================================================================================
; _Base32_BuildTable(): Builds a conversion table
; ====================================================================================================
Func _Base32_BuildTable()
	For $i = 0 To UBound($_BASE32_DECODE_TABLE) - 1
		$_BASE32_DECODE_TABLE[$i] = 0xFF
	Next
	For $i = 0 To StringLen($BASE32CHARS) - 1
		$_BASE32_DECODE_TABLE[Asc(StringMid($BASE32CHARS, $i + 1, 1))] = $i
		If $i < 24 Then
			$_BASE32_DECODE_TABLE[Asc(StringLower(StringMid($BASE32CHARS, $i + 1, 1)))] = $i
		EndIf
	Next
	$BASE32_INIT = 1
	Return 1
EndFunc   ;==>_Base32_BuildTable

; ====================================================================================================
; __Split_Key:  Internal function
; splits a string into an array of characters and strip the count value from the first element.
; ====================================================================================================
Func __Split_Key($szKey, $szDelim = "")
	If $szKey = "" Then Return SetError(1, 0, 0)
	If IsArray($szKey) Then Return $szKey
	Local $iCount, $iTotal = 0, $szTemp = ""
	Local $aTemp = StringSplit($szKey, $szDelim)
	If Not @error Then
		$iCount = $aTemp[0]
		For $x = 1 To $iCount
			$iTotal += 1
			$aTemp[$x - 1] = $aTemp[$x]
		Next
		ReDim $aTemp[$iTotal]
		Return $aTemp
	EndIf
	Return SetError(1, 0, 0)
EndFunc   ;==>__Split_Key

Func RandomPassword($Length, $Fmt = 0)
    Local $buff
    Local $i
    Local $n

    Local Const $Alpha = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
    Local Const $ADigits = "0123456789"
    Local Const $Special = "!#$%&'()*+,-./:;<=>?@[\]^_`{|}~"
    ;Password include file
    Local $pwsMask = ""

    $pwsMask = $Alpha & $ADigits

    ;This creates the random password.
    For $i = 1 To $Length
        ;Pick a random chat between 1 and the pwsMask Length
        $n = Int(Random(1, StringLen($pwsMask)))
        ;Concat each chat that has been picked out of pwsMask to $buff
        $buff = $buff & StringMid($pwsMask, $n, 1)
    Next
    Return $buff
EndFunc   ;==>RandomPassword