تشخیص لرزش گوشی در اندروید
سلام دوستان امروز میخواهیم به تشخیص لرزش گوشی در اندروید یا shake در اندروید بپردازیم.منظور از shake و لرزش در اندروید هنگامی است که گوشی خود را تکان می دهید شاید بار ها در برنامه های مختلف دیده باشید که با تکان دادن گوشی عملیاتی انجام داده میشود.برای اینکار روش های مختلفی را داریم و ما در اینجا به روشی میپردازیم که نسبتا جدید و دقیق تر است.دوستان بررسی تمام بخش های این دستورات از حوصله این اموزش خارج است و میتوانید قسمت های مختلف ان را در سایت در صورت وجود پیدا کنید.
قبل از شروع ابتدا اجازه دسترسی به برناممان می دهیم :
1 | <uses-permission android:name="android.permission.READ_PHONE_STATE"></uses-permission> |
ما برای اینکار از AccelerometerListener استفاده میکنیم که باید ان را در قالب interface ایجاد کنیم و اکتیویتی اصلیمان را از این رابط implements میکنیم که در بخش کد های MainActivity خواهید دید.
خب قبل از رفتن به اکتیویتی اصلی لازمه که ابتدا این interface را ایجاد کنید برای اینکار هنگام ایجاد یک فایل جاوا interface را انتخاب کنید سپس کد های زیر را در ان بنویسید در اینجا ما نام فایل را AccelerometerListener قرار داده ایم :
1 2 3 4 | public interface AccelerometerListener { public void onAccelerationChanged(float x, float y, float z); public void onShake(float force); } |
حالا یک کلاس ایجاد کنید و کد های زیر را در ان قرار دهید نام این کلاس در اینجا AccelerometerManager می باشد:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 | import android.content.Context; import android.hardware.Sensor; import android.hardware.SensorEvent; import android.hardware.SensorEventListener; import android.hardware.SensorManager; import android.widget.Toast; import java.util.List; /** * Created by Sepehr on 18/07/2017. */ public class AccelerometerManager { private static Context aContext=null; /** Accuracy configuration */ private static float threshold = 15.0f; private static int interval = 200; private static Sensor sensor; private static SensorManager sensorManager; // you could use an OrientationListener array instead // if you plans to use more than one listener private static AccelerometerListener listener; /** indicates whether or not Accelerometer Sensor is supported */ private static Boolean supported; /** indicates whether or not Accelerometer Sensor is running */ private static boolean running = false; /** * Returns true if the manager is listening to orientation changes */ public static boolean isListening() { return running; } /** * Unregisters listeners */ public static void stopListening() { running = false; try { if (sensorManager != null && sensorEventListener != null) { sensorManager.unregisterListener(sensorEventListener); } } catch (Exception e) {} } /** * Returns true if at least one Accelerometer sensor is available */ public static boolean isSupported(Context context) { aContext = context; if (supported == null) { if (aContext != null) { sensorManager = (SensorManager) aContext. getSystemService(Context.SENSOR_SERVICE); // Get all sensors in device List<Sensor> sensors = sensorManager.getSensorList( Sensor.TYPE_ACCELEROMETER); supported = new Boolean(sensors.size() > 0); } else { supported = Boolean.FALSE; } } return supported; } /** * Configure the listener for shaking * @param threshold * minimum acceleration variation for considering shaking * @param interval * minimum interval between to shake events */ public static void configure(int threshold, int interval) { AccelerometerManager.threshold = threshold; AccelerometerManager.interval = interval; } /** * Registers a listener and start listening * @param accelerometerListener * callback for accelerometer events */ public static void startListening( AccelerometerListener accelerometerListener ) { sensorManager = (SensorManager) aContext. getSystemService(Context.SENSOR_SERVICE); // Take all sensors in device List<Sensor> sensors = sensorManager.getSensorList( Sensor.TYPE_ACCELEROMETER); if (sensors.size() > 0) { sensor = sensors.get(0); // Register Accelerometer Listener running = sensorManager.registerListener( sensorEventListener, sensor, SensorManager.SENSOR_DELAY_GAME); listener = accelerometerListener; } } /** * Configures threshold and interval * And registers a listener and start listening * @param accelerometerListener * callback for accelerometer events * @param threshold * minimum acceleration variation for considering shaking * @param interval * minimum interval between to shake events */ public static void startListening( AccelerometerListener accelerometerListener, int threshold, int interval) { configure(threshold, interval); startListening(accelerometerListener); } /** * The listener that listen to events from the accelerometer listener */ private static SensorEventListener sensorEventListener = new SensorEventListener() { private long now = 0; private long timeDiff = 0; private long lastUpdate = 0; private long lastShake = 0; private float x = 0; private float y = 0; private float z = 0; private float lastX = 0; private float lastY = 0; private float lastZ = 0; private float force = 0; public void onAccuracyChanged(Sensor sensor, int accuracy) {} public void onSensorChanged(SensorEvent event) { // use the event timestamp as reference // so the manager precision won't depends // on the AccelerometerListener implementation // processing time now = event.timestamp; x = event.values[0]; y = event.values[1]; z = event.values[2]; // if not interesting in shake events // just remove the whole if then else block if (lastUpdate == 0) { lastUpdate = now; lastShake = now; lastX = x; lastY = y; lastZ = z; Toast.makeText(aContext,"No Motion detected", Toast.LENGTH_SHORT).show(); } else { timeDiff = now - lastUpdate; if (timeDiff > 0) { /*force = Math.abs(x + y + z - lastX - lastY - lastZ) / timeDiff;*/ force = Math.abs(x + y + z - lastX - lastY - lastZ); if (Float.compare(force, threshold) >0 ) { //Toast.makeText(Accelerometer.getContext(), //(now-lastShake)+" >= "+interval, 1000).show(); if (now - lastShake >= interval) { // trigger shake event listener.onShake(force); } else { Toast.makeText(aContext,"No Motion detected", Toast.LENGTH_SHORT).show(); } lastShake = now; } lastX = x; lastY = y; lastZ = z; lastUpdate = now; } else { Toast.makeText(aContext,"No Motion detected", Toast.LENGTH_SHORT).show(); } } // trigger change event listener.onAccelerationChanged(x, y, z); } }; } |
خب امیدوارم با دیدن این کد ها نامید نشده باشید.در اینجا بخش اصلی کار ما در متد SensorEventListener انجام می شود که با تعریف تعدادی متغییر همراه است که وضعیت لرزش یا عدم لرزش به کمک ان ها انجام می شود.حالا میرسیم به اکتیویتی اصلیمان همانطور که قبلا گفتیم باید از رابط AccelerometerListener استفاده کنیم برای اینکار بصورت زیر عمل میکنیم و بقیه کد هارا هم مینویسیم:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 | public class MainActivity extends AppCompatActivity implements AccelerometerListener { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); } public void onAccelerationChanged(float x, float y, float z) { // TODO Auto-generated method stub } public void onShake(float force) { // Do your stuff here // Called when Motion Detected Toast.makeText(getBaseContext(), "Motion detected", Toast.LENGTH_SHORT).show(); } @Override public void onResume() { super.onResume(); Toast.makeText(getBaseContext(), "onResume Accelerometer Started", Toast.LENGTH_SHORT).show(); //Check device supported Accelerometer senssor or not if (AccelerometerManager.isSupported(this)) { //Start Accelerometer Listening AccelerometerManager.startListening(this); } } @Override public void onStop() { super.onStop(); //Check device supported Accelerometer senssor or not if (AccelerometerManager.isListening()) { //Start Accelerometer Listening AccelerometerManager.stopListening(); Toast.makeText(getBaseContext(), "onStop Accelerometer Stoped", Toast.LENGTH_SHORT).show(); } } @Override public void onDestroy() { super.onDestroy(); Log.i("Sensor", "Service distroy"); //Check device supported Accelerometer senssor or not if (AccelerometerManager.isListening()) { //Start Accelerometer Listening AccelerometerManager.stopListening(); Toast.makeText(getBaseContext(), "onDestroy Accelerometer Stoped", Toast.LENGTH_SHORT).show(); } } } |
خب همانطور که قبلا رابطی با نام AccelerometerListener ایجاد کردیم اکتیویتی اصلیمان را از ان implements کردیم.سپس از متد هایonResume و onShake و onStop و onDestroy استفاده کردیم که با سه تای ان ها اشنایی پیدا کردیم در بحث اکتیویتی ها و متد onShake مبحث جدید میباشد که همانطور که از toast ان متوجه هستید هنگام تکان دادن گوشی عملیات داخل ان انجام می شود.
امیدوارم از اموزش لذت برده باشید و مفید بوده باشه.
موفق باشید..
خیلی خوبه.مهندس لطفا نسخه api که استفاده میکنید رو تو اموزشاتون قید کنین