android 远程显示设备与本地设备坐标转换

前段时间在做一个android设备控制android设备的程序,写了一个获取坐标的点,由于使用太多的if else判断条件,虽然能实现获取x,y的功能,自己写的自己看着就已经头晕了,于是今天花了点时间,整理了一下。我实现的场景是,当我的手机被投射到另一个android设备上,通过surfaceview显示手机屏幕(视频流),我不知道手机是竖屏还是横屏,如果在显示端坐处理,只能比较图片,看那边有黑边。显示效果可能有三种,如下:
这里写图片描述
在这种情况先获取显示视频流surfaceview的x,y需要计算转换发送到手机端,这样操作才是同一个点。
下面通过一个例子来了解计算过程,可以通过两个Imageview来模拟远程显示设备和本地设备,在远程显示的Imageview上点击,通过Ontouch方法拿到x,y值,通过计算在本地Imageview上画出点,看远程点击位置是不是跟本地换算出来的位置点能一一对应上,我的手机在开发者选项中开启了指针轨迹,在远程Imageview上操作的轨迹会被记录下来,在本地Imageview上具体点会点出红点,看实例图,如下:
这里写图片描述这里写图片描述
具体实现代码:

package com.example.darren.surfacepro;

import android.content.Context;
import android.view.WindowManager;

/**
 * Created by darren.qi on 2013/4/22.
 */
public class LogicReckon {
    private int mRemoteDeviceWidth = 700;
    private int mRemoteDeviceHeight = 650;
    private int mLocalDeviceWidth;
    private int mLocalDeviceHeight;
    private int mOrientation=1;
    private Context mContext=null;

    public LogicReckon(Context context) {
        mContext=context;
    }

    public void setOrientation(int val)
    {
        WindowManager wm = (WindowManager) mContext.getSystemService(Context.WINDOW_SERVICE);
        mLocalDeviceWidth = 700;
        mLocalDeviceHeight = 350;
        mOrientation=val;
    }

    public PointDevice convert(float x,float y)
    {
        PointDevice point=new PointDevice();
        double scaling=(mLocalDeviceHeight*(1.0d)/mLocalDeviceWidth);
        double scalingHeight=mLocalDeviceHeight*(1.0d)/mRemoteDeviceHeight;
        double scalingWidth=mLocalDeviceWidth*(1.0d)/mRemoteDeviceWidth;
        double height= (scaling*mRemoteDeviceWidth);
        double width= (mRemoteDeviceHeight/scaling);
        double realheight=0;
        double realwidth=0;
        double Ay=0;
        double Ax=0;

        //取远程设备的宽做基准
        if(height<=mRemoteDeviceHeight)
        {
            realwidth=mRemoteDeviceWidth;
            realheight=height;
            Ay=(mRemoteDeviceHeight-height)/2;
            if((y-Ay)<0||(y-Ay)>realheight)
                return null;
            scalingHeight=mLocalDeviceHeight*(1.0d)/realheight;
            point.setX((float) (x * scalingWidth)).setY((float) ((y-Ay)*scalingHeight));
        }
        //取远程设备的高为做基准
        else if(width<=mRemoteDeviceWidth)
        {

            realwidth=width;
            realheight=mRemoteDeviceHeight;
            Ax=(mRemoteDeviceWidth-width)/2;
            if((x-Ax)<0||(x-Ax)>realwidth)
                return null;
            scalingWidth=mLocalDeviceWidth*(1.0d)/realwidth;
            point.setX((float) ((x-Ax) * scalingWidth)).setY((float) (y * scalingHeight));
        }
        return point;
    }
    public class PointDevice{
        private float x;
        private float y;

        public float getX() {
            return x;
        }

        public PointDevice setX(float x) {
            this.x = x;
            return this;
        }

        public float getY() {
            return y;
        }

        public PointDevice setY(float y) {
            this.y = y;
            return this;
        }
    }
}

这段代码放置到手机端,当手机端通过连接方式usb或者tcp获得到显示设备端的x,y值,通过onConfigurationChanged判断横竖屏后获得宽高度,转换得到真正的x,y位置,模拟input实时motion事件出来,手机就会还原显示端在surfaceview上的操作。

当一张图片在imageview上放大缩小或者移动后,想获取在屏幕上点击后,真正的图片上的位置点,类似,显示一张图片,当点击某个位置后,在点击位置上绘制图片或者做标记之类的。这种情况可以使用Imageview上移动缩放的矩阵来获取真正相对于图片的左上角的位置点。可以通过一行代码计算出相对点,等以后有时间了在整理一下之前代码,也贴出来吧。
[测试demo下载]

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值