avatar_Mucit23

Pwm Modülünde Sabit Duty ve değişken frekans

Başlatan Mucit23, 16 Eylül 2012, 21:52:21

Mucit23

Merhabalar Ete hocam..

Ufak bir problemim var sizin fikrinizi almak istiyorum. Bir çalışma için step motorun devrini istediğim şekilde ayarlamam gerekiyor. Yaklaşık 100 RPm ile çıkabilirse eğer 3000 rpm hıza çıkarmam gerekiyor. 2000 rpm den sonra motorda tork denen birşey kalmıyor. Bunu tecrübe etmiştim ama zaten motor mili boşta olacak.

Motoru L297-L298 ikilisini kullanarak sürüyorum. L297 nin clock girişine İşlemcinin PWM modülünü kullanarak clock frekansı uygulamayı düşündüm. Ama bu biraz karmaşık bir iş sanırım. Duty değerini değiştirmekten daha zor. Hedefim PWM çıkışında %50 sabir duty ve 250Hz ile 10Khz arasında değişken frekans almayı düşündüm. Ama gerçekten kolay bir iş değil çünkü her seferinde pwm frekansını hesaplamalı, PR2 değerini belirlemeli Gerekiyorsa Timer2 Bölücü oranını değiştirmek gerekiyor.
Acaba bu konuda herhangi bir çalışmanız oldumu Nasıl yapabilirim böyle birşeyi.

Bir sorum daha olacak.

Elimdeki çoğu motorlar 1.8 derece adım açısına sahip. Dolayısıyla bir turda 200 pals verilmesi gerekiyor. L297 de yarım veya tam adım sürüş modu veya pini var. Bu belirlemiş olduğum 1 tur için 200pals değeri yarım adım sürüş modu içinmi geçerli? Eğer durum böyleyse tam adım sürüşte bir tur için motora 100 clock palsimi vermek gerekir?
Bir ulusu yok etmenin En iyi yolu o ulusun dilini yok etmektir.

www.arectron.com/

ete

HPWM sinyallerinde değişken frekans olayını daha önce kullanmış idim. Benzer şekilde step motor sinyal frekansını değiştirerek hız ayarı yapmıştım. İşin temel mantığı PR2 register değerinin değişmesine dayanıyor. Elbette frekans aralığı aynı bölücü ile her frekansa ulaşmanı sağlamıyo. Onuda bir (genelde) veya iki if satırı ile bölücü değiştirerek halletmiştim.
Örnek vermek gerekirse diyelimki motora min 500 Hz , max 3000 Hz lik bir sinyal uygulayacaksın.
500 hz değerlerimiz şöyle;
Bölücü 1/16 , PR2 değeri 124, Duty değeri (%50) 250
3000 Hz için değerlerimiz ;
Bölücü yine 1/16 , PR2 değeri 20 , duty değeri 42
Bu durumda PR2 değerini 124 den 20 ye kademeli olarak düşürdüğün taktirde 500 ile 3000 Hz arasında ayarlı frekansın olur. Bu işi bir pot ile yapacaksan,
Pot değeri sıfır iken PR2=124 çıkmalı
Pot değeri 1023 iken PR2=20 çıkmalıdır. Bunların nasıl hesaplanacağını artık yapabilirsin sanırım. Yapamaz isen onuda açıklarım. Bu arada unutmaman gereken şey PR2 nin her yeni değerinde %50 Duty değerini hesaplaman gerekir. (DUTY DEĞERİ=(PR2+1)*4*Duty% )

1,8 derecelik motorlar için 200 puls tam adım sürme için gerekli olan puls miktarıdır. yarım adım için 400 puls vermen gerekir.

Ete




Mucit23

Anladım hocam. Akşam biraz uğraşayım. Okadar kesin bir frekansa ihtiyacım yok çünkü devrin kesin olması gerekmiyor. Zaten diyelim 500hz ile 10000 hz lazım ise aradaki tüm değerleri tutturmak mümkün değil. Aradaki değerler ne çıkarsa o olacak.  Mesela Baktımda 500 Hz ile 10000 hz arasında ayarlamak istersem hiç bölücüyü değiştirmeden(1/16) istediğim aralıkta pwm frekansı alabiliyorum. Ama 10000 hz de pwm çözünürlüğü 6 bite düşüyormuş zaten önemli değil benim duty değerim sabit kalacak.
Sizin derslerde hesapları olacaktı. Bakayım yaparım mutlaka
Bir ulusu yok etmenin En iyi yolu o ulusun dilini yok etmektir.

