using System.Collections; using System.Collections.Generic; using System.IO; using UnityEngine; #pragma warning disable IDE0090 // Use 'new(...)' public class Main : MonoBehaviour { #region Constants string capturedFramesPath; #endregion #region Camera GUI fields float m_FieldOfView = 60.0f; float m_camPosX = 0.0f; float m_camPosY = 0.0f; float m_camPosZ = 0.0f; float m_camLookAtX = 0.0f; float m_camLookAtY = 0.0f; float m_camLookAtZ = 0.0f; float newCameraPosX = 0.0f; float newCameraPosY = 0.0f; float newCameraPosZ = 0.0f; float camera_rotation = 1.1f; float m_CameraR = 20f; Vector3 lightDir = new Vector3(10.0f, 10.0f, 10.0f); #endregion #region Object fields GameObject mainCamera; GameObject directionalLight; GameObject ground; int numOfTrees; int numOfRows; #endregion #region Ground fields readonly float m_groundWidth = 200f; readonly float m_groundHeight = 200f; Shader m_groundShader; public Texture m_groundTexture; #endregion #region Tree fields public GameObject tree1; public GameObject tree2; public GameObject tree3; public System.Random random = new System.Random(); public List renderedTrees = new List(); float m_TreesZShift = 0.0f; float m_TreesXShift = 0.0f; #endregion #region Helper fields float m_LightIntensity = 1.0f; Vector2Int textureCameraSize = new Vector2Int(800, 600); GameObject textureCamera; readonly int ScreenshotsPerSecond = 1; int FrameCounter = 0; bool m_capturingFrames = false; #endregion #region Unity methods [System.Diagnostics.CodeAnalysis.SuppressMessage("CodeQuality", "IDE0051:Remove unused private members", Justification = "Unity method")] void Start() { //camera mainCamera = new GameObject(); mainCamera.AddComponent(); mainCamera.transform.position = new Vector3(m_camPosX, m_camPosY, m_camPosZ); mainCamera.transform.LookAt(new Vector3(m_camLookAtX, m_camLookAtY, m_camLookAtZ), new Vector3(0.0f, 1.0f, 0.0f)); mainCamera.name = "MainCamera"; textureCamera = new GameObject(); textureCamera.AddComponent(); textureCamera.transform.position = new Vector3(m_camPosX, m_camPosY, m_camPosZ); textureCamera.transform.LookAt(new Vector3(m_camLookAtX, m_camLookAtY, m_camLookAtZ), new Vector3(0.0f, 1.0f, 0.0f)); textureCamera.name = "TextureCamera"; RenderTexture renderTexture = new RenderTexture(textureCameraSize.x, textureCameraSize.y, 24); textureCamera.GetComponent().targetTexture = renderTexture; //-------------------------------------------------------------------------------------------------------------------- //directional light directionalLight = new GameObject(); directionalLight.AddComponent(); directionalLight.name = "Directional Light"; directionalLight.GetComponent().type = LightType.Directional; directionalLight.GetComponent().shadows = LightShadows.Soft; directionalLight.GetComponent().color = Color.white; directionalLight.GetComponent().useColorTemperature = true; directionalLight.GetComponent().colorTemperature = 5900; directionalLight.transform.position = new Vector3(10, 10.0f, 10.0f); directionalLight.transform.Rotate(lightDir.x, lightDir.y, lightDir.z, Space.Self); //--------------------------------------------------------------------------------------------------------------------- // create prefabs int positionShift_x = 500; int positionShift_z = 500; int treesNumber = 20; int rowsNumber = 15; int gridShiftX = 5; int gridShiftZ = 10; int randomShiftX; int randomShiftZ; numOfTrees = treesNumber; numOfRows = rowsNumber; int maxShiftValue = 5; for (int i = 0; i < treesNumber * gridShiftX; i += gridShiftX) { for (int k = 0; k < rowsNumber * gridShiftZ; k += gridShiftZ) { Vector3 rotationVector = new Vector3(0, Random.Range(0.0f, 360.0f), 0); randomShiftX = random.Next(0, maxShiftValue); randomShiftZ = random.Next(0, maxShiftValue); GameObject tree = SelectRandomTree(); renderedTrees.Add(Instantiate(tree, new Vector3(i + positionShift_x + randomShiftX, 0, k + positionShift_z + randomShiftZ), Quaternion.Euler(rotationVector))); } } capturedFramesPath = Path.Combine(Application.dataPath, "..", "..", "Trees", tree1.name); if (!Directory.Exists(capturedFramesPath)) { Directory.CreateDirectory(capturedFramesPath); } //--------------------------------------------------------------------------------------------------------------------- //ground m_groundShader = Shader.Find("Standard"); m_groundTexture.wrapMode = TextureWrapMode.Mirror; ground = new GameObject("Ground"); MeshRenderer groundMeshRenderer = ground.AddComponent(); groundMeshRenderer.material = new Material(m_groundShader) { mainTexture = m_groundTexture }; groundMeshRenderer.material.SetTextureScale("_MainTex", new Vector2(m_groundWidth, m_groundHeight)); MeshFilter groundMeshFilter = ground.AddComponent(); Mesh groundMesh = new Mesh(); Vector3[] vertices = new Vector3[4] { new Vector3(m_groundWidth/20, 0.0f,m_groundHeight/20), new Vector3(m_groundWidth/20+1500, 0.0f, m_groundHeight/20), new Vector3(m_groundWidth/20+1500, .0f, m_groundHeight/20+1500), new Vector3(m_groundWidth/20, 0.0f, m_groundHeight/20+1500), }; groundMesh.vertices = vertices; int[] indices = new int[6] { 0, 3, 2, 0, 2, 1 }; groundMesh.triangles = indices; Vector3[] normals = new Vector3[4] { new Vector3(0,1,0), new Vector3(0,1,0), new Vector3(0,1,0), new Vector3(0,1,0), }; groundMesh.normals = normals; Vector2[] uv = new Vector2[4] { new Vector2(0, 0), new Vector2(1, 0), new Vector2(0, 1), new Vector2(1, 1) }; groundMesh.uv = uv; groundMeshFilter.mesh = groundMesh; } [System.Diagnostics.CodeAnalysis.SuppressMessage("CodeQuality", "IDE0051:Remove unused private members", Justification = "Unity method")] void Update() { newCameraPosX = m_CameraR * Mathf.Cos(camera_rotation) + 500f + m_camPosX; newCameraPosY = 10f + m_camPosY; newCameraPosZ = m_CameraR * Mathf.Sin(camera_rotation) + 500f + m_camPosZ; Vector3 pos = new Vector3(newCameraPosX, newCameraPosY, newCameraPosZ); Vector3 lookAt = new Vector3(500f + m_camLookAtX, 1f + m_camLookAtY, 500f + m_camLookAtZ); mainCamera.GetComponent().fieldOfView = m_FieldOfView; mainCamera.GetComponent().transform.position = pos; mainCamera.GetComponent().transform.LookAt(lookAt); camera_rotation += 0.001f; if (m_TreesXShift != 0.0f || m_TreesZShift != 0.0f) { for (int i = 0; i < renderedTrees.Count; i++) { Vector3 currentPosition = renderedTrees[i].transform.position; float shiftValueZ = m_TreesZShift * ((i % numOfRows) - numOfRows / 2); float shiftValueX = m_TreesXShift * (i / numOfRows - numOfTrees / 2); renderedTrees[i].transform.position = new Vector3(currentPosition.x + shiftValueX, currentPosition.y, currentPosition.z + shiftValueZ); } m_TreesXShift = 0.0f; m_TreesZShift = 0.0f; } directionalLight.GetComponent().intensity = m_LightIntensity; textureCamera.GetComponent().fieldOfView = m_FieldOfView; textureCamera.GetComponent().transform.position = pos; textureCamera.GetComponent().transform.LookAt(lookAt); //textureCamera.transform.RotateAround(new Vector3(0.0f, 0.0f, 0.0f), new Vector3(0.0f, 1.0f, 0.0f), 1); } [System.Diagnostics.CodeAnalysis.SuppressMessage("CodeQuality", "IDE0051:Remove unused private members", Justification = "Unity method")] void OnGUI() { int buttonHeight = 30; int labelHeight = 20; int spacing = 10; int y = 20; GUIStyle labelStyle = new GUIStyle() { normal = new GUIStyleState() { textColor = Color.red, background = Texture2D.blackTexture }, }; GUI.Label(new Rect(10, y, 100, labelHeight), "Field of View", labelStyle); m_FieldOfView = GUI.HorizontalSlider(new Rect(120, y, 150, labelHeight), m_FieldOfView, 20.0f, 150.0f); y += labelHeight + spacing; GUI.Label(new Rect(10, y, 100, labelHeight), "Camera position X", labelStyle); m_camPosX = GUI.HorizontalSlider(new Rect(120, y, 150, labelHeight), m_camPosX, -300.0f, 300.0f); y += labelHeight + spacing; GUI.Label(new Rect(10, y, 100, labelHeight), "Camera position Y", labelStyle); m_camPosY = GUI.HorizontalSlider(new Rect(120, y, 150, labelHeight), m_camPosY, -30.0f, 100.0f); y += labelHeight + spacing; GUI.Label(new Rect(10, y, 100, labelHeight), "Camera position Z", labelStyle); m_camPosZ = GUI.HorizontalSlider(new Rect(120, y, 150, labelHeight), m_camPosZ, -300.0f, 300.0f); y += labelHeight + spacing; GUI.Label(new Rect(10, y, 100, labelHeight), "Look At X", labelStyle); m_camLookAtX = GUI.HorizontalSlider(new Rect(120, y, 150, labelHeight), m_camLookAtX, -300.0f, 300.0f); y += labelHeight + spacing; GUI.Label(new Rect(10, y, 100, labelHeight), "Look At Y", labelStyle); m_camLookAtY = GUI.HorizontalSlider(new Rect(120, y, 150, labelHeight), m_camLookAtY, -300.0f, 300.0f); y += labelHeight + spacing; GUI.Label(new Rect(10, y, 100, labelHeight), "Look At Z", labelStyle); m_camLookAtZ = GUI.HorizontalSlider(new Rect(120, y, 150, labelHeight), m_camLookAtZ, -300.0f, 300.0f); y += labelHeight + spacing; GUI.Label(new Rect(10, y, 100, labelHeight), "Camera rotation", labelStyle); m_CameraR = GUI.HorizontalSlider(new Rect(120, y, 150, labelHeight), m_CameraR, -150.0f, 150.0f); y += labelHeight + spacing; GUI.Label(new Rect(10, y, 100, labelHeight), "Light intensity", labelStyle); m_LightIntensity = GUI.HorizontalSlider(new Rect(120, y, 150, labelHeight), m_LightIntensity, 0.0f, 5.0f); y += labelHeight + spacing; GUI.Label(new Rect(10, y, 100, labelHeight), "Trees spacing X", labelStyle); y += labelHeight + spacing; if (GUI.Button(new Rect(10, y, 95, buttonHeight), "+")) { m_TreesXShift = 1.0f; } if (GUI.Button(new Rect(115, y, 95, buttonHeight), "-")) { m_TreesXShift = -1.0f; } y += buttonHeight + spacing; GUI.Label(new Rect(10, y, 100, labelHeight), "Trees spacing Z", labelStyle); y += labelHeight + spacing; if (GUI.Button(new Rect(10, y, 95, buttonHeight), "+")) { m_TreesZShift = 1.0f; } if (GUI.Button(new Rect(115, y, 95, buttonHeight), "-")) { m_TreesZShift = -1.0f; } y += buttonHeight + spacing; if (GUI.Button(new Rect(10, y, 200, buttonHeight), m_capturingFrames ? "Stop capturing frames" : "Start capturing frames")) { m_capturingFrames = !m_capturingFrames; if (m_capturingFrames) { StartCoroutine("CaptureAndSaveFrames"); } else { StopCoroutine("CaptureAndSaveFrames"); } } } #endregion #region On click behaviours [System.Diagnostics.CodeAnalysis.SuppressMessage("CodeQuality", "IDE0051:Remove unused private members", Justification = "Method accessed by name")] IEnumerator CaptureAndSaveFrames() { while (true) { yield return new WaitForEndOfFrame(); RenderTexture currentRT = RenderTexture.active; RenderTexture.active = textureCamera.GetComponent().targetTexture; textureCamera.GetComponent().Render(); Texture2D offscreenTexture = new Texture2D(textureCamera.GetComponent().targetTexture.width, textureCamera.GetComponent().targetTexture.height, TextureFormat.RGB24, false); offscreenTexture.ReadPixels(new Rect(0, 0, textureCamera.GetComponent().targetTexture.width, textureCamera.GetComponent().targetTexture.height), 0, 0, false); offscreenTexture.Apply(); RenderTexture.active = currentRT; ++FrameCounter; string path = Path.Combine(capturedFramesPath, FrameCounter.ToString() + ".png"); byte[] bytes = offscreenTexture.EncodeToPNG(); File.WriteAllBytes(path, bytes); Debug.Log(path); UnityEngine.Object.Destroy(offscreenTexture); yield return new WaitForSeconds(1.0f / ScreenshotsPerSecond); } } #endregion #region Helpers GameObject SelectRandomTree() { List list = new List { tree1, tree2, tree3 }; // parszywy kod ale nie mam teraz weny int rnd = UnityEngine.Random.Range(0, 11); if (rnd == 10) { return list[2]; } if (rnd == 9) { return list[1]; } else { return list[0]; } } #endregion } #pragma warning restore IDE0090 // Use 'new(...)'