스크린샷 기능 구현
초기에 게임 컨셉이 힐링이었을 때
게임내에 스크린샷 찍는 기능을 넣기로 했었는데
컨셉이 바뀌면서 굳이 스크린샷 기능을 구현할 필요를 못느껴서 빼게 되었다.
근데이미 만들어 둔 것을 그냥 지워버리긴 아까워서 포스팅 해본다.
스크린샷 기능 구현
먼저 스크립트는 아래의 두가지를 작성해준다.
using UnityEngine;
using UnityEngine.UI;
public class UIGameDirector : MonoBehaviour
{
public Button btnScreenshot;
public Screenshot screenshot;
private void Start()
{
Debug.Log("GameDirector Init");
this.btnScreenshot.onClick.AddListener(() =>
{
this.screenshot.StartCoroutine(this.screenshot.CorScreenshot());
this.screenshot.StopCoroutine(this.screenshot.CorScreenshot());
});
}
}
using System.Collections;
using UnityEngine;
public class Screenshot : MonoBehaviour
{
public IEnumerator CorScreenshot()
{
//WaitForEndOfFrame() 현재 프레임이 완료될 때까지 대기
yield return new WaitForEndOfFrame();
//imgBytes 변수를 byte 배열로 초기화
byte[] imgBytes;
//path 변수를 문자열로 초기화,
//스크린샷이 저장될 경로와 파일 이름을 지정
string path = @"C:\screenshot\test.png";
//스크린샷 이미지 저장할 Texture2D 타입 객체 변수 초기화
//생성자의 인수로 스크린의 크기, TextureFormat 지정
Texture2D texture = new Texture2D(Screen.width, Screen.height, TextureFormat.RGB24, false);
//스크린의 모든 픽셀 값을 texture에 저장
texture.ReadPixels(new Rect(0, 0, Screen.width, Screen.height), 0, 0, false);
//texture 변경 사항 적용
texture.Apply();
//texture 이미지를 PNG 형식으로 인코딩하고 결과를 imgBytes에 저장
imgBytes = texture.EncodeToPNG();
//imgBytes 배열에 저장된 값을 파일로 만든다.
//이 때 파일 경로는 path에 저장된 값
System.IO.File.WriteAllBytes(path, imgBytes);
}
}
그리고 필요한 오브젝트는
스크린샷 버튼,
디렉터(UIGameDirector),
스크린샷 기능(Screenshot) 오브젝트 세 가지이다.
각 오브젝트에 스크립트를 붙이고 필요한 것들을 어싸인 해준다.
실행 결과
새로 알게된 것
ReadPixels() 메소드는 현재 프레임 버퍼로부터 픽셀들을 읽어온다.
따라서 프레임 버퍼가 초기화된 이후에 호출해야 한다.
그래서 Screenshot() 코루틴 처음 부분에 WaitForEndOfFrame()을 호출해
현재 프레임이 완료되는 것을 기다리고 다음 과정을 진행하도록 했다.
참고
https://docs.unity3d.com/kr/530/ScriptReference/Texture2D.ReadPixels.html
Texture2D-ReadPixels - Unity 스크립팅 API
Read pixels from screen into the saved texture data.
docs.unity3d.com
https://docs.unity3d.com/kr/530/ScriptReference/WaitForEndOfFrame.html
UnityEngine.WaitForEndOfFrame - Unity 스크립팅 API
Waits until the end of the frame after all cameras and GUI is rendered, just before displaying the frame on screen.
docs.unity3d.com