电脑知识|欧美黑人一区二区三区|软件|欧美黑人一级爽快片淫片高清|系统|欧美黑人狂野猛交老妇|数据库|服务器|编程开发|网络运营|知识问答|技术教程文章 - 好吧啦网

您的位置:首頁技術(shù)文章
文章詳情頁

Android如何監(jiān)聽屏幕旋轉(zhuǎn)

瀏覽:3日期:2022-09-20 15:11:25
背景

關(guān)于個(gè)人,前段時(shí)間由于業(yè)務(wù)太忙,所以一直沒有來得及思考并且沉淀點(diǎn)東西;同時(shí)組內(nèi)一個(gè)個(gè)都在業(yè)務(wù)上能有自己的思考和總結(jié),在這樣的氛圍下,不由自主的驅(qū)使周末開始寫點(diǎn)東西,希望自己除了日常忙于業(yè)務(wù),可以沉淀點(diǎn)東西,加上自己的成長..

關(guān)于切入點(diǎn),最近在做應(yīng)⽤內(nèi)懸浮球功能時(shí),需要監(jiān)聽屏幕旋轉(zhuǎn)事件來對懸浮球的位置進(jìn)⾏調(diào)整,發(fā)現(xiàn)有些情況下并不能收到系統(tǒng)回調(diào),思考了⼀翻,做了⼀個(gè)屏幕旋轉(zhuǎn)的模擬監(jiān)聽,基本上能達(dá)到⽬的。

問題

懸浮球在停⽌拖拽后,需要貼邊到⼿機(jī)屏幕的左右兩側(cè)。

在豎屏狀態(tài)下,x坐標(biāo)為0即為左邊緣,x坐 標(biāo)為屏幕寬度即為右邊緣。

但是在橫屏狀態(tài)下,情況就⽐較復(fù)雜了。現(xiàn)在⼤部分Android⼿機(jī)都是劉 海屏的設(shè)計(jì),在全屏狀態(tài)下,懸浮球貼邊時(shí)不能收到劉海下⾯去,不然就點(diǎn)不到了。

所以此時(shí)需要算 出劉海的寬度,以此寬度作為懸浮球左邊的起始位置,這樣懸浮球貼邊的時(shí)候就不會(huì)躲到劉海下⾯ 去。 如下圖所示

Android如何監(jiān)聽屏幕旋轉(zhuǎn)

但是在屏幕旋轉(zhuǎn)之后,劉海到了右邊,左邊就不應(yīng)該以劉海的寬度作為懸浮球的起點(diǎn)了。 這樣的話就需要監(jiān)聽屏幕的旋轉(zhuǎn)了,配合屏幕⽅向的⻆度,就能正確判斷。監(jiān)聽屏幕的旋轉(zhuǎn)只需要重 寫Activity的onConfiguratuonChanged⽣命周期。

override fun onConfigurationChanged(newConfig: Configuration) { super.onConfigurationChanged(newConfig) Log.i(TAG, 'on configuration changed')}

在AndroidManifest中配置

android:configChanges='orientation|screenSize'

此時(shí)發(fā)現(xiàn)了⼀個(gè)問題,當(dāng)把Activity的screenOrientation設(shè)置成sensorLandscape時(shí),即使屏幕旋轉(zhuǎn) 也收不到這個(gè)回調(diào)(這個(gè)和之前的理解有點(diǎn)不⼀樣)。于是將screenOrientation設(shè)置成sensor,屏 幕旋轉(zhuǎn)就能正常回調(diào)到這⾥,多試⼏次發(fā)現(xiàn),只有在橫屏和豎屏之間切換時(shí)才能收到回調(diào),如果直接 將橫屏倒過來,就是橫屏狀態(tài)不變,⽅向調(diào)轉(zhuǎn),此時(shí)也不會(huì)收到回調(diào)。

解決思路

既然onConfigurationChanged收不到回調(diào),還有另外⼀個(gè)辦法,就是監(jiān)聽屏幕⽅向度數(shù),代碼如下

