4. Maschere

4.1   Colori differenti in maschere continue 4.22 Valore predefinito dal record precedente
4.2   Riferimento ad una sottomaschera/sottoreport 4.23 Disattivare i tasti PaginaSu/PaginaGiù
4.3   Sincronizzare le maschere 4.24 Posizionare il cursore/la selezione
4.4   Cercare un record 4.25 Evitare duplicati
4.5   Lo stesso record dopo un Requery 4.26 Associare una etichetta
4.6   Mostrare diverse istanze di una maschera 4.27 E-mail con indirizzo da casella di testo
4.7   Cambiare l'ordinamento di una maschera 4.28 Il testo descrizione non appare
4.8   Cambiare una sottomaschera 4.29 La rotellina del mouse scorre i record
4.9   Salva/Cancella non funziona in una maschera popup di A97 4.30 Intestazione Colonne in visualizzazione foglio dati
4.10 Cambiare riga con il tasto freccia 4.31 Mostrare GIF animate
4.11 Salvare valori calcolati 4.32 Chiedere prima di salvare un record
4.12 Casella combinata/di riepilogo - Selezionare una riga 4.33 Controllare se un record è primo, ultimo o nuovo
4.13 Casella combinata - Aggiungere un nuovo record 4.34 Tutti i controlli scompaiono
4.14 Aprire una casella combinata via codice 4.35 Nascondere il pulsante di chiusura in una maschera di A97
4.15 Casella combinata/di riepilogo - Accesso all'ennesima colonna 4.36 Dipendenza delle caselle combinate/riepilogo
4.16 Casella di riepilogo - Allineamento a destra 4.37 Eseguire calcoli nelle caselle di testo
4.17 Struttura a schede - evento cambiamento pagina 4.38 Evitare il cambio record da tastiera
4.18 Struttura a Schede - Cambia pagina con la tastiera 4.39 Numero/Somma incrementale in una maschera
4.19 Verificare se una maschera è aperta 4.40 Recuperare una selezione multipla di record
4.20 Determinare la risoluzione dello schermo 4.41 Casella di testo per l'inserimento di un password
4.21 Adattare le maschere alla risoluzione dello schermo
   
4.1 Colori differenti in maschere continue
http://www.donkarl.com/it?FAQ4.1 aggiornato 2010-03-17

Problema

In una maschera continua desideri che certi record o campi siano formattati in maniera particolare. Se tenti di assegnare tale formattazione (per esempio via codice o espressioni con qualche condizione), i cambiamenti avverranno per tutti i record.

Causa

Le impostazioni di formato in una maschera di Access (anche in modalità continua) vengono salvate tutte assieme in un solo posto e quindi applicate a tutti i record.

Soluzione

Nelle versioni uguali o successive ad A00, puoi usare la "Formattazione Condizionale". Per far ciò, apri la maschera in visualizzazione struttura, evidenzia un controllo e nel menu Formato scegli la voce "Formattazione condizionale". Le impostazioni sono anche modificabili via VBA, vedi <F1> per  "FormatConditions".

Possibilità nelle precedenti versioni di Access:
Riguardo al colore del testo puoi usare la proprietà Formato per distinguere tra 4 differenti condizioni ed assegnare colori diversi. Esamina l'Help in linea riguardo la "Proprietà Formato" per i dati di tipo Numerico e Valuta.

Riguardo ai colori di sfondo, vi sono diversi trucchi (controlli in secondo piano, caratteri giganti, BMP ecc.). Puoi scaricare un piccolo esempio qui: colorend.zip (11 KB).

Stephen Lebans mostra alcune soluzioni che utilizzano le API:
http://www.lebans.com/formatbycriteria.htm

Dev Ashish ha un esempio per il record corrente:
http://www.mvps.org/access/forms/frm0047.htm

Silvio Savoldi risolve il problema come indicato nella FAQ intitolata "Formattazione Condizionale nelle maschere continue" pubblicata nella Sezione Forms del http://www.sitocomune.com.

in alto

4.2 Riferimento ad una sottomaschera/sottoreport
http://www.donkarl.com/it?FAQ4.2 aggiornato 2012-12-14

Problema

Il riferimento ad un campo o una proprietà di una sottomaschera o di un sottoreport non funziona.

Soluzione

La sintassi per riferirsi ad un controllo in una sottomaschera è:

Forms![NomeMascheraPrincipale]![ControlloSottomaschera_in_MascheraPrincipale].Form![Controllo_in_Sottomaschera]

"ControlloSottomaschera_in_MascheraPrincipale" sta a significare il nome del controllo che contiene la sottomaschera. Esso è il valore della proprietà "Nome" del controllo e non è necessario che sia identico al nome della maschera che viene utilizzata come sottomaschera, cioè la proprietà Oggetto Origine. Confondere queste proprietà è l'errore più frequente con questi riferimenti.

Dalla Maschera Principale è sufficiente usare:
Me![ControlloSottomaschera_in_MascheraPrincipale].Form![Controllo_in_Sottomaschera]

Per spostare il fuoco su un controllo in una sottomaschera o p.e. per utilizzare il metodo GoToRecord per la sottomaschera, devi prima spostare il fuoco sul controllo della sottomaschera:

Me![ControlloSottomaschera_in_MascheraPrincipale].SetFocus
Me![ControlloSottomaschera_in_MascheraPrincipale].Form![Controllo_in_Sottomaschera].SetFocus


rispetto a

Me![ControlloSottomaschera_in_MascheraPrincipale].SetFocus
DoCmd.GoToRecord , , acNext


Per i report la sintassi è la stessa. Devi soltanto sostituire "Forms" con "Reports" e "Form" con "Report".

Dev Ashish mostra esempi per tutte le possibili varianti:
http://www.mvps.org/access/forms/frm0031.htm

