- Labornetzteil AliExpress         
Seite 3 von 3 ErsteErste 123
Ergebnis 21 bis 23 von 23

Thema: 'Schiefes Koordinatensystem' begradigen

  1. #21
    Erfahrener Benutzer Roboter Genie
    Registriert seit
    08.07.2004
    Ort
    Südhessen
    Beiträge
    1.312
    Anzeige

    Powerstation Test
    Also ich muss sagen: mare_crisium: RESPEKT! Es funktioniert sogar. Danke für Deine Zeit, ich werde sicher auch davon profitieren.

  2. #22
    Erfahrener Benutzer Robotik Einstein Avatar von Jaecko
    Registriert seit
    16.10.2006
    Ort
    Lkr. Rottal/Inn
    Alter
    41
    Beiträge
    2.009
    So... hab nun noch etwas am Code rumgebastelt.
    Die Get-Funktion liefert nun neben der Position auch einen Rückgabewert, ob die Positionen verwertbar sind (return 1) oder ungültig (unendlich, ausserhalb des Displaybereichs etc; return 0).
    Somit gibts nun eigentlich keine Fehlpositionen mehr (ausser man drückt zu lasch drauf, dass es zwischen den beiden Touchfolien keinen richtigen Kontakt gibt, aber da hilft dann auch kein noch so guter Algorithmus mehr).

    Hier mal die relevanten Ausschnitte aus den Sourcefiles:

    touchpad_cfg.h
    Code:
    #ifndef _TOUCHPAD_CFG_H_
    #define _TOUCHPAD_CFG_H_
    
    // Those can be determined by a calibration procedure (touch all 4 corners)
    // Here they are loaded with default values
    ui16_t r0[2] = { 101, 145 };
    ui16_t r1[2] = { 867, 150 };
    ui16_t r2[2] = { 848, 802 };
    ui16_t r3[2] = { 102, 759 };
    
    
    #define LCD_Width   128   // Display width in pixels
    #define LCD_Height   64   // Display height in pixels
    #define Iterations    5   // Iteration steps for determining the exact position
    #define X 0               // Vector index for X-Coordinates
    #define Y 1               // Vector index for Y-Coordinates
    
    
    // select method for calculation with determinant:
    //#define DETERMINANT_DIVISION
    #define DETERMINANT_MULTIPLICATION
    
    #ifdef DETERMINANT_DIVISION
      #ifdef DETERMINANT_MULTIPLICATION
        #error "Only one method for determinant allowed: MULTIPLICATION or DIVISION!"
      #endif
    #endif
    
    #ifndef DETERMINANT_DIVISION
      #ifndef DETERMINANT_MULTIPLICATION
        #error "One method for determinant has to be chosen: MULTIPLICATION or DIVISION!"
      #endif
    #endif
    
    #endif
    touchpad.h
    Code:
    #ifndef _TOUCHPAD_H_
    #define _TOUCHPAD_H_
    
    #define POSITION_VALID   1
    #define POSITION_INVALID 0
    
    ui8_t TPAD_Pressed(void);
    ui8_t TPAD_GetPosPrecise(ui8_t *xp, ui8_t *yp);
    void TPAD_Calibrate(void);
    #endif

    touchpad.c
    Code:
    #include "touchpad.h"
    #include "touchpad_cfg.h"
    
    // variables for precise algorithm; declared here to save stack memory
      ui16_t r_raw[2];    // raw value vector
      double W = 0;       // Iteration parameter; Start value = 0
      i16_t r1_r0[2];    // solution vector for r1 - r0
      i16_t r3_r0[2];    // solution vector for r3 - r0
      i16_t rraw_r0[2];  // solution vector for rraw - r0
      i32_t D;           // determinant
      double D_inv;      // 1 / determinant;
      //i32_t D_part[2];   // partial solution for determinant
      double factor[2];  // solution vector factors
      i16_t r01_r32[2];  // solution vector for (r0 - r1) - (r3 - r2)
      double solVec[2];  // soluton vector
      double D_XY[2];    // determinant D_X, D_Y
    
    
    static inline void _delay4Cycles(ui16_t __count)
    {
      if (__count == 0)
      {
        __asm__ __volatile__("rjmp 1f\n 1:");
      }
      else
      {
        __asm__ __volatile__ (
          "1: sbiw %0,1" "\n\t"
          "brne 1b"
          : "=w" (__count)
          : "0" (__count)
          );
      }
    }
    
    #define delay(us) _delay4Cycles(((F_CPU / 4000)*us)/1000)
    
    void TPAD_Calibrate(void)
    {
      // The used delay-command is needed to minimize pipeline-effects
      // and therefore to prevent calculation errors.
      
      // Constant values, needed for calculation; constant for an iteration:
      // r1-r0
      r1_r0[X] = r1[X] - r0[X];
      delay(1);
      r1_r0[Y] = r1[Y] - r0[Y];
      delay(1);
    
      // r3-r0
      r3_r0[X] = r3[X] - r0[X];
      delay(1);
      r3_r0[Y] = r3[Y] - r0[Y];
      delay(1);
    
      // Determinant
      D = ((i32_t) r1_r0[X] * (i32_t) r3_r0[Y]) - ((i32_t) r1_r0[Y] * (i32_t) r3_r0[X]);
      delay(1);
      
      #ifdef DETERMINANT_MULTIPLICATION
        D_inv = (double) 1 / (double) D;
        delay(1);
      #endif
    
      // (r0 - r1) - (r3 - r2)
      r01_r32[X] = (r0[X] - r1[X]) - (r3[X] - r2[X]);
      delay(1);
      r01_r32[Y] = (r0[Y] - r1[Y]) - (r3[Y] - r2[Y]);
      delay(1);
    }
    
    
    ui8_t TPAD_GetPosPrecise(ui8_t *xp, ui8_t *yp)
    {
      // Thanks to mare_crisium for providing the mathematical algorithm
    
      ui8_t step;
      ui8_t retval;
    
      TPAD_GetPos(&r_raw[X], &r_raw[Y]); // get raw values via 'old' method (ADC-Values)
    
      // r_raw - r0
      rraw_r0[X] = r_raw[X] - r0[X];
      rraw_r0[Y] = r_raw[Y] - r0[Y];
      
      // Iteration loop
      for (step = 0 ; step < Iterations ; step++)
      {  
        // Solution vector
        solVec[X] = (double) rraw_r0[X] - (W * (double) r01_r32[X]);
        solVec[Y] = (double) rraw_r0[Y] - (W * (double) r01_r32[Y]);
    
        // Determinant
        D_XY[X] = -(((double) r3_r0[X] * solVec[Y]) - ((double) r3_r0[Y] * solVec[X]));
        D_XY[Y] =   ((double) r1_r0[X] * solVec[Y]) - ((double) r1_r0[Y] * solVec[X]);
    
        // factor
        #ifdef DETERMINANT_DIVISION
          factor[X] = (double) D_XY[X] / (double) D;
          factor[Y] = (double) D_XY[Y] / (double) D;
        #endif
        
        #ifdef DETERMINANT_MULTIPLICATION
          factor[X] = (double) D_XY[X] * (double) D_inv;
          factor[Y] = (double) D_XY[Y] * (double) D_inv;
        #endif
    
        // New iteration parameter:
        W = factor[X] * factor[Y];
      }
      
      *xp = (i16_t) (factor[X] * ((double) (LCD_Width - 1)));
      *yp = (i16_t) (factor[Y] * ((double) (LCD_Height - 1)));
    
      // check if values are valid  
      if ((*xp > (LCD_Width - 1)) || (*yp > (LCD_Height - 1)))
      {
        // values invalid: return 0
        retval = POSITION_INVALID;
      }
      else
      {
        // values valid: return 1
        retval = POSITION_VALID;
      }
      return(retval);
    }

    Von der Anwendung her siehts dann z.B. so aus:
    Code:
    ...
    ui8_t x;
    ui8_t y;
    ...
    if (TPAD_Pressed())  // Funktion zum Prüfen, ob die AD-Werte > 0 sind.
    {
      if(TPAD_GetPosPrecise(&x, &y))
      {
        if ((x > 0) && (x < 15) && (y > 10) && (y < 26))
        {
           mach wat;
        }
      }
    }
    ...
    #ifndef MfG
    #define MfG

  3. #23
    Erfahrener Benutzer Roboter Experte
    Registriert seit
    10.10.2004
    Ort
    Reutlingen
    Alter
    35
    Beiträge
    704
    Ein anderer Ansatz wäre das Gram-Schmidtsche Orthogonalisierungsverfahren gewesen.
    (Könnte auch sein dass hier sowas schon erwähnt wurde,bin bissle müde und verpeilt) aber hier gibts mal nen kleinen Link zum Thema:

    http://de.wikipedia.org/wiki/Gram-Sc...rungsverfahren

    lg
    Michi
    mfg
    Michael Eisele

    www.brainrobots.de
    www.facebook.com/brainrobots
    ---
    the most astonishing adventure in the universe begins when the world ends
    ---

Seite 3 von 3 ErsteErste 123

Berechtigungen

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

12V Akku bauen