Jump to content

[ASK] format number as we type


Recommended Posts

Newbie need help again :)

How to format numbers as user type it in the GuiCtrlCreateInput Box.

I would like to format the number realtime into currency format 999,999,999,999 when user type numbers into the inputbox.

So when a user enter number 1999, the number change to 1,999 automatically even before user leave the inputbox.

Thanks a lot ;)

Link to comment
Share on other sites

  • Moderators

michaelslamet,

That was fun! ;)

; Credit to Valik for the DllCall lines

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <EditConstants.au3>

$hGUI = GUICreate("Test", 500, 500)

$hInput = GUICtrlCreateInput ("", 10,  20, 300, 20)

GuiSetState(@SW_SHOW)

GUIRegisterMsg($WM_COMMAND, "_WM_COMMAND")

While 1
    If GUIGetMsg() = $GUI_EVENT_CLOSE Then Exit
WEnd

Func _WM_COMMAND($hWnd, $iMsg, $wParam, $lParam)

    Local $iIDFrom = BitAND($wParam, 0xFFFF);LoWord
    Local $iCode = BitShift($wParam, 16)    ;HiWord
    Local $sDecimal = ""

    If $iIDFrom = $hInput And $iCode = $EN_CHANGE Then

        $sInput = GUICtrlRead($hInput)
        ; Check contents for invalid characters - only leave leading minus, digits and a decimal point
        If StringRegExp($sInput, '[^\d.-]|([{0-9,1}^\A-])[^\d.]') Then $sInput = StringRegExpReplace($sInput, '[^\d.-]|([{0-9,1}^\A-])[^\d.]', '\1')
        ; Check if only leadign minus is present
        If $sInput = "-" Then Return
        ; If decimal point present strip decimal digits
        Local $iDecimal = StringInStr($sInput, ".")
        If $iDecimal Then
            $sDecimal = StringMid($sInput, $iDecimal)
            $sInput = StringMid($sInput, 1, $iDecimal - 1)
        EndIf
        ; Add seperators to integer value
        Local $aRes = DllCall("kernel32.dll", "int", "GetNumberFormatW", "int", 0x0400, "dword", 0, "wstr", $sInput, "ptr", 0, "ptr", 0, "int", 0)
        If @error Then Return
        Local $pBuffer = DllStructCreate("wchar[" & $aRes[0] + 1 & "]")
        $aRes = DllCall("kernel32.dll", "int", "GetNumberFormatW", "int", 0x0400, "dword", 0, "wstr", $sInput, "ptr", 0, "ptr", DllStructGetPtr($pBuffer), "int", $aRes[0])
        If @error Then Return
        $sOutput = StringTrimRight(DllStructGetData($pBuffer, 1), 3)
        ; Put separated data back into input
        If Number($sOutput) Then
            ; Add decimal digits if required
            If $sDecimal Then $sOutput &= $sDecimal
            GUICtrlSetData($hInput, $sOutput)
        Else
            GUICtrlSetData($hInput, "")
        EndIf
    EndIf

EndFunc;==>_WM_COMMAND

I think I have covered all the bases - it works for positive and negative numbers, integer or decimal and you can modify the integer part even if the decimal part already exists. :)

M23

Public_Domain.png.2d871819fcb9957cf44f4514551a2935.png Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind

Open spoiler to see my UDFs:

Spoiler

ArrayMultiColSort ---- Sort arrays on multiple columns
ChooseFileFolder ---- Single and multiple selections from specified path treeview listing
Date_Time_Convert -- Easily convert date/time formats, including the language used
ExtMsgBox --------- A highly customisable replacement for MsgBox
GUIExtender -------- Extend and retract multiple sections within a GUI
GUIFrame ---------- Subdivide GUIs into many adjustable frames
GUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView items
GUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeView
Marquee ----------- Scrolling tickertape GUIs
NoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxes
Notify ------------- Small notifications on the edge of the display
Scrollbars ----------Automatically sized scrollbars with a single command
StringSize ---------- Automatically size controls to fit text
Toast -------------- Small GUIs which pop out of the notification area

 

Link to comment
Share on other sites

I will definitely use GetNumberFormatW sometime in the future. Surprised this isn't in WinAPIEx.au3.

UDF List:

 
_AdapterConnections()_AlwaysRun()_AppMon()_AppMonEx()_ArrayFilter/_ArrayReduce_BinaryBin()_CheckMsgBox()_CmdLineRaw()_ContextMenu()_ConvertLHWebColor()/_ConvertSHWebColor()_DesktopDimensions()_DisplayPassword()_DotNet_Load()/_DotNet_Unload()_Fibonacci()_FileCompare()_FileCompareContents()_FileNameByHandle()_FilePrefix/SRE()_FindInFile()_GetBackgroundColor()/_SetBackgroundColor()_GetConrolID()_GetCtrlClass()_GetDirectoryFormat()_GetDriveMediaType()_GetFilename()/_GetFilenameExt()_GetHardwareID()_GetIP()_GetIP_Country()_GetOSLanguage()_GetSavedSource()_GetStringSize()_GetSystemPaths()_GetURLImage()_GIFImage()_GoogleWeather()_GUICtrlCreateGroup()_GUICtrlListBox_CreateArray()_GUICtrlListView_CreateArray()_GUICtrlListView_SaveCSV()_GUICtrlListView_SaveHTML()_GUICtrlListView_SaveTxt()_GUICtrlListView_SaveXML()_GUICtrlMenu_Recent()_GUICtrlMenu_SetItemImage()_GUICtrlTreeView_CreateArray()_GUIDisable()_GUIImageList_SetIconFromHandle()_GUIRegisterMsg()_GUISetIcon()_Icon_Clear()/_Icon_Set()_IdleTime()_InetGet()_InetGetGUI()_InetGetProgress()_IPDetails()_IsFileOlder()_IsGUID()_IsHex()_IsPalindrome()_IsRegKey()_IsStringRegExp()_IsSystemDrive()_IsUPX()_IsValidType()_IsWebColor()_Language()_Log()_MicrosoftInternetConnectivity()_MSDNDataType()_PathFull/GetRelative/Split()_PathSplitEx()_PrintFromArray()_ProgressSetMarquee()_ReDim()_RockPaperScissors()/_RockPaperScissorsLizardSpock()_ScrollingCredits_SelfDelete()_SelfRename()_SelfUpdate()_SendTo()_ShellAll()_ShellFile()_ShellFolder()_SingletonHWID()_SingletonPID()_Startup()_StringCompact()_StringIsValid()_StringRegExpMetaCharacters()_StringReplaceWholeWord()_StringStripChars()_Temperature()_TrialPeriod()_UKToUSDate()/_USToUKDate()_WinAPI_Create_CTL_CODE()_WinAPI_CreateGUID()_WMIDateStringToDate()/_DateToWMIDateString()Au3 script parsingAutoIt SearchAutoIt3 PortableAutoIt3WrapperToPragmaAutoItWinGetTitle()/AutoItWinSetTitle()CodingDirToHTML5FileInstallrFileReadLastChars()GeoIP databaseGUI - Only Close ButtonGUI ExamplesGUICtrlDeleteImage()GUICtrlGetBkColor()GUICtrlGetStyle()GUIEventsGUIGetBkColor()Int_Parse() & Int_TryParse()IsISBN()LockFile()Mapping CtrlIDsOOP in AutoItParseHeadersToSciTE()PasswordValidPasteBinPosts Per DayPreExpandProtect GlobalsQueue()Resource UpdateResourcesExSciTE JumpSettings INISHELLHOOKShunting-YardSignature CreatorStack()Stopwatch()StringAddLF()/StringStripLF()StringEOLToCRLF()VSCROLLWM_COPYDATAMore Examples...

