unity实现框选效果
思路:
在uinity中既可以将屏幕坐标转换为世界坐标,也可以将世界坐标转换为屏幕坐标。这样的话我们就可以通过判断物体在世界坐标转换为平幕坐标是否在鼠标框选的矩形区域坐标内,来判断物体是否在框选范围。
使用到的API:
GL:http://wiki.ceeger.com/script/unityengine/classes/gl/gl,用来实现在鼠标拖动时在屏幕中绘制出矩形区域。
Camera:http://wiki.ceeger.com/script/unityengine/classes/camera/camera.worldtoscreenpoint,将世界坐标转换为屏幕坐标
将可选取的对象放置在 characters集合中,rectMat的材质为使用sprite下的default类型的shader的材质即可。
using UnityEngine;
using System.Collections;
using System.Collections.Generic; public class SelectObjects : MonoBehaviour
{ public List<GameObject> characters;
public Color rectColor = Color.green; private Vector3 start = Vector3.zero;//记下鼠标按下位置 // private Material rectMat = null;//画线的材质 不设定系统会用当前材质画线 结果不可控
public Material rectMat = null;//这里使用Sprite下的defaultshader的材质即可 private bool drawRectangle = false;//是否开始画线标志 // Use this for initialization void Start()
{ // rectMat = new Material("Shader \"Lines/Colored Blended\" {" +
//
// "SubShader { Pass { " +
//
// " Blend SrcAlpha OneMinusSrcAlpha " +
//
// " ZWrite Off Cull Off Fog { Mode Off } " +
//
// " BindChannels {" +
//
// " Bind \"vertex\", vertex Bind \"color\", color }" +
//
// "} } }");//生成画线的材质 rectMat.hideFlags = HideFlags.HideAndDontSave; rectMat.shader.hideFlags = HideFlags.HideAndDontSave;//不显示在hierarchy面板中的组合,不保存到场景并且卸载Resources.UnloadUnusedAssets不卸载的对象。 } void Update()
{ if (Input.GetMouseButtonDown())
{ drawRectangle = true;//如果鼠标左键按下 设置开始画线标志 start = Input.mousePosition;//记录按下位置 }
else if (Input.GetMouseButtonUp())
{ drawRectangle = false;//如果鼠标左键放开 结束画线
checkSelection(start,Input.mousePosition);
}
} void OnPostRender()
{//画线这种操作推荐在OnPostRender()里进行 而不是直接放在Update,所以需要标志来开启 if (drawRectangle)
{ Vector3 end = Input.mousePosition;//鼠标当前位置 GL.PushMatrix();//保存摄像机变换矩阵,把投影视图矩阵和模型视图矩阵压入堆栈保存 if (!rectMat) return; rectMat.SetPass();//为渲染激活给定的pass。 GL.LoadPixelMatrix();//设置用屏幕坐标绘图 GL.Begin(GL.QUADS);//开始绘制矩形 GL.Color(new Color(rectColor.r, rectColor.g, rectColor.b, 0.1f));//设置颜色和透明度,方框内部透明 //绘制顶点
GL.Vertex3(start.x, start.y, ); GL.Vertex3(end.x, start.y, ); GL.Vertex3(end.x, end.y, ); GL.Vertex3(start.x, end.y, ); GL.End(); GL.Begin(GL.LINES);//开始绘制线 GL.Color(rectColor);//设置方框的边框颜色 边框不透明 GL.Vertex3(start.x, start.y, ); GL.Vertex3(end.x, start.y, ); GL.Vertex3(end.x, start.y, ); GL.Vertex3(end.x, end.y, ); GL.Vertex3(end.x, end.y, ); GL.Vertex3(start.x, end.y, ); GL.Vertex3(start.x, end.y, ); GL.Vertex3(start.x, start.y, ); GL.End(); GL.PopMatrix();//恢复摄像机投影矩阵 } } //检测被选择的物体
void checkSelection(Vector3 start, Vector3 end)
{ Vector3 p1 = Vector3.zero; Vector3 p2 = Vector3.zero; if (start.x > end.x)
{//这些判断是用来确保p1的xy坐标小于p2的xy坐标,因为画的框不见得就是左下到右上这个方向的 p1.x = end.x; p2.x = start.x; } else { p1.x = start.x; p2.x = end.x; } if (start.y > end.y)
{ p1.y = end.y; p2.y = start.y; } else { p1.y = start.y; p2.y = end.y; } foreach (GameObject obj in characters)
{//把可选择的对象保存在characters数组里 Vector3 location = Camera.main.WorldToScreenPoint(obj.transform.position);//把对象的position转换成屏幕坐标 if (location.x < p1.x || location.x > p2.x || location.y < p1.y || location.y > p2.y || location.z < Camera.main.nearClipPlane || location.z > Camera.main.farClipPlane)//z方向就用摄像机的设定值,看不见的也不需要选择了 {
//disselecting(obj);//上面的条件是筛选 不在选择范围内的对象,然后进行取消选择操作,比如把物体放到default层,就不显示轮廓线了
print("---"+obj.name);
} else {
//selecting(obj);//否则就进行选中操作,比如把物体放到画轮廓线的层去
print("+++" + obj.name); } } }
}
效果:
unity实现框选效果的更多相关文章
- JavaScript实现框选效果
<html> <head> <title>region</title> <style> body { margin: 0; padding: ...
- vue封装一个简单的div框选时间的组件
记录一下我前段时间封装的一个vue组件吧.技术需要积累,有时间我把我之前写的还不错的组件都开源出来.并尝试vue和react 两种方式的组件封装.今天简单写下鼠标框选div选中效果的封装吧. div框 ...
- [转]结合轮廓显示,实现完整的框选目标(附Demo代码)
原地址:http://www.cnblogs.com/88999660/articles/2887078.html 几次看见有人问框选物体的做法,之前斑竹也介绍过,用画的框生成的视椎,用经典图形学的视 ...
- unity3d结合轮廓显示,实现完整的框选目标(附Demo代码)
原地址:http://dong2008hong.blog.163.com/blog/static/469688272013111554511948/ 在unity里实现,其实很简单,因为有两个前提:1 ...
- jQuery实现全选效果【转】
这是一段用jquery实现全选的代码,主要思路如下: 1.所有的复选框都有单击事件,所有效果都是在单击事件下实现的 2.全选复选框所实现的功能与其他复选选项实现的功能不同,所有在单击事件内做一个判断, ...
- Javascript实现鼠标框选元素后拖拽被框选的元素
之前需要做一个框选元素后拖拽被框选中的元素功能,在网上找资料做了一些修改,基本达到了需要的效果,希望对也需要实现框选后拖拽元素功能的人有用. 页面加载后效果 框选后的内容可以拖拽,如下图: 代码下载
- ListView鼠标框选实现蓝色蒙板
此问题留心已久,今日方悉心求之,记录心得. ListView控件,不论Delphi中的TListView还是c#中的ListView,在开启其MultiSelect属性时,鼠标框选只是显示框张,如下图 ...
- 原生js实现在表格用鼠标框选并有反选功能
今天应同学要求,需要写一个像Excel那样框选高亮,并且实现框选区域实现反选功能.要我用原生js写,由于没什么经验翻阅了很多资料,第一次写文章希望各位指出不足!! 上来先建表 <div clas ...
- Cesium实现右键框选
思路 1.先取消地图的右键事件 2.右键框选事件,屏幕坐标转为经纬度坐标 取消地图的右键事件 //此处容易犯一个错误:以为右键事件绑定了缩放功能,伪代码即 Cesium.MouseEvent.右键事件 ...
随机推荐
- FreeRTOS 查询任务 剩余的栈空间的 方法
FreeRTOS 源码下载地址 1.官方文档提供了 函数 用来查询 任务 剩余 栈 空间,首先是看官方的文档解释(某位大神 翻译 的 官方文档.) 参数解释: xTask:被查询任 ...
- idea操作 clone项目、 import项目所有注解全部报错
操作:从现有的git上边clone项目,前提是开发工具,开发环境都一样错误类型:所有的注解全部报错 原因: 是选择了Create from existing source 一路Next下去,Maven ...
- HP-UNIX平台修改Oracle processes参数报错:ORA-27154、ORA-27300、ORA-27301、ORA-27302
OS 版本 :HP-UX B.11.31Oracle版本:11.2.0.4 (RAC) (一)问题描述 最近发现无法连接上数据库,报错信息为“ORA-00020:maximum number ...
- Struts2知识点小结汇总
Struts2部分 1. JavaEE软件三层结构和MVC的区别? JavaEE软件三层机构是由sun公司提供JavaEE开发规范的:Web层(表现层).业务逻辑层.数据持久层.[其中WEB层会使用前 ...
- #leetcode刷题之路37-解数独
编写一个程序,通过已填充的空格来解决数独问题.一个数独的解法需遵循如下规则:数字 1-9 在每一行只能出现一次.数字 1-9 在每一列只能出现一次.数字 1-9 在每一个以粗实线分隔的 3x3 宫内只 ...
- Zabbix——创建网络配置模板
前提条件: Zabbix版本为4.0 创建网络配置模板: Template Net Network Generic Device SNMPv2 h3c Template Module EtherLik ...
- HTML中汉字空格占位符
== 普通的英文半角空格 == == == no-break space (普通的英文半角空格但不换行) == 中文全角空格 (一个中文宽度) == == en空格 (半个中文 ...
- Flask第三方组件之flask_session
flask默认提供了session, 但是存在以下问题: ① session数据存在客户端, 不安全 ② 大小有限制 ③ 增加了客户端的压力 所以才产生了很多第三方的session机制, 我使用的是f ...
- 微信小程序 唯一标识 加减
var nums = 'goods_list[' + e.currentTarget.dataset.indexs+'].goods_num' //console.log(nuns) var num ...
- 微信小程序快速转成百度小程序的方法
1.安装Node.js(>8.5.0)https://nodejs.org/ npm升级到最新版本的方法:npm install -g npm自动更新到最新版本 2.配置cnpm:在命令行中输入 ...