![]() |
Ini-Einstellung umwandeln für Komponente
Hallo,
ich steh gerade auf dem Schlauch. Ich hab eine Ini-Datei in der man Einstellungen für die serielle Schnittstelle machen kann. Als Komponente nutz ich die VAComm von TMS Software. Dort wird z. b. Stopbit als Aufzählung (Type) benutzt. Nun möcht ich aber in der Ini-Datei eine ganz normale Eingabe wie z. B.:
Code:
Leider muss ich aber dann die Eingaben "umwandeln", bevor ich die Komponente beschreiben kann.
[RS232]
Parity=EVEN Stopbit=1 Momentan mach ich das in einer Function und auf String basierend.
Delphi-Quellcode:
Nur gefällt mir das nicht wirklich!
function TMaskForm.COM_Auswahl(Auswahl: TCOM_Auswahl; S: String): Variant;
begin // S := AnsiLowerCase(S); case Auswahl of COM_Databit: begin If S = '4' then Result := db4; If S = '5' then Result := db5; If S = '6' then Result := db6; If S = '7' then Result := db7; If S = '8' then Result := db8; end; COM_Stopbit: begin If S = '1' then Result := sb1; If S = '1.5' then Result := sb15; If S = '2' then Result := sb2; end; COM_Parity: begin If S = 'none' then Result := paNone; If S = 'even' then Result := paEven; If S = 'mark' then Result := paMark; If S = 'odd' then Result := paOdd; If S = 'space' then Result := paSpace; end; end; end; Gibt es denn vielleicht eine andere Möglichkeit? Was mir noch einfallen würde, das wäre die Auswahl als Index auszulesen um dann mit einem Cast auf die Auswahl die Komponente zu beschreiben. |
AW: Ini-Einstellung umwandeln für Komponente
Delphi-Quellcode:
so definieren und dann die Array Werte vergleichen
const
cDataBit : array [TDataBit?] of string = ( '4', '6', ...); |
AW: Ini-Einstellung umwandeln für Komponente
Über die RTTI kannst du diese ENUMs auch direkt in Strings umwandeln und zurück.
Oder du nimmst einfache Casts ala Ord, und konvertierst die ENUMs in Integer. |
AW: Ini-Einstellung umwandeln für Komponente
Converterklassen bauen.
Delphi-Quellcode:
uses StrUtils;
Type TParityConverter = Class Private Class Const ParitySettings = Array [paEven..paSpace] Of String = ('even','mark','odd','space'); Public Class Function FromString (setting : String) : TParity; Class Function ToString (setting : TParity) : String; End; Class Function TParityConverter.FromString (setting : String) : TParity; Var p : Integer; Begin p := IndexText (setting, ParitySettings); if p=-1 then Raise EConvertException.CreateFmt('Unknown parity setting %s', [setting]) else result := TParity(p); End; Class Function TParityConverter.ToString (setting : TParity) : String; Begin Try Result := ParritySettings[Ord(setting)]; Except Raise EConvertException.CreateFmt('Invalid parity (%d)',[setting]); End End; |
AW: Ini-Einstellung umwandeln für Komponente
wobei Sir Rufo's Ansatz mir hier am schlanksten erscheint ...
|
AW: Ini-Einstellung umwandeln für Komponente
Zitat:
Falls jemand mal nachschauen möchte:
Delphi-Quellcode:
procedure TodProp.LoadPropValue(const od: Tod; PropName, PropValue: String);
var Context: TRttiContext; RttiType: TRttiType; PropInfo: TRttiProperty; F: Boolean; Attr: TCustomAttribute; Value: TValue; InstOd: TInstOd; _od, iod: Tod; _PropName: String; V: Integer; begin if (not Assigned(od)) or (PropName = '') then Exit; _od := od; _PropName := PropName; CorrectSubOd(_od, _PropName); if not Assigned(_od) then Exit; Context := TRttiContext.Create; RttiType := Context.GetType(_od.ClassType); if Assigned(RttiType) then begin for PropInfo in RttiType.GetProperties do begin if PropInfo.Name <> _PropName then Continue; F := False; for Attr in PropInfo.GetAttributes do begin if Attr is AttrOd then F := True; end; if F then begin Value := TValue.Empty; case PropInfo.PropertyType.TypeKind of tkUnknown: ; tkInteger: Value := TValue.From(StrToIntDef(PropValue, 0)); tkChar: ; tkEnumeration: // <<<<<================================= HIER if TryStrToInt(PropValue, V) then Value := TValue.FromOrdinal(PropInfo.PropertyType.Handle, V) else Value := TValue.FromOrdinal(PropInfo.PropertyType.Handle, GetEnumValue(PropInfo.PropertyType.Handle, PropValue)); tkFloat: if PropInfo.GetValue(_od).IsType<TDateTime> then Value := TValue.From(StrToDateTimeDef(PropValue, 0)) else if PropInfo.GetValue(_od).IsType<TTime> then Value := TValue.From(StrToTimeDef(PropValue, 0)) else Value := TValue.From(StrToFloatDef(PropValue, 0)); tkString: Value := TValue.From(PropValue); tkSet: ; tkClass: begin iod := FoundOd(PatternToId(PropValue)); if (Assigned(iod)) or (AssignInstOdFlag) then begin Value := iod; end else begin InstOd := TInstOd.Create; InstOd.od := _od; InstOd.PropName := _PropName; InstOd.Id := PropValue; InstOdList.Add(InstOd); end; end; tkMethod: ; tkWChar: ; tkLString: ; tkWString: ; tkVariant: ; tkArray: ; tkRecord: ; tkInterface: ; tkInt64: ; tkDynArray: ; tkUString: Value := TValue.From(PropValue); tkClassRef: ; tkPointer: ; tkProcedure: ; end; if not Value.IsEmpty then PropInfo.SetValue(_od, Value); end; end; end; Context.Free; end; function TodProp.GetPropValue(const od: Tod; PropName: String): String; var PropValue: String; Context: TRttiContext; RttiType: TRttiType; PropInfo: TRttiProperty; F: Boolean; Attr: TCustomAttribute; Value: TValue; O: TObject; _od: Tod; _PropName: String; begin Result := ''; if (not Assigned(od)) or (PropName = '') then Exit; if Lowercase(PropName) = Lowercase('odId') then Exit(od.odId); _od := od; _PropName := PropName; CorrectSubOd(_od, _PropName); if not Assigned(_od) then Exit; Context := TRttiContext.Create; RttiType := Context.GetType(_od.ClassType); if Assigned(RttiType) then begin for PropInfo in RttiType.GetProperties do begin if PropInfo.Name <> _PropName then Continue; F := False; for Attr in PropInfo.GetAttributes do begin if Attr is AttrOd then F := True; end; if F then begin PropValue := ''; Value := PropInfo.GetValue(_od); case Value.Kind of tkUnknown: ; tkInteger: if Value.AsInteger = 0 then PropValue := '' else PropValue := inttostr(Value.AsInteger); tkChar: ; tkEnumeration: // <<<<<================================= HIER if Value.AsOrdinal = 0 then PropValue := '' else PropValue := GetEnumName(Value.TypeInfo, Value.AsOrdinal); tkFloat: if Value.AsExtended = 0 then PropValue := '' else if Value.IsType<TDateTime> then PropValue := DateTimeToStr(Value.AsExtended) else if Value.IsType<TTime> then PropValue := TimeToStr(Value.AsExtended) else PropValue := FloatToStr(Value.AsExtended); tkString: PropValue := Value.AsString; tkSet: ; tkClass: begin O := Value.AsObject; try if (O <> nil) and (O is Tod) then PropValue := (O as Tod).odId; except PropValue := ''; end; end; tkMethod: ; tkWChar: ; tkLString: ; tkWString: ; tkVariant: ; tkArray: ; tkRecord: ; tkInterface: ; tkInt64: ; tkDynArray: ; tkUString: PropValue := Value.AsString; tkClassRef: ; tkPointer: ; tkProcedure: ; end; if PropValue <> '' then Result := PropValue; end; end; end; Context.Free; end; |
AW: Ini-Einstellung umwandeln für Komponente
ist ja nicht gerade DRY ;)
Leg dir doch eine interne Procedure an, die lesen und schreiben kann mit einem zusätzlichen Parameter (lesend/schreibend). Mit deinen vorhandenen procedures rufst du dann nur noch diese interne auf und schon ist es DRY und KISS ;) |
AW: Ini-Einstellung umwandeln für Komponente
Zitat:
Die Idee mit dem Array ist gut. Ich habs folgendermaßen gemacht:
Delphi-Quellcode:
und frag dann so ab:
cDataBit: array [0..4] of string = ('4', '5', '6', '7', '8');
Delphi-Quellcode:
Ich wollt eigentlich Sir Rufo´s Idee übernehmen und den Typ ins Array übernehmen, also so:
for i := low(cDataBit) to high(cDataBit) do
If cDataBit[i] = S then begin Result := TVaDatabits(i); break; end;
Delphi-Quellcode:
.
cDataBit: array [TVaDataBits] of string = ('4', '5', '6', '7', '8');
Nur dann erhalte ich bei der for-Schleife:
Delphi-Quellcode:
.
for i := low(cDataBit) to high(cDataBit) do
folgende Fehlermeldung: Zitat:
Delphi-Quellcode:
TVaDatabits = (db4, db5, db6, db7, db8);
|
AW: Ini-Einstellung umwandeln für Komponente
@Helmi
der Zugriff bei Sir Rufos's Variante ist viel einfacher
Delphi-Quellcode:
Const
c:Array[TPrintScale] of String=('None', 'Proportional', 'PrintToFit') ; procedure TForm1.Button1Click(Sender: TObject); begin Caption := c[poPrintToFit]; end; |
AW: Ini-Einstellung umwandeln für Komponente
Zitat:
Ich habe einen String, den ich als Auswahl nutzen möchte, nicht anders rum. |
AW: Ini-Einstellung umwandeln für Komponente
Zitat:
Noch schlanker geht es so:
Delphi-Quellcode:
//Schreiben
MyIni.WriteInteger ('COM','Parity',Ord(MyComport.Parity)); //Lesen MyComPort.Parity := TParity(MyIni.ReadInteger ('COM','Parity',0)); |
AW: Ini-Einstellung umwandeln für Komponente
so würd ich aber nur den Index der Auswahl in der Ini-Datei haben
Ich möchte aber in der Ini-Datei angeben, z. B. Parity=Even und dann im Code auf die Com-Komponente
Delphi-Quellcode:
schreiben
Parity := paEven
|
AW: Ini-Einstellung umwandeln für Komponente
Warum willst Du denn nicht einfach
Delphi-Quellcode:
in Deine Ini schreiben und auf die ganze "Übersetzung" verzichten.
Parity=paEven
So macht es ja die IDE auch in ihren Formular-Dateien. |
AW: Ini-Einstellung umwandeln für Komponente
@Furtbichler
wobei es dann nicht mehr bei allem lesbar ist und die RTTI-Variante näher dran wäre.
Delphi-Quellcode:
Function GetIndexOf(Const Find:String;a:Array of String;Highest:Integer;Default:Integer=0):Integer;
var I: Integer; begin Result := Default; for I := 0 to Highest do if a[i] = Find then Result := i; end; ps := TPrintScale(GetIndexOf('None',c,Ord(poPrintToFit),Ord(poProportional))); |
AW: Ini-Einstellung umwandeln für Komponente
Zitat:
Zitat:
|
AW: Ini-Einstellung umwandeln für Komponente
Zitat:
Delphi-Quellcode:
Entweder du gehts dein Array durch und schaust wo sich der String versteckt.
Const
c:Array[TPrintScale] of String=('None', 'Proportional', 'PrintToFit') ; Oder, wenn man den ENUM über die RTTI in einen String umgewandelt hat, dann wandelt man den String über die RTTI wieder in den Enum (Integer+Cast) zurück. |
AW: Ini-Einstellung umwandeln für Komponente
Zitat:
Zitat:
|
AW: Ini-Einstellung umwandeln für Komponente
Zum Mitschreiben:
Delphi-Quellcode:
uses TypInfo; MyCom.Parity := TParity(GetEnumValue(TypeInfo(TParity),myParityStringFromINI)); MyIni.WriteString('COM','Parity', GetEnumName(TypeInfo(TParity), Integer(MyCOM.Parity)) ; |
AW: Ini-Einstellung umwandeln für Komponente
Zitat:
Meine (aufwendigere) Methode funktioniert dagegen mit allen Enum-Objektpropertys und ermittelt den richtigen Typ dynamisch. Wenn Du den Typ selbst kennst, ist es natürlich schneller und einfacher, den Typ direkt festzulegen. |
AW: Ini-Einstellung umwandeln für Komponente
Zitat:
Und Dank euch allen! |
Alle Zeitangaben in WEZ +1. Es ist jetzt 22:26 Uhr. |
Powered by vBulletin® Copyright ©2000 - 2025, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024-2025 by Thomas Breitkreuz