Updated: 22/04/2018

Link to comment
Share on other sites

This will allow one decimal point only.

$Frm_Main = GUICreate("Test Window")
$In_1 = GUICtrlCreateInput("123", 10, 10, 150, 20)
$In_2 = GUICtrlCreateInput("1234", 10, 40, 150, 20)
$In_3 = GUICtrlCreateInput("$987", 10, 70, 150, 20)
$In_4 = GUICtrlCreateInput("-$98765", 10, 100, 150, 20)

GUISetState()
While 1
    $Msg = GUIGetMsg()
    For $i = $In_1 To $In_4
        $iNum = 0
        If GUICtrlRead($i) <> "" Then
            $sChr = GUICtrlRead($i)
            $iLen = StringLen($sChr)
            StringReplace($sChr, ",", ",")
            $iNum = @extended
            If (Int(($iLen - $iNum - 1) / 3) <> $iNum) Or (StringRight($sChr, 1) = ".") Or _
                    ($iLen > 3 And StringMid($sChr, $iLen - 3, 1) <> ",") Then _
                    GUICtrlSetData($i, _StringAddThousandsSep(StringReplace($sChr, ",", "")))
        EndIf
    Next
    Switch $Msg
        Case -3
            ExitLoop
        Case Else
    EndSwitch
WEnd


; Modified from http://www.autoitscript.com/forum/index.php?showtopic=113446&view=findpost&p=793903
Func _StringAddThousandsSep($sString, $sThousands = ",", $sDecimal = ".")
    Local $aNumber, $sLeft, $sResult = "", $iNegSign = "", $DolSgn = "", $sDecPt = ""
    If Number(StringRegExpReplace($sString, "[^0-9\-.+]", "\1")) < 0 Then $iNegSign = "-" ; Allows for a negative value
    If StringRegExp($sString, "\$") And StringRegExpReplace($sString, "[^0-9]", "\1") <> "" Then $DolSgn = "$" ; Allow for Dollar sign
    $aNumber = StringRegExp($sString, "(\d+)\D?(\d*)", 1)
    If UBound($aNumber) = 2 Then
        $sLeft = $aNumber[0]
        While StringLen($sLeft)
            $sResult = $sThousands & StringRight($sLeft, 3) & $sResult
            $sLeft = StringTrimRight($sLeft, 3)
        WEnd
        $sResult = StringTrimLeft($sResult, 1); Strip leading thousands separator
        If $aNumber[1] <> "" Then $sResult &= $sDecimal & $aNumber[1] ; Add decimal
    EndIf
    If StringRight($sString, 1) = "." And StringInStr($sString, ".") = StringLen($sString) Then $sDecPt = "." ; Allow for adding deciminal point.
    Return $iNegSign & $DolSgn & $sResult & $sDecPt; Adds minus or "" (nothing)and Adds $ or ""
EndFunc   ;==>_StringAddThousandsSep
Link to comment
Share on other sites

  • Moderators

Malkey,

So much for: "I think I have covered all the bases"! :idiot:

M23

Edit: This only allows one decimal point - anyone find any other bugs? :)

; Credit to Valik for the DllCall lines

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <EditConstants.au3>

$hGUI = GUICreate("Test", 500, 500)

$hInput = GUICtrlCreateInput ("", 10,  20, 300, 20)

GuiSetState(@SW_SHOW)

GUIRegisterMsg($WM_COMMAND, "_WM_COMMAND")

While 1
    If GUIGetMsg() = $GUI_EVENT_CLOSE Then Exit
WEnd

Func _WM_COMMAND($hWnd, $iMsg, $wParam, $lParam)

    Local $iIDFrom = BitAND($wParam, 0xFFFF);LoWord
    Local $iCode = BitShift($wParam, 16)    ;HiWord
    Local $sDecimal = ""

    If $iIDFrom = $hInput And $iCode = $EN_CHANGE Then

        $sInput = GUICtrlRead($hInput)
        ; Check contents for invalid characters - only leave leading minus, digits and decimal points
        If StringRegExp($sInput, '[^\d.-]|([{0-9,1}^\A-])[^\d.]') Then $sInput = StringRegExpReplace($sInput, '[^\d.-]|([{0-9,1}^\A-])[^\d.]', '\1')
        ; Check for multiple decimals
        StringRegExpReplace($sInput, "\.", "")
        If @extended > 1 Then $sInput = StringTrimRight($sInput, 1)
        ; Check if only leading minus is present
        If $sInput = "-" Then Return
        ; If decimal point present strip decimal digits
        Local $iDecimal = StringInStr($sInput, ".")
        If $iDecimal Then
            $sDecimal = StringMid($sInput, $iDecimal)
            $sInput = StringMid($sInput, 1, $iDecimal - 1)
        EndIf
        ; Add seperators to integer value
        Local $aRes = DllCall("kernel32.dll", "int", "GetNumberFormatW", "int", 0x0400, "dword", 0, "wstr", $sInput, "ptr", 0, "ptr", 0, "int", 0)
        If @error Then Return
        Local $pBuffer = DllStructCreate("wchar[" & $aRes[0] + 1 & "]")
        $aRes = DllCall("kernel32.dll", "int", "GetNumberFormatW", "int", 0x0400, "dword", 0, "wstr", $sInput, "ptr", 0, "ptr", DllStructGetPtr($pBuffer), "int", $aRes[0])
        If @error Then Return
        $sOutput = StringTrimRight(DllStructGetData($pBuffer, 1), 3)
        ; Put separated data back into input
        If Number($sOutput) Then
            ; Add decimal digits if required
            If $sDecimal Then $sOutput &= $sDecimal
            GUICtrlSetData($hInput, $sOutput)
        Else
            GUICtrlSetData($hInput, "")
        EndIf
    EndIf