mOrientationEventListener = object : OrientationEventListener(this) { override fun onOrientationChanged(orientation: Int) { Log.i(TAG, 'on orientation changed angle is $orientation') if (orientation > 340 || orientation < 20) { //0 } else if (orientation in 71..109) { //90 } else if (orientation in 161..199) { //180 } else if (orientation in 251..289) { //270 } }}

通過度數(shù)來判斷劉海是在左邊還是在右邊,即270度時(shí)在左邊,90度時(shí)在右邊。這種⽅式看起來可以 解決問題,但是多旋轉(zhuǎn)⼏次就發(fā)現(xiàn)⼜有其他問題。按照正常思維,屏幕的顯示⽅向應(yīng)該和這個(gè)度數(shù)⼀ 致才對,即屏幕的顯示應(yīng)該是⾃上⽽下的。但是下圖就不是這樣。

Android如何監(jiān)聽屏幕旋轉(zhuǎn)

此時(shí)度數(shù)為90,屏幕卻倒⽴著顯示的,并沒有旋轉(zhuǎn)成正⽴狀態(tài),但是按照上⾯的代碼,會(huì)將90度判定 為正常90度正⽴顯示的狀態(tài),此時(shí)去修改懸浮球的位置就是錯(cuò)誤的。

那如果在收到onOrientationChanged這個(gè)回調(diào)時(shí)能判斷⼀下屏幕顯示的⽅向呢,就是在度數(shù)達(dá)到90 度范圍時(shí),同時(shí)判斷屏幕的顯示⽅向,即兩個(gè)條件同時(shí)滿⾜才判定成屏幕旋轉(zhuǎn)了。

⽤下⾯的代碼判定屏幕顯示⽅向

val windowManager = context.getSystemService(Context.WINDOW_SERVICE) asWindowManagerval rotation = windowManager.defaultDisplay?.rotation//rotation為常量0、1、2、3,分別表示屏幕的四個(gè)⽅向

通過這樣的判斷基本上能將屏幕旋轉(zhuǎn)事件監(jiān)聽準(zhǔn)確了,onOrientationChanged這個(gè)回調(diào)很靈敏,⼿ 機(jī)屏幕稍微動(dòng)⼀下就會(huì)回調(diào)。那我希望模擬正常的屏幕旋轉(zhuǎn)事件來修改懸浮球的位置,總不能很頻繁 的刷新吧。這⾥做⼀下控制就好,全部代碼如下:

object ScreenOrientationHelper { val ORIENTATION_TYPE_0 = 0 val ORIENTATION_TYPE_90 = 90 val ORIENTATION_TYPE_180 = 180 val ORIENTATION_TYPE_270 = 270 private var mOrientationEventListener: OrientationEventListener? = null private var mScreenOrientationChangeListener: ScreenOrientationChangeListener? = null private var currentType = ORIENTATION_TYPE_0 fun init(context: Context, listener: ScreenOrientationChangeListener) { mScreenOrientationChangeListener = listener mOrientationEventListener = object : OrientationEventListener(context) { override fun onOrientationChanged(orientation: Int) { if (mScreenOrientationChangeListener == null) { return } if (orientation > 340 || orientation < 20) { //0 if (currentType == 0) { return } if (getScreenRotation(context) == Surface.ROTATION_0) { mScreenOrientationChangeListener!!.onChange(ORIENTATION_TYPE_0) currentType = ORIENTATION_TYPE_0 } } else if (orientation in 71..109) { //90 if (currentType == 90) { return } val angle = getScreenRotation(context) if (angle == Surface.ROTATION_270) { mScreenOrientationChangeListener!!.onChange(ORIENTATION_TYPE_90) currentType = ORIENTATION_TYPE_90 } } else if (orientation in 161..199) { //180 if (currentType == 180) { return } val angle = getScreenRotation(context) if (angle == Surface.ROTATION_180) { mScreenOrientationChangeListener!!.onChange(ORIENTATION_TYPE_180) currentType = ORIENTATION_TYPE_180 } } else if (orientation in 251..289) { //270 if (currentType == 270) { return } val angle = getScreenRotation(context) if (angle == Surface.ROTATION_90) { mScreenOrientationChangeListener!!.onChange(ORIENTATION_TYPE_270) currentType = ORIENTATION_TYPE_270 } } } } register() } private fun getScreenRotation(context: Context): Int { val windowManager = context.getSystemService(Context.WINDOW_SERVICE) as WindowManager return windowManager.defaultDisplay?.rotation ?: 0 } fun register() { if (mOrientationEventListener != null) { mOrientationEventListener!!.enable() } } fun unRegister() { if (mOrientationEventListener != null) { mOrientationEventListener!!.disable() } } interface ScreenOrientationChangeListener { /** * * @param orientation */ fun onChange(orientation: Int) }}

使⽤的話,直接這樣:

ScreenOrientationHelper.init(this, object :ScreenOrientationHelper.ScreenOrientationChangeListener { override fun onChange(orientation: Int) { when(orientation) { ScreenOrientationHelper.ORIENTATION_TYPE_0 -> {} ScreenOrientationHelper.ORIENTATION_TYPE_90 -> {} ScreenOrientationHelper.ORIENTATION_TYPE_180 -> {} ScreenOrientationHelper.ORIENTATION_TYPE_270 -> {} } }})

通過上⾯的代碼發(fā)現(xiàn),在onOrientationChanged回調(diào)90度范圍內(nèi)時(shí),判定屏幕顯示⽅向是和 Surface.ROTATION_270⽐較的,⽽270范圍內(nèi)時(shí)是和Surface.ROTATION_90⽐較的。看得出來⻆度 是順時(shí)針遞增的,⽽屏幕⽅向是逆時(shí)針計(jì)算度數(shù)的。

其他問題

在測試過程中,上⾯的⽅案還存在另外⼀個(gè)問題,雖然onOrientationChanged這個(gè)回調(diào)很靈敏,但 是也有度數(shù)不變⽽屏幕⽅向旋轉(zhuǎn)的情況發(fā)⽣,即保持屏幕⽅向不變,⽽是增加屏幕的坡度(將⼿機(jī)⼀ 邊貼在桌⾯,慢慢⽴起來),在坡度達(dá)到⼀定時(shí),屏幕會(huì)發(fā)⽣旋轉(zhuǎn),此時(shí)onOrientationChanged是 不會(huì)回調(diào)的,因?yàn)闆]有變化。這樣就收不到屏幕旋轉(zhuǎn)的回調(diào)了,但是在實(shí)際⽤⼿機(jī)的場景中,這種情 況是⽐較少的,可以親身試試看。

小結(jié)

在平時(shí)開發(fā)中,要區(qū)分是哪種狀態(tài)橫屏的場景⽐較少,否則我認(rèn)為Android會(huì)給出準(zhǔn)確的回調(diào)的。 Android設(shè)備碎⽚化嚴(yán)重,除了劉海,在屏幕的下邊緣還有虛擬導(dǎo)航欄,在不同的系統(tǒng)設(shè)置下,這個(gè) 導(dǎo)航欄不顯示狀態(tài)會(huì)不⼀樣。那么這時(shí)候在懸浮球貼邊這個(gè)需求中就不僅僅要考慮劉海了,還得考慮 導(dǎo)航欄。更有甚者,在旋轉(zhuǎn)過程中,虛擬導(dǎo)航欄會(huì)⼀直保持在⼀個(gè)⽅向,和劉海疊加。那么要清楚的 算位置,第⼀步就是要監(jiān)聽屏幕的旋轉(zhuǎn)了。

以上就是如何監(jiān)聽Android屏幕旋轉(zhuǎn)的詳細(xì)內(nèi)容,更多關(guān)于監(jiān)聽Android屏幕旋轉(zhuǎn)的資料請關(guān)注好吧啦網(wǎng)其它相關(guān)文章!

標(biāo)簽: Android
相關(guān)文章:
主站蜘蛛池模板: 小型气象站_便携式自动气象站_校园气象站-竞道气象设备网 | 电动卫生级调节阀,电动防爆球阀,电动软密封蝶阀,气动高压球阀,气动对夹蝶阀,气动V型调节球阀-上海川沪阀门有限公司 | 金库门,金库房,金库门厂家,金库门价格-河北特旺柜业有限公司 | 扒渣机厂家_扒渣机价格_矿用扒渣机_铣挖机_撬毛台车_襄阳永力通扒渣机公司 | 环讯传媒,永康网络公司,永康网站建设,永康小程序开发制作,永康网站制作,武义网页设计,金华地区网站SEO优化推广 - 永康市环讯电子商务有限公司 | 365文案网_全网创意文案句子素材站 | 无锡网站建设_小程序制作_网站设计公司_无锡网络公司_网站制作 | 空心明胶胶囊|植物胶囊|清真胶囊|浙江绿键胶囊有限公司欢迎您! | 贵州科比特-防雷公司厂家提供贵州防雷工程,防雷检测,防雷接地,防雷设备价格,防雷产品报价服务-贵州防雷检测公司 | 跨境物流_美国卡派_中大件运输_尾程派送_海外仓一件代发 - 广州环至美供应链平台 | Win10系统下载_32位/64位系统/专业版/纯净版下载 | 酵素生产厂家_酵素OEM_酵素加盟_酵素ODM_酵素原料厂家_厦门益力康 | 安全阀_弹簧式安全阀_美标安全阀_工业冷冻安全阀厂家-中国·阿司米阀门有限公司 | 全自动烧卖机厂家_饺子机_烧麦机价格_小笼汤包机_宁波江北阜欣食品机械有限公司 | 安徽免检低氮锅炉_合肥燃油锅炉_安徽蒸汽发生器_合肥燃气锅炉-合肥扬诺锅炉有限公司 | 西门子代理商_西门子变频器总代理-翰粤百科 | 广州活动策划公司-15+年专业大型公关活动策划执行管理经验-睿阳广告 | 学校用栓剂模,玻璃瓶轧盖钳,小型安瓿熔封机,实验室安瓿熔封机-长沙中亚制药设备有限公司 | 布袋式除尘器|木工除尘器|螺旋输送机|斗式提升机|刮板输送机|除尘器配件-泊头市德佳环保设备 | Eiafans.com_环评爱好者 环评网|环评论坛|环评报告公示网|竣工环保验收公示网|环保验收报告公示网|环保自主验收公示|环评公示网|环保公示网|注册环评工程师|环境影响评价|环评师|规划环评|环评报告|环评考试网|环评论坛 - Powered by Discuz! | 阳光模拟试验箱_高低温试验箱_高低温冲击试验箱_快速温变试验箱|东莞市赛思检测设备有限公司 | 永嘉县奥阳陶瓷阀门有限公司 | 2025黄道吉日查询、吉时查询、老黄历查询平台- 黄道吉日查询网 | 楼承板-开闭口楼承板-无锡海逵楼承板 | 恒温恒湿试验箱厂家-高低温试验箱维修价格_东莞环仪仪器_东莞环仪仪器 | 房车价格_依维柯/大通/东风御风/福特全顺/江铃图片_云梯搬家车厂家-程力专用汽车股份有限公司 | 网站seo优化_seo云优化_搜索引擎seo_启新网络服务中心 | 深圳侦探联系方式_深圳小三调查取证公司_深圳小三分离机构 | 电杆荷载挠度测试仪-电杆荷载位移-管桩测试仪-北京绿野创能机电设备有限公司 | 定硫仪,量热仪,工业分析仪,马弗炉,煤炭化验设备厂家,煤质化验仪器,焦炭化验设备鹤壁大德煤质工业分析仪,氟氯测定仪 | 苗木价格-苗木批发-沭阳苗木基地-沭阳花木-长之鸿园林苗木场 | 飞行者联盟-飞机模拟机_无人机_低空经济_航空技术交流平台 | 艺术涂料|木纹漆施工|稻草漆厂家|马来漆|石桦奴|水泥漆|选加河南天工涂料 | 酸度计_PH计_特斯拉计-西安云仪 纯水电导率测定仪-万用气体检测仪-低钠测定仪-米沃奇科技(北京)有限公司www.milwaukeeinst.cn | 济南玻璃安装_济南玻璃门_济南感应门_济南玻璃隔断_济南玻璃门维修_济南镜片安装_济南肯德基门_济南高隔间-济南凯轩鹏宇玻璃有限公司 | 高压绝缘垫-红色配电房绝缘垫-绿色高压绝缘地毯-上海苏海电气 | 游泳池设计|设备|配件|药品|吸污机-东莞市太平洋康体设施有限公司 | 北京网站建设首页,做网站选【优站网】,专注北京网站建设,北京网站推广,天津网站建设,天津网站推广,小程序,手机APP的开发。 | 胶泥瓷砖胶,轻质粉刷石膏,嵌缝石膏厂家,腻子粉批发,永康家德兴,永康市家德兴建材厂 | 旋转/数显粘度计-运动粘度测定仪-上海平轩科学仪器 | 中央空调温控器_风机盘管温控器_智能_液晶_三速开关面板-中央空调温控器厂家 |