當前位置:
首頁 > 科技 > 這交互炸了 陀螺儀圖片「VR 看房」效果

這交互炸了 陀螺儀圖片「VR 看房」效果

原標題:這交互炸了 陀螺儀圖片「VR 看房」效果


本文作者


作者:jiangye


鏈接:


https://www.jianshu.com/p/1d3abe34c895

本文由作者授權發布。


1


概述


最近要抽取年前做的 VR 看房的相關功能至單獨的倉庫,藉此機會對其中利用陀螺儀滑動圖片的處理方式,以及平滑過渡至 VR 看房場景的過程做一個說明,也能讓接手 VR 相關模塊的同事更快了解其實現方式。



平滑過渡至 VR看房 場景


首先解析利用陀螺儀滑動圖片的處理方式。


在這裡主要說一說自己的思路,具體代碼會在最後給出 Demo 以供參考。


2


思路

為試驗該效果,自定義了一個繼承自ImageView的GyroscopeImageView,再寫一個實現SensorEventListener介面的GyroscopeManager。


在其onSensorChanged回調中利用陀螺儀感測器角度的變化來換算出圖片需要滑動的距離,並調用GyroscopeImageView的invalidate()方法,在GyroscopeImageView的onDraw方法中利用canvas.translate來改變圖片的位置。


效果如下:



圖片隨陀螺儀感測器滑動效果


在開發過程中注意到的問題:


1. 圖片的尺寸要合理,寬高略大於控制項能有較好的視覺效果。


2. 監聽陀螺儀感測器事件耗電,要在合適的時候註冊和註銷對感測器的監聽。


3. 當應用內有多個GyroscopeImageView時,要對它們進行合理的管理。


作為一個寫在獨立倉庫中的功能,要讓業務方能夠方便地接入使用。

但關於上面提到的前兩個問題,還需業務方的配合來解決:


1. 業務方在使用GyroscopeImageView控制項時,需要告知我們控制項的寬高,這樣我們能合理地對圖像尺寸做處理。


//例如用 Picasso載入圖像 可將控制項的寬高傳入自定義的 TransFormation 來處理圖像大小


Picasso. get()


.load(picUrl)


.transform( newGyroscopeTransFormation(width, height))


. into(gyroscopeImageView);


2. 業務方需要在相關Activity的onResume和onPause中對陀螺儀感測器進行註冊和註銷監聽。


@OverrideprotectedvoidonResume(){


super.onResume();

//利用我們的 GyroscopeManager 來註冊感測器監聽


GyroscopeManager.getInstance().register( this);


}


@OverrideprotectedvoidonPause(){


super.onPause();


//利用我們的 GyroscopeManager 來註銷監聽


GyroscopeManager.getInstance().unregister( this);


}


這樣看起來業務方接入還是比較簡單的。

重點分析一下第三個問題:

如何對應用內的GyroscopeImageView進行合理的管理。

3. 當有多個GyroscopeImageView存在時,GyroscopeManager應只對當前Activity中正在展示的GyroscopeImageView進行刷新。


想到View在添加至Window時會調用 View.onAttachedToWindow(),之後才進行繪製,當View與Window分離時會調用onAttachedToWindow()


由此得出的初步想法:在GyroscopeManager中維護一個GyroscopeImageView的集合。在GyroscopeImageView的onAttachedToWindow方法中將自身加入該集合,onDetachedFromWindow時將自身從集合中移除。而GyroscopeManager在感測器的回調中,去通知集合內的 view 進行刷新。


調試中發現該想法考慮不周,如果在一個包含GyroscopeImageView的頁面 Activity1 之上開啟一個 Activity2,此時 Activity1 內的GyroscopeImageView還在PhoneWindow內沒有調用onDetachedFromWindow(),因此該View還在 GyroscopeManager所維護的集合中。


若 Activity2 中也有GyroscopeImageView,則會註冊感測器監聽,且刷新集合內所有GyroscopeImageView。這樣一來被覆蓋在下層的 Activity1 內的GyroscopeImageView也會被通知刷新,這是沒有必要的,因為此時它並不可見。所以還需維護一個需要感測器處理的 Activity, 只通知該 Activity 內的GyroscopeImageView進行刷新。


最後針對GyroscopeImageView維護了一個Map:


Map<GyroscopeImageView, Boolean>


其 value 為Boolean標識該GyroscopeImageView是否需要被GyroscopeManager通知刷新。通過 Activity 的狀態變化來設置Map中各個GyroscopeImageView對應的 value,進行合理控制。


3

平滑過渡至 VR 場景頁


接下來說說從房源詳情頁平滑過渡至 VR 場景頁的動畫。


同樣先談一談實現該效果的思路,最後會給出 Demo 以供參考。


此處從房源詳情頁 Activity 跳轉至 VR 場景的 Activity,不同 Activity 內的 View 之間做動畫可以使用 Activity 轉場動畫。


但是我們GyroscopeImageView內的圖片是可滑動的,使用 Activity 轉場動畫會發現控制項內的圖片會瞬間居中回正,然後再擴展到全屏,該居中的過程較為突兀,有明顯的閃動感。


更加平滑的效果是使GyroscopeImageView內的圖片直接從當前的狀態擴展至全屏,最終放棄Activity轉場動畫,並提出如下解決方案:


1. 首先記錄第一個 Activity 中GyroscopeImageView控制項的位置和其內部圖片的偏移量。


2. 在第二個 Activity 中放置一個相同位置的ImageView, 並展示相同偏移量的圖片,用來覆蓋住上個頁面的GyroscopeImageView控制項。然後將該ImageView擴展至全屏做動畫。


3. 把第二個 Activity 的背景設為透明。


平滑的過度動畫


Demo地址:

https://github.com/JY39/GyroscopeImageDemo

喜歡這篇文章嗎?立刻分享出去讓更多人知道吧!

本站內容充實豐富,博大精深,小編精選每日熱門資訊,隨時更新,點擊「搶先收到最新資訊」瀏覽吧!


請您繼續閱讀更多來自 鴻洋 的精彩文章:

TAG:鴻洋 |