in alto

4.3 Sincronizzare le maschere
http://www.donkarl.com/it?FAQ4.3 aggiornato 2013-09-04

Problema

Desideri che scegliendo un record in una maschera, un'altra maschera immediatamente mostri lo stesso record.

Soluzione

Supponiamo che in entrambe le maschere il campo unico e comparabile, sia chiamato "Id". Allora in un evento appropriato, a. e. SuCorrente della prima maschera, puoi usare:

Forms!frmMaschera2.Recordset.FindFirst "Id = " & Me!Id

L'uso del Recordset della maschera è possibile da Access 2000. In versioni più vecchie puoi usare il RecordsetClone. Qui un esempio: Articolo KB tedesco con DB d'esempio

in alto

4.4 Cercare un record
http://www.donkarl.com/it?FAQ4.4 aggiornato 2012-12-18

Problema

Hai una casella di testo o una casella combinata non associate, chiamate p.e "txtRicerca". Dopo che ne hai inserito o scelto un valore, p.e. un numero fattura, desideri che venga cercato e mostrato il record con questo numero fattura.

Soluzione

Se nella maschera c'è un controllo visibile e capace di ricevere il fuoco, che visualizza il numero fattura, allora puoi usare il metodo FindRecord nell'evento Dopo Aggiornamento del tuo controllo di ricerca:

Me!FatturaNr.SetFocus
DoCmd.FindRecord Me!txtRicerca


Altrimenti puoi usare il seguente codice generato nell'evento Dopo Aggiornamento del controllo di ricerca:

Me.Recordset.FindFirst "FatturaNr = " & Me!txtRicerca
'o se FatturaNr non è di un tipo numero ma del tipo testo:
'Me.Recordset.FindFirst "FatturaNr = '" & Me!txtRicerca & "'"


L'uso del Recordset della maschera è possibile da Access 2000. In versioni più vecchie puoi usare il RecordsetClone. Qui un esempio: Articolo KB tedesco con DB d'esempio

in alto

4.5 Lo stesso record dopo un Requery
http://www.donkarl.com/it?FAQ4.5 aggiornato 2012-12-18

Problema

Devi utilizzare il Requery per aggiornare i dati nella tua maschera, ma l'effetto del Requery è che il fuoco torna al primo record della maschera. Invece desideri che esso rimanga dove prima si trovava.

Soluzione

Salva l'Id (un campo univoco) del record corrente. Allora puoi tornare sul record dopo l'esecuzione di Requery:

Dim lngStore As Long

lngStore = Me!Id

'riduce lo sfarfallio dello schermo
Me.Painting = False

Me.Requery
Me.Recordset.FindFirst "Id = " & lngStore

Me.Painting = True

in alto

4.6 Mostrare diverse istanze di una maschera
http://www.donkarl.com/it?FAQ4.6

Problema

Vuoi aprire una maschera più di una volta, cioè mostrarla sullo schermo più volte p.e. per essere in grado di mostrare record diversi in maschere affiancate.

Soluzione

Nelle versioni >=A95 puoi aprire istanze multiple di una maschera.
p.e. nella sezione di dichiarazione del modulo di una maschera scrivi:

Dim FormAgain As New Form_NomeDellaTuaMaschera

Poi in un evento appropriato rendi visibile la seconda istanza e la piazzerai in un punto differente dello schermo perchè altrimenti si sovrapporrà sulla prima istanza.

With FormAgain
    .Visible = True
    DoCmd.MoveSize 2000, 2000
End With


Vedi anche http://support.microsoft.com/?kbid=210248
Articolo KB tedesco con DB d'esempio

in alto

4.7 Cambiare l'ordinamento di una maschera
http://www.donkarl.com/it?FAQ4.7

Problema

Vuoi cambiare il tipo di ordinamento in una maschera senza usare i pulsanti Ordinamento crescente/decrescente nella barra dei comandi ma p.e. con un click di un tuo pulsante.

Soluzione

O crei una stringa SQL con una clausola ORDER BY e la usi come origine record della maschera, oppure imposti le proprietà OrderBy e OrderByOn della maschera, via codice:

Esempio con stringa SQL:

Dim strSQL As String
strSQL = "SELECT * FROM tbl_Clienti ORDER BY tbl_Clienti.Cognome;"
Me.RecordSource = strSQL


Se non hai molta esperienza con il linguaggio SQL o se l'espressione SQL è più complessa, allora la maniera comoda è quella di creare una query nella griglia di struttura query di Access e copiare il codice SQL dalla visualizzazione SQL della struttura query.

Di solito il miglior modo per effettuare l'ordinamento dei record è quello di cambiarne l'origine. Non solo perché risulta più professionale ma anche perché se effettui l'ordinamento utilizzando le proprietà della maschera (non importa se nell'interfaccia utente o da codice) Access salva l'ultimo criterio di ordinamento nella proprietà OrderBy della maschera. Tuttavia alcuni esempi:

'Ordinamento ascendente per il campo Cognome
Me.OrderBy = "Cognome"
Me.OrderByOn = True


'Ordinamento decrescente
Me.OrderBy = "Cognome desc"
Me.OrderByOn = True


Access salva l'ultimo ordinamento. Per prevenire gli effetti indesiderati di ciò quando la prossima volta apri la maschera, devi scrivere la seguente riga nel codice dell'evento Su Apertura della maschera:
Me.OrderBy = ""

vedi anche http://support.microsoft.com/?kbid=207769
Articolo KB tedesco con DB d'esempio

in alto

4.8 Cambiare una sottomaschera
http://www.donkarl.com/it?FAQ4.8 aggiornato 2012-06-08

Problema

In esecuzione vuoi usare maschere diverse come sottomaschere nello stesso controllo sottomaschera.

Soluzione

