Radiohobby Forum

Интернет конференция журнала "Радиохобби"

Вы не вошли.

Объявление

Подписка на новые материалы от Николая Сухова - ролики, схемы, модели, онлайн конференции, консультации, чат.

Внимание! Почта в доменах Яндекс и Mail.ru не будет работать в профилях форумчан, из-за введённых правительством Украины санкций против этих компаний. Всем, кто ранее использовал подобную почту, для сохранения прежней функциональности форума, рекомендуется её поменять.

Огромная просьба, заливать тематические картинки и файлы в личные файловые каталоги на форуме, чтобы они не потерялись, со временем!

Ссылка "Загрузки" находится справа внизу формы набора сообщения.

Подписка на журнал "Радиохобби" прекращена. Подробности. Форум же - продолжает свою работу.

#161 09.10.2006 00:13:59

ASni
Участник
Откуда: Николаев / Украина
Здесь с 18.11.2004
Сообщений: 34

Re: AVR для "чайников"

Спасибо, теперь понял.
Если бы там было не умножение, а сдвиг, возможно додумался бы сам smile

да, и еще
вот так не лучше будет?

INTERRUPT(SIG_INPUT_CAPTURE1)
{
  unsigned int CurrentTime;
  CurrentTime = (256 * ICR1H) + ICR1L;
  sprintf(buffer, "%06u rpm", (unsigned long)60E6 / (unsigned long)CurrentTime );
  SetLCDPosition(3, 4);
  ShowStr(buffer);
  TCNT1 = 0;
}

на одну переменную и условие меньше ...

Вне форума

#162 10.10.2006 22:21:05

Liv
Ветеран
Откуда: Минск
Здесь с 08.02.2004
Сообщений: 1,233

Re: AVR для "чайников"

Думаю, что в таком варианте программа будет неработоспособной, так как нужно измерять время между двумя захватами, а не индицировать просто состояние счетчика в момент захвата.

Вне форума

#163 17.10.2006 07:55:40

Матроскин
Ветеран
Откуда: Краснодар
Здесь с 06.02.2006
Сообщений: 2,022

Re: AVR для "чайников"

2 Liv
Я Вам как-то письмо присылал, насчет валкодера. Не получали??


......There is someone in my head, but it's not me.......

Вне форума

#164 17.10.2006 22:36:05

Liv
Ветеран
Откуда: Минск
Здесь с 08.02.2004
Сообщений: 1,233

Re: AVR для "чайников"

Что-то у меня с почтой не то. И на Телесисах жалуются, что не отвечаю на письма. Пишите лучше в форум.

Вне форума

#165 18.10.2006 07:37:17

Матроскин
Ветеран
Откуда: Краснодар
Здесь с 06.02.2006
Сообщений: 2,022

Re: AVR для "чайников"

Liv пишет:

Что-то у меня с почтой не то. И на Телесисах жалуются, что не отвечаю на письма. Пишите лучше в форум.

А Вы e-mail сделайте на каком-нибудь русском сервере, mail.ru например, а на старом поставьте переадресацию на первое время. Х его з, что там с этим yahoo происходит.

Ну а я напишу тут, то, что было в том письме.

У меня опять есть к Вам вопросы. С управлением питанием слава Богу, разобрались, идем дальше.
Валкодер. Такой, как в старых шариковых мышках. Из колесика с прорезями и двух оптопар. Хочется мне разобраться, как его применить, например, для регулирования громкости. Самая большая трудность – определить направление вращения вала. Я тут разрисовал, как я понимаю ситуацию. Состояние, когда оптопара затемнена, будем считать единицей. Риски на оси t  означают время изменения состояния оптопар (считаем, что вал вращают с постоянной скоростью, значит изменения происходят периодически с постоянной частотой).
c49b987aed3e.jpg
Я думал, как определить направление и решил, что надо смотреть, какая из двух оптопар первой изменит состояние. В каком бы положении не находился вал, при вращении вправо первой изменит состояние оптопара А, затем Б. Если влево – то наоборот. Верно? Или есть другой способ? Один знакомый делал такую штуку на ПЛИС, так он для определения направления сдвигал один сигнал относительно другого на один такт и делал между ними xor. В результате xor получал при вращении вправо 1, влево – 0. Но то на ПЛИС, там он D-триггер поставил и один сигнал относительно другого сдвинул, в МК по-моему это не очень удобно. Что посоветуете??
И еще есть вопрос. Импульсы с фототранзисторов оптопар далеко не прямоугольны. Чтоб МК не сбоил и четко отделял 0 от 1 надо наверно какое-нибудь пороговое устройство поставить?? Триггеры Шмидта например?

