Controlador
A figura a seguir ilustra os três tipos de erros de posicionamento de um micromouse em uma célula do maze. O controlador deve ser capaz de minimizar ao máximo estes erros para que o robô tenha sucesso durante a execução do percurso. Simplificadamente, o erro lateral e o erro de direção podem ser corrigidos com auxílio dos sensores laterais que, intuitivamente, fornecem o quanto o micromouse está alinhado ou não no maze, de tal forma que no caso ideal as leituras destes dois sensores devem ser iguais. Já para correção do erro longitudinal podem ser usadas as transições de paredes (parede/sem parede/poste) e também usar os sensores frontais quando se tiver parede frontal.
O controlador Proporcional-Derivativo (PD) pode ser utilizado nesta aplicação e abaixo é apresentado um diagrama de blocos do controlador proposto. Neste controlador são ajustados dois setpoints, a velocidade translacional (speedX) e a velocidade rotacional (speedW). As variáveis manipuladas são as razões cíclicas (duty cycle) dos dois motores. Em uma reta o speedW deve ser zero, enquanto que em curvas speedX e speedW são constantes diferentes de zero, e para realizar uma curva em torno do próprio eixo do robô (curva pivot) speedX deverá ser igual a zero.
Código de exemplo que implementa este controlador:
// Controlador de velocidade para movimento translacional + rotacional void controlador(void) { // Calcula as realimentações dos encoders, sensores e giroscópio // K_GYRO e K_SENSORES são constantes para ajustar as escalas feedbackEncW = deltaEncR - deltaEncL; feedbackSensores = erroSensores / K_SENSORES; feedbackGyro = gyro / K_GYRO; // Calcula os PVs (process variable) do controlador pvX = deltaEncR + deltaEncL; pvW = 0; if(usarEncoders) pvW += feedbackEncW; if(usarSensores) pvW += feedbackSensores; if(usarGyro) pvW += feedbackGyro; // Calcula os erros (erro = Setpoint - PV) // O "+=" representa a operação integrativa da velocidade = posição erroPosX += speedX - pvX; erroPosW += speedW - pvW; // Realiza o controlador PD (Proporcional Derivativo) // KP_X, KD_X, KP_W e KD_W são as constantes do controlador PD posPwmX = KP_X * erroPosX + KD_X * (erroPosX - erroAnteriorPosX); posPwmW = KP_W * erroPosW + KD_W * (erroPosW - erroAnteriorPosW); // Registra os erros anteriores para a ação derivativa erroAnteriorPosX = erroPosX; erroAnteriorPosW = erroPosW; // Calcula os PWMs dos motores da esquerda e da direita pwmL = pwmX - pwmW; pwmR = pwmX + pwmW; // Realiza o comando para atualizar os PWMs dos motores setPwmL(pwmL); setPwmR(pwmR); }
Observação: esta função deve ser chamada em um intervalo fixo de tempo, por exemplo: 1ms ou 10ms.
Uma das técnicas utilizadas para gerar os setpoints das velocidades é a de perfil de velocidade (speed profiler), a qual gera um perfil trapezoidal de velocidade em função do tempo, conforme a figura a seguir, e com isso, a distância percorrida pelo robô é obtida a partir da área do trapézio. As rampas entre [t0; t1] e [t2; t3] são necessárias, pois não é possível acelerar ou desacelerar instantaneamente o micromouse.
Abaixo têm-se os dois principais perfis de velocidade utilizados. Veja este vídeo de exemplo.
Materiais de referência: Ng Beng Kiat: Workshop in Micromouse e Green Ye: Project Futura