www.arectron.com/

KAZIMUGUR


Mucit23

Hocam LCD buton felan bir sürü ıvır zıvır olacak. Bi hocam istiyor aslında. Menüden Devri seçecek, Sürüş modunu seçecek devrini değiştirecek. Örnek bir uygulama bana lazım değil. Bittiğinde paylaşırım herhalde. 
Bir ulusu yok etmenin En iyi yolu o ulusun dilini yok etmektir.

www.arectron.com/

Mucit23

Hocam Sadece bir konu aklıma takıldı. Normalde 4Mhz de 1/16 bölücü oranı ile 500 Hz ile 10Khz arasında ayarlamak istiyorum. 500 hz net alabiliyorum ama tam olarak 10Khz çıkmıyor. 10416 küsür bir değer alıyorum. Bu değerler PR2 Registerinin 5-124 arasında bir değer almasıyla Sağlanıyor PR2 5 olduğu zaman 10416 Hz alıyorum. 10416Hz alsam bir problem olmuyor ama yapmışken tam olarak yapayım diyorum. Max değer 10000hz olması için bir if ile PR2 Değeri 5 olduğu zaman Bölücü oranını 1/1 veya 1/4 yapsam bir problem olurmu. Sizin daha iyi bir öneriniz varmıdır?

Birde PR2 Değerinden motor frekansını hesaplayamadım. Daha önce Yaptığım başka bir uygulamada Aşağıdaki formülü kullanmışım.
FREKANS=62500/(PR2+1)
Buradaki 62500 değerini nasıl hesapladık. Pek yabancı gelmiyor...
Bir ulusu yok etmenin En iyi yolu o ulusun dilini yok etmektir.

www.arectron.com/

ete

FREKANS=62500/(PR2+1) formülü şu şekilde hesaplanır. Bu formül 4 Mhz osc frekansı için geçerlidir.
PR2=(Fosc/(4*Bölücü*Freq))-1  şeklinde verilmiş bir formülümüz mevcut.
Buradan frekansı çekecek olursak, (Bölücü değeri 16 alıyoruz)
PR2=(Fosc/64*Freq)-1
PR2=Fosc/64* Freq - 64*Freq/64*Freq
PR2=(Fosc-64* Freq)/64*Freq
PR2 * 64 * Freq = Fosc - 64 * Freq
PR2*64*Freq + 64*Freq=Fosc
Freq * 64 (PR2 + 1) = Fosc
Freq= Fosc/64*(PR2+1)
Freq= 4.000.000 /64 *(PR2+1)
Freq=62500/(PR2+1)
şeklindedir.

Sinyal frekansından devir hesabı zor değil sanırım.
her 200 Hz de 1 devir/sn  olduğuna göre  bunu önce dakika cinsine çevirmek gerekir.
1 dev/sn * 60 sn/1 dak = 60 dev/dak eder. 1 hz için ise bu  60/200 yani  3/10 dev/dak dır.
O halde hemen örnek yapalım 1000 Hz de devir nedir dersek 1000 * 3/10 = 300 dev/dak. dır diyebiliriz.
Yarım adımda devir miktarı yarıya düşecektir unutma.

Ete


Mucit23

Anladım hocam Hesap işini.

Step motorlar ençok hangi adım açılarında üretiliyor. Biraz Piyasaya baktım ençok 1.8 derecelik var. Ayrıca 7.5 derece açıya sahip olanlarda bulunuyor. Bunun dışında kullanılan varmı?
Bir ulusu yok etmenin En iyi yolu o ulusun dilini yok etmektir.

www.arectron.com/

Mucit23