EndFunc;==>_WM_COMMAND

Edit: Even better IMO. ;)

; Credit to Valik for the DllCall lines

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <EditConstants.au3>

$hGUI = GUICreate("Test", 500, 500)

$hInput = GUICtrlCreateInput ("", 10,  20, 300, 20)

GuiSetState(@SW_SHOW)

GUIRegisterMsg($WM_COMMAND, "_WM_COMMAND")

While 1
    If GUIGetMsg() = $GUI_EVENT_CLOSE Then Exit
WEnd

Func _WM_COMMAND($hWnd, $iMsg, $wParam, $lParam)

    Local $iIDFrom = BitAND($wParam, 0xFFFF);LoWord
    Local $iCode = BitShift($wParam, 16)    ;HiWord
    Local $sDecimal = ""

    If $iIDFrom = $hInput And $iCode = $EN_CHANGE Then

        $sInput = GUICtrlRead($hInput)
        ; Check contents for invalid characters - only leave leading minus, digits and decimal points
        If StringRegExp($sInput, '[^\d.-]|([{0-9,1}^\A-])[^\d.]') Then $sInput = StringRegExpReplace($sInput, '[^\d.-]|([{0-9,1}^\A-])[^\d.]', '\1')
        ; Check for multiple decimals
        StringRegExpReplace($sInput, "\.", "")
        If @extended > 1 Then $sInput = StringMid($sInput, 1, StringInStr($sInput, ".", 0, -1) - 1)
        ; Check if only leading minus is present
        If $sInput = "-" Then Return
        ; If decimal point present strip decimal digits
        Local $iDecimal = StringInStr($sInput, ".")
        If $iDecimal Then
            $sDecimal = StringMid($sInput, $iDecimal)
            $sInput = StringMid($sInput, 1, $iDecimal - 1)
        EndIf
        ; Add seperators to integer value
        Local $aRes = DllCall("kernel32.dll", "int", "GetNumberFormatW", "int", 0x0400, "dword", 0, "wstr", $sInput, "ptr", 0, "ptr", 0, "int", 0)
        If @error Then Return
        Local $pBuffer = DllStructCreate("wchar[" & $aRes[0] + 1 & "]")
        $aRes = DllCall("kernel32.dll", "int", "GetNumberFormatW", "int", 0x0400, "dword", 0, "wstr", $sInput, "ptr", 0, "ptr", DllStructGetPtr($pBuffer), "int", $aRes[0])
        If @error Then Return
        $sOutput = StringTrimRight(DllStructGetData($pBuffer, 1), 3)
        ; Put separated data back into input
        If Number($sOutput) Then
            ; Add decimal digits if required
            If $sDecimal Then $sOutput &= $sDecimal
            GUICtrlSetData($hInput, $sOutput)
        Else
            GUICtrlSetData($hInput, "")
        EndIf
    EndIf

EndFunc;==>_WM_COMMAND
Edited by Melba23

Public_Domain.png.2d871819fcb9957cf44f4514551a2935.png Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind

Open spoiler to see my UDFs:

Spoiler

ArrayMultiColSort ---- Sort arrays on multiple columns
ChooseFileFolder ---- Single and multiple selections from specified path treeview listing
Date_Time_Convert -- Easily convert date/time formats, including the language used
ExtMsgBox --------- A highly customisable replacement for MsgBox
GUIExtender -------- Extend and retract multiple sections within a GUI
GUIFrame ---------- Subdivide GUIs into many adjustable frames
GUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView items
GUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeView
Marquee ----------- Scrolling tickertape GUIs
NoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxes
Notify ------------- Small notifications on the edge of the display
Scrollbars ----------Automatically sized scrollbars with a single command
StringSize ---------- Automatically size controls to fit text
Toast -------------- Small GUIs which pop out of the notification area

 

Link to comment
Share on other sites

problem with caret pos due to GUICtrlSetData

modified ... :)

seems like am becoming an expert into solving caret position problems.... rofl...

; Credit to Valik for the DllCall lines

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <EditConstants.au3>
#include <GuiEdit.au3>

$hGUI = GUICreate("Test", 500, 500)

$hInput = GUICtrlCreateInput("", 10, 20, 300, 20)

GUISetState(@SW_SHOW)

GUIRegisterMsg($WM_COMMAND, "_WM_COMMAND")

While 1
    If GUIGetMsg() = $GUI_EVENT_CLOSE Then Exit
WEnd

