Introduzione a Visual Basic Premessa Questo testo è stato tratto dal sito, sintetizzato e rielaborato in formato PDF esclusivamente per uso didattico. Il corso è pensato per quanti non hanno alcuna conoscenza di programmazione. Si consiglia di seguire questo corso avendo a disposizione l'help fornito dall'msdn, per avere informazioni più dettaglie sugli argomenti affronti. Innanzitutto è bene spiegare cosa si intende per Visual Basic: con questo termine si può intendere sia il programma che consente di sviluppare applicazioni per Windows, sia il linguaggio di programmazione in cui tali applicazioni vengono scritte. Concentriamoci per ora sulla seconda accezione del termine: il Visual Basic è chiamo così perché deriva dal linguaggio BASIC (Beginners All-Purpose Symbolic Instruction Code), un tipo di linguaggio semplice e molto diffuso che era implemento, ad es., nei mitici Commodore 64; nel corso dell'evoluzione del BASIC si sono aggiunte molte istruzioni e sono cambie diverse carteristiche, la principale delle quali è indica dal termine "visual": come vedremo tra poco, infatti, per progettare l'interfaccia grafica di un'applicazione si ha a disposizione un ambiente grafico in cui si possono utilizzare numerosi componenti di vario tipo, come i pulsanti, le caselle di testo ecc. In questo modo è possibile creare l'interfaccia grafica in modo semplice e veloce, senza dover ogni volta scrivere le istruzioni necessarie per ordinare al computer di creare le finestre di cui abbiamo bisogno, come invece accadrebbe se utilizzassimo un linguaggio non "visuale". Per rendersene conto, cominciamo a vedere come si presenta l'ambiente di progettazione di Visual Basic 6.0, cioè il programma che si avvia cliccando sul menu Start-Programmi-Microsoft Visual Basic 6.0: quello che vi si presenta è l'ide (Integred Development Environment, Ambiente di Sviluppo Integro), e al suo interno ci sono diverse finestre: scegliendo di creare un nuovo progetto "exe standard" (Fig.1) Fig.1: Apertura di un nuovo progetto "EXE Standard" Fig.2: Casella degli strumenti utilizzabili in Visual Basic. al centro compare una finestra con un "form": i form rappresentano le finestre che saranno visualizze dalla vostra applicazione; a sinistra compare la "casella degli strumenti" (Fig.2), con una serie di icone ciascuna delle quali rappresenta un particolare oggetto inseribile sul form: ad es., ci sono le label (etichette), le textbox (caselle di testo), i commandbutton (pulsanti), ecc.; selezionando un'icona è possibile disegnare direttamente sul form l'oggetto ad essa associo. A destra compaiono la finestra di gestione dei progetti e la finestra delle proprietà (Fig.3): la prima fornisce l'insieme dei file che compongono il progetto di applicazione che state creando, mentre la seconda visualizza le proprietà dell'oggetto selezionato sul form: all'inizio, dato che il form è vuoto, la finestra delle proprietà elencherà proprio quelle del form; inserendo un oggetto qualunque sul form, verranno visualizze le proprietà dell'oggetto appena inserito. Quelli visibili all'apertura dell'applicazione sono i controlli standard (o di default). Per visualizzare o gestire l'aggiunta/rimozione di altri controlli cliccare col pulsante destro del mouse sulla finestra "Generale".
Fig.3: La finestra delle Proprietà visualizza le proprietà dell'oggetto seleziono sul form. A seconda dell'oggetto selezionato, le proprietà visualizze nella tabella saranno differenti. Per modificare una proprietà fare clic sulla casella corrispondente alla seconda colonna. A questo punto può essere richiesto di immettere manualmente dati come numeri, lettere o simboli, oppure scegliere tra più possibilità elencate o ancora potrà comparire una finestra di dialogo collegata all'argomento. Ogni oggetto, o controllo, presente nella casella degli strumenti è dotato di un insieme di proprietà, metodi ed eventi. Proprietà le proprietà rappresentano gli attributi che definiscono l'aspetto e varie funzionalità di ogni controllo; ad es., la proprietà Name indica il nome con cui quel controllo è identifico all'interno del codice; le proprietà Height e Width indicano l'altezza e la larghezza del controllo, ecc. Molte proprietà sono comuni a diversi oggetti (ad es. qualunque controllo dispone della proprietà Name), altre invece sono specifiche di un controllo particolare (ad es., la proprietà Interval è disponibile solo per il controllo Timer). Solitamente le proprietà possono essere lette e anche imposte, ovvero è possibile sia leggere il valore della proprietà, sia assegnare ad essa un nuovo valore: in tal caso si dice che la proprietà è di lettura e scrittura; tuttavia esistono anche proprietà di sola lettura, alle quali non è possibile assegnare un nuovo valore, e di sola scrittura. Metodi un metodo è un'azione che l'oggetto può eseguire: ad es., l'oggetto form dispone dei metodi Show e Hide, che rispettivamente mostrano oppure nascondono il form all'utente; il controllo picturebox, invece, dispone del metodo Pset, che serve ad assegnare un certo colore ad un punto del picturebox. Come per le proprietà, alcuni metodi sono comuni a diversi controlli, altri invece sono specifici di un controllo particolare. Eventi gli eventi sono, come dice il nome, "situazioni" generate dal controllo quando si verificano certe condizioni; solitamente, ma non necessariamente, gli eventi si producono in conseguenza di un'azione dell'utente: per es., quando l'utente fa clic su un pulsante, il controllo che identifica quel pulsante genera un evento click; un esempio di evento non generato dall'utente è l'evento Timer del controllo omonimo, che viene generato dopo un certo numero di millisecondi specifico dalla proprietà Interval. Cliccando due volte di seguito su un controllo contenuto nel form, o sul form stesso, si apre un'altra finestra, l'editor del codice, in cui il programmatore può scrivere le istruzioni necessarie a
far compiere al computer determine operazioni. L'editor del codice si presenta con un'area bianca in cui va scritto, appunto, il codice, e con due caselle a discesa poste nella parte superiore della finestra (Fig.4): la casella di sinistra fornisce l'elenco degli oggetti disponibili sul form selezionato, oltre alla sezione Generale, che serve per le dichiarazioni, come vedremo oltre; la casella di destra fornisce invece un elenco degli eventi associati al controllo selezionato nella casella di sinistra. Fig.4: Casella destra e sinistra Ad es., selezionando nella casella di sinistra l'oggetto form e nella casella di destra l'evento click, verrà visualizza nell'area del codice la sezione reliva all'evento click dell'oggetto form, in cui il programmatore può scrivere le istruzioni che devono essere eseguite quando l'utente fa clic sul form. Per accedere alle proprietà e ai metodi dei vari controlli, bisogna scrivere il nome del controllo seguito da un punto "." e dal nome del metodo o della proprietà (ad es. "Form1.Show" oppure "Command1.Caption"). Passiamo ora alle fondamenta del linguaggio Visual Basic. Come ogni linguaggio di programmazione, il Visual Basic è costituito da un insieme di parole chiave, funzioni, istruzioni che seguendo determine regole sintattiche permettono al programmatore di impartire "ordini" al computer al fine di produrre un certo risultato. Prima di vedere nello specifico quali sono le particolarità del linguaggio Visual Basic, è necessaria un'introduzione sulle principali strutture che carterizzano un qualunque linguaggio di programmazione: Istruzioni un'istruzione è un insieme di una o più parole che indicano al computer di eseguire una particolare operazione: ad es., l'istruzione Print permette di scrivere o mostrare una certa informazione sullo schermo, o anche su un file, a seconda del contesto in cui si usa. Routine una routine è un insieme di una o più istruzioni, eseguite in risposta ad un'azione dell'utente, come ad es. la pressione di un tasto, oppure in seguito ad una "chiamata" della routine da parte del programmatore. Variabili le variabili sono dei "contenitori" alle quali è associato un certo valore (non necessariamente numerico); ad es., se la variabile di nome messaggio contiene il valore "questo è un messaggio di prova", utilizzando l'istruzione Print seguita dal nome della variabile (cioè scrivendo: print messaggio) potremo vedere visualizza, ad es. su una finestra, la frase "questo è un messaggio di prova". Tornando al Visual Basic, cominciamo col vedere come si dichiarano le variabili, ovvero come si fa a ordinare al computer di utilizzare una certa variabile e di assegnare a quest'ultima un certo valore; la sintassi per dichiarare una variabile in Visual Basic è la seguente: Dim NomeVariabile As TipoVariabile Ad esempio: Dim Pippo As Integer mentre per assegnarle un valore bisogna scrivere il nome della variabile, il simbolo "=" e il valore da assegnare (es.: pippo=10). Il nome della variabile è a completa discrezione del programmatore, tuttavia bisogna osservare qualche restrizione: ad es., il nome non può essere più lungo di 255 caratteri, non può contenere punti o spazi, deve iniziare con una lettera, non può essere uguale a una delle parole-chiave utilizze da Visual Basic Ad es., non si può fare:
Dim dim As Integer perché "dim" è una parola riserva per la dichiarazione delle variabili. Il tipo della variabile indica il tipo di valore che è possibile assegnare alla variabile, ed è possibile scegliere tra diverse alternive; i tipi principali supporti da Visual Basic sono: Tipo di di Spazio occupo in memoria Intervallo di valori Byte 1 byte 0/255 Integer 2 byte -32768/+32767 Long 4 byte -2147483648 / +2147483647 String variabile da 0 a circa 65000 carteri Ce ne sono anche altri, ma per ora bastano questi; come si può notare, i tipi di variabili si distinguono sia per la quantità di memoria che richiedono, sia per l'intervallo di valori che possono assumere; i primi tre tipi servono per memorizzare valori numerici, mentre il quarto memorizza delle stringhe, ovvero delle sequenze di caratteri (parole o frasi, come nell'esempio della variabile messaggio, in cui messaggio è una variabile di tipo string). La dichiarazione delle variabili, in Visual Basic, non è obbligoria: quando Visual Basic trova un nome di variabile non dichiarato, crea automicamente una variabile con quel nome (è ciò che si chiama dichiarazione implicita); questa può sembrare una bella comodità, ma in realtà è più una fonte di errori che altro: basta infatti un piccolo errore nel digitare il nome di una variabile, e Visual Basic penserà NON che la variabile è sempre la stessa ma con un nome sbagliato, BENSÌ che si tratta di un'altra variabile, che verrà automicamente creata. Così, se per es. scrivo: Dim Pippo As Integer Pippo = 10 Pipo = 5 dove per errore nella terza riga ho scritto "pipo" anziché "pippo", non avrò una sola variabile (pippo) che contiene il valore 5, ma DUE variabili (Pippo e Pipo) che contengono rispettivamente i valori 10 e 5. Per evitare questo tipo di errori, è possibile rendere obbligoria la dichiarazione esplicita di TUTTE le variabili: per fare ciò, bisogna andare sul menù strumenti, scegliere opzioni, e selezionare la casella "dichiarazione di variabili obbligoria": nella sezione "generale" del nostro form sarà automicamente aggiunta l'istruzione: Option Explicit che per l'appunto informa visual basic del fatto che la dichiarazione esplicita è obbligoria. In questo modo Visual Basic genererà un errore perché riconosce che la variabile "Pipo" non è sta dichiarata.
Le variabili in Visual Basic CORSO DI VISUAL BASIC DI GIORGIO ABRAINI Una cosa importante da tenere presente a proposito delle variabili è la loro area di visibilità: ciò deriva dal fatto che una variabile può essere dichiarata in punti diversi del codice, e cioè nella sezione dichiarazioni di un form oppure all'interno di una routine; nel primo caso, la variabile sarà visibile, e quindi potrà essere utilizzata, in tutto il form (si dice che è una variabile dichiarata a livello di modulo); nel secondo caso la variabile sarà visibile soltanto all'interno della routine in cui è dichiarata (si dice che è una variabile locale). Per capire bene la differenza proviamo ad aprire un nuovo progetto e a scrivere, nella sezione dichiarazioni del form: Dim VarGen As Integer Public Sub Prova() Dim VarLoc As Integer VarGen=1 VarLoc=1 e, nella routine Load del form: Private Sub Form_Load() Prova VarGen=2 VarLoc=2 Debug.Print VarGen, VarLoc Nota: il comando Debug.Print viene utilizzato per visualizzare il valore delle due variabili nella finestra Immediata. In parole povere, abbiamo dichiarato una variabile di nome VarGen visibile in tutto il form, e una variabile di nome VarLoc visibile solo nella routine di nome Prova: all'interno di questa routine alle due variabili viene assegnato il valore 1, mentre quando il form viene caricato si verifica l'evento Load, durante il quale vengono eseguite le istruzioni che abbiamo appena inserito: dapprima viene eseguita la routine prova con le sue due istruzioni, dopodichè alle due variabili viene assegnato il valore 2; infine il valore delle due variabili viene visualizzato nella finestra "Immediata", di cui si parlerà più avanti. Per visualizzare la finestra basta andare sul menù "Visualizza" e scegliere la voce "Finestra Immediata". Ora, proviamo a mandare in esecuzione il nostro progetto andando sul menu Esegui e scegliendo Avvia, oppure premendo il tasto F5: quello che succederà è l'interruzione del programma con la visualizzazione del seguente messaggio di errore: variabile non definita. dove la variabile è quella evidenzia, cioè la variabile VarLoc. Questo succede proprio perché all'esterno della routine Prova la variabile locale VarLoc non esiste: infatti le variabili locali vengono create all'inizio della routine in cui sono dichiarate, e automaticamente distrutte quando la routine finisce di essere eseguita. La variabile VarGen, invece, è visibile sia nell'evento load del form, sia nella routine prova, proprio perché è stata dichiarata nella sezione delle dichiarazioni generali del form. Faccio notare che se si prova a eliminare l'istruzione Option Explicit che, se avete seguito il mio suggerimento (v. lezione precente), dovrebbe essere inserita automicamente, quando il
progetto viene avviato non si verifica alcun errore e nella finestra immediata viene stampa la riga: 2 2 Questo succede perché senza l'istruzione Option Explicit durante l'esecuzione vengono create DUE variabili VarLoc: una dichiarata esplicitamente nella routine Prova e distrutta alla fine della routine, l'altra dichiarata implicitamente nell'evento load del form e a cui viene assegnato il valore 2, che viene poi correttamente visualizzato nella finestra immediata. Dato che in una applicazione possono esserci ben più di un unico form, ci si può chiedere se le variabili dichiare a livello di modulo in un certo form siano visibili anche negli altri form: la risposta è positiva solo se nella dichiarazione delle variabili si usa la parola chiave Public, ad es.: Public VarGen As Integer questa parola chiave specifica appunto che la variabile dichiarata è pubblica, cioè è visibile in tutta l'applicazione a cui appartiene il form in cui è dichiarata; utilizzando invece la parola chiave Private o la classica Dim, la variabile sarà privata e quindi visibile solo nel form in cui è dichiarata. Prima ho detto che le variabili locali vengono create all'inizio della routine in cui sono dichiare e distrutte alla fine: da ciò deriva che se la stessa routine viene richiama più volte, la variabile viene creata e distrutta altrettante volte, ed ogni volta la variabile creata non ha alcuna connessione con la variabile omonima creata la volta precedente. Se ad esempio modifichiamo la nostra routine Prova in questo modo: Public Sub Prova () Dim VarLoc As Integer VarLoc=VarLoc + 1 Debug.Print VarLoc E nell'evento Load scriviamo: Prive Sub Form_Load() Prova Prova e proviamo ad avviare il progetto, vedremo che nella finestra immedia viene scritto: 1 1 e non, come qualcuno si potrebbe aspettare: 1 2 Se si desidera che una variabile locale conservi il proprio valore tra una chiama e l'altra della routine, bisogna dichiararla con la parola chiave Stic: Public Sub Prova() Stic VarLoc As Integer VarLoc = VarLoc + 1 Debug.Print VarLoc
Se proviamo ancora ad eseguire il progetto, vedremo che questa volta nella finestra Immediata appare scritto: 1 2 La variabile VarLoc viene quindi creata solo una volta (la prima volta che la routine viene eseguita) e viene distrutta solo quando chiudiamo l'applicazione (cliccando ovviamente sulla X in alto a destra nel form, come per qualunque altra finestra); tuttavia questa variabile è ancora una variabile locale, quindi non è utilizzabile all'esterno della routine. Il motivo per cui VarLoc assume il valore 1 dopo l'istruzione: Varloc = Varloc + 1 è presto detto: in Visual Basic ogni variabile numerica viene automicamente inizializza al valore 0 quando viene creata; le variabili stringa, invece, vengono inizializze con una stringa vuota, ossia con zero caratteri. Nota: Nel caso in cui si assegnino nomi composti agli elementi del codice la cui denominazione è arbitraria (variabili, costanti, procedure, funzioni), è buona norma mantenere la prima lettera maiuscola di ciascun nome, in modo da operare una separazione intuitiva. Nel corso di questa lezione ad esempio si è trattata la variabile VarLoc il cui nome deriva dall'unione dei nomi Variabile Locale. Lo stesso vale per VarGen, unione di Variabile e Generale
Le routine in Visual Basic CORSO DI VISUAL BASIC DI GIORGIO ABRAINI Dopo aver visto in dettaglio le variabili, vediamo meglio le routine. Innanzitutto bisogna dire che le routine, come le variabili, devono essere dichiare: la dichiarazione avviene specificando la parola chiave Sub (in seguito vedremo che si possono utilizzare anche altre parole chiave) seguita dal nome della routine e da due parentesi tonde, la prima aperta e la seconda chiusa (tra poco vedremo cosa si può mettere all'interno delle parentesi). Ad esempio: La parola Sub può essere preceduta dalle parole chiave Prive o Public (NON da Dim: quest'ultima serve solo per le variabili), a seconda che la routine debba essere visibile solo nel form corrente o in tutto il progetto. Per inserire una routine è talvolta più comodo andare sul menù strumenti e scegliere inserisci routine: nella casella di testo in cui appare il cursore scrivete il nome della routine (le altre opzioni per ora lasciele così come sono) e premete OK. La dichiarazione delle routine serve a indicare dove INIZIA la routine: per indicare dove FINISCE è necessario scrivere dopo l'ultima istruzione appartenente alla routine. Quindi: Nella prima lezione avevo detto che le routine sono un'insieme di più istruzioni: esse risultano molto comode quando si ha bisogno di eseguire più volte uno stesso gruppo di istruzioni, in modo che quando si ha necessità di eseguire una certa operazione, è sufficiente richiamare quella routine anziché riscrivere ogni volta le medesime istruzioni. Supponiamo, ad es., di voler calcolare i quadrati dei valori 2, 5, e 8 e di volerli visualizzare nella finestra Immediata: senza usare le routine saremmo costretti a scrivere (ad es. nell'evento Load del nostro form): Prive Sub Form_Load() 'dichiaro la variabile: Dim x As Integer x = 2 ^ 2 'il simbolo "^" serve a indicare l'elevamento a potenza 'stampo il risultato: Debug.Print x x = 5 ^ 2 Debug.Print x x = 8 ^ 2 Debug.Print x Nota: il simbolo " ' " serve a indicare un commento al codice: il commento viene del tutto ignorato da Visual Basic, la sua utilità deriva dal fatto che permette a chi legge il codice di comprendere meglio cosa fanno le istruzioni.
Utilizzando invece una routine di nome "Quadrato" che calcola il quadrato di un numero potremmo scrivere, nella sezione delle dichiarazioni: Dim x As Integer Prive Sub Quadrato() 'qui inizia la routine Dim y As Integer'dichiaro una variabile locale y = x ^ 2 'calcolo il quadrato Debug.Print y 'stampo il risultato 'qui finisce la routine e, nell'evento Load del form: Public Sub Form_Load () x = 2 'imposto la variabile Quadrato 'calcolo il quadrato e stampo il risultato x = 5 Quadrato x = 8 Quadrato In un esempio così semplice è poco utile ricorrere alle routine, ma se pensate che una routine potrebbe contenere centinaia di istruzioni che vanno ripetute più o meno spesso vi accorgerete della loro grande utilità; un aspetto da non trascurare è infatti anche la leggibilità del codice, ovvero la sua facilità di comprensione: utilizzando le routine per eseguire operazioni complesse è molto più semplice capire come funziona un programma (procedendo con gli esempi ve ne renderete conto sempre meglio). Nell'esempio qui sopra abbiamo imposto una variabile dichiarata a livello di modulo (la variabile x) in modo che potesse essere utilizzata anche nella routine: in realtà ciò non è necessario, infatti è possibile utilizzare il passaggio di parametri alla routine. Un parametro è una variabile che viene comunicata alla routine, la quale può utilizzarla più o meno come se fosse una sua variabile locale: in questo modo è possibile travalicare i limiti imposti dall'area di visibilità delle variabili (v. lez. precedente). Ad es., se noi avessimo dichiarato la variabile x non nella sezione delle dichiarazioni ma all'interno dell'evento Load, avremmo ottenuto un errore del tipo: perché la variabile non sarebbe stata visibile nella routine quadrato (a meno che abbiate dimenticato di inserire l'istruzione "Option Explicit": d'ora in poi darò sempre per scontato che sia attivata la dichiarazione obbligoria delle variabili). Invece utilizzando il passaggio di parametri questo problema non sussiste più. Per indicare a Visual Basic che la nostra routine vuole uno o più parametri bisogna elencare i parametri, o argomenti, all'interno delle parentesi nella dichiarazione della routine: Private Sub Quadrato (Param As Integer) Dim y As Integer y = Param ^ 2 Debug.Print y
Come avrete notato, l'indicazione dell'argomento segue le stesse regole della dichiarazione delle variabili, eccezion fatta per la parola chiave Dim (o Prive o public) che in questo caso NON va inserita perché non avrebbe senso: l'argomento di una routine è utilizzabile solo all'interno di quella routine. Per indicare più parametri bisogna separarli con la virgola: ad es:... (Param1 As Integer, Param2 As String...)... Il nome del parametro non ha nulla a che vedere col nome della variabile passata come argomento (nel nostro caso la variabile x): nel caso in cui i nomi fossero uguali, all'interno della routine verrebbe comunque utilizzato il parametro e non la variabile originaria. All'interno dell'evento load del form potremo ora scrivere: Public Sub Form_Load() Dim x As Integer x = 2 Quadrato x x = 5 Quadrato x x = 8 Quadrato x e nella finestra immediata vedremo: Nuralmente l'argomento da passare alla routine può essere una variabile dichiarata da noi, ma anche un valore fisso: possiamo quindi fare a meno, nel nostro caso, di utilizzare la variabile x e scrivere direttamente: Public Sub Form_Load() Quadrato (2) 'oppure Quadrato 2 Quadrato (5) 'oppure Quadrato 5 Quadrato (8) 'oppure Quadrato 8 ottenendo il medesimo risultato: ogni volta che viene chiamata la routine quadrato, la variabile param assumerà di volta in volta il valore 2, 5, 8. Avrete sicuramente capito che per eseguire una routine è sufficiente scriverne il nome, eventualmente seguito dagli argomenti richiesti dalla routine: gli argomenti andranno separi da virgole nel caso siano più di uno (ad es. quadrato 2, 3, "Pippo" se gli argomenti sono tre: i primi due numerici e il terzo una stringa). E' però possibile anche utilizzare l'istruzione Call, seguita dal nome della routine e dai parametri, questa volta però obbligoriamente racchiusi tra parentesi: oppure: Call Quadrato (2) Call Quadrato (2, 3, Pippo) se gli argomenti sono diversi. L'uso delle parentesi sarà fondamentale nell'uso delle funzioni, che vedremo la prossima volta.
Le funzioni in Visual Basic CORSO DI VISUAL BASIC DI GIORGIO ABRAINI La differenza tra una routine e una funzione è che la prima esegue un certo numero di istruzioni, la seconda esegue un certo numero di istruzioni e in più restituisce un valore, che quindi può essere memorizzato in una variabile. L'uso delle funzioni è comodo quando è opportuno sapere quale sia il risultato finale delle operazioni eseguite: ad es., la funzione potrebbe restituire un valore di errore se qualcosa è andato storto durante la sua esecuzione, oppure potrebbe restituire il risultato di un'operazione matematica come quella eseguita dalla routine quadrato che abbiamo visto nella lezione precedente. Per dichiarare una funzione bisogna usare la parola chiave Function al posto di Sub; inoltre è sempre meglio, se possibile, specificare il tipo di dati restituito dalla funzione. Ad es.: Prive Function Quadrato (Param As Integer) As Long Quadrato=Param ^ 2 Debug.Print Quadrato End Function Il valore che la funzione deve restituire deve essere assegnato al nome della funzione: Quadrato = Param ^ 2 che viene quindi trattato come se fosse una variabile: perciò rispetto alla routine Quadrato (v.lez. precedente) si può fare a meno di dichiarare una variabile locale a cui assegnare il risultato dell'elevamento a potenza. Inoltre, possiamo fare a meno di usare l'istruzione Debug.Print all'interno della funzione, perché il valore che vogliamo visualizzare è quello restituito dalla funzione e quindi è visibile anche all'esterno di essa: nell'evento Load del form, anziché scrivere Quadrato 2 Quadrato 5 Quadrato 8 possiamo quindi scrivere: Debug.Print Quadrato(2) Debug.Print Quadrato(5) Debug.Print Quadrato(8) In questo caso è necessario usare le parentesi tonde: queste vanno sempre indicate se si vuole che la funzione restituisca effettivamente un valore; infatti è anche possibile richiamare la funzione senza parentesi: Quadrato 2 come se fosse una routine, ma non sarà possibile scrivere: Debug.Print Quadrato 2 perché chiamando la funzione senza usare le parentesi si impedisce che essa restituisca un valore. Lo stesso accade se si chiama la funzione con l'istruzione Call; pertanto mentre una routine può essere chiama indifferentemente con o senza le parentesi, una funzione deve essere chiama con le parentesi (ma senza usare l'istruzione Call) affinché restituisca un valore. Per quanto riguarda il passaggio di parametri, valgono le stesse regole che abbiamo visto per le routine; a questo proposito c'è da sapere un'altra cosa: i parametri possono essere preceduti dalla parola chiave ByVal o ByRef. Queste parole chiave specificano, rispettivamente, che il parametro viene passo per valore o per riferimento: senza entrare troppo nei dettagli, è sufficiente dire che nel primo caso la funzione (o la routine) conosce soltanto il valore della variabile passa come
argomento, mentre nel secondo caso conosce, per così dire, la variabile stessa, potendo quindi intervenire direttamente su di essa. Concretamente ciò significa che se la variabile è passata per valore, la funzione (o la routine) potrà eseguire operazioni sul valore della variabile ma non potrà modificarla; se invece la variabile è passata per riferimento, la funzione potrà modificare direttamente la variabile. Un esempio chiarirà tutto: creiamo una funzione con due argomenti, uno passato per valore, l'altro per riferimento e facciamo qualche operazione su di essi: Prive Function Prova (ByVal Valore As Integer, _ ByRef Riferimento As Integer) As Integer Valore = Valore + 1 Riferimento = Riferimento + 1 Prova = Valore + Riferimento End Function La funzione non fa altro che incrementare di 1 i due argomenti e restituirne la somma. Ora dichiariamo, nell'evento Load del form, due variabili e passiamole alla funzione: Prive Sub Form_Load() Dim Var1 As Integer, Var2 As Integer Dim Risultato As Integer Var1 = 3 Var2 = 10 Risultato = Prova(Var1, Var2) Debug.Print Risultato Debug.Print Var1, Var2 Eseguendo il progetto, noteremo che nella finestra immediata compaiono i valori: 15 è il risultato della funzione ((3+1)+(10+1)=15); la variabile Var1, che è sta passata per valore e che quindi non ha potuto essere stata modificata, conserva il valore che aveva prima della chiamata della funzione, cioè 3; invece Var2, che è sta passata per riferimento, è stata effettivamente modificata durante l'esecuzione della funzione, e infatti dopo la chiama ha assunto il valore 11, cioè il valore originario più 1. Se non viene specifica né ByVal né ByRef, Visual Basic penserà automicamente che la variabile è stata passata per riferimento: questa infatti è l'impostazione predefinita. Un'altra parola chiave che può precedere gli argomenti è Optional: questa specifica che l'argomento seguente non è obbligorio, e in tal caso è possibile indicare un valore di default che l'argomento deve assumere nel caso in cui l'istruzione chiamante la funzione (o la routine) ometta effettivamente il parametro. Ad es.: Prive Function Prova (A As Integer, Optional B As Integer = 1) As Integer Prova = A + B End Function se nell'evento Load del form scriviamo: Prive Sub Form_Load() Debug.Print Prova(2) Debug.Print Prova(2, 3)
vedremo nella finestra immediata: 3 5 Nel primo caso, infatti, il parametro B è omesso e quindi assumerà per default il valore 1. Come per le routine, anche le variabili locali di una funzione possono essere dichiare Static per indicare che il loro valore viene mantenuto tra una chiamata e l'altra della funzione (v.lez. 2): se si vuole che TUTTE le variabili locali siano statiche, si può dichiarare la funzione in questo modo: Prive Stic Function Prova() As Integer Dim A As String 'variabile statica Dim B As Long 'variabile statica End Function Le variabili locali saranno statiche anche se nella loro dichiarazione non è stata specifica la parola chiave Static.
Il primo programma in Visual Basic Ora che conosciamo le basi fondamentali della programmazione, possiamo avvicinarci alla creazione del nostro primo programma: il classico "Hello World!", ovvero un programma che non fa altro che visualizzare un messaggio di saluto. Per fare ciò cominciamo col creare un nuovo progetto e a inserire nel form una Label, cioè un'etichetta: il controllo Label lo trove sulla casella degli strumenti che solitamente si trova sul bordo sinistro dello schermo, ed è quello indico dall'icona "A". Una Label è un controllo che permette di visualizzare una stringa: una volta inserita sul form, potremo vedere le sue proprietà nella finestra delle proprietà, posta sulla destra dello schermo; le proprietà possono essere visualizzate in ordine alfabetico o per Categoria: scegliendo l'ordine alfabetico, vedremo innanzitutto la proprietà Name che è la prima dell'elenco e che definisce il nome con cui si può fare riferimento al controllo all'interno del codice, come si può leggere anche nella descrizione fornita nella parte inferiore della finestra delle proprietà. Il nome predefinito, per qualunque controllo, è dato dal nome del tipo di controllo (nel nostro caso Label) più un numero che viene incremento ogni volta che si aggiunge un altro controllo dello stesso tipo: se prove ad aggiungere un'altra Label sul form, vedrete che il suo nome predefinito sarà Label2, e così via. Diamo un'occhiata ad altre proprietà interessanti: la proprietà Caption ad es., assume il valore "Label1": provando a modificare questo valore (basta cliccarci sopra una volta e scrivere) vedrete che cambierà anche la stringa visualizza sul form (per ora lascie pure "Label1"); pertanto sarà questa la proprietà che dovremo opportunamente impostare per visualizzare il messaggio di saluto. Prima di vedere come, inseriamo sul form anche un CommandButton, cioè un pulsante, che trovate anch'esso sulla casella degli strumenti. Nella finestra delle proprietà, modificate la proprietà Caption e assegnegli il valore "Saluta!" (senza scrivere anche le virgolette). La posizione dell'etichetta e del pulsante sul form può essere cambia semplicemente puntando il mouse sul controllo e trascinandolo nella posizione voluta. Ora andate sulla finestra del codice (se non la vedete cliccate due volte sul form, oppure cliccate sulla prima icona che vedete nella finestra del progetto, facendo attenzione ad aver selezionato la voce "Form1" nella medesima finestra): selezione la voce Command1 dall'elenco degli oggetti e la voce click dall'elenco delle routine, e vi troverete, ovviamente, nella parte di codice che verrà eseguita quando si fa click sul pulsante: ora, all'interno di questa routine scrivete: Label1.Caption = "Hello World!"
Prove ad avviare il progetto premendo F5 e cliccate sul pulsante "Saluta": il testo dell'etichetta diventerà "Hello World!". Quello che succede dovrebbe essere evidente: cliccando sul pulsante viene scateno l'evento Click relativo ad esso, e viene quindi eseguita l'istruzione che abbiamo inserito noi, e che imposta il valore della proprietà caption dell'etichetta a "Hello World!". Si dice che questa proprietà viene impostata in fase di esecuzione, ovvero mentre il programma è in esecuzione; la proprietà caption del pulsante, invece, è stato impostato in fase di progettazione, ovvero quando abbiamo "disegnato" la nostra applicazione. Volendo, avremmo potuto impostare la proprietà Caption dell'etichetta già in fase di esecuzione: in tal caso non avremmo avuto bisogno del pulsante "Saluta". Proviamo ora a migliorare un po' la nostra applicazione: di solito è buona norma inizializzare il valore di proprietà o variabili che andranno in seguito modificate; ad esempio, prima di premere il pulsante "Saluta", l'etichetta mostrava la stringa "Label1", cosa non molto bella a vedersi: quindi è meglio annullare la proprietà Caption. E' possibile farlo in fase di progettazione, cancellando "Label1" nella finestra delle proprietà e premendo Invio; in fase di esecuzione, bisogna usare l'istruzione: Label1.Caption = "" dove tra le virgolette non ci devono essere spazi: è una "stringa nulla", di lunghezza zero, che non contiene alcun carattere. Questa istruzione dovremmo metterla in una routine che viene eseguita subito, non appena l'applicazione viene avviata: il posto più adatto è senz'altro la routine Load del form, quella che abbiamo usato per i nostri esempi nelle lezioni precedenti; infatti l'evento Load del form viene generato prima della visualizzazione della finestra. Se volessimo poter annullare, ossia cancellare, il saluto, dovremmo inserire sul form un altro pulsante: assegne il valore "Annulla" (sempre senza le virgolette) alla proprietà Caption e, nella routine Click (del Command2, non del Command1!) ripetete l'istruzione: Label1.Caption = "" E' buona norma, inoltre, inserire un pulsante per uscire dal programma, anche se non è necessario in quanto basta premere la X in alto a destra nel form per chiudere l'applicazione; per terminare un programma, bisogna "scaricare" tutti i form attualmente caricati in memoria (nel nostro caso solo il form Form1): nella routine Click del pulsante Command3, quindi, dovremo scrivere: Unload Form1 L'istruzione unload serve appunto ad eliminare dalla memoria del computer i riferimenti al form di nome Form1, e di conseguenza a terminare l'applicazione; l'istruzione determina la generazione dell'evento Unload, che è il corrispettivo dell'evento Load di cui si è detto sopra; analogamente, esiste anche l'istruzione Load che serve per "caricare" un form in memoria. Al posto di "Form1" è possibile utilizzare la parola chiave Me, che indica, in questo caso, il form corrente, ossia quello a cui appartiene la riga di codice che sta per essere eseguita. La Caption del pulsante Command3 andrebbe imposta, per esempio, a "Esci". Se proviamo ad eseguire l'applicazione, vedremo inizialmente solo i tre pulsanti "Saluta", "Annulla" ed "Esci": premendo "Saluta", il programma visualizzerà il messaggio di saluto, premendo "Annulla" questo messaggio scomparirà e premendo "Esci" chiuderemo il programma. Questo esempio è ovviamente molto semplice, ma cercate di apprezzare il fatto che abbiamo creato un'applicazione completa scrivendo soltanto 4 righe di
codice. Per migliorare ulteriormente il nostro programma potremmo, ad es., cambiare la stringa che compare nella barra del titolo del form (nel nostro caso "Form1"): anche in questo caso si tratta della proprietà Caption (del form); basta andare nella finestra della proprietà, selezionare il form dalla casella a discesa, selezionare la proprietà Caption e scrivere, ad esempio: "Programma di esempio Hello World". Posizionando i pulsanti sul form, probabilmente non sarete riusciti (almeno non al primo colpo) a farli delle stesse dimensioni: per renderli uguali basta selezionarli tutti insieme, come si fa per selezionare più file in Gestione Risorse, cioè disegnando un rettangolo torno ad essi oppure cliccandoci sopra tenendo premuto il tasto Ctrl; dopodichè, andate sul menù Formato - Rendi uguale e scegliete Entrambe: i tre pulsanti avranno tutti la stessa altezza e larghezza. Nel caso non siano allineati, potete selezionarli e andare sul menù Formato - Allinea e scegliere la voce opportuna. Inoltre, è opportuno modificare i nomi dei vari controlli: ad esempio, il nome dell'etichetta potrebbe essere "lblhelloworld" (senza spazi, mi raccomando); quello dei pulsanti "cmdsaluta", "cmdannulla", "cmdesci"; naturalmente in tal caso bisogna modificare anche le istruzioni del codice. Così: diventa: Label1.Caption = "" lblhelloword.caption = "" e così via. Il motivo per cui i nomi sono preceduti da lbl o cmd ve lo spiegherò la prossima volta.
Convenzioni Come promesso, cominciamo a vedere cosa sono e come si usano le cosiddette convenzioni di scrittura del codice: tali convenzioni sono regole che ogni programmatore dovrebbe seguire, al fine di scrivere un codice facilmente comprensibile e modificabile per chiunque abbia l'occasione di leggerlo ed eventualmente correggerlo e migliorarlo; rappresentano una sorta di galateo del programmatore, che permette di standardizzare il codice e quindi di renderne più semplice la lettura, la comprensione e la diffusione. Le convenzioni più semplici sono quelle che riguardano la denominazione di oggetti e variabili: secondo tali convenzioni è bene utilizzare un prefisso di due o tre caratteri specificato per ogni tipo di oggetto o variabile: ad es., se utilizziamo un CommandButton dovremmo usare il prefisso cmd; per le etichette (c.d. Label) il prefisso è lbl, per i form è frm, e così via. Leggendo un codice di questo tipo: frmmain.show cmdsave_click saremmo in grado di intuire subito che prima di tutto viene visualizzato il form frmmain e dopo viene richiamata la routine corrispondente all'evento Click di un CommandButton. Senza usare i prefissi, non avremmo potuto sapere a priori a quale oggetto si riferisse la routine Click. Analogo discorso vale per le variabili: innanzitutto è bene usare una lettera per indicarne l'area di validità: g per le variabili globali, o pubbliche, m per quelle private ma dichiarate a livello di modulo (quindi nella sezione dichiarazioni di un form, ad esempio); per le variabili locali delle routine non si usa alcun prefisso. Poi bisognerebbe utilizzare un altro prefisso per indicare il tipo di variabile: str per le stringhe, int per gli integer, lng per i long, ecc. Ad esempio: gstrusername indica una variabile pubblica che contiene il nome dell'utente (e quindi si tratta di una stringa). Ci sono poi delle convenzioni per la strutturazione del codice, ovvero l'inserimento di commenti e l'uso di una formattazione adeguata del codice: ad esempio, ogni subroutine o funzione dovrebbe includere un commento che ne indichi lo scopo, il significato delle variabili richieste in input, il valore restituito, e ogni altra informazione non direttamente intuibile dal codice ma che serve a capire meglio cosa fa e come funziona la routine. Per quanto riguarda la formattazione del codice, bisognerebbe utilizzare i rientri: consideriamo ad es. queste istruzioni: Dim base As Double Dim altezza As Double Dim lato As Double If Val(TBaltezza.Text) And Val(TBbase.Text) Then base = TBbase.Text altezza = TBaltezza.Text lato = Math.Sqrt((base / 2) ^ 2 + (altezza) ^ 2) If base = 0 Or altezza = 0 Then Lbrisposta.Text = "non è un triangolo" & " ma un segmento!" Else Lbrisposta.Text = "l'area del triangolo è" & Str(base * altezza / 2) Lbperimetro.Text = "il perimetro del triangolo è " & Str(2 * lato + base) End If Else MsgBox("inserire numeri") TBaltezza.Text = "" TBbase.Text = "" End If La cosa importante è sapere che queste istruzioni sono nidificate, ovvero contenute l'una nell'altra: il blocco if end if contiene un altro blocco if endif, che a sua volta contiene una serie
di istruzioni. La nidificazione è appunto immediamente evidenziata dal rientro delle varie istruzioni: maggiore è il rientro, maggiore è il livello logico di nidificazione; è un po' lo stesso principio utilizzo da Gestione risorse per visualizzare la gerarchia delle directories(cartelle): più una cartella è "rientrata", meno importante è il suo livello gerarchico. Queste sono alcune delle convenzioni di scrittura del codice: altre le vedremo strada facendo.
variabili Booleane e loro utilizzo Ora ricordiamo le operazioni logiche e delle variabili booleane (pron. buleàne). I concetti di vero e falso,introdotte inn primo liceo quando abbiamo parlato di logica. Questi due concetti sono fondamentali per l'intero mondo dei computer, anzi per lo stesso funzionamento dei computer: infatti, come tutti sanno, un computer si basa su una logica binaria, in cui ogni singolo bit può assumere due soli valori: 0 e 1, che possono essere logicamente associati ai valori falso e vero. Il logico e matematico George Boole, vissuto nel XIX secolo, sviluppò un insieme di regole (che formano l'algebra booleana) per eseguire operazioni logiche sui valori vero e falso. Le principali regole, che abbiamo già studiato sono: And (congiunzione), Or (disgiunzione), Not (negazione), Xor (exclusive Or) In Visual Basic esiste un tipo di variabile particolare, il tipo Boolean, che indica proprio una variabile booleana, che può assumere il valore vero o falso, o meglio True o False, che sono le parole chiave utilizzate nell'ambito delle operazioni logiche booleane. Lo schema del risultato degli operori logici And, Or, Xor è il seguente: A B A and B A or B A Xor B True True True True False True False False True True False True False True True False False False False False Come si può notare, la congiunzione (And) di due espressioni è vera solo se sono vere entrambe le espressioni ("io lavoro a Milano e a Torino" è vera solo se è contemporaneamente vero che lavoro a Milano e che lavoro a Torino); la disgiunzione (Or) è vera solo se è vera almeno una delle due espressioni ("io lavoro a Milano o a Torino" è vera se lavoro sia a Milano che a Torino, ma è vera anche se lavoro a Milano e a Brescia o se lavoro a Torino e a Roma; sarà invece falsa solo se non lavoro né a Milano né a Torino). La disgiunzione esclusiva (Xor) non è immediamente intuibile come la congiunzione e la disgiunzione, ma è un misto di queste due operazioni e della negazione: l'xor restituisce True solo se le due espressioni sono diverse, mentre restituisce False solo se le due espressioni sono uguali; corrisponde alla "o" disgiuntiva, come quando si dice "io lavoro o a Milano o a Torino": mentre l'or permette la compresenza di entrambe le alternive, l'xor ne esclude una delle due. La negazione, infine, coinvolge una sola espressione e restituisce semplicemente il suo opposto: Not True = False Not False = True Questi operori possono essere raggruppati insieme in espressioni logiche più o meno complesse: (True Or False) And True
Ci sono altri due operori logici disponibili in Visual Basic, che sono utilizzi molto raramente ma che potrebbero comunque essere utili: l'equivalenza detta anche coimplicazione (se e solo se) che in Vb è Eqv e l'implicazione materiale (se allora) che in Vb è Imp: A B A Eqv B A imp B True True True True True False False False False True False True False False True True L'istruzione principale che fa uso di espressioni booleane è il costrutto "if condizione then istruzione" che, come dice il nome, esegue una o più istruzioni se si verifica una certa condizione. Ad esempio, l'istruzione: If lblname.visible = True Then lblname.text = "Pippo" End if aggiorna la proprietà Caption dell'etichetta lblname se questa etichetta è visibile: il tipo della proprietà Visible, infatti, è proprio Boolean. Quando Visual Basic deve eseguire un'istruzione come quella riportata, prima di tutto verifica se l'espressione compresa tra le parole chiave If e Then è vera o falsa: se l'etichetta è visibile (cioè se la proprietà visible è uguale a True), la condizione è verificata e quindi sarà eseguita l'istruzione seguente la parola chiave Then; altrimenti la condizione non sarà verificata e l'istruzione sarà del tutto ignorata. L'istruzione If Then permette di eseguire certe istruzioni anche nel caso in cui la condizione non sia verifica: ciò è possibile grazie alla parola chiave Else, ad esempio: If strname = "Pippo" Then frmprova.show Else frmprova.hide End If Se la variabile stringa strname è uguale a "Pippo", il form frmprova viene mostrato, altrimenti viene nascosto. In questo modo è possibile ottenere una certa flessibilità nell'esecuzione condizionale di un gruppo di istruzioni. All'interno di ogni blocco If Then è possibile inserire qualunque istruzione, anche un'altra If Then (si parla dei cosiddetti blocchi annidati); ad esempio si potrebbe fare: If intx > 10 Then If intx > 100 Then inty = intx / 2 Else inty = intx + 10 End If ElseIf intx > 5 Then inty = 0 Else
End If bvalue = True In questo blocco viene valutato il valore della variabile Integer intx: se è maggiore di 10, viene effettuato un ulteriore controllo: se intx è maggiore di 100, viene posto inty = intx/2, altrimenti inty = intx+10; se invece intx non è maggiore di 10 (cioè intx <= 10), Visual Basic controlla se intx > 5: in questo caso si pone inty = 0. Se infine intx <= 5, la variabile booleana bvalue viene imposta a True. E' chiaro quindi che l'istruzione If Then permette di effettuare confronti flessibili e ramificati per determinare quali istruzioni è opportuno eseguire. Ma non basta: le condizioni da valutare possono essere espressioni anche molto complesse, utilizzando gli operori logici che abbiamo visto nella lezione precedente; ad esempio: If ((intx> 10 And intx < 100) Or (intx > 200 And intx<= inty / 3)) Imp bvalue = False Then... End If La valutazione della condizione segue le regole generali per l'uso delle parentesi: dapprima viene confronto il valore di intx con 10 e con 100: se è compreso tra questi due valori (esclusi gli estremi), l'espressione nella prima sotto-parentesi sarà True; poi intx viene confrontato con 200 e con inty / 3: se è compreso tra questi due valori, la seconda sotto-parentesi sarà True; se almeno una delle due sotto-parentesi è True, anche la superparentesi sarà True. Infine viene confronta la variabile bvalue con il valore False: se bvalue è False, l'espressione "bvalue = False" sarà True, e quindi lo sarà anche l'intera condizione valutata dalla If; se invece bvalue = True, la seconda espressione sarà False: in tal caso l'intera condizione sarà True solo se anche la super-parentesi sarà False. Un esempio dovrebbe chiarire tutto: supponiamo che intx = 90, inty = 600, bvalue = True; allora avremo: If ((True And True) Or (False And True)) Imp False Then che corrisponde a: If (True Or False) Imp False Then che corrisponde a: If True Imp False Then Siccome True Imp False restituisce False, le istruzioni successive a Then non saranno eseguite. Vi faccio notare che Visual Basic valuta sempre tutte le espressioni, anche se in qualche caso è inutile; supponiamo ad esempio di avere: If intx > 10 And intx < 20 Then con intx = 5; sapendo che intx > 10 è False e che il valore della condizione dipende dall'operatore And, si potrebbe anche fare a meno di confrontare intx con 20, perché qualunque sia il risultato di questo confronto la condizione sarà comunque False. Visual Basic invece li fa sempre tutti, e nel caso di controlli pesanti bisognerebbe tenerne conto, facendo in modo che vengano valute solo le espressioni strettamente necessarie. Ad es., l'istruzione: If intx > 10 And intx < 20 Then intx = intx * 2 End If potrebbe essere modifica in questo modo: If intx > 10 Then if intx < 20 Then IntX = IntX * 2 End If End If
In questo modo, se intx=5, Visual Basic non perde tempo a confrontare intx con 20, perché già la prima condizione è falsa, e quindi il secondo blocco If sarà ignorato.