Şu PR2 Registerine sadece Yazmamı yapılabiliyor? Ben PR2 registerinin değerini almak istiyorum ama olması gerekenden çok farklı değerler alıyorum. Bu konuda bilginiz varmı?
Bir ulusu yok etmenin En iyi yolu o ulusun dilini yok etmektir.

www.arectron.com/

ete

PR registeri ile işim hep ona değer vermek yönünde oldu. Hiç değerini okumak zorunda kalmadım. Bilemiyorum. Okuyunca değer göremiyorsan regsiter tek yönlü çalışıyodur.

Ete

Mucit23

Anladım hocam. Hocam Direk PR2 Regsiteriyle Çalışıyordum. Motor yön değiştirme felan yapılınca Motorun yavaş bir şekilde durdurulup eski devrine getirmem gerekiyordu. Bu işlemi yapmadan önce dedim ilk önce PR2 nin değerini alayım. Motor yönünü değiştirdikten sonra yine aynı devire çıkarayım. Ama her seferinde değişik bir değer alınca aklımda soru işareti oluştu. Neyse bende tüm işlemleri direk PR2 üzerinde yapmam önce geçici bir değişkende çalışıp her değişiklikte PR2 yi güncellerim.
Bir ulusu yok etmenin En iyi yolu o ulusun dilini yok etmektir.

www.arectron.com/

Mucit23

Hocam merhaba. Yapması biraz zor olduğunu düşündüğüm bir konuyu sizlere danışmak istiyorum.

Daha önce Frekansı değiştirmek için hep Pr2 registerinin değerini değiştiriyordum. Bölücü sabit kaldığı için PR2 registerin değeri Hangi frekansa denk geliyorsa ona eyvallah ediyordum :) Böyle olunca yüksek frekanslarda frekans çözünürlüğü azaldığı için benim istediğim devirlere yaklaşamıyordum.

Amacım Girdiğim RPM değerinden İlk önce çıkması gereken frekansı sonra ise o frekansa en uygun bölücüyü ve PR2 registerinin değerini hesaplamak istiyorum. Bayağı zor bir işlem. Ama yapılabilirsede PWM donanımının çok güzel bir kullanım örneği elde edilmiş olur.

Elimde 1.8 ve 7.5 derece açılara sahip motorlar var. Sistemi bu iki motora uyumlu çalışacak şekilde kuruyorum. Menüden Sürüş modu seçilebiliyor(Tam-Yarım)

PWM modülünde kendime max ve min frekanslar belirledim. Max. 5000Hz min 250Hz frekans alalım.

250Hz deki 1.8 derecelik motorun tam sürüş modunda devrini hesaplamak için (250*60)/200 = 75 devir/dak çıkar.
Aynı frekansda 7.5 derecelik motoru tam devirle sürersek (250*60)/48=312,5 devir/dak çıkar.

Sürüş modu yarım olursa devir yarı yarıya düşer.

Birde max frekans olun 5000Hz ile düşünelim. 1.8 derecelik motorun devri (5000*60)/200=1500Rpm olur. Şuanda bana gayet yeterli.
7.5 derece için  (5000*60)/48=6250Rpm çıkar. Bu devre çıkmasını beklemiyorum. Bu yüzden 7.5 derecelik motor takıldığında bir sınırlma koyalım.

Her neyse

Ben şimdilik tüm hesaplarımı 1.8 derece göre yapayım.

Eğer PR2 yerine sadece devirle oynayıp PR2 registerinie kendim hesaplarsam motor devrini 10'ar 10'ar arttırırım. örneğin 100 rpm için basit bir hesaplama yaparsak. 333Hz gibi bir değer bulurnur.  Bu değere en yakın pr2 değerini hesaplamam lazım. Tabi bölücü felanda ayarlanacak. Bu konuda hiç fiikir yürütemiyorum şuanda sizin bir fikriniz varmı. Picin dahili PWM donanımı ile ne derece mümkün olabilir

Bir ulusu yok etmenin En iyi yolu o ulusun dilini yok etmektir.

www.arectron.com/

Mucit23

Hocam şimdi düşünüyorum pek mümkün olmuyor. Nekadar bolücüyle oynasamda istediğim frekans larda çıkış almam mümkün değil.
Zaten bu hali ile pr2 registerinin tüm ara değerlerini kullanıyorum.