Con VBA puoi cambiare la proprietà SourceObject del controllo sottomaschera (nell'esempio "sfcontrol") nella maschera principale:

Me!sfcontrol.SourceObject = "MiaProssimaSottoMaschera"

Se con ciò anche i campi collegati della sottomaschera e della maschera principale sono differenti, devi cambiare le proprietà Collega campi secondari e Collega campi master del controllo sottomaschera:

Me!sfcontrol.LinkChildFields = "CampoInSottomaschera"
Me!sfcontrol.LinkMasterFields = "CampoInMascheraPrincipale"


Access automaticamente collega la chiave primaria (se presente). Così se il tuo campo collegato non è chiave primaria ne devi settare le proprietà a una stringa vuota prima di poterlo cambiare ai nuovi valori:

Me!sfcontrol.SourceObject = "MiaProssimaSottoMaschera"
Me!sfcontrol.LinkChildFields = ""
Me!sfcontrol.LinkMasterFields = ""
Me!sfcontrol.LinkChildFields = "CampoInSottomaschera"
Me!sfcontrol.LinkMasterFields = "CampoInMascheraPrincipale"


Articolo KB tedesco con DB d'esempio

in alto

4.9 Salva/Cancella non funziona in una maschera popup di A97
http://www.donkarl.com/it?FAQ4.9 aggiornato 2009-10-20

Problema

In una maschera popup di A97 stai utilizzando del codice che è stato prodotto con l'autocomposizione. Nel codice vi sono dei comandi che utilizzano DoMenuItem p.e. per salvare o cancellare un record. Queste istruzioni non funzionano.

Causa

In A97 DoMenuItem non opera in una maschera popup, cioè perfino con VBA le voci di menù non sono raggiungibili in una maschera popup. (in altre versioni ciò dovrebbe funzionare)

Soluzione

Sostituisci i DoMenuItem con RunCommand. p.e.

salva il record corrente: RunCommand acCmdSaveRecord
cancella il record corrente: RunCommand acCmdDeleteRecord

È' sempre raccomandabile sostituire il "datato" DoMenuItem. Esiste solo per ragioni di compatibilità e d'altronde la Microsoft non ha aggiornato le autocomposizioni da tanto tempo. In ogni caso i RunCommand sono molto più significativi.

in alto

4.10 Cambiare riga con il tasto freccia
http://www.donkarl.com/it?FAQ4.10

Problema

In una maschera continua vuoi usare i tasti sù e giù per cambiare record, così come in un foglio dati o nelle tabelle o query.

Soluzione

Imposta la proprietà KeyPreview (Anteprima tasti) della maschera a . Utilizza il seguente codice nell'evento KeyDown (Su tasto giù) della maschera:

On Error Resume Next 'se primo o ultimo record
Select Case KeyCode
    Case vbKeyDown
        KeyCode = 0
        DoCmd.GoToRecord , , acNext
    Case vbKeyUp
        KeyCode = 0
        DoCmd.GoToRecord , , acPrevious
End Select


Articolo KB tedesco con DB d'esempio

in alto

4.11 Salvare valori calcolati
http://www.donkarl.com/it?FAQ4.11 aggiornato 2009-10-29

Problema

Vuoi salvare il risultato di un controllo calcolato nella tabella che è origine dati della maschera.

Soluzione

Generalmente non è una buona abitudine salvare i valori calcolati. Prima dovresti valutare bene se è veramente necessario salvarlo, dato che solitamente può essere ricalcolato anche in seguito. Salvare i valori calcolati può essere utile se alcuni parametri possono variare nel tempo e non vuoi tenere traccia dei vecchi valori in una tabella storica aggiuntiva, o se lavori con formule complesse e salvando il valore puoi risparmiare in seguito il tempo necessario ad eseguire il calcolo.

Ovviamente ti servirà nella tabella un campo in cui salvare il valore.
Poi puoi usare il seguente codice, nell'evento Dopo Aggiornamento di ciascun controllo interessato dal calcolo o nell'evento Prima di Aggiornare della maschera:

Me!NomeCampoDellaTabella = Me!NomeControlloCalcolato

in alto

4.12 Casella combinata/di riepilogo - Selezionare una riga
http://www.donkarl.com/it?FAQ4.12

Problema

Vuoi selezionare una riga specifica in una casella combinata o in una casella di riepilogo oppure p.e. definire la prima riga come valore predefinito così che si trovi già scelto all'apertura della maschera.

Soluzione

Usa il seguente codice nella routine evento Su Apertura della maschera:

Me!NomeCasella = Me!NomeCasella.ItemData(0)
oppure
come espressione nella proprietà Valore Predefinito della casella:
[NomeCasella].[ItemData](0)

L'indice della proprietà ItemData inizia con 0 = riga 1, 1 = riga 2 ecc.

in alto

4.13 Casella combinata - Aggiungere un nuovo record
http://www.donkarl.com/it?FAQ4.13

Problema

Vuoi aggiungere un nuovo record ad una casella combinata (combo box).

Soluzione

Variante 1

L'utente scrive nella casella un valore non presente nell'elenco. Lo vuoi aggiungere all'origine dati in automatico, senza chiedere conferme. Quindi devi:
- ordinare la casella dopo che il campo ha avuto l'inserimento
- impostare la proprieta Solo in elenco a
- utilizzare il seguente codice nell'evento Su non in elenco della combo

'************** INIZIO CODICE **************
Response = acDataErrAdded

Dim db As DAO.Database
Dim rs As DAO.Recordset
Set db = CurrentDb
Set rs = db.OpenRecordset("NomeTabella", dbOpenDynaset)

rs.AddNew
rs!NomeCampo = NewData
rs.Update

rs.Close : Set rs = Nothing
Set db = Nothing

'************** FINE CODICE **************

Variante 2

Diciamo che tu hai una maschera "frm_Fattura" con una combo "cbo_RicercaClienti" (la colonna associata è "IdCliente"). Se l'utente digita un nuovo valore nella combo tu prima glielo chiedi, poi apri una maschera di inserimento dati ("frm_NuovoCliente"), acquisisci il nome del (nuovo) cliente e permetti che l'utente aggiunga ulteriori dati nella maschera di inserimento. Dopo la chiusura della maschera la combo mostrerà il nuovo valore. Per raggiungere ciò utilizza il seguente codice nell'evento Su non in elenco della combo:

'************** INIZIO CODICE **************
If MsgBox("Questo è un nuovo cliente. Vuoi creare un nuovo record?", vbYesNo) = vbYes Then
  Response = acDataErrContinue
  DoCmd.OpenForm "frm_NuovoCliente", , , , acFormAdd
  Forms!frm_NuovoCliente!NomeCliente = NewData
Else 'p.e. nel caso di un errore di digitazione
  Response = acDataErrContinue
  Me!cbo_RicercaClienti.Undo
End If

'************** FINE CODICE **************

Nell'evento Su chiusura della maschera di inserimento:
Forms!frm_Fattura!cbo_RicercaCliente = Me!IdCliente
Forms!frm_Fattura!cbo_RicercaCliente.Requery

in alto

4.14 Aprire una casella combinata via codice
http://www.donkarl.com/it?FAQ4.14

Problema

Vuoi aprire l'elenco di una combo senza che sia necessario fare click sul pulsante della combo.

Soluzione

A partire dal A95 esiste un metodo speciale chiamato Dropdown:

Me!MiaCasellaCombinata.SetFocus
Me!MiaCasellaCombinata.Dropdown

In A2 potresti farlo solo con Sendkeys "%{down}" o SendKeys "{F4}". Questo non è consigliabile poiché Sendkeys ha dei bug.

in alto

4.15 Casella combinata/di riepilogo - Accesso all'ennesima colonna
http://www.donkarl.com/it?FAQ4.15

Problema

Hai una casella combinata o una casella di riepilogo e vuoi ottenere il valore di una colonna che non è la colonna associata.

Soluzione

Utilizza la proprietà Column(Index)
L'indice (Index) parte da 0 per la prima colonna. Così se p.e. vuoi mostrare il valore della seconda colonna di una combo in una casella di testo, puoi usare il seguente Origine controllo per la casella di testo:

=[MiaCasellaCombinata].[Column](1)

Se vuoi salvare il valore della colonna in un campo diverso puoi assegnarlo con il seguente codice, p.e., nell'evento Dopo Aggiornamento della combo:

Me!MioControlloOCampo=Me!MiaCasellaCombinata.Column(1)

in alto

4.16 Casella di riepilogo - Allineamento a destra
http://www.donkarl.com/it?FAQ4.16

Problema

Desideri l'allineamento a destra per la colonna di una casella di riepilogo (solitamente per le cifre).

Soluzione

Non c'è nulla di predisposto per ottenerlo. Le colonne delle caselle di riepilogo sono sempre considerate come testo e giustificate a sinistra. Vi è un vecchio sistema:

- scegliere un font non-proporzionale per la casella di riepilogo (p.e. uno dei font Courier)
- utilizzare una query come origine dati
- nella query usare la seguente espressione p.e. per un campo chiamato "Prezzo"

Space(12-Len(Format([Prezzo];"#.##0,00"))) & Format([Prezzo];"#.##0,00")

Questa dà una stringa con 12 caratteri riempita con gli spazi all'inizio. Questo esempio è sufficiente per cifre fino ai singoli milioni.

Altra possibilità è utilizzare le API. Ciò spesso è addirittura meno affidabile, ma dai uno sguardo all'interessante esperimento di Stephen Lebans:
http://www.lebans.com/justicombo.htm

in alto

4.17 Struttura a schede - evento cambiamento pagina
http://www.donkarl.com/it?FAQ4.17

Problema

Vuoi interagire con il cambiamento della pagina in un controllo Struttura a Schede e non trovi un evento appropriato.

Soluzione

Quando cambi la pagina facendo click sulla scheda lanci l'evento Su modifica del controllo Struttura a Schede. In questo evento puoi leggere la proprietà PageIndex del controllo. È uguale alla proprietà standard Value. Dunque nell'evento Su Modifica del controllo Struttura a Schede puoi utilizzare semplicemente:

Select Case MioControlloSchede
  Case 0
    'hai cliccato sulla prima pagina
  Case 1
    'seconda pagina
  'ecc.
End Select

in alto

4.18 Struttura a Schede - Cambia pagina con la tastiera
http://www.donkarl.com/it?FAQ4.18

Problema

Quando il fuoco si trova sull'ultimo controllo della prima pagina di una struttura a schede, vorresti posizionarti al primo controllo della seconda pagina premendo INVIO, Freccia giù o TAB.

Soluzione

Usa il codice seguente a fronte dell'evento Su tasto giù dell'ultimo controllo della prima pagina:

Select Case KeyCode
  Case vbKeyReturn, vbKeyDown, vbKeyTab And (Shift And acShiftMask) = 0
    KeyCode = 0    
    Me!MioPrimoControlloSullaProssimaPagina.SetFocus
End Select


articolo KB tedesco con DB d'esempio

in alto

4.19 Verificare se una maschera è aperta
http://www.donkarl.com/it?FAQ4.19

Problema

Vuoi sapere se una certa maschera è aperta in questo momento p.e. per usarla in una condizione nel tuo codice o in una espressione.

Soluzione

Nelle versioni >=A00 trovi la proprietà IsLoaded per gli oggetti di Access:

CurrentProject.AllForms("NomeMiaMaschera").IsLoaded

Questa proprietà restituisce Vero o Falso.

Alternativamente e in A95 e A97 puoi usare SysCmd. Copia il codice seguente in un modulo standard:

Public Function fctIsFormOpen(StrName As String) As Boolean
  fctIsFormOpen = (SysCmd(acSysCmdGetObjectState, acForm, StrName) > 0)
End Function


In VBA puoi usare una istruzione come questa:
If fctIsFormOpen("NomeMiaMaschera") Then ...

Puoi anche usare
fctIsFormOpen("NomeMiaMaschera")
in espressioni dell'interfaccia di Access p.e. nella colonna condizione di una macro.

in alto

4.20 Determinare la risoluzione dello schermo
http://www.donkarl.com/it?FAQ4.20

Problema

Vuoi determinare la risoluzione corrente dello schermo.

Soluzione

Copia il codice seguente nella sezione dichiarazioni di un nuovo modulo standard:

Declare Function GetSystemMetrics Lib "user32" (ByVal nIndex As Long) As Long
Const SM_CXSCREEN = 0
Const SM_CYSCREEN = 1


Quindi potrai richiamare la funzione API, p.e. con una funzione, in questo modo:

Public Function fctResolution()
  fctResolution = "pixels horizontal: " & GetSystemMetrics(SM_CXSCREEN) & _
  "  vertical: " & GetSystemMetrics(SM_CYSCREEN)
End Function

in alto

4.21 Adattare le maschere alla risoluzione dello schermo
http://www.donkarl.com/it?FAQ4.21 aggiornato 2012-12-07

Problema

Desideri adattare le dimensioni delle maschere, la posizione e la grandezza dei controlli ecc. alla risoluzione corrente dello schermo.

Soluzione

Un metodo tecnicamente semplice ma con più lavoro di manutenzione è creare più versioni di una maschera e aprire quella giusta secondo la risoluzione dello schermo.

Da Access 2007 esiste la funzionalità di ancoraggio (anchoring) per l'adattamento delle dimensioni dei controlli.

Oltre a ciò l'adattamento delle maschere necessita di parecchio codice. Spesso ci sono problemi in dettaglio con le proporzioni, le dimensioni dei caratteri, ecc. Ciò può anche accadere con i vari strumenti su Internet come:

- Form Resizer For Microsoft Access http://jamiessoftware.tk/resizeform/afr.exe
- Access Developer's Handbook scaling/resizing utility http://www.developershandbook.com/Downloads/ADHResize.zip
- ShrinkerStretcher http://www.peterssoftware.com

in alto

4.22 Valore predefinito dal record precedente
http://www.donkarl.com/it?FAQ4.22 aggiornato 2005-08-02

Problema

Dopo aver inserito un valore in un record vuoi che diventi il valore predefinito per un nuovo record, in modo tale che l'utente non debba inserirlo di nuovo ma lo possa cambiare su richiesta.

Soluzione

Sull'evento Dopo aggiornamento del controllo o della maschera puoi usare il seguente codice:

per una stringa
Me!MioControllo.DefaultValue = Chr$(34) & Me!MioControllo & Chr$(34)

per una data
Me!MioControllo.DefaultValue = Str(CDbl(Me!MioControllo))

per altri tipi di dati (numeri, si/no, ecc.)
Me!MioControllo.DefaultValue = Me!MioControllo

Articolo KB tedesco con DB d'esempio

in alto

4.23 Disattivare i tasti PaginaSu/PaginaGiù
http://www.donkarl.com/it?FAQ4.23

Problema

Con i tasti <PaginaSu> e <PaginaGiù> l'utente può passare ad un altro record. Vuoi disabilitare ciò.

Soluzione

Imposta la proprietà Anteprima tasti della maschera a .

Sull'evento Su tasto giù della maschera puoi usare:
If KeyCode = vbKeyPageUp Or KeyCode = vbKeyPageDown Then KeyCode = 0

Nelle maschere tutti i tasti sono programmabili con VBA in questo modo.

Se vuoi soltanto disattivare i tasti speciali di Access puoi usare la voce del menu Strumenti/Avvio/Avanzate/Usa tasti speciali Access. Altrimenti puoi usare una macro chiamata Autokeys. Vedi <F1> Help.

in alto

4.24 Posizionare il cursore/la selezione
http://www.donkarl.com/it?FAQ4.24

Problema

In una casella di testo vuoi posizionare il cursore "automaticamente" all'inizio o alla fine del testo, oppure vuoi selezionare l'intero testo.

Soluzione

Puoi impostare il comportamento del cursore per tutto il database attraverso il menù Strumenti/Opzioni/Tastiera/Comportamento cursore nel campo.

I controlli li puoi programmare singolarmente. O utilizzi le seguenti istruzioni VBA nell'evento Su Invio o Su click del controllo oppure prima posizioni il cursore all'interno del controllo p.e. con:
Me!MiCasellaDiTesto.SetFocus

Impostare il cursore all'inizio del testo:
Me!MioControllo.SelStart = 0

Impostare il cursore alla fine del testo:
Me!MioControllo.SelStart = Len("" & Me!MioControllo)

Selezionare l'intero testo:
Me!MioControllo.SelStart = 0
Me!MioControllo.SelLength = Len("" & Me!MioControllo)


La stringa vuota impedisce l'errore della funzione Len se non vi è alcun testo. Invece, puoi anche usare: Len(Nz(Me!MioControllo))

Articolo KB tedesco con DB d'esempio

in alto

4.25 Evitare duplicati
http://www.donkarl.com/it?FAQ4.25 aggiornato 2005-12-07

Problema

Vuoi evitare che l'utente inserisca in un campo un valore che è già nella tabella sottostante. Se tenta di fare ciò dovrebbe apparire un messaggio d'errore di facile comprensione.

Soluzione

Variante 1

Nella tabella imposta un indice Sì (duplicati non ammessi) nel campo.
Nel codice dell'evento Su errore della maschera scrivi:

If DataErr = 3022 Then
  Response = acDataErrContinue
  MsgBox Me!MioControllo & " Già esiste.", vbOKOnly, "Duplicato!"
  Me!MioControllo.SetFocus
End If


Variante 2

Con il metodo precedente il controllo avviene non prima che il record sia salvato, cioè normalmente al cambio di record. Se vuoi il controllo immediatamente dopo l'inserimento del valore, puoi usare l'evento Prima di aggiornare del controllo, e codice come questo:

If Not IsNull(Dlookup("MioCampo", "MiaTabella", _
    "MioCampo = " & Chr$(34) & Me!MioControllo & Chr$(34))) _
    And Me!MioControllo <> nz(Me!MioControllo.OldValue) Then

  MsgBox Me!MioControllo & " Già esiste.", vbOKOnly, "Duplicato!"
  Cancel = True

End If


La seconda riga del codice è giusto per gestire il tipo testo. Se invece si tratta di un numero la seconda riga dev'essere:

"MioCampo = " & Str(Me!MioControllo))) _