Func _WM_COMMAND($hWnd, $iMsg, $wParam, $lParam)

    Local $iIDFrom = BitAND($wParam, 0xFFFF);LoWord
    Local $iCode = BitShift($wParam, 16) ;HiWord
    Local $sDecimal = ""
    Local $col

    If $iIDFrom = $hInput And $iCode = $EN_CHANGE Then

        $sInput = GUICtrlRead($hInput)
        $col = ControlCommand("", "", $hInput, 'GetCurrentCol', '')
        $val_input_len_old = StringLen($sInput)
        ConsoleWrite($col & ' ')
        ; Check contents for invalid characters - only leave leading minus, digits and decimal points
        If StringRegExp($sInput, '[^\d.-]|([{0-9,1}^\A-])[^\d.]') Then $sInput = StringRegExpReplace($sInput, '[^\d.-]|([{0-9,1}^\A-])[^\d.]', '\1')
        ; Check for multiple decimals
        StringRegExpReplace($sInput, "\.", "")
        If @extended > 1 Then $sInput = StringMid($sInput, 1, StringInStr($sInput, ".", 0, -1) - 1)
        ; Check if only leading minus is present
        If $sInput = "-" Then Return
        ; If decimal point present strip decimal digits
        Local $iDecimal = StringInStr($sInput, ".")
        If $iDecimal Then
            $sDecimal = StringMid($sInput, $iDecimal)
            $sInput = StringMid($sInput, 1, $iDecimal - 1)
        EndIf
        ; Add seperators to integer value
        Local $aRes = DllCall("kernel32.dll", "int", "GetNumberFormatW", "int", 0x0400, "dword", 0, "wstr", $sInput, "ptr", 0, "ptr", 0, "int", 0)
        If @error Then Return
        Local $pBuffer = DllStructCreate("wchar[" & $aRes[0] + 1 & "]")
        $aRes = DllCall("kernel32.dll", "int", "GetNumberFormatW", "int", 0x0400, "dword", 0, "wstr", $sInput, "ptr", 0, "ptr", DllStructGetPtr($pBuffer), "int", $aRes[0])
        If @error Then Return
        $sOutput = StringTrimRight(DllStructGetData($pBuffer, 1), 3)
        ; Put separated data back into input
        If Number($sOutput) Then
            ; Add decimal digits if required
            If $sDecimal Then $sOutput &= $sDecimal
            GUICtrlSetData($hInput, $sOutput)
        Else
            GUICtrlSetData($hInput, "")
        EndIf
        $val_input_len_new = StringLen(GUICtrlRead($hInput))
        If $val_input_len_new - $val_input_len_old == 0 Then
            _GUICtrlEdit_SetSel($hInput, $col-1, $col-1)
        ElseIf $val_input_len_new - $val_input_len_old == 1 Then
            _GUICtrlEdit_SetSel($hInput, $col , $col )
        EndIf
    EndIf

EndFunc   ;==>_WM_COMMAND
Edited by deltarocked
Link to comment
Share on other sites

  • Moderators

deltarocked,

I see you have already posted a solution - here is mine: :)

; Credit to Valik for the DllCall lines

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <EditConstants.au3>

Global $hGUI = GUICreate("Test", 500, 500)

Global $hInput = GUICtrlCreateInput ("", 10,  20, 300, 20)

GuiSetState(@SW_SHOW)

GUIRegisterMsg($WM_COMMAND, "_WM_COMMAND")

While 1
    If GUIGetMsg() = $GUI_EVENT_CLOSE Then Exit
WEnd

Func _WM_COMMAND($hWnd, $iMsg, $wParam, $lParam)

    #forceref $hWnd, $iMsg, $lParam

    Local $iIDFrom = BitAND($wParam, 0xFFFF);LoWord
    Local $iCode = BitShift($wParam, 16)    ;HiWord
    Local $sDecimal = ""

    If $iIDFrom = $hInput And $iCode = $EN_CHANGE Then

        ; Get caret position
        Local $tCaret = DllStructCreate("uint")
        GUICtrlSendMsg($hInput, $EM_GETSEL, DllStructGetPtr($tCaret), DllStructGetPtr($tCaret))
        Local $iCaret = DllStructGetData($tCaret, 1)
        ; Read input
        Local $sInput = GUICtrlRead($hInput)
        ; Determine digits to left of cursor
        Local $sLeadIn = StringReplace(StringLeft($sInput, $iCaret), ",", "")
        ; Check contents for invalid characters - only leave leading minus, digits and decimal points
        If StringRegExp($sInput, '[^\d.-]|([{0-9,1}^\A-])[^\d.]') Then $sInput = StringRegExpReplace($sInput, '[^\d.-]|([{0-9,1}^\A-])[^\d.]', '\1')
        ; Check for multiple decimals
        StringRegExpReplace($sInput, "\.", "")
        If @extended > 1 Then $sInput = StringMid($sInput, 1, StringInStr($sInput, ".", 0, -1) - 1)
        ; Check if only leading minus is present
        If $sInput = "-" Then Return
        ; If decimal point present strip decimal digits
        Local $iDecimal = StringInStr($sInput, ".")
        If $iDecimal Then
            $sDecimal = StringMid($sInput, $iDecimal)
            $sInput = StringMid($sInput, 1, $iDecimal - 1)
        EndIf
        ; Add seperators to integer value
        Local $aRes = DllCall("kernel32.dll", "int", "GetNumberFormatW", "int", 0x0400, "dword", 0, "wstr", $sInput, "ptr", 0, "ptr", 0, "int", 0)
        If @error Then Return
        Local $pBuffer = DllStructCreate("wchar[" & $aRes[0] + 1 & "]")
        $aRes = DllCall("kernel32.dll", "int", "GetNumberFormatW", "int", 0x0400, "dword", 0, "wstr", $sInput, "ptr", 0, "ptr", DllStructGetPtr($pBuffer), "int", $aRes[0])
        If @error Then Return
        Local $sOutput = StringTrimRight(DllStructGetData($pBuffer, 1), 3)
        ; Put separated data back into input
        If Number($sOutput) Then
            ; Add decimal digits if required
            If $sDecimal Then $sOutput &= $sDecimal
            GUICtrlSetData($hInput, $sOutput)
        Else
            GUICtrlSetData($hInput, "")
        EndIf
        ; Reset caret
        Local $j = 1
        For $i = 1 To StringLen($sOutput)
            If StringMid($sOutput, $i, 1) = StringMid($sLeadIn, $j, 1) Then
                $j += 1
                If $j > StringLen($sLeadIn) Then ExitLoop
            EndIf
        Next
        If StringMid($sOutput, $i, 1) = "," Then $i += 1
        GUICtrlSendMsg($hInput, $EM_SETSEL, $i, $i)

    EndIf

EndFunc;==>_WM_COMMAND

M23

Public_Domain.png.2d871819fcb9957cf44f4514551a2935.png Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind

Open spoiler to see my UDFs:

Spoiler

ArrayMultiColSort ---- Sort arrays on multiple columns
ChooseFileFolder ---- Single and multiple selections from specified path treeview listing
Date_Time_Convert -- Easily convert date/time formats, including the language used
ExtMsgBox --------- A highly customisable replacement for MsgBox
GUIExtender -------- Extend and retract multiple sections within a GUI
GUIFrame ---------- Subdivide GUIs into many adjustable frames
GUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView items
GUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeView
Marquee ----------- Scrolling tickertape GUIs
NoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxes
Notify ------------- Small notifications on the edge of the display
Scrollbars ----------Automatically sized scrollbars with a single command
StringSize ---------- Automatically size controls to fit text
Toast -------------- Small GUIs which pop out of the notification area

 

Link to comment
Share on other sites

deltarocked,

I see you have already posted a solution - here is mine: :)

M23

but with all this am still unable to find a solution for the damn firefox and its ever persistent ole objects. any leads?