Belki bu iş için özel entegreler vardır. Veyahut pwm kullanmadan birazcık uğraşarak timerlerle yapılabilir.

Bir ulusu yok etmenin En iyi yolu o ulusun dilini yok etmektir.

www.arectron.com/

oguztkn

#13
Merhaba,

Konuyu hortlatmış olacağım ama aynı sorun olduğundan yeni başlık istemedim.

18f45k22 kullanıyorum. DVR8825 sürücü step kanalı CCP5 (PORTE.2) Dır ucu ise PORTC.7 ye bağlı. Puls sayılarını sayabilmem için de ccp5 kanalı aynı zamanda PORTB.0 a bağlı. Sürücünün m0-m1-m2 uçları 1/8 step konumunda bağlı. Motorum nema 17hs3001-20b 1,5a faz akımı var. Sürünün akım ayarını uygun şekilde ayarladım. Beslemem ise 12v 5A.

Şimdi bu hali ile ben 1600 puls verdiğimde motorum 1 tur atması gerekir

ASM
    __CONFIG _CONFIG1H, _FOSC_INTIO67_1H & _PLLCFG_OFF_1H & _PRICLKEN_ON_1H & _FCMEN_OFF_1H & _IESO_OFF_1H        
    __CONFIG _CONFIG2L, _PWRTEN_ON_2L & _BOREN_OFF_2L & _BORV_285_2L 
    __CONFIG _CONFIG2H, _WDTEN_OFF_2H & _WDTPS_32_2H                                                                                    
    __CONFIG _CONFIG3H, _CCP2MX_PORTB3_3H & _PBADEN_OFF_3H & _CCP3MX_PORTE0_3H & _HFOFST_OFF_3H & _T3CMX_PORTC0_3H & _P2BMX_PORTC0_3H & _MCLRE_INTMCLR_3H
    __CONFIG _CONFIG4L, _STVREN_OFF_4L & _LVP_OFF_4L & _XINST_OFF_4L & _DEBUG_OFF_4L
    __CONFIG _CONFIG5L, _CP0_ON_5L & _CP1_ON_5L & _CP2_ON_5L & _CP3_ON_5L    
    __CONFIG _CONFIG5H, _CPB_ON_5H & _CPD_ON_5H
    __CONFIG _CONFIG6L, _WRT0_OFF_6L & _WRT1_OFF_6L & _WRT2_OFF_6L & _WRT3_OFF_6L
    __CONFIG _CONFIG6H, _WRTC_OFF_6H & _WRTB_OFF_6H & _WRTD_OFF_6H 
    __CONFIG _CONFIG7L, _EBTR0_OFF_7L & _EBTR1_OFF_7L & _EBTR2_OFF_7L & _EBTR3_OFF_7L 
    __CONFIG _CONFIG7H, _EBTRB_OFF_7H 
endasm
;===============================================================================
DEFINE OSC 4
OSCCON  = %01010100        
OSCTUNE = %00000000 
;===============================================================================
DEFINE LCD_DREG      PORTD
DEFINE LCD_DBIT          4
DEFINE LCD_EREG      PORTD
DEFINE LCD_EBIT          0
DEFINE LCD_RWREG     PORTD
DEFINE LCD_RWBIT         1
DEFINE LCD_RSREG     PORTD
DEFINE LCD_RSBIT         2
DEFINE LCD_BITS          4
DEFINE LCD_LINES         4
DEFINE I2C_SLOW          1


DEFINE CCP5_REG PORTE
DEFINE CCP5_BIT 2 

TRISA=0:TRISB=%00000001:TRISC=0:TRISD=0:TRISE=0
PORTA=0:PORTB=0:PORTC=0:PORTD=0:PORTE=0

