PDA

Visualizza la versione completa : [delphi]: form dipendenti


schumi83
06-05-2002, 15:51
ciao,
ho due form. Nel primo (form1) c'è un dbedit "cliente" con accanto un tasto
"cerca". Premendo questo tasto si apre il secondo form (form2) costituito da
una dbgrid e alcuni DBedit per la ricerca dei clienti. Vorrei che l'utente
una volta effettuata la ricerca e trovato il record desiderato nella DBgrid
(questo lo so fare...) debba cliccare su quest'ultimo per aggiungere il
nominativo del cliente nel DBEdit del form1. Come faccio a legare i due
form????

ciao

alka
06-05-2002, 19:03
Dal punto di vista teorico, potresti visualizzare il secondo form utilizzando il metodo ShowModal; il controllo del programma non passa al form chiamante (Form1) fino a quando il Form2 è visibile. Per la chiusura del Form2, potresti posizionare su di esso due controlli TBitBtn. Impostando la proprietà Kind nel modo opportuno (vedi la Guida in linea), puoi rendere questi pulsanti capaci di chiudere la form restituendo un valore di ritorno ("Ok" oppure "Annulla"): questo ti serve solamente per stabilire se l'utente ha convalidato la propria scelta.
Se l'utente conferma la selezione del cliente dalla DBGrid, una volta che la Form2 è stata chiusa, puoi ispezionare gli oggetti contenuti al suo interno, tra cui il record corrente del Dataset "CLIENTE", allo scopo di individuare quale record della tabella è stato selezionato. Ti scrivo un esempio:


procedure TForm1.Button1Click(Sender: TObject);
var
Form2: TForm2;
Id: Integer;
begin
Application.CreateForm(TForm2, Form2);
try
if Form2.ShowModal = mrOk then
begin
Id := Form2.TableRicerca.FieldByName('ID').AsInteger;
Self.TableCliente.Locate('ID', Id, []);
end;
finally
Form2.Free;
end;
end;

(non ho testato il codice per questioni di tempo)

Fai qualche prova...

Ciao!

schumi83
08-05-2002, 13:52
ciao alka,

la ricerca funziona bene solo se clicco su bitbtn ok e non succede nulla se clicco direttamnete sul record della dbgrid. Vorrei che cliccando due volte sul record il valore dell'Id va in un dbedit cliente del form principale. Un'altro problema si presenta quando voglio inserire un nuovo record nella form principale. Cliccando sul button per effettuare la ricerca, mi visualizza solo i precedenti record annullando l'inserimento.
Come posso fare?

matsoftware
08-05-2002, 14:01
Devi richiamare la procedure Bibtn1Click nell'evento onClick della dbgrid ;)

alka
08-05-2002, 14:09
E' evidente che non succeda nulla selezionando un record dalla DBGrid, poichè i dati visualizzati sul controllo vengono prelevati da una sorgente differente da quella utilizzata dal DBEdit.
Se vuoi che il DBEdit venga impostato immediatamente al record selezionato dalla DBGrid, potresti collegare il componente DataSource associato alla DBGrid alla stessa tabella a cui è collegato il componente DataSource associato al DBEdit. In questo modo, entrambi i controlli visuali si riferiscono alla stessa fonte di dati, quindi selezionando un diverso record dalla DBGrid, il cursore della tabella dati si sposterà e nel campo DBEdit verrà visualizzato il valore del campo associato per il record corrente. Fatto questo, potresti anche fare a meno della coppia di pulsanti "Ok" e "Annulla", utilizzando solamente un tasto "Chiudi" per nascondere la finestra di ricerca con la DBGrid.
In questo modo, risolveresti anche il problema di inserimento del nuovo record. Attualmente, vedi solamente i record precedentemente inseriti poichè, con molta probabilità, la finestra di ricerca non viene distrutta alla sua chiusura, oppure ti sei dimenticato di fare la Commit di una transazione per scrivere fisicamente tutte le modifiche apportate sul database (che formato di database usi??). Puoi provare a chiudere e riaprire la tabella a cui è collegata la DBGrid per aggiornare i record al suo interno.
Comunque, usando il metodo indicato sopra, credo che arriverai a risolvere entrambi i problemi.