Заранее спасибо!

Отредактировано Матроскин (18.10.2006 07:41:23)


......There is someone in my head, but it's not me.......

Вне форума

#166 18.10.2006 14:30:14

Maxim
Учаснег
Откуда: Донецк
Здесь с 04.10.2005
Сообщений: 726

Re: AVR для "чайников"

Матроскин пишет:

..Валкодер. Такой, как в старых шариковых мышках.. Что посоветуете??..

Полагаю будет уместно: www.vegalab.ru/index.php?option=com_con … &Itemid=54
В книжке в справочнике Э. Реда по ВЧ схемотехнике (издание не помню, есть не во всех) во вспомогательных устройствах опИсан принцип и приведен работающий оптический валкодер smile
А еще, тем же порядком можно сделать бойкий валкодер из шагового двигателя от старого дисковода, да и в принципе мз любого компактного униполярного:
ru3ga.qrz.ru/UZLY/encod.htm


Учите матчасть!

Вне форума

#167 18.10.2006 18:51:21

Матроскин
Ветеран
Откуда: Краснодар
Здесь с 06.02.2006
Сообщений: 2,022

Re: AVR для "чайников"

Все, что по этим ссылкам, я уже видел. Тут прикол вот в чем. Продаются готовые валкодеры, такие как в мыши. Выглядит как резик переменный. Дает такой же двухзначный код 00-01-11-10-00. Вот его я хочу использовать.
Из шаговика валкодер очень громоздкий будет, да и впомогательная схема сложновата. Можно программно сделать все с "мышиным" вариантом.


......There is someone in my head, but it's not me.......

Вне форума

#168 18.10.2006 21:40:09

Liv
Ветеран
Откуда: Минск
Здесь с 08.02.2004
Сообщений: 1,233

Re: AVR для "чайников"

Я использую энкодеры фирмы Bourns типа PEC-16. Обрабатываю энкодер и его кнопку в основном цикле программы. Если программа чем-то занята, то она всё равно не сможет отреагировать на вращение энкодера, а буферизовать проделанный поворот и откладывать его обрботку - это уже слишком. Обработка энкодера по прерываниям неудобна, так как требуется давить дребезг. Более того, чтобы корректно реализовать квадратурный декодер 1х (или 2х, 4х), прерывания должны происходить не по фронту или спаду одного из сигналов, а по любому изменению состояния энкодера. Отсюда следует порочность декодера типа "программный D-триггер, один сигнал энкодера на вход D, второй - на C". При такой реализации INC/DEC всегда происходит по фронту одного из сигналов энкодера, что есть неправильно. Если вал энкдера просто пошевелить на месте, может насчитаться куча импульсов. INC/DEC нужно делать по изменению состояния двух сигналов, чтобы и INC, и DEC происходили в одной и той же точке, но при её проходе с разными направлениями вращения. Информацию о построении правильных квадратурных декодеров можно почерпнуть из описания спец. микросхем, например, HCTL-2000. Если установить время подавления дребезга 5 мс, как советуют в даташит, то при быстром вращении импульсы пропускаются. Это воспринимается пользователем как глючная работа системы. Учитывая то, что на оборот у него 24 импульса, а на каждый импульс состояние выходов меняется 4 раза (именно на этом факте основаны так называемые 4-x квадратурные декодеры), то время подавления дребезга нужно сильно уменьшать. На практике приемлемым оказалось время подавления дребезга 300 мкс. С таким временем практически невозможно повернуть вал так, чтобы импульсы пропускались. С другой стороны, проблем с дребезгом тоже не обнаружено. Столь малые времена, к сожалению, не могут быть сформированы системным таймером как большинство других временных интервалов в программе. Поэтому приходится применять "тупую" задержку в виде цикла. Для таких малых интервалов это вполне допустимо, потери производительности процессора будут минимальными. Тем более, что обработка энкодера - это общение с пользователем, который всегда является самым медленным звеном системы smile Более того, если какая-то задача в основном цикле захочет временно забрать все ресурсы процессора (за вычетом потерь на прерывания), она сможет это сделать. В это время энкодер обслуживаться не будет. Для кнопки время подавления дребезга должно быть существенно большим, я использую 50 мс. Уж очень разные механические характеристики контактных групп кнопки и энкодера.

