如何仅响应UI图像中的触摸?

时间:2019-03-01 15:26:29

标签: ios unity3d

我一直在动脑筋,使用我能想到的每个Google搜索短语,但尚未找到解决方案。

我有一个带有3D场景和浮动在其上的UI元素的Unity应用。有一个UI元素是量角器的图像。该图像需要围绕场景进行旋转,缩放和缩放。所有这些都有效,唯一的收获是,无论用户触摸量角器或其他位置,量角器总是会做出反应,这无关紧要。

我从寻找类似Swift的someCGRect.contains(someCGPoint)的东西开始,这样我就可以忽略那些不在量角器范围之内的东西。图片似乎没有这种属性,所以我做了很多其他搜索。

我终于找到了这个视频; https://www.youtube.com/watch?v=sXc8baUK3iY基本上满足了我的需求……除了不起作用。

视频使用对撞机和刚体,然后在代码中检查对撞机是否与接触点重叠。看起来正是我所需要的。不幸的是,无论碰触到哪里,都不会与碰触器重叠。经过一些Debug.Log之后,我发现对撞机的范围报告为(0, 0, 0)。这就是为什么所有接触都没有重叠的明显原因,但是我不知道如何将范围设为除0以外的任何值。

以下是图像上附加的对撞机和刚体的信息:

  • Box Collider 2D:
    • 由Composite使用:true
    • 自动平铺:false
    • 偏移量:(0,0)
    • 大小:(1,1)
  • 2D刚体:
    • 身体类型:运动学
    • 材料:无(2D物理材料)
    • 模拟:是
    • 使用完整的运动学联系方式:false
    • 碰撞检测:离散
    • 睡眠模式:开始唤醒
    • 插值:无
    • 约束:无
  • 复合对撞机2D:
    • 材料:无(2D物理材料)
    • 是触发器:false
    • 效应器使用:false
    • 偏移量:(0,0)
    • 几何类型:多边形
    • 发电类型:同步
    • 顶点距离:0.0005

有一个按钮,可以使用以下代码打开和关闭量角器:

public void toggle() {
    this.enabled = !this.enabled;
    this.gameObject.SetActive(this.enabled);
}

量角器开始可见生命,但是Start()立即呼叫toggle(),因此用户将其视为生命的起点。

这是执行测试以查看是否应响应触摸的代码:

void checkTouches() {
    if (Input.touchCount <= 0) {
        return;
    }
    bool oneTouchIn = false;
    Collider2D collider = GetComponent<Collider2D>();
    Debug.Log(" The bounds of the collider are: " + collider.bounds); 
    // The above always logs the extents as (0,0,0).
    foreach (Touch touch in Input.touches) {
        Vector2 touchPos = Camera.main.ScreenToWorldPoint(touch.position);
        if(collider.OverlapPoint(touchPos)) {
            // Since the extents are all 0 we never find any overlaps
            oneTouchIn = true;
            break;
        }
    }
    if (!oneTouchIn) {
        return; // Always ends up here
    }
    // We must have at least one touch that is in our bounds.
    // Do stuff with the touch(es) here…
}

自从SDK发行以来,我就一直在用Objective-C进行iOS开发,而自Swift推出以来一直在用Swift进行开发,但是我对Unity还是很陌生。我确定问题是我缺少一些愚蠢的东西,但是我找不到它。

有人知道我要使当前版本正常工作所缺少的内容吗,或者仅响应有界触摸的另一种方法吗?

1 个答案:

答案 0 :(得分:2)

  

图片似乎没有这样的属性

没有Image组件本身不具备此功能...

但是每个UI RectTransform都具有GameObject组件的rect属性。

它称为Contains。所以你可以做

RectTransform imgRectTransform = imageObject.GetComponent<RectTransform>();
Vector2 localTouchPosition = imgRectTransform.InverseTransformPoint(Touch.position);
if (imgRectTransform.rect.Contains(localToichPosition)) { ... }

或者,您可以在目标图片上的组件中使用IPointerEnterHandlerIPointerExitHandler接口,例如

public class DragableHandler : MonkBehaviour, IPointerEnterHandler, IPointerExitHandler
{
    public bool IsHover {get; private set; }

    //Detect if the Cursor starts to pass over the GameObject
    public void OnPointerEnter(PointerEventData pointerEventData)
    {
        //Output to console the GameObject's name and the following message
        Debug.Log("Cursor Entering " + name + " GameObject");
        IsHover = true;
    }

    //Detect when Cursor leaves the GameObject
    public void OnPointerExit(PointerEventData pointerEventData)
    {
        //Output the following message with the GameObject's name
        Debug.Log("Cursor Exiting " + name + " GameObject");
        IsHover = false;
    }
}

然后在脚本中使用

进行检查
if(imageObject.GetComponent<DragableHandler>().IsHover) { ... }

还要确保我们EventSystem您还添加了Touch Input Module并检查了标记Force Module Active