Elektroda.pl
Elektroda.pl
X

Search our partners

Find the latest content on electronic components. Datasheets.com
Elektroda.pl
Please add exception to AdBlock for elektroda.pl.
If you watch the ads, you support portal and users.

programowanie VBA

Piotrek 81 28 Jan 2009 10:31 2917 19
  • #1
    Piotrek 81
    Level 14  
    Witam
    Mam taki oto kod
    Code:
    Private Sub Workbook_Activate()
    
     Dim NumerWiersza
     Dim OdczytywanyWiersz
     Open "licznik.txt" For Input As #1
      Do While Not EOF(1)
       Line Input #1, OdczytywanyWiersz
       Range("E4").Value = OdczytywanyWiersz
       Loop
     Close #1
    End Sub



    Private Sub Workbook_Open()
     Dim LiczbaOdwiedzin
      Open "licznik.txt" For Append As #1
      Close #1

      Open "licznik.txt" For Input As #1
       Do While Not EOF(1)
        Input #1, LiczbaOdwiedzin
         If LiczbaOdwiedzin = "" Then
          LiczbaOdwiedzin = 0
         End If
       Loop
      Close #1

      Open "licznik.txt" For Output As #1
       LiczbaOdwiedzin = LiczbaOdwiedzin + 1
        Write #1, LiczbaOdwiedzin
      Close #1
     
    End Sub

    Uzywan tego jako licznik w exelu. Dziala swietnie tylko na maly problem po zapisaniu nowego pliku i ponownego jego otwarciu licznik znowu zmiena liczbe, przy zapisaniu kopiuje makro do nowego pliku. Jak zmienic kod lub co dopisac zeby po zapisaniu pliku licznik przestal dzialac.
  • #2
    adamas_nt
    Moderator of Programming
    Kod jest dobry, ale nie w tych procedurach zdarzeń. Wydaje mi się, że masz wszystko w module a nie w kodzie arkusza.
    Najprościej zmień:
    Private Sub Workbook_Activate() na: Private Sub Auto_Open()
    Private Sub Workbook_Open() na: Private Sub Auto_Close

    2. Jeżeli kod jest w szablonie to będzie we wszystkich nowych plikach. A po drugie wszystkie Twoje utworzone arkusze będą dopisywać się do pliku licznik.txt (chyba, że o to Ci chodzi).
  • #3
    marek003
    Level 40  
    Ten program tak ma działać i tak działa.
    Po prostu po skopiowaniu makra do nowego pliku i ponownym jego otwarciu makro szuka pliku "licznik.txt" i jeżeli go znajdzie dodaje kolejny numer.

    Aby tego uniknąć należałoby np. połączyć nazwę pliku licznika z nazwa pliku excela i wtedy dla każdego nowego pliku xls będzie nowy plik txt.

    I tu będzie jeszcze jedno ale ... plik z licznikiem w przypadku tego makra jest zapisywany w "moje dokumenty" bez względu gdzie znajduje się plik z excelem. O ile w jednym katalogu nie może być pliku z tą samą nazwą i rozszerzeniem o tyle w różnych katalogach już to może być. Więc może ustawiać lokalizacje pliku licznika (txt) w katalogu w którym znajduje sie plik xls.
  • #4
    Piotrek 81
    Level 14  
    Cos kolo tego. Podam przyklad :
    Mam plik BOOK1 ( w tym pliku dziala licznik), wprowadzam dane do pliku i zapisuje jako BOOK2 ( w tym pliku licznik nie dziala i po zapisaniu informacja jest slata tak ze moge plik otwierac wiele razy bez zmiany informacji). Tak wiec BOOK1 jast niezalezny od reszty plikow.
  • #5
    adamas_nt
    Moderator of Programming
    marek003 wrote:
    Ten program tak ma działać i tak działa.

    Racja. Teraz (w chwili spokoju) "załapałem", że chodzi o Workbook a nie o Wrksheet. Przepraszam za wypisywanie głupot :)

    Jest jeden wspólny licznik zapisany w licznik.txt dla wszystkich tych plików excel'a, w których działa ten kod. Teraz pytanie: Chcemy liczyć otwarcie każdego pliku osobno, czy wszystkich z tej grupy? Ta postać ma sens tylko w tym drugim przypadku. W pierwszym przypadku lepiej zapisać licznik w arkuszu.
  • #6
    marek003
    Level 40  
    Piotrek 81 wrote:
    Cos kolo tego. Podam przyklad :
    Mam plik BOOK1 ( w tym pliku dziala licznik), wprowadzam dane do pliku i zapisuje jako BOOK2 ( w tym pliku licznik nie dziala i po zapisaniu informacja jest slata tak ze moge plik otwierac wiele razy bez zmiany informacji). Tak wiec BOOK1 jast niezalezny od reszty plikow.


    Dobrze rozumiem?

    Plik zapisany w stylu "zapisz jako.." (nowy plik) ma nie mieć makra? Ma mieć tylko zapisany ostatni licznik w E4?
    Tak?

    Dodano po 11 [minuty]:

    Jaką masz wersję Excela ?
  • #7
    adamas_nt
    Moderator of Programming
    Piotrek 81 wrote:
    Cos kolo tego. Podam przyklad :
    Mam plik BOOK1 ( w tym pliku dziala licznik), wprowadzam dane do pliku i zapisuje jako BOOK2 ( w tym pliku licznik nie dziala i po zapisaniu informacja jest slata tak ze moge plik otwierac wiele razy bez zmiany informacji). Tak wiec BOOK1 jast niezalezny od reszty plikow.


    Sposób1. Przed zapisaniem usunąć procedurę dodawania i zapisywania licznika.
    Sposób2. w procedurze ustawić warunek np:
    If ActiveWorkbook.Name = "BOOK1.xls" Then
    (...)
    End If
  • #8
    marek003
    Level 40  
    adamas_nt wrote:

    Sposób1. Przed zapisaniem usunąć procedurę dodawania i zapisywania licznika.
    Sposób2. w procedurze ustawić warunek np:
    If ActiveWorkbook.Name = "BOOK1.xls" Then
    (...)
    End If


    Przy sposobie 2 makro zawsze będzie kopiowane i przy uruchamianiu pojawiać się będzie monit o makrach. Chociaż nie będzie działać z nieodpowiednią nazwą pliku. Ale jeżeli to nie przeszkadza to ok.

    Wersja 2007 już potrafi zapisywać skoroszyty bez makr (A nawet jeżeli jest makro to inaczej zapisuje taki plik (inne rozszerzenie).
    Można to ostatecznie zastosować dogrywając do systemu "przelotkę" która pozwala otwierać pliki zapisane w formacie 2007 (.xlsx). (na marginesie przydaje się nie tylko do poruszanego tematu)

    I wtedy po "zapisz jako ..." wybrać format skoroszytu 2007 (.xlsx) wtedy zostanie plik nagrany bez makra. (o to zapyta się excel - czy jesteś pewny ze chcesz nagrać plik bez makra).
    A po otwarciu nie będzie makra - jednak będzie w formacie 2007 więc żeby go otworzyć ktoś będzie musiał mieć excel2007 lub wgraną "przelotkę"
    Tu strona z "przelotką":
    http://www.microsoft.com/downloads/details.as...FamilyID=941B3470-3AE9-4AEE-8F43-C6BB74CD1466
  • #9
    Piotrek 81
    Level 14  
    Exela mam w wersji 2003. Licznik ma dzialac tylko dla BOOK1 bo jest to master plik. Poznij jest juz nie potrzebny.

    Poprostu tworze mala baze danych w exelu i jak otworze BOOK1 i dodam do niego informacje to licznik przypisze mu odpowiedni numer. Pozniej zapisze pod inna nazwa i to konie polonczenia z plikiem BOOK1. Tak wiec plik BOOK1 to moj podstawowy plik. To taka autonumeracja.
  • #10
    adamas_nt
    Moderator of Programming
    Najlepiej byłoby jednak usuwać kod przed zapisaniem kopii. I dla pewności (gdybyś jednak zapomniał) postawić warunek wykonywania procedury w BOOK1.xls:
    Code:
    Private Sub Workbook_Open()
    
    If ActiveWorkbook.Name = "BOOK1.xls" Then
    Dim LiczbaOdwiedzin
    'Twoja procedura
    End If
    End Sub


    Dopisanie jeszcze trzech linijek:
    Code:
    If ActiveWorkbook.Name <> "BOOK1.xls" Then
    
    MsgBox "Usuń kod..."
    End If
    spowoduje wyświetlenie komunikatu w pliku o innej nazwie niż "BOOK1", a w którym zostawiłeś makro.

    p.s.
    Niepotrzebnie otwierasz (i zaraz zamykasz)w tryb dopisywania:
    Code:
      Open "licznik.txt" For Append As #1
    
      Close #1


    Rozważ zapisywanie wartości w komórce a nie w pliku tekstowym. Ktoś lub coś może usunąć ten plik z dysku. Na innym komputerze lub w innej lokalizacji VB zgłosi błąd. Dane licznika będą zamknięte w arkuszu i nic z zewnątrz nie będzie miało wpływu na jego stan.
  • #11
    Piotrek 81
    Level 14  
    A mogl bys powiedziec jak zmienic ten kod zeby zapislywal licznik w arkuszu a nie w pliku
  • #12
    adamas_nt
    Moderator of Programming
    Najlepiej przeznaczyć na to osobny, ukryty arkusz o nazwie np. "licznik". Instrukcja przypisania:
    Worksheets("licznik").Cells(4, 7).Value = LiczbaOdwiedzin
    Możesz sporo uprościć kod. Powinien zamknąć się w kilku linijkach, zaraz coś napiszemy...
  • #13
    Piotrek 81
    Level 14  
    dzieki bardzo bede wdzieczny za pomoc.
  • #14
    adamas_nt
    Moderator of Programming
    Code:
    Private Sub Workbook_Open()
    
    'Komunikat o obecności kodu w kopii
    If ActiveWorkbook.Name <> "BOOK1.xls" Then
        MsgBox "Usuń kod..."
        Exit Sub 'opuszczenie procedury
    End If

    'jezeli komorka jest pusta (Null) wpisujemy 1, bo pierwsze odwiedziny
    If Worksheets("licznik").Cells(1, 1).Value = "" Then
        Worksheets("licznik").Cells(1, 1).Value = 1
    End If
    'pobranie wartości z komorki A1 w arkuszu "licznik"
    'tu dobrze byloby dopisac nazwe arkusza roboczego...
    Range("E4").Value = Worksheets("licznik").Cells(1, 1)

    'zwiekszamy wartosc licznika
    Worksheets("licznik").Cells(1, 1) = Worksheets("licznik").Cells(1, 1) + 1
     
    End Sub

    Uruchamiany przy otwarciu. I to wystarczy.
    >marek003 Sprawdź i popraw w razie czego...

    p.s.
    Trochę jeszcze uprościłem...
  • #15
    Piotrek 81
    Level 14  
    Usunelem swoj kod i wstawilem twoj ale nie dziala. Zmienilem nazwe arkusza na licznik i nie wiem co jest nie tak.
  • #16
    adamas_nt
    Moderator of Programming
    A gdzie go wkleiłeś? (powinien być w ThisWorbook)
    Ewentualnie zmień nagłówek na: Private Sub Auto_Open()
    Arkusz "licznik" to dodatkowy (nie roboczy)?

    ---------
    Edit
    -----------

    Tu masz przykład. Uwaga na nazwę. Zapisz w innej lokalizacji niż swój.
    Warto też w ostatniej linii (przed End Sub) dopisać:
    ActiveWorkbook.Save
  • #17
    Piotrek 81
    Level 14  
    Sprawdzilem i dziala ale nie do konca tak jak na byc. Jak otworzysz plik BOOK1 to licznik pokazal 1 potem zapisujesz go w plikU o nazwie BOOK2 jest ok przy otwieranu tego pliku nic sie juz nie zmienia. Pozniej otwierasz plik BOOK1 i powinno byc 2 ale dalej jest 1 czyli licznik nie dziala. Licznik dziala dopiero jak Otworze i zapisze plik BOOK1, nie dziala w opcji zapisz jako.
  • #18
    adamas_nt
    Moderator of Programming
    Dopisz przed End Sub:
    ActiveWorkbook.Save

    Nr licznika zostanie zapisany zaraz po jego zwiększeniu. Pierwotnie przy starcie miałeś to zapisywane w licznik.txt - moja wina (coś mi się dzisiaj mózg zawiesza).
  • #19
    Piotrek 81
    Level 14  
    Dziala zarabiscie. Wielkie dzieki. Znasz jakos dobra ksiazke lub strone gdzie moge sobie przyswoic VBA.