Visual Studio LightSwitch in de praktijk–Deel 6–Logica toevoegen aan een entiteit

Note: since there’s quite a lot of content on Visual Studio LightSwitch available in English on the web already, I decided to publish this series in Dutch.

Begin 2011 heeft Microsoft de eerste beta van VS LightSwitch met Go-Live licentie gelanceerd, een nieuw product in de Visual Studio familie, waarmee razendsnel zowel web- als desktop SilverLight "Line of Business" applicaties kunnen worden gemaakt. Hoewel de doelgroep van VS LightSwitch niet primair bestaat uit hard-core .net developers, zal het ook voor deze groep zeker waardevol kunnen zijn om de mogelijkheden en beperkingen van LightSwitch te leren kennen.

In de aanloop naar DevDays11 ben ik begonnen met een serie blogs over dit onderwerp. De eerste post was het inleidende artikel. De volgende artikelen zijn/worden:

Inleiding

Eén van de belangrijke functionaliteiten van de applicatie die ik in deze serie artikelen aan het maken ben, is het eenvoudig kunnen maken van een doorlopende afspraak. De use case is op zich niet moeilijk:

Een docent moet eenvoudig kunnen registreren dat met een student is afgesproken dat deze van datum A tot datum B, op bepaalde momenten in de week voor ondersteuning langs komt. In het overzicht afspraken moeten de studenten die ten gevolge van een dergelijke afspraak worden verwacht, ook te zien zijn, en moet kunnen worden geregistreerd of zij daadwerkelijk zijn gekomen.

Hoewel er – zoals zo vaak in software ontwikkeling – natuurlijk meer wegen zijn die naar Rome leiden, heb ik er hier voor gekozen om bij het bewaren van een DoorlopendeAfspraak te zorgen dat individuele afspraken worden aangemaakt, die aan de DoorlopendeAfspraak gekoppeld zijn. Dat houdt natuurlijk ook in dat, indien de DoorlopendeAfspraak gewijzigd wordt, de bijbehorende afspraken die vòòr vandaag liggen, ook moeten worden aangepast.

Bij een DoorlopendeAfspraak wordt voor iedere dag van de week (maandag t/m vrijdag) vastgelegd of de student op die dat dient de komen (middels een boolean veld) en zo ja, om hoe laat (string). Vooral voor wat betreft het tijd-veld zijn natuurlijk andere keuzes mogelijk, maar omdat ik hier met een bestaand datamodel te maken heb, kies ik nu hiervoor.

Om te beginnen pas ik de visual tree wat aan om het scherm handiger te laten werken en vooral wat minder langerekt te zijn. Dit scherm telt immers veel, kleine velden:

image
Figuur 1: Aanpassingen aan de visual tree voor een handiger schermlayout

De UI is hiermee wat mij betreft klaar. Alles wat ik nu nog moet doen, is het toevoegen van de juiste logica om:

  1. de tijdvelden alleen-lezen te maken wanneer de bijbehorende CheckBox niet is aangevinkt
  2. de tijdvelden te valideren
  3. alle Afspraken te maken wanneer de DoorlopendeAfspraak wordt opgeslagen

Voor al deze aanpassingen moet ik dus NIET in de Screen Designer zijn, maar in de DataModel Designer. Het is hier namelijk geen logica van het scherm waar we het over hebben, maar van het model. Ik dubbelklik in de Solution Explorer dus op de entiteit DoorlopendeAfspraken om op de juiste plaats in de DataModel Designer te komen.

Wie het eerst komt, die het eerst maalt, dus ik begin bij puntje 1. Hiervoor selecteer ik het veld “MaandagTijd” en klik rechts boven in het scherm het menu Write Code open. Je ziet dat er een behoorlijke hoeveelheid methodes is, waarop ik met code kan inhaken. Bovenaan staan gelukkig de methoden die van toepassing zijn op de geselecteerde eigenschap. Ik heb hier dus de _IsReadOnly methode nodig:

image
Figuur 2: De vele methoden om op in te haken bij een entiteit

