[Gelöst] Table Box - Werte werden nicht wirklich angezeigt

17. Juni 2008 15:19

Hallo Community,

ich hab da mal wieder ein recht merkwürdiges Problem.

Zur Anzeige von Zeiterfassungsdaten habe ich eine Tablebox erwählt. Die Table Box deshalb, weil ich neben den Feldern der Tabelle auch eigene Werte anzeigen können muss. Nun beziehen sich die Felder für Tabellendaten auf eine Temporäre Tabelle, die ich gefiltert befülle (was auch einfandfrei funktioniert). In der Temporären sind alle Tage des Monats enthalten, für Juni also 01.09. - 30.06.

Wenn ich nun aber die temporäre Tabelle anzeigen lassen will, wird nur ein Wert (von 30 in der Tabelle) angezeigt.
Code:
fnZeigeMonatsdaten(parMANr : Code[10];parMonat : Integer;parJahr : Integer)
//********************************************************************************
//*****
//********************************************************************************
varStartdatumL := fnHoleGrenzDatum(parMonat,parJahr,'ERSTER');
varEndeDatumL := fnHoleGrenzDatum(parMonat,parJahr,'LETZTER');
AnzahlWerktage := hFunktionen.fnArbeitstageImMonat(parMonat,parJahr);

varSuchDatumL := varStartdatumL;
tmpArbeitszeiten.RESET;
tmpArbeitszeiten.DELETEALL;

WHILE varSuchDatumL <= varEndeDatumL DO BEGIN
  varZEArbeitszeitenL.RESET;
  varZEArbeitszeitenL.SETRANGE("Personal Nr.", parMANr);
  varZEArbeitszeitenL.SETRANGE(Datum, varSuchDatumL);

  IF varZEArbeitszeitenL.FINDSET(FALSE) THEN BEGIN

    tmpArbeitszeiten.INIT;
    tmpArbeitszeiten."Personal Nr." := parMANr;
    tmpArbeitszeiten.Datum := varSuchDatumL;
    tmpArbeitszeiten.Mitarbeiter := varZEArbeitszeitenL.fnHoleMitarbeiterName(parMANr);
    tmpArbeitszeiten.Erfassungszeit := fnLetzteArbeitszeitBuchung(parMANr,varSuchDatumL);
    tmpArbeitszeiten.Startzeit := fnHoleMinStartzeit(parMANr,varSuchDatumL);
    tmpArbeitszeiten.Endezeit := fnHoleMaxEndezeit(parMANr,varSuchDatumL);
    tmpArbeitszeiten."Startzeit Abrechnung" :=
                              tmpArbeitszeiten.fnRundeAbrechnungszeit(TRUE,
                              CREATEDATETIME(varSuchDatumL,tmpArbeitszeiten.Startzeit));
    tmpArbeitszeiten."Endezeit Abrechnung" :=
                              tmpArbeitszeiten.fnRundeAbrechnungszeit(FALSE,
                              CREATEDATETIME(varSuchDatumL,tmpArbeitszeiten.Endezeit));
    IF varZEArbeitszeitenL.COUNT > 1 THEN BEGIN
      tmpArbeitszeiten.Buchungsnotiz := 'mehrere Einträge';
      tmpArbeitszeiten.Typ := '?';
      tmpArbeitszeiten."Typ-Bezeichung" := 'Mehrfacheintrag';
    END ELSE BEGIN
      tmpArbeitszeiten.Buchungsnotiz := varZEArbeitszeitenL.Buchungsnotiz;
      tmpArbeitszeiten.Typ := Typ;
      tmpArbeitszeiten."Typ-Bezeichung" := varZEArbeitszeitenL."Typ-Bezeichung";
    END;
    tmpArbeitszeiten.Gruppierung := varZEArbeitszeitenL.Gruppierung;
    tmpArbeitszeiten.Funktion := varZEArbeitszeitenL.Funktion;
    tmpArbeitszeiten.INSERT;


  END ELSE BEGIN
     //Leerzeilen (fürs Wochenende /Feiertage) eintragen
     tmpArbeitszeiten.INIT;
     tmpArbeitszeiten."Personal Nr." := parMANr;
     tmpArbeitszeiten.Mitarbeiter := tmpArbeitszeiten.fnHoleMitarbeiterName(parMANr);
     tmpArbeitszeiten.Erfassungszeit := CREATEDATETIME(varSuchDatumL,TIME);
     tmpArbeitszeiten.Datum := varSuchDatumL;
     tmpArbeitszeiten.INSERT;

  END;
  varSuchDatumL := CALCDATE('1T',varSuchDatumL);
