Domanda.

Ciao Ennius
sono Giandomenico da Milano
volevo chiederti, se possibile un aiuto su un problema che credo sia banale, ma conoscendo poco il VB non capisco dove sta il problema.
ho prelevato e adattato alle mie necessità il programma Mio DB2000.
tutto funziona bene, ma c'è un problema ed è questo: quando si usa il tasto elimina l'intero record viene eliminato e le celle seguenti vengono spostate in su.
fin qui tutto bene, però rimane un buco (o più a seconda di quante righe si eliminano) nella numerazione della prima colonna (colonna A).
dato che ho necessità che la colonna 1 sia numerata progressivamente da 1 fino all'ultimo record ho cercato di aggiungere alla macro che elimina, un pezzo di routine, ed è questo:
1) conta le righe occupate da dati (funziona)
2) dimmi quante sono (funziona)
3) con il ciclo for-next riscrivi a partire da A4 fino alla fine i numeri da 1 alla fine (non funziona)

Range("A4").End(xlDown).Select
R = ActiveCell.Row
MsgBox R
For P = 4 To R
Range("A(P)").Select
Range("A(P)").Value = P - 3
Next P


probabilmente non uso l'istruzione giusta perchè la routine si ferma all'istruzione Range. potresti aiutarmi ?
grazie

Giandomenico Santelli
 

Risposta.

ciao Giandomenico, a parte il fatto che esiste già l'istruzione collegata al pulsante "Elimina", che come vedi, ripristina il numero delle righe:
Private Sub CommandButton3_Click()
If NRec = 0 Then Exit Sub
dimmi = MsgBox("Sicuro di voler eliminare questo record ?", vbYesNo)
If dimmi = vbNo Then Exit Sub
Elencodb.Rows(IndRec + 1).Delete
ControllaDbase
If IndRec = NRec + 1 Then IndRec = IndRec - 1
CollegaDati (IndRec)
End Sub

e quindi da quanto mi dici probabilmente hai fatto qualche errore nelle modifiche da te apportate, ti vorrei ricordare che nella pagina dalla quale hai scaricato il programma, è scritto che "non fornirò spiegazioni" sulle routine usate.
Comunque la tua routine sotto è sbagliata, tu, con la seguente riga:
Range("A4").End(xlDown).Select
stai facendo selezionare la cella che si trova partendo dalla A4, MA ALLA FINE (End) delle celle occupate: in pratica se dalla A4 alla A10 ad esempio, le celle contengono valori, ti viene selezionata la cella A10, cioè la fine delle celle che contengono valori a partire dalla A4. capito? Quindi ciò che credi con la tua:
3) con il ciclo for-next riscrivi a partire da A4 fino alla fine i numeri da 1 alla fine (non funziona)
in realtà non avviene mai.
Poi citi:"fino alla fine" - alla fine di cosa? del foglio di lavoro? guada che sono più di 65000 righe. Meglio sarebbe far controllare se nella colonna a destra, dove ci dovrebbe essere sicuramente un dato (nome, op. art, opp. codice, o quel che sarà). Immagino che se tieni un elenco i dati inseriti siano su righe conseguenti, e quindi il numero indice si dovrà fermare sulla stessa riga dell'ultimo dato. una soluzione è questa: ogni volta che cancelli una riga, scrivi di nuovo in A4 il numero uno, poi con un ciclo che controlla se nella colonna B stessa riga, esiste un dato, fai sommare il valore della cella A precedente, così:
Sub Rinumera()
Dim Cel As Object
[A4].Value = 1
'si imposta la cella A4 a 1
'poi: per ogni cella nella colonna B, da B5 e fino all'ultima ella in B occupata da dati. Ovviamente la cella 'B4 dovrà necessariamente contenere almeno un dato

For Each Cel in Range([B5], [B5].End(xlDown))
'se la cella sarà diversa da vuoto (cioè contiene dati)
If Cel <> "" Then
'nella cella a lato con scarto di 1 colonna a sinistra (Offset(0, -1) mettiamo il valore che
'sarà nella cella a lato con scarto di una colonna E DI una riga sopra (Cel.Offset(-1, -1)) più 1

Cel.Offset(0, -1) = Cel.Offset(-1, -1) + 1
End If
Next
End Sub


e così ottieni di rinumerare tutte le righe dopo averne eliminate quante vorrai, Unico inconveniente: se cancelli la riga 4 e la riga 5 sarà vuota, End, cercandoti l'ultima cella occupata in B, si precipita a Fine foglio. Meglio se allora usi quest'altra routine nella quale è necessario però definire prima il range su cui intervenire, per esempio, puoi decidere di rinumerare tutte le celle fino alla 1000:
Sub Rinumera2()
Dim Cel As Object
[A4].Value = 1
'si imposta la cella A4 a 1
'poi: per ogni cella a partire dalla A5 fino alla A1000
For Each Cel In Range("A5:A1000")
'la cella sarà uguale al valore della cella sopra + 1
Cel = Cel.Offset(-1, 0) + 1
Next
End Sub


Spero tu capisca, attenzione a non sovrapporre istruzioni con quelle esistenti, saluti, ennius

 

Conferma.

grazie Ennius per l'aiuto.
problema risolto.
entrambe le soluzioni sono valide.
Giandomenico