Программа построена следующим образом: в начале программы один раз вызывается инициализация энкодера iEnc. В основном цикле, который "крутится" с той частотой, которую позволяет процессор и его загрузка на данный момент, вызывается основная задача энкодера mEnc. Она в глобальной переменной Msg оставляет код события энкодера. Этот код передается всем задачам основного цикла, любая из них может его обработать. Функция mEnc вызывает функцию сканирования энкодера EScan, осуществляет подавление дребезга, реализует 1х квадратурный декодер и формирует код события. Квадратурный декодер большей кратности применить тоже можно, но для PEC-16 именно для декодера 1х на каждый щелчок приходится один инкремент/декремент.

Вот текст модуля поддержки энкодера:

;Encoder support module

;----------------------------------------------------------------------------

;Constantes:

.equ	ENDEB	= 300			;encoder debounce delay, uS
.equ	SWDEB	= 50000			;switch button debounce delay, uS

;----------------------------------------------------------------------------

;Derivated constantes:

.equ	ENDEBV = ENDEB/100

.if ENDEBV > MAXBYTE
.error "out of range constant"
.endif

.equ	SWDEBV = SWDEB/100

.if ENDEBV > MAXBYTE
.error "out of range constant"
.endif

;----------------------------------------------------------------------------

;Messages:

.equ	msgNop	= 0x00			;no operation
.equ	msgInc	= 0x01			;increment
.equ	msgDec	= 0x02			;decrement
.equ	msgKdn	= 0x03			;key down
.equ	msgKup	= 0x04			;key up

;----------------------------------------------------------------------------

.DSEG	;Data segment

;----------------------------------------------------------------------------

.CSEG	;Code segment

;----------------------------------------------------------------------------

;Encoder subsystem init:

iEnc:	ldi	Msg,msgNop		;no operation
	rcall	EScan			;scan encoder
	mov	EncSt,temp		;save encoder state
	ret

;----------------------------------------------------------------------------

;Encoder read:

mEnc:	rcall	EScan			;scan encoder
	mov	Cnt,temp		;save encoder state
	eor	temp,EncSt		;check for changes
	breq	no_ch			;return, no changes

	ldi	temp,ENDEBV		;debounce delay for encoder
	bbrc	temp,2,no_sw
	ldi	temp,SWDEBV		;debounce delay for switch button
no_sw:	rcall	Delay

	rcall	EScan			;scan encoder
	cp	temp,Cnt		;check encoder state
	brne	no_ch			;return, bounce
	
	mov	temp,EncSt		;previous encoder state
	mov	EncSt,Cnt		;save new encoder state

;Switch button check:

	bbrc	temp,2,s_0
	bbrs	Cnt,2,q1x		;no changes
	ldi	Msg,msgKdn		;key down message
	rjmp	e_ret
s_0:	bbrc	Cnt,2,q1x		;no changes
	ldi	Msg,msgKup		;key up message
	rjmp	e_ret
	
;1x quadrature decoder:

q1x:	bbrc	temp,0,a_0
a_1:	bbrc	Cnt,0,a_10
	rjmp	no_ch
a_0:	bbrs	Cnt,0,a_01
	rjmp	no_ch
a_01:	bbrc	Cnt,1,pls
	rjmp	no_ch
a_10:	bbrc	Cnt,1,min
	rjmp	no_ch

pls:	ldi	Msg,msgInc		;send increment message
	rjmp	e_ret
		
min:	ldi	Msg,msgDec		;send decrement message
	rjmp	e_ret

no_ch:	ldi	Msg,msgNop		;send no operation message
e_ret:	ret

;----------------------------------------------------------------------------

;Scan encoder:
;Out:	temp - encoder state

EScan:	clr	temp
	Skip_if_Port_EF1_0
	stbr	temp,0
	Skip_if_Port_EF2_0
	stbr	temp,1
	Skip_if_Port_ESB_0
	stbr	temp,2
	ret	

;----------------------------------------------------------------------------

;Delay:
;Input:	temp = delay [x100 uS]

Delay:	push	Cnt
de2:	ldi	Cnt,FCLK/100000
de1:	dec	Cnt			;1 +
	nop				;1 +
	nop				;1 +
	nop				;1 +
	nop				;1 +
	nop				;1 +
	nop				;1 +
	nop				;1 +
	brne	de1			;2 = 10
	dec	temp
	brne	de2
	pop	Cnt
	ret

;----------------------------------------------------------------------------

Вот текст основного модуля программы:


;* Title	: Encoder PEC-16 test
;* Version	: 1.00
;* Target	: ATmega8
;* Author	: wubblick@yahoo.com