END;

//Anzeige der Daten per Messagebox
tmpArbeitszeiten.FINDFIRST;
REPEAT
  msg := 'Datum: ' + FORMAT(tmpArbeitszeiten.Datum) + '\';
  msg := msg + 'Mitarbeiter: ' + tmpArbeitszeiten.Mitarbeiter + '\';
  msg := msg + 'Start: ' + FORMAT(tmpArbeitszeiten.Startzeit) + ' Ende: ' + FORMAT(tmpArbeitszeiten.Endezeit) + '\';
  MESSAGE(msg);
UNTIL tmpArbeitszeiten.NEXT = 0;

tmpArbeitszeiten.SETVIEW('SORTING(Datum) ORDER(Ascending)');

CurrForm.UPDATE(FALSE);


Sieht vielleicht etwas wild aus, der Code :-) , aber ich frage mich ja auch nur warum die temporäre Tabelle nicht alle Werte anzeigt (wie in der Messagebox, die gibt in der Schleife jeden Wert korrekt an) sondern nur einen einzigen, und da auch noch einen aus der Mitte, nämlich den 16.06. ....

Ratloser Gruß

Carsten
Zuletzt geändert von CaddyM am 19. Juni 2008 10:52, insgesamt 1-mal geändert.

17. Juni 2008 20:19

Hast du die Form genauso gemacht, wie die Form der Artikelverfolgungszeilen (6510 glaub ich) mit temp. Records umgeht? Achte dort auf die Form-Trigger.

Wenn du die Messagebox nicht anzeigst - erfolgt dann noch irgendwo ein FIND('-') auf die temp. Recordvariable?

18. Juni 2008 07:29

Versuche es mal mit einem "tmpArbeitszeiten.RESET;",
bevor du die tmp Tabelle abrufts.

Michael

18. Juni 2008 08:12

Natalie hat geschrieben:Hast du die Form genauso gemacht, wie die Form der Artikelverfolgungszeilen (6510 glaub ich) mit temp. Records umgeht? Achte dort auf die Form-Trigger.

Wenn du die Messagebox nicht anzeigst - erfolgt dann noch irgendwo ein FIND('-') auf die temp. Recordvariable?


Hm, also 6510 liegt ausserhalb unserer Entwicklungslizenz (das ist echt ein Thema was ich langsam hasse ....) - kann ich von daher also nicht nachvollziehen. Wenn du die OnFindRecord und OnNextRecord meinst: sa steht Code drin den ich net nachvollziehen kann. Beispiel:
Code:
Form - OnFindRecord(Which : Text[1024]) : Boolean
tmpArbeitszeiten := Rec;
IF NOT tmpArbeitszeiten.FIND(Which) THEN
  EXIT(FALSE);
Rec := tmpArbeitszeiten;
EXIT(TRUE);


Ein find('-') hab ich mal probehalber eingebaut (wobei das ja eigentlich auch nur den Cursor auf dem ersten Datensatz positioniert) - ohne Ergebnis. Sieht also am Ende des Codes nun so aus:
Code:
tmpArbeitszeiten.FINDFIRST;
REPEAT
  msg := 'Datum: ' + FORMAT(tmpArbeitszeiten.Datum) + '\';
  msg := msg + 'Mitarbeiter: ' + tmpArbeitszeiten.Mitarbeiter + '\';
  msg := msg + 'Start: ' + FORMAT(tmpArbeitszeiten.Startzeit) + ' Ende: ' + FORMAT(tmpArbeitszeiten.Endezeit) + '\';
  MESSAGE(msg);
UNTIL tmpArbeitszeiten.NEXT = 0;

