Bagaimana cara mengakses data akselerometer / giroskop dari Javascript?

142

Saya baru-baru ini menemukan beberapa situs web yang tampaknya mengakses akselerometer atau giroskop di laptop saya, mendeteksi perubahan orientasi atau gerakan.

Bagaimana ini dilakukan? Haruskah saya berlangganan beberapa jenis acara pada windowobjek?

Di perangkat mana (laptop, ponsel, tablet) ini diketahui berfungsi?


NB : Sebenarnya saya sudah mengetahui (sebagian) jawaban atas pertanyaan ini, dan saya akan segera mempostingnya. Alasan bahwa saya posting pertanyaan di sini, adalah untuk membiarkan orang lain tahu bahwa data accelerometer yang tersedia di Javascript (pada perangkat tertentu) dan untuk menantang masyarakat untuk posting temuan baru pada subjek. Saat ini, sepertinya hampir tidak ada dokumentasi dari fitur tersebut.

Jørn Schou-Rode
sumber
Usaha yang bagus, terima kasih banyak. Apakah menurut Anda 3 tahun kemudian jawabannya memerlukan pembaruan?
Bartek Banachewicz
@BartekBanachewicz Terima kasih telah menelepon saya untuk yang satu ini. Saya akan mentransfer jawaban ke "wiki komunitas", berharap bahwa seseorang dengan pengetahuan yang lebih terkini akan memperbaruinya untuk mencerminkan keadaan seni saat ini.
Jørn Schou-Rode
Saya tidak dapat menemukan apakah operasi ini memerlukan izin pengguna. Saya tidak ingin membuat pertanyaan baru karena sangat cocok dengan pertanyaan Anda. Mungkin kita bisa menambahkan ini di sini? Adakah yang tahu jika ini membutuhkan persetujuan eksplisit? Apakah ini yang terjadi di semua browser dan semua OS seluler?
Perak

Jawaban:

11

Cara untuk melakukan ini di 2019+ adalah dengan menggunakan DeviceOrientationAPI . Ini berfungsi di sebagian besar browser modern pada desktop dan seluler.

window.addEventListener("deviceorientation", handleOrientation, true);

Setelah mendaftarkan event listener Anda (dalam hal ini, fungsi JavaScript disebut handleOrientation ()), fungsi listener Anda secara berkala dipanggil dengan data orientasi yang diperbarui.

Acara orientasi berisi empat nilai:

  • DeviceOrientationEvent.absolute
  • DeviceOrientationEvent.alpha
  • DeviceOrientationEvent.beta
  • DeviceOrientationEvent.gamma

Fungsi event handler bisa terlihat seperti ini:

function handleOrientation(event) {
  var absolute = event.absolute;
  var alpha    = event.alpha;
  var beta     = event.beta;
  var gamma    = event.gamma;
  // Do stuff with the new orientation data
}
str
sumber
182

Saat ini ada tiga peristiwa berbeda yang mungkin atau mungkin tidak dipicu saat perangkat klien berpindah. Dua di antaranya berfokus pada orientasi dan yang terakhir tentang gerak :

  • ondeviceorientationdiketahui berfungsi pada versi desktop Chrome, dan sebagian besar laptop Apple tampaknya memiliki perangkat keras yang diperlukan agar ini berfungsi. Ini juga berfungsi pada Mobile Safari di iPhone 4 dengan iOS 4.2. Dalam fungsi event handler, Anda dapat mengakses alpha, beta, gammanilai-nilai pada data acara disediakan sebagai satu-satunya argumen untuk fungsi.

  • onmozorientationdidukung pada Firefox 3.6 dan yang lebih baru. Sekali lagi, ini diketahui berfungsi pada sebagian besar laptop Apple, tetapi mungkin bekerja pada mesin Windows atau Linux dengan akselerometer juga. Dalam fungsi event handler, mencari x, y, zbidang data acara disediakan sebagai argumen pertama.

  • ondevicemotiondiketahui bekerja di iPhone 3GS + 4 dan iPad (keduanya dengan iOS 4.2), dan menyediakan data yang terkait dengan akselerasi perangkat klien saat ini. Data acara diteruskan ke fungsi pengendali memiliki accelerationdan accelerationIncludingGravity, yang keduanya memiliki tiga bidang untuk setiap sumbu: x, y,z