ADCON0.0=0:ANSELA=0:ANSELB=0:ANSELC=0:ANSELD=0:ANSELE=0 
;===============================================================================
RCON.7=0:PMD0=1:PMD2=1:CM1CON0.7=0:IOCB=%00000000:WPUB=%00011111
SLRCON=0:CTMUCONH.7=0:SRCON0.7=0:VREFCON0.7=0        
;===============================================================================
INTCON=%11010000:INTCON2=%01000000:INTCON3=%00000000
PIR1=0:PIR2=0:PIR3=0:PIR4=0:PIR5=0                  
PIE1=0:PIE3=0:PIE4=0:PIE5=0                          
IPR1=0:IPR3=0:IPR4=0:IPR5=0                            
;===============================================================================
temp var byte
SAYAC VAR WORD
bayrak var bit
PWMDEGER var word
x var word
FREQ VAR WORD
T VAR WORD
DUTY VAR WORD

CCPTMRS1.3=0:CCPTMRS1.2=0
T2CON=%01111010
PR2=249
sayac=0
PORTC.7=0
T2CON.2=1
Basla:
  
  CCP5CON.2=1
  CCP5CON.3=1

FOR FREQ=500 to 15200  
T=1000**1000
T=DIV32 FREQ
PR2=(T/16)-1
DUTY=(PR2+1)*2  
X=DUTY
CCP5CON.4=X.0
CCP5CON.5=X.1
CCPR5L=x>>2
  if sayac>1600 then goto dur  
  PORTA.1=0 
Next

goto basla


dur:
  lcdout $FE,$80,dec5 freq," ",dec4 PR2," ",dec5 sayac
  CCP5CON.2=0
  CCP5CON.3=0
  PORTC.6=1
  PORTA.1=1
  i2cread PORTC.2,PORTC.1,$73,[temp]
  
  if temp.6=0 and bayrak=0 then 
  sayac=0
  PORTC.6=0
  bayrak=1
  goto basla
  ENDIF
  
  if temp.6=1 and bayrak=1 then bayrak=0
goto dur

DISABLE
Kesme:

    SAYAC=SAYAC+1
    INTCON.1=0  
 
;===============================================================================
resume
enable
end

Bu kod ile 1 tur atıyor ama peş peşe birkaç kere çalıştırdığımda kaymaya başlıyor. Bu kod bloğunu bie konuda verdiğiniz örnekten edindim uyarladım.

Benim amacım ekrandan butonlar ile cm girip motorun o kadar ilerlemesini yapmak istiyorum. Ama bundan önce kalkış rampasında takıldım. Nerede hata yapıyorum acaba ?


Şimdiden Teşekkürler...

ete

Programın eksiklerini tamamlayınca biraz olsun doğru çalışmaya başladı.
Bir iki ilave ile en azından simulasyonda ard arda sürekli olarak 1600 sayac değerinde ekrana yakaladığı sayac değerini doğru olarak verdirebiliyorum.
Programın dur kısmına ve kesme kısmına bir iki eklemem oldu. Buraya bakarak kendi programını yeniden düzenle ve çalıştır bakalım sonuç ne olacak.

Ete
#CONFIG
    __CONFIG _CONFIG1H, _FOSC_INTIO67_1H & _PLLCFG_OFF_1H & _PRICLKEN_ON_1H & _FCMEN_OFF_1H & _IESO_OFF_1H        
    __CONFIG _CONFIG2L, _PWRTEN_ON_2L & _BOREN_OFF_2L & _BORV_285_2L 
    __CONFIG _CONFIG2H, _WDTEN_OFF_2H & _WDTPS_32_2H                                                                                    
    __CONFIG _CONFIG3H, _CCP2MX_PORTB3_3H & _PBADEN_OFF_3H & _CCP3MX_PORTE0_3H & _HFOFST_OFF_3H & _T3CMX_PORTC0_3H & _P2BMX_PORTC0_3H & _MCLRE_INTMCLR_3H
    __CONFIG _CONFIG4L, _STVREN_OFF_4L & _LVP_OFF_4L & _XINST_OFF_4L & _DEBUG_OFF_4L
    __CONFIG _CONFIG5L, _CP0_ON_5L & _CP1_ON_5L & _CP2_ON_5L & _CP3_ON_5L    
    __CONFIG _CONFIG5H, _CPB_ON_5H & _CPD_ON_5H
    __CONFIG _CONFIG6L, _WRT0_OFF_6L & _WRT1_OFF_6L & _WRT2_OFF_6L & _WRT3_OFF_6L
    __CONFIG _CONFIG6H, _WRTC_OFF_6H & _WRTB_OFF_6H & _WRTD_OFF_6H 
    __CONFIG _CONFIG7L, _EBTR0_OFF_7L & _EBTR1_OFF_7L & _EBTR2_OFF_7L & _EBTR3_OFF_7L 
    __CONFIG _CONFIG7H, _EBTRB_OFF_7H 
