热门标签 | HotTags
当前位置:  开发笔记 > 编程语言 > 正文

reactnative触摸遥控器解决方案

完整代码(不可完全复制,仅供参考逻辑)***Createdbyappleon2016117.*importReact,{Component}fromreact;im

完整代码(不可完全复制,仅供参考逻辑

/**
* Created by apple on 2016/11/7.
*/
import React,{ Component } from 'react';
import {
View,
Navigator,
StyleSheet,
Image,
TouchableOpacity,
Alert,
Text,
TouchableHighlight,
PanResponder,
Animated,
Easing
} from 'react-native';
import Language from '../../common/language';
import Nav from '../../common/MineNav';
import Util from '../../common/common';
import Gsoap from '../../common/gsoap';
import * as TYPES from '../../common/types';

var TouchRemote = React.createClass({
debugMsg: true,
_panResponder: null,
movePos: [],
bounceValue: new Animated.Value(0),
getDefaultProps: function () {
return ({
controlType: "keyBoardType",
connectSTBToken: {}
});
},
getInitialState: function () {
return {
powerState: false,
homeState: false,
keyBoard: false,//up down left right ok
menuState: false,
backState: false,
volumeUpState: false,
volumeDownState: false
};
},
componentWillMount: function () {
this.console("compOnentWillMount===controlType:" + this.props.controlType + ";connectSTBToken:" + JSON.stringify(this.props.connectSTBToken));
this._panRespOnder= PanResponder.create({
// 要求成为响应者:
onStartShouldSetPanResponder: (evt, gestureState) => true,
onStartShouldSetPanResponderCapture: (evt, gestureState) => true,
onMoveShouldSetPanResponder: (evt, gestureState) => true,
onMoveShouldSetPanResponderCapture: (evt, gestureState) => true,

onPanResponderGrant: (evt, gestureState) => {
// 开始手势操作。给用户一些视觉反馈,让他们知道发生了什么事情!
// gestureState.{x,y}0 现在会被设置为0
this.movePos = [];
this.console("touch start===X:" + gestureState.x0 + "===Y:" + gestureState.y0);
this.movePos.push(Math.floor(gestureState.x0), Math.floor(gestureState.y0));
},
onPanResponderMove: (evt, gestureState) => {
// 最近一次的移动距离为gestureState.move{X,Y}
// 从成为响应者开始时的累计手势移动距离为gestureState.d{x,y}
},
onPanResponderTerminationRequest: (evt, gestureState) => true,
onPanResponderRelease: (evt, gestureState) => {
// 用户放开了所有的触摸点,且此时视图已经成为了响应者。
// 一般来说这意味着一个手势操作已经成功完成。
this.console("touch end===moveX:" + gestureState.moveX + "===moveY:" + gestureState.moveY);
this.movePos.push(Math.floor(gestureState.moveX), Math.floor(gestureState.moveY));
this.moveActionEnd(this.movePos);
},
onPanResponderTerminate: (evt, gestureState) => {
// 另一个组件已经成为了新的响应者,所以当前手势将被取消。
this.console("what???");
},
onShouldBlockNativeResponder: (evt, gestureState) => {
// 返回一个布尔值,决定当前组件是否应该阻止原生组件成为JS响应者
// 默认返回true。目前暂时只支持android。
return true;
}
});
},
actAnimationStart: function () {
this.console("actAnimationStart");
// 可选的基本动画类型: spring, decay, timing
this.bounceValue.setValue(0);
Animated.timing(
/**
* 将`bounceValue`值动画化的意思是,在以Animated为前缀名的组件中,比如此例中的Animated.Image,
* 将`bounceValue`值所赋予的样式就是会跟随`bounceValue`值的变化而改变样式的,
* `bounceValue`值的改变在Animated.timing()函数中改变,此例中`bounceValue`值将从0变化至1,变化的时间为200ms
* 也就是说,以Animated为前缀名的组件Image(Animated.Image),将在200ms的时间内,透明度从0变化至1
* */
this.bounceValue,// 将`bounceValue`值动画化
{
toValue: 1,// 将其值以动画的形式改到一个较小值
duration: 180,
easing: Easing.ease
}
).start(() => {
this.actAnimationEnd()
});
},
actAnimationEnd: function () {
this.console("actAnimationEnd");
// 可选的基本动画类型: spring, decay, timing
this.bounceValue.setValue(1);
Animated.timing(
this.bounceValue,// 将`bounceValue`值动画化
{
toValue: 0,// 将其值以动画的形式改到一个较小值
duration: 300,
easing: Easing.ease
}
).start();
},
moveActionEnd: function (movePos) {
this.console("movePos" + JSON.stringify(movePos));
let [sX, sY, eX, eY] = movePos;
let x = eX - sX, y = eY - sY, direction;
let z = Math.sqrt(Math.pow(x, 2) + Math.pow(y, 2));
if ((eX == 0 && eY == 0) || z <20) {//移动距离小于20像素视为点击
direction = -1;
} else {
direction = Math.round(( ( ( Math.atan2(y, x) * ( 180 / Math.PI ) ) + 180 ) / 90) + 3) % 4;
}
this.console("角度:" + direction);// 点击(-1) 上(0) 右(1) 下(2) 左(3)
switch (direction) {
case -1:
this.keyPressIn(6);
break;
case 0:
this.keyPressIn(2);
break;
case 1:
this.keyPressIn(5);
break;
case 2:
this.keyPressIn(3);
break;
case 3:
this.keyPressIn(4);
break;
default :
break;
}
},
keyPressIn: function (keyCode) {
let _keyString = '';
switch (keyCode) {
case 0://POWER
this.setState({powerState: true});
_keyString = 'POWER';
break;
case 1://HOME
this.setState({homeState: true});
_keyString = 'HOME';
break;
case 2://UP
this.setState({keyBoard: 'up'});
this.actAnimationStart();
_keyString = 'UP';
break;
case 3://DOWN
this.setState({keyBoard: 'down'});
this.actAnimationStart();
_keyString = 'DOWN';
break;
case 4://LEFT
this.setState({keyBoard: 'left'});
this.actAnimationStart();
_keyString = 'LEFT';
break;
case 5://RIGHT
this.setState({keyBoard: 'right'});
this.actAnimationStart();
_keyString = 'RIGHT';
break;
case 6://CENTER
this.setState({keyBoard: 'center'});
this.actAnimationStart();
_keyString = 'CENTER';
break;
case 7://RED
break;
case 8://MENU
this.setState({menuState: true});
_keyString = 'MENU';
break;
case 9://BACK
this.setState({backState: true});
_keyString = 'BACK';
break;
case 10://VOLUME_UP
this.setState({volumeUpState: true});
_keyString = 'VOLUME_UP';
break;
case 11://VOLUME_DOWN
this.setState({volumeDownState: true});
_keyString = 'VOLUME_DOWN';
break;
default:
break;
}
this.console("userID:" + this.props.connectSTBToken.userId + ";stbToken:" + this.props.connectSTBToken.userToken + ";keyCode:" + keyCode+ ";keyString:" + _keyString);
if (this.props.connectSTBToken.userId && this.props.connectSTBToken.userToken) {
let {userId, userToken} = this.props.connectSTBToken;
let that = this;
Gsoap.sendRemoteControlKeyOnSTBDevice(userId, userToken, _keyString, (statusCode, statusMessage) => {
that.console("keyPressIn===statusCode:" + statusCode + ";statusMessage:" + statusMessage);
switch (statusCode) {
case 2000:
//success
break;
default:
break;
}
});
}
},
keyBoardImg: function () {
let keyBoardImg = ' ';
switch (this.state.keyBoard) {
case 'up':
keyBoardImg = TYPES.REMOTE_TOUCH_UP;
break;
case 'down':
keyBoardImg = TYPES.REMOTE_TOUCH_DOWN;
break;
case 'left':
keyBoardImg = TYPES.REMOTE_TOUCH_LEFT;
break;
case 'right':
keyBoardImg = TYPES.REMOTE_TOUCH_RIGHT;
break;
case 'center':
keyBoardImg = TYPES.REMOTE_TOUCH_OK;
break;
}
return keyBoardImg;
},
render: function () {
let keyBoardImg = this.keyBoardImg();
return (
{...this._panResponder.panHandlers}>
+++xq debug+++touchRemote===" + msg + "===") : null;
}
});

const styles = StyleSheet.create({
wrap: {
flex: 1,
flexDirection: 'column',
justifyContent: 'flex-start',
alignItems: 'center',
paddingHorizontal: Util.screenWidth / 10,
paddingVertical: Util.screenHeight / 25,
backgroundColor: "#eaeff0"
},
topContainer: {
flexDirection: 'row',
justifyContent: 'space-between',
width: Util.screenWidth / 10 * 8,
paddingHorizontal: 15
},
StopHomeIcon: {
//13 : 7
width: Util.screenWidth / 7 * 1.6,
height: Util.screenWidth / 13 * 1.6
},

touchContainer: {
width: Util.screenWidth,
height: Util.screenWidth / 8 * 5 + Util.screenWidth / 11 * 1.2,
paddingHorizontal: 15,
marginTop: 15,
marginBottom: 15,
alignItems: 'center',
justifyContent: 'center'
},

middleContainer: {
flexDirection: 'row',
justifyContent: 'center',
width: Util.screenWidth / 10 * 8,
paddingHorizontal: 15,
marginVertical: 10
},
middleContainer_BG: {
width: Util.screenWidth / 8 * 5,
height: Util.screenWidth / 8 * 5,
flexDirection: 'column',
justifyContent: 'flex-start',
alignItems: 'center'
},
upIcon: {
flex: 1,
width: Util.screenWidth / 8 * 5 / 4 * 1.5
},
middleToolWrap: {
flex: 1,
flexDirection: 'row'
},
middleTool: {
flex: 1
},
dowIcon: {
flex: 1,
width: Util.screenWidth / 8 * 5 / 4 * 1.5
},

bottomContainer: {
width: Util.screenWidth / 8 * 5,
height: Util.screenWidth / 8 * 3.5,
flexDirection: 'column',
justifyContent: 'flex-start',
alignItems: 'center'
},
bottomIconStyle: {
//11 : 7
width: Util.screenWidth / 7 * 1.2,
height: Util.screenWidth / 11 * 1.2
},
bottomToolWrap: {
width: Util.screenWidth / 8 * 5,
flexDirection: 'row',
alignItems: 'center',
justifyContent: 'space-between'
}
});

module.exports = TouchRemote;



推荐阅读
  • 本文详细介绍了Android中的坐标系以及与View相关的方法。首先介绍了Android坐标系和视图坐标系的概念,并通过图示进行了解释。接着提到了View的大小可以超过手机屏幕,并且只有在手机屏幕内才能看到。最后,作者表示将在后续文章中继续探讨与View相关的内容。 ... [详细]
  • React基础篇一 - JSX语法扩展与使用
    本文介绍了React基础篇一中的JSX语法扩展与使用。JSX是一种JavaScript的语法扩展,用于描述React中的用户界面。文章详细介绍了在JSX中使用表达式的方法,并给出了一个示例代码。最后,提到了JSX在编译后会被转化为普通的JavaScript对象。 ... [详细]
  • 本文概述了JNI的原理以及常用方法。JNI提供了一种Java字节码调用C/C++的解决方案,但引用类型不能直接在Native层使用,需要进行类型转化。多维数组(包括二维数组)都是引用类型,需要使用jobjectArray类型来存取其值。此外,由于Java支持函数重载,根据函数名无法找到对应的JNI函数,因此介绍了JNI函数签名信息的解决方案。 ... [详细]
  • 近来有一个需求,是需要在androidjava基础库中插入一些log信息,完成这个工作需要的前置条件有编译好的android源码具体android源码如何编译,这 ... [详细]
  • RN即ReactNative基于React框架针对移动端的跨平台框架,在学习RN前建议最好熟悉下html,css,js,当然如果比较急,那就直接上手吧,毕竟用学习前面基础的时间,R ... [详细]
  • Android中高级面试必知必会,积累总结
    本文介绍了Android中高级面试的必知必会内容,并总结了相关经验。文章指出,如今的Android市场对开发人员的要求更高,需要更专业的人才。同时,文章还给出了针对Android岗位的职责和要求,并提供了简历突出的建议。 ... [详细]
  • 本文介绍了OC学习笔记中的@property和@synthesize,包括属性的定义和合成的使用方法。通过示例代码详细讲解了@property和@synthesize的作用和用法。 ... [详细]
  • 在说Hibernate映射前,我们先来了解下对象关系映射ORM。ORM的实现思想就是将关系数据库中表的数据映射成对象,以对象的形式展现。这样开发人员就可以把对数据库的操作转化为对 ... [详细]
  • 1,关于死锁的理解死锁,我们可以简单的理解为是两个线程同时使用同一资源,两个线程又得不到相应的资源而造成永无相互等待的情况。 2,模拟死锁背景介绍:我们创建一个朋友 ... [详细]
  • CentOS 7部署KVM虚拟化环境之一架构介绍
    本文介绍了CentOS 7部署KVM虚拟化环境的架构,详细解释了虚拟化技术的概念和原理,包括全虚拟化和半虚拟化。同时介绍了虚拟机的概念和虚拟化软件的作用。 ... [详细]
  • 本文介绍了如何使用Express App提供静态文件,同时提到了一些不需要使用的文件,如package.json和/.ssh/known_hosts,并解释了为什么app.get('*')无法捕获所有请求以及为什么app.use(express.static(__dirname))可能会提供不需要的文件。 ... [详细]
  • 如何用JNI技术调用Java接口以及提高Java性能的详解
    本文介绍了如何使用JNI技术调用Java接口,并详细解析了如何通过JNI技术提高Java的性能。同时还讨论了JNI调用Java的private方法、Java开发中使用JNI技术的情况以及使用Java的JNI技术调用C++时的运行效率问题。文章还介绍了JNIEnv类型的使用方法,包括创建Java对象、调用Java对象的方法、获取Java对象的属性等操作。 ... [详细]
  • 本文介绍了在Android Studio中使用命令行build gradle的方法,并解决了一些常见问题,包括手动配置gradle环境变量和解决External Native Build Issues的方法。同时提供了相关参考文章链接。 ... [详细]
  • ReactJSUIAnt设计空组件原文:https://w ... [详细]
  • 认识Vue关于Vue的描述有不少,不外乎都会拿来与Angular和React对比,同样头顶MVVM双向数据驱动设计模式光环的Angular自然被对比的最多,但到目前为止,Angul ... [详细]
author-avatar
手机用户随便转转
这个家伙很懒,什么也没留下!
PHP1.CN | 中国最专业的PHP中文社区 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved | 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有