Table of Contents

Servomoteur

Necessary knowledge: [HW] Motor Module, [HW] Sensors Module, [AVR] Digital Inputs/Outputs, [LIB] Motors, [LIB] Analog to Digital Converter

Connaissances nécessaires: [HW] motor, [HW] sensor, [AVR] Entrées/sorties numériques, [LIB] motor, [LIB] Convertisseur analogique numérique

Théorie

Servomoteur RC
La relation entre la largeur du signal et la position du servomoteur PWM.

Les Servomoteurs sont souvent utilisés dans les modèles radio-contrôlés (RC), et sont très utiles dans beaucoup de cas d’application de petite robotique parce qu’ils sont très compacts et très peu chers. Un servomoteur RC est composé d’un moteur DC, d’une boite de vitesse, d’un capteur de retour de position (habituellement un potentiomètre) ainsi que des électroniques de commande. Le servomoteur RC peut être contrôlé par un signal externe à large impulsion de modulation (PWM). Si un signal rencontre le servomoteur timingrequirements RC, cela défini habituellement une position cible d'entrée pour l’électronique de commande du servomoteur. Les électroniques du servomoteur comparent la position de l’arbre avec la position en entrée, en essayant de trouver la position de l’arbre qui correspond. Le signal de contrôle de la position est un signal sinusoïdal (d’onde) au carré continu, tel que dans la figure. Les servomoteurs RC (radio-contrôlés) sont des actionneurs très courants en robotique et en construction de modèles. Les servomoteurs RC sont composés d’un petit moteur DC, d’un engrenage de réduction et d’un matériel de contrôle logique. Habituellement le rotor du servomoteur bouge jusqu’à une certaine position en essayant de conserver cette position. La position du rotor dépend du signal de contrôle reçu par le servomoteur. En fonction du type de servomoteur, l’angle de rotation maximum du moteur peut changer. Les Servomoteurs qui tournent de manière constante sont rares. Dans ce cas le signal de contrôle ne détermine pas l’angle de révolution mais la vitesse de rotation. Les Servomoteurs “hack” sont bien plus courants. Cela rend la position qui détermine le servomoteur vers une rotation constante. This makes the position determining servo motor to constantly revolving servo Dans ce cas le potentiomètre de retour de position est remplacé par deux résistances fixes et le résistor mécanique qui empêche toutes les rotations est retiré de la boite de vitesse. Une caractéristique très importante du servomoteur est son ratio poids-puissance.

Le signal de contrôle du servomoteur est une impulsion spécifique avec un signal modulé (PWM), qui avec l’impulsion détermine la position du rotor. La période du signal est de 20 ms (50 Hz) et la largeur du pic est de 1 ms – 2 ms. 1 ms marque l’une des positions extrêmes et 2 ms marque la seconde. 1,5 ms marque la position centrale du rotor du servomoteur.

Le servomoteur RC traditionnel est aussi connu sous le nom de servomoteur analogique. Parce que dans les dix dernières années beaucoup de servomoteurs numériques sont devenus courants. La différence entre les deux est que dans les servomoteurs analogiques, le moteur est contrôlé par le même signal PWM d’entrée de 50 Hz. Alors que dans les servomoteurs numériques, le moteur est contrôlé par un micro-contrôleur avec une fréquence plus grande. Le signal d’entrée est le même pour les servomoteurs digitaux mais une fréquence de modulation du moteur plus grande permet de déterminer la position plus rapidement et avec plus de précision.

Pratique

Sur la carte des modules des moteurs du Home Lab il y a deux plugs pour connecter le servomoteur RC. L’extrémité PWM du plugs est connectée aux broches PB5 et PB6 du micro-contrôleur, avec les différentes fonctions en tant que sortie pour comparer les unités A et B du timer 1. Le timer 1 est capable de produire le signal PWM et permet donc de contrôler très simplement dans le programme. La seule difficulté est d’initialiser le timer.

Le timer 1 peut être initialisé en mode de production du PWM, où la valeur maximum du timer est déterminée avec le registre ICR. With the maximum value changed in the program and in the pace divider (taktijagur?) of the timer, the precise PWM frequency for controlling the servo motor con be determined En comparant les registre du timer, on peut définir les longueurs des deux demi périodes les plus hautes du signal PWM. Le timer a une unité spéciale de comparaison qui surveille la valeur du compteur et s’il reste égal à la valeur du registre de comparaison alors il change la valeur de sortie des unités de sortie. Le code suivant est le programme de la librairie du Home Lab qui permet le contrôle du servomoteur. L’objectif est d’utiliser les paramètres déterminés par des fonctions macro pour le timer. Par exemple la période utilise la constante F_CPU, qui marque le rythme de l’horloge du micro-contrôleur. En utilisant ces macros, il n’est pas nécessaire de calculer les paramètres du timer pour différents rythmes d’horloge et le compilateur convertit de toute façon les opérations en constantes, donc la mémoire du programme n’augmente pas et ne demande pas plus de temps.

