포탈 모작 스크립트 수정
: 기존 URP 사용 -> URP 사용 X
: 하나의 카메라가 아닌 각 포탈에 카메라를 위치시켜 총 2개의 카메라를 사용
PortalCamera.cs
using System.Collections; using System.Collections.Generic; using UnityEngine; public class PortalCamera : MonoBehaviour { [SerializeField] private Portal[] portals = new Portal[2]; [SerializeField] private Camera portalCameraA; // 포탈 A 전용 카메라 [SerializeField] private Camera portalCameraB; // 포탈 B 전용 카메라 [SerializeField] private int iterations = 7; private RenderTexture renderTextureA; private RenderTexture renderTextureB; private void Awake() { // 화면 해상도에 맞게 RenderTexture를 생성 renderTextureA = new RenderTexture(Screen.width, Screen.height, 24, RenderTextureFormat.ARGB32); renderTextureB = new RenderTexture(Screen.width, Screen.height, 24, RenderTextureFormat.ARGB32); } void Start() { // 각 포탈의 Material에 상대 포탈의 RenderTexture를 설정 portals[0].Renderer.material.mainTexture = renderTextureB; // 포탈 A에 포탈 B의 텍스처를 설정 portals[1].Renderer.material.mainTexture = renderTextureA; // 포탈 B에 포탈 A의 텍스처를 설정 // 각 포탈 카메라의 RenderTexture를 설정 portalCameraA.targetTexture = renderTextureA; portalCameraB.targetTexture = renderTextureB; } void Update() { // RenderTexture의 해상도가 화면 크기에 맞지 않으면 재설정 UpdateRenderTextures(); // 두 포탈이 배치되어 있지 않으면 렌더링을 건너뜀 if (!portals[0].IsPlaced || !portals[1].IsPlaced) { return; } // 포탈 A에서 포탈 B를 통한 뷰를 렌더링 if (portals[0].Renderer.isVisible) { RenderPortalView(portalCameraA, portals[0], portals[1]); } // 포탈 B에서 포탈 A를 통한 뷰를 렌더링 if (portals[1].Renderer.isVisible) { RenderPortalView(portalCameraB, portals[1], portals[0]); } } private void UpdateRenderTextures() { // 화면 크기가 변경되었으면 RenderTexture를 새로 생성 if (renderTextureA.width != Screen.width || renderTextureA.height != Screen.height) { renderTextureA.Release(); renderTextureB.Release(); renderTextureA = new RenderTexture(Screen.width, Screen.height, 24, RenderTextureFormat.ARGB32); renderTextureB = new RenderTexture(Screen.width, Screen.height, 24, RenderTextureFormat.ARGB32); // 각 포탈의 Material에 새로운 RenderTexture를 다시 설정 portals[0].Renderer.material.mainTexture = renderTextureB; portals[1].Renderer.material.mainTexture = renderTextureA; // 각 포탈 카메라의 RenderTexture를 설정 portalCameraA.targetTexture = renderTextureA; portalCameraB.targetTexture = renderTextureB; } } private void RenderPortalView(Camera portalCamera, Portal inPortal, Portal outPortal) { portalCamera.clearFlags = CameraClearFlags.SolidColor; portalCamera.backgroundColor = Color.white; Transform inTransform = inPortal.transform; Transform outTransform = outPortal.transform; Transform cameraTransform = portalCamera.transform; cameraTransform.position = transform.position; cameraTransform.rotation = transform.rotation; // 카메라를 반복적으로 이동시켜 포탈 렌더링 효과 적용 for (int i = 0; i < iterations; i++) { Vector3 relativePos = inTransform.InverseTransformPoint(cameraTransform.position); relativePos = Quaternion.Euler(0.0f, 180.0f, 0.0f) * relativePos; cameraTransform.position = outTransform.TransformPoint(relativePos); Quaternion relativeRot = Quaternion.Inverse(inTransform.rotation) * cameraTransform.rotation; relativeRot = Quaternion.Euler(0.0f, 180.0f, 0.0f) * relativeRot; cameraTransform.rotation = outTransform.rotation * relativeRot; } // 카메라에 설정된 RenderTexture로 렌더링 portalCamera.Render(); } }