2013-04-11 5 views
8

Ich möchte den Abstand zwischen der Kamera und dem object.For dies erkannt berechnen ich viele Methoden ausprobiert, habe ich versucht, den Winkel zwischen dem Objekt und der Kamera zu finden, mit Beschleunigungsmesser und dannwie können wir Abstand zwischen Objekt und Android-Handy-Kamera messen

d = h * verwenden a ist

h tan Höhe von von der Basis im allgemeinen der 1,4

ist und ich versuchte, den Winkel zu berechnen, indem Orientierungsverfahren unter Verwendung erhalten. Bitte lassen Sie mich wissen, wo ich falsch mache. Es war mehr als 2 Tage, die ich mit dieser Anforderung kämpfte. Wir haben uns verschiedene Kameraanwendungen angeschaut, die im Android Store verfügbar sind und versucht haben, die Funktionalität derselben zu verstehen, aber nichts war fruchtbar.

mSensorManager = (SensorManager) getSystemService(SENSOR_SERVICE); 
      accSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER); 
      magnetSensor = mSensorManager 
        .getDefaultSensor(Sensor.TYPE_MAGNETIC_FIELD); 
    @Override 
    public void onAccuracyChanged(Sensor sensor, int accuracy) { 
     // TODO Auto-generated method stub 

    } 

    @Override 
    public void onSensorChanged(SensorEvent event) { 
     // TODO Auto-generated method stub 
     if (event.sensor.getType() == Sensor.TYPE_ACCELEROMETER) 
      gravity = event.values; 
     if (event.sensor.getType() == Sensor.TYPE_MAGNETIC_FIELD) 
      geoMagnetic = event.values; 
     if (gravity != null && geoMagnetic != null) { 
      float R[] = new float[9]; 
      float I[] = new float[9]; 
      boolean success = SensorManager.getRotationMatrix(R, I, gravity, 
        geoMagnetic); 
      if (success) { 
       /* Orientation has azimuth, pitch and roll */ 
       float orientation[] = new float[3]; 
       //SensorManager.remapCoordinateSystem(R, 1, 3, orientation); 
       SensorManager.getOrientation(R, orientation); 
       azimut = 57.29578F * orientation[0]; 
       pitch = 57.29578F * orientation[1]; 
       roll = 57.29578F * orientation[2]; 
      } 
     } 
    } 


     captureButton.setOnClickListener(new View.OnClickListener() { 
      @Override 
      public void onClick(View v) { 
       // get an image from the camera 

       double d = (Math.tan(Math.toRadians(Math.abs(pitch))) * sensorHeight); 
       Toast.makeText(
         getApplicationContext(), 
         "Distance = " 
           + String.valueOf(d) 
             + "m Angle = " 
             + String.valueOf(Math.toRadians(Math.abs(pitch))), 
         Toast.LENGTH_LONG).show(); 


      } 
     }); 



protected void onResume() { 
     super.onResume(); 
     mSensorManager.registerListener(this, accSensor, 
       SensorManager.SENSOR_DELAY_NORMAL); 
     mSensorManager.registerListener(this, magnetSensor, 
       SensorManager.SENSOR_DELAY_NORMAL); 
    } 
+1

Wie würde der Winkel auf den Abstand beziehen? Was, wenn ich auf einem Balkon stehe? Wie können Sie die Entfernung messen, wenn Sie die Abmessungen des aufgenommenen Objekts nicht kennen? Und wie viel Objektiv- und optische Sensordichte verwenden Sie? –

+0

Der Zweck der App ist es, den Abstand zwischen einem Objekt und der Kamera zu finden. Vorausgesetzt beide stehen auf dem gleichen Boden. Wir versuchen nicht, die Größe des Objekts zu messen. –

+0

Außerdem möchten Sie bei http://stackoverflow.com/q/4588485 aussehen –

Antwort

5

Ihre getRotationMatrix gibt wahrscheinlich false zurück! Sie sollten die Werte in Ihre eigenen Vektoren kopieren, damit sie nicht durcheinander geraten! Verwenden Sie dazu die clone() -Methode!

if (event.sensor.getType() == Sensor.TYPE_ACCELEROMETER) 
     gravity = event.values.clone(); 
    if (event.sensor.getType() == Sensor.TYPE_MAGNETIC_FIELD) 
     geoMagnetic = event.values.clone(); 

mit Ihrem Code und diese Änderung konnte ich die Azimut/Pitch/Roll-Werte erhalten, ohne dass dies den Erfolg Flagge ändern false zurück:

Log.d("a", "orientation values: " + azimut + "/" + pitch + "/" + roll); 
05-21 16:07:55.743: D/a(29429): orientation values: 77.71578/43.352722/-152.39603 
05-21 16:07:55.883: D/a(29429): orientation values: 175.26134/23.031355/-148.72844 
05-21 16:07:56.793: D/a(29429): orientation values: -146.3089/4.1098075/-14.46417 

Sie den PITCH-Wert, wenn Sie verwenden sollten, Halten Sie das Telefon im Hochformat. Wenn Sie das Telefon im Querformat halten, sollten Sie den ROLL-Wert verwenden.

Wenn Sie das Telefon mit einer 1,4 Höhe halten, dann werden Sie haben:

float dist = Math.abs((float) (1.4f * Math.tan(pitch * Math.PI/180))); 

Bitte beachten Sie, dass Sie RADIANS und nicht GRAD auf der Math.tan Funktion verwendet werden soll.

Getestet habe ich hier und die Werte scheinen gültig zu sein!

+0

versuchte dies aber noch das Problem besteht. –

+0

Was ist das Problem? Sie wollten wissen, was Sie falsch machen, und Sie erhalten die Werte nicht richtig. Ich habe genau die gleichen Code nur mit dem hier erwähnt geändert und ich war in der Lage, die Azimut/Pitch/Roll-Werte zu erhalten ... – thiagolr

+0

ich auch die Werte immer bin, aber ich habe, um den Abstand zwischen dem Objekt zu berechnen und der Kamera der Verwendung von Tonhöhe (Mit d = h * tan (a), wobei d die Entfernung h ist Sensorhöhe und a ist der Nickwinkel).Ich habe über die Google gesucht und diese Methode implementiert, um die Entfernung zu erhalten. Aber die Entfernung, die mit dieser Tonhöhe berechnet wurde, ergibt den falschen Wert. –

1

Der letzte Code ist

mSensorManager = (SensorManager) getSystemService(SENSOR_SERVICE); 
      accSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER); 
      magnetSensor = mSensorManager 
        .getDefaultSensor(Sensor.TYPE_MAGNETIC_FIELD); 
    @Override 
    public void onAccuracyChanged(Sensor sensor, int accuracy) { 
     // TODO Auto-generated method stub 

    } 

    @Override 
    public void onSensorChanged(SensorEvent event) { 
     // TODO Auto-generated method stub 
     if (event.sensor.getType() == Sensor.TYPE_ACCELEROMETER) 
      gravity = event.values; 
     if (event.sensor.getType() == Sensor.TYPE_MAGNETIC_FIELD) 
      geoMagnetic = event.values; 
     if (gravity != null && geoMagnetic != null) { 
      float R[] = new float[9]; 
      float I[] = new float[9]; 
      boolean success = SensorManager.getRotationMatrix(R, I, gravity, 
        geoMagnetic); 
      if (success) { 
       /* Orientation has azimuth, pitch and roll */ 
       float orientation[] = new float[3]; 
       //SensorManager.remapCoordinateSystem(R, 1, 3, orientation); 
       SensorManager.getOrientation(R, orientation); 
       azimut = 57.29578F * orientation[0]; 
       pitch = 57.29578F * orientation[1]; 
       roll = 57.29578F * orientation[2]; 
      } 
     } 
    } 


     captureButton.setOnClickListener(new View.OnClickListener() { 
      @Override 
      public void onClick(View v) { 
       // get an image from the camera 

       float d = Math.abs((float) (1.4f * Math.tan(pitch * Math.PI/180))); 
       Toast.makeText(
         getApplicationContext(), 
         "Distance = " 
           + String.valueOf(d) 
             + "m Angle = " 
             + String.valueOf(Math.toRadians(Math.abs(pitch))), 
         Toast.LENGTH_LONG).show(); 


      } 
     }); 



protected void onResume() { 
     super.onResume(); 
     mSensorManager.registerListener(this, accSensor, 
       SensorManager.SENSOR_DELAY_NORMAL); 
     mSensorManager.registerListener(this, magnetSensor, 
       SensorManager.SENSOR_DELAY_NORMAL); 
    }