//
// The value of the timer (20 ms)for achieving the full period of PWM.
// F_CPU is the clock rate of the micro controller which is divided with 50 Hz and 8.
//
//
#define PWM_PERIOD      (F_CPU / 8 / 50)
 
//
// Middle position of PWM servo (5 ms / 20 ms)
// Middle position is 15/200 of full period.
//
#define PWM_MIDDLE_POS  (PWM_PERIOD * 15 / 200)
 
//
// Factor for converting the percents (-100% to 100%)to periods.
// +1 is added to ensure that semi periods would reach to the boundaries of 1 ms and 2 ms or // a little over.
//
#define PWM_RATIO       (PWM_PERIOD / 20 / 2 / 100 + 1)
 
//
// Set-up of the pins.
//
static pin servo_pins[2] =
{
	PIN(B, 5), PIN(B, 6)
};
 
//
// Preparing the servo motor for working.
//
void servomotor_init(unsigned char index)
{
	// The pin of PWM signal for output.
	pin_setup_output(servo_pins[index]); 
 
	// Setup of timer 1.
	// Pace divider (taktijagur?) 8
	// Fast PWM mode, where TOP = ICR
	// OUTA and OUTB to low in comparisson.
	timer1_init_fast_pwm(
		TIMER1_PRESCALE_8,
		TIMER1_FAST_PWM_TOP_ICR,
		TIMER1_FAST_PWM_OUTPUT_CLEAR_ON_MATCH,
		TIMER1_FAST_PWM_OUTPUT_CLEAR_ON_MATCH,
		TIMER1_FAST_PWM_OUTPUT_DISABLE);
 
	// Determining the period by maximum value.
	timer1_set_input_capture_value(PWM_PERIOD);	
}
 
//
// Determining the position of the servo motor.
// The parameter of the position is from -100% to +100%.
//
void servomotor_position(unsigned char index, signed short position)
{	
	switch (index)
	{
		case 0:			
			timer1_set_compare_match_unitA_value(
				PWM_MIDDLE_POS + position * PWM_RATIO);
			break;
 
		case 1:
			timer1_set_compare_match_unitB_value(
				PWM_MIDDLE_POS + position * PWM_RATIO);
			break;
	}
}

Le programme en exemple utilise des fonctions décrites dans la librairie du Home Lab. Au début du programme le premier signal PWM du servomoteur est initialisé avec la fonction servomotor_init. La valeur de la position du servomoteur est récupérée par la voie numéro 3 du convertisseur analogique-numérique, à laquelle est connectée un potentiomètre de la carte des capteurs. Pour récupérer la plage nécessaire de -100 % - +100 % pour contrôler le servomoteur, la moitié de la valeur maximum (512) est soustraite à la valeur de l’ADC et le résultat est divisé par 5. Le résultat est de +/- 102, mais certaines petites inexactitudes ne comptent pas parce que le servomoteur peut avoir une relation différente entre le signal PWM et l’angle de rotation. Dans les applications, nous devons finalement déterminer la largeur de la demi-période du signal PWM en utilisant la méthode du test-and-error. Aussi le contrôle à distance du modèle RC a des occasions correspondantes à la configuration précise. Also the remote controls of RC models have corresponding opportunities for precise setup Lorsque le programme démarre la position du rotor du servomoteur se cale sur la position du potentiomètre.

//
// Testing program of the motor's module of the Homelab kit.
//
#include <homelab/adc.h>
#include <homelab/module/motors.h>
 
//
// Main program.
//
int main(void)
{
	short position;
 
	// Set-up of the ADC.
	adc_init(ADC_REF_AVCC, ADC_PRESCALE_8);
 
	// Set-up of the motor.
	servomotor_init(0);
 
	// Endless loop.
	while (true)
	{
		// Reading the position of the potentiometer and converting the range of
		// the servo motor.
		position = ((short)adc_get_value(3) - (short)512) / (short)5;
 
		// Determining the position of the servo motor.
		servomotor_position(0, position);
	}
}