tmpArbeitszeiten.RESET;
tmpArbeitszeiten.SETVIEW('SORTING(Datum) ORDER(Ascending)');
tmpArbeitszeiten.FIND('-');

CurrForm.UPDATE(FALSE);

Als einziger Datensatz wird der 17.06.2008 angezeigt, obwohl die Tabelle die 30 Datensätze für den ganzen Monat enthält.
Zuletzt geändert von CaddyM am 18. Juni 2008 08:25, insgesamt 1-mal geändert.

18. Juni 2008 08:15

mespelage hat geschrieben:Versuche es mal mit einem "tmpArbeitszeiten.RESET;",
bevor du die tmp Tabelle abrufts.

Michael


Siehe oben, ohne Erfolg :-?

18. Juni 2008 08:21

ich meinte allerdings vor dem FINFIRST

Code:
tmpArbeitszeiten.RESET;
tmpArbeitszeiten.FINDFIRST;
REPEAT
  msg := 'Datum: ' + FORMAT(tmpArbeitszeiten.Datum) + '\';
  msg := msg + 'Mitarbeiter: ' + tmpArbeitszeiten.Mitarbeiter + '\';
  msg := msg + 'Start: ' + FORMAT(tmpArbeitszeiten.Startzeit) + ' Ende: ' + FORMAT(tmpArbeitszeiten.Endezeit) + '\';
  MESSAGE(msg);
UNTIL tmpArbeitszeiten.NEXT = 0;

18. Juni 2008 08:28

mespelage hat geschrieben:ich meinte allerdings vor dem FINFIRST


Auch da bleibt das Ergebnis das gleiche. Das FINDFIRST dort war ja nur gedacht für die Messagebox, um vom ersten Datensatz an wieder anzuzeigen. Ich hab jedenfalls davor auch mal ein Reset eingesetzt - ohne Erfolg.

18. Juni 2008 08:32

Kein Problem, hier der Inhalt der Formtrigger:

OnFindRecord
Code:
TempRec:= Rec;
IF NOT TempRec.FIND(Which) THEN
  EXIT(FALSE);
Rec := TempRec;
EXIT(TRUE);


OnNextRecord

Code:
TempRec := Rec;
CurrentSteps := TempRec.NEXT(Steps);
IF CurrentSteps <> 0 THEN
  Rec := TempRec;
EXIT(CurrentSteps);

18. Juni 2008 08:58

Ja, diese beiden Codeblöcke sind eingesetzt (muss ich mir auch mal erklären lassen was es damit genau auf sich hat :) )

18. Juni 2008 09:04

An welcher Stelle füllst du den temporären Record?

18. Juni 2008 09:19

Innerhalb der

WHILE varSuchDatumL <= varEndeDatumL DO BEGIN

Schleife. Laut der Messagebox ist ja auch alles gefüllt wie es soll, mit der gehe ich ja derzeit zum Testen in einer weiteren Schleife über alle Einträge in dem temporären Record, nachdem er gefüllt sein müsste.

18. Juni 2008 10:41

Nein, meine Frage war: Wo wird dieser ganze Prozess angestoßen?
In einem Formtrigger? In einer ausgelagerten Funktion? Vor dem Öffnen? Nach dem Öffnen?

18. Juni 2008 12:05

Ah so ^^ (obwohl - jetzt grade bilde ich das mit einem Button nach, und dort im OnPush wird die Funktion aufgerufen).

Geplant ist es aber (weil dieses Formular als Subform genutzt wird), im OnActivate des Subform-Controls. Muss ich so machen weil sich anderswo in dem Hauptformular Daten (Mitarbeiter) geändert haben können und darum das Subform beim erneuten Anzeigen mit aktualisierten Daten angezeigt werden soll.

Ich setzte genau dieses Subform in unterschiedlichen Arten in dem übergeordneten Formluar ein - immer mit einer temporären Tabelle - und diese Ansicht ist die Einzige, die nicht geht. Das macht mich ziemlich konfus, weil ich im Code und in der Logik eigentlich keinen Fehler finde und es eben in andren Codebereichen funktioniert. Hier z.B.:
Code:
fnSetAbwesendeMitarbeiter()
//**********************************************************************
//***** Ermittlung von Nicht-Anwesenden Mitarbeitern.
//***** Definiton "Nicht anwesend":
//***** - Letzter Eintrag ist kein Eintragstyp 'A' an dem Tag
//***** - Letzte Endezeit < Ansichtszeit
//**********************************************************************