GUICtrlSendMsg($hInput, $EM_SETSEL, $i, $i) --> I was searching for this .... M23 gr8... thx...

Edited by deltarocked
Link to comment
Share on other sites

michaelslamet,

That was fun! :idiot:

; Credit to Valik for the DllCall lines

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <EditConstants.au3>

$hGUI = GUICreate("Test", 500, 500)

$hInput = GUICtrlCreateInput ("", 10,  20, 300, 20)

GuiSetState(@SW_SHOW)

GUIRegisterMsg($WM_COMMAND, "_WM_COMMAND")

While 1
    If GUIGetMsg() = $GUI_EVENT_CLOSE Then Exit
WEnd

Func _WM_COMMAND($hWnd, $iMsg, $wParam, $lParam)

    Local $iIDFrom = BitAND($wParam, 0xFFFF);LoWord
    Local $iCode = BitShift($wParam, 16)    ;HiWord
    Local $sDecimal = ""

    If $iIDFrom = $hInput And $iCode = $EN_CHANGE Then

        $sInput = GUICtrlRead($hInput)
        ; Check contents for invalid characters - only leave leading minus, digits and a decimal point
        If StringRegExp($sInput, '[^\d.-]|([{0-9,1}^\A-])[^\d.]') Then $sInput = StringRegExpReplace($sInput, '[^\d.-]|([{0-9,1}^\A-])[^\d.]', '\1')
        ; Check if only leadign minus is present
        If $sInput = "-" Then Return
        ; If decimal point present strip decimal digits
        Local $iDecimal = StringInStr($sInput, ".")
        If $iDecimal Then
            $sDecimal = StringMid($sInput, $iDecimal)
            $sInput = StringMid($sInput, 1, $iDecimal - 1)
        EndIf
        ; Add seperators to integer value
        Local $aRes = DllCall("kernel32.dll", "int", "GetNumberFormatW", "int", 0x0400, "dword", 0, "wstr", $sInput, "ptr", 0, "ptr", 0, "int", 0)
        If @error Then Return
        Local $pBuffer = DllStructCreate("wchar[" & $aRes[0] + 1 & "]")
        $aRes = DllCall("kernel32.dll", "int", "GetNumberFormatW", "int", 0x0400, "dword", 0, "wstr", $sInput, "ptr", 0, "ptr", DllStructGetPtr($pBuffer), "int", $aRes[0])
        If @error Then Return
        $sOutput = StringTrimRight(DllStructGetData($pBuffer, 1), 3)
        ; Put separated data back into input
        If Number($sOutput) Then
            ; Add decimal digits if required
            If $sDecimal Then $sOutput &= $sDecimal
            GUICtrlSetData($hInput, $sOutput)
        Else
            GUICtrlSetData($hInput, "")
        EndIf
    EndIf

EndFunc;==>_WM_COMMAND

I think I have covered all the bases - it works for positive and negative numbers, integer or decimal and you can modify the integer part even if the decimal part already exists. ;)

M23

Hi M23,

Thanks a lot for your reply.

It works perfectly as I try, but you're so advance and now I confuse how to integrate this into my code :)) haha

Link to comment
Share on other sites

  • Moderators

michaelslamet,

If you post the code I can help. :)

M23

Public_Domain.png.2d871819fcb9957cf44f4514551a2935.png Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind

Open spoiler to see my UDFs:

Spoiler

ArrayMultiColSort ---- Sort arrays on multiple columns
ChooseFileFolder ---- Single and multiple selections from specified path treeview listing
Date_Time_Convert -- Easily convert date/time formats, including the language used
ExtMsgBox --------- A highly customisable replacement for MsgBox
GUIExtender -------- Extend and retract multiple sections within a GUI
GUIFrame ---------- Subdivide GUIs into many adjustable frames
GUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView items
GUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeView
Marquee ----------- Scrolling tickertape GUIs
NoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxes
Notify ------------- Small notifications on the edge of the display
Scrollbars ----------Automatically sized scrollbars with a single command
StringSize ---------- Automatically size controls to fit text
Toast -------------- Small GUIs which pop out of the notification area

 

Link to comment
Share on other sites

@M23

Hmmmmm. Did we forget about that UDF that was removed?

It's still available here

Scroll down to _StringAddThousandsSep() but read the Notes section of the header.

George

Question about decompiling code? Read the decompiling FAQ and don't bother posting the question in the forums.

Be sure to read and follow the forum rules. -AKA the AutoIt Reading and Comprehension Skills test.***

The PCRE (Regular Expression) ToolKit for AutoIT - (Updated Oct 20, 2011 ver:3.0.1.13) - Please update your current version before filing any bug reports. The installer now includes both 32 and 64 bit versions. No change in version number.

Visit my Blog .. currently not active but it will soon be resplendent with news and views. Also please remove any links you may have to my website. it is soon to be closed and replaced with something else.

"Old age and treachery will always overcome youth and skill!"

Link to comment
Share on other sites

  • Moderators

George,

Does not handle decimals or a leading minus as far as I can see - so I will stick with mine! :)

M23

Public_Domain.png.2d871819fcb9957cf44f4514551a2935.png Any of my own code posted anywhere on the forum is available for use by others without any restriction of any kind

Open spoiler to see my UDFs:

Spoiler

ArrayMultiColSort ---- Sort arrays on multiple columns
ChooseFileFolder ---- Single and multiple selections from specified path treeview listing
Date_Time_Convert -- Easily convert date/time formats, including the language used
ExtMsgBox --------- A highly customisable replacement for MsgBox
GUIExtender -------- Extend and retract multiple sections within a GUI
GUIFrame ---------- Subdivide GUIs into many adjustable frames
GUIListViewEx ------- Insert, delete, move, drag, sort, edit and colour ListView items
GUITreeViewEx ------ Check/clear parent and child checkboxes in a TreeView
Marquee ----------- Scrolling tickertape GUIs
NoFocusLines ------- Remove the dotted focus lines from buttons, sliders, radios and checkboxes
Notify ------------- Small notifications on the edge of the display
Scrollbars ----------Automatically sized scrollbars with a single command
StringSize ---------- Automatically size controls to fit text
Toast -------------- Small GUIs which pop out of the notification area

 

Link to comment
Share on other sites

yes it does

Edit:

Actually I'll have to play to test it but I thing an srer will do it too.

Edited by GEOSoft

George

Question about decompiling code? Read the decompiling FAQ and don't bother posting the question in the forums.