#ENDCONFIG
;===============================================================================
DEFINE OSC 4
OSCCON  = %01010100        
OSCTUNE = %00000000 
;===============================================================================
DEFINE LCD_DREG      PORTD
DEFINE LCD_DBIT          4
DEFINE LCD_EREG      PORTD
DEFINE LCD_EBIT          0
DEFINE LCD_RWREG     PORTD
DEFINE LCD_RWBIT         1
DEFINE LCD_RSREG     PORTD
DEFINE LCD_RSBIT         2
DEFINE LCD_BITS          4
DEFINE LCD_LINES         4
DEFINE I2C_SLOW          1


DEFINE CCP5_REG PORTE
DEFINE CCP5_BIT 2 

TRISA=0:TRISB=%00000001:TRISC=0:TRISD=0:TRISE=0
PORTA=0:PORTB=0:PORTC=0:PORTD=0:PORTE=0

ADCON0.0=0:ANSELA=0:ANSELB=0:ANSELC=0:ANSELD=0:ANSELE=0 
;===============================================================================
RCON.7=0:PMD0=1:PMD2=1:CM1CON0.7=0:IOCB=%00000000:WPUB=%00011111
SLRCON=0:CTMUCONH.7=0:SRCON0.7=0:VREFCON0.7=0        
;===============================================================================
INTCON=%10010000:INTCON2=%01000000:INTCON3=%00000000
PIR1=0:PIR2=0:PIR3=0:PIR4=0:PIR5=0                  
PIE1=0:PIE3=0:PIE4=0:PIE5=0                          
IPR1=0:IPR3=0:IPR4=0:IPR5=0                            
;===============================================================================
temp var byte
SAYAC VAR WORD 60
bayrak var bit
PWMDEGER var word
x var word
FREQ VAR WORD
T VAR WORD
DUTY VAR WORD
HOP VAR BIT
lcdout $fe,1
pause 250

CCPTMRS1.3=0:CCPTMRS1.2=0
T2CON=%01111010  '%xxxxx100=1/1  , %xxxxx101=1/4 , %xxxxxx110=1/16 
PR2=249
sayac=0
PORTC.7=0
T2CON.2=1
ON INTERRUPT GOTO KESME

Basla:
  
  CCP5CON.2=1
  CCP5CON.3=1

FOR FREQ=500 to 15200  
T=1000**1000
T=DIV32 FREQ
PR2=(T/16)-1
DUTY=(PR2+1)*2  
X=DUTY
CCP5CON.4=X.0
CCP5CON.5=X.1
CCPR5L=x>>2
'  if sayac=1600 then goto dur  
IF HOP=1 THEN DUR
  PORTA.1=0 
Next

goto basla


dur:
    INTCON.4=0
    LCDOUT $FE,1  
  lcdout $FE,$80,dec5 freq," ",dec4 PR2," ",dec5 sayac
  CCP5CON.2=0
  CCP5CON.3=0
  PORTC.6=1
  PORTA.1=1
'  i2cread PORTC.2,PORTC.1,$73,[temp]

'  if temp.6=0 and bayrak=0 then 
'  sayac=0
'  PORTC.6=0
'  bayrak=1


'  goto basla
'  ENDIF
    HOP=0
  SAYAC=0   
  INTCON.4=1 
  if temp.6=1 and bayrak=1 then bayrak=0

goto BASLA

DISABLE
Kesme:

    SAYAC=SAYAC+1
    IF SAYAC=1600 THEN 
       INTCON.4=0
       HOP=1
    ENDIF   
    INTCON.1=0  
 
;===============================================================================
resume
enable
end


Powered by EzPortal