Seite 1 von 2

Mit StringGadget Kommazahl einlesen

Verfasst: 10.02.2013 18:57
von marcelx
Hallo,

ich möchte mit StringGadget Kommazahl einlesen.
Im CodeArchiv/Gadgets/StringGadget/ habe ich StringGadget_Numeric.pb gefunden.
Gibt es so was für Kommazahlen (einlesen von z.B. 0,99 oder 123 oder 123,9) ?

Danke und Gruß
MarceX

Re: Mit StringGadget Kommazahl einlesen

Verfasst: 10.02.2013 19:20
von RSBasic

Re: Mit StringGadget Kommazahl einlesen

Verfasst: 10.02.2013 19:21
von ts-soft
Der Code im CodeArchiv hat eher nichts mit Deiner Frage zu tun, jedenfalls sehe ich da den Zusammenhang nicht.

Hier ein Beispiel (Windows-Only), das nur die Zahlen, sowie das Komma akzeptieren.
Achtung: Das Komma wird auch mehrfach akzeptiert. Wenn das nicht gewünscht ist, sind noch
Erweiterungen notwendig.

Code: Alles auswählen

EnableExplicit

Procedure cbStringGadget(hWnd, uMsg, wParam, lParam)
  Protected oldproc = GetProp_(hWnd, "oldproc")
 
  Select uMsg
    Case #WM_NCDESTROY
      RemoveProp_(hWnd, "oldproc")
    Case #WM_CHAR
      Select wParam
        Case 48 To 57, 44 ; 0 - 9, komma
        Default
          ProcedureReturn 0 ; kein gültiges Zeichen
      EndSelect
  EndSelect
  
  ProcedureReturn CallWindowProc_(oldproc, hWnd, uMsg, wParam, lParam)
EndProcedure