Be sure to read and follow the forum rules. -AKA the AutoIt Reading and Comprehension Skills test.***

The PCRE (Regular Expression) ToolKit for AutoIT - (Updated Oct 20, 2011 ver:3.0.1.13) - Please update your current version before filing any bug reports. The installer now includes both 32 and 64 bit versions. No change in version number.

Visit my Blog .. currently not active but it will soon be resplendent with news and views. Also please remove any links you may have to my website. it is soon to be closed and replaced with something else.

"Old age and treachery will always overcome youth and skill!"

Link to comment
Share on other sites

  • Moderators

This is something I've worked on for myself in the past.

I'm partial to _StringAddThousandsSep() for obvious reasons, but particularly because I like being able to utilize the locale for other languages.

Anyway, here's a scaled down version of how I use mine.

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <GUIEdit.au3>

; do whatever locale func you want to figure out the real ones automagically
Global $gs_thoussep = ","
Global $gs_decsep = "."

Global $gh_gui = GUICreate("MyGUI", 200, 150)
Global $gi_input = GUICtrlCreateInput("", 50, 65, 100, 20)
Global $gh_input = GUICtrlGetHandle($gi_input)

GUIRegisterMsg($WM_COMMAND, "_WM_COMMAND")
GUISetState()

While GUIGetMsg() <> -3
WEnd

Func _WM_COMMAND($h_wnd, $i_msg, $w_param, $l_param)
    #forceref $h_wnd, $i_msg, $w_param, $l_param

    Local $n_notify_code = BitShift($w_param, 16)
    Local $n_id = BitAND($w_param, 0x0000FFFF)

    Switch $l_param
        Case $gh_input
            Switch $n_notify_code
                Case $EN_CHANGE
                    Return _Edit_FormatNumberByThousand($l_param)
            EndSwitch
    EndSwitch

    Return $GUI_RUNDEFMSG
EndFunc

Func _Edit_FormatNumberByThousand($h_ctrl)

    Local $s_change_text, $i_str_len, $f_dec

    Local $s_input_text = _GUICtrlEdit_GetText($h_ctrl)
    Local $i_input_len = StringLen($s_input_text)

    If $s_input_text Then
        $s_input_text = StringRegExpReplace($s_input_text, "(^-|\d+|\" & $gs_decsep & ")|(\D)", "$1")
        If StringInStr($s_input_text, $gs_decsep, 1, 2) Then
            $s_input_text = StringTrimRight($s_input_text, 1)
        EndIf
        If StringLen($s_input_text) = 0 Then
            _GUICtrlEdit_SetText($h_ctrl, "")
        ElseIf $s_input_text = "-" Then
            _GUICtrlEdit_SetText($h_ctrl, $s_input_text)
            _GUICtrlEdit_SetSel($h_ctrl, 1, 1)
        Else
            If StringRight($s_input_text, 1) = $gs_decsep Then $f_dec = True
            $s_change_text = __StringAddThousandsSep($s_input_text)
            If $f_dec Then $s_change_text &= $gs_decsep
            $i_str_len = StringLen($s_change_text)
            _GUICtrlEdit_SetText($h_ctrl, $s_change_text)
            _GUICtrlEdit_SetSel($h_ctrl, $i_str_len, $i_str_len)
        EndIf
    EndIf

    Return $GUI_RUNDEFMSG
EndFunc

Func __StringAddThousandsSep($s_string, $i_convert_lcid = -1, $i_current_lcid = -1)

    If $i_current_lcid = -1 Or $i_current_lcid = Default Then $i_current_lcid = 0x0400
    If $i_convert_lcid = -1 Or $i_convert_lcid = Default Then $i_convert_lcid = 0x0400

   ; Get lcid decimal and thousands separators
    Local $t_buff_tmp = DllStructCreate("char[4]")
    DllCall("kernel32.dll", "int", "GetLocaleInfo", "int", $i_current_lcid, _
        "int", 0x0E, "ptr", DllStructGetPtr($t_buff_tmp), "int", 4)
    If @error Then Return SetError(1, 0, "")
    Local $s_cur_dec = DllStructGetData($t_buff_tmp, 1)

    DllCall("kernel32.dll", "int", "GetLocaleInfo", "int", $i_convert_lcid, _
        "int", 0x0E, "ptr", DllStructGetPtr($t_buff_tmp), "int", 4)
    If @error Then Return SetError(1, 0, "")
    Local $s_con_dec = DllStructGetData($t_buff_tmp, 1)

    DllCall("kernel32.dll", "int", "GetLocaleInfo", "int", $i_convert_lcid, _
        "int", 0x0F, "ptr", DllStructGetPtr($t_buff_tmp), "int", 4)
    If @error Then Return SetError(1, 0, "")
    Local $s_con_tho = DllStructGetData($t_buff_tmp, 1)

   ; For later formatting
    Local $i_number = StringRegExpReplace($s_string, "(\" & $s_cur_dec & "\d+\z)|(^-|\d+)|(\D)", "$2")
    Local $i_dec = StringRegExpReplace($s_string, "(.+?\" & $s_cur_dec & ")(\d+\z)", "$2")
    If @extended = 0 Then $i_dec = ""

    Local $i_str_len = StringLen($s_string) * 4
    Local $t_numberfmt = DllStructCreate("uint;uint;uint;ptr;ptr;uint")
    Local $t_thousands = DllStructCreate("wchar[2]")
    Local $t_decimal = DllStructCreate("wchar[2]")
    Local $t_buffer = DllStructCreate("wchar[" & $i_str_len & "]")

    DllStructSetData($t_thousands, 1, $s_con_tho)
    DllStructSetData($t_decimal, 1, $s_con_dec)
    DllStructSetData($t_numberfmt, 3, 3)
    DllStructSetData($t_numberfmt, 4, DllStructGetPtr($t_decimal))
    DllStructSetData($t_numberfmt, 5, DllStructGetPtr($t_thousands))
    DllStructSetData($t_numberfmt, 6, 1)

    DllCall("kernel32.dll", "int", "GetNumberFormatW", _
        "int", $i_convert_lcid, "int", 0, _
        "wstr", $i_number, "ptr", DllStructGetPtr($t_numberfmt), _
        "ptr", DllStructGetPtr($t_buffer), "int", $i_str_len)

    If $i_dec = "" Then $s_con_dec = ""
    Return DllStructGetData($t_buffer, 1) & $s_con_dec & $i_dec
