227 lines
6.7 KiB
C#
227 lines
6.7 KiB
C#
using System;
|
|
using FairyGUI;
|
|
using FairyGUI.Utils;
|
|
using System.Collections;
|
|
using UnityEngine;
|
|
using UnityEngine.Rendering.Universal;
|
|
using Object = UnityEngine.Object;
|
|
|
|
namespace NBF
|
|
{
|
|
[Serializable]
|
|
public class ModelViewRenderImage
|
|
{
|
|
private ModelViewerSettings _viewerSettings;
|
|
public Transform modelRoot { get; private set; }
|
|
|
|
Camera _camera;
|
|
Image _image;
|
|
Transform _root;
|
|
Transform _background;
|
|
Transform _model;
|
|
RenderTexture _renderTexture;
|
|
int _width;
|
|
int _height;
|
|
bool _cacheTexture;
|
|
float _rotating;
|
|
|
|
const int RENDER_LAYER = 0;
|
|
const int HIDDEN_LAYER = 10;
|
|
|
|
public ModelViewRenderImage(GGraph holder)
|
|
{
|
|
_width = (int)holder.width;
|
|
_height = (int)holder.height;
|
|
_cacheTexture = true;
|
|
|
|
_image = new Image();
|
|
holder.SetNativeObject(_image);
|
|
|
|
|
|
_root = new GameObject("RenderImage").transform;
|
|
_root.transform.position = Vector3.zero;
|
|
// _root.SetParent(_camera.transform, false);
|
|
SetLayer(_root.gameObject, HIDDEN_LAYER);
|
|
Object.DontDestroyOnLoad(_root.gameObject);
|
|
|
|
Object prefab = Resources.Load("RenderTexture/RenderImageCamera");
|
|
GameObject go = (GameObject)Object.Instantiate(prefab, _root, false);
|
|
|
|
// ConfigurableJoint
|
|
|
|
_camera = go.GetComponent<Camera>();
|
|
_camera.transform.position = Vector3.zero;
|
|
_camera.cullingMask = 1 << RENDER_LAYER;
|
|
_camera.enabled = false;
|
|
Object.DontDestroyOnLoad(_camera.gameObject);
|
|
|
|
|
|
modelRoot = new GameObject("model_root").transform;
|
|
modelRoot.SetParent(_root, false);
|
|
|
|
_background = new GameObject("background").transform;
|
|
_background.SetParent(_root, false);
|
|
|
|
_image.onAddedToStage.Add(OnAddedToStage);
|
|
_image.onRemovedFromStage.Add(OnRemoveFromStage);
|
|
|
|
|
|
_viewerSettings = new ModelViewerSettings();
|
|
|
|
if (_image.stage != null)
|
|
OnAddedToStage();
|
|
else
|
|
_camera.gameObject.SetActive(false);
|
|
}
|
|
|
|
public void LoadModel(string model)
|
|
{
|
|
this.UnloadModel();
|
|
|
|
Object prefab = Resources.Load(model);
|
|
GameObject go = ((GameObject)Object.Instantiate(prefab));
|
|
var joint = go.GetComponent<Joint>();
|
|
if (joint != null)
|
|
{
|
|
Object.Destroy(joint);
|
|
}
|
|
|
|
_model = go.transform;
|
|
_model.SetParent(this.modelRoot, false);
|
|
_model.localPosition = Vector3.zero;
|
|
_model.localScale = Vector3.one;
|
|
_model.localEulerAngles = Vector3.zero;
|
|
ModelViewerUtils.InitSetting(go, _viewerSettings);
|
|
Review();
|
|
}
|
|
|
|
public void UnloadModel()
|
|
{
|
|
if (_model != null)
|
|
{
|
|
_model.gameObject.SetActive(false);
|
|
Object.Destroy(_model.gameObject);
|
|
_model = null;
|
|
}
|
|
|
|
_rotating = 0;
|
|
}
|
|
|
|
|
|
public void Review()
|
|
{
|
|
_model.position = _viewerSettings.objectPosition;
|
|
_model.localScale = _viewerSettings.objectScale;
|
|
_model.eulerAngles = _viewerSettings.objectRotation;
|
|
|
|
|
|
_camera.clearFlags = CameraClearFlags.Nothing;
|
|
_camera.transform.position = _viewerSettings.cameraPosition;
|
|
_camera.transform.LookAt(_viewerSettings.cameraTarget);
|
|
_camera.orthographic = _viewerSettings.cameraOrtho;
|
|
_camera.orthographicSize = _viewerSettings.cameraSize;
|
|
_camera.orthographicSize /= _viewerSettings.camerasScaleFactor;
|
|
|
|
_camera.fieldOfView = _viewerSettings.cameraFov;
|
|
float fov = 2 * Mathf.Rad2Deg * Mathf.Atan2(
|
|
Mathf.Tan(_camera.fieldOfView * Mathf.Deg2Rad / 2), _viewerSettings.camerasScaleFactor
|
|
);
|
|
if (fov < 0)
|
|
fov += 180;
|
|
_camera.fieldOfView = fov;
|
|
|
|
_camera.nearClipPlane = 0.001f;
|
|
_camera.farClipPlane = 10000;
|
|
_camera.depthTextureMode = DepthTextureMode.Depth;
|
|
_camera.clearFlags = CameraClearFlags.Color;
|
|
_camera.GetUniversalAdditionalCameraData().renderPostProcessing = false; //URP only
|
|
}
|
|
|
|
public void Dispose()
|
|
{
|
|
UnloadModel();
|
|
Object.Destroy(_camera.gameObject);
|
|
DestroyTexture();
|
|
|
|
_image.Dispose();
|
|
_image = null;
|
|
}
|
|
|
|
|
|
void CreateTexture()
|
|
{
|
|
if (_renderTexture != null)
|
|
return;
|
|
|
|
_renderTexture = new RenderTexture(1024, 1024, 24, RenderTextureFormat.ARGB32)
|
|
{
|
|
antiAliasing = 1,
|
|
filterMode = FilterMode.Bilinear,
|
|
anisoLevel = 0,
|
|
useMipMap = false
|
|
};
|
|
_image.texture = new NTexture(_renderTexture);
|
|
_image.blendMode = BlendMode.Off;
|
|
}
|
|
|
|
void DestroyTexture()
|
|
{
|
|
if (_renderTexture != null)
|
|
{
|
|
Object.Destroy(_renderTexture);
|
|
_renderTexture = null;
|
|
_image.texture = null;
|
|
}
|
|
}
|
|
|
|
void OnAddedToStage()
|
|
{
|
|
if (_renderTexture == null)
|
|
CreateTexture();
|
|
|
|
Timers.inst.AddUpdate(Render);
|
|
_camera.gameObject.SetActive(true);
|
|
|
|
Render();
|
|
}
|
|
|
|
void OnRemoveFromStage()
|
|
{
|
|
if (!_cacheTexture)
|
|
DestroyTexture();
|
|
|
|
Timers.inst.Remove(Render);
|
|
_camera.gameObject.SetActive(false);
|
|
}
|
|
|
|
void Render(object param = null)
|
|
{
|
|
if (_rotating != 0 && modelRoot != null)
|
|
{
|
|
Vector3 localRotation = modelRoot.localRotation.eulerAngles;
|
|
localRotation.y += _rotating;
|
|
modelRoot.localRotation = Quaternion.Euler(localRotation);
|
|
}
|
|
|
|
SetLayer(_root.gameObject, RENDER_LAYER);
|
|
|
|
_camera.targetTexture = _renderTexture;
|
|
RenderTexture old = RenderTexture.active;
|
|
RenderTexture.active = _renderTexture;
|
|
GL.Clear(true, true, Color.clear);
|
|
_camera.Render();
|
|
RenderTexture.active = old;
|
|
|
|
SetLayer(_root.gameObject, HIDDEN_LAYER);
|
|
}
|
|
|
|
void SetLayer(GameObject go, int layer)
|
|
{
|
|
Transform[] transforms = go.GetComponentsInChildren<Transform>(true);
|
|
foreach (Transform t in transforms)
|
|
{
|
|
t.gameObject.layer = layer;
|
|
}
|
|
}
|
|
}
|
|
} |