in alto

4.26 Associare una etichetta
http://www.donkarl.com/it?FAQ4.26

Problema

Hai un controllo senza una etichetta associata e vuoi creare tale etichetta per essere in grado p.e., di attivare il controllo genitore facendo click sulla sua etichetta, di muovere insieme entrambi i controlli in modalità Struttura, ecc.

Soluzione

Crea un etichetta non associata.
Usa il comando Taglia sull'etichetta.
Seleziona il controllo che diverrà il controllo genitore.
Usa il comando Incolla.
Ora l'etichetta è associata al controllo scelto in precedenza.

in alto

4.27 E-mail con indirizzo da casella di testo
http://www.donkarl.com/it?FAQ4.27

Problema

In una maschera hai una casella di testo con un indirizzo e-mail e vuoi aprire il tuo programma standard di posta elettronica per inviare una nuova e-mail con l'indirizzo che è nella tua casella di testo.

Soluzione

Utilizza il codice seguente (per >=A97):
DoCmd.SendObject , , , Me!MiaCasellaDiTesto , , , , , True

Nota: Se hai modificato il testo e il cursore è ancora nella casella di testo quando vuoi inviare la e-mail, devi utilizzare la proprietà Text:
DoCmd.SendObject , , , Me!MiaCasellaDiTesto.Text , , , , , True