Vervolgens kom ik in een code editor tik ik de bijzonder eenvoudige regel code die ervoor zorgt dat het veld op het juist emoment niet meer wijzigbaar is:

   1:  public partial class DoorlopendeAfspraak
   2:  {
   3:      partial void MaandagTijd_IsReadOnly(ref bool result)
   4:      {
   5:          result = !Maandag;
   6:      }
   7:  }






.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, “Courier New”, courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }

Listing 1: Zorgen dat een veld “alleen lezen” wordt



Natuurlijk kopieer ik dit voor de velden van de andere dagen.



De validatie (punt 2) werkt op dezelfde manier:



   1:  partial void MaandagTijd_Validate(EntityValidationResultsBuilder results)
   2:  {
   3:      TimeSpan time;
   4:      if (!TimeSpan.TryParseExact(MaandagTijd, "H:mm", System.Globalization.CultureInfo.CurrentCulture, out time))
   5:      {
   6:          results.AddPropertyError("Tijd bij maandag is incorrect.");
   7:      }
   8:  }






.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, “Courier New”, courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }

Listing 2: Validatie voor een veld toevoegen



En tenslotte punt 3: het toevoegen van logica waarmee alle afspraken die voortvloeien uit de DoorlopendeAfspraak, worden toegevoegd in de database. Op dezelfde plaats als hiervoor in Figuur 2, klik ik op DoorlopendeAfspraken_Inserting. Het EntityObject dat ik hier aan het toevoegen ben, krijg ik als parameter mee in de methode. Deze gebruik ik dan ook bij het manipuleren van de data:



   1:  partial void DoorlopendeAfspraken_Inserting(DoorlopendeAfspraak entity)
   2:  {
   3:      // hier alle afspraken maken zolang de doorlopendaAfspraak loopt
   4:      var t = entity.BeginDatum;
   5:      if (t < DateTime.Today) t = DateTime.Today;
   6:   
   7:      while (t <= entity.EindDatum)
   8:      {
   9:          switch (t.DayOfWeek)
  10:          {
  11:              case DayOfWeek.Monday:
  12:                  if (entity.Maandag)
  13:                  {
  14:                      var a = entity.Afspraken.AddNew();
  15:                      a.DatumTijd = t.Date.Add(ParseTijd(entity.MaandagTijd));
  16:   
  17:                      a.Locatie = entity.Locatie;
  18:                      a.Student = entity.Student;
  19:                  }
  20:                  break;
  21:              default:
  22:                  break;
  23:          }
  24:          t = t.AddDays(1);
  25:      }
  26:  }






.csharpcode, .csharpcode pre
{
font-size: small;
color: black;
font-family: consolas, “Courier New”, courier, monospace;
background-color: #ffffff;
/*white-space: pre;*/
}
.csharpcode pre { margin: 0em; }
.csharpcode .rem { color: #008000; }
.csharpcode .kwrd { color: #0000ff; }
.csharpcode .str { color: #006080; }
.csharpcode .op { color: #0000c0; }
.csharpcode .preproc { color: #cc6633; }
.csharpcode .asp { background-color: #ffff00; }
.csharpcode .html { color: #800000; }
.csharpcode .attr { color: #ff0000; }
.csharpcode .alt
{
background-color: #f4f4f4;
width: 100%;
margin: 0em;
}
.csharpcode .lnum { color: #606060; }

Listing 3: Logica om Afpsraken te maken bij het toevoegen van een doorlopende afspraak



Ik heb omwille van de duidelijkheid de meeste dagen weggelaten. Het gaat om het principe en dat lijkt me duidelijk zo. Merk op dat ik hier dus niet zelf hoef te zorgen voor het daadwerkelijk opslaan in de database. Ik pas alleen het model aan, LightSwitch zorgt dat de wijzigingen uit het model in de Database terecht komen.



Zoals je eerder al zag, is er een groot aantal methodes waarvoor je code kunt schrijven. Dit maakt een LightSwitch applicatie bijzonder flexibel en aanpasbaar. De voorbeelden die ik hier gebruikt heb, zijn slechts enkele van de mogelijkheden.

Leave a Reply

Your email address will not be published. Required fields are marked *


*

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>