在Unity中实现《星际拓荒》的量子石头效应

在游戏星际拓荒(outer wilds)中有一个很有趣的设定,当玩家不观察到石头时石头会在不同的平台上随机移动,而当玩家观察时石头会静止不动。

判断物体是否被观察到

做出类似的效果并不难,关键在于怎么判断一个物体是否被玩家所观测到,我们可以采用:

 bool IsInView(Vector3 position)
 {
     Vector3 screenPoint = mainCamera.WorldToViewportPoint(position);
     return screenPoint.z > 0 && screenPoint.x > 0 && screenPoint.x < 1 && screenPoint.y > 0 && screenPoint.y < 1;
 }

 WorldToViewportPoint是Unity 中Camera类的一种方法,用于将世界坐标转换为视口坐标。视口坐标是一种标准化的坐标系,范围从 (0,0) 到 (1,1),表示相机视图中的位置。

具体来说,这个方法的作用是将一个世界坐标系中的点(通常是 3D 坐标)转换为基于屏幕视口的 2D 坐标。视口坐标系的 (0,0) 位置对应屏幕的左下角,(1,1) 位置对应屏幕的右上角。

当物体处于 (0,0) 到 (1,1)的范围即表示我们观察到物体

让物体在不同平台间移动

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class test : MonoBehaviour
{
 
    public Camera mainCamera;
    public Transform[] positions; // 三个位置
    public Transform objectToMove; // 要移动的物体
   
    // Start is called before the first frame update
    void Start()
    {
        
    }
    bool IsInView(Vector3 position)
    {
        Vector3 screenPoint = mainCamera.WorldToViewportPoint(position);
        return screenPoint.z > 0 && screenPoint.x > 0 && screenPoint.x < 1 && screenPoint.y > 0 && screenPoint.y < 1;
    }
    void MoveObjectToRandomPosition()
    {
        // 获取所有不在视线内的位置
        var outOfViewPositions = new List<Transform>();
        foreach (var pos in positions)
        {
            if (!IsInView(pos.position))
            {
                outOfViewPositions.Add(pos);
            }
        }

        // 如果有不在视线内的位置,则随机选择一个进行移动
        if (outOfViewPositions.Count > 0)
        {
            int randomIndex = Random.Range(0, outOfViewPositions.Count);
            objectToMove.position = outOfViewPositions[randomIndex].position;
        }
    }
    // Update is called once per frame
    void Update()
    {
        if (!IsInView(objectToMove.position))
        {
            MoveObjectToRandomPosition();
        }
    }
}

添加三个位置到transform的列表,并生成一个随机数来实现物体的移动就行。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值