Con il metodo SendObject puoi anche collocare, p. e., il soggetto e il testo della e-mail. Vedi <F1>.

Se vuoi assolutamente utilizzare un campo ipertesto invece di un campo testo, c'è il problema che il normale utente non sa che dovrebbe inserire "mailto:" davanti al vero indirizzo e-mail. Se non fa così Access lo tratta sempre come indirizzo web, imposta automaticamente "http://" davanti al testo e apre il browser. Se vuoi evitare ciò, puoi correggere l'inserimento nell'evento Dopo aggiornamento della casella di testo:

If InStr(Me!MiaCasellaDiTesto, "@") > 0 Then
  If InStr(Me!MiaCasellaDiTesto, "#http") > 0 Then
    Me!MiaCasellaDiTesto = "#mailto:" & Mid(Me!MiaCasellaDiTesto, 1, InStr(Me!MiaCasellaDiTesto, "#http") - 1) & "#"
  End If
End If

in alto

4.28 Il testo descrizione non appare
http://www.donkarl.com/it?FAQ4.28

Problema

Hai inserito un testo nella proprietà Testo descrizione controllo di un controllo, ma quando passi il puntatore del mouse sopra al controllo il testo non compare.

Soluzione

Probabilmente c'è un rettangolo trasparente o qualcosa di simile attorno o sopra al controllo e perciò il controllo non è in primo piano. In questo caso (o anche se non vi è nulla sopra il controllo) seleziona il controllo in visualizzazione struttura e fai click sulla voce di menu Formato/Porta in primo piano.

