Last active
June 20, 2024 17:26
-
-
Save kurtdekker/2b4c2076b201abb8955f7423006ba8cc to your computer and use it in GitHub Desktop.
Low-resolution (LORES) rendering in Unity3D
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using UnityEngine; | |
// @kurtdekker - Cheesy quick way to do low-resolution in Unity3D: | |
// | |
// This script creates and controls the final Camera, not the Main Camera. | |
// | |
// Player Scene, when loaded, MUST have a Main Camera that we hijack. | |
// | |
// DO NOT DROP THIS ON A CAMERA! | |
// | |
// How to use: You have TWO choices. Do only ONE of the following: | |
// | |
// - from your own code call the static Create() method | |
// | |
// or... | |
// | |
// - drop this script on a blank GameObject (NOT the Camera!) | |
// | |
// You can even have your scene running already and add this in | |
// via either of the two above methods and it should Just Work(tm). | |
// | |
// In all cases it expects an Unlit/Texture Material asset to | |
// be located somewhere in Resources/LORES/Unlit.mat | |
// | |
public partial class LORES : MonoBehaviour | |
{ | |
//--------------------------- BEGIN SOURCE DATA | |
public const int DefaultScanlines = 200; | |
public const FilterMode DefaultFilterMode = FilterMode.Point; | |
// This is just "kinda far away." If you prefer, use Layers and selective | |
// rendering and you can have it all physically in the same location. | |
Vector3 farawayDistantPoint = new Vector3( 500, 0, 0); | |
Material UnlitMaterial { get { | |
// this allows things like FLIR materials to be injected | |
if (injectedMtl) | |
{ | |
return injectedMtl; | |
} | |
return Resources.Load<Material>( "LORES/Unlit"); | |
} | |
} | |
//--------------------------- END SOURCE DATA | |
Material injectedMtl; | |
// alternate way of injecting a material such as for my FLIR package | |
public void InjectMaterial( Material m) | |
{ | |
injectedMtl = m; | |
} | |
RenderTexture rt; | |
Camera mainCam; | |
Renderer rend; | |
Material mtl; | |
int scanLines = DefaultScanlines; | |
FilterMode filterMode = DefaultFilterMode; | |
public static LORES Create( int scanLines = DefaultScanlines, FilterMode filterMode = DefaultFilterMode) | |
{ | |
var LR = new GameObject( "LORES.Create(" + scanLines + ");").AddComponent<LORES>(); | |
LR.scanLines = scanLines; | |
LR.filterMode = filterMode; | |
LR.RemakeStage(); | |
return LR; | |
} | |
void Reset() | |
{ | |
name = GetType() + ".PlacedInScene"; | |
} | |
void Start() | |
{ | |
RemakeStage(); | |
OrientationChangeSensor.Create( transform, RemakeStage); | |
} | |
GameObject container; | |
void RemakeStage() | |
{ | |
mainCam = null; | |
if (container) | |
{ | |
Destroy( container); | |
rend = null; | |
} | |
container = new GameObject("StageContainer"); | |
container.transform.SetParent(transform); | |
container.transform.localPosition = Vector3.zero; | |
container.transform.localRotation = Quaternion.identity; | |
var stageCam = new GameObject(GetType() + ".Camera").AddComponent<Camera>(); | |
stageCam.transform.SetParent( container.transform); | |
stageCam.transform.localPosition = Vector3.back * 2.0f; | |
stageCam.orthographic = true; | |
stageCam.orthographicSize = 0.5f; | |
stageCam.nearClipPlane = 1.0f; | |
stageCam.farClipPlane = 3.0f; | |
var quad = GameObject.CreatePrimitive( PrimitiveType.Quad); | |
quad.transform.SetParent( container.transform); | |
quad.transform.localPosition = Vector3.zero; | |
quad.transform.localScale = new Vector3( (float)Screen.width / Screen.height, 1.0f, 1.0f); | |
mtl = UnlitMaterial; | |
rend = quad.GetComponent<Renderer>(); | |
rend.material = mtl; | |
// unhook | |
mtl.mainTexture = null; | |
stageCam.targetTexture = null; | |
container.transform.position = farawayDistantPoint; | |
} | |
void MakeRenderTexture() | |
{ | |
if (rt) | |
{ | |
Destroy(rt); | |
} | |
int height = scanLines; | |
int width = (height * Screen.width) / Screen.height; | |
rt = new RenderTexture( width, height, 32); | |
rt.filterMode = filterMode; | |
mainCam.targetTexture = rt; | |
mtl.mainTexture = rt; | |
rend.material = mtl; // JIC | |
} | |
void Update() | |
{ | |
if (!mainCam) | |
{ | |
mainCam = Camera.main; | |
if (mainCam) | |
{ | |
MakeRenderTexture(); | |
} | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment