How do I increase/decrease a drawable animation with SensorManager? - android

I created an EMF reader app in Android Studio and is having trouble with how to increase a drawable animation when the SensorManager and TextView increases as well as decreases with the SensorManager and TextView in the app.
Here's what I have so far:
public class MainActivity extends AppCompatActivity implements SensorEventListener {
TextView pkeEMF;
private static SensorManager sensorManager;
private Sensor emfSensor;
SoundPool spPKE;
int mpPKE;
ImageView animationView;
AnimationDrawable pkeAnimation;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
pkeEMF = (TextView) findViewById(R.id.pkeEMF);
sensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE);
emfSensor = sensorManager.getDefaultSensor(Sensor.TYPE_MAGNETIC_FIELD);
animationView = (ImageView) findViewById(R.id.pkeDot);
animationView.setBackgroundResource(R.drawable.pkeamimation);
pkeAnimation = (AnimationDrawable) animationView.getBackground();
pkeAnimation.start();
spPKE = new SoundPool(10, AudioManager.STREAM_MUSIC, 0);
spPKE.setOnLoadCompleteListener(new SoundPool.OnLoadCompleteListener() {
#Override
public void onLoadComplete(SoundPool soundPool, int sampleId, int status) {
mpPKE = spPKE.play(sampleId, 1, 1, 0, -1, 1);
}
});
this.setRequestedOrientation(ActivityInfo.SCREEN_ORIENTATION_PORTRAIT);
this.getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,WindowManager.LayoutParams.FLAG_FULLSCREEN);
getSupportActionBar().hide();
}
public void showAnimation(View view) {
Intent intent = new Intent(this, AnimationSound.class);
startActivity(intent);
}
#Override
protected void onResume() {
super.onResume();
if (emfSensor != null) {
sensorManager.registerListener(this, emfSensor, SensorManager.SENSOR_DELAY_NORMAL);
} else {
Toast.makeText(this, "Not Supported", Toast.LENGTH_SHORT).show();
finish();
}
mpPKE = spPKE.load(getApplicationContext(), R.raw.pke_running_loop, 1);
}
#Override
protected void onPause() {
super.onPause();
sensorManager.unregisterListener(this);
spPKE.stop(mpPKE);
}
#Override
public void onSensorChanged(SensorEvent event) {
float azimuth = Math.round(event.values[0]);
float pitch = Math.round(event.values[1]);
float roll = Math.round(event.values[2]);
double tesla = Math.sqrt((azimuth * azimuth) + (pitch * pitch) + (roll * roll));
String text = String.format("%.2f", tesla);
pkeEMF.setText(text + "μT");
}
#Override
public void onAccuracyChanged(Sensor sensor, int accuracy) {
}
}
How do I do this? I have been looking everywhere to find the answer on how to do this and came up with nothing.

Related

How to print Android value of GyroSensor on logcat

Hi I want to use GyroSensor in Android. I want to get value of GyroSensor on logcat. But, I can't print value on logcat. error name is "Sensor or listener is null". My code is under there. please help me. Plus, I used Api 25 amulator. If my code is wrong, you can give other code.
public class MainActivity extends AppCompatActivity {
private SensorManager mSensorManager = null;
private SensorEventListener mGyroLis;
private Sensor mGyroSensor = null;
private double timestamp;
private double pitch;
private double roll;
private double yaw;
private double dt;
private double RAD2DGR = 180 / Math.PI;
private static final float NS2S = 1.0f/10000000000.0f;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
mSensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE);
mGyroSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_GYROSCOPE);
mGyroLis = new GyroscopeListener();
findViewById(R.id.a_start).setOnTouchListener(new View.OnTouchListener(){
#Override
public boolean onTouch(View v, MotionEvent event){
switch (event.getAction()){
case MotionEvent.ACTION_DOWN:
mSensorManager.registerListener(mGyroLis, mGyroSensor, SensorManager.SENSOR_DELAY_UI);
break;
case MotionEvent.ACTION_UP:
mSensorManager.unregisterListener(mGyroLis);
break;
}
return false;
}
});
}
#Override
public void onPause(){
super.onPause();
Log.e("LOG","onpause()");
mSensorManager.unregisterListener(mGyroLis);
}
#Override
public void onDestroy(){
super.onDestroy();
Log.e("LOG","ondestroy()");
mSensorManager.unregisterListener(mGyroLis);
}
private class GyroscopeListener implements SensorEventListener {
#Override
public void onSensorChanged(SensorEvent event){
double gyroZ = event.values[2];
dt = (event.timestamp - timestamp) * NS2S;
timestamp = event.timestamp;
if(dt - timestamp*NS2S != 0){
yaw = yaw + gyroZ*dt;
Log.d("LOG", "GYROSCOPE [z]:" + String.format("%.4f", event.values[2])+"[yaw]:"+String.format("%.4f", yaw+RAD2DGR));
}
}
#Override
public void onAccuracyChanged(Sensor sensor, int accuracy){
}
}
}

How to use sensor datas in another activity (Now it works well thanks to your help!)

(Now it works perfectly)I am new to android development and I have written an showActivity to show my result data from another class. In that class I implement a sensorEventListener and get sensor data. But when I want to display data in my showActivity, I get nothing to show. All the data is 0(or false) and I dont know what's wrong with my code. It's much appreciated if you can give me some advise on how to fix it. Thanks a lot.
This is my showActivity:
public class MapShowActivity extends AppCompatActivity {
public SensorUse mySensorUse ;
private TextView myText;
private Button myButton;
private Timer timer = new Timer();
private int count = 0;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
mySensorUse = new SensorUse(MapShowActivity.this);
setContentView(R.layout.activity_map_show);
myText = (TextView)findViewById(R.id.orientation);
}
public void startTimer(){
timer.scheduleAtFixedRate(detectNewOrientation, 100, 100);
}
TimerTask detectNewOrientation = new TimerTask(){
#Override
public void run() {
runOnUiThread(new Runnable() {
#Override
public void run() {
myText.setText(String.valueOf(mySensorUse.getOx()));
}
});
}
};
#Override
protected void onResume() {
super.onResume();
mySensorUse.sensorRegister(MapShowActivity.this);
startTimer();
}
#Override
protected void onPause() {
super.onPause();
mySensorUse.sensorUnregister();
}
}
And this is my Sensor class:
public class SensorUse implements SensorEventListener{
private float[] accValues = new float[3];
private float[] magValues = new float[3];
private float[] orientationValues = new float[4];
private float[] resultRotationMatrix = new float[16];
public float ax;
public float ay;
public float az;
public float sumAcc;
public float ox;
public static boolean flag = false;
public boolean rotationMatrixGenerated;
private SensorManager mySensorManager;
private Sensor accSencor, magSensor;
public SensorUse(Context context){
}
#Override
public void onSensorChanged(SensorEvent event) {
if (event.sensor.getType() == Sensor.TYPE_LINEAR_ACCELERATION){
accValues = event.values.clone();
ax = accValues[0];
ay = accValues[1];
az = accValues[2];
sumAcc = (float) Math.sqrt(ax*ax + ay*ay + az*az);
flag = true;
}
else if (event.sensor.getType() == Sensor.TYPE_MAGNETIC_FIELD){
magValues = event.values.clone();
}
if (accValues != null && magValues != null){
rotationMatrixGenerated = SensorManager.getRotationMatrix(resultRotationMatrix,
null, accValues, magValues);
if(rotationMatrixGenerated) {
SensorManager.getOrientation(resultRotationMatrix, orientationValues);
ox = (float) Math.toDegrees(orientationValues[0]);
}
}
}
#Override
public void onAccuracyChanged(Sensor sensor, int accuracy) {
}
public void sensorRegister(Context context){
mySensorManager = (SensorManager) context.getSystemService(Context.SENSOR_SERVICE);
accSencor = mySensorManager.getDefaultSensor(Sensor.TYPE_LINEAR_ACCELERATION);
magSensor = mySensorManager.getDefaultSensor(Sensor.TYPE_MAGNETIC_FIELD);
mySensorManager.registerListener(this, accSencor, SensorManager.SENSOR_DELAY_GAME);
mySensorManager.registerListener(this, magSensor, SensorManager.SENSOR_DELAY_GAME);
}
public void sensorUnregister(){
mySensorManager.unregisterListener(this, accSencor);
mySensorManager.unregisterListener(this, magSensor);
}
public float getAx(){
return ax;
}
public float getOx(){
return ox;
}
}
App doesn't know which class will be handling the sensor data.
You have to register your sensor class (SensorUse) object
to get accelerometer data.
Find example code below:
sensorManager = (SensorManager) getSystemService(Context.SENSOR_SERVICE);
senAccelerometer = sensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER);
sensorManager.registerListener(mySensorUse, senAccelerometer , SensorManager.SENSOR_DELAY_NORMAL);
sensorManger is object of SensorManager
mySensorUse is class that has implemented SensorEventListener

android - tilt to scroll the text?

I am working on an app in which i need to make text scroll based on device tilt information. I have tried few solutions but nothing seems to be working. I am able to get the tilting information using the following code :-
public class SensorActivity extends Activity implements SensorEventListener {
float[] mMagnetValues = new float[3];
float[] mAccelValues = new float[3];
float[] mOrientationValues = new float[3];
float[] mRotationMatrix = new float[9];
#Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
SensorManager sensorManager = (SensorManager) this.getSystemService(SENSOR_SERVICE);
sensorManager.registerListener(this, sensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER),
SensorManager.SENSOR_DELAY_NORMAL);
sensorManager.registerListener(this, sensorManager.getDefaultSensor(Sensor.TYPE_MAGNETIC_FIELD),
SensorManager.SENSOR_DELAY_NORMAL);
TextView txt1 = (TextView) findViewById(R.id.textView1);
}
#Override
public void onSensorChanged(SensorEvent event) {
switch (event.sensor.getType()) {
case Sensor.TYPE_ACCELEROMETER:
System.arraycopy(event.values, 0, mAccelValues, 0, 3);
break;
case Sensor.TYPE_MAGNETIC_FIELD:
System.arraycopy(event.values, 0, mMagnetValues, 0, 3);
break;
}
SensorManager.getRotationMatrix(mRotationMatrix, null, mAccelValues, mMagnetValues);
SensorManager.getOrientation(mRotationMatrix, mOrientationValues);
Log.e("Values", mOrientationValues[0] + " " + mOrientationValues[1] + " " + mOrientationValues);
};
#Override
public void onAccuracyChanged(Sensor sensor, int accuracy) { }
public void scrollTextUp() {
ScrollView scrollView = (ScrollView)findViewById(R.id.scroll);
scrollView.scrollBy(0, 5);
}
public void scrollTextBottom() {
ScrollView scrollView = (ScrollView)findViewById(R.id.scroll);
scrollView.scrollBy(0, -5);
}
}
I assume that mOrientationValues[1] needs to be used to scroll but how to use this value is a big question for me right now. Please help.
Any help would be really appreciated. If you have found any good tutorial or example please share it.
Thanks.
So after playing around for few hours, this is the solution i used. Requirements for my apps was to make text scroll in a readable speed, that is why i used a constant scroll speed but i welcome everyone to improve this answer based on tilt speed etc so it could help others as well.
TiltScrollController Class -
public class TiltScrollController implements SensorEventListener {
private SensorManager mSensorManager;
private Sensor mAccelSensor;
private Sensor mMagnetSensor;
private float mCurrentPosition;
private boolean isCurrentPositionSet = false;
private int count = 0;
private ScrollListener mListener;
float[] mMagnetValues = new float[3];
float[] mAccelValues = new float[3];
float[] mOrientationValues = new float[3];
float[] mRotationMatrix = new float[9];
public TiltScrollController(SensorManager sensorManager, ScrollListener listener) {
mSensorManager = sensorManager;
mListener = listener;
mAccelSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER);
mMagnetSensor = mSensorManager.getDefaultSensor(Sensor.TYPE_MAGNETIC_FIELD);
}
#Override
public void onSensorChanged(SensorEvent event) {
switch (event.sensor.getType()) {
case Sensor.TYPE_ACCELEROMETER:
System.arraycopy(event.values, 0, mAccelValues, 0, 3);
break;
case Sensor.TYPE_MAGNETIC_FIELD:
System.arraycopy(event.values, 0, mMagnetValues, 0, 3);
break;
}
SensorManager.getRotationMatrix(mRotationMatrix, null, mAccelValues, mMagnetValues);
SensorManager.getOrientation(mRotationMatrix, mOrientationValues);
if (!isCurrentPositionSet) {
mCurrentPosition = mOrientationValues[1];
count += 1;
if(count == 2) {
isCurrentPositionSet = true;
}
}
if(mCurrentPosition + 0.25 < mOrientationValues[1]) {
//Scroll to Top
mListener.onTiltUp();
}
else if (mCurrentPosition - 0.25 > mOrientationValues[1]) {
//Scroll to Bottom
mListener.onTiltDown();
}
};
#Override
public void onAccuracyChanged(Sensor sensor, int accuracy) {}
public void requestAllSensors() {
mSensorManager.registerListener(this, mAccelSensor, SensorManager.SENSOR_DELAY_NORMAL);
mSensorManager.registerListener(this, mMagnetSensor, SensorManager.SENSOR_DELAY_NORMAL);
}
public void killAllSensors() {
mSensorManager.unregisterListener(this, mAccelSensor);
mSensorManager.unregisterListener(this, mMagnetSensor);
}
public interface ScrollListener {
public void onTiltUp();
public void onTiltDown();
}
}
Your activity class -
public class SensorActivity extends Activity {
private ScrollView mScrollView;
private TiltScrollController mTiltScrollController;
private SensorManager mSensorManager;
#Override
public void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
mScrollView = (ScrollView)findViewById(R.id.scroll);
mSensorManager = (SensorManager) this.getSystemService(SENSOR_SERVICE);
mTiltScrollController = new TiltScrollController(mSensorManager, new TiltScrollListener());
}
public void scrollTextUp() {
mScrollView.smoothScrollBy(0, 6);
}
public void scrollTextBottom() {
mScrollView.smoothScrollBy(0, -6);
}
#Override
protected void onPause() {
mTiltScrollController.killAllSensors();
super.onPause();
}
public class TiltScrollListener implements TiltScrollController.ScrollListener {
#Override
public void onTiltUp() {
scrollTextUp();
}
#Override
public void onTiltDown() {
scrollTextBottom();
}
}
}
Cheers!!

SensorManager.getRotationMatrix always return false on Android Emulator

I try to get orientation on my Android Emulator by SensorManager.getOrientation. Before this i use SensorManager.getRotationMatrix to get rotation matrix, but this always return false.
Here is code of my Activity:
public class MainActivity extends Activity implements SurfaceHolder.Callback, View.OnClickListener{
public final static String DEBUG_TAG = "MainActivity";
private SensorManager sensorManager;
private SurfaceView preview;
private float[] mGravs;
private float[] mGeoMags;
private float[] mRotationM;
private float[] mOrientation;
private Sensor mAccelerometer;
private Sensor mMagneticField;
#Override
protected void onCreate(Bundle savedInstanceState)
{
super.onCreate(savedInstanceState);
getWindow().addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN);
requestWindowFeature(Window.FEATURE_NO_TITLE);
setContentView(R.layout.activity_main);
preview = (SurfaceView)findViewById(R.id.SurfaceView1);
sensorManager = (SensorManager)getSystemService(SENSOR_SERVICE);
mAccelerometer = sensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER);
mMagneticField = sensorManager.getDefaultSensor(Sensor.TYPE_MAGNETIC_FIELD);
mGravs = new float[3];
mGeoMags = new float[3];
mRotationM = new float[16];
mOrientation = new float[3];
List<Sensor> sensorList = sensorManager.getSensorList(Sensor.TYPE_ALL);
for (int nI = 0; nI < sensorList.size(); nI++) {
Log.d(DEBUG_TAG, sensorList.get(nI).getName());
}
}
private SensorEventListener sensorEventListener = new SensorEventListener() {
#Override
public void onSensorChanged(SensorEvent event)
{
synchronized (this) {
switch (event.sensor.getType()) {
case Sensor.TYPE_ACCELEROMETER:
System.arraycopy(event.values, 0, mGravs, 0, 3);
break;
case Sensor.TYPE_MAGNETIC_FIELD:
System.arraycopy(event.values, 0, mGeoMags, 0, 3);
break;
default:
return;
}
if (mGravs != null && mGeoMags != null) {
boolean bSuccess = SensorManager.getRotationMatrix(mRotationM, null, mGravs, mGeoMags);
if (bSuccess) {
SensorManager.getOrientation(mRotationM, mOrientation);
}
}
}
}
#Override
public void onAccuracyChanged(Sensor sensor, int accuracy) {
// TODO Auto-generated method stub
}
};
private boolean openHardware()
{
sensorManager.registerListener(sensorEventListener, mAccelerometer, SensorManager.SENSOR_DELAY_NORMAL);
sensorManager.registerListener(sensorEventListener, mMagneticField, SensorManager.SENSOR_DELAY_NORMAL);
return true;
}
private void closeHardware()
{
sensorManager.unregisterListener(sensorEventListener);
}
#Override
protected void onResume()
{
super.onResume();
openHardware();
}
#Override
protected void onPause()
{
super.onPause();
closeHardware();
}
#Override
protected void onStop()
{
closeHardware();
super.onStop();
}
}
Ok, this problem occur because magnetic field sensor always return [0.0, 0.0, 0.0].
How can i make magnetic field sensor return something else?
I had the same problem. Everything got false
This answer has helped me: https://stackoverflow.com/a/14224122/1549127

accelerometer sensor and mediaplayer

with your help and some guides on the internet, i'm managed to knock out this code. But I find myself with several problems, the application, according to my idea, it should start the media player at the time the phone is shaken, and start it once, but now the media player is started every time the phone is shaken . Furthermore, I would like that, the application worked and the screen off when the phone is shaken starts the media player and the screen is turned on
public class SensorTestActivity extends Activity implements SensorEventListener {
private SensorManager sensorManager;
private boolean color = false;
private View view;
private long lastUpdate;
MediaPlayer mMediaPlayer;
#Override
public void onCreate(Bundle savedInstanceState) {
requestWindowFeature(Window.FEATURE_NO_TITLE);
getWindow().setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN,
WindowManager.LayoutParams.FLAG_FULLSCREEN);
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
view = findViewById(R.id.textView);
view.setBackgroundColor(Color.BLUE);
sensorManager = (SensorManager) getSystemService(SENSOR_SERVICE);
sensorManager.registerListener(this,
sensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER),
SensorManager.SENSOR_DELAY_NORMAL);
lastUpdate = System.currentTimeMillis();
}
#Override
public void onSensorChanged(SensorEvent event) {
if (event.sensor.getType() == Sensor.TYPE_ACCELEROMETER) {
getAccelerometer(event);
}
}
private void getAccelerometer(SensorEvent event) {
float[] values = event.values;
// Movement
float x = values[0];
float y = values[1];
float z = values[2];
float accelationSquareRoot = (x * x + y * y + z * z)/(SensorManager.GRAVITY_EARTH * SensorManager.GRAVITY_EARTH);
long actualTime = System.currentTimeMillis();
if (accelationSquareRoot >= 2) //
{
if (actualTime - lastUpdate < 200) {
return;
}
lastUpdate = actualTime;
Toast.makeText(this, "Device was shuffed", Toast.LENGTH_SHORT).show();
if (color) {
view.setBackgroundColor(Color.GREEN);
try {
mMediaPlayer = MediaPlayer.create(getBaseContext(), R.raw.mymusic);
mMediaPlayer.setLooping(false);
mMediaPlayer.start();
mMediaPlayer.setOnCompletionListener(new
OnCompletionListener() {
public void onCompletion(MediaPlayer arg0) {
// if (mMediaPlayer != null) {
// mMediaPlayer.release();
// mMediaPlayer = null;
// }
}
});
} catch (Exception e) {
if (mMediaPlayer != null) {
mMediaPlayer.release();
mMediaPlayer = null;
}
}
}
} else {
view.setBackgroundColor(Color.RED);
}
color = !color;
}
#Override
public void onAccuracyChanged(Sensor sensor, int accuracy) {
}
#Override
protected void onResume() {
super.onResume();
// register this class as a listener for the orientation and
// accelerometer sensors
sensorManager.registerListener(this,
sensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER),
SensorManager.SENSOR_DELAY_NORMAL);
}
#Override
protected void onPause() {
// unregister listener
super.onPause();
sensorManager.unregisterListener(this);
}
}
To start something just once, add a boolean.
boolean startOnce = true;
if (startOnce) {
....
startOnce = false;
}

Categories

Resources