FoxPro Document Display
Het bouwen van een high-speed document viewer voor oudere FoxPro-applicaties zonder eerst de host-applicatie te vragen om te moderniseren.
Plattform
Visual FoxPro / ActiveX
Stapel
C++, ATL, COM, GDI, WIC, PDFium
Doel
Snelle in-form weergave van JPG, PNG en PDF-bestanden
Overzicht van het project
Dit project oplost een veel voorkomend legacy-software-probleem: gebruikers hebben behoefte aan een modern documentbekijken in een applicatie die nooit voor hem is ontworpen. In dit geval is de hostomgeving Visual FoxPro, wat betekent dat de oplossing zich moest gedragen als een klassieke ActiveX-besturing, een conservatieve COM-interface moest blootstellen, strikt 32-bit bleef en onstabiliteit moest voorkomen die het hostproces zou kunnen verlagen.
Het resultaat is: FoxDocViewerHet ondersteunt PDF's via PDFium, afbeeldingsformaten via Windows Imaging Component, en pakt de hele pijplijn in een interface die FoxPro betrouwbaar kan noemen met behulp van vertrouwde typen zoals BSTR, LANG, Twee keer en VARIANT.
Hoe de uitvoering werkt
De architectuur wordt opzettelijk verdeeld in gefocuste lagen, zodat de COM-geconfronteerde schelp klein blijft en de renderinglogic uitbreidbaar blijft.
1. Een COM-schuil die op FoxPro is afgestemd
De ActiveX controle is gebouwd met ATL en onthult een dubbele interface voor late binding en vtable toegang. In de praktijk betekent dat FoxPro de kijker kan besturen met eenvoudige oproepen zoals het laden van een documentlijst, het verplaatsen tussen pagina's, het veranderen van zoomniveaus en het lezen van de staat zoals pagina's telling of het actieve documentpad.
Een subtiel onderdeel van de implementatie is de path ingestion layer. FoxPro kan arrays uitzenden in vormen die niet altijd intuïtief zijn, met inbegrip van eendimensionale en tweedimensionale varianten. Veiligheid De waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van de waarde van
2. Een controller die navigatie, zoom en staat bezit
Achter de ActiveX-laag zit een toegewijde bekijkbeheerder. Deze klasse weet niets over Win32 schilderen of COM, die de logica schoon houdt. Het bezit het huidige document, de huidige pagina, zoommodus, zoompercentage en cache levenscyclus.
Dat scheiding is belangrijk omdat het een historisch rommelig soort component verandert in een voorspelbare staat machine. Het schakelen van documenten resets de actieve pagina, fit modus herbereken zoom van het cliënt gebied, en de fout staat wordt gehandhaafd op één plaats in plaats van door te lekken via meerdere lagen.
3. Format adapters voor PDF's en afbeeldingen
De kijker gebruikt afzonderlijke adapters voor verschillende bestandstypen. JPG en PNG decoderen worden behandeld via Windows Imaging Component, die afbeeldingen omzet in een genormale 32-bit BGRA-formaat en schaalt ze met de hogere kwaliteit interpolatie van WIC. PDF's worden behandeld via PDFium, dynamisch geladen op runtime in plaats van statisch gekoppeld aan de bediening.
Deze dynamische laadstrategie is belangrijk voor de implementatie. pdfium.dll De host blijft in leven, en de implementatiefouten worden weergegeven als herstellbare runtime feedback in plaats van een gebroken registratie- of startfout.
4. Snelle rendering door caching en preloading
De implementatie maakt gebruik van een beperkte minst recent gebruikte pagina cache gesloten door document, pagina en zoom emmer. Zoom waarden worden opzettelijk ingewikkeld in emmers, zodat de cache niet op elke kleine zoom verandering trasht. Dit is een van die details die een buitengewone invloed heeft op de waargenomen snelheid.
De bediening is ook voorzien van een lichte timer die aangrenzende pagina's vooraf weergeeft wanneer de gebruikersinterface inactief is. Dat betekent dat de volgende of vorige pagina vaak al warm is in het geheugen bij de tijd dat de gebruiker navigert, waardoor het draaien van pagina's onmiddellijk voelt, ook al gebeurt decodering en rasterisering in native code achter de schermen.
5. Flikkervrij tekenen in een ouderwetse host
De laatste fase is de renderingsmachine, die een back buffer buiten het scherm gebruikt en GDI wordt gebruikt om in het besturingsvenster zonder flitsen te schilderen. Scrollbalken worden bijgewerkt vanaf de logische doekgrootte, pagina's worden gecentreerd wanneer ze kleiner zijn dan de viewport, en de back buffer groeit alleen wanneer het nodig is om de grootte te houden churn goedkoop.
Dit klinkt misschien laag, maar het is precies waar het vertrouwen van de gebruiker wordt gewonnen of verloren in desktopsoftware.
Belangrijke uitdagingen
Modern rendering overbruggen met een legacy applicatiemodel
De host-applicatie verwacht een klassiek COM-gedrag, niet een moderne embedded browser of beheerde runtime. Dat sluit veel eenvoudige oplossingen uit en dwingt de implementatie om binnen de beperkingen van ActiveX, 32-bit hosting en de berichtgedreven levenscyclus van een traditionele Windows-controle te passen.
Het maken van FoxPro datastructuren voorspelbaar
FoxPro array gedrag kan verrassend ongemakkelijk zijn wanneer waarden de COM-grens overschrijden. VARIANT en Veiligheid Het werk met real-world interoperabiliteit betekende het verantwoorden van hoe FoxPro daadwerkelijk arrays uitzendt, niet hoe een pure COM-specificatie zegt dat het moet.
Balancerende snelheid met geheugengebruik
PDF's en afbeeldingen met een hoge resolutie kunnen snel geheugen verbruiken zodra ze rasterig zijn gemaakt. De cache van pagina's gebruikt daarom een beperkte capaciteit met uitzetting, terwijl zoombucketing een vloed van bijna identieke gecacheerde bitmaps voorkomt. Het doel was geen maximale caching tegen elke prijs, maar een stabiele reactiviteit onder realistische desktopworkloads.
Veilig mislukken binnen het gastproces
Een harde crash in de kijker zou een harde crash in FoxPro zelf zijn. Vanwege dat, de controle was ontworpen om fouten te melden door staat en gebeurtenissen, oude inhoud zichtbaar te houden als een nieuw document niet wordt geladen, en systeembronnen deterministisch vrij te geven. Stabiliteit was geen leuk te hebben functie; het maakte deel uit van de productdefinitie.
Het resultaat
FoxDocViewer geeft een oude zakelijke applicatie een moderne documenten bekijken mogelijkheid zonder het herschrijven van het hostplatform. Gebruikers kunnen PDF's en afbeeldingen binnen de bestaande workflow openen, pagina's snel navigeren, zoomen en bewegen tussen documenten met minimale latentie.
Vanuit een ingenieursperspectief is het project een goed voorbeeld van pragmatische modernisering: de interface conservatief houden, formatespecifieke logica isoleren, het renderingspad optimaliseren waar het van belang is en de interoperabiliteit en de afhandeling van storingen behandelen als eerste-klasse ontwerpproblemen in plaats van achterafdenken.
Belangrijkste punten
Native ActiveX control voor Visual FoxPro. Dynamische PDFium integratie. WIC ondersteunde afbeelding decoderen. Double-buffered GDI rendering. Error-first COM-ontwerp dat het hostproces beschermt.