in alto

4.29 La rotellina del mouse scorre i record
http://www.donkarl.com/it?FAQ4.29 aggiornato 2009-10-20

Problema

L'utente può spostarsi da un record all'altro usando la rotellina del mouse. Vuoi evitare questo comportamento.
In A97 può anche accadere che perfino un piccolo movimento della rotellina del mouse provochi un tumultuoso scorrimento dei record.

Soluzione

Da A07 il problema non esiste più perché lo spostamento con la rotellina è disattivato.
Per le versioni fino a A03 c'è il codice di Wayne Phillips per intercettare i comandi del mouse che evita l'utilizzo di DLL esterne:
http://www.everythingaccess.com/tutorials.asp?ID=A-new-method-for-disabling-the-Mouse-Scroll-Wheel-in-Access-forms

Le soluzioni classiche funzionano con le DLL:
http://www.lebans.com/mousewheelonoff.htm
http://www.mantuanet.it/alessandro.baraldi (sezione API)
http://support.microsoft.com/?kbid=278379
http://www.mvps.org/access/api/api0036.htm

Lo scorrimento tumultuoso dei record con un Intellimouse dovrebbe essere sistemato dal SR2 di Office97 o con più recenti driver di mouse:
http://support.microsoft.com/?kbid=192008

in alto

4.30 Intestazione Colonne in visualizzazione foglio dati
http://www.donkarl.com/it?FAQ4.30 aggiornato 2007-01-03

Problema

Apri una maschera in visualizzazione foglio dati e vuoi cambiare l'intestazione della colonna ma non trovi una proprietà o una impostazione conforme.

Soluzione

Vi sono due modi per ricavare l'intestazione di una colonna:

1. Se il controllo non ha un'etichetta associata allora la proprietà Nome elemento del controllo viene utilizzata come intestazione della colonna. In questo modo puoi adattare questa proprietà per cambiare l'intestazione della colonna.

2. Se vi è un'etichetta associata allora la sua proprietà Etichetta è usata quale intestazione della colonna e anche così lo stesso controllo etichetta non è mai mostrato in visualizzazione foglio dati. Pertanto puoi adattare questa proprietà in visualizzazione struttura o con VBA per modificare l'intestazione della colonna. La FAQ 4.26 descrive come associare una etichetta ad un controllo esistente.

in alto

4.31 Mostrare GIF animate
http://www.donkarl.com/it?FAQ4.31 aggiornato 2008-11-22

Problema

Vuoi mostrare immagini GIF animate in una maschera.

Soluzione

senza controlli ActiveX:
http://www.lebans.com/animatedgifplayer.htm

controlli ActiveX:
MS fornisce il Microsoft Animation Control (incluso in alcune classi MSComCtl e in ODE/MOD)
vedi anche http://support.microsoft.com/?kbid=209919
come Shareware: Animation Gif Control http://www.jcomsoft.com/anigif.htm

Altra possibilità è quella di utilizzare il Webbrowser Control o il DHTML Edit Control di MS Internet Explorer.

in alto

4.32 Chiedere prima di salvare un record
http://www.donkarl.com/it?FAQ4.32

Problema

Se un record è stato modificato non vuoi che sia salvato automaticamente ma prima vuoi una richiesta di conferma.

Soluzione

Utilizza il codice seguente nella procedura d'evento Prima di aggiornare della maschera:

If MsgBox("Salvare le modifiche?", vbYesNo, "Salvare?") = vbNo Then
  Me.Undo 'annulla tutte le modifiche nel record
  Cancel = True 'evita successivi eventi
End If

in alto

4.33 Controllare se un record è primo, ultimo o nuovo
http://www.donkarl.com/it?FAQ4.33

Problema

Vuoi verificare da programma se il record corrente in una maschera è il primo, l'ultimo o uno nuovo.

Soluzione

Utilizza il seguente codice in un evento appropriato, per esempio Su corrente della maschera:

If Me.CurrentRecord = 1 Then MsgBox "Sono il primo!"

Me.RecordsetClone.MoveLast
If Me.CurrentRecord = Me.RecordsetClone.RecordCount Then MsgBox "Sono l'ultimo!"

If Me.NewRecord Then MsgBox "Sono nuovo qui."


Ci sono ulteriori spiegazioni sull'Help in linea usando le parole chiave "CurrentRecord" e "NewRecord".

in alto

4.34 Tutti i controlli scompaiono
http://www.donkarl.com/it?FAQ4.34

Problema

Una maschera che è aperta in visualizzazione Maschera è completamente vuota, cioè non mostra alcun controllo. Mentre in visualizzazione struttura i controlli sono ancora visibili.

Causa

La ragione più comune per questo comportamento è che la tabella sottostante o più spesso la query (nella proprietà Origine record) non restituisce alcun record. In aggiunta la possibilità di creare nuovi record è disabilitata nella query o nella maschera. P. e., la query non è aggiornabile o la proprietà della maschera Consenti aggiunte è impostata a No.

Soluzione

Devi assicurarti che l'origine dati restituisca i record o ti permetta l'aggiunta di nuovi record. Così devi modificare la query o la proprietà della maschera per consentire aggiunte.

Se invece vuoi che almeno un pulsante sia visibile (p.e. per chiudere la maschera) devi soltanto spostare il pulsante o qualsiasi controllo nella sezione intestazione o piè di pagina della maschera poiché solo la sezione Corpo maschera diventa vuota.

Ulteriori informazioni: http://support.microsoft.com/?kbid=93261

in alto

4.35 Nascondere il pulsante di chiusura in una maschera di A97
http://www.donkarl.com/it?FAQ4.35

Problema

Non vuoi che il pulsante di chiusura compaia nella barra del titolo di una maschera di Access. Esiste una conforme proprietà per le maschere che disabilita (appare grigio) il simbolo di chiusura se la maschera non è massimizzata, ma A97 ha un bug che rende nuovamente attivo il pulsante di chiusura nelle maschere massimizzate (nelle versioni più recenti questo è stato risolto).

Soluzione

Se vuoi soltanto evitare la chiusura della maschera puoi intercettarla nell'evento Su scaricamento della maschera (FAQ 1.12). Ciò ha il vantaggio che sia la combinazione di tasti di Windows [Ctrl+F4] che la voce di menu non funzionano più.

Comunque il malfunzionamento in A97 può solo essere evitato dall'uso delle funzioni API.
L'esempio di codice di Terry Kreft mostra come adattare le dimensioni della maschera a quelle della finestra MDI di Access invece di massimizzarla.
http://www.mvps.org/access/api/api0022.htm

in alto

4.36 Dipendenza delle caselle combinate/riepilogo
http://www.donkarl.com/it?FAQ4.36 aggiornato 2006-09-16

Problema

In una maschera hai 2 o più caselle combinate o di riepilogo e vuoi che il contenuto della seconda casella combinata/riepilogo dipenda dalla prima, cioè mostri solo i record della categoria che è stata scelta nella prima.

Soluzione

Nota: Le caselle combinate e riepilogo possono essere trattate allo stesso modo. Senza andare a fondo nella strutturazione delle tabelle utilizzate, in generale tra queste dovrà sussistere una relazione di 1->n.

Supponiamo di avere una maschera "frm_Prodotti" con due caselle combinate. La "cbo_Categorie" che mostra le categorie del prodotto, e la "cbo_Prodotti", che mostra i prodotti. Ora, scegliendo una categoria nella prima (superiore) casella combinata, vuoi che la seconda casella (dipendente) mostri solo i prodotti che appartengono a questa categoria.