EndFunc

I hadn't really gone over the other entries, but if M23's works, it is probably something similar or along the same lines.

Edited by SmOke_N

Common sense plays a role in the basics of understanding AutoIt... If you're lacking in that, do us all a favor, and step away from the computer.

Link to comment
Share on other sites

  • 4 years later...

Thanks for all your examples. I've been using the search and trying to use your code but I'm not able to perform a simple real time number operation :'(

This is a reduced copy of my code:

#include <WindowsConstants.au3>
#include <GUIConstants.au3>

Global $mainGUI = GUICreate("", 410, 75, -1, -1)
GUISetState(@SW_SHOW, $mainGUI)
WinSetOnTop($mainGUI, "", 1)

GUICtrlCreateLabel("Quantity at morning",5,8,130,33,$ES_CENTER)
Local $firstnumber = GUICtrlCreateInput("", 5, 30, 130, 35, BitOR($ES_NUMBER, $ES_CENTER))
GUICtrlSetFont(-1, 16, 700)
GUICtrlCreateLabel("Quantity at night",140,8,130,33,$ES_CENTER)
Local $secondnumber = GUICtrlCreateInput("", 140, 30, 130, 35, BitOR($ES_NUMBER, $ES_CENTER))
GUICtrlSetFont(-1, 16, 700)
GUICtrlCreateLabel("Pieces produced today",275,8,130,33,$ES_CENTER)
Local $lastnumber = GUICtrlCreateInput("", 275, 30, 130, 35, BitOR($ES_NUMBER, $ES_CENTER))
GUICtrlSetFont(-1, 16, 700)

GUIRegisterMsg($WM_COMMAND, "_WM_COMMAND")


While 1
    $msg = GUIGetMsg()

    Switch $msg
        Case $GUI_EVENT_CLOSE
            Exit

    EndSwitch

WEnd



Func _WM_COMMAND($hWnd, $iMsg, $wParam, $lParam)

    Local $iIDFrom = BitAND($wParam, 0xFFFF);LoWord
    Local $iCode = BitShift($wParam, 16) ;HiWord
    Local $sDecimal = ""


    If $iIDFrom = $firstnumber And $iCode = $EN_CHANGE Then
        $sInput = GUICtrlRead($firstnumber)
        Local $Output = _StringAddThousandsSep($sInput)
        GUICtrlSetData($firstnumber, $Output)
    EndIf

    If $iIDFrom = $secondnumber And $iCode = $EN_CHANGE Then
        $sInput = GUICtrlRead($secondnumber)
        Local $Output = _StringAddThousandsSep($sInput)
        GUICtrlSetData($secondnumber, $Output)
        If GUICtrlRead($firstnumber) <> "" Then
            $first = GUICtrlRead($firstnumber)
            StringRegExpReplace($first, ".", ""); I remove the thousand separator from the string
            $second = GUICtrlRead($secondnumber)
            StringRegExpReplace($second, ".", "")
            $diff = Number($second) - Number($first)
            Local $Output = _StringAddThousandsSep($diff)
            GUICtrlSetData($lastnumber, $Output)
        EndIf
    EndIf

    If $iIDFrom = $lastnumber And $iCode = $EN_CHANGE Then
        $sInput = GUICtrlRead($lastnumber)
        Local $Output = _StringAddThousandsSep($sInput)
        GUICtrlSetData($lastnumber, $Output)
    EndIf

EndFunc   ;==>_WM_COMMAND


Func _StringAddThousandsSep($s_string, $i_convert_lcid = -1, $i_current_lcid = -1)
    ; $LOCALE_USER_DEFAULT = 0x0400
    If $i_current_lcid = -1 Or $i_current_lcid = Default Then $i_current_lcid = 0x0400
    If $i_convert_lcid = -1 Or $i_convert_lcid = Default Then $i_convert_lcid = 0x0400

    ; Get lcid decimal and thousands separators
    Local $t_buff_tmp = DllStructCreate("char[4]")
    DllCall("kernel32.dll", "int", "GetLocaleInfo", "int", $i_current_lcid, _
            "int", 0x0E, "ptr", DllStructGetPtr($t_buff_tmp), "int", 4)
    If @error Then Return SetError(1, 0, "")
    Local $s_cur_dec = DllStructGetData($t_buff_tmp, 1)

    DllCall("kernel32.dll", "int", "GetLocaleInfo", "int", $i_convert_lcid, _
            "int", 0x0E, "ptr", DllStructGetPtr($t_buff_tmp), "int", 4)
    If @error Then Return SetError(1, 0, "")
    Local $s_con_dec = DllStructGetData($t_buff_tmp, 1)

    DllCall("kernel32.dll", "int", "GetLocaleInfo", "int", $i_convert_lcid, _
            "int", 0x0F, "ptr", DllStructGetPtr($t_buff_tmp), "int", 4)
    If @error Then Return SetError(1, 0, "")
    Local $s_con_tho = DllStructGetData($t_buff_tmp, 1)

    ; For later formatting
    Local $i_number = StringRegExpReplace($s_string, "(\" & $s_cur_dec & "\d+\z)|(^-|\d+)|(\D)", "$2")
    Local $i_dec = StringRegExpReplace($s_string, "(.+?\" & $s_cur_dec & ")(\d+\z)", "$2")
    If @extended = 0 Then $i_dec = ""

    Local $i_str_len = StringLen($s_string) * 4
    Local $t_numberfmt = DllStructCreate("uint;uint;uint;ptr;ptr;uint")
    Local $t_thousands = DllStructCreate("wchar[2]")
    Local $t_decimal = DllStructCreate("wchar[2]")
    Local $t_buffer = DllStructCreate("wchar[" & $i_str_len & "]")

    DllStructSetData($t_thousands, 1, $s_con_tho)
    DllStructSetData($t_decimal, 1, $s_con_dec)
    DllStructSetData($t_numberfmt, 3, 3)
    DllStructSetData($t_numberfmt, 4, DllStructGetPtr($t_decimal))
    DllStructSetData($t_numberfmt, 5, DllStructGetPtr($t_thousands))
    DllStructSetData($t_numberfmt, 6, 1)

    DllCall("kernel32.dll", "int", "GetNumberFormatW", _
            "int", $i_convert_lcid, "int", 0, _
            "wstr", $i_number, "ptr", DllStructGetPtr($t_numberfmt), _
            "ptr", DllStructGetPtr($t_buffer), "int", $i_str_len)

    If $i_dec = "" Then $s_con_dec = ""
    Return DllStructGetData($t_buffer, 1) & $s_con_dec & $i_dec
