DCPROGRESS mit INDEX ON ?

Moderator: Moderatoren

Antworten
xbaseklaus
Rekursionen-Architekt
Rekursionen-Architekt
Beiträge: 246
Registriert: Mi, 04. Jun 2014 12:01
Wohnort: FRANKEN

DCPROGRESS mit INDEX ON ?

Beitrag von xbaseklaus »

So , da mich gestern TOM mit meiner Frage nach der Verwendung von DCPROGRESS mit INDEX ON im Regen stehen hat lassen , muss ich das Thema nochmal aufgreifen.
Ich hat geschrieben:"wie muss der CODE verändert werden um hier ein DCPROGRESS vernünftig einzubauen:"
Tom hat geschrieben:"Dafür gibt es fertige Beispiele in der eXpress++-Installation. Einfach mal nachschauen.
Herzlich..."
Also ich hab mir die Beispiele angeschaut komm aber trotzdem nicht weiter :-(
Ich brauch es zwar nicht unbedingt ... aber es wäre ein schönes GIMIMK und natürlich wurmt
mich es jetzt, dass ich da irgenwie nicht durchsteige :banghead:

Ich habs soweit hinbekommen das er den PROGRESS BAR anzeigt aber er bleibt bei 0 stehen und der INDEX ist angelegt :angry4:

os ähnlich schaut der CODE aus: ( habe ihn natürlich von den SAMPLES abgekupfert, anscheinend aber nicht gut genug .

kann mich jemand :idea:


*PROGRESS BAR

Code: Alles auswählen

procedure main
#include 'dcdialog.ch'
#include 'xbp.ch'
#include 'gra.ch'
#pragma library("c:\alaska\exp18\bin\dclipx.lib")

LOCAL Getlist := {}, oProgress, oDialog

USE LAGER1

@ 2,5 DCSAY 'INDEXERSTELLUNG'

@ 4,5 DCPROGRESS oProgress ;
       SIZE 55,1.5 ;
       PERCENT ;
       EVERY 5 ;
       MAXCOUNT RecCount() COLOR GRA_CLR_BLUE

DCREAD GUI ;
   TITLE 'TEST' ;
   PARENT @oDialog ;
   FIT ;
   EXIT ;
   MODAL

oDialog:show()

INDEX ON artikelnr TO lnr EVAL _Progress( oProgress )

oDialog:Destroy()
RETURN 


FUNCTION _Progress ( oProgress )
LOCAL nMaxCount := RecCount()
DC_GetProgress( oProgress, RecNo() )
RETURN oProgress
Benutzeravatar
Tom
Der Entwickler von "Deep Thought"
Der Entwickler von "Deep Thought"
Beiträge: 9358
Registriert: Do, 22. Sep 2005 23:11
Wohnort: Berlin
Hat sich bedankt: 101 Mal
Danksagung erhalten: 361 Mal
Kontaktdaten:

Re: DCPROGRESS mit INDEX ON ?

Beitrag von Tom »

Nicht "EVAL" im INDEX ON, sondern "WHILE", und der Ausdruck danach als Codeblock.
Herzlich,
Tom
xbaseklaus
Rekursionen-Architekt
Rekursionen-Architekt
Beiträge: 246
Registriert: Mi, 04. Jun 2014 12:01
Wohnort: FRANKEN

Re: DCPROGRESS mit INDEX ON ?

Beitrag von xbaseklaus »

Tom hat geschrieben:Nicht "EVAL" im INDEX ON, sondern "WHILE", und der Ausdruck danach als Codeblock.
Hi Tom , danke erstmal für den Hinweis.

Jetzt weiss ich ich muß WHILE verwenden und einen CODEBLOCK {|| } , aber ich komm trotzdem nicht weiter.

Könntest du nicht einfach, wenn ich dich ganz LIEB BITTE meinen CODE vervollständigen so dass er funktioniert :bs: :angel5:

mfg Klaus
Benutzeravatar
brandelh
Foren-Moderator
Foren-Moderator
Beiträge: 15695
Registriert: Mo, 23. Jan 2006 20:54
Wohnort: Germersheim
Hat sich bedankt: 65 Mal
Danksagung erhalten: 33 Mal
Kontaktdaten:

Re: DCPROGRESS mit INDEX ON ?

Beitrag von brandelh »

das sollte dem alten Befehl entsprechen, falls deine DBE kein WHILE unterstützt, kannst du da auch FOR nehmen.

Code: Alles auswählen

INDEX ON artikelnr TO lnr WHILE {|| _Progress( oProgress ), .t. } 
Gruß
Hubert
Benutzeravatar
Tom
Der Entwickler von "Deep Thought"
Der Entwickler von "Deep Thought"
Beiträge: 9358
Registriert: Do, 22. Sep 2005 23:11
Wohnort: Berlin
Hat sich bedankt: 101 Mal
Danksagung erhalten: 361 Mal
Kontaktdaten:

Re: DCPROGRESS mit INDEX ON ?

Beitrag von Tom »

FOR sollte man nicht nehmen, da es Bestandteil des Indexes wird (FOR !Deleted() o.ä.). Sobald man den Index dann öffnet und bearbeitet, wird versucht, diesen Codeblock bei Änderungen zu evaluieren.
Herzlich,
Tom
xbaseklaus
Rekursionen-Architekt
Rekursionen-Architekt
Beiträge: 246
Registriert: Mi, 04. Jun 2014 12:01
Wohnort: FRANKEN

Re: DCPROGRESS mit INDEX ON ?

Beitrag von xbaseklaus »

brandelh hat geschrieben:das sollte dem alten Befehl entsprechen, falls deine DBE kein WHILE unterstützt, kannst du da auch FOR nehmen.

Code: Alles auswählen

INDEX ON artikelnr TO lnr WHILE {|| _Progress( oProgress ), .t. } 
Danke erstmal , das Problem ist aber

genau so hatte ich es nach dem HINWEIS von TOM auch geändert --- THE RESULT ist aber es hat sich nichts geändert -> PROGRESS BAR bleibt beim 0 stehen , wie vorher auch , und beendet sich dann nach der reorganisation.

Bei Verwendung von FOR bekomme ich ne Fehlermeldung:

Code: Alles auswählen

------------------------------------------------------------------------------
ERROR LOG of "C:\w2014\dcp1\project.EXE" Date: 06/06/2014 11:57:27

Xbase++ version     : Xbase++ (R) Version 1.82.306
Operating system    : Windows  06.01 Build 07601 Service Pack 1
------------------------------------------------------------------------------
oError:args         :
          -> VALTYPE: C VALUE: lnr
          -> VALTYPE: U VALUE: NIL
          -> VALTYPE: C VALUE: artikelnr
          -> VALTYPE: B VALUE: {|| artikelnr}
          -> VALTYPE: U VALUE: NIL
          -> VALTYPE: L VALUE: .F.
oError:canDefault   : Y
oError:canRetry     : Y
oError:canSubstitute: N
oError:cargo        : NIL
oError:description  : Operating system error
oError:filename     : 
oError:genCode      :         40
oError:operation    : OrdCreate
oError:osCode       :          1
oError:severity     :          2
oError:subCode      :          4
oError:subSystem    : BASE
oError:thread       :          1
oError:tries        :          1
------------------------------------------------------------------------------
CALLSTACK:
------------------------------------------------------------------------------
Called from MAIN(28)
Benutzeravatar
Tom
Der Entwickler von "Deep Thought"
Der Entwickler von "Deep Thought"
Beiträge: 9358
Registriert: Do, 22. Sep 2005 23:11
Wohnort: Berlin
Hat sich bedankt: 101 Mal
Danksagung erhalten: 361 Mal
Kontaktdaten:

Re: DCPROGRESS mit INDEX ON ?

Beitrag von Tom »

Nicht FOR verwenden!

Es ist nicht sehr sinnvoll, in der Aktualisierungsfunktion für den Fortschrittsbalken RecCount() andauernd zu ermitteln. Sinnvoller wäre es, diesen Wert einmal - vor dem Reindex - zu erheben und der Funktion zu übergeben. Und da WHILE einmal pro Datensatz evaluiert wird, würde ich in der _Progress-Funktion eine STATIC setzen, auf 0 initialisieren und bei jedem Aufruf erhöhen. Dann stimmte auch der Zähler:

Code: Alles auswählen

nMax := RecCount()

_Progress()

INDEX ... WHILE {||_Progress(oProgress,nMax) ... }

FUNCTION _Progress(oProgress,nMax)
STATIC nCount := 0
IF PCount()>0
  nCount ++
  DC_GetProgress(oProgress,nCount,nMax)
ENDIF
RETURN nil
(Ins Blaue.)
Herzlich,
Tom
Benutzeravatar
brandelh
Foren-Moderator
Foren-Moderator
Beiträge: 15695
Registriert: Mo, 23. Jan 2006 20:54
Wohnort: Germersheim
Hat sich bedankt: 65 Mal
Danksagung erhalten: 33 Mal
Kontaktdaten:

Re: DCPROGRESS mit INDEX ON ?

Beitrag von brandelh »

Tom hat geschrieben:FOR sollte man nicht nehmen, da es Bestandteil des Indexes wird (FOR !Deleted() o.ä.). Sobald man den Index dann öffnet und bearbeitet, wird versucht, diesen Codeblock bei Änderungen zu evaluieren.
stimmt, das hatte ich vergessen.

In den Programmen, in denen ich noch so eine Taskbar drinn habe, nutze ich DBCreateIndex() heute OrdCreate(), dort kann man den Indexbegriff als Text und den Codeblock getrennt angeben.

Die Syntax stimmt, soweit es den Aufruf aus INDEX angeht, allerdings weiß ich nicht wie DC... den Laufbalken vorsieht, eigentlich müsste man nicht nur das Control angeben, sondern entweder die aktuelle Workarea oder DBPosition() ... damit das Control weiß wo man steht.
Gruß
Hubert
Benutzeravatar
brandelh
Foren-Moderator
Foren-Moderator
Beiträge: 15695
Registriert: Mo, 23. Jan 2006 20:54
Wohnort: Germersheim
Hat sich bedankt: 65 Mal
Danksagung erhalten: 33 Mal
Kontaktdaten:

Re: DCPROGRESS mit INDEX ON ?

Beitrag von brandelh »

Der Codeblock von WHILE muss auf jeden Fall ein .t. zurückgeben, sonst wird abgebrochen.
Ich hatte oben , .t. angehängt, aber in deiner Funktion wäre es sinnvoller direkt dort die Rückgabe auf .t. zu ändern.

Und wenn ich mir ansehe was TOM geschrieben hat, fehlt dir ein Parameter bei

Code: Alles auswählen

DC_GetProgress( oProgress, RecNo() )
den RecCount() hast du zwar in einer Var gespeichert, aber nicht verwendet !

ich ändere mal den Rückgabewert, damit er direkt die richtige "weiterindizieren" Antwort an WHILE gibt:

Code: Alles auswählen

FUNCTION _Progress(oProgress,nMax)
STATIC nCount := 0
IF PCount()>0
  nCount ++
  DC_GetProgress(oProgress,nCount,nMax)
ENDIF
RETURN .t.
und nun fällt mir ein, wird der Codeblock überhaupt richtig von INDEX übersetzt ?
Versuche es mal so ... mit den Änderungen von TOM und mir:

Code: Alles auswählen

nMax := LastRec()
INDEX ON ... TO ... WHILE _Progress(oProgress,nMax) // nMax sollte man VORHER ermitteln und in der Var speichern, das ist schneller
Gruß
Hubert
Benutzeravatar
Tom
Der Entwickler von "Deep Thought"
Der Entwickler von "Deep Thought"
Beiträge: 9358
Registriert: Do, 22. Sep 2005 23:11
Wohnort: Berlin
Hat sich bedankt: 101 Mal
Danksagung erhalten: 361 Mal
Kontaktdaten:

Re: DCPROGRESS mit INDEX ON ?

Beitrag von Tom »

@Hubert: Das Control benötigt an dieser Stelle nichts weiter als zwei Zahlen, nämlich einen aktuellen Wert und den Maximalwert.

@Klaus: Ich würde empfehlen, aus dem DCPROGRESS einen prozentualen Fortschrittszähler zu machen (DCPROGRESS ... PERCENT EVERY nMax/100 MAXCOUNT nMax) und ihn wirklich nur zu aktualisieren, wenn der Wert steigt. Ansonsten hast Du nämlich ein hübsches Gimmick, aber auch noch eine Funktionalität, die Reorganisationen deutlich verlangsamt. Ich mache derlei inzwischen nicht mehr, um genau das zu vermeiden, sondern lasse einen Fortschrittsbalken ohne Zählfunktion (sog. Marquee) anzeigen, der einfach in einem getrennten Thread vor sich hindaddelt, ohne große Ressourcen zu beanspruchen, während die Reorganisation wirklich nichts weiter tut als zu reorganisieren. Den Anwendern genügt der Eindruck, dass etwas passiert. Allerdings müsste man dafür andere Controls verwenden (nativ/Win-API oder z.B. Codejock).
Herzlich,
Tom
Benutzeravatar
brandelh
Foren-Moderator
Foren-Moderator
Beiträge: 15695
Registriert: Mo, 23. Jan 2006 20:54
Wohnort: Germersheim
Hat sich bedankt: 65 Mal
Danksagung erhalten: 33 Mal
Kontaktdaten:

Re: DCPROGRESS mit INDEX ON ?

Beitrag von brandelh »

Tom hat geschrieben:@Hubert: Das Control benötigt an dieser Stelle nichts weiter als zwei Zahlen, nämlich einen aktuellen Wert und den Maximalwert.
Das Control (ich vermute hier oProgress) vielleicht, aber du selbst hast die Function
DC_GetProgress(oProgress,nCount,nMax)
aufgerufen, also erst das Control und dann die beiden Zahlen. Er hat das nicht.

Der Befehl INDEX ... WHILE ... benötigt aber auf jeden Fall eine .t., sonst bricht er ab.
WHILE <lWhileCondition>
<lWhileCondition> ist ein optionaler logischer Ausdruck, der eine Bedingung vorgibt. Datensätze werden ab dem aktuellen Datensatz so lange in den Index aufgenommen, wie <lWhileCondition> den Wert .T. (wahr) liefert. Sobald der Ausdruck den Wert .F. (falsch) ergibt, wird der Vorgang abgebrochen.
in meinem ersten Beispiel habe ich einen codeblock an WHILE übergeben, bin mir aber nicht sicher, dass dieser in diesem Zusammenhang dann auch ausgeführt wird.
Oder man schreibt WHILE EVAL( {|| ... } ) ...
Ich würde empfehlen, aus dem DCPROGRESS einen prozentualen Fortschrittszähler zu machen
z.B. so ... ?

Code: Alles auswählen

FUNCTION _Progress(oProgress,nMax)
STATIC nCount := 0, nAltPro := 0
LOCAL nPro
IF PCount()>0
  nCount ++
  nPro :=  int( nCount/nMax*100 )
  if nPro > nAltPro
     nAltPro := nPro
     DC_GetProgress(oProgress,nCount,nMax) // ich weiß nicht wie sich das hier verhält, ich habe kein eXpress !
  endif 
ENDIF
RETURN .t.
Die Berechnung je Satz macht zeitlich kaum etwas aus, der Aufruf z.B. von ? / @ SAY oder oTxt:caption := "..." jedoch schon wenn es viele Durchläufe sind !
Gruß
Hubert
xbaseklaus
Rekursionen-Architekt
Rekursionen-Architekt
Beiträge: 246
Registriert: Mi, 04. Jun 2014 12:01
Wohnort: FRANKEN

Re: DCPROGRESS mit INDEX ON ?

Beitrag von xbaseklaus »

Ich komm da auf keinen grünen Zweig -> habs aufgegeben :confused2:
Antworten