Procedure SubClassStringGadget(ID)
  Protected oldproc = SetWindowLongPtr_(GadgetID(ID), #GWL_WNDPROC, @cbStringGadget())
  ProcedureReturn SetProp_(GadgetID(ID), "oldproc", oldproc)
EndProcedure

OpenWindow(0, #PB_Ignore, #PB_Ignore, 250, 80, "")
StringGadget(0, 10, 10, 200, 20, "")
SubClassStringGadget(0)
Repeat
  Select WaitWindowEvent()
    Case #PB_Event_CloseWindow
      Break
  EndSelect
ForEver
Gruß
Thomas

Re: Mit StringGadget Kommazahl einlesen

Verfasst: 10.02.2013 19:47
von marcelx
Danke RSBasic und ts-soft

damit kann ich schon was anfangen

Re: Mit StringGadget Kommazahl einlesen

Verfasst: 10.02.2013 19:56
von ts-soft
Hab mal so erweitert, das Backspace funktioniert und das Komma nur einmal eingegeben werden kann:

Code: Alles auswählen

EnableExplicit

Procedure cbStringGadget(hWnd, uMsg, wParam, lParam)
  Protected oldproc = GetProp_(hWnd, "oldproc")
 
  Select uMsg
    Case #WM_NCDESTROY
      RemoveProp_(hWnd, "oldproc")
    Case #WM_CHAR
      Select wParam
        Case '0' To '9', #VK_BACK
        Case ','
          If CountString(GetGadgetText(GetProp_(hWnd, "PB_ID")), ",")
            ProcedureReturn 0
          EndIf
        Default
          ProcedureReturn 0 ; kein gültiges Zeichen
      EndSelect
  EndSelect
 
  ProcedureReturn CallWindowProc_(oldproc, hWnd, uMsg, wParam, lParam)
EndProcedure

Procedure SubClassStringGadget(ID)
  Protected oldproc = SetWindowLongPtr_(GadgetID(ID), #GWL_WNDPROC, @cbStringGadget())
  ProcedureReturn SetProp_(GadgetID(ID), "oldproc", oldproc)
EndProcedure

OpenWindow(0, #PB_Ignore, #PB_Ignore, 250, 80, "")
StringGadget(0, 10, 10, 200, 20, "")
SubClassStringGadget(0)
Repeat
  Select WaitWindowEvent()
    Case #PB_Event_CloseWindow
      Break
  EndSelect
ForEver 
Ich hoffe, ich habe nicht noch mehr übersehen :)

Re: Mit StringGadget Kommazahl einlesen

Verfasst: 10.02.2013 20:11
von marcelx
So funktioniert es.

Was ich haben wollte, ist die Eingabe wie z.B. -123 (negative Werte) 123,56 (positive Werte mit maximale 2 Stellen nach den Komma)

Mit diese Basis kann ich (denke ich) was anfangen.

Re: Mit StringGadget Kommazahl einlesen

Verfasst: 10.02.2013 20:20
von ts-soft
Naja, bin mir nicht so sicher ob Du das packst und wenn ich gerade bei bin :wink:

Code: Alles auswählen

EnableExplicit

Procedure cbStringGadget(hWnd, uMsg, wParam, lParam)
  Protected oldproc = GetProp_(hWnd, "oldproc")
 
  Select uMsg
    Case #WM_NCDESTROY
      RemoveProp_(hWnd, "oldproc")
    Case #WM_CHAR
      Select wParam
        Case '0' To '9', #VK_BACK
        Case '-'
          If CountString(GetGadgetText(GetProp_(hWnd, "PB_ID")), "-")
            ProcedureReturn 0
          EndIf
          SetGadgetText(GetProp_(hWnd, "PB_ID"), "-" +   GetGadgetText(GetProp_(hWnd, "PB_ID")))
          ProcedureReturn 0  
        Case ','
          If CountString(GetGadgetText(GetProp_(hWnd, "PB_ID")), ",")
            ProcedureReturn 0
          EndIf
        Default
          ProcedureReturn 0 ; kein gültiges Zeichen
      EndSelect
  EndSelect
 
  ProcedureReturn CallWindowProc_(oldproc, hWnd, uMsg, wParam, lParam)
EndProcedure

Procedure SubClassStringGadget(ID)
  Protected oldproc = SetWindowLongPtr_(GadgetID(ID), #GWL_WNDPROC, @cbStringGadget())
  ProcedureReturn SetProp_(GadgetID(ID), "oldproc", oldproc)
EndProcedure

OpenWindow(0, #PB_Ignore, #PB_Ignore, 250, 80, "")
StringGadget(0, 10, 10, 200, 20, "")
SubClassStringGadget(0)
Repeat
  Select WaitWindowEvent()
    Case #PB_Event_CloseWindow
      Break
  EndSelect
ForEver 
Es kann nur einmal minus eingefügt werde und dieses wird auch gleich an den Anfang gerückt.

Man könnte auch auf Len(...) = 0 prüfen und nur dann das - zulassen. Ist vielleicht etwas irritierend,
wenn ein Minus an den Anfang rückt :mrgreen:

Re: Mit StringGadget Kommazahl einlesen

Verfasst: 10.02.2013 20:39
von Danilo
Oder mit regulären Ausdrücken prüfen:

Code: Alles auswählen

;
; by Danilo
;
; http://www.purebasic.fr/german/viewtopic.php?f=16&t=26388&start=7
;
; Nummern-Eingabe Beispiele: 123  567,88  -12  -4,5
;
OpenWindow(0, #PB_Ignore, #PB_Ignore, 250, 80, "")
StringGadget(0, 10, 10, 200, 20, "")

CreateRegularExpression(0,"^\-{0,1}\d*$|^\-{0,1}\d+\,\d{0,2}$|^$") ; ^       = Anfang des Strings
                                                                   ; $       = Ende des Strings
                                                                   ; \d      = Dezimalzahl 0-9
                                                                   ; +       = 1 oder mehr Vorkommen
                                                                   ; *       = 0 oder mehr Vorkommen
                                                                   ; |       = alternative Moeglichkeit (Or in PureBasic)
                                                                   ; \,      = Komma
                                                                   ; \-{0,1} = Minus{0 oder 1 mal}
                                                                   ; \d{0,2} = Dezimalzahl 0-9 { 0 bis 2 mal }
Repeat
  Select WaitWindowEvent()
    Case #PB_Event_CloseWindow
      Break
    Case #PB_Event_Gadget
      If EventGadget() = 0 And EventType() = #PB_EventType_Change
        txt$ = GetGadgetText(0)
        If MatchRegularExpression(0,txt$)=0                           ; wenn kein Treffer, dann wieder vorherigen text setzen
          SendMessage_(GadgetID(0),#EM_GETSEL,0,@endpos) : endpos - 1 ; cursor position holen
          SetGadgetText(0,old$)                                       ; alten text wieder setzen
          SendMessage_(GadgetID(0),#EM_SETSEL,endpos,endpos)          ; cursor position wieder setzen
        Else
          old$ = txt$
        EndIf
      EndIf
  EndSelect
ForEver

Re: Mit StringGadget Kommazahl einlesen

Verfasst: 10.02.2013 21:00
von ts-soft
@Danilo
:allright: , aber ich bekomme beim entwerfen des Ausdrucks immer einen Wurm im Kopf :lol:

Re: Mit StringGadget Kommazahl einlesen

Verfasst: 10.02.2013 22:18
von marcelx
@Danilo

deine Lösung mit RegularExpression finde ich super und es funktioniert