Ciao!

schumi83
08-05-2002, 18:13
ciao,

se collego la dbgrid alla stessa tabella del dbedit questo mi visualizzerà le informazioni del form principale "abbonamenti" e non + quelle del cliente. Come ti ho scritto prima il problema sorge per l'inserimento di un nuovo record. Vorrei che la ricerca funzionasse anche per un nuovo inserimento facilitando la scelta di un nuovo cliente copiando l'Id della tabella clienti nel dbedit "cliente" della tabella "abbonamenti".

ciao

schumi83
08-05-2002, 18:18
si può fare in modo che quando lo stato è di "append" venga copiato solo l'id del cliente della tabella "clienti" nel dbedit "cliente" della tabella abbonamenti?

schumi83
08-05-2002, 18:19
il database è in access

alka
09-05-2002, 15:02
Riassumendo in pratica, ciò che vuoi ottenere è la selezione di un cliente in base al nome (o altro campo significativo); selezionato il cliente, l'ID associato viene copiato direttamente nel campo relativo di una tabella associata ("Abbonamenti", giusto?).
Credo che tu stia cercando di implementare quello che genericamente si chiama Lookup.
Esistono già dei controlli visuali Delphi in grado di gestire questo tipo di situazione; puoi aggiungere campi di Lookup anche alle tabelle posizionate sul tuo form. Suppongo che tu stia usando il BDE per accedere al database.

Ad ogni modo, puoi provare questa soluzione. Nel form degli Abbonamenti aggiungi un componente Table collegato alla tabella Clienti e il relativo componente DataSource. Per la selezione del cliente, disponi sul form il controllo TDBLookupComboBox (lo trovi nella pagina "Data Controls" della Palette). Ora devi impostare le relazioni in modo adeguato. Imposta la proprietà ListSource al componente DataSource collegato alla tabella dei Clienti: questa è la tabella dalla quale verranno prelevati i valori da visualizzare nel controllo ComboBox. Imposta la proprietà ListField per indicare il campo da cui prelevare i valori (nel tuo caso, presumo sia "Nome" o qualcosa del genere). Questo controllo visualizzerà valori dalla tabella dei Clienti, ma dobbiamo utilizzarlo per modificare quella degli Abbonamenti, quindi devi impostare la proprietà DataSource al componente omonimo associato alla tabella Abbonamenti. La proprietà DataField va impostata con il campo della tabella Abbonamenti che intendi completare attraverso questo controllo visuale (nel tuo caso, presumo sarà qualcosa del tipo "IDCliente"). Riepilogando, hai istruito il controllo affinchè visualizzi e modifichi l'ID del cliente della tabella Abbonamenti visualizzando però i nomi di tali clienti al posto dell'ID, prelevando i dati dal campo "Nome" della tabella Clienti. Ti manca solo un passaggio: indicare al controllo quale campo della tabella Clienti deve essere confrontato con il campo "IDCliente" di Abbonamenti per completare la relazione; per fare ciò, imposta la proprietà KeyField al campo della tabella Clienti che contiene l'ID.

Sono consapevole di aver creato un bel po' di confusione, poichè è più facile da fare che da spiegare. Riassumendo:

DataSource: ABBONAMENTI
DataField: ABBONAMENTI.IdCliente
ListSource: CLIENTI
KeyField: CLIENTI.Id
ListField: CLIENTI.Nome


Credo che sia il metodo più pulito in assoluto per completare i campi di tabelle correlate attraverso una chiave primaria identificativa senza complicarsi la vita con form esterni o altro.
Può sembrare complesso all'inizio, ma quando avrai appreso il concetto, credo che adotterai questa soluzione.

Good luck! :)

schumi83
09-05-2002, 17:02
ciao alka,

grazie per i suggerimenti. Proverò così come hai detto. Un altro problema che ho incontrato sempre nel form abbonamenti è il preview di un report. In pratica nel form abbonamenti c'è un speedbutton che mi apre un preview di un report del contratto abbonamento. Entrambi hanno la stessa table, ma il preview mostra sempre i dati relativi al primo record. Come posso fare per far visualizzare l'anteprima dell'abbonamento selezionato in form abbonamneti??

grazie!

Loading