Info-books
BI5c
Inform 5-6
Toegepaste Informatica Boekhouden-informatica Informaticabeheer
Deel 5c:
Programmeren voor een bedrijfseconomische toepassing: een facturatie in Access 2000/2002 J. Gils – E. Goossens
Hoofdstuk 6 Betalingen registreren en opvolgen
6.1
De betalingen registreren
6.1.1 Probleemstelling
De kredietwaardige klanten betalen hun facturen pas na een bepaalde termijn. In een dialoogvenster wordt in een keuzelijst met invoervak het factuurnummer gevraagd. Als het factuurnummer gekend is worden de belangrijkste gegevens van de factuur en van de klant getoond. De bedragen worden zowel in USD als in EUR weergegeven. We gaan er van uit dat een klant zowel in EUR als in USD kan betalen en dat het mogelijk is dat de klant slechts een deel van het bedrag betaalt. Standaard wordt in het selectievakje ‘Klant betaalt in Euro’ de waarde getoond die in de klantenfiche opgeslagen is. 6.1.2 Probleemanalyse Het invulformulier FRM FACTUURBETAAL wordt ontworpen op basis van een query, QRYFACTUURGEGEVENS, die de nodige velden voor dit formulier bevat. Het veld FA _BETDATUM moet nog aan de query toegevoegd worden. TIP
Als je in deze query geen gebruik maakt van criteria, dan kun je hem ook nog voor andere doeleinden gebruiken: een lijst met de slechte betalers, de brief aan de slechte betalers, …
De tabel TBLFACTUUR bevat een veld FA _SALDO waarin het bedrag wordt bijgehouden dat de klant nog moet betalen. Het wegschrijven van deze factuurgegevens gebeurt in de procedure EINDTOTALEN (). Er zijn twee mogelijkheden: ? de klant is kredietwaardig en krijgt een betalingstermijn; ? in het veld FA _SALDO komt het eindtotaal van de factuur (in EUR); J. Gils – E. Goossens
Bedrijfseconomische toepassing
77
? ? ?
in het veld FA _DATUM komt de factuurdatum; in het veld FA _VERVALDAG komt de vervaldag, dit is de factuurdatum + de betalingstermijn. de klant is niet kredietwaardig en krijgt geen betalingstermijn. ? in het veld FA _SALDO komt 0: de klant moet bij ontvangst van de factuur onmiddellijk betalen; ? in de velden FA _DATUM , FA _VERVALDAG en FA _BETDATUM komt de factuurdatum.
Het formulier bevat drie invoervelden: ? de keuzelijst waarin je het factuurnummer kiest: CBOFA _NR; De keuzelijst moet alleen maar de facturen tonen die nog niet betaald zijn: FA _SALDO>0. De gegevens van de keuzelijst komen uit dezelfde query als de gegevens op het formulier. ? het selectievakje om aan te geven of de klant in USD of in EUR betaalt: CHK EUR; Dit mag geen afhankelijk besturingselement zijn omdat een wijziging in dit veld zou doorgetrokken worden naar het veld KL_EUR uit de tabel TBLKLANT. ? het tekstvak waarin het betaald bedrag komt: TXTBETAALDBEDRAG. De opmaak van dit veld hangt af van de waarde in KL_EUR uit de tabel TBLKLANT. In de andere velden mag een wijziging niet mogelijk zijn. Als je de keuzelijst ontwerpt op basis van ‘Een record in het formulier opzoeken op basis van de waarde die geselecteerd is in de keuzelijst met invoervak’, dan zullen de afhankelijke velden op het invulformulier automatisch de factuurgegevens tonen. Na een selectie in de keuzelijst moet je de opmaak van het invoerveld voor het te betalen bedrag, TXTBETAALD BEDRAG, aanpassen aan een EUR- of een USD-opmaak. Deze opmaak hangt af van het veld KL_EUR uit de tabel TBLKLANT, waarin bewaard wordt of de klant in EUR of in USD gefactureerd wordt. Dit veld moet ook in de query van de keuzelijst opgenomen worden. Met behulp van tekstvakken wordt de waarde in USD berekend. Om vergissingen te vermijden wordt een betaling maar effectief na een klik op de knop ‘Registratie’. In dat geval moeten drie acties uitgevoerd worden: ? de ingevoerde waarde in TXTBETAALD BEDRAG van het saldo, FA _SALDO, aftrekken; ? de betaaldatum, FA _BETDATUM , wegschrijven; ? de waarde van het vak TXTBETAALD BEDRAG terug op 0 zetten. Het is goed mogelijk dat de klant alleen maar een deel van de factuur betaalt. TIP
Omwille van omzettings- en afrondingsproble men kan het zijn dat een waarde, ingevoerd in USD, niet exact overeenkomt met de waarde in EUR. Je lost dit probleem met de volgende uitspraak op: als de absolute waarde van het verschil van het saldo en het betaalde bedrag kleiner is dan of gelijk is aan 0,01 dan mag je de betaalde waarde gelijkstellen aan het saldo. dblBedrag = txtBetaaldBedrag.Value If Abs(dblBedrag - [FA_SALDO]) <= 0.01 Then dblBedrag = [FA_SALDO]
78
Bedrijfseconomische toepassing
J. Gils – E. Goossens
Als je het formulier opent, zal de focus altijd op de eerste record van de query gericht zijn: het gevolg daarvan is dat alle gekoppelde velden een waarde zullen bevatten. Dit detail kun je oplossen door alle objecten op het formulier te verbergen, behalve de keuzelijst en de knop ‘Sluiten’. Nadat je in de keuzelijst een keuze gemaakt hebt worden alle objecten zichtbaar gemaakt. Dim intTeller As Integer If Not (txtBetaaldBedrag.Visible) Then For intTeller = 0 To Me.Controls.Count – 1 Me.Controls(intTeller).Visible = True Next intTeller End If
De besturingselementen (Controls) hebben allemaal een volgnummer. Het aantal besturingselementen wordt gegeven door Me.Controls.Count. Elk besturingselement kun je afzonderlijk benaderen via Me.Controls(index) waarbij voor het eerste element de index gelijk is aan 0 en voor het laatste gelijk aan Me.Controls.Count - 1. Een goed programma laat ook geen invoer toe die groter is dan het te betalen saldo. Overzicht: Na een selectie in de keuzelijst (Na Bijwerken) moeten zes taken uitgevoerd worden: ? de overeenkomstige record in de query opzoeken; De code hiervan wordt automatisch gegenereerd tijdens het ontwerp van de keuzelijst. ? als er nog onzichtbare besturingselementen zijn moeten die zichtbaar gemaakt worden; ? de waarde van KL_EUR naar het selectievakje CHK EUR kopiëren; ? de opmaak van TXTBETAALD BEDRAG in USD of EUR tonen, afhankelijk van de waarde in CHK EUR; ? het label dat bij dit tekstvak hoort een gepast opschrift geven; ? het invoervak TXTBETAALD BEDRAG de focus geven. Na een wijziging in het selectievakje CHK EUR moeten de volgende taken uitgevoerd worden: ? de opmaak van TXTBETAALD BEDRAG in USD of EUR tonen; ? het label van dit tekstvak een gepast opschrift geven; ? het invoervak TXTBETAALD BEDRAG de focus geven. Bij klikken op de knop ‘Registreren’ moeten de volgende taken uitgevoerd worden: ? het ingevoerde bedrag eventueel omzetten naar EUR, afhankelijk van de waarde in CHK EUR, en in dat geval afrondingsfouten voorkomen; ? de gebeurtenis annuleren als de ingevoerde waarde groter is dan het saldo, in het andere geval moet de ingevoerde waarde van het saldo afgetrokken worden; ? de betaaldatum in het veld FA _BETDATUM van TBLFACTUUR wegschrijven; ? het invoervak TXTBETAALD BEDRAG terug op 0 zetten; ? de keuzelijst CBOFA _NR de focus geven. Bij klikken op de knop ‘Einde’ moet het formulier gesloten worden.
J. Gils – E. Goossens
Bedrijfseconomische toepassing
79
6.1.3 Objectentabel Formulier Besturingselementen
frmFactuurBetaal cboFa_Nr, lblFa_Nr lblEUR, chkEUR txtBetaaldBedrag, lblBetaaldBedrag FA _SALDO, txtSaldo, lblSaldo KL_NR, lblKlant KL_NAAM, WOONPL FA _DATUM , lblDatum FA _VERVALDAG, lblVervaldag TOTAAL, txtTotaal, lblTotaal cmdSluiten, cmdRegistreer
6.1.4 Oplossing Opdrachten 1. De query met de factuur- en klantgegevens ontwerpen a. Ontwerp of wijzig de query QRYFACTUURGEGEVENS die alle gegevens bevat die nodig zijn om het invulformulier te ontwerpen. Uit welke tabellen komen de gegevens? b. Het factuurtotaal bereken je in een rekenveld, TOTAAL. c. Vermits deze query ook voor andere doeleinden gebruikt zal worden, moet je ook het volledige klantadres erin opnemen. Daarom zet je beter geen criterium bij het veld FA _SALDO. d. Bewaar tenslotte de query onder de naam QRYFACTUURGEGEVENS. 2. Het invulformulier om betalingen te registreren ontwerpen a. Ontwerp een nieuw formulier met de query QRYFACTUUR GEGEVENS als recordbron. Wijzig de eigenschappen van het formulier zodanig dat er geen navigatiebalken, schuifbalken, … getoond worden. Laat voorlopig de eigenschap KNOP S LUITEN op JA staan. b. Zet de wizard af, voeg de knop ‘Einde’ toe en noem hem CMDEINDE. Verbind de knop met de gepaste actie. c. Voeg de knop ‘Registreren’ toe en noem hem CMDREGISTREREN . d. Voeg de keuzelijst met invoervak, CBOFA _NR, toe: dit is een keuzelijst die een record opzoekt op basis van de geselecteerde waarde. De gekozen waarde in de keuzelijst mag niet in een veld opgeslagen worden: kies de optie WAARDE BEWAREN VOOR LATER GEBRUIK. De keuze lijst moet het factuurnummer, de naam en de woonplaats van de klant tonen. Open het eigenschappenvenster van de keuzelijst, ga naar de rijbron en open de query. Het veld FA _SALDO moet in de query opgenomen zijn omdat hierin een criterium komt. Welk criterium? (Welke facturen wil je tonen?) e. Teken een selectievakje en noem het CHK EUR. f. Zet de overige besturingselementen op het formulier. Noem het veld met het betaald bedrag TXTBETAALD BEDRAG. g. Verberg alle besturingelementen behalve de keuzelijst en de knop ‘Einde’. Wijzigingen zijn alleen maar toegelaten in de keuzelijst, het selectievakje CHK EUR en het veld TXTBETAALD BEDRAG. h. Bewaar het formulier en noem het FRM FACTUURBETAAL. 80
Bedrijfseconomische toepassing
J. Gils – E. Goossens
i. Verbind de knop CBOFA _NR met de gewenste programmacode. j. Verbind de keuzelijst CMDREGISTREREN met de gewenste programmacode. Wat moet je allemaal voorzien? ? als het nodig is het betaalde bedrag omzetten in EUR en de afrondingsfout omze ilen; ? als het betaalde bedrag groter is dan het saldo een boodschap geven en de gebeurtenis annuleren; ? het saldo verminderen; ? het tekstvak TXTBETAALD BEDRAG terug op 0 zetten. k. Test de werking van het formulier. l. Druk de programmacode af. Er duikt nu een onverwacht probleem op! In het formulier FRM FACTUUR zijn wijzigingen alleen maar toegestaan als je in de laatste record zit. Dit wordt geregeld via de procedures WIJZIGINGEN TOEGELATEN () en W IJZIGINGEN VERBODEN () die opgeroepen worden BIJ AANWIJZEN van het formulier, m.a.w. telkens als een factuur op het scherm getoond wordt. De eindtotalen worden altijd weggeschreven bij verlaten van het subformulier, dit wordt niet belet door de procedure WIJZIGEN VERBODEN(). Stel dat je de betaling van een factuur registreert, dan wordt het saldo op 0 gezet en wordt de betaaldatum in FA _BETDATUM genoteerd. Als je dat betaalde factuur via het formulier FRM FACTUUR opent, en je klikt in de artikelenlijst, dan worden de eindtotalen opnieuw weggeschreven bij verlaten van de artikelenlijst en dus ook het saldo wordt opnieuw weggeschreven … en de klant kan opnieuw betalen. Hoe oplossen? Als een betaling nog niet geregistreerd is, dan zal het veld FA _BETDATUM een null- waarde bevatten. Hiermee kun je het probleem oplossen. ? In de gebeurtenisprocedure BIJ AANWIJZEN van frmFactuur moet je een voorwaarde bijzetten: als het factuurnummer null is of je zit in de laatste record EN het veld FA _BETDATUM is null dan mag je wijzigen. Private Sub Form_Current() '[cboKlant].SetFocus If ([FA_NR] = DMax("Fa_nr", "tblFactuur") Or IsNull([FA_NR])) And IsNull([FA_BETDATUM]) Then ... End Sub
?
In de procedure Eindtotalen() mogen de totalen niet weggeschreven worden als de betaaldatum ingevuld is, wijzig daarom de programmacode als volgt: Private Sub Eindtotalen() If IsNull([FA_BETDATUM]) Then If blnEUR Then ... End Sub
TIP
‘If Form.AllowEdits then’ kun je in de procedure Eindtotalen() ook gebruiken in plaats van ‘If IsNull([FA_BETDATUM]) Then’.
J. Gils – E. Goossens
Bedrijfseconomische toepassing
81
6.2
Een maanbrief aan de wanbetalers
82
Bedrijfseconomische toepassing
J. Gils – E. Goossens
6.2.1 Probleemstelling Maandelijks wordt een maanbrief gestuurd naar alle klanten die hun factuur niet tijdig betaald hebben. Omdat het mogelijk is dat een klant meerdere facturen niet tijdig betaald heeft, moet de brief een overzicht geven van alle onbetaalde facturen. 6.2.2 Probleemanalyse Dit is een voorbeeld van een rapport dat de factuurgegevens groepeert per klant. De rijbron van dit rapport is de query QRYFACTUUR GEGEVENS. Waarschijnlijk bevat de query nog niet alle velden, daarom moet de query aangepast worden. TIP
Voeg alleen maar velden achteraan toe want anders krijg je problemen met de verwijzingen zoals Column(1).
Een klant heeft niet tijdig betaald als: ? het saldo, FA _SALDO, groter is dan 0; ? en de vervaldag, FA _ VERVALDAG, overschreden is. Omdat het niet de bedoeling is een criterium in de query te zetten, moet je in dit geval het criterium bij de rapporteigenschap FILTER zetten. Vergeet niet de filter aan te zetten!
TIP
Als je wel een criterium in de query zet, kun je deze query alleen maar voor deze toepassing gebruiken. Als de filter toch problemen zou geven, vertrek dan van een nieuwe query.
Aangezien het de bedoeling is dat de onbetaalde facturen per klant afgedrukt worden, moet er gegroepeerd worden per klant. De volledige brief met de klantgegevens wordt in de KL_NR-koptekst en KL_NR-voettekst gezet. De factuurgegevens komen in de detailsectie. De factuurgegevens moeten volgens FA _NR gesorteerd worden. Bij de eigenschappen van KL_NR-koptekst moet je N IEUWE PAGINA instellen op VOOR SECTIE. 6.2.3 Oplossing Opdracht 3. De maanbrief ontwerpen a. Open een nieuw rapport, kies de query QRYFACTUUR GEGEVENS als recordbron. b. Klik op de knop SORTEREN EN GROEPEREN . Groepeer op het veld KL_ NR, voorzie een koptekst en een voettekst. Sorteer ook op het veld FA _NR. c. Tracht het bijgevoegde ontwerp na te maken. J. Gils – E. Goossens
Bedrijfseconomische toepassing
83
TIP
84
Als er geen klant voldoet aan de voorwaarde voor een maanbrief, dan zal er een lege brief met foutmeldingen afgedrukt worden. Wil je dit omzeilen dan moet je het rapport vanuit een formulier oproepen zodat je eerst kunt testen of er wel een maanbrief gestuurd moet worden.
Bedrijfseconomische toepassing
J. Gils – E. Goossens
Besluit Omdat het mogelijk is dat een klant een factuur maar gedeeltelijk betaalt, moet in de tabel TBLFACTUUR het saldo bijgehouden worden dat de klant nog moet betalen. Tevens wordt de betaaldatum weggeschreven. Deze datum is belangrijk als je een overzicht van de omzet over een bepaalde periode wilt maken. Dankzij de vervaldag en het saldo krijg je een overzicht van de klanten die te laat zijn met betalingen. Aan die klanten kun je een brief sturen. Zo’n brief kun je in een tekstverwerker ontwerpen en koppelen aan een query die de gewenste adressen levert of je kunt zo’n brief via een rapport afdrukken. Deze laatste methode is de snelste en eenvoudigste maar ze laat geen improvisatieruimte aan een niet ingewijde gebruiker. In deze toepassingen wordt veel gebruik gemaakt van keuzelijsten waaruit meerdere waarden met de eigenschap Column() afgelezen worden en die vervolgens aan andere nietafhankelijke besturingselementen toegewezen worden. De collectie Controls is de verzameling van alle besturingselementen op een rapport of een formulier. Elk besturingselement krijgt in die verzame ling een volgnummer en is bereikbaar via de eigenschap Controls(index). De nummering begint bij nul. Met behulp van een lusstructuur kunnen alle objecten bewerkt worden. De uitdrukking Controls.Count geeft het aantal besturingselementen. Er kunnen afrondingsfouten optreden bij de omzetting van USD naar EUR. Alhoewel de fouten zeer klein zijn kunnen ze toch aanleiding geven tot onverwachte problemen. Daarom moet er bij de vergelijking van een omgezet bedrag naar EUR met een niet omgezet bedrag in EUR rekening gehouden worden met een miniem verschil dat uiteindelijk verwaarloosd moet worden.
Wat je moet kennen en kunnen: ? ? ?
een geschikte oplossing vinden voor een reëel bedrijfsprobleem; alert zijn voor afrondingsfouten; de betekenis van een afhankelijk en een niet-afhankelijk besturingselement juist inschatten.
Opdrachten 4. Druk een lijst af met klanten die overtijd zijn met hun betalingen. 5. Druk van de niet betaalde facturen waarvan de vervaldag verstreken is, per klant een lijst met de gegevens van de niet betaalde facturen. 6. Druk een lijst af met binnengekomen betalingen in een bepaalde periode. 7. Druk van één klant een lijst af met alle facturen in een bepaalde periode.
J. Gils – E. Goossens
Bedrijfseconomische toepassing
85