fnSetzeUeberschrift('Abwesende Mitarbeiter (Heute)');
varPruefZeitpunkt := TIME;
NAPAMitarbeiterL.SETRANGE(Status,NAPAMitarbeiterL.Status::anlegen,NAPAMitarbeiterL.Status::Aktiv);
IF NAPAMitarbeiterL.FINDSET(FALSE,FALSE) THEN BEGIN
  REPEAT
    varIstAbwesend := FALSE;
    ArbeitszeitenL.RESET;
    //Alles Anzeigen, was nicht Arbeitszeit ist
    ArbeitszeitenL.SETRANGE("Personal Nr.",NAPAMitarbeiterL."Nr.");
    ArbeitszeitenL.SETRANGE(Datum,TODAY);
    ArbeitszeitenL.SETFILTER(Typ,'<>%1','A');
    IF ArbeitszeitenL.FINDLAST THEN BEGIN
       tmpArbeitszeiten.INIT;
       tmpArbeitszeiten := ArbeitszeitenL;
       tmpArbeitszeiten.INSERT;
      varIstAbwesend := TRUE;
    END;

    IF NOT varIstAbwesend THEN BEGIN
      ArbeitszeitenL.RESET;
      ArbeitszeitenL.SETRANGE("Personal Nr.", NAPAMitarbeiterL."Nr.");
      ArbeitszeitenL.SETRANGE(Datum, TODAY);
      ArbeitszeitenL.SETRANGE(Typ, 'A');
      ArbeitszeitenL.SETFILTER(Endezeit, '<>%1', 0T);
      IF ArbeitszeitenL.FINDLAST THEN BEGIN
        IF ArbeitszeitenL.Endezeit < varPruefZeitpunkt THEN BEGIN
          tmpArbeitszeiten.INIT;
          tmpArbeitszeiten := ArbeitszeitenL;
          tmpArbeitszeiten.INSERT;
          varIstAbwesend := TRUE;
        END;
      END;
    END;
  UNTIL NAPAMitarbeiterL.NEXT = 0;
END;

CurrForm.UPDATE(FALSE);

Das ist ein weiterer Codeblock in der selben Form, und der arbeitet einwandfrei ....

18. Juni 2008 13:13

Ich muss gestehen, ich hab noch nie versucht, temporäre Record in einer Subform anzuzeigen.
OnActivate reich nicht. Bei Änderung des entsprechenden Filterwertes in der Subform muss die Subform eine Funktion der Subform aufrufen. Und in dieser Funktion muss das Füllen des temp. Records enthalten sein.

Bei nicht temporären Records stellt sich dieses Problem nicht. Durch den Subformlink (also kein Quelltext) aktualisiert sich die Subform immer automatisch.

18. Juni 2008 13:31

Also meinst du, ich sollte in dem Trigger eine Funktion der Subform aufrufen, die die Tabelle neu befüllt und anschliessend ein TempTabelle.UPDATE(false) aufruft? Wieso muss das ganze auch so kompliziert sein ... oO - ich glaube mit einem anderen Lizenzmodell wäre das einfacher, welches mich nicht so bei der Erstellung von Subforms einschränkt. Aber naja - ich werde das gleich probieren und dann sehen wir weiter.

19. Juni 2008 10:51

Ok, ich hab nun eine Menge rumprobiert. Glücklicherweise hab ich vor einer Woche ein Sicherung angelegt. Die hab ich dann probeweise mal gestartet und voila - es läuft dort. Also muss ich in der letzten Woche irgendwo eine Macke reinprogrammiert haben. Ich kann zwar nicht sagen was es letztendlich war (die Tabelle oder das Formular), weil ich beides ersetzt habe, aber immerhin können wir uns wieder wichtigeren Themen zuwenden. Von daher also:

Gelöst!

19. Juni 2008 11:01

Falls du diese Macke doch noch findest, lass uns bitte teilhaben :-)