;----------------------------------------------------------------------------

.include "m8def.inc"
.include "macros.mac"
.include "Header.asm"

;------------------------- Interrupt Vectors: -------------------------------

.CSEG					;code segment
.org	0
	rjmp	Init			;reset vector
.org	OC1Aaddr
	rjmp	Timer			;Timer1 OC vector
.org	SPMaddr+1			;skip vector table

;-------------------- Program Execution Starts Here: ------------------------

Init:	ldy	RAMEND	
	out	SPL,YL			;locate stack
	out	SPH,YH
	rcall	iWdog			;start internal watchdog
	rcall	iPorts			;ports init
	rcall	iVar			;variables init
	rcall	iTimer			;system timer init
	rcall	iEnc			;encoder subsystem init
	;...
	sei				;interrupts enable

;Main loop:

Main:	rcall	mEnc			;read encoder
	;process encoder messages
	;...
	rcall	mWdog			;watchdog restart
	rjmp 	Main			;loop

;------------------------- Subroutines area: --------------------------------

;Internal watchdog init:

iWdog:	wdr
	ldi	temp,(1<	out	WDTCR,temp	
	ldi	temp,(1<	out	WDTCR,temp		;watchdog enable, period 260 mS	

;Internal watchdog restart:

mWdog:	bbrc	FLAGS,WUpd,nu
	clbr	FLAGS,WUpd
	wdr				;internal watchdog restart
nu:	ret

;----------------------------------------------------------------------------

;Ports init:
	
iPorts:	ldi	temp,PUPB
	out	PORTB,temp		;init PORTB and on/off pullup
	ldi	temp,DIRB	
	out	DDRB,temp		;set PORTB direction
	
	ldi	temp,PUPC
	out	PORTC,temp		;init PORTC and on/off pullup
	ldi	temp,DIRC
	out	DDRC,temp		;set PORTC direction

	ldi	temp,PUPD
	out	PORTD,temp		;init PORTD and on/off pullup
	ldi	temp,DIRD
	out	DDRD,temp		;set PORTD direction
	ret

;----------------------------------------------------------------------------

;Variables init:

iVar:	clr	FLAGS			;clear flags
	ret

;----------------------------------------------------------------------------

;System timer init:

iTimer:	ldi	temp,0
	out	TCCR1A,temp		;OC disable, PWM disable
	ldi	temp,(1<	out	TCCR1B,temp		;CTC, CK/1

	ldi	temp,byte2(T1Div-1)
	out	OCR1AH,temp		;compare register load	
	ldi	temp,byte1(T1Div-1)
	out	OCR1AL,temp

	in	temp,TIMSK
	ori	temp,(1<	out	TIFR,temp		;clear pending interrupts
	out	TIMSK,temp		;output compare interrupt enable
	ret

;System timer interrupt:

Timer:	push	temp
	in	temp,SREG		;save status register
	push	temp
	stbr	Flags,WUpd		;set watchdog update flag
	;...

	pop	temp
	out	SREG,temp		;restore status register
	pop	temp
	reti
	
;----------------------------------------------------------------------------

.include "Encoder.asm"			;link encoder control module

;----------------------------------------------------------------------------

Вот заголовочный файл проекта:


;Project header file

;----------------------------------------------------------------------------

;Constantes:

.equ	FCLK	= 10000000		;Fclk, Hz
.equ	TSYS	= 1000			;time base, uS

;----------------------------------------------------------------------------

;Derivated constantes:

.equ MAXBYTE = 0xFF
.equ MAXWORD = 0xFFFF

.equ T1Div = ((((Fclk/1000)*Tsys)/100)+5)/10	;CK/1

.if T1Div > MAXWORD
.error "out of range constant"
.endif

;----------------------------------------------------------------------------

;Port Definitions:

.equ	DIRB	= 0b11111111		;Port B direction
.equ	PUPB	= 0b00000000		;Port B pull-ups

.equ	DIRC	= 0b11001111		;Port C direction
.equ	PUPC	= 0b00110000		;Port C pull-ups
.equ	EF2	= PC4			; Encoder F2
.equ	EF1	= PC5			; Encoder F1

.macro	Skip_if_Port_EF1_0		;skip if EF1 = 0
	sbic	PINC,EF1
.endm

.macro	Skip_if_Port_EF2_0		;skip if EF2 = 0
	sbic	PINC,EF2
.endm

.equ	DIRD	= 0b11111110		;Port D direction
.equ	PUPD	= 0b00000001		;Port D pull-ups
.equ	ESB	= PD0			; Encoder SB

.macro	Skip_if_Port_ESB_0		;skip if ESB = 0
	sbic	PIND,ESB
.endm

;----------------------------------------------------------------------------

;Global Register Variables:

;r0, r1 used with mul instruction

.def	EncSt	= r2			;store encoder state

.def	temp	= r16			;temporary register temp
.def	Cnt	= r17			;temporary register Cnt
.def	Msg	= r18			;message code

.def	FLAGS	= r25			;flags
 .equ	WUpd	= 0			;watchdog update flag

;r26,r27 used as X-register
;r28,r29 used as Y-register
;r30,r31 used as Z-register

;----------------------------------------------------------------------------

Вот файл макросов, которые могут встречаться в данном проекте:


;***** Macros

.macro	clbr			;clear bit in register
	cbr @0,exp2(@1)
.endm

.macro	stbr			;set bit in register
	sbr @0,exp2(@1)
.endm

.macro	bbrc			;branch if bit in register clear
	sbrs @0,@1
	rjmp @2
.endm

.macro	bbrs			;branch if bit in register set
	sbrc @0,@1
	rjmp @2
.endm

.macro	bbic			;branch if bit in I/O clear
	sbis @0,@1
	rjmp @2
.endm

.macro	bbis			;branch if bit in I/O set
	sbic @0,@1
	rjmp @2
.endm

.macro	addi			;add immediate 
	subi @0,-@1
.endm

.macro	ldx			;load XL, XH with word
	ldi 	XL,byte1(@0)
	ldi 	XH,byte2(@0)
.endm

.macro	ldy			;load YL, YH with word
	ldi	YL,byte1(@0)
	ldi	YH,byte2(@0)
.endm

.macro	ldz			;load ZL, ZH with word
	ldi	ZL,byte1(@0)
	ldi	ZH,byte2(@0)
.endm

.macro	table			;load Z pointer
	ldi	ZL,low (@0*2)
	ldi	ZH,high(@0*2)
.endm

.macro	stdi			;store immediate indirect with displacement
	ldi	temp,@1
	std	@0,temp
.endm

.macro	ldsx			;load XL, XH from memory
	lds 	XL,@0+0
	lds 	XH,@0+1
.endm

.macro	ldsy			;load YL, YH from memory
	lds 	YL,@0+0
	lds 	YH,@0+1
.endm

.macro	ldsz			;load ZL, ZH from memory
	lds 	ZL,@0+0
	lds 	ZH,@0+1
.endm

.macro	stsx			;store XL, XH in memory
	sts 	@0+0,XL
	sts 	@0+1,XH
.endm

.macro	stsy			;store YL, YH in memory
	sts 	@0+0,YL
	sts 	@0+1,YH
.endm

.macro	stsz			;store ZL, ZH in memory
	sts 	@0+0,ZL
	sts 	@0+1,ZH
.endm

Отредактировано Liv (18.10.2006 21:40:43)

Вне форума

#169 19.10.2006 07:13:26

Матроскин
Ветеран
Откуда: Краснодар
Здесь с 06.02.2006
Сообщений: 2,022

Re: AVR для "чайников"

Спасибо!

Liv пишет:

Я использую энкодеры фирмы Bourns типа PEC-16. Обрабатываю энкодер и его кнопку в основном цикле программы.

А что за зверь?? мож ссылку дадите, а то я ничего не накопал. Я так понимаю, он контактный. Тут у нас вряд ли такое можно купить sad

Блин, не думал, что все так сложно. Ну чтож, будем копать. Хотя наверное попозже. Сечас занялся переделкой и переразводкой своего УМЗЧ ВВ. Хочется его в божеский вид привести.


......There is someone in my head, but it's not me.......

Вне форума

#170 19.10.2006 23:12:17

Liv
Ветеран
Откуда: Минск
Здесь с 08.02.2004
Сообщений: 1,233

Re: AVR для "чайников"

Матроскин пишет:

А что за зверь?? мож ссылку дадите, а то я ничего не накопал.

Я вот не понимаю таких вопросов. Вы где копали, в огороде, что-ли? Задаете в google PEC-16 и первая же ссылка - datasheet.

Вне форума

Сейчас в этой теме пользователей: 0, гостей: 1
[Bot] ClaudeBot

Подвал форума

Под управлением FluxBB
Модифицировал Visman

[ Сгенерировано за 0.245 сек, 7 запросов выполнено - Использовано памяти: 661.59 Кбайт (Пик: 711.96 Кбайт) ]