Situs web contoh "pendeteksi gempa" menggunakan serangkaian ifpernyataan untuk mencari tahu peristiwa mana yang harus dilampirkan (dalam urutan yang agak diprioritaskan) dan meneruskan data yang diterima ke tiltfungsi umum :

if (window.DeviceOrientationEvent) {
    window.addEventListener("deviceorientation", function () {
        tilt([event.beta, event.gamma]);
    }, true);
} else if (window.DeviceMotionEvent) {
    window.addEventListener('devicemotion', function () {
        tilt([event.acceleration.x * 2, event.acceleration.y * 2]);
    }, true);
} else {
    window.addEventListener("MozOrientation", function () {
        tilt([orientation.x * 50, orientation.y * 50]);
    }, true);
}

Faktor konstan 2 dan 50 digunakan untuk "menyelaraskan" bacaan dari dua kejadian terakhir dengan yang dari kejadian pertama, tetapi ini sama sekali bukan representasi yang tepat. Untuk proyek "mainan" sederhana ini, ini berfungsi dengan baik, tetapi jika Anda perlu menggunakan data untuk sesuatu yang sedikit lebih serius, Anda harus membiasakan diri dengan unit nilai yang diberikan dalam berbagai acara dan memperlakukannya dengan hormat :)

Jørn Schou-Rode
sumber
9
terkadang sebuah jawaban berhasil!
Scott Evernden
1
Jika ada yang bertanya-tanya - ondevicemotion berfungsi untuk Firefox 8.0 tetapi diskalakan dengan salah (0-9), tetapi ini tampaknya diperbaiki di versi yang lebih baru (10.0). Tidak ada yang berfungsi di Opera Mobile dan semua yang standar berfungsi dengan baik di browser default Nokia N9.
Nux
2
Acara MozOrientation telah dihapus karena sudah usang di Firefox 6. Jadi sekarang mereka semua menggunakan API standar.
Chris Morgan
Ini sepertinya tidak berfungsi di Firefox 30, seperti yang ditunjukkan di biola ini . :(
bwinton
sidenote: Plax.js , yang digunakan di halaman 404 dan 500 github, menggunakan ondeviceorientation .
Yosh
22

Tidak dapat menambahkan komentar ke penjelasan luar biasa di posting lain tetapi ingin menyebutkan bahwa sumber dokumentasi yang bagus dapat ditemukan di sini .

Ini cukup untuk mendaftarkan fungsi kejadian untuk akselerometer seperti ini:

if(window.DeviceMotionEvent){
  window.addEventListener("devicemotion", motion, false);
}else{
  console.log("DeviceMotionEvent is not supported");
}

dengan pawang:

function motion(event){
  console.log("Accelerometer: "
    + event.accelerationIncludingGravity.x + ", "
    + event.accelerationIncludingGravity.y + ", "
    + event.accelerationIncludingGravity.z
  );
}

Dan untuk magnetometer, penangan kejadian berikut harus didaftarkan:

if(window.DeviceOrientationEvent){
  window.addEventListener("deviceorientation", orientation, false);
}else{
  console.log("DeviceOrientationEvent is not supported");
}

dengan penangan:

function orientation(event){
  console.log("Magnetometer: "
    + event.alpha + ", "
    + event.beta + ", "
    + event.gamma
  );
}

Ada juga bidang yang ditentukan dalam peristiwa gerakan untuk giroskop tetapi tampaknya tidak didukung secara universal (misalnya tidak berfungsi pada Catatan Samsung Galaxy).

Ada kode kerja sederhana di GitHub

Magang Tak Terbatas
sumber
Jika sensor dinonaktifkan di iOS <13, window.DeviceOrientationEvent mengembalikan undefined?
savram
1

Fallback yang berguna di sini: https://developer.mozilla.org/en-US/docs/Web/Events/MozOrientation

function orientationhandler(evt){


  // For FF3.6+
  if (!evt.gamma && !evt.beta) {
    evt.gamma = -(evt.x * (180 / Math.PI));
    evt.beta = -(evt.y * (180 / Math.PI));
  }

  // use evt.gamma, evt.beta, and evt.alpha 
  // according to dev.w3.org/geo/api/spec-source-orientation


}

window.addEventListener('deviceorientation',  orientationhandler, false);
window.addEventListener('MozOrientation',     orientationhandler, false);
Luckylooke
sumber