macro spostamento dati



  • macro spostamento dati
    di pero13 (utente non iscritto) data: 19/12/2012 00:04:23

    ciao...avrei un problema nella creazione di una macro che ritengo semplice, ma che essendo un neofita mi sta facendo impazzire...

    - nel foglio2 di excel ho questa matrice che indica la quantità di codici venduti in un determinato mese dell'anno.

    codice1 codice 2
    gen 2010 5 9
    feb 2010 8 2
    marz 2010 11 5
    etc ... ...

    - nel foglio1 ho una colonna vuota così composta :

    codice ?
    gen 2010
    feb 2010
    marz 2010
    etc

    dove c'è scritto "codice ?" ho creato un menù a tendina che mi permettere di scegliere fra il "codice 1" o il "codice 2"...la macro di cui necessito, non deve far altro che riportare i dati (presenti nel foglio2) relativi al codice che vado a sezionare dal menù, nelle corrispondenti caselle vuote del foglio1.



  • di HarryBosch data: 19/12/2012 19:56:33

    Ciao pero13
    quali sono le caselle vuote del foglio1 alle quali ti riferisci? la colonna 2?
    Perché volendo si potrebbe risolvere anche con una formula:
    - utilizzando un "se" per verificare il contenuto della cella A1 (quella che contiene codice 1 o 2)
    - e due cerca verticale: a seconda del "se", ricerchi nel foglio2, in base al riferimento di data, la colonna del codice1 o del codice2

    ad esempio, in B2 la formula dovrebbe essere così:
    =SE($A$1="codice1";CERCA.VERT(A2;Foglio2!A:C;2;FALSO);CERCA.VERT(A2;Foglio2!A:C;3;FALSO))
    da ricopiare nelle celle in basso.

    Però mi sembra che ti interessano anche le macro. Avresti voglia di postare il tuo tentativo così vediamo di "correggere" il tiro?



  • di pero13 (utente non iscritto) data: 19/12/2012 21:12:44

    ciao a tutti...per ora ho risolto il problema con questa macro in allegato...
    è inutile che vi spieghi come funziona...basta aprire il file per capire il meccanismo!

    in ogni caso, Grazie HarryBosch! se ti va di dare un occhiata al file fammi sapere cosa ne pensi!



  • di HarryBosch data: 20/12/2012 01:53:56

    Che dire, hai già fatto molto bene. L'evento change è quello che ti serve.
    Semmai, invece della funzione "confronta", personalmente trovo più adatto utilizzare il "Find".
    Ti riallego il file con l'uso di quest'ultimo.

    Per il resto non vedo ottimizzazioni, al massimo puoi riferirti ad un range con l'utilizzo delle sole parentesi quadre.
    Nota importante: è necessario impedire l'inserimento nella cella B1 di valori estranei all'elenco, lavoro che hai fatto eseguire alla convalida dati; altrimenti in entrambi i codici avresti un errore proprio nella funzione match o find, che si dovrebbe risolvere intercettando appunto l'errore.
    Il problema della convalida, è che se fai un copia e incolla (sulla cella B1) ti casca l'impalcatura ^_^



  • di pero13 (utente non iscritto) data: 20/12/2012 14:27:22

    Grazie mille Harrybosch! effettivamente il tuo codice è molto più snello e intuitivo per un neofita come come me!
    approfitto delle tue abilità per chiederti un'altra piccola cosa...
    nel Foglio "Correlazione" per poter selezionare il codice da cercare, ho inserito un menù a tendina ( o elenco) tramite una classica "convalida dati" ... il problema è che quando la cella selezionata con il puntatore non è B1 , la freccettina del menù sparisce!!
    c'è un modo per renderla visibile in maniera permanente ?
    in caso contrario, mi consiglieresti di inserire una "casella combinata" che abbia le stesse funzioni ( non saprei bene come fare onestamente) ?



  • di HarryBosch data: 21/12/2012 01:43:53

    Si, la freccettina la vedi solo quando selezioni la cella B1.
    Le Combobox sono molto interessanti e ti invito a studiarne l'utilizzo; ti riallego il file "combobox" dove ho sostituito la convalida, inserendo una combo dai controlli ActiveX.
    Come noterai il codice si compone di due parti:
    - con la prima routine, appena clicco sul bottoncino (DropButtonClick), carico la combo con una lista; e qua ci sono diversi metodi: puoi impostare l'intervallo direttamente nelle proprietà (ListFillRange), oppure passargli i valori aggiungendoli via codice (.AddItem) o ancora assegnandogli un array di valori, come nell'esempio che ti ho postato.
    - la seconda routine controlla l'evento "Change", proprio come era stato usato precedentemente: al variare del valore vengono cercati i valori nell'altro foglio.

    Ti cito soltanto alcune delle diverse proprietà della combo, che potrebbero tornarti utili:
    - DropButtonStyle: per visualizzare il tasto in modo diverso, con stili differenti oltre la classica freccetta rivolta verso il basso
    - Style: che di default è impostato a 0 e permette di scrivere dentro la combo; se selezionato su 2- impedisce la scrittura e permette la sola scelta dall'elenco (come in questo caso)
    - List Row: per scegliere quante righe visualizzare

    Ti lascio scoprire tutte le altre; per aprire le proprietà della combo sul foglio, cliccaci sopra con il tasto destro dopo questo passaggio: -->Sviluppo-->Modalità progettazione. Troverai le proprietà del controllo




  • di pero13 (utente non iscritto) data: 21/12/2012 09:32:31

    Veramente grazie mille!

    ...Per riempire la variabile elenco, invece che utilizzare l'array ( noioso perché riempito a mano e poco funzionale in caso dovessi aggiungere altri codici), ho semplicemente inserito un riferimento alla pagina "Domanda" e all'intervallo dove sono contenuti i nomi dei 3 codici ( li ho dovuti trasporre in verticale).

    Per quanto riguarda le altre proprietà della Combo, mi sto divertendo a modificarle !

    Qui la parte di codice " modificata":
     
    Private Sub ComboBox1_DropButtonClick()
        Dim elenco As Variant
        elenco = [Domanda!i3:i5]   'Al posto di mettere array (...) 
        ComboBox1.List = elenco



  • di HarryBosch data: 21/12/2012 11:30:44

    Esattamente! E hai capito che la combo richiede un range verticale, altrimenti ti mostra solo il primo valore.
    Però si può ovviare anche a questo, inserendo la funzione "Trasponi" che permette appunto di trasporre in colonna dati che sono elencati in riga.

    Con una sola istruzione, popoleresti la combo così:
    ComboBox1.List = Application.Transpose(Sheets("Domanda mensile").[b1:d1])

    E naturalmente puoi anche rendere l'intervallo dinamico: se i codici possono essere aggiunti continuamente, non ha senso continuare a ritoccare il codice; possiamo farlo fare alla macro, come nell'esempio sotto.
    In sostanza "rng" terrà in considerazione fino all'ultima cella occupata della prima riga.
    E tale intervallo sarà trasposto nella combo.

     
    Private Sub ComboBox1_DropButtonClick()
        Dim rng As Range
        With Sheets("Domanda mensile")
            Set rng = .Range(.[b1], .Cells(1, .[b1].End(xlToRight).Column))
        End With
        ComboBox1.List = Application.Transpose(rng)
    End Sub



  • di pero13 (utente non iscritto) data: 21/12/2012 14:37:48

    ho provato il codice che hai inserito poco fa, ma ti devo dire che purtroppo non mi funziona...quando cambio codice dal menù a tendina non modifica i dati sottostanti!
    a guardarlo il codice mi sembra perfetto, non capisco dove sia l'errore!



  • di HarryBosch data: 21/12/2012 14:54:23

    Ma infatti la routine che ti ho postato non modifica i dati sottostanti: serve solamente a caricare i dati nella combobox.

    Oltre a questa devi anche inserire l'evento change per la modifica, che già avevamo visto:
     
    Private Sub ComboBox1_Change()
        Dim Colonna As Integer
        With Sheets("Domanda mensile")
            Colonna = .Rows(1).Find(ComboBox1.Value).Column
            [b2:b25] = .Range(.Cells(2, Colonna), .Cells(25, Colonna)).Value
        End With
    End Sub
    



  • di pero13 (utente non iscritto) data: 21/12/2012 14:58:49

    ho risolto con il codice allegato! mi ero dimenticato di aggiungere al tuo codice , il comando di riempimento della colonna nella pagina "Correlazione" in base al codice scelto ...

    prova a testarlo e verifica questo piccolo bug ( che non riesco a risolvere ) : aggiungi alla pagina "Domanda" un nuovo codice ( per es: codice 4 ) senza necessariamente inserire dati numerici sotto ; questo compare correttamente nel menù a tendina del primo foglio "Correlazione"; ora prova a selezionarlo dalla tendina e lascialo selezionato; torna nella pagina "Domanda" e cancella il codice 4 appena aggiunto ; ora, ritorna nella pagina "Correlazione" e prova cambiare codice dal menù a tendina!

    P.s mentre scrivevo il mess ho letto la tua risposta!
     
    Private Sub ComboBox1_DropButtonClick()
        Dim rng As Range
        Dim Colonna As Integer
        
        With Sheets("Domanda")
            Set rng = .Range(.[b1], .Cells(1, .[b1].End(xlToRight).Column))
    
            Colonna = .Rows(1).Find(ComboBox1.Value).Column
            
            [b2:b25] = .Range(.Cells(2, Colonna), .Cells(25, Colonna)).Value
     
         End With
        
        ComboBox1.List = Application.Transpose(rng)
        
      
    End Sub



  • di pero13 (utente non iscritto) data: 21/12/2012 15:05:43

    niente...utilizzando 2 procedure separate, come giustamente mi hai allegato/ consigliato tu, il bug non esce fuori... evidentemente ,con il codice che ti ho allegato io, veniva fuori perchè ho messo tutto dentro allo stesso With e non avevo inserito la routine ComboBox1_Change()

    che schifezze che combino



  • di pero13 (utente non iscritto) data: 21/12/2012 15:57:26

    ciao, ti vorrei sottoporre un'ulteriore problematica sopraggiunta ( se sarai così gentile da ascoltarmi ancora) :

    in allegato ti ho messo il file, perfettamente funzionante ( grazie a te ovviamente )...ora , nel primo foglio "Correlazione", ho inserito 2 celle che mi calcolano la media e la varianza dei dati che via via vengono riportati... ovviamente i valori cambiano al variare del codice sezionato... esiste un modo per far si che , al variare del codice nel menù a tendina, i valori di "media" e "varianza" del foglio "Correlazione" vengano automaticamente salvati nel foglio "Domanda" nelle caselle in basso? mi serve che vengano "memorizzati" in maniera permanente, e che quindi al variare del codice selezionato non spariscano...



  • di HarryBosch data: 21/12/2012 17:09:50

    Si, devi tenere i due eventi separati, non va bene metterli assieme come avevi tentato/pasticciato ^_^

    Per inserire i due nuovi valori dovrebbero bastarti due piccole istruzioni che assegnino il valore alla giusta colonna; colonna che è già individuata in precedenza dal Find.
    Prova a modificare l'evento Change come sotto.
     
    Private Sub ComboBox1_Change()
        Dim Colonna As Integer
        With Sheets("Domanda")
            Colonna = .Rows(1).Find(ComboBox1.Value).Column
            [b2:b25] = .Range(.Cells(2, Colonna), .Cells(25, Colonna)).Value
            
            .Cells(28, Colonna) = [d28]
            .Cells(29, Colonna) = [d29]
        End With
    End Sub



  • di pero13 (utente non iscritto) data: 22/12/2012 12:07:19

    essendo all'inzio, e non conoscendo ancora bene le funzioni,le proprietà, oggetti etc, anche le cose così semplici mi fanno impazzire ...
    ti ringrazio nuovamente! tutto funziona alla perfezione!