* test_s3b_dupa_ui.prg * UI VIZIBIL: capturi "DUPA" pe frm_facturare_articole2 (COMUN\clase\ofacturare.vc2), dupa * aplatizarea chenarelor (BorderWidth=0 pe containere, confirmata in binar). Copie a * test_s3b_referinta_ui.prg cu ACELASI mediu / aceiasi 4 pasi / aceleasi etichete de pas, dar cu * iesirile in fisiere separate (nu suprascrie referinta) ca sa poata fi comparate una langa alta. * * Rulare: powershell -ExecutionPolicy Bypass -File test_s3b_dupa_ui.ps1 (timeout >= 300s) * Log: facturare_unificat\probe_totaluri_log.txt ; capturi in screenshots_dupa\ ; * geometrie in out\geom_dupa_.tsv SET SAFETY OFF SET TALK OFF SET NOTIFY OFF PUBLIC gcUILog, gcSyncDir, gnFail, gnPass gcUILog = "D:\ROA\ROAFACTURARE\COMUN\utile\Teste\facturare_unificat\probe_totaluri_log.txt" gcSyncDir = "D:\ROA\ROAFACTURARE\COMUN\utile\Teste\facturare_unificat\uisync_probe\" STRTOFILE("START " + TTOC(DATETIME()) + CHR(13) + CHR(10), gcUILog) gnFail = 0 gnPass = 0 PUBLIC gcRaport gcRaport = "" ON ERROR DO AfErr WITH ERROR(), MESSAGE(), PROGRAM(), LINENO() ON SHUTDOWN QUIT IF !DIRECTORY("D:\ROA\ROAFACTURARE\COMUN\utile\Teste\facturare_unificat\out") MD "D:\ROA\ROAFACTURARE\COMUN\utile\Teste\facturare_unificat\out" ENDIF DO "D:\ROA\ROAFACTURARE\COMUN\utile\Teste\test_init_env_auto_roafacturare.prg" WITH 'CENTRAL', 'MARIUSM_AUTO', 'ROMFASTSOFT' IF TYPE('gnHandle') <> 'N' OR gnHandle <= 0 DO AfLog WITH "FAIL: conexiune Oracle esuata" DO Final ENDIF SET PROCEDURE TO "D:\ROA\ROAFACTURARE\COMUN\utile\Teste\mock_amessagebox.prg", "D:\ROA\ROAFACTURARE\COMUN\utile\Teste\ui_harness.prg" ADDITIVE PUBLIC gcMockUltimMesaj, gnMockUltimTip gcMockUltimMesaj = "" gnMockUltimTip = 0 DO AfLog WITH "ENV OK, gnAn=" + TRANSFORM(gnAn) + " gnLuna=" + TRANSFORM(gnLuna) IF !actualizeaza_optiuni_program() DO AfLog WITH "FAIL: actualizeaza_optiuni_program()" DO Final ENDIF gnScadereStoc = 0 * seriile de facturi (tipdoc 5) si de incasare (3/16/26) sunt pe utilizator in MARIUSM_AUTO gnIdUtil = 8 goExecutor.oExecuta([begin pack_sesiune.set_Id_Util(?gnIdUtil); end;]) DO AfLog WITH "gnScadereStoc=" + TRANSFORM(gnScadereStoc) * gridextras.vcx e referit din ofacturare.vcx cu cale relativa, rezolvabila doar din exe/IDE SET CLASSLIB TO "D:\ROA\ROAFACTURARE\COMUN\utile\gridextras\gridextras.vcx" ADDITIVE SET PATH TO "D:\ROA\ROAFACTURARE\COMUN\utile\gridextras" ADDITIVE * grd_factura.cCodMat.cboCodmat e declarat AS combosql OF cautare.vcx, dar clasa e in _cb_base.vcx SET CLASSLIB TO "D:\ROA\ROAFACTURARE\COMUN\clase\_cb_base.vcx" ADDITIVE IF USED('crscursuri') USE IN crscursuri ENDIF CREATE CURSOR crscursuri (curs N(12,4), nume_val C(10), multiplicator N(6)) DO creeaza_facturacrs WITH 'crsfactura' SELECT *, CAST(NULL AS C(100)) AS gestiune FROM crsfactura INTO CURSOR crsfact_tmp READWRITE USE IN crsfactura SELECT * FROM crsfact_tmp INTO CURSOR crsfactura READWRITE USE IN crsfact_tmp * cboTipFactura (RowSourceType=3) citeste cursorul local saft_tip_facturi ca pe un tabel - * fara el deschis explicit, Createobject('frm_facturare_articole2') da "File 'saft_tip_facturi.dbf' does not exist" IF !USED('saft_tip_facturi') update_saft_tip_facturi() ENDIF PRIVATE poDate, poGeneratorNumere, loForm, lcTsv, lcRaportFile lcRaportFile = "D:\ROA\ROAFACTURARE\COMUN\utile\Teste\facturare_unificat\out\geom_dupa_raport.txt" * document nou: poDate.incasat ramane 0 la construire - identic Scenariul A din test_s3b_incasare_nealocare.prg poDate = CREATEOBJECT("oDateFactura", 25000, 1) poDate.nIdTipDoc = 5 poDate.totalctva = 1000 DO AfLog WITH "poDate.tip=" + TRANSFORM(poDate.tip) + " poDate.eProforma=" + TRANSFORM(poDate.eProforma) + " poDate.incasat=" + TRANSFORM(poDate.incasat) poGeneratorNumere = CREATEOBJECT("oGeneratorNumere") poGeneratorNumere.ResetNumere() DO ProbaSerii WITH poDate.nIdTipDoc poDate.rezultat_serii = poGeneratorNumere.creeaza_cursor_serii(poDate.nIdTipDoc) loForm = CREATEOBJECT('frm_facturare_articole2') DO Assert WITH VARTYPE(loForm) = 'O', "Createobject frm_facturare_articole2" IF VARTYPE(loForm) <> 'O' DO Final ENDIF DO Assert WITH ObjExists(loForm, 'opt_incasat'), "opt_incasat prezent (poDate.tip intre 1 si 4, deci grupul de incasare exista)" loForm.WindowType = 0 loForm.Show() loForm.WindowState = 2 DOEVENTS FORCE * PROBA aseaza_totaluri(): dovada daca metoda ruleaza si daca scrierile ei sunt anulate ulterior LOCAL lcC, loErr, lcAntePost PRIVATE pcProbeLog pcProbeLog = "D:\ROA\ROAFACTURARE\COMUN\utile\Teste\facturare_unificat\out\probe_totaluri.log" STRTOFILE("PROBA aseaza_totaluri - " + TTOC(DATETIME()) + CHR(13) + CHR(10), pcProbeLog) DO ProbeDumpBanda WITH loForm, "INAINTE" TRY loForm.aseaza_totaluri() STRTOFILE("aseaza_totaluri() a rulat FARA eroare" + CHR(13) + CHR(10), pcProbeLog, 1) CATCH TO loErr STRTOFILE("aseaza_totaluri() a ARUNCAT eroare: " + loErr.Message + " la linia " + TRANSFORM(loErr.LineNo) + " in " + loErr.Procedure + CHR(13) + CHR(10), pcProbeLog, 1) ENDTRY DOEVENTS FORCE DO ProbeDumpBanda WITH loForm, "DUPA (imediat, fara alt eveniment)" STRTOFILE("ltotaluri_asezate=" + TRANSFORM(loForm.ltotaluri_asezate) + CHR(13) + CHR(10), pcProbeLog, 1) WITH loForm.clb_total_baza.lb_explicatie lcC = "lb_explicatie: Caption=[" + .Caption + "] AutoSize=" + TRANSFORM(.AutoSize) + " Width=" + TRANSFORM(.Width) + ; " FontName=" + .FontName + " FontSize=" + TRANSFORM(.FontSize) + " FontBold=" + TRANSFORM(.FontBold) + ; " TXTWIDTH=" + TRANSFORM(TXTWIDTH(ALLTRIM(.Caption), .FontName, .FontSize, IIF(.FontBold, "B", ""))) + ; " FONTMETRIC(6)=" + TRANSFORM(FONTMETRIC(6, .FontName, .FontSize, IIF(.FontBold, "B", ""))) + ; " PRODUS+4=" + TRANSFORM(CEILING(TXTWIDTH(ALLTRIM(.Caption), .FontName, .FontSize, IIF(.FontBold, "B", "")) * FONTMETRIC(6, .FontName, .FontSize, IIF(.FontBold, "B", ""))) + 4) STRTOFILE(lcC + CHR(13) + CHR(10), pcProbeLog, 1) ENDWITH WITH loForm.clb_total_baza.lb_nume_nat lcC = "lb_nume_nat: Caption=[" + .Caption + "] AutoSize=" + TRANSFORM(.AutoSize) + " Width=" + TRANSFORM(.Width) + ; " FontName=" + .FontName + " FontSize=" + TRANSFORM(.FontSize) + " FontBold=" + TRANSFORM(.FontBold) + ; " TXTWIDTH=" + TRANSFORM(TXTWIDTH(ALLTRIM(.Caption), .FontName, .FontSize, IIF(.FontBold, "B", ""))) + ; " FONTMETRIC(6)=" + TRANSFORM(FONTMETRIC(6, .FontName, .FontSize, IIF(.FontBold, "B", ""))) + ; " PRODUS+4=" + TRANSFORM(CEILING(TXTWIDTH(ALLTRIM(.Caption), .FontName, .FontSize, IIF(.FontBold, "B", "")) * FONTMETRIC(6, .FontName, .FontSize, IIF(.FontBold, "B", ""))) + 4) STRTOFILE(lcC + CHR(13) + CHR(10), pcProbeLog, 1) ENDWITH * al doilea apel direct - daca DUPA1 ramane pe valorile vechi, verificam daca inca o rulare produce alta geometrie * (adica scrierile ei ies, dar sunt suprascrise de altceva DUPA ce iese din metoda, nu ignorate de la inceput) TRY loForm.aseaza_totaluri() CATCH TO loErr STRTOFILE("al doilea apel a ARUNCAT eroare: " + loErr.Message + CHR(13) + CHR(10), pcProbeLog, 1) ENDTRY DO ProbeDumpBanda WITH loForm, "DUPA AL DOILEA APEL (fara DOEVENTS intre)" DOEVENTS FORCE DO ProbeDumpBanda WITH loForm, "DUPA AL DOILEA APEL + DOEVENTS FORCE" * PEMSTATUS: confirma daca ltotaluri_asezate exista cu adevarat ca membru pe instanta STRTOFILE("PEMSTATUS ltotaluri_asezate (5=property)=" + TRANSFORM(PEMSTATUS(loForm, 'ltotaluri_asezate', 5)) + CHR(13) + CHR(10), pcProbeLog, 1) * Ipoteza Anchor: un resize REAL de fereastra (WindowState 2->0->2, ca la Show() initial) * reseteaza Left/Width ale containerelor ancorate DUPA ce codul din Resize() le-a scris? loForm.WindowState = 0 DOEVENTS FORCE loForm.WindowState = 2 DOEVENTS FORCE DO ProbeDumpBanda WITH loForm, "DUPA WindowState 2->0->2 (resize real de fereastra)" DO AfLog WITH "Proba scrisa in " + pcProbeLog STRTOFILE(gcRaport, lcRaportFile) DO AfLog WITH "Raport geometrie scris in " + lcRaportFile * nicio alocare de numar nu s-a facut (opt_incasat.Value neschimbat) - Release direct, fara curatenie loForm.Release() RELEASE loForm DO Final *---------------------------------------------------------------------------------------- PROCEDURE DumpSiAnalizeaza * Parcurge Thisform.Objects (top-level, fara recursie in containere), scrie .tsv cu * Name/Class/Left/Top/Width/Height/Visible pentru fiecare obiect cu geometrie, apoi * calculeaza suprapuneri (2D), iesire din zona utila a formularului si perechi lipite * (<4px) pe orizontala/verticala, doar intre controale Visible=.T. Adauga sectiunea la gcRaport. LPARAMETERS toForm, tcEticheta, tcTsvPath LOCAL i, j, loO, lcOut, lnN, lnCount, llVis LOCAL ARRAY laN[400], laC[400], laL[400], laT[400], laW[400], laH[400], laV[400] lnN = 0 lcOut = "Name" + CHR(9) + "Class" + CHR(9) + "Left" + CHR(9) + "Top" + CHR(9) + "Width" + CHR(9) + "Height" + CHR(9) + "Visible" + CHR(13) + CHR(10) lnCount = toForm.Objects.Count FOR i = 1 TO lnCount loO = toForm.Objects(i) IF TYPE('loO.Left') = 'N' AND TYPE('loO.Top') = 'N' AND TYPE('loO.Width') = 'N' AND TYPE('loO.Height') = 'N' AND lnN < 400 llVis = IIF(TYPE('loO.Visible') = 'L', loO.Visible, .T.) lnN = lnN + 1 laN[lnN] = loO.Name laC[lnN] = loO.Class laL[lnN] = loO.Left laT[lnN] = loO.Top laW[lnN] = loO.Width laH[lnN] = loO.Height laV[lnN] = llVis lcOut = lcOut + loO.Name + CHR(9) + loO.Class + CHR(9) + TRANSFORM(loO.Left) + CHR(9) + TRANSFORM(loO.Top) + CHR(9) + TRANSFORM(loO.Width) + CHR(9) + TRANSFORM(loO.Height) + CHR(9) + TRANSFORM(llVis) + CHR(13) + CHR(10) ENDIF ENDFOR STRTOFILE(lcOut, tcTsvPath) DO AfLog WITH "GEOMETRIE [" + tcEticheta + "]: " + TRANSFORM(lnN) + " controale cu geometrie din " + TRANSFORM(lnCount) + " obiecte totale -> " + tcTsvPath LOCAL lnAL, lnAT, lnAR, lnAB, lnBL, lnBT, lnBR, lnBB, lnOvX, lnOvY, lnGap LOCAL lcSectiune lcSectiune = "=== " + tcEticheta + " (forma " + TRANSFORM(toForm.Width) + "x" + TRANSFORM(toForm.Height) + ") ===" + CHR(13) + CHR(10) FOR i = 1 TO lnN IF !laV[i] LOOP ENDIF lnAL = laL[i] lnAT = laT[i] lnAR = laL[i] + laW[i] lnAB = laT[i] + laH[i] IF lnAL < 0 OR lnAT < 0 OR lnAR > toForm.Width OR lnAB > toForm.Height lcSectiune = lcSectiune + "IESIT: " + laN[i] + " (" + laC[i] + ") Left=" + TRANSFORM(lnAL) + " Top=" + TRANSFORM(lnAT) + " Right=" + TRANSFORM(lnAR) + " Bottom=" + TRANSFORM(lnAB) + CHR(13) + CHR(10) ENDIF FOR j = i + 1 TO lnN IF !laV[j] LOOP ENDIF lnBL = laL[j] lnBT = laT[j] lnBR = laL[j] + laW[j] lnBB = laT[j] + laH[j] lnOvX = MIN(lnAR, lnBR) - MAX(lnAL, lnBL) lnOvY = MIN(lnAB, lnBB) - MAX(lnAT, lnBT) IF lnOvX > 0 AND lnOvY > 0 lcSectiune = lcSectiune + "SUPRAPUNERE: " + laN[i] + " (" + laC[i] + ") x " + laN[j] + " (" + laC[j] + ") " + TRANSFORM(lnOvX) + "x" + TRANSFORM(lnOvY) + "px" + CHR(13) + CHR(10) ELSE IF lnOvY > 0 AND lnOvX <= 0 AND -lnOvX < 4 lnGap = -lnOvX lcSectiune = lcSectiune + "LIPIT-ORIZ: " + laN[i] + " - " + laN[j] + " gap=" + TRANSFORM(lnGap) + "px" + CHR(13) + CHR(10) ENDIF IF lnOvX > 0 AND lnOvY <= 0 AND -lnOvY < 4 lnGap = -lnOvY lcSectiune = lcSectiune + "LIPIT-VERT: " + laN[i] + " - " + laN[j] + " gap=" + TRANSFORM(lnGap) + "px" + CHR(13) + CHR(10) ENDIF ENDIF ENDFOR ENDFOR gcRaport = gcRaport + lcSectiune + CHR(13) + CHR(10) ENDPROC PROCEDURE DumpGrilaRecursiv * Harta de geometrie recursiva: coboara in .Objects pe oricate niveluri (containere compozite * clb_tx_simplu / ct_clb_cautare / etc.), scrie Name ca traseu punctat de la formular * (Ct_clb_agent.clb_tx_cautare.Lb_simplu1), plus AbsLeft/AbsTop absolute fata de formular * si Caption/Value taiat la 40 caractere - necesare ca sa se detecteze suprapunerile si * textele taiate din interiorul containerelor, invizibile in harta plata geom_dupa_*.tsv. LPARAMETERS toForm, tcTsvPath LOCAL lcOut lcOut = "Name" + CHR(9) + "Class" + CHR(9) + "Left" + CHR(9) + "Top" + CHR(9) + "Width" + CHR(9) + "Height" + CHR(9) + "Visible" + CHR(9) + "AbsLeft" + CHR(9) + "AbsTop" + CHR(9) + "Caption" + CHR(13) + CHR(10) lcOut = lcOut + ColectGrila(toForm, "", 0, 0, 0, .T.) STRTOFILE(lcOut, tcTsvPath) DO AfLog WITH "GEOMETRIE-GRILA: scris " + tcTsvPath ENDPROC FUNCTION ColectGrila * Recursie pe .Objects (nu PEMSTATUS) - garda Type('loO.Left')='N' fiindca nu orice membru * are geometrie (separatoare, columns de grid etc. nu ajung aici, gridurile nu au .Objects). * coloana Visible e vizibilitatea EFECTIVA (proprie AND a parintelui) - un copil dintr-un * container ascuns are Visible propriu .T. dar nu se deseneaza. LPARAMETERS toContainer, tcPrefix, tnParentAbsLeft, tnParentAbsTop, tnDepth, tlParentVisEff LOCAL i, loO, lcName, lnAbsL, lnAbsT, lcCaption, llVisEff, lcVisTxt, lcOut IF tnDepth > 15 RETURN "" ENDIF lcOut = "" FOR i = 1 TO toContainer.Objects.Count loO = toContainer.Objects(i) IF TYPE('loO.Left') = 'N' AND TYPE('loO.Top') = 'N' AND TYPE('loO.Width') = 'N' AND TYPE('loO.Height') = 'N' lcName = IIF(EMPTY(tcPrefix), loO.Name, tcPrefix + "." + loO.Name) lnAbsL = tnParentAbsLeft + loO.Left lnAbsT = tnParentAbsTop + loO.Top lcCaption = "" IF TYPE('loO.Caption') = 'C' lcCaption = loO.Caption ELSE IF TYPE('loO.Value') = 'C' lcCaption = loO.Value ENDIF ENDIF lcCaption = STRTRAN(lcCaption, CHR(9), " ") lcCaption = LEFT(lcCaption, 40) llVisEff = IIF(TYPE('loO.Visible') = 'L', loO.Visible, .T.) AND tlParentVisEff lcVisTxt = TRANSFORM(llVisEff) lcOut = lcOut + lcName + CHR(9) + loO.Class + CHR(9) + TRANSFORM(loO.Left) + CHR(9) + TRANSFORM(loO.Top) + CHR(9) + TRANSFORM(loO.Width) + CHR(9) + TRANSFORM(loO.Height) + CHR(9) + lcVisTxt + CHR(9) + TRANSFORM(lnAbsL) + CHR(9) + TRANSFORM(lnAbsT) + CHR(9) + lcCaption + CHR(13) + CHR(10) IF TYPE('loO.Objects.Count') = 'N' lcOut = lcOut + ColectGrila(loO, lcName, lnAbsL, lnAbsT, tnDepth + 1, llVisEff) ENDIF ENDIF ENDFOR RETURN lcOut ENDFUNC PROCEDURE ProbeDumpBanda * Logheaza Left/Width pentru cele sase containere ale benzii de totaluri, cu eticheta data. LPARAMETERS toForm, tcEticheta LOCAL lcL, laNume[6], i laNume[1] = "clb_total_baza" laNume[2] = "clb_discount_articole" laNume[3] = "clb_discount" laNume[4] = "clb_motiv_discount" laNume[5] = "clb_total_tva" laNume[6] = "clb_total_factura" lcL = "--- " + tcEticheta + " ---" + CHR(13) + CHR(10) FOR i = 1 TO 6 lcL = lcL + laNume[i] + " Left=" + TRANSFORM(EVALUATE("toForm." + laNume[i] + ".Left")) + ; " Width=" + TRANSFORM(EVALUATE("toForm." + laNume[i] + ".Width")) + ; " Anchor=" + TRANSFORM(EVALUATE("toForm." + laNume[i] + ".Anchor")) + CHR(13) + CHR(10) ENDFOR STRTOFILE(lcL, pcProbeLog, 1) ENDPROC PROCEDURE ProbaSerii * apel direct al procedurii Oracle din creeaza_cursor_serii: logheaza eroarea reala (goExecutor * ar deschide amessagebox modal, care agata rularea headless) si incalzeste starea pachetului LPARAMETERS tnIdTipDoc LOCAL lnOk, laErr[1], i, lcSql PRIVATE pnIdTipDoc, pnRezultat pnIdTipDoc = tnIdTipDoc pnRezultat = 0 lcSql = "{call " + gcS + ".pack_serii_numere.verifica_cursor_serii(?pnIdTipDoc,?gnIdUtil,?gnIdSucursala,?@pnRezultat)}" FOR i = 1 TO 3 lnOk = SQLEXEC(gnHandle, lcSql, "crsprobaserii") IF lnOk > 0 DO AfLog WITH "proba serii OK la incercarea " + TRANSFORM(i) + ", pnRezultat=" + TRANSFORM(pnRezultat) + " randuri=" + TRANSFORM(RECCOUNT("crsprobaserii")) USE IN (SELECT("crsprobaserii")) EXIT ELSE AERROR(laErr) DO AfLog WITH "proba serii ESEC la incercarea " + TRANSFORM(i) + ": " + TRANSFORM(laErr[1]) + " / " + TRANSFORM(laErr[2]) + " / " + TRANSFORM(laErr[5]) ENDIF ENDFOR ENDPROC FUNCTION ObjExists * cautare recursiva: controalele mutate in containere nu mai sunt in Objects direct LPARAMETERS toContainer, tcName LOCAL i, loO FOR i = 1 TO toContainer.Objects.Count loO = toContainer.Objects(i) IF UPPER(loO.Name) == UPPER(tcName) RETURN .T. ENDIF IF TYPE('loO.Objects.Count') = 'N' IF ObjExists(loO, tcName) RETURN .T. ENDIF ENDIF ENDFOR RETURN .F. ENDFUNC PROCEDURE Assert LPARAMETERS tlCond, tcMsg IF tlCond gnPass = gnPass + 1 DO AfLog WITH "PASS: " + tcMsg ELSE gnFail = gnFail + 1 DO AfLog WITH "FAIL: " + tcMsg ENDIF ENDPROC PROCEDURE AfLog LPARAMETERS tcMsg STRTOFILE(tcMsg + CHR(13) + CHR(10), gcUILog, 1) ENDPROC PROCEDURE AfErr LPARAMETERS tnErr, tcMsg, tcProg, tnLine gnFail = gnFail + 1 DO AfLog WITH "ERROR " + TRANSFORM(tnErr) + " [" + tcProg + ":" + TRANSFORM(tnLine) + "] " + tcMsg ENDPROC PROCEDURE Final DO AfLog WITH "TOTAL pass=" + TRANSFORM(gnPass) + " fail=" + TRANSFORM(gnFail) DO AfLog WITH "END " + TTOC(DATETIME()) DO HarnessDone WITH 'done' QUIT ENDPROC