EndFunc   ;==>_StringAddThousandsSep

My problem is that I'm trying to update the value of some inputs to add the thousand separator as I type into they, and also perform a simple sum. But the results are:

 

1.png

But for big quantities:

2.png

 

Of all the tests that I've done with the results got searching this is the only one that works fine for me with quantities like 100.000 and 1.000.000

I'm not going to use decimal places or negative values. My goal is to automatize the data recollection in our job. I want to use the point (".") as thousand separator.

I've tried to change the value of $i_convert_lcid = 0x0400 to spanish values and the result wans't better.

Any help or tip would be pretty apreciatted.

 

Greets from Barcelona

 

Edit: I'm going to create a new thread as my problem is different from what the OP was asking.

Edited by Qwerty212
Link to comment
Share on other sites

Melba,
Your code doesn't allow  0.25  :)

Here is some regex fun

; https://www.autoitscript.com/forum/topic/170558-guictrlcreateinput-to-accept-only-formattted-numbers/

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>
#include <EditConstants.au3>
Opt("GUIOnEventMode", 1)

$hGUI = GUICreate("Currency Decimal Separator", 232, 90)
$Label = GUICtrlCreateLabel("Enter some numbers", 22, 8, 163, 17)
$input = GUICtrlCreateInput("", 22, 30, 165, 24)
GUICtrlSetLimit(-1, 19)
GUICtrlSetFont(-1, 12)
GUISetState()

GUIRegisterMsg($WM_COMMAND, '_WM_COMMAND')
GUISetOnEvent($GUI_EVENT_CLOSE, "_Exit")

While Sleep(1000)
WEnd

Func _Exit()
    GUIDelete()
    Exit
EndFunc

Func _WM_COMMAND($hWnd, $Msg, $wParam, $lParam)
 Local $id = BitAND($wParam, 0x0000FFFF)
 Local $code = BitShift($wParam, 16)
   If $id = $input AND $code = $EN_UPDATE Then
        GUICtrlSetData($input, _FormatInputNumber(GUICtrlRead($input)))
    EndIf
    Return $GUI_RUNDEFMSG
EndFunc

Func _FormatInputNumber($iNumber, $sSep = ",", $sDec = ".", $iDecPlace = 2)
    $iNumber = StringRegExpReplace(StringRegExpReplace(StringRegExpReplace($iNumber, "[^0-9" & $sDec & "-]", ""), '(?<!^)-|(^-?0)\K0|^-?\K0(?=[^0' & $sSep & '])', ""), '^(-?)\Q' & $sDec & '\E', "${1}0" & $sDec)
    Local $s = StringSplit(StringReplace($iNumber, $sSep, ""), $sDec)
    Return StringRegExpReplace($s[1], '(?<=\d)(?=(\d{3})+$)', $sSep) & (($s[0] = 1) ? "" : $sDec & StringLeft($s[2], $iDecPlace)) 
EndFunc

Easily adaptable for european number format
It handles leading minus and ALL decimals - theorically  :D

Edit
Damn I didn't pay attention to the date of this topic...

Edited by mikell
Link to comment
Share on other sites

  • 9 months later...

Hey mikell,

thanks a lot for the code, integrates nicely in my little project!

Unfortunately, I'm still trying to find my way around AutoIt and that RegEx magic is beyond me as well. May I ask how I could deny negativ numbers and force cents for a price? For example, user enters 1 and hits tab, it changes to 1.00, enters 3.5 and it changes to 3.50 etc.

Any help is greatly appreciated! :)

Cheers,

Noodles

Link to comment
Share on other sites

Please try this   :)
You will need to declare the thousands and decimal separators as global vars at the top of the script
This code uses a button, to make it work with TAB key just have a look at GUISetAccelerators in the help file

#include <GUIConstantsEx.au3>
#include <WindowsConstants.au3>

Opt("GUIOnEventMode", 1)

Global $sSep = ".", $sDec = ","

$hGUI = GUICreate("Currency Decimal Separator", 232, 90)
$Label = GUICtrlCreateLabel("Enter some numbers", 22, 8, 163, 17)
$input = GUICtrlCreateInput("", 22, 30, 165, 24)
GUICtrlSetLimit(-1, 19)
GUICtrlSetFont(-1, 12)
$btn = GUICtrlCreateButton("format cents", 22, 60, 80, 22)
GUICtrlSetOnEvent(-1, "_format_cents")
GUISetState()

GUIRegisterMsg($WM_COMMAND, '_WM_COMMAND')
GUISetOnEvent($GUI_EVENT_CLOSE, "_Exit")

While Sleep(10)
WEnd


Func _WM_COMMAND($hWnd, $Msg, $wParam, $lParam)
    If BitAND($wParam, 0x0000FFFF) = $input Then
        GUICtrlSetData($input, _FormatInputNumber(GUICtrlRead($input)))
    EndIf
    Return $GUI_RUNDEFMSG
EndFunc

Func _FormatInputNumber($iNumber)
  $iNumber = StringRegExpReplace(StringRegExpReplace($iNumber, '^' & $sDec, "0" & $sDec), "[^0-9" & $sDec & "]", "")
  Local $s = StringSplit(StringReplace($iNumber, $sSep, ""), $sDec)
  Return StringRegExpReplace($s[1], '(?<=\d)(?=(\d{3})+$)', $sSep) & (($s[0] = 1) ? "" : $sDec & StringLeft($s[2], 2))
EndFunc

Func _format_cents()
  Local $s = StringSplit(GUICtrlRead($input), $sDec)
  GUICtrlSetData($input, $s[1] & $sDec & (($s[0] = 1) ? "00" : StringTrimLeft(StringFormat("%2f", "." & $s[2]), 2)))
EndFunc

Func _Exit()
    Exit
EndFunc

 

Edited by mikell
Link to comment
Share on other sites

This is awesome, thanks much for helping out - that code works beautifully! :)

I'll leave a note as soon as I've managed to figure out the completion upon tabbing out, thanks for the hint regarding GUISetAccelerators, I don't think I'd have found that connection either. Much left to learn. :P

Link to comment
Share on other sites

Create an account or sign in to comment

You need to be a member in order to leave a comment

Create an account

Sign up for a new account in our community. It's easy!

Register a new account

Sign in

Already have an account? Sign in here.

Sign In Now
 Share

  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...