123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388 |
- using System.Collections;
- using System.Collections.Generic;
- using UnityEngine;
- using UnityEditor;
- namespace RenderHeads.Media.AVProVideo.Editor
- {
- [CanEditMultipleObjects()]
- [CustomEditor(typeof(MediaReference))]
- public class MediaReferenceEditor : UnityEditor.Editor
- {
- internal const string SettingsPrefix = "AVProVideo-MediaReferenceEditor-";
- private SerializedProperty _propMediaPath;
- private SerializedProperty _propHints;
- private SerializedProperty _propPlatformMacOS;
- private SerializedProperty _propPlatformWindows;
- private SerializedProperty _propPlatformAndroid;
- private SerializedProperty _propPlatformIOS;
- private SerializedProperty _propPlatformTvOS;
- private SerializedProperty _propPlatformWindowsUWP;
- private SerializedProperty _propPlatformWebGL;
- //private SerializedProperty _propAlias;
- void OnEnable()
- {
- _propMediaPath = this.CheckFindProperty("_mediaPath");
- _propHints = this.CheckFindProperty("_hints");
- _propPlatformMacOS = this.CheckFindProperty("_macOS");
- _propPlatformWindows = this.CheckFindProperty("_windows");
- _propPlatformAndroid = this.CheckFindProperty("_android");
- _propPlatformIOS = this.CheckFindProperty("_iOS");
- _propPlatformTvOS = this.CheckFindProperty("_tvOS");
- _propPlatformWindowsUWP = this.CheckFindProperty("_windowsUWP");
- _propPlatformWebGL = this.CheckFindProperty("_webGL");
- //_propAlias = CheckFindProperty("_alias");
- _zoomToFill = EditorPrefs.GetBool(SettingsPrefix + "ZoomToFill", _zoomToFill);
- _thumbnailTime = EditorPrefs.GetFloat(SettingsPrefix + "ThumbnailTime", _thumbnailTime);
- }
- void OnDisable()
- {
- EndGenerateThumbnails(false);
- RemoveProgress();
- EditorPrefs.SetBool(SettingsPrefix + "ZoomToFill", _zoomToFill);
- EditorPrefs.SetFloat(SettingsPrefix + "ThumbnailTime", _thumbnailTime);
- }
- public override void OnInspectorGUI()
- {
- //MediaPlayer media = (this.target) as MediaPlayer;
- //this.DrawDefaultInspector();
- serializedObject.Update();
- GUILayout.Label("Media Reference");
- EditorGUILayout.Space();
- //EditorGUILayout.PropertyField(_propAlias);
- //EditorGUILayout.Space();
- {
- string mediaName = _propMediaPath.FindPropertyRelative("_path").stringValue;
- GUILayout.BeginVertical(GUI.skin.box);
- MediaPlayerEditor.OnInspectorGUI_CopyableFilename(mediaName);
- GUILayout.EndVertical();
- }
- EditorGUILayout.PropertyField(_propMediaPath);
- MediaPathDrawer.ShowBrowseButton(_propMediaPath);
- EditorGUILayout.Space();
- //GUILayout.Label("Media Hints", EditorStyles.boldLabel);
- EditorGUILayout.PropertyField(_propHints);
- EditorGUILayout.PropertyField(_propPlatformMacOS, new GUIContent("macOS"));
- EditorGUILayout.PropertyField(_propPlatformWindows, new GUIContent("Windows"));
- EditorGUILayout.PropertyField(_propPlatformAndroid, new GUIContent("Android"));
- EditorGUILayout.PropertyField(_propPlatformIOS, new GUIContent("iOS"));
- EditorGUILayout.PropertyField(_propPlatformTvOS, new GUIContent("tvOS"));
- EditorGUILayout.PropertyField(_propPlatformWindowsUWP, new GUIContent("UWP"));
- EditorGUILayout.PropertyField(_propPlatformWebGL, new GUIContent("WebGL"));
- EditorGUILayout.Space();
- EditorGUILayout.Space();
-
- serializedObject.ApplyModifiedProperties();
- bool beginGenerateThumbnails = false;
-
- GUILayout.FlexibleSpace();
- EditorGUI.BeginDisabledGroup(IsGeneratingThumbnails());
- GUILayout.BeginHorizontal();
- _thumbnailTime = GUILayout.HorizontalSlider(_thumbnailTime, 0f, 1f, GUILayout.ExpandWidth(true));
- _zoomToFill = GUILayout.Toggle(_zoomToFill, "Zoom And Crop", GUI.skin.button, GUILayout.ExpandWidth(false));
- GUILayout.EndHorizontal();
- if (GUILayout.Button("Generate Thumbnail"))
- {
- beginGenerateThumbnails = true;
- }
- EditorGUI.EndDisabledGroup();
- if (beginGenerateThumbnails)
- {
- BeginGenerateThumbnails();
- }
- if (IsGeneratingThumbnails())
- {
- ShowProgress();
- }
- if (!IsGeneratingThumbnails())
- {
- RemoveProgress();
- }
- }
- private void ShowProgress()
- {
- // Show cancellable progress
- float t = (float)_targetIndex / (float)this.targets.Length;
- t = 0.25f + t * 0.75f;
- MediaReference media = (this.targets[_targetIndex]) as MediaReference;
-
- #if UNITY_2020_1_OR_NEWER
- if (_progressId < 0)
- {
- //Progress.RegisterCancelCallback(_progressId...)
- _progressId = Progress.Start("[AVProVideo] Generating Thumbnails...", null, Progress.Options.Managed);
- }
- Progress.Report(_progressId, t, media.MediaPath.Path);
- #else
- if (EditorUtility.DisplayCancelableProgressBar("[AVProVideo] Generating Thumbnails...", media.MediaPath.Path, t))
- {
- EndGenerateThumbnails(false);
- }
- #endif
- }
- private void RemoveProgress()
- {
- #if UNITY_2020_1_OR_NEWER
- if (_progressId >= 0)
- {
- Progress.Remove(_progressId);
- _progressId = -1;
- }
- #else
- EditorUtility.ClearProgressBar();
- #endif
- }
- #if UNITY_2020_1_OR_NEWER
- private int _progressId = -1;
- #endif
- private float _thumbnailTime;
- private bool _zoomToFill = false;
- private int _lastFrame;
- private BaseMediaPlayer _thumbnailPlayer;
- private int _mediaFrame = -1;
- private int _targetIndex = 0;
- private float _timeoutTimer = 0f;
- private bool IsGeneratingThumbnails()
- {
- return (_thumbnailPlayer != null);
- }
- private void BeginGenerateThumbnails()
- {
- EditorApplication.update -= UpdateGenerateThumbnail;
- Debug.Assert(_thumbnailPlayer == null);
- #if UNITY_EDITOR_WIN
- if (WindowsMediaPlayer.InitialisePlatform())
- {
- MediaPlayer.OptionsWindows options = new MediaPlayer.OptionsWindows();
- _thumbnailPlayer = new WindowsMediaPlayer(options);
- }
- #elif UNITY_EDITOR_OSX
- {
- MediaPlayer.OptionsApple options = new MediaPlayer.OptionsApple(MediaPlayer.OptionsApple.TextureFormat.BGRA, MediaPlayer.OptionsApple.Flags.None);
- _thumbnailPlayer = new AppleMediaPlayer(options);
- }
- #endif
- if (_thumbnailPlayer != null)
- {
- _targetIndex = 0;
- BeginNextThumbnail(0);
- }
- else
- {
- EndGenerateThumbnails(false);
- }
- }
- private void BeginNextThumbnail(int index)
- {
- EditorApplication.update -= UpdateGenerateThumbnail;
- _mediaFrame = -1;
- _timeoutTimer = 0f;
- if (_thumbnailPlayer != null)
- {
- if (index < this.targets.Length)
- {
- _targetIndex = index;
- MediaReference media = (this.targets[_targetIndex]) as MediaReference;
- string path = media.MediaPath.GetResolvedFullPath();
- bool openedMedia = false;
- if (!string.IsNullOrEmpty(path))
- {
- if (_thumbnailPlayer.OpenMedia(path, 0, string.Empty, media.Hints, 0, false))
- {
- openedMedia = true;
- EditorApplication.update += UpdateGenerateThumbnail;
- }
- }
- if (!openedMedia)
- {
- // If the media failed to open, continue to the next one
- BeginNextThumbnail(_targetIndex + 1);
- }
- }
- else
- {
- EndGenerateThumbnails(true);
- }
- }
- }
- private void EndGenerateThumbnails(bool updateAssets)
- {
- EditorApplication.update -= UpdateGenerateThumbnail;
- if (_thumbnailPlayer != null)
- {
- _thumbnailPlayer.CloseMedia();
- _thumbnailPlayer.Dispose();
- _thumbnailPlayer = null;
- }
- _mediaFrame = -1;
- if (updateAssets)
- {
- // This forces the static preview to refresh
- foreach (Object o in this.targets)
- {
- EditorUtility.SetDirty(o);
- AssetPreview.GetAssetPreview(o);
- }
- AssetDatabase.SaveAssets();
- }
- }
- private void UpdateGenerateThumbnail()
- {
- if (Time.renderedFrameCount == _lastFrame)
- {
- // In at least Unity 5.6 we have to force refresh of the UI otherwise the render thread doesn't run to update the textures
- this.Repaint();
- UnityEditorInternal.InternalEditorUtility.RepaintAllViews();
- return;
- }
- // Wait for a frame to be rendered
- Debug.Assert(_thumbnailPlayer != null);
- if (_thumbnailPlayer != null)
- {
- _timeoutTimer += Time.unscaledDeltaTime;
- bool nextVideo = false;
- _thumbnailPlayer.Update();
- _thumbnailPlayer.Render();
- if (_mediaFrame < 0 && _thumbnailPlayer.CanPlay())
- {
- _thumbnailPlayer.MuteAudio(true);
- _thumbnailPlayer.Play();
- _thumbnailPlayer.Seek(_thumbnailPlayer.GetDuration() * _thumbnailTime);
- _mediaFrame = _thumbnailPlayer.GetTextureFrameCount();
- }
- if (_thumbnailPlayer.GetTexture() != null)
- {
- if (_mediaFrame != _thumbnailPlayer.GetTextureFrameCount() && _thumbnailPlayer.GetTextureFrameCount() > 3)
- {
- bool prevSRGB = GL.sRGBWrite;
- GL.sRGBWrite = false;
- RenderTexture rt2 = null;
- // TODO: move this all into VideoRender as a resolve method
- {
- Material materialResolve = new Material(Shader.Find(VideoRender.Shader_Resolve));
- VideoRender.SetupVerticalFlipMaterial(materialResolve, _thumbnailPlayer.RequiresVerticalFlip());
- VideoRender.SetupAlphaPackedMaterial(materialResolve, _thumbnailPlayer.GetTextureAlphaPacking());
- VideoRender.SetupGammaMaterial(materialResolve, !_thumbnailPlayer.PlayerSupportsLinearColorSpace());
- RenderTexture prev = RenderTexture.active;
- // Scale to fit and downsample
- rt2 = RenderTexture.GetTemporary(128, 128, 0, RenderTextureFormat.ARGB32, RenderTextureReadWrite.sRGB);
- RenderTexture.active = rt2;
- GL.Clear(false, true, new Color(0f, 0f, 0f, 0f));
- ScaleMode scaleMode = ScaleMode.ScaleToFit;
- if (_zoomToFill)
- {
- scaleMode = ScaleMode.ScaleAndCrop;
- }
- VideoRender.DrawTexture(new Rect(0f, 0f, 128f, 128f), _thumbnailPlayer.GetTexture(), scaleMode, _thumbnailPlayer.GetTextureAlphaPacking(), _thumbnailPlayer.GetTexturePixelAspectRatio(), materialResolve);
- RenderTexture.active = prev;
- Material.DestroyImmediate(materialResolve); materialResolve = null;
- }
-
- Texture2D readTexture = new Texture2D(128, 128, TextureFormat.RGBA32, true, false);
- Helper.GetReadableTexture(rt2, readTexture);
- MediaReference mediaRef = (this.targets[_targetIndex]) as MediaReference;
- mediaRef.GeneratePreview(readTexture);
- DestroyImmediate(readTexture); readTexture = null;
- RenderTexture.ReleaseTemporary(rt2);
- GL.sRGBWrite = prevSRGB;
- nextVideo = true;
- Debug.Log("Thumbnail Written");
- }
- }
- if (!nextVideo)
- {
- // If there is an error or it times out, then skip this media
- if (_timeoutTimer > 10f || _thumbnailPlayer.GetLastError() != ErrorCode.None)
- {
- MediaReference mediaRef = (this.targets[_targetIndex]) as MediaReference;
- mediaRef.GeneratePreview(null);
- nextVideo = true;
- }
- }
- if (nextVideo)
- {
- BeginNextThumbnail(_targetIndex + 1);
- }
- }
- _lastFrame = Time.renderedFrameCount;
- }
- public override bool HasPreviewGUI()
- {
- return true;
- }
- public override void OnPreviewGUI(Rect r, GUIStyle background)
- {
- Texture texture = RenderStaticPreview(string.Empty, null, 128, 128);
- if (texture)
- {
- GUI.DrawTexture(r, texture, ScaleMode.ScaleToFit, true);
- }
- }
- public override Texture2D RenderStaticPreview(string assetPath, Object[] subAssets, int width, int height)
- {
- MediaReference media = this.target as MediaReference;
- if (media)
- {
- bool isLinear = false;
- #if !UNITY_2018_1_OR_NEWER
- // NOTE: These older versions of Unity don't handle sRGB in the editor correctly so a workaround is to create texture as linear
- isLinear = true;
- #endif
- Texture2D result = new Texture2D(width, height, TextureFormat.RGBA32, true, isLinear);
- if (!media.GetPreview(result))
- {
- DestroyImmediate(result); result = null;
- }
- return result;
- }
- return null;
- }
- }
- }
|