- MultiPlus Wechselrichter Insel und Nulleinspeisung Conrad         
Ergebnis 1 bis 10 von 41

Thema: Bascom: Schrittmotorsteuerung mit Drehencoder?

Hybrid-Darstellung

Vorheriger Beitrag Vorheriger Beitrag   Nächster Beitrag Nächster Beitrag
  1. #1
    Erfahrener Benutzer Robotik Einstein Avatar von Searcher
    Registriert seit
    07.06.2009
    Ort
    NRW
    Beiträge
    1.715
    Blog-Einträge
    133
    Zitat Zitat von MrMiffy08 Beitrag anzeigen
    Code:
    Isr_timer0:
       Timer0_reload = 100                                      'Vorgabe für 50 / sec
       Timer0 = Timer0_reload + Wert
    
       If Timer0 = 25 Then   'Wertbegrenzung nach unten
       Timer0 = 25
       End If
    
       If Timer0 = 255 Then  'Wertbegrenzung nach oben
       Timer0 = 255
       End If
    
       Toggle Led_gelb                                          '= Stepper_takt
    Return
    
    
    Linksroutine:
    Decr Wert
    Return
    
    Rechtsroutine:
    Incr Wert
    Return
    Wie Dein Programm im Ganzen funktioniert, hab ich jetzt nicht nachvollzogen aber Folgendes fiel mir auf:

    In der Isr_Timer0 wird erst der Timer0 gesetzt und dann abgefragt und eventuell nochmal gesetzt. Man könnte erst Timer0_reload und Wert verrechnen und dann abhängig vom errechneten Wert in der Bedingung den Timer0 nur einmal setzen und verhindert somit unnötiges "Hüpfen" des Timers. Timer0 ist ja keine Variable, sondern eine Hardwareeinheit im µC deren Veränderung ja auch gleich Auswirkung auf die HW hat.

    läuft der Timer über wenn ich den DE über den Wert hinaus drehe. Wie kann ich das verhindern?
    In der Links-, Rechtsroutine kannst Du den Wert doch auch begrenzen? Je nachdem wie groß er ist, eben nicht mehr decrementieren oder incrementieren?

    Gruß
    Searcher
    Hoffentlich liegt das Ziel auch am Weg
    ..................................................................Der Weg zu einigen meiner Konstruktionen

  2. #2
    Neuer Benutzer
    Registriert seit
    30.09.2012
    Ort
    bei Berlin
    Beiträge
    2
    Hallo MrMiffy08 und auch alle anderen,
    ich bin auch ein Neuling bei der AVR-Programmierung und
    beschaeftige mich seit ca. einem Monat mit BASCOM. Hab mir das myAVR-MK2 und das LCD-Add_on
    zugelegt und probiere und lerne damit die Programmierung.
    Zusätzlich habe ich den DE von Pollin gekauft und mich in den verschiedenen Foren umgesehen.
    Dort habe ich auch die DE-Routinen von Screwdriver gefunden und für sehr gut befunden.
    Eine dieser DE-Routinen habe ich dann übernommen und verwende diese nun immer.

    Habe deine Code-Schnipsel und deine Anforderungen zusammen gewuerfelt und mal ein Prog
    dafuer erstellt. Auf meiner HW funzt es einwandfrei. Im Anhang mein Code.

    Wichtiger Hinweis:
    Kann so nicht fuer die Ansteuerung eines Schrittmotors uebernommen werden! Es sind diverse
    Aenderungen/Anpassungen noetig, aber die geforderte Funktion eine LED schnell bzw. langsam
    blicken zu lassen ist gegeben. Damit man den DE nicht ständig drehen muss um etwas zu sehen,
    habe ich eine Schrittweitenanpassung benutzt. So ist es jetzt moeglich in 20 Schritten
    die Blinkfrequenz zu veraendern. Solltest du den Bereich erweitern, so achte darauf,
    dass der neu erstellte Timer1_start-wert nicht über die Grenze von 2hoch16 überschreitet,
    denn dann funzt Timer1 nicht!

    Nun noch ein Hinweis an Alle die dieses lesen: Es mag sein dass man das Ergebnis dieses
    Prog einfacher und schneller und besser und kuerzer hinbekommt.
    Doch bedenkt bitte, ich bin, wie oben schon angemerkt, noch ein Anfaenger.

    Achja, die Aussage von Searcher kann ichnur bestätigen.

    So, hier nun mein Bascom-Programm:
    ENCODER_Test-V4.bas

    Hoffe es hilft dir weiter.

    Gruss
    EF_Arcturus (Wolfgang)

  3. #3
    Benutzer Stammmitglied
    Registriert seit
    02.04.2009
    Beiträge
    78
    Hallo Wolfgang,

    vielen Dank für deinen anregenden Beitrag! Die Routine von Screwdrivver hatte ich auch schon mal am Wickel, aber einfach zu wenig verstanden und daher wieder beiseite gelegt. Mit Deinen Anpassungen sieht das schon recht interessant aus, aber ich glaube ich werde mit meiner Einfach.- Version erst einmal weiter machen, bis das so läuft wie ich es brauche.
    Dann will ich mich gerne reinstürzen und Deinem Vorschlag folgen, dazu reicht aber mein momentaner Gehirnschmalz nicht.
    Außerdem bin ich auf mittlerweile bestehende Hardware angewiesen, mit einem Tiny2313, also das Umfiedeln ist nicht die Welt aber ich stelle das mal an zweite Stelle. Im Moment bastele ich an dem o.a. Code weiter, komme morgen wieder rein.
    LG MM

  4. #4
    Benutzer Stammmitglied
    Registriert seit
    02.04.2009
    Beiträge
    78
    Hallo zusammen,

    so, ich habe jetzt mal ein bisschen an den Werten geschraubt (mein Schrittmotor kam beim schnellsten Turn nicht mehr mit) und habe versucht die Begrenzung in die Inc/Dec Routine einzubinden. Bin aber etwas ratlos, denn das hat nun gar nichts gebracht, obwohl ich rein rechnerisch weit vor dem höchsten Timerwert ende (bei 50+155 = 205) - was ist denn das? Wieso läuft da der TImer immer noch über statt bei 205 zu stoppen? Versteh ich nicht. Was mache ich falsch?

    Und zum Thema -
    In der Isr_Timer0 wird erst der Timer0 gesetzt und dann abgefragt und eventuell nochmal gesetzt. Man könnte erst
    Timer0_reload und Wert verrechnen und dann abhängig vom errechneten Wert in der Bedingung den
    Timer0 nur einmal setzen und verhindert somit unnötiges "Hüpfen" des Timers.
    ist das in meinem Code jetzt so richtig? Oder muss ich an anderer Stelle noch was ändern?

    Vielen Dank für weitere Hilfe!

    Aktueller Stand:
    Code:
    $regfile = "attiny2313.dat"
    $crystal = 8000000
    $hwstack = 32
    $swstack = 10
    $framesize = 40
    $baud = 9600
    ' BASCOM-Programm
    ' Stefan Hoffmann 2009
    ' Drehimpulsgeber/Encoder     mit ENCODER-Befehl
    '
    ' In: Drehimpulsgeber an d.0 und d.1 sowie Taster
    
    '-----Deklarationen fuer Drehimpulsgeber:
    
    
      ' Testprogramm  für A3967 Platine mit Dir Step und Enable
    
    $regfile = "attiny2313.dat"
    $framesize = 32
    $swstack = 32
    $hwstack = 32
    $crystal = 8000000                                          'Quarzfrequenz
    $baud = 9600
    
    
    Config Timer0 = Timer , Prescale = 1024                     'Timer1 Deklarationen für den Takt des Steppers
    Enable Timer0
    'Timsk.toie0 = 1      'hab ich mal wegkommentiert.....
    Dim Timer0_reload As Word
    Portd.4 = 1                                                 ' Pullup Widerstand ein   für Enable - ****Enable =0 bedeutet Motor On!!!!  ****
    Enable Interrupts
    On Timer0 Isr_timer0                                        'Deklaration der Timerroutine
    
    
                    ' Inputs: Drehimpulsgeber an d.0 und d.1 sowie Taster an d.3
             '-----Deklarationen fuer Drehimpulsgeber:
    Config Pind.0 = Input
        Encoder_a Alias Pind.0                                  'Encoder Signal B  an Pin 2
    Config Pind.1 = Input
        Encoder_b Alias Pind.1                                  'Encoder Signal A  an Pin 3
    Config Pind.3 = Input
        Taster1 Alias Pind.3                                    'Taster
    
    Pind.0 = 1                                                  'Pullups für den Drehencoder
    Pind.1 = 1
    Pind.3 = 1
                                                       'LED-Outputs stellvertretend für Step, Dir, Enable
                                                      ' In der endgültigen Hardware liegen: Step/Takt auf PD.2 / Taster auf PD.3 / Enable auf PD4 / Richtung auf PD5 /
    Config Portd.2 = Output
        Portd.2 = 0                                             'das ist Step/Takt - Pin 6   - alles mit Pulldown + LEd_gelb
    Config Portd.5 = Output
        Portd.5 = 0                                             ' Pin 9  - der hier steht für Dir
    Config Portb.4 = Output
        Portb.4 = 0                                             ' Pin 16   -  diese Led steht für Enable
    
    Led_gelb Alias Portd.2
    Led_gruen Alias Portd.5
    Led_rot Alias Portb.4
    
    Dim Wert As Word
    Wert = 50                                                   'willkürlich gewählter Startwert
    Dim Zustand As Byte
    
           '***********Hauptschleife:**********
    Do
    
    Led_rot = 0                                                 'Enable ein
    Led_gruen = 1                                               'Dir
    Zustand = Encoder(pind.0 , Pind.1 , Linksroutine , Rechtsroutine , 0)
    
    Loop
    
    End
    
    Isr_timer0:
      Timer0_reload = 50                    'Vorgabe für 38 / sec
      Timer0 = Timer0_reload + Wert
    
      Toggle Led_gelb                                           '= Stepper_takt
    
    Return
    
    
    Linksroutine:
    Decr Wert
       If Wert = 10 Then
       Wert = 10
       End If
    Return
    
    Rechtsroutine:
    Incr Wert
       If Wert = 155 Then
       Wert = 155
       End If
    Return

  5. #5
    Erfahrener Benutzer Robotik Einstein Avatar von Searcher
    Registriert seit
    07.06.2009
    Ort
    NRW
    Beiträge
    1.715
    Blog-Einträge
    133
    Zitat Zitat von MrMiffy08 Beitrag anzeigen
    Wieso läuft da der TImer immer noch über statt bei 205 zu stoppen? Versteh ich nicht. Was mache ich falsch?
    Ich weis nicht genau, was Du mit Timerüberlauf meinst, weil ich vielleicht auch immer noch nicht wirklich die Ansteuerung des Steppers verstehe - was Du eigentlich genau erwartest - wie Du auf einen Timerüberlauf schließt.

    Der Timer0 läuft immer bis 255 und macht dann den Overflow Interrupt. In der ISR wird der TCNT0 nun auf 50 + Wert gesetzt. Läuft also von da aus wieder bis 255 usw.

    Code:
     Isr_timer0:   
      Timer0_reload = 50     'Vorgabe für 38 / sec   
      Timer0 = Timer0_reload + Wert    
      Toggle Led_gelb                         '= Stepper_takt  
    Return
    
    Linksroutine:
       Decr Wert
       If Wert = 10 Then
         Wert = 10
       End If
    Return
    
    Rechtsroutine:
       Incr Wert
       If Wert = 155 Then
         Wert = 155
       End If
    Return
    ist das in meinem Code jetzt so richtig? Oder muss ich an anderer Stelle noch was ändern?
    Hatte ich im Prinzip so gemeint.

    If wert = 10 then Wert = 10 bringt nichts. Wenn Wert auf 9 ist, bleibt er auf 9.
    besser
    If Wert <= 10 Then Wert = 10
    Natürlich auch in der Rechtsroutine beachten

    Aber wie gesagt: Was erwartest Du genau und was tut Dein Programm nicht richtig? Wie stellst Du den Timerüberlauf fest?

    Gruß
    Searcher
    Geändert von Searcher (22.10.2012 um 12:12 Uhr)
    Hoffentlich liegt das Ziel auch am Weg
    ..................................................................Der Weg zu einigen meiner Konstruktionen

  6. #6
    Benutzer Stammmitglied
    Registriert seit
    02.04.2009
    Beiträge
    78
    Hallo Searcher,

    vielen Dank für Deine Antwort!
    Also das Programm soll eigentlich so funktionieren:
    Der Timer soll einen Takt machen, der mit Hilfe des Drehencoders in der Frequenz veränderbar ist, dieses Taktsignal soll auf den Stepperchip (Allegro A3967) gehen und für ihn das Step-Signal darstellen. Daneben braucht der Chip noch Enable (B.4 auf Low gesetzt) und Dir (an D.5), was ich noch gar nicht implementiert habe, das kommt noch. (Da möchte ich, dass der Stepper auf Tastendruck am DE einige volle Umdrehungen rechts herum, dann links herum macht.)

    Diese Takterhöhung/-erniedrigung geht ja nun schon mal, allerdings macht der Takt bei Erreichen des niedrigsten oder höchsten Wertes einen Sprung (das meinte ich mit Überlauf, ist unglücklich ausgedrückt) und geht auf die höchste bzw. niedrigste Taktrate. Ich möchte, dass der Takt bei der jeweils höchsten/niedrigsten Frequenz stehenbleibt und nicht zu einer anderen Geschwindigkeit wechselt.

    Ja, ich sehe schon, als Anfänger benutzt man Vokabeln, die eigentlich was anderes meinen ohne zu ahnen dass das missverständlich ist. Ich komme aber mit Eurer Hilfe so langsam weiter...

    LG MrMiffy

  7. #7
    Erfahrener Benutzer Robotik Einstein Avatar von Searcher
    Registriert seit
    07.06.2009
    Ort
    NRW
    Beiträge
    1.715
    Blog-Einträge
    133
    Zitat Zitat von MrMiffy08 Beitrag anzeigen
    Diese Takterhöhung/-erniedrigung geht ja nun schon mal, allerdings macht der Takt bei Erreichen des niedrigsten oder höchsten Wertes einen Sprung (das meinte ich mit Überlauf, ist unglücklich ausgedrückt) und geht auf die höchste bzw. niedrigste Taktrate. Ich möchte, dass der Takt bei der jeweils höchsten/niedrigsten Frequenz stehenbleibt und nicht zu einer anderen Geschwindigkeit wechselt.
    Das war/ist vermutlich jetzt noch die Abfrage in der Links- Rechtsroutine. Da kann "Wert" überlaufen. Schau meinen letzten Beitrag zu der Abfrage darin.

    Ja, ich sehe schon, als Anfänger benutzt man Vokabeln, die eigentlich was anderes meinen ohne zu ahnen dass das missverständlich ist.
    Null Problemo. Wir waren alle mal Anfänger und solange Du dran bleibst wird das schon. Auch ich zähle mich nicht zu den Nichtanfängern

    Gruß
    Searcher
    Hoffentlich liegt das Ziel auch am Weg
    ..................................................................Der Weg zu einigen meiner Konstruktionen

  8. #8
    Benutzer Stammmitglied
    Registriert seit
    02.04.2009
    Beiträge
    78
    Hallo zusammen,
    noch mal Dank an Searcher für die Hinweise!
    Ich habe das > und < eingefügt und siehe da: Jetzt funktioniert es endlich wie es soll: Der Schritti dreht - mit gedrosseltem Tempo los, kann schneller durch den DE gesteuert werden und bleibt nun auhc bei der jeweiligen Max. und Min.- Geschwindigkeit stehen. Super!
    Etwas Feintuning an den Werten für den Timer und dem Wert asus dem Drehencoder, und jetzt passt alles.

    Ich werde nun noch das Enable für gesteuerten Stop und das Dir für eine Hin und Her-Bewegung implementieren. Wahrscheinlich brauche ich dann noch mal Hilfe, aber ich schraube erst mal ein wenig herum, will ja auch was lernen...

    Aktueller Code:

    Code:
    $regfile = "attiny2313.dat"
    $crystal = 8000000
    $hwstack = 32
    $swstack = 10
    $framesize = 40
    $baud = 9600
    ' BASCOM-Programm
    ' Stefan Hoffmann 2009
    ' Drehimpulsgeber/Encoder     mit ENCODER-Befehl
    '
    ' In: Drehimpulsgeber an d.0 und d.1 sowie Taster
    
    ' Testprogramm  für A3967 Platine mit Dir Step und Enable
    
    $regfile = "attiny2313.dat"
    $framesize = 32
    $swstack = 32
    $hwstack = 32
    $crystal = 8000000                                          'Interner Osz. 8 MHz
    $baud = 9600
    
    
    Config Timer0 = Timer , Prescale = 1024                     'Timer1 Deklarationen für den Takt des Steppers
    Enable Timer0
    Dim Timer0_reload As Word
    Portd.4 = 1                                                 'Pullup Widerstand ein   für Enable - ****Enable =0 bedeutet Motor On!!!!  ****
    Enable Interrupts
    On Timer0 Isr_timer0                                        'Deklaration der Timerroutine
    
             ' Inputs: Drehimpulsgeber an d.0 und d.1 sowie Taster an d.3
             '-----Deklarationen fuer Drehimpulsgeber:
    Config Pind.0 = Input
        Encoder_a Alias Pind.0                                  'Encoder Signal B  an Pin 2
    Config Pind.1 = Input
        Encoder_b Alias Pind.1                                  'Encoder Signal A  an Pin 3
    Config Pind.3 = Input
        Taster1 Alias Pind.3                                    'Taster
    
    Pind.0 = 1                                                  'Pullups für den Drehencoder
    Pind.1 = 1
    Pind.3 = 1
                                                       'LED-Outputs stellvertretend für Step, Dir, Enable
                                                      ' In der endgültigen Hardware liegen: Step/Takt auf PD.2 / Taster auf PD.3 / Enable auf PD4 / Richtung auf PD5 /
    Config Portd.2 = Output
        Portd.2 = 0                                             'das ist Step/Takt - Pin 6   - alles mit Pulldown + LEd_gelb
    Config Portd.5 = Output
        Portd.5 = 0                                             ' Pin 9  -  Dir - Richtungssignal
    Config Portd.4 = Output
        Portd.4 = 0                                             ' Pin 16   -   Enable - generelles Ein-Ausschaltsignal
    
    Motor_step Alias Portd.2
    Led_gruen Alias Portd.5
    Chip_enable Alias Portd.4
    
    Dim Wert As Word
    Wert = 2                                                    'willkürlich gewählter Startwert
    Dim Zustand As Byte
    
           '***********Hauptschleife:**********
    Do
    
    Chip_enable = 0                                             'Enable ein
    Led_gruen = 1                                               'Dir
    Zustand = Encoder(pind.0 , Pind.1 , Linksroutine , Rechtsroutine , 0)
    
    Loop
    
    End
    
    Isr_timer0:
      Timer0_reload = 4                                         'Vorgabe für 38 / sec
      Timer0 = Timer0_reload + Wert
      Toggle Motor_step                                         '= Stepper_takt
    Return
    
    Linksroutine:
    Decr Wert
       If Wert <= 1 Then
       Wert = 1
       End If
    Return
    
    Rechtsroutine:
    Incr Wert
       If Wert >= 230 Then
       Wert = 230
       End If
    Return

Ähnliche Themen

  1. Schrittmotorsteuerung LB1845 und atmega48 in BASCOM
    Von chris155 im Forum Basic-Programmierung (Bascom-Compiler)
    Antworten: 2
    Letzter Beitrag: 09.05.2010, 18:41
  2. Wie Drehencoder anschließen ?
    Von Blamaster im Forum Elektronik
    Antworten: 8
    Letzter Beitrag: 07.09.2009, 19:01
  3. Menüsteuerung mit Drehencoder ?
    Von Blamaster im Forum Basic-Programmierung (Bascom-Compiler)
    Antworten: 25
    Letzter Beitrag: 30.06.2009, 22:34
  4. Drehencoder auswerten
    Von MartinFunk im Forum C - Programmierung (GCC u.a.)
    Antworten: 11
    Letzter Beitrag: 16.05.2007, 16:05
  5. Drehencoder Panasonic
    Von Mr-400-Volt im Forum Software, Algorithmen und KI
    Antworten: 0
    Letzter Beitrag: 04.02.2007, 20:47

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • Anhänge hochladen: Nein
  • Beiträge bearbeiten: Nein
  •  

fchao-Sinus-Wechselrichter AliExpress