← العودة للموقع

عمل تطبيق بوصلة بواسطة Android studio

تاريخ النشر: ٥‏/١٠‏/٢٠٢٦

تطبيق البوصلة هو أحد التطبيقات المهمة التي نحتاج إليها في الكثير من البرامج، سواءً كان هذا التطبيق منفصلاً أو كان جزءاً من تطبيق أوسع مثل بعض التطبيقات الإسلامية التي تساعد على معرفة اتجاه القبلة أو أوقات الصلوات وما شابه ذلك.


دعنا نخض في الموضوع مباشرة.

افتح مشروعاً جديداً في اندرويد استوديو من قائمة ملف ثم قم بتسمية المشروع كما تريد، ثم ابدأ بالإجراءات التالية :


أولاً لعمل تطبيق بوصلة نحن نحتاج إلى اثنين من الاستشعارات :

Accelerometer sensor, Magento motor sensor


إذا كان جهازك يحتوي على هذين الاستشعارين فسيعمل تطبيق البوصلة عندك بكل سهولة، ودون مشاكل.

سوف نستعمل منطقة استشعارالتسارع Accelerometer sensor مع مستشعر المحرك المغناطيسي Magento motor

sensor وسنحصل على مصفوفة الدوران Rotation matrix، ومن ثم سنحصل على الإتجاه Orientation.

لكي لا نطيل الشرح وتتعقد عليكم بعض الأمور دعنا نخض في الشفرة مباشرة .


أولاً : ينبغي عليك أن تتحصل على صور مثل الصور المرفقة التالية ثم تقوم بتجهيزها كما ينبغي وتقوم بتسميتها بالشكل الصحيح ووضعها داخل مجلد drawable.


صورة توضيحية


ضع هاتين الصورتين داخل مجلد drawable وقم بتسميتهم على التوالي بالأسماء التالية :

compass33.png,

compass4.png


طبعاً بإمكانك تغيير كل هذه الأسماء وأيضاً الصور يمكنك أن تختار ما تشاء ولكن يفضل عمل ذلك بعد تجربة هذه الشفرة كما هي حتى لا تواجهك اخطاء بسيطة تأخذ من وقتك الكثير.


ثانياً : نحتاج لعمل ملف xml Activity وليكن باسم activity_main_compass2.xml ثم نكتب فيه الشفرة التالية :

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"

xmlns:app="http://schemas.android.com/apk/res-auto"

xmlns:tools="http://schemas.android.com/tools"

android:layout_width="match_parent"

android:layout_height="match_parent">


<ImageView

android:id="@+id/backgnd"

android:layout_width="match_parent"

android:layout_height="match_parent"

android:layout_centerHorizontal="true"

app:srcCompat="@android:color/black" />


<ImageView

android:id="@+id/imgBasicCompass"

android:layout_width="wrap_content"

android:layout_height="wrap_content"

android:layout_centerHorizontal="true"

android:src="@drawable/compass33" />


<ImageView

android:id="@+id/imageViewCompass"

android:layout_width="wrap_content"

android:layout_height="wrap_content"

android:layout_centerHorizontal="true"

android:src="@drawable/compass4" />

</RelativeLayout>


ثالثاً : نتوجه إلى الشفرة الرئيسية وهي Activity Main java ونكتب الكود التالي:

تحت اسم التطبيق داخل ال acitivity انسخ والصق الكود التالي :


import android.hardware.Sensor;

import android.hardware.SensorEvent;

import android.hardware.SensorEventListener;

import android.hardware.SensorManager;

import android.os.Bundle;

import android.view.WindowManager;

import android.view.animation.Animation;

import android.view.animation.RotateAnimation;

import android.widget.ImageView;

import androidx.appcompat.app.AppCompatActivity;


public class MainActivityCompass extends AppCompatActivity implements SensorEventListener{

private ImageView imageView;

private float[] mGravity = new float[3];

private float[] mGeoMagnetic = new float[3];

private float azimuth=0f;

private float currentAzimuth =0f;

private SensorManager mSensorManager;

@Override

protected void onCreate (Bundle savedInstanceState) {

super.onCreate(savedInstanceState);

setContentView(R.layout.activity_main_compass2);

getWindow().addFlags(WindowManager.LayoutParams.FLAG_KEEP_SCREEN_ON);

imageView = findViewById(R.id.imageViewCompass);

mSensorManager = (SensorManager) getSystemService(SENSOR_SERVICE);

}

@Override

protected void onResume(){

super.onResume();

mSensorManager.registerListener(this, mSensorManager.getDefaultSensor(Sensor.TYPE_MAGNETIC_FIELD), SensorManager.SENSOR_DELAY_GAME);

mSensorManager.registerListener(this, mSensorManager.getDefaultSensor(Sensor.TYPE_ACCELEROMETER), SensorManager.SENSOR_DELAY_GAME);

}

@Override

protected void onPause() {

super.onPause();

mSensorManager.unregisterListener(this);

}

@Override

public void onSensorChanged(SensorEvent sensorEvent) {

final float alpha= 0.97f;

synchronized (this) {

if(sensorEvent.sensor.getType()== Sensor.TYPE_ACCELEROMETER) {

mGravity[0]=alpha*mGravity[0]+(1-alpha)*sensorEvent.values[0];

mGravity[1]=alpha*mGravity[1]+(1-alpha)*sensorEvent.values[1];

mGravity[2]=alpha*mGravity[2]+(1-alpha)*sensorEvent.values[2];

}


if(sensorEvent.sensor.getType()== Sensor.TYPE_MAGNETIC_FIELD) {

mGeoMagnetic[0]=alpha*mGeoMagnetic[0]+(1-alpha)*sensorEvent.values[0];

mGeoMagnetic[1]=alpha*mGeoMagnetic[1]+(1-alpha)*sensorEvent.values[1];

mGeoMagnetic[2]=alpha*mGeoMagnetic[2]+(1-alpha)*sensorEvent.values[2];

}


float R[] = new float[9];

float I[] = new float[9];

boolean succsess = SensorManager.getRotationMatrix(R,I,mGravity,mGeoMagnetic);

if(succsess){

float orientation[] = new float[3];

SensorManager.getOrientation(R,orientation);

azimuth = (float)Math.toDegrees(orientation[0]);

azimuth = (azimuth + 360)%360;

Animation anim = new RotateAnimation(-currentAzimuth, -azimuth,

Animation.RELATIVE_TO_SELF,0.5f, Animation.RELATIVE_TO_SELF,0.5f);

currentAzimuth = azimuth;

anim.setDuration(500);

anim.setRepeatCount(0);

anim.setFillAfter(true);

imageView.startAnimation(anim);

}

}

}

@Override

public void onAccuracyChanged(Sensor sensor, int accuracy) {

}

}


والآن يمكنك أن تقوم بتجربة المشروع على جوالك والاستمتاع به وإذا كانت لديك ملاحظات أو تحسينات على المشروع الرجاء كتابتها في التعليقات لتعم الفائدة على الجميع.

https://www.youtube.com/watch?v=5pFUiNmuJ5M


وللمزيد من الشرح ومعرفة التفاصيل عن ما تم كتابته في الشفرة يرجى الرجوع إلى المرجع الأساسي

المرجع : https://www.youtube.com/watch?v=IzzGVLnZBfQ