Il punto cruciale è l'origine riga della cbo_Prodotti.
Questa può essere una query salvata che ha un criterio alla colonna CategoriaID con un riferimento alla casella combinata superiore:
Forms!frm_Prodotti!cbo_Categorie

Ma l'origine può anche essere una stringa SQL che hai digitato nella proprietà Origine riga della dipendente casella combinata o che è impostata nel codice dell'evento Dopo aggiornamento della casella combinata superiore:

Me!cbo_Prodotti.RowSource = "SELECT NomeProdotto FROM tbl_Prodotti WHERE CategoriaId= " & Me!cbo_Categorie

Se non hai impostato dinamicamente l'origine riga della casella combinata dipendente (come mostrato nell'ultimo esempio) ma, p.e. è una query salvata, allora in aggiunta devi aggiornare la visualizzazione. Per ottenere ciò puoi utilizzare il metodo Requery nel codice dell'evento Dopo aggiornamento della casella combinata superiore:
Me!cbo_Prodotti.Requery

in alto

4.37 Eseguire calcoli nelle caselle di testo
http://www.donkarl.com/it?FAQ4.37 aggiornato 2007-01-03

Problema

Vuoi inserire una formula di calcolo in una casella di testo e vedere il risultato in un'altra.

Soluzione

Per ottenere ciò puoi utilizzare la funzione Eval. Supponiamo che le tue caselle di testo siano chiamate "txt_Formula" e "txt_Risultato". Nella proprietà Origine controllo della txt_Risultato potresti usare:

=Eval([txt_Formula])

Comunque, spesso è motivo di disturbo che per Eval si usi il punto come separatore decimale. Se vuoi usare la virgola nella formula puoi utilizzare le funzioni stringa, o nelle versioni >=A00 è molto più semplice l'utilizzo della funzione Replace per sostituire la virgola con il punto per Eval. Allora, l'espressione nel campo txt_Risultato diventerebbe:

=Eval(Replace([txt_Formula];",";"."))

In questo modo il risultato è soltanto mostrato nel controllo. Se vuoi salvarlo vedi Salvare valori calcolati.

in alto

4.38 Evitare il cambio record da tastiera
http://www.donkarl.com/it?FAQ4.38 aggiornato 2007-01-03

Problema

Vuoi evitare che premendo i tasti Tab, Invio, o Freccia nel primo/ultimo controllo di una maschera si passi al precedente/successivo record.

Soluzione

Imposta la proprietà Sequenza della maschera a Record corrente.

Vedi anche Disattivare i tasti PaginaSu/PaginaGiù

in alto

4.39 Numero/Somma incrementale in una maschera
http://www.donkarl.com/it?FAQ4.39 aggiornato 2016-09-06

Problema

Vuoi che in una casella di testo appaia un numero od una somma incrementale.

Soluzione

Numero incrementale

Puoi utilizzare una query come origine del record che calcoli già il numero incrementale.
Un'altro metodo è quello di usare la proprietà AbsolutePosition di un recordset DAO.
Copia la seguente funzione nel modulo della maschera:

'************* INIZIO CODICE ************
Function FctNr()
'restituisce un numero incrementale in una maschera
'lo mostra in una casella di testo con Origine controllo: =FctNr()

  On Error GoTo FctNr_Error

  Me.RecordsetClone.Bookmark = Me.Bookmark
  FctNr = Me.RecordsetClone.AbsolutePosition + 1

FctNr_Exit:
  Exit Function

FctNr_Error:
  If Err.Number = 3021 Then FctNr = 0   'nuovo record
  Resume FctNr_Exit

End Function
'************* FINE CODICE ************


Somma incrementale

Vi sono, inoltre, parecchie possibilità, p. e., via DAO:
Somma incrementale in una maschera
Somma incrementale in una maschera con più codice
o utilizzando la funzione DSum:
Somma incrementale in una maschera con DSum

in alto

4.40 Recuperare una selezione multipla di record
http://www.donkarl.com/it?FAQ4.40

Problema

Vuoi selezionare più record in una maschera e poi ritrovare in VBA quali record sono stati selezionati.

Soluzione

Il selettore record in Access permette solo di selezionare record consecutivi. Il tasto <Ctrl> non ha la funzione convenzionale di Windows di una selezione discontinua. Così se hai selezionato record multipli con il selettore record puoi utilizzare la proprietà SelTop e SelHeight della maschera per determinare i record selezionati. Vi sono esempi completi nella KB:
http://support.microsoft.com/?kbid=294202

Se invece vuoi selezionare record che non si succedono uno dopo l'altro l'usuale scappatoia è quello di utilizzare un casella di controllo associata che deve essere impostata in ciascun record desiderato e resettata p.e. tutto in una volta con una query di aggiornamento. Un altro metodo è l'uso di una casella di riepilogo con la sua proprietà Selezione multipla impostata ad Estesa.

in alto

4.41 Casella di testo per l'inserimento di un password
http://www.donkarl.com/it?FAQ4.41 aggiornato 2011-04-30

Problema

Vuoi usare una casella di testo per inserire un password e vedere soltano i soliti asterischi invece del testo.

Soluzione

Imposta la proprietà Maschera di input della casella di testo a: Password

Due note sulla tematica:

- Una domanda frequente è se questo sia anche possibile con un Inputbox di VBA.
Risposta: No. Si deve usare una casella di testo in una maschera.

- Se con il cursore nella casella di password viene attivato il controllo ortografia con <F7> o la voce del menù/ribbon, il testo si vede in chiaro nella finestra di dialogo del controllo ortografia. Se questo è un problema, dovresti disattivare il tasto speciale (nelle impostazioni d'avvio o con un macro di assegnazione tasti) e nascondere la relativa voce di menù/ribbon.

in alto