| Autor |
Beitrag |
Alpha_Wolf
      
Beiträge: 297
Ubuntu, Win XP, Win Vista
C#, Delphi 6 Prof, Delphi 2007 Prof, Java
|
Verfasst: Mo 24.01.05 13:57
Hallo Leute,
habe folgende(s) Aufgabe/Problem..
Würde gerne die Eingabe einer Edit soweit begrenzen, dass der User nur Zahlen und Kommas eingeben kann und natürlich die Eingabe mit der Backspace taste wieder löschen kann.
Nur irgendwie schaff ich das nur mit integer also mit der Prozedur Val. Gibt es da ne Prozedur die das verhindert?
Ist es denn sinnvoll einen Gleitkommawert als Single zu definieren. Die Editbox rundet nämlich immer automatisch..
Wäre für jede Art der Hilfe dankbar.
|
|
retnyg
      
Beiträge: 2754
SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
|
Verfasst: Mo 24.01.05 14:04
prüfe in dem ereignis onkeydown die übergebenen parameter ob die zahlen oder beistriche sind.
zb so :
var erlaubt : string;
erlaubt := '1234567890,';
if pos(chr(key), erlaubt) > 0 then bla...
|
|
Alpha_Wolf 
      
Beiträge: 297
Ubuntu, Win XP, Win Vista
C#, Delphi 6 Prof, Delphi 2007 Prof, Java
|
Verfasst: Mo 24.01.05 14:18
vom prinzip find ichs gut..danke
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8:
| var erlaubt: string; begin erlaubt := '1234567890,'; if pos(chr(key), erlaubt) <> 0 then begin ShowMessage ('Dies ist eine Zahl'); end; |
So wie ich das sehe hast du mich wohl falsch verstanden.. er prüft nun das ich welche eingegeben habe und macht danach wie hier im beispiel
ne Message.
Würde das aber genau andersrum haben wenn er Zahlen und n komma eingibt dann nix. Wenn er allerdings versucht Buchstaben oder andere Sonderzeichen einzugeben dann sollte beim verlassen der Edit eine Meldung kommen das der angegebene Wert keine Gleitkommazahl ist.
Moderiert von raziel: Code- durch Delphi-Tags ersetzt.
|
|
mirom
      
Beiträge: 56
Win2000, Win XP
|
Verfasst: Mo 24.01.05 14:32
...aber vorsicht...
Nutzer kann auch so etwas eingeben: '125..58' ( zwei komma statt eine ), was auch eine Exception mit StrToFloat auslöst. Ich habe eine Function geschrieben, die alle eventualitäten prüft:
1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13: 14: 15: 16: 17: 18: 19: 20: 21: 22: 23: 24: 25: 26: 27: 28: 29: 30: 31: 32: 33: 34: 35: 36: 37:
| function OnlyAllowedCharakters(inn: string; onlyNum: Boolean): string; var decOnce: boolean; i: integer; dd: double; txt: string; begin
txt := ''; decOnce := False; for i := 1 to Length(inn) do begin if onlyNum=True then begin if (inn[i] in ['0'..'9', '-']) then begin txt := txt + inn[i]; end else if inn[i]='.' then begin if decOnce=False then txt := txt + inn[i]; decOnce := True; end else if inn[i]=',' then begin if decOnce=False then txt := txt + '.'; decOnce := True; end; end else begin if (inn[i] in ['0'..'9', 'A'..'Z', '-', '.', '_', ' ']) then begin txt := txt + inn[i]; end else if (inn[i] in ['a'..'z']) then begin txt := txt + UpperCase(inn[i]); end; end; end;
if (onlyNum=True) then begin if Not(TryStrToFloat(txt, dd, FormatSettings)) then txt := ''; end;
Result := txt;
end; |
wobei
inn: string :: eingegeben
onlyNum: Boolean :: fals wahr, werden nur num. eingaben akzeptiert
Diese funktion ist eine allgemeine abschränkung von eingabe. Ich habe sie mit OnExit event von EditBox verknüpft.
Hoffe hat geholfen...
Miro M
Moderiert von Christian S.: Code- durch Delphi-Tags ersetzt.
|
|
retnyg
      
Beiträge: 2754
SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
|
Verfasst: Mo 24.01.05 14:35
| Alpha_Wolf hat folgendes geschrieben: | | vom prinzip find ichs gut..danke |
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8:
| procedure TForm1.Edit1KeyDown(Sender: TObject; var Key: Word; Shift: TShiftState); var erlaubt: string; begin erlaubt := '1234567890,'; if pos(chr(key), erlaubt) <> 0 then edit1.text := edit1.text + chr(key); |
rein theoretisch sollten damit nur noch buchstaben in das edit wandern, die auch erwünscht sind.
|
|
retnyg
      
Beiträge: 2754
SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
|
Verfasst: Mo 24.01.05 14:42
|
|
retnyg
      
Beiträge: 2754
SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
|
Verfasst: Mo 24.01.05 14:59
nun bleibt sogar der cursor bei falschem zeichen an der richtigen posi:
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12: 13:
| procedure TForm1.Edit1KeyUp(Sender: TObject; var Key: Word; Shift: TShiftState); var erlaubt: string; begin erlaubt := '1234567890,'; if (pos(chr(key), erlaubt) = 0) and (key <> 188)then begin edit1.text := copy(edit1.text,0,length(edit1.text)-1); edit1.SelStart := length(edit1.text); end; end; |
nun definierst du noch erlaubt als konstante und schon ist alles schön gelöst =)
|
|
Alpha_Wolf 
      
Beiträge: 297
Ubuntu, Win XP, Win Vista
C#, Delphi 6 Prof, Delphi 2007 Prof, Java
|
Verfasst: Mo 24.01.05 19:28
Habs mir mal in ruhe durchgedacht und n kumpel von mir hat das noch verfeinert..
Im KeyPress:
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11:
| begin if key in ['0'..'9', ','] then begin if key = ',' then begin if pos(',', Edit1.Text) > 0 then begin key := #0; end; end; end else begin key := #0; end; end; |
retnyg deine Source ist net schlecht aber fehleranfällig und der User fühlt sich wohl ein wenig vereppelt wenn er chars eingibt und diese wieder verschwinden.. an sich ist der Code nicht falsch.. find ihn sogar gut.. auch für andere sachen.
Durch meinen Code wird die Eingabe von Buchstaben gänzlich verhindert.. das einzige was noch optimiert werden muss ist das, dass am anfang kein Komma stehen darf aber das werde ich morgen machen.
Mirom dein Code ist echt sehr gut nur für meine Zwecke etwas zu krass.. 2 Edits zu maskieren und dafür ne halbe Seite Code zu brauchen ist nicht grade optimal. Hast du den eigentlich frei geschrieben oder kopiert?
Ich will euch hier nicht angreifen es sollte einfach nur ein Hinweis sein. Bin selbst noch ziemlicher Anfänger.. aber Kritik hat ja auch seine guten Seiten.
Danke für eure antworten, die haben mir wirklich geholfen.. davon lebt das board ja.
Gruß
A_W
|
|
mirom
      
Beiträge: 56
Win2000, Win XP
|
Verfasst: Mo 24.01.05 20:00
@Alpha_Wolf
Selbst geschrieben. Ich muss für meine application strenge kontrolle durchführen - und - ich lasse lieber Rechner arbeiten als meine Application zu absturz bringen ( halbe seite code ; ist dass viel ? ).
Grüße,
Miro M.
|
|
retnyg
      
Beiträge: 2754
SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
|
Verfasst: Mo 24.01.05 22:22
| Alpha_Wolf hat folgendes geschrieben: |
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11:
| begin if key in ['0'..'9', ','] then begin if key = ',' then begin if pos(',', Edit1.Text) > 0 then begin key := #0; end; end; end else begin key := #0; end; end; |
|
saubere lösung, auf das wollte ich eigentlich hinaus...hab mich eigentlich gewundert dass der key trotzdem durchrauscht auch wenn ich das abfange...dass man den auf #0 setzen muss da wär ich jetzt nicht draufgekommen :P
|
|
retnyg
      
Beiträge: 2754
SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
|
Verfasst: Di 25.01.05 03:06
wobei, so wär es eigentlich noch schöner :
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10:
| const erlaubt = '1234567890,'; syskeys = [188,8];
...
procedure TForm1.Edit1KeyPress(Sender: TObject; var Key: Char); begin if (pos(key, erlaubt) > 0) or (ord(key) in syskeys) then else key := #0; end; |
|
|
Alpha_Wolf 
      
Beiträge: 297
Ubuntu, Win XP, Win Vista
C#, Delphi 6 Prof, Delphi 2007 Prof, Java
|
Verfasst: Di 25.01.05 08:26
| mirom hat folgendes geschrieben: | @Alpha_Wolf
ich lasse lieber Rechner arbeiten als meine Application zu absturz bringen ( halbe seite code ; ist dass viel ? ).
|
Du hast recht. Eine halbe Seite ist nun wirklich nicht viel. Nur an sich ist mein Code ja nun auch nicht falsch und funktioniert einwandfrei. Was du nicht wissen konntest ist, dass diese kleine Abfrage sich nur auf einen minimal kleinen Teil einer sehr großen Applikation bezieht. Solange die Einsparungen nicht an der Qualität nagen ist es ja in Ordnung.
Aber dein Code ist echt gut durchdacht. Bin mir sicher das er mir nochmal helfen wird.
@retnyg
deine Lösung gefällt mir sehr gut..!
EDIT:
Hier nochmal mein Code mit Backspace.. Das einzige auf was ich grad überhaupt nicht komme ist, wie ich es schaffe das Komma an erster Stelle zu verhindern das zB.: ,34 nicht möglich ist.
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10:
| if key in ['0'..'9', ',', #8] then begin if key = ',' then begin if pos(',', Edit1.Text) > 0 then begin key := #0; end; end; end else begin key := #0; end; end; |
Wie kann ich es in diesem Code erreichen das keine Kommas an erster Stelle geschrieben werden?
Danke
A_W
|
|
retnyg
      
Beiträge: 2754
SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
|
Verfasst: Di 25.01.05 12:00
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9: 10: 11: 12:
| const erlaubt = '1234567890,'; syskeys = [188,8];
...
procedure TForm1.Edit1KeyPress(Sender: TObject; var Key: Char); begin if (length(edit1.text) = 0) and (ord(key) = 188) then key := #0 else if (pos(key, erlaubt) > 0) or (ord(key) in syskeys) then else key := #0; end; |
|
|
retnyg
      
Beiträge: 2754
SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
|
Verfasst: Di 25.01.05 12:17
oder: (so kann nur EIN beistrich eingegeben werden)
Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9:
| procedure TForm1.Edit1KeyPress(Sender: TObject; var Key: Char); begin if key = ',' then (if (pos(',',edit1.text) = 0) and (length(edit1.text) <> 0) then else key := #0) else if (pos(key, erlaubt) > 0) or (ord(key) in syskeys) then else key := #0; end; |
|
|
Lossy eX
      
Beiträge: 1048
Erhaltene Danke: 4
|
Verfasst: Di 25.01.05 12:22
@retnyg: Man könnte dennoch ein Komma an erster Stelle eingeben. Der Benutzer könnte ja zu erst eine andere Zahl eintippen. Dann nach vorne springen und ein Komma eingeben. Ich finde Konstrukte wie then else nicht sonderlich sauber und ein wenig irreführend. Dann würde ich lieber die Abfrage negieren.
@Alpha_Wolf: Delphi-Quelltext 1: 2: 3: 4: 5: 6: 7: 8: 9:
| if key in ['0'..'9', ',', #8] then begin if key = ',' then begin if (pos(',', (Sender as TEdit).Text) > 0) or ((Sender as TEdit).SelStart = 0) then begin key := #0; end; end; end else begin key := #0; end; |
Ich denke mal, dass sollte genügen. Nur besteht jetzt noch das Problem, dass der Benutzer die Zeichen vor dem Komma löschen kann. An der Stelle stellt sich aber die Frage. Entweder man verbietet das löschen der letzten Zahl (vor dem Komma) oder man ersetzt diese dann durch eine 0 oder man entfernt das Komma mit. Wobei mir die Möglichkeit mit der 0 am Besten gefällt, da dort die Zahl als solche erhalten bleibt und keinen völlig neuen (und vor allem falschen) Wert annimmt.
Sender as TEdit ist eine Möglichkeit den Sender als ein TEdit zu casten. So könntest du dieses Event noch bei anderen Eingabefelden einsetzen ohne, dass du es neu Programmieren musst.
_________________ Nur die Menschheit ist arrogant genug, um zu glauben sie sei die einzige intelligente Lebensform im All. Wo nicht mal das nachhaltig bewiesen wurde.
|
|
retnyg
      
Beiträge: 2754
SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
|
Verfasst: Di 25.01.05 12:30
@lossy ex: stimmt, der user könnte probieren die routine auszutricksen indem er mit dem cursor eines zurückgeht, nachdem er bereits eine zahl eingegeben hat.
drum ist Tedit(sender).selstart <> 0 noch eleganter als length(edit1.text) <> 0
|
|
retnyg
      
Beiträge: 2754
SNES, GB, GBA, CPC, A500, 486/66, P4/3.0HT: NintendOS, AmigaOS, DoS
Delphi 5, Delphi 7
|
Verfasst: Di 25.01.05 12:41
| Lossy eX hat folgendes geschrieben: | Ich finde Konstrukte wie then else nicht sonderlich sauber und ein wenig irreführend. Dann würde ich lieber die Abfrage negieren.  |
hmm ich finde das eigentlich ziemlich elegant, aber du könntest es folgendermassen machen, damit niemand verwirrt ist: then asm NOP end else

|
|
Alpha_Wolf 
      
Beiträge: 297
Ubuntu, Win XP, Win Vista
C#, Delphi 6 Prof, Delphi 2007 Prof, Java
|
Verfasst: Di 25.01.05 13:05
@Lossy eX
Vielen Dank. Ist wohl einer der besten Lösungen.
Hmm wenns noch fragen dazu gibt werd ich mich melden.. vorerst aber nicht
Danke an